Shop OBEX P1 Docs P2 Docs Learn Events
positive incrementing a for next loop with starting number less than ending num — Parallax Forums

positive incrementing a for next loop with starting number less than ending num

RandyRandy Posts: 79
edited 2006-10-14 00:27 in BASIC Stamp
I have (I need) a routine for reading an EEPROM with a for next loop that may have a starting number less than the ending number. The program·writes··data in 16 byte chunks to a 24LC128 EEPROM. Each time it writes the address is increased by 16 for the next WRITE. On·request it will read the data to StampDAQ. In order to not constantly write to the same addresses,·after a down load from the EEPROM the program will start the next write at the·last address read. If it gets to the·end of page address of the EEPROM it will roll to address 0 and continue from there. By using GETs, PUTs, READs and WRITEs the program knows where to start and end a·WRITE or READ·and not to overwrite data that has not been downloaded. If the stored data does not pass address 0, downloading is no problem. If it does then the starting address is less than the ending address and the BS2 wants the for next loop to count down instead of up. I am using the EEPROM address for the counter in the loop with a·STEP 16. How can I force it to count up regardless of the begining or ending numbers? I tried adding 15 inside the loop plus the one from the FOR NEXT loop (default STEP 1) but if the start is less than the end it subtracts one in the loop. I suspect I could always start at address 0 and it would take several years to wear out the EEPROM but I want to know how to do this. Assuming I can figure out how I wil include the part of the program in question as an attachment.

Randy

