]> git.proxmox.com Git - mirror_edk2.git/blame - Tools/Source/GenBuild/org/tianocore/build/pcd/action/CollectPCDAction.java
Add DATUM_TYPE checking for FEATURE_FLAG PCD entry. For FEATURE_FLAG PCD, the datum...
[mirror_edk2.git] / Tools / Source / GenBuild / org / tianocore / build / pcd / action / CollectPCDAction.java
CommitLineData
878ddf1f 1/** @file\r
2 CollectPCDAction class.\r
3\r
4 This action class is to collect PCD information from MSA, SPD, FPD xml file.\r
5 This class will be used for wizard and build tools, So it can *not* inherit\r
6 from buildAction or wizardAction.\r
7 \r
8Copyright (c) 2006, Intel Corporation\r
9All rights reserved. This program and the accompanying materials\r
10are licensed and made available under the terms and conditions of the BSD License\r
11which accompanies this distribution. The full text of the license may be found at\r
12http://opensource.org/licenses/bsd-license.php\r
13 \r
14THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
15WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
16\r
17**/\r
18package org.tianocore.build.pcd.action;\r
19\r
6ff7a41c 20import java.io.BufferedReader; \r
878ddf1f 21import java.io.File;\r
99d2c3c4 22import java.io.FileReader;\r
878ddf1f 23import java.io.IOException;\r
6f7e61a0 24import java.math.BigInteger;\r
878ddf1f 25import java.util.ArrayList;\r
99d2c3c4 26import java.util.Collections;\r
27import java.util.Comparator;\r
878ddf1f 28import java.util.HashMap;\r
29import java.util.List;\r
30import java.util.Map;\r
31import java.util.UUID;\r
32\r
33import org.apache.xmlbeans.XmlException;\r
34import org.apache.xmlbeans.XmlObject;\r
6ff7a41c 35import org.tianocore.DynamicPcdBuildDefinitionsDocument;\r
36import org.tianocore.DynamicPcdBuildDefinitionsDocument.DynamicPcdBuildDefinitions;\r
6ff7a41c 37import org.tianocore.DynamicPcdBuildDefinitionsDocument.DynamicPcdBuildDefinitions.PcdBuildData;\r
6f7e61a0 38import org.tianocore.DynamicPcdBuildDefinitionsDocument.DynamicPcdBuildDefinitions.PcdBuildData.SkuInfo;\r
8840ad58 39import org.tianocore.FrameworkModulesDocument;\r
878ddf1f 40import org.tianocore.FrameworkPlatformDescriptionDocument;\r
8840ad58 41import org.tianocore.FrameworkPlatformDescriptionDocument.FrameworkPlatformDescription;\r
878ddf1f 42import org.tianocore.ModuleSADocument;\r
8840ad58 43import org.tianocore.ModuleSADocument.ModuleSA;\r
878ddf1f 44import org.tianocore.PackageSurfaceAreaDocument;\r
6ff7a41c 45import org.tianocore.PcdBuildDefinitionDocument.PcdBuildDefinition;\r
878ddf1f 46import org.tianocore.build.global.GlobalData;\r
47import org.tianocore.build.global.SurfaceAreaQuery;\r
48import org.tianocore.build.pcd.action.ActionMessage;\r
6ff7a41c 49import org.tianocore.build.pcd.entity.DynamicTokenValue;\r
878ddf1f 50import org.tianocore.build.pcd.entity.MemoryDatabaseManager;\r
51import org.tianocore.build.pcd.entity.SkuInstance;\r
52import org.tianocore.build.pcd.entity.Token;\r
53import org.tianocore.build.pcd.entity.UsageInstance;\r
54import org.tianocore.build.pcd.exception.EntityException;\r
55\r
99d2c3c4 56class StringTable {\r
57 private ArrayList<String> al; \r
32648c62 58 private ArrayList<String> alComments;\r
99d2c3c4 59 private String phase;\r
60 int len; \r
32648c62 61 int bodyStart;\r
62 int bodyLineNum;\r
99d2c3c4 63\r
64 public StringTable (String phase) {\r
65 this.phase = phase;\r
66 al = new ArrayList<String>();\r
32648c62 67 alComments = new ArrayList<String>();\r
99d2c3c4 68 len = 0;\r
32648c62 69 bodyStart = 0;\r
70 bodyLineNum = 0;\r
99d2c3c4 71 }\r
72\r
73 public String getSizeMacro () {\r
74 return String.format(PcdDatabase.StringTableSizeMacro, phase, getSize());\r
75 }\r
76\r
77 private int getSize () {\r
32648c62 78 //\r
79 // We have at least one Unicode Character in the table.\r
80 //\r
99d2c3c4 81 return len == 0 ? 1 : len;\r
82 }\r
83\r
32648c62 84 public int getTableLen () {\r
85 return al.size() == 0 ? 1 : al.size();\r
86 }\r
99d2c3c4 87\r
88 public String getExistanceMacro () {\r
89 return String.format(PcdDatabase.StringTableExistenceMacro, phase, (al.size() == 0)? "TRUE":"FALSE");\r
90 }\r
91\r
92 public String getTypeDeclaration () {\r
93\r
32648c62 94 String output;\r
99d2c3c4 95\r
32648c62 96 final String stringTable = "StringTable";\r
97 final String tab = "\t";\r
98 final String newLine = ";\r\n";\r
99d2c3c4 99\r
32648c62 100 output = "/* StringTable */\r\n";\r
99d2c3c4 101\r
32648c62 102 if (al.size() == 0) {\r
103 output += tab + String.format("UINT16 %s[1] /* StringTable is Empty */", stringTable) + newLine;\r
104 }\r
99d2c3c4 105\r
32648c62 106 for (int i = 0; i < al.size(); i++) {\r
107 String str = al.get(i);\r
99d2c3c4 108\r
32648c62 109 if (i == 0) {\r
110 //\r
111 // StringTable is a well-known name in the PCD DXE driver\r
112 //\r
113 output += tab + String.format("UINT16 %s[%d] /* %s */", stringTable, str.length() + 1, alComments.get(i)) + newLine;\r
114 } else {\r
115 output += tab + String.format("UINT16 %s_%d[%d] /* %s */", stringTable, i, str.length() + 1, alComments.get(i)) + newLine;\r
116 }\r
117 }\r
99d2c3c4 118\r
32648c62 119 return output;\r
99d2c3c4 120\r
121 }\r
122\r
123 public ArrayList<String> getInstantiation () {\r
32648c62 124 ArrayList<String> output = new ArrayList<String>();\r
99d2c3c4 125\r
32648c62 126 output.add("/* StringTable */"); \r
99d2c3c4 127\r
32648c62 128 if (al.size() == 0) {\r
129 output.add("{ 0 }");\r
130 } else {\r
131 String str;\r
99d2c3c4 132\r
32648c62 133 for (int i = 0; i < al.size(); i++) {\r
134 str = String.format("L\"%s\" /* %s */", al.get(i), alComments.get(i));\r
135 if (i != al.size() - 1) {\r
136 str += ",";\r
137 }\r
138 output.add(str);\r
139 }\r
140 }\r
99d2c3c4 141\r
142 return output;\r
143 }\r
144\r
145 public int add (String str, Token token) {\r
146 int i;\r
147\r
148 i = len;\r
149 //\r
150 // Include the NULL character at the end of String\r
151 //\r
152 len += str.length() + 1; \r
153 al.add(str);\r
32648c62 154 alComments.add(token.getPrimaryKeyString());\r
99d2c3c4 155\r
156 return i;\r
157 }\r
158}\r
159\r
160class SizeTable {\r
161 private ArrayList<Integer> al;\r
32648c62 162 private ArrayList<String> alComments;\r
99d2c3c4 163 private String phase;\r
164 private int len;\r
32648c62 165 private int bodyStart;\r
166 private int bodyLineNum;\r
99d2c3c4 167\r
168 public SizeTable (String phase) {\r
169 this.phase = phase;\r
170 al = new ArrayList<Integer>();\r
32648c62 171 alComments = new ArrayList<String>();\r
99d2c3c4 172 len = 0;\r
32648c62 173 bodyStart = 0;\r
174 bodyLineNum = 0;\r
99d2c3c4 175 }\r
176\r
177 public String getTypeDeclaration () {\r
178 return String.format(PcdDatabase.SizeTableDeclaration, phase);\r
179 }\r
180\r
181 public ArrayList<String> getInstantiation () {\r
32648c62 182 ArrayList<String> Output = new ArrayList<String>();\r
99d2c3c4 183\r
184 Output.add("/* SizeTable */");\r
185 Output.add("{");\r
32648c62 186 bodyStart = 2;\r
187\r
188 if (al.size() == 0) {\r
189 Output.add("0");\r
190 } else {\r
191 for (int index = 0; index < al.size(); index++) {\r
192 Integer n = al.get(index);\r
193 String str = n.toString();\r
194\r
195 if (index != (al.size() - 1)) {\r
196 str += ",";\r
197 }\r
198\r
199 str += " /* " + alComments.get(index) + " */"; \r
200 Output.add(str);\r
201 bodyLineNum++;\r
202 \r
203 }\r
204 }\r
205 Output.add("}");\r
99d2c3c4 206\r
207 return Output;\r
208 }\r
209\r
32648c62 210 public int getBodyStart() {\r
211 return bodyStart;\r
212 }\r
99d2c3c4 213\r
32648c62 214 public int getBodyLineNum () {\r
215 return bodyLineNum;\r
216 }\r
99d2c3c4 217\r
218 public int add (Token token) {\r
219 int index = len;\r
220\r
221 len++; \r
222 al.add(token.datumSize);\r
32648c62 223 alComments.add(token.getPrimaryKeyString());\r
99d2c3c4 224\r
225 return index;\r
226 }\r
4acf8ce7 227 \r
32648c62 228 private int getDatumSize(Token token) {\r
229 /*\r
230 switch (token.datumType) {\r
231 case Token.DATUM_TYPE.UINT8:\r
232 return 1;\r
233 default:\r
234 return 0;\r
235 }\r
236 */\r
237 return 0;\r
238 }\r
99d2c3c4 239\r
32648c62 240 public int getTableLen () {\r
241 return al.size() == 0 ? 1 : al.size();\r
242 }\r
99d2c3c4 243\r
244}\r
245\r
246class GuidTable {\r
247 private ArrayList<UUID> al;\r
32648c62 248 private ArrayList<String> alComments;\r
99d2c3c4 249 private String phase;\r
250 private int len;\r
32648c62 251 private int bodyStart;\r
252 private int bodyLineNum;\r
99d2c3c4 253\r
254 public GuidTable (String phase) {\r
255 this.phase = phase;\r
256 al = new ArrayList<UUID>();\r
32648c62 257 alComments = new ArrayList<String>();\r
99d2c3c4 258 len = 0;\r
32648c62 259 bodyStart = 0;\r
260 bodyLineNum = 0;\r
99d2c3c4 261 }\r
262\r
263 public String getSizeMacro () {\r
264 return String.format(PcdDatabase.GuidTableSizeMacro, phase, getSize());\r
265 }\r
266\r
267 private int getSize () {\r
268 return (al.size() == 0)? 1 : al.size();\r
269 }\r
270\r
271 public String getExistanceMacro () {\r
272 return String.format(PcdDatabase.GuidTableExistenceMacro, phase, (al.size() == 0)? "TRUE":"FALSE");\r
273 }\r
274\r
275 public String getTypeDeclaration () {\r
276 return String.format(PcdDatabase.GuidTableDeclaration, phase);\r
277 }\r
278\r
32648c62 279 private String getUuidCString (UUID uuid) {\r
280 String[] guidStrArray;\r
281\r
282 guidStrArray =(uuid.toString()).split("-");\r
283\r
284 return String.format("{ 0x%s, 0x%s, 0x%s, { 0x%s, 0x%s, 0x%s, 0x%s, 0x%s, 0x%s, 0x%s, 0x%s } }",\r
285 guidStrArray[0],\r
286 guidStrArray[1],\r
287 guidStrArray[2],\r
288 (guidStrArray[3].substring(0, 2)),\r
289 (guidStrArray[3].substring(2, 4)),\r
290 (guidStrArray[4].substring(0, 2)),\r
291 (guidStrArray[4].substring(2, 4)),\r
292 (guidStrArray[4].substring(4, 6)),\r
293 (guidStrArray[4].substring(6, 8)),\r
294 (guidStrArray[4].substring(8, 10)),\r
295 (guidStrArray[4].substring(10, 12))\r
296 );\r
297 }\r
99d2c3c4 298\r
299 public ArrayList<String> getInstantiation () {\r
32648c62 300 ArrayList<String> Output = new ArrayList<String>();\r
99d2c3c4 301\r
302 Output.add("/* GuidTable */");\r
303 Output.add("{");\r
32648c62 304 bodyStart = 2;\r
99d2c3c4 305\r
32648c62 306 if (al.size() == 0) {\r
307 Output.add(getUuidCString(new UUID(0, 0)));\r
308 }\r
99d2c3c4 309 \r
310 for (Object u : al) {\r
311 UUID uuid = (UUID)u;\r
32648c62 312 String str = getUuidCString(uuid);\r
99d2c3c4 313\r
32648c62 314 if (al.indexOf(u) != (al.size() - 1)) {\r
315 str += ",";\r
316 }\r
99d2c3c4 317 Output.add(str);\r
32648c62 318 bodyLineNum++;\r
99d2c3c4 319\r
320 }\r
32648c62 321 Output.add("}");\r
99d2c3c4 322\r
323 return Output;\r
324 }\r
325\r
32648c62 326 public int getBodyStart() {\r
327 return bodyStart;\r
328 }\r
99d2c3c4 329\r
32648c62 330 public int getBodyLineNum () {\r
331 return bodyLineNum;\r
332 }\r
99d2c3c4 333\r
334 public int add (UUID uuid, String name) {\r
335 int index = len;\r
336 //\r
337 // Include the NULL character at the end of String\r
338 //\r
339 len++; \r
340 al.add(uuid);\r
341\r
342 return index;\r
343 }\r
344\r
32648c62 345 public int getTableLen () {\r
346 return al.size() == 0 ? 0 : al.size();\r
347 }\r
99d2c3c4 348\r
349}\r
350\r
351class SkuIdTable {\r
352 private ArrayList<Integer[]> al;\r
32648c62 353 private ArrayList<String> alComment;\r
99d2c3c4 354 private String phase;\r
355 private int len;\r
32648c62 356 private int bodyStart;\r
357 private int bodyLineNum;\r
99d2c3c4 358\r
359 public SkuIdTable (String phase) {\r
360 this.phase = phase;\r
361 al = new ArrayList<Integer[]>();\r
32648c62 362 alComment = new ArrayList<String>();\r
363 bodyStart = 0;\r
364 bodyLineNum = 0;\r
99d2c3c4 365 len = 0;\r
366 }\r
367\r
368 public String getSizeMacro () {\r
369 return String.format(PcdDatabase.SkuIdTableSizeMacro, phase, getSize());\r
370 }\r
371\r
372 private int getSize () {\r
373 return (al.size() == 0)? 1 : al.size();\r
374 }\r
375\r
376 public String getExistanceMacro () {\r
377 return String.format(PcdDatabase.SkuTableExistenceMacro, phase, (al.size() == 0)? "TRUE":"FALSE");\r
378 }\r
379\r
380 public String getTypeDeclaration () {\r
381 return String.format(PcdDatabase.SkuIdTableDeclaration, phase);\r
382 }\r
383\r
384 public ArrayList<String> getInstantiation () {\r
32648c62 385 ArrayList<String> Output = new ArrayList<String> ();\r
99d2c3c4 386\r
387 Output.add("/* SkuIdTable */");\r
388 Output.add("{");\r
32648c62 389 bodyStart = 2;\r
99d2c3c4 390\r
32648c62 391 if (al.size() == 0) {\r
392 Output.add("0");\r
393 }\r
99d2c3c4 394 \r
395 for (int index = 0; index < al.size(); index++) {\r
32648c62 396 String str;\r
99d2c3c4 397\r
32648c62 398 str = "/* " + alComment.get(index) + "*/ ";\r
399 str += "/* MaxSku */ ";\r
99d2c3c4 400\r
401\r
32648c62 402 Integer[] ia = al.get(index);\r
99d2c3c4 403\r
32648c62 404 str += ia[0].toString() + ", ";\r
405 for (int index2 = 1; index2 < ia.length; index2++) {\r
406 str += ia[index2].toString();\r
407 if (index != al.size() - 1) {\r
408 str += ", ";\r
409 }\r
410 }\r
99d2c3c4 411\r
412 Output.add(str);\r
32648c62 413 bodyLineNum++;\r
99d2c3c4 414\r
415 }\r
416\r
32648c62 417 Output.add("}");\r
99d2c3c4 418\r
419 return Output;\r
420 }\r
421\r
422 public int add (Token token) {\r
423\r
32648c62 424 int index;\r
99d2c3c4 425\r
6ff7a41c 426 Integer [] skuIds = new Integer[token.skuData.size() + 1];\r
427 skuIds[0] = new Integer(token.skuData.size());\r
32648c62 428 for (index = 1; index < skuIds.length; index++) {\r
429 skuIds[index] = new Integer(token.skuData.get(index - 1).id);\r
430 }\r
99d2c3c4 431\r
432 index = len;\r
433\r
434 len += skuIds.length; \r
435 al.add(skuIds);\r
32648c62 436 alComment.add(token.getPrimaryKeyString());\r
99d2c3c4 437\r
438 return index;\r
439 }\r
440\r
32648c62 441 public int getTableLen () {\r
442 return al.size() == 0 ? 1 : al.size();\r
443 }\r
99d2c3c4 444\r
445}\r
446\r
447class LocalTokenNumberTable {\r
448 private ArrayList<String> al;\r
32648c62 449 private ArrayList<String> alComment;\r
99d2c3c4 450 private String phase;\r
451 private int len;\r
99d2c3c4 452\r
453 public LocalTokenNumberTable (String phase) {\r
454 this.phase = phase;\r
455 al = new ArrayList<String>();\r
32648c62 456 alComment = new ArrayList<String>();\r
99d2c3c4 457\r
458 len = 0;\r
459 }\r
460\r
461 public String getSizeMacro () {\r
3496595d 462 return String.format(PcdDatabase.LocalTokenNumberTableSizeMacro, phase, getSize())\r
463 + String.format(PcdDatabase.LocalTokenNumberSizeMacro, phase, al.size());\r
99d2c3c4 464 }\r
465\r
466 public int getSize () {\r
467 return (al.size() == 0)? 1 : al.size();\r
468 }\r
469\r
470 public String getExistanceMacro () {\r
471 return String.format(PcdDatabase.DatabaseExistenceMacro, phase, (al.size() == 0)? "TRUE":"FALSE");\r
472 }\r
473\r
474 public String getTypeDeclaration () {\r
475 return String.format(PcdDatabase.LocalTokenNumberTableDeclaration, phase);\r
476 }\r
477\r
478 public ArrayList<String> getInstantiation () {\r
32648c62 479 ArrayList<String> output = new ArrayList<String>();\r
99d2c3c4 480\r
481 output.add("/* LocalTokenNumberTable */");\r
482 output.add("{");\r
99d2c3c4 483\r
32648c62 484 if (al.size() == 0) {\r
485 output.add("0");\r
486 }\r
99d2c3c4 487 \r
488 for (int index = 0; index < al.size(); index++) {\r
32648c62 489 String str;\r
99d2c3c4 490\r
32648c62 491 str = (String)al.get(index);\r
99d2c3c4 492\r
32648c62 493 str += " /* " + alComment.get(index) + " */ ";\r
99d2c3c4 494\r
495\r
32648c62 496 if (index != (al.size() - 1)) {\r
497 str += ",";\r
498 }\r
99d2c3c4 499\r
500 output.add(str);\r
501\r
502 }\r
503\r
32648c62 504 output.add("}");\r
99d2c3c4 505\r
506 return output;\r
507 }\r
508\r
509 public int add (Token token) {\r
510 int index = len;\r
32648c62 511 String str;\r
99d2c3c4 512\r
513 len++; \r
514\r
32648c62 515 str = String.format(PcdDatabase.offsetOfStrTemplate, phase, token.hasDefaultValue() ? "Init" : "Uninit", token.getPrimaryKeyString());\r
99d2c3c4 516\r
f63ef4b2 517 if (token.isUnicodeStringType()) {\r
32648c62 518 str += " | PCD_TYPE_STRING";\r
519 }\r
99d2c3c4 520\r
6ff7a41c 521 if (token.isSkuEnable()) {\r
32648c62 522 str += " | PCD_TYPE_SKU_ENABLED";\r
523 }\r
99d2c3c4 524\r
6ff7a41c 525 if (token.getDefaultSku().type == DynamicTokenValue.VALUE_TYPE.HII_TYPE) {\r
32648c62 526 str += " | PCD_TYPE_HII";\r
527 }\r
99d2c3c4 528\r
6ff7a41c 529 if (token.getDefaultSku().type == DynamicTokenValue.VALUE_TYPE.VPD_TYPE) {\r
32648c62 530 str += " | PCD_TYPE_VPD";\r
531 }\r
532 \r
99d2c3c4 533 al.add(str);\r
32648c62 534 alComment.add(token.getPrimaryKeyString());\r
99d2c3c4 535\r
536 return index;\r
537 }\r
538}\r
539\r
540class ExMapTable {\r
541\r
32648c62 542 class ExTriplet {\r
543 public Integer guidTableIdx;\r
544 public Long exTokenNumber;\r
545 public Long localTokenIdx;\r
546 \r
547 public ExTriplet (int guidTableIdx, long exTokenNumber, long localTokenIdx) {\r
548 this.guidTableIdx = new Integer(guidTableIdx);\r
549 this.exTokenNumber = new Long(exTokenNumber);\r
550 this.localTokenIdx = new Long(localTokenIdx);\r
551 }\r
552 }\r
99d2c3c4 553\r
554 private ArrayList<ExTriplet> al;\r
32648c62 555 private ArrayList<String> alComment;\r
99d2c3c4 556 private String phase;\r
557 private int len;\r
32648c62 558 private int bodyStart;\r
559 private int bodyLineNum;\r
560 private int base;\r
99d2c3c4 561\r
562 public ExMapTable (String phase) {\r
563 this.phase = phase;\r
564 al = new ArrayList<ExTriplet>();\r
32648c62 565 alComment = new ArrayList<String>();\r
566 bodyStart = 0;\r
567 bodyLineNum = 0;\r
99d2c3c4 568 len = 0;\r
569 }\r
570\r
571 public String getSizeMacro () {\r
572 return String.format(PcdDatabase.ExMapTableSizeMacro, phase, getTableLen())\r
32648c62 573 + String.format(PcdDatabase.ExTokenNumber, phase, al.size());\r
99d2c3c4 574 }\r
575\r
576 private int getSize () {\r
577 return (al.size() == 0)? 1 : al.size();\r
578 }\r
579\r
580 public String getExistanceMacro () {\r
581 return String.format(PcdDatabase.ExMapTableExistenceMacro, phase, (al.size() == 0)? "TRUE":"FALSE");\r
582 }\r
583\r
584 public String getTypeDeclaration () {\r
585 return String.format(PcdDatabase.ExMapTableDeclaration, phase);\r
586 }\r
587\r
588 public ArrayList<String> getInstantiation () {\r
32648c62 589 ArrayList<String> Output = new ArrayList<String>();\r
99d2c3c4 590\r
591 Output.add("/* ExMapTable */");\r
592 Output.add("{");\r
32648c62 593 bodyStart = 2;\r
99d2c3c4 594\r
32648c62 595 if (al.size() == 0) {\r
596 Output.add("{0, 0, 0}");\r
597 }\r
99d2c3c4 598 \r
32648c62 599 int index;\r
99d2c3c4 600 for (index = 0; index < al.size(); index++) {\r
32648c62 601 String str;\r
99d2c3c4 602\r
32648c62 603 ExTriplet e = (ExTriplet)al.get(index);\r
99d2c3c4 604\r
32648c62 605 str = "{ " + e.exTokenNumber.toString() + ", ";\r
606 str += e.localTokenIdx.toString() + ", ";\r
607 str += e.guidTableIdx.toString();\r
99d2c3c4 608\r
32648c62 609 str += " /* " + alComment.get(index) + " */";\r
99d2c3c4 610\r
32648c62 611 if (index != al.size() - 1) {\r
612 str += ",";\r
613 }\r
99d2c3c4 614\r
615 Output.add(str);\r
32648c62 616 bodyLineNum++;\r
99d2c3c4 617\r
618 }\r
619\r
32648c62 620 Output.add("}");\r
99d2c3c4 621\r
622 return Output;\r
623 }\r
624\r
625 public int add (int localTokenIdx, long exTokenNum, int guidTableIdx, String name) {\r
626 int index = len;\r
627\r
628 len++; \r
629 al.add(new ExTriplet(guidTableIdx, exTokenNum, localTokenIdx));\r
32648c62 630 alComment.add(name);\r
99d2c3c4 631\r
632 return index;\r
633 }\r
634\r
32648c62 635 public int getTableLen () {\r
636 return al.size() == 0 ? 1 : al.size();\r
637 }\r
99d2c3c4 638\r
639}\r
640\r
641class PcdDatabase {\r
642\r
643 public final static String ExMapTableDeclaration = "DYNAMICEX_MAPPING ExMapTable[%s_EXMAPPING_TABLE_SIZE];\r\n";\r
644 public final static String GuidTableDeclaration = "EFI_GUID GuidTable[%s_GUID_TABLE_SIZE];\r\n";\r
3496595d 645 public final static String LocalTokenNumberTableDeclaration = "UINT32 LocalTokenNumberTable[%s_LOCAL_TOKEN_NUMBER_TABLE_SIZE];\r\n";\r
99d2c3c4 646 public final static String StringTableDeclaration = "UINT16 StringTable[%s_STRING_TABLE_SIZE];\r\n";\r
3496595d 647 public final static String SizeTableDeclaration = "UINT16 SizeTable[%s_LOCAL_TOKEN_NUMBER_TABLE_SIZE];\r\n";\r
99d2c3c4 648 public final static String SkuIdTableDeclaration = "UINT8 SkuIdTable[%s_SKUID_TABLE_SIZE];\r\n";\r
649\r
650\r
651 public final static String ExMapTableSizeMacro = "#define %s_EXMAPPING_TABLE_SIZE %d\r\n";\r
32648c62 652 public final static String ExTokenNumber = "#define %s_EX_TOKEN_NUMBER %d\r\n";\r
99d2c3c4 653 public final static String GuidTableSizeMacro = "#define %s_GUID_TABLE_SIZE %d\r\n";\r
3496595d 654 public final static String LocalTokenNumberTableSizeMacro = "#define %s_LOCAL_TOKEN_NUMBER_TABLE_SIZE %d\r\n";\r
655 public final static String LocalTokenNumberSizeMacro = "#define %s_LOCAL_TOKEN_NUMBER %d\r\n";\r
99d2c3c4 656 public final static String StringTableSizeMacro = "#define %s_STRING_TABLE_SIZE %d\r\n";\r
657 public final static String SkuIdTableSizeMacro = "#define %s_SKUID_TABLE_SIZE %d\r\n";\r
658\r
659\r
660 public final static String ExMapTableExistenceMacro = "#define %s_EXMAP_TABLE_EMPTY %s\r\n"; \r
661 public final static String GuidTableExistenceMacro = "#define %s_GUID_TABLE_EMPTY %s\r\n";\r
662 public final static String DatabaseExistenceMacro = "#define %s_DATABASE_EMPTY %s\r\n";\r
663 public final static String StringTableExistenceMacro = "#define %s_STRING_TABLE_EMPTY %s\r\n";\r
664 public final static String SkuTableExistenceMacro = "#define %s_SKUID_TABLE_EMPTY %s\r\n";\r
665\r
32648c62 666 public final static String offsetOfSkuHeadStrTemplate = "offsetof(%s_PCD_DATABASE, %s.%s_SkuDataTable)";\r
667 public final static String offsetOfStrTemplate = "offsetof(%s_PCD_DATABASE, %s.%s)";\r
99d2c3c4 668\r
32648c62 669 private StringTable stringTable;\r
670 private GuidTable guidTable;\r
671 private LocalTokenNumberTable localTokenNumberTable;\r
672 private SkuIdTable skuIdTable;\r
673 private SizeTable sizeTable;\r
674 private ExMapTable exMapTable;\r
99d2c3c4 675\r
32648c62 676 private ArrayList<Token> alTokens;\r
677 private String phase;\r
678 private int assignedTokenNumber;\r
4acf8ce7 679 \r
680 //\r
681 // After Major changes done to the PCD\r
682 // database generation class PcdDatabase\r
683 // Please increment the version and please\r
684 // also update the version number in PCD\r
685 // service PEIM and DXE driver accordingly.\r
686 //\r
687 private final int version = 1;\r
99d2c3c4 688\r
32648c62 689 private String hString;\r
690 private String cString;\r
99d2c3c4 691\r
692\r
32648c62 693 class AlignmentSizeComp implements Comparator<Token> {\r
99d2c3c4 694 public int compare (Token a, Token b) {\r
32648c62 695 return getAlignmentSize(b) \r
696 - getAlignmentSize(a);\r
697 }\r
698 }\r
699\r
700 public PcdDatabase (ArrayList<Token> alTokens, String exePhase, int startLen) {\r
701 phase = exePhase;\r
702\r
703 stringTable = new StringTable(phase);\r
704 guidTable = new GuidTable(phase);\r
705 localTokenNumberTable = new LocalTokenNumberTable(phase);\r
706 skuIdTable = new SkuIdTable(phase);\r
707 sizeTable = new SizeTable(phase);\r
708 exMapTable = new ExMapTable(phase); \r
709\r
710 assignedTokenNumber = startLen;\r
711 this.alTokens = alTokens;\r
712 }\r
713\r
714 private void getTwoGroupsOfTokens (ArrayList<Token> alTokens, List<Token> initTokens, List<Token> uninitTokens) {\r
715 for (int i = 0; i < alTokens.size(); i++) {\r
8840ad58 716 Token t = (Token)alTokens.get(i);\r
32648c62 717 if (t.hasDefaultValue()) {\r
718 initTokens.add(t);\r
719 } else {\r
720 uninitTokens.add(t);\r
721 }\r
722 }\r
723\r
724 return;\r
725 }\r
726\r
727 private int getAlignmentSize (Token token) {\r
6ff7a41c 728 if (token.getDefaultSku().type == DynamicTokenValue.VALUE_TYPE.HII_TYPE) {\r
32648c62 729 return 2;\r
730 }\r
731\r
6ff7a41c 732 if (token.getDefaultSku().type == DynamicTokenValue.VALUE_TYPE.VPD_TYPE) {\r
32648c62 733 return 4;\r
734 }\r
735\r
f63ef4b2 736 if (token.isUnicodeStringType()) {\r
32648c62 737 return 2;\r
738 }\r
739\r
740 switch (token.datumType) {\r
741 case UINT8:\r
742 return 1;\r
743 case UINT16:\r
744 return 2;\r
745 case UINT32:\r
746 return 4;\r
747 case UINT64:\r
748 return 8;\r
749 case POINTER:\r
750 return 1;\r
751 case BOOLEAN:\r
752 return 1;\r
753 }\r
754 return 1;\r
755 }\r
756\r
757 public String getCString () {\r
758 return cString;\r
759 }\r
760\r
761 public String getHString () {\r
762 return hString;\r
763 }\r
99d2c3c4 764\r
6ff7a41c 765 public void genCode () \r
766 throws EntityException {\r
99d2c3c4 767\r
32648c62 768 final String newLine = "\r\n";\r
32648c62 769 final String declNewLine = ";\r\n";\r
770 final String tab = "\t";\r
32648c62 771 final String commaNewLine = ", \r\n";\r
772\r
773 int i;\r
774 ArrayList<String> decla;\r
775 ArrayList<String> inst;\r
776\r
777 String macroStr = "";\r
778 String initDeclStr = "";\r
779 String initInstStr = "";\r
780 String uninitDeclStr = "";\r
781\r
782 List<Token> initTokens = new ArrayList<Token> ();\r
783 List<Token> uninitTokens = new ArrayList<Token> ();\r
784 \r
785 HashMap <String, ArrayList<String>> initCode = new HashMap<String, ArrayList<String>> ();\r
786 HashMap <String, ArrayList<String>> uninitCode = new HashMap<String, ArrayList<String>> ();\r
787\r
788 getTwoGroupsOfTokens (alTokens, initTokens, uninitTokens);\r
789\r
790 //\r
791 // Generate Structure Declaration for PcdTokens without Default Value\r
792 // PEI_PCD_DATABASE_INIT\r
793 //\r
6a4cae58 794 java.util.Comparator<Token> comparator = new AlignmentSizeComp();\r
4c114006 795 java.util.Collections.sort(initTokens, comparator);\r
32648c62 796 initCode = processTokens(initTokens);\r
797\r
798 //\r
799 // Generate Structure Declaration for PcdTokens without Default Value\r
800 // PEI_PCD_DATABASE_UNINIT\r
801 //\r
4c114006 802 java.util.Collections.sort(uninitTokens, comparator);\r
32648c62 803 uninitCode = processTokens(uninitTokens);\r
804\r
805 //\r
806 // Generate size info Macro for all Tables\r
807 //\r
808 macroStr += guidTable.getSizeMacro();\r
809 macroStr += stringTable.getSizeMacro();\r
810 macroStr += skuIdTable.getSizeMacro();\r
811 macroStr += localTokenNumberTable.getSizeMacro();\r
812 macroStr += exMapTable.getSizeMacro();\r
813\r
814 //\r
815 // Generate existance info Macro for all Tables\r
816 //\r
817 macroStr += guidTable.getExistanceMacro();\r
818 macroStr += stringTable.getExistanceMacro();\r
819 macroStr += skuIdTable.getExistanceMacro();\r
820 macroStr += localTokenNumberTable.getExistanceMacro();\r
821 macroStr += exMapTable.getExistanceMacro();\r
822\r
823 //\r
824 // Generate Structure Declaration for PcdTokens with Default Value\r
825 // for example PEI_PCD_DATABASE_INIT\r
826 //\r
827 initDeclStr += "typedef struct {" + newLine;\r
828 {\r
829 initDeclStr += tab + exMapTable.getTypeDeclaration();\r
830 initDeclStr += tab + guidTable.getTypeDeclaration();\r
831 initDeclStr += tab + localTokenNumberTable.getTypeDeclaration();\r
832 initDeclStr += tab + stringTable.getTypeDeclaration();\r
833 initDeclStr += tab + sizeTable.getTypeDeclaration();\r
834 initDeclStr += tab + skuIdTable.getTypeDeclaration();\r
835 if (phase.equalsIgnoreCase("PEI")) {\r
836 initDeclStr += tab + "SKU_ID SystemSkuId;" + newLine;\r
837 }\r
838\r
839 decla = initCode.get(new String("Declaration"));\r
840 for (i = 0; i < decla.size(); i++) {\r
841 initDeclStr += tab + decla.get(i) + declNewLine;\r
842 }\r
843\r
844 //\r
845 // Generate Structure Declaration for PcdToken with SkuEnabled\r
846 //\r
847 decla = initCode.get("DeclarationForSku");\r
848\r
849 for (i = 0; i < decla.size(); i++) {\r
850 initDeclStr += tab + decla.get(i) + declNewLine;\r
851 }\r
852 }\r
853 initDeclStr += String.format("} %s_PCD_DATABASE_INIT;\r\n\r\n", phase);\r
854\r
855 //\r
856 // Generate MACRO for structure intialization of PCDTokens with Default Value\r
857 // The sequence must match the sequence of declaration of the memembers in the structure\r
858 String tmp = String.format("%s_PCD_DATABASE_INIT g%sPcdDbInit = { ", phase.toUpperCase(), phase.toUpperCase());\r
859 initInstStr += tmp + newLine;\r
860 initInstStr += tab + genInstantiationStr(exMapTable.getInstantiation()) + commaNewLine;\r
861 initInstStr += tab + genInstantiationStr(guidTable.getInstantiation()) + commaNewLine;\r
862 initInstStr += tab + genInstantiationStr(localTokenNumberTable.getInstantiation()) + commaNewLine; \r
32648c62 863 initInstStr += tab + genInstantiationStr(stringTable.getInstantiation()) + commaNewLine;\r
864 initInstStr += tab + genInstantiationStr(sizeTable.getInstantiation()) + commaNewLine;\r
865 initInstStr += tab + genInstantiationStr(skuIdTable.getInstantiation()) + commaNewLine;\r
866 //\r
867 // For SystemSkuId\r
868 //\r
869 if (phase.equalsIgnoreCase("PEI")) {\r
870 initInstStr += tab + "0" + tab + "/* SystemSkuId */" + commaNewLine;\r
871 }\r
872\r
873 inst = initCode.get("Instantiation");\r
874 for (i = 0; i < inst.size(); i++) {\r
875 initInstStr += tab + inst.get(i) + commaNewLine;\r
876 }\r
877\r
878 inst = initCode.get("InstantiationForSku");\r
879 for (i = 0; i < inst.size(); i++) {\r
880 initInstStr += tab + inst.get(i);\r
881 if (i != inst.size() - 1) {\r
882 initInstStr += commaNewLine;\r
883 }\r
884 }\r
885\r
886 initInstStr += "};";\r
887\r
888 uninitDeclStr += "typedef struct {" + newLine;\r
889 {\r
890 decla = uninitCode.get("Declaration");\r
891 if (decla.size() == 0) {\r
892 uninitDeclStr += "UINT8 dummy /* The UINT struct is empty */" + declNewLine;\r
893 } else {\r
894 \r
895 for (i = 0; i < decla.size(); i++) {\r
896 uninitDeclStr += tab + decla.get(i) + declNewLine;\r
897 }\r
898 \r
899 decla = uninitCode.get("DeclarationForSku");\r
900 \r
901 for (i = 0; i < decla.size(); i++) {\r
902 uninitDeclStr += tab + decla.get(i) + declNewLine;\r
903 }\r
904 }\r
905 }\r
906 uninitDeclStr += String.format("} %s_PCD_DATABASE_UNINIT;\r\n\r\n", phase);\r
907\r
908 cString = initInstStr + newLine;\r
909 hString = macroStr + newLine \r
910 + initDeclStr + newLine\r
911 + uninitDeclStr + newLine\r
912 + newLine;\r
4acf8ce7 913 \r
914 hString += String.format("#define PCD_%s_SERVICE_DRIVER_VERSION %d", phase, version);\r
32648c62 915\r
916 }\r
917\r
918 private String genInstantiationStr (ArrayList<String> alStr) {\r
919 String str = "";\r
920 for (int i = 0; i< alStr.size(); i++) {\r
921 str += "\t" + alStr.get(i);\r
922 if (i != alStr.size() - 1) {\r
923 str += "\r\n";\r
924 }\r
925 }\r
926\r
927 return str;\r
928 }\r
929\r
6ff7a41c 930 private HashMap<String, ArrayList<String>> processTokens (List<Token> alToken) \r
931 throws EntityException {\r
32648c62 932\r
32648c62 933 HashMap <String, ArrayList<String>> map = new HashMap<String, ArrayList<String>>();\r
934\r
935 ArrayList<String> decl = new ArrayList<String>();\r
936 ArrayList<String> declForSkuEnableType = new ArrayList<String>();\r
937 ArrayList<String> inst = new ArrayList<String>();\r
938 ArrayList<String> instForSkuEnableType = new ArrayList<String>();\r
939\r
940 for (int index = 0; index < alToken.size(); index++) {\r
941 Token token = alToken.get(index);\r
942\r
6ff7a41c 943 if (token.isSkuEnable()) {\r
32648c62 944 //\r
945 // BugBug: Schema only support Data type now\r
946 //\r
947 int tableIdx;\r
948\r
949 tableIdx = skuIdTable.add(token);\r
950\r
951 decl.add(getSkuEnabledTypeDeclaration(token));\r
952 if (token.hasDefaultValue()) {\r
953 inst.add(getSkuEnabledTypeInstantiaion(token, tableIdx)); \r
954 }\r
955\r
956 declForSkuEnableType.add(getDataTypeDeclarationForSkuEnabled(token));\r
957 if (token.hasDefaultValue()) {\r
958 instForSkuEnableType.add(getDataTypeInstantiationForSkuEnabled(token));\r
959 }\r
960\r
961 } else {\r
6ff7a41c 962 if (token.getDefaultSku().type == DynamicTokenValue.VALUE_TYPE.HII_TYPE) {\r
32648c62 963 decl.add(getVariableEnableTypeDeclaration(token));\r
964 inst.add(getVariableEnableInstantiation(token));\r
6ff7a41c 965 } else if (token.getDefaultSku().type == DynamicTokenValue.VALUE_TYPE.VPD_TYPE) {\r
32648c62 966 decl.add(getVpdEnableTypeDeclaration(token));\r
967 inst.add(getVpdEnableTypeInstantiation(token));\r
f63ef4b2 968 } else if (token.isUnicodeStringType()) {\r
32648c62 969 decl.add(getStringTypeDeclaration(token));\r
970 inst.add(getStringTypeInstantiation(stringTable.add(token.getStringTypeString(), token), token));\r
971 }\r
972 else {\r
973 decl.add(getDataTypeDeclaration(token));\r
974 if (token.hasDefaultValue()) {\r
975 inst.add(getDataTypeInstantiation(token));\r
976 }\r
977 }\r
978 }\r
979\r
980 sizeTable.add(token);\r
981 localTokenNumberTable.add(token);\r
8840ad58 982 token.tokenNumber = assignedTokenNumber++;\r
32648c62 983\r
984 }\r
985\r
986 map.put("Declaration", decl);\r
987 map.put("DeclarationForSku", declForSkuEnableType);\r
988 map.put("Instantiation", inst);\r
989 map.put("InstantiationForSku", instForSkuEnableType);\r
990\r
991 return map;\r
992 }\r
993\r
994 private String getSkuEnabledTypeDeclaration (Token token) {\r
995 return String.format("SKU_HEAD %s;\r\n", token.getPrimaryKeyString());\r
996 }\r
997\r
998 private String getSkuEnabledTypeInstantiaion (Token token, int SkuTableIdx) {\r
999\r
1000 String offsetof = String.format(PcdDatabase.offsetOfSkuHeadStrTemplate, phase, token.hasDefaultValue()? "Init" : "Uninit", token.getPrimaryKeyString());\r
1001 return String.format("{ %s, %d }", offsetof, SkuTableIdx);\r
1002 }\r
1003\r
1004 private String getDataTypeDeclarationForSkuEnabled (Token token) {\r
1005 String typeStr = "";\r
1006\r
1007 if (token.datumType == Token.DATUM_TYPE.UINT8) {\r
1008 typeStr = "UINT8 %s_%s[%d];\r\n";\r
1009 } else if (token.datumType == Token.DATUM_TYPE.UINT16) {\r
1010 typeStr = "UINT16 %s_%s[%d];\r\n";\r
1011 } else if (token.datumType == Token.DATUM_TYPE.UINT32) {\r
1012 typeStr = "UINT32 %s_%s[%d];\r\n";\r
1013 } else if (token.datumType == Token.DATUM_TYPE.UINT64) {\r
1014 typeStr = "UINT64 %s_%s[%d];\r\n";\r
1015 } else if (token.datumType == Token.DATUM_TYPE.BOOLEAN) {\r
1016 typeStr = "BOOLEAN %s_%s[%d];\r\n";\r
1017 } else if (token.datumType == Token.DATUM_TYPE.POINTER) {\r
6ff7a41c 1018 return String.format("UINT8 %s_%s[%d];\r\n", token.getPrimaryKeyString(), "SkuDataTable", token.datumSize * token.skuData.size());\r
32648c62 1019 } \r
1020\r
6ff7a41c 1021 return String.format(typeStr, token.getPrimaryKeyString(), "SkuDataTable", token.skuData.size());\r
32648c62 1022\r
1023 }\r
1024\r
1025 private String getDataTypeInstantiationForSkuEnabled (Token token) {\r
1026 String str = "";\r
1027\r
1028 if (token.datumType == Token.DATUM_TYPE.POINTER) {\r
6ff7a41c 1029 return String.format("UINT8 %s_%s[%d]", token.getPrimaryKeyString(), "SkuDataTable", token.datumSize * token.skuData.size());\r
32648c62 1030 } else {\r
1031 str = "{ ";\r
6ff7a41c 1032 for (int idx = 0; idx < token.skuData.size(); idx++) {\r
32648c62 1033 str += token.skuData.get(idx).toString();\r
6ff7a41c 1034 if (idx != token.skuData.size() - 1) {\r
32648c62 1035 str += ", ";\r
1036 }\r
1037 }\r
1038 str += "}";\r
1039\r
1040 return str;\r
1041 }\r
1042\r
1043 }\r
1044\r
1045 private String getDataTypeInstantiation (Token token) {\r
1046\r
32648c62 1047 if (token.datumType == Token.DATUM_TYPE.POINTER) {\r
6ff7a41c 1048 return String.format("%s /* %s */", token.getDefaultSku().value, token.getPrimaryKeyString());\r
32648c62 1049 } else {\r
6ff7a41c 1050 return String.format("%s /* %s */", token.getDefaultSku().value, token.getPrimaryKeyString());\r
32648c62 1051 }\r
1052 }\r
1053\r
1054\r
1055 private String getDataTypeDeclaration (Token token) {\r
1056\r
1057 String typeStr = "";\r
1058\r
1059 if (token.datumType == Token.DATUM_TYPE.UINT8) {\r
1060 typeStr = "UINT8";\r
1061 } else if (token.datumType == Token.DATUM_TYPE.UINT16) {\r
1062 typeStr = "UINT16";\r
1063 } else if (token.datumType == Token.DATUM_TYPE.UINT32) {\r
1064 typeStr = "UINT32";\r
1065 } else if (token.datumType == Token.DATUM_TYPE.UINT64) {\r
1066 typeStr = "UINT64";\r
1067 } else if (token.datumType == Token.DATUM_TYPE.BOOLEAN) {\r
1068 typeStr = "BOOLEAN";\r
1069 } else if (token.datumType == Token.DATUM_TYPE.POINTER) {\r
1070 return String.format("UINT8 %s[%d]", token.getPrimaryKeyString(), token.datumSize);\r
1071 } else {\r
1072 }\r
1073\r
1074 return String.format("%s %s", typeStr, token.getPrimaryKeyString());\r
1075 }\r
1076\r
1077 private String getVpdEnableTypeDeclaration (Token token) {\r
1078 return String.format("VPD_HEAD %s", token.getPrimaryKeyString());\r
1079 }\r
1080\r
1081 private String getVpdEnableTypeInstantiation (Token token) {\r
6ff7a41c 1082 return String.format("{ %s } /* %s */", token.getDefaultSku().vpdOffset,\r
32648c62 1083 token.getPrimaryKeyString());\r
1084 }\r
1085\r
1086 private String getStringTypeDeclaration (Token token) {\r
1087 return String.format("UINT16 %s", token.getPrimaryKeyString());\r
1088 }\r
1089\r
1090 private String getStringTypeInstantiation (int StringTableIdx, Token token) {\r
1091 return String.format ("%d /* %s */", StringTableIdx,\r
1092 token.getPrimaryKeyString()); \r
1093 }\r
1094\r
1095\r
1096 private String getVariableEnableTypeDeclaration (Token token) {\r
1097 return String.format("VARIABLE_HEAD %s", token.getPrimaryKeyString());\r
1098 }\r
1099\r
6ff7a41c 1100 private String getVariableEnableInstantiation (Token token) \r
1101 throws EntityException {\r
1102 //\r
1103 // Need scott fix\r
1104 // \r
1105 return String.format("{ %d, %d, %s } /* %s */", guidTable.add(token.getDefaultSku().variableGuid, token.getPrimaryKeyString()),\r
1106 stringTable.add(token.getDefaultSku().getStringOfVariableName(), token),\r
1107 token.getDefaultSku().variableOffset, \r
32648c62 1108 token.getPrimaryKeyString());\r
1109 }\r
1110\r
1111 public int getTotalTokenNumber () {\r
1112 return sizeTable.getTableLen();\r
1113 }\r
99d2c3c4 1114\r
1115 public static String getPcdDatabaseCommonDefinitions () \r
1116 throws EntityException {\r
1117\r
1118 String retStr = "";\r
1119 try {\r
32648c62 1120 File file = new File(GlobalData.getWorkspacePath() + File.separator + \r
1121 "Tools" + File.separator + \r
1122 "Conf" + File.separator +\r
1123 "Pcd" + File.separator +\r
1124 "PcdDatabaseCommonDefinitions.sample");\r
99d2c3c4 1125 FileReader reader = new FileReader(file);\r
1126 BufferedReader in = new BufferedReader(reader);\r
1127 String str;\r
1128 while ((str = in.readLine()) != null) {\r
1129 retStr = retStr +"\r\n" + str;\r
1130 }\r
1131 } catch (Exception ex) {\r
1132 throw new EntityException("Fatal error when generating PcdDatabase Common Definitions");\r
1133 }\r
1134\r
1135 return retStr;\r
1136 }\r
1137\r
32648c62 1138 public static String getPcdDxeDatabaseDefinitions () \r
1139 throws EntityException {\r
1140\r
1141 String retStr = "";\r
1142 try {\r
1143 File file = new File(GlobalData.getWorkspacePath() + File.separator + \r
1144 "Tools" + File.separator + \r
1145 "Conf" + File.separator +\r
1146 "Pcd" + File.separator +\r
1147 "PcdDatabaseDxeDefinitions.sample");\r
1148 FileReader reader = new FileReader(file);\r
1149 BufferedReader in = new BufferedReader(reader);\r
1150 String str;\r
1151 while ((str = in.readLine()) != null) {\r
1152 retStr = retStr +"\r\n" + str;\r
1153 }\r
1154 } catch (Exception ex) {\r
1155 throw new EntityException("Fatal error when generating PcdDatabase Dxe Definitions");\r
1156 }\r
1157\r
1158 return retStr;\r
1159 }\r
1160\r
1161 public static String getPcdPeiDatabaseDefinitions () \r
1162 throws EntityException {\r
1163\r
1164 String retStr = "";\r
1165 try {\r
1166 File file = new File(GlobalData.getWorkspacePath() + File.separator + \r
1167 "Tools" + File.separator + \r
1168 "Conf" + File.separator +\r
1169 "Pcd" + File.separator +\r
1170 "PcdDatabasePeiDefinitions.sample");\r
1171 FileReader reader = new FileReader(file);\r
1172 BufferedReader in = new BufferedReader(reader);\r
1173 String str;\r
1174 while ((str = in.readLine()) != null) {\r
1175 retStr = retStr +"\r\n" + str;\r
1176 }\r
1177 } catch (Exception ex) {\r
1178 throw new EntityException("Fatal error when generating PcdDatabase Pei Definitions");\r
1179 }\r
1180\r
1181 return retStr;\r
1182 }\r
99d2c3c4 1183\r
1184}\r
1185\r
8840ad58 1186class ModuleInfo {\r
1187 public ModuleSADocument.ModuleSA module;\r
1188 public UsageInstance.MODULE_TYPE type;\r
1189\r
1190 public ModuleInfo (ModuleSADocument.ModuleSA module, UsageInstance.MODULE_TYPE type) {\r
1191 this.module = module;\r
1192 this.type = type;\r
1193 }\r
1194}\r
1195\r
878ddf1f 1196/** This action class is to collect PCD information from MSA, SPD, FPD xml file.\r
1197 This class will be used for wizard and build tools, So it can *not* inherit\r
1198 from buildAction or UIAction.\r
1199**/\r
1200public class CollectPCDAction {\r
1201 /// memoryDatabase hold all PCD information collected from SPD, MSA, FPD.\r
1202 private MemoryDatabaseManager dbManager;\r
1203\r
1204 /// Workspacepath hold the workspace information.\r
1205 private String workspacePath;\r
1206\r
1207 /// FPD file is the root file. \r
1208 private String fpdFilePath;\r
1209\r
1210 /// Message level for CollectPCDAction.\r
1211 private int originalMessageLevel;\r
1212\r
8840ad58 1213 /// Cache the fpd docment instance for private usage.\r
1214 private FrameworkPlatformDescriptionDocument fpdDocInstance;\r
1215\r
878ddf1f 1216 /**\r
1217 Set WorkspacePath parameter for this action class.\r
1218\r
1219 @param workspacePath parameter for this action\r
1220 **/\r
1221 public void setWorkspacePath(String workspacePath) {\r
1222 this.workspacePath = workspacePath;\r
1223 }\r
1224\r
1225 /**\r
1226 Set action message level for CollectPcdAction tool.\r
1227\r
1228 The message should be restored when this action exit.\r
1229\r
1230 @param actionMessageLevel parameter for this action\r
1231 **/\r
1232 public void setActionMessageLevel(int actionMessageLevel) {\r
1233 originalMessageLevel = ActionMessage.messageLevel;\r
1234 ActionMessage.messageLevel = actionMessageLevel;\r
1235 }\r
1236\r
1237 /**\r
1238 Set FPDFileName parameter for this action class.\r
1239\r
1240 @param fpdFilePath fpd file path\r
1241 **/\r
1242 public void setFPDFilePath(String fpdFilePath) {\r
1243 this.fpdFilePath = fpdFilePath;\r
1244 }\r
1245\r
1246 /**\r
1247 Common function interface for outer.\r
1248 \r
1249 @param workspacePath The path of workspace of current build or analysis.\r
1250 @param fpdFilePath The fpd file path of current build or analysis.\r
1251 @param messageLevel The message level for this Action.\r
1252 \r
1253 @throws Exception The exception of this function. Because it can *not* be predict\r
1254 where the action class will be used. So only Exception can be throw.\r
1255 \r
1256 **/\r
1257 public void perform(String workspacePath, String fpdFilePath, \r
1258 int messageLevel) throws Exception {\r
1259 setWorkspacePath(workspacePath);\r
1260 setFPDFilePath(fpdFilePath);\r
1261 setActionMessageLevel(messageLevel);\r
1262 checkParameter();\r
1263 execute();\r
1264 ActionMessage.messageLevel = originalMessageLevel;\r
1265 }\r
1266\r
1267 /**\r
1268 Core execution function for this action class.\r
1269 \r
1270 This function work flows will be:\r
8840ad58 1271 1) Collect and prepocess PCD information from FPD file, all PCD\r
1272 information will be stored into memory database.\r
1273 2) Generate 3 strings for\r
1274 a) All modules using Dynamic(Ex) PCD entry.(Token Number)\r
1275 b) PEI PCDDatabase (C Structure) for PCD Service PEIM.\r
1276 c) DXE PCD Database (C structure) for PCD Service DXE.\r
99d2c3c4 1277 \r
878ddf1f 1278 \r
1279 @throws EntityException Exception indicate failed to execute this action.\r
1280 \r
1281 **/\r
1282 private void execute() throws EntityException {\r
8840ad58 1283 //\r
1284 // Get memoryDatabaseManager instance from GlobalData.\r
1285 // The memoryDatabaseManager should be initialized for whatever build\r
1286 // tools or wizard tools\r
1287 //\r
1288 if((dbManager = GlobalData.getPCDMemoryDBManager()) == null) {\r
1289 throw new EntityException("The instance of PCD memory database manager is null");\r
1290 }\r
878ddf1f 1291\r
1292 //\r
1293 // Collect all PCD information defined in FPD file.\r
1294 // Evenry token defind in FPD will be created as an token into \r
1295 // memory database.\r
1296 //\r
8840ad58 1297 createTokenInDBFromFPD();\r
99d2c3c4 1298 \r
1299 //\r
1300 // Call Private function genPcdDatabaseSourceCode (void); ComponentTypeBsDriver\r
1301 // 1) Generate for PEI, DXE PCD DATABASE's definition and initialization.\r
32648c62 1302 //\r
1303 genPcdDatabaseSourceCode ();\r
1304 \r
878ddf1f 1305 }\r
1306\r
32648c62 1307 /**\r
1308 This function generates source code for PCD Database.\r
1309 \r
1310 @param void\r
1311 @throws EntityException If the token does *not* exist in memory database.\r
99d2c3c4 1312\r
32648c62 1313 **/\r
8840ad58 1314 private void genPcdDatabaseSourceCode()\r
1315 throws EntityException {\r
32648c62 1316 String PcdCommonHeaderString = PcdDatabase.getPcdDatabaseCommonDefinitions ();\r
99d2c3c4 1317\r
32648c62 1318 ArrayList<Token> alPei = new ArrayList<Token> ();\r
1319 ArrayList<Token> alDxe = new ArrayList<Token> ();\r
99d2c3c4 1320\r
32648c62 1321 dbManager.getTwoPhaseDynamicRecordArray(alPei, alDxe);\r
99d2c3c4 1322 PcdDatabase pcdPeiDatabase = new PcdDatabase (alPei, "PEI", 0);\r
32648c62 1323 pcdPeiDatabase.genCode();\r
1324 dbManager.PcdPeimHString = PcdCommonHeaderString + pcdPeiDatabase.getHString()\r
1325 + PcdDatabase.getPcdPeiDatabaseDefinitions();\r
1326 dbManager.PcdPeimCString = pcdPeiDatabase.getCString();\r
99d2c3c4 1327\r
1328 PcdDatabase pcdDxeDatabase = new PcdDatabase (alDxe, \r
32648c62 1329 "DXE",\r
1330 alPei.size()\r
1331 );\r
1332 pcdDxeDatabase.genCode();\r
1333 dbManager.PcdDxeHString = dbManager.PcdPeimHString + pcdDxeDatabase.getHString()\r
1334 + PcdDatabase.getPcdDxeDatabaseDefinitions();\r
1335 dbManager.PcdDxeCString = pcdDxeDatabase.getCString();\r
1336 }\r
1337\r
1338 /**\r
8840ad58 1339 Get component array from FPD.\r
878ddf1f 1340 \r
8840ad58 1341 This function maybe provided by some Global class.\r
878ddf1f 1342 \r
8840ad58 1343 @return List<ModuleInfo> the component array.\r
878ddf1f 1344 \r
8840ad58 1345 */\r
1346 private List<ModuleInfo> getComponentsFromFPD() \r
878ddf1f 1347 throws EntityException {\r
8840ad58 1348 HashMap<String, XmlObject> map = new HashMap<String, XmlObject>();\r
1349 List<ModuleInfo> allModules = new ArrayList<ModuleInfo>();\r
1350 ModuleInfo current = null;\r
1351 int index = 0;\r
1352 org.tianocore.Components components = null;\r
1353 FrameworkModulesDocument.FrameworkModules fModules = null;\r
1354 java.util.List<ModuleSADocument.ModuleSA> modules = null;\r
1355 \r
878ddf1f 1356\r
8840ad58 1357 if (fpdDocInstance == null) {\r
1358 try {\r
1359 fpdDocInstance = (FrameworkPlatformDescriptionDocument)XmlObject.Factory.parse(new File(fpdFilePath));\r
1360 } catch(IOException ioE) {\r
1361 throw new EntityException("File IO error for xml file:" + fpdFilePath + "\n" + ioE.getMessage());\r
1362 } catch(XmlException xmlE) {\r
1363 throw new EntityException("Can't parse the FPD xml fle:" + fpdFilePath + "\n" + xmlE.getMessage());\r
1364 }\r
878ddf1f 1365\r
878ddf1f 1366 }\r
1367\r
8840ad58 1368 //\r
1369 // Check whether FPD contians <FramworkModules>\r
1370 // \r
1371 fModules = fpdDocInstance.getFrameworkPlatformDescription().getFrameworkModules();\r
1372 if (fModules == null) {\r
1373 return null;\r
1374 }\r
878ddf1f 1375\r
8840ad58 1376 //\r
1377 // BUGBUG: The following is work around code, the final component type should be get from\r
1378 // GlobalData class.\r
1379 // \r
1380 components = fModules.getSEC();\r
1381 if (components != null) {\r
1382 modules = components.getModuleSAList();\r
1383 for (index = 0; index < modules.size(); index ++) {\r
1384 allModules.add(new ModuleInfo(modules.get(index), UsageInstance.MODULE_TYPE.SEC));\r
878ddf1f 1385 }\r
8840ad58 1386 }\r
878ddf1f 1387\r
8840ad58 1388 components = fModules.getPEICORE();\r
1389 if (components != null) {\r
1390 modules = components.getModuleSAList();\r
1391 for (index = 0; index < modules.size(); index ++) {\r
1392 allModules.add(new ModuleInfo(modules.get(index), UsageInstance.MODULE_TYPE.PEI_CORE));\r
878ddf1f 1393 }\r
1394 }\r
878ddf1f 1395\r
8840ad58 1396 components = fModules.getPEIM();\r
1397 if (components != null) {\r
1398 modules = components.getModuleSAList();\r
1399 for (index = 0; index < modules.size(); index ++) {\r
1400 allModules.add(new ModuleInfo(modules.get(index), UsageInstance.MODULE_TYPE.PEIM));\r
1401 }\r
878ddf1f 1402 }\r
878ddf1f 1403\r
8840ad58 1404 components = fModules.getDXECORE();\r
1405 if (components != null) {\r
1406 modules = components.getModuleSAList();\r
1407 for (index = 0; index < modules.size(); index ++) {\r
1408 allModules.add(new ModuleInfo(modules.get(index), UsageInstance.MODULE_TYPE.DXE_CORE));\r
1409 }\r
878ddf1f 1410 }\r
1411\r
8840ad58 1412 components = fModules.getDXEDRIVERS();\r
1413 if (components != null) {\r
1414 modules = components.getModuleSAList();\r
1415 for (index = 0; index < modules.size(); index ++) {\r
1416 allModules.add(new ModuleInfo(modules.get(index), UsageInstance.MODULE_TYPE.DXE_DRIVERS));\r
1417 }\r
878ddf1f 1418 }\r
1419\r
8840ad58 1420 components = fModules.getOTHERCOMPONENTS();\r
1421 if (components != null) {\r
1422 modules = components.getModuleSAList();\r
1423 for (index = 0; index < modules.size(); index ++) {\r
1424 allModules.add(new ModuleInfo(modules.get(index), UsageInstance.MODULE_TYPE.OTHER_COMPONENTS));\r
1425 }\r
1426 }\r
1427 \r
1428 return allModules;\r
878ddf1f 1429 }\r
1430\r
1431 /**\r
1432 Create token instance object into memory database, the token information\r
1433 comes for FPD file. Normally, FPD file will contain all token platform \r
1434 informations.\r
878ddf1f 1435 \r
1436 @return FrameworkPlatformDescriptionDocument The FPD document instance for furture usage.\r
1437 \r
1438 @throws EntityException Failed to parse FPD xml file.\r
1439 \r
1440 **/\r
8840ad58 1441 private void createTokenInDBFromFPD() \r
878ddf1f 1442 throws EntityException {\r
8840ad58 1443 int index = 0;\r
1444 int index2 = 0;\r
1445 int pcdIndex = 0;\r
6ff7a41c 1446 List<PcdBuildDefinition.PcdData> pcdBuildDataArray = new ArrayList<PcdBuildDefinition.PcdData>();\r
1447 PcdBuildDefinition.PcdData pcdBuildData = null;\r
8840ad58 1448 Token token = null;\r
8840ad58 1449 SkuInstance skuInstance = null;\r
1450 int skuIndex = 0;\r
1451 List<ModuleInfo> modules = null;\r
1452 String primaryKey = null;\r
8840ad58 1453 String exceptionString = null;\r
1454 UsageInstance usageInstance = null;\r
1455 String primaryKey1 = null;\r
1456 String primaryKey2 = null;\r
1457 boolean isDuplicate = false;\r
6ff7a41c 1458 Token.PCD_TYPE pcdType = Token.PCD_TYPE.UNKNOWN;\r
1459 Token.DATUM_TYPE datumType = Token.DATUM_TYPE.UNKNOWN;\r
1460 int tokenNumber = 0;\r
1461 String moduleName = null;\r
1462 String datum = null;\r
1463 int maxDatumSize = 0;\r
878ddf1f 1464\r
1465 //\r
6ff7a41c 1466 // ----------------------------------------------\r
1467 // 1), Get all <ModuleSA> from FPD file.\r
1468 // ----------------------------------------------\r
878ddf1f 1469 // \r
8840ad58 1470 modules = getComponentsFromFPD();\r
878ddf1f 1471\r
8840ad58 1472 if (modules == null) {\r
7db4ab70 1473 throw new EntityException("[FPD file error] No modules in FPD file, Please check whether there are elements in <FrameworkModules> in FPD file!");\r
878ddf1f 1474 }\r
1475\r
1476 //\r
6ff7a41c 1477 // -------------------------------------------------------------------\r
1478 // 2), Loop all modules to process <PcdBuildDeclarations> for each module.\r
1479 // -------------------------------------------------------------------\r
8840ad58 1480 // \r
1481 for (index = 0; index < modules.size(); index ++) {\r
1482 isDuplicate = false;\r
1483 for (index2 = 0; index2 < index; index2 ++) {\r
1484 //\r
1485 // BUGBUG: For transition schema, we can *not* get module's version from \r
1486 // <ModuleSAs>, It is work around code.\r
1487 // \r
1488 primaryKey1 = UsageInstance.getPrimaryKey(modules.get(index).module.getModuleName(), \r
833b1541 1489 null,\r
1490 null, \r
1491 null, \r
8840ad58 1492 modules.get(index).module.getArch().toString(),\r
1493 null);\r
1494 primaryKey2 = UsageInstance.getPrimaryKey(modules.get(index2).module.getModuleName(), \r
833b1541 1495 null, \r
1496 null, \r
1497 null, \r
8840ad58 1498 modules.get(index2).module.getArch().toString(), \r
1499 null);\r
1500 if (primaryKey1.equalsIgnoreCase(primaryKey2)) {\r
1501 isDuplicate = true;\r
1502 break;\r
1503 }\r
1504 }\r
878ddf1f 1505\r
8840ad58 1506 if (isDuplicate) {\r
1507 continue;\r
1508 }\r
878ddf1f 1509\r
6ff7a41c 1510 //\r
1511 // It is legal for a module does not contains ANY pcd build definitions.\r
1512 // \r
1513 if (modules.get(index).module.getPcdBuildDefinition() == null) {\r
8840ad58 1514 continue;\r
6ff7a41c 1515 }\r
1516 \r
1517 pcdBuildDataArray = modules.get(index).module.getPcdBuildDefinition().getPcdDataList();\r
1518\r
1519 moduleName = modules.get(index).module.getModuleName();\r
878ddf1f 1520\r
878ddf1f 1521 //\r
6ff7a41c 1522 // ----------------------------------------------------------------------\r
1523 // 2.1), Loop all Pcd entry for a module and add it into memory database.\r
1524 // ----------------------------------------------------------------------\r
8840ad58 1525 // \r
1526 for (pcdIndex = 0; pcdIndex < pcdBuildDataArray.size(); pcdIndex ++) {\r
1527 pcdBuildData = pcdBuildDataArray.get(pcdIndex);\r
1528 primaryKey = Token.getPrimaryKeyString(pcdBuildData.getCName(),\r
1529 translateSchemaStringToUUID(pcdBuildData.getTokenSpaceGuid()));\r
6ff7a41c 1530 pcdType = Token.getpcdTypeFromString(pcdBuildData.getItemType().toString());\r
1531 datumType = Token.getdatumTypeFromString(pcdBuildData.getDatumType().toString());\r
1532 tokenNumber = Integer.decode(pcdBuildData.getToken().toString());\r
1533 datum = pcdBuildData.getValue();\r
1534 maxDatumSize = pcdBuildData.getMaxDatumSize();\r
8840ad58 1535\r
bab72a57 1536 if ((pcdType == Token.PCD_TYPE.FEATURE_FLAG) &&\r
1537 (datumType != Token.DATUM_TYPE.BOOLEAN)){\r
1538 exceptionString = String.format("[FPD file error] For PCD %s in module %s, the PCD type is FEATRUE_FLAG but "+\r
1539 "datum type of this PCD entry is not BOOLEAN!",\r
1540 pcdBuildData.getCName(),\r
1541 moduleName);\r
1542 throw new EntityException(exceptionString);\r
1543 }\r
1544\r
833b1541 1545 //\r
1546 // Check <TokenSpaceGuid> is exist? In future, because all schema verification will tools\r
1547 // will check that, following checking code could be removed.\r
1548 // \r
1549 if (pcdBuildData.getTokenSpaceGuid() == null) {\r
1550 exceptionString = String.format("[FPD file error] There is no <TokenSpaceGuid> for PCD %s in module %s! This is required!",\r
1551 pcdBuildData.getCName(),\r
1552 moduleName);\r
1553 throw new EntityException(exceptionString);\r
1554 }\r
1555\r
6ff7a41c 1556 //\r
1557 // -------------------------------------------------------------------------------------------\r
1558 // 2.1.1), Do some necessary checking work for FixedAtBuild, FeatureFlag and PatchableInModule\r
1559 // -------------------------------------------------------------------------------------------\r
1560 // \r
1561 if (!Token.isDynamic(pcdType)) {\r
1562 //\r
1563 // Value is required.\r
1564 // \r
1565 if (datum == null) {\r
7db4ab70 1566 exceptionString = String.format("[FPD file error] There is no value for PCD entry %s in module %s!",\r
6ff7a41c 1567 pcdBuildData.getCName(),\r
1568 moduleName);\r
1569 throw new EntityException(exceptionString);\r
1570 }\r
1571\r
1572 //\r
1573 // Check whether the datum size is matched datum type.\r
1574 // \r
6f7e61a0 1575 if ((exceptionString = verifyDatum(pcdBuildData.getCName(), \r
1576 moduleName,\r
1577 datum,\r
1578 datumType,\r
1579 maxDatumSize)) != null) {\r
6ff7a41c 1580 throw new EntityException(exceptionString);\r
1581 }\r
1582 }\r
8840ad58 1583\r
6ff7a41c 1584 //\r
1585 // ---------------------------------------------------------------------------------\r
1586 // 2.1.2), Create token or update token information for current anaylized PCD data.\r
1587 // ---------------------------------------------------------------------------------\r
1588 // \r
8840ad58 1589 if (dbManager.isTokenInDatabase(primaryKey)) {\r
1590 //\r
1591 // If the token is already exist in database, do some necessary checking\r
1592 // and add a usage instance into this token in database\r
1593 // \r
1594 token = dbManager.getTokenByKey(primaryKey);\r
6ff7a41c 1595 \r
1596 //\r
1597 // checking for DatumType, DatumType should be unique for one PCD used in different\r
1598 // modules.\r
1599 // \r
1600 if (token.datumType != datumType) {\r
7db4ab70 1601 exceptionString = String.format("[FPD file error] The datum type of PCD entry %s is %s, which is different with %s defined in before!",\r
6ff7a41c 1602 pcdBuildData.getCName(), \r
1603 pcdBuildData.getDatumType().toString(), \r
1604 Token.getStringOfdatumType(token.datumType));\r
1605 throw new EntityException(exceptionString);\r
1606 }\r
8840ad58 1607\r
878ddf1f 1608 //\r
6ff7a41c 1609 // Check token number is valid\r
8840ad58 1610 // \r
6ff7a41c 1611 if (tokenNumber != token.tokenNumber) {\r
7db4ab70 1612 exceptionString = String.format("[FPD file error] The token number of PCD entry %s in module %s is different with same PCD entry in other modules!",\r
6ff7a41c 1613 pcdBuildData.getCName(),\r
1614 moduleName);\r
8840ad58 1615 throw new EntityException(exceptionString);\r
1616 }\r
1617\r
878ddf1f 1618 //\r
6ff7a41c 1619 // For same PCD used in different modules, the PCD type should all be dynamic or non-dynamic.\r
8840ad58 1620 // \r
6ff7a41c 1621 if (token.isDynamicPCD != Token.isDynamic(pcdType)) {\r
7db4ab70 1622 exceptionString = String.format("[FPD file error] For PCD entry %s in module %s, you define dynamic or non-dynamic PCD type which"+\r
6ff7a41c 1623 "is different with others module's",\r
1624 token.cName,\r
1625 moduleName);\r
8840ad58 1626 throw new EntityException(exceptionString);\r
1627 }\r
6ff7a41c 1628\r
1629 if (token.isDynamicPCD) {\r
1630 //\r
1631 // Check datum is equal the datum in dynamic information.\r
1632 // For dynamic PCD, you can do not write <Value> in sperated every <PcdBuildDefinition> in different <ModuleSA>,\r
1633 // But if you write, the <Value> must be same as the value in <DynamicPcdBuildDefinitions>.\r
1634 // \r
1635 if (!token.isSkuEnable() && \r
7db4ab70 1636 (token.getDefaultSku().type == DynamicTokenValue.VALUE_TYPE.DEFAULT_TYPE) &&\r
1637 (datum != null)) {\r
1638 if (!datum.equalsIgnoreCase(token.getDefaultSku().value)) {\r
1639 exceptionString = String.format("[FPD file error] For dynamic PCD %s in module %s, the datum in <ModuleSA> is "+\r
6ff7a41c 1640 "not equal to the datum in <DynamicPcdBuildDefinitions>, it is "+\r
7db4ab70 1641 "illega! You could no set <Value> in <ModuleSA> for a dynamic PCD!",\r
6ff7a41c 1642 token.cName,\r
1643 moduleName);\r
7db4ab70 1644 throw new EntityException(exceptionString);\r
6ff7a41c 1645 }\r
1646 }\r
7db4ab70 1647\r
1648 if ((maxDatumSize != 0) &&\r
1649 (maxDatumSize != token.datumSize)){\r
1650 exceptionString = String.format("[FPD file error] For dynamic PCD %s in module %s, the max datum size is %d which "+\r
1651 "is different with <MaxDatumSize> %d defined in <DynamicPcdBuildDefinitions>!",\r
1652 token.cName,\r
1653 moduleName,\r
1654 maxDatumSize,\r
1655 token.datumSize);\r
1656 throw new EntityException(exceptionString);\r
1657 }\r
6ff7a41c 1658 }\r
1659 \r
8840ad58 1660 } else {\r
1661 //\r
1662 // If the token is not in database, create a new token instance and add\r
1663 // a usage instance into this token in database.\r
1664 // \r
1665 token = new Token(pcdBuildData.getCName(), \r
1666 translateSchemaStringToUUID(pcdBuildData.getTokenSpaceGuid()));\r
6ff7a41c 1667 \r
1668 token.datumType = datumType;\r
1669 token.tokenNumber = tokenNumber;\r
1670 token.isDynamicPCD = Token.isDynamic(pcdType);\r
1671 token.datumSize = maxDatumSize;\r
1672 \r
1673 if (token.isDynamicPCD) {\r
1674 //\r
1675 // For Dynamic and Dynamic Ex type, need find the dynamic information\r
1676 // in <DynamicPcdBuildDefinition> section in FPD file.\r
1677 // \r
1678 updateDynamicInformation(moduleName, \r
1679 token,\r
1680 datum,\r
1681 maxDatumSize);\r
8840ad58 1682 }\r
6ff7a41c 1683 \r
8840ad58 1684 dbManager.addTokenToDatabase(primaryKey, token);\r
878ddf1f 1685 }\r
878ddf1f 1686\r
878ddf1f 1687 //\r
6ff7a41c 1688 // -----------------------------------------------------------------------------------\r
1689 // 2.1.3), Add the PcdType in current module into this Pcd token's supported PCD type.\r
1690 // -----------------------------------------------------------------------------------\r
1691 // \r
1692 token.updateSupportPcdType(pcdType);\r
1693\r
1694 //\r
1695 // ------------------------------------------------\r
1696 // 2.1.4), Create an usage instance for this token.\r
1697 // ------------------------------------------------\r
8840ad58 1698 // \r
1699 usageInstance = new UsageInstance(token, \r
6ff7a41c 1700 moduleName, \r
833b1541 1701 null,\r
1702 null,\r
1703 null,\r
8840ad58 1704 modules.get(index).type, \r
6ff7a41c 1705 pcdType,\r
8840ad58 1706 modules.get(index).module.getArch().toString(), \r
1707 null,\r
6ff7a41c 1708 datum,\r
1709 maxDatumSize);\r
8840ad58 1710 token.addUsageInstance(usageInstance);\r
878ddf1f 1711 }\r
878ddf1f 1712 }\r
878ddf1f 1713 }\r
1714\r
6f7e61a0 1715 /**\r
1716 Verify the datum value according its datum size and datum type, this\r
1717 function maybe moved to FPD verification tools in future.\r
1718 \r
1719 @param cName\r
1720 @param moduleName\r
1721 @param datum\r
1722 @param datumType\r
1723 @param maxDatumSize\r
1724 \r
1725 @return String\r
1726 */\r
1727 /***/\r
1728 public String verifyDatum(String cName,\r
1729 String moduleName,\r
1730 String datum, \r
1731 Token.DATUM_TYPE datumType, \r
1732 int maxDatumSize) {\r
1733 String exceptionString = null;\r
1734 int value;\r
1735 BigInteger value64;\r
1736 String subStr;\r
f63ef4b2 1737 int index;\r
6f7e61a0 1738\r
1739 if (moduleName == null) {\r
1740 moduleName = "section <DynamicPcdBuildDefinitions>";\r
1741 } else {\r
1742 moduleName = "module " + moduleName;\r
1743 }\r
1744\r
1745 if (maxDatumSize == 0) {\r
1746 exceptionString = String.format("[FPD file error] You maybe miss <MaxDatumSize> for PCD %s in %s",\r
1747 cName,\r
1748 moduleName);\r
1749 return exceptionString;\r
1750 }\r
1751\r
1752 switch (datumType) {\r
1753 case UINT8:\r
1754 if (maxDatumSize != 1) {\r
1755 exceptionString = String.format("[FPD file error] The datum type of PCD data %s in %s "+\r
1756 "is UINT8, but datum size is %d, they are not matched!",\r
1757 cName,\r
1758 moduleName,\r
1759 maxDatumSize);\r
1760 return exceptionString;\r
1761 }\r
1762\r
1763 if (datum != null) {\r
1764 try {\r
1765 value = Integer.decode(datum);\r
1766 } catch (NumberFormatException nfeExp) {\r
1767 exceptionString = String.format("[FPD file error] The datum for PCD %s in %s is not valid "+\r
1768 "digital format of UINT8",\r
1769 cName,\r
1770 moduleName);\r
1771 return exceptionString;\r
1772 }\r
1773 if (value > 0xFF) {\r
1774 exceptionString = String.format("[FPD file error] The datum for PCD %s in %s is %s exceed"+\r
1775 " the max size of UINT8 - 0xFF",\r
1776 cName, \r
1777 moduleName,\r
1778 datum);\r
1779 return exceptionString;\r
1780 }\r
1781 }\r
1782 break;\r
1783 case UINT16:\r
1784 if (maxDatumSize != 2) {\r
1785 exceptionString = String.format("[FPD file error] The datum type of PCD data %s in %s "+\r
1786 "is UINT16, but datum size is %d, they are not matched!",\r
1787 cName,\r
1788 moduleName,\r
1789 maxDatumSize);\r
1790 return exceptionString;\r
1791 }\r
1792 if (datum != null) {\r
1793 try {\r
1794 value = Integer.decode(datum);\r
1795 } catch (NumberFormatException nfeExp) {\r
1796 exceptionString = String.format("[FPD file error] The datum for PCD %s in %s is "+\r
1797 "not valid digital of UINT16",\r
1798 cName,\r
1799 moduleName);\r
1800 return exceptionString;\r
1801 }\r
1802 if (value > 0xFFFF) {\r
1803 exceptionString = String.format("[FPD file error] The datum for PCD %s in %s is %s "+\r
1804 "which exceed the range of UINT16 - 0xFFFF",\r
1805 cName, \r
1806 moduleName,\r
1807 datum);\r
1808 return exceptionString;\r
1809 }\r
1810 }\r
1811 break;\r
1812 case UINT32:\r
1813 if (maxDatumSize != 4) {\r
1814 exceptionString = String.format("[FPD file error] The datum type of PCD data %s in %s "+\r
1815 "is UINT32, but datum size is %d, they are not matched!",\r
1816 cName,\r
1817 moduleName,\r
1818 maxDatumSize);\r
1819 return exceptionString;\r
1820 }\r
1821\r
1822 if (datum != null) {\r
1823 try {\r
1824 if (datum.length() > 2) {\r
1825 if ((datum.charAt(0) == '0') && \r
1826 ((datum.charAt(1) == 'x') || (datum.charAt(1) == 'X'))){\r
1827 subStr = datum.substring(2, datum.length());\r
1828 value64 = new BigInteger(subStr, 16);\r
1829 } else {\r
1830 value64 = new BigInteger(datum);\r
1831 }\r
1832 } else {\r
1833 value64 = new BigInteger(datum);\r
1834 }\r
1835 } catch (NumberFormatException nfeExp) {\r
1836 exceptionString = String.format("[FPD file error] The datum for PCD %s in %s is not "+\r
1837 "valid digital of UINT32",\r
1838 cName,\r
1839 moduleName);\r
1840 return exceptionString;\r
1841 }\r
1842\r
1843 if (value64.bitLength() > 32) {\r
1844 exceptionString = String.format("[FPD file error] The datum for PCD %s in %s is %s which "+\r
1845 "exceed the range of UINT32 - 0xFFFFFFFF",\r
1846 cName, \r
1847 moduleName,\r
1848 datum);\r
1849 return exceptionString;\r
1850 }\r
1851 }\r
1852 break;\r
1853 case UINT64:\r
1854 if (maxDatumSize != 8) {\r
1855 exceptionString = String.format("[FPD file error] The datum type of PCD data %s in %s "+\r
1856 "is UINT64, but datum size is %d, they are not matched!",\r
1857 cName,\r
1858 moduleName,\r
1859 maxDatumSize);\r
1860 return exceptionString;\r
1861 }\r
1862\r
1863 if (datum != null) {\r
1864 try {\r
1865 if (datum.length() > 2) {\r
1866 if ((datum.charAt(0) == '0') && \r
1867 ((datum.charAt(1) == 'x') || (datum.charAt(1) == 'X'))){\r
1868 subStr = datum.substring(2, datum.length());\r
1869 value64 = new BigInteger(subStr, 16);\r
1870 } else {\r
1871 value64 = new BigInteger(datum);\r
1872 }\r
1873 } else {\r
1874 value64 = new BigInteger(datum);\r
1875 }\r
1876 } catch (NumberFormatException nfeExp) {\r
1877 exceptionString = String.format("[FPD file error] The datum for PCD %s in %s is not valid"+\r
1878 " digital of UINT64",\r
1879 cName,\r
1880 moduleName);\r
1881 return exceptionString;\r
1882 }\r
1883\r
1884 if (value64.bitLength() > 64) {\r
1885 exceptionString = String.format("[FPD file error] The datum for PCD %s in %s is %s "+\r
1886 "exceed the range of UINT64 - 0xFFFFFFFFFFFFFFFF",\r
1887 cName, \r
1888 moduleName,\r
1889 datum);\r
1890 return exceptionString;\r
1891 }\r
1892 }\r
1893 break;\r
1894 case BOOLEAN:\r
1895 if (maxDatumSize != 1) {\r
1896 exceptionString = String.format("[FPD file error] The datum type of PCD data %s in %s "+\r
1897 "is BOOLEAN, but datum size is %d, they are not matched!",\r
1898 cName,\r
1899 moduleName,\r
1900 maxDatumSize);\r
1901 return exceptionString;\r
1902 }\r
1903\r
1904 if (datum != null) {\r
1905 if (!(datum.equalsIgnoreCase("TRUE") ||\r
1906 datum.equalsIgnoreCase("FALSE"))) {\r
1907 exceptionString = String.format("[FPD file error] The datum type of PCD data %s in %s "+\r
1908 "is BOOELAN, but value is not 'true'/'TRUE' or 'FALSE'/'false'",\r
1909 cName,\r
1910 moduleName);\r
1911 return exceptionString;\r
1912 }\r
1913\r
1914 }\r
1915 break;\r
1916 case POINTER:\r
1917 if (datum == null) {\r
1918 break;\r
1919 }\r
1920\r
1921 char ch = datum.charAt(0);\r
1922 int start, end;\r
1923 String strValue;\r
1924 //\r
1925 // For void* type PCD, only three datum is support:\r
1926 // 1) Unicode: string with start char is "L"\r
1927 // 2) Ansci: String start char is ""\r
1928 // 3) byte array: String start char "{"\r
1929 // \r
1930 if (ch == 'L') {\r
1931 start = datum.indexOf('\"');\r
1932 end = datum.lastIndexOf('\"');\r
1933 if ((start > end) || \r
1934 (end > datum.length())||\r
1935 ((start == end) && (datum.length() > 0))) {\r
f63ef4b2 1936 exceptionString = String.format("[FPD file error] The datum type of PCD %s in %s is VOID* and datum is "+\r
6f7e61a0 1937 "a UNICODE string because start with L\", but format maybe"+\r
1938 "is not right, correct UNICODE string is L\"...\"!",\r
1939 cName,\r
1940 moduleName);\r
1941 return exceptionString;\r
1942 }\r
1943\r
1944 strValue = datum.substring(start + 1, end);\r
1945 if ((strValue.length() * 2) > maxDatumSize) {\r
f63ef4b2 1946 exceptionString = String.format("[FPD file error] The datum type of PCD %s in %s is VOID*, and datum is "+\r
6f7e61a0 1947 "a UNICODE string, but the datum size is %d exceed to <MaxDatumSize> : %d",\r
1948 cName,\r
1949 moduleName,\r
1950 strValue.length() * 2, \r
1951 maxDatumSize);\r
1952 return exceptionString;\r
1953 }\r
1954 } else if (ch == '\"'){\r
1955 start = datum.indexOf('\"');\r
1956 end = datum.lastIndexOf('\"');\r
1957 if ((start > end) || \r
1958 (end > datum.length())||\r
1959 ((start == end) && (datum.length() > 0))) {\r
f63ef4b2 1960 exceptionString = String.format("[FPD file error] The datum type of PCD %s in %s is VOID* and datum is "+\r
6f7e61a0 1961 "a ANSCII string because start with \", but format maybe"+\r
1962 "is not right, correct ANSIC string is \"...\"!",\r
1963 cName,\r
1964 moduleName);\r
1965 return exceptionString;\r
1966 }\r
1967 strValue = datum.substring(start + 1, end);\r
1968 if ((strValue.length()) > maxDatumSize) {\r
f63ef4b2 1969 exceptionString = String.format("[FPD file error] The datum type of PCD %s in %s is VOID*, and datum is "+\r
6f7e61a0 1970 "a ANSCI string, but the datum size is %d which exceed to <MaxDatumSize> : %d",\r
1971 cName,\r
1972 moduleName,\r
1973 strValue.length(),\r
1974 maxDatumSize);\r
1975 return exceptionString;\r
1976 }\r
1977 } else if (ch =='{') {\r
1978 String[] strValueArray;\r
1979\r
1980 start = datum.indexOf('{');\r
1981 end = datum.lastIndexOf('}');\r
f63ef4b2 1982 strValue = datum.substring(start + 1, end);\r
1983 strValue = strValue.trim();\r
1984 if (strValue.length() == 0) {\r
1985 break;\r
1986 }\r
6f7e61a0 1987 strValueArray = strValue.split(",");\r
f63ef4b2 1988 for (index = 0; index < strValueArray.length; index ++) {\r
1989 try{\r
2435723a 1990 value = Integer.decode(strValueArray[index].trim());\r
f63ef4b2 1991 } catch (NumberFormatException nfeEx) {\r
1992 exceptionString = String.format("[FPD file error] The datum type of PCD %s in %s is VOID*, and "+\r
1993 "it is byte array in fact. For every byte in array should be a valid"+\r
1994 "byte digital, but element %s is not a valid byte digital!",\r
1995 cName,\r
1996 moduleName,\r
1997 strValueArray[index]);\r
1998 return exceptionString;\r
1999 }\r
2000 if (value > 0xFF) {\r
2001 exceptionString = String.format("[FPD file error] The datum type of PCD %s in %s is VOID*, "+\r
2002 "it is byte array in fact. But the element of %s exceed the byte range",\r
2003 cName,\r
2004 moduleName,\r
2005 strValueArray[index]);\r
2006 return exceptionString;\r
2007 }\r
2008 }\r
2009\r
6f7e61a0 2010 if (strValueArray.length > maxDatumSize) {\r
f63ef4b2 2011 exceptionString = String.format("[FPD file error] The datum type of PCD %s in %s is VOID*, and datum is byte"+\r
6f7e61a0 2012 "array, but the number of bytes is %d which exceed to <MaxDatumSzie> : %d!",\r
2013 cName,\r
2014 moduleName,\r
2015 strValueArray.length,\r
2016 maxDatumSize);\r
2017 return exceptionString;\r
2018 }\r
2019 } else {\r
f63ef4b2 2020 exceptionString = String.format("[FPD file error] The datum type of PCD %s in %s is VOID*. For VOID* type, you have three format choise:\n "+\r
6f7e61a0 2021 "1) UNICODE string: like L\"xxxx\";\r\n"+\r
2022 "2) ANSIC string: like \"xxx\";\r\n"+\r
2023 "3) Byte array: like {0x2, 0x45, 0x23}\r\n"+\r
2024 "But the datum in seems does not following above format!",\r
2025 cName, \r
2026 moduleName);\r
2027 return exceptionString;\r
2028 }\r
2029 break;\r
2030 default:\r
2031 exceptionString = String.format("[FPD file error] For PCD entry %s in %s, datum type is unknown, it should be one of "+\r
2032 "UINT8, UINT16, UINT32, UINT64, VOID*, BOOLEAN",\r
2033 cName,\r
2034 moduleName);\r
2035 return exceptionString;\r
2036 }\r
2037 return null;\r
2038 }\r
2039\r
878ddf1f 2040 /**\r
6ff7a41c 2041 Get dynamic information for a dynamic PCD from <DynamicPcdBuildDefinition> seciton in FPD file.\r
8840ad58 2042 \r
6ff7a41c 2043 This function should be implemented in GlobalData in future.\r
8840ad58 2044 \r
6ff7a41c 2045 @param token The token instance which has hold module's PCD information\r
2046 @param moduleName The name of module who will use this Dynamic PCD.\r
8840ad58 2047 \r
6ff7a41c 2048 @return DynamicPcdBuildDefinitions.PcdBuildData\r
2049 */\r
2050 /***/\r
2051 private DynamicPcdBuildDefinitions.PcdBuildData getDynamicInfoFromFPD(Token token,\r
2052 String moduleName)\r
878ddf1f 2053 throws EntityException {\r
6ff7a41c 2054 int index = 0;\r
2055 String exceptionString = null;\r
2056 String dynamicPrimaryKey = null;\r
2057 DynamicPcdBuildDefinitions dynamicPcdBuildDefinitions = null;\r
2058 List<DynamicPcdBuildDefinitions.PcdBuildData> dynamicPcdBuildDataArray = null;\r
878ddf1f 2059\r
3d52de13 2060 //\r
8840ad58 2061 // If FPD document is not be opened, open and initialize it.\r
2062 // \r
2063 if (fpdDocInstance == null) {\r
2064 try {\r
2065 fpdDocInstance = (FrameworkPlatformDescriptionDocument)XmlObject.Factory.parse(new File(fpdFilePath));\r
2066 } catch(IOException ioE) {\r
2067 throw new EntityException("File IO error for xml file:" + fpdFilePath + "\n" + ioE.getMessage());\r
2068 } catch(XmlException xmlE) {\r
2069 throw new EntityException("Can't parse the FPD xml fle:" + fpdFilePath + "\n" + xmlE.getMessage());\r
2070 }\r
3d52de13 2071 }\r
878ddf1f 2072\r
6ff7a41c 2073 dynamicPcdBuildDefinitions = fpdDocInstance.getFrameworkPlatformDescription().getDynamicPcdBuildDefinitions();\r
2074 if (dynamicPcdBuildDefinitions == null) {\r
7db4ab70 2075 exceptionString = String.format("[FPD file error] There are no <PcdDynamicBuildDescriptions> in FPD file but contains Dynamic type "+\r
6ff7a41c 2076 "PCD entry %s in module %s!",\r
2077 token.cName,\r
2078 moduleName);\r
2079 throw new EntityException(exceptionString);\r
3d52de13 2080 }\r
8840ad58 2081\r
6ff7a41c 2082 dynamicPcdBuildDataArray = dynamicPcdBuildDefinitions.getPcdBuildDataList();\r
2083 for (index = 0; index < dynamicPcdBuildDataArray.size(); index ++) {\r
833b1541 2084 //\r
2085 // Check <TokenSpaceGuid> is exist? In future, because all schema verification will tools\r
2086 // will check that, following checking code could be removed.\r
2087 // \r
2088 if (dynamicPcdBuildDataArray.get(index).getTokenSpaceGuid() == null) {\r
2089 exceptionString = String.format("[FPD file error] There is no <TokenSpaceGuid> for PCD %s in <DynamicPcdBuildDefinitions>! This is required!",\r
2090 dynamicPcdBuildDataArray.get(index).getCName());\r
2091 throw new EntityException(exceptionString);\r
2092 }\r
2093\r
6ff7a41c 2094 dynamicPrimaryKey = Token.getPrimaryKeyString(dynamicPcdBuildDataArray.get(index).getCName(),\r
2095 translateSchemaStringToUUID(dynamicPcdBuildDataArray.get(index).getTokenSpaceGuid()));\r
2096 if (dynamicPrimaryKey.equalsIgnoreCase(token.getPrimaryKeyString())) {\r
2097 return dynamicPcdBuildDataArray.get(index);\r
2098 }\r
8840ad58 2099 }\r
2100\r
6ff7a41c 2101 return null;\r
2102 }\r
2103\r
6ff7a41c 2104 /**\r
2105 Update dynamic information for PCD entry.\r
2106 \r
2107 Dynamic information is retrieved from <PcdDynamicBuildDeclarations> in\r
2108 FPD file.\r
2109 \r
2110 @param moduleName The name of the module who use this PCD\r
2111 @param token The token instance\r
2112 @param datum The <datum> in module's PCD information\r
2113 @param maxDatumSize The <maxDatumSize> in module's PCD information\r
2114 \r
2115 @return Token\r
2116 */\r
2117 private Token updateDynamicInformation(String moduleName, \r
2118 Token token,\r
2119 String datum,\r
2120 int maxDatumSize) \r
2121 throws EntityException {\r
2122 int index = 0;\r
2123 int offset;\r
2124 String exceptionString = null;\r
2125 DynamicTokenValue dynamicValue;\r
2126 SkuInstance skuInstance = null;\r
2127 String temp;\r
2128 boolean hasSkuId0 = false;\r
38ee8d9e 2129 Token.PCD_TYPE pcdType = Token.PCD_TYPE.UNKNOWN;\r
2130 int tokenNumber = 0;\r
6ff7a41c 2131\r
2132 List<DynamicPcdBuildDefinitions.PcdBuildData.SkuInfo> skuInfoList = null;\r
2133 DynamicPcdBuildDefinitions.PcdBuildData dynamicInfo = null;\r
2134\r
2135 dynamicInfo = getDynamicInfoFromFPD(token, moduleName);\r
2136 if (dynamicInfo == null) {\r
7db4ab70 2137 exceptionString = String.format("[FPD file error] For Dynamic PCD %s used by module %s, "+\r
6ff7a41c 2138 "there is no dynamic information in <DynamicPcdBuildDefinitions> "+\r
2139 "in FPD file, but it is required!",\r
2140 token.cName,\r
2141 moduleName);\r
2142 throw new EntityException(exceptionString);\r
2143 }\r
878ddf1f 2144\r
7db4ab70 2145 token.datumSize = dynamicInfo.getMaxDatumSize();\r
2146\r
6f7e61a0 2147 exceptionString = verifyDatum(token.cName, \r
2148 moduleName,\r
2149 null, \r
2150 token.datumType, \r
2151 token.datumSize);\r
7db4ab70 2152 if (exceptionString != null) {\r
2153 throw new EntityException(exceptionString);\r
2154 }\r
2155\r
2156 if ((maxDatumSize != 0) && \r
2157 (maxDatumSize != token.datumSize)) {\r
2158 exceptionString = String.format("FPD file error] For dynamic PCD %s, the datum size in module %s is %d, but "+\r
2159 "the datum size in <DynamicPcdBuildDefinitions> is %d, they are not match!",\r
2160 token.cName,\r
2161 moduleName, \r
2162 maxDatumSize,\r
2163 dynamicInfo.getMaxDatumSize());\r
2164 throw new EntityException(exceptionString);\r
2165 }\r
38ee8d9e 2166 tokenNumber = Integer.decode(dynamicInfo.getToken().toString());\r
2167 if (tokenNumber != token.tokenNumber) {\r
2168 exceptionString = String.format("[FPD file error] For dynamic PCD %s, the token number in module %s is 0x%x, but"+\r
2169 "in <DynamicPcdBuildDefinictions>, the token number is 0x%x, they are not match!",\r
2170 token.cName,\r
2171 moduleName,\r
2172 token.tokenNumber,\r
2173 tokenNumber);\r
2174 throw new EntityException(exceptionString);\r
2175 }\r
2176\r
2177 pcdType = Token.getpcdTypeFromString(dynamicInfo.getItemType().toString());\r
2178 if (pcdType == Token.PCD_TYPE.DYNAMIC_EX) {\r
2179 token.dynamicExTokenNumber = tokenNumber;\r
2180 }\r
7db4ab70 2181\r
6ff7a41c 2182 skuInfoList = dynamicInfo.getSkuInfoList();\r
878ddf1f 2183\r
6ff7a41c 2184 //\r
2185 // Loop all sku data \r
2186 // \r
2187 for (index = 0; index < skuInfoList.size(); index ++) {\r
2188 skuInstance = new SkuInstance();\r
2189 //\r
2190 // Although SkuId in schema is BigInteger, but in fact, sku id is 32 bit value.\r
2191 // \r
2192 temp = skuInfoList.get(index).getSkuId().toString();\r
2193 skuInstance.id = Integer.decode(temp);\r
6ff7a41c 2194 if (skuInstance.id == 0) {\r
2195 hasSkuId0 = true;\r
2196 }\r
2197 //\r
2198 // Judge whether is DefaultGroup at first, because most case is DefautlGroup.\r
2199 // \r
2200 if (skuInfoList.get(index).getValue() != null) {\r
2201 skuInstance.value.setValue(skuInfoList.get(index).getValue());\r
6f7e61a0 2202 if ((exceptionString = verifyDatum(token.cName, \r
2203 null, \r
2204 skuInfoList.get(index).getValue(), \r
2205 token.datumType, \r
2206 token.datumSize)) != null) {\r
2207 throw new EntityException(exceptionString);\r
2208 }\r
2209\r
6ff7a41c 2210 token.skuData.add(skuInstance);\r
8840ad58 2211\r
878ddf1f 2212 //\r
6ff7a41c 2213 // Judege wether is same of datum between module's information\r
2214 // and dynamic information.\r
8840ad58 2215 // \r
6ff7a41c 2216 if (datum != null) {\r
2217 if ((skuInstance.id == 0) &&\r
2218 !datum.equalsIgnoreCase(skuInfoList.get(index).getValue())) {\r
6f7e61a0 2219 exceptionString = "[FPD file error] For dynamic PCD " + token.cName + ", the value in module " + moduleName + " is " + datum.toString() + " but the "+\r
7db4ab70 2220 "value of sku 0 data in <DynamicPcdBuildDefinition> is " + skuInstance.value.value + ". They are must be same!"+\r
2221 " or you could not define value for a dynamic PCD in every <ModuleSA>!"; \r
8840ad58 2222 throw new EntityException(exceptionString);\r
2223 }\r
6ff7a41c 2224 }\r
2225 continue;\r
2226 }\r
8840ad58 2227\r
6ff7a41c 2228 //\r
2229 // Judge whether is HII group case.\r
2230 // \r
2231 if (skuInfoList.get(index).getVariableName() != null) {\r
2232 exceptionString = null;\r
2233 if (skuInfoList.get(index).getVariableGuid() == null) {\r
7db4ab70 2234 exceptionString = String.format("[FPD file error] For dynamic PCD %s in <DynamicPcdBuildDefinitions> section in FPD "+\r
6ff7a41c 2235 "file, who use HII, but there is no <VariableGuid> defined for Sku %d data!",\r
2236 token.cName,\r
2237 index);\r
2238 \r
2239 }\r
2240\r
2241 if (skuInfoList.get(index).getVariableOffset() == null) {\r
7db4ab70 2242 exceptionString = String.format("[FPD file error] For dynamic PCD %s in <DynamicPcdBuildDefinitions> section in FPD "+\r
6ff7a41c 2243 "file, who use HII, but there is no <VariableOffset> defined for Sku %d data!",\r
2244 token.cName,\r
2245 index);\r
2246 }\r
2247\r
2248 if (skuInfoList.get(index).getHiiDefaultValue() == null) {\r
7db4ab70 2249 exceptionString = String.format("[FPD file error] For dynamic PCD %s in <DynamicPcdBuildDefinitions> section in FPD "+\r
6ff7a41c 2250 "file, who use HII, but there is no <HiiDefaultValue> defined for Sku %d data!",\r
2251 token.cName,\r
2252 index);\r
878ddf1f 2253 }\r
6ff7a41c 2254\r
2255 if (exceptionString != null) {\r
2256 throw new EntityException(exceptionString);\r
2257 }\r
6f7e61a0 2258\r
2259 if ((exceptionString = verifyDatum(token.cName, \r
2260 null, \r
2261 skuInfoList.get(index).getHiiDefaultValue(), \r
2262 token.datumType, \r
2263 token.datumSize)) != null) {\r
2264 throw new EntityException(exceptionString);\r
2265 }\r
2266\r
6ff7a41c 2267 offset = Integer.decode(skuInfoList.get(index).getVariableOffset());\r
2268 if (offset > 0xFFFF) {\r
7db4ab70 2269 throw new EntityException(String.format("[FPD file error] For dynamic PCD %s , the variable offset defined in sku %d data "+\r
6ff7a41c 2270 "exceed 64K, it is not allowed!",\r
2271 token.cName,\r
2272 index));\r
2273 }\r
2274\r
2275 skuInstance.value.setHiiData(skuInfoList.get(index).getVariableName(),\r
2276 translateSchemaStringToUUID(skuInfoList.get(index).getVariableGuid().toString()),\r
2277 skuInfoList.get(index).getVariableOffset(),\r
2278 skuInfoList.get(index).getHiiDefaultValue());\r
2279 token.skuData.add(skuInstance);\r
2280 continue;\r
878ddf1f 2281 }\r
6ff7a41c 2282\r
2283 if (skuInfoList.get(index).getVpdOffset() != null) {\r
2284 skuInstance.value.setVpdData(skuInfoList.get(index).getVpdOffset());\r
2285 token.skuData.add(skuInstance);\r
2286 continue;\r
2287 }\r
2288\r
7db4ab70 2289 exceptionString = String.format("[FPD file error] For dynamic PCD %s, the dynamic info must "+\r
6ff7a41c 2290 "be one of 'DefaultGroup', 'HIIGroup', 'VpdGroup'.",\r
2291 token.cName);\r
8840ad58 2292 throw new EntityException(exceptionString);\r
2293 }\r
2294\r
6ff7a41c 2295 if (!hasSkuId0) {\r
7db4ab70 2296 exceptionString = String.format("[FPD file error] For dynamic PCD %s in <DynamicPcdBuildDefinitions>, there are "+\r
6ff7a41c 2297 "no sku id = 0 data, which is required for every dynamic PCD",\r
2298 token.cName);\r
7db4ab70 2299 throw new EntityException(exceptionString);\r
6ff7a41c 2300 }\r
2301\r
8840ad58 2302 return token;\r
2303 }\r
2304\r
2305 /**\r
2306 Translate the schema string to UUID instance.\r
2307 \r
2308 In schema, the string of UUID is defined as following two types string:\r
2309 1) GuidArrayType: pattern = 0x[a-fA-F0-9]{1,8},( )*0x[a-fA-F0-9]{1,4},(\r
2310 )*0x[a-fA-F0-9]{1,4}(,( )*\{)?(,?( )*0x[a-fA-F0-9]{1,2}){8}( )*(\})?\r
2311 \r
2312 2) GuidNamingConvention: pattern =\r
2313 [a-fA-F0-9]{8}-[a-fA-F0-9]{4}-[a-fA-F0-9]{4}-[a-fA-F0-9]{4}-[a-fA-F0-9]{12}\r
2314 \r
2315 This function will convert string and create uuid instance.\r
2316 \r
2317 @param uuidString UUID string in XML file\r
2318 \r
2319 @return UUID UUID instance\r
2320 **/\r
2321 private UUID translateSchemaStringToUUID(String uuidString) \r
2322 throws EntityException {\r
2323 String temp;\r
2324 String[] splitStringArray;\r
2325 int index;\r
2326 int chIndex;\r
2327 int chLen;\r
2328\r
2329 if (uuidString == null) {\r
2330 return null;\r
2331 }\r
2332\r
2333 if (uuidString.length() == 0) {\r
2334 return null;\r
2335 }\r
2336\r
6ff7a41c 2337 if (uuidString.equals("0") ||\r
2338 uuidString.equalsIgnoreCase("0x0")) {\r
2339 return new UUID(0, 0);\r
2340 }\r
2341\r
8840ad58 2342 //\r
2343 // If the UUID schema string is GuidArrayType type then need translate \r
2344 // to GuidNamingConvention type at first.\r
2345 // \r
2346 if ((uuidString.charAt(0) == '0') && ((uuidString.charAt(1) == 'x') || (uuidString.charAt(1) == 'X'))) {\r
2347 splitStringArray = uuidString.split("," );\r
2348 if (splitStringArray.length != 11) {\r
7db4ab70 2349 throw new EntityException ("[FPD file error] Wrong format for UUID string: " + uuidString);\r
8840ad58 2350 }\r
2351\r
2352 //\r
2353 // Remove blank space from these string and remove header string "0x"\r
2354 // \r
2355 for (index = 0; index < 11; index ++) {\r
2356 splitStringArray[index] = splitStringArray[index].trim();\r
2357 splitStringArray[index] = splitStringArray[index].substring(2, splitStringArray[index].length());\r
2358 }\r
2359\r
2360 //\r
2361 // Add heading '0' to normalize the string length\r
2362 // \r
2363 for (index = 3; index < 11; index ++) {\r
2364 chLen = splitStringArray[index].length();\r
2365 for (chIndex = 0; chIndex < 2 - chLen; chIndex ++) {\r
2366 splitStringArray[index] = "0" + splitStringArray[index];\r
2367 }\r
2368 }\r
2369\r
2370 //\r
2371 // construct the final GuidNamingConvention string\r
2372 // \r
2373 temp = String.format("%s-%s-%s-%s%s-%s%s%s%s%s%s",\r
2374 splitStringArray[0],\r
2375 splitStringArray[1],\r
2376 splitStringArray[2],\r
2377 splitStringArray[3],\r
2378 splitStringArray[4],\r
2379 splitStringArray[5],\r
2380 splitStringArray[6],\r
2381 splitStringArray[7],\r
2382 splitStringArray[8],\r
2383 splitStringArray[9],\r
2384 splitStringArray[10]);\r
2385 uuidString = temp;\r
2386 }\r
2387\r
2388 return UUID.fromString(uuidString);\r
878ddf1f 2389 }\r
2390\r
2391 /**\r
2392 check parameter for this action.\r
2393 \r
2394 @throws EntityException Bad parameter.\r
2395 **/\r
2396 private void checkParameter() throws EntityException {\r
2397 File file = null;\r
2398\r
2399 if((fpdFilePath == null) ||(workspacePath == null)) {\r
2400 throw new EntityException("WorkspacePath and FPDFileName should be blank for CollectPCDAtion!");\r
2401 }\r
2402\r
2403 if(fpdFilePath.length() == 0 || workspacePath.length() == 0) {\r
2404 throw new EntityException("WorkspacePath and FPDFileName should be blank for CollectPCDAtion!");\r
2405 }\r
2406\r
2407 file = new File(workspacePath);\r
2408 if(!file.exists()) {\r
2409 throw new EntityException("WorkpacePath " + workspacePath + " does not exist!");\r
2410 }\r
2411\r
2412 file = new File(fpdFilePath);\r
2413\r
2414 if(!file.exists()) {\r
2415 throw new EntityException("FPD File " + fpdFilePath + " does not exist!");\r
2416 }\r
2417 }\r
2418\r
2419 /**\r
2420 Test case function\r
2421\r
2422 @param argv parameter from command line\r
2423 **/\r
2424 public static void main(String argv[]) throws EntityException {\r
2425 CollectPCDAction ca = new CollectPCDAction();\r
6f7e61a0 2426 ca.setWorkspacePath("m:/tianocore_latest/edk2");\r
2427 ca.setFPDFilePath("m:/tianocore_latest/edk2/EdkNt32Pkg/Nt32.fpd");\r
878ddf1f 2428 ca.setActionMessageLevel(ActionMessage.MAX_MESSAGE_LEVEL);\r
2429 GlobalData.initInfo("Tools" + File.separator + "Conf" + File.separator + "FrameworkDatabase.db",\r
6f7e61a0 2430 "m:/tianocore_latest/edk2");\r
878ddf1f 2431 ca.execute();\r
2432 }\r
2433}\r