|
Page 1 of 1
|
[ 13 posts ] |
|
3.05: issue in switch statement with ubyte and array
| Author |
Message |
|
mightor
Moderator
Joined: Wed Mar 05, 2008 8:14 am Posts: 2906 Location: Rotterdam, The Netherlands
|
 Re: 3.05: issue in switch statement with ubyte and array
Can you report this issue to the usual email address?  - Xander
_________________| Some people, when confronted with a problem, think, "I know, I'll use threads," | and then two they hav erpoblesms. (@nedbat)| My Blog: I'd Rather Be Building Robots| ROBOTC 3rd Party Driver Suite: [ Project Page]
|
| Thu Jan 19, 2012 2:33 pm |
|
 |
|
MHTS
Guru
Joined: Sun Nov 15, 2009 5:46 am Posts: 1023
|
 Re: 3.05: issue in switch statement with ubyte and array
RobotC seems to confuse easily between signed and unsigned values. I'd bet the ubyte somehow got converted to a signed 16-bit value in the switch statement. Just for fun if you have time, try this and see if it works.
|
| Thu Jan 19, 2012 6:21 pm |
|
 |
|
MHTS
Guru
Joined: Sun Nov 15, 2009 5:46 am Posts: 1023
|
 Re: 3.05: issue in switch statement with ubyte and array
I encountered this bug before. It was a 16-bit value not an ubyte. But whenever I defined something that's the most significant bit, the code doesn't work. So it has something to do with signed and unsigned. At that time, I thought it was my fault because there is no "unsigned" 16-bit value in RobotC. But since you reproduced this issue with 8-bit, I think it is a similar issue.
|
| Fri Jan 20, 2012 4:03 am |
|
 |
|
Dick Swan
Creator
Joined: Fri Feb 09, 2007 9:21 am Posts: 613
|
 Re: 3.05: issue in switch statement with ubyte and array
Yes. This was a bug in the compiler code generation. The fix is made and will hopefully be in the next update release.
|
| Fri Jan 20, 2012 10:50 am |
|
 |
|
MHTS
Guru
Joined: Sun Nov 15, 2009 5:46 am Posts: 1023
|
 Re: 3.05: issue in switch statement with ubyte and array
Sorry, 0x80 sign extended to 16-bit is not -1, it should have been -128 (0xff80). So it might work with either case 0xff80 or case -128 if you are still curious to try it.
|
| Fri Jan 20, 2012 2:50 pm |
|
 |
|
MHTS
Guru
Joined: Sun Nov 15, 2009 5:46 am Posts: 1023
|
 Re: 3.05: issue in switch statement with ubyte and array
I think this bug has been around for a while and not specific to 3.05. I have noticed it a long time ago, but I didn't have time to narrow it down to the conclusion we have now. I believe the compiler might have generated a 16-bit compare instruction that automatically sign extended the 8-bit value that caused this issue.
|
| Sun Jan 22, 2012 12:12 am |
|
 |
|
mightor
Moderator
Joined: Wed Mar 05, 2008 8:14 am Posts: 2906 Location: Rotterdam, The Netherlands
|
 Re: 3.05: issue in switch statement with ubyte and array
Would doing something like this help at all? - Xander
_________________| Some people, when confronted with a problem, think, "I know, I'll use threads," | and then two they hav erpoblesms. (@nedbat)| My Blog: I'd Rather Be Building Robots| ROBOTC 3rd Party Driver Suite: [ Project Page]
|
| Sun Jan 22, 2012 2:50 am |
|
 |
|
MHTS
Guru
Joined: Sun Nov 15, 2009 5:46 am Posts: 1023
|
 Re: 3.05: issue in switch statement with ubyte and array
It's hard to tell. Without knowing how the compiler generated the code, can't tell if that would fix the problem. But of course, you just need to put the code in and try  In any case, Dick said it's already fixed. It's just an exercise for the curious minds.
|
| Sun Jan 22, 2012 5:03 am |
|
 |
|
MHTS
Guru
Joined: Sun Nov 15, 2009 5:46 am Posts: 1023
|
 Re: 3.05: issue in switch statement with ubyte and array
