Shop OBEX P1 Docs P2 Docs Learn Events
I2C.BSP & BS2P - Can't write, but reads already writen EPROM properly. — Parallax Forums

I2C.BSP & BS2P - Can't write, but reads already writen EPROM properly.

CuriousOneCuriousOne Posts: 931
edited 2014-01-26 11:53 in BASIC Stamp
Hello.

I have BS2P & stamps in class board and wanted to work with I2C. I've copied the program I2C.BSP from reference manual, and attached EPROM according to schematics. One difference is that I have 24C32 eprom, while program says 24LC16. The code is below:
' I2C.bsp
' This program demonstrates writing and reading every location in a 24LC16B
' EEPROM using the BS2p/BS2pe's I2C commands. Connect the BS2p, BS2pe, or
' BS2px to the 24LC16B DIP EEPROM as shown in the diagram in the I2CIN or
' I2COUT command description.
' {$STAMP BS2p}
' {$PBASIC 2.5}
#IF ($STAMP < BS2P) #THEN
#ERROR "Program requires BS2p, BS2pe, or BS2px."
#ENDIF
SDA PIN 1 ' I2C SDA pin
SCL PIN 0
addr VAR Word ' internal address
block VAR Nib ' block address in 24LC16
value VAR Byte ' value to write
check VAR Nib ' for checking retuned values
result VAR Byte(16) ' array for returned value
Write_To_EEPROM:
DEBUG "Writing...", CR
PAUSE 2000
FOR addr = 0 TO 2047 STEP 16 ' loop through all addresses
block = addr.NIB2 << 1 ' calculate block address
value = addr >> 4 ' create value from upper 8 bits
' write 16 bytes
I2COUT SDA, $A0 | block, addr, [REP value\16]
PAUSE 5
DEBUG "Addr: ", DEC4 addr, "-", DEC4 addr + 15, " ",
"Value: ", DEC3 value, CR
NEXT
PAUSE 2000
Read_From_EEPROM:
DEBUG CR, "Reading...", CR
PAUSE 2000
FOR addr = 0 TO 2047 STEP 16
block = addr.NIB2 << 1
value = addr >> 4
I2CIN SDA, $A1 | block, addr, [STR result\16]
FOR check = 0 TO 15
IF (result(check) <> value) THEN Error
NEXT
DEBUG "Addr: ", DEC4 addr, "-", DEC4 addr + 15, " ",
"Value: ", DEC3 result, CR
NEXT
PAUSE 100
DEBUG CR, "All locations passed"
END
Error:
DEBUG "Error at location: ", DEC4 addr + check, CR,
"Found: ", DEC3 result(check), ", Expected: ", DEC3 value
END

It stops, because does not reads what expected. But, if I comment the code: IF (result(check) <> value) THEN Error
The read operation continiues successfully, and I can see the contents of eeprom, it being read properly.

What can be the cause?

