• AVR Freaks

Hot!XC8 Optimization Bug

Author
MB1
New Member
  • Total Posts : 10
  • Reward points : 0
  • Joined: 2007/06/21 15:26:18
  • Location: 0
  • Status: offline
2020/10/17 13:02:10 (permalink)
0

XC8 Optimization Bug

Applies at least to Versions 2.10 and 2.30
 
Writing to TMR5 (16 bit write) behaves properly with optimization level '0' and incorrectly with optimization level 's'
 
  With Optimization level set to '0'
 30660 ;onewire.c: 929: TMR5 = 0;
 30661 00585C 0E00 movlw 0
 30662 00585E 6EC2 movwf 194,c ;volatile
 30663 005860 0E00 movlw 0
 30664 005862 6EC1 movwf 193,c ;volatile
 
With Optimization level set to 's'
 73563 ; BSR set to: 1
 73564 ;onewire.c: 723: TMR5 = 0;
 73565 01BF5C 6AC1 clrf 193,c ;volatile
 73566 01BF5E 6AC2 clrf 194,c ;volatile
 73567 01BF60 i1l27794:

 
As seen in the assembly listing the write order to TMR5H and TMR5L is correct for level '0' 
and incorrect for level 's' optimization. Strange thing is only global optimization setting seems
to cause problem, if I set file optimization to '0' but global optimization is 's' the problem persists.
Workaround is to do two separate writes, TMR5H then TMR5L
#1

