]> git.proxmox.com Git - mirror_edk2.git/blobdiff - BaseTools/Source/Python/Workspace/WorkspaceDatabase.py
Sync BaseTools Branch (version r2362) to EDKII main trunk.
[mirror_edk2.git] / BaseTools / Source / Python / Workspace / WorkspaceDatabase.py
index 12c3324b8dfa834321116cc11e10007219308821..ac2ca057ccdf9682ac5e51e2a2895a70ae77db84 100644 (file)
@@ -1,7 +1,7 @@
 ## @file\r
 # This file is used to create a database used by build tool\r
 #\r
-# Copyright (c) 2008 - 2010, Intel Corporation. All rights reserved.<BR>\r
+# Copyright (c) 2008 - 2011, Intel Corporation. All rights reserved.<BR>\r
 # This program and the accompanying materials\r
 # are licensed and made available under the terms and conditions of the BSD License\r
 # which accompanies this distribution.  The full text of the license may be found at\r
@@ -18,6 +18,7 @@ import sqlite3
 import os\r
 import os.path\r
 import pickle\r
+import uuid\r
 \r
 import Common.EdkLogger as EdkLogger\r
 import Common.GlobalData as GlobalData\r
@@ -73,6 +74,8 @@ class DscBuildData(PlatformBuildClassObject):
         TAB_DSC_DEFINES_MAKEFILE_NAME           :   "_MakefileName",\r
         TAB_DSC_DEFINES_BS_BASE_ADDRESS         :   "_BsBaseAddress",\r
         TAB_DSC_DEFINES_RT_BASE_ADDRESS         :   "_RtBaseAddress",\r
+        #TAB_DSC_DEFINES_RFC_LANGUAGES           :   "_RFCLanguages",\r
+        #TAB_DSC_DEFINES_ISO_LANGUAGES           :   "_ISOLanguages",\r
     }\r
 \r
     # used to compose dummy library class name for those forced library instances\r
@@ -99,6 +102,10 @@ class DscBuildData(PlatformBuildClassObject):
         RecordList = self._RawData[MODEL_META_DATA_DEFINE, self._Arch]\r
         for Record in RecordList:\r
             GlobalData.gEdkGlobal[Record[0]] = Record[1]\r
+        \r
+        RecordList = self._RawData[MODEL_META_DATA_GLOBAL_DEFINE, self._Arch]\r
+        for Record in RecordList:\r
+            GlobalData.gGlobalDefines[Record[0]] = Record[1]\r
 \r
     ## XXX[key] = value\r
     def __setitem__(self, key, value):\r
@@ -135,6 +142,9 @@ class DscBuildData(PlatformBuildClassObject):
         self._Pcds              = None\r
         self._BuildOptions      = None\r
         self._LoadFixAddress    = None\r
+        self._RFCLanguages      = None\r
+        self._ISOLanguages      = None\r
+        self._VpdToolGuid       = None\r
 \r
     ## Get architecture\r
     def _GetArch(self):\r
@@ -188,6 +198,45 @@ class DscBuildData(PlatformBuildClassObject):
                     self._SkuName = Record[1]\r
             elif Name == TAB_FIX_LOAD_TOP_MEMORY_ADDRESS:\r
                 self._LoadFixAddress = Record[1]\r
+            elif Name == TAB_DSC_DEFINES_RFC_LANGUAGES:\r
+                if not Record[1] or Record[1][0] != '"' or Record[1][-1] != '"' or len(Record[1]) == 1:\r
+                    EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'language code for RFC_LANGUAGES must have double quotes around it, for example: RFC_LANGUAGES = "en-us;zh-hans"',\r
+                                    File=self.MetaFile, Line=Record[-1])\r
+                LanguageCodes = Record[1][1:-1]\r
+                if not LanguageCodes:\r
+                    EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'one or more RFC4646 format language code must be provided for RFC_LANGUAGES statement',\r
+                                    File=self.MetaFile, Line=Record[-1])                \r
+                LanguageList = GetSplitValueList(LanguageCodes, TAB_SEMI_COLON_SPLIT)\r
+                # check whether there is empty entries in the list\r
+                if None in LanguageList:\r
+                    EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'one or more empty language code is in RFC_LANGUAGES statement',\r
+                                    File=self.MetaFile, Line=Record[-1])                      \r
+                self._RFCLanguages = LanguageList\r
+            elif Name == TAB_DSC_DEFINES_ISO_LANGUAGES:\r
+                if not Record[1] or Record[1][0] != '"' or Record[1][-1] != '"' or len(Record[1]) == 1:\r
+                    EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'language code for ISO_LANGUAGES must have double quotes around it, for example: ISO_LANGUAGES = "engchn"',\r
+                                    File=self.MetaFile, Line=Record[-1])\r
+                LanguageCodes = Record[1][1:-1]\r
+                if not LanguageCodes:\r
+                    EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'one or more ISO639-2 format language code must be provided for ISO_LANGUAGES statement',\r
+                                    File=self.MetaFile, Line=Record[-1])                    \r
+                if len(LanguageCodes)%3:\r
+                    EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'bad ISO639-2 format for ISO_LANGUAGES',\r
+                                    File=self.MetaFile, Line=Record[-1])\r
+                LanguageList = []\r
+                for i in range(0, len(LanguageCodes), 3):\r
+                    LanguageList.append(LanguageCodes[i:i+3])\r
+                self._ISOLanguages = LanguageList               \r
+            elif Name == TAB_DSC_DEFINES_VPD_TOOL_GUID:\r
+                #\r
+                # try to convert GUID to a real UUID value to see whether the GUID is format \r
+                # for VPD_TOOL_GUID is correct.\r
+                #\r
+                try:\r
+                    uuid.UUID(Record[1])\r
+                except:\r
+                    EdkLogger.error("build", FORMAT_INVALID, "Invalid GUID format for VPD_TOOL_GUID", File=self.MetaFile)\r
+                self._VpdToolGuid = Record[1]                   \r
         # set _Header to non-None in order to avoid database re-querying\r
         self._Header = 'DUMMY'\r
 \r
