Using AT24C02A EEPROM

Posted on
  • Hello,

    I'm trying to wire up and 24C02A EEPROM and read-write data on it.
    I'm using this datasheet : http://pdf.datasheetcatalog.com/datashee­ts/90/80419_DS.pdf

    I'm using SMT32F4 Discovery.

    I have vired as this

    EEPROM VCC -> Board 5V
    EEPROM CSS -> Board Ground
    EEPROM SCL -> Board SCL (B8)
    EEPROM SDA -> Board SDA (B9)

    Then I'm using this code;

    I2C1.setup({scl:B8,sda:B9});
    var eeprom=require("AT24").connect(I2C2, 8, 256, 1);
    console.log(eeprom.read(0x64,"Merhaba Dunya"));
    

    But I'm getting this error :

    
    Uncaught Error: I2C device not responding
     at line 1 col 50
    ...writeTo(this.i(a),this.a(a));return this.i2c.readFrom(this.i...
                                   ^
    in function "read" called from line 1 col 42
    console.log(eeprom.read(0,"Merhaba Dunya"));
                                              ^
    
    

    What I'm doing wrong?

  • Have you added pullup resistors on SCL and SDA? That's the No.1 problem with I2c usually :)

  • You need pullups on SDA and SCL if you don't have them already. 10k ohm resistor from SDA to Vcc, and SCL to Vcc.

    I2C1.setup({scl:B8,sda:B9}); //okay
    var eeprom=require("AT24").connect(I2C2, 8, 256, 1); //you're passing I2C2, but you just set up I2C1, not I2C2
    console.log(eeprom.read(0x64,"Merhaba Dunya"));  //what on earth is this expected to do? the .read() method takes 2 arguments, an address, and a number of bytes. Those look like the arguments you'd use for a write operation.  
    
  • Yes, I had many mistakes on code; Also I had misakes on wiring.

    Here is the correct one

    EEPROM VCC -> Board 5V
    EEPROM CSS -> Board Ground
    EEPROM SCL -> Board SCL (B10)
    EEPROM SDA -> Board SDA (B11)

    Also I have placed two 10k ohm resistors between VCC -> SCL and VCC ->SDA

    I2C2.setup({scl:B10,sda:B11});
    var eeprom=require("AT24").connect(I2C2, 8, 256, 0);
    console.log(eeprom.write(0x64,"Merhaba")­);
    console.log(eeprom.read(0x64,7));
    
    

    line console.log(eeprom.write(0x64,"Merhaba")­); outputs 7

    but console.log(eeprom.read(0x64,7)); delays 10-12 seconds and outputs this error;

    Uncaught InternalError: Timeout on I2C Read Receive Mode
     at line 2 col 2
    b)}
      ^
    in function "read" called from line 1 col 31
    console.log(eeprom.read(0x64,7));
    
  • Try (or executing it one line at a time in the console - point being just to get a delay between the read and write)

    
    I2C2.setup({scl:B10,sda:B11});
    var eeprom=require("AT24").connect(I2C2, 8, 256, 0);
    console.log(eeprom.write(0x64,"Merhaba")­);
    
    setTimeout("console.log(eeprom.read(0x64­,7));",20);
    
    

    When you write a single page, it just returns - it doesn't wait out the 10ms internally timed write cycle, so it may still be unresponsive in write cycle if you try to access it immediately after that.

  • No way. I have tried on the console manually. And tried as you give with setTimeout. But still the same error.

    I'm not soldering it, may this cause the problem? I'm pluging pins and cables on the board.

  • Oh, I see the problem - the module is expecting capacity in kbits, (so you can just use the number from the part number). Should be 2, not 256 as the capacity. This confuses it, because the larger ones use 2 bytes + a few for the address, instead of 1.

    So write works (it's writing "dMerhaba" (d being 0x64) to address 0, but the read attempt is invalid, because it's expecting the master to read after 1 byte of address, but the master keeps sending data for another byte.

  • @DrAzzy Thanks for your response, I have revised the code like this;

    I2C2.setup({scl:B10,sda:B11});
    var eeprom=require("AT24").connect(I2C2, 8, 2, 0);
    console.log(eeprom.write(0x64,"Merhaba")­);
    setTimeout("console.log(eeprom.read(0x64­,7));",20);
    

    But It is the same result.

  • This is strange - what really confuses me is that the write doesn't fail, but the read does.
    Some sanity checks:
    You have a decoupling cap on it, right? If not, try putting 0.1uf cap (ceramic) between Vcc and Gnd right next to the chip.

    Failing that

    Run this and report results:

    
    I2C2.setup({scl:B10,sda:B11});
    var eeprom=require("AT24").connect(I2C2, 8, 2, 0);
    console.log(eeprom.a(eeprom.i2ca)); //check that I2C addressing is being done right
    console.log(eeprom.i(0x64)); //check that memory addressing is being done right
    console.log(eeprom.cap); //sanity check - should be 256 (capacity supplied as kbits, but internally handled in bytes. 
    I2C2.writeTo(0x50,0); //select address 0 manually
    I2C2.readFrom(0x50,8); //read 8 characters manually
    I2C2.writeTo(0x50,0x64); //select address 0x64 manually
    I2C2.readFrom(0x50,8); //read 8 characters manually
    
    

    I've got a small AT24-series chip at home that I can check this on, but unless something broke very recently, i don't know what it could be.

  • @DrAzzy I have not decoupling cap, I'm going to buy and apply it.
    But I have tried your code without decoupling cap. I think results are good;

    >console.log(eeprom.a(eeprom.i2ca)); //check that I2C addressing is being done right
    function () { [native code] }
    =undefined
    >console.log(eeprom.i(0x64)); //check that memory addressing is being done right
    80
    =undefined
    >console.log(eeprom.cap); //sanity check - should be 256 (capacity supplied as kbits, but internally handled in bytes.
    256
    =undefined
    >I2C2.writeTo(0x50,0); //select address 0 manually
    =undefined
    >I2C2.readFrom(0x50,8); //read 8 characters manually
    =[ 255, 255, 255, 255, 255, 255, 255, 255 ]
    >I2C2.writeTo(0x50,0x64); //select address 0x64 manually
    =undefined
    >I2C2.readFrom(0x50,8); //read 8 characters manually
    =[ 110, 97, 117, 111, 119, 117, 105, 111 ]
    > 
    

    Also I don't know does it care but here is some results about addressing ;

    >eeprom.i(2);
    =80
    >eeprom.i(0x64);
    =80
    >eeprom.i(0x50);
    =80
    >eeprom.i(1);
    =80
    >eeprom.i(0);
    =80
    > 
    

    One more test result is below, I think it writes and reads when I try manually

    >I2C2.writeTo(0x50,0x64);
    =undefined
    >I2C2.writeTo(0x50,0x64,"MERHABA");
    =undefined
    >I2C2.writeTo(0x50,0x64);
    =undefined
    >I2C2.readFrom(0x50,7);
    =[ 77, 69, 82, 72, 65, 66, 65 ]
    
  • eeprom.a() should return a 1 or 2 byte string, not a native code function. In this case it should return: "P".

    This is pure JS - it has nothing to do with the connected device.

    I also cannot reproduce that behavior on my system - I get the correct results...

    console.log(eeprom.a(eeprom.i2ca));
    P

    What version of Espruino firmware are you using?

    I'm also PMing Gordon, maybe he might have some insight here.

  • my process.version output is "1v72"

    By the way I'm not using this module : http://www.espruino.com/modules/AT24.js
    I think my AT24 Module is build-in

  • Ok, that's a strange one... First off I'd advise you update your firmware to the latest version (1v75) and see if it still happens - it's available from the Download page.

    If you've got require("AT24") in the Web IDE then it'll be automatically downloading and using that module though - unless somehow you're doing something else...

  • There is no built-in AT24 module.

    If you put require("AT24") on the right side of the IDE, and tell it to send, there are only three places it could get the AT24 module from.

    Either it's using the one from espruino.com/modules, or you have an AT24.js on an SD card and the board supports that (I don't know if that board does), or you have the sandbox enabled and an AT24.js or AT24.min.js in the modules directory in your espruino sandbox directory.

    Please make sure you are using the version from espruino.com/modules (you can do require("http://espruino.com/modules/AT24.js").co­nnect(...) from the right side of the IDE, and it will make sure to get it from there - though I suspect that's already where it's coming from; i'd be very surprised if there were weird versions of my module floating around).

    (note - if you examine the code, it won't look the same as in the .js , because the IDE sends the minified versions of the modules (.min.js ), to reduce memory use)

    I would definitely update firmware to latest available, though I would expect it to work on v72 (but not anything before that).

    Finally, if all that doesn't change behavior, can I see a console.log(eeprom.a)? That should print out the js function that's somehow returning native function.

  • @Gordon OK, I'm going to update firmware.

    I have realized that E.toString() return value as native code

    >E.toString(65)
    ="function () { [native code] }"
    
  • I have updated the firmware here is the test results

    >console.log(eeprom.a(eeprom.i2ca));
    2
    =undefined
    >console.log(eeprom.i(0x64));
    80
    =undefined
    >console.log(eeprom.cap);
    256
    =undefined
    >I2C2.writeTo(0x50,0);
    =undefined
    >I2C2.readFrom(0x50,8);
    =new Uint8Array([255, 255, 255, 255, 255, 255, 255, 255])
    >I2C2.writeTo(0x50,0x64);
    =undefined
    >I2C2.readFrom(0x50,8);
    =new Uint8Array([77, 69, 82, 72, 65, 66, 65, 111])
    
    
    >eeprom.write(0x64,"Merhaba")
    =7
    >eeprom.read(0x64,7)
    =new Uint8Array([77, 101, 114, 104, 97, 98, 97])
    

    I think it has been done.

  • Hurray!

  • Great!

    I see what was happening now - E.toString must not have existed in 1v72. Instead, it was calling the built-in function Object.toString on E (which would ignore the first argument).

    If I'm honest, toString was probably a bad name for the E.toString function given the name clash - but hey, too late now :)

  • Post a reply
    • Bold
    • Italics
    • Link
    • Image
    • List
    • Quote
    • code
    • Preview
About

Using AT24C02A EEPROM

Posted by Avatar for fobus @fobus

Actions