www.mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik AVR: Pinstatus in Byte schreiben


Autor: lightninglord (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo Zusammen,

ich hab ein kleines programmiertechnisches Problem: Das ganze ist eine 
art SPI-Verschnitt ( leider ist der HWSPI schon mit dem Funkmodul 
beschäftigt . Ich möchte bei jedem LOW auf dem CK den DA einlesen und in 
das Bit an der j-ten stelle im digi_data-Array im i-ten Byte schreiben. 
So hier mein Code dazu:
for (j=0; j<8; j++)
    {
      while (DIGI_PIN & (1<<DIGI_CK));            //Warte auf LOW
      
      digi_data[i] |= (DIGI_PIN && (1<<DIGI_DA)) & (1<<j);  //Schreibe PIN in Bit j

      
      while (!(DIGI_PIN & (1<<DIGI_CK)));            //Warte auf HIGH

    }

Leider funktioniert es nicht, ich hab schon ein bisschen mit dem 
Simulator rungespielt aber ich bekomme einfach nichts in meine Bytes 
geschrieben. Könnt ihr mir helfen, ich finde meinen Denkfehler leider 
nicht.

Grüßle

lightninglord

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
lightninglord schrieb:

>       digi_data[i] |= (DIGI_PIN && (1<<DIGI_DA)) & (1<<j);  //Schreibe

                                  **
Das ist ein logisches Und. Du willst eine binäre Und Verknüpfung des Pin 
Inhalts mit 1<<DIGI_DA   ->  & verwenden

Das nächste Problem ist, dass dieses nicht 0 oder 1 ergibt, sondern 0 
bzw. 1<<DIGI_DA, je nach Zustand das Pins.

Versuch dich nicht selbst auszutricksen, indem du möglichst komplizierte 
Verknüpfungen machst. Oft ist der klarste Weg auch der Beste

    if( DIGI_PIN & ( 1<<DIGI_DA) )
      digi_data[i] |= (1<<j);

PS: Du möchtest das variable Schieben der 1 mit j auf jeden Fall weg 
haben. Die Operation ist nämlich ziemlich teuer und man kann sie ganz 
leicht umgehen.

Autor: lightninglord (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>PS: Du möchtest das variable Schieben der 1 mit j auf jeden Fall weg
>haben. Die Operation ist nämlich ziemlich teuer und man kann sie ganz
>leicht umgehen.

Hätteste mir nen kleinen Tip, mein C ist etwas eingerostet.

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
lightninglord schrieb:
>>PS: Du möchtest das variable Schieben der 1 mit j auf jeden Fall weg
>>haben. Die Operation ist nämlich ziemlich teuer und man kann sie ganz
>>leicht umgehen.
>
> Hätteste mir nen kleinen Tip, mein C ist etwas eingerostet.

Gesehen über die Schleife, was ergibt denn i<<j wenn sich j langsam von 
0 bis 8 aufbaut.

   00000001
   00000010
   00000100
   00001000
   00010000
   00100000
   01000000
   10000000

Nun muss man das aber nicht über 1<<j jedesmal neu errechnen. Es gneügt 
doch, wenn man sich vor der Schleife eine Maske mit einer 1 zurechtlegt 
und diese Maske in jedem Schleifendurchlauf um 1 nach links schiebt.
   uint8_t mask = 0x01;

   digi_data[i] = 0;
   for( j = 0; j < 8; ++j ) {
     if( DIGI_PIN & ( 1<<DIGI_DA) )
       digi_data[i] |= mask;

     mask = mask << 1;
   }

und schon ist aus dem variablen Schieben ein konstantes Schieben um 
jeweils 1 geworden. (Ganz abgesehen davon, dass das dann in Summe 
weniger Schiebevorgänge sind :-)

Autor: lightninglord (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Dank dir, das war so einfach, da bin ich jetzt ned drauf gekommen, hab 
mich schon in struckt anfangen Einzulesen, wird wohl Zeit Mittag zu 
machen ;-)

Danke nochmals.

Grüßle

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
(Alternativ könnte man auch immer nur das unterste Bit in digi_data[i] 
setzen und dafür digi_data[i] um jeweils 1 Stelle nach links schieben)
   digi_data[i] = 0;
   for( j = 0; j < 8; ++j ) {
     digi_data[i] = digi_data[i] << 1;
     if( DIGI_PIN & ( 1<<DIGI_DA) )
       digi_data[i] |= 0x01;
   }

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.