@@ -251,7 +300,7 @@ class DscBuildData(PlatformBuildClassObject):
             if self._Header == None:\r
                 self._GetHeaderInfo()\r
             if self._BuildTargets == None:\r
-                self._BuildTargets = ['DEBUG', 'RELEASE']\r
+                self._BuildTargets = ['DEBUG', 'RELEASE', 'NOOPT']\r
         return self._BuildTargets\r
 \r
     ## Retrieve SKUID_IDENTIFIER\r
@@ -267,6 +316,8 @@ class DscBuildData(PlatformBuildClassObject):
     def _SetSkuName(self, Value):\r
         if Value in self.SkuIds:\r
             self._SkuName = Value\r
+            # Needs to re-retrieve the PCD information\r
+            self._Pcds = None\r
 \r
     def _GetFdfFile(self):\r
         if self._FlashDefinition == None:\r
@@ -321,6 +372,33 @@ class DscBuildData(PlatformBuildClassObject):
                 self._LoadFixAddress = ''\r
         return self._LoadFixAddress\r
 \r
+    ## Retrieve RFCLanguage filter\r
+    def _GetRFCLanguages(self):\r
+        if self._RFCLanguages == None:\r
+            if self._Header == None:\r
+                self._GetHeaderInfo()\r
+            if self._RFCLanguages == None:\r
+                self._RFCLanguages = []\r
+        return self._RFCLanguages\r
+\r
+    ## Retrieve ISOLanguage filter\r
+    def _GetISOLanguages(self):\r
+        if self._ISOLanguages == None:\r
+            if self._Header == None:\r
+                self._GetHeaderInfo()\r
+            if self._ISOLanguages == None:\r
+                self._ISOLanguages = []\r
+        return self._ISOLanguages\r
+\r
+    ## Retrieve the GUID string for VPD tool\r
+    def _GetVpdToolGuid(self):\r
+        if self._VpdToolGuid == None:\r
+            if self._Header == None:\r
+                self._GetHeaderInfo()\r
+            if self._VpdToolGuid == None:\r
+                self._VpdToolGuid = ''\r
+        return self._VpdToolGuid\r
+      \r
     ## Retrieve [SkuIds] section information\r
     def _GetSkuIds(self):\r
         if self._SkuIds == None:\r
@@ -418,6 +496,7 @@ class DscBuildData(PlatformBuildClassObject):
                             '',\r
                             MaxDatumSize,\r
                             {},\r
+                            False,\r
                             None\r
                             )\r
                     Module.Pcds[PcdCName, TokenSpaceGuid] = Pcd\r
@@ -485,7 +564,7 @@ class DscBuildData(PlatformBuildClassObject):
                         continue\r
                     self._LibraryClasses[LibraryClass, ModuleType] = LibraryInstance\r
 \r
-            # for R8 style library instances, which are listed in different section\r
+            # for EDK style library instances, which are listed in different section\r
             RecordList = self._RawData[MODEL_EFI_LIBRARY_INSTANCE, self._Arch]\r
             for Record in RecordList:\r
                 File = PathClass(NormPath(Record[0], Macros), GlobalData.gWorkspace, Arch=self._Arch)\r
@@ -560,13 +639,10 @@ class DscBuildData(PlatformBuildClassObject):
             PcdDict[Arch, PcdCName, TokenSpaceGuid] = Setting\r
         # Remove redundant PCD candidates\r
         for PcdCName, TokenSpaceGuid in PcdSet:\r
-            ValueList = ['', '', '']\r
             Setting = PcdDict[self._Arch, PcdCName, TokenSpaceGuid]\r
             if Setting == None:\r
                 continue\r
-            TokenList = Setting.split(TAB_VALUE_SPLIT)\r
-            ValueList[0:len(TokenList)] = TokenList\r
-            PcdValue, DatumType, MaxDatumSize = ValueList\r
+            PcdValue, DatumType, MaxDatumSize = AnalyzePcdData(Setting)\r
             Pcds[PcdCName, TokenSpaceGuid] = PcdClassObject(\r
                                                 PcdCName,\r
                                                 TokenSpaceGuid,\r
@@ -576,6 +652,7 @@ class DscBuildData(PlatformBuildClassObject):
                                                 '',\r
                                                 MaxDatumSize,\r
                                                 {},\r
+                                                False,\r
                                                 None\r
                                                 )\r
         return Pcds\r
