wrote: > There seems to be some confusion here. We got the eval package through our > distributor, and they told us that this was a good deal because we get (and > I quote) "...a years support & free upgrades for a year". > > Now a Metrowerks representative is contradicting that. I don't know your circumstances. There may be extenuating circumstances. This needs to be handled on a case by case basis. > Of course, I don't know who is at fault here, but I do not like what I am > hearing. > > It now looks like we are obliged to pay the full price just to be able to > create production intent code. Whatever else, this is not a good public > relations exercise by Metrowerks/Motorola. I know that Metrowerks has historically done the right thing for our customers and has always been fair. I just can't comment, without knowing all of the details and your case/circumstance may be unique. If you can send me more information, I'd be happy to work with you to find a fair and equitable solution. Ron -- Ron Liechty, Ombudsman for Metrowerks Corporation |
|
Re: CodeWarrior 4 Upgrading
Started by ●September 30, 2002
Reply by ●October 1, 20022002-10-01
The work-around for this bug is described below: 1) For every build target in every product, select "Write constant data to .rodata section" in the "{Target} Settings > Code Generation > M56800 Processor" settings. 2) For every build target in every product, edit the "linker.cmd" file so that every place that has a ".data" section will also have the corresponding ".rodata" section. Example: #******************************************************************************* .ApplicationConstData : { const.c (.rodata) # <==== ADDED for bug fix const.c (.data) appconstP.c (.rodata) # <==== ADDED for bug fix appconstP.c (.data) } > .pConstFlash #******************************************************************************* Regards, Art Johnson Senior Systems Analyst PMC Prime Mover Controls Inc. 3600 Gilmore Way Burnaby, B.C., Canada V5G 4R8 Phone: 604 433-4644 FAX: 604 433-5570 Email: http://www.pmc-controls.com -----Original Message----- From: Roberts, Drew [mailto:] Sent: Tuesday, October 01, 2002 6:49 AM To: Art Johnson Subject: RE: [motoroladsp] Re: CodeWarrior 4 Upgrading Art I agree with you about upgrading and its cost (or costs by not upgrading), but version 5, although a step up is causing other problems. The "new" feature you discuss, regarding const data, is interesting. We are using 805's and 807's running on internal memory and noticed the same thing. What is the workaround? It is not causing us a problem at the moment, but the 805 project is new and I'm sure that having the const data taking up internal ram will bite us in the end. Thanks Drew Roberts Software Project Engineer Nordson Corp. -----Original Message----- From: Art Johnson [mailto:] Sent: Tuesday, October 01, 2002 9:22 AM To: wdhaan; Cc: Kevin Ackerley (E-mail); Ed Baillie (E-mail); Greg Clark Subject: RE: [motoroladsp] Re: CodeWarrior 4 Upgrading While I agree that CodeWarrior 5 produces poorer code than 4.0.2 in this example, when changing data in any shared resource (like a GPIO port or globally shared memory), one should never assume that the compiler will generate code that performs the operation atomically (ie as one indivisible operation). This is particularly important when you are using a RealTime Operating System (RTOS) (we use the DSPOS RTOS in all our applications). The generally accepted way of coding to prevent this sort of problem with a shared resource is shown by the following example from one of our programs: #define Sci0_Tx_Connect( ) \ { \ register WORD interrupt; \ interrupt = Disable_Int(); \ g_p_dspregs->pwma.pmout &= ~SCI0_TX_ENABLE_BIT; \ Enable_Int(interrupt); \ } #define Sci0_Tx_Disconnect( ) \ { \ register WORD interrupt; \ interrupt = Disable_Int(); \ g_p_dspregs->pwma.pmout |= SCI0_TX_ENABLE_BIT; \ Enable_Int(interrupt); \ } The functions Disable_Int() and Enable_Int() are provided by the DSPOS library. In this example, we are using one output on PWMA to control the Transmit Enable pin of an RS-485 transceiver for the SCI0 serial port. In any case, as I mentioned before, the very serious bugs that exist in CodeWarrior 4.x and earlier mean that you are taking a big risk of having your program crash in an unpredictable manner. We stumbled upon the "local variable bug inside a function" almost by accident. It was discovered when we were tracking down a completely different CodeWarrior bug. Our software could easily have been sent out with this "time bomb" embedded in it. For the above reasons, anyone with an older version of CodeWarrior should upgrade to version 5.0 with the 5.0.2 patch. I agree with you, that in my 26+ years experience I have never seen a compiler as buggy as CodeWarrior. While no product this complex is ever "perfect", the bugs we keep finding go way beyond what is acceptable. The Metrowerks compiler writers apparently don't even understand basic ANSI C concepts like the meaning of the keywords "volatile" or "const". This is not exotic, high-level stuff, it's basically kindergarten-level C programming. You might expect these sorts of problems in Version 1.0 of some product, but they should not exist in a "mature" product like Version 5.0 (which we recently had to buy to get some other bugs fixed). They even deliberately introduced a bug into Version 5.0 (Compiler/linker puts const data into X RAM) that contravenes the ANSI C standard meaning of "const". They refused to fix this bug (they think it's actually a "new, improved feature"), but gave us a work-around that cost me weeks of work to change every build target of every project we have here. I'm sure we'll never know how much all this extra time and effort has cost our company (both in direct development costs and lost sales due to delayed product launches), but I'm sure it's well over $100,000. Forcing us to pay for an upgrade rather than issuing patches to version 4.x is just adding insult to injury. Maybe that's the price you have to pay to design in leading-edge devices ... Regards, Art Johnson Senior Systems Analyst PMC Prime Mover Controls Inc. 3600 Gilmore Way Burnaby, B.C., Canada V5G 4R8 Phone: 604 433-4644 FAX: 604 433-5570 Email: http://www.pmc-controls.com -----Original Message----- From: wdhaan [mailto:] Sent: Tuesday, October 01, 2002 12:55 AM To: Subject: [motoroladsp] Re: CodeWarrior 4 Upgrading Hi, Upgrade from Codewarrior 4 to 5? I did it, but I returned to version 4.0.2, due to the following new bug in version 5: *********** C-listing #define GPIOD_BASE 0x13E0 // Table 3-36 for DSP56F807 #define GPIO_D_DR *(WORD *) (0x1+GPIOD_BASE) GPIO_D_DR |= 0x02; // set GPIO-D1 to 1 *********** Assembly listing Codewarrior version 4.0.2 orc #2,X:13e1 *********** Assembly listing Codewarrior version 5 movei #5089,R0 nop move X:(R0),X0 orc #2,X0 ; <=== What happens if here an interrupt occurs? move X0,X:(R0) The problem of this bug is not the additional memory nor the additional execution time, but the problem is if during the main program an interrupt function occurs, which sets f.e. GPIO-D7. In this case the main program resets the GPIO-D7 value, just set by the interrupt function. In this way you get software bugs, which are difficult to reproduce and difficult to find! This is only one bug of my Codewarrior bug collection (most of them have not been solved in version 5). I have sent them to Metrowerks, but only very few have been answered (some after half a year). I have 14 years experience in developing embedded software, but I have never used a compiler with so many bugs as Codewarrior. We paid the full price for Codewarrior version 4 and my supplier understood that I was not willing to pay a cent for version 5, so I got the upgrade to version 5 for free. However now I use version 4.0.2 for compilation and version 5 for debugging Kind regards, Wim de Haan Exendis B.V. W.J. de Haan P.O.box 56, 6710 BB Ede Keesomstraat 4, 6716 AB Ede The Netherlands. Tel: +31- 318 - 676305 _____________________________________ Note: If you do a simple "reply" with your email client, only the author of this message will receive your answer. You need to do a "reply all" if you want your answer to be distributed to the entire group. _____________________________________ About this discussion group: To Join: To Post: To Leave: Archives: http://www.yahoogroups.com/group/motoroladsp More Groups: http://www.dsprelated.com/groups.php3 ">http://docs.yahoo.com/info/terms/ _____________________________________ Note: If you do a simple "reply" with your email client, only the author of this message will receive your answer. You need to do a "reply all" if you want your answer to be distributed to the entire group. _____________________________________ About this discussion group: To Join: To Post: To Leave: Archives: http://www.yahoogroups.com/group/motoroladsp More Groups: http://www.dsprelated.com/groups.php3 ">http://docs.yahoo.com/info/terms/ |
Reply by ●October 1, 20022002-10-01
The "local variable bug inside a function" is described below,
taken from my bug report to Metrowerks: =============================================== Bug #1: Here's the source code in one part of the program that generates incorrect assembly code. The "interrupt" value is a local variable declared inside the function: interrupt = Disable_Int(); Ext_Flash_Write_Word( SST39LF2_4_800A_SDP_ADDR1, SST39LF2_4_800A_SDP_DATA1 ); Ext_Flash_Write_Word( SST39LF2_4_800A_SDP_ADDR2, SST39LF2_4_800A_SDP_DATA2 ); Ext_Flash_Write_Word( SST39LF2_4_800A_SDP_ADDR3, SST39LF2_4_800A_CMD3_PROGRAM ); Ext_Flash_Write_Word( perw_chip_addr, test2 ); Enable_Int(interrupt); Ext_Flash_Write_Word() is a macro. The assembly code generated by CodeWarrior is shown below. Here's the "interrupt = Disable_Int();" code: P:000004DF: E9C80102 jsr 0x000102 P:000004E1: 91F9 move Y0,X:(SP-0x0007) Disable_Int() is at address 0x000102 and the "interrupt" local variable has been assigned to X:(SP-0x0007). . . (Code from the macros not shown) . Now here's the "Enable_Int(interrupt);" code: P:0000052F: 87C70FFF movei #4095,B1 P:00000531: F35460B3 move X:0x60b3,Y1 P:00000533: F15460B2 move X:0x60b2,Y0 P:00000535: 7603 and B1,Y0 P:00000536: 8801 move Y0,R0 P:00000537: B03A moves X:0x003a,X0 P:00000538: D0402000 move X0,X:(R0+0x2000) P:0000053A: 8103 move Y1,Y0 P:0000053B: E9C80106 jsr 0x000106 Enable_Int() is at address 0x000106. Note that the "interrupt" value was loaded from X:0x60b3, not from X:(SP-0x0007) where it was saved!!! =============================================== Regards, Art Johnson Senior Systems Analyst PMC Prime Mover Controls Inc. 3600 Gilmore Way Burnaby, B.C., Canada V5G 4R8 Phone: 604 433-4644 FAX: 604 433-5570 Email: http://www.pmc-controls.com -----Original Message----- From: Wim de Haan [mailto:] Sent: Tuesday, October 01, 2002 7:26 AM To: Art Johnson Subject: RE: [motoroladsp] Re: CodeWarrior 4 Upgrading Dear Art, Thank you for your mail. Of course I understand your solution/work around, with disabling interrupts. However this ought not to be necessary if a processor has an atomic instruction for changing one bit in a port (I admit this is wishful thinking when using Codewarrior). You mentioned a "local variable bug inside a function". Which bug do you exactly mean. Do you mean the bug/undocumented feature, that for a function a kind of stack frame is built at addresses 0x30..0x3F (in assembly called mr0..mr15). This stack frame is saved on stack at next function entry. Or do you mean the bug in the listing below? Kind regards, Wim de Haan Exendis B.V. W.J. de Haan P.O.box 56, 6710 BB Ede Keesomstraat 4, 6716 AB Ede The Netherlands. Tel: +31- 318 - 676305 /* The following interrupt functions are not well compiled, as only the registers used by the interrupt function itself, are stored on stack. However the registers used by library functions called from interrupt functions are not saved on stack. This causes unpredictable strange effects for the main function were those registers are used. */ void Bug1_interrupt_function(void); void Bug2_interrupt_function(void); unsigned U1, U2; #pragma interrupt void Bug1_interrupt_function(void) {// At function entry the LA and LC registers are not saved U1=U2%10;// This uses the ARTREMU16Z asm function, // which uses "do" instruction, so LA and LC are destroyed //Even if LA and LC were saved, HWS is not saved, so interrupt on interrupt can cause //hardware stack overflow } unsigned long L1, L2; #pragma interrupt void Bug2_interrupt_function(void) //EVEN MORE WORSE {// At function entry the Y0, Y1, LA, LC registers are not saved L1=L2/31;// This uses the ARTDIVU32UZ asm function, // which uses Y0 and Y1 registers and "do" instruction, so Y0, Y1, LA, LC are destroyed //Even if Y0, Y1, LA, LC were saved, HWS is not saved, so interrupt on interrupt can cause //hardware stack overflow } GLOBAL FBug1_interrupt_function ORG P: FBug1_interrupt_function: lea (SP)+ move N,X:(SP)+ move Y0,X:(SP)+ move Y1,X:(SP) movei #10,Y1 move X:FU2,Y0 jsr ARTREMU16Z move Y0,X:FU1 pop Y1 pop Y0 pop N rti GLOBAL FBug2_interrupt_function ORG P: FBug2_interrupt_function: lea (SP)+ move N,X:(SP)+ move A0,X:(SP)+ move A1,X:(SP)+ move A2,X:(SP)+ move B0,X:(SP) move B1,X:(SP)+ move B2,X:(SP)+ movei #0,B movei #31,B0 push B0 push B1 move X:FL2+1,A move X:FL2,A0 jsr ARTDIVU32UZ pop pop move A1,X:FL1+1 move A0,X:FL1 pop B2 pop B1 pop B0 pop A2 pop A1 pop A0 pop N rti ; From library file rtrem16.asm ARTREMU16Z: tstw y1 bge nohighbit2 cmp y1,y0 blo Done4 sub y1,y0 bra Done4 nohighbit2: clr A ; clear A move y0,a0 ; save dividend in a0 clr B move y1,b1 ; Save divisor in B do #16,endloop2 div y1,A ; form quotient in a0 remainder in a1 endloop2: tst A bge around4 add B,A ; fix remainder around4: move a1,y0 ; save rem in y0 Done4: rts ; From library file artdivu32uz.asm ARTDIVU32UZ: clr B ; clear register for resulting quotient ; bfset #$0100,omr ; make sure the CC bit is set move a0,y0 move a1,y1 ; move A to y1:y0 move x:(sp-2),a move x:(sp-3),a0 ; load divisor into A bfclr #1,sr ; clear the carry bit move #32,LC ; I don't know why I can't use immediate #32 do LC,endloop rol y0 rol y1 bcc notthisbit asl B bfset #1,b0 bra around notthisbit: asl B around: sub A,B ; If carry is clear, sub was OK. bcc nottoobig ; otherwise, restore B add A,B nottoobig: bfchg #1,sr ; reverse cc bit nop nop endloop: rol y0 rol y1 move y1,A ; move result to A move y0,a0 IF REV_B ; bfclr #$0100,omr ; set CC setting to 36 bits ENDIF rts -----Original Message----- From: Art Johnson [mailto:] Sent: dinsdag 1 oktober 2002 15:22 To: wdhaan; Cc: Kevin Ackerley (E-mail); Ed Baillie (E-mail); Greg Clark Subject: RE: [motoroladsp] Re: CodeWarrior 4 Upgrading While I agree that CodeWarrior 5 produces poorer code than 4.0.2 in this example, when changing data in any shared resource (like a GPIO port or globally shared memory), one should never assume that the compiler will generate code that performs the operation atomically (ie as one indivisible operation). This is particularly important when you are using a RealTime Operating System (RTOS) (we use the DSPOS RTOS in all our applications). The generally accepted way of coding to prevent this sort of problem with a shared resource is shown by the following example from one of our programs: #define Sci0_Tx_Connect( ) \ { \ register WORD interrupt; \ interrupt = Disable_Int(); \ g_p_dspregs->pwma.pmout &= ~SCI0_TX_ENABLE_BIT; \ Enable_Int(interrupt); \ } #define Sci0_Tx_Disconnect( ) \ { \ register WORD interrupt; \ interrupt = Disable_Int(); \ g_p_dspregs->pwma.pmout |= SCI0_TX_ENABLE_BIT; \ Enable_Int(interrupt); \ } The functions Disable_Int() and Enable_Int() are provided by the DSPOS library. In this example, we are using one output on PWMA to control the Transmit Enable pin of an RS-485 transceiver for the SCI0 serial port. In any case, as I mentioned before, the very serious bugs that exist in CodeWarrior 4.x and earlier mean that you are taking a big risk of having your program crash in an unpredictable manner. We stumbled upon the "local variable bug inside a function" almost by accident. It was discovered when we were tracking down a completely different CodeWarrior bug. Our software could easily have been sent out with this "time bomb" embedded in it. For the above reasons, anyone with an older version of CodeWarrior should upgrade to version 5.0 with the 5.0.2 patch. I agree with you, that in my 26+ years experience I have never seen a compiler as buggy as CodeWarrior. While no product this complex is ever "perfect", the bugs we keep finding go way beyond what is acceptable. The Metrowerks compiler writers apparently don't even understand basic ANSI C concepts like the meaning of the keywords "volatile" or "const". This is not exotic, high-level stuff, it's basically kindergarten-level C programming. You might expect these sorts of problems in Version 1.0 of some product, but they should not exist in a "mature" product like Version 5.0 (which we recently had to buy to get some other bugs fixed). They even deliberately introduced a bug into Version 5.0 (Compiler/linker puts const data into X RAM) that contravenes the ANSI C standard meaning of "const". They refused to fix this bug (they think it's actually a "new, improved feature"), but gave us a work-around that cost me weeks of work to change every build target of every project we have here. I'm sure we'll never know how much all this extra time and effort has cost our company (both in direct development costs and lost sales due to delayed product launches), but I'm sure it's well over $100,000. Forcing us to pay for an upgrade rather than issuing patches to version 4.x is just adding insult to injury. Maybe that's the price you have to pay to design in leading-edge devices ... Regards, Art Johnson Senior Systems Analyst PMC Prime Mover Controls Inc. 3600 Gilmore Way Burnaby, B.C., Canada V5G 4R8 Phone: 604 433-4644 FAX: 604 433-5570 Email: http://www.pmc-controls.com -----Original Message----- From: wdhaan [mailto:] Sent: Tuesday, October 01, 2002 12:55 AM To: Subject: [motoroladsp] Re: CodeWarrior 4 Upgrading Hi, Upgrade from Codewarrior 4 to 5? I did it, but I returned to version 4.0.2, due to the following new bug in version 5: *********** C-listing #define GPIOD_BASE 0x13E0 // Table 3-36 for DSP56F807 #define GPIO_D_DR *(WORD *) (0x1+GPIOD_BASE) GPIO_D_DR |= 0x02; // set GPIO-D1 to 1 *********** Assembly listing Codewarrior version 4.0.2 orc #2,X:13e1 *********** Assembly listing Codewarrior version 5 movei #5089,R0 nop move X:(R0),X0 orc #2,X0 ; <=== What happens if here an interrupt occurs? move X0,X:(R0) The problem of this bug is not the additional memory nor the additional execution time, but the problem is if during the main program an interrupt function occurs, which sets f.e. GPIO-D7. In this case the main program resets the GPIO-D7 value, just set by the interrupt function. In this way you get software bugs, which are difficult to reproduce and difficult to find! This is only one bug of my Codewarrior bug collection (most of them have not been solved in version 5). I have sent them to Metrowerks, but only very few have been answered (some after half a year). I have 14 years experience in developing embedded software, but I have never used a compiler with so many bugs as Codewarrior. We paid the full price for Codewarrior version 4 and my supplier understood that I was not willing to pay a cent for version 5, so I got the upgrade to version 5 for free. However now I use version 4.0.2 for compilation and version 5 for debugging Kind regards, Wim de Haan Exendis B.V. W.J. de Haan P.O.box 56, 6710 BB Ede Keesomstraat 4, 6716 AB Ede The Netherlands. Tel: +31- 318 - 676305 |