WRITE prob during power cycle 18f6722


Closed Thread
Results 1 to 11 of 11
  1. #1
    Join Date
    Jun 2007
    Posts
    26

    Default WRITE prob during power cycle 18f6722

    latest versions, 18f6722, pickit 2


    ok, heres the deal. Everything is hunky doory until you switch the machine off and on again, It somtimes will write to the eeprom when it shouldn't.

    So I looked at the datasheet and theres several things on this prob. It talks about "WREN" and here at this forum I found this

    ASM
    bsf EECON1, WR
    nop
    bcf EECON1, WREN
    endasm

    the datasheet also talked about several other things so i put them in my inc file

    NOLIST
    ifdef PM_USED
    LIST
    "Error: PM does not support this device. Use MPASM."
    NOLIST
    else
    LIST
    LIST p = 18F6722, r = dec, w = -311, w = -230, f = inhx32
    INCLUDE "P18F6722.INC" ; MPASM Header
    __CONFIG _CONFIG1H, _OSC_HS_1H ; _OSC_XT_1H
    __CONFIG _CONFIG2L, _PWRT_ON_2L & _BOREN_NOSLP_2L & _BORV_1_2L
    __CONFIG _CONFIG2H, _WDT_ON_2H & _WDTPS_512_2H
    __CONFIG _CONFIG3H, _MCLRE_ON_3H
    __CONFIG _CONFIG4L, _LVP_OFF_4L & _XINST_OFF_4L
    NOLIST
    endif
    LIST
    EEPROM_START EQU 0F00000h
    BLOCK_SIZE EQU 64

    Strangly enough I had the same issue with another project and fixed it by getting rid of the power capacitor.


    the WREN I dont really understand, I prefer basic ver asm. can someone help me out here to understand this a bit.

  2. #2
    Join Date
    Jul 2003
    Posts
    2,405


    Did you find this post helpful? Yes | No

    Default

    Strangly enough I had the same issue with another project and fixed it by getting rid of the power capacitor.
    If you have a routine that's writing to EEPROM, and a large value cap on the power rail, it
    may still have enough time to write to EEPROM before the cap discharges after removing
    power.

    Or, are you saying, you get writes on power down without any routine in your code that
    writes to EEPROM?

    the WREN I dont really understand
    WREN is a bit in EECON1, that, when set, allows writes to Flash program or data EEPROM.

    Normally this bit will be set at the start of an EEPROM write routine, and then cleared once
    the write is complete.
    Regards,

    -Bruce
    tech at rentron.com
    http://www.rentron.com

  3. #3
    Join Date
    Jun 2007
    Posts
    26


    Did you find this post helpful? Yes | No

    Default Brown-out or somthing like that

    I have brown-out on and i have tried several settings, but it dosn't help. I believe I need to use WREN and write together. Heres a direct quote from the datasheet.

    "There are conditions when the device may not want to
    write to the data EEPROM memory. To protect against
    spurious EEPROM writes, various mechanisms have
    been implemented. On power-up, the WREN bit is
    cleared. In addition, writes to the EEPROM are blocked
    during the Power-up Timer period (TPWRT,
    parameter 33).

    The write initiate sequence and the WREN bit together
    help prevent an accidental write during brown-out,
    power glitch or software malfunction."

    I believe this is exactly what I need. But its all in ASM.

    CLRF EEADR ; Start at address 0
    CLRF EEADRH ;
    BCF EECON1, CFGS ; Set for memory
    BCF EECON1, EEPGD ; Set for Data EEPROM
    BCF INTCON, GIE ; Disable interrupts
    BSF EECON1, WREN ; Enable writes
    Loop ; Loop to refresh array
    BSF EECON1, RD ; Read current address
    MOVLW 55h ;
    MOVWF EECON2 ; Write 55h
    MOVLW 0AAh ;
    MOVWF EECON2 ; Write 0AAh
    BSF EECON1, WR ; Set WR bit to begin write
    BTFSC EECON1, WR ; Wait for write to complete
    BRA $-2
    INCFSZ EEADR, F ; Increment address
    BRA LOOP ; Not zero, do it again
    INCFSZ EEADRH, F ; Increment the high address
    BRA LOOP ; Not zero, do it again
    BCF EECON1, WREN ; Disable writes
    BSF INTCON, GIE ; Enable interrupts

    The question is how do I only write my two Variables to eeprom if all is well (within voltage range). One of these variables is a byte and the other is a word.

    As to your questions, This is a modification of a machine. I can't remove any capacitors from the power supply like i could in the other project that had the same issue. I would like to resolve this problem once and for all, not for just this project but also for all projects to come.

    I do write to the eeprom. but i do not want to write if the system is powering down or up.

    Thank you for your time....

  4. #4
    Join Date
    Jul 2003
    Posts
    2,405


    Did you find this post helpful? Yes | No

    Default

    I wouldn't bother with assembler since PBP has WRITE. That should be all you need.

    WREN is clear on power-up so I'm not sure how spurious writes would happen at POR.

    You could clear EECON1 at power-up with EECON1 = 0 just in case.

    This 18F part has a high/low voltage detect, comparators, and several settings for the
    brown-out-reset voltage, so you have quite a few options.

    If you have a spare input, and can use it to allow EEPROM writes only when a button is
    pressed, it would be a good test. Maybe even blink an LED before & after an EEPROM
    write. Then you could monitor the LED to see where the un-intended write was taking
    place.
    Regards,

    -Bruce
    tech at rentron.com
    http://www.rentron.com

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


    Did you find this post helpful? Yes | No

    Default

    The code shown from the data sheet will "Refresh" the entire EEPROM space.
    It's a procedure that should only be done once every couple month/years in order to meet the 40 year data retention spec. I don't think that's what you're looking for

    But in that code, you can also see the required Write Sequence that involves setting 3 bits in EECON1, writing 55h AAh to EECON2, before setting the WR bit in EECON1 which actually initiates the write.

    The sequence was designed to prevent any unintentional writes, and it's unlikely that writes to EEPROM on power-up are due to PIC registers not being set properly. And, like Bruce says, that sequence is already included in PBP's WRITE command, so there's no need to do it separately in ASM.

    However, there is a minimum voltage requirement for EEPROM writes. And if you are trying to write to EEPROM immediately on power-up to record the number of times it's been powered on/off for instance, then Large capacitors on the power rail may not have fully charged by the time it starts trying to write. This could cause unpredictable results.

    The current Brown-out detector settings in your config are ...

    _BOREN_NOSLP_2L ; Brown-out Reset enabled in hardware only and disabled in Sleep mode (SBOREN is disabled)

    Using the "No Sleep" BOR mode, implies that you may be using Sleep Mode on your board. Perhaps there's a battery backup that keeps it running when there's no power?

    If that's the case, then BOR will be disabled, and when main power is restored, it may try to write before the voltage is above the minimum.

    _BORV_1_2L ; second highest voltage setting

    The "second highest voltage setting" can switch anywhere between 4.11 and 4.55V. If that particular chip switches at the low end of the range, it could also be writing with a low voltage.

    If any of this is actually relevant to your problem, then a simple pause 1000 (or less) at the beginning should take care of it. Or, any other method that insures voltage is sufficient, before attempting to write.

    HTH,
    DT

  6. #6
    Join Date
    Jun 2007
    Posts
    26


    Did you find this post helpful? Yes | No

    Default I Believe my prob is.....

    The machine I am modifying sends a signal at power down not when powering up(I have a "pause 2000" when powering up). This signal is a glitch. And I do not want to record this signal. It is not always there otherwise I would just subtract it from the total at power up.

    So I'm trying to figure a way to not record this if the voltage is under, lets say 4.5v. The power supply is 5v, so anything under 4.5 would mean it is powering down. It may need to be a bit higher but I'm not sure.

    I kind of thought that was what Brown-out was for, but it dosn't seem to be doing any good.

    I put a loop with a variable to help this problem, and it has cut back alot of the false writes.

    TOTALTEMP=TOTALTEMP+1
    IF TOTALTEMP>200 THEN
    READ 8,MONEY
    IF MONEY <> CREDIT THEN
    WRITE 8,CREDIT
    GOSUB WRTOTAL
    TOTALTEMP=0
    ELSE
    ENDIF
    TOTALTEMP=0
    ELSE
    ENDIF

    But it still dose a false write every once in awhile, before it was almost every shutdown.

    Also, There is no battery backup. when this machine shuts down, the pic also is shutting down. however the pic can run as low as I think 2 volts. so any false readings from a pin could cause the pic to write and I dont want to.
    Last edited by jason; - 18th August 2007 at 00:31. Reason: update

  7. #7
    Join Date
    Nov 2003
    Location
    Wellton, U.S.A.
    Posts
    5,924


    Did you find this post helpful? Yes | No

    Default

    A similar problem was talked about here. http://www.picbasic.co.uk/forum/showthread.php?t=5649
    The question was how to write data as the power was being cut. Same thing but backwards for you.

    Use a comparator to monitor the voltage and make your own brown out control.

    Use a backup battery and monitor the machine power, when machine power is cut the PIC will then go into a shut down sequence shutting off the battery power.

    I think this is the closest thing to "fail safe" you will get, think of a good UPS system with voltage monitoring on a server.
    Dave
    Always wear safety glasses while programming.

  8. #8
    Join Date
    Jun 2007
    Posts
    26


    Did you find this post helpful? Yes | No

    Default And the price goes up.......

    this is to be fabricated by the hundreds, price is an issue.

    What about the onboard "HLVD"

    But then again its all in ASM. It talks about these steps

    1. Write the value to the HLVDL3:HLVDL0 bits that
    selects the desired HLVD trip point.
    2. Set the VDIRMAG bit to detect high voltage
    (VDIRMAG = 1) or low voltage (VDIRMAG = 0).
    3. Enable the HLVD module by setting the
    HLVDEN bit.
    4. Clear the HLVD interrupt flag (PIR2<2>), which
    may have been set from a previous interrupt.
    5. Enable the HLVD interrupt if interrupts are
    desired by setting the HLVDIE and GIE bits
    (PIE2<2> and INTCON<7>). An interrupt will not
    be generated until the IRVST bit is set.

    How do I write these values that it needs. Can I do it in PicBasic pro?

  9. #9
    Join Date
    Jul 2003
    Posts
    2,405


    Did you find this post helpful? Yes | No

    Default

    How do I write these values that it needs. Can I do it in PicBasic pro?
    REGISTER = VALUE.

    I.E. HLVDCON = %01010101. Assuming %01010101 is the value you want placed in the
    register.

    Doesn't get much easier than that eh..;o}
    Regards,

    -Bruce
    tech at rentron.com
    http://www.rentron.com

  10. #10
    Join Date
    Mar 2009
    Location
    Colorado
    Posts
    378


    Did you find this post helpful? Yes | No

    Default PBP to use the HLVD but one statement doesn't execute??

    Quote Originally Posted by jason View Post
    this is to be fabricated by the hundreds, price is an issue.

    What about the onboard "HLVD"

    But then again its all in ASM. It talks about these steps

    1. Write the value to the HLVDL3:HLVDL0 bits that
    selects the desired HLVD trip point.
    2. Set the VDIRMAG bit to detect high voltage
    (VDIRMAG = 1) or low voltage (VDIRMAG = 0).
    3. Enable the HLVD module by setting the
    HLVDEN bit.
    4. Clear the HLVD interrupt flag (PIR2<2>), which
    may have been set from a previous interrupt.
    5. Enable the HLVD interrupt if interrupts are
    desired by setting the HLVDIE and GIE bits
    (PIE2<2> and INTCON<7>). An interrupt will not
    be generated until the IRVST bit is set.

    How do I write these values that it needs. Can I do it in PicBasic pro?
    I have been working with the onboard HLVD module in a 18F4550 to use it as a low voltage monitor for my application. I am posting my current PBP code below that is suppose to do steps 1-5 you list above that are called out in the Data Sheet. I am prettry sure this is the right code, but it wasn't working, so I ran an ICD on it and discovered that when it gets to this procedure which is located in my main program loop, the first HLVDCON statement executes to clear HLVDCON.4, however the next statement (HLVDCON = %00011101) which is suppose to perform steps 1-3 in your above listing, doesn't execute....nor do any of the remaining statements in this process block execute...instead the program always jumps to an Interrupt Service Routine that is suppose to service a DT_INTS-18 interrupt triggered by a real-time clock. However the RTC interrupt isn't timed to happen when this happens. I can't figure out why this this HLVDCON statement is not executing and the rest of this block is not executing in the main loop before the interrupt happens.

    Can anyone advise me what is happening here and how to fix it??

    Code:
    ' Test for low battery conditon
            ' Set registers for using HLVD feature
                HLVDCON.4 = 0   'Disable the module by clearing HLVDCON.4
                ' Set the trip point at Vdd=4.4 vdc by setting HLVD3:HLVDL0=1101
                ' Set VDIRMAG=0 (HLVDCON.7) to detect low voltage transition
                ' Enable the HLVD module (HLVDCON.4=1)
                  HLVDCON = %00011101
                ' Clear the HLVDIF interrupt flage (PIR2<2>)
                  PIR2.2 = 0 
                ' Enable the HLVD interrupt
                  PIE2.2 = 1
                  INTCON.7 = 1
                ' Set IRVST bit (HLVDCON.5 =1) to allow interrupt generation
                  HLVDCON.5 =1
            If PIR2.2 =1 THEN ' Test for HLVD interrupt (HLVDIF bit = 1)
               For I = 0 TO 4 ' Blink the RED LED 5X as low battery warning
                   High LED_RED   
                   Pause 500
                   LOW LED_RED
                   pause 500
               next
            ENDIF
    Last edited by jellis00; - 22nd May 2010 at 03:33. Reason: Code correction

  11. #11
    Join Date
    Mar 2009
    Location
    Colorado
    Posts
    378


    Did you find this post helpful? Yes | No

    Wink Problem solved!

    For those people who might visit this thread I will post the solution to using the HLVD module as I was able to resolve with some offline support from Darrel Taylor.

    First, you need to make sure you have setup a DT_INTS-18 interrupt for the HLVD module by inclusion of this code:
    Code:
    ASM
    INT_LIST  macro    ; IntSource,         Label,  Type, ResetFlag?
            ;INT_Handler   USB_Handler
            INT_Handler   HLVD_INT,        _LowVolt, PBP,  yes
        endm
        INT_CREATE                ; Creates the interrupt processor
    ENDASM
    Then you need to insert this in your code ahead of the main loop to setup the use of the HLVD module.

    Code:
           
     ' Set registers for using HLVD feature
              ' Step 1-Disable the module by clearing HLVDCON.4
            		HLVDCON.4 = 0 	' Implement Step 1           
              ' Step2 HLVD3:HLVDL0=1101 'Set the trip point at Vdd=4.33 vdc
              ' Step3 HLVDCON.7=0 'Set VDIRMAG=0 to detect low voltage transition
              ' Step4 HLVDCON.4=1 'Enable the HLVD module
                  	HLVDCON = %00011101   'Implements Steps 2-4
              ' Clear the HLVDIF interrupt flag (PIR2<2>)
     		        PIR2.2 = 0 
              ' Enable the HLVD interrupt
    @    INT_ENABLE   HLVD_INT ; enable HLVD interrupt
    Then you need to create an interrupt service routine (ISR) nead the end of your code as follows:
    Code:
    LowVolt:
       ' Blink LED_RED 5X to indicate Low Battery voltage detected
            For i = 0 to 4
               HIGH LED_RED
               Pause 500
               LOW LED_RED
               PAUSE 500
            Next
    @ INT_DISABLE HLVD_INT      ; This statement very important, else code will lockup on exit
                                                ; from the ISR to main program. 
            ' Resume Main Program
    @ INT_RETURN
    '------------------{ End of Interrupt Handlers }-------------------------
    Hope this might help someone!

Similar Threads

  1. WRITE: One more PBP 2.60 Surprise ...
    By Acetronics2 in forum mel PIC BASIC Pro
    Replies: 22
    Last Post: - 26th August 2009, 09:10
  2. Battery powered applications
    By NavMicroSystems in forum Off Topic
    Replies: 7
    Last Post: - 22nd June 2009, 07:12
  3. Need the code to write to a memory
    By Hamlet in forum General
    Replies: 0
    Last Post: - 20th August 2007, 00:22
  4. Changing declared variables names on the fly
    By jessey in forum mel PIC BASIC Pro
    Replies: 15
    Last Post: - 16th December 2006, 06:34
  5. Storing Strings using the Write command
    By BobP in forum mel PIC BASIC Pro
    Replies: 2
    Last Post: - 1st November 2005, 11:31

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