Forum: Mikrocontroller und Digitale Elektronik Zweierkomplement uint8_t richtig ausgeben


von Fridolin O. (muebau)


Lesenswert?

Hi,
ich muss 10 Bit im Zweierkomplement mit itoa(..) ausgeben.

Ich habe Daten (10 Bit) in zwei Bytes:
1
uint8_t write_buf[]

Nach etwas hin und her Schieberei habe ich 10 Bit:
1
int16_t data

Das Bit an der 10. Stelle (9. Bit) ist das Vorzeichenbit.

Wie bekomme ich das nun mit itoa(...) ausgeben?
Solange es sich um positive Werte handelt ist alles gut.

Negativ (problematisch):
Bis jetzt habe ich das Vorzeichenbit an der 16. Stelle gesetzt und an 
der 10. Stelle gelöscht wenn es gesetzt war.
Leider klappt es nicht.

Wo liegt mein Fehler?

Tschuess muebau

von Uwe H. (mistert)


Lesenswert?

In Zeile 23 bei Zeichen 42 liegt der Fehler...

von Stefan E. (sternst)


Lesenswert?

Fridolin Onteca schrieb:
> Bis jetzt habe ich das Vorzeichenbit an der 16. Stelle gesetzt und an
> der 10. Stelle gelöscht wenn es gesetzt war.
> Leider klappt es nicht.

Weil schlicht falsch. Richtig:
Wenn Bit an 10. Stelle gesetzt, dann zusätzlich alle Bits oberhalb davon 
auch setzen.

von Fridolin O. (muebau)


Lesenswert?

Stefan Ernst schrieb:
> Weil schlicht falsch. Richtig:
> Wenn Bit an 10. Stelle gesetzt, dann zusätzlich alle Bits oberhalb davon
> auch setzen.

Vielen Dank.
Das Bit an der 10. Stelle ebenfalls?

Tschuess muebau

@
Uwe H. schrieb:
> In Zeile 23 bei Zeichen 42 liegt der Fehler...
???
http://de.wikipedia.org/wiki/Troll_%28Netzkultur%29

von DirkB (Gast)


Lesenswert?

Wenn du als int16_t schiebst, kommt es richtig raus.

von Werner (Gast)


Lesenswert?

Fridolin Onteca schrieb:
> Stefan Ernst schrieb:
>> Wenn Bit an 10. Stelle gesetzt, dann zusätzlich alle Bits oberhalb davon
>> auch setzen.
>
> Das Bit an der 10. Stelle ebenfalls?

Nicht nötig, das ist dann schon gesetzt ;-)

von Fridolin O. (muebau)


Lesenswert?

Werner schrieb:
> Nicht nötig, das ist dann schon gesetzt ;-)

Ja, das hatte ich so sagen wollen :-)

Vielen Dank.

Tschuess muebau

von Daniel H. (Firma: keine) (commander)


Lesenswert?

Fridolin Onteca schrieb:
> @
> Uwe H. schrieb:
>> In Zeile 23 bei Zeichen 42 liegt der Fehler...
> ???
> http://de.wikipedia.org/wiki/Troll_%28Netzkultur%29

Nein, kein Troll, wir mögen es hier nur gerne wenn man uns auch 
Quellcode zeigt, ansonsten endet das oftmals in rätseln und mutmaßen.

von Fridolin O. (muebau)


Lesenswert?

Hallo,

Daniel H. schrieb:
> Nein, kein Troll, wir mögen es hier nur gerne wenn man uns auch
> Quellcode zeigt, ansonsten endet das oftmals in rätseln und mutmaßen.

ich hatte das schon hier versucht.
Beitrag "Werte eines BMA020 (vorzeichenlos) ausgeben (vorzeichenbehaftet)"
:-)

Ich hatte aber den Eindruck zu viel ins Detail gegangen zu sein. Da ich 
mir erarbeitet hatte wo mein Problem zu liegen scheint, schien mir eine 
gezielte Frage sinnvollen um Antworten zu erhalten.

Ich bin aber immer für konstruktive Kritik offen und dankbar.

Tschüss muebau

PS:
So der "Trollvorwurf" ungerechtfertigt war, nehme ich ihn in aller Form 
zurück. ;-)

von Fridolin O. (muebau)


Lesenswert?

Hi,
die Version mit den 10 Bit funktioniert.

Bis jetzt hatte ich gedacht diese einfach von
1
uint8_t

in die itoa(...) Funktion packen zu können.

Da kommen nur positive werte raus. Was geht da schief. Es handelt sich 
zwar um einen uint8_t, die Daten in der Variable sind aber signed 8 Bit 
im Zweierkomplement.

Macht der Compiler das was oder was mache ich da falsch?

Tschuess muebau

von Stefan E. (sternst)


Lesenswert?

Fridolin Onteca schrieb:
> Es handelt sich
> zwar um einen uint8_t, die Daten in der Variable sind aber signed 8 Bit
> im Zweierkomplement.

Und woher soll der Compiler das wissen, wo du ihm mit "uint8_t" doch 
explizit sagst, dass der Wert kein Vorzeichen hat?

von Yalu X. (yalu) (Moderator)


Lesenswert?

Ohne Verzweigung und explizites Bitgepopel:
1
  struct z { signed int z:10; };
2
3
  int z = 0x2d4;        // -300 als 10-Bit-Wert
4
  z = (struct z){z}.z;  // Vorzeichenerweiterung nach int

Leider tut sich da der GCC etwas schwer bei der Optimierung.

von Fridolin O. (muebau)


Lesenswert?

Hi,
Yalu X. schrieb:
> Ohne Verzweigung und explizites Bitgepopel:
>
>
1
>   struct z { signed int z:10; };
2
> 
3
>   int z = 0x2d4;        // -300 als 10-Bit-Wert
4
>   z = (struct z){z}.z;  // Vorzeichenerweiterung nach int
5
>
>
> Leider tut sich da der GCC etwas schwer bei der Optimierung.

Das mit den 10 Bit laeuft.
Ich will aber auch eine 8 Bit Variante. Hierbei liegen die Daten in 
einem uint8_t und das Vorzeichen ist auch an der 8. Stelle. Um dem 
Compiler das richtig zu verkaufen sollte doch folgendes reichen, nicht?
1
uint8_t x;
2
itoa((int)x);

Leider kommen hier auch nur positive Werte.

Tschuess muebau

von Stefan E. (sternst)


Lesenswert?

Fridolin Onteca schrieb:
> Um dem
> Compiler das richtig zu verkaufen sollte doch folgendes reichen, nicht?

Nein. Der komplette positive Wertebereich eines uint8_t passt auch in 
ein int. Wo sollen da die negativen Zahlen herkommen? Du musst ihm 
sagen, dass die 8 Bit in Wirklichkeit ein Vorzeichen beinhalten.
1
itoa((int8_t)x);

von Fridolin O. (muebau)


Lesenswert?

Hi,
Stefan Ernst schrieb:
> Fridolin Onteca schrieb:
>> Um dem
>> Compiler das richtig zu verkaufen sollte doch folgendes reichen, nicht?
>
> Nein. Der komplette positive Wertebereich eines uint8_t passt auch in
> ein int. Wo sollen da die negativen Zahlen herkommen? Du musst ihm
> sagen, dass die 8 Bit in Wirklichkeit ein Vorzeichen beinhalten.
>
1
itoa((int8_t)x);

natürlich!

Jetzt verstehe ich auch warum er das nicht "richtig" gemacht hat.

Vielen Dank.

Tschuess muebau

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.