@@ -593,22 +670,20 @@ class DscBuildData(PlatformBuildClassObject):
         # PCD settings for certain ARCH and SKU\r
         #\r
         PcdDict = tdict(True, 4)\r
-        PcdSet = set()\r
+        PcdList = []\r
         # Find out all possible PCD candidates for self._Arch\r
         RecordList = self._RawData[Type, self._Arch]\r
         for TokenSpaceGuid, PcdCName, Setting, Arch, SkuName, Dummy3, Dummy4 in RecordList:\r
-            PcdSet.add((PcdCName, TokenSpaceGuid))\r
+            PcdList.append((PcdCName, TokenSpaceGuid))\r
             PcdDict[Arch, SkuName, PcdCName, TokenSpaceGuid] = Setting\r
         # Remove redundant PCD candidates, per the ARCH and SKU\r
-        for PcdCName, TokenSpaceGuid in PcdSet:\r
-            ValueList = ['', '', '']\r
+        for PcdCName, TokenSpaceGuid in PcdList:\r
             Setting = PcdDict[self._Arch, self.SkuName, PcdCName, TokenSpaceGuid]\r
             if Setting == None:\r
                 continue\r
-            TokenList = Setting.split(TAB_VALUE_SPLIT)\r
-            ValueList[0:len(TokenList)] = TokenList\r
-            PcdValue, DatumType, MaxDatumSize = ValueList\r
-\r
+                      \r
+            PcdValue, DatumType, MaxDatumSize = AnalyzePcdData(Setting)\r
+                \r
             SkuInfo = SkuInfoClass(self.SkuName, self.SkuIds[self.SkuName], '', '', '', '', '', PcdValue)\r
             Pcds[PcdCName, TokenSpaceGuid] = PcdClassObject(\r
                                                 PcdCName,\r
@@ -619,6 +694,7 @@ class DscBuildData(PlatformBuildClassObject):
                                                 '',\r
                                                 MaxDatumSize,\r
                                                 {self.SkuName : SkuInfo},\r
+                                                False,\r
                                                 None\r
                                                 )\r
         return Pcds\r
@@ -644,13 +720,10 @@ class DscBuildData(PlatformBuildClassObject):
             PcdDict[Arch, SkuName, PcdCName, TokenSpaceGuid] = Setting\r
         # Remove redundant PCD candidates, per the ARCH and SKU\r
         for PcdCName, TokenSpaceGuid in PcdSet:\r
-            ValueList = ['', '', '', '']\r
             Setting = PcdDict[self._Arch, self.SkuName, PcdCName, TokenSpaceGuid]\r
             if Setting == None:\r
                 continue\r
-            TokenList = Setting.split(TAB_VALUE_SPLIT)\r
-            ValueList[0:len(TokenList)] = TokenList\r
-            VariableName, VariableGuid, VariableOffset, DefaultValue = ValueList\r
+            VariableName, VariableGuid, VariableOffset, DefaultValue = AnalyzeHiiPcdData(Setting)\r
             SkuInfo = SkuInfoClass(self.SkuName, self.SkuIds[self.SkuName], VariableName, VariableGuid, VariableOffset, DefaultValue)\r
             Pcds[PcdCName, TokenSpaceGuid] = PcdClassObject(\r
                                                 PcdCName,\r
@@ -661,6 +734,7 @@ class DscBuildData(PlatformBuildClassObject):
                                                 '',\r
                                                 '',\r
                                                 {self.SkuName : SkuInfo},\r
+                                                False,\r
                                                 None\r
                                                 )\r
         return Pcds\r
@@ -678,23 +752,26 @@ class DscBuildData(PlatformBuildClassObject):
         # PCD settings for certain ARCH and SKU\r
         #\r
         PcdDict = tdict(True, 4)\r
-        PcdSet = set()\r
+        PcdList = []\r
         # Find out all possible PCD candidates for self._Arch\r
         RecordList = self._RawData[Type, self._Arch]\r
         for TokenSpaceGuid, PcdCName, Setting, Arch, SkuName, Dummy3, Dummy4 in RecordList:\r
-            PcdSet.add((PcdCName, TokenSpaceGuid))\r
+            PcdList.append((PcdCName, TokenSpaceGuid))\r
             PcdDict[Arch, SkuName, PcdCName, TokenSpaceGuid] = Setting\r
         # Remove redundant PCD candidates, per the ARCH and SKU\r
-        for PcdCName, TokenSpaceGuid in PcdSet:\r
-            ValueList = ['', '']\r
+        for PcdCName, TokenSpaceGuid in PcdList:\r
             Setting = PcdDict[self._Arch, self.SkuName, PcdCName, TokenSpaceGuid]\r
             if Setting == None:\r
                 continue\r
