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