Forum: Mikrocontroller und Digitale Elektronik ATmega8 - binär zu hex umwandeln


von peter (Gast)


Lesenswert?

hallo,

kann mir jemand sagen wie man eine Funktion in Assembler schreibt, die 
einen vom Poti eingestellten Wert aus einem A/D-Wandler in eine 
Hexadezimal-Form umwandelt? Bin Anfänger und verstehe das mit dem 
Umwandel nicht. Benutze den ATmega8.

von Volker S. (volkerschulz)


Lesenswert?

Eine Zahl ist als Zahl gespeichert, egal wie man sie nun notiert. Was 
genau willst Du umwandeln? Eine Zahl (in einem Register) in HEX-ASCII, 
also in lesbare Hexadezimalzeichen?

Volker

von peter (Gast)


Lesenswert?

genau! also einen binären Wert in eine Hexadezimalzeichen, die den 
gleichen Wert haben. Muss diesen Hexadezimalzeichen auf nem Display 
ausgeben.

von Chris (Gast)


Lesenswert?


von Karl H. (kbuchegg)


Lesenswert?

peter schrieb:
> genau! also einen binären Wert in eine Hexadezimalzeichen, die den
> gleichen Wert haben. Muss diesen Hexadezimalzeichen auf nem Display
> ausgeben.

Im Rechner ist alles grundsätzlich einfach nur eine Zahl.
Du willst eine Textrepräsentierung erzeugen, für diese Zahl, wobei die 
Textrepräsentierung die Zahl in Hexadezimaler Form wiedergibt.

Soviel zur Nomenklatur, damit es keine Misverständnisse gibt.

Hast du die 8 Bit in einem Register vorliegen

   1111 1111

so sind die oberen 4 Bit (ein sog. Nibble) eine Hex-Ziffer und die 
unteren 4 Bit eine Hex Ziffer.
Das Bitmuster
     1111 1111

wird Hexadezimal als FF notiert. Dies deshalb weil

    binär   Hex       binär  Hex
    0000     0        1000   8
    0001     1        1001   9
    0010     2        1010   A
    0011     3        1011   B
    0100     4        1100   C
    0101     5        1101   D
    0110     6        1110   E
    0111     7        1111   F

wichtig: die beiden Kolonnen 'binär' und 'hex' sind die gleichen Zahlen, 
nur anders hingeschrieben.

Um also das auszugebende Zeichen für ein Nibble zu bestimmen, müssen wir 
wissen, welches ASCII Zeichen auszugeben ist, wenn das Bitmuster zb. 
0010 lautet. Das muss klarerweise das Zeichen sein, das im ASCII Code 
als '2' angeführt ist.
Siehst du dir jetzt eine ASCII Tabelle an, dann stellst du fest, dass 
die Zeichen für '0' .. '9' praktischerweise alle hintereinander kommen.

http://de.wikipedia.org/wiki/American_Standard_Code_for_Information_Interchange

Das Zeichen '0' hat den ASCII Code 0x30

wenn du also zum ASCII Code für '0' das Nibble dazuaddierst, dann ergibt 
sich

    0011 0000      ( = hex 30, der ASCII Code für '0' )
    0000 0010      ( dazu das Nibble, für welches wir den Code brauchen)
  -------------
    0011 0010

0011 0010  ist aber die binäre SChreibweise für hex 32. Und das ist 
genau der ASCII Code für '2'. Schickst du diesen Code an ein 
Ausgabegerät, so wird es das Zeichen '2' anzeigen.

Dies geht solange gut, solange sich das Nibble im Bereich 0 bis 9 
bewegt. Hat das Nibble den Wert A oder darüber, dann geht das nicht 
mehr. Anstatt dem ASCII Code der Ziffern, muss bei einem Nibble von 1010 
(also Hex A) der ASCII Code für 'A' rauskommen. Der ASCII Code lautet 
0x41 (einfach in der ASCII Tabelle nachsehen.
Hat dein Nibble also den Wert A, dann rechnet man Nibble + ASCII Code 
für A - 10

Und damit hast du die Ausgabe eines Nibbles fertig

   if Wert des Nibbles kleiner hex-A ?
     gib aus 'Wert des Nibbles' + ASCII Code für '0' (=0x30)
   else
     gib aus "Wert des Nibbles' + ASCII Code für 'A' - 10

Jetzt hast du aber nicht einfach nur 1 Nibble, sondern ein Register 
enthält 2 davon: Ein niederwertiges NIbble und ein höherwertiges NIbble

    8765 4321   (das sind die Bitpositionen)

Aber, und das ist das schöne an Hex, die beiden sind in Hex-Schreibweise 
voneinander unabhängig. Für Hex Ausgabe reicht es, wenn du zunächst die
Bitpositionen 8765 zurechtschiebst

     8765 4321   ->   0000 8765

und die Nibbleausgabe machst, und danach das niederwertige Nibble 
isolierst

     8765 4321   ->   0000 4321

und die Nibbleausgabe machst.

Aus dem Bitmuster

     1011 0110

wird so zunächst das höherwertige Nibble extrahiert   1011, für welches 
die Nibbleausgabe das ASCII Zeichen 'B' an die Ausgabe schickt und dann 
das Nibble 0110, für welches die Nibbleausgabe das Zeichen '6' an die 
Ausgabe schickt. Auf der Ausgabe steht dann B6 und das ist genau die 
hexadezimale Schreibweise für 1011 0110  (und jetzt weißt du auch, warum 
man Binärzahlen gerne in 4-er Gruppen schreibt. Weil dann die Umwandlung 
in eine Hex-Schreibweise mit obiger Tabelle ganz einfach ist)

von Mr. Yesterday (Gast)


Lesenswert?

Das Thema hatte wir gestern schonmal :)

Beitrag "Hex Wert als Hex Wert ausgeben"

von peter (Gast)


Lesenswert?

Vielen Dank  Karl heinz Buchegger!

Verstehe das jetzt schon viel besser =)

Ich versuche dann mal die Umwandlung und die Ausgabe zu schreiben.
Echt gute Unterstützung hier!!

Gruß Peter

von L. K. (ladde)


Lesenswert?

Wieso noch selber schreiben (die Umwandlung)?
Denke mal, kompakter / effizienter als 
http://elm-chan.org/docs/avrlib/mk_hex.txt bekommts hier keiner hin ;-)
Immer wieder beeindruckend, was für sparsame Routinen da dokumentiert 
sind...

Bin zwar auch Anfänger, aber konnte den Code recht schnell 
nachvollziehen. (Hab hoffentlich nichts falsch verstanden)

Musst nur deinen ADC-Wert in zwei Register packen (var0 und var1) und 
mk_h16 aufrufen.

Zur Ausgabe dann noch eine Routine ("xmit") schreiben, die var0 ans LCD 
schickt.

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.