-            TokenList = Setting.split(TAB_VALUE_SPLIT)\r
-            ValueList[0:len(TokenList)] = TokenList\r
-            VpdOffset, MaxDatumSize = ValueList\r
-\r
-            SkuInfo = SkuInfoClass(self.SkuName, self.SkuIds[self.SkuName], '', '', '', '', VpdOffset)\r
+            #\r
+            # For the VOID* type, it can have optional data of MaxDatumSize and InitialValue\r
+            # For the Integer & Boolean type, the optional data can only be InitialValue.\r
+            # At this point, we put all the data into the PcdClssObject for we don't know the PCD's datumtype\r
+            # until the DEC parser has been called.\r
+            # \r
+            VpdOffset, MaxDatumSize, InitialValue = AnalyzeVpdPcdData(Setting)\r
+\r
+            SkuInfo = SkuInfoClass(self.SkuName, self.SkuIds[self.SkuName], '', '', '', '', VpdOffset, InitialValue)\r
             Pcds[PcdCName, TokenSpaceGuid] = PcdClassObject(\r
                                                 PcdCName,\r
                                                 TokenSpaceGuid,\r
@@ -704,6 +781,7 @@ class DscBuildData(PlatformBuildClassObject):
                                                 '',\r
                                                 MaxDatumSize,\r
                                                 {self.SkuName : SkuInfo},\r
+                                                False,\r
                                                 None\r
                                                 )\r
         return Pcds\r
@@ -733,7 +811,7 @@ class DscBuildData(PlatformBuildClassObject):
     #\r
     def AddPcd(self, Name, Guid, Value):\r
         if (Name, Guid) not in self.Pcds:\r
-            self.Pcds[Name, Guid] = PcdClassObject(Name, Guid, '', '', '', '', '', {}, None)\r
+            self.Pcds[Name, Guid] = PcdClassObject(Name, Guid, '', '', '', '', '', {}, False, None)\r
         self.Pcds[Name, Guid].DefaultValue = Value\r
 \r
     Arch                = property(_GetArch, _SetArch)\r
@@ -752,7 +830,9 @@ class DscBuildData(PlatformBuildClassObject):
     BsBaseAddress       = property(_GetBsBaseAddress)\r
     RtBaseAddress       = property(_GetRtBaseAddress)\r
     LoadFixAddress      = property(_GetLoadFixAddress)\r
-\r
+    RFCLanguages        = property(_GetRFCLanguages)\r
+    ISOLanguages        = property(_GetISOLanguages)\r
+    VpdToolGuid         = property(_GetVpdToolGuid)   \r
     SkuIds              = property(_GetSkuIds)\r
     Modules             = property(_GetModules)\r
     LibraryInstances    = property(_GetLibraryInstances)\r
@@ -760,7 +840,7 @@ class DscBuildData(PlatformBuildClassObject):
     Pcds                = property(_GetPcds)\r
     BuildOptions        = property(_GetBuildOptions)\r
 \r
-## Platform build information from DSC file\r
+## Platform build information from DEC file\r
 #\r
 #  This class is used to retrieve information stored in database and convert them\r
 # into PackageBuildClassObject form for easier use for AutoGen.\r
@@ -789,6 +869,7 @@ class DecBuildData(PackageBuildClassObject):
         TAB_DEC_DEFINES_PACKAGE_NAME                : "_PackageName",\r
         TAB_DEC_DEFINES_PACKAGE_GUID                : "_Guid",\r
         TAB_DEC_DEFINES_PACKAGE_VERSION             : "_Version",\r
+        TAB_DEC_DEFINES_PKG_UNI_FILE                : "_PkgUniFile",\r
     }\r
 \r
 \r
@@ -830,6 +911,7 @@ class DecBuildData(PackageBuildClassObject):
         self._PackageName       = None\r
         self._Guid              = None\r
         self._Version           = None\r
+        self._PkgUniFile        = None\r
         self._Protocols         = None\r
         self._Ppis              = None\r
         self._Guids             = None\r
@@ -1043,7 +1125,6 @@ class DecBuildData(PackageBuildClassObject):
             PcdSet.add((PcdCName, TokenSpaceGuid))\r
 \r
         for PcdCName, TokenSpaceGuid in PcdSet:\r
-            ValueList = ['', '', '']\r
             #\r
             # limit the ARCH to self._Arch, if no self._Arch found, tdict\r
             # will automatically turn to 'common' ARCH and try again\r
@@ -1051,9 +1132,9 @@ class DecBuildData(PackageBuildClassObject):
             Setting = PcdDict[self._Arch, PcdCName, TokenSpaceGuid]\r
             if Setting == None:\r
                 continue\r
-            TokenList = Setting.split(TAB_VALUE_SPLIT)\r
-            ValueList[0:len(TokenList)] = TokenList\r
-            DefaultValue, DatumType, TokenNumber = ValueList\r
+\r
+            DefaultValue, DatumType, TokenNumber = AnalyzePcdData(Setting)\r
+                                       \r
             Pcds[PcdCName, TokenSpaceGuid, self._PCD_TYPE_STRING_[Type]] = PcdClassObject(\r
                                                                             PcdCName,\r
                                                                             TokenSpaceGuid,\r
@@ -1063,6 +1144,7 @@ class DecBuildData(PackageBuildClassObject):
                                                                             TokenNumber,\r
                                                                             '',\r
                                                                             {},\r
+                                                                            False,\r
                                                                             None\r
                                                                             )\r
         return Pcds\r
