This is the mail archive of the crossgcc@sources.redhat.com mailing list for the crossgcc project.
See the CrossGCC FAQ for lots more information.
Index Nav: | [Date Index] [Subject Index] [Author Index] [Thread Index] | |
---|---|---|
Message Nav: | [Date Prev] [Date Next] | [Thread Prev] [Thread Next] |
Other format: | [Raw text] |
I've found a bug in the gcc build on http://www.davehylands.com/avi/index.htm that I've been trying. This isn't just an inconvenience thing, but a matter of incorrectly generated code when the -fomit-frame-pointer flag is on. I normally have that flag on, since gdb does not need the frame pointer for debugging, and without it the compiler saves a few instructions and cycles, and has another free register to use. But with it enabled, the compiler produces incorrect code (example below) - it reads function parameters from the wrong place, and it uses incorrect addresses for local variables. I notice (from http://www.davehylands.com/avi/compile_instructions_for_gcc.htm ) that this build has a patch called gcc-3.3.1-coldfire-frame.patch.txt (available from Avi's site) - I don't know if this is a standard or commonly used patch, but it seems to provide the "interrupt" attribute (which is essential for my program - I am running bare-bones without an OS on one of our own cards, and I much prefer the "interrupt" attribute to writing assembly wrappers). I don't know if the patch is related to the problem or not. An example of the problem is the function: // ************************* extern void sendMessage(char *p); void sendDec(unsigned long val) { /* Convert a long int to decimal and send it. */ char s[12]; char *p = &s[11]; *p-- = 0; if (val == 0) { *p-- = '0'; } else { while (val) { *p-- = (val % 10) + '0'; val /= 10; }; }; sendMessage((p+1)); } // ************************* When compiled with gcc 2.95 and -fomit-frame-pointer, the listing starts: 93:utils.c **** void sendDec(unsigned long int val) { 446 .LM60: 68K GAS page 9 447 017c 514F subq.w #8,%sp 448 017e 514F subq.w #8,%sp 449 0180 48E7 3020 movm.l #0x3020,-(%sp) 450 0184 242F 0020 move.l 32(%sp),%d2 94:utils.c **** /* Convert a long int to decimal and send it. */ 95:utils.c **** 96:utils.c **** char s[12]; 452 .LM61: 453 .LBB11: 97:utils.c **** char *p = &s[11]; 455 .LM62: 456 0188 41EF 0017 lea (23,%sp),%a0 98:utils.c **** 99:utils.c **** *p-- = 0; 458 .LM63: 459 018c 4210 clr.b (%a0) 460 018e 5388 subq.l #1,%a0 That code works fine. But if I compile it using the patched 3.3.1 and -fomit-frame-pointer, the listing starts: 93:utils.c **** void sendDec(dword val) { 308 .loc 1 93 0 309 0188 514F subq.w #8,%sp 310 018a 514F subq.w #8,%sp 311 .LCFI6: 312 018c 2F02 move.l %d2,-(%sp) 313 .LCFI7: 314 018e 242F 0014 move.l 20(%sp),%d2 94:utils.c **** /* Convert a long int to decimal and send it. */ 95:utils.c **** 96:utils.c **** char s[12]; 97:utils.c **** char *p = &s[11]; 315 .loc 1 97 0 316 .LBB10: 317 0192 41EF 000B lea (11,%sp),%a0 98:utils.c **** 99:utils.c **** *p-- = 0; 318 .loc 1 99 0 319 0196 4210 clr.b (%a0) 320 0198 5388 subq.l #1,%a0 The parameter is being read from the wrong place on the stack, and the pointer p is set incorrectly. If I don't have -fomit-frame-pointer, the code is correct - even with -O3 and a few other optomisations turned on. David Brown System Developer WestControl a.s Norway "Utvikling er kunsten av å vikle seg ut av det man har viklet seg inn i" ------ Want more information? See the CrossGCC FAQ, http://www.objsw.com/CrossGCC/ Want to unsubscribe? Send a note to crossgcc-unsubscribe@sources.redhat.com
Index Nav: | [Date Index] [Subject Index] [Author Index] [Thread Index] | |
---|---|---|
Message Nav: | [Date Prev] [Date Next] | [Thread Prev] [Thread Next] |