Hallo,
ich versuche mich mit dem I2C Bus, doch leider klappt es nicht wie es
soll.
Vorneweg, der Bus scheint in Ordnung zu sein, ich kann über den
entsprechenden Treiber die Temperatur eines LM75 über I2C auslesen. Ich
arbeite auf einem PPC405GPr.
Doch wenn ich ohne Treiber direkt darauf zugreifen will, oder auch auf
andere Bausteine, dann klappt das nicht.
Ich habe zwei Dinge versucht. Erst mit dem Programm i2cdetect:
http://www.lm-sensors.org/wiki/man/i2cdetect
1
i2cdetect -l
sagt mir
1
i2c-0 i2c IBM IIC I2C adapter
Mein Bus ist der i2c-0, soweit alles ok. Doch wenn ich
1
i2cdetect i2c-0
ausführe erhalte ich
1
Error: I2C bus name doesn't match any bus present!
:-( Dann habe ich versucht selbst ein paar Zeilen zu coden:
1
int file;
2
char *filename = "/dev/i2c-0";
3
//const gchar *buffer;
4
5
if ((file = open(filename, O_RDWR)) < 0) {
6
/* ERROR HANDLING: you can check errno to see what went wrong */
7
perror("Failed to open the i2c bus");
8
exit(1);
9
}
10
11
int addr = 0x93; // Adresse des LM75 0b10010011
12
13
if (ioctl(file, I2C_SLAVE, addr) < 0) {
14
perror("Failed to acquire bus access and/or talk to slave");
15
/* ERROR HANDLING; you can check errno to see what went wrong */
16
exit(1);
17
}
Dies bricht ab mit
1
Failed to acquire bus access and/or talk to slave: Invalid argument
Hat wer eine Idee was da falsch läuft? Warum "invalid argument"? Und
warum funktioniert nicht mal i2cdetect?
Vielen Dank,
Reto
Reto H. schrieb:> Mein Bus ist der i2c-0, soweit alles ok. Doch wenn ich> i2cdetect i2c-0> ausführe erhalte ich> Error: I2C bus name doesn't match any bus present!>
in deinem Fall muss es heissen:
1
i2cdetect 0
Reto H. schrieb:> Dies bricht ab mit> Failed to acquire bus access and/or talk to slave: Invalid argument
Ich tippe mal, dass deine Slave-Adresse nicht stimmt. Du musst die
eintragen, die du mit i2cdetect ermittelst...
Grundsätzliches zu I2C (unter Linux) mal hier auf dieser Seite:
http://bralug.de/wiki/BLIT2008-Board_mit_i2c-tiny-usb-Firmware
Grüße Uwe
Nur stimmen die Adressen nicht mit dem überein was ich erwartet hätte.
Ich weiss von devices an den Adressen 49, 4a, 4b und 51... Hm... und was
bedeutet UU?
Na gut, ein weiterer Leseversuch von Adresse 0x91 und 0xA5 aber immer
noch der selbe Fehler: "invalid argument". Doch welches? Am "int addr"
wird es wohl nicht liegen, oder? Ist mit meinem "file" etwas nicht in
Ordnung? Oder ein falches include, sodass "I2C_SLAVE" nicht stimmt? Habe
"i2c-dev.h" includiert.
Hat wer ne weitere Idee? Danke!
Hm, mir fällt gerade auf die mit UU sind genau die Adressen, die über
einen Treiber laufen: 49, 4a, 4b und 51...
Und im Code steht UU bedeutet EBUSY. Sind die wohl mit dem Treiber
beschäftigt und so kann ich nicht gleichzeitig darauf zugreifen?
Aber auf die anderen, z.B. 0x91 oder 0xA5 sollte ich doch problemlos
zugreifen können?
Als ich das letzte Mal mit I²C Adressen gearbeitet habe, waren die 7
Bits lang. Dazu kommt ein R/W Bit. Der Wert 0x93 sieht eher nicht wie
eine gültige Adresse aus - zu viele Bits.
Jim Meba schrieb:> Und im Code steht UU bedeutet EBUSY. Sind die wohl mit dem Treiber> beschäftigt und so kann ich nicht gleichzeitig darauf zugreifen?>
wie du richtig erkannt hast, mit UU werden die Devices gekennzeichnet,
die zwar erkannt werden, aber bereits durch etwas anderes benutzt
werden. Ich vermute mal, dass das Kernelmodul lm75 am laufen ist. Dieses
müsstest du entladen (rmmod lm75).
Jim Meba schrieb:> Als ich das letzte Mal mit I²C Adressen gearbeitet habe, waren die 7> Bits lang. Dazu kommt ein R/W Bit. Der Wert 0x93 sieht eher nicht wie> eine gültige Adresse aus - zu viele Bits.>
korrekt, es muss die 7-Bit-Adresse, ohne dem R/W-Bit angegeben werden.
Also, wie ich eingangs schon geschrieben hatte, so wie es i2cdetect
anzeigt. In deinem Fall also 0x49, 0x4a usw.. Ob das R/W-Bit gesetzt
wird, wird intern entschieden, je nach dem ob mit read() oder write()
(oder z.B. auch i2cget, i2cset aus den i2c-Tools) zugegriffen wird.
Darum musst du dich nicht kümmern. Mit der richtigen Adresse sollte dein
Codeschnipsel funktionieren...
Grüße Uwe
Eine eigene Frage?
Dieser Thread ist über 14 Jahre alt.
Stell sie in einem eigenen Thread – dort lesen mehr Leute mit, und sie wird öfter und schneller beantwortet.