From 185a983b3ce78a1813458352b3ad9945781ebb6d Mon Sep 17 00:00:00 2001 From: "Ryan C. Gordon" Date: Thu, 4 Jan 2018 00:26:52 -0500 Subject: [PATCH] DosFlatToSel() needs to save off registers. It's not syscall calling convention, and CSet/2 generates thunks that call this function but expect %ecx to not be altered by it. Save off a bunch, just in case. --- native/doscalls.c | 17 +++++++++++++++-- 1 file changed, 15 insertions(+), 2 deletions(-) diff --git a/native/doscalls.c b/native/doscalls.c index 5670b76..89e63ee 100644 --- a/native/doscalls.c +++ b/native/doscalls.c @@ -657,13 +657,26 @@ ULONG _DosFlatToSel(PVOID ptr) } // _DosFlatToSel // DosFlatToSel() passes its argument in %eax, so a little asm to bridge that... +// Note that this isn't syscall calling conventions at all; CSet/2 generates +// thunking code that expects this function to preserve %ecx, so we'll just +// go ahead and save a bunch of stuff, just in case. __asm__ ( ".globl DosFlatToSel \n\t" ".type DosFlatToSel, @function \n\t" "DosFlatToSel: \n\t" - " pushl %eax \n\t" + " pushl %ebx \n\t" // save off a bunch of stuff. Better safe than sorry. + " pushl %ecx \n\t" + " pushl %edx \n\t" + " pushl %edi \n\t" + " pushl %esi \n\t" + " pushl %eax \n\t" // the actual argument to DosFlatToSel. " call _DosFlatToSel \n\t" - " addl $4, %esp \n\t" + " addl $4, %esp \n\t" // clear argument to DosFlatToSel. + " popl %esi \n\t" + " popl %edi \n\t" + " popl %edx \n\t" // save off a bunch of stuff. + " popl %ecx \n\t" + " popl %ebx \n\t" " ret \n\t" ".size _DosFlatToSel, .-_DosFlatToSel \n\t" );