I2C-Kommunikation schlägt fehl

Hallo allerseits!

I²C ist ja eine schöne Sache – echt klasse wär‘s, wenn es funktionieren würde. Aber egal, was ich anstelle, ich bekomme die Kommunikation mit dem SAA 1064 (7-Segment-Anzeigen-Treiber für 4 Ziffern mit I²C) nicht hin.

An den Pull-Up-Widerständen kann’s nicht liegen, denn die sind da, wo sie hin gehören (nein, darauf falle ich so schnell nicht noch einmal herein!).

Im Datenblatt zum SAA 1064 (siehe Datenblatt) ist beschrieben, wie eine Kommunikation ablaufen muss, aber ich bekomme das einfach nicht hin.

Jede Hilfe ist hochwillkommen!

Gregor

Ein Foto des Steckbretts gibt es hier
Der momentan nicht funktionierende Sketch:

#include <Wire.h>

// SAA 1064 Test

// Der SAA 1064 ist ein Vier-Sieben-Segment-Anzeigen-Treiber
// mit I2C



byte SAA_addr=0x70; // Adresse zum Lesen


void setup()
{
  Serial.begin(9600); // Serielle Schnittstelle initialisieren
  Serial.println("[setup()] Beginne ...");
  Wire.begin(); // Arduino ist Master
}

void loop()
{
  Serial.print  ("[loop()] SAA_addr ist ");
  Serial.println(SAA_addr);
  Serial.print  ("[loop()] Beginne Kommunikation ... ");
  Serial.println("Wire.beginTransmission(SAA_addr)");

  Wire.beginTransmission(SAA_addr);
  //Wire.write(SAA_addr); // Adresse
  //Wire.endTransmission();
  
  //Wire.beginTransmission(SAA_addr);
  Wire.write(B00000000); // Instruction Byte (control register);
  Wire.write(B01101111); // Control Byte: 7 = don't care
                         //               6 = add 12 mA to segment output current
                         //               5 = add  6 mA to segment output current
                         //               4 = add  3 mA to segment output current
                         //               3 = all segments switched on for test
                         //               2 = digits 2+4 are blanked/not blanked
                         //               1 = digits 1+3 are blanked/not blanked
                         //               0 = 1 (dynamic mode [use digits 1,2,3,4])
  Wire.write(0x11); // Data digit 1
  Wire.write(0x22); // Data digit 2
  Wire.write(0x33); // Data digit 3
  Wire.write(0x44); // Data digit 4
  Wire.endTransmission();

  Serial.println();
  delay(1000);
}

A0 und A1 Eingänge korrekt beschaltet damit die Adresse stimmt?

Das ist etwas seltsam. Im Pinout ist da Pin 1 ADR, aber dann gibt es im Protokoll 2 Adress-Bits. Dann müsste es doch auch zwei Pins geben?

Nachtrag. Ah, ich sehe es wird mit der Spannung bestimmt. Das ist mal was neues. Low, sollte dann aber korrekt 0 sein.

Ja, da mir I2C noch ziemlich neu ist, habe ich mir einen Merkzettel an meinen Switch geklebt: A4=SDA, A5=SCL.

Alles ordentlich mit 4k7-Pull-ups, doppelt gecheckt.

Was ich bereits probiert habe, ist teilweise auch am auskommentierten Code zu sehen. Wenn Du das Foto anguckst: Die obere Schaltung ist eine Uhr mit DS1307, dort hatte ich auch Probleme, hab’s dann aber mit hängen und würgen zu Fuß hinbekommen. Nur bei diesem doofen SAA1064 klappt einfach gar nichts.

Gruß

Gregor

Was hälst Du von byte SAA_addr=0x38; So weit ich weiß, zählt das Read/Write-Bit nicht mit, oder?

Mal den i2c adress scanner laufen lassen

Was mir etwas seltsam vorkommt ist die Multiplexer-Schaltung.

Laut dem hier:
https://developer.mbed.org/users/wim/notebook/saa1064-i2c-7-segment-led-driver/

Sind da keine Widerstände drin. Und ein Transistor scheint nicht vollständig beschaltet zu sein. Man sieht es aber schlecht.

Gibt sicherlich auch irgendwo eine fertige Lib. Die in dem Link ist aber nicht für den Arduino. Die hier schon:

agmue:
Was hälst Du von byte SAA_addr=0x38; So weit ich weiß, zählt das Read/Write-Bit nicht mit, oder?

Ich habe soeben noch einen Scan hochgeladen: Wie’s zu laufen hätte

Dort steht, dass die Adresse 0x70 ist.

Gruß

Gregor

Den I2C-Scanner mitlaufen zu lassen ist eine gute Idee. Muss nur noch ein Steckbrett frei räumen ...

