gcc using clobbered register as input with inline assembly
Zack Weinberg
zackw@stanford.edu
Mon Mar 26 10:20:00 GMT 2001
On Mon, Mar 26, 2001 at 11:41:13AM -0600, Timur Tabi wrote:
> egcs-2.91.66 on Red Hat Linux 6.2 (2.2.14 kernel)
>
> I have this inline assembly code:
>
> _inline void
> BeginCpuTick(
> u64 * const pTime
> ){
> ASSERT(pTime);
> __asm__ __volatile__ (
> "rdtsc \n\t"
> "mov %%eax, (%1) \n\t"
> "mov %%edx, 4(%1) \n\t"
> : "=m" (*pTime)
> : "r" (pTime)
> : "eax", "edx"
> );
> }
>
> According to the documentation, because I specified eax and edx as
> clobbered registers, gcc should not be using them as inputs or outputs.
> But that's exactly what's happening in my case.
Clobbers happen *after* the asm completes. You have to do the moves
separately, or let the compiler do them for you, e.g:
inline void
BeginCpuTick(u64 *const pTime)
{
register u64 xtime;
asm volatile ("rdtsc" : "=A" (xtime));
*pTime = xtime;
}
-- 3.0 -O2 -fomit-frame-pointer gives me
BeginCpuTick:
#APP
rdtsc
#NO_APP
movl 4(%esp), %ecx
movl %eax, (%ecx)
movl %edx, 4(%ecx)
ret
2.95 unfortunately puts some extra moves in there.
zw
More information about the Gcc-bugs
mailing list