Hallo an alle,

hier mal ein Programmschnippsel für die Neugierigen, die wissen wollen wie es geht: (Und es geht gut!)

Code:
/*----------------------------------------------------------------------------
   Defines: Adresse vom BMA020-3D-Beschleunigungssensor
*/
#define   I2C_BMA_W   0x70
#define   I2C_BMA_R   0x71

int16_t     x, y, z;
uint8_t     ret;

   /*
      Lesen von 6 Registern ab Register 0x02. X, Y, Z-Koordinate
   */
   ret = StartI2C (I2C_BMA_W);
   ret = WriteI2C (0x02);
         StopI2C  ();

   ret = StartI2C (I2C_BMA_R);
   ret = ReadI2C  (ACK); x = (int16_t)ret;
   ret = ReadI2C  (ACK); x = x | ((int16_t)ret << 8); x /= 64;
   ret = ReadI2C  (ACK); y = (int16_t)ret;
   ret = ReadI2C  (ACK); y = y | ((int16_t)ret << 8); y /= 64;
   ret = ReadI2C  (ACK); z = (int16_t)ret;
   ret = ReadI2C  (NAK); z = z | ((int16_t)ret << 8); z /= 64;
         StopI2C  ();
Um z.B. das Status-Register 14 (Hex) auszulesen macht man folgendes:
Code:
/*----------------------------------------------------------------------------
   Defines: Adresse vom BMA020-3D-Beschleunigungssensor
*/
#define   I2C_BMA_W   0x70
#define   I2C_BMA_R   0x71

  /*
    Lesen des Status-Registers 0x14 : reserviert:7:5 range:4:3 bandwidth:2:0
  */
uint8_t     ret, r14;
uint8_t     range;

  ret = StartI2C (I2C_BMA_W);
  ret = WriteI2C (0x14);
        StopI2C  ();

  ret = StartI2C (I2C_BMA_R);
  r14 = ReadI2C  (NAK);
        StopI2C  ();
  range = (r14 & 0b00011000) >> 3;

Und bei mir betrug die Lieferzeit nur ca. 10 Tage. Jippie

Gruß
Sternthaler

[edit 11.10.2010]
Auf Wunsch eine kleine Erklärung für die Berechnung der x-, y-, z-Werte.

Für X steht im oberen Code-Block folgendes:
Zeile 1) ret = ReadI2C (ACK); x = (int16_t)ret;
Zeile 2) ret = ReadI2C (ACK); x = x | ((int16_t)ret << 8 ); x /= 64;

In Zeile 1) wird beim ersten ReadI2C der Wert vom Register 0x02 aus dem Chip gelesen. Darin sind nur die beiden obersten Bit relevant für das X-Ergebnis. Es sind die beiden untersten Bits vom gesamten 10-Bit-Messwert.
Trotzdem wird diese Byte nun als 16-Bitwert in der Variablen x gespeichert.
In Zeile 2) wird mit dem nächsten ReadI2C das Register 0x03 aus dem Chip gelesen. (Die Adresse wird automatisch vom Chip hochgezählt.)
Dahinter wird nun das in Zeile 1) gelesene BIT-Muster mit |-Zeichen und dem in Zeile 2) gelesenen und mit dem <<8 um 8 BIT nach links geschobenem Registerwert aus 0x03 'verbunden'.
=> 0000 0000 ??-- ----: Die 2 Bits aus Zeile 1) in der 16-Bit-Variablen x
Bit-ODER-Verknüpft (|-Zeichen) mit dem um 8 Bit nach links geschobenem Wert aus Zeile 2)
=> ???? ???? 0000 0000: Die oberen 8 Bit vom Messwert. Ergibt:
----------------------------
=> ???? ???? ??-- ----

Die ? sind also nun die 10 Bit Messergebnis
Die - sind Bits, die auch gelesen wurden, aber hier nicht interessieren.
Die 0 sind Bits, die wir bewusst gesetzt hatten.

Jetzt noch in Zeile 2) mit dem x /= 64 diese Ergebnis einfach um 6 Bit nach rechts schieben. (Man kann auch schreiben x = x / 64
Man hätte auch x = ( x | ((int16_t)ret << 8 ) ) >> 6; schreiben können. Das macht der Compiler sowiso daraus.

Also ist das Ergebnis nun:
=> 0000 00?? ???? ????

Und damit haben wir die 10 Bit X-Messwert 'greifbar'.
ACHTUNG: Das höchste ?-Bit ist ein Vorzeichen.
Die Zählweise für den Betrag des Wertes kann man am besten in der Doku nachlesen.

Datenblatt: BMA020
Die Register sind auf Seite 9 beschreiben.
Die Zählweise vom Ergebnis ist auf Seite 21.

Viel Spaß beim Lesen wünscht
Sternthaler