This is the mail archive of the
gcc-help@gcc.gnu.org
mailing list for the GCC project.
Re: Optimisation puzzle
Erik <sigra@home.se> writes:
> From man:puts I see that it is declared "int puts(const char
> *)". This means that puts does not promise to leave its argument
> unchanged. Therefore the caller must push the argument anew before
> each call. If it had been declared "int puts(const char * const)"
> instead, the push should be moved outside the loop. Unfortunately this
> does not seem to work. I tried with the following program:
> void q(const unsigned int);
> void f() {for (unsigned int x = 0; x != 10; x++) q(77);}
>
> and built it with "gcc -std=c99 -Os -Wall -Wextra -Werror -S":
> .L2:
> subl $12, %esp
> incl %ebx
> pushl $77
> call q
> addl $16, %esp
> cmpl $10, %ebx
> jne .L2
>
> As you can see, "pushl $77" is still inside the loop even though q
> promises to not change its argument. This must be a bug.
This is not a bug. const on an automatic variable in C is more
advisory than anything else. You are not permitted to change a const
object, but you can cast its address to a non-const pointer. The only
time const really means something is when it is applied to a global or
static variable. In that case the compiler is permitted to put the
variable in read-only storage.
That is, this is legal C:
int
q (const unsigned int i)
{
int *p = (int *) &i;
*p = 1;
return i;
}
Ian