]> git.proxmox.com Git - mirror_edk2.git/blame - Vlv2TbltDevicePkg/PlatformDxe/BoardId.c
MdeModulePkg: Fix use-after-free error in InstallConfigurationTable()
[mirror_edk2.git] / Vlv2TbltDevicePkg / PlatformDxe / BoardId.c
CommitLineData
3cbfba02
DW
1/** @file\r
2\r
3 Copyright (c) 2004 - 2014, Intel Corporation. All rights reserved.<BR>\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
14Module Name:\r
15\r
16\r
17 BoardId.c\r
18\r
19Abstract:\r
20\r
21 Initialization for the board ID.\r
22\r
23 This code should be common across a chipset family of products.\r
24\r
25\r
26\r
27--*/\r
28\r
29#include "PchRegs.h"\r
30#include "PlatformDxe.h"\r
31#include <Guid/IdccData.h>\r
32#include <Guid/EfiVpdData.h>\r
33#include <Protocol/DataHub.h>\r
34\r
35\r
36extern EFI_GUID mPlatformDriverGuid;\r
37\r
38//\r
39// Global module data\r
40//\r
41UINT32 mBoardId;\r
42UINT8 mBoardIdIndex;\r
43EFI_BOARD_FEATURES mBoardFeatures;\r
44UINT16 mSubsystemDeviceId;\r
45UINT16 mSubsystemAudioDeviceId;\r
46CHAR8 BoardAaNumber[7];\r
47BOOLEAN mFoundAANum;\r
48\r
49/**\r
50\r
51 Write the boardid variable if it does not already exist.\r
52\r
53**/\r
54VOID\r
55InitializeBoardId (\r
56 )\r
57{\r
58\r
59 UINT32 BoardIdBufferSize;\r
60 EFI_IDCC_BOARD_FORM_FACTOR IdccBoardFormFactor;\r
61 EFI_DATA_HUB_PROTOCOL *DataHub;\r
62 EFI_STATUS Status;\r
63 DMI_DATA DmiDataVariable;\r
64 UINTN Size;\r
65#if defined(DUPLICATE_AA_NO_BASE_ADDR)\r
66 CHAR8 DuplicateAaNoAscii[sizeof(DmiDataVariable.BaseBoardVersion)];\r
67 UINTN iter;\r
68#endif\r
69#if defined(GPIO_BOARD_ID_SUPPORT) && GPIO_BOARD_ID_SUPPORT != 0\r
70 UINT8 Data8;\r
71#endif\r
72\r
73 //\r
74 // Update data from the updatable DMI data area\r
75 //\r
76 Size = sizeof (DMI_DATA);\r
77 SetMem(&DmiDataVariable, Size, 0xFF);\r
78 Status = gRT->GetVariable (\r
79 DMI_DATA_NAME,\r
80 &gDmiDataGuid,\r
81 NULL,\r
82 &Size,\r
83 &DmiDataVariable\r
84 );\r
85\r
86#if defined(DUPLICATE_AA_NO_BASE_ADDR)\r
87 //\r
88 // Get AA# from flash descriptor region\r
89 //\r
90 EfiSetMem(DuplicateAaNoAscii, sizeof(DuplicateAaNoAscii), 0xFF);\r
91 FlashRead((UINT8 *)(UINTN)DUPLICATE_AA_NO_BASE_ADDR,\r
92 (UINT8 *)DuplicateAaNoAscii,\r
93 sizeof(DuplicateAaNoAscii));\r
94\r
95 //\r
96 // Validate AA# read from VPD\r
97 //\r
98 for (iter = 0; iter < sizeof(DuplicateAaNoAscii); iter++) {\r
99 if ((DuplicateAaNoAscii[iter] != 0xFF) &&\r
100 (DuplicateAaNoAscii[iter] != DmiDataVariable.BaseBoardVersion[iter])) {\r
101 DmiDataVariable.BaseBoardVersion[iter] = DuplicateAaNoAscii[iter];\r
102 }\r
103 }\r
104\r
105 Status = EFI_SUCCESS;\r
106#endif\r
107\r
108 mFoundAANum = FALSE;\r
109\r
110 //\r
111 // No variable...no copy\r
112 //\r
113 if (EFI_ERROR (Status)) {\r
114 mBoardIdIndex = 0; // If we can't find the BoardId in the table, use the first entry\r
115 } else {\r
116 //\r
117 // This is the correct method of checking for AA#.\r
118 //\r
119 CopyMem(&BoardAaNumber, ((((UINT8*)&DmiDataVariable.BaseBoardVersion)+2)), 6);\r
120 BoardAaNumber[6] = 0;\r
121 for (mBoardIdIndex = 0; mBoardIdIndex < mBoardIdDecodeTableSize; mBoardIdIndex++) {\r
122 if (AsciiStrnCmp(mBoardIdDecodeTable[mBoardIdIndex].AaNumber, BoardAaNumber, 6) == 0) {\r
123 mFoundAANum = TRUE;\r
124 break;\r
125 }\r
126 }\r
127\r
128 if(!mFoundAANum) {\r
129 //\r
130 // Add check for AA#'s that is programmed without the AA as leading chars.\r
131 //\r
132 CopyMem(&BoardAaNumber, (((UINT8*)&DmiDataVariable.BaseBoardVersion)), 6);\r
133 BoardAaNumber[6] = 0;\r
134 for (mBoardIdIndex = 0; mBoardIdIndex < mBoardIdDecodeTableSize; mBoardIdIndex++) {\r
135 if (AsciiStrnCmp(mBoardIdDecodeTable[mBoardIdIndex].AaNumber, BoardAaNumber, 6) == 0) {\r
136 mFoundAANum = TRUE;\r
137 break;\r
138 }\r
139 }\r
140 }\r
141 }\r
142\r
143#if defined(GPIO_BOARD_ID_SUPPORT) && GPIO_BOARD_ID_SUPPORT != 0\r
144 //\r
145 // If we can't find the BoardAA# in the table, find BoardId\r
146 //\r
147 if (mFoundAANum != TRUE) {\r
148 //\r
149 // BoardID BIT Location\r
150 // 0 GPIO33 (ICH)\r
151 // 1 GPIO34 (ICH)\r
152 //\r
153 Data8 = IoRead8(GPIO_BASE_ADDRESS + R_PCH_GPIO_SC_LVL2);\r
154\r
155 //\r
156 // BoardId[0]\r
157 //\r
158 mBoardId = (UINT32)((Data8 >> 1) & BIT0);\r
159 //\r
160 // BoardId[1]\r
161 //\r
162 mBoardId |= (UINT32)((Data8 >> 1) & BIT1);\r
163\r
164 for (mBoardIdIndex = 0; mBoardIdIndex < mBoardIdDecodeTableSize; mBoardIdIndex++) {\r
165 if (mBoardIdDecodeTable[mBoardIdIndex].BoardId == mBoardId) {\r
166 break;\r
167 }\r
168 }\r
169#endif\r
170 if (mBoardIdIndex == mBoardIdDecodeTableSize) {\r
171 mBoardIdIndex = 0; // If we can't find the BoardId in the table, use the first entry\r
172 }\r
173#if defined(GPIO_BOARD_ID_SUPPORT) && GPIO_BOARD_ID_SUPPORT != 0\r
174 }\r
175#endif\r
176\r
177 mBoardFeatures = mBoardIdDecodeTable[mBoardIdIndex].Features;\r
178 mSubsystemDeviceId = mBoardIdDecodeTable[mBoardIdIndex].SubsystemDeviceId;\r
179 mSubsystemAudioDeviceId = mBoardIdDecodeTable[mBoardIdIndex].AudioSubsystemDeviceId;\r
180\r
181 //\r
182 // Set the BoardFeatures variable\r
183 //\r
184 BoardIdBufferSize = sizeof (mBoardFeatures);\r
185 gRT->SetVariable (\r
186 BOARD_FEATURES_NAME,\r
187 &gEfiBoardFeaturesGuid,\r
188 EFI_VARIABLE_NON_VOLATILE |\r
189 EFI_VARIABLE_BOOTSERVICE_ACCESS |\r
190 EFI_VARIABLE_RUNTIME_ACCESS,\r
191 BoardIdBufferSize,\r
192 &mBoardFeatures\r
193 );\r
194\r
195 //\r
196 // Get the Data Hub protocol\r
197 //\r
198 Status = gBS->LocateProtocol (\r
199 &gEfiDataHubProtocolGuid,\r
200 NULL,\r
201 (VOID **) &DataHub\r
202 );\r
203 if (!(EFI_ERROR(Status))) {\r
204 //\r
205 // Fill out data\r
206 //\r
207 IdccBoardFormFactor.IdccHeader.Type = EFI_IDCC_BOARD_FORM_FACTOR_TYPE;\r
208 IdccBoardFormFactor.IdccHeader.RecordLength = sizeof(EFI_IDCC_BOARD_FORM_FACTOR);\r
209 if ((mBoardFeatures & B_BOARD_FEATURES_FORM_FACTOR_ATX) || (mBoardFeatures & B_BOARD_FEATURES_FORM_FACTOR_MICRO_ATX)) {\r
210 IdccBoardFormFactor.BoardFormFactor = ATX_FORM_FACTOR; // ATX\r
211 } else {\r
212 IdccBoardFormFactor.BoardFormFactor = BTX_FORM_FACTOR; // BTX\r
213 }\r
214\r
215 //\r
216 // Publish the Board Form Factor value for IDCC\r
217 //\r
218 Status = DataHub->LogData (\r
219 DataHub,\r
220 &gIdccDataHubGuid,\r
221 &mPlatformDriverGuid,\r
222 EFI_DATA_RECORD_CLASS_DATA,\r
223 &IdccBoardFormFactor,\r
224 sizeof(EFI_IDCC_BOARD_FORM_FACTOR)\r
225 );\r
226 }\r
227}\r
228\r