on 09/02/2012 17:00 Andriy Gapon said the following:
>
> The code in question:
>
> void cpuid(unsigned info, unsigned *eax, unsigned *ebx, unsigned *ecx,
> unsigned *edx)
> {
> #ifdef __GNUC__
> #if defined(__i386__) || defined(__x86_64__)
> *eax = info;
> __asm volatile
> ("mov %%ebx, %%edi;" /* 32bit PIC: don't clobber ebx */
> "cpuid;"
> "mov %%ebx, %%esi;"
> "mov %%edi, %%ebx;"
> :"+a" (*eax), "=S" (*ebx), "=c" (*ecx), "=d" (*edx)
> : :"edi");
> #endif
> #endif
> }
>
> On 64-bit systems upper half of %rbx gets clobbered, because only %ebx is
> preserved via %edi.
>
Just to add some details, here's assembly produced with gcc 4.6.2 and options
-O2
-fno-strict-aliasing -march=nocona -msse2:
Dump of assembler code for function xf_post_connect:
0x000000000040cf0e <+0>: push %r13
0x000000000040cf10 <+2>: push %r12
0x000000000040cf12 <+4>: push %rbp
0x000000000040cf13 <+5>: push %rbx
0x000000000040cf14 <+6>: sub $0xa8,%rsp
0x000000000040cf1b <+13>: mov %rdi,%rbp
0x000000000040cf1e <+16>: mov (%rdi),%rax
0x000000000040cf21 <+19>: mov 0x128(%rax),%rbx
0x000000000040cf28 <+26>: mov 0x10(%rbx),%rax
0x000000000040cf2c <+30>: mov 0xb0(%rax),%r12
0x000000000040cf33 <+37>: mov %rbx,%rdi
0x000000000040cf36 <+40>: callq 0x40cd99 <xf_get_pixmap_info>
0x000000000040cf3b <+45>: cmp $0x1,%eax
0x000000000040cf3e <+48>: je 0x40cf50 <xf_post_connect+66>
0x000000000040cf40 <+50>: xor %eax,%eax
0x000000000040cf42 <+52>: add $0xa8,%rsp
0x000000000040cf49 <+59>: pop %rbx
0x000000000040cf4a <+60>: pop %rbp
0x000000000040cf4b <+61>: pop %r12
0x000000000040cf4d <+63>: pop %r13
0x000000000040cf4f <+65>: retq
0x000000000040cf50 <+66>: mov 0x0(%rbp),%rax
0x000000000040cf54 <+70>: mov 0xb8(%rax),%rdi
0x000000000040cf5b <+77>: callq 0x40aaf0 <xf_register_graphics>
0x000000000040cf60 <+82>: mov 0xe8(%rbx),%ecx
0x000000000040cf66 <+88>: test %ecx,%ecx
0x000000000040cf68 <+90>: je 0x40d20b <xf_post_connect+765>
0x000000000040cf6e <+96>: mov $0x21,%esi
0x000000000040cf73 <+101>: cmpl $0x11,0x20(%rbx)
0x000000000040cf77 <+105>: mov $0x9,%eax
0x000000000040cf7c <+110>: cmovl %eax,%esi
0x000000000040cf7f <+113>: xor %edx,%edx
0x000000000040cf81 <+115>: mov %rbp,%rdi
0x000000000040cf84 <+118>: callq 0x404470 <gdi_init@plt>
0x000000000040cf89 <+123>: mov 0x0(%rbp),%rax
0x000000000040cf8d <+127>: mov 0x98(%rax),%rax
0x000000000040cf94 <+134>: mov 0x48(%rax),%rdx
0x000000000040cf98 <+138>: mov %rdx,0xf0(%rbx)
0x000000000040cf9f <+145>: mov 0x58(%rax),%r13
0x000000000040cfa3 <+149>: test %r13,%r13
0x000000000040cfa6 <+152>: je 0x40cfc9 <xf_post_connect+187>
0x000000000040cfa8 <+154>: mov $0x1,%eax
0x000000000040cfad <+159>: mov %ebx,%edi
0x000000000040cfaf <+161>: cpuid
0x000000000040cfb1 <+163>: mov %ebx,%esi
0x000000000040cfb3 <+165>: mov %edi,%ebx
0x000000000040cfb5 <+167>: xor %esi,%esi
0x000000000040cfb7 <+169>: and $0x4000000,%edx
0x000000000040cfbd <+175>: setne %sil
0x000000000040cfc1 <+179>: mov %r13,%rdi
0x000000000040cfc4 <+182>: callq 0x404960 <rfx_context_set_cpu_opt@plt>
0x000000000040cfc9 <+187>: mov 0x58(%rbp),%rax
0x000000000040cfcd <+191>: mov 0x44(%rax),%eax
=> 0x000000000040cfd0 <+194>: mov %eax,0x2c(%rbx)
Arrow marks the point where xfreerdp crashed.
This dump should illustrate how %rbx gets corrupted.
--
Andriy Gapon
------------------------------------------------------------------------------
Virtualization & Cloud Management Using Capacity Planning
Cloud computing makes use of virtualization - but cloud computing
also focuses on allowing computing to be delivered as a service.
http://www.accelacomm.com/jaw/sfnl/114/51521223/
_______________________________________________
Freerdp-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/freerdp-devel