18 Replies Related Threads

    jtemples
    عُضْوٌ جَدِيد
    • Total Posts : 12019
    • Reward points : 0
    • Joined: 2004/02/13 12:31:19
    • Location: Southern California
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/17 13:11:25 (permalink)
    +2 (2)
    The compiler does not know anything about the requirements of peripherals.  If a peripheral  needs a specific write order, it's your responsibility to write that code.  The fact that it happens to work with a particular compiler setting doesn't mean it's a bug if it happens not to work with another setting.
    #2
    MB1
    New Member
    • Total Posts : 10
    • Reward points : 0
    • Joined: 2007/06/21 15:26:18
    • Location: 0
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/17 13:24:12 (permalink)
    0
    I agree with your statement, but then the 16 bit definition of that register should probably not be in the
    .h file if the writes to it are not going to be properly handled.
    #3
    jtemples
    عُضْوٌ جَدِيد
    • Total Posts : 12019
    • Reward points : 0
    • Joined: 2004/02/13 12:31:19
    • Location: Southern California
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/17 14:22:14 (permalink)
    +1 (1)
    No, you don't want a compiler that imposes restrictions to try to protect you from yourself.
    #4
    ric
    Super Member
    • Total Posts : 28713
    • Reward points : 0
    • Joined: 2003/11/07 12:41:26
    • Location: Australia, Melbourne
    • Status: online
    Re: XC8 Optimization Bug 2020/10/17 14:26:07 (permalink)
    +2 (2)
    However I agree with MB1.
    The definition to access the timer register as 16 bit should not exist if it's not safe to use. Leave the standard definitions for the upper and lower 8 bit registers.

    I also post at: PicForum
    Links to useful PIC information: http://picforum.ric323.co...opic.php?f=59&t=15
    NEW USERS: Posting images, links and code - workaround for restrictions.
    To get a useful answer, always state which PIC you are using!
    #5
    1and0
    Access is Denied
    • Total Posts : 11353
    • Reward points : 0
    • Joined: 2007/05/06 12:03:20
    • Location: Harry's Gray Matter
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/17 17:43:28 (permalink)
    0
    I understand the C Standard does not require the compiler to read and write multiple-byte variables in a certain order. Given the requirements of the PIC peripherals, why can't the XC8 Compiler be a bit smarter when reading and writing to the TMRx register pairs? I would go a bit further, why not read and write multiple-byte variables in a certain order? What would be so bad with that? It does not violate the C Standard.
    #6
    jtemples
    عُضْوٌ جَدِيد
    • Total Posts : 12019
    • Reward points : 0
    • Joined: 2004/02/13 12:31:19
    • Location: Southern California
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/17 17:54:33 (permalink)
    0
    What if there was a register that needed to be written the opposite of the "certain order"?
    #7
    1and0
    Access is Denied
    • Total Posts : 11353
    • Reward points : 0
    • Joined: 2007/05/06 12:03:20
    • Location: Harry's Gray Matter
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/17 17:57:35 (permalink)
    +2 (2)
    jtemples
    What if there was a register that needed to be written the opposite of the "certain order"?

    Then do NOT define a multiple-byte identifier for that SFR register(s). ;)
     
    #8
    1and0
    Access is Denied
    • Total Posts : 11353
    • Reward points : 0
    • Joined: 2007/05/06 12:03:20
    • Location: Harry's Gray Matter
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/17 18:00:40 (permalink)
    +2 (2)
    MB1
    Workaround is to do two separate writes, TMR5H then TMR5L

    Use the READTIMERx() and WRITETIMERx() macros provided by XC8. These guarantee the correct byte order is used.
    #9
    jtemples
    عُضْوٌ جَدِيد
    • Total Posts : 12019
    • Reward points : 0
    • Joined: 2004/02/13 12:31:19
    • Location: Southern California
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/17 18:06:11 (permalink)
    0
    ...and/or write to the 16-bit register via pointers if you need that abstraction.
    #10
    1and0
    Access is Denied
    • Total Posts : 11353
    • Reward points : 0
    • Joined: 2007/05/06 12:03:20
    • Location: Harry's Gray Matter
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/17 18:10:10 (permalink)
    0
    My point was if the compiler reads and writes in a "certain order" there would be a gain and certainty. Nothing to lose, as 8-bit PICs go.
    #11
    Murton Pike Systems
    Senior Member
    • Total Posts : 49
    • Reward points : 0
    • Joined: 2020/09/10 02:13:01
    • Location: 0
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/17 19:47:52 (permalink)
    0
    Sods law states if there is a way for it to be coded wrong then it will !
     
    #12
    MB1
    New Member
    • Total Posts : 10
    • Reward points : 0
    • Joined: 2007/06/21 15:26:18
    • Location: 0
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/18 01:04:28 (permalink)
    -1 (1)
    1and0
    MB1
    Workaround is to do two separate writes, TMR5H then TMR5L

    Use the READTIMERx() and WRITETIMERx() macros provided by XC8. These guarantee the correct byte order is used.



    WRITETIMER5() unfortunately does not exist, which if I remember correctly is why I used the 16 Bit declaration in the first place.
    #13
    ric
    Super Member
    • Total Posts : 28713
    • Reward points : 0
    • Joined: 2003/11/07 12:41:26
    • Location: Australia, Melbourne
    • Status: online
    Re: XC8 Optimization Bug 2020/10/18 01:31:48 (permalink)
    +1 (1)
    This is WRITETIMER3(), so you can just edit it to make your own
    #define WRITETIMER3(x) ((void)(TMR3H=((x)>>8),TMR3L=((x)&0xFF)))

     

    I also post at: PicForum
    Links to useful PIC information: http://picforum.ric323.co...opic.php?f=59&t=15
    NEW USERS: Posting images, links and code - workaround for restrictions.
    To get a useful answer, always state which PIC you are using!
    #14
    1and0
    Access is Denied
    • Total Posts : 11353
    • Reward points : 0
    • Joined: 2007/05/06 12:03:20
    • Location: Harry's Gray Matter
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/18 10:22:44 (permalink)
    -1 (1)
    Or use this
    #define WRITETIMER(n,x) ((void)(TMR##n##H=((x)>>8),TMR##n##L=((x)&0xFF)))


    Excerpt from pic18.h
    /* Accurate read/write macros for 16-Bit timers */
    /*** please note, the timer needs to be enabled ***
     *** to handle 16-Bit read/write operations for ***
     *** these routines to be of benefit ***/
    #define WRITETIMER0(x) ((void)(TMR0H=((x)>>8),TMR0L=((x)&0xFF)))
    #define WRITETIMER1(x) ((void)(TMR1H=((x)>>8),TMR1L=((x)&0xFF)))
    #define WRITETIMER3(x) ((void)(TMR3H=((x)>>8),TMR3L=((x)&0xFF)))
    #define READTIMER0() (TMR0)
    #define READTIMER1() (TMR1)
    #define READTIMER3() (TMR3)

    shows that the 16-bit reads are little-endian, and the 16-bit writes could be either big- or little-endian.
     
    post edited by 1and0 - 2020/10/18 11:10:07
    #15
    crosland
    Super Member
    • Total Posts : 2059
    • Reward points : 0
    • Joined: 2005/05/10 10:55:05
    • Location: Warks, UK
    • Status: online
    Re: XC8 Optimization Bug 2020/10/18 10:40:45 (permalink)
    +1 (1)
    The compiler knows, for example, how to generate the correct sequence for EEPROM unlocking.
     
    It's perfectly reasonable to expect it to generate the correct sequence for 16 bit registers that are defined in the device header files.
     
    I would open a support ticket and report this as a bug.
    #16
    1and0
    Access is Denied
    • Total Posts : 11353
    • Reward points : 0
    • Joined: 2007/05/06 12:03:20
    • Location: Harry's Gray Matter
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/18 11:13:18 (permalink)
    0
    crosland
    The compiler knows, for example, how to generate the correct sequence for EEPROM unlocking.

    Most of the time; unfortunately, there are cases where BANKSEL is inserted inside the sequence. ;)
     

    It's perfectly reasonable to expect it to generate the correct sequence for 16 bit registers that are defined in the device header files.
     
    I would open a support ticket and report this as a bug.

    They already know; otherwise; there wouldn't be the macros listed in Post #15.
    #17
    ric
    Super Member
    • Total Posts : 28713
    • Reward points : 0
    • Joined: 2003/11/07 12:41:26
    • Location: Australia, Melbourne
    • Status: online
    Re: XC8 Optimization Bug 2020/10/18 12:19:23 (permalink)
    0
    1and0
    Or use this
    #define WRITETIMER(n,x) ((void)(TMR##n##H=((x)>>8),TMR##n##L=((x)&0xFF)))


    Nice. :)

    Excerpt from pic18.h
    /* Accurate read/write macros for 16-Bit timers */
    /*** please note, the timer needs to be enabled ***
     *** to handle 16-Bit read/write operations for ***
     *** these routines to be of benefit ***/
    #define WRITETIMER0(x) ((void)(TMR0H=((x)>>8),TMR0L=((x)&0xFF)))
    #define WRITETIMER1(x) ((void)(TMR1H=((x)>>8),TMR1L=((x)&0xFF)))
    #define WRITETIMER3(x) ((void)(TMR3H=((x)>>8),TMR3L=((x)&0xFF)))
    #define READTIMER0() (TMR0)
    #define READTIMER1() (TMR1)
    #define READTIMER3() (TMR3)

    shows that the 16-bit reads are little-endian, and the 16-bit writes could be either big- or little-endian.

    That's an old version.
    The latest files have a bit more mucking around on the READ defines....:
    /* Accurate read/write macros for 16-Bit timers */
    /*** please note, the timer needs to be enabled ***
     *** to handle 16-Bit read/write operations for ***
     *** these routines to be of benefit ***/
    #define WRITETIMER0(x) ((void)(TMR0H=((x)>>8),TMR0L=((x)&0xFF)))
    #define WRITETIMER1(x) ((void)(TMR1H=((x)>>8),TMR1L=((x)&0xFF)))
    #define WRITETIMER3(x) ((void)(TMR3H=((x)>>8),TMR3L=((x)&0xFF)))
    #define _NO_READTIMER_SUP(n) __attribute__((__unsupported__("The READTIMER" #n "() macro is not available with the current device.")))
    #ifdef TMR0
    #define READTIMER0() (TMR0)
    #else
    _NO_READTIMER_SUP(0) unsigned short __readtimer0(void);
    #define READTIMER0() __readtimer0()
    #endif
    #ifdef TMR1
    #define READTIMER1() (TMR1)
    #else
    _NO_READTIMER_SUP(1) unsigned short __readtimer1(void);
    #define READTIMER1() __readtimer1()
    #endif
    #ifdef TMR3
    #define READTIMER3() (TMR3)
    #else
    _NO_READTIMER_SUP(3) unsigned short __readtimer3(void);
    #define READTIMER3() __readtimer3()
    #endif

     

    I also post at: PicForum
    Links to useful PIC information: http://picforum.ric323.co...opic.php?f=59&t=15
    NEW USERS: Posting images, links and code - workaround for restrictions.
    To get a useful answer, always state which PIC you are using!
    #18
    MB1
    New Member
    • Total Posts : 10
    • Reward points : 0
    • Joined: 2007/06/21 15:26:18
    • Location: 0
    • Status: offline
    Re: XC8 Optimization Bug 2020/10/18 12:38:07 (permalink)
    0
    Should a bug report not also be that there is no timer 5 macro support?
    I am using a PIC18LF67K40
    #19
    Jump to:
    © 2020 APG vNext Commercial Version 4.5