Did test case #8 work?
|
| Sun Jan 22, 2012 1:58 pm |
|
 |
|
MHTS
Guru
Joined: Sun Nov 15, 2009 5:46 am Posts: 1023
|
 Re: 3.05: issue in switch statement with ubyte and array
Hmm, so it is not 16-bit?! Try 32-bit (i.e. case 0xffffff80).
|
| Sun Jan 22, 2012 2:58 pm |
|
 |
|
mightor
Moderator
Joined: Wed Mar 05, 2008 8:14 am Posts: 2906 Location: Rotterdam, The Netherlands
|
 Re: 3.05: issue in switch statement with ubyte and array
 |  |  |  | Code: //////////////////////////////////////////////////////////////////////////////////////////////////////////// // DEFINITIONS //////////////////////////////////////////////////////////////////////////////////////////////////////////// #define HOME_MAP_NBR_X 33 #define HOME_MAP_NBR_Y 20
typedef struct { ubyte info; ubyte reel; ubyte path; ubyte dist; } S_CELL;
typedef struct { ubyte nbr_x; ubyte nbr_y; S_CELL cell[HOME_MAP_NBR_X][HOME_MAP_NBR_Y]; } S_HOME;
//////////////////////////////////////////////////////////////////////////////////////////////////////////// // DECLARATIONS //////////////////////////////////////////////////////////////////////////////////////////////////////////// S_HOME home;
//////////////////////////////////////////////////////////////////////////////////////////////////////////// // CODES //////////////////////////////////////////////////////////////////////////////////////////////////////////// task main() // // // Constants Pool: // //0000: 80FF0000 long "65408" //0004: 255800 string "%X" //0007: 23312078 3830206F 6B00 string "#1 x80 ok" //0011: 23312078 38302065 727200 string "#1 x80 err" //001C: 23322078 3830206F 6B2000 string "#2 x80 ok " //0027: 23322078 38302065 727200 string "#2 x80 err" //0032: 23332078 3830206F 6B00 string "#3 x80 ok" //003C: 23332078 38302065 727200 string "#3 x80 err" //0047: 23342078 3830206F 6B00 string "#4 x80 ok" //0051: 23342078 38302065 727200 string "#4 x80 err" //005C: 23352078 3830206F 6B00 string "#5 x80 ok" //0066: 23352078 38302065 727200 string "#5 x80 err" //0071: 2336202D 31323820 6F6B00 string "#6 -128 ok" //007C: 2336202D 31323820 65727200 string "#6 -128 err" //0088: 2337202D 31206F6B 00 string "#7 -1 ok" //0091: 2337202D 31206572 7200 string "#7 -1 err" //009B: 23382078 46463830 206F6B00 string "#8 xFF80 ok" //00A7: 23382078 46463830 20657272 00 string "#8 xFF80 err" //00B4: // //Constants Summary Items: 18, Size: 180 bytes // //Code segment: main(); Task: 0 // 0000: 11117300 bFloatDuringInactiveMotorPWM = 0 0004: 67180000000000000000 defineMUXes(none, none, none, none, none, none, none, none, none, none, none, none, none, none, none, none) : 0000000000000000 0016: 6767010004 ClearSensors(S1..S4) 001B: 11390000 bMotorReflected[motorA] = 0 001F: 11380001 nMotorPIDSpeedCtrl[motorA] = 1 0023: 11390100 bMotorReflected[motorB] = 0 0027: 11380101 nMotorPIDSpeedCtrl[motorB] = 1 002B: 11390200 bMotorReflected[motorC] = 0 002F: 11380201 nMotorPIDSpeedCtrl[motorC] = 1 { // Display eraseDisplay(); 0033: 9800 eraseDisplay()
int x=0; 0035: 122B2A05020000 G1322 = 0 int y=0; 003C: 122B2B05020000 G1323 = 0 home.cell[0][0].info = 0x80; 0043: 11340280 G01H(byte) = 128 writeDebugStreamLine("%X",home.cell[0][0].info); 0047: 8D2B2E05340200 G1326(long) = G01H(byte) // Convert 'short' to 'long' 004E: EF11320400012B2E05 writeDebugStreamLine("%X", home.cell[0][0].info) writeDebugStreamLine("%X",home.cell[x][y].info); 0057: 2F2B2A052000 BoundsCheck(G1322, 33) 005D: 2F2B2B051300 BoundsCheck(G1323, 20) 0063: AA2B2D052B2A05021400 G1325 = G1322 * 20 006D: 082B2D052B2B05 G1325 += G1323 0074: 0A2B2D05020400 G1325 *= 4 007B: 7D2B2E052D0200 G1326 = addrOf G01H(byte) // Convert to RAM address [3] 0082: 082B2D052B2E05 G1325 += G1326 0089: 8F2B2D053A2D05 G1325 = *G1325 // Convert 'ubyte' to 'short' 0090: 8D2B2E052B2D05 G1326(long) = G1325 // Convert 'short' to 'long' 0097: EF11320400012B2E05 writeDebugStreamLine("%X", home.cell[x][y].info) // test case #1 switch(home.cell[0][0].info) 00A0: 23020280003402000A00 TestAndBranchUnsignedByteVarFar(128 != G01H(byte), L00B2) // case label 128 { case 0x80: writeDebugStreamLine("#1 x80 ok"); break; 00AA: EF1132070000 writeDebugStreamLine("#1 x80 ok") 00B0: 7907 BranchNear(L00B8) // Goto break location (67) default: writeDebugStreamLine("#1 x80 err"); break; 00B2: EF1132110000 L00B2: writeDebugStreamLine("#1 x80 err") } // test case #2 switch(home.cell[x][y].info) 00B8: 2F2B2A052000 L00B8: BoundsCheck(G1322, 33) 00BE: 2F2B2B051300 BoundsCheck(G1323, 20) 00C4: AA2B2D052B2A05021400 G1325 = G1322 * 20 00CE: 082B2D052B2B05 G1325 += G1323 00D5: 0A2B2D05020400 G1325 *= 4 00DC: 7D2B2E052D0200 G1326 = addrOf G01H(byte) // Convert to RAM address [3] 00E3: 082B2D052B2E05 G1325 += G1326 00EA: 992D5C0A3A2D05 G1326H(byte) = *G1325 00F1: 8F2B2E052D5C0A G1326 = G1326H(byte) // Convert 'ubyte' to 'short' 00F8: 25020280002B2E050A00 TestAndBranchIntFar(128 != G1326, L010A) // case label 128 { case 0x80: writeDebugStreamLine("#2 x80 ok "); break; 0102: EF11321C0000 writeDebugStreamLine("#2 x80 ok ") 0108: 7907 BranchNear(L0110) // Goto break location (69) default: writeDebugStreamLine("#2 x80 err"); break; 010A: EF1132270000 L010A: writeDebugStreamLine("#2 x80 err") } // test case #3 switch((ubyte)home.cell[x][y].info) 0110: 2F2B2A052000 L0110: BoundsCheck(G1322, 33) 0116: 2F2B2B051300 BoundsCheck(G1323, 20) 011C: AA2B2D052B2A05021400 G1325 = G1322 * 20 0126: 082B2D052B2B05 G1325 += G1323 012D: 0A2B2D05020400 G1325 *= 4 0134: 7D2B2E052D0200 G1326 = addrOf G01H(byte) // Convert to RAM address [3] 013B: 082B2D052B2E05 G1325 += G1326 0142: 992D5C0A3A2D05 G1326H(byte) = *G1325 0149: 8F2B2E052D5C0A G1326 = G1326H(byte) // Convert 'ubyte' to 'short' 0150: 25020280002B2E050A00 TestAndBranchIntFar(128 != G1326, L0162) // case label 128 { case 0x80: writeDebugStreamLine("#3 x80 ok"); break; 015A: EF1132320000 writeDebugStreamLine("#3 x80 ok") 0160: 7907 BranchNear(L0168) // Goto break location (71) default: writeDebugStreamLine("#3 x80 err"); break; 0162: EF11323C0000 L0162: writeDebugStreamLine("#3 x80 err") } // test case #4 switch(((ubyte)home.cell[x][y].info)) 0168: 2F2B2A052000 L0168: BoundsCheck(G1322, 33) 016E: 2F2B2B051300 BoundsCheck(G1323, 20) 0174: AA2B2D052B2A05021400 G1325 = G1322 * 20 017E: 082B2D052B2B05 G1325 += G1323 0185: 0A2B2D05020400 G1325 *= 4 018C: 7D2B2E052D0200 G1326 = addrOf G01H(byte) // Convert to RAM address [3] 0193: 082B2D052B2E05 G1325 += G1326 019A: 992D5C0A3A2D05 G1326H(byte) = *G1325 01A1: 8F2B2E052D5C0A G1326 = G1326H(byte) // Convert 'ubyte' to 'short' 01A8: 25020280002B2E050A00 TestAndBranchIntFar(128 != G1326, L01BA) // case label 128 { case 0x80: writeDebugStreamLine("#4 x80 ok"); break; 01B2: EF1132470000 writeDebugStreamLine("#4 x80 ok") 01B8: 7907 BranchNear(L01C0) // Goto break location (73) default: writeDebugStreamLine("#4 x80 err"); break; 01BA: EF1132510000 L01BA: writeDebugStreamLine("#4 x80 err") } // test case #5 ubyte ub = home.cell[x][y].info; 01C0: 2F2B2A052000 L01C0: BoundsCheck(G1322, 33) 01C6: 2F2B2B051300 BoundsCheck(G1323, 20) 01CC: AA2B2D052B2A05021400 G1325 = G1322 * 20 01D6: 082B2D052B2B05 G1325 += G1323 01DD: 0A2B2D05020400 G1325 *= 4 01E4: 7D2B2E052D0200 G1326 = addrOf G01H(byte) // Convert to RAM address [3] 01EB: 082B2D052B2E05 G1325 += G1326 01F2: 9934580A3A2D05 G1324H(byte) = *G1325 switch(ub) 01F9: 230202800034580A0A00 TestAndBranchUnsignedByteVarFar(128 != G1324H(byte), L020B) // case label 128 { case 0x80: writeDebugStreamLine("#5 x80 ok"); break; 0203: EF11325C0000 writeDebugStreamLine("#5 x80 ok") 0209: 7907 BranchNear(L0211) // Goto break location (75) default: writeDebugStreamLine("#5 x80 err"); break; 020B: EF1132660000 L020B: writeDebugStreamLine("#5 x80 err") } // test case #6 switch(home.cell[x][y].info) 0211: 2F2B2A052000 L0211: BoundsCheck(G1322, 33) 0217: 2F2B2B051300 BoundsCheck(G1323, 20) 021D: AA2B2D052B2A05021400 G1325 = G1322 * 20 0227: 082B2D052B2B05 G1325 += G1323 022E: 0A2B2D05020400 G1325 *= 4 0235: 7D2B2E052D0200 G1326 = addrOf G01H(byte) // Convert to RAM address [3] 023C: 082B2D052B2E05 G1325 += G1326 0243: 992D5C0A3A2D05 G1326H(byte) = *G1325 024A: 8F2B2E052D5C0A G1326 = G1326H(byte) // Convert 'ubyte' to 'short' 0251: 25020280FF2B2E050A00 TestAndBranchIntFar(-128 != G1326, L0263) // case label -128 { case -128: writeDebugStreamLine("#6 -128 ok"); break; 025B: EF1132710000 writeDebugStreamLine("#6 -128 ok") 0261: 7907 BranchNear(L0269) // Goto break location (77) default: writeDebugStreamLine("#6 -128 err"); break; 0263: EF11327C0000 L0263: writeDebugStreamLine("#6 -128 err") } // test case #7 switch(home.cell[x][y].info) 0269: 2F2B2A052000 L0269: BoundsCheck(G1322, 33) 026F: 2F2B2B051300 BoundsCheck(G1323, 20) 0275: AA2B2D052B2A05021400 G1325 = G1322 * 20 027F: 082B2D052B2B05 G1325 += G1323 0286: 0A2B2D05020400 G1325 *= 4 028D: 7D2B2E052D0200 G1326 = addrOf G01H(byte) // Convert to RAM address [3] 0294: 082B2D052B2E05 G1325 += G1326 029B: 992D5C0A3A2D05 G1326H(byte) = *G1325 02A2: 8F2B2E052D5C0A G1326 = G1326H(byte) // Convert 'ubyte' to 'short' 02A9: 250202FFFF2B2E050A00 TestAndBranchIntFar(-1 != G1326, L02BB) // case label -1 { case -1: writeDebugStreamLine("#7 -1 ok"); break; 02B3: EF1132880000 writeDebugStreamLine("#7 -1 ok") 02B9: 7907 BranchNear(L02C1) // Goto break location (79) default: writeDebugStreamLine("#7 -1 err"); break; 02BB: EF1132910000 L02BB: writeDebugStreamLine("#7 -1 err") } // test case #8 switch(home.cell[x][y].info) 02C1: 2F2B2A052000 L02C1: BoundsCheck(G1322, 33) 02C7: 2F2B2B051300 BoundsCheck(G1323, 20) 02CD: AA2B2D052B2A05021400 G1325 = G1322 * 20 02D7: 082B2D052B2B05 G1325 += G1323 02DE: 0A2B2D05020400 G1325 *= 4 02E5: 7D2B2E052D0200 G1326 = addrOf G01H(byte) // Convert to RAM address [3] 02EC: 082B2D052B2E05 G1325 += G1326 02F3: 992D5C0A3A2D05 G1326H(byte) = *G1325 02FA: 8F2B2E052D5C0A G1326 = G1326H(byte) // Convert 'ubyte' to 'short' 0301: 8D2B2E052B2E05 G1326(long) = G1326 // Convert 'short' to 'long' 0308: 24023200002B2E050900 TestAndBranchLongFar(65408 != G1326(long), L0319) // case label 65408 { case 0xFF80:writeDebugStreamLine("#8 xFF80 ok"); break; 0312: EF11329B0000 writeDebugStreamLine("#8 xFF80 ok") 0318: FE Return() // Replace 'bra' default: writeDebugStreamLine("#8 xFF80 err"); break; 0319: EF1132A70000 L0319: writeDebugStreamLine("#8 xFF80 err") 031F: FE Return() // main() 0000: FE Return() // _main__() |  |  |  |  |
_________________| Some people, when confronted with a problem, think, "I know, I'll use threads," | and then two they hav erpoblesms. (@nedbat)| My Blog: I'd Rather Be Building Robots| ROBOTC 3rd Party Driver Suite: [ Project Page]
|
| Sun Jan 22, 2012 3:19 pm |
|
 |