@@ -1116,6 +1198,7 @@ class InfBuildData(ModuleBuildClassObject):
         TAB_INF_DEFINES_COMPONENT_TYPE              : "_ComponentType",\r
         TAB_INF_DEFINES_MAKEFILE_NAME               : "_MakefileName",\r
         #TAB_INF_DEFINES_CUSTOM_MAKEFILE             : "_CustomMakefile",\r
+        TAB_INF_DEFINES_DPX_SOURCE                  :"_DxsFile",\r
         TAB_INF_DEFINES_VERSION_NUMBER              : "_Version",\r
         TAB_INF_DEFINES_VERSION_STRING              : "_Version",\r
         TAB_INF_DEFINES_VERSION                     : "_Version",\r
@@ -1196,6 +1279,7 @@ class InfBuildData(ModuleBuildClassObject):
         self._Header_               = None\r
         self._AutoGenVersion        = None\r
         self._BaseName              = None\r
+        self._DxsFile               = None\r
         self._ModuleType            = None\r
         self._ComponentType         = None\r
         self._BuildType             = None\r
@@ -1276,18 +1360,16 @@ class InfBuildData(ModuleBuildClassObject):
             if Name in self:\r
                 self[Name] = Record[1]\r
             # some special items in [Defines] section need special treatment\r
-            elif Name in ('EFI_SPECIFICATION_VERSION', 'UEFI_SPECIFICATION_VERSION'):\r
+            elif Name in ('EFI_SPECIFICATION_VERSION', 'UEFI_SPECIFICATION_VERSION', 'EDK_RELEASE_VERSION', 'PI_SPECIFICATION_VERSION'):\r
+                if Name in ('EFI_SPECIFICATION_VERSION', 'UEFI_SPECIFICATION_VERSION'):\r
+                    Name = 'UEFI_SPECIFICATION_VERSION'\r
                 if self._Specification == None:\r
                     self._Specification = sdict()\r
-                self._Specification['UEFI_SPECIFICATION_VERSION'] = Record[1]\r
-            elif Name == 'EDK_RELEASE_VERSION':\r
-                if self._Specification == None:\r
-                    self._Specification = sdict()\r
-                self._Specification[Name] = Record[1]\r
-            elif Name == 'PI_SPECIFICATION_VERSION':\r
-                if self._Specification == None:\r
-                    self._Specification = sdict()\r
-                self._Specification[Name] = Record[1]\r
+                self._Specification[Name] = GetHexVerValue(Record[1])\r
+                if self._Specification[Name] == None:\r
+                    EdkLogger.error("build", FORMAT_NOT_SUPPORTED,\r
+                                    "'%s' format is not supported for %s" % (Record[1], Name),\r
+                                    File=self.MetaFile, Line=Record[-1])\r
             elif Name == 'LIBRARY_CLASS':\r
                 if self._LibraryClass == None:\r
                     self._LibraryClass = []\r
@@ -1339,13 +1421,23 @@ class InfBuildData(ModuleBuildClassObject):
                 self._Defs[Name] = Record[1]\r
 \r
         #\r
-        # Retrieve information in sections specific to R8.x modules\r
+        # Retrieve information in sections specific to EDK.x modules\r
         #\r
         if self._AutoGenVersion >= 0x00010005:   # _AutoGenVersion may be None, which is less than anything\r
             if not self._ModuleType:\r
                 EdkLogger.error("build", ATTRIBUTE_NOT_AVAILABLE,\r
                                 "MODULE_TYPE is not given", File=self.MetaFile)\r
-            if (self._Specification == None) or (not 'PI_SPECIFICATION_VERSION' in self._Specification) or (self._Specification['PI_SPECIFICATION_VERSION'] < 0x0001000A):\r
+            if self._ModuleType not in SUP_MODULE_LIST:\r
+                RecordList = self._RawData[MODEL_META_DATA_HEADER, self._Arch, self._Platform]\r
+                for Record in RecordList:\r
+                    Name = Record[0]\r
+                    if Name == "MODULE_TYPE":\r
+                        LineNo = Record[6]\r
+                        break\r
+                EdkLogger.error("build", FORMAT_NOT_SUPPORTED,\r
+                                "MODULE_TYPE %s is not supported for EDK II, valid values are:\n %s" % (self._ModuleType,' '.join(l for l in SUP_MODULE_LIST)), \r
+                                File=self.MetaFile, Line=LineNo)             \r
+            if (self._Specification == None) or (not 'PI_SPECIFICATION_VERSION' in self._Specification) or (int(self._Specification['PI_SPECIFICATION_VERSION'], 16) < 0x0001000A):\r
                 if self._ModuleType == SUP_MODULE_SMM_CORE:\r
                     EdkLogger.error("build", FORMAT_NOT_SUPPORTED, "SMM_CORE module type can't be used in the module with PI_SPECIFICATION_VERSION less than 0x0001000A", File=self.MetaFile)                \r
             if self._Defs and 'PCI_DEVICE_ID' in self._Defs and 'PCI_VENDOR_ID' in self._Defs \\r
@@ -1356,6 +1448,17 @@ class InfBuildData(ModuleBuildClassObject):
                 self._BuildType = 'UEFI_HII'\r
             else:\r
                 self._BuildType = self._ModuleType.upper()\r
