]> git.proxmox.com Git - mirror_edk2.git/blame - Vlv2TbltDevicePkg/SmBiosMiscDxe/MiscOemType0x90Function.c
SecurityPkg: Add DEBUG messages for TPM2Startup
[mirror_edk2.git] / Vlv2TbltDevicePkg / SmBiosMiscDxe / MiscOemType0x90Function.c
CommitLineData
3cbfba02
DW
1/*++\r
2\r
3Copyright (c) 1999 - 2014, Intel Corporation. All rights reserved.\r
4 \r\r
5 This program and the accompanying materials are licensed and made available under\r\r
6 the terms and conditions of the BSD License that accompanies this distribution. \r\r
7 The full text of the license may be found at \r\r
8 http://opensource.org/licenses/bsd-license.php. \r\r
9 \r\r
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, \r\r
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. \r\r
12 \r\r
13\r
14\r
15\r
16Module Name:\r
17\r
18 MiscOemType0x88Function.c\r
19\r
20Abstract:\r
21\r
22 The function that processes the Smbios data type 0x88 before they\r
23 are submitted to Data Hub\r
24\r
25--*/\r
26\r
27#include "CommonHeader.h"\r
28\r
29#include "MiscSubclassDriver.h"\r
30#include <Library/PrintLib.h>\r
31#include <Library/CpuIA32.h>\r
32#include <Protocol/DxeSmmReadyToLock.h>\r
33\r
34\r
35VOID\r
36GetCPUStepping ( )\r
37{\r
38 CHAR16 Buffer[40];\r
39\r
40 UINT16 FamilyId;\r
41 UINT8 Model;\r
42 UINT8 SteppingId;\r
43 UINT8 ProcessorType;\r
44\r
45\r
46 EfiCpuVersion (&FamilyId, &Model, &SteppingId, &ProcessorType);\r
47\r
48 //\r
49 //we need raw Model data\r
50 //\r
51 Model = Model & 0xf;\r
52\r
53 //\r
54 //Family/Model/Step\r
55 //\r
56 UnicodeSPrint (Buffer, sizeof (Buffer), L"%d/%d/%d", FamilyId, Model, SteppingId);\r
57 HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_PROCESSOR_STEPPING), Buffer, NULL);\r
58\r
59}\r
60\r
61EFI_STATUS\r
62SearchChildHandle(\r
63 EFI_HANDLE Father,\r
64 EFI_HANDLE *Child\r
65 )\r
66{\r
67 EFI_STATUS Status;\r
68 UINTN HandleIndex;\r
69 EFI_GUID **ProtocolGuidArray = NULL;\r
70 UINTN ArrayCount;\r
71 UINTN ProtocolIndex;\r
72 UINTN OpenInfoCount;\r
73 UINTN OpenInfoIndex;\r
74 EFI_OPEN_PROTOCOL_INFORMATION_ENTRY *OpenInfo = NULL;\r
75 UINTN mHandleCount;\r
76 EFI_HANDLE *mHandleBuffer= NULL;\r
77\r
78 //\r
79 // Retrieve the list of all handles from the handle database\r
80 //\r
81 Status = gBS->LocateHandleBuffer (\r
82 AllHandles,\r
83 NULL,\r
84 NULL,\r
85 &mHandleCount,\r
86 &mHandleBuffer\r
87 );\r
88\r
89 for (HandleIndex = 0; HandleIndex < mHandleCount; HandleIndex++) {\r
90 //\r
91 // Retrieve the list of all the protocols on each handle\r
92 //\r
93 Status = gBS->ProtocolsPerHandle (\r
94 mHandleBuffer[HandleIndex],\r
95 &ProtocolGuidArray,\r
96 &ArrayCount\r
97 );\r
98 if (!EFI_ERROR (Status)) {\r
99 for (ProtocolIndex = 0; ProtocolIndex < ArrayCount; ProtocolIndex++) {\r
100 Status = gBS->OpenProtocolInformation (\r
101 mHandleBuffer[HandleIndex],\r
102 ProtocolGuidArray[ProtocolIndex],\r
103 &OpenInfo,\r
104 &OpenInfoCount\r
105 );\r
106\r
107 if (!EFI_ERROR (Status)) {\r
108 for (OpenInfoIndex = 0; OpenInfoIndex < OpenInfoCount; OpenInfoIndex++) {\r
109 if(OpenInfo[OpenInfoIndex].AgentHandle == Father) {\r
110 if ((OpenInfo[OpenInfoIndex].Attributes & EFI_OPEN_PROTOCOL_BY_CHILD_CONTROLLER) == EFI_OPEN_PROTOCOL_BY_CHILD_CONTROLLER) {\r
111 *Child = mHandleBuffer[HandleIndex];\r
112 Status = EFI_SUCCESS;\r
113 goto TryReturn;\r
114 }\r
115 }\r
116 }\r
117 Status = EFI_NOT_FOUND;\r
118 }\r
119 }\r
120 if(OpenInfo != NULL) {\r
121 FreePool(OpenInfo);\r
122 OpenInfo = NULL;\r
123 }\r
124 }\r
125 if(ProtocolGuidArray != NULL) {\r
126 FreePool (ProtocolGuidArray);\r
127 ProtocolGuidArray = NULL;\r
128 }\r
129 }\r
130TryReturn:\r
131 if(OpenInfo != NULL) {\r
132 FreePool (OpenInfo);\r
133 OpenInfo = NULL;\r
134 }\r
135 if(ProtocolGuidArray != NULL) {\r
136 FreePool(ProtocolGuidArray);\r
137 ProtocolGuidArray = NULL;\r
138 }\r
139 if(mHandleBuffer != NULL) {\r
140 FreePool (mHandleBuffer);\r
141 mHandleBuffer = NULL;\r
142 }\r
143 return Status;\r
144}\r
145\r
146EFI_STATUS\r
147JudgeHandleIsPCIDevice(\r
148 EFI_HANDLE Handle,\r
149 UINT8 Device,\r
150 UINT8 Funs\r
151 )\r
152{\r
153 EFI_STATUS Status;\r
154 EFI_DEVICE_PATH *DPath;\r
155 EFI_DEVICE_PATH *DevicePath;\r
156\r
157 Status = gBS->HandleProtocol (\r
158 Handle,\r
159 &gEfiDevicePathProtocolGuid,\r
160 (VOID **) &DPath\r
161 );\r
162 if(!EFI_ERROR(Status)) {\r
163 DevicePath = DPath;\r
164 while(!IsDevicePathEnd(DPath)) {\r
165 if((DPath->Type == HARDWARE_DEVICE_PATH) && (DPath->SubType == HW_PCI_DP)) {\r
166 PCI_DEVICE_PATH *PCIPath;\r
167 PCIPath = (PCI_DEVICE_PATH*) DPath;\r
168 DPath = NextDevicePathNode(DPath);\r
169\r
170 if(IsDevicePathEnd(DPath) && (PCIPath->Device == Device) && (PCIPath->Function == Funs)) {\r
171 return EFI_SUCCESS;\r
172 }\r
173 } else {\r
174 DPath = NextDevicePathNode(DPath);\r
175 }\r
176 }\r
177 }\r
178 return EFI_UNSUPPORTED;\r
179}\r
180\r
181EFI_STATUS\r
182GetDriverName(\r
183 EFI_HANDLE Handle\r
184)\r
185{\r
186 EFI_DRIVER_BINDING_PROTOCOL *BindHandle = NULL;\r
187 EFI_STATUS Status;\r
188 UINT32 Version;\r
189 UINT16 *Ptr;\r
190 CHAR16 Buffer[40];\r
191 STRING_REF TokenToUpdate;\r
192 Status = gBS->OpenProtocol(\r
193 Handle,\r
194 &gEfiDriverBindingProtocolGuid,\r
195 (VOID**)&BindHandle,\r
196 NULL,\r
197 NULL,\r
198 EFI_OPEN_PROTOCOL_GET_PROTOCOL\r
199 );\r
200\r
201 if (EFI_ERROR(Status)) {\r
202 return EFI_NOT_FOUND;\r
203 }\r
204\r
205 Version = BindHandle->Version;\r
206 Ptr = (UINT16*)&Version;\r
207 UnicodeSPrint(Buffer, sizeof (Buffer), L"%d.%d.%d", Version >> 24 , (Version >>16)& 0x0f ,*(Ptr));\r
208\r
209 TokenToUpdate = (STRING_REF)STR_MISC_GOP_VERSION;\r
210 HiiSetString(mHiiHandle, TokenToUpdate, Buffer, NULL);\r
211\r
212 return EFI_SUCCESS;\r
213}\r
214\r
215EFI_STATUS\r
216GetGOPDriverName()\r
217{\r
218 UINTN HandleCount;\r
219 EFI_HANDLE *Handles= NULL;\r
220 UINTN Index;\r
221 EFI_STATUS Status;\r
222 EFI_HANDLE Child = 0;\r
223\r
224 Status = gBS->LocateHandleBuffer(\r
225 ByProtocol,\r
226 &gEfiDriverBindingProtocolGuid,\r
227 NULL,\r
228 &HandleCount,\r
229 &Handles\r
230 );\r
231\r
232 for (Index = 0; Index < HandleCount ; Index++) {\r
233 Status = SearchChildHandle(Handles[Index], &Child);\r
234 if(!EFI_ERROR(Status)) {\r
235 Status = JudgeHandleIsPCIDevice(Child, 0x02, 0x00);\r
236 if(!EFI_ERROR(Status)) {\r
237 return GetDriverName(Handles[Index]);\r
238 }\r
239 }\r
240 }\r
241 return EFI_UNSUPPORTED;\r
242}\r
243\r
244VOID\r
245GetUcodeVersion()\r
246{\r
247 UINT32 MicroCodeVersion;\r
248 CHAR16 Buffer[40];\r
249\r
250 //\r
251 // Microcode Revision\r
252 //\r
253 EfiWriteMsr (EFI_MSR_IA32_BIOS_SIGN_ID, 0);\r
254 EfiCpuid (EFI_CPUID_VERSION_INFO, NULL);\r
255 MicroCodeVersion = (UINT32) RShiftU64 (EfiReadMsr (EFI_MSR_IA32_BIOS_SIGN_ID), 32);\r
256 UnicodeSPrint (Buffer, sizeof (Buffer), L"%x", MicroCodeVersion);\r
257 HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_UCODE_VERSION), Buffer, NULL);\r
258}\r
259\r
260/**\r
261 Publish the smbios OEM type 0x90.\r
262\r
263 @param Event - Event whose notification function is being invoked (gEfiDxeSmmReadyToLockProtocolGuid).\r
264 @param Context - Pointer to the notification functions context, which is implementation dependent.\r
265\r
266 @retval None\r
267\r
268**/\r
269EFI_STATUS\r
270EFIAPI\r
271AddSmbiosT0x90Callback (\r
272 IN EFI_EVENT Event,\r
273 IN VOID *Context\r
274 )\r
275{\r
276 EFI_STATUS Status;\r
277 UINTN SECVerStrLen = 0;\r
278 UINTN uCodeVerStrLen = 0;\r
279 UINTN GOPStrLen = 0;\r
280 UINTN SteppingStrLen = 0;\r
281 SMBIOS_TABLE_TYPE90 *SmbiosRecord;\r
282 EFI_SMBIOS_HANDLE SmbiosHandle;\r
283 EFI_MISC_OEM_TYPE_0x90 *ForType90InputData;\r
284 CHAR16 *SECVer;\r
285 CHAR16 *uCodeVer;\r
286 CHAR16 *GOPVer;\r
287 CHAR16 *Stepping;\r
288 STRING_REF TokenToGet;\r
289 CHAR8 *OptionalStrStart;\r
290 EFI_SMBIOS_PROTOCOL *SmbiosProtocol;\r
291\r
292 ForType90InputData = (EFI_MISC_OEM_TYPE_0x90 *)Context;\r
293\r
294 DEBUG ((EFI_D_INFO, "Executing SMBIOS T0x90 callback.\n"));\r
295\r
296 gBS->CloseEvent (Event); // Unload this event.\r
297\r
298 //\r
299 // First check for invalid parameters.\r
300 //\r
301 if (Context == NULL) {\r
302 return EFI_INVALID_PARAMETER;\r
303 }\r
304\r
305 Status = gBS->LocateProtocol (\r
306 &gEfiSmbiosProtocolGuid,\r
307 NULL,\r
308 (VOID *) &SmbiosProtocol\r
309 );\r
310 ASSERT_EFI_ERROR (Status);\r
311\r
312 GetUcodeVersion();\r
313 GetGOPDriverName();\r
314 GetCPUStepping();\r
315\r
316 TokenToGet = STRING_TOKEN (STR_MISC_SEC_VERSION);\r
317 SECVer = SmbiosMiscGetString (TokenToGet);\r
318 SECVerStrLen = StrLen(SECVer);\r
319 if (SECVerStrLen > SMBIOS_STRING_MAX_LENGTH) {\r
320 return EFI_UNSUPPORTED;\r
321 }\r
322\r
323 TokenToGet = STRING_TOKEN (STR_MISC_UCODE_VERSION);\r
324 uCodeVer = SmbiosMiscGetString (TokenToGet);\r
325 uCodeVerStrLen = StrLen(uCodeVer);\r
326 if (uCodeVerStrLen > SMBIOS_STRING_MAX_LENGTH) {\r
327 return EFI_UNSUPPORTED;\r
328 }\r
329\r
330 TokenToGet = STRING_TOKEN (STR_MISC_GOP_VERSION);\r
331 GOPVer = SmbiosMiscGetString (TokenToGet);\r
332 GOPStrLen = StrLen(GOPVer);\r
333 if (GOPStrLen > SMBIOS_STRING_MAX_LENGTH) {\r
334 return EFI_UNSUPPORTED;\r
335 }\r
336\r
337 TokenToGet = STRING_TOKEN (STR_MISC_PROCESSOR_STEPPING);\r
338 Stepping = SmbiosMiscGetString (TokenToGet);\r
339 SteppingStrLen = StrLen(Stepping);\r
340\r
341\r
342 if (SteppingStrLen > SMBIOS_STRING_MAX_LENGTH) {\r
343 return EFI_UNSUPPORTED;\r
344 }\r
345\r
346 SmbiosRecord = AllocatePool(sizeof (SMBIOS_TABLE_TYPE90) + SECVerStrLen + 1 + uCodeVerStrLen + 1 + GOPStrLen + 1 + SteppingStrLen + 1 + 1);\r
347 ZeroMem(SmbiosRecord, sizeof (SMBIOS_TABLE_TYPE90) + SECVerStrLen + 1 + uCodeVerStrLen + 1 + GOPStrLen + 1 + SteppingStrLen + 1 + 1);\r
348\r
349 SmbiosRecord->Hdr.Type = EFI_SMBIOS_TYPE_FIRMWARE_VERSION_INFO;\r
350 SmbiosRecord->Hdr.Length = sizeof (SMBIOS_TABLE_TYPE90);\r
351\r
352 //\r
353 // Make handle chosen by smbios protocol.add automatically.\r
354 //\r
355 SmbiosRecord->Hdr.Handle = 0;\r
356\r
357 //\r
358 // SEC VERSION will be the 1st optional string following the formatted structure.\r
359 //\r
360 SmbiosRecord->SECVersion = 0;\r
361\r
362 //\r
363 // Microcode VERSION will be the 2nd optional string following the formatted structure.\r
364 //\r
365 SmbiosRecord->uCodeVersion = 2;\r
366\r
367 //\r
368 // GOP VERSION will be the 3rd optional string following the formatted structure.\r
369 //\r
370 SmbiosRecord->GOPVersion = 3;\r
371\r
372 //\r
373 // CPU Stepping will be the 4th optional string following the formatted structure.\r
374 //\r
375 SmbiosRecord->CpuStepping = 4;\r
376\r
377 OptionalStrStart = (CHAR8 *)(SmbiosRecord + 1);\r
378 UnicodeStrToAsciiStr(SECVer, OptionalStrStart);\r
379 UnicodeStrToAsciiStr(uCodeVer, OptionalStrStart + SECVerStrLen + 1);\r
380 UnicodeStrToAsciiStr(GOPVer, OptionalStrStart + SECVerStrLen + 1 + uCodeVerStrLen + 1);\r
381 UnicodeStrToAsciiStr(Stepping, OptionalStrStart + SECVerStrLen + 1 + uCodeVerStrLen + 1 + GOPStrLen + 1);\r
382\r
383 //\r
384 // Now we have got the full smbios record, call smbios protocol to add this record.\r
385 //\r
386 SmbiosHandle = SMBIOS_HANDLE_PI_RESERVED;\r
387 Status = SmbiosProtocol-> Add(\r
388 SmbiosProtocol,\r
389 NULL,\r
390 &SmbiosHandle,\r
391 (EFI_SMBIOS_TABLE_HEADER *) SmbiosRecord\r
392 );\r
393\r
394 FreePool(SmbiosRecord);\r
395 return Status;\r
396}\r
397\r
398\r
399/**\r
400 This function makes boot time changes to the contents of the\r
401 MiscOemType0x90 (Type 0x90).\r
402\r
403 @param RecordData Pointer to copy of RecordData from the Data Table.\r
404\r
405 @retval EFI_SUCCESS All parameters were valid.\r
406 @retval EFI_UNSUPPORTED Unexpected RecordType value.\r
407 @retval EFI_INVALID_PARAMETER Invalid parameter was found.\r
408\r
409**/\r
410MISC_SMBIOS_TABLE_FUNCTION(MiscOemType0x90)\r
411{\r
412 EFI_STATUS Status;\r
413 static BOOLEAN CallbackIsInstalledT0x90 = FALSE;\r
414 VOID *AddSmbiosT0x90CallbackNotifyReg;\r
415 EFI_EVENT AddSmbiosT0x90CallbackEvent;\r
416\r
417 //\r
418 // This callback will create a OEM Type 0x90 record.\r
419 //\r
420 if (CallbackIsInstalledT0x90 == FALSE) {\r
421 CallbackIsInstalledT0x90 = TRUE; // Prevent more than 1 callback.\r
422 DEBUG ((EFI_D_INFO, "Create Smbios T0x90 callback.\n"));\r
423\r
424 //\r
425 // gEfiDxeSmmReadyToLockProtocolGuid is ready\r
426 //\r
427 Status = gBS->CreateEvent (\r
428 EVT_NOTIFY_SIGNAL,\r
429 TPL_CALLBACK,\r
430 (EFI_EVENT_NOTIFY)AddSmbiosT0x90Callback,\r
431 RecordData,\r
432 &AddSmbiosT0x90CallbackEvent\r
433 );\r
434\r
435 ASSERT_EFI_ERROR (Status);\r
436 if (EFI_ERROR (Status)) {\r
437 return Status;\r
438\r
439 }\r
440\r
441 Status = gBS->RegisterProtocolNotify (\r
442 &gEfiDxeSmmReadyToLockProtocolGuid,\r
443 AddSmbiosT0x90CallbackEvent,\r
444 &AddSmbiosT0x90CallbackNotifyReg\r
445 );\r
446\r
447 return Status;\r
448 }\r
449\r
450 return EFI_SUCCESS;\r
451\r
452}\r