|
MHTS
Guru
Joined: Sun Nov 15, 2009 5:46 am Posts: 1023
|
 Re: 3.05: issue in switch statement with ubyte and array
Ah, just as I expected the following compare instruction is treating the ubyte as "int" which really means "signed short". The case 0xff80 doesn't work because the compiler is generating a different instruction. Xander, can you tell us how you generated the assembly listing?  That's useful to debug compiler issues. [EDIT]: Ah never mind, found it. "View->Assembly (F9)".
|
| Sun Jan 22, 2012 3:32 pm |
|
 |
|
mightor
Moderator
Joined: Wed Mar 05, 2008 8:14 am Posts: 2906 Location: Rotterdam, The Netherlands
|
 Re: 3.05: issue in switch statement with ubyte and array
Yeah, I hit that by accident once and it's proven quite useful since  - Xander
_________________| Some people, when confronted with a problem, think, "I know, I'll use threads," | and then two they hav erpoblesms. (@nedbat)| My Blog: I'd Rather Be Building Robots| ROBOTC 3rd Party Driver Suite: [ Project Page]
|
| Sun Jan 22, 2012 3:39 pm |
|
|
|
Page 1 of 1
|
[ 13 posts ] |
|
Who is online |
Users browsing this forum: mightor and 1 guest |
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot post attachments in this forum
|
|