+            \r
+            if self._DxsFile:\r
+                File = PathClass(NormPath(self._DxsFile), self._ModuleDir, Arch=self._Arch)\r
+                # check the file validation\r
+                ErrorCode, ErrorInfo = File.Validate(".dxs", CaseSensitive=False)\r
+                if ErrorCode != 0:\r
+                    EdkLogger.error('build', ErrorCode, ExtraData=ErrorInfo,\r
+                                    File=self.MetaFile, Line=LineNo)\r
+                if self.Sources == None:\r
+                    self._Sources = []\r
+                self._Sources.append(File)\r
         else:\r
             self._BuildType = self._ComponentType.upper()\r
             if not self._ComponentType:\r
@@ -1402,7 +1505,7 @@ class InfBuildData(ModuleBuildClassObject):
                         else:\r
                             Tool = ToolList[0]\r
                         ToolChain = "*_*_*_%s_FLAGS" % Tool\r
-                        ToolChainFamily = 'MSFT'    # R8.x only support MSFT tool chain\r
+                        ToolChainFamily = 'MSFT'    # EDK.x only support MSFT tool chain\r
                         #ignore not replaced macros in value\r
                         ValueList = GetSplitValueList(' ' + Value, '/D')\r
                         Dummy = ValueList[0]\r
@@ -1437,6 +1540,15 @@ class InfBuildData(ModuleBuildClassObject):
                 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No BASE_NAME name", File=self.MetaFile)\r
         return self._BaseName\r
 \r
+    ## Retrieve DxsFile\r
+    def _GetDxsFile(self):\r
+        if self._DxsFile == None:\r
+            if self._Header_ == None:\r
+                self._GetHeaderInfo()\r
+            if self._DxsFile == None:\r
+                self._DxsFile = ''\r
+        return self._DxsFile\r
+\r
     ## Retrieve MODULE_TYPE\r
     def _GetModuleType(self):\r
         if self._ModuleType == None:\r
@@ -1619,7 +1731,7 @@ class InfBuildData(ModuleBuildClassObject):
                 ToolCode = Record[3]\r
                 FeatureFlag = Record[4]\r
                 if self._AutoGenVersion < 0x00010005:\r
-                    # old module source files (R8)\r
+                    # old module source files (EDK)\r
                     File = PathClass(NormPath(Record[0], Macros), self._ModuleDir, self._SourceOverridePath,\r
                                      '', False, self._Arch, ToolChainFamily, '', TagName, ToolCode)\r
                     # check the file validation\r
@@ -1656,13 +1768,13 @@ class InfBuildData(ModuleBuildClassObject):
                 self._LibraryClasses[Lib] = Instance\r
         return self._LibraryClasses\r
 \r
-    ## Retrieve library names (for R8.x style of modules)\r
+    ## Retrieve library names (for EDK.x style of modules)\r
     def _GetLibraryNames(self):\r
         if self._Libraries == None:\r
             self._Libraries = []\r
             RecordList = self._RawData[MODEL_EFI_LIBRARY_INSTANCE, self._Arch, self._Platform]\r
             for Record in RecordList:\r
-                # in case of name with '.lib' extension, which is unusual in R8.x inf\r
+                # in case of name with '.lib' extension, which is unusual in EDK.x inf\r
                 Record = ReplaceMacros(Record, GlobalData.gEdkGlobal, False)\r
                 LibraryName = os.path.splitext(Record[0])[0]\r
                 if LibraryName not in self._Libraries:\r
@@ -1717,14 +1829,14 @@ class InfBuildData(ModuleBuildClassObject):
                 self._Guids[CName] = Value\r
         return self._Guids\r
 \r
-    ## Retrieve include paths necessary for this module (for R8.x style of modules)\r
+    ## Retrieve include paths necessary for this module (for EDK.x style of modules)\r
     def _GetIncludes(self):\r
         if self._Includes == None:\r
             self._Includes = []\r
             if self._SourceOverridePath:\r
                 self._Includes.append(self._SourceOverridePath)\r
             RecordList = self._RawData[MODEL_EFI_INCLUDE, self._Arch, self._Platform]\r
-            # [includes] section must be used only in old (R8.x) inf file\r
+            # [includes] section must be used only in old (EDK.x) inf file\r
             if self.AutoGenVersion >= 0x00010005 and len(RecordList) > 0:\r
                 EdkLogger.error('build', FORMAT_NOT_SUPPORTED, "No [include] section allowed",\r
                                 File=self.MetaFile, Line=RecordList[0][-1]-1)\r
@@ -1784,7 +1896,7 @@ class InfBuildData(ModuleBuildClassObject):
     ## Retrieve PCDs used in this module\r
     def _GetPcds(self):\r
         if self._Pcds == None:\r
-            self._Pcds = {}\r
+            self._Pcds = sdict()\r
             self._Pcds.update(self._GetPcd(MODEL_PCD_FIXED_AT_BUILD))\r
             self._Pcds.update(self._GetPcd(MODEL_PCD_PATCHABLE_IN_MODULE))\r
             self._Pcds.update(self._GetPcd(MODEL_PCD_FEATURE_FLAG))\r
