Hallo Freunde ! Ich möchte mal um Unterstützung bitten. Seit Tagen bemühe ich mich, um ein Schreib-/Lesezugriff vom ATmega zum I2C Speicher hinzubekommen. Es misslingt mir aber nur....Habe bislang nach dem Buch: "AVR Mikrocontroller Programmierung in C" von Heimo Gaicher probiert... Nun habe ich ein Tutorial das im Internet vorgestellt wurde versucht, auch wieder ohne Erfolg. :(( Das "AT24C64 Modul" (Steckbrett) habe ich auf Funktion mittels Arduino getestet, da geht es. Ich habe den Code(Main-,Headerdatei usw.) gezipt und auf meinen Webspace gelegt. http://oderlachs.de/code/AVR/I2C_Demo.zip Vielleicht kann wer bitte drüber schauen. Das ich in der Main eine c- und nicht die h-Datei includiere, hat den Grund das ich mit Geany unter Linux arbeite. Gruss und Dank Gerhard Nachtrag : schon der Aufruf ret = i2c_start(Dev24C02+1); in main bringt alle LEDs , also Fehler ..aber warum ???
:
Bearbeitet durch User
Gerhard H. schrieb: > Vielleicht kann wer bitte drüber schauen. Warum hast du die I2C Adresse geändert ?
1 | #define Dev24C02 0xA0 // device address of EEPROM 24C02, see datasheet
|
Und die SCL und SDA pins (und PORT), CPU_FREQ entsprechend angepasst ? P.S. Um nutzlosen Diskussionen vorzubeugen, Bild anbei.
:
Bearbeitet durch User
Hallo Marc ! Die I2C Addr vom AT24C64 ist 0x50....lt Datenblatt und lt I2C Scanner. Mit dieser Ardresse kann ich den EEprom auch mittels Arduino beschreiben/auslesen. Beim Atmega32 habe ich PortC.0 als SCL und PortC.1 als SDA verbunden. Das habe ich nach dem Pinout im Datenblatt Atmega32. bei Ltg sind per 7k5 Widerstände gegen +5V (Ub) gelegt. Ich arbeite mit dem STK500 von ATMEL. Gruss und Dank Gerhard Ich kann natürlich auch mal was falsch lesen....dank der guten schlechten Augen ;)...Will hier keinem was widerlegen !
:
Bearbeitet durch User
Gerhard H. schrieb: > Die I2C Addr vom AT24C64 ist 0x50....lt Datenblatt und lt I2C Scanner. Nein. Das ist wahrscheinlich bei Arduino so, weil er die Adresse nach links schiebt. Ich glaube, dass die Fleury-library nicht nach links schiebt. Probiere es doch mit 0xA0.
Marc V. schrieb: > Ich glaube, dass die Fleury-library nicht nach links schiebt. So isses. Für ein EEPROM wäre 0xA0 oder eben 0xA1 richtig.
Habt erst mal vielen, vielen herzlichen Dank, die Addr 0xA0 geht dann erst mal , jedenfalls sind die Fehler-LEDs aus, nach den dem I2C Start Aufruf... Nun ja, es sind mal wieder gewisse Anfängerfallen in die ich da trete. Werde mal berichten wie ich das Problem I2C-EEprom weiter in den Griff bekomme...oder auch nicht ;) Ich arbeite auch ungern so mit was "fremden Code", wenn ich nicht genau weiss was da geschieht. Die Druckfehlerteufel sind ja auch bei sogenannten Fachbücher eine grosse Plage....ein falsch gedrucktes Zeichen kann da schon ne Menge bewirken. Gruss und Dank Gerhard
Der Admin mag mir verzeihen, das ich neu Schreiben, aber beim Editieren, habe ich immer Probleme... Also heute konnte ich Dank Regenwetter und darum "Gartenfrei" hatte, ein neues Progrämmchen für I2C Verbindung schreiben. Ich habe mich da sehr an das Beispiel aus dem oben genannten Buch gehalten. http://oderlachs.de/code/AVR/Neu_TWI.zip Ich glaube das dies ja auch so funktioniert, aber das weitaus grössere Problem für mich ist die Kommunikation/Protokollablauf mit dem EEprom. Ich dachte das man ja da von Speicherstelle 0...bis Ende einfach draufschreiben kann.... Beim Lesen desselben kann man wohl von Speicherstelle 0 kontinuierlich weiter Auslesen kann. Doch dieses hier : http://oderlachs.de/code/AVR/EEProm_I2C AT_24C64.pdf beweist mir aber was anderes. Nun schau ich erst mal da wie Ochs in Uhrwerk auf den ersten Blick Vielleicht hat ja ein netter User hier bitte für mich ein wenig Starthilfe, damit ich in die Gedankengänge komme ?? Gruss und Dank Gerhard
Gerhard H. schrieb: > Ich dachte das man ja da von Speicherstelle 0...bis Ende einfach > draufschreiben kann.... Kann man auch, dauert aber länger. Und - ein EEPROM ist kein Ersatz für RAM, sondern eben ein nichtflüchtiger Speicher, der bei jedem Schreiben (und da muss man sich drüber klar werden) ein wenig 'abgenutzt' wird. Das ist bei 1.000 oder 10.000 Schreibvorgängen noch kein Problem, aber bei etwa 1.000.000 Schreibvorgängen auf eine Zelle dann doch. Deswegen möchten die meisten Leute gar nicht hunderte von Zellen am Stück beschreiben, sondern nur die, die wirklich übers Ausschalten hinweg gespeichert werden müssen und das sind im Allgemeinen sehr wenige.
Nun ja, das mit der "Haltbarkeit" ist mir bekannt. Mir geht es darum ein etwa halbes Jahr dort Klimadaten zu speichern. Diese sollen dann später ausgelesen werden können..da dachte ich mir solch ein Chip wäre da das "Beste" . Er wird alle 24h einmal beschrieben...vielleicht auch alle 12h aber das sollt auch in ca 6 Monaten noch nicht an die Haltbarkeitsgrenze gelangen. Ich lasse mich aber gern des Besseren belehren ! Für mich ist diese Hardwareverwendung noch Neuland. Auch ist es Hobbyprojekt, muss also nicht all zu sehr sicherheitsrelevant sein. Wenn ich das Datenblatt so richtig verstanden habe müsste ein solcher stilisierter Programmablauf möglich sein:
1 | /*
|
2 | *
|
3 | * Ablauf Kommunikation mit I2C Speicher AT24C64
|
4 | *
|
5 | *
|
6 | *
|
7 | * lt. Figure 2. Byte Write S.11 Datasheet
|
8 | */
|
9 | |
10 | TWI_Start(); |
11 | |
12 | MaWriteACK( DEV_ADDR_WR ); // Master write Device-Adresse to Slave, wartet auf ACK vom Slave |
13 | |
14 | MaWriteACK( PageADDR_MSB ); // Master write MSB-Page-Adresse to Slave, wartet auf ACK vom Slave |
15 | |
16 | MaWriteACK( PageADDR_LSB ); // Master write LSB-Page-Adresse to Slave, wartet auf ACK vom Slave |
17 | |
18 | MaWriteACK( Data_1 ); // Master write Datenbyte 1 to Slave, wartet auf ACK vom Slave |
19 | |
20 | MaWriteACK( Data_2 ); // Master write Datenbyte 2 to Slave, wartet auf ACK vom Slave |
21 | .......
|
22 | .......
|
23 | MaWriteACK( Data_n ); // Master write Datenbyte n to Slave, wartet auf ACK vom Slave |
24 | |
25 | TWI_Stop(); |
26 | |
27 | |
28 | /**********************
|
29 | /
|
30 | / ein TWI_RE_START() wo, noch nicht ganz begriffen ????
|
31 | /
|
32 | /**********************/
|
Gerhard
:
Bearbeitet durch User
Gerhard H. schrieb: > ein TWI_RE_START() wo, noch nicht ganz begriffen ???? Das ist eine Eigenart des EEPROM. Du startest normal mit einem TWI Write auf die Schreibadresse (0xA0), um den Adresszähler des EEPROM einzustellen. Nun kommt der TWI Restart mit EEPROM Adresse 0xA1, um dann das Datum zu lesen. Der Restart wird also nur gebraucht, um Daten vom EEPROM zu lesen und nicht für den Schreibvorgang. Wenn du dirs einfach machen willst, Peter Fleury hat in seinen I²C Bibliotheken ein Beispiel fürs EEPROM und auch sonst ist die Bibliothek recht pflegeleicht.
>Ich dachte das man ja da von Speicherstelle 0...bis Ende einfach >draufschreiben kann.... Nur innerhalb einer Page kann man mehrere Bytes auf einmal schreiben. Wenn die Page z.B. 32Byte hat, du aber 33Bytes sendest gibt es ein Rollover der Page und Byte33 landet am Anfang der Page und nicht in der nächsten Page. Wenn du zwei Byte sendest und das erste auf Adresse 31 der Page liegt bekommst du auch ein Rollover der Page. Du musst also immer darauf achten dass ein Page Schreibzugriff nicht über eine Pagegrenze drüber geht.
Gerhard H. schrieb: > / ein TWI_RE_START() wo, noch nicht ganz begriffen ???? Matthias S. hat es dir schon erklärt aber hier noch einmal:
1 | /* Random read (beliebige Adresse) */
|
2 | TWI_Start(); |
3 | MaWriteACK( DEV_ADDR_WR ); // Master sendet Device-Adresse+WR to Slave, wartet auf ACK vom Slave |
4 | MaWriteACK( PageADDR_MSB ); // Master write MSB-Page-Adresse to Slave, wartet auf ACK vom Slave |
5 | MaWriteACK( PageADDR_LSB ); // Master write LSB-Page-Adresse to Slave, wartet auf ACK vom Slave |
6 | |
7 | /* Jetzt kommt repeated start, um auf lesen umzuschalten */
|
8 | TWI_Start(); |
9 | MaReadACK( DEV_ADDR_RD ); // Master sendet Device-Adresse+RD to Slave, wartet auf ACK vom Slave |
10 | |
11 | /* Jetzt werden (als Beispiel) 3 Bytes eingelesen */
|
12 | x = MaReadByteAck(); |
13 | y = MaReadByteAck(); |
14 | z = MaReadByteNack(); |
15 | TWI_STOP(); |
Falls du jetzt wieder Start und DEV_ADR_RD sendest, wird aus der Adresse 3 gelesen (unter der Voraussetzung, dass PageADDR_LSB und PageADDR_MSB Null waren.
Hi Nachdem Du mit Schreiben oder Lesen fertig bist, kannst Du mit TWI_STOP() den Bus frei geben (ein anderer Master könnte sich jetzt den Bus schnappen), oder per TWI_Re_Start() direkt eine neue Anfrage senden - da kann kein anderer Master 'reinquatschen', da der Bus ja noch belegt ist und zwischendrin nicht freigegeben wurde. ... wobei ein START und ein RE_START genau die selbe Funktionalität haben - kann aber sein, daß hier ein START nicht geht oder einen Fehler auswirft. Wenn ich Dich richtig verstanden habe, willst Du Sensordaten über Monate aufzeichnen - so weit, (wohl) kein Problem. Dann liegen zwischen den Schreibzugriffen aber 'Welten' an µC-Zeit - Theoretisch sollte der Bus aber die ganze Zeit 'Dir' gehören, wenn Du Diesen nicht frei gibst. Wenn aber auch noch von 'wo Anders' auf den Bus zugegriffen werden soll (Multi-Master), wäre es sinniger, den Bus wieder frei zu geben und nur 'anzufordern', wenn Du Daten zum Wegschreiben hast oder Daten lesen willst. Habe selber aber bisher nur I2C-Displays beschrieben, also nicht wirklich viel Erfahrung und 'nur' Alles selbst zusammen gereimt. MfG Edit holger schrieb: >Wenn die Page z.B. 32Byte hat, du aber 33Bytes sendest gibt es ein >Rollover der Page und Byte33 landet am Anfang der Page und nicht in der >nächsten Page. Wenn du zwei Byte sendest und das erste auf Adresse 31 >der Page liegt bekommst du auch ein Rollover der Page. Werden dann die vorderen Bytes teilweise überschrieben? Da - meines Verständnis nach - erst geleert werden müssen (aber auf 1 geschrieben werden) und beim Beschreiben 'nur' auf Null geändert werden - sollte ich im Schlimmsten Fall später nur noch Nullen im EEprom lesen können, oder? Danke
:
Bearbeitet durch User
>Werden dann die vorderen Bytes teilweise überschrieben?
Ja, die werden überschrieben.
>Da - meines Verständnis nach - erst geleert werden müssen (aber auf 1 >geschrieben werden) und beim Beschreiben 'nur' auf Null geändert werden >- sollte ich im Schlimmsten Fall später nur noch Nullen im EEprom lesen >können, oder? Nein, da wird nichts geleert. Geschrieben wird erstmal nur in den Pagebuffer. Und der Pagebuffer wird erst nach I2C-Stop ins EEPROM geschrieben. Es stehen später nicht nur Nullen im EEPROM drin.
Hallo Freunde ! Ich möchte erst mal denen einen grossen Dank zollen(!!!), die mir das nun wohl auch für mich begreifend erklärt haben. Ich denke schon, das ich damit erst mal etwas weiter komme, freu. Ja ich habe so eigenständig noch nie was mit I2C gemacht, nun per Arduino, da gibst ja Libs/Exemples ohne Ende. Für einen Atmega8 mal was in Bascom, aber das ist was anderes, auch schon fast vorgefertigtes. Gut, es gibt vieles von P.Fleury, aber ich habe damit auch meine Probleme gehabt es zu begreifen, anzuwenden. Ich glaube auch mein grösster Mangel ist, dass ich kaum English kann, auch keinen Gusto mehr aufs Erlernen habe, weil mir das im Alter auch sehr schwer fällt. Ich werde über Erfolg und Niederlage berichten..... Gruss und Dank Gerhard
In diesem Fall wäre vielleicht ein SPI-EEPROM wie 25LC256 bzw. 25LC1024 praktischer gewesen. Ich zumindest arbeite lieber mit SPI als mit I2C, wenn es Pin- und Leitungsanzahl irgendwie hergeben.
PS: vielleicht hätten auch die 4 KiB EEPROM eines ATmega1284 für die rund 400 Messungen gereicht.
Ja bestimmt hätte das gereicht, aber ich habe zwei Gründe für meine Variante: 1. Verwendung von Bauteilen aus der Bauteilkiste 2. ist der EEprom auf einer steckbaren Lpl. , kann abgezogen und daheim ausgewertet werden. Gerhard
Gerhard H. schrieb: > Gut, es gibt vieles von P.Fleury, aber ich habe damit auch meine > Probleme gehabt es zu begreifen, anzuwenden. Man muss bei der Fleury Lib eigentlich nur verstehen, das es eine Variante für das Hardware TWI Interface gibt und eine für Soft-TWI. Wenn man 'twimaster.S' kompiliert, ist das die Soft-TWI Variante, die auf jedem AVR läuft, man muss dann aber auch in 'twimaster.S' die benutzten Pins deklarieren. Wenn man stattdessen 'twimaster.c' ins Projekt einfügt, muss man auch die Pins benutzen, die der AVR für TWI reserviert hat, da nun die TWI Hardware des AVR benutzt wird.
Danke Matthias ! Es ist ja noch kein Meister vom Himmel gefallen, vieleicht schaffe ich ja noch die "Gesellenprüfung". ;) Ich weiss ja Dank der vielen Infos, die hier kamen, nun ne ganze Menge mehr . Gruss & Dank Gerhard
Hallo ! Ich kann erst mal "voller Stolz" berichten, dass eine Porterweiterung mit I2C Chip PCF8574 wunderbar klappt, dann werde ich das andere auch noch schaffen. Euch allen nochmals vielen herzlichen Dank für Eure Hilfe. Gruss Gerhard
Hallo Freunde ! Ich glaube ich muss nochmals um Hilfe bitten. Noch nicht so ganz will es mir gelingen, den Eeprom per I2C zu beschreiben/auszulesen. Ich habe jetzt einen AT24C04 verwendet und den Programmablauf nach oben von Euch gezeigten Ablauf geschrieben . Mein Code hier als zip : http://oderlachs.de/code/AVR/TWI_Eeprom.zip Am PortA liegen 8 LED zur binären Anzeige des gelesenen Bytes. Am PortB liegen die 7 Error-LEDs . Da die LEDs gegen +Ub liegen wird mit 0(GND) auf ON geschaltet. Ein Fehler wird mir nicht angezeigt, nur ist die Byte-Anzeige PortA immer dieselbe "01011000", egal welches Byte ich schreibe. Vielleicht habe ich was übersehen, mein Code sollte selbsterklärend an Hand der Kommentare sein. Vielleicht kann ja wer mal BITTE drüberschauen. Gruss und Dank Gerhard
Gerhard H. schrieb: > Ich habe jetzt einen AT24C04 verwendet Die kleinen werden aber anders adressiert. Da sind die oberen Bits mit in der I2C-Adresse verwurstet. Gerhard H. schrieb: > Mein Code hier als zip Was stört Dich am Dateianhang?
Hallo Peter ! Dateianhang, na ich möchte nicht das Forum hier mit Codeanhang vollmüllen, zum Anderen kann ich per FTP schnell mal aktualisieren auf meinem Webspace. Ich lesen gerade im Datenblatt, aber so richtig habe ich es noch nicht "gefressen" mir Adressierung & Speicherzelle(Schreiben/Lesen). Ist auch für mich ein Erstlingswerk auf dieser Ebene. Gruss Gerhard
Hallo Freunde ! Nun habe ich ein Tutorial im web gefunden , was auch bei mir geht ! :=) http://www.circuitstoday.com/use-external-eeprom-avr-atmega32 Ich weiss noch nicht was ich bei mir immer falsch hatte, ich werde mal den Code der einzelen Funktionen/Routinen vergleichen. Damit hat sich das Problem erst mal"sozusagen erledigt" freu, anhand des Sourcecodes werde ich dann auch verstehen wie es gehandelt wird beim I2C-EEprom. Vor allem ist es mir ja wichtig herrauszubekommen, was trotz der vielen versch. Anleitungen und Tutus falsch war. Gruss und Dank Gerhard
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.