]> git.proxmox.com Git - mirror_edk2.git/blob - EdkCompatibilityPkg/Foundation/Library/Thunk16/X64/Thunk16.S
Update the copyright notice format
[mirror_edk2.git] / EdkCompatibilityPkg / Foundation / Library / Thunk16 / X64 / Thunk16.S
1 #*****************************************************************************
2 #*
3 #* Copyright (c) 2008 - 2009, Intel Corporation. All rights reserved.<BR>
4 #* This program and the accompanying materials
5 #* are licensed and made available under the terms and conditions of the BSD License
6 #* which accompanies this distribution. The full text of the license may be found at
7 #* http://opensource.org/licenses/bsd-license.php
8 #*
9 #* THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
10 #* WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
11 #*
12 #* Module Name:
13 #*
14 #* Thunk.S
15 #*
16 #* Abstract:
17 #*
18 #* Real mode thunk
19 #*
20 #*****************************************************************************
21 #include <EfiBind.h>
22
23
24
25 .data
26
27 .globl ASM_PFX(mCode16Size)
28
29 .data
30 mCode16Size: .long _Code16End - _Code16Addr
31
32
33 NullSegSel: .quad 0
34 _16CsSegSel:
35 .word -1
36 .word 0
37 .byte 0
38 .byte 0x9b
39 .byte 0x8f #16-bit segment
40 .byte 0
41 _16DsSegSel:
42 .word -1
43 .word 0
44 .byte 0
45 .byte 0x93
46 .byte 0x8f #16-bit segment
47 .byte 0
48
49 _16Gdtr:
50 .word _16Gdtr - NullSegSel - 1
51 .long NullSegSel
52 .code:
53
54 #IA32_REGS STRUC 4t
55 #_EDI DD ?
56 #_ESI DD ?
57 #_EBP DD ?
58 #_ESP DD ?
59 #_EBX DD ?
60 #_EDX DD ?
61 #_ECX DD ?
62 #_EAX DD ?
63 #_DS DW ?
64 #_ES DW ?
65 #_FS DW ?
66 #_GS DW ?
67 #_RFLAGS DQ ?
68 #_EIP DD ?
69 #_CS DW ?
70 #_SS DW ?
71 #IA32_REGS ENDS
72
73 #_STK16 STRUC 1t
74 #RetEip DD ?
75 #RetCs DW ?
76 #ThunkFlags DW ?
77 #SavedGdtr FWORD ?
78 #Resvd1 DW ?
79 #SavedCr0 DD ?
80 #SavedCr4 DD ?
81 #_STK16 ENDS
82
83 ASM_PFX(Thunk16):
84 push %rbp
85 push %rbx
86 push %rsi
87 push %rdi
88 push %r12
89 push %r13
90 push %r14
91 push %r15
92 pushq %fs
93 pushq %gs
94 movl %ds,%r12d
95 movl %es,%r13d
96 movl %ss,%r14d
97 mov %rsp,%r15
98 mov %rcx,%rsi
99 movzwq 0x36(%rsi),%r10 #movzx r10, (IA32_REGS ptr [rsi])._SS
100 xor %rdi,%rdi
101 mov 0xc(%rsi),%edi #mov edi, (IA32_REGS ptr [rsi])._ESP
102 add $0xffffffffffffffb0,%rdi #add rdi, - sizeof (IA32_REGS) - sizeof (_STK16)
103 push %rdi
104 imul $0x10,%r10,%rax
105 add %rax,%rdi
106 pushq $0xe #push sizeof (IA32_REGS) / 4
107 pop %rcx
108 rep movsl %ds:(%rsi),%es:(%rdi)
109 pop %rbx #rbx <- 16-bit stack offset
110 lea Label,%eax #42 <_Thunk16+0x42>
111 stos %eax,%es:(%rdi)
112 movl %cs,%eax #return segment
113 stos %ax,%es:(%rdi)
114 mov %edx,%eax #THUNK Flags
115 stos %ax,%es:(%rdi)
116 sgdt 0x58(%rsp) #save GDTR
117 mov 0x58(%rsp),%rax
118 stos %rax,%es:(%rdi)
119 mov %cr0,%rax #save CR0
120 mov %eax,%esi #esi <- CR0 to set
121 stos %eax,%es:(%rdi)
122 mov %cr4,%rax #save CR4
123 stos %eax,%es:(%rdi)
124 sidt 0x58(%rsp) #save IDTR
125 and $0x7ffffffe,%esi #clear PE & PG bits
126 mov %r10,%rdi #rdi <- 16-bit stack segment
127 shl $0x10,%r8
128 push %r8 #far jmp address
129 lea Label_16Bit,%eax
130 push %rax
131 movw $0x8,0x4(%rsp)
132 lgdt _16Gdtr #bugbug: may not match.
133 lret
134 Label_16Bit:
135 .byte 0x66
136 movl $0xc0000080,%ecx
137 mov %rsi,%cr0 #disable PE & PG
138 rdmsr
139 and $0xfe,%ah
140 wrmsr #clear LME bit
141 mov %cr4,%rax
142 and $0xcf,%al #clear PAE & PSE
143 mov %rax,%cr4
144 lret
145
146 Label:
147 xor %rax,%rax
148 movl %ss,%eax
149 shl $0x4,%eax
150 add %esp,%eax
151 mov %r15,%rsp
152 lidt 0x58(%rsp)
153 movl %r12d,%ds
154 movl %r13d,%es
155 movl %r14d,%ss
156 popq %gs
157 popq %fs
158 pop %r15
159 pop %r14
160 pop %r13
161 pop %r12
162 pop %rdi
163 pop %rsi
164 pop %rbx
165 pop %rbp
166 retq
167
168
169 .p2align 4
170
171 _Code16Addr:
172 ASM_PFX(RealMode):
173 movl %edi,%ss
174 mov %bx,%sp #set up 16-bit stack
175 .byte 0x2e
176 .byte 0x0f
177 .byte 0x01
178 .byte 0x1e
179 .word _16Idtr - _Code16Addr #lidt _16Idtr
180 .byte 0x66
181 .byte 0x61 #popad
182 .byte 0x1f #pop ds
183 .byte 0x07 #pop es
184 popq %fs
185 popq %gs
186 add $0x8,%esp #skip RFLAGS
187 .byte 0x67 #test [esp + 0eh], 1
188 .byte 0xf7
189 .byte 0x44
190 .byte 0x24
191 .byte 0x0e
192 .byte 0x01
193 .byte 0x00
194 jz 1f
195 pushfq #pushf, actually
196 1:
197 .byte 0x0e #push cs
198 .byte 0x68 #push /iw
199 .word FarCallRet - _Code16Addr
200 jz 2f
201 .byte 0x66
202 ljmp *6(%esp)
203 2:
204 .byte 0x66
205 ljmp *4(%esp)
206 FarCallRet:
207 .byte 0x66
208 push $0x00 #push a dword of zero
209 .byte 0x66
210 pushf #pushfd, actually
211 pushq %gs
212 pushq %fs
213 .byte 0x06 #push %es
214 .byte 0x1e #push %ds
215 .byte 0x66
216 .byte 0x60
217 cli
218 .byte 0x66 #sizeof (IA32_REGS) = 13 * 4 = 52
219 lgdt 64(%esp) #lgdt (_STK16 ptr [esp + sizeof (IA32_REGS)]).SavedGdtr
220 .byte 0x66
221 mov 76(%esp), %eax
222 mov %rax, %cr4
223 .byte 0x66
224 mov $0xc0000080, %ecx
225 rdmsr
226 orb $1, %ah
227 wrmsr
228 .byte 0x66
229 mov 72(%esp), %eax
230 mov %rax, %cr0 #restore CR0
231 .byte 0x66
232 ljmpl *52(%esp)
233
234 _16Idtr:
235 .word 0x3ff #FWORD (1 SHL 10) - 1
236 .byte 0x00