app(&foo); // output: x0 = 100 and y1 = 101.000000
app(&foo2); // it actually works // the output is the same!
return (0);
}
Although foo and foo2 have different C-types, one can actually cast one to
the other without
causing any problems. This is amazing! When I first saw a similar example
generated from ATS
source, I thought it was a bug in the ATS compiler
If parameters are passed in registers, then this behavior
is easy to understand because the code for foo is just the same
as the code for foo2:
x0 is mapped to the same integer register
y1 is mapped to the same float point register.
However, the parametes of C functions are stack-allocated. This is
why I got puzzled.
By studying the assembly code generated by gcc, I think this is what
happens at run-time:
first integer argument is always in %edi
first double argument is always in %xmm
They are not passed on stack but there is memory on stack reserved
for these arguments. Say you use a pointer to the first double argument.
Then the compiler generates code to move the content of %xmm into the memory
reserved for the first double argument.
This strategy is used by gcc. Whatever used by gcc is really a de facto
standard; so everyone
else does the same thing (clang, tcc, etc).On Sunday, January 3, 2016 at 8:17:28 AM UTC-5, Jyun-Yan You wrote:
Compiler doesn’t swap arguments.
It works because doubles are passed to different set of registers (xmm) on
x86-64.
If it compiles with -m32, result is wrong.
On Saturday, January 2, 2016 at 10:13:56 AM UTC+8, gmhwxi wrote:
Today I was realy surprised by the following example in C:
app(&foo); // output: x0 = 100 and y1 = 101.000000
app(&foo2); // it actually works // the output is the same!
return (0);
}
Although foo and foo2 have different C-types, one can actually cast one
to the other without
causing any problems. This is amazing! When I first saw a similar example
generated from ATS
source, I thought it was a bug in the ATS compiler
Compiler doesn’t swap arguments.
It works because doubles are passed to different set of registers (xmm) on
x86-64.
If it compiles with -m32, result is wrong.On Saturday, January 2, 2016 at 10:13:56 AM UTC+8, gmhwxi wrote:
Today I was realy surprised by the following example in C:
app(&foo); // output: x0 = 100 and y1 = 101.000000
app(&foo2); // it actually works // the output is the same!
return (0);
}
Although foo and foo2 have different C-types, one can actually cast one to
the other without
causing any problems. This is amazing! When I first saw a similar example
generated from ATS
source, I thought it was a bug in the ATS compiler