mikrocontroller.net

Forum: Compiler & IDEs Einzelne Bits setzen


Autor: Andy11 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Da ich mich gerade in C einarbeite habe ich einmal ein paar Fragen zum 
setzen von Bits in einer uint8_t Variable.

Aus Tutorial:
>#include <avr/io.h>
>...
>#define MEINBIT 2
>...
>PORTA |= (1 << MEINBIT);    /* setzt Bit 2 an PortA auf 1 */
>PORTA &= ~(1 << MEINBIT);   /* loescht Bit 2 an PortA */

Wieso löscht gerade dieser Ausdruck (|=) die Bits und der (&= ~) löscht 
sie?
Ist das eine Festlegung oder haben diese Zeichen irgend einen 
Zusammenhang mit dem Löschen und setzen von Bits?

Wieso geht das nicht einfach so: PORTB.0 = 1, x.5 = 1 ? Wäre das nicht 
logischer?
Ich weiß das geht mit struct aber kann ich mit struct auch einfach sagen

PORTB = x(Variable vom struct und besteht aus 8 Bit)
und jetzt kann ich den PORTB vom x aus steuern?
Leider kann ich noch nicht simulieren da mein Eclipse nicht Debuggen 
kann, deswegen die Fragen.

lg andy

Autor: Wolfgang Bengfort (et-tutorials) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo Andy11,
ich habe zu diesem Thema ein Video gedreht.
Vielleicht hilft es Dir...

http://et-tutorials.de/1908/bitweise-manipulation/

Autor: Rolf Magnus (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Andy11 schrieb:
> Wieso löscht gerade dieser Ausdruck (|=) die Bits und der (&= ~) löscht
> sie?
> Ist das eine Festlegung oder haben diese Zeichen irgend einen
> Zusammenhang mit dem Löschen und setzen von Bits?

Dazu bietet es sich an, ein Buch über die Grundlagen von C zu lesen. Die 
obigen "Zechen" (Operatoren) führen bitweise Boole'sche Operationen 
durch.

> Wieso geht das nicht einfach so: PORTB.0 = 1, x.5 = 1 ? Wäre das nicht
> logischer?

Es würde halt gegen die ISO-C-Spezifikation verstoßen. In C gibt es 
keine Bit-Datentypen.

> Ich weiß das geht mit struct

Du meinst vermutlich Bitfelder.

> aber kann ich mit struct auch einfach sagen
>
> PORTB = x(Variable vom struct und besteht aus 8 Bit)
> und jetzt kann ich den PORTB vom x aus steuern?

PORTB ist vom Typ uint8_t. Dem kann man keine Struktur zuweisen.

> Leider kann ich noch nicht simulieren da mein Eclipse nicht Debuggen
> kann, deswegen die Fragen.

Was würdest du denn simulieren wollen? Deine Ideen wird der Compiler 
schon gar nicht akzeptieren.

Autor: narf (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
PORTA |= (1 << MEINBIT)

oder anders ausgedrückt

PORTA = PORTA | (1 << MEINBIT)

dein neues bit wird mit dem alten portwert verodert

bei &=  auch nur wird es vorher negiert und dann verundet

Autor: narf (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
asso ..
es gibt welche die haben sowas mit Portx.bit  gebaut
es geht also ...

muss ma gucken .. irgendwo hab ich da noch was

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
narf schrieb:

> es gibt welche die haben sowas mit Portx.bit  gebaut
> es geht also ...

Zwei Wege: Der eine geht über Bitfelder und wurde bereits angerissen. 
Kommt sowas wie PORTA.BIT0 = 1 raus. PORTA.0 geht so nicht.

Der andere Weg ist die Verwendung von C als Basis einer eigenen frisch 
erfundenen Programmiersprache mit solchen Erweiterungen wie PORTA.0 = 1, 
die man frecherweise trotzdem C nennt. Nachteil: Portierungsfalle, kommt 
man schlecht wieder von weg.

Autor: Andy11 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Wolfgang Bengfort schrieb:
> Hallo Andy11,
> ich habe zu diesem Thema ein Video gedreht.
> Vielleicht hilft es Dir...

ok, das Video habe ich mir zwar angeschaut, mir hilft aber das

narf schrieb:
> PORTA |= (1 << MEINBIT)
>
> oder anders ausgedrückt
>
> PORTA = PORTA | (1 << MEINBIT)
>
> dein neues bit wird mit dem alten portwert verodert
>
> bei &=  auch nur wird es vorher negiert und dann verundet

besser.
Ich weiß was |= bedeutet und ich weiß auch warum da was gesetzt wird, 
die Frage ging eher auf das &=~
Was macht die Welle nach dem Gleich?

A. K. schrieb:
> Zwei Wege: Der eine geht über Bitfelder und wurde bereits angerissen.
> Kommt sowas wie PORTA.BIT0 = 1 raus. PORTA.0 geht so nicht.

Genau so habe ich das gemeint. Dann würde ich aber unnötig Speicher 
verschwenden oder?

lg andy

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Andy11 schrieb:

> Dann würde ich aber unnötig Speicher verschwenden oder?

Nur wenn der Compiler dusselig genug ist, diese 1-Bit Bitfelder nicht 
auf die gleiche Art zu behandeln. Versuch macht kluch. Bei GCC m.W. kein 
Problem. Man muss "nur" für jedes vermaledeite I/O-Register so eine 
Bitfeld-Struct definieren.

Autor: Rufus Τ. Firefly (rufus) (Moderator) Benutzerseite
Datum:

Bewertung
1 lesenswert
nicht lesenswert
Andy11 schrieb:
> die Frage ging eher auf das &=~
> Was macht die Welle nach dem Gleich?

Die Tilde invertiert jedes einzelne Bit.

Beispiel:

Bit 3 setzen:

  a |= (1 << 3);

  a |= 0x08;

  a |= 0b00001000;

Bit 3 löschen:

  a &= ~(1 << 3);

  a &= ~0x08;

  a &= ~0b00001000;

  a &= 0b11110111;

Autor: Andy11 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
A. K. schrieb:
> Nur wenn der Compiler dusselig genug ist, diese 1-Bit Bitfelder nicht
> auf die gleiche Art zu behandeln. Versuch macht kluch. Bei GCC m.W. kein
> Problem. Man muss "nur" für jedes vermaledeite I/O-Register so eine
> Bitfeld-Struct definieren.

okay, das ist ja was positives

Rufus t. Firefly schrieb:
> Die Tilde invertiert jedes einzelne Bit.
>
> Beispiel:
>
> Bit 3 setzen:
>
>   a |= (1 << 3);
>
>   a |= 0x08;
>
>   a |= 0b00001000;
>
> Bit 3 löschen:
>
>   a &= ~(1 << 3);
>
>   a &= ~0x08;
>
>   a &= ~0b00001000;
>
>   a &= 0b11110111;

cool danke, weiß jetz was das is, danke

lg andy

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.