On Sun, Mar 4, 2012 at 7:04 PM, Kevin O'Connor kevin@koconnor.net wrote:
On Sun, Mar 04, 2012 at 03:03:49AM +0000, Julian Pidancet wrote:
I've done further debugging, and you can ignore all of the crap above. x86emu badly handles the retl instruction and only pops a 16bit wide value from the stack, whereas the corresponding calll pushes a 32bit return address. leavel suffers from the same problem.
Well, that's unfortunate. The system SeaBIOS uses to get gcc compiled code working in 16bit mode is going to generate "retl" instructions.
It may be possible to post-process the resulting assembler code, but (assuming we could) it would be quite ugly.
I've applied the following patch to x86emu and it seems to work better:
So, I guess the question is, how important is support for current/legacy x86emu versions?
I've tried to replace .code16gcc with .code16 in src/code16gcc.s to see if gcc would be able to generate code which doesn't use 32bit version of the call/ret instructions. The result was quite disappointing, it generates functions like this:
push %ebp mov %esp,%ebp [...] call 123 <func> [...] leave ret
Which seems correct, except that the prologue pushes 32bit on the stack, whereas the epilogue pops 16bit. (Could it be a GCC bug ?)
I am going to propose a patch to xorg-devel in the next few days, but in the meantime, it would be nice to find a solution in SeaBIOS so the code can work with older versions of Xorg.
I've done my testing with a 64bit machine though, I am wondering if there is a way to force Xorg to use vm86 at least on 32bit machines. Anybody knows anything about that ?