Forum: Mikrocontroller und Digitale Elektronik Umwandlung 16-Bit-Zahl in H-Byte und L-Byte


von wern (Gast)


Lesenswert?

Hallo,

kann jemand sagen, was die einfachste Möglichkeit ist, in C mit dem 
AVR-Studio eine 16-Bit-Zahl in ihr H-Byte und L-Byte aufzuschlüsseln?

Als Beispiel:

uint16_t sechzehn = 43760;

uint8_t lowbyte;
uint8_t highbyte;

Nehme an, das LOW Byte erhält man so:

lowbyte = sechzehn;

Wenn man den Inhalt der Variable sechzehn dann um 8 Binärstellen 
verschiebt, bekommt man das HIGH Byte auf die gleiche Weise, oder?

shift um 8 Stellen
highbyte = sechzehn;

Stimmt das so? Wenn ja, woher weiß man, in welche Richtung verschoben 
werden muss?

Letzte Frage: ist das in Bezug auf verbrauchte Rechentakte auch der 
schnellste Weg oder gibt es noch einen schnelleren (bzw. einfacheren)?

von amateur (Gast)


Lesenswert?

Spar' Dir die Schubserei und schau' mal unter dem Stichwort union nach.

von leichenfinder (Gast)


Lesenswert?

amateur schrieb:
> Spar' Dir die Schubserei und schau' mal unter dem Stichwort union nach.

Laut Standard nicht definiert. Frage kommt alle 3 Tage, Antwort: shiften 
ist am besten.

von Pink S. (pinkshell)


Lesenswert?

So
1
   uint16_t baud;
2
   ...
3
   UBRRH = (uint8_t) (baud >> 8);
4
   UBRRL = (uint8_t) baud;
wird es auch gerne gemacht (aus dem Tutorial oben links)

von amateur (Gast)


Lesenswert?

Viele der "kleinen" können es nur einmal zur gleichen Zeit. D.H. 8 
Befehle nur für die Schiebung.

Kein Problem, wenn man sowieso Urlaub hat.

An der Arbeit würde ich dann schon eher mit casts rumfummeln.

Das gute, alte Wort besteht ja immer noch aus 2 Bytes auch wenn es seit 
neuestem meist uint?_t gerufen wird.

von wern (Gast)


Lesenswert?

Danke für die Antworten!


Pink Shell schrieb:
> uint16_t baud;
>    ...
>    UBRRH = (uint8_t) (baud >> 8);
>    UBRRL = (uint8_t) baud;

Das (uint8_t) castet die "untersuchte" Variable, nehme ich an...

(baud >> 8) verändert die Variable baud nicht?



Wie viele Takte benötigen die beiden Operationen?
UBRRH = (uint8_t) (baud >> 8);
UBRRL = (uint8_t) baud;

Nehme an, die untere Zeile benötigt einen Takt. Und die obere?

von wern (Gast)


Lesenswert?

Überschnitten!

amateur schrieb:
> Viele der "kleinen" können es nur einmal zur gleichen Zeit. D.H. 8
> Befehle nur für die Schiebung.
>
> Kein Problem, wenn man sowieso Urlaub hat.
>
> An der Arbeit würde ich dann schon eher mit casts rumfummeln.

8 Takte nur für das Bit-Schieben??? Geht das irgendwie schneller?

von Simon K. (simon) Benutzerseite


Lesenswert?

wern schrieb:
> Überschnitten!
>
> amateur schrieb:
>> Viele der "kleinen" können es nur einmal zur gleichen Zeit. D.H. 8
>> Befehle nur für die Schiebung.
>>
>> Kein Problem, wenn man sowieso Urlaub hat.
>>
>> An der Arbeit würde ich dann schon eher mit casts rumfummeln.
>
> 8 Takte nur für das Bit-Schieben??? Geht das irgendwie schneller?

Das is Unsinn. Schieben kostet genau einen Takt und das Schieben um 8 
kostet natürlich gar keine Instruktion, da auf Byteebene zugegriffen 
wird.

von amateur (Gast)


Lesenswert?

Ein cleverer Compiler schafft das auch in einem Tackt/Befehl.

von Simon K. (simon) Benutzerseite


Lesenswert?

amateur schrieb:
> Ein cleverer Compiler schafft das auch in einem Tackt/Befehl.

Lerne zitieren.

Wie auch immer ,ein 8 Bit Shift benötigt gar keinen Takt (angenommen es 
geht um 8 Bitter, bzw. AVRs).

von c-hater (Gast)


Lesenswert?

amateur schrieb:

> Viele der "kleinen" können es nur einmal zur gleichen Zeit. D.H. 8
> Befehle nur für die Schiebung.

Nein. Sogar C-Compiler sind heutzutage clever genug, zu erkennen, daß 
sie im Spezialfall des Vielfachen der grundlegenden Datenbreite der 
Architektur nicht bitweise schieben müssen, sondern eben in den größeren 
Häppchen dieser Datenbreite "umkopieren" können. Im konkreten Fall wird 
natürlich nichtmal was kopiert, sondern einfach nur auf das richtige 
Byte zugegriffen und fertig ist der Lack.

von wern (Gast)


Lesenswert?

Danke für die vielen Antworten!

Dann sind meine Fragen von oben so weit geklärt.



Was mich noch interessieren würde, bei AVR-Registern, die ein H und ein 
L Byte haben, wird zuerst das H und dann das L Register geschrieben und 
der AVR setzt erst dann die beiden Werte um.
Oder?

von wern (Gast)


Lesenswert?

...  also sprich:

wenn der L-Wert geschrieben wurde, werden H und L eines Registers 
aktiv...?

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.