PDA

Archiv verlassen und diese Seite im Standarddesign anzeigen : 24C64 (A) will nicht!?



BASTIUniversal
01.02.2006, 15:42
Hallo!
Nachdem ich jetzt einiges probiert hab (und auch im Forum gesucht habe) und trotzdem nicht weiter komme frag ich euch jetzt doch mal...:
Ich hab mir ein kleines Board für den Mega48 entworfen, unteranderem mit einem 24C64 darauf, um auch mal über längere Zeit Daten aufzuzeichnen.
Zum Testen des EEPROM's hab ich nun mal nach vielen eigenen Versuchen das Beispiel aus RN-Wissen auf meinen Controller angepasst und draufgespielt. Die Werte sende ich an meinen PC.

Wenn ich das Programm nun laufen lasse bekomme ich als gelesenen Wert nur 255 zurück (wenn ich die SDA-Brücke trenne bekomme ich 0)!
An der Hardware liegt es wahrscheinlich nicht, ich hab den 24C64 schon gegen einen anderen ausgetauscht. Die Pullups an SDA und SCL sind vorhanden (10k), ich hab dem ROM sogar nen 100nF Kondensator verpasst! Die Adressleitungen liegen alle auf GND, daraus müsste sich die Adresse &B10100000 zum schreiben und &B10100001 zum lesen ergeben. Write Protect (WP) liegt auch auf GND, müsste somit also aus sein.
Der Mega48 läuft mit 16MHz und 5V...alles durch viele 100n und einen 470µF Elko "abgesichert". SDA und SCL sind auf den Ports C4 und 5, mit I2CDelay hab ich auch schon rumprobiert...auch nix!

Woran kann das liegen?
Ich hab die Bascom Demo 1.11.8.1 drauf, der Code steht hier: https://www.roboternetz.de/wissen/index.php/Bascom_und_I2C_EEprom

Danke für eure Hilfe die Ihr mir immer gebt O:)

Ruppi
01.02.2006, 16:06
Hallo!
Ich würde sagen - fast richtig. Du hast zum Einen die Adressen für's Lesen bzw. Schreiben vertauscht und zum Anderen musst Du bedenken, dass Du ein Eeprom mit einem größeren Speicherbereich hast, als das im Beispiel. Das bedeutet, dass Du eine 16bit Adresse übergeben musst, also 2 Bytes. Dann sollte es gehen... Den Elko sowie den 100nF kannst Du getrost weglassen, das geht auch so.

Gruß, Ruppi

BASTIUniversal
01.02.2006, 16:39
Hallo!
Vielen Dank für die Hilfe...!
Die Adressen waren korrekt, aber die 16Bit Adressen hab ich übersehen.
Wegen diesen Adressen hab ich nochmal Tut. und Datenblatt durchgelesen, und mir ist aufgefallen, dass laut Datenblatt zuerst das Adresss MSB dann LSB gesendet wird. Im Tutorial kommt allerdings zuerst die Adresse_Low dann Adresse_High!?
Ist das so OK?

MfG

Ruppi
01.02.2006, 16:47
Hatte das mit den Slave-Adressen anderes in Erinnerung, bist Du sicher?? Bei der Adresse für den Speicherbereich muss erst das MSB übertragen werden!

Ruppi

BASTIUniversal
01.02.2006, 17:12
Naja, ich kann mir da nicht unsicher sein...so wie ich die Adressen oben aufgeschrieben hab funktionierts!
Im Datenblatt steht bei "Byte Write" folgendes: "Following the START condition from the master, the control code (four bits), the chip select (three bits), and the R/W bit (which is a logic low)..."