Comments

  • RandyRandy Posts: 79
    edited 2006-10-13 02:58
    Looks like I didn't figure out the attachment. How about this.

    GET 19, ee_add.HIGHBYTE
    GET 21, ee_add.LOWBYTE
    GET 23, clear
    GET 27, startadd.HIGHBYTE
    GET 28, startadd.LOWBYTE

    last_add = ee_add - 16
    IF last_add > 16368 THEN last_add = 16368
    IF last_add = ee_add THEN nodata
    ee_add = startadd

    HIGH enRS
    PAUSE 50
    SEROUT RSdin,Rbaud, [noparse][[/noparse]"DUMPING",CR]

    FOR ee_add = startadd TO last_add STEP 16
    IF ee_add = 16384 THEN ee_add = 0
    I2CIN SDA,$A1, ee_add.HIGHBYTE\ee_add.LOWBYTE, [noparse][[/noparse]secs, mins, hrs, date, month, year,outside.HIGHBYTE,outside.LOWBYTE, supply8,retrn8,supply11,retrn11,chilledsupply,chilledretrn,retrn9,retrn10]
    hrstime = (12 - (24 - (hrs10 * 10 + hrs01) // 12))
    IF (hrs > 17) THEN afternoon
    IF hrs = 0 THEN hrstime =12
    SEROUT RSdin, Rbaud, [noparse][[/noparse]"DATA,",HEX2 month,"/",HEX2 date,"/",HEX2 year," ", DEC hrstime,":",HEX2 mins,":",HEX2 secs," _AM ",",",
    SDEC Outside,",",DEC supply8,",", DEC retrn8,",", DEC supply11,",", DEC retrn11,",", DEC chilledsupply,",", DEC chilledretrn,",",DEC retrn9,",",DEC retrn10,",", CR]
    GOTO finish

    afternoon:
    SEROUT RSdin, Rbaud, [noparse][[/noparse]"DATA,",HEX2 month,"/",HEX2 date,"/",HEX2 year," ", DEC hrstime,":",HEX2 mins,":",HEX2 secs," _PM ",",",
    SDEC Outside,",",DEC supply8,",", DEC retrn8,",", DEC supply11,",", DEC retrn11,",", DEC chilledsupply,",", DEC chilledretrn,",",DEC retrn9,",",DEC retrn10,",", CR]

    finish:
    NEXT


    Thanks, Randy
  • Mike GreenMike Green Posts: 23,101
    edited 2006-10-13 03:03
    How about not using a FOR loop and using IFs, assignments, and GOTOs? That way you can make the increment/decrement as complex as you want and the ending condition just as complicated.
  • RandyRandy Posts: 79
    edited 2006-10-13 12:57
    Thanks Mike,
    What is an assignment?
    I can't picture using IFs and GOTOs, could you give me a short example?
    There could be just one, or even none, or as many as 1024 addresses to read sequentially. It depends on how much data was writen and how long since the last dump.
    Randy
  • Bruce BatesBruce Bates Posts: 3,045
    edited 2006-10-13 14:40
    Randy -

    An assignment statement is generally something like one of the following, depending on the context:

    A = 1

    B - 255

    Dist = Rate * Time

    Or something similar.

    Regards,

    Bruce Bates

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    <!--StartFragment -->
  • Mike GreenMike Green Posts: 23,101
    edited 2006-10-13 14:52
    Randy,
    Much better if you sketch out in words exactly what you're trying to do, step by step, from the standpoint of the problem to be solved like:
    If the sky is grey and it's above freezing outside, then put on a light coat and carry an umbrella -or- The buffer is 16 bytes long. Starting at the beginning of the buffer, put in 2 bytes of data at a time. When the buffer is full, start over at the beginning and discard any existing saved values.
    Mike
  • Tracy AllenTracy Allen Posts: 6,662
    edited 2006-10-13 15:18
    There are lots of ways to do this. My preferred method is to keep as my primary index, not the physical start and end address, but the base record number and current number of records, and then those are mapped into the physical memory addresses when you go to READ and WRITE the data. Both are pointers, chasing one another through the memory array as data is added and then offloaded to stampDAQ. Logical addresses of records are separated from the details of the memory array.

    In your example, the physcal array goes from 0 to 16383, and each record is 16 bytes. That gives you 1024 possible records. The number of records * 16 modulo 16384 points to the next free memory location for write:

    Dwrite:
      IF Nrecs=1024 THEN RETURN  ' full, you could alternatively implement wraparound
      ee_add = Nrecs + Nbase * 16 // 16384  ' base plus number of records gives next free location   
      I2COUT SDA,$A1, ee_add.HIGHBYTE\ee_add.LOWBYTE,...[noparse][[/noparse]  16 bytes  ]
      Nrecs = Nrecs+1 max 1024   
    RETURN
    
    Doffload:
      IF Nrecs=0 THEN RETURN ' no data
      ee_add = Nbase * 16 // 16384  ' base location for oldest data to offload.
      I2CIN SDA,$A1, ee_add.HIGHBYTE\ee_add.LOWBYTE,...[noparse][[/noparse]  16 bytes  ]
      ' send data here or after return from subroutine
      Nbase = Nbase+1  ' one record sent
      Nrecs = Nrecs - 1   ' one less record in database
    RETURN
    



    It is fine to store those pointers in scratchpad, but I like to store them in non volatile memory in the clock RAM.

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Tracy Allen
    www.emesystems.com

    Post Edited (Tracy Allen) : 10/13/2006 3:37:00 PM GMT
  • metron9metron9 Posts: 1,100
    edited 2006-10-13 17:40
    Here is a document about O buffers and EEPROM that may help.

    http://www.atmel.com/dyn/resources/prod_documents/doc2526.pdf

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Think outside the BOX!
  • RandyRandy Posts: 79
    edited 2006-10-14 00:27
    Thanks to all of you for the responses.

    Yes Mike, once the brain returned to operation a couple of IFs and GOTOs and a trio of FOR NEXTs has everything working perfectly.

    Tracy I haven't tried implementing your idea yet but I like it. Especiallly using the clock RAM as it has back up power. Currently I am periodicly writing the addresses to a protected DATA location in the STAMP for retrival after a power outage. Here I am worrying about wearing out a $3.00 EEPROM while writing over and over to the same location in a $50.00 STAMP when I could be doing it to a $2.50 clock that doesn't forget as its power never goes out. With as infrequently as the writes happen it will be 100 years before any of them quit but I like to learn and use what I hope is good engineering.

    metron9 I downloaded the atmel info but haven't read it yet.

    Again thanks

    Randy
Sign In or Register to comment.