X-Git-Url: https://git.proxmox.com/?p=mirror_edk2.git;a=blobdiff_plain;f=BaseTools%2FSource%2FPython%2FCommon%2FMisc.py;h=af374d804d86b8a01a5fee2ae38b0c2968169eaf;hp=777450d81860a1e9e92daf9d9405c68315a82eba;hb=4faf13222edead307109bf8c747200ea3fb617c0;hpb=47fea6afd74af76c7e2a2b03d319b7ac035ac26a diff --git a/BaseTools/Source/Python/Common/Misc.py b/BaseTools/Source/Python/Common/Misc.py index 777450d818..af374d804d 100644 --- a/BaseTools/Source/Python/Common/Misc.py +++ b/BaseTools/Source/Python/Common/Misc.py @@ -1,7 +1,7 @@ ## @file # Common routines used by all tools # -# Copyright (c) 2007 - 2015, Intel Corporation. All rights reserved.
+# Copyright (c) 2007 - 2018, Intel Corporation. All rights reserved.
# This program and the accompanying materials # are licensed and made available under the terms and conditions of the BSD License # which accompanies this distribution. The full text of the license may be found at @@ -36,7 +36,9 @@ from CommonDataClass.DataClass import * from Parsing import GetSplitValueList from Common.LongFilePathSupport import OpenLongFilePath as open from Common.MultipleWorkspace import MultipleWorkspace as mws - +import uuid +from CommonDataClass.Exceptions import BadExpression +import subprocess ## Regular expression used to find out place holders in string template gPlaceholderPattern = re.compile("\$\{([^$()\s]+)\}", re.MULTILINE | re.UNICODE) @@ -67,14 +69,32 @@ def GetVariableOffset(mapfilepath, efifilepath, varnames): if (firstline.startswith("Archive member included ") and firstline.endswith(" file (symbol)")): return _parseForGCC(lines, efifilepath, varnames) + if firstline.startswith("# Path:"): + return _parseForXcode(lines, efifilepath, varnames) return _parseGeneral(lines, efifilepath, varnames) +def _parseForXcode(lines, efifilepath, varnames): + status = 0 + ret = [] + for index, line in enumerate(lines): + line = line.strip() + if status == 0 and line == "# Symbols:": + status = 1 + continue + if status == 1 and len(line) != 0: + for varname in varnames: + if varname in line: + m = re.match('^([\da-fA-FxX]+)([\s\S]*)([_]*%s)$' % varname, line) + if m != None: + ret.append((varname, m.group(1))) + return ret + def _parseForGCC(lines, efifilepath, varnames): """ Parse map file generated by GCC linker """ status = 0 sections = [] varoffset = [] - for line in lines: + for index, line in enumerate(lines): line = line.strip() # status machine transection if status == 0 and line == "Memory Configuration": @@ -88,14 +108,23 @@ def _parseForGCC(lines, efifilepath, varnames): continue # status handler - if status == 2: + if status == 3: m = re.match('^([\w_\.]+) +([\da-fA-Fx]+) +([\da-fA-Fx]+)$', line) if m != None: sections.append(m.groups(0)) for varname in varnames: - m = re.match("^([\da-fA-Fx]+) +[_]*(%s)$" % varname, line) + Str = '' + m = re.match("^.data.(%s)" % varname, line) if m != None: - varoffset.append((varname, int(m.groups(0)[0], 16) , int(sections[-1][1], 16), sections[-1][0])) + m = re.match(".data.(%s)$" % varname, line) + if m != None: + Str = lines[index + 1] + else: + Str = line[len(".data.%s" % varname):] + if Str: + m = re.match('^([\da-fA-Fx]+) +([\da-fA-Fx]+)', Str.strip()) + if m != None: + varoffset.append((varname, int(m.groups(0)[0], 16) , int(sections[-1][1], 16), sections[-1][0])) if not varoffset: return [] @@ -794,13 +823,18 @@ def GetRelPath(Path1, Path2): # # @param CName The CName of the GUID # @param PackageList List of packages looking-up in +# @param Inffile The driver file # # @retval GuidValue if the CName is found in any given package # @retval None if the CName is not found in all given packages # -def GuidValue(CName, PackageList): +def GuidValue(CName, PackageList, Inffile = None): for P in PackageList: - if CName in P.Guids: + GuidKeys = P.Guids.keys() + if Inffile and P._PrivateGuids: + if not Inffile.startswith(P.MetaFile.Dir): + GuidKeys = (dict.fromkeys(x for x in P.Guids if x not in P._PrivateGuids)).keys() + if CName in GuidKeys: return P.Guids[CName] return None @@ -808,13 +842,18 @@ def GuidValue(CName, PackageList): # # @param CName The CName of the GUID # @param PackageList List of packages looking-up in +# @param Inffile The driver file # # @retval GuidValue if the CName is found in any given package # @retval None if the CName is not found in all given packages # -def ProtocolValue(CName, PackageList): +def ProtocolValue(CName, PackageList, Inffile = None): for P in PackageList: - if CName in P.Protocols: + ProtocolKeys = P.Protocols.keys() + if Inffile and P._PrivateProtocols: + if not Inffile.startswith(P.MetaFile.Dir): + ProtocolKeys = (dict.fromkeys(x for x in P.Protocols if x not in P._PrivateProtocols)).keys() + if CName in ProtocolKeys: return P.Protocols[CName] return None @@ -822,13 +861,18 @@ def ProtocolValue(CName, PackageList): # # @param CName The CName of the GUID # @param PackageList List of packages looking-up in +# @param Inffile The driver file # # @retval GuidValue if the CName is found in any given package # @retval None if the CName is not found in all given packages # -def PpiValue(CName, PackageList): +def PpiValue(CName, PackageList, Inffile = None): for P in PackageList: - if CName in P.Ppis: + PpiKeys = P.Ppis.keys() + if Inffile and P._PrivatePpis: + if not Inffile.startswith(P.MetaFile.Dir): + PpiKeys = (dict.fromkeys(x for x in P.Ppis if x not in P._PrivatePpis)).keys() + if CName in PpiKeys: return P.Ppis[CName] return None @@ -1397,6 +1441,208 @@ def ParseConsoleLog(Filename): Opr.close() Opw.close() +def AnalyzePcdExpression(Setting): + Setting = Setting.strip() + # There might be escaped quote in a string: \", \\\" , \', \\\' + Data = Setting + # There might be '|' in string and in ( ... | ... ), replace it with '-' + NewStr = '' + InSingleQuoteStr = False + InDoubleQuoteStr = False + Pair = 0 + for Index, ch in enumerate(Data): + if ch == '"' and not InSingleQuoteStr: + if Data[Index - 1] != '\\': + InDoubleQuoteStr = not InDoubleQuoteStr + elif ch == "'" and not InDoubleQuoteStr: + if Data[Index - 1] != '\\': + InSingleQuoteStr = not InSingleQuoteStr + elif ch == '(' and not (InSingleQuoteStr or InDoubleQuoteStr): + Pair += 1 + elif ch == ')' and not (InSingleQuoteStr or InDoubleQuoteStr): + Pair -= 1 + + if (Pair > 0 or InSingleQuoteStr or InDoubleQuoteStr) and ch == TAB_VALUE_SPLIT: + NewStr += '-' + else: + NewStr += ch + FieldList = [] + StartPos = 0 + while True: + Pos = NewStr.find(TAB_VALUE_SPLIT, StartPos) + if Pos < 0: + FieldList.append(Setting[StartPos:].strip()) + break + FieldList.append(Setting[StartPos:Pos].strip()) + StartPos = Pos + 1 + + return FieldList + +def ParseDevPathValue (Value): + DevPathList = [ "Path","HardwarePath","Pci","PcCard","MemoryMapped","VenHw","Ctrl","BMC","AcpiPath","Acpi","PciRoot", + "PcieRoot","Floppy","Keyboard","Serial","ParallelPort","AcpiEx","AcpiExp","AcpiAdr","Msg","Ata","Scsi", + "Fibre","FibreEx","I1394","USB","I2O","Infiniband","VenMsg","VenPcAnsi","VenVt100","VenVt100Plus", + "VenUtf8","UartFlowCtrl","SAS","SasEx","NVMe","UFS","SD","eMMC","DebugPort","MAC","IPv4","IPv6","Uart", + "UsbClass","UsbAudio","UsbCDCControl","UsbHID","UsbImage","UsbPrinter","UsbMassStorage","UsbHub", + "UsbCDCData","UsbSmartCard","UsbVideo","UsbDiagnostic","UsbWireless","UsbDeviceFirmwareUpdate", + "UsbIrdaBridge","UsbTestAndMeasurement","UsbWwid","Unit","iSCSI","Vlan","Uri","Bluetooth","Wi-Fi", + "MediaPath","HD","CDROM","VenMedia","Media","Fv","FvFile","Offset","RamDisk","VirtualDisk","VirtualCD", + "PersistentVirtualDisk","PersistentVirtualCD","BbsPath","BBS","Sata" ] + if '\\' in Value: + Value.replace('\\', '/').replace(' ', '') + for Item in Value.split('/'): + Key = Item.strip().split('(')[0] + if Key not in DevPathList: + pass + + Cmd = 'DevicePath ' + '"' + Value + '"' + try: + p = subprocess.Popen(Cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE, shell=True) + out, err = p.communicate() + except Exception, X: + raise BadExpression("DevicePath: %s" % (str(X)) ) + finally: + subprocess._cleanup() + p.stdout.close() + p.stderr.close() + if err: + raise BadExpression("DevicePath: %s" % str(err)) + Size = len(out.split()) + out = ','.join(out.split()) + return '{' + out + '}', Size + +def ParseFieldValue (Value): + if type(Value) == type(0): + return Value, (Value.bit_length() + 7) / 8 + if type(Value) <> type(''): + raise BadExpression('Type %s is %s' %(Value, type(Value))) + Value = Value.strip() + if Value.startswith('UINT8') and Value.endswith(')'): + Value, Size = ParseFieldValue(Value.split('(', 1)[1][:-1]) + if Size > 1: + raise BadExpression('Value (%s) Size larger than %d' %(Value, Size)) + return Value, 1 + if Value.startswith('UINT16') and Value.endswith(')'): + Value, Size = ParseFieldValue(Value.split('(', 1)[1][:-1]) + if Size > 2: + raise BadExpression('Value (%s) Size larger than %d' %(Value, Size)) + return Value, 2 + if Value.startswith('UINT32') and Value.endswith(')'): + Value, Size = ParseFieldValue(Value.split('(', 1)[1][:-1]) + if Size > 4: + raise BadExpression('Value (%s) Size larger than %d' %(Value, Size)) + return Value, 4 + if Value.startswith('UINT64') and Value.endswith(')'): + Value, Size = ParseFieldValue(Value.split('(', 1)[1][:-1]) + if Size > 8: + raise BadExpression('Value (%s) Size larger than %d' % (Value, Size)) + return Value, 8 + if Value.startswith('GUID') and Value.endswith(')'): + Value = Value.split('(', 1)[1][:-1].strip() + if Value[0] == '{' and Value[-1] == '}': + TmpValue = GuidStructureStringToGuidString(Value) + if len(TmpValue) == 0: + raise BadExpression("Invalid GUID value string %s" % Value) + Value = TmpValue + if Value[0] == '"' and Value[-1] == '"': + Value = Value[1:-1] + try: + Value = "'" + uuid.UUID(Value).get_bytes_le() + "'" + except ValueError, Message: + raise BadExpression('%s' % Message) + Value, Size = ParseFieldValue(Value) + return Value, 16 + if Value.startswith('L"') and Value.endswith('"'): + # Unicode String + # translate escape character + Value = Value[1:] + try: + Value = eval(Value) + except: + Value = Value[1:-1] + List = list(Value) + List.reverse() + Value = 0 + for Char in List: + Value = (Value << 16) | ord(Char) + return Value, (len(List) + 1) * 2 + if Value.startswith('"') and Value.endswith('"'): + # ASCII String + # translate escape character + try: + Value = eval(Value) + except: + Value = Value[1:-1] + List = list(Value) + List.reverse() + Value = 0 + for Char in List: + Value = (Value << 8) | ord(Char) + return Value, len(List) + 1 + if Value.startswith("L'") and Value.endswith("'"): + # Unicode Character Constant + # translate escape character + Value = Value[1:] + try: + Value = eval(Value) + except: + Value = Value[1:-1] + List = list(Value) + if len(List) == 0: + raise BadExpression('Length %s is %s' % (Value, len(List))) + List.reverse() + Value = 0 + for Char in List: + Value = (Value << 16) | ord(Char) + return Value, len(List) * 2 + if Value.startswith("'") and Value.endswith("'"): + # Character constant + # translate escape character + try: + Value = eval(Value) + except: + Value = Value[1:-1] + List = list(Value) + if len(List) == 0: + raise BadExpression('Length %s is %s' % (Value, len(List))) + List.reverse() + Value = 0 + for Char in List: + Value = (Value << 8) | ord(Char) + return Value, len(List) + if Value.startswith('{') and Value.endswith('}'): + # Byte array + Value = Value[1:-1] + List = [Item.strip() for Item in Value.split(',')] + List.reverse() + Value = 0 + RetSize = 0 + for Item in List: + ItemValue, Size = ParseFieldValue(Item) + RetSize += Size + for I in range(Size): + Value = (Value << 8) | ((ItemValue >> 8 * I) & 0xff) + return Value, RetSize + if Value.startswith('DEVICE_PATH(') and Value.endswith(')'): + Value = Value.replace("DEVICE_PATH(", '').rstrip(')') + Value = Value.strip().strip('"') + return ParseDevPathValue(Value) + if Value.lower().startswith('0x'): + Value = int(Value, 16) + if Value == 0: + return 0, 1 + return Value, (Value.bit_length() + 7) / 8 + if Value[0].isdigit(): + Value = int(Value, 10) + if Value == 0: + return 0, 1 + return Value, (Value.bit_length() + 7) / 8 + if Value.lower() == 'true': + return 1, 1 + if Value.lower() == 'false': + return 0, 1 + return Value, 1 + ## AnalyzeDscPcd # # Analyze DSC PCD value, since there is no data type info in DSC @@ -1423,53 +1669,32 @@ def ParseConsoleLog(Filename): # Index: The index where PcdValue is in ValueList # def AnalyzeDscPcd(Setting, PcdType, DataType=''): - Setting = Setting.strip() - # There might be escaped quote in a string: \", \\\" - Data = Setting.replace('\\\\', '//').replace('\\\"', '\\\'') - # There might be '|' in string and in ( ... | ... ), replace it with '-' - NewStr = '' - InStr = False - Pair = 0 - for ch in Data: - if ch == '"': - InStr = not InStr - elif ch == '(' and not InStr: - Pair += 1 - elif ch == ')' and not InStr: - Pair -= 1 - - if (Pair > 0 or InStr) and ch == TAB_VALUE_SPLIT: - NewStr += '-' - else: - NewStr += ch - FieldList = [] - StartPos = 0 - while True: - Pos = NewStr.find(TAB_VALUE_SPLIT, StartPos) - if Pos < 0: - FieldList.append(Setting[StartPos:].strip()) - break - FieldList.append(Setting[StartPos:Pos].strip()) - StartPos = Pos + 1 + FieldList = AnalyzePcdExpression(Setting) IsValid = True if PcdType in (MODEL_PCD_FIXED_AT_BUILD, MODEL_PCD_PATCHABLE_IN_MODULE, MODEL_PCD_FEATURE_FLAG): Value = FieldList[0] Size = '' if len(FieldList) > 1: - Type = FieldList[1] - # Fix the PCD type when no DataType input - if Type == 'VOID*': - DataType = 'VOID*' - else: + if FieldList[1].upper().startswith("0X") or FieldList[1].isdigit(): Size = FieldList[1] + else: + DataType = FieldList[1] + if len(FieldList) > 2: Size = FieldList[2] - if DataType == 'VOID*': - IsValid = (len(FieldList) <= 3) - else: + if DataType == "": IsValid = (len(FieldList) <= 1) - return [Value, '', Size], IsValid, 0 + else: + IsValid = (len(FieldList) <= 3) +# Value, Size = ParseFieldValue(Value) + if Size: + try: + int(Size,16) if Size.upper().startswith("0X") else int(Size) + except: + IsValid = False + Size = -1 + return [str(Value), '', str(Size)], IsValid, 0 elif PcdType in (MODEL_PCD_DYNAMIC_DEFAULT, MODEL_PCD_DYNAMIC_EX_DEFAULT): Value = FieldList[0] Size = Type = '' @@ -1487,11 +1712,18 @@ def AnalyzeDscPcd(Setting, PcdType, DataType=''): Size = str(len(Value.split(","))) else: Size = str(len(Value) -2 + 1 ) - if DataType == 'VOID*': - IsValid = (len(FieldList) <= 3) - else: + if DataType == "": IsValid = (len(FieldList) <= 1) - return [Value, Type, Size], IsValid, 0 + else: + IsValid = (len(FieldList) <= 3) + + if Size: + try: + int(Size,16) if Size.upper().startswith("0X") else int(Size) + except: + IsValid = False + Size = -1 + return [Value, Type, str(Size)], IsValid, 0 elif PcdType in (MODEL_PCD_DYNAMIC_VPD, MODEL_PCD_DYNAMIC_EX_VPD): VpdOffset = FieldList[0] Value = Size = '' @@ -1503,11 +1735,17 @@ def AnalyzeDscPcd(Setting, PcdType, DataType=''): Size = FieldList[1] if len(FieldList) > 2: Value = FieldList[2] - if DataType == 'VOID*': - IsValid = (len(FieldList) <= 3) + if DataType == "": + IsValid = (len(FieldList) <= 1) else: - IsValid = (len(FieldList) <= 2) - return [VpdOffset, Size, Value], IsValid, 2 + IsValid = (len(FieldList) <= 3) + if Size: + try: + int(Size,16) if Size.upper().startswith("0X") else int(Size) + except: + IsValid = False + Size = -1 + return [VpdOffset, str(Size), Value], IsValid, 2 elif PcdType in (MODEL_PCD_DYNAMIC_HII, MODEL_PCD_DYNAMIC_EX_HII): HiiString = FieldList[0] Guid = Offset = Value = Attribute = '' @@ -1606,10 +1844,10 @@ def CheckPcdDatum(Type, Value): if Type == "VOID*": ValueRe = re.compile(r'\s*L?\".*\"\s*$') if not (((Value.startswith('L"') or Value.startswith('"')) and Value.endswith('"')) - or (Value.startswith('{') and Value.endswith('}')) + or (Value.startswith('{') and Value.endswith('}')) or (Value.startswith("L'") or Value.startswith("'") and Value.endswith("'")) ): return False, "Invalid value [%s] of type [%s]; must be in the form of {...} for array"\ - ", or \"...\" for string, or L\"...\" for unicode string" % (Value, Type) + ", \"...\" or \'...\' for string, L\"...\" or L\'...\' for unicode string" % (Value, Type) elif ValueRe.match(Value): # Check the chars in UnicodeString or CString is printable if Value.startswith("L"): @@ -1635,7 +1873,7 @@ def CheckPcdDatum(Type, Value): return False, "Invalid value [%s] of type [%s];"\ " must be a hexadecimal, decimal or octal in C language format." % (Value, Type) else: - return False, "Invalid type [%s]; must be one of VOID*, BOOLEAN, UINT8, UINT16, UINT32, UINT64." % (Type) + return True, "StructurePcd" return True, "" @@ -1950,61 +2188,167 @@ class PeImageClass(): Value = (Value << 8) | int(ByteList[index]) return Value +class DefaultStore(): + def __init__(self,DefaultStores ): + self.DefaultStores = DefaultStores + def DefaultStoreID(self,DefaultStoreName): + for key,value in self.DefaultStores.items(): + if value == DefaultStoreName: + return key + return None + def GetDefaultDefault(self): + if not self.DefaultStores or "0" in self.DefaultStores: + return "0",TAB_DEFAULT_STORES_DEFAULT + else: + minvalue = min([int(value_str) for value_str in self.DefaultStores.keys()]) + return (str(minvalue), self.DefaultStores[str(minvalue)]) + def GetMin(self,DefaultSIdList): + if not DefaultSIdList: + return "STANDARD" + storeidset = {storeid for storeid, storename in self.DefaultStores.values() if storename in DefaultSIdList} + if not storeidset: + return "" + minid = min(storeidset ) + for sid,name in self.DefaultStores.values(): + if sid == minid: + return name class SkuClass(): DEFAULT = 0 SINGLE = 1 MULTIPLE =2 - def __init__(self,SkuIdentifier='', SkuIds={}): + def __init__(self,SkuIdentifier='', SkuIds=None): + if SkuIds is None: + SkuIds = {} + + for SkuName in SkuIds: + SkuId = SkuIds[SkuName][0] + skuid_num = int(SkuId,16) if SkuId.upper().startswith("0X") else int(SkuId) + if skuid_num > 0xFFFFFFFFFFFFFFFF: + EdkLogger.error("build", PARAMETER_INVALID, + ExtraData = "SKU-ID [%s] value %s exceeds the max value of UINT64" + % (SkuName, SkuId)) self.AvailableSkuIds = sdict() self.SkuIdSet = [] self.SkuIdNumberSet = [] + self.SkuData = SkuIds + self.__SkuInherit = {} + self.__SkuIdentifier = SkuIdentifier if SkuIdentifier == '' or SkuIdentifier is None: self.SkuIdSet = ['DEFAULT'] self.SkuIdNumberSet = ['0U'] elif SkuIdentifier == 'ALL': self.SkuIdSet = SkuIds.keys() - self.SkuIdNumberSet = [num.strip() + 'U' for num in SkuIds.values()] + self.SkuIdNumberSet = [num[0].strip() + 'U' for num in SkuIds.values()] else: r = SkuIdentifier.split('|') - self.SkuIdSet=[r[k].strip() for k in range(len(r))] + self.SkuIdSet=[(r[k].strip()).upper() for k in range(len(r))] k = None try: - self.SkuIdNumberSet = [SkuIds[k].strip() + 'U' for k in self.SkuIdSet] + self.SkuIdNumberSet = [SkuIds[k][0].strip() + 'U' for k in self.SkuIdSet] except Exception: EdkLogger.error("build", PARAMETER_INVALID, ExtraData = "SKU-ID [%s] is not supported by the platform. [Valid SKU-ID: %s]" - % (k, " ".join(SkuIds.keys()))) - if len(self.SkuIdSet) == 2 and 'DEFAULT' in self.SkuIdSet and SkuIdentifier != 'ALL': - self.SkuIdSet.remove('DEFAULT') - self.SkuIdNumberSet.remove('0U') + % (k, " | ".join(SkuIds.keys()))) for each in self.SkuIdSet: if each in SkuIds: - self.AvailableSkuIds[each] = SkuIds[each] + self.AvailableSkuIds[each] = SkuIds[each][0] else: EdkLogger.error("build", PARAMETER_INVALID, ExtraData="SKU-ID [%s] is not supported by the platform. [Valid SKU-ID: %s]" - % (each, " ".join(SkuIds.keys()))) + % (each, " | ".join(SkuIds.keys()))) + if self.SkuUsageType != self.SINGLE: + self.AvailableSkuIds.update({'DEFAULT':0, 'COMMON':0}) + if self.SkuIdSet: + GlobalData.gSkuids = (self.SkuIdSet) + if 'COMMON' in GlobalData.gSkuids: + GlobalData.gSkuids.remove('COMMON') + if self.SkuUsageType == self.SINGLE: + if len(GlobalData.gSkuids) != 1: + if 'DEFAULT' in GlobalData.gSkuids: + GlobalData.gSkuids.remove('DEFAULT') + if GlobalData.gSkuids: + GlobalData.gSkuids.sort() + + def GetNextSkuId(self, skuname): + if not self.__SkuInherit: + self.__SkuInherit = {} + for item in self.SkuData.values(): + self.__SkuInherit[item[1]]=item[2] if item[2] else "DEFAULT" + return self.__SkuInherit.get(skuname,"DEFAULT") + + def GetSkuChain(self,sku): + if sku == "DEFAULT": + return ["DEFAULT"] + skulist = [sku] + nextsku = sku + while 1: + nextsku = self.GetNextSkuId(nextsku) + skulist.append(nextsku) + if nextsku == "DEFAULT": + break + skulist.reverse() + return skulist + def SkuOverrideOrder(self): + skuorderset = [] + for skuname in self.SkuIdSet: + skuorderset.append(self.GetSkuChain(skuname)) + skuorder = [] + for index in range(max([len(item) for item in skuorderset])): + for subset in skuorderset: + if index > len(subset)-1: + continue + if subset[index] in skuorder: + continue + skuorder.append(subset[index]) + + return skuorder + def __SkuUsageType(self): + if self.__SkuIdentifier.upper() == "ALL": + return SkuClass.MULTIPLE + if len(self.SkuIdSet) == 1: if self.SkuIdSet[0] == 'DEFAULT': return SkuClass.DEFAULT else: return SkuClass.SINGLE + elif len(self.SkuIdSet) == 2: + if 'DEFAULT' in self.SkuIdSet: + return SkuClass.SINGLE + else: + return SkuClass.MULTIPLE else: return SkuClass.MULTIPLE + def DumpSkuIdArrary(self): + ArrayStrList = [] + if self.SkuUsageType == SkuClass.SINGLE: + ArrayStr = "{0x0}" + else: + for skuname in self.AvailableSkuIds: + if skuname == "COMMON": + continue + while skuname != "DEFAULT": + ArrayStrList.append(hex(int(self.AvailableSkuIds[skuname]))) + skuname = self.GetNextSkuId(skuname) + ArrayStrList.append("0x0") + ArrayStr = "{" + ",".join(ArrayStrList) + "}" + return ArrayStr def __GetAvailableSkuIds(self): return self.AvailableSkuIds def __GetSystemSkuID(self): if self.__SkuUsageType() == SkuClass.SINGLE: - return self.SkuIdSet[0] + if len(self.SkuIdSet) == 1: + return self.SkuIdSet[0] + else: + return self.SkuIdSet[0] if self.SkuIdSet[0] != 'DEFAULT' else self.SkuIdSet[1] else: return 'DEFAULT' def __GetAvailableSkuIdNumber(self): @@ -2033,6 +2377,55 @@ def PackRegistryFormatGuid(Guid): int(Guid[4][-2:], 16) ) +def BuildOptionPcdValueFormat(TokenSpaceGuidCName, TokenCName, PcdDatumType, Value): + if PcdDatumType not in [TAB_UINT8, TAB_UINT16, TAB_UINT32, TAB_UINT64,'BOOLEAN']: + if Value.startswith('L') or Value.startswith('"'): + if not Value[1]: + EdkLogger.error("build", FORMAT_INVALID, 'For Void* type PCD, when specify the Value in the command line, please use the following format: "string", L"string", H"{...}"') + Value = Value + elif Value.startswith('H'): + if not Value[1]: + EdkLogger.error("build", FORMAT_INVALID, 'For Void* type PCD, when specify the Value in the command line, please use the following format: "string", L"string", H"{...}"') + Value = Value[1:] + else: + if not Value[0]: + EdkLogger.error("build", FORMAT_INVALID, 'For Void* type PCD, when specify the Value in the command line, please use the following format: "string", L"string", H"{...}"') + Value = '"' + Value + '"' + + IsValid, Cause = CheckPcdDatum(PcdDatumType, Value) + if not IsValid: + EdkLogger.error("build", FORMAT_INVALID, Cause, ExtraData="%s.%s" % (TokenSpaceGuidCName, TokenCName)) + if PcdDatumType == 'BOOLEAN': + Value = Value.upper() + if Value == 'TRUE' or Value == '1': + Value = '1' + elif Value == 'FALSE' or Value == '0': + Value = '0' + return Value +## Get the integer value from string like "14U" or integer like 2 +# +# @param Input The object that may be either a integer value or a string +# +# @retval Value The integer value that the input represents +# +def GetIntegerValue(Input): + if type(Input) in (int, long): + return Input + String = Input + if String.endswith("U"): + String = String[:-1] + if String.endswith("ULL"): + String = String[:-3] + if String.endswith("LL"): + String = String[:-2] + + if String.startswith("0x") or String.startswith("0X"): + return int(String, 16) + elif String == '': + return 0 + else: + return int(String) + ## # # This acts like the main() function for the script, unless it is 'import'ed into another