Zu den Kondensatoren: Die sind schon drauf und wieder runter mach ich se nimmer [-(

Danke nochmals!

Rage_Empire
02.02.2006, 07:33
Vieleicht kann da dir geholfen werden:

https://www.roboternetz.de/phpBB2/zeigebeitrag.php?t=15661&highlight=


Ansonsten.....

$lib "i2c_TWI.lib"
Config Scl = Portc.0 'PINs für I2C Bus
Config Sda = Portc.1
I2cinit

Config Twi = 400000

Dim Eehead(2) As Byte
Dim Eebyte(4) As Byte
Dim Eesingle As Single At Eebyte Overlay
Dim Eeword(2) As Word At Eesingle Overlay
Dim Eebanz As Byte
Dim Ee_adresse01 As Word At Eehead Overlay
Dim Eead As Word

Const 24c64w = &B10100000
Const 24c64r = &B10100001


'Definition der Funktionen ++++++++++++++++++++++++++++++++++++++++++++++++++ ++
Declare Function Loadbyte(byval Ee_adresse As Word) As Byte
Declare Function Loadword(byval Ee_adresse As Word) As Word
Declare Function Loadsingle(byval Ee_adresse As Word) As Single
Declare Sub Savebyte(byval Ee_daten As Byte , Byval Ee_adresse As Word)
Declare Sub Saveword(byval Ee_daten As Word , Byval Ee_adresse As Word)
Declare Sub Savesingle(byval Ee_daten As Single , Byval Ee_adresse As Word )

Goto 001

Sub Savebyte(byval Ee_daten As Byte , Byval Ee_adresse As Word)
Eebyte(1) = Ee_daten
Ee_adresse01 = Ee_adresse
Eebanz = 1 : Gosub Write_ee
End Sub

Sub Saveword(byval Ee_daten As Word , Byval Ee_adresse As Word)
Eeword(1) = Ee_daten
Ee_adresse01 = Ee_adresse
Eebanz = 2 : Gosub Write_ee
End Sub

Sub Savesingle(byval Ee_daten As Single , Byval Ee_adresse As Word )
Eesingle = Ee_daten
Ee_adresse01 = Ee_adresse
Eebanz = 4 : Gosub Write_ee
End Sub


Function Loadbyte(byval Ee_adresse As Word) As Byte
Ee_adresse01 = Ee_adresse
Eebanz = 1 : Gosub Read_ee
Loadbyte = Eebyte(1)
End Function

Function Loadword(byval Ee_adresse As Word) As Word
Ee_adresse01 = Ee_adresse
Eebanz = 2 : Gosub Read_ee
Loadword = Eeword(1)
End Function

Function Loadsingle(byval Ee_adresse As Word) As Single
Ee_adresse01 = Ee_adresse
Eebanz = 4 : Gosub Read_ee
Loadsingle = Eesingle
End Function






'Routine zum schreiben von Daten in das EEPROM ++++++++++++++++++++++++++++++++
Write_ee:
'Disable Interrupts
Eead = Eead + Eebanz
Eebanz = Eebanz + 2
I2csend 24c64w , Eehead(1) , Eebanz
'Waitms 10
'Enable Interrupts
'If Err = 1 Then Call Error(55)

Return


'Routine zum lesen von Daten aus dem EEPROM ++++++++++++++++++++++++++++++++++++
Read_ee:
'Disable Interrupts
Eead = Eead + Eebanz
I2csend 24c64w , Eehead(1) , 2
'Waitms 10
I2creceive 24c64r , Eebyte(1) , 0 , Eebanz
'Waitms 1
'Enable Interrupts
'If Err = 1 Then Call Error(55)

Return

001:

Dim Ins As Single
Dim Inw As Word
Dim Inb As Byte
Dim I As Word

Do
Input "Single: " , Ins
For I = 20 To 100 Step 4
Call Savesingle(ins , I)
Next I
Print "gespeicherter Wert: " ; Ins
Ins = Loadsingle(20)
Print "geladener Wert: " ; Ins

Input "Word: " , Inw
Call Saveword(inw , 10)
Print "gespeicherter Wert: " ; Inw
Inw = Loadword(10)
Print "geladener Wert: " ; Inw

Input "Byte: " , Inb
Call Savebyte(inb , 30)
Print "gespeicherter Wert: " ; Inb
Inb = Loadbyte(30)
Print "geladener Wert: " ; Inb
Loop
For I = 10 To 410 Step 4
Call Savesingle(0 , I)
Next I

Roberto
02.02.2006, 11:14
Hallo Basti..

Funktioniert das letzte Beispiel (für den 256er) nicht bei dir.
(https://www.roboternetz.de/wissen/index.php/Bascom_und_I2C_EEprom)
Sollt eigentlich für den ..64er auch funktionieren.. ?!

Habe wegen den High/Low Adressen nachgeschaut.
Dürftest recht haben.
Also zuerst High dann Low Adresse...
Vielleicht kann das jemand bestätigen, dann werde ich das ändern..
Muss eh in den nächsten Tagen in EEprom was machen, dann werde ich das gleich testen ..

Rage_Empire
02.02.2006, 12:02
...also mein Source ist zwar für nen 24c64er eeprom geschreiben, dürfte aber auch mit größeren ohne probleme gehen. Hat bis jetzt bei jedem prima funktioniert.

Roberto
02.02.2006, 14:05
Hallo Rage_empire

Ohne dir nahe zu treten ;-)

Dein Code wird wohl funktionieren, aber ob das auch was für Anfänger ist (inkl.mir :-) ) ?!

Darum habe ich ja auch einen einfachen Code im RN-Wissen geschrieben, den man leichter verstehen kann.
Ich weis nicht, ob es für Basti... was bringt, wenn er einfach deinen Code in sein Programm kopiert ohne ihn zu verstehen ?! ;-)

