WRITECODE stores wrong 14-bit word values in FlashMEM


Closed Thread
Results 1 to 19 of 19
  1. #1
    Join Date
    Jan 2009
    Location
    Delaware
    Posts
    19

    Question WRITECODE stores wrong 14-bit word values in FlashMEM

    Hello!

    I am using WRITECODE and READCODE at run time in a PIC16F876A. I send in a series of 70 or more words from my PC (none larger than a 14 bit value) and WRITECODE them into upper FlashRAM sequential addresses (not overwriting program memory).

    But when I later READCODE the values from memory, some (about 20%) of the values are wrong. The errors do not follow any particular pattern in the memory sequence that I can see.

    I know the 14-bit values are being received correctly by the PIC because I send them back out to an LCD for view prior to the WRITECODE instruction. I have confirmed the errors by sending the READCODE values back to the PC and compared them with what was sent.

    The PIC16F876A data sheet talks about writing in blocks of 4 words, not crossing page boundaries, and that a write is really an erase-then-write operation, but I thought that PBP took care of all that for WRITECODE and READCODE.

    I will be glad to post the code here if needed, but before doing that I need to ask a basic question:

    Am I supposed to use ERASECODE before using WRITECODE on a PIC16F876A?

    I would appreciate any guidance you can give on this.

    Thank you,
    Bob Pigford
    Newark, Delaware

  2. #2


    Did you find this post helpful? Yes | No

    Default

    Hi Bob. I'm not an expert at this but I use 16F872 & '873 a lot. Instead of READCODE and WRITECODE, try using READ and WRITE. I believe you are writing to program memory space instead of eeprom.

  3. #3
    Join Date
    Aug 2006
    Location
    Look, behind you.
    Posts
    2,818


    Did you find this post helpful? Yes | No

    Default

    Hi Bob,
    Check these 2 links from Melanie:
    http://www.picbasic.co.uk/forum/showthread.php?t=137
    http://www.picbasic.co.uk/forum/showthread.php?t=545
    Should be something in there that is helpful.
    If you do not believe in MAGIC, Consider how currency has value simply by printing it, and is then traded for real assets.
    .
    Gold is the money of kings, silver is the money of gentlemen, barter is the money of peasants - but debt is the money of slaves
    .
    There simply is no "Happy Spam" If you do it you will disappear from this forum.

  4. #4
    Join Date
    Jan 2009
    Location
    Delaware
    Posts
    19


    Did you find this post helpful? Yes | No

    Default Thanks for the suggestions - still working on it

    Quote Originally Posted by peterdeco1 View Post
    Hi Bob. I'm not an expert at this but I use 16F872 & '873 a lot. Instead of READCODE and WRITECODE, try using READ and WRITE. I believe you are writing to program memory space instead of eeprom.
    To: Peterdeco1
    Thanks for the suggestion, but I do want to write to program RAM (flash RAM) because the EEPROM space will be too small for the 2000 words I want to be able to store eventually.

    To: Joe S.
    I appreciate those links and I have read and re-read the good info from Melanie several times. She still does not clarify the need for a ERASECODE prior to WRITECODE, though. In fact, after previous readings of her posts, I had assumed that I needed just WRITECODE and READCODE and that PBP took care of all the details.

    Please send more suggestions. I appreciate all help!
    Bob

  5. #5
    Join Date
    Jul 2003
    Location
    Colorado Springs
    Posts
    4,959


    Did you find this post helpful? Yes | No

    Default

    On the 16F87x and 16F87xA series, ERASECODE will not work. In fact, if you try to use the statement, it will generate an error since there isn't a bit called "FREE" in the EECON1 register.

    And yes, PBP takes care of most of the details. But there are still some things the user needs to understand first.

    As you've already mentioned, with the A version of these chips, you have to write in blocks of 4-words at a time.
    Not just any 4 words, they have to be aligned to a physical Flash boundary.

    <table><tr><td><img src="http://www.picbasic.co.uk/forum/attachment.php?attachmentid=3294&stc=1&d=123862608 0" /></td><td valign=top>Since you want up to 2k of space, I assume you're starting at the beginning of Flash Page 3 ($1800).

    Blocks always start at the address where the 2 lsb's = 0. So in this case the first block is at $1800.

    From there you need to write 4-words consecutively. When it does WRITECODE on 1803 (the 4th word), the contents of the Block will be erased automatically, and the new data will be written.

    While erasing, the CPU will "Halt" for approx. 4mS. The OSC is still running, Timers are counting (if used) and the USART will continue receiving data. But SERIN(2) or DEBUGIN cannot receive data during that time. It's easy to miss data if not using the USART.<HR>
    If you are attempting to READCODE the word that was just WRITECODEd, for verification ... unless all 4 words of that block have been written, you will not get the expected value back.
    <hr>
    If you are using Interrupts in your program, they should be disabled globally before writing to FLASH. If an interrupt occurs in the middle of a WRITECODE statement, the procedure can be disrupted and no write will happen, or incorrect data may be written.</td></tr></table>

    I could probably ramble on for awhile, so if that doesn't point you in a direction, perhaps a peek at the code might shed new light.

    <!-- Name:  FlashBlocks.gif
