I am trying to figure out how to write to the data EEPROM on the PIC16F18877 in Assembly. This the first time I am trying to use it and I've read through the datasheet several times (although I sometimes find Microchip's documentation to be lack/unclear) and tried Googling for solution with no luck.
My goal was to read from 0xF001, then write 0x25 to that location, and finally read it back. The initial read returns 0x0, even though the EE Data Memory window shows all locations as 0xFF, and then readback just returns 0x0 as I clear the location before readback to ensure I am reading back the data in the EEPROM and not a previous value.
I am sure I a missing something simple/obvious, but I can't seem to figure out what it is. This is the (non-working) code I came up with:
MOVLW 01h
MOVWF eeprom_addr_low
MOVLW 0F0h
MOVWF eeprom_addr_high
;READ EEPROM
BANKSEL NVMADRL
MOVLW eeprom_addr_low
MOVWF NVMADRL
MOVLW eeprom_addr_high
MOVWF NVMADRH
BSF NVMCON1,6 ;NVMREGS
BSF NVMCON1,0 ;RD
MOVF NVMDATL,W
MOVWF eeprom_data_low
MOVF NVMDATH,W
MOVWF eeprom_data_high
;WRITE EEPROM
BANKSEL NVMADRH
MOVF eeprom_addr_high,W
MOVWF NVMADRH
MOVF eeprom_addr_low,W
MOVWF NVMADRL
BSF NVMCON1,2 ;WREN
BSF NVMCON1,6 ;LWL0
writeLoop:
MOVLW 025h
MOVWF NVMDATL
MOVLW 00h ;0x00
MOVWF NVMDATH
MOVLW eeprom_addr_low ;01h
MOVWF NVMADRL
MOVLW eeprom_addr_high ;0F0h
MOVWF NVMADRH
BSF NVMCON1,2 ;WREN
unlockSeq:
BCF INTCON,7 ;GIE
MOVLW 055h
MOVWF NVMCON2
MOVLW 0AAh
MOVWF NVMCON2
BSF NVMCON1,1 ;WR
BSF INTCON,7 ;GIE
BCF NVMCON1,2 ;WREN
readBack:
MOVLW 00h
MOVWF NVMDATL ;Just clearing it to confirm if the readback is working for debugging purposes
MOVWF NVMDATH
MOVLW eeprom_addr_low
MOVWF NVMADRL
MOVLW eeprom_addr_high
MOVWF NVMADRH
BSF NVMCON1,6
BSF NVMCON1,0
MOVF NVMDATL,W
MOVWF eeprom_data_low
MOVF NVMDATH,W
MOVWF eeprom_data_high
I also attempted to add a loop to wait for the read to be completed as my understand is that bit 0 of NVMCON1 will be cleared once the read is completed. However, if I add this:
waitForRead:
BTFSC NVMCON1,0
GOTO waitForRead
then it goes into an infinite loop.
Any help/guidance would be greatly appreciated as I am stuck on exactly what I am missing.
So after playing around with it some more I was able to get the read/write/read to work with the following code:
It seems there were two issues:
I wasn't waiting for the write to complete and trying to read it back to quickly.
The MPLAB Simulator seems to be kind of broken. That is, sometimes I would run the code a second time (after it was working) without making any changes and the initial read from the EEPROM would return 0x0, instead of the expected 0xFF (which is the default value for all locations when starting up). Cleaning/rebuilding occasionally fixed this, but sometimes I would have to completely restart MPLAB and then immediately debug the code and it worked as expected. Curious if anyone else has run into this.