Was anderes...
Stimmt das jetzt, dass die High Adresse zuerst kommt und dann die Low-Adresse?
Wenn ja, wäre eigentlich mein Beispiel dann wohl falsch.?!

l.G. Roberto

albundy
02.02.2006, 14:14
Stimmt das jetzt, dass die High Adresse zuerst kommt und dann die Low-Adresse?


Wenn man dem Datenblatt vertrauen kann, stimmt es.


Therefore the next byte transmitted by
the master is the high-order byte of the word address
and will be written into the address pointer of the 24C64.
The next byte is the least significant address byte . After
receiving another acknowledge signal from the 24C64
the master device will transmit the data word to be written
into the addressed memory location.

Roberto
02.02.2006, 14:16
Habs jetzt geändert.
Vielleicht kann es jemand kontrolieren, ob es jetzt so stimmt :-) ?!

BASTIUniversal
02.02.2006, 15:09
Hallo!
Verstanden hab ich das ganze, ist ja auch nicht sonderlich schwer (wenn man das Datenblatt nebenher liest).
Funktionieren tut das ganze auch...hab ich auch geschrieben:

...so wie ich die Adressen oben aufgeschrieben hab funktionierts!

Nach meinem (mit Hilfe des EEPROM's gebauten) Druckmesser wird's in den nächsten Tagen schlechteres Wetter :^o

Jetzt muss ich nurnoch mit nem OpAmp oder so das Signal auf meinen ADC anpassen...der Sensor gibt nämlich ein Signal von max. 4,521 bis 4,659V von sich (45,9mV/kPa).
Das würde bei meinem ADC einen Wert von 778 bis 870 (950hPa bis 1050hPa) bedeuten...der ADC wäre da also nicht wirklich "ausgelastet"!
Hat da vielleicht noch jemand ne passende Schaltung dafür? Ne Referenzspannung zum genauen erfassen der Betriebsspannung bräuchte ich für ne genaue Messung auch noch (die interne Referenz im Mega ist nur 1,1V!)

Danke!

Rage_Empire
03.02.2006, 08:08
@roberto

du hast sicherlich nicht ganz unrecht. Ich hatte das auch nicht in 5minuten zusammen. Aber kommt als nächstes nicht die Frage, wie ich ein Long, ein Word oder ein Single in ein EEPROM speichere / lese? Ich meine, man muß ja das Rad nicht immer neu erfinden und wenn sich jemand etwas gewagtere Sources anschaut kann er durchaus was dabei lernen...geht mir jedenfalls oft so.