Moin, ich habe eine Problem für das ich bis jetzt keine Lösung gefunden habe. Ich habe ein System mit 10 I2C Bussen an denen verschiedene Erweiterungskarten hängen können. Gesteuert werden alle Busse über ein Phytec Modul mit einem 8051 Controller. Mein Problem sind jetzt die Ansteuerroutinen für die einzelnen Busse. Ich möchte nur eine Routine haben, die per Paramter übergeben bekommt, welchen Bus sie ansprechen soll. So in etwa: "send_Ack(Busnumber); Nur leider weiß ich jetzt nicht, wie ich eine effiziente "Übersetzung" von Busnumber in den entsprechenden Pin machen kann. Die bisherige Lösung macht das einfach über if-Abfragen- was allerdings alles andere als schnell ist. Kann ich in C irgnedwie direkt auf die Pin-Adressen zugreifen und so das Problem mit einer einfachen Rechnung/Tabelle lösen oder muß ich eine Routine für jeden Bus schreiben, damit die Verarbeitung schneller wird? MfG Mike
was bringt dir so ein system? ist doch nicht wirklich sinn eines Buses alles extra zu hängen...
Der I2C-Bus ist dafür gedacht, dass mehrere Devices gleichzeitig auf EINEM Bus hängen können... das Devices reagieren dann darauf, dass seine Nummer auf dem Bus angefragt wird. Wichtig ist nur, dass die Gesamtkapazität der Leitung einen gewissen Grenzwert (glaube das waren 400pF) nicht überschreitet.
Die Hardware stammt leider nicht von mir. Der ursprüngliche Gedanke ist, daß es möglich ist verschiedene Karten anzuschließen und jederzeit tauschen zu können. Hierbei soll es egal sein, wo die Karten angeschlossen werden und auch was auf den Karten realisiert ist. Es soll auch möglich sein 2 gleiche Karten einzustecken, ohne das irgend etwas daran geändert werden muß. Die einzelnen Busse sind einfach dazu da, das ganze sauber zu trennen und auf den Karten können dann auch noch beliebig viele I2C Bausteine an dem entsprechenden Bus hängen
Man kann zuerst mal alle SCL zusammenfassen, denn ohne Start/Stop auf SDA interessiert sich kein Slave dafür, was auf SCL passiert. Und dann 8 * SDA auf einem Port zusammen fassen, dann kann man die jeweilige SDA-Leitung per Maskenbyte auswählen: Maske = 0x01: SDA0 Maske = 0x80: SDA7 Z.B. für Port P1: SDA = 1: P1 |= Maske; SDA = 0: P1 &= ~Maske; if SDA == 1: if(P1 & Maske) Peter
@Peter: danke, das das was ich gesucht habe. Funktioniert auch, ist aber leider immer noch zu langsam. Aber ich fürchte das liegt eher an der Hardware. Das Phytec mit 12 Mhz Quarz schafft es einfach nicht 7 I2C Kommandos (jeweils 3Byte) innerhalb von 1 ms zu verschicken. Mike
"Das Phytec mit 12 Mhz Quarz schafft es einfach nicht 7 I2C Kommandos (jeweils 3Byte) innerhalb von 1 ms zu verschicken." Das geht prinzipiell nicht ! I2C ist für viele I2C-Bausteine auf 100kHz begrenzt. D.h. 10 7 3 * 10µs = 2,1ms reine Transferrate ohne jeden Softwareoverhead. Und je nach Leitungslänge sind nichtmal die 100kHz drin. Man muß immer vor der Busauswahl ermitteln, ob die benötigte Transferrate überhaupt möglich ist. Und es ist nicht verkehrt, wenn dabei noch reichlich Reserven drin sind (10-fach). Peter
Das wollte ich eigentlich damit sagen. Allerdings brauchten die vorhandenen Rouitinen 120 ms für die Übertragung. Und das war doc hetwas sehr viel. Mike
Es kommt drauf an, was Du noch alles so machst. Die Datenmengen müssen ja irgendwie aufbereitet / ausgewertet werden. Der reine I2C-Transfer sollte aber innerhalb 10ms zu packen sein, also z.B. aus einem SRAM-Puffer ausgeben. Peter
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
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.