@@ -1814,7 +1926,12 @@ class InfBuildData(ModuleBuildClassObject):
         if self._Depex == None:\r
             self._Depex = tdict(False, 2)\r
             RecordList = self._RawData[MODEL_EFI_DEPEX, self._Arch]\r
-\r
+            \r
+            # If the module has only Binaries and no Sources, then ignore [Depex] \r
+            if self.Sources == None or self.Sources == []:\r
+              if self.Binaries <> None and self.Binaries <> []:\r
+                return self._Depex\r
+                \r
             # PEIM and DXE drivers must have a valid [Depex] section\r
             if len(self.LibraryClass) == 0 and len(RecordList) == 0:\r
                 if self.ModuleType == 'DXE_DRIVER' or self.ModuleType == 'PEIM' or self.ModuleType == 'DXE_SMM_DRIVER' or \\r
@@ -1879,13 +1996,13 @@ class InfBuildData(ModuleBuildClassObject):
 \r
     ## Retrieve PCD for given type\r
     def _GetPcd(self, Type):\r
-        Pcds = {}\r
+        Pcds = sdict()\r
         PcdDict = tdict(True, 4)\r
-        PcdSet = set()\r
+        PcdList = []\r
         RecordList = self._RawData[Type, self._Arch, self._Platform]\r
         for TokenSpaceGuid, PcdCName, Setting, Arch, Platform, Dummy1, LineNo in RecordList:\r
             PcdDict[Arch, Platform, PcdCName, TokenSpaceGuid] = (Setting, LineNo)\r
-            PcdSet.add((PcdCName, TokenSpaceGuid))\r
+            PcdList.append((PcdCName, TokenSpaceGuid))\r
             # get the guid value\r
             if TokenSpaceGuid not in self.Guids:\r
                 Value = GuidValue(TokenSpaceGuid, self.Packages)\r
@@ -1897,13 +2014,11 @@ class InfBuildData(ModuleBuildClassObject):
                 self.Guids[TokenSpaceGuid] = Value\r
 \r
         # resolve PCD type, value, datum info, etc. by getting its definition from package\r
-        for PcdCName, TokenSpaceGuid in PcdSet:\r
-            ValueList = ['', '']\r
+        for PcdCName, TokenSpaceGuid in PcdList:\r
             Setting, LineNo = PcdDict[self._Arch, self.Platform, PcdCName, TokenSpaceGuid]\r
             if Setting == None:\r
                 continue\r
-            TokenList = Setting.split(TAB_VALUE_SPLIT)\r
-            ValueList[0:len(TokenList)] = TokenList\r
+            ValueList = AnalyzePcdData(Setting)\r
             DefaultValue = ValueList[0]\r
             Pcd = PcdClassObject(\r
                     PcdCName,\r
@@ -1914,6 +2029,7 @@ class InfBuildData(ModuleBuildClassObject):
                     '',\r
                     '',\r
                     {},\r
+                    False,\r
                     self.Guids[TokenSpaceGuid]\r
                     )\r
 \r
@@ -1927,7 +2043,7 @@ class InfBuildData(ModuleBuildClassObject):
                 #   "FixedAtBuild", "PatchableInModule", "FeatureFlag", "Dynamic", "DynamicEx"\r
                 #\r
                 PcdType = self._PCD_TYPE_STRING_[Type]\r
-                if Type in [MODEL_PCD_DYNAMIC, MODEL_PCD_DYNAMIC_EX]:\r
+                if Type == MODEL_PCD_DYNAMIC:\r
                     Pcd.Pending = True\r
                     for T in ["FixedAtBuild", "PatchableInModule", "FeatureFlag", "Dynamic", "DynamicEx"]:\r
                         if (PcdCName, TokenSpaceGuid, T) in Package.Pcds:\r
@@ -1940,6 +2056,55 @@ class InfBuildData(ModuleBuildClassObject):
                     PcdInPackage = Package.Pcds[PcdCName, TokenSpaceGuid, PcdType]\r
                     Pcd.Type = PcdType\r
                     Pcd.TokenValue = PcdInPackage.TokenValue\r
