]> git.proxmox.com Git - mirror_edk2.git/blame - IntelFspWrapperPkg/Library/SecPeiFspPlatformSecLibSample/Ia32/SecEntry.asm
Add IntelFspWrapper to support boot EDKII on FSP bin.
[mirror_edk2.git] / IntelFspWrapperPkg / Library / SecPeiFspPlatformSecLibSample / Ia32 / SecEntry.asm
CommitLineData
a33a2f62
JY
1;------------------------------------------------------------------------------\r
2;\r
3; Copyright (c) 2014, Intel Corporation. All rights reserved.<BR>\r
4; This program and the accompanying materials\r
5; are licensed and made available under the terms and conditions of the BSD License\r
6; which accompanies this distribution. The full text of the license may be found at\r
7; http://opensource.org/licenses/bsd-license.php.\r
8;\r
9; THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
10; WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
11;\r
12; Module Name:\r
13;\r
14; SecEntry.asm\r
15;\r
16; Abstract:\r
17;\r
18; This is the code that goes from real-mode to protected mode.\r
19; It consumes the reset vector, calls TempRamInit API from FSP binary.\r
20;\r
21;------------------------------------------------------------------------------\r
22\r
23#include "Fsp.h"\r
24\r
25.686p\r
26.xmm\r
27.model small, c\r
28\r
29EXTRN CallPeiCoreEntryPoint:NEAR\r
30EXTRN TempRamInitParams:FAR\r
31\r
32; Pcds\r
33EXTRN PcdGet32 (PcdFlashFvFspBase):DWORD\r
34EXTRN PcdGet32 (PcdFlashFvFspSize):DWORD\r
35\r
36_TEXT_REALMODE SEGMENT PARA PUBLIC USE16 'CODE'\r
37 ASSUME CS:_TEXT_REALMODE, DS:_TEXT_REALMODE\r
38\r
39;----------------------------------------------------------------------------\r
40;\r
41; Procedure: _ModuleEntryPoint\r
42;\r
43; Input: None\r
44;\r
45; Output: None\r
46;\r
47; Destroys: Assume all registers\r
48;\r
49; Description:\r
50;\r
51; Transition to non-paged flat-model protected mode from a\r
52; hard-coded GDT that provides exactly two descriptors.\r
53; This is a bare bones transition to protected mode only\r
54; used for a while in PEI and possibly DXE.\r
55;\r
56; After enabling protected mode, a far jump is executed to\r
57; transfer to PEI using the newly loaded GDT.\r
58;\r
59; Return: None\r
60;\r
61; MMX Usage:\r
62; MM0 = BIST State\r
63; MM5 = Save time-stamp counter value high32bit\r
64; MM6 = Save time-stamp counter value low32bit.\r
65;\r
66;----------------------------------------------------------------------------\r
67\r
68align 4\r
69_ModuleEntryPoint PROC NEAR C PUBLIC\r
70 fninit ; clear any pending Floating point exceptions\r
71 ;\r
72 ; Store the BIST value in mm0\r
73 ;\r
74 movd mm0, eax\r
75\r
76 ;\r
77 ; Save time-stamp counter value\r
78 ; rdtsc load 64bit time-stamp counter to EDX:EAX\r
79 ;\r
80 rdtsc\r
81 movd mm5, edx\r
82 movd mm6, eax\r
83\r
84 ;\r
85 ; Load the GDT table in GdtDesc\r
86 ;\r
87 mov esi, OFFSET GdtDesc\r
88 DB 66h\r
89 lgdt fword ptr cs:[si]\r
90\r
91 ;\r
92 ; Transition to 16 bit protected mode\r
93 ;\r
94 mov eax, cr0 ; Get control register 0\r
95 or eax, 00000003h ; Set PE bit (bit #0) & MP bit (bit #1)\r
96 mov cr0, eax ; Activate protected mode\r
97\r
98 mov eax, cr4 ; Get control register 4\r
99 or eax, 00000600h ; Set OSFXSR bit (bit #9) & OSXMMEXCPT bit (bit #10)\r
100 mov cr4, eax\r
101\r
102 ;\r
103 ; Now we're in 16 bit protected mode\r
104 ; Set up the selectors for 32 bit protected mode entry\r
105 ;\r
106 mov ax, SYS_DATA_SEL\r
107 mov ds, ax\r
108 mov es, ax\r
109 mov fs, ax\r
110 mov gs, ax\r
111 mov ss, ax\r
112\r
113 ;\r
114 ; Transition to Flat 32 bit protected mode\r
115 ; The jump to a far pointer causes the transition to 32 bit mode\r
116 ;\r
117 mov esi, offset ProtectedModeEntryLinearAddress\r
118 jmp fword ptr cs:[si]\r
119\r
120_ModuleEntryPoint ENDP\r
121_TEXT_REALMODE ENDS\r
122\r
123_TEXT_PROTECTED_MODE SEGMENT PARA PUBLIC USE32 'CODE'\r
124 ASSUME CS:_TEXT_PROTECTED_MODE, DS:_TEXT_PROTECTED_MODE\r
125\r
126;----------------------------------------------------------------------------\r
127;\r
128; Procedure: ProtectedModeEntryPoint\r
129;\r
130; Input: None\r
131;\r
132; Output: None\r
133;\r
134; Destroys: Assume all registers\r
135;\r
136; Description:\r
137;\r
138; This function handles:\r
139; Call two basic APIs from FSP binary\r
140; Initializes stack with some early data (BIST, PEI entry, etc)\r
141;\r
142; Return: None\r
143;\r
144;----------------------------------------------------------------------------\r
145\r
146align 4\r
147ProtectedModeEntryPoint PROC NEAR PUBLIC\r
148\r
149 ; Find the fsp info header\r
150 mov edi, PcdGet32 (PcdFlashFvFspBase)\r
151 mov ecx, PcdGet32 (PcdFlashFvFspSize)\r
152\r
153 mov eax, dword ptr [edi + FVH_SIGINATURE_OFFSET]\r
154 cmp eax, FVH_SIGINATURE_VALID_VALUE\r
155 jnz FspHeaderNotFound\r
156\r
157 xor eax, eax\r
158 mov ax, word ptr [edi + FVH_EXTHEADER_OFFSET_OFFSET]\r
159 cmp ax, 0\r
160 jnz FspFvExtHeaderExist\r
161\r
162 xor eax, eax\r
163 mov ax, word ptr [edi + FVH_HEADER_LENGTH_OFFSET] ; Bypass Fv Header\r
164 add edi, eax\r
165 jmp FspCheckFfsHeader\r
166\r
167FspFvExtHeaderExist:\r
168 add edi, eax\r
169 mov eax, dword ptr [edi + FVH_EXTHEADER_SIZE_OFFSET] ; Bypass Ext Fv Header\r
170 add edi, eax\r
171\r
172 ; Round up to 8 byte alignment\r
173 mov eax, edi\r
174 and al, 07h\r
175 jz FspCheckFfsHeader\r
176\r
177 and edi, 0FFFFFFF8h\r
178 add edi, 08h\r
179\r
180FspCheckFfsHeader:\r
181 ; Check the ffs guid\r
182 mov eax, dword ptr [edi]\r
183 cmp eax, FSP_HEADER_GUID_DWORD1\r
184 jnz FspHeaderNotFound\r
185\r
186 mov eax, dword ptr [edi + 4]\r
187 cmp eax, FSP_HEADER_GUID_DWORD2\r
188 jnz FspHeaderNotFound\r
189\r
190 mov eax, dword ptr [edi + 8]\r
191 cmp eax, FSP_HEADER_GUID_DWORD3\r
192 jnz FspHeaderNotFound\r
193\r
194 mov eax, dword ptr [edi + 0Ch]\r
195 cmp eax, FSP_HEADER_GUID_DWORD4\r
196 jnz FspHeaderNotFound\r
197\r
198 add edi, FFS_HEADER_SIZE_VALUE ; Bypass the ffs header\r
199\r
200 ; Check the section type as raw section\r
201 mov al, byte ptr [edi + SECTION_HEADER_TYPE_OFFSET]\r
202 cmp al, 019h\r
203 jnz FspHeaderNotFound\r
204\r
205 add edi, RAW_SECTION_HEADER_SIZE_VALUE ; Bypass the section header\r
206 jmp FspHeaderFound\r
207\r
208FspHeaderNotFound:\r
209 jmp $\r
210\r
211FspHeaderFound:\r
212 ; Get the fsp TempRamInit Api address\r
213 mov eax, dword ptr [edi + FSP_HEADER_IMAGEBASE_OFFSET]\r
214 add eax, dword ptr [edi + FSP_HEADER_TEMPRAMINIT_OFFSET]\r
215\r
216 ; Setup the hardcode stack\r
217 mov esp, OFFSET TempRamInitStack\r
218\r
219 ; Call the fsp TempRamInit Api\r
220 jmp eax\r
221\r
222TempRamInitDone:\r
223 cmp eax, 0\r
224 jnz FspApiFailed\r
225\r
226 ; ECX: start of range\r
227 ; EDX: end of range\r
228 mov esp, edx\r
229 push edx\r
230 push ecx\r
231 push eax ; zero - no hob list yet\r
232 call CallPeiCoreEntryPoint\r
233\r
234FspApiFailed:\r
235 jmp $\r
236\r
237align 10h\r
238TempRamInitStack:\r
239 DD OFFSET TempRamInitDone\r
240 DD OFFSET TempRamInitParams\r
241\r
242ProtectedModeEntryPoint ENDP\r
243\r
244;\r
245; ROM-based Global-Descriptor Table for the Tiano PEI Phase\r
246;\r
247align 16\r
248PUBLIC BootGdtTable\r
249\r
250;\r
251; GDT[0]: 0x00: Null entry, never used.\r
252;\r
253NULL_SEL EQU $ - GDT_BASE ; Selector [0]\r
254GDT_BASE:\r
255BootGdtTable DD 0\r
256 DD 0\r
257;\r
258; Linear data segment descriptor\r
259;\r
260LINEAR_SEL EQU $ - GDT_BASE ; Selector [0x8]\r
261 DW 0FFFFh ; limit 0xFFFFF\r
262 DW 0 ; base 0\r
263 DB 0\r
264 DB 092h ; present, ring 0, data, expand-up, writable\r
265 DB 0CFh ; page-granular, 32-bit\r
266 DB 0\r
267;\r
268; Linear code segment descriptor\r
269;\r
270LINEAR_CODE_SEL EQU $ - GDT_BASE ; Selector [0x10]\r
271 DW 0FFFFh ; limit 0xFFFFF\r
272 DW 0 ; base 0\r
273 DB 0\r
274 DB 09Bh ; present, ring 0, data, expand-up, not-writable\r
275 DB 0CFh ; page-granular, 32-bit\r
276 DB 0\r
277;\r
278; System data segment descriptor\r
279;\r
280SYS_DATA_SEL EQU $ - GDT_BASE ; Selector [0x18]\r
281 DW 0FFFFh ; limit 0xFFFFF\r
282 DW 0 ; base 0\r
283 DB 0\r
284 DB 093h ; present, ring 0, data, expand-up, not-writable\r
285 DB 0CFh ; page-granular, 32-bit\r
286 DB 0\r
287\r
288;\r
289; System code segment descriptor\r
290;\r
291SYS_CODE_SEL EQU $ - GDT_BASE ; Selector [0x20]\r
292 DW 0FFFFh ; limit 0xFFFFF\r
293 DW 0 ; base 0\r
294 DB 0\r
295 DB 09Ah ; present, ring 0, data, expand-up, writable\r
296 DB 0CFh ; page-granular, 32-bit\r
297 DB 0\r
298;\r
299; Spare segment descriptor\r
300;\r
301SYS16_CODE_SEL EQU $ - GDT_BASE ; Selector [0x28]\r
302 DW 0FFFFh ; limit 0xFFFFF\r
303 DW 0 ; base 0\r
304 DB 0Eh ; Changed from F000 to E000.\r
305 DB 09Bh ; present, ring 0, code, expand-up, writable\r
306 DB 00h ; byte-granular, 16-bit\r
307 DB 0\r
308;\r
309; Spare segment descriptor\r
310;\r
311SYS16_DATA_SEL EQU $ - GDT_BASE ; Selector [0x30]\r
312 DW 0FFFFh ; limit 0xFFFF\r
313 DW 0 ; base 0\r
314 DB 0\r
315 DB 093h ; present, ring 0, data, expand-up, not-writable\r
316 DB 00h ; byte-granular, 16-bit\r
317 DB 0\r
318\r
319;\r
320; Spare segment descriptor\r
321;\r
322SPARE5_SEL EQU $ - GDT_BASE ; Selector [0x38]\r
323 DW 0 ; limit 0\r
324 DW 0 ; base 0\r
325 DB 0\r
326 DB 0 ; present, ring 0, data, expand-up, writable\r
327 DB 0 ; page-granular, 32-bit\r
328 DB 0\r
329GDT_SIZE EQU $ - BootGdtTable ; Size, in bytes\r
330\r
331;\r
332; GDT Descriptor\r
333;\r
334GdtDesc: ; GDT descriptor\r
335 DW GDT_SIZE - 1 ; GDT limit\r
336 DD OFFSET BootGdtTable ; GDT base address\r
337\r
338\r
339ProtectedModeEntryLinearAddress LABEL FWORD\r
340ProtectedModeEntryLinearOffset LABEL DWORD\r
341 DD OFFSET ProtectedModeEntryPoint ; Offset of our 32 bit code\r
342 DW LINEAR_CODE_SEL\r
343\r
344_TEXT_PROTECTED_MODE ENDS\r
345END\r