Hi GCClers,
I searched hard, but couldn't determine conclusively if the C standard
allows to alias a void* pointer with a char* pointer.
If that's not undefined behavior, then the following may be a glitch in
GCC 4.1.0 when compiled with -O2.
Here's the ugly minimal piece of code:
/* ASSUME pointer POINTS TO AN INTEGER THAT SPECIFIES THE INCREMENT
================================================================ */
int increment(int *pointer)
{ return(*pointer); }
/* INCREMENT A POINTER BY THE NUMBER OF BYTES POINTED TO
===================================================== */
void *incremented(void *pointer)
{ int inc=increment(pointer);
*((char**)&pointer)+=inc;
return(pointer); }
What goes wrong is that the function incremented() increments the
pointer, but returns the original, non-incremented value.
Here's the assembly code:
Dump of assembler code for function incremented:
0x08051f80 <incremented+0>: push %ebp
0x08051f81 <incremented+1>: mov %esp,%ebp
0x08051f83 <incremented+3>: push %ebx
0x08051f84 <incremented+4>: sub $0x4,%esp
0x08051f87 <incremented+7>: mov 0x8(%ebp),%ebx
0x08051f8a <incremented+10>: mov %ebx,(%esp)
0x08051f8d <incremented+13>: call 0x8051f70 <increment>
0x08051f92 <incremented+18>: add %eax,0x8(%ebp)
0x08051f95 <incremented+21>: mov %ebx,%eax
******************************************************************
-->> Here's the problem, line above should read mov 0x8(%ebp),%eax
******************************************************************
0x08051f97 <incremented+23>: add $0x4,%esp
0x08051f9a <incremented+26>: pop %ebx
0x08051f9b <incremented+27>: pop %ebp
0x08051f9c <incremented+28>: ret
0x08051f9d <incremented+29>: lea 0x0(%esi),%esi
Thanks for your time, and BTW: is there a 'better' construct for
incrementing a void* pointer other than *((char**)&pointer)+=inc ? ;-)
Greetings,
Elmar