+                    \r
+                    #\r
+                    # Check whether the token value exist or not.\r
+                    #\r
+                    if Pcd.TokenValue == None or Pcd.TokenValue == "":\r
+                        EdkLogger.error(\r
+                                'build',\r
+                                FORMAT_INVALID,\r
+                                "No TokenValue for PCD [%s.%s] in [%s]!" % (TokenSpaceGuid, PcdCName, str(Package)),\r
+                                File =self.MetaFile, Line=LineNo,\r
+                                ExtraData=None\r
+                                )                        \r
+                    #\r
+                    # Check hexadecimal token value length and format.\r
+                    #\r
+                    ReIsValidPcdTokenValue = re.compile(r"^[0][x|X][0]*[0-9a-fA-F]{1,8}$", re.DOTALL)\r
+                    if Pcd.TokenValue.startswith("0x") or Pcd.TokenValue.startswith("0X"):\r
+                        if ReIsValidPcdTokenValue.match(Pcd.TokenValue) == None:\r
+                            EdkLogger.error(\r
+                                    'build',\r
+                                    FORMAT_INVALID,\r
+                                    "The format of TokenValue [%s] of PCD [%s.%s] in [%s] is invalid:" % (Pcd.TokenValue, TokenSpaceGuid, PcdCName, str(Package)),\r
+                                    File =self.MetaFile, Line=LineNo,\r
+                                    ExtraData=None\r
+                                    )\r
+                            \r
+                    #\r
+                    # Check decimal token value length and format.\r
+                    #                            \r
+                    else:\r
+                        try:\r
+                            TokenValueInt = int (Pcd.TokenValue, 10)\r
+                            if (TokenValueInt < 0 or TokenValueInt > 4294967295):\r
+                                EdkLogger.error(\r
+                                            'build',\r
+                                            FORMAT_INVALID,\r
+                                            "The format of TokenValue [%s] of PCD [%s.%s] in [%s] is invalid, as a decimal it should between: 0 - 4294967295!"% (Pcd.TokenValue, TokenSpaceGuid, PcdCName, str(Package)),\r
+                                            File =self.MetaFile, Line=LineNo,\r
+                                            ExtraData=None\r
+                                            )                                \r
+                        except:\r
+                            EdkLogger.error(\r
+                                        'build',\r
+                                        FORMAT_INVALID,\r
+                                        "The format of TokenValue [%s] of PCD [%s.%s] in [%s] is invalid, it should be hexadecimal or decimal!"% (Pcd.TokenValue, TokenSpaceGuid, PcdCName, str(Package)),\r
+                                        File =self.MetaFile, Line=LineNo,\r
+                                        ExtraData=None\r
+                                        )\r
+                    \r
                     Pcd.DatumType = PcdInPackage.DatumType\r
                     Pcd.MaxDatumSize = PcdInPackage.MaxDatumSize\r
                     Pcd.InfDefaultValue = Pcd.DefaultValue\r
@@ -1949,12 +2114,13 @@ class InfBuildData(ModuleBuildClassObject):
             else:\r
                 EdkLogger.error(\r
                             'build',\r
-                            PARSER_ERROR,\r
+                            FORMAT_INVALID,\r
                             "PCD [%s.%s] in [%s] is not found in dependent packages:" % (TokenSpaceGuid, PcdCName, self.MetaFile),\r
                             File =self.MetaFile, Line=LineNo,\r
                             ExtraData="\t%s" % '\n\t'.join([str(P) for P in self.Packages])\r
                             )\r
             Pcds[PcdCName, TokenSpaceGuid] = Pcd\r
+\r
         return Pcds\r
 \r
     Arch                    = property(_GetArch, _SetArch)\r
@@ -1977,7 +2143,8 @@ class InfBuildData(ModuleBuildClassObject):
     ConstructorList         = property(_GetConstructor)\r
     DestructorList          = property(_GetDestructor)\r
     Defines                 = property(_GetDefines)\r
-\r
+    DxsFile                 = property(_GetDxsFile)\r
+    \r
     Binaries                = property(_GetBinaryFiles)\r
     Sources                 = property(_GetSourceFiles)\r
     LibraryClasses          = property(_GetLibraryClassUses)\r
@@ -1994,7 +2161,7 @@ class InfBuildData(ModuleBuildClassObject):
 \r
 ## Database\r
 #\r
-#   This class defined the build databse for all modules, packages and platform.\r
+#   This class defined the build database for all modules, packages and platform.\r
 # It will call corresponding parser for the given file if it cannot find it in\r
 # the database.\r
 #\r
@@ -2108,6 +2275,7 @@ class WorkspaceDatabase(object):
     # @prarm RenewDb=False      Create new database file if it's already there\r
     #\r
     def __init__(self, DbPath, GlobalMacros={}, RenewDb=False):\r
+        self._DbClosedFlag = False\r
         self._GlobalMacros = GlobalMacros\r
 \r
         if DbPath == None or DbPath == '':\r
@@ -2261,9 +2429,11 @@ determine whether database file is out of date!\n")
     # Close the connection and cursor\r
     #\r
     def Close(self):\r
-        self.Conn.commit()\r
-        self.Cur.close()\r
-        self.Conn.close()\r
+        if not self._DbClosedFlag:\r
+            self.Conn.commit()\r
+            self.Cur.close()\r
+            self.Conn.close()\r
+            self._DbClosedFlag = True\r
 \r
     ## Get unique file ID for the gvien file\r
     def GetFileId(self, FilePath):\r
@@ -2287,6 +2457,13 @@ determine whether database file is out of date!\n")
             Result = self.Cur.execute("select min(ID) from %s" % (TableName)).fetchall()\r
             if Result[0][0] != -1:\r
                 return False\r
+            #\r
+            # Check whether the meta data file has external dependency by comparing the time stamp\r
+            #\r
+            Sql = "select Value1, Value2 from %s where Model=%d" % (TableName, MODEL_EXTERNAL_DEPENDENCY)\r
+            for Dependency in self.Cur.execute(Sql).fetchall():\r
+                if str(os.stat(Dependency[0])[8]) != Dependency[1]:\r
+                    return False\r
         except:\r
             return False\r
         return True\r