Programmiersprache C/C++

Byte-Anordnung

Bei Variablen der int-Typfamilie kann unterschieden werden, in welcher Form die Werte auf dem zugeordneten Speicherplatz abgelegt wird.
Beispiel:
  short s = 0x0102;          /* 2 Byte */
  long l = 0x01020304;       /* 4 Byte */
Im zugeordneten Speicherbereich können die Werte in folgender Weise angeordnet werden:
  short
    01 02                     M68xxx, Z8000          big endian
    02 01                     intel 80x86, VAX       little endian

  long
    01 02 03 04               M68xxx, Z8000
    04 03 02 01               intel 80x86, VAX
    02 01 04 03               PDP-11
Programm zur Demonstration der Byte-Anordnung:
  #include <stdio.h>

  int main(void)
  {
    union {
      short i;
      unsigned char c[2];
    } x;

    union {
      long i;
      unsigned char c[4];
    } y;

    x.i = 0x0102;
    printf("%08x %d %d %d %d %d\n", x.i, x.i, x.c[0], x.c[1]);
    printf("%08x %d %02x %02x %02x %02x\n", x.i, x.i, x.c[0], x.c[1]);

    y.i = 0x01020304;
    printf("%08x %d %d %d %d %d\n",
           y.i, y.i, y.c[0], y.c[1], y.c[2], y.c[3]);
    printf("%08x %d %02x %02x %02x %02x\n",
           y.i, y.i, y.c[0], y.c[1], y.c[2], y.c[3]);

    return 0;
  }

  Ergebnis auf PC mit 80x86:
    00000102 258 2 1
    00000102 258 02 01
    01020304 16909060 4 3 2 1
    01020304 16909060 04 03 02 01

  Ergebnis auf Workstation (Sparc, Motorola):
    00000102 258 1 2
    00000102 258 01 02
    01020304 16909060 1 2 3 4
    01020304 16909060 01 02 03 04
Die Operatoren und Funktionen des C/C++ Systems sind so implementiert, daß für den Programmierer die Byte-Anordnung keine Rolle spielt - die Portabilität der Programme wird durch sie nicht berührt.
Portabilitätsprobleme entstehen nur dann, wenn der Programmierer systemnahe Operationen vornimmt, die auf einer bestimmten Byte-Anordnung beruhen !
Werden aus irgendwelchen Gründen solche Operationen benötigt, dann ist Sorge zu tragen, daß von der jeweils richtigen Byte-Anordnung ausgegangen wird.
Im einfachsten Fall kann das durch bedingte Compilation erfolgen: Beim Compilieren sind entsprechende Optionen zu setzen. Dies sollte aber nach Möglichkeit automatisiert werden !
(Es sollte nicht erwartet werden, daß jeder Nutzer jederzeit weiß, welche Byte-Anordnung sein Rechner verwendet.)

Das folgende Programm demonstriert, wie die Byte-Anordnung ermittelt werden kann:

  #include <stdio.h>
  
  #define N sizeof(long)
  
  int main(void)
  {
    union {
      long l;
      char c[N];
    } u;
  
    u.l = 1;
    if ( u.c[0] == 1 )
      printf("Little Endian\n");
    else if ( u.c[N-1] == 1 )
      printf("Big Endian\n");
    else
      printf("???");
  
    return 0;
  }
Das folgende (Scherz-)Programm zeigt, daß die Beachtung der Byte-Anordnung wichtig sein kann:
  #include <stdio.h>
  
  int main(void)
  {
    union {
      char c[16];
      long z[4];
    } geheim, *p;
  
    p = &geheim;
  
  #if defined BIG_ENDIAN  && defined LITTLE_ENDIAN
    #error "Bitte Byte-Ordnung eindeuting definieren !"
  #elif defined LITTLE_ENDIAN
    p->z[0] = 0x6c6c6548;
    p->z[1] = 0x57202c6f;
    p->z[2] = 0x646c726f;
    p->z[3] = 0x000a2120;
  #elif defined BIG_ENDIAN
    p->z[0] = 0x48656c6c;
    p->z[1] = 0x6f2c2057;
    p->z[2] = 0x6f726c64;
    p->z[3] = 0x20210a00;
  #else
    #error "Bitte Byte-Ordnung definieren !"
  #endif
  
    printf("%s", p->z);
  
    return 0;
  }
Hier muß der Nutzer mit Hilfe von symbolischen Konstanten angeben, welche Byte-Anordnung sein Rechner verwendet.
Bemerkung: Eine automatische Ermittlung der Byte-Anordnung wie zuvor demonstriert wäre natürlich nutzerfreundlicher und vor allem auch sicherer.

Hinweis:
Im obigen Beispiel kann die symbolische Konstante, die zur Festlegung der Byte-Anordnung verwendet wird, beim Compiler-Aufruf gesetzt werden, z.B.

  cc geheim.c -DBIG_ENDIAN
Das Programm liefert
  Hello, World !           bei korrekter Nutzung
  lleHW ,odlro             sonst

Zurück zum Menü
Zurück zur vorigen Seite Weiter zur nächsten Seite

P. Böhme, 22.02.1996