Comments

  • CuriousOneCuriousOne Posts: 931
    edited 2014-01-14 04:18
    I've tried to play with pullup resistors. With 2.2k or 4.7k ones, reading is fine, write does not works. With 10k ones, neither works.

    Tried to play with write protect pin - no changes
  • GenetixGenetix Posts: 1,749
    edited 2014-01-14 15:35
  • davejamesdavejames Posts: 4,047
    edited 2014-01-14 19:42
    Curious - please take no offense, but do you understand how the I2C protocol is supposed to work?

    If not, this is a good place to start:

    http://www.nxp.com/documents/user_manual/UM10204.pdf

    This is straight from the horse's mouth (aka "the people that created I2C"). :thumb:
  • CuriousOneCuriousOne Posts: 931
    edited 2014-01-15 01:30
    Personally I dislike I2C, but I'm forced to use it, since several sensors I need are only I2C capable. I decided to start what with parallax provides (sample code). And since this sample code does not works, I'd like to hear, if possible, what exactly wrong is with this sample code, why it does not works.
  • Hal AlbachHal Albach Posts: 747
    edited 2014-01-15 08:20
    The Basic Stamp Manual indicates that for hardware I2C on the BS2P, SDA must be 0 or 8 and SCL 1 or 9. I'm not sure what the BS2P will do when you reverse the pins.
  • ZootZoot Posts: 2,227
    edited 2014-01-15 19:20
    Your code will not work for at least two reasons:

    - SDA must be pin 0 or pin 8. Doesn't matter if you define SCL, it is always the "next pin up" from SDA. So if SDA is pin0, then SCL must be pin1. If SDA is pin8, SCL must be pin9. On the BS2p40 you can use either MAIN or AUX pins, btw.

    - I believe you are assigning your address wrong, unless you have multiple EEPROMs on the I2C bus. The first byte in the I2C stream is the chip address, which is controlled by the address pins on the EEPROM. The last bit of this first byte address is the read/write bit; on the BS2p you do NOT need to set this bit, as I2COUT/I2CIN set it automatically (but it never hurts to set it if you want code clarity). The next byte(s) are the address within the chip to write to. You are ORing the "block" variable onto your address which I don't think is doing what you intend.
  • CuriousOneCuriousOne Posts: 931
    edited 2014-01-15 21:05
    Ok, will check it later today, thanks!
  • CuriousOneCuriousOne Posts: 931
    edited 2014-01-15 23:47
    I don't have multiple eeproms, and playing with SDA/SCL pin numbers changes nothing - if they are wrong, it does not reads at all. Tried swapping them already.
  • ZootZoot Posts: 2,227
    edited 2014-01-16 07:48
    The is nothing to "play" with. SDA *must* be defined as pin0 or pin8 and you must wire SDA to that pin. SCL must be wired to the next pin up from SDA (either 1 or 9). Pullups in 2.2 - 4.7k should be fine.

    Post your most recent code if you are still having trouble.
  • CuriousOneCuriousOne Posts: 931
    edited 2014-01-16 21:28
    I meant that I tried 0-1, 1-0, 8-9, 9-8 combos. It does not works a all, or works only for read. The code I'm using is posted in 1st post.
  • ZootZoot Posts: 2,227
    edited 2014-01-17 12:11
    There is no way your code works properly, and if you think it is reading the EEPROM then that may just be coincidence. And if you tried other pins, then your code would be different. Trying 0-1, 1-0 combos is pointless. SDA must, must, must be pin 0 or pin 8, SCL must, must, must be pin 1 (if SDA is pin0) or pin 9 if SDA is pin 8 (and SDA must be defined as such in the code).

    It might help if you post the most recent code you tried and even a photo of your wiring (for example, are you sure that the address select pins on the EEPROM are wired properly, etc.).

    Then revisit your code and look at my earlier comments.
  • Hal AlbachHal Albach Posts: 747
    edited 2014-01-19 16:28
    Until you change the pin assignment for SDA to 0 in your code it won't matter how you play with or hook up the EEPROM. Make sure wire the EEPROM correctly. On nearly all 8 pin I2C EEPROMS SDA is pin 5 and SCL is pin 6.
  • CuriousOneCuriousOne Posts: 931
    edited 2014-01-25 23:48
    Yes, I have changed SDA to PIN 0. It works, but it only reads. Can't write.
  • Hal AlbachHal Albach Posts: 747
    edited 2014-01-26 06:18
    Please verify your connections, EEPROM pins 1,2,3,4, and 7 grounded, pin 6 to P0, Pin 5 to P1, and pin 8 to + power. Even though the A0-A2 and WP pins have internal pulldowns, ground them anyway.
    Also, the data sheets specify a maximum page write time of 5 ms for the 24LC16B and 10 ms for the 24C32. You might want to try changing the PAUSE 5 statement that follows I2COUT... to PAUSE 10.
    And make sure you have changed the pin assignments in the program so that SDA is Pin 0 and SCL is pin 1.
    If the EEPROM still won't write then you probably have a faulty device.
  • ZootZoot Posts: 2,227
    edited 2014-01-26 11:53
    Post your actual most recent code, not a description of your code.
Sign In or Register to comment.