Serenifly:
Was mir etwas seltsam vorkommt ist die Multiplexer-Schaltung.
... laut ...
Sind da keine Widerstände drin. Und ein Transistor scheint nicht vollständig beschaltet zu sein. Man sieht es aber schlecht.

Da gibt es auch eine fertige Lib. Dann siehst du ob es am Code liegt.

Ups! Fertige Lib?! Wo?! Was?! Gebt mir bitte drei Minuten ...

gregorss:
Dort steht, dass die Adresse 0x70 ist.

Genau auf diese Seite schaue ich und lese "valid addresses HEX 70, 72, 74 and 76 for writing and 71, 73, 75 and 77 for reading". Ungewöhnlich ist eine unterschiedliche Adresse für Lesen und Schreiben. Ich meine, Wire ergänzt das entsprechende Bit selbstständig. Kann mich irren. Der Scanner wird es zeigen.

agmue:
Genau auf diese Seite schaue ich und lese “valid addresses HEX 70, 72, 74 and 76 for writing and 71, 73, 75 and 77 for reading”. Ungewöhnlich ist eine unterschiedliche Adresse für Lesen und Schreiben. Ich meine, Wire ergänzt das entsprechende Bit selbstständig. Kann mich irren. Der Scanner wird es zeigen.

Okay. Bitte gib mir ein/zwei Stunden. Essen muss sein, Steckbrett freiräumen auch. Sobald ich den Scanner probiert habe, bin ich wieder zurück.

Seufz …

Gregor

Der Scanner liest aber und schaut ob was empfangen wird. Dadurch kann das verwirren!

Also die Lib die ich gefunden habe macht das:

SAA1064::_init( void ) {

  _i2cAddress = 0x70 >> 1; // shifted, due to pin 1 is grounded (VEE) -> 0x70

...
}

Also wenn man eigentlich 0x70 hat wird auf 0x38 geschrieben. Dann hattest du recht :slight_smile:

Nochmal. Arduino Lib hier:

Hier gibt es auch Code:

Sendet auch auf 0x70 >> 1

Und überprüfe wie gesagt mal deine Multiplexer Transistoren

gregorss:
Okay. Bitte gib mir ein/zwei Stunden. Essen muss sein, Steckbrett freiräumen auch.

Nur die Ruhe, ich gehe jetzt sowieso schlafen.

Serenifly:
Also wenn man eigentlich 0x70 hat wird auf 0x38 geschrieben. Dann hattest du recht :slight_smile:

Das beschert süße Träume ... gute Nacht! :sleeping:

Sodele ...

agmue:
Genau auf diese Seite schaue ich und lese "valid addresses HEX 70, 72, 74 and 76 for writing and 71, 73, 75 and 77 for reading". Ungewöhnlich ist eine unterschiedliche Adresse für Lesen und Schreiben. Ich meine, Wire ergänzt das entsprechende Bit selbstständig. Kann mich irren. Der Scanner wird es zeigen.

Die Verbindungen habe ich soeben noch einmal überprüft, da stimmt alles. Die Widerstände am Multiplexer-Transistor (dem „unteren“ im o. g. Foto) habe ich durch Drahtbrücken ersetzt (ich dachte, das sei nur ein Prinzipschaltbild und habe daher zuerst die Widerstände eingesetzt).

Den I²C-Scanner konnte ich auf die Schnelle mit einem freien UNO realisieren. Seltsam finde ich die Ausgabe

...
133411  53      0x35            .       .       .       .       .       .       .
133414  54      0x36            .       .       .       .       .       .       .
133416  55      0x37            .       .       .       .       .       .       .
133420  56      0x38            V       V       .       .       .       .       .
133422  57      0x39            .       .       .       .       .       .       .
133425  58      0x3A            .       .       .       .       .       .       .
133428  59      0x3B            .       .       .       .       .       .       .
...

des Scanners. Aber nach dem, was Du noch geschrieben hattest, erscheint das nicht vollkommen daneben zu sein. Aber egal, ob ich für die Adresse 0x70, 0x71 oder 0x38 angebe: Es tut sich nichts.

Naja ... Du gehst in die Falle, dann mache ich das wohl auch besser. Ich hoffe, ich finde noch den Punkt, an dem es schiefläuft. Wenn nicht ... bis morgen!

Gregor

Mit der SAA1064-Lib sieht‘s jetzt gut aus. Ich bekomme zwar halbwegs wirre 7-Segment-Anzeigen, aber die Segmente den richtigen Pins zuzuordnen und/oder schlechte Kontakte zu beseitigen dürfte kein Problem sein.

Danke für die Hilfe!!! Nachdem ich das mit der DS1307-Uhr hinbekommen hatte, dachte ich, dass das ja nicht mehr sooo schwer sein kann, aber der Teufel steckt da wohl ziemlich tief im Detail :-/

Gruß

Gregor