Views: 1270
Size:  5.2 KB -->
    DT

  6. #6
    Join Date
    Aug 2006
    Location
    SWITZERLAND (french speaking)
    Posts
    891


    Did you find this post helpful? Yes | No

    Default my experience (PIC 16F88)

    Hello Bob,

    Even if very risky (and surely very amateur wise), I'm using the program memory in one of my gadgets for months now using the WRITECODE command.

    At the start, I used ERASECODE prior to WRITECODE according to this statement:
    <img src="http://www.picbasic.co.uk/forum/attachment.php?attachmentid=3296&stc=1&d=123866553 2">

    After lots of tests, I can say that ERASECODE is not making any difference (if not used, I save some memory space).

    The only thing I'm sure about is, that WRITECODE will "rewrite" four (4) words at the time (!!!).
    Attached Images Attached Images  
    Roger

  7. #7
    Join Date
    Jan 2009
    Location
    Delaware
    Posts
    19


    Did you find this post helpful? Yes | No

    Default

    Quote Originally Posted by Darrel Taylor View Post
    On the 16F87x and 16F87xA series, ERASECODE will not work. In fact, if you try to use the statement, it will generate an error since there isn't a bit called "FREE" in the EECON1 register.

    And yes, PBP takes care of most of the details. But there are still some things the user needs to understand first.

    As you've already mentioned, with the A version of these chips, you have to write in blocks of 4-words at a time.
    Not just any 4 words, they have to be aligned to a physical Flash boundary.

    <table><tr><td><img src="http://www.picbasic.co.uk/forum/attachment.php?attachmentid=3294&stc=1&d=123862608 0" /></td><td valign=top>Since you want up to 2k of space, I assume you're starting at the beginning of Flash Page 3 ($1800).

    Blocks always start at the address where the 2 lsb's = 0. So in this case the first block is at $1800.

    From there you need to write 4-words consecutively. When it does WRITECODE on 1803 (the 4th word), the contents of the Block will be erased automatically, and the new data will be written.

    While erasing, the CPU will "Halt" for approx. 4mS. The OSC is still running, Timers are counting (if used) and the USART will continue receiving data. But SERIN(2) or DEBUGIN cannot receive data during that time. It's easy to miss data if not using the USART.<HR>
    If you are attempting to READCODE the word that was just WRITECODEd, for verification ... unless all 4 words of that block have been written, you will not get the expected value back.
    <hr>
    If you are using Interrupts in your program, they should be disabled globally before writing to FLASH. If an interrupt occurs in the middle of a WRITECODE statement, the procedure can be disrupted and no write will happen, or incorrect data may be written.</td></tr></table>

    I could probably ramble on for awhile, so if that doesn't point you in a direction, perhaps a peek at the code might shed new light.

    <!-- Attachment 3294 -->
    Thank you all!

    Ahhh. I see. I will now:
    1) Start my WRITECODE at an appropriate address (block start boundary).
    2) Make sure that the last of my many consecutive WRITECODE instructions are padded with enough additional WRITECODE instructions to fill the last block completely.
    3) If I go back and try to WRITECODE over a previously written address, I must know where it was in that block of addresses, then re-write the adjacent values for a total of 4 WRITECODE instructions to fill that block again.

    I will report back!

    Thanks again.
    Bob

  8. #8
    Join Date
    Jan 2009
    Location
    Delaware
    Posts
    19


    Did you find this post helpful? Yes | No

    Default Found the problem - ARRAY variables!

    Hello all!

    Following Darrel Taylor's excellent instructions, I was careful to WRITECODE to 4 word (complete) blocks starting at $1800 (or any other address where the two LSBs are 0's). I still saw wrong stored values. Every 6th address (and a few others) had an error ... VERY strange behavior.

    I had been using 12 WORD sized array variables of 3 elements each, stuffing the last 2 variables of each array into memory (WRITECODE). Suspecting that array variables were the culprits, I changed to 36 individual WORD variables along with all the repetitive code required. NOW IT WORKS!

    The PBP manual (pg 25) says clearly that "The compiler will assure that arrays, as well as simple variables, will fit in memory before successfully compiling."

    My code is about 4100 WORDs in size. It compiled just fine, albiet showing three notes at the bottom of the screen that code page boundaries were being crossed. I had assumed that since the code compiled just fine, that the 3 warnings pertained to the overall size of my code. BUT, perhaps those were warnings that arrays would not work.

    BUT why did it still compile OK? Did the PBP compiler let me down?

    Makes me wary of using array variables. I need to learn more about this in the future!

    Thanks again to all for your help!
    Bob Pigford
    Newark, Delaware

  9. #9
    Join Date
    Jul 2003
    Location
    Colorado Springs
    Posts
    4,959


    Did you find this post helpful? Yes | No

    Default

    Great! Glad it helped.
    Quote Originally Posted by BobPigford
    Makes me wary of using array variables.
    Nothing to worry about there. Arrays work perfectly with PBP.
    And yes, PBP makes sure the arrays will fit in a BANK of RAM.

    The crossing boundary warnings refer to the FLASH memory used by the program. The same area of memory that you are WRITECODEing to.
    Arrays can not cause that warning.

    Array indexes always start at 0.
    So if you have a word array of 3 elements, the index goes from 0 to 2.
    It's easy to forget and try to use 1 - 3, but 3 would be outside of the array, probably a RAM location used by another variable.

    PBP does not do any "Range Checking". It's up to you to stay within the bounds of the array.

    Just about any good program will use arrays in some form or another.
    So yup, time to learn ... then play ... then learn more ...
    <br>
    DT

  10. #10
    Join Date
    Jan 2009
    Location
    Miami, Florida USA
    Posts
    637


    Did you find this post helpful? Yes | No

    Default

    Darrel,
    From reading other posts and other documentation (if I understood them correctly) when using arrays in a pic16fxxx and if the program crosses the memory boundary then that would be looking for trouble. In other words, if you are using arrays all over the place in your program, then your program has to fit in one memory block which is ussually not the case. Otherwise, the program won't work properly.
    I personally like arrays. They make your program looks neat and more profesional, but also my programs are usually bigger than 2K.

    Any comments on this?

    Robert

  11. #11
    Join Date
    Jul 2003
    Location
    Colorado Springs
    Posts
    4,959


    Did you find this post helpful? Yes | No

    Default

    NO! Not true at all.

    The size of your program has NO effect on arrays.
    Arrays are in RAM, the program is in FLASH.

    You may be thinking of the problems that can happen with the BRANCH command if the code is larger than 2K. In which case you need to use BRANCHL.
    DT

  12. #12
    Join Date
    Jan 2009
    Location
    Delaware
    Posts
    19


    Did you find this post helpful? Yes | No

    Smile Well, I was careful about arrays, perhaps I missed something.

    Darrel, et al,

    I understand going out of bounds of a dimensioned array, and that arrays start at 0. I believe that my use of array variables was correct, but I will go back and look again. Perhaps I missed something.

    I am glad to hear that PBP did not let me down, per se, as array variables are held in RAM and arrays crossing any page boundaries are handled by PBP.

    So, I guess I will have to go back and bang out the code with array variables again. It may be a while, but I will report back.

    Thanks to all for your help!
    Bob Pigford
    Newark, DE, USA

  13. #13
    Join Date
    Jan 2009
    Location
    Delaware
    Posts
    19


    Did you find this post helpful? Yes | No

    Cool Oops - I "misspoke" about arrays and boundaries

    Quote Originally Posted by BobPigford View Post
    I am glad to hear that PBP did not let me down, per se, as array variables are held in RAM and arrays crossing any page boundaries are handled by PBP.
    Oops. I should not have talked about arrays crossing any boundaries since Darrel reminded me that they are in RAM. Sorry.

    Bob

  14. #14
    Join Date
    Jan 2009
    Location
    Miami, Florida USA
    Posts
    637


    Did you find this post helpful? Yes | No

    Default

    Darrel,
    I think my confusion comes from the PicBasic Pro Manual, section 4.5, "Arrays".
    "Arrays must fit entirely within one RAM bank on 12-bit, 14-bit or pic17cxxx devices."

    Yeap, I know the program is not stored in RAM. But, what are the implications of this limit to one RAM bank for arrays? Would it be only the limited number of elements in an array?

    Robert

  15. #15
    Join Date
    Jul 2003
    Location
    Colorado Springs
    Posts
    4,959


    Did you find this post helpful? Yes | No

    Default

    Quote Originally Posted by rsocor01 View Post
    But, what are the implications of this limit to one RAM bank for arrays? Would it be only the limited number of elements in an array?
    Exactly.

    The largest amount of GP ram in a 16F's bank is 96 bytes. (chip dependant)
    So the biggest WORD array you can make has 48 elements.

    You could have 3 arrays with 48 words, but not all in one.

    hth,
    DT

  16. #16
    Join Date
    Jan 2009
    Location
    Delaware
    Posts
    19


    Did you find this post helpful? Yes | No

    Default Issues remain with array variables - syntax issues?

    Hello!

    Thanks again to all who pointed out that writing to FlashRAM has to be done in blocks and starting at addresses where the last two bits of address are 00!
    That knowledge allowed me to make my program work OK, but not in an efficient way. I could not get array variables to work for me. I ended up creating 36 separate word variables to get the job done.

    But, I realized that I had not posted anything about my array variable issues since last April. I am still wondering what I was doing wrong. Please help me better understand array variables.

    Below are some snippets of my code that are germane to the issue.

    Program background:

    My program runs on a PIC16F876A at 20 mHz

    At run time, I stuff 14-bit word sized data from a PC into upper FlashRam, then with a switch closure, I change to a routine that reads the words at those addresses and displays them bit-wise. The serial transfer of words and stuffing into FlashRAM works well and I have verified that the correct 14 bit words are correctly placed into FlashRAM.

    When I read words from FlashRAM, these words are put into 2 of my array variables for my subsequent bit-wise display.

    It helps to "conceptualize" the layout of those array variables like this:

    MAX1A[0] MAX2A[0] MAX3A[0] MAX4A[0] MAX5A[0] MAX6A[0]
    MAX1B[0] MAX2B[0] MAX3B[0] MAX4B[0] MAX5B[0] MAX6B[0]

    MAX1A[1] MAX2A[1] MAX3A[1] MAX4A[1] MAX5A[1] MAX6A[1]
    MAX1B[1] MAX2B[1] MAX3B[1] MAX4B[1] MAX5B[1] MAX6B[1]

    MAX1A[2] MAX2A[2] MAX3A[2] MAX4A[2] MAX5A[2] MAX6A[2]
    MAX1B[2] MAX2B[2] MAX3B[2] MAX4B[2] MAX5B[2] MAX6B[2]

    This comprises 12 array variables, each with 3 elements [0, 1, 2].

    After I display them (display code not shown - it works well), I move those last 6 words from the last array elements to their left adjacent array variables with a "riffle" routine that also works well (shown in my code snippets below). Then the program loops and repeats reading words from FlashRAM and displaying them until I reach a preset address in upper FlashRAM.

    What DOES NOT work is the stuffing of words into the array elements in the last column. Wrong values appear there, and the program slows to a crawl, updating about once every 30 seconds or even longer. When complied, no errors are generated.
    But when I use 36 separate word variables in place of the array elements, all works well.

    Snippets of my code that apply:

    Code:
    'snippet from my program
    'array variables declared
    MAX1A   VAR WORD[2]
    MAX1B   VAR WORD[2]
    MAX2A   VAR WORD[2]
    MAX2B   VAR WORD[2]
    MAX3A   VAR WORD[2]
    MAX3B   VAR WORD[2]
    MAX4A   VAR WORD[2]
    MAX4B   VAR WORD[2]
    MAX5A   VAR WORD[2]
    MAX5B   VAR WORD[2]
    MAX6A   VAR WORD[2]
    MAX6B   VAR WORD[2]
    
    'code loop that gets WORD values from FlashRAM and stuffs it into
    'the elements of 2 arrays
        readcode mempntr, MAX6A[0]
        mempntr = mempntr + 1
        readcode mempntr, MAX6B[0]
        mempntr = mempntr + 1
        readcode mempntr, MAX6A[1]
        mempntr = mempntr + 1
        readcode mempntr, MAX6B[1]
        mempntr = mempntr + 1    
        readcode mempntr, MAX6A[2]
        mempntr = mempntr + 1
        readcode mempntr, MAX6B[2]
        mempntr = mempntr + 1
        
    'other code that moves word values from one array element to another
    'so it can be displayed by other routines, then goes back 
    '6 more words, displays them, etc.
    
    Riffle:
      for N = 0 to 2  'move all words to the left for all 3 screens worth of WORDs
        MAX1A[N] = MAX2A[N] : MAX2A[N] = MAX3A[N] : MAX3A[N] = MAX4A[N] : MAX4A[N] = MAX5A[N] : MAX5A[N] = MAX6A[N]
        MAX1B[N] = MAX2B[N] : MAX2B[N] = MAX3B[N] : MAX3B[N] = MAX4B[N] : MAX4B[N] = MAX5B[N] : MAX5A[N] = MAX6B[N]
      next N

    There must still be something I do not understand about array usage and syntax under PICBasicPro. Please point me in the right direction with regard to array variables.

    Thank you to all who are patient with me and offer to help!
    Bob Pigford
    Newark, DE, USA

  17. #17
    Join Date
    Mar 2004
    Location
    San Antonio, Texas
    Posts
    9


    Did you find this post helpful? Yes | No

    Default

    Looking at 4.5 Arrays in the manual it looks like you need to redefining your element from word[2] to word[3]

  18. #18
    Join Date
    Jan 2009
    Location
    Delaware
    Posts
    19


    Did you find this post helpful? Yes | No

    Default Array variables and my lack of knowledge

    Quote Originally Posted by Dick M View Post
    Looking at 4.5 Arrays in the manual it looks like you need to redefining your element from word[2] to word[3]
    Thank you, Dick M. Could it be this simple?
    In the manual example in section 4.5 it reads:

    " shark VAR BYTE[10]
    fish VAR BYTE[8]
    The first array location is element 0. In the fish array defined above, the elements are numbered fish[0] to fish[7] yielding 8 elements in total."

    Gee, I had previously thought that the highest element would be #7, therefore expecting the highest number element to be used in the VAR definition. After rereading the manual (how many times did I already read the manual on this, yet I missed it), it SURE LOOKS LIKE I HAD IT ALL WRONG!!!!!

    Wow, all this struggling. How annoying it will be to find out that I declared my array VARs incorrectly. Of course, it would have been nice if the COMPILER would have reported an error, but I still feel like such a dunce. I will try it again and report back. MANY thanks, Dick M!
    Bob

    Now I must go back to PBP and try it all again!

  19. #19
    Join Date
    Jan 2009
    Location
    Delaware
    Posts
    19


    Did you find this post helpful? Yes | No

    Default PBP array are "dimensioned" differently that other BASICs

    Well, I checked my understand of dimensioning arrays in other forms of BASIC. In other BASICs,
    DIM fish(20)
    creates an array of 21 elements (0 through 20). Hence, the source of my confusion.

    In PBP:
    fish VAR WORD[20] has 20 elements (0 through 19).

    Getting smarter as I go.

    Bob

Similar Threads

  1. Bits, Bytes Words and Arrays
    By Melanie in forum FAQ - Frequently Asked Questions
    Replies: 24
    Last Post: - 14th June 2016, 08:55
  2. Minimizing code space
    By Tobias in forum mel PIC BASIC Pro
    Replies: 2
    Last Post: - 30th May 2009, 08:25
  3. DS2760 Thermocouple Kit from Parallax in PicBasicPro
    By seanharmon in forum mel PIC BASIC Pro
    Replies: 3
    Last Post: - 9th July 2008, 00:19
  4. pic to pic ir link versus wired link : help please anyone
    By xnihilo in forum mel PIC BASIC Pro
    Replies: 13
    Last Post: - 30th May 2008, 22:01
  5. calculation problem
    By nicolelawsc in forum mel PIC BASIC Pro
    Replies: 2
    Last Post: - 31st March 2006, 16:23

Members who have read this thread : 1

You do not have permission to view the list of names.

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts