Bei 8Bit Erkennung von 2Bit wechsel.

Gast #1608017
Hallo,

ich stehe vor folgendem Problem...

Ich habe 24Bit die ich ab intr X polle (4x 8Bit ATMEGA16 PORTA,B,C) und 
möchte bei jedem der 8Bit einen wechsel von 2Bit feststellen können.

Meine Kenntnisse in C reichen leider nicht sehr weit für eine "elegante" 
Lösung und würde es bisher wie folgt versuchen...

int ME_Alert (int leg1_sav, int leg2_sav, usw...)
{
int i;
i=0;
  while (PD2 == 0 & i<=2)
  {
  if (LEG1_STATUS = leg1_sav) {}
    else{i++}
  if (LEG2_STATUS = leg2_sav) {}
    else{i++}
  if (LEG3_STATUS = leg3_sav) {}
    else{i++}
  if (LEG4_STATUS = leg4_sav) {}
    else{i++}
  }
return i;
}

wobei
#define LEG1_STATUS  (PINA & 0xFC)
#define LEG2_STATUS  ((PINA & 0x03) | (PINB & 0x0F))
#define LEG3_STATUS  ((PINB & 0xF0) | (PINC & 0xC0))
#define LEG4_STATUS  (PINC & 0x3F)

Danke vorab für Eure hilfe!!!

Gruß Nacho
Gast
1) Code Tags benutzen!
2) if(a = b) ist an dieser Stelle falsch, da es eine Zuweisung ist. (a 
== b) ist hier richtig.
3)
1
 if (LEG1_STATUS = leg1_sav) {}
2
    else{i++}
3

4
// besser, schneller, übersichtlicher ist
5
if(LEG1_STATUS != leg1_sav) 
6
{
7
    i++;
8
}

4) So richtig verstehe ich nicht, was du erreichen willst. Willst du 
LEG1_STATUS mit einem anderen Bitmuster prüfen?
Gast
Hab ich eben noch übersehen:
1
while ((PD2 == 0) && (i<=2))

Ein &-Zeichen ist eine binäre Verknüfpung. Zwei &-Zeichen ist eine 
logische Verknüpfung.
Gast
> Hab ich eben noch übersehen:
> while ((PD2 == 0) && (i<=2))
>
>
> Ein &-Zeichen ist eine binäre Verknüfpung. Zwei &-Zeichen ist eine
> logische Verknüpfung.

Außerdem ist PD2 eine Konstante, die den Wert 2 hat, wird also sowieso 
niemals gleich 0 sein.
Gast
Zunächst mal danke für die Hinweise Lordziu...

Zu deiner Frage wo ich hin möchte...

Ich frage vor dem pollen einmalig den Status meiner DIs ab. Der Wert 
wird in legx_sav abgelegt. jedes "leg" soll nun nachher mit seiner 
legx_sav verglichen werden.
Beim pollen möchte ich feststellen, ob bei legx_status gegnüber legx_sav 
kein, ein, zwei oder mehrere Bits geflippt sind...

Wenn zwei oder mehr Bits pro legx ihren wert geändert haben soll wird 
Funktion Y ausgeführt werden...

Mein Hauptproblem ist wie gesagt das feststellen wieviele bits gegenüber 
dem abgesicherten wert geflippt sind...

Als Bsp.:
angenommen logx_sav = 0b00010100

1. Abfrage ergibt:
logx_status = 0b01010100    //1Bit... Ohne Auswirkungen

2. Abfrage ergibt:
logx_status = 0b01010101    //2Bit... Funktion Y ausführen

Verständlicher? :)

Gruß Nacho
Gast
>> In Assembler kein Problem.
>
> In C auch nicht ^^ (nur halt ein bisschen langsamer)
Ja, vielleicht so  ;-))
1
#include <inttypes.h>
2

3
// bla...bla..code..code
4

5
uint8_t number=ui8; // Byte, von dem wir wissen wollen,
6
                        // wie viele Bits gesetzt sind
7
uint8_t count=0;    // Anzahl der Bits in "ui8"
8

9
/* dann irgenwo: */
10
    asm volatile ( 
11
                    "ldi r16,8              \n\t"
12
                    "mov __tmp_reg__, %1    \n\t"
13
                    "clr %0                 \n\t"
14
                    "L_0:" "rol __tmp_reg__ \n\t"
15
                    "brcc L_1               \n\t"
16
                    "inc %0                 \n\t"
17
                    "L_1:""dec r16          \n\t"
18
                    "brne L_0               \n\t" 
19
                    :"=&r" (count)
20
                    :"r" (number)
21
                    :"r16"
22
                );

Natürlich ohne Gewähr. Ginge vielleicht auch unter Umgehung der 
"mov"-Zeile, aber ich habe mit dem Inlne-Assembler wenig Übung und bin 
da eher vorsichtig.
Hi
Da ich kein C kann, ( noooch niicht) mal kurz, wie's gehen sollte
Wert_alt XOR Wert_Neu -> Ergebnis gewechselte Bits
Wert_alt AND Gewechselte Bits -> Flanke nach 0 / zwar nicht gefragt
Wert_Neu AND  Gewechselte Bits -> Flanke nach 1/ dto
Gewechselte Bits schieben und Carry-Flag abfragen, bei Carry Zähler 
Incrementen..
Sollte in jeder Sprache umsetzbar sein.
Gruß oldmax
Gast
> Wert_alt XOR Wert_Neu -> Ergebnis gewechselte Bits
... nicht nötig
> Gewechselte Bits schieben und Carry-Flag abfragen, bei Carry Zähler
> Incrementen..
Letzteres ist genau, was mein Inline-Assembler-Programm (s.o.) macht.

Antwort schreiben

Eine eigene Frage? Dieser Thread ist über 16 Jahre alt. Stell sie in einem eigenen Thread – dort lesen mehr Leute mit, und sie wird öfter und schneller beantwortet.

Neuen Thread starten

Eine Lösung, Ergänzung oder Rückmeldung zu diesem Thread? Dann antworte hier.

Formatierung
  • [c]C-Code[/c]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] – Link zu einem Artikel
  • Verweis auf einen anderen Beitrag: Rechtsklick auf dessen Beitrags-ID (#8078628), „Adresse kopieren“, in den Text einfügen

Mehr zur Formatierung

Längeren Sourcecode als Anhang, nicht in den Text. JPG nur für Fotos und Scans; Zeichnungen und Screenshots als PNG oder GIF. Siehe Bildformate.

Schon registriert? Anmelden

Wird nicht angezeigt. Wir schicken dir einen Link; sobald du damit bestätigst, erscheint dein Beitrag.

Mit dem Abschicken legst du einen kostenlosen Account an und erkennst die Nutzungsbedingungen und die Datenschutzerklärung an.