summaryrefslogtreecommitdiffstats
path: root/src/arch/i386/transitions/librm.S
diff options
context:
space:
mode:
authorMichael Brown2007-01-09 15:13:06 +0100
committerMichael Brown2007-01-09 15:13:06 +0100
commita9369bb50369ca38731ccc3edfa449b9909b4753 (patch)
treef8fea34c1d8bd2f31e5782819a590e806bc01ae6 /src/arch/i386/transitions/librm.S
parentDefine "connected" as (diff)
downloadipxe-a9369bb50369ca38731ccc3edfa449b9909b4753.tar.gz
ipxe-a9369bb50369ca38731ccc3edfa449b9909b4753.tar.xz
ipxe-a9369bb50369ca38731ccc3edfa449b9909b4753.zip
Leave protected-mode return address on PM stack when issuing a
real_call(), rather than moving it to the RM stack and back again. This allows the real-mode function to completely destroy the stack contents, provided that it manages to return to real_call().
Diffstat (limited to 'src/arch/i386/transitions/librm.S')
-rw-r--r--src/arch/i386/transitions/librm.S21
1 files changed, 10 insertions, 11 deletions
diff --git a/src/arch/i386/transitions/librm.S b/src/arch/i386/transitions/librm.S
index 9edbd473..e916ba57 100644
--- a/src/arch/i386/transitions/librm.S
+++ b/src/arch/i386/transitions/librm.S
@@ -455,28 +455,25 @@ prot_call:
.code32
.globl real_call
real_call:
- /* Create register dump on PM stack */
+ /* Create register dump and function pointer copy on PM stack */
pushal
+ pushl RC_OFFSET_FUNCTION(%esp)
- /* Switch to real mode and move register dump to RM stack */
- movl $RC_OFFSET_END, %ecx
+ /* Switch to real mode and move register dump to RM stack */
+ movl $( RC_OFFSET_RETADDR + 4 /* function pointer copy */ ), %ecx
pushl $1f
jmp prot_to_real
.section ".text16"
.code16
1:
- /* Construct call to real-mode function */
- movw %sp, %bp
- movw RC_OFFSET_FUNCTION(%bp), %ax
- movw %ax, rc_function
-
/* Call real-mode function */
+ popl rc_function
popal
call *rc_function
pushal
/* Switch to protected mode and move register dump back to PM stack */
- movl $RC_OFFSET_END, %ecx
+ movl $RC_OFFSET_RETADDR, %ecx
pushl $1f
jmp real_to_prot
.section ".text"
@@ -487,9 +484,11 @@ real_call:
ret
- /* Function vector, used because */
+ /* Function vector, used because "call xx(%sp)" is not a valid
+ * 16-bit expression.
+ */
.section ".data16"
-rc_function: .word 0
+rc_function: .word 0, 0
/****************************************************************************
* Stored real-mode and protected-mode stack pointers