2 CollectPCDAction class.
4 This action class is to collect PCD information from MSA, SPD, FPD xml file.
5 This class will be used for wizard and build tools, So it can *not* inherit
6 from buildAction or wizardAction.
8 Copyright (c) 2006, Intel Corporation
9 All rights reserved. This program and the accompanying materials
10 are licensed and made available under the terms and conditions of the BSD License
11 which accompanies this distribution. The full text of the license may be found at
12 http://opensource.org/licenses/bsd-license.php
14 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
15 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
18 package org
.tianocore
.build
.pcd
.action
;
20 import java
.io
.BufferedReader
;
22 import java
.io
.FileReader
;
23 import java
.io
.IOException
;
24 import java
.math
.BigInteger
;
25 import java
.util
.ArrayList
;
26 import java
.util
.Comparator
;
27 import java
.util
.HashMap
;
28 import java
.util
.Iterator
;
29 import java
.util
.List
;
32 import java
.util
.UUID
;
33 import java
.util
.regex
.Matcher
;
34 import java
.util
.regex
.Pattern
;
36 import org
.apache
.xmlbeans
.XmlException
;
37 import org
.apache
.xmlbeans
.XmlObject
;
38 import org
.tianocore
.DynamicPcdBuildDefinitionsDocument
.DynamicPcdBuildDefinitions
;
39 import org
.tianocore
.FrameworkModulesDocument
;
40 import org
.tianocore
.ModuleSADocument
;
41 import org
.tianocore
.PcdBuildDefinitionDocument
;
42 import org
.tianocore
.PcdBuildDefinitionDocument
.PcdBuildDefinition
;
43 import org
.tianocore
.PlatformSurfaceAreaDocument
;
44 import org
.tianocore
.build
.fpd
.FpdParserTask
;
45 import org
.tianocore
.build
.global
.GlobalData
;
46 import org
.tianocore
.build
.id
.FpdModuleIdentification
;
47 import org
.tianocore
.build
.id
.ModuleIdentification
;
48 import org
.tianocore
.pcd
.action
.ActionMessage
;
49 import org
.tianocore
.pcd
.entity
.CommonDefinition
;
50 import org
.tianocore
.pcd
.entity
.DynamicTokenValue
;
51 import org
.tianocore
.pcd
.entity
.MemoryDatabaseManager
;
52 import org
.tianocore
.pcd
.entity
.SkuInstance
;
53 import org
.tianocore
.pcd
.entity
.Token
;
54 import org
.tianocore
.pcd
.entity
.UsageIdentification
;
55 import org
.tianocore
.pcd
.entity
.UsageInstance
;
56 import org
.tianocore
.pcd
.exception
.EntityException
;
59 CStructTypeDeclaration
61 This class is used to store the declaration string, such as
62 "UINT32 PcdPlatformFlashBaseAddress", of
63 each memember in the C structure, which is a standard C language
64 feature used to implement a simple and efficient database for
65 dynamic(ex) type PCD entry.
68 class CStructTypeDeclaration
{
74 public CStructTypeDeclaration (String key
, int alignmentSize
, String cCode
, boolean initTable
) {
76 this.alignmentSize
= alignmentSize
;
78 this.initTable
= initTable
;
85 This class is used to store the String in a PCD database.
89 private ArrayList
<String
> al
;
90 private ArrayList
<String
> alComments
;
94 public StringTable (String phase
) {
96 al
= new ArrayList
<String
>();
97 alComments
= new ArrayList
<String
>();
101 public String
getSizeMacro () {
102 return String
.format(PcdDatabase
.StringTableSizeMacro
, phase
, getSize());
105 private int getSize () {
107 // We have at least one Unicode Character in the table.
109 return len
== 0 ?
1 : len
;
112 public String
getExistanceMacro () {
113 return String
.format(PcdDatabase
.StringTableExistenceMacro
, phase
, (al
.size() == 0)?
"TRUE":"FALSE");
116 public void genCode (ArrayList
<CStructTypeDeclaration
> declaList
, HashMap
<String
, String
> instTable
) {
117 final String stringTable
= "StringTable";
118 final String tab
= "\t";
119 final String newLine
= "\r\n";
120 final String commaNewLine
= ",\r\n";
122 CStructTypeDeclaration decl
;
124 String cDeclCode
= "";
125 String cInstCode
= "";
128 // If we have a empty StringTable
130 if (al
.size() == 0) {
131 cDeclCode
+= String
.format("%-20s%s[1]; /* StringTable is empty */", "UINT16", stringTable
) + newLine
;
132 decl
= new CStructTypeDeclaration (
140 cInstCode
= String
.format("/* %s */", stringTable
) + newLine
+ tab
+ "{ 0 }";
141 instTable
.put(stringTable
, cInstCode
);
145 // If there is any String in the StringTable
147 for (int i
= 0; i
< al
.size(); i
++) {
148 String str
= al
.get(i
);
149 String stringTableName
;
153 // StringTable is a well-known name in the PCD DXE driver
155 stringTableName
= stringTable
;
158 stringTableName
= String
.format("%s_%d", stringTable
, i
);
161 cDeclCode
+= String
.format("%-20s%s[%d]; /* %s */", "UINT16",
162 stringTableName
, str
.length() + 1,
167 cInstCode
= "/* StringTable */" + newLine
;
170 cInstCode
+= tab
+ String
.format("L\"%s\" /* %s */", al
.get(i
), alComments
.get(i
));
171 if (i
!= al
.size() - 1) {
172 cInstCode
+= commaNewLine
;
176 decl
= new CStructTypeDeclaration (
184 instTable
.put(stringTable
, cInstCode
);
188 public int add (String inputStr
, Token token
) {
192 String str
= inputStr
;
195 // The input can be two types:
196 // "L\"Bootmode\"" or "Bootmode".
197 // We drop the L\" and \" for the first type.
198 if (str
.startsWith("L\"") && str
.endsWith("\"")) {
199 str
= str
.substring(2, str
.length() - 1);
202 // Check if StringTable has this String already.
203 // If so, return the current pos.
205 for (i
= 0, pos
= 0; i
< al
.size(); i
++) {
206 String s
= al
.get(i
);;
211 pos
= s
.length() + 1;
216 // Include the NULL character at the end of String
218 len
+= str
.length() + 1;
220 alComments
.add(token
.getPrimaryKeyString());
229 This class is used to store the Size information for
230 POINTER TYPE PCD entry in a PCD database.
234 private ArrayList
<ArrayList
<Integer
>> al
;
235 private ArrayList
<String
> alComments
;
237 private String phase
;
239 public SizeTable (String phase
) {
240 al
= new ArrayList
<ArrayList
<Integer
>>();
241 alComments
= new ArrayList
<String
>();
246 public String
getSizeMacro () {
247 return String
.format(PcdDatabase
.SizeTableSizeMacro
, phase
, getSize());
250 private int getSize() {
251 return len
== 0 ?
1 : len
;
254 public void genCode (ArrayList
<CStructTypeDeclaration
> declaList
, HashMap
<String
, String
> instTable
, String phase
) {
255 final String name
= "SizeTable";
257 CStructTypeDeclaration decl
;
260 cCode
= String
.format(PcdDatabase
.SizeTableDeclaration
, phase
);
261 decl
= new CStructTypeDeclaration (
270 cCode
= PcdDatabase
.genInstantiationStr(getInstantiation());
271 instTable
.put(name
, cCode
);
274 private ArrayList
<String
> getInstantiation () {
275 final String comma
= ",";
276 ArrayList
<String
> Output
= new ArrayList
<String
>();
278 Output
.add("/* SizeTable */");
280 if (al
.size() == 0) {
283 for (int index
= 0; index
< al
.size(); index
++) {
284 ArrayList
<Integer
> ial
= al
.get(index
);
288 for (int index2
= 0; index2
< ial
.size(); index2
++) {
289 str
+= " " + ial
.get(index2
).toString();
290 if (index2
!= ial
.size() - 1) {
295 str
+= " /* " + alComments
.get(index
) + " */";
297 if (index
!= (al
.size() - 1)) {
310 public void add (Token token
) {
313 // We only have size information for POINTER type PCD entry.
315 if (token
.datumType
!= Token
.DATUM_TYPE
.POINTER
) {
319 ArrayList
<Integer
> ial
= token
.getPointerTypeSize();
324 alComments
.add(token
.getPrimaryKeyString());
334 This class is used to store the GUIDs in a PCD database.
337 private ArrayList
<UUID
> al
;
338 private ArrayList
<String
> alComments
;
339 private String phase
;
341 private int bodyLineNum
;
343 public GuidTable (String phase
) {
345 al
= new ArrayList
<UUID
>();
346 alComments
= new ArrayList
<String
>();
351 public String
getSizeMacro () {
352 return String
.format(PcdDatabase
.GuidTableSizeMacro
, phase
, getSize());
355 private int getSize () {
356 return (al
.size() == 0)?
1 : al
.size();
359 public String
getExistanceMacro () {
360 return String
.format(PcdDatabase
.GuidTableExistenceMacro
, phase
, (al
.size() == 0)?
"TRUE":"FALSE");
363 public void genCode (ArrayList
<CStructTypeDeclaration
> declaList
, HashMap
<String
, String
> instTable
, String phase
) {
364 final String name
= "GuidTable";
366 CStructTypeDeclaration decl
;
369 cCode
+= String
.format(PcdDatabase
.GuidTableDeclaration
, phase
);
370 decl
= new CStructTypeDeclaration (
379 cCode
= PcdDatabase
.genInstantiationStr(getInstantiation());
380 instTable
.put(name
, cCode
);
383 private String
getUuidCString (UUID uuid
) {
384 String
[] guidStrArray
;
386 guidStrArray
=(uuid
.toString()).split("-");
388 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}}",
392 (guidStrArray
[3].substring(0, 2)),
393 (guidStrArray
[3].substring(2, 4)),
394 (guidStrArray
[4].substring(0, 2)),
395 (guidStrArray
[4].substring(2, 4)),
396 (guidStrArray
[4].substring(4, 6)),
397 (guidStrArray
[4].substring(6, 8)),
398 (guidStrArray
[4].substring(8, 10)),
399 (guidStrArray
[4].substring(10, 12))
403 private ArrayList
<String
> getInstantiation () {
404 ArrayList
<String
> Output
= new ArrayList
<String
>();
406 Output
.add("/* GuidTable */");
409 if (al
.size() == 0) {
410 Output
.add("\t" + getUuidCString(new UUID(0, 0)));
413 for (int i
= 0; i
< al
.size(); i
++) {
414 String str
= "\t" + getUuidCString(al
.get(i
));
416 str
+= "/* " + alComments
.get(i
) + " */";
417 if (i
!= (al
.size() - 1)) {
429 public int add (UUID uuid
, String name
) {
431 // Check if GuidTable has this entry already.
432 // If so, return the GuidTable index.
434 for (int i
= 0; i
< al
.size(); i
++) {
435 if (al
.get(i
).compareTo(uuid
) == 0) {
442 alComments
.add(name
);
445 // Return the previous Table Index
455 This class is used to store the SKU IDs in a PCD database.
459 private ArrayList
<Integer
[]> al
;
460 private ArrayList
<String
> alComment
;
461 private String phase
;
464 public SkuIdTable (String phase
) {
466 al
= new ArrayList
<Integer
[]>();
467 alComment
= new ArrayList
<String
>();
471 public String
getSizeMacro () {
472 return String
.format(PcdDatabase
.SkuIdTableSizeMacro
, phase
, getSize());
475 private int getSize () {
476 return (len
== 0)?
1 : len
;
479 public String
getExistanceMacro () {
480 return String
.format(PcdDatabase
.SkuTableExistenceMacro
, phase
, (al
.size() == 0)?
"TRUE":"FALSE");
483 public void genCode (ArrayList
<CStructTypeDeclaration
> declaList
, HashMap
<String
, String
> instTable
, String phase
) {
484 final String name
= "SkuIdTable";
486 CStructTypeDeclaration decl
;
489 cCode
+= String
.format(PcdDatabase
.SkuIdTableDeclaration
, phase
);
490 decl
= new CStructTypeDeclaration (
499 cCode
= PcdDatabase
.genInstantiationStr(getInstantiation());
500 instTable
.put(name
, cCode
);
503 // SystemSkuId is in PEI phase PCD Database
505 if (phase
.equalsIgnoreCase("PEI")) {
506 decl
= new CStructTypeDeclaration (
509 String
.format("%-20sSystemSkuId;\r\n", "SKU_ID"),
514 instTable
.put("SystemSkuId", "0");
519 private ArrayList
<String
> getInstantiation () {
520 ArrayList
<String
> Output
= new ArrayList
<String
> ();
522 Output
.add("/* SkuIdTable */");
525 if (al
.size() == 0) {
529 for (int index
= 0; index
< al
.size(); index
++) {
532 str
= "/* " + alComment
.get(index
) + "*/ ";
533 str
+= "/* MaxSku */ ";
536 Integer
[] ia
= al
.get(index
);
538 str
+= "\t" + ia
[0].toString() + ", ";
539 for (int index2
= 1; index2
< ia
.length
; index2
++) {
540 str
+= ia
[index2
].toString();
541 if (!((index2
== ia
.length
- 1) && (index
== al
.size() - 1))) {
555 public int add (Token token
) {
561 // Check if this SKU_ID Array is already in the table
565 Integer
[] s
= (Integer
[]) o
;
566 boolean different
= false;
567 if (s
[0] == token
.getSkuIdCount()) {
568 for (index
= 1; index
< s
.length
; index
++) {
569 if (s
[index
] != token
.skuData
.get(index
-1).id
) {
584 Integer
[] skuIds
= new Integer
[token
.skuData
.size() + 1];
585 skuIds
[0] = new Integer(token
.skuData
.size());
586 for (index
= 1; index
< skuIds
.length
; index
++) {
587 skuIds
[index
] = new Integer(token
.skuData
.get(index
- 1).id
);
592 len
+= skuIds
.length
;
594 alComment
.add(token
.getPrimaryKeyString());
601 class LocalTokenNumberTable
{
602 private ArrayList
<String
> al
;
603 private ArrayList
<String
> alComment
;
604 private String phase
;
607 public LocalTokenNumberTable (String phase
) {
609 al
= new ArrayList
<String
>();
610 alComment
= new ArrayList
<String
>();
615 public String
getSizeMacro () {
616 return String
.format(PcdDatabase
.LocalTokenNumberTableSizeMacro
, phase
, getSize())
617 + String
.format(PcdDatabase
.LocalTokenNumberSizeMacro
, phase
, al
.size());
620 public int getSize () {
621 return (al
.size() == 0)?
1 : al
.size();
624 public String
getExistanceMacro () {
625 return String
.format(PcdDatabase
.DatabaseExistenceMacro
, phase
, (al
.size() == 0)?
"TRUE":"FALSE");
628 public void genCode (ArrayList
<CStructTypeDeclaration
> declaList
, HashMap
<String
, String
> instTable
, String phase
) {
629 final String name
= "LocalTokenNumberTable";
631 CStructTypeDeclaration decl
;
634 cCode
+= String
.format(PcdDatabase
.LocalTokenNumberTableDeclaration
, phase
);
635 decl
= new CStructTypeDeclaration (
643 cCode
= PcdDatabase
.genInstantiationStr(getInstantiation());
644 instTable
.put(name
, cCode
);
647 private ArrayList
<String
> getInstantiation () {
648 ArrayList
<String
> output
= new ArrayList
<String
>();
650 output
.add("/* LocalTokenNumberTable */");
653 if (al
.size() == 0) {
657 for (int index
= 0; index
< al
.size(); index
++) {
660 str
= "\t" + (String
)al
.get(index
);
662 str
+= " /* " + alComment
.get(index
) + " */ ";
665 if (index
!= (al
.size() - 1)) {
678 public int add (Token token
) {
684 str
= String
.format(PcdDatabase
.offsetOfStrTemplate
, phase
, token
.hasDefaultValue() ?
"Init" : "Uninit", token
.getPrimaryKeyString());
686 if (token
.isUnicodeStringType()) {
687 str
+= " | PCD_TYPE_STRING";
690 if (token
.isSkuEnable()) {
691 str
+= " | PCD_TYPE_SKU_ENABLED";
694 if (token
.getDefaultSku().type
== DynamicTokenValue
.VALUE_TYPE
.HII_TYPE
) {
695 str
+= " | PCD_TYPE_HII";
698 if (token
.getDefaultSku().type
== DynamicTokenValue
.VALUE_TYPE
.VPD_TYPE
) {
699 str
+= " | PCD_TYPE_VPD";
702 switch (token
.datumType
) {
705 str
+= " | PCD_DATUM_TYPE_UINT8";
708 str
+= " | PCD_DATUM_TYPE_UINT16";
711 str
+= " | PCD_DATUM_TYPE_UINT32";
714 str
+= " | PCD_DATUM_TYPE_UINT64";
717 str
+= " | PCD_DATUM_TYPE_POINTER";
722 alComment
.add(token
.getPrimaryKeyString());
731 This class is used to store the table of mapping information
732 between DynamicEX ID pair(Guid, TokenNumber) and
733 the local token number assigned by PcdDatabase class.
740 This class is used to store the mapping information
741 between DynamicEX ID pair(Guid, TokenNumber) and
742 the local token number assigned by PcdDatabase class.
745 public Integer guidTableIdx
;
746 public Long exTokenNumber
;
747 public Long localTokenIdx
;
749 public ExTriplet (int guidTableIdx
, long exTokenNumber
, long localTokenIdx
) {
750 this.guidTableIdx
= new Integer(guidTableIdx
);
751 this.exTokenNumber
= new Long(exTokenNumber
);
752 this.localTokenIdx
= new Long(localTokenIdx
);
756 private ArrayList
<ExTriplet
> al
;
757 private Map
<ExTriplet
, String
> alComment
;
758 private String phase
;
760 private int bodyLineNum
;
762 public ExMapTable (String phase
) {
764 al
= new ArrayList
<ExTriplet
>();
765 alComment
= new HashMap
<ExTriplet
, String
>();
770 public String
getSizeMacro () {
771 return String
.format(PcdDatabase
.ExMapTableSizeMacro
, phase
, getTableLen())
772 + String
.format(PcdDatabase
.ExTokenNumber
, phase
, al
.size());
775 public String
getExistanceMacro () {
776 return String
.format(PcdDatabase
.ExMapTableExistenceMacro
, phase
, (al
.size() == 0)?
"TRUE":"FALSE");
779 public void genCode (ArrayList
<CStructTypeDeclaration
> declaList
, HashMap
<String
, String
> instTable
, String phase
) {
780 final String exMapTableName
= "ExMapTable";
784 CStructTypeDeclaration decl
;
787 cCode
+= String
.format(PcdDatabase
.ExMapTableDeclaration
, phase
);
788 decl
= new CStructTypeDeclaration (
797 cCode
= PcdDatabase
.genInstantiationStr(getInstantiation());
798 instTable
.put(exMapTableName
, cCode
);
801 private ArrayList
<String
> getInstantiation () {
802 ArrayList
<String
> Output
= new ArrayList
<String
>();
804 Output
.add("/* ExMapTable */");
806 if (al
.size() == 0) {
807 Output
.add("\t{0, 0, 0}");
811 for (index
= 0; index
< al
.size(); index
++) {
814 ExTriplet e
= (ExTriplet
)al
.get(index
);
816 str
= "\t" + "{ " + String
.format("0x%08X", e
.exTokenNumber
) + ", ";
817 str
+= e
.localTokenIdx
.toString() + ", ";
818 str
+= e
.guidTableIdx
.toString();
820 str
+= "}" + " /* " + alComment
.get(e
) + " */" ;
822 if (index
!= al
.size() - 1) {
836 public int add (int localTokenIdx
, long exTokenNum
, int guidTableIdx
, String name
) {
840 ExTriplet et
= new ExTriplet(guidTableIdx
, exTokenNum
, localTokenIdx
);
843 alComment
.put(et
, name
);
848 private int getTableLen () {
849 return al
.size() == 0 ?
1 : al
.size();
853 // To simplify the algorithm for GetNextToken and GetNextTokenSpace in
854 // PCD PEIM/Driver, we need to sort the ExMapTable according to the
859 class ExTripletComp
implements Comparator
<ExTriplet
> {
860 public int compare (ExTriplet a
, ExTriplet b
) {
861 if (a
.guidTableIdx
== b
.guidTableIdx
) {
863 // exTokenNumber is long, we can't use simple substraction.
865 if (a
.exTokenNumber
> b
.exTokenNumber
) {
867 } else if (a
.exTokenNumber
== b
.exTokenNumber
) {
874 return a
.guidTableIdx
- b
.guidTableIdx
;
878 private void sortTable () {
879 java
.util
.Comparator
<ExTriplet
> comparator
= new ExTripletComp();
880 java
.util
.Collections
.sort(al
, comparator
);
887 This class is used to generate C code for Autogen.h and Autogen.c of
888 a PCD service DXE driver and PCD service PEIM.
892 private final static int SkuHeadAlignmentSize
= 4;
893 private final String newLine
= "\r\n";
894 private final String commaNewLine
= ",\r\n";
895 private final String tab
= "\t";
896 public final static String ExMapTableDeclaration
= "DYNAMICEX_MAPPING ExMapTable[%s_EXMAPPING_TABLE_SIZE];\r\n";
897 public final static String GuidTableDeclaration
= "EFI_GUID GuidTable[%s_GUID_TABLE_SIZE];\r\n";
898 public final static String LocalTokenNumberTableDeclaration
= "UINT32 LocalTokenNumberTable[%s_LOCAL_TOKEN_NUMBER_TABLE_SIZE];\r\n";
899 public final static String StringTableDeclaration
= "UINT16 StringTable[%s_STRING_TABLE_SIZE];\r\n";
900 public final static String SizeTableDeclaration
= "SIZE_INFO SizeTable[%s_SIZE_TABLE_SIZE];\r\n";
901 public final static String SkuIdTableDeclaration
= "UINT8 SkuIdTable[%s_SKUID_TABLE_SIZE];\r\n";
904 public final static String ExMapTableSizeMacro
= "#define %s_EXMAPPING_TABLE_SIZE %d\r\n";
905 public final static String ExTokenNumber
= "#define %s_EX_TOKEN_NUMBER %d\r\n";
906 public final static String GuidTableSizeMacro
= "#define %s_GUID_TABLE_SIZE %d\r\n";
907 public final static String LocalTokenNumberTableSizeMacro
= "#define %s_LOCAL_TOKEN_NUMBER_TABLE_SIZE %d\r\n";
908 public final static String LocalTokenNumberSizeMacro
= "#define %s_LOCAL_TOKEN_NUMBER %d\r\n";
909 public final static String SizeTableSizeMacro
= "#define %s_SIZE_TABLE_SIZE %d\r\n";
910 public final static String StringTableSizeMacro
= "#define %s_STRING_TABLE_SIZE %d\r\n";
911 public final static String SkuIdTableSizeMacro
= "#define %s_SKUID_TABLE_SIZE %d\r\n";
914 public final static String ExMapTableExistenceMacro
= "#define %s_EXMAP_TABLE_EMPTY %s\r\n";
915 public final static String GuidTableExistenceMacro
= "#define %s_GUID_TABLE_EMPTY %s\r\n";
916 public final static String DatabaseExistenceMacro
= "#define %s_DATABASE_EMPTY %s\r\n";
917 public final static String StringTableExistenceMacro
= "#define %s_STRING_TABLE_EMPTY %s\r\n";
918 public final static String SkuTableExistenceMacro
= "#define %s_SKUID_TABLE_EMPTY %s\r\n";
920 public final static String offsetOfSkuHeadStrTemplate
= "offsetof(%s_PCD_DATABASE, %s.%s_SkuDataTable)";
921 public final static String offsetOfVariableEnabledDefault
= "offsetof(%s_PCD_DATABASE, %s.%s_VariableDefault_%d)";
922 public final static String offsetOfStrTemplate
= "offsetof(%s_PCD_DATABASE, %s.%s)";
924 private final static String skuDataTableTemplate
= "SkuDataTable";
927 private StringTable stringTable
;
928 private GuidTable guidTable
;
929 private LocalTokenNumberTable localTokenNumberTable
;
930 private SkuIdTable skuIdTable
;
931 private SizeTable sizeTable
;
932 private ExMapTable exMapTable
;
934 private ArrayList
<Token
> alTokens
;
935 private String phase
;
936 private int assignedTokenNumber
;
939 // Use two class global variable to store
942 private String privateGlobalName
;
943 private String privateGlobalCCode
;
945 // After Major changes done to the PCD
946 // database generation class PcdDatabase
947 // Please increment the version and please
948 // also update the version number in PCD
949 // service PEIM and DXE driver accordingly.
951 private final int version
= 2;
953 private String hString
;
954 private String cString
;
957 Constructor for PcdDatabase class.
959 <p>We have two PCD dynamic(ex) database for the Framework implementation. One
960 for PEI phase and the other for DXE phase. </p>
962 @param alTokens A ArrayList of Dynamic(EX) PCD entry.
963 @param exePhase The phase to generate PCD database for: valid input
965 @param startLen The starting Local Token Number for the PCD database. For
966 PEI phase, the starting Local Token Number starts from 0.
967 For DXE phase, the starting Local Token Number starts
968 from the total number of PCD entry of PEI phase.
971 public PcdDatabase (ArrayList
<Token
> alTokens
, String exePhase
, int startLen
) {
974 stringTable
= new StringTable(phase
);
975 guidTable
= new GuidTable(phase
);
976 localTokenNumberTable
= new LocalTokenNumberTable(phase
);
977 skuIdTable
= new SkuIdTable(phase
);
978 sizeTable
= new SizeTable(phase
);
979 exMapTable
= new ExMapTable(phase
);
982 // Local token number 0 is reserved for INVALID_TOKEN_NUMBER.
983 // So we will increment 1 for the startLen passed from the
986 assignedTokenNumber
= startLen
+ 1;
987 this.alTokens
= alTokens
;
990 private void getNonExAndExTokens (ArrayList
<Token
> alTokens
, List
<Token
> nexTokens
, List
<Token
> exTokens
) {
991 for (int i
= 0; i
< alTokens
.size(); i
++) {
992 Token t
= (Token
)alTokens
.get(i
);
993 if (t
.isDynamicEx()) {
1003 private int getDataTypeAlignmentSize (Token token
) {
1004 switch (token
.datumType
) {
1022 private int getHiiPtrTypeAlignmentSize(Token token
) {
1023 switch (token
.datumType
) {
1033 if (token
.isHiiEnable()) {
1034 if (token
.isHiiDefaultValueUnicodeStringType()) {
1046 private int getAlignmentSize (Token token
) {
1047 if (token
.getDefaultSku().type
== DynamicTokenValue
.VALUE_TYPE
.HII_TYPE
) {
1051 if (token
.getDefaultSku().type
== DynamicTokenValue
.VALUE_TYPE
.VPD_TYPE
) {
1055 if (token
.isUnicodeStringType()) {
1059 return getDataTypeAlignmentSize(token
);
1062 public String
getCString () {
1066 public String
getHString () {
1070 private void genCodeWorker(Token t
,
1071 ArrayList
<CStructTypeDeclaration
> declaList
,
1072 HashMap
<String
, String
> instTable
, String phase
)
1073 throws EntityException
{
1075 CStructTypeDeclaration decl
;
1078 // Insert SKU_HEAD if isSkuEnable is true
1080 if (t
.isSkuEnable()) {
1082 tableIdx
= skuIdTable
.add(t
);
1083 decl
= new CStructTypeDeclaration(t
.getPrimaryKeyString(),
1084 SkuHeadAlignmentSize
, getSkuEnabledTypeDeclaration(t
), true);
1085 declaList
.add(decl
);
1086 instTable
.put(t
.getPrimaryKeyString(),
1087 getSkuEnabledTypeInstantiaion(t
, tableIdx
));
1091 // Insert PCD_ENTRY declaration and instantiation
1093 getCDeclarationString(t
);
1095 decl
= new CStructTypeDeclaration(privateGlobalName
,
1096 getAlignmentSize(t
), privateGlobalCCode
, t
.hasDefaultValue());
1097 declaList
.add(decl
);
1099 if (t
.hasDefaultValue()) {
1100 instTable
.put(privateGlobalName
,
1101 getTypeInstantiation(t
, declaList
, instTable
, phase
)
1107 private void ProcessTokens (List
<Token
> tokens
,
1108 ArrayList
<CStructTypeDeclaration
> cStructDeclList
,
1109 HashMap
<String
, String
> cStructInstTable
,
1112 throws EntityException
{
1114 for (int idx
= 0; idx
< tokens
.size(); idx
++) {
1115 Token t
= tokens
.get(idx
);
1117 genCodeWorker (t
, cStructDeclList
, cStructInstTable
, phase
);
1120 localTokenNumberTable
.add(t
);
1121 t
.tokenNumber
= assignedTokenNumber
++;
1124 // Add a mapping if this dynamic PCD entry is a EX type
1126 if (t
.isDynamicEx()) {
1127 exMapTable
.add((int)t
.tokenNumber
,
1128 t
.dynamicExTokenNumber
,
1129 guidTable
.add(translateSchemaStringToUUID(t
.tokenSpaceName
), t
.getPrimaryKeyString()),
1130 t
.getPrimaryKeyString()
1137 public void genCode () throws EntityException
{
1139 ArrayList
<CStructTypeDeclaration
> cStructDeclList
= new ArrayList
<CStructTypeDeclaration
>();
1140 HashMap
<String
, String
> cStructInstTable
= new HashMap
<String
, String
>();
1142 List
<Token
> nexTokens
= new ArrayList
<Token
> ();
1143 List
<Token
> exTokens
= new ArrayList
<Token
> ();
1145 getNonExAndExTokens (alTokens
, nexTokens
, exTokens
);
1148 // We have to process Non-Ex type PCD entry first. The reason is
1149 // that our optimization assumes that the Token Number of Non-Ex
1150 // PCD entry start from 1 (for PEI phase) and grows continously upwards.
1152 // EX type token number starts from the last Non-EX PCD entry and
1153 // grows continously upwards.
1155 ProcessTokens (nexTokens
, cStructDeclList
, cStructInstTable
, phase
);
1156 ProcessTokens (exTokens
, cStructDeclList
, cStructInstTable
, phase
);
1158 stringTable
.genCode(cStructDeclList
, cStructInstTable
);
1159 skuIdTable
.genCode(cStructDeclList
, cStructInstTable
, phase
);
1160 exMapTable
.genCode(cStructDeclList
, cStructInstTable
, phase
);
1161 localTokenNumberTable
.genCode(cStructDeclList
, cStructInstTable
, phase
);
1162 sizeTable
.genCode(cStructDeclList
, cStructInstTable
, phase
);
1163 guidTable
.genCode(cStructDeclList
, cStructInstTable
, phase
);
1165 hString
= genCMacroCode ();
1167 HashMap
<String
, String
> result
;
1169 result
= genCStructCode(cStructDeclList
,
1174 hString
+= result
.get("initDeclStr");
1175 hString
+= result
.get("uninitDeclStr");
1177 hString
+= String
.format("#define PCD_%s_SERVICE_DRIVER_VERSION %d", phase
, version
);
1179 cString
= newLine
+ newLine
+ result
.get("initInstStr");
1183 private String
genCMacroCode () {
1184 String macroStr
= "";
1187 // Generate size info Macro for all Tables
1189 macroStr
+= guidTable
.getSizeMacro();
1190 macroStr
+= stringTable
.getSizeMacro();
1191 macroStr
+= skuIdTable
.getSizeMacro();
1192 macroStr
+= localTokenNumberTable
.getSizeMacro();
1193 macroStr
+= exMapTable
.getSizeMacro();
1194 macroStr
+= sizeTable
.getSizeMacro();
1197 // Generate existance info Macro for all Tables
1199 macroStr
+= guidTable
.getExistanceMacro();
1200 macroStr
+= stringTable
.getExistanceMacro();
1201 macroStr
+= skuIdTable
.getExistanceMacro();
1202 macroStr
+= localTokenNumberTable
.getExistanceMacro();
1203 macroStr
+= exMapTable
.getExistanceMacro();
1205 macroStr
+= newLine
;
1210 private HashMap
<String
, String
> genCStructCode(
1211 ArrayList
<CStructTypeDeclaration
> declaList
,
1212 HashMap
<String
, String
> instTable
,
1217 HashMap
<String
, String
> result
= new HashMap
<String
, String
>();
1218 HashMap
<Integer
, ArrayList
<String
>> alignmentInitDecl
= new HashMap
<Integer
, ArrayList
<String
>>();
1219 HashMap
<Integer
, ArrayList
<String
>> alignmentUninitDecl
= new HashMap
<Integer
, ArrayList
<String
>>();
1220 HashMap
<Integer
, ArrayList
<String
>> alignmentInitInst
= new HashMap
<Integer
, ArrayList
<String
>>();
1223 // Initialize the storage for each alignment
1225 for (i
= 8; i
> 0; i
>>=1) {
1226 alignmentInitDecl
.put(new Integer(i
), new ArrayList
<String
>());
1227 alignmentInitInst
.put(new Integer(i
), new ArrayList
<String
>());
1228 alignmentUninitDecl
.put(new Integer(i
), new ArrayList
<String
>());
1231 String initDeclStr
= "typedef struct {" + newLine
;
1232 String initInstStr
= String
.format("%s_PCD_DATABASE_INIT g%sPcdDbInit = { ", phase
.toUpperCase(), phase
.toUpperCase()) + newLine
;
1233 String uninitDeclStr
= "typedef struct {" + newLine
;
1236 // Sort all C declaration and instantiation base on Alignment Size
1238 for (Object d
: declaList
) {
1239 CStructTypeDeclaration decl
= (CStructTypeDeclaration
) d
;
1241 if (decl
.initTable
) {
1242 alignmentInitDecl
.get(new Integer(decl
.alignmentSize
)).add(decl
.cCode
);
1243 alignmentInitInst
.get(new Integer(decl
.alignmentSize
)).add(instTable
.get(decl
.key
));
1245 alignmentUninitDecl
.get(new Integer(decl
.alignmentSize
)).add(decl
.cCode
);
1250 // Generate code for every alignment size
1252 boolean uinitDatabaseEmpty
= true;
1253 for (int align
= 8; align
> 0; align
>>= 1) {
1254 ArrayList
<String
> declaListBasedOnAlignment
= alignmentInitDecl
.get(new Integer(align
));
1255 ArrayList
<String
> instListBasedOnAlignment
= alignmentInitInst
.get(new Integer(align
));
1256 for (i
= 0; i
< declaListBasedOnAlignment
.size(); i
++) {
1257 initDeclStr
+= tab
+ declaListBasedOnAlignment
.get(i
);
1258 initInstStr
+= tab
+ instListBasedOnAlignment
.get(i
);
1261 // We made a assumption that both PEI_PCD_DATABASE and DXE_PCD_DATABASE
1262 // has a least one data memember with alignment size of 1. So we can
1263 // remove the last "," in the C structure instantiation string. Luckily,
1264 // this is true as both data structure has SKUID_TABLE anyway.
1266 if ((align
== 1) && (i
== declaListBasedOnAlignment
.size() - 1)) {
1267 initInstStr
+= newLine
;
1269 initInstStr
+= commaNewLine
;
1273 declaListBasedOnAlignment
= alignmentUninitDecl
.get(new Integer(align
));
1275 if (declaListBasedOnAlignment
.size() != 0) {
1276 uinitDatabaseEmpty
= false;
1279 for (Object d
: declaListBasedOnAlignment
) {
1280 String s
= (String
)d
;
1281 uninitDeclStr
+= tab
+ s
;
1285 if (uinitDatabaseEmpty
) {
1286 uninitDeclStr
+= tab
+ String
.format("%-20sdummy; /* PCD_DATABASE_UNINIT is emptry */\r\n", "UINT8");
1289 initDeclStr
+= String
.format("} %s_PCD_DATABASE_INIT;", phase
) + newLine
+ newLine
;
1290 initInstStr
+= "};" + newLine
;
1291 uninitDeclStr
+= String
.format("} %s_PCD_DATABASE_UNINIT;", phase
) + newLine
+ newLine
;
1293 result
.put("initDeclStr", initDeclStr
);
1294 result
.put("initInstStr", initInstStr
);
1295 result
.put("uninitDeclStr", uninitDeclStr
);
1300 public static String
genInstantiationStr (ArrayList
<String
> alStr
) {
1302 for (int i
= 0; i
< alStr
.size(); i
++) {
1306 str
+= alStr
.get(i
);
1307 if (i
!= alStr
.size() - 1) {
1315 private String
getSkuEnabledTypeDeclaration (Token token
) {
1316 return String
.format("%-20s%s;\r\n", "SKU_HEAD", token
.getPrimaryKeyString());
1319 private String
getSkuEnabledTypeInstantiaion (Token token
, int SkuTableIdx
) {
1321 String offsetof
= String
.format(PcdDatabase
.offsetOfSkuHeadStrTemplate
, phase
, token
.hasDefaultValue()?
"Init" : "Uninit", token
.getPrimaryKeyString());
1322 return String
.format("{ %s, %d } /* SKU_ENABLED: %s */", offsetof
, SkuTableIdx
, token
.getPrimaryKeyString());
1325 private String
getDataTypeInstantiationForVariableDefault (Token token
, String cName
, int skuId
) {
1326 return String
.format("%s /* %s */", token
.skuData
.get(skuId
).value
.hiiDefaultValue
, cName
);
1329 private String
getCType (Token t
)
1330 throws EntityException
{
1332 if (t
.isHiiEnable()) {
1333 return "VARIABLE_HEAD";
1336 if (t
.isVpdEnable()) {
1340 if (t
.isUnicodeStringType()) {
1341 return "STRING_HEAD";
1344 switch (t
.datumType
) {
1358 throw new EntityException("Unknown type in getDataTypeCDeclaration");
1363 // privateGlobalName and privateGlobalCCode is used to pass output to caller of getCDeclarationString
1365 private void getCDeclarationString(Token t
)
1366 throws EntityException
{
1368 if (t
.isSkuEnable()) {
1369 privateGlobalName
= String
.format("%s_%s", t
.getPrimaryKeyString(), skuDataTableTemplate
);
1371 privateGlobalName
= t
.getPrimaryKeyString();
1374 String type
= getCType(t
);
1375 if ((t
.datumType
== Token
.DATUM_TYPE
.POINTER
) && (!t
.isHiiEnable()) && (!t
.isUnicodeStringType())) {
1377 if (t
.isASCIIStringType()) {
1379 // Build tool will add a NULL string at the end of the ASCII string
1381 bufferSize
= t
.datumSize
+ 1;
1383 bufferSize
= t
.datumSize
;
1385 privateGlobalCCode
= String
.format("%-20s%s[%d][%d];\r\n", type
, privateGlobalName
, t
.getSkuIdCount(), bufferSize
);
1387 privateGlobalCCode
= String
.format("%-20s%s[%d];\r\n", type
, privateGlobalName
, t
.getSkuIdCount());
1391 private String
getDataTypeDeclarationForVariableDefault (Token token
, String cName
, int skuId
)
1392 throws EntityException
{
1396 if (token
.datumType
== Token
.DATUM_TYPE
.UINT8
) {
1398 } else if (token
.datumType
== Token
.DATUM_TYPE
.UINT16
) {
1400 } else if (token
.datumType
== Token
.DATUM_TYPE
.UINT32
) {
1402 } else if (token
.datumType
== Token
.DATUM_TYPE
.UINT64
) {
1404 } else if (token
.datumType
== Token
.DATUM_TYPE
.BOOLEAN
) {
1405 typeStr
= "BOOLEAN";
1406 } else if (token
.datumType
== Token
.DATUM_TYPE
.POINTER
) {
1408 if (token
.isHiiDefaultValueUnicodeStringType()) {
1411 // Include the NULL charactor
1413 size
= token
.datumSize
/ 2 + 1;
1416 if (token
.isHiiDefaultValueASCIIStringType()) {
1418 // Include the NULL charactor
1420 size
= token
.datumSize
+ 1;
1422 size
= token
.datumSize
;
1425 return String
.format("%-20s%s[%d];\r\n", typeStr
, cName
, size
);
1427 throw new EntityException("Unknown DATUM_TYPE type in when generating code for VARIABLE_ENABLED PCD entry");
1430 return String
.format("%-20s%s;\r\n", typeStr
, cName
);
1433 private String
getTypeInstantiation (Token t
, ArrayList
<CStructTypeDeclaration
> declaList
, HashMap
<String
, String
> instTable
, String phase
) throws EntityException
{
1438 s
= String
.format("/* %s */", t
.getPrimaryKeyString()) + newLine
;
1439 s
+= tab
+ "{" + newLine
;
1441 for (i
= 0; i
< t
.skuData
.size(); i
++) {
1442 if (t
.isUnicodeStringType()) {
1443 s
+= tab
+ tab
+ String
.format("{ %d }", stringTable
.add(t
.skuData
.get(i
).value
.value
, t
));
1444 } else if (t
.isHiiEnable()) {
1445 /* VPD_HEAD definition
1447 UINT16 GuidTableIndex; // Offset in Guid Table in units of GUID.
1448 UINT16 StringIndex; // Offset in String Table in units of UINT16.
1449 UINT16 Offset; // Offset in Variable
1450 UINT16 DefaultValueOffset; // Offset of the Default Value
1453 String variableDefaultName
= String
.format("%s_VariableDefault_%d", t
.getPrimaryKeyString(), i
);
1455 s
+= tab
+ tab
+ String
.format("{ %d, %d, %s, %s }", guidTable
.add(t
.skuData
.get(i
).value
.variableGuid
, t
.getPrimaryKeyString()),
1456 stringTable
.add(t
.skuData
.get(i
).value
.getStringOfVariableName(), t
),
1457 t
.skuData
.get(i
).value
.variableOffset
,
1458 String
.format("offsetof(%s_PCD_DATABASE, Init.%s)", phase
, variableDefaultName
)
1461 // We need to support the default value, so we add the declaration and
1462 // the instantiation for the default value.
1464 CStructTypeDeclaration decl
= new CStructTypeDeclaration (variableDefaultName
,
1465 getHiiPtrTypeAlignmentSize(t
),
1466 getDataTypeDeclarationForVariableDefault(t
, variableDefaultName
, i
),
1469 declaList
.add(decl
);
1470 instTable
.put(variableDefaultName
, getDataTypeInstantiationForVariableDefault (t
, variableDefaultName
, i
));
1471 } else if (t
.isVpdEnable()) {
1476 s
+= tab
+ tab
+ String
.format("{ %s }", t
.skuData
.get(i
).value
.vpdOffset
);
1478 if (t
.isByteStreamType()) {
1480 // Byte stream type input has their own "{" "}", so we won't help to insert.
1482 s
+= tab
+ tab
+ String
.format(" %s ", t
.skuData
.get(i
).value
.value
);
1484 s
+= tab
+ tab
+ String
.format("{ %s }", t
.skuData
.get(i
).value
.value
);
1488 if (i
!= t
.skuData
.size() - 1) {
1501 public static String
getPcdDatabaseCommonDefinitions ()
1502 throws EntityException
{
1506 File file
= new File(GlobalData
.getWorkspacePath() + File
.separator
+
1507 "Tools" + File
.separator
+
1508 "Conf" + File
.separator
+
1509 "Pcd" + File
.separator
+
1510 "PcdDatabaseCommonDefinitions.sample");
1511 FileReader reader
= new FileReader(file
);
1512 BufferedReader in
= new BufferedReader(reader
);
1514 while ((str
= in
.readLine()) != null) {
1515 retStr
= retStr
+"\r\n" + str
;
1517 } catch (Exception ex
) {
1518 throw new EntityException("Fatal error when generating PcdDatabase Common Definitions");
1524 public static String
getPcdDxeDatabaseDefinitions ()
1525 throws EntityException
{
1529 File file
= new File(GlobalData
.getWorkspacePath() + File
.separator
+
1530 "Tools" + File
.separator
+
1531 "Conf" + File
.separator
+
1532 "Pcd" + File
.separator
+
1533 "PcdDatabaseDxeDefinitions.sample");
1534 FileReader reader
= new FileReader(file
);
1535 BufferedReader in
= new BufferedReader(reader
);
1537 while ((str
= in
.readLine()) != null) {
1538 retStr
= retStr
+"\r\n" + str
;
1540 } catch (Exception ex
) {
1541 throw new EntityException("Fatal error when generating PcdDatabase Dxe Definitions");
1547 public static String
getPcdPeiDatabaseDefinitions ()
1548 throws EntityException
{
1552 File file
= new File(GlobalData
.getWorkspacePath() + File
.separator
+
1553 "Tools" + File
.separator
+
1554 "Conf" + File
.separator
+
1555 "Pcd" + File
.separator
+
1556 "PcdDatabasePeiDefinitions.sample");
1557 FileReader reader
= new FileReader(file
);
1558 BufferedReader in
= new BufferedReader(reader
);
1560 while ((str
= in
.readLine()) != null) {
1561 retStr
= retStr
+"\r\n" + str
;
1563 } catch (Exception ex
) {
1564 throw new EntityException("Fatal error when generating PcdDatabase Pei Definitions");
1571 Translate the schema string to UUID instance.
1573 In schema, the string of UUID is defined as following two types string:
1574 1) GuidArrayType: pattern = 0x[a-fA-F0-9]{1,8},( )*0x[a-fA-F0-9]{1,4},(
1575 )*0x[a-fA-F0-9]{1,4}(,( )*\{)?(,?( )*0x[a-fA-F0-9]{1,2}){8}( )*(\})?
1577 2) GuidNamingConvention: pattern =
1578 [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}
1580 This function will convert string and create uuid instance.
1582 @param uuidString UUID string in XML file
1584 @return UUID UUID instance
1586 private UUID
translateSchemaStringToUUID(String uuidString
)
1587 throws EntityException
{
1589 String
[] splitStringArray
;
1594 if (uuidString
== null) {
1598 if (uuidString
.length() == 0) {
1602 if (uuidString
.equals("0") ||
1603 uuidString
.equalsIgnoreCase("0x0")) {
1604 return new UUID(0, 0);
1607 uuidString
= uuidString
.replaceAll("\\{", "");
1608 uuidString
= uuidString
.replaceAll("\\}", "");
1611 // If the UUID schema string is GuidArrayType type then need translate
1612 // to GuidNamingConvention type at first.
1614 if ((uuidString
.charAt(0) == '0') && ((uuidString
.charAt(1) == 'x') || (uuidString
.charAt(1) == 'X'))) {
1615 splitStringArray
= uuidString
.split("," );
1616 if (splitStringArray
.length
!= 11) {
1617 throw new EntityException ("[FPD file error] Wrong format for UUID string: " + uuidString
);
1621 // Remove blank space from these string and remove header string "0x"
1623 for (index
= 0; index
< 11; index
++) {
1624 splitStringArray
[index
] = splitStringArray
[index
].trim();
1625 splitStringArray
[index
] = splitStringArray
[index
].substring(2, splitStringArray
[index
].length());
1629 // Add heading '0' to normalize the string length
1631 for (index
= 3; index
< 11; index
++) {
1632 chLen
= splitStringArray
[index
].length();
1633 for (chIndex
= 0; chIndex
< 2 - chLen
; chIndex
++) {
1634 splitStringArray
[index
] = "0" + splitStringArray
[index
];
1639 // construct the final GuidNamingConvention string
1641 temp
= String
.format("%s-%s-%s-%s%s-%s%s%s%s%s%s",
1642 splitStringArray
[0],
1643 splitStringArray
[1],
1644 splitStringArray
[2],
1645 splitStringArray
[3],
1646 splitStringArray
[4],
1647 splitStringArray
[5],
1648 splitStringArray
[6],
1649 splitStringArray
[7],
1650 splitStringArray
[8],
1651 splitStringArray
[9],
1652 splitStringArray
[10]);
1656 return UUID
.fromString(uuidString
);
1660 /** Module Info class is the data structure to hold information got from GlobalData.
1664 /// Module's ID for a <ModuleSA>
1666 private FpdModuleIdentification moduleId
;
1668 /// <PcdBuildDefinition> xmlobject in FPD file for a <ModuleSA>
1670 private PcdBuildDefinitionDocument
.PcdBuildDefinition pcdBuildDef
;
1672 public ModuleInfo (FpdModuleIdentification moduleId
, XmlObject pcdDef
) {
1673 this.moduleId
= moduleId
;
1674 this.pcdBuildDef
= ((PcdBuildDefinitionDocument
)pcdDef
).getPcdBuildDefinition();
1677 public FpdModuleIdentification
getModuleId (){
1681 public PcdBuildDefinitionDocument
.PcdBuildDefinition
getPcdBuildDef(){
1686 /** This action class is to collect PCD information from MSA, SPD, FPD xml file.
1687 This class will be used for wizard and build tools, So it can *not* inherit
1688 from buildAction or UIAction.
1690 public class CollectPCDAction
{
1692 /// memoryDatabase hold all PCD information collected from SPD, MSA, FPD.
1694 private MemoryDatabaseManager dbManager
;
1696 /// Workspacepath hold the workspace information.
1698 private String workspacePath
;
1700 /// FPD file is the root file.
1702 private String fpdFilePath
;
1704 /// Message level for CollectPCDAction.
1706 private int originalMessageLevel
;
1708 /// Cache the fpd docment instance for private usage.
1710 private PlatformSurfaceAreaDocument fpdDocInstance
;
1714 private static String xmlObjectName
= "PcdBuildDefinition";
1717 Set WorkspacePath parameter for this action class.
1719 @param workspacePath parameter for this action
1721 public void setWorkspacePath(String workspacePath
) {
1722 this.workspacePath
= workspacePath
;
1726 Set action message level for CollectPcdAction tool.
1728 The message should be restored when this action exit.
1730 @param actionMessageLevel parameter for this action
1732 public void setActionMessageLevel(int actionMessageLevel
) {
1733 originalMessageLevel
= ActionMessage
.messageLevel
;
1734 ActionMessage
.messageLevel
= actionMessageLevel
;
1738 Set FPDFileName parameter for this action class.
1740 @param fpdFilePath fpd file path
1742 public void setFPDFilePath(String fpdFilePath
) {
1743 this.fpdFilePath
= fpdFilePath
;
1747 Common function interface for outer.
1749 @param workspacePath The path of workspace of current build or analysis.
1750 @param fpdFilePath The fpd file path of current build or analysis.
1751 @param messageLevel The message level for this Action.
1753 @throws Exception The exception of this function. Because it can *not* be predict
1754 where the action class will be used. So only Exception can be throw.
1757 public void perform(String workspacePath
, String fpdFilePath
,
1758 int messageLevel
) throws Exception
{
1759 setWorkspacePath(workspacePath
);
1760 setFPDFilePath(fpdFilePath
);
1761 setActionMessageLevel(messageLevel
);
1764 ActionMessage
.messageLevel
= originalMessageLevel
;
1768 Core execution function for this action class.
1770 This function work flows will be:
1771 1) Collect and prepocess PCD information from FPD file, all PCD
1772 information will be stored into memory database.
1773 2) Generate 3 strings for
1774 a) All modules using Dynamic(Ex) PCD entry.(Token Number)
1775 b) PEI PCDDatabase (C Structure) for PCD Service PEIM.
1776 c) DXE PCD Database (C structure) for PCD Service DXE.
1779 @throws EntityException Exception indicate failed to execute this action.
1782 public void execute() throws EntityException
{
1784 // Get memoryDatabaseManager instance from GlobalData.
1785 // The memoryDatabaseManager should be initialized for whatever build
1786 // tools or wizard tools
1788 if((dbManager
= GlobalData
.getPCDMemoryDBManager()) == null) {
1789 throw new EntityException("The instance of PCD memory database manager is null");
1793 // Collect all PCD information defined in FPD file.
1794 // Evenry token defind in FPD will be created as an token into
1797 createTokenInDBFromFPD();
1800 // Generate for PEI, DXE PCD DATABASE's definition and initialization.
1802 genPcdDatabaseSourceCode ();
1807 This function generates source code for PCD Database.
1810 @throws EntityException If the token does *not* exist in memory database.
1813 private void genPcdDatabaseSourceCode()
1814 throws EntityException
{
1815 String PcdCommonHeaderString
= PcdDatabase
.getPcdDatabaseCommonDefinitions();
1817 ArrayList
<Token
> alPei
= new ArrayList
<Token
> ();
1818 ArrayList
<Token
> alDxe
= new ArrayList
<Token
> ();
1820 dbManager
.getTwoPhaseDynamicRecordArray(alPei
, alDxe
);
1821 PcdDatabase pcdPeiDatabase
= new PcdDatabase (alPei
, "PEI", 0);
1822 pcdPeiDatabase
.genCode();
1823 MemoryDatabaseManager
.PcdPeimHString
= PcdCommonHeaderString
+ pcdPeiDatabase
.getHString() +
1824 PcdDatabase
.getPcdPeiDatabaseDefinitions();
1825 MemoryDatabaseManager
.PcdPeimCString
= pcdPeiDatabase
.getCString();
1827 PcdDatabase pcdDxeDatabase
= new PcdDatabase(alDxe
, "DXE", alPei
.size());
1828 pcdDxeDatabase
.genCode();
1829 MemoryDatabaseManager
.PcdDxeHString
= MemoryDatabaseManager
.PcdPeimHString
+ pcdDxeDatabase
.getHString() +
1830 PcdDatabase
.getPcdDxeDatabaseDefinitions();
1831 MemoryDatabaseManager
.PcdDxeCString
= pcdDxeDatabase
.getCString();
1835 Get component array from FPD.
1837 This function maybe provided by some Global class.
1839 @return List<ModuleInfo> the component array.
1842 private List
<ModuleInfo
> getComponentsFromFPD()
1843 throws EntityException
{
1844 List
<ModuleInfo
> allModules
= new ArrayList
<ModuleInfo
>();
1845 FrameworkModulesDocument
.FrameworkModules fModules
= null;
1846 ModuleSADocument
.ModuleSA
[] modules
= null;
1847 Map
<FpdModuleIdentification
, XmlObject
> pcdBuildDefinitions
= null;
1849 pcdBuildDefinitions
= GlobalData
.getFpdPcdBuildDefinitions();
1850 if (pcdBuildDefinitions
== null) {
1855 // Loop map to retrieve all PCD build definition and Module id
1857 Iterator item
= pcdBuildDefinitions
.keySet().iterator();
1858 while (item
.hasNext()){
1859 FpdModuleIdentification id
= (FpdModuleIdentification
) item
.next();
1860 allModules
.add(new ModuleInfo(id
, pcdBuildDefinitions
.get(id
)));
1867 Create token instance object into memory database, the token information
1868 comes for FPD file. Normally, FPD file will contain all token platform
1871 @return FrameworkPlatformDescriptionDocument The FPD document instance for furture usage.
1873 @throws EntityException Failed to parse FPD xml file.
1876 private void createTokenInDBFromFPD()
1877 throws EntityException
{
1881 List
<PcdBuildDefinition
.PcdData
> pcdBuildDataArray
= new ArrayList
<PcdBuildDefinition
.PcdData
>();
1882 PcdBuildDefinition
.PcdData pcdBuildData
= null;
1884 List
<ModuleInfo
> modules
= null;
1885 String primaryKey
= null;
1886 String exceptionString
= null;
1887 UsageInstance usageInstance
= null;
1888 String primaryKey1
= null;
1889 String primaryKey2
= null;
1890 boolean isDuplicate
= false;
1891 Token
.PCD_TYPE pcdType
= Token
.PCD_TYPE
.UNKNOWN
;
1892 Token
.DATUM_TYPE datumType
= Token
.DATUM_TYPE
.UNKNOWN
;
1893 long tokenNumber
= 0;
1894 String moduleName
= null;
1895 String datum
= null;
1896 int maxDatumSize
= 0;
1897 String
[] tokenSpaceStrRet
= null;
1898 UsageIdentification usageId
= null;
1899 ModuleIdentification moduleId
= null;
1902 // ----------------------------------------------
1903 // 1), Get all <ModuleSA> from FPD file.
1904 // ----------------------------------------------
1906 modules
= getComponentsFromFPD();
1908 if (modules
== null) {
1909 throw new EntityException("[FPD file error] No modules in FPD file, Please check whether there are elements in <FrameworkModules> in FPD file!");
1913 // -------------------------------------------------------------------
1914 // 2), Loop all modules to process <PcdBuildDeclarations> for each module.
1915 // -------------------------------------------------------------------
1917 for (index
= 0; index
< modules
.size(); index
++) {
1919 // It is legal for a module does not contains ANY pcd build definitions.
1921 if (modules
.get(index
).getPcdBuildDef() == null) {
1925 pcdBuildDataArray
= modules
.get(index
).getPcdBuildDef().getPcdDataList();
1927 moduleName
= modules
.get(index
).getModuleId().getModule().getName();
1930 // ----------------------------------------------------------------------
1931 // 2.1), Loop all Pcd entry for a module and add it into memory database.
1932 // ----------------------------------------------------------------------
1934 for (pcdIndex
= 0; pcdIndex
< pcdBuildDataArray
.size(); pcdIndex
++) {
1935 pcdBuildData
= pcdBuildDataArray
.get(pcdIndex
);
1938 tokenSpaceStrRet
= GlobalData
.getGuidInfoFromCname(pcdBuildData
.getTokenSpaceGuidCName());
1939 } catch ( Exception e
) {
1940 throw new EntityException ("Faile get Guid for token " + pcdBuildData
.getCName() + ":" + e
.getMessage());
1943 if (tokenSpaceStrRet
== null) {
1944 throw new EntityException ("Fail to get Token space guid for token" + pcdBuildData
.getCName());
1947 primaryKey
= Token
.getPrimaryKeyString(pcdBuildData
.getCName(), tokenSpaceStrRet
[1]);
1948 pcdType
= Token
.getpcdTypeFromString(pcdBuildData
.getItemType().toString());
1949 datumType
= Token
.getdatumTypeFromString(pcdBuildData
.getDatumType().toString());
1950 tokenNumber
= Long
.decode(pcdBuildData
.getToken().toString());
1951 if (pcdBuildData
.getValue() != null) {
1952 datum
= pcdBuildData
.getValue().toString();
1956 maxDatumSize
= pcdBuildData
.getMaxDatumSize();
1958 if ((pcdType
== Token
.PCD_TYPE
.FEATURE_FLAG
) &&
1959 (datumType
!= Token
.DATUM_TYPE
.BOOLEAN
)){
1960 exceptionString
= String
.format("[FPD file error] For PCD %s in module %s, the PCD type is FEATRUE_FLAG but "+
1961 "datum type of this PCD entry is not BOOLEAN!",
1962 pcdBuildData
.getCName(),
1964 throw new EntityException(exceptionString
);
1968 // -------------------------------------------------------------------------------------------
1969 // 2.1.1), Do some necessary checking work for FixedAtBuild, FeatureFlag and PatchableInModule
1970 // -------------------------------------------------------------------------------------------
1972 if (!Token
.isDynamic(pcdType
)) {
1974 // Value is required.
1976 if (datum
== null) {
1977 exceptionString
= String
.format("[FPD file error] There is no value for PCD entry %s in module %s!",
1978 pcdBuildData
.getCName(),
1980 throw new EntityException(exceptionString
);
1984 // Check whether the datum size is matched datum type.
1986 if ((exceptionString
= verifyDatum(pcdBuildData
.getCName(),
1990 maxDatumSize
)) != null) {
1991 throw new EntityException(exceptionString
);
1996 // ---------------------------------------------------------------------------------
1997 // 2.1.2), Create token or update token information for current anaylized PCD data.
1998 // ---------------------------------------------------------------------------------
2000 if (dbManager
.isTokenInDatabase(primaryKey
)) {
2002 // If the token is already exist in database, do some necessary checking
2003 // and add a usage instance into this token in database
2005 token
= dbManager
.getTokenByKey(primaryKey
);
2008 // checking for DatumType, DatumType should be unique for one PCD used in different
2011 if (token
.datumType
!= datumType
) {
2012 exceptionString
= String
.format("[FPD file error] The datum type of PCD entry %s is %s, which is different with %s defined in before!",
2013 pcdBuildData
.getCName(),
2014 pcdBuildData
.getDatumType().toString(),
2015 Token
.getStringOfdatumType(token
.datumType
));
2016 throw new EntityException(exceptionString
);
2020 // Check token number is valid
2022 if (tokenNumber
!= token
.tokenNumber
) {
2023 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!",
2024 pcdBuildData
.getCName(),
2026 throw new EntityException(exceptionString
);
2030 // For same PCD used in different modules, the PCD type should all be dynamic or non-dynamic.
2032 if (token
.isDynamicPCD
!= Token
.isDynamic(pcdType
)) {
2033 exceptionString
= String
.format("[FPD file error] For PCD entry %s in module %s, you define dynamic or non-dynamic PCD type which"+
2034 "is different with others module's",
2037 throw new EntityException(exceptionString
);
2040 if (token
.isDynamicPCD
) {
2042 // Check datum is equal the datum in dynamic information.
2043 // For dynamic PCD, you can do not write <Value> in sperated every <PcdBuildDefinition> in different <ModuleSA>,
2044 // But if you write, the <Value> must be same as the value in <DynamicPcdBuildDefinitions>.
2046 if (!token
.isSkuEnable() &&
2047 (token
.getDefaultSku().type
== DynamicTokenValue
.VALUE_TYPE
.DEFAULT_TYPE
) &&
2049 if (!datum
.equalsIgnoreCase(token
.getDefaultSku().value
)) {
2050 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s in module %s, the datum in <ModuleSA> is "+
2051 "not equal to the datum in <DynamicPcdBuildDefinitions>, it is "+
2052 "illega! You could no set <Value> in <ModuleSA> for a dynamic PCD!",
2055 throw new EntityException(exceptionString
);
2059 if ((maxDatumSize
!= 0) &&
2060 (maxDatumSize
!= token
.datumSize
)){
2061 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s in module %s, the max datum size is %d which "+
2062 "is different with <MaxDatumSize> %d defined in <DynamicPcdBuildDefinitions>!",
2067 throw new EntityException(exceptionString
);
2073 // If the token is not in database, create a new token instance and add
2074 // a usage instance into this token in database.
2077 tokenSpaceStrRet
= GlobalData
.getGuidInfoFromCname(pcdBuildData
.getTokenSpaceGuidCName());
2078 } catch (Exception e
) {
2079 throw new EntityException("Fail to get token space guid for token " + token
.cName
);
2082 if (tokenSpaceStrRet
== null) {
2083 throw new EntityException("Fail to get token space guid for token " + token
.cName
);
2086 token
= new Token(pcdBuildData
.getCName(), tokenSpaceStrRet
[1]);
2088 token
.datumType
= datumType
;
2089 token
.tokenNumber
= tokenNumber
;
2090 token
.isDynamicPCD
= Token
.isDynamic(pcdType
);
2091 token
.datumSize
= maxDatumSize
;
2093 if (token
.isDynamicPCD
) {
2095 // For Dynamic and Dynamic Ex type, need find the dynamic information
2096 // in <DynamicPcdBuildDefinition> section in FPD file.
2098 updateDynamicInformation(moduleName
,
2104 dbManager
.addTokenToDatabase(primaryKey
, token
);
2108 // -----------------------------------------------------------------------------------
2109 // 2.1.3), Add the PcdType in current module into this Pcd token's supported PCD type.
2110 // -----------------------------------------------------------------------------------
2112 token
.updateSupportPcdType(pcdType
);
2115 // ------------------------------------------------
2116 // 2.1.4), Create an usage instance for this token.
2117 // ------------------------------------------------
2119 moduleId
= modules
.get(index
).getModuleId().getModule();
2120 usageId
= new UsageIdentification (moduleId
.getName(),
2122 moduleId
.getPackage().getName(),
2123 moduleId
.getPackage().getGuid(),
2124 modules
.get(index
).getModuleId().getArch(),
2125 moduleId
.getVersion(),
2126 moduleId
.getModuleType());
2127 usageInstance
= new UsageInstance(token
,
2132 token
.addUsageInstance(usageInstance
);
2137 // ------------------------------------------------
2138 // 3), Add unreference dynamic_Ex pcd token into Pcd database.
2139 // ------------------------------------------------
2141 List
<Token
> tokenArray
= getUnreferencedDynamicPcd();
2142 if (tokenArray
!= null) {
2143 for (index
= 0; index
< tokenArray
.size(); index
++) {
2144 dbManager
.addTokenToDatabase(tokenArray
.get(index
).getPrimaryKeyString(),
2145 tokenArray
.get(index
));
2150 private List
<Token
> getUnreferencedDynamicPcd () throws EntityException
{
2151 List
<Token
> tokenArray
= new ArrayList
<Token
>();
2153 DynamicPcdBuildDefinitions dynamicPcdBuildDefinitions
= null;
2154 List
<DynamicPcdBuildDefinitions
.PcdBuildData
> dynamicPcdBuildDataArray
= null;
2155 DynamicPcdBuildDefinitions
.PcdBuildData pcdBuildData
= null;
2156 List
<DynamicPcdBuildDefinitions
.PcdBuildData
.SkuInfo
> skuInfoList
= null;
2157 Token
.PCD_TYPE pcdType
;
2158 SkuInstance skuInstance
= null;
2159 String primaryKey
= null;
2160 boolean hasSkuId0
= false;
2161 int index
, offset
, index2
;
2163 String exceptionString
;
2164 String hiiDefaultValue
;
2165 String tokenSpaceStrRet
[];
2166 String variableGuidString
[];
2169 // Open fpd document to get <DynamicPcdBuildDefinition> Section.
2170 // BUGBUG: the function should be move GlobalData in furture.
2172 if (fpdDocInstance
== null) {
2174 fpdDocInstance
= (PlatformSurfaceAreaDocument
)XmlObject
.Factory
.parse(new File(fpdFilePath
));
2175 } catch(IOException ioE
) {
2176 throw new EntityException("File IO error for xml file:" + fpdFilePath
+ "\n" + ioE
.getMessage());
2177 } catch(XmlException xmlE
) {
2178 throw new EntityException("Can't parse the FPD xml fle:" + fpdFilePath
+ "\n" + xmlE
.getMessage());
2182 dynamicPcdBuildDefinitions
= fpdDocInstance
.getPlatformSurfaceArea().getDynamicPcdBuildDefinitions();
2183 if (dynamicPcdBuildDefinitions
== null) {
2187 dynamicPcdBuildDataArray
= dynamicPcdBuildDefinitions
.getPcdBuildDataList();
2188 for (index2
= 0; index2
< dynamicPcdBuildDataArray
.size(); index2
++) {
2189 pcdBuildData
= dynamicPcdBuildDataArray
.get(index2
);
2191 tokenSpaceStrRet
= GlobalData
.getGuidInfoFromCname(pcdBuildData
.getTokenSpaceGuidCName());
2192 } catch ( Exception e
) {
2193 throw new EntityException ("Faile get Guid for token " + pcdBuildData
.getCName() + ":" + e
.getMessage());
2196 if (tokenSpaceStrRet
== null) {
2197 throw new EntityException ("Fail to get Token space guid for token" + pcdBuildData
.getCName());
2200 primaryKey
= Token
.getPrimaryKeyString(pcdBuildData
.getCName(),
2201 tokenSpaceStrRet
[1]);
2203 if (dbManager
.isTokenInDatabase(primaryKey
)) {
2207 pcdType
= Token
.getpcdTypeFromString(pcdBuildData
.getItemType().toString());
2208 if (pcdType
!= Token
.PCD_TYPE
.DYNAMIC_EX
) {
2209 throw new EntityException (String
.format("[FPD file error] It not allowed for DYNAMIC PCD %s who is no used by any module",
2210 pcdBuildData
.getCName()));
2214 // Create new token for unreference dynamic PCD token
2216 token
= new Token(pcdBuildData
.getCName(), tokenSpaceStrRet
[1]);
2217 token
.datumSize
= pcdBuildData
.getMaxDatumSize();
2220 token
.datumType
= Token
.getdatumTypeFromString(pcdBuildData
.getDatumType().toString());
2221 token
.tokenNumber
= Long
.decode(pcdBuildData
.getToken().toString());
2222 token
.dynamicExTokenNumber
= token
.tokenNumber
;
2223 token
.isDynamicPCD
= true;
2224 token
.updateSupportPcdType(pcdType
);
2226 exceptionString
= verifyDatum(token
.cName
,
2231 if (exceptionString
!= null) {
2232 throw new EntityException(exceptionString
);
2235 skuInfoList
= pcdBuildData
.getSkuInfoList();
2238 // Loop all sku data
2240 for (index
= 0; index
< skuInfoList
.size(); index
++) {
2241 skuInstance
= new SkuInstance();
2243 // Although SkuId in schema is BigInteger, but in fact, sku id is 32 bit value.
2245 temp
= skuInfoList
.get(index
).getSkuId().toString();
2246 skuInstance
.id
= Integer
.decode(temp
);
2247 if (skuInstance
.id
== 0) {
2251 // Judge whether is DefaultGroup at first, because most case is DefautlGroup.
2253 if (skuInfoList
.get(index
).getValue() != null) {
2254 skuInstance
.value
.setValue(skuInfoList
.get(index
).getValue().toString());
2255 if ((exceptionString
= verifyDatum(token
.cName
,
2257 skuInfoList
.get(index
).getValue().toString(),
2259 token
.datumSize
)) != null) {
2260 throw new EntityException(exceptionString
);
2263 token
.skuData
.add(skuInstance
);
2269 // Judge whether is HII group case.
2271 if (skuInfoList
.get(index
).getVariableName() != null) {
2272 exceptionString
= null;
2273 if (skuInfoList
.get(index
).getVariableGuid() == null) {
2274 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s in <DynamicPcdBuildDefinitions> section in FPD "+
2275 "file, who use HII, but there is no <VariableGuid> defined for Sku %d data!",
2278 if (exceptionString
!= null) {
2279 throw new EntityException(exceptionString
);
2283 if (skuInfoList
.get(index
).getVariableOffset() == null) {
2284 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s in <DynamicPcdBuildDefinitions> section in FPD "+
2285 "file, who use HII, but there is no <VariableOffset> defined for Sku %d data!",
2288 if (exceptionString
!= null) {
2289 throw new EntityException(exceptionString
);
2293 if (skuInfoList
.get(index
).getHiiDefaultValue() == null) {
2294 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s in <DynamicPcdBuildDefinitions> section in FPD "+
2295 "file, who use HII, but there is no <HiiDefaultValue> defined for Sku %d data!",
2298 if (exceptionString
!= null) {
2299 throw new EntityException(exceptionString
);
2303 if (skuInfoList
.get(index
).getHiiDefaultValue() != null) {
2304 hiiDefaultValue
= skuInfoList
.get(index
).getHiiDefaultValue().toString();
2306 hiiDefaultValue
= null;
2309 if ((exceptionString
= verifyDatum(token
.cName
,
2313 token
.datumSize
)) != null) {
2314 throw new EntityException(exceptionString
);
2317 offset
= Integer
.decode(skuInfoList
.get(index
).getVariableOffset());
2318 if (offset
> 0xFFFF) {
2319 throw new EntityException(String
.format("[FPD file error] For dynamic PCD %s , the variable offset defined in sku %d data "+
2320 "exceed 64K, it is not allowed!",
2326 // Get variable guid string according to the name of guid which will be mapped into a GUID in SPD file.
2328 variableGuidString
= GlobalData
.getGuidInfoFromCname(skuInfoList
.get(index
).getVariableGuid().toString());
2329 if (variableGuidString
== null) {
2330 throw new EntityException(String
.format("[GUID Error] For dynamic PCD %s, the variable guid %s can be found in all SPD file!",
2332 skuInfoList
.get(index
).getVariableGuid().toString()));
2334 String variableStr
= skuInfoList
.get(index
).getVariableName();
2335 Pattern pattern
= Pattern
.compile("0x([a-fA-F0-9]){4}");
2336 Matcher matcher
= pattern
.matcher(variableStr
);
2337 List
<String
> varNameList
= new ArrayList
<String
>();
2338 while (matcher
.find()){
2339 String str
= variableStr
.substring(matcher
.start(),matcher
.end());
2340 varNameList
.add(str
);
2343 skuInstance
.value
.setHiiData(varNameList
,
2344 translateSchemaStringToUUID(variableGuidString
[1]),
2345 skuInfoList
.get(index
).getVariableOffset(),
2346 skuInfoList
.get(index
).getHiiDefaultValue().toString());
2347 token
.skuData
.add(skuInstance
);
2351 if (skuInfoList
.get(index
).getVpdOffset() != null) {
2352 skuInstance
.value
.setVpdData(skuInfoList
.get(index
).getVpdOffset());
2353 token
.skuData
.add(skuInstance
);
2357 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s, the dynamic info must "+
2358 "be one of 'DefaultGroup', 'HIIGroup', 'VpdGroup'.",
2360 throw new EntityException(exceptionString
);
2364 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s in <DynamicPcdBuildDefinitions>, there are "+
2365 "no sku id = 0 data, which is required for every dynamic PCD",
2367 throw new EntityException(exceptionString
);
2370 tokenArray
.add(token
);
2377 Verify the datum value according its datum size and datum type, this
2378 function maybe moved to FPD verification tools in future.
2389 public String
verifyDatum(String cName
,
2392 Token
.DATUM_TYPE datumType
,
2394 String exceptionString
= null;
2400 if (moduleName
== null) {
2401 moduleName
= "section <DynamicPcdBuildDefinitions>";
2403 moduleName
= "module " + moduleName
;
2406 if (maxDatumSize
== 0) {
2407 exceptionString
= String
.format("[FPD file error] You maybe miss <MaxDatumSize> for PCD %s in %s",
2410 return exceptionString
;
2413 switch (datumType
) {
2415 if (maxDatumSize
!= 1) {
2416 exceptionString
= String
.format("[FPD file error] The datum type of PCD data %s in %s "+
2417 "is UINT8, but datum size is %d, they are not matched!",
2421 return exceptionString
;
2424 if (datum
!= null) {
2426 value
= Integer
.decode(datum
);
2427 } catch (NumberFormatException nfeExp
) {
2428 exceptionString
= String
.format("[FPD file error] The datum for PCD %s in %s is not valid "+
2429 "digital format of UINT8",
2432 return exceptionString
;
2435 exceptionString
= String
.format("[FPD file error] The datum for PCD %s in %s is %s exceed"+
2436 " the max size of UINT8 - 0xFF",
2440 return exceptionString
;
2445 if (maxDatumSize
!= 2) {
2446 exceptionString
= String
.format("[FPD file error] The datum type of PCD data %s in %s "+
2447 "is UINT16, but datum size is %d, they are not matched!",
2451 return exceptionString
;
2453 if (datum
!= null) {
2455 value
= Integer
.decode(datum
);
2456 } catch (NumberFormatException nfeExp
) {
2457 exceptionString
= String
.format("[FPD file error] The datum for PCD %s in %s is "+
2458 "not valid digital of UINT16",
2461 return exceptionString
;
2463 if (value
> 0xFFFF) {
2464 exceptionString
= String
.format("[FPD file error] The datum for PCD %s in %s is %s "+
2465 "which exceed the range of UINT16 - 0xFFFF",
2469 return exceptionString
;
2474 if (maxDatumSize
!= 4) {
2475 exceptionString
= String
.format("[FPD file error] The datum type of PCD data %s in %s "+
2476 "is UINT32, but datum size is %d, they are not matched!",
2480 return exceptionString
;
2483 if (datum
!= null) {
2485 if (datum
.length() > 2) {
2486 if ((datum
.charAt(0) == '0') &&
2487 ((datum
.charAt(1) == 'x') || (datum
.charAt(1) == 'X'))){
2488 subStr
= datum
.substring(2, datum
.length());
2489 value64
= new BigInteger(subStr
, 16);
2491 value64
= new BigInteger(datum
);
2494 value64
= new BigInteger(datum
);
2496 } catch (NumberFormatException nfeExp
) {
2497 exceptionString
= String
.format("[FPD file error] The datum for PCD %s in %s is not "+
2498 "valid digital of UINT32",
2501 return exceptionString
;
2504 if (value64
.bitLength() > 32) {
2505 exceptionString
= String
.format("[FPD file error] The datum for PCD %s in %s is %s which "+
2506 "exceed the range of UINT32 - 0xFFFFFFFF",
2510 return exceptionString
;
2515 if (maxDatumSize
!= 8) {
2516 exceptionString
= String
.format("[FPD file error] The datum type of PCD data %s in %s "+
2517 "is UINT64, but datum size is %d, they are not matched!",
2521 return exceptionString
;
2524 if (datum
!= null) {
2526 if (datum
.length() > 2) {
2527 if ((datum
.charAt(0) == '0') &&
2528 ((datum
.charAt(1) == 'x') || (datum
.charAt(1) == 'X'))){
2529 subStr
= datum
.substring(2, datum
.length());
2530 value64
= new BigInteger(subStr
, 16);
2532 value64
= new BigInteger(datum
);
2535 value64
= new BigInteger(datum
);
2537 } catch (NumberFormatException nfeExp
) {
2538 exceptionString
= String
.format("[FPD file error] The datum for PCD %s in %s is not valid"+
2539 " digital of UINT64",
2542 return exceptionString
;
2545 if (value64
.bitLength() > 64) {
2546 exceptionString
= String
.format("[FPD file error] The datum for PCD %s in %s is %s "+
2547 "exceed the range of UINT64 - 0xFFFFFFFFFFFFFFFF",
2551 return exceptionString
;
2556 if (maxDatumSize
!= 1) {
2557 exceptionString
= String
.format("[FPD file error] The datum type of PCD data %s in %s "+
2558 "is BOOLEAN, but datum size is %d, they are not matched!",
2562 return exceptionString
;
2565 if (datum
!= null) {
2566 if (!(datum
.equalsIgnoreCase("TRUE") ||
2567 datum
.equalsIgnoreCase("FALSE"))) {
2568 exceptionString
= String
.format("[FPD file error] The datum type of PCD data %s in %s "+
2569 "is BOOELAN, but value is not 'true'/'TRUE' or 'FALSE'/'false'",
2572 return exceptionString
;
2578 if (datum
== null) {
2582 char ch
= datum
.charAt(0);
2586 // For void* type PCD, only three datum is support:
2587 // 1) Unicode: string with start char is "L"
2588 // 2) Ansci: String start char is ""
2589 // 3) byte array: String start char "{"
2592 start
= datum
.indexOf('\"');
2593 end
= datum
.lastIndexOf('\"');
2594 if ((start
> end
) ||
2595 (end
> datum
.length())||
2596 ((start
== end
) && (datum
.length() > 0))) {
2597 exceptionString
= String
.format("[FPD file error] The datum type of PCD %s in %s is VOID* and datum is "+
2598 "a UNICODE string because start with L\", but format maybe"+
2599 "is not right, correct UNICODE string is L\"...\"!",
2602 return exceptionString
;
2605 strValue
= datum
.substring(start
+ 1, end
);
2606 if ((strValue
.length() * 2) > maxDatumSize
) {
2607 exceptionString
= String
.format("[FPD file error] The datum type of PCD %s in %s is VOID*, and datum is "+
2608 "a UNICODE string, but the datum size is %d exceed to <MaxDatumSize> : %d",
2611 strValue
.length() * 2,
2613 return exceptionString
;
2615 } else if (ch
== '\"'){
2616 start
= datum
.indexOf('\"');
2617 end
= datum
.lastIndexOf('\"');
2618 if ((start
> end
) ||
2619 (end
> datum
.length())||
2620 ((start
== end
) && (datum
.length() > 0))) {
2621 exceptionString
= String
.format("[FPD file error] The datum type of PCD %s in %s is VOID* and datum is "+
2622 "a ANSCII string because start with \", but format maybe"+
2623 "is not right, correct ANSIC string is \"...\"!",
2626 return exceptionString
;
2628 strValue
= datum
.substring(start
+ 1, end
);
2629 if ((strValue
.length()) > maxDatumSize
) {
2630 exceptionString
= String
.format("[FPD file error] The datum type of PCD %s in %s is VOID*, and datum is "+
2631 "a ANSCI string, but the datum size is %d which exceed to <MaxDatumSize> : %d",
2636 return exceptionString
;
2638 } else if (ch
=='{') {
2639 String
[] strValueArray
;
2641 start
= datum
.indexOf('{');
2642 end
= datum
.lastIndexOf('}');
2643 strValue
= datum
.substring(start
+ 1, end
);
2644 strValue
= strValue
.trim();
2645 if (strValue
.length() == 0) {
2646 exceptionString
= String
.format ("[FPD file error] The datum type of PCD %s in %s is VOID*, and "+
2647 "it is byte array in fact, but '{}' is not valid for NULL datam but"+
2651 return exceptionString
;
2653 strValueArray
= strValue
.split(",");
2654 for (index
= 0; index
< strValueArray
.length
; index
++) {
2656 value
= Integer
.decode(strValueArray
[index
].trim());
2657 } catch (NumberFormatException nfeEx
) {
2658 exceptionString
= String
.format("[FPD file error] The datum type of PCD %s in %s is VOID*, and "+
2659 "it is byte array in fact. For every byte in array should be a valid"+
2660 "byte digital, but element %s is not a valid byte digital!",
2663 strValueArray
[index
]);
2664 return exceptionString
;
2667 exceptionString
= String
.format("[FPD file error] The datum type of PCD %s in %s is VOID*, "+
2668 "it is byte array in fact. But the element of %s exceed the byte range",
2671 strValueArray
[index
]);
2672 return exceptionString
;
2676 if (strValueArray
.length
> maxDatumSize
) {
2677 exceptionString
= String
.format("[FPD file error] The datum type of PCD %s in %s is VOID*, and datum is byte"+
2678 "array, but the number of bytes is %d which exceed to <MaxDatumSzie> : %d!",
2681 strValueArray
.length
,
2683 return exceptionString
;
2686 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 "+
2687 "1) UNICODE string: like L\"xxxx\";\r\n"+
2688 "2) ANSIC string: like \"xxx\";\r\n"+
2689 "3) Byte array: like {0x2, 0x45, 0x23}\r\n"+
2690 "But the datum in seems does not following above format!",
2693 return exceptionString
;
2697 exceptionString
= String
.format("[FPD file error] For PCD entry %s in %s, datum type is unknown, it should be one of "+
2698 "UINT8, UINT16, UINT32, UINT64, VOID*, BOOLEAN",
2701 return exceptionString
;
2707 Get dynamic information for a dynamic PCD from <DynamicPcdBuildDefinition> seciton in FPD file.
2709 This function should be implemented in GlobalData in future.
2711 @param token The token instance which has hold module's PCD information
2712 @param moduleName The name of module who will use this Dynamic PCD.
2714 @return DynamicPcdBuildDefinitions.PcdBuildData
2717 private DynamicPcdBuildDefinitions
.PcdBuildData
getDynamicInfoFromFPD(Token token
,
2719 throws EntityException
{
2721 String exceptionString
= null;
2722 String dynamicPrimaryKey
= null;
2723 DynamicPcdBuildDefinitions dynamicPcdBuildDefinitions
= null;
2724 List
<DynamicPcdBuildDefinitions
.PcdBuildData
> dynamicPcdBuildDataArray
= null;
2725 String
[] tokenSpaceStrRet
= null;
2728 // If FPD document is not be opened, open and initialize it.
2729 // BUGBUG: The code should be moved into GlobalData in future.
2731 if (fpdDocInstance
== null) {
2733 fpdDocInstance
= (PlatformSurfaceAreaDocument
)XmlObject
.Factory
.parse(new File(fpdFilePath
));
2734 } catch(IOException ioE
) {
2735 throw new EntityException("File IO error for xml file:" + fpdFilePath
+ "\n" + ioE
.getMessage());
2736 } catch(XmlException xmlE
) {
2737 throw new EntityException("Can't parse the FPD xml fle:" + fpdFilePath
+ "\n" + xmlE
.getMessage());
2741 dynamicPcdBuildDefinitions
= fpdDocInstance
.getPlatformSurfaceArea().getDynamicPcdBuildDefinitions();
2742 if (dynamicPcdBuildDefinitions
== null) {
2743 exceptionString
= String
.format("[FPD file error] There are no <PcdDynamicBuildDescriptions> in FPD file but contains Dynamic type "+
2744 "PCD entry %s in module %s!",
2747 throw new EntityException(exceptionString
);
2750 dynamicPcdBuildDataArray
= dynamicPcdBuildDefinitions
.getPcdBuildDataList();
2751 for (index
= 0; index
< dynamicPcdBuildDataArray
.size(); index
++) {
2752 //String tokenSpaceGuidString = GlobalData.getGuidInfoFromCname(dynamicPcdBuildDataArray.get(index).getTokenSpaceGuidCName())[1];
2753 String tokenSpaceGuidString
= null;
2755 tokenSpaceStrRet
= GlobalData
.getGuidInfoFromCname(dynamicPcdBuildDataArray
.get(index
).getTokenSpaceGuidCName());
2756 } catch (Exception e
) {
2757 throw new EntityException ("Fail to get token space guid for token " + dynamicPcdBuildDataArray
.get(index
).getCName());
2760 if (tokenSpaceStrRet
== null) {
2761 throw new EntityException ("Fail to get token space guid for token " + dynamicPcdBuildDataArray
.get(index
).getCName());
2764 dynamicPrimaryKey
= Token
.getPrimaryKeyString(dynamicPcdBuildDataArray
.get(index
).getCName(),
2765 tokenSpaceStrRet
[1]);
2766 if (dynamicPrimaryKey
.equalsIgnoreCase(token
.getPrimaryKeyString())) {
2767 return dynamicPcdBuildDataArray
.get(index
);
2775 Update dynamic information for PCD entry.
2777 Dynamic information is retrieved from <PcdDynamicBuildDeclarations> in
2780 @param moduleName The name of the module who use this PCD
2781 @param token The token instance
2782 @param datum The <datum> in module's PCD information
2783 @param maxDatumSize The <maxDatumSize> in module's PCD information
2787 private Token
updateDynamicInformation(String moduleName
,
2791 throws EntityException
{
2794 String exceptionString
= null;
2795 DynamicTokenValue dynamicValue
;
2796 SkuInstance skuInstance
= null;
2798 boolean hasSkuId0
= false;
2799 Token
.PCD_TYPE pcdType
= Token
.PCD_TYPE
.UNKNOWN
;
2800 long tokenNumber
= 0;
2801 String hiiDefaultValue
= null;
2802 String
[] variableGuidString
= null;
2804 List
<DynamicPcdBuildDefinitions
.PcdBuildData
.SkuInfo
> skuInfoList
= null;
2805 DynamicPcdBuildDefinitions
.PcdBuildData dynamicInfo
= null;
2807 dynamicInfo
= getDynamicInfoFromFPD(token
, moduleName
);
2808 if (dynamicInfo
== null) {
2809 exceptionString
= String
.format("[FPD file error] For Dynamic PCD %s used by module %s, "+
2810 "there is no dynamic information in <DynamicPcdBuildDefinitions> "+
2811 "in FPD file, but it is required!",
2814 throw new EntityException(exceptionString
);
2817 token
.datumSize
= dynamicInfo
.getMaxDatumSize();
2819 exceptionString
= verifyDatum(token
.cName
,
2824 if (exceptionString
!= null) {
2825 throw new EntityException(exceptionString
);
2828 if ((maxDatumSize
!= 0) &&
2829 (maxDatumSize
!= token
.datumSize
)) {
2830 exceptionString
= String
.format("FPD file error] For dynamic PCD %s, the datum size in module %s is %d, but "+
2831 "the datum size in <DynamicPcdBuildDefinitions> is %d, they are not match!",
2835 dynamicInfo
.getMaxDatumSize());
2836 throw new EntityException(exceptionString
);
2838 tokenNumber
= Long
.decode(dynamicInfo
.getToken().toString());
2839 if (tokenNumber
!= token
.tokenNumber
) {
2840 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s, the token number in module %s is 0x%x, but"+
2841 "in <DynamicPcdBuildDefinictions>, the token number is 0x%x, they are not match!",
2846 throw new EntityException(exceptionString
);
2849 pcdType
= Token
.getpcdTypeFromString(dynamicInfo
.getItemType().toString());
2850 token
.dynamicExTokenNumber
= tokenNumber
;
2852 skuInfoList
= dynamicInfo
.getSkuInfoList();
2855 // Loop all sku data
2857 for (index
= 0; index
< skuInfoList
.size(); index
++) {
2858 skuInstance
= new SkuInstance();
2860 // Although SkuId in schema is BigInteger, but in fact, sku id is 32 bit value.
2862 temp
= skuInfoList
.get(index
).getSkuId().toString();
2863 skuInstance
.id
= Integer
.decode(temp
);
2864 if (skuInstance
.id
== 0) {
2868 // Judge whether is DefaultGroup at first, because most case is DefautlGroup.
2870 if (skuInfoList
.get(index
).getValue() != null) {
2871 skuInstance
.value
.setValue(skuInfoList
.get(index
).getValue().toString());
2872 if ((exceptionString
= verifyDatum(token
.cName
,
2874 skuInfoList
.get(index
).getValue().toString(),
2876 token
.datumSize
)) != null) {
2877 throw new EntityException(exceptionString
);
2880 token
.skuData
.add(skuInstance
);
2883 // Judege wether is same of datum between module's information
2884 // and dynamic information.
2886 if (datum
!= null) {
2887 if ((skuInstance
.id
== 0) &&
2888 !datum
.toString().equalsIgnoreCase(skuInfoList
.get(index
).getValue().toString())) {
2889 exceptionString
= "[FPD file error] For dynamic PCD " + token
.cName
+ ", the value in module " + moduleName
+ " is " + datum
.toString() + " but the "+
2890 "value of sku 0 data in <DynamicPcdBuildDefinition> is " + skuInstance
.value
.value
+ ". They are must be same!"+
2891 " or you could not define value for a dynamic PCD in every <ModuleSA>!";
2892 throw new EntityException(exceptionString
);
2899 // Judge whether is HII group case.
2901 if (skuInfoList
.get(index
).getVariableName() != null) {
2902 exceptionString
= null;
2903 if (skuInfoList
.get(index
).getVariableGuid() == null) {
2904 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s in <DynamicPcdBuildDefinitions> section in FPD "+
2905 "file, who use HII, but there is no <VariableGuid> defined for Sku %d data!",
2908 if (exceptionString
!= null) {
2909 throw new EntityException(exceptionString
);
2913 if (skuInfoList
.get(index
).getVariableOffset() == null) {
2914 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s in <DynamicPcdBuildDefinitions> section in FPD "+
2915 "file, who use HII, but there is no <VariableOffset> defined for Sku %d data!",
2918 if (exceptionString
!= null) {
2919 throw new EntityException(exceptionString
);
2923 if (skuInfoList
.get(index
).getHiiDefaultValue() == null) {
2924 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s in <DynamicPcdBuildDefinitions> section in FPD "+
2925 "file, who use HII, but there is no <HiiDefaultValue> defined for Sku %d data!",
2928 if (exceptionString
!= null) {
2929 throw new EntityException(exceptionString
);
2933 if (skuInfoList
.get(index
).getHiiDefaultValue() != null) {
2934 hiiDefaultValue
= skuInfoList
.get(index
).getHiiDefaultValue().toString();
2936 hiiDefaultValue
= null;
2939 if ((exceptionString
= verifyDatum(token
.cName
,
2943 token
.datumSize
)) != null) {
2944 throw new EntityException(exceptionString
);
2947 offset
= Integer
.decode(skuInfoList
.get(index
).getVariableOffset());
2948 if (offset
> 0xFFFF) {
2949 throw new EntityException(String
.format("[FPD file error] For dynamic PCD %s , the variable offset defined in sku %d data "+
2950 "exceed 64K, it is not allowed!",
2956 // Get variable guid string according to the name of guid which will be mapped into a GUID in SPD file.
2958 variableGuidString
= GlobalData
.getGuidInfoFromCname(skuInfoList
.get(index
).getVariableGuid().toString());
2959 if (variableGuidString
== null) {
2960 throw new EntityException(String
.format("[GUID Error] For dynamic PCD %s, the variable guid %s can be found in all SPD file!",
2962 skuInfoList
.get(index
).getVariableGuid().toString()));
2964 String variableStr
= skuInfoList
.get(index
).getVariableName();
2965 Pattern pattern
= Pattern
.compile("0x([a-fA-F0-9]){4}");
2966 Matcher matcher
= pattern
.matcher(variableStr
);
2967 List
<String
> varNameList
= new ArrayList
<String
>();
2968 while (matcher
.find()){
2969 String str
= variableStr
.substring(matcher
.start(),matcher
.end());
2970 varNameList
.add(str
);
2973 skuInstance
.value
.setHiiData(varNameList
,
2974 translateSchemaStringToUUID(variableGuidString
[1]),
2975 skuInfoList
.get(index
).getVariableOffset(),
2976 skuInfoList
.get(index
).getHiiDefaultValue().toString());
2977 token
.skuData
.add(skuInstance
);
2981 if (skuInfoList
.get(index
).getVpdOffset() != null) {
2982 skuInstance
.value
.setVpdData(skuInfoList
.get(index
).getVpdOffset());
2983 token
.skuData
.add(skuInstance
);
2987 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s, the dynamic info must "+
2988 "be one of 'DefaultGroup', 'HIIGroup', 'VpdGroup'.",
2990 throw new EntityException(exceptionString
);
2994 exceptionString
= String
.format("[FPD file error] For dynamic PCD %s in <DynamicPcdBuildDefinitions>, there are "+
2995 "no sku id = 0 data, which is required for every dynamic PCD",
2997 throw new EntityException(exceptionString
);
3004 Translate the schema string to UUID instance.
3006 In schema, the string of UUID is defined as following two types string:
3007 1) GuidArrayType: pattern = 0x[a-fA-F0-9]{1,8},( )*0x[a-fA-F0-9]{1,4},(
3008 )*0x[a-fA-F0-9]{1,4}(,( )*\{)?(,?( )*0x[a-fA-F0-9]{1,2}){8}( )*(\})?
3010 2) GuidNamingConvention: pattern =
3011 [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}
3013 This function will convert string and create uuid instance.
3015 @param uuidString UUID string in XML file
3017 @return UUID UUID instance
3019 private UUID
translateSchemaStringToUUID(String uuidString
)
3020 throws EntityException
{
3022 String
[] splitStringArray
;
3027 if (uuidString
== null) {
3031 if (uuidString
.length() == 0) {
3035 if (uuidString
.equals("0") ||
3036 uuidString
.equalsIgnoreCase("0x0")) {
3037 return new UUID(0, 0);
3040 uuidString
= uuidString
.replaceAll("\\{", "");
3041 uuidString
= uuidString
.replaceAll("\\}", "");
3044 // If the UUID schema string is GuidArrayType type then need translate
3045 // to GuidNamingConvention type at first.
3047 if ((uuidString
.charAt(0) == '0') && ((uuidString
.charAt(1) == 'x') || (uuidString
.charAt(1) == 'X'))) {
3048 splitStringArray
= uuidString
.split("," );
3049 if (splitStringArray
.length
!= 11) {
3050 throw new EntityException ("[FPD file error] Wrong format for UUID string: " + uuidString
);
3054 // Remove blank space from these string and remove header string "0x"
3056 for (index
= 0; index
< 11; index
++) {
3057 splitStringArray
[index
] = splitStringArray
[index
].trim();
3058 splitStringArray
[index
] = splitStringArray
[index
].substring(2, splitStringArray
[index
].length());
3062 // Add heading '0' to normalize the string length
3064 for (index
= 3; index
< 11; index
++) {
3065 chLen
= splitStringArray
[index
].length();
3066 for (chIndex
= 0; chIndex
< 2 - chLen
; chIndex
++) {
3067 splitStringArray
[index
] = "0" + splitStringArray
[index
];
3072 // construct the final GuidNamingConvention string
3074 temp
= String
.format("%s-%s-%s-%s%s-%s%s%s%s%s%s",
3075 splitStringArray
[0],
3076 splitStringArray
[1],
3077 splitStringArray
[2],
3078 splitStringArray
[3],
3079 splitStringArray
[4],
3080 splitStringArray
[5],
3081 splitStringArray
[6],
3082 splitStringArray
[7],
3083 splitStringArray
[8],
3084 splitStringArray
[9],
3085 splitStringArray
[10]);
3089 return UUID
.fromString(uuidString
);
3093 check parameter for this action.
3095 @throws EntityException Bad parameter.
3097 private void checkParameter() throws EntityException
{
3100 if((fpdFilePath
== null) ||(workspacePath
== null)) {
3101 throw new EntityException("WorkspacePath and FPDFileName should be blank for CollectPCDAtion!");
3104 if(fpdFilePath
.length() == 0 || workspacePath
.length() == 0) {
3105 throw new EntityException("WorkspacePath and FPDFileName should be blank for CollectPCDAtion!");
3108 file
= new File(workspacePath
);
3109 if(!file
.exists()) {
3110 throw new EntityException("WorkpacePath " + workspacePath
+ " does not exist!");
3113 file
= new File(fpdFilePath
);
3115 if(!file
.exists()) {
3116 throw new EntityException("FPD File " + fpdFilePath
+ " does not exist!");
3123 @param argv parameter from command line
3125 public static void main(String argv
[]) throws EntityException
{
3126 CollectPCDAction ca
= new CollectPCDAction();
3127 String projectDir
= "x:/edk2";
3128 ca
.setWorkspacePath(projectDir
);
3129 ca
.setFPDFilePath(projectDir
+ "/EdkNt32Pkg/Nt32.fpd");
3130 ca
.setActionMessageLevel(ActionMessage
.MAX_MESSAGE_LEVEL
);
3131 GlobalData
.initInfo("Tools" + File
.separator
+ "Conf" + File
.separator
+ "FrameworkDatabase.db",
3134 System
.out
.println("After initInfo!");
3135 FpdParserTask fpt
= new FpdParserTask();
3136 fpt
.parseFpdFile(new File(projectDir
+ "/EdkNt32Pkg/Nt32.fpd"));