2017-11-24 14:30:11 +08:00
## @file
# This file is used to create a database used by build tool
#
2025-06-06 16:04:29 -07:00
# Copyright (c) 2008 - 2025, Intel Corporation. All rights reserved.<BR>
2017-11-24 14:30:11 +08:00
# (C) Copyright 2016 Hewlett Packard Enterprise Development LP<BR>
2025-07-01 08:52:39 +00:00
# Copyright (C) 2025 Advanced Micro Devices, Inc. All rights reserved.
2019-04-03 16:03:11 -07:00
# SPDX-License-Identifier: BSD-2-Clause-Patent
2017-11-24 14:30:11 +08:00
#
## Platform build information from DSC file
#
# This class is used to retrieve information stored in database and convert them
# into PlatformBuildClassObject form for easier use for AutoGen.
#
2018-10-15 08:27:53 +08:00
from __future__ import print_function
from __future__ import absolute_import
2018-05-19 18:50:25 +08:00
from Common.StringUtils import *
2017-11-24 14:30:11 +08:00
from Common.DataType import *
from Common.Misc import *
from types import *
2018-03-07 14:14:43 +08:00
from Common.Expression import *
2017-11-24 14:30:11 +08:00
from CommonDataClass.CommonClass import SkuInfoClass
2021-09-23 16:59:03 +08:00
from Common.TargetTxtClassObject import TargetTxtDict , gDefaultTargetTxtFile
from Common.ToolDefClassObject import ToolDefDict , gDefaultToolsDefFile
2018-07-13 18:18:46 +08:00
from .MetaDataTable import *
from .MetaFileTable import *
from .MetaFileParser import *
2017-11-24 14:30:11 +08:00
2018-07-13 18:18:46 +08:00
from .WorkspaceCommon import GetDeclaredPcd
2017-11-24 14:30:11 +08:00
from Common.Misc import AnalyzeDscPcd
2019-05-09 17:19:56 +08:00
from Common.Misc import ProcessDuplicatedInf , RemoveCComments , ArrayIndex
2017-11-24 14:30:11 +08:00
import re
from Common.Parsing import IsValidWord
from Common.VariableAttributes import VariableAttributes
import Common.GlobalData as GlobalData
import subprocess
2018-12-16 15:19:42 +08:00
from functools import reduce
2018-02-28 13:59:19 +08:00
from Common.Misc import SaveFileOnChange
2017-11-24 14:30:11 +08:00
from Workspace.BuildClassObject import PlatformBuildClassObject , StructurePcd , PcdClassObject , ModuleBuildClassObject
2018-06-25 18:31:33 +08:00
from collections import OrderedDict , defaultdict
2024-02-07 09:20:35 -08:00
import json
2025-06-06 16:04:29 -07:00
import os
2024-02-07 09:20:35 -08:00
import shutil
2025-06-06 16:04:29 -07:00
import sys
2017-11-24 14:30:11 +08:00
2019-01-11 02:39:47 +08:00
def _IsFieldValueAnArray ( Value ):
Value = Value . strip ()
if Value . startswith ( TAB_GUID ) and Value . endswith ( ')' ):
return True
if Value . startswith ( 'L"' ) and Value . endswith ( '"' ) and len ( list ( Value [ 2 : - 1 ])) > 1 :
return True
if Value [ 0 ] == '"' and Value [ - 1 ] == '"' and len ( list ( Value [ 1 : - 1 ])) > 1 :
return True
if Value [ 0 ] == '{' and Value [ - 1 ] == '}' :
return True
if Value . startswith ( "L'" ) and Value . endswith ( "'" ) and len ( list ( Value [ 2 : - 1 ])) > 1 :
return True
if Value [ 0 ] == "'" and Value [ - 1 ] == "'" and len ( list ( Value [ 1 : - 1 ])) > 1 :
return True
return False
2017-11-24 14:30:11 +08:00
PcdValueInitName = 'PcdValueInit'
2020-03-11 17:51:21 +08:00
PcdValueCommonName = 'PcdValueCommon'
2024-02-07 09:20:35 -08:00
StructuredPcdsDataName = 'StructuredPcdsData.json'
2017-11-24 14:30:11 +08:00
PcdMainCHeader = '''
/**
DO NOT EDIT
FILE auto-generated
**/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <PcdValueCommon.h>
'''
PcdMainCEntry = '''
int
main (
int argc,
char *argv[]
)
{
return PcdValueMain (argc, argv);
}
'''
PcdMakefileHeader = '''
#
# DO NOT EDIT
# This file is auto-generated by build utility
#
'''
2017-12-26 13:16:17 +08:00
WindowsCFLAGS = 'CFLAGS = $(CFLAGS) /wd4200 /wd4034 /wd4101 '
2023-02-16 08:40:46 -07:00
LinuxCFLAGS = 'CFLAGS += -Wno-pointer-to-int-cast -Wno-unused-variable '
2023-12-06 12:27:02 -08:00
PcdMakefileEnd = r '''
2017-11-24 14:30:11 +08:00
!INCLUDE $(BASE_TOOLS_PATH)\Source\C\Makefiles\ms.common
!INCLUDE $(BASE_TOOLS_PATH)\Source\C\Makefiles\ms.app
'''
2018-10-22 11:24:13 +08:00
AppTarget = '''
all: $(APPFILE)
2022-04-08 00:59:03 +08:00
$(APPLICATION): $(OBJECTS)
$(APPFILE): $(APPLICATION)
2018-10-22 11:24:13 +08:00
%s
'''
2017-11-24 14:30:11 +08:00
PcdGccMakefile = '''
2025-06-06 16:04:29 -07:00
MAKEROOT ?= $(EDK_TOOLS_PATH) %s Source %s C
2017-11-24 14:30:11 +08:00
LIBS = -lCommon
2025-06-06 16:04:29 -07:00
''' % ( os . sep , os . sep )
2017-11-24 14:30:11 +08:00
2018-04-20 23:51:24 +08:00
variablePattern = re . compile ( r '[\t\s]*0[xX][a-fA-F0-9]+$' )
2018-08-27 09:29:37 +08:00
SkuIdPattern = re . compile ( r '^[a-zA-Z_][a-zA-Z0-9_]*$' )
2018-04-14 04:51:31 +08:00
## regular expressions for finding decimal and hex numbers
2023-12-06 12:27:02 -08:00
Pattern = re . compile ( r '^[1-9]\d*|0$' )
2018-04-14 04:51:31 +08:00
HexPattern = re . compile ( r '0[xX][0-9a-fA-F]+$' )
2018-03-16 17:40:00 +08:00
## Regular expression for finding header file inclusions
from AutoGen.GenMake import gIncludePattern
## Find dependencies for one source file
#
# By searching recursively "#include" directive in file, find out all the
# files needed by given source file. The dependecies will be only searched
# in given search path list.
#
# @param SearchPathList The list of search path
#
# @retval list The list of files the given source file depends on
#
2018-06-25 18:31:33 +08:00
def GetDependencyList ( FileStack , SearchPathList ):
2018-03-16 17:40:00 +08:00
DepDb = dict ()
DependencySet = set ( FileStack )
while len ( FileStack ) > 0 :
F = FileStack . pop ()
FullPathDependList = []
CurrentFileDependencyList = []
if F in DepDb :
CurrentFileDependencyList = DepDb [ F ]
else :
try :
Fd = open ( F , 'r' )
FileContent = Fd . read ()
2018-06-25 18:31:25 +08:00
except BaseException as X :
2018-03-16 17:40:00 +08:00
EdkLogger . error ( "build" , FILE_OPEN_FAILURE , ExtraData = F + " \n\t " + str ( X ))
finally :
if "Fd" in dir ( locals ()):
Fd . close ()
if len ( FileContent ) == 0 :
continue
2018-10-15 08:27:53 +08:00
2019-02-20 23:21:31 +08:00
try :
if FileContent [ 0 ] == 0xff or FileContent [ 0 ] == 0xfe :
FileContent = FileContent . decode ( 'utf-16' )
else :
FileContent = FileContent . decode ()
except :
# The file is not txt file. for example .mcb file
continue
2018-03-16 17:40:00 +08:00
IncludedFileList = gIncludePattern . findall ( FileContent )
for Inc in IncludedFileList :
Inc = Inc . strip ()
Inc = os . path . normpath ( Inc )
CurrentFileDependencyList . append ( Inc )
DepDb [ F ] = CurrentFileDependencyList
CurrentFilePath = os . path . dirname ( F )
PathList = [ CurrentFilePath ] + SearchPathList
for Inc in CurrentFileDependencyList :
for SearchPath in PathList :
FilePath = os . path . join ( SearchPath , Inc )
if not os . path . exists ( FilePath ):
continue
if FilePath not in DependencySet :
FileStack . append ( FilePath )
FullPathDependList . append ( FilePath )
break
DependencySet . update ( FullPathDependList )
DependencyList = list ( DependencySet ) # remove duplicate ones
return DependencyList
2017-11-24 14:30:11 +08:00
class DscBuildData ( PlatformBuildClassObject ):
# dict used to convert part of [Defines] to members of DscBuildData directly
_PROPERTY_ = {
#
# Required Fields
#
TAB_DSC_DEFINES_PLATFORM_NAME : "_PlatformName" ,
TAB_DSC_DEFINES_PLATFORM_GUID : "_Guid" ,
TAB_DSC_DEFINES_PLATFORM_VERSION : "_Version" ,
TAB_DSC_DEFINES_DSC_SPECIFICATION : "_DscSpecification" ,
# TAB_DSC_DEFINES_OUTPUT_DIRECTORY : "_OutputDirectory",
# TAB_DSC_DEFINES_SUPPORTED_ARCHITECTURES : "_SupArchList",
# TAB_DSC_DEFINES_BUILD_TARGETS : "_BuildTargets",
TAB_DSC_DEFINES_SKUID_IDENTIFIER : "_SkuName" ,
# TAB_DSC_DEFINES_FLASH_DEFINITION : "_FlashDefinition",
TAB_DSC_DEFINES_BUILD_NUMBER : "_BuildNumber" ,
TAB_DSC_DEFINES_MAKEFILE_NAME : "_MakefileName" ,
TAB_DSC_DEFINES_BS_BASE_ADDRESS : "_BsBaseAddress" ,
TAB_DSC_DEFINES_RT_BASE_ADDRESS : "_RtBaseAddress" ,
# TAB_DSC_DEFINES_RFC_LANGUAGES : "_RFCLanguages",
# TAB_DSC_DEFINES_ISO_LANGUAGES : "_ISOLanguages",
}
# used to compose dummy library class name for those forced library instances
_NullLibraryNumber = 0
## Constructor of DscBuildData
#
# Initialize object of DscBuildData
#
# @param FilePath The path of platform description file
# @param RawData The raw data of DSC file
# @param BuildDataBase Database used to retrieve module/package information
# @param Arch The target architecture
# @param Platform (not used for DscBuildData)
# @param Macros Macros used for replacement in DSC file
#
2018-04-16 21:52:13 +08:00
def __init__ ( self , FilePath , RawData , BuildDataBase , Arch = TAB_ARCH_COMMON , Target = None , Toolchain = None ):
2017-11-24 14:30:11 +08:00
self . MetaFile = FilePath
self . _RawData = RawData
self . _Bdb = BuildDataBase
self . _Arch = Arch
self . _Target = Target
self . _Toolchain = Toolchain
2017-12-26 13:16:17 +08:00
self . _ToolChainFamily = None
2017-11-24 14:30:11 +08:00
self . _Clear ()
2018-02-28 13:59:19 +08:00
self . WorkspaceDir = os . getenv ( "WORKSPACE" ) if os . getenv ( "WORKSPACE" ) else ""
2017-12-22 20:46:15 +08:00
self . DefaultStores = None
2025-06-06 16:04:29 -07:00
MingwBaseToolsBuild = None
if sys . platform == 'win32' :
MingwBaseToolsBuild = os . getenv ( "BASETOOLS_MINGW_BUILD" )
if MingwBaseToolsBuild is not None :
try :
MingwBaseToolsBuild = int ( MingwBaseToolsBuild )
except :
pass
try :
MingwBaseToolsBuild = bool ( MingwBaseToolsBuild )
except :
pass
if not isinstance ( MingwBaseToolsBuild , bool ):
MingwBaseToolsBuild = False
self . _MingwBaseToolsBuild = MingwBaseToolsBuild
2017-12-22 20:07:54 +08:00
self . SkuIdMgr = SkuClass ( self . SkuName , self . SkuIds )
2021-06-08 10:31:55 +08:00
self . UpdatePcdTypeDict ()
2018-02-28 13:59:19 +08:00
@property
def OutputPath ( self ):
if os . getenv ( "WORKSPACE" ):
2018-06-25 18:31:33 +08:00
return os . path . join ( os . getenv ( "WORKSPACE" ), self . OutputDirectory , self . _Target + "_" + self . _Toolchain , PcdValueInitName )
2018-02-28 13:59:19 +08:00
else :
return os . path . dirname ( self . DscFile )
2017-11-24 14:30:11 +08:00
## XXX[key] = value
def __setitem__ ( self , key , value ):
self . __dict__ [ self . _PROPERTY_ [ key ]] = value
## value = XXX[key]
def __getitem__ ( self , key ):
return self . __dict__ [ self . _PROPERTY_ [ key ]]
## "in" test support
def __contains__ ( self , key ):
return key in self . _PROPERTY_
## Set all internal used members of DscBuildData to None
def _Clear ( self ):
self . _Header = None
self . _PlatformName = None
self . _Guid = None
self . _Version = None
self . _DscSpecification = None
self . _OutputDirectory = None
self . _SupArchList = None
self . _BuildTargets = None
self . _SkuName = None
self . _PcdInfoFlag = None
self . _VarCheckFlag = None
self . _FlashDefinition = None
self . _Prebuild = None
self . _Postbuild = None
self . _BuildNumber = None
self . _MakefileName = None
self . _BsBaseAddress = None
self . _RtBaseAddress = None
self . _SkuIds = None
self . _Modules = None
self . _LibraryInstances = None
self . _LibraryClasses = None
self . _Pcds = None
self . _DecPcds = None
self . _BuildOptions = None
self . _ModuleTypeOptions = None
self . _LoadFixAddress = None
self . _RFCLanguages = None
self . _ISOLanguages = None
self . _VpdToolGuid = None
2018-09-11 06:18:05 +08:00
self . _MacroDict = None
2017-12-22 20:46:15 +08:00
self . DefaultStores = None
2017-11-24 14:30:11 +08:00
## Get current effective macros
2018-09-11 06:18:05 +08:00
@property
def _Macros ( self ):
if self . _MacroDict is None :
self . _MacroDict = {}
self . _MacroDict . update ( GlobalData . gPlatformDefines )
self . _MacroDict . update ( GlobalData . gGlobalDefines )
self . _MacroDict . update ( GlobalData . gCommandLineDefines )
return self . _MacroDict
2017-11-24 14:30:11 +08:00
## Get architecture
2018-09-11 06:18:05 +08:00
@property
def Arch ( self ):
2017-11-24 14:30:11 +08:00
return self . _Arch
2019-04-03 10:17:02 +08:00
@property
def Dir ( self ):
return self . MetaFile . Dir
2017-11-24 14:30:11 +08:00
## Retrieve all information in [Defines] section
#
2019-02-06 15:44:39 +08:00
# (Retrieving all [Defines] information in one-shot is just to save time.)
2017-11-24 14:30:11 +08:00
#
def _GetHeaderInfo ( self ):
RecordList = self . _RawData [ MODEL_META_DATA_HEADER , self . _Arch ]
for Record in RecordList :
Name = Record [ 1 ]
# items defined _PROPERTY_ don't need additional processing
# some special items in [Defines] section need special treatment
if Name == TAB_DSC_DEFINES_OUTPUT_DIRECTORY :
self . _OutputDirectory = NormPath ( Record [ 2 ], self . _Macros )
if ' ' in self . _OutputDirectory :
EdkLogger . error ( "build" , FORMAT_NOT_SUPPORTED , "No space is allowed in OUTPUT_DIRECTORY" ,
File = self . MetaFile , Line = Record [ - 1 ],
ExtraData = self . _OutputDirectory )
elif Name == TAB_DSC_DEFINES_FLASH_DEFINITION :
self . _FlashDefinition = PathClass ( NormPath ( Record [ 2 ], self . _Macros ), GlobalData . gWorkspace )
ErrorCode , ErrorInfo = self . _FlashDefinition . Validate ( '.fdf' )
if ErrorCode != 0 :
EdkLogger . error ( 'build' , ErrorCode , File = self . MetaFile , Line = Record [ - 1 ],
ExtraData = ErrorInfo )
elif Name == TAB_DSC_PREBUILD :
PrebuildValue = Record [ 2 ]
if Record [ 2 ][ 0 ] == '"' :
if Record [ 2 ][ - 1 ] != '"' :
EdkLogger . error ( 'build' , FORMAT_INVALID , 'Missing double quotes in the end of %s statement.' % TAB_DSC_PREBUILD ,
File = self . MetaFile , Line = Record [ - 1 ])
PrebuildValue = Record [ 2 ][ 1 : - 1 ]
self . _Prebuild = PrebuildValue
elif Name == TAB_DSC_POSTBUILD :
PostbuildValue = Record [ 2 ]
if Record [ 2 ][ 0 ] == '"' :
if Record [ 2 ][ - 1 ] != '"' :
EdkLogger . error ( 'build' , FORMAT_INVALID , 'Missing double quotes in the end of %s statement.' % TAB_DSC_POSTBUILD ,
File = self . MetaFile , Line = Record [ - 1 ])
PostbuildValue = Record [ 2 ][ 1 : - 1 ]
self . _Postbuild = PostbuildValue
elif Name == TAB_DSC_DEFINES_SUPPORTED_ARCHITECTURES :
self . _SupArchList = GetSplitValueList ( Record [ 2 ], TAB_VALUE_SPLIT )
elif Name == TAB_DSC_DEFINES_BUILD_TARGETS :
self . _BuildTargets = GetSplitValueList ( Record [ 2 ])
elif Name == TAB_DSC_DEFINES_SKUID_IDENTIFIER :
2018-03-27 04:25:43 +08:00
if self . _SkuName is None :
2017-11-24 14:30:11 +08:00
self . _SkuName = Record [ 2 ]
2017-12-22 20:07:54 +08:00
if GlobalData . gSKUID_CMD :
self . _SkuName = GlobalData . gSKUID_CMD
2017-11-24 14:30:11 +08:00
elif Name == TAB_DSC_DEFINES_PCD_INFO_GENERATION :
self . _PcdInfoFlag = Record [ 2 ]
elif Name == TAB_DSC_DEFINES_PCD_VAR_CHECK_GENERATION :
self . _VarCheckFlag = Record [ 2 ]
elif Name == TAB_FIX_LOAD_TOP_MEMORY_ADDRESS :
try :
self . _LoadFixAddress = int ( Record [ 2 ], 0 )
except :
EdkLogger . error ( "build" , PARAMETER_INVALID , "FIX_LOAD_TOP_MEMORY_ADDRESS %s is not valid dec or hex string" % ( Record [ 2 ]))
elif Name == TAB_DSC_DEFINES_RFC_LANGUAGES :
if not Record [ 2 ] or Record [ 2 ][ 0 ] != '"' or Record [ 2 ][ - 1 ] != '"' or len ( Record [ 2 ]) == 1 :
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"' ,
File = self . MetaFile , Line = Record [ - 1 ])
LanguageCodes = Record [ 2 ][ 1 : - 1 ]
if not LanguageCodes :
EdkLogger . error ( 'build' , FORMAT_NOT_SUPPORTED , 'one or more RFC4646 format language code must be provided for RFC_LANGUAGES statement' ,
File = self . MetaFile , Line = Record [ - 1 ])
LanguageList = GetSplitValueList ( LanguageCodes , TAB_SEMI_COLON_SPLIT )
# check whether there is empty entries in the list
if None in LanguageList :
EdkLogger . error ( 'build' , FORMAT_NOT_SUPPORTED , 'one or more empty language code is in RFC_LANGUAGES statement' ,
File = self . MetaFile , Line = Record [ - 1 ])
self . _RFCLanguages = LanguageList
elif Name == TAB_DSC_DEFINES_ISO_LANGUAGES :
if not Record [ 2 ] or Record [ 2 ][ 0 ] != '"' or Record [ 2 ][ - 1 ] != '"' or len ( Record [ 2 ]) == 1 :
EdkLogger . error ( 'build' , FORMAT_NOT_SUPPORTED , 'language code for ISO_LANGUAGES must have double quotes around it, for example: ISO_LANGUAGES = "engchn"' ,
File = self . MetaFile , Line = Record [ - 1 ])
LanguageCodes = Record [ 2 ][ 1 : - 1 ]
if not LanguageCodes :
EdkLogger . error ( 'build' , FORMAT_NOT_SUPPORTED , 'one or more ISO639-2 format language code must be provided for ISO_LANGUAGES statement' ,
File = self . MetaFile , Line = Record [ - 1 ])
if len ( LanguageCodes ) % 3 :
EdkLogger . error ( 'build' , FORMAT_NOT_SUPPORTED , 'bad ISO639-2 format for ISO_LANGUAGES' ,
File = self . MetaFile , Line = Record [ - 1 ])
LanguageList = []
for i in range ( 0 , len ( LanguageCodes ), 3 ):
LanguageList . append ( LanguageCodes [ i : i + 3 ])
self . _ISOLanguages = LanguageList
2021-11-04 19:28:53 +08:00
elif Name == TAB_DSC_DEFINES_VPD_AUTHENTICATED_VARIABLE_STORE :
if TAB_DSC_DEFINES_VPD_AUTHENTICATED_VARIABLE_STORE not in gCommandLineDefines :
gCommandLineDefines [ TAB_DSC_DEFINES_VPD_AUTHENTICATED_VARIABLE_STORE ] = Record [ 2 ] . strip ()
2017-11-24 14:30:11 +08:00
elif Name == TAB_DSC_DEFINES_VPD_TOOL_GUID :
#
# try to convert GUID to a real UUID value to see whether the GUID is format
# for VPD_TOOL_GUID is correct.
#
try :
uuid . UUID ( Record [ 2 ])
except :
EdkLogger . error ( "build" , FORMAT_INVALID , "Invalid GUID format for VPD_TOOL_GUID" , File = self . MetaFile )
self . _VpdToolGuid = Record [ 2 ]
2021-06-08 10:31:55 +08:00
elif Name == TAB_DSC_DEFINES_PCD_DYNAMIC_AS_DYNAMICEX :
if TAB_DSC_DEFINES_PCD_DYNAMIC_AS_DYNAMICEX not in gCommandLineDefines :
gCommandLineDefines [ TAB_DSC_DEFINES_PCD_DYNAMIC_AS_DYNAMICEX ] = Record [ 2 ] . strip ()
2017-11-24 14:30:11 +08:00
elif Name in self :
self [ Name ] = Record [ 2 ]
# set _Header to non-None in order to avoid database re-querying
self . _Header = 'DUMMY'
## Retrieve platform name
2018-09-11 06:18:05 +08:00
@property
def PlatformName ( self ):
2018-03-27 04:25:43 +08:00
if self . _PlatformName is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _PlatformName is None :
2017-11-24 14:30:11 +08:00
EdkLogger . error ( 'build' , ATTRIBUTE_NOT_AVAILABLE , "No PLATFORM_NAME" , File = self . MetaFile )
return self . _PlatformName
2018-09-11 06:18:05 +08:00
@property
def Platform ( self ):
return self . PlatformName
2017-11-24 14:30:11 +08:00
## Retrieve file guid
2018-09-11 06:18:05 +08:00
@property
def Guid ( self ):
2018-03-27 04:25:43 +08:00
if self . _Guid is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _Guid is None :
2017-11-24 14:30:11 +08:00
EdkLogger . error ( 'build' , ATTRIBUTE_NOT_AVAILABLE , "No PLATFORM_GUID" , File = self . MetaFile )
return self . _Guid
## Retrieve platform version
2018-09-11 06:18:05 +08:00
@property
def Version ( self ):
2018-03-27 04:25:43 +08:00
if self . _Version is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _Version is None :
2017-11-24 14:30:11 +08:00
EdkLogger . error ( 'build' , ATTRIBUTE_NOT_AVAILABLE , "No PLATFORM_VERSION" , File = self . MetaFile )
return self . _Version
## Retrieve OUTPUT_DIRECTORY
2018-09-11 06:18:05 +08:00
@property
def OutputDirectory ( self ):
2018-03-27 04:25:43 +08:00
if self . _OutputDirectory is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _OutputDirectory is None :
2017-11-24 14:30:11 +08:00
self . _OutputDirectory = os . path . join ( "Build" , self . _PlatformName )
return self . _OutputDirectory
## Retrieve SUPPORTED_ARCHITECTURES
2018-09-11 06:18:05 +08:00
@property
def SupArchList ( self ):
2018-03-27 04:25:43 +08:00
if self . _SupArchList is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _SupArchList is None :
2017-11-24 14:30:11 +08:00
EdkLogger . error ( 'build' , ATTRIBUTE_NOT_AVAILABLE , "No SUPPORTED_ARCHITECTURES" , File = self . MetaFile )
return self . _SupArchList
## Retrieve BUILD_TARGETS
2018-09-11 06:18:05 +08:00
@property
def BuildTargets ( self ):
2018-03-27 04:25:43 +08:00
if self . _BuildTargets is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _BuildTargets is None :
2017-11-24 14:30:11 +08:00
EdkLogger . error ( 'build' , ATTRIBUTE_NOT_AVAILABLE , "No BUILD_TARGETS" , File = self . MetaFile )
return self . _BuildTargets
2018-09-11 06:18:05 +08:00
@property
def PcdInfoFlag ( self ):
2018-03-27 04:25:43 +08:00
if self . _PcdInfoFlag is None or self . _PcdInfoFlag . upper () == 'FALSE' :
2017-11-24 14:30:11 +08:00
return False
elif self . _PcdInfoFlag . upper () == 'TRUE' :
return True
else :
return False
2018-09-11 06:18:05 +08:00
@property
def VarCheckFlag ( self ):
2018-03-27 04:25:43 +08:00
if self . _VarCheckFlag is None or self . _VarCheckFlag . upper () == 'FALSE' :
2017-11-24 14:30:11 +08:00
return False
elif self . _VarCheckFlag . upper () == 'TRUE' :
return True
else :
return False
2017-12-22 20:07:54 +08:00
# # Retrieve SKUID_IDENTIFIER
2018-09-11 06:18:05 +08:00
@property
def SkuName ( self ):
2018-03-27 04:25:43 +08:00
if self . _SkuName is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _SkuName is None :
2018-04-16 21:52:13 +08:00
self . _SkuName = TAB_DEFAULT
2017-11-24 14:30:11 +08:00
return self . _SkuName
## Override SKUID_IDENTIFIER
2018-09-11 06:18:05 +08:00
@SkuName.setter
def SkuName ( self , Value ):
2017-11-24 14:30:11 +08:00
self . _SkuName = Value
2018-09-11 06:18:05 +08:00
@property
def FlashDefinition ( self ):
2018-03-27 04:25:43 +08:00
if self . _FlashDefinition is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _FlashDefinition is None :
2017-11-24 14:30:11 +08:00
self . _FlashDefinition = ''
return self . _FlashDefinition
2018-09-11 06:18:05 +08:00
@property
def Prebuild ( self ):
2018-03-27 04:25:43 +08:00
if self . _Prebuild is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _Prebuild is None :
2017-11-24 14:30:11 +08:00
self . _Prebuild = ''
return self . _Prebuild
2018-09-11 06:18:05 +08:00
@property
def Postbuild ( self ):
2018-03-27 04:25:43 +08:00
if self . _Postbuild is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _Postbuild is None :
2017-11-24 14:30:11 +08:00
self . _Postbuild = ''
return self . _Postbuild
## Retrieve FLASH_DEFINITION
2018-09-11 06:18:05 +08:00
@property
def BuildNumber ( self ):
2018-03-27 04:25:43 +08:00
if self . _BuildNumber is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _BuildNumber is None :
2017-11-24 14:30:11 +08:00
self . _BuildNumber = ''
return self . _BuildNumber
## Retrieve MAKEFILE_NAME
2018-09-11 06:18:05 +08:00
@property
def MakefileName ( self ):
2018-03-27 04:25:43 +08:00
if self . _MakefileName is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _MakefileName is None :
2017-11-24 14:30:11 +08:00
self . _MakefileName = ''
return self . _MakefileName
## Retrieve BsBaseAddress
2018-09-11 06:18:05 +08:00
@property
def BsBaseAddress ( self ):
2018-03-27 04:25:43 +08:00
if self . _BsBaseAddress is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _BsBaseAddress is None :
2017-11-24 14:30:11 +08:00
self . _BsBaseAddress = ''
return self . _BsBaseAddress
## Retrieve RtBaseAddress
2018-09-11 06:18:05 +08:00
@property
def RtBaseAddress ( self ):
2018-03-27 04:25:43 +08:00
if self . _RtBaseAddress is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _RtBaseAddress is None :
2017-11-24 14:30:11 +08:00
self . _RtBaseAddress = ''
return self . _RtBaseAddress
## Retrieve the top address for the load fix address
2018-09-11 06:18:05 +08:00
@property
def LoadFixAddress ( self ):
2018-03-27 04:25:43 +08:00
if self . _LoadFixAddress is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _LoadFixAddress is None :
2017-11-24 14:30:11 +08:00
self . _LoadFixAddress = self . _Macros . get ( TAB_FIX_LOAD_TOP_MEMORY_ADDRESS , '0' )
try :
self . _LoadFixAddress = int ( self . _LoadFixAddress , 0 )
except :
EdkLogger . error ( "build" , PARAMETER_INVALID , "FIX_LOAD_TOP_MEMORY_ADDRESS %s is not valid dec or hex string" % ( self . _LoadFixAddress ))
#
# If command line defined, should override the value in DSC file.
#
2018-04-10 22:20:06 +08:00
if 'FIX_LOAD_TOP_MEMORY_ADDRESS' in GlobalData . gCommandLineDefines :
2017-11-24 14:30:11 +08:00
try :
self . _LoadFixAddress = int ( GlobalData . gCommandLineDefines [ 'FIX_LOAD_TOP_MEMORY_ADDRESS' ], 0 )
except :
EdkLogger . error ( "build" , PARAMETER_INVALID , "FIX_LOAD_TOP_MEMORY_ADDRESS %s is not valid dec or hex string" % ( GlobalData . gCommandLineDefines [ 'FIX_LOAD_TOP_MEMORY_ADDRESS' ]))
if self . _LoadFixAddress < 0 :
EdkLogger . error ( "build" , PARAMETER_INVALID , "FIX_LOAD_TOP_MEMORY_ADDRESS is set to the invalid negative value 0x %x " % ( self . _LoadFixAddress ))
if self . _LoadFixAddress != 0xFFFFFFFFFFFFFFFF and self . _LoadFixAddress % 0x1000 != 0 :
EdkLogger . error ( "build" , PARAMETER_INVALID , "FIX_LOAD_TOP_MEMORY_ADDRESS is set to the invalid unaligned 4K value 0x %x " % ( self . _LoadFixAddress ))
return self . _LoadFixAddress
## Retrieve RFCLanguage filter
2018-09-11 06:18:05 +08:00
@property
def RFCLanguages ( self ):
2018-03-27 04:25:43 +08:00
if self . _RFCLanguages is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _RFCLanguages is None :
2017-11-24 14:30:11 +08:00
self . _RFCLanguages = []
return self . _RFCLanguages
## Retrieve ISOLanguage filter
2018-09-11 06:18:05 +08:00
@property
def ISOLanguages ( self ):
2018-03-27 04:25:43 +08:00
if self . _ISOLanguages is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _ISOLanguages is None :
2017-11-24 14:30:11 +08:00
self . _ISOLanguages = []
return self . _ISOLanguages
2018-09-11 06:18:05 +08:00
2017-11-24 14:30:11 +08:00
## Retrieve the GUID string for VPD tool
2018-09-11 06:18:05 +08:00
@property
def VpdToolGuid ( self ):
2018-03-27 04:25:43 +08:00
if self . _VpdToolGuid is None :
if self . _Header is None :
2017-11-24 14:30:11 +08:00
self . _GetHeaderInfo ()
2018-03-27 04:25:43 +08:00
if self . _VpdToolGuid is None :
2017-11-24 14:30:11 +08:00
self . _VpdToolGuid = ''
return self . _VpdToolGuid
## Retrieve [SkuIds] section information
2018-09-11 06:18:05 +08:00
@property
def SkuIds ( self ):
2018-03-27 04:25:43 +08:00
if self . _SkuIds is None :
2018-04-04 05:03:09 +08:00
self . _SkuIds = OrderedDict ()
2017-11-24 14:30:11 +08:00
RecordList = self . _RawData [ MODEL_EFI_SKU_ID , self . _Arch ]
for Record in RecordList :
2018-04-20 23:51:42 +08:00
if not Record [ 0 ]:
2017-11-24 14:30:11 +08:00
EdkLogger . error ( 'build' , FORMAT_INVALID , 'No Sku ID number' ,
File = self . MetaFile , Line = Record [ - 1 ])
2018-04-20 23:51:42 +08:00
if not Record [ 1 ]:
2017-11-24 14:30:11 +08:00
EdkLogger . error ( 'build' , FORMAT_INVALID , 'No Sku ID name' ,
File = self . MetaFile , Line = Record [ - 1 ])
2018-04-14 04:51:31 +08:00
if not Pattern . match ( Record [ 0 ]) and not HexPattern . match ( Record [ 0 ]):
2018-01-22 13:38:39 +08:00
EdkLogger . error ( 'build' , FORMAT_INVALID , "The format of the Sku ID number is invalid. It only support Integer and HexNumber" ,
2017-12-22 20:46:15 +08:00
File = self . MetaFile , Line = Record [ - 1 ])
2018-08-27 09:29:37 +08:00
if not SkuIdPattern . match ( Record [ 1 ]) or ( Record [ 2 ] and not SkuIdPattern . match ( Record [ 2 ])):
EdkLogger . error ( 'build' , FORMAT_INVALID , "The format of the Sku ID name is invalid. The correct format is '(a-zA-Z_)(a-zA-Z0-9_)*'" ,
2017-12-22 20:46:15 +08:00
File = self . MetaFile , Line = Record [ - 1 ])
2018-04-14 04:51:29 +08:00
self . _SkuIds [ Record [ 1 ] . upper ()] = ( str ( DscBuildData . ToInt ( Record [ 0 ])), Record [ 1 ] . upper (), Record [ 2 ] . upper ())
2018-04-16 21:52:13 +08:00
if TAB_DEFAULT not in self . _SkuIds :
self . _SkuIds [ TAB_DEFAULT ] = ( "0" , TAB_DEFAULT , TAB_DEFAULT )
if TAB_COMMON not in self . _SkuIds :
self . _SkuIds [ TAB_COMMON ] = ( "0" , TAB_DEFAULT , TAB_DEFAULT )
2017-11-24 14:30:11 +08:00
return self . _SkuIds
2018-04-14 04:51:29 +08:00
@staticmethod
def ToInt ( intstr ):
2018-06-25 18:31:33 +08:00
return int ( intstr , 16 ) if intstr . upper () . startswith ( "0X" ) else int ( intstr )
2018-04-14 04:51:29 +08:00
2017-12-22 20:46:15 +08:00
def _GetDefaultStores ( self ):
2018-03-27 04:25:43 +08:00
if self . DefaultStores is None :
2018-04-04 05:03:09 +08:00
self . DefaultStores = OrderedDict ()
2017-12-22 20:46:15 +08:00
RecordList = self . _RawData [ MODEL_EFI_DEFAULT_STORES , self . _Arch ]
for Record in RecordList :
2018-04-20 23:51:42 +08:00
if not Record [ 0 ]:
2017-12-22 20:46:15 +08:00
EdkLogger . error ( 'build' , FORMAT_INVALID , 'No DefaultStores ID number' ,
File = self . MetaFile , Line = Record [ - 1 ])
2018-04-20 23:51:42 +08:00
if not Record [ 1 ]:
2017-12-22 20:46:15 +08:00
EdkLogger . error ( 'build' , FORMAT_INVALID , 'No DefaultStores ID name' ,
File = self . MetaFile , Line = Record [ - 1 ])
2018-04-14 04:51:31 +08:00
if not Pattern . match ( Record [ 0 ]) and not HexPattern . match ( Record [ 0 ]):
2018-01-22 13:46:52 +08:00
EdkLogger . error ( 'build' , FORMAT_INVALID , "The format of the DefaultStores ID number is invalid. It only support Integer and HexNumber" ,
File = self . MetaFile , Line = Record [ - 1 ])
if not IsValidWord ( Record [ 1 ]):
EdkLogger . error ( 'build' , FORMAT_INVALID , "The format of the DefaultStores ID name is invalid. The correct format is '(a-zA-Z0-9_)(a-zA-Z0-9_-.)*'" ,
File = self . MetaFile , Line = Record [ - 1 ])
2018-06-25 18:31:33 +08:00
self . DefaultStores [ Record [ 1 ] . upper ()] = ( DscBuildData . ToInt ( Record [ 0 ]), Record [ 1 ] . upper ())
2017-12-22 20:46:15 +08:00
if TAB_DEFAULT_STORES_DEFAULT not in self . DefaultStores :
2018-06-25 18:31:33 +08:00
self . DefaultStores [ TAB_DEFAULT_STORES_DEFAULT ] = ( 0 , TAB_DEFAULT_STORES_DEFAULT )
2018-04-10 22:20:06 +08:00
GlobalData . gDefaultStores = sorted ( self . DefaultStores . keys ())
2017-12-22 20:46:15 +08:00
return self . DefaultStores
2017-11-24 14:30:11 +08:00
2019-01-10 17:03:29 +08:00
def OverrideDuplicateModule ( self ):
RecordList = self . _RawData [ MODEL_META_DATA_COMPONENT , self . _Arch ]
Macros = self . _Macros
Components = {}
for Record in RecordList :
ModuleId = Record [ 6 ]
file_guid = self . _RawData [ MODEL_META_DATA_HEADER , self . _Arch , None , ModuleId ]
file_guid_str = file_guid [ 0 ][ 2 ] if file_guid else "NULL"
ModuleFile = PathClass ( NormPath ( Record [ 0 ], Macros ), GlobalData . gWorkspace , Arch = self . _Arch )
if self . _Arch != TAB_ARCH_COMMON and ( file_guid_str , str ( ModuleFile )) in Components :
self . _RawData . DisableOverrideComponent ( Components [( file_guid_str , str ( ModuleFile ))])
Components [( file_guid_str , str ( ModuleFile ))] = ModuleId
self . _RawData . _PostProcessed = False
2019-11-14 09:27:42 +08:00
## Retrieve packages this Platform depends on
@cached_property
def Packages ( self ):
RetVal = set ()
RecordList = self . _RawData [ MODEL_META_DATA_PACKAGE , self . _Arch ]
Macros = self . _Macros
for Record in RecordList :
File = PathClass ( NormPath ( Record [ 0 ], Macros ), GlobalData . gWorkspace , Arch = self . _Arch )
# check the file validation
ErrorCode , ErrorInfo = File . Validate ( '.dec' )
if ErrorCode != 0 :
LineNo = Record [ - 1 ]
EdkLogger . error ( 'build' , ErrorCode , ExtraData = ErrorInfo , File = self . MetaFile , Line = LineNo )
# parse this package now. we need it to get protocol/ppi/guid value
RetVal . add ( self . _Bdb [ File , self . _Arch , self . _Target , self . _Toolchain ])
return RetVal
2017-11-24 14:30:11 +08:00
## Retrieve [Components] section information
2018-09-11 06:18:05 +08:00
@property
def Modules ( self ):
2018-03-27 04:25:43 +08:00
if self . _Modules is not None :
2017-11-24 14:30:11 +08:00
return self . _Modules
2019-01-10 17:03:29 +08:00
self . OverrideDuplicateModule ()
2018-04-04 05:03:09 +08:00
self . _Modules = OrderedDict ()
2017-11-24 14:30:11 +08:00
RecordList = self . _RawData [ MODEL_META_DATA_COMPONENT , self . _Arch ]
Macros = self . _Macros
for Record in RecordList :
ModuleFile = PathClass ( NormPath ( Record [ 0 ], Macros ), GlobalData . gWorkspace , Arch = self . _Arch )
2017-12-22 20:46:15 +08:00
ModuleId = Record [ 6 ]
LineNo = Record [ 7 ]
2017-11-24 14:30:11 +08:00
# check the file validation
ErrorCode , ErrorInfo = ModuleFile . Validate ( '.inf' )
if ErrorCode != 0 :
EdkLogger . error ( 'build' , ErrorCode , File = self . MetaFile , Line = LineNo ,
ExtraData = ErrorInfo )
2020-11-04 11:01:39 +08:00
ModuleBuildData = self . _Bdb [ ModuleFile , self . _Arch , self . _Target , self . _Toolchain ]
2017-11-24 14:30:11 +08:00
Module = ModuleBuildClassObject ()
Module . MetaFile = ModuleFile
2020-11-04 11:01:39 +08:00
Module . Guid = ModuleBuildData . Guid
2017-11-24 14:30:11 +08:00
# get module private library instance
RecordList = self . _RawData [ MODEL_EFI_LIBRARY_CLASS , self . _Arch , None , ModuleId ]
for Record in RecordList :
LibraryClass = Record [ 0 ]
LibraryPath = PathClass ( NormPath ( Record [ 1 ], Macros ), GlobalData . gWorkspace , Arch = self . _Arch )
LineNo = Record [ - 1 ]
# check the file validation
ErrorCode , ErrorInfo = LibraryPath . Validate ( '.inf' )
if ErrorCode != 0 :
EdkLogger . error ( 'build' , ErrorCode , File = self . MetaFile , Line = LineNo ,
ExtraData = ErrorInfo )
if LibraryClass == '' or LibraryClass == 'NULL' :
self . _NullLibraryNumber += 1
LibraryClass = 'NULL %d ' % self . _NullLibraryNumber
EdkLogger . verbose ( "Found forced library for %s \n\t %s [ %s ]" % ( ModuleFile , LibraryPath , LibraryClass ))
Module . LibraryClasses [ LibraryClass ] = LibraryPath
if LibraryPath not in self . LibraryInstances :
self . LibraryInstances . append ( LibraryPath )
2020-11-04 11:01:39 +08:00
S_PcdSet = []
2017-11-24 14:30:11 +08:00
# get module private PCD setting
for Type in [ MODEL_PCD_FIXED_AT_BUILD , MODEL_PCD_PATCHABLE_IN_MODULE , \
MODEL_PCD_FEATURE_FLAG , MODEL_PCD_DYNAMIC , MODEL_PCD_DYNAMIC_EX ]:
RecordList = self . _RawData [ Type , self . _Arch , None , ModuleId ]
2018-06-25 18:31:33 +08:00
for TokenSpaceGuid , PcdCName , Setting , Dummy1 , Dummy2 , Dummy3 , Dummy4 , Dummy5 in RecordList :
2017-11-24 14:30:11 +08:00
TokenList = GetSplitValueList ( Setting )
DefaultValue = TokenList [ 0 ]
2018-02-26 15:36:47 +08:00
# the format is PcdName| Value | VOID* | MaxDatumSize
if len ( TokenList ) > 2 :
MaxDatumSize = TokenList [ 2 ]
2017-11-24 14:30:11 +08:00
else :
MaxDatumSize = ''
TypeString = self . _PCD_TYPE_STRING_ [ Type ]
2020-11-04 11:01:39 +08:00
TCName , PCName , DimensionAttr , Field = self . ParsePcdNameStruct ( TokenSpaceGuid , PcdCName )
if ( "." in TokenSpaceGuid or "[" in PcdCName ):
S_PcdSet . append ([ TCName , PCName , DimensionAttr , Field , ModuleBuildData . Guid , "" , Dummy5 , AnalyzePcdExpression ( Setting )[ 0 ]])
DefaultValue = ''
if ( PCName , TCName ) not in Module . Pcds :
Pcd = PcdClassObject (
PCName ,
TCName ,
TypeString ,
'' ,
DefaultValue ,
'' ,
MaxDatumSize ,
{},
False ,
None ,
IsDsc = True )
Module . Pcds [ PCName , TCName ] = Pcd
Module . StrPcdSet = S_PcdSet
for TCName , PCName , _ , _ , _ , _ , _ , _ in S_PcdSet :
if ( PCName , TCName ) in Module . Pcds :
Module . StrPcdOverallValue [( PCName , TCName )] = Module . Pcds [( PCName , TCName )] . DefaultValue , self . MetaFile , Dummy5
2017-11-24 14:30:11 +08:00
# get module private build options
RecordList = self . _RawData [ MODEL_META_DATA_BUILD_OPTION , self . _Arch , None , ModuleId ]
2018-06-25 18:31:33 +08:00
for ToolChainFamily , ToolChain , Option , Dummy1 , Dummy2 , Dummy3 , Dummy4 , Dummy5 in RecordList :
2017-11-24 14:30:11 +08:00
if ( ToolChainFamily , ToolChain ) not in Module . BuildOptions :
Module . BuildOptions [ ToolChainFamily , ToolChain ] = Option
else :
OptionString = Module . BuildOptions [ ToolChainFamily , ToolChain ]
Module . BuildOptions [ ToolChainFamily , ToolChain ] = OptionString + " " + Option
RecordList = self . _RawData [ MODEL_META_DATA_HEADER , self . _Arch , None , ModuleId ]
if RecordList :
if len ( RecordList ) != 1 :
EdkLogger . error ( 'build' , OPTION_UNKNOWN , 'Only FILE_GUID can be listed in <Defines> section.' ,
File = self . MetaFile , ExtraData = str ( ModuleFile ), Line = LineNo )
ModuleFile = ProcessDuplicatedInf ( ModuleFile , RecordList [ 0 ][ 2 ], GlobalData . gWorkspace )
ModuleFile . Arch = self . _Arch
2020-11-04 11:01:39 +08:00
Module . Guid = RecordList [ 0 ][ 2 ]
for item in Module . StrPcdSet :
item [ 4 ] = RecordList [ 0 ][ 2 ]
2017-11-24 14:30:11 +08:00
self . _Modules [ ModuleFile ] = Module
return self . _Modules
## Retrieve all possible library instances used in this platform
2018-09-11 06:18:05 +08:00
@property
def LibraryInstances ( self ):
2018-03-27 04:25:43 +08:00
if self . _LibraryInstances is None :
2018-09-11 06:18:05 +08:00
self . LibraryClasses
2017-11-24 14:30:11 +08:00
return self . _LibraryInstances
## Retrieve [LibraryClasses] information
2018-09-11 06:18:05 +08:00
@property
def LibraryClasses ( self ):
2018-03-27 04:25:43 +08:00
if self . _LibraryClasses is None :
2017-11-24 14:30:11 +08:00
self . _LibraryInstances = []
#
# tdict is a special dict kind of type, used for selecting correct
# library instance for given library class and module type
#
LibraryClassDict = tdict ( True , 3 )
# track all library class names
LibraryClassSet = set ()
RecordList = self . _RawData [ MODEL_EFI_LIBRARY_CLASS , self . _Arch , None , - 1 ]
Macros = self . _Macros
for Record in RecordList :
2018-06-25 18:31:33 +08:00
LibraryClass , LibraryInstance , Dummy , Arch , ModuleType , Dummy , Dummy , LineNo = Record
2017-11-24 14:30:11 +08:00
if LibraryClass == '' or LibraryClass == 'NULL' :
self . _NullLibraryNumber += 1
LibraryClass = 'NULL %d ' % self . _NullLibraryNumber
EdkLogger . verbose ( "Found forced library for arch= %s \n\t %s [ %s ]" % ( Arch , LibraryInstance , LibraryClass ))
LibraryClassSet . add ( LibraryClass )
LibraryInstance = PathClass ( NormPath ( LibraryInstance , Macros ), GlobalData . gWorkspace , Arch = self . _Arch )
# check the file validation
ErrorCode , ErrorInfo = LibraryInstance . Validate ( '.inf' )
if ErrorCode != 0 :
EdkLogger . error ( 'build' , ErrorCode , File = self . MetaFile , Line = LineNo ,
ExtraData = ErrorInfo )
2018-04-16 21:52:13 +08:00
if ModuleType != TAB_COMMON and ModuleType not in SUP_MODULE_LIST :
2017-11-24 14:30:11 +08:00
EdkLogger . error ( 'build' , OPTION_UNKNOWN , "Unknown module type [ %s ]" % ModuleType ,
File = self . MetaFile , ExtraData = LibraryInstance , Line = LineNo )
2022-08-26 10:06:20 +08:00
LibraryClassDict [ Arch , ModuleType , LibraryClass ] = LibraryInstance
2017-11-24 14:30:11 +08:00
if LibraryInstance not in self . _LibraryInstances :
self . _LibraryInstances . append ( LibraryInstance )
# resolve the specific library instance for each class and each module type
self . _LibraryClasses = tdict ( True )
for LibraryClass in LibraryClassSet :
# try all possible module types
for ModuleType in SUP_MODULE_LIST :
2022-08-26 10:06:20 +08:00
LibraryInstance = LibraryClassDict [ self . _Arch , ModuleType , LibraryClass ]
2018-03-27 04:25:43 +08:00
if LibraryInstance is None :
2017-11-24 14:30:11 +08:00
continue
self . _LibraryClasses [ LibraryClass , ModuleType ] = LibraryInstance
RecordList = self . _RawData [ MODEL_EFI_LIBRARY_INSTANCE , self . _Arch ]
for Record in RecordList :
File = PathClass ( NormPath ( Record [ 0 ], Macros ), GlobalData . gWorkspace , Arch = self . _Arch )
LineNo = Record [ - 1 ]
# check the file validation
ErrorCode , ErrorInfo = File . Validate ( '.inf' )
if ErrorCode != 0 :
EdkLogger . error ( 'build' , ErrorCode , File = self . MetaFile , Line = LineNo ,
ExtraData = ErrorInfo )
if File not in self . _LibraryInstances :
self . _LibraryInstances . append ( File )
#
# we need the module name as the library class name, so we have
# to parse it here. (self._Bdb[] will trigger a file parse if it
# hasn't been parsed)
#
Library = self . _Bdb [ File , self . _Arch , self . _Target , self . _Toolchain ]
self . _LibraryClasses [ Library . BaseName , ':dummy:' ] = Library
return self . _LibraryClasses
def _ValidatePcd ( self , PcdCName , TokenSpaceGuid , Setting , PcdType , LineNo ):
2018-12-13 16:16:25 +08:00
if not self . _DecPcds :
2017-12-22 20:04:04 +08:00
2017-11-24 14:30:11 +08:00
FdfInfList = []
if GlobalData . gFdfParser :
FdfInfList = GlobalData . gFdfParser . Profile . InfList
PkgSet = set ()
for Inf in FdfInfList :
ModuleFile = PathClass ( NormPath ( Inf ), GlobalData . gWorkspace , Arch = self . _Arch )
if ModuleFile in self . _Modules :
continue
ModuleData = self . _Bdb [ ModuleFile , self . _Arch , self . _Target , self . _Toolchain ]
PkgSet . update ( ModuleData . Packages )
2019-11-14 09:27:42 +08:00
if self . Packages :
PkgSet . update ( self . Packages )
2018-06-25 18:31:33 +08:00
self . _DecPcds , self . _GuidDict = GetDeclaredPcd ( self , self . _Bdb , self . _Arch , self . _Target , self . _Toolchain , PkgSet )
2018-02-07 21:37:26 +08:00
self . _GuidDict . update ( GlobalData . gPlatformPcds )
2017-12-22 20:04:04 +08:00
if ( PcdCName , TokenSpaceGuid ) not in self . _DecPcds :
2017-11-24 14:30:11 +08:00
EdkLogger . error ( 'build' , PARSER_ERROR ,
2018-08-29 23:15:55 +08:00
"Pcd ( %s . %s ) defined in DSC is not declared in DEC files referenced in INF files in FDF. Arch: [' %s ']" % ( TokenSpaceGuid , PcdCName , self . _Arch ),
2017-11-24 14:30:11 +08:00
File = self . MetaFile , Line = LineNo )
ValueList , IsValid , Index = AnalyzeDscPcd ( Setting , PcdType , self . _DecPcds [ PcdCName , TokenSpaceGuid ] . DatumType )
2017-12-01 14:15:59 +08:00
if not IsValid :
if PcdType not in [ MODEL_PCD_FEATURE_FLAG , MODEL_PCD_FIXED_AT_BUILD ]:
EdkLogger . error ( 'build' , FORMAT_INVALID , "Pcd format incorrect." , File = self . MetaFile , Line = LineNo ,
ExtraData = " %s . %s | %s " % ( TokenSpaceGuid , PcdCName , Setting ))
else :
if ValueList [ 2 ] == '-1' :
EdkLogger . error ( 'build' , FORMAT_INVALID , "Pcd format incorrect." , File = self . MetaFile , Line = LineNo ,
ExtraData = " %s . %s | %s " % ( TokenSpaceGuid , PcdCName , Setting ))
2018-01-27 00:28:05 +08:00
if ValueList [ Index ]:
DatumType = self . _DecPcds [ PcdCName , TokenSpaceGuid ] . DatumType
2018-11-07 17:18:34 +08:00
if "{CODE(" not in ValueList [ Index ]:
try :
ValueList [ Index ] = ValueExpressionEx ( ValueList [ Index ], DatumType , self . _GuidDict )( True )
except BadExpression as Value :
EdkLogger . error ( 'Parser' , FORMAT_INVALID , Value , File = self . MetaFile , Line = LineNo ,
ExtraData = "PCD [ %s . %s ] Value \" %s \" " % (
TokenSpaceGuid , PcdCName , ValueList [ Index ]))
except EvaluationException as Excpt :
if hasattr ( Excpt , 'Pcd' ):
if Excpt . Pcd in GlobalData . gPlatformOtherPcds :
EdkLogger . error ( 'Parser' , FORMAT_INVALID , "Cannot use this PCD ( %s ) in an expression as"
" it must be defined in a [PcdsFixedAtBuild] or [PcdsFeatureFlag] section"
" of the DSC file" % Excpt . Pcd ,
File = self . MetaFile , Line = LineNo )
else :
EdkLogger . error ( 'Parser' , FORMAT_INVALID , "PCD ( %s ) is not defined in DSC file" % Excpt . Pcd ,
File = self . MetaFile , Line = LineNo )
2017-11-24 14:30:11 +08:00
else :
2018-11-07 17:18:34 +08:00
EdkLogger . error ( 'Parser' , FORMAT_INVALID , "Invalid expression: %s " % str ( Excpt ),
2017-11-24 14:30:11 +08:00
File = self . MetaFile , Line = LineNo )
2018-01-27 00:28:05 +08:00
2017-11-24 14:30:11 +08:00
if ValueList [ Index ]:
Valid , ErrStr = CheckPcdDatum ( self . _DecPcds [ PcdCName , TokenSpaceGuid ] . DatumType , ValueList [ Index ])
if not Valid :
EdkLogger . error ( 'build' , FORMAT_INVALID , ErrStr , File = self . MetaFile , Line = LineNo ,
ExtraData = " %s . %s " % ( TokenSpaceGuid , PcdCName ))
2018-08-23 12:40:37 +08:00
if PcdType in ( MODEL_PCD_DYNAMIC_DEFAULT , MODEL_PCD_DYNAMIC_EX_DEFAULT , MODEL_PCD_FIXED_AT_BUILD , MODEL_PCD_PATCHABLE_IN_MODULE ):
2019-05-09 17:19:56 +08:00
if self . _DecPcds [ PcdCName , TokenSpaceGuid ] . DatumType . strip () != ValueList [ 1 ] . strip ():
2019-05-07 15:14:14 +08:00
DecPcd = self . _DecPcds [ PcdCName , TokenSpaceGuid ]
EdkLogger . error ( 'build' , FORMAT_INVALID ,
"Pcd datumtype used in DSC file is not the same as its declaration. DatumType: %s " % DecPcd . DatumType ,
File = self . MetaFile , Line = LineNo ,
ExtraData = "Dsc: %s . %s | %s \n Dec: %s . %s | %s | %s | %s " % ( TokenSpaceGuid , PcdCName , Setting , TokenSpaceGuid , \
PcdCName , DecPcd . DefaultValue , DecPcd . DatumType , DecPcd . TokenValue ))
2018-01-27 00:28:05 +08:00
if ( TokenSpaceGuid + '.' + PcdCName ) in GlobalData . gPlatformPcds :
if GlobalData . gPlatformPcds [ TokenSpaceGuid + '.' + PcdCName ] != ValueList [ Index ]:
GlobalData . gPlatformPcds [ TokenSpaceGuid + '.' + PcdCName ] = ValueList [ Index ]
2022-04-18 16:15:21 +08:00
GlobalData . gPlatformFinalPcds [ TokenSpaceGuid + '.' + PcdCName ] = ValueList [ Index ]
2017-11-24 14:30:11 +08:00
return ValueList
2018-06-25 18:31:33 +08:00
def _FilterPcdBySkuUsage ( self , Pcds ):
2017-12-22 20:46:15 +08:00
available_sku = self . SkuIdMgr . AvailableSkuIdSet
sku_usage = self . SkuIdMgr . SkuUsageType
if sku_usage == SkuClass . SINGLE :
for pcdname in Pcds :
pcd = Pcds [ pcdname ]
2018-04-16 21:52:13 +08:00
Pcds [ pcdname ] . SkuInfoList = { TAB_DEFAULT : pcd . SkuInfoList [ skuid ] for skuid in pcd . SkuInfoList if skuid in available_sku }
2018-06-25 18:31:35 +08:00
if isinstance ( pcd , StructurePcd ) and pcd . SkuOverrideValues :
2018-04-16 21:52:13 +08:00
Pcds [ pcdname ] . SkuOverrideValues = { TAB_DEFAULT : pcd . SkuOverrideValues [ skuid ] for skuid in pcd . SkuOverrideValues if skuid in available_sku }
2017-12-22 20:46:15 +08:00
else :
for pcdname in Pcds :
pcd = Pcds [ pcdname ]
Pcds [ pcdname ] . SkuInfoList = { skuid : pcd . SkuInfoList [ skuid ] for skuid in pcd . SkuInfoList if skuid in available_sku }
2018-06-25 18:31:35 +08:00
if isinstance ( pcd , StructurePcd ) and pcd . SkuOverrideValues :
2017-12-01 22:00:07 +08:00
Pcds [ pcdname ] . SkuOverrideValues = { skuid : pcd . SkuOverrideValues [ skuid ] for skuid in pcd . SkuOverrideValues if skuid in available_sku }
2017-12-22 20:46:15 +08:00
return Pcds
2018-09-11 06:18:05 +08:00
2018-06-25 18:31:33 +08:00
def CompleteHiiPcdsDefaultStores ( self , Pcds ):
2017-12-22 20:04:04 +08:00
HiiPcd = [ Pcds [ pcd ] for pcd in Pcds if Pcds [ pcd ] . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ], self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ]]]
DefaultStoreMgr = DefaultStore ( self . DefaultStores )
for pcd in HiiPcd :
for skuid in pcd . SkuInfoList :
skuobj = pcd . SkuInfoList . get ( skuid )
2018-04-11 07:17:20 +08:00
if TAB_DEFAULT_STORES_DEFAULT not in skuobj . DefaultStoreDict :
2018-04-28 06:32:52 +08:00
PcdDefaultStoreSet = set ( defaultstorename for defaultstorename in skuobj . DefaultStoreDict )
2017-12-22 20:04:04 +08:00
mindefaultstorename = DefaultStoreMgr . GetMin ( PcdDefaultStoreSet )
2018-12-09 21:44:13 +08:00
skuobj . DefaultStoreDict [ TAB_DEFAULT_STORES_DEFAULT ] = skuobj . DefaultStoreDict [ mindefaultstorename ]
2017-12-22 20:04:04 +08:00
return Pcds
2018-01-31 16:49:14 +08:00
def RecoverCommandLinePcd ( self ):
2018-03-08 13:56:21 +08:00
def UpdateCommandLineValue ( pcd ):
if pcd . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_FIXED_AT_BUILD ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_PATCHABLE_IN_MODULE ]]:
pcd . PcdValueFromComm = pcd . DefaultValue
elif pcd . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ], self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ]]:
2018-04-16 21:52:13 +08:00
pcd . PcdValueFromComm = pcd . SkuInfoList . get ( TAB_DEFAULT ) . HiiDefaultValue
2018-03-08 13:56:21 +08:00
else :
2018-04-16 21:52:13 +08:00
pcd . PcdValueFromComm = pcd . SkuInfoList . get ( TAB_DEFAULT ) . DefaultValue
2018-03-08 13:56:21 +08:00
for pcd in self . _Pcds :
2018-06-25 18:31:33 +08:00
if isinstance ( self . _Pcds [ pcd ], StructurePcd ) and ( self . _Pcds [ pcd ] . PcdValueFromComm or self . _Pcds [ pcd ] . PcdFieldValueFromComm ):
2018-03-08 13:56:21 +08:00
UpdateCommandLineValue ( self . _Pcds [ pcd ])
2018-01-31 16:49:14 +08:00
def __ParsePcdFromCommandLine ( self ):
if GlobalData . BuildOptionPcd :
for i , pcd in enumerate ( GlobalData . BuildOptionPcd ):
2018-06-25 18:31:35 +08:00
if isinstance ( pcd , tuple ):
2018-01-31 16:49:14 +08:00
continue
( pcdname , pcdvalue ) = pcd . split ( '=' )
if not pcdvalue :
EdkLogger . error ( 'build' , AUTOGEN_ERROR , "No Value specified for the PCD %s ." % ( pcdname ))
if '.' in pcdname :
2018-06-25 18:31:33 +08:00
( Name1 , Name2 ) = pcdname . split ( '.' , 1 )
2018-01-31 16:49:14 +08:00
if "." in Name2 :
2018-06-25 18:31:33 +08:00
( Name3 , FieldName ) = Name2 . split ( "." , 1 )
if (( Name3 , Name1 )) in self . DecPcds :
2018-01-31 16:49:14 +08:00
HasTokenSpace = True
TokenCName = Name3
TokenSpaceGuidCName = Name1
else :
FieldName = Name2
TokenCName = Name1
TokenSpaceGuidCName = ''
HasTokenSpace = False
else :
2018-06-25 18:31:33 +08:00
if (( Name2 , Name1 )) in self . DecPcds :
2018-01-31 16:49:14 +08:00
HasTokenSpace = True
TokenCName = Name2
TokenSpaceGuidCName = Name1
FieldName = ""
else :
FieldName = Name2
TokenCName = Name1
TokenSpaceGuidCName = ''
HasTokenSpace = False
else :
FieldName = ""
TokenCName = pcdname
TokenSpaceGuidCName = ''
HasTokenSpace = False
TokenSpaceGuidCNameList = []
FoundFlag = False
PcdDatumType = ''
2018-03-07 14:14:43 +08:00
DisplayName = TokenCName
if FieldName :
DisplayName = TokenCName + '.' + FieldName
2018-01-31 16:49:14 +08:00
if not HasTokenSpace :
for key in self . DecPcds :
2018-03-07 14:14:43 +08:00
PcdItem = self . DecPcds [ key ]
if TokenCName == PcdItem . TokenCName :
if not PcdItem . TokenSpaceGuidCName in TokenSpaceGuidCNameList :
if len ( TokenSpaceGuidCNameList ) < 1 :
TokenSpaceGuidCNameList . append ( PcdItem . TokenSpaceGuidCName )
TokenSpaceGuidCName = PcdItem . TokenSpaceGuidCName
PcdDatumType = PcdItem . DatumType
FoundFlag = True
else :
EdkLogger . error (
'build' ,
AUTOGEN_ERROR ,
"The Pcd %s is found under multiple different TokenSpaceGuid: %s and %s ." % ( DisplayName , PcdItem . TokenSpaceGuidCName , TokenSpaceGuidCNameList [ 0 ])
)
2018-01-31 16:49:14 +08:00
else :
if ( TokenCName , TokenSpaceGuidCName ) in self . DecPcds :
2018-03-12 15:09:03 +08:00
PcdDatumType = self . DecPcds [( TokenCName , TokenSpaceGuidCName )] . DatumType
2018-01-31 16:49:14 +08:00
FoundFlag = True
if not FoundFlag :
if HasTokenSpace :
2018-03-07 14:14:43 +08:00
EdkLogger . error ( 'build' , AUTOGEN_ERROR , "The Pcd %s . %s is not found in the DEC file." % ( TokenSpaceGuidCName , DisplayName ))
2018-01-31 16:49:14 +08:00
else :
2018-03-07 14:14:43 +08:00
EdkLogger . error ( 'build' , AUTOGEN_ERROR , "The Pcd %s is not found in the DEC file." % ( DisplayName ))
pcdvalue = pcdvalue . replace ( " \\\\\\ '" , ' \\\\\\ "' ) . replace ( ' \\\' ' , ' \' ' ) . replace ( ' \\\\\\ "' , " \\ '" )
if FieldName :
2018-04-14 04:51:29 +08:00
pcdvalue = DscBuildData . HandleFlexiblePcd ( TokenSpaceGuidCName , TokenCName , pcdvalue , PcdDatumType , self . _GuidDict , FieldName )
2018-03-07 14:14:43 +08:00
else :
2018-04-14 04:51:29 +08:00
pcdvalue = DscBuildData . HandleFlexiblePcd ( TokenSpaceGuidCName , TokenCName , pcdvalue , PcdDatumType , self . _GuidDict )
2018-03-07 14:14:43 +08:00
IsValid , Cause = CheckPcdDatum ( PcdDatumType , pcdvalue )
if not IsValid :
EdkLogger . error ( "build" , FORMAT_INVALID , Cause , ExtraData = " %s . %s " % ( TokenSpaceGuidCName , TokenCName ))
2018-06-25 18:31:33 +08:00
GlobalData . BuildOptionPcd [ i ] = ( TokenSpaceGuidCName , TokenCName , FieldName , pcdvalue , ( "build command options" , 1 ))
2018-03-07 14:14:43 +08:00
2018-10-24 14:46:09 +08:00
if GlobalData . BuildOptionPcd :
2019-08-02 14:40:31 +08:00
inf_objs = [ item for item in self . _Bdb . _CACHE_ . values () if item . Arch == self . Arch and item . MetaFile . Ext . lower () == '.inf' ]
2018-10-24 14:46:09 +08:00
for pcd in GlobalData . BuildOptionPcd :
( TokenSpaceGuidCName , TokenCName , FieldName , pcdvalue , _ ) = pcd
2019-08-02 14:40:31 +08:00
for BuildData in inf_objs :
2018-01-31 16:49:14 +08:00
for key in BuildData . Pcds :
PcdItem = BuildData . Pcds [ key ]
if ( TokenSpaceGuidCName , TokenCName ) == ( PcdItem . TokenSpaceGuidCName , PcdItem . TokenCName ) and FieldName == "" :
2018-03-07 14:14:43 +08:00
PcdItem . DefaultValue = pcdvalue
2018-10-19 15:25:39 +08:00
PcdItem . PcdValueFromComm = pcdvalue
2018-09-12 17:19:26 +08:00
#In command line, the latter full assign value in commandLine should override the former field assign value.
#For example, --pcd Token.pcd.field="" --pcd Token.pcd=H"{}"
delete_assign = []
field_assign = {}
if GlobalData . BuildOptionPcd :
for pcdTuple in GlobalData . BuildOptionPcd :
TokenSpaceGuid , Token , Field = pcdTuple [ 0 ], pcdTuple [ 1 ], pcdTuple [ 2 ]
if Field :
if ( TokenSpaceGuid , Token ) not in field_assign :
field_assign [ TokenSpaceGuid , Token ] = []
field_assign [ TokenSpaceGuid , Token ] . append ( pcdTuple )
else :
if ( TokenSpaceGuid , Token ) in field_assign :
delete_assign . extend ( field_assign [ TokenSpaceGuid , Token ])
field_assign [ TokenSpaceGuid , Token ] = []
for item in delete_assign :
GlobalData . BuildOptionPcd . remove ( item )
2018-03-07 14:14:43 +08:00
2018-04-14 04:51:29 +08:00
@staticmethod
def HandleFlexiblePcd ( TokenSpaceGuidCName , TokenCName , PcdValue , PcdDatumType , GuidDict , FieldName = '' ):
2018-03-07 14:14:43 +08:00
if FieldName :
IsArray = False
TokenCName += '.' + FieldName
if PcdValue . startswith ( 'H' ):
2019-01-11 02:39:47 +08:00
if FieldName and _IsFieldValueAnArray ( PcdValue [ 1 :]):
2018-04-11 09:14:05 -07:00
PcdDatumType = TAB_VOID
2018-03-07 14:14:43 +08:00
IsArray = True
if FieldName and not IsArray :
return PcdValue
try :
PcdValue = ValueExpressionEx ( PcdValue [ 1 :], PcdDatumType , GuidDict )( True )
2018-06-25 18:31:25 +08:00
except BadExpression as Value :
2018-03-07 14:14:43 +08:00
EdkLogger . error ( 'Parser' , FORMAT_INVALID , 'PCD [ %s . %s ] Value " %s ", %s ' %
( TokenSpaceGuidCName , TokenCName , PcdValue , Value ))
elif PcdValue . startswith ( "L'" ) or PcdValue . startswith ( "'" ):
2019-01-11 02:39:47 +08:00
if FieldName and _IsFieldValueAnArray ( PcdValue ):
2018-04-11 09:14:05 -07:00
PcdDatumType = TAB_VOID
2018-03-07 14:14:43 +08:00
IsArray = True
if FieldName and not IsArray :
return PcdValue
try :
PcdValue = ValueExpressionEx ( PcdValue , PcdDatumType , GuidDict )( True )
2018-06-25 18:31:25 +08:00
except BadExpression as Value :
2018-03-07 14:14:43 +08:00
EdkLogger . error ( 'Parser' , FORMAT_INVALID , 'PCD [ %s . %s ] Value " %s ", %s ' %
( TokenSpaceGuidCName , TokenCName , PcdValue , Value ))
elif PcdValue . startswith ( 'L' ):
PcdValue = 'L"' + PcdValue [ 1 :] + '"'
2019-01-11 02:39:47 +08:00
if FieldName and _IsFieldValueAnArray ( PcdValue ):
2018-04-11 09:14:05 -07:00
PcdDatumType = TAB_VOID
2018-03-07 14:14:43 +08:00
IsArray = True
if FieldName and not IsArray :
return PcdValue
try :
PcdValue = ValueExpressionEx ( PcdValue , PcdDatumType , GuidDict )( True )
2018-06-25 18:31:25 +08:00
except BadExpression as Value :
2018-03-07 14:14:43 +08:00
EdkLogger . error ( 'Parser' , FORMAT_INVALID , 'PCD [ %s . %s ] Value " %s ", %s ' %
( TokenSpaceGuidCName , TokenCName , PcdValue , Value ))
else :
if PcdValue . upper () == 'FALSE' :
PcdValue = str ( 0 )
if PcdValue . upper () == 'TRUE' :
PcdValue = str ( 1 )
if not FieldName :
2018-04-11 09:14:05 -07:00
if PcdDatumType not in TAB_PCD_NUMERIC_TYPES :
2018-03-07 14:14:43 +08:00
PcdValue = '"' + PcdValue + '"'
2018-10-15 20:43:47 +08:00
elif not PcdValue . isdigit () and not PcdValue . upper () . startswith ( '0X' ):
PcdValue = '"' + PcdValue + '"'
2018-03-07 14:14:43 +08:00
else :
IsArray = False
Base = 10
if PcdValue . upper () . startswith ( '0X' ):
Base = 16
try :
Num = int ( PcdValue , Base )
except :
PcdValue = '"' + PcdValue + '"'
2019-01-11 02:39:47 +08:00
if _IsFieldValueAnArray ( PcdValue ):
2018-04-11 09:14:05 -07:00
PcdDatumType = TAB_VOID
2018-03-07 14:14:43 +08:00
IsArray = True
if not IsArray :
return PcdValue
try :
PcdValue = ValueExpressionEx ( PcdValue , PcdDatumType , GuidDict )( True )
2018-06-25 18:31:25 +08:00
except BadExpression as Value :
2018-03-07 14:14:43 +08:00
EdkLogger . error ( 'Parser' , FORMAT_INVALID , 'PCD [ %s . %s ] Value " %s ", %s ' %
( TokenSpaceGuidCName , TokenCName , PcdValue , Value ))
return PcdValue
2017-11-24 14:30:11 +08:00
## Retrieve all PCD settings in platform
2018-09-11 06:18:05 +08:00
@property
def Pcds ( self ):
2018-03-27 04:25:43 +08:00
if self . _Pcds is None :
2018-04-04 05:03:09 +08:00
self . _Pcds = OrderedDict ()
2018-01-31 16:49:14 +08:00
self . __ParsePcdFromCommandLine ()
2017-11-24 14:30:11 +08:00
self . _Pcds . update ( self . _GetPcd ( MODEL_PCD_FIXED_AT_BUILD ))
self . _Pcds . update ( self . _GetPcd ( MODEL_PCD_PATCHABLE_IN_MODULE ))
self . _Pcds . update ( self . _GetPcd ( MODEL_PCD_FEATURE_FLAG ))
self . _Pcds . update ( self . _GetDynamicPcd ( MODEL_PCD_DYNAMIC_DEFAULT ))
self . _Pcds . update ( self . _GetDynamicHiiPcd ( MODEL_PCD_DYNAMIC_HII ))
self . _Pcds . update ( self . _GetDynamicVpdPcd ( MODEL_PCD_DYNAMIC_VPD ))
self . _Pcds . update ( self . _GetDynamicPcd ( MODEL_PCD_DYNAMIC_EX_DEFAULT ))
self . _Pcds . update ( self . _GetDynamicHiiPcd ( MODEL_PCD_DYNAMIC_EX_HII ))
self . _Pcds . update ( self . _GetDynamicVpdPcd ( MODEL_PCD_DYNAMIC_EX_VPD ))
2017-12-22 20:46:15 +08:00
self . _Pcds = self . CompletePcdValues ( self . _Pcds )
2018-06-22 17:14:13 +08:00
self . _Pcds = self . OverrideByFdfOverAll ( self . _Pcds )
self . _Pcds = self . OverrideByCommOverAll ( self . _Pcds )
2017-11-24 14:30:11 +08:00
self . _Pcds = self . UpdateStructuredPcds ( MODEL_PCD_TYPE_LIST , self . _Pcds )
2017-12-22 20:04:04 +08:00
self . _Pcds = self . CompleteHiiPcdsDefaultStores ( self . _Pcds )
2017-12-22 20:46:15 +08:00
self . _Pcds = self . _FilterPcdBySkuUsage ( self . _Pcds )
2018-03-02 18:11:13 +08:00
2018-01-31 16:49:14 +08:00
self . RecoverCommandLinePcd ()
2017-11-24 14:30:11 +08:00
return self . _Pcds
## Retrieve [BuildOptions]
2018-09-11 06:18:05 +08:00
@property
def BuildOptions ( self ):
2018-03-27 04:25:43 +08:00
if self . _BuildOptions is None :
2018-04-04 05:03:09 +08:00
self . _BuildOptions = OrderedDict ()
2017-11-24 14:30:11 +08:00
#
# Retrieve build option for EDKII and EDK style module
#
for CodeBase in ( EDKII_NAME , EDK_NAME ):
RecordList = self . _RawData [ MODEL_META_DATA_BUILD_OPTION , self . _Arch , CodeBase ]
2018-06-25 18:31:33 +08:00
for ToolChainFamily , ToolChain , Option , Dummy1 , Dummy2 , Dummy3 , Dummy4 , Dummy5 in RecordList :
2018-04-16 21:52:13 +08:00
if Dummy3 . upper () != TAB_COMMON :
2017-12-22 20:53:01 +08:00
continue
2017-11-24 14:30:11 +08:00
CurKey = ( ToolChainFamily , ToolChain , CodeBase )
#
# Only flags can be appended
#
if CurKey not in self . _BuildOptions or not ToolChain . endswith ( '_FLAGS' ) or Option . startswith ( '=' ):
self . _BuildOptions [ CurKey ] = Option
else :
2017-12-22 20:53:01 +08:00
if ' ' + Option not in self . _BuildOptions [ CurKey ]:
self . _BuildOptions [ CurKey ] += ' ' + Option
2017-11-24 14:30:11 +08:00
return self . _BuildOptions
def GetBuildOptionsByModuleType ( self , Edk , ModuleType ):
2018-03-27 04:25:43 +08:00
if self . _ModuleTypeOptions is None :
2018-04-04 05:03:09 +08:00
self . _ModuleTypeOptions = OrderedDict ()
2017-11-24 14:30:11 +08:00
if ( Edk , ModuleType ) not in self . _ModuleTypeOptions :
2018-04-04 05:03:09 +08:00
options = OrderedDict ()
2017-11-24 14:30:11 +08:00
self . _ModuleTypeOptions [ Edk , ModuleType ] = options
DriverType = ' %s . %s ' % ( Edk , ModuleType )
2018-04-16 21:52:13 +08:00
CommonDriverType = ' %s . %s ' % ( TAB_COMMON , ModuleType )
2017-12-22 20:53:01 +08:00
RecordList = self . _RawData [ MODEL_META_DATA_BUILD_OPTION , self . _Arch ]
2018-06-25 18:31:33 +08:00
for ToolChainFamily , ToolChain , Option , Dummy1 , Dummy2 , Dummy3 , Dummy4 , Dummy5 in RecordList :
2017-12-22 20:53:01 +08:00
Type = Dummy2 + '.' + Dummy3
if Type . upper () == DriverType . upper () or Type . upper () == CommonDriverType . upper ():
2017-11-24 14:30:11 +08:00
Key = ( ToolChainFamily , ToolChain , Edk )
if Key not in options or not ToolChain . endswith ( '_FLAGS' ) or Option . startswith ( '=' ):
options [ Key ] = Option
else :
2017-12-22 20:53:01 +08:00
if ' ' + Option not in options [ Key ]:
options [ Key ] += ' ' + Option
2017-11-24 14:30:11 +08:00
return self . _ModuleTypeOptions [ Edk , ModuleType ]
2018-04-20 23:51:27 +08:00
@staticmethod
def GetStructurePcdInfo ( PcdSet ):
structure_pcd_data = defaultdict ( list )
2017-11-24 14:30:11 +08:00
for item in PcdSet :
2018-06-25 18:31:33 +08:00
structure_pcd_data [( item [ 0 ], item [ 1 ])] . append ( item )
2017-11-24 14:30:11 +08:00
return structure_pcd_data
2018-04-14 04:51:29 +08:00
@staticmethod
2018-06-22 17:14:13 +08:00
def OverrideByFdf ( StruPcds , workspace ):
if GlobalData . gFdfParser is None :
return StruPcds
StructurePcdInFdf = OrderedDict ()
fdfpcd = GlobalData . gFdfParser . Profile . PcdDict
fdfpcdlocation = GlobalData . gFdfParser . Profile . PcdLocalDict
for item in fdfpcd :
if len ( item [ 2 ]) and ( item [ 0 ], item [ 1 ]) in StruPcds :
StructurePcdInFdf [( item [ 1 ], item [ 0 ], item [ 2 ] )] = fdfpcd [ item ]
GlobalPcds = {( item [ 0 ], item [ 1 ]) for item in StructurePcdInFdf }
for Pcd in StruPcds . values ():
if ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName ) not in GlobalPcds :
continue
FieldValues = OrderedDict ()
for item in StructurePcdInFdf :
if ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName ) == ( item [ 0 ], item [ 1 ]) and item [ 2 ]:
FieldValues [ item [ 2 ]] = StructurePcdInFdf [ item ]
for field in FieldValues :
if field not in Pcd . PcdFieldValueFromFdf :
Pcd . PcdFieldValueFromFdf [ field ] = [ "" , "" , "" ]
Pcd . PcdFieldValueFromFdf [ field ][ 0 ] = FieldValues [ field ]
Pcd . PcdFieldValueFromFdf [ field ][ 1 ] = os . path . relpath ( fdfpcdlocation [( Pcd . TokenCName , Pcd . TokenSpaceGuidCName , field )][ 0 ], workspace )
Pcd . PcdFieldValueFromFdf [ field ][ 2 ] = fdfpcdlocation [( Pcd . TokenCName , Pcd . TokenSpaceGuidCName , field )][ 1 ]
return StruPcds
@staticmethod
def OverrideByComm ( StruPcds ):
2018-03-02 18:11:13 +08:00
StructurePcdInCom = OrderedDict ()
for item in GlobalData . BuildOptionPcd :
2018-06-25 18:31:33 +08:00
if len ( item ) == 5 and ( item [ 1 ], item [ 0 ]) in StruPcds :
StructurePcdInCom [( item [ 0 ], item [ 1 ], item [ 2 ] )] = ( item [ 3 ], item [ 4 ])
GlobalPcds = {( item [ 0 ], item [ 1 ]) for item in StructurePcdInCom }
2018-01-31 16:49:14 +08:00
for Pcd in StruPcds . values ():
2018-06-25 18:31:33 +08:00
if ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName ) not in GlobalPcds :
2018-01-31 16:49:14 +08:00
continue
2018-03-02 18:11:13 +08:00
FieldValues = OrderedDict ()
for item in StructurePcdInCom :
2018-06-25 18:31:33 +08:00
if ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName ) == ( item [ 0 ], item [ 1 ]) and item [ 2 ]:
2018-03-02 18:11:13 +08:00
FieldValues [ item [ 2 ]] = StructurePcdInCom [ item ]
for field in FieldValues :
if field not in Pcd . PcdFieldValueFromComm :
2018-06-25 18:31:33 +08:00
Pcd . PcdFieldValueFromComm [ field ] = [ "" , "" , "" ]
2018-03-02 18:11:13 +08:00
Pcd . PcdFieldValueFromComm [ field ][ 0 ] = FieldValues [ field ][ 0 ]
Pcd . PcdFieldValueFromComm [ field ][ 1 ] = FieldValues [ field ][ 1 ][ 0 ]
Pcd . PcdFieldValueFromComm [ field ][ 2 ] = FieldValues [ field ][ 1 ][ 1 ]
2018-01-31 16:49:14 +08:00
return StruPcds
2018-04-14 04:51:29 +08:00
2018-06-22 17:14:13 +08:00
def OverrideByCommOverAll ( self , AllPcds ):
2018-01-31 16:49:14 +08:00
def CheckStructureInComm ( commpcds ):
if not commpcds :
return False
if len ( commpcds [ 0 ]) == 5 :
return True
return False
2018-09-25 13:20:46 +08:00
NoFiledValues = OrderedDict ()
2018-01-31 16:49:14 +08:00
if CheckStructureInComm ( GlobalData . BuildOptionPcd ):
2018-09-25 13:20:46 +08:00
StructurePcdInCom = OrderedDict ()
for item in GlobalData . BuildOptionPcd :
StructurePcdInCom [( item [ 0 ], item [ 1 ], item [ 2 ] )] = ( item [ 3 ], item [ 4 ])
for item in StructurePcdInCom :
if not item [ 2 ]:
NoFiledValues [( item [ 0 ], item [ 1 ])] = StructurePcdInCom [ item ]
2018-01-31 16:49:14 +08:00
else :
2018-09-25 13:20:46 +08:00
for item in GlobalData . BuildOptionPcd :
NoFiledValues [( item [ 0 ], item [ 1 ])] = [ item [ 2 ]]
2018-06-25 18:31:33 +08:00
for Guid , Name in NoFiledValues :
if ( Name , Guid ) in AllPcds :
Pcd = AllPcds . get (( Name , Guid ))
if isinstance ( self . _DecPcds . get (( Pcd . TokenCName , Pcd . TokenSpaceGuidCName ), None ), StructurePcd ):
self . _DecPcds . get (( Pcd . TokenCName , Pcd . TokenSpaceGuidCName )) . PcdValueFromComm = NoFiledValues [( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )][ 0 ]
2018-03-02 18:11:13 +08:00
else :
2018-10-19 20:11:01 +08:00
Pcd . PcdValueFromComm = NoFiledValues [( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )][ 0 ]
Pcd . DefaultValue = NoFiledValues [( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )][ 0 ]
2018-03-02 18:11:13 +08:00
for sku in Pcd . SkuInfoList :
SkuInfo = Pcd . SkuInfoList [ sku ]
if SkuInfo . DefaultValue :
2018-10-19 20:11:01 +08:00
SkuInfo . DefaultValue = NoFiledValues [( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )][ 0 ]
2018-03-02 18:11:13 +08:00
else :
2018-10-19 20:11:01 +08:00
SkuInfo . HiiDefaultValue = NoFiledValues [( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )][ 0 ]
2018-03-02 18:11:13 +08:00
for defaultstore in SkuInfo . DefaultStoreDict :
2018-10-19 20:11:01 +08:00
SkuInfo . DefaultStoreDict [ defaultstore ] = NoFiledValues [( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )][ 0 ]
2018-03-21 10:36:59 +08:00
if Pcd . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ], self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ]]:
2018-04-11 09:14:05 -07:00
if Pcd . DatumType == TAB_VOID :
2018-03-21 10:36:59 +08:00
if not Pcd . MaxDatumSize :
Pcd . MaxDatumSize = '0'
2018-06-25 18:31:33 +08:00
CurrentSize = int ( Pcd . MaxDatumSize , 16 ) if Pcd . MaxDatumSize . upper () . startswith ( "0X" ) else int ( Pcd . MaxDatumSize )
2018-03-21 10:36:59 +08:00
OptionSize = len (( StringToArray ( Pcd . PcdValueFromComm )) . split ( "," ))
MaxSize = max ( CurrentSize , OptionSize )
Pcd . MaxDatumSize = str ( MaxSize )
2018-01-31 16:49:14 +08:00
else :
2018-06-25 18:31:33 +08:00
PcdInDec = self . DecPcds . get (( Name , Guid ))
2018-01-31 16:49:14 +08:00
if PcdInDec :
2018-10-19 20:11:01 +08:00
PcdInDec . PcdValueFromComm = NoFiledValues [( Guid , Name )][ 0 ]
2018-01-31 16:49:14 +08:00
if PcdInDec . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_FIXED_AT_BUILD ],
2018-03-20 14:57:04 +08:00
self . _PCD_TYPE_STRING_ [ MODEL_PCD_PATCHABLE_IN_MODULE ],
2018-08-29 16:47:59 +08:00
self . _PCD_TYPE_STRING_ [ MODEL_PCD_FEATURE_FLAG ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX ]]:
2019-07-22 11:09:22 +08:00
self . _Pcds [ Name , Guid ] = copy . deepcopy ( PcdInDec )
self . _Pcds [ Name , Guid ] . DefaultValue = NoFiledValues [( Guid , Name )][ 0 ]
2018-08-29 16:47:59 +08:00
if PcdInDec . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX ]]:
2019-07-22 11:09:22 +08:00
self . _Pcds [ Name , Guid ] . SkuInfoList = { TAB_DEFAULT : SkuInfoClass ( TAB_DEFAULT , self . SkuIds [ TAB_DEFAULT ][ 0 ], '' , '' , '' , '' , '' , NoFiledValues [( Guid , Name )][ 0 ])}
2018-01-31 16:49:14 +08:00
return AllPcds
2018-06-22 17:14:13 +08:00
def OverrideByFdfOverAll ( self , AllPcds ):
if GlobalData . gFdfParser is None :
return AllPcds
NoFiledValues = GlobalData . gFdfParser . Profile . PcdDict
2018-07-16 17:38:44 +08:00
for Name , Guid , Field in NoFiledValues :
2018-06-22 17:14:13 +08:00
if len ( Field ):
continue
2018-07-16 17:38:44 +08:00
Value = NoFiledValues [( Name , Guid , Field )]
2018-06-22 17:14:13 +08:00
if ( Name , Guid ) in AllPcds :
Pcd = AllPcds . get (( Name , Guid ))
if isinstance ( self . _DecPcds . get (( Pcd . TokenCName , Pcd . TokenSpaceGuidCName ), None ), StructurePcd ):
self . _DecPcds . get (( Pcd . TokenCName , Pcd . TokenSpaceGuidCName )) . PcdValueFromComm = Value
else :
Pcd . PcdValueFromComm = Value
Pcd . DefaultValue = Value
for sku in Pcd . SkuInfoList :
SkuInfo = Pcd . SkuInfoList [ sku ]
if SkuInfo . DefaultValue :
SkuInfo . DefaultValue = Value
else :
SkuInfo . HiiDefaultValue = Value
for defaultstore in SkuInfo . DefaultStoreDict :
SkuInfo . DefaultStoreDict [ defaultstore ] = Value
if Pcd . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ], self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ]]:
if Pcd . DatumType == TAB_VOID :
if not Pcd . MaxDatumSize :
Pcd . MaxDatumSize = '0'
CurrentSize = int ( Pcd . MaxDatumSize , 16 ) if Pcd . MaxDatumSize . upper () . startswith ( "0X" ) else int ( Pcd . MaxDatumSize )
OptionSize = len (( StringToArray ( Pcd . PcdValueFromComm )) . split ( "," ))
MaxSize = max ( CurrentSize , OptionSize )
Pcd . MaxDatumSize = str ( MaxSize )
else :
PcdInDec = self . DecPcds . get (( Name , Guid ))
if PcdInDec :
2018-07-16 17:38:44 +08:00
PcdInDec . PcdValueFromFdf = Value
2018-06-22 17:14:13 +08:00
if PcdInDec . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_FIXED_AT_BUILD ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_PATCHABLE_IN_MODULE ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_FEATURE_FLAG ]]:
2019-07-22 11:09:22 +08:00
self . _Pcds [ Name , Guid ] = copy . deepcopy ( PcdInDec )
self . _Pcds [ Name , Guid ] . DefaultValue = Value
2018-06-22 17:14:13 +08:00
return AllPcds
2018-11-07 17:18:34 +08:00
def ParsePcdNameStruct ( self , NamePart1 , NamePart2 ):
TokenSpaceCName = PcdCName = DimensionAttr = Field = ""
if "." in NamePart1 :
TokenSpaceCName , TempPcdCName = NamePart1 . split ( "." )
if "[" in TempPcdCName :
PcdCName = TempPcdCName [: TempPcdCName . index ( "[" )]
DimensionAttr = TempPcdCName [ TempPcdCName . index ( "[" ):]
else :
PcdCName = TempPcdCName
Field = NamePart2
else :
TokenSpaceCName = NamePart1
if "[" in NamePart2 :
PcdCName = NamePart2 [: NamePart2 . index ( "[" )]
DimensionAttr = NamePart2 [ NamePart2 . index ( "[" ):]
else :
PcdCName = NamePart2
return TokenSpaceCName , PcdCName , DimensionAttr , Field
2017-11-24 14:30:11 +08:00
def UpdateStructuredPcds ( self , TypeList , AllPcds ):
2017-12-01 22:00:07 +08:00
DynamicPcdType = [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_DEFAULT ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_VPD ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_DEFAULT ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_VPD ]]
2017-11-24 14:30:11 +08:00
Pcds = AllPcds
2017-12-22 20:46:15 +08:00
DefaultStoreMgr = DefaultStore ( self . DefaultStores )
2018-09-04 15:51:05 +08:00
SkuIds = self . SkuIds
2018-09-26 16:04:06 +08:00
self . SkuIdMgr . AvailableSkuIdSet . update ({ TAB_DEFAULT : 0 })
2018-04-12 16:53:53 -07:00
DefaultStores = { storename for pcdobj in AllPcds . values () for skuobj in pcdobj . SkuInfoList . values () for storename in skuobj . DefaultStoreDict }
2018-10-24 20:31:23 +08:00
DefaultStores . add ( TAB_DEFAULT_STORES_DEFAULT )
2017-11-24 14:30:11 +08:00
S_PcdSet = []
# Find out all possible PCD candidates for self._Arch
RecordList = []
2017-12-22 20:04:04 +08:00
2017-11-24 14:30:11 +08:00
for Type in TypeList :
RecordList . extend ( self . _RawData [ Type , self . _Arch ])
2018-06-25 18:31:33 +08:00
for TokenSpaceGuid , PcdCName , Setting , Arch , SkuName , default_store , Dummy4 , Dummy5 in RecordList :
2017-12-22 20:04:04 +08:00
SkuName = SkuName . upper ()
default_store = default_store . upper ()
2018-04-16 21:52:13 +08:00
SkuName = TAB_DEFAULT if SkuName == TAB_COMMON else SkuName
2017-12-22 20:46:15 +08:00
if SkuName not in SkuIds :
continue
2018-11-07 17:18:34 +08:00
TCName , PCName , DimensionAttr , Field = self . ParsePcdNameStruct ( TokenSpaceGuid , PcdCName )
pcd_in_dec = self . _DecPcds . get (( PCName , TCName ), None )
if pcd_in_dec is None :
EdkLogger . error ( 'build' , PARSER_ERROR ,
"Pcd ( %s . %s ) defined in DSC is not declared in DEC files. Arch: [' %s ']" % ( TCName , PCName , self . _Arch ),
File = self . MetaFile , Line = Dummy5 )
if SkuName in SkuIds and ( "." in TokenSpaceGuid or "[" in PcdCName ):
if not isinstance ( pcd_in_dec , StructurePcd ):
EdkLogger . error ( 'build' , PARSER_ERROR ,
"Pcd ( %s . %s ) is not declared as Structure PCD in DEC files. Arch: [' %s ']" % ( TCName , PCName , self . _Arch ),
File = self . MetaFile , Line = Dummy5 )
2017-12-22 20:04:04 +08:00
2018-11-07 17:18:34 +08:00
S_PcdSet . append ([ TCName , PCName , DimensionAttr , Field , SkuName , default_store , Dummy5 , AnalyzePcdExpression ( Setting )[ 0 ]])
2020-11-04 11:01:39 +08:00
ModuleScopeOverallValue = {}
for m in self . Modules . values ():
mguid = m . Guid
if m . StrPcdSet :
S_PcdSet . extend ( m . StrPcdSet )
mguid = m . StrPcdSet [ 0 ][ 4 ]
for ( PCName , TCName ) in m . StrPcdOverallValue :
Value , dsc_file , lineNo = m . StrPcdOverallValue [( PCName , TCName )]
ModuleScopeOverallValue . setdefault (( PCName , TCName ),{})[ mguid ] = Value , dsc_file , lineNo
2017-11-24 14:30:11 +08:00
# handle pcd value override
2018-04-20 23:51:27 +08:00
StrPcdSet = DscBuildData . GetStructurePcdInfo ( S_PcdSet )
2018-02-28 13:59:20 +08:00
S_pcd_set = OrderedDict ()
2017-11-24 14:30:11 +08:00
for str_pcd in StrPcdSet :
2017-12-22 20:46:15 +08:00
str_pcd_obj = Pcds . get (( str_pcd [ 1 ], str_pcd [ 0 ]), None )
str_pcd_dec = self . _DecPcds . get (( str_pcd [ 1 ], str_pcd [ 0 ]), None )
2018-11-07 17:18:34 +08:00
str_pcd_obj_str = StructurePcd ()
str_pcd_obj_str . copy ( str_pcd_dec )
if str_pcd_obj :
str_pcd_obj_str . copy ( str_pcd_obj )
if str_pcd_obj . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ], self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ]]:
str_pcd_obj_str . DefaultFromDSC = { skuname :{ defaultstore : str_pcd_obj . SkuInfoList [ skuname ] . DefaultStoreDict . get ( defaultstore , str_pcd_obj . SkuInfoList [ skuname ] . HiiDefaultValue ) for defaultstore in DefaultStores } for skuname in str_pcd_obj . SkuInfoList }
else :
str_pcd_obj_str . DefaultFromDSC = { skuname :{ defaultstore : str_pcd_obj . SkuInfoList [ skuname ] . DefaultStoreDict . get ( defaultstore , str_pcd_obj . SkuInfoList [ skuname ] . DefaultValue ) for defaultstore in DefaultStores } for skuname in str_pcd_obj . SkuInfoList }
for str_pcd_data in StrPcdSet [ str_pcd ]:
if str_pcd_data [ 4 ] in SkuIds :
str_pcd_obj_str . AddOverrideValue ( str_pcd_data [ 3 ], str ( str_pcd_data [ 7 ]), TAB_DEFAULT if str_pcd_data [ 4 ] == TAB_COMMON else str_pcd_data [ 4 ], TAB_DEFAULT_STORES_DEFAULT if str_pcd_data [ 5 ] == TAB_COMMON else str_pcd_data [ 5 ], self . MetaFile . File if self . WorkspaceDir not in self . MetaFile . File else self . MetaFile . File [ len ( self . WorkspaceDir ) if self . WorkspaceDir . endswith ( os . path . sep ) else len ( self . WorkspaceDir ) + 1 :], LineNo = str_pcd_data [ 6 ], DimensionAttr = str_pcd_data [ 2 ])
2020-11-04 11:01:39 +08:00
elif GlobalData . gGuidPattern . match ( str_pcd_data [ 4 ]):
str_pcd_obj_str . AddComponentOverrideValue ( str_pcd_data [ 3 ], str ( str_pcd_data [ 7 ]), str_pcd_data [ 4 ] . replace ( "-" , "S" ), self . MetaFile . File if self . WorkspaceDir not in self . MetaFile . File else self . MetaFile . File [ len ( self . WorkspaceDir ) if self . WorkspaceDir . endswith ( os . path . sep ) else len ( self . WorkspaceDir ) + 1 :], LineNo = str_pcd_data [ 6 ], DimensionAttr = str_pcd_data [ 2 ])
PcdComponentValue = ModuleScopeOverallValue . get (( str_pcd_obj_str . TokenCName , str_pcd_obj_str . TokenSpaceGuidCName ))
for module_guid in PcdComponentValue :
str_pcd_obj_str . PcdValueFromComponents [ module_guid . replace ( "-" , "S" )] = PcdComponentValue [ module_guid ]
2018-11-07 17:18:34 +08:00
S_pcd_set [ str_pcd [ 1 ], str_pcd [ 0 ]] = str_pcd_obj_str
2017-11-24 14:30:11 +08:00
# Add the Structure PCD that only defined in DEC, don't have override in DSC file
2017-12-26 11:33:33 +08:00
for Pcd in self . DecPcds :
2018-06-25 18:31:35 +08:00
if isinstance ( self . _DecPcds [ Pcd ], StructurePcd ):
2017-11-24 14:30:11 +08:00
if Pcd not in S_pcd_set :
str_pcd_obj_str = StructurePcd ()
str_pcd_obj_str . copy ( self . _DecPcds [ Pcd ])
str_pcd_obj = Pcds . get ( Pcd , None )
if str_pcd_obj :
str_pcd_obj_str . copy ( str_pcd_obj )
2018-02-07 12:10:29 +08:00
if str_pcd_obj . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ], self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ]]:
str_pcd_obj_str . DefaultFromDSC = { skuname :{ defaultstore : str_pcd_obj . SkuInfoList [ skuname ] . DefaultStoreDict . get ( defaultstore , str_pcd_obj . SkuInfoList [ skuname ] . HiiDefaultValue ) for defaultstore in DefaultStores } for skuname in str_pcd_obj . SkuInfoList }
else :
str_pcd_obj_str . DefaultFromDSC = { skuname :{ defaultstore : str_pcd_obj . SkuInfoList [ skuname ] . DefaultStoreDict . get ( defaultstore , str_pcd_obj . SkuInfoList [ skuname ] . DefaultValue ) for defaultstore in DefaultStores } for skuname in str_pcd_obj . SkuInfoList }
2017-11-24 14:30:11 +08:00
S_pcd_set [ Pcd ] = str_pcd_obj_str
if S_pcd_set :
2019-02-01 10:11:20 +08:00
GlobalData . gStructurePcd [ self . Arch ] = S_pcd_set . copy ()
self . FilterStrcturePcd ( S_pcd_set )
2017-12-22 20:46:15 +08:00
for stru_pcd in S_pcd_set . values ():
for skuid in SkuIds :
if skuid in stru_pcd . SkuOverrideValues :
continue
nextskuid = self . SkuIdMgr . GetNextSkuId ( skuid )
2017-12-22 20:04:04 +08:00
NoDefault = False
2018-02-28 13:59:21 +08:00
if skuid not in stru_pcd . SkuOverrideValues :
while nextskuid not in stru_pcd . SkuOverrideValues :
2018-04-16 21:52:13 +08:00
if nextskuid == TAB_DEFAULT :
2018-02-28 13:59:21 +08:00
NoDefault = True
break
nextskuid = self . SkuIdMgr . GetNextSkuId ( nextskuid )
2018-09-04 14:13:18 +08:00
stru_pcd . SkuOverrideValues [ skuid ] = copy . deepcopy ( stru_pcd . SkuOverrideValues [ nextskuid ]) if not NoDefault else copy . deepcopy ({ defaultstorename : stru_pcd . DefaultValues for defaultstorename in DefaultStores } if DefaultStores else {}) #{TAB_DEFAULT_STORES_DEFAULT:stru_pcd.DefaultValues})
2018-02-28 13:59:21 +08:00
if not NoDefault :
2018-06-25 18:31:33 +08:00
stru_pcd . ValueChain . add (( skuid , '' ))
2019-02-18 17:53:09 +08:00
if 'DEFAULT' in stru_pcd . SkuOverrideValues and not GlobalData . gPcdSkuOverrides . get (( stru_pcd . TokenCName , stru_pcd . TokenSpaceGuidCName )):
GlobalData . gPcdSkuOverrides . update (
{( stru_pcd . TokenCName , stru_pcd . TokenSpaceGuidCName ): { 'DEFAULT' : stru_pcd . SkuOverrideValues [ 'DEFAULT' ]}})
2017-12-18 12:42:41 +08:00
if stru_pcd . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ], self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ]]:
for skuid in SkuIds :
nextskuid = skuid
NoDefault = False
if skuid not in stru_pcd . SkuOverrideValues :
while nextskuid not in stru_pcd . SkuOverrideValues :
2018-04-16 21:52:13 +08:00
if nextskuid == TAB_DEFAULT :
2017-12-18 12:42:41 +08:00
NoDefault = True
break
nextskuid = self . SkuIdMgr . GetNextSkuId ( nextskuid )
if NoDefault :
continue
2018-04-28 06:32:52 +08:00
PcdDefaultStoreSet = set ( defaultstorename for defaultstorename in stru_pcd . SkuOverrideValues [ nextskuid ])
2017-12-18 12:42:41 +08:00
mindefaultstorename = DefaultStoreMgr . GetMin ( PcdDefaultStoreSet )
for defaultstoreid in DefaultStores :
if defaultstoreid not in stru_pcd . SkuOverrideValues [ skuid ]:
2018-11-08 14:03:38 +08:00
stru_pcd . SkuOverrideValues [ skuid ][ defaultstoreid ] = CopyDict ( stru_pcd . SkuOverrideValues [ nextskuid ][ mindefaultstorename ])
2018-06-25 18:31:33 +08:00
stru_pcd . ValueChain . add (( skuid , defaultstoreid ))
2018-06-22 17:14:13 +08:00
S_pcd_set = DscBuildData . OverrideByFdf ( S_pcd_set , self . WorkspaceDir )
S_pcd_set = DscBuildData . OverrideByComm ( S_pcd_set )
2020-11-04 11:01:39 +08:00
2025-11-04 08:24:54 +01:00
# Create a tool to calculate structure pcd value
2017-11-24 14:30:11 +08:00
Str_Pcd_Values = self . GenerateByteArrayValue ( S_pcd_set )
2020-11-04 11:01:39 +08:00
2017-11-24 14:30:11 +08:00
if Str_Pcd_Values :
2018-06-25 18:31:33 +08:00
for ( skuname , StoreName , PcdGuid , PcdName , PcdValue ) in Str_Pcd_Values :
2017-12-22 20:46:15 +08:00
str_pcd_obj = S_pcd_set . get (( PcdName , PcdGuid ))
2017-11-24 14:30:11 +08:00
if str_pcd_obj is None :
2018-06-25 18:31:26 +08:00
print ( PcdName , PcdGuid )
2017-11-24 14:30:11 +08:00
raise
if str_pcd_obj . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ]]:
2017-12-22 20:46:15 +08:00
if skuname not in str_pcd_obj . SkuInfoList :
str_pcd_obj . SkuInfoList [ skuname ] = SkuInfoClass ( SkuIdName = skuname , SkuId = self . SkuIds [ skuname ][ 0 ], HiiDefaultValue = PcdValue , DefaultStore = { StoreName : PcdValue })
2017-11-24 14:30:11 +08:00
else :
2017-12-22 20:46:15 +08:00
str_pcd_obj . SkuInfoList [ skuname ] . HiiDefaultValue = PcdValue
str_pcd_obj . SkuInfoList [ skuname ] . DefaultStoreDict . update ({ StoreName : PcdValue })
2017-11-24 14:30:11 +08:00
elif str_pcd_obj . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_FIXED_AT_BUILD ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_PATCHABLE_IN_MODULE ]]:
2018-04-16 21:52:13 +08:00
if skuname in ( self . SkuIdMgr . SystemSkuId , TAB_DEFAULT , TAB_COMMON ):
2017-12-22 20:46:15 +08:00
str_pcd_obj . DefaultValue = PcdValue
2020-11-04 11:01:39 +08:00
else :
#Module Scope Structure Pcd
moduleguid = skuname . replace ( "S" , "-" )
if GlobalData . gGuidPattern . match ( moduleguid ):
for component in self . Modules . values ():
if component . Guid == moduleguid :
component . Pcds [( PcdName , PcdGuid )] . DefaultValue = PcdValue
2017-11-24 14:30:11 +08:00
else :
2017-12-22 20:46:15 +08:00
if skuname not in str_pcd_obj . SkuInfoList :
2017-12-01 22:00:07 +08:00
nextskuid = self . SkuIdMgr . GetNextSkuId ( skuname )
NoDefault = False
while nextskuid not in str_pcd_obj . SkuInfoList :
2018-04-16 21:52:13 +08:00
if nextskuid == TAB_DEFAULT :
2017-12-01 22:00:07 +08:00
NoDefault = True
break
nextskuid = self . SkuIdMgr . GetNextSkuId ( nextskuid )
str_pcd_obj . SkuInfoList [ skuname ] = copy . deepcopy ( str_pcd_obj . SkuInfoList [ nextskuid ]) if not NoDefault else SkuInfoClass ( SkuIdName = skuname , SkuId = self . SkuIds [ skuname ][ 0 ], DefaultValue = PcdValue )
str_pcd_obj . SkuInfoList [ skuname ] . SkuId = self . SkuIds [ skuname ][ 0 ]
str_pcd_obj . SkuInfoList [ skuname ] . SkuIdName = skuname
2017-11-24 14:30:11 +08:00
else :
2017-12-22 20:46:15 +08:00
str_pcd_obj . SkuInfoList [ skuname ] . DefaultValue = PcdValue
for str_pcd_obj in S_pcd_set . values ():
if str_pcd_obj . Type not in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ]]:
continue
2018-04-28 06:32:52 +08:00
PcdDefaultStoreSet = set ( defaultstorename for skuobj in str_pcd_obj . SkuInfoList . values () for defaultstorename in skuobj . DefaultStoreDict )
2017-12-22 20:46:15 +08:00
DefaultStoreObj = DefaultStore ( self . _GetDefaultStores ())
mindefaultstorename = DefaultStoreObj . GetMin ( PcdDefaultStoreSet )
str_pcd_obj . SkuInfoList [ self . SkuIdMgr . SystemSkuId ] . HiiDefaultValue = str_pcd_obj . SkuInfoList [ self . SkuIdMgr . SystemSkuId ] . DefaultStoreDict [ mindefaultstorename ]
2017-11-24 14:30:11 +08:00
for str_pcd_obj in S_pcd_set . values ():
2017-12-22 20:04:04 +08:00
2018-12-15 00:15:21 +08:00
str_pcd_obj . MaxDatumSize = DscBuildData . GetStructurePcdMaxSize ( str_pcd_obj )
2017-11-24 14:30:11 +08:00
Pcds [ str_pcd_obj . TokenCName , str_pcd_obj . TokenSpaceGuidCName ] = str_pcd_obj
2018-09-25 10:55:30 +08:00
Pcds [ str_pcd_obj . TokenCName , str_pcd_obj . TokenSpaceGuidCName ] . CustomAttribute [ 'IsStru' ] = True
2017-11-24 14:30:11 +08:00
2017-12-01 22:00:07 +08:00
for pcdkey in Pcds :
pcd = Pcds [ pcdkey ]
2018-04-16 21:52:13 +08:00
if TAB_DEFAULT not in pcd . SkuInfoList and TAB_COMMON in pcd . SkuInfoList :
pcd . SkuInfoList [ TAB_DEFAULT ] = pcd . SkuInfoList [ TAB_COMMON ]
del pcd . SkuInfoList [ TAB_COMMON ]
elif TAB_DEFAULT in pcd . SkuInfoList and TAB_COMMON in pcd . SkuInfoList :
del pcd . SkuInfoList [ TAB_COMMON ]
2017-12-01 22:00:07 +08:00
2019-02-01 15:41:06 +08:00
list ( map ( self . FilterSkuSettings , [ Pcds [ pcdkey ] for pcdkey in Pcds if Pcds [ pcdkey ] . Type in DynamicPcdType ]))
2017-11-24 14:30:11 +08:00
return Pcds
2018-11-01 22:57:08 +08:00
@cached_property
def PlatformUsedPcds ( self ):
FdfInfList = []
if GlobalData . gFdfParser :
FdfInfList = GlobalData . gFdfParser . Profile . InfList
FdfModuleList = [ PathClass ( NormPath ( Inf ), GlobalData . gWorkspace , Arch = self . _Arch ) for Inf in FdfInfList ]
AllModulePcds = set ()
2019-01-23 10:16:00 +08:00
ModuleSet = set ( list ( self . _Modules . keys ()) + FdfModuleList )
2018-11-01 22:57:08 +08:00
for ModuleFile in ModuleSet :
ModuleData = self . _Bdb [ ModuleFile , self . _Arch , self . _Target , self . _Toolchain ]
AllModulePcds = AllModulePcds | ModuleData . PcdsName
for ModuleFile in self . LibraryInstances :
ModuleData = self . _Bdb . CreateBuildObject ( ModuleFile , self . _Arch , self . _Target , self . _Toolchain )
AllModulePcds = AllModulePcds | ModuleData . PcdsName
return AllModulePcds
2025-07-01 08:52:39 +00:00
#Filter the StructurePcd that is not used by any module in dsc file and fdf file.
2018-11-01 22:57:08 +08:00
def FilterStrcturePcd ( self , S_pcd_set ):
UnusedStruPcds = set ( S_pcd_set . keys ()) - self . PlatformUsedPcds
for ( Token , TokenSpaceGuid ) in UnusedStruPcds :
del S_pcd_set [( Token , TokenSpaceGuid )]
2017-11-24 14:30:11 +08:00
## Retrieve non-dynamic PCD settings
#
# @param Type PCD type
#
# @retval a dict object contains settings of given PCD type
#
def _GetPcd ( self , Type ):
2018-04-04 05:03:09 +08:00
Pcds = OrderedDict ()
2017-11-24 14:30:11 +08:00
#
# tdict is a special dict kind of type, used for selecting correct
# PCD settings for certain ARCH
#
2017-12-22 20:04:04 +08:00
AvailableSkuIdSet = copy . copy ( self . SkuIds )
2017-11-24 14:30:11 +08:00
2018-10-24 20:31:23 +08:00
PcdDict = tdict ( True , 4 )
2019-04-26 10:29:58 +08:00
PcdList = []
2017-11-24 14:30:11 +08:00
# Find out all possible PCD candidates for self._Arch
RecordList = self . _RawData [ Type , self . _Arch ]
2018-04-04 05:03:09 +08:00
PcdValueDict = OrderedDict ()
2018-06-25 18:31:33 +08:00
for TokenSpaceGuid , PcdCName , Setting , Arch , SkuName , Dummy3 , Dummy4 , Dummy5 in RecordList :
2017-12-22 20:04:04 +08:00
SkuName = SkuName . upper ()
2018-04-16 21:52:13 +08:00
SkuName = TAB_DEFAULT if SkuName == TAB_COMMON else SkuName
2017-12-22 20:04:04 +08:00
if SkuName not in AvailableSkuIdSet :
EdkLogger . error ( 'build ' , PARAMETER_INVALID , 'Sku %s is not defined in [SkuIds] section' % SkuName ,
File = self . MetaFile , Line = Dummy5 )
2018-11-07 17:18:34 +08:00
if SkuName in ( self . SkuIdMgr . SystemSkuId , TAB_DEFAULT , TAB_COMMON ):
2019-04-26 10:29:58 +08:00
if "." not in TokenSpaceGuid and "[" not in PcdCName and ( PcdCName , TokenSpaceGuid , SkuName , Dummy5 ) not in PcdList :
PcdList . append (( PcdCName , TokenSpaceGuid , SkuName , Dummy5 ))
2018-11-07 17:18:34 +08:00
PcdDict [ Arch , PcdCName , TokenSpaceGuid , SkuName ] = Setting
2017-11-24 14:30:11 +08:00
2019-04-26 10:29:58 +08:00
for PcdCName , TokenSpaceGuid , SkuName , Dummy4 in PcdList :
2017-11-24 14:30:11 +08:00
Setting = PcdDict [ self . _Arch , PcdCName , TokenSpaceGuid , SkuName ]
2018-03-27 04:25:43 +08:00
if Setting is None :
2017-11-24 14:30:11 +08:00
continue
PcdValue , DatumType , MaxDatumSize = self . _ValidatePcd ( PcdCName , TokenSpaceGuid , Setting , Type , Dummy4 )
2018-08-03 15:46:20 +08:00
if MaxDatumSize :
if int ( MaxDatumSize , 0 ) > 0xFFFF :
EdkLogger . error ( 'build' , FORMAT_INVALID , "The size value must not exceed the maximum value of 0xFFFF (UINT16) for %s ." % "." . join (( TokenSpaceGuid , PcdCName )),
File = self . MetaFile , Line = Dummy4 )
if int ( MaxDatumSize , 0 ) < 0 :
EdkLogger . error ( 'build' , FORMAT_INVALID , "The size value can't be set to negative value for %s ." % "." . join (( TokenSpaceGuid , PcdCName )),
File = self . MetaFile , Line = Dummy4 )
2017-11-24 14:30:11 +08:00
if ( PcdCName , TokenSpaceGuid ) in PcdValueDict :
2019-05-09 17:19:56 +08:00
PcdValueDict [ PcdCName , TokenSpaceGuid ][ SkuName ] = ( PcdValue , DatumType , MaxDatumSize , Dummy4 )
2017-11-24 14:30:11 +08:00
else :
2019-05-09 17:19:56 +08:00
PcdValueDict [ PcdCName , TokenSpaceGuid ] = { SkuName :( PcdValue , DatumType , MaxDatumSize , Dummy4 )}
2017-11-24 14:30:11 +08:00
2018-11-28 09:58:55 +08:00
for (( PcdCName , TokenSpaceGuid ), PcdSetting ) in PcdValueDict . items ():
2017-12-22 20:46:15 +08:00
if self . SkuIdMgr . SystemSkuId in PcdSetting :
2019-05-09 17:19:56 +08:00
PcdValue , DatumType , MaxDatumSize , _ = PcdSetting [ self . SkuIdMgr . SystemSkuId ]
2018-08-29 06:50:34 +08:00
elif TAB_DEFAULT in PcdSetting :
2019-05-09 17:19:56 +08:00
PcdValue , DatumType , MaxDatumSize , _ = PcdSetting [ TAB_DEFAULT ]
2018-08-29 06:50:34 +08:00
elif TAB_COMMON in PcdSetting :
2019-05-09 17:19:56 +08:00
PcdValue , DatumType , MaxDatumSize , _ = PcdSetting [ TAB_COMMON ]
2018-08-29 06:50:34 +08:00
else :
PcdValue = None
DatumType = None
MaxDatumSize = None
2017-11-24 14:30:11 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] = PcdClassObject (
PcdCName ,
TokenSpaceGuid ,
self . _PCD_TYPE_STRING_ [ Type ],
DatumType ,
PcdValue ,
'' ,
MaxDatumSize ,
{},
False ,
None ,
IsDsc = True )
2018-10-24 20:31:23 +08:00
for SkuName in PcdValueDict [ PcdCName , TokenSpaceGuid ]:
Settings = PcdValueDict [ PcdCName , TokenSpaceGuid ][ SkuName ]
if SkuName not in Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValue :
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValue [ SkuName ] = {}
2019-05-09 17:19:56 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValueInfo [ SkuName ] = {}
2018-10-24 20:31:23 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValue [ SkuName ][ TAB_DEFAULT_STORES_DEFAULT ] = Settings [ 0 ]
2019-05-09 17:19:56 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValueInfo [ SkuName ][ TAB_DEFAULT_STORES_DEFAULT ] = ( self . MetaFile . File , Settings [ 3 ])
2017-11-24 14:30:11 +08:00
return Pcds
2018-12-15 00:15:21 +08:00
@staticmethod
def GetStructurePcdMaxSize ( str_pcd ):
2017-11-24 14:30:11 +08:00
pcd_default_value = str_pcd . DefaultValue
2018-12-15 00:15:21 +08:00
sku_values = [ skuobj . HiiDefaultValue if str_pcd . Type in [ DscBuildData . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ], DscBuildData . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ]] else skuobj . DefaultValue for skuobj in str_pcd . SkuInfoList . values ()]
2017-11-24 14:30:11 +08:00
sku_values . append ( pcd_default_value )
def get_length ( value ):
Value = value . strip ()
2017-12-19 16:01:38 +08:00
if len ( value ) > 1 :
2018-04-27 00:57:56 +08:00
if Value . startswith ( TAB_GUID ) and Value . endswith ( ')' ):
2017-12-19 16:01:38 +08:00
return 16
if Value . startswith ( 'L"' ) and Value . endswith ( '"' ):
return len ( Value [ 2 : - 1 ])
if Value [ 0 ] == '"' and Value [ - 1 ] == '"' :
return len ( Value ) - 2
2018-12-15 00:15:21 +08:00
if Value . strip () . startswith ( "{CODE(" ):
tmpValue = RemoveCComments ( Value )
return len ( tmpValue . split ( "," ))
if ( Value [ 0 ] == '{' and Value [ - 1 ] == '}' ):
2017-12-19 16:01:38 +08:00
return len ( Value . split ( "," ))
if Value . startswith ( "L'" ) and Value . endswith ( "'" ) and len ( list ( Value [ 2 : - 1 ])) > 1 :
return len ( list ( Value [ 2 : - 1 ]))
if Value [ 0 ] == "'" and Value [ - 1 ] == "'" and len ( list ( Value [ 1 : - 1 ])) > 1 :
return len ( Value ) - 2
2017-11-24 14:30:11 +08:00
return len ( Value )
2018-04-28 06:32:54 +08:00
return str ( max ( get_length ( item ) for item in sku_values ))
2017-11-24 14:30:11 +08:00
2018-04-14 04:51:29 +08:00
@staticmethod
def ExecuteCommand ( Command ):
2017-11-24 14:30:11 +08:00
try :
Process = subprocess . Popen ( Command , stdout = subprocess . PIPE , stderr = subprocess . PIPE , shell = True )
except :
2018-01-31 17:32:01 +08:00
EdkLogger . error ( 'Build' , COMMAND_FAILURE , 'Can not execute command: %s ' % Command )
2017-11-24 14:30:11 +08:00
Result = Process . communicate ()
2019-12-02 11:50:48 +08:00
return Process . returncode , Result [ 0 ] . decode ( errors = 'ignore' ), Result [ 1 ] . decode ( errors = 'ignore' )
2017-11-24 14:30:11 +08:00
2018-04-14 04:51:29 +08:00
@staticmethod
def IntToCString ( Value , ValueSize ):
2017-11-24 14:30:11 +08:00
Result = '"'
if not isinstance ( Value , str ):
for Index in range ( 0 , ValueSize ):
Result = Result + ' \\ x %02x ' % ( Value & 0xff )
Value = Value >> 8
Result = Result + '"'
return Result
2018-06-25 18:31:33 +08:00
def GenerateSizeFunction ( self , Pcd ):
2018-02-28 13:59:20 +08:00
CApp = "// Default Value in Dec \n "
CApp = CApp + "void Cal_ %s _ %s _Size(UINT32 *Size){ \n " % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
2019-05-09 17:19:56 +08:00
if Pcd . IsArray () and Pcd . Capacity [ - 1 ] != "-1" :
CApp += " *Size = (sizeof ( %s ) > *Size ? sizeof ( %s ) : *Size); \n " % ( Pcd . DatumType , Pcd . DatumType )
else :
if "{CODE(" in Pcd . DefaultValueFromDec :
CApp += " *Size = (sizeof ( %s _ %s _INIT_Value) > *Size ? sizeof ( %s _ %s _INIT_Value) : *Size); \n " % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
2018-12-24 18:24:46 +08:00
if Pcd . Type in PCD_DYNAMIC_TYPE_SET | PCD_DYNAMIC_EX_TYPE_SET :
for skuname in Pcd . SkuInfoList :
skuobj = Pcd . SkuInfoList [ skuname ]
if skuobj . VariableName :
for defaultstore in skuobj . DefaultStoreDict :
pcddef = self . GetPcdDscRawDefaultValue ( Pcd , skuname , defaultstore )
2019-05-09 17:19:56 +08:00
if pcddef :
if "{CODE(" in pcddef :
CApp += " *Size = (sizeof ( %s _ %s _ %s _ %s _Value) > *Size ? sizeof ( %s _ %s _ %s _ %s _Value) : *Size); \n " % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , skuname , defaultstore , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , skuname , defaultstore )
else :
CApp += " *Size = %s > *Size ? %s : *Size; \n " % ( self . GetStructurePcdMaxSize ( Pcd ), self . GetStructurePcdMaxSize ( Pcd ))
2018-12-24 18:24:46 +08:00
else :
pcddef = self . GetPcdDscRawDefaultValue ( Pcd , skuname , TAB_DEFAULT_STORES_DEFAULT )
2019-05-09 17:19:56 +08:00
if pcddef :
if "{CODE(" in pcddef :
CApp += " *Size = (sizeof ( %s _ %s _ %s _ %s _Value) > *Size ? sizeof ( %s _ %s _ %s _ %s _Value) : *Size); \n " % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , skuname , TAB_DEFAULT_STORES_DEFAULT , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , skuname , TAB_DEFAULT_STORES_DEFAULT )
else :
CApp += " *Size = %s > *Size ? %s : *Size; \n " % ( self . GetStructurePcdMaxSize ( Pcd ), self . GetStructurePcdMaxSize ( Pcd ))
2018-12-24 18:24:46 +08:00
else :
pcddef = self . GetPcdDscRawDefaultValue ( Pcd , TAB_DEFAULT , TAB_DEFAULT_STORES_DEFAULT )
2019-05-09 17:19:56 +08:00
if pcddef :
if "{CODE(" in pcddef :
CApp += " *Size = (sizeof ( %s _ %s _ %s _ %s _Value) > *Size ? sizeof ( %s _ %s _ %s _ %s _Value) : *Size); \n " % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , TAB_DEFAULT , TAB_DEFAULT_STORES_DEFAULT , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , TAB_DEFAULT , TAB_DEFAULT_STORES_DEFAULT )
else :
CApp += " *Size = %s > *Size ? %s : *Size; \n " % ( self . GetStructurePcdMaxSize ( Pcd ), self . GetStructurePcdMaxSize ( Pcd ))
ActualCap = []
2018-11-07 17:18:34 +08:00
for index in Pcd . DefaultValues :
2019-05-09 17:19:56 +08:00
if index :
ActualCap . append ( index )
2018-11-07 17:18:34 +08:00
FieldList = Pcd . DefaultValues [ index ]
2018-02-28 13:59:20 +08:00
if not FieldList :
continue
for FieldName in FieldList :
FieldName = "." + FieldName
2019-01-11 02:39:47 +08:00
IsArray = _IsFieldValueAnArray ( FieldList [ FieldName . strip ( "." )][ 0 ])
2018-02-28 13:59:20 +08:00
if IsArray and not ( FieldList [ FieldName . strip ( "." )][ 0 ] . startswith ( '{GUID' ) and FieldList [ FieldName . strip ( "." )][ 0 ] . endswith ( '}' )):
try :
2018-04-11 09:14:05 -07:00
Value = ValueExpressionEx ( FieldList [ FieldName . strip ( "." )][ 0 ], TAB_VOID , self . _GuidDict )( True )
2018-02-28 13:59:20 +08:00
except BadExpression :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " %
( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName . strip ( '.' ))), FieldList [ FieldName . strip ( "." )][ 1 ], FieldList [ FieldName . strip ( "." )][ 2 ]))
Value , ValueSize = ParseFieldValue ( Value )
2019-03-26 17:32:01 +08:00
if not Pcd . IsArray ():
2019-01-21 17:44:50 +08:00
CApp = CApp + ' __FLEXIBLE_SIZE(*Size, %s , %s , %d / __ARRAY_ELEMENT_SIZE( %s , %s ) + (( %d %% __ARRAY_ELEMENT_SIZE( %s , %s )) ? 1 : 0)); // From %s Line %d Value %s \n ' % ( Pcd . DatumType , FieldName . strip ( "." ), ValueSize , Pcd . DatumType , FieldName . strip ( "." ), ValueSize , Pcd . DatumType , FieldName . strip ( "." ), FieldList [ FieldName . strip ( "." )][ 1 ], FieldList [ FieldName . strip ( "." )][ 2 ], FieldList [ FieldName . strip ( "." )][ 0 ]);
2018-02-28 13:59:20 +08:00
else :
NewFieldName = ''
FieldName_ori = FieldName . strip ( '.' )
while '[' in FieldName :
NewFieldName = NewFieldName + FieldName . split ( '[' , 1 )[ 0 ] + '[0]'
2019-05-09 17:19:56 +08:00
Array_Index = int ( FieldName . split ( '[' , 1 )[ 1 ] . split ( ']' , 1 )[ 0 ])
2018-02-28 13:59:20 +08:00
FieldName = FieldName . split ( ']' , 1 )[ 1 ]
FieldName = NewFieldName + FieldName
2019-03-26 17:32:01 +08:00
while '[' in FieldName and not Pcd . IsArray ():
2018-02-28 13:59:20 +08:00
FieldName = FieldName . rsplit ( '[' , 1 )[ 0 ]
2019-05-09 17:19:56 +08:00
CApp = CApp + ' __FLEXIBLE_SIZE(*Size, %s , %s , %d ); // From %s Line %d Value %s \n ' % ( Pcd . DatumType , FieldName . strip ( "." ), Array_Index + 1 , FieldList [ FieldName_ori ][ 1 ], FieldList [ FieldName_ori ][ 2 ], FieldList [ FieldName_ori ][ 0 ])
2022-03-15 20:16:54 +08:00
flexisbale_size_statement_cache = set ()
2018-02-28 13:59:20 +08:00
for skuname in Pcd . SkuOverrideValues :
2018-04-16 21:52:13 +08:00
if skuname == TAB_COMMON :
2018-02-28 13:59:20 +08:00
continue
for defaultstorenameitem in Pcd . SkuOverrideValues [ skuname ]:
CApp = CApp + "// SkuName: %s , DefaultStoreName: %s \n " % ( skuname , defaultstorenameitem )
2018-11-07 17:18:34 +08:00
for index in Pcd . SkuOverrideValues [ skuname ][ defaultstorenameitem ]:
2019-05-09 17:19:56 +08:00
if index :
ActualCap . append ( index )
2018-11-07 17:18:34 +08:00
for FieldList in [ Pcd . SkuOverrideValues [ skuname ][ defaultstorenameitem ][ index ]]:
if not FieldList :
continue
for FieldName in FieldList :
2022-03-15 20:16:54 +08:00
fieldinfo = tuple ( FieldList [ FieldName ])
if fieldinfo in flexisbale_size_statement_cache :
continue
flexisbale_size_statement_cache . add ( fieldinfo )
2018-11-07 17:18:34 +08:00
FieldName = "." + FieldName
2019-01-11 02:39:47 +08:00
IsArray = _IsFieldValueAnArray ( FieldList [ FieldName . strip ( "." )][ 0 ])
2018-11-07 17:18:34 +08:00
if IsArray and not ( FieldList [ FieldName . strip ( "." )][ 0 ] . startswith ( '{GUID' ) and FieldList [ FieldName . strip ( "." )][ 0 ] . endswith ( '}' )):
try :
Value = ValueExpressionEx ( FieldList [ FieldName . strip ( "." )][ 0 ], TAB_VOID , self . _GuidDict )( True )
except BadExpression :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " %
( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName . strip ( '.' ))), FieldList [ FieldName . strip ( "." )][ 1 ], FieldList [ FieldName . strip ( "." )][ 2 ]))
Value , ValueSize = ParseFieldValue ( Value )
2019-03-26 17:32:01 +08:00
if not Pcd . IsArray ():
2019-01-21 17:44:50 +08:00
CApp = CApp + ' __FLEXIBLE_SIZE(*Size, %s , %s , %d / __ARRAY_ELEMENT_SIZE( %s , %s ) + (( %d %% __ARRAY_ELEMENT_SIZE( %s , %s )) ? 1 : 0)); // From %s Line %d Value %s \n ' % ( Pcd . DatumType , FieldName . strip ( "." ), ValueSize , Pcd . DatumType , FieldName . strip ( "." ), ValueSize , Pcd . DatumType , FieldName . strip ( "." ), FieldList [ FieldName . strip ( "." )][ 1 ], FieldList [ FieldName . strip ( "." )][ 2 ], FieldList [ FieldName . strip ( "." )][ 0 ]);
2018-11-07 17:18:34 +08:00
else :
NewFieldName = ''
FieldName_ori = FieldName . strip ( '.' )
while '[' in FieldName :
NewFieldName = NewFieldName + FieldName . split ( '[' , 1 )[ 0 ] + '[0]'
2019-05-09 17:19:56 +08:00
Array_Index = int ( FieldName . split ( '[' , 1 )[ 1 ] . split ( ']' , 1 )[ 0 ])
2018-11-07 17:18:34 +08:00
FieldName = FieldName . split ( ']' , 1 )[ 1 ]
FieldName = NewFieldName + FieldName
2019-03-26 17:32:01 +08:00
while '[' in FieldName and not Pcd . IsArray ():
2018-11-07 17:18:34 +08:00
FieldName = FieldName . rsplit ( '[' , 1 )[ 0 ]
2019-05-09 17:19:56 +08:00
CApp = CApp + ' __FLEXIBLE_SIZE(*Size, %s , %s , %d ); // From %s Line %d Value %s \n ' % ( Pcd . DatumType , FieldName . strip ( "." ), Array_Index + 1 , FieldList [ FieldName_ori ][ 1 ], FieldList [ FieldName_ori ][ 2 ], FieldList [ FieldName_ori ][ 0 ])
2018-06-22 17:14:13 +08:00
if Pcd . PcdFieldValueFromFdf :
CApp = CApp + "// From fdf \n "
for FieldName in Pcd . PcdFieldValueFromFdf :
FieldName = "." + FieldName
2019-01-11 02:39:47 +08:00
IsArray = _IsFieldValueAnArray ( Pcd . PcdFieldValueFromFdf [ FieldName . strip ( "." )][ 0 ])
2018-06-22 17:14:13 +08:00
if IsArray and not ( Pcd . PcdFieldValueFromFdf [ FieldName . strip ( "." )][ 0 ] . startswith ( '{GUID' ) and Pcd . PcdFieldValueFromFdf [ FieldName . strip ( "." )][ 0 ] . endswith ( '}' )):
try :
Value = ValueExpressionEx ( Pcd . PcdFieldValueFromFdf [ FieldName . strip ( "." )][ 0 ], TAB_VOID , self . _GuidDict )( True )
except BadExpression :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " %
( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName . strip ( '.' ))), Pcd . PcdFieldValueFromFdf [ FieldName . strip ( "." )][ 1 ], Pcd . PcdFieldValueFromFdf [ FieldName . strip ( "." )][ 2 ]))
Value , ValueSize = ParseFieldValue ( Value )
2019-03-26 17:32:01 +08:00
if not Pcd . IsArray ():
2019-01-21 17:44:50 +08:00
CApp = CApp + ' __FLEXIBLE_SIZE(*Size, %s , %s , %d / __ARRAY_ELEMENT_SIZE( %s , %s ) + (( %d %% __ARRAY_ELEMENT_SIZE( %s , %s )) ? 1 : 0)); // From %s Line %d Value %s \n ' % ( Pcd . DatumType , FieldName . strip ( "." ), ValueSize , Pcd . DatumType , FieldName . strip ( "." ), ValueSize , Pcd . DatumType , FieldName . strip ( "." ), Pcd . PcdFieldValueFromFdf [ FieldName . strip ( "." )][ 1 ], Pcd . PcdFieldValueFromFdf [ FieldName . strip ( "." )][ 2 ], Pcd . PcdFieldValueFromFdf [ FieldName . strip ( "." )][ 0 ]);
2018-06-22 17:14:13 +08:00
else :
NewFieldName = ''
FieldName_ori = FieldName . strip ( '.' )
while '[' in FieldName :
NewFieldName = NewFieldName + FieldName . split ( '[' , 1 )[ 0 ] + '[0]'
2019-05-09 17:19:56 +08:00
Array_Index = int ( FieldName . split ( '[' , 1 )[ 1 ] . split ( ']' , 1 )[ 0 ])
2018-06-22 17:14:13 +08:00
FieldName = FieldName . split ( ']' , 1 )[ 1 ]
FieldName = NewFieldName + FieldName
while '[' in FieldName :
FieldName = FieldName . rsplit ( '[' , 1 )[ 0 ]
2019-05-09 17:19:56 +08:00
CApp = CApp + ' __FLEXIBLE_SIZE(*Size, %s , %s , %d ); // From %s Line %s Value %s \n ' % ( Pcd . DatumType , FieldName . strip ( "." ), Array_Index + 1 , Pcd . PcdFieldValueFromFdf [ FieldName_ori ][ 1 ], Pcd . PcdFieldValueFromFdf [ FieldName_ori ][ 2 ], Pcd . PcdFieldValueFromFdf [ FieldName_ori ][ 0 ])
2018-03-02 18:11:13 +08:00
if Pcd . PcdFieldValueFromComm :
CApp = CApp + "// From Command Line \n "
for FieldName in Pcd . PcdFieldValueFromComm :
FieldName = "." + FieldName
2019-01-11 02:39:47 +08:00
IsArray = _IsFieldValueAnArray ( Pcd . PcdFieldValueFromComm [ FieldName . strip ( "." )][ 0 ])
2018-03-02 23:51:56 +08:00
if IsArray and not ( Pcd . PcdFieldValueFromComm [ FieldName . strip ( "." )][ 0 ] . startswith ( '{GUID' ) and Pcd . PcdFieldValueFromComm [ FieldName . strip ( "." )][ 0 ] . endswith ( '}' )):
2018-03-02 18:11:13 +08:00
try :
2018-04-11 09:14:05 -07:00
Value = ValueExpressionEx ( Pcd . PcdFieldValueFromComm [ FieldName . strip ( "." )][ 0 ], TAB_VOID , self . _GuidDict )( True )
2018-03-02 18:11:13 +08:00
except BadExpression :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " %
2018-03-02 23:51:56 +08:00
( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName . strip ( '.' ))), Pcd . PcdFieldValueFromComm [ FieldName . strip ( "." )][ 1 ], Pcd . PcdFieldValueFromComm [ FieldName . strip ( "." )][ 2 ]))
2018-03-02 18:11:13 +08:00
Value , ValueSize = ParseFieldValue ( Value )
2019-03-26 17:32:01 +08:00
if not Pcd . IsArray ():
2019-01-21 17:44:50 +08:00
CApp = CApp + ' __FLEXIBLE_SIZE(*Size, %s , %s , %d / __ARRAY_ELEMENT_SIZE( %s , %s ) + (( %d %% __ARRAY_ELEMENT_SIZE( %s , %s )) ? 1 : 0)); // From %s Line %d Value %s \n ' % ( Pcd . DatumType , FieldName . strip ( "." ), ValueSize , Pcd . DatumType , FieldName . strip ( "." ), ValueSize , Pcd . DatumType , FieldName . strip ( "." ), Pcd . PcdFieldValueFromComm [ FieldName . strip ( "." )][ 1 ], Pcd . PcdFieldValueFromComm [ FieldName . strip ( "." )][ 2 ], Pcd . PcdFieldValueFromComm [ FieldName . strip ( "." )][ 0 ]);
2018-03-02 18:11:13 +08:00
else :
NewFieldName = ''
FieldName_ori = FieldName . strip ( '.' )
while '[' in FieldName :
NewFieldName = NewFieldName + FieldName . split ( '[' , 1 )[ 0 ] + '[0]'
2019-05-09 17:19:56 +08:00
Array_Index = int ( FieldName . split ( '[' , 1 )[ 1 ] . split ( ']' , 1 )[ 0 ])
2018-03-02 18:11:13 +08:00
FieldName = FieldName . split ( ']' , 1 )[ 1 ]
FieldName = NewFieldName + FieldName
2019-03-26 17:32:01 +08:00
while '[' in FieldName and not Pcd . IsArray ():
2018-03-02 18:11:13 +08:00
FieldName = FieldName . rsplit ( '[' , 1 )[ 0 ]
2019-05-09 17:19:56 +08:00
CApp = CApp + ' __FLEXIBLE_SIZE(*Size, %s , %s , %d ); // From %s Line %d Value %s \n ' % ( Pcd . DatumType , FieldName . strip ( "." ), Array_Index + 1 , Pcd . PcdFieldValueFromComm [ FieldName_ori ][ 1 ], Pcd . PcdFieldValueFromComm [ FieldName_ori ][ 2 ], Pcd . PcdFieldValueFromComm [ FieldName_ori ][ 0 ])
2018-11-07 17:18:34 +08:00
if Pcd . GetPcdMaxSize ():
CApp = CApp + " *Size = ( %d > *Size ? %d : *Size); // The Pcd maxsize is %d \n " % ( Pcd . GetPcdMaxSize (), Pcd . GetPcdMaxSize (), Pcd . GetPcdMaxSize ())
2019-05-09 17:19:56 +08:00
ArraySizeByAssign = self . CalculateActualCap ( ActualCap )
if ArraySizeByAssign > 1 :
CApp = CApp + " *Size = ( %d > *Size ? %d : *Size); \n " % ( ArraySizeByAssign , ArraySizeByAssign )
2018-02-28 13:59:20 +08:00
CApp = CApp + "} \n "
return CApp
2019-05-09 17:19:56 +08:00
def CalculateActualCap ( self , ActualCap ):
if not ActualCap :
return 1
maxsize = 1
for item in ActualCap :
index_elements = ArrayIndex . findall ( item )
rt = 1
for index_e in index_elements :
index_num = index_e . lstrip ( "[" ) . rstrip ( "]" ) . strip ()
if not index_num :
# Not support flexiable pcd array assignment
return 1
index_num = int ( index_num , 16 ) if index_num . startswith (( "0x" , "0X" )) else int ( index_num )
rt = rt * ( index_num + 1 )
if rt > maxsize :
maxsize = rt
return maxsize
2018-04-14 04:51:29 +08:00
@staticmethod
2018-12-24 18:24:46 +08:00
def GenerateSizeStatments ( Pcd , skuname , defaultstorename ):
2018-11-07 17:18:34 +08:00
if Pcd . IsArray ():
r_datatype = [ Pcd . BaseDatumType ]
2018-12-24 18:24:46 +08:00
lastoneisEmpty = False
2018-11-07 17:18:34 +08:00
for dem in Pcd . Capacity :
2018-12-24 18:24:46 +08:00
if lastoneisEmpty :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . " %
( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName ))))
if dem == '0' or dem == "-1" :
2018-11-07 17:18:34 +08:00
r_datatype . append ( "[1]" )
2018-12-24 18:24:46 +08:00
lastoneisEmpty = True
2018-11-07 17:18:34 +08:00
else :
r_datatype . append ( "[" + dem + "]" )
2018-12-24 18:24:46 +08:00
if Pcd . Type in [ MODEL_PCD_DYNAMIC_EX_HII , MODEL_PCD_DYNAMIC_HII ]:
PcdDefValue = Pcd . SkuInfoList . get ( skuname ) . DefaultStoreDict . get ( defaultstorename )
elif Pcd . Type in [ MODEL_PCD_DYNAMIC_EX_DEFAULT , MODEL_PCD_DYNAMIC_VPD , MODEL_PCD_DYNAMIC_DEFAULT , MODEL_PCD_DYNAMIC_EX_VPD ]:
PcdDefValue = Pcd . SkuInfoList . get ( skuname ) . DefaultValue
else :
PcdDefValue = Pcd . DefaultValue
if lastoneisEmpty :
if "{CODE(" not in PcdDefValue :
2019-01-21 17:44:50 +08:00
sizebasevalue_plus = "( %s / sizeof( %s ) + 1)" % (( DscBuildData . GetStructurePcdMaxSize ( Pcd ), Pcd . BaseDatumType ))
sizebasevalue = "( %s / sizeof( %s ))" % (( DscBuildData . GetStructurePcdMaxSize ( Pcd ), Pcd . BaseDatumType ))
2018-12-24 18:24:46 +08:00
sizeof = "sizeof( %s )" % Pcd . BaseDatumType
2019-01-21 17:44:50 +08:00
CApp = ' int ArraySize = %s %% %s ? %s : %s ; \n ' % ( ( DscBuildData . GetStructurePcdMaxSize ( Pcd ), sizeof , sizebasevalue_plus , sizebasevalue ))
CApp += ' Size = ArraySize * sizeof( %s ); \n ' % Pcd . BaseDatumType
2018-12-24 18:24:46 +08:00
else :
CApp = " Size = 0; \n "
else :
CApp = ' Size = sizeof( %s ); \n ' % ( "" . join ( r_datatype ) )
2018-11-07 17:18:34 +08:00
else :
CApp = ' Size = sizeof( %s ); \n ' % ( Pcd . DatumType )
2018-02-28 13:59:20 +08:00
CApp = CApp + ' Cal_ %s _ %s _Size(&Size); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
return CApp
2018-04-14 04:51:29 +08:00
2018-11-07 17:18:34 +08:00
def GetIndicator ( self , index , FieldName , Pcd ):
def cleanupindex ( indexstr ):
return indexstr . strip ( "[" ) . strip ( "]" ) . strip ()
index_elements = ArrayIndex . findall ( index )
pcd_capacity = Pcd . Capacity
if index :
indicator = "(Pcd"
if len ( pcd_capacity ) > 2 :
2018-12-16 15:19:42 +08:00
for i in range ( 0 , len ( index_elements )):
2018-11-07 17:18:34 +08:00
index_ele = index_elements [ i ]
index_num = index_ele . strip ( "[" ) . strip ( "]" ) . strip ()
if i == len ( index_elements ) - 2 :
indicator += "+ %d *Size/sizeof( %s )/ %d + %s )" % ( int ( cleanupindex ( index_elements [ i + 1 ])), Pcd . BaseDatumType , reduce ( lambda x , y : int ( x ) * int ( y ), pcd_capacity [: - 1 ]), cleanupindex ( index_elements [ i ]))
break
else :
indicator += " + %d * %s *Size/sizeof( %s )/ %d " % ( int ( cleanupindex ( index_elements [ i ])), reduce ( lambda x , y : int ( x ) * int ( y ), pcd_capacity [ i + 1 : - 1 ]), Pcd . BaseDatumType , reduce ( lambda x , y : int ( x ) * int ( y ), pcd_capacity [: - 1 ]))
elif len ( pcd_capacity ) == 2 :
indicator += "+ %d *Size/sizeof( %s )/ %d + %s )" % ( int ( cleanupindex ( index_elements [ 0 ])), Pcd . BaseDatumType , int ( pcd_capacity [ 0 ]), index_elements [ 1 ] . strip ( "[" ) . strip ( "]" ) . strip ())
elif len ( pcd_capacity ) == 1 :
index_ele = index_elements [ 0 ]
index_num = index_ele . strip ( "[" ) . strip ( "]" ) . strip ()
indicator += " + %s )" % ( index_num )
else :
indicator = "Pcd"
if FieldName :
indicator += "->" + FieldName
return indicator
2018-06-25 18:31:33 +08:00
def GenerateDefaultValueAssignFunction ( self , Pcd ):
2018-02-28 13:59:20 +08:00
CApp = "// Default value in Dec \n "
2018-11-07 17:18:34 +08:00
CApp = CApp + "void Assign_ %s _ %s _Default_Value( %s *Pcd){ \n " % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . BaseDatumType )
2018-02-28 13:59:20 +08:00
CApp = CApp + ' UINT32 FieldSize; \n '
CApp = CApp + ' CHAR8 *Value; \n '
2019-05-09 17:19:56 +08:00
CApp = CApp + ' UINT32 PcdArraySize; \n '
2018-02-28 13:59:20 +08:00
DefaultValueFromDec = Pcd . DefaultValueFromDec
2019-01-11 02:39:47 +08:00
IsArray = _IsFieldValueAnArray ( Pcd . DefaultValueFromDec )
2018-02-28 13:59:20 +08:00
if IsArray :
try :
2018-04-11 09:14:05 -07:00
DefaultValueFromDec = ValueExpressionEx ( Pcd . DefaultValueFromDec , TAB_VOID )( True )
2018-02-28 13:59:20 +08:00
except BadExpression :
EdkLogger . error ( "Build" , FORMAT_INVALID , "Invalid value format for %s . %s , from DEC: %s " %
( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , DefaultValueFromDec ))
2018-03-08 13:56:21 +08:00
DefaultValueFromDec = StringToArray ( DefaultValueFromDec )
2018-02-28 13:59:20 +08:00
Value , ValueSize = ParseFieldValue ( DefaultValueFromDec )
2019-01-21 17:44:50 +08:00
if IsArray :
2019-05-09 17:19:56 +08:00
#
# Use memcpy() to copy value into field
#
if Pcd . IsArray ():
pcdarraysize = Pcd . PcdArraySize ()
if "{CODE(" in Pcd . DefaultValueFromDec :
if Pcd . Capacity [ - 1 ] != "-1" :
2022-08-30 18:20:54 +08:00
CApp = CApp + '__STATIC_ASSERT(sizeof( %s _ %s _INIT_Value) <= %d * sizeof( %s ), "Pcd %s . %s Value in Dec exceed the array capability %s "); // From %s Line %s \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , pcdarraysize , Pcd . BaseDatumType , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . DatumType , Pcd . DefaultValueFromDecInfo [ 0 ], Pcd . DefaultValueFromDecInfo [ 1 ])
2019-05-09 17:19:56 +08:00
CApp = CApp + ' PcdArraySize = sizeof( %s _ %s _INIT_Value); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
CApp = CApp + ' memcpy (Pcd, %s _ %s _INIT_Value,PcdArraySize); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
else :
if Pcd . Capacity [ - 1 ] != "-1" :
2022-08-30 18:20:54 +08:00
CApp = CApp + '__STATIC_ASSERT( %d <= %d * sizeof( %s ), "Pcd %s . %s Value in Dec exceed the array capability %s "); // From %s Line %s \n ' % ( ValueSize , pcdarraysize , Pcd . BaseDatumType , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . DatumType , Pcd . DefaultValueFromDecInfo [ 0 ], Pcd . DefaultValueFromDecInfo [ 1 ])
2019-05-09 17:19:56 +08:00
CApp = CApp + ' PcdArraySize = %d ; \n ' % ValueSize
CApp = CApp + ' Value = %s ; // From DEC Default Value %s \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ), Pcd . DefaultValueFromDec )
CApp = CApp + ' memcpy (Pcd, Value, PcdArraySize); \n '
2018-11-07 17:18:34 +08:00
else :
2019-05-09 17:19:56 +08:00
if "{CODE(" in Pcd . DefaultValueFromDec :
CApp = CApp + ' PcdArraySize = sizeof( %s _ %s _INIT_Value); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
CApp = CApp + ' memcpy (Pcd, & %s _ %s _INIT_Value,PcdArraySize); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
else :
CApp = CApp + ' Value = %s ; // From DEC Default Value %s \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ), Pcd . DefaultValueFromDec )
CApp = CApp + ' memcpy (Pcd, Value, %d ); \n ' % ( ValueSize )
2019-01-21 17:44:50 +08:00
elif isinstance ( Value , str ):
CApp = CApp + ' Pcd = %s ; // From DEC Default Value %s \n ' % ( Value , Pcd . DefaultValueFromDec )
2018-11-07 17:18:34 +08:00
for index in Pcd . DefaultValues :
FieldList = Pcd . DefaultValues [ index ]
2018-02-28 13:59:20 +08:00
if not FieldList :
continue
for FieldName in FieldList :
2019-01-11 02:39:47 +08:00
IsArray = _IsFieldValueAnArray ( FieldList [ FieldName ][ 0 ])
2018-02-28 13:59:20 +08:00
if IsArray :
try :
2018-04-11 09:14:05 -07:00
FieldList [ FieldName ][ 0 ] = ValueExpressionEx ( FieldList [ FieldName ][ 0 ], TAB_VOID , self . _GuidDict )( True )
2018-02-28 13:59:20 +08:00
except BadExpression :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " %
2018-06-25 18:31:33 +08:00
( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName )), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ]))
2018-02-28 13:59:20 +08:00
try :
Value , ValueSize = ParseFieldValue ( FieldList [ FieldName ][ 0 ])
except Exception :
2018-06-25 18:31:33 +08:00
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " % ( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName )), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ]))
2018-11-07 17:18:34 +08:00
indicator = self . GetIndicator ( index , FieldName , Pcd )
2019-01-21 17:44:50 +08:00
if IsArray :
2018-02-28 13:59:20 +08:00
#
# Use memcpy() to copy value into field
#
2019-02-14 16:48:03 +08:00
CApp = CApp + ' FieldSize = __FIELD_SIZE( %s , %s ); \n ' % ( Pcd . BaseDatumType , FieldName )
2018-04-14 04:51:29 +08:00
CApp = CApp + ' Value = %s ; // From %s Line %d Value %s \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2019-02-14 16:48:03 +08:00
CApp = CApp + ' __STATIC_ASSERT((__FIELD_SIZE( %s , %s ) >= %d ) || (__FIELD_SIZE( %s , %s ) == 0), "Input buffer exceeds the buffer array"); // From %s Line %d Value %s \n ' % ( Pcd . BaseDatumType , FieldName , ValueSize , Pcd . BaseDatumType , FieldName , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2018-11-07 17:18:34 +08:00
CApp = CApp + ' memcpy (& %s , Value, (FieldSize > 0 && FieldSize < %d ) ? FieldSize : %d ); \n ' % ( indicator , ValueSize , ValueSize )
2019-01-21 17:44:50 +08:00
elif isinstance ( Value , str ):
CApp = CApp + ' %s = %s ; // From %s Line %d Value %s \n ' % ( indicator , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2018-02-28 13:59:20 +08:00
else :
2018-09-04 17:26:11 +08:00
if '[' in FieldName and ']' in FieldName :
Index = int ( FieldName . split ( '[' )[ 1 ] . split ( ']' )[ 0 ])
CApp = CApp + ' __STATIC_ASSERT(( %d < __ARRAY_SIZE(Pcd-> %s )) || (__ARRAY_SIZE(Pcd-> %s ) == 0), "array index exceeds the array number"); // From %s Line %d Index of %s \n ' % ( Index , FieldName . split ( '[' )[ 0 ], FieldName . split ( '[' )[ 0 ], FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldName )
2018-02-28 13:59:20 +08:00
if ValueSize > 4 :
2018-11-07 17:18:34 +08:00
CApp = CApp + ' %s = %d ULL; // From %s Line %d Value %s \n ' % ( indicator , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2018-02-28 13:59:20 +08:00
else :
2018-11-07 17:18:34 +08:00
CApp = CApp + ' %s = %d ; // From %s Line %d Value %s \n ' % ( indicator , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2018-02-28 13:59:21 +08:00
CApp = CApp + "} \n "
return CApp
2018-04-14 04:51:29 +08:00
@staticmethod
def GenerateDefaultValueAssignStatement ( Pcd ):
2018-02-28 13:59:21 +08:00
CApp = ' Assign_ %s _ %s _Default_Value(Pcd); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
return CApp
2018-04-14 04:51:29 +08:00
2018-12-24 18:24:46 +08:00
def GetPcdDscRawDefaultValue ( self , Pcd , SkuName , DefaultStoreName ):
2018-10-24 20:31:23 +08:00
if Pcd . Type in PCD_DYNAMIC_TYPE_SET or Pcd . Type in PCD_DYNAMIC_EX_TYPE_SET :
if ( SkuName , DefaultStoreName ) == ( TAB_DEFAULT , TAB_DEFAULT_STORES_DEFAULT ):
pcddefaultvalue = Pcd . DefaultFromDSC . get ( TAB_DEFAULT , {}) . get ( TAB_DEFAULT_STORES_DEFAULT ) if Pcd . DefaultFromDSC else None
else :
pcddefaultvalue = Pcd . DscRawValue . get ( SkuName , {}) . get ( DefaultStoreName )
2018-02-28 13:59:21 +08:00
else :
2018-10-24 20:31:23 +08:00
pcddefaultvalue = Pcd . DscRawValue . get ( SkuName , {}) . get ( TAB_DEFAULT_STORES_DEFAULT )
2018-11-07 17:18:34 +08:00
2018-12-24 18:24:46 +08:00
return pcddefaultvalue
2019-05-09 17:19:56 +08:00
def GetPcdDscRawValueInfo ( self , Pcd , SkuName , DefaultStoreName ):
DscValueInfo = Pcd . DscRawValueInfo . get ( SkuName , {}) . get ( DefaultStoreName )
if DscValueInfo :
dscfilepath , lineno = DscValueInfo
else :
dscfilepath = self . MetaFile . File
lineno = ""
return dscfilepath , lineno
2018-12-24 18:24:46 +08:00
def GenerateInitValueFunction ( self , Pcd , SkuName , DefaultStoreName ):
CApp = "// Value in Dsc for Sku: %s , DefaultStore %s \n " % ( SkuName , DefaultStoreName )
CApp = CApp + "void Assign_ %s _ %s _ %s _ %s _Value( %s *Pcd){ \n " % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName , Pcd . BaseDatumType )
CApp = CApp + ' UINT32 FieldSize; \n '
CApp = CApp + ' CHAR8 *Value; \n '
2019-05-09 17:19:56 +08:00
CApp = CApp + ' UINT32 PcdArraySize; \n '
2018-12-24 18:24:46 +08:00
CApp = CApp + "// SkuName: %s , DefaultStoreName: %s \n " % ( TAB_DEFAULT , TAB_DEFAULT_STORES_DEFAULT )
inherit_OverrideValues = Pcd . SkuOverrideValues [ SkuName ]
2019-05-09 17:19:56 +08:00
dscfilepath , lineno = self . GetPcdDscRawValueInfo ( Pcd , SkuName , DefaultStoreName )
if lineno :
valuefrom = " %s Line %s " % ( dscfilepath , str ( lineno ))
else :
valuefrom = dscfilepath
2018-12-24 18:24:46 +08:00
pcddefaultvalue = self . GetPcdDscRawDefaultValue ( Pcd , SkuName , DefaultStoreName )
2018-11-07 17:18:34 +08:00
if pcddefaultvalue :
FieldList = pcddefaultvalue
2019-01-11 02:39:47 +08:00
IsArray = _IsFieldValueAnArray ( FieldList )
2018-11-07 17:18:34 +08:00
if IsArray :
if "{CODE(" not in FieldList :
2018-02-28 13:59:20 +08:00
try :
2018-04-11 09:14:05 -07:00
FieldList = ValueExpressionEx ( FieldList , TAB_VOID )( True )
2018-02-28 13:59:20 +08:00
except BadExpression :
EdkLogger . error ( "Build" , FORMAT_INVALID , "Invalid value format for %s . %s , from DSC: %s " %
( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldList ))
2018-11-07 17:18:34 +08:00
Value , ValueSize = ParseFieldValue ( FieldList )
2018-02-28 13:59:21 +08:00
2018-11-07 17:18:34 +08:00
if ( SkuName , DefaultStoreName ) == ( TAB_DEFAULT , TAB_DEFAULT_STORES_DEFAULT ):
if isinstance ( Value , str ):
if "{CODE(" in Value :
2019-05-09 17:19:56 +08:00
if Pcd . IsArray () and Pcd . Capacity [ - 1 ] != "-1" :
pcdarraysize = Pcd . PcdArraySize ()
2022-08-30 18:20:54 +08:00
CApp = CApp + '__STATIC_ASSERT(sizeof( %s _ %s _ %s _ %s _Value) <= %d * sizeof( %s ), "Pcd %s . %s Value in Dsc exceed the array capability %s "); // From %s \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName , pcdarraysize , Pcd . BaseDatumType , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . DatumType , valuefrom )
2019-05-09 17:19:56 +08:00
CApp = CApp + ' PcdArraySize = sizeof( %s _ %s _ %s _ %s _Value); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName )
CApp = CApp + ' memcpy (Pcd, & %s _ %s _ %s _ %s _Value,PcdArraySize); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName )
2018-11-07 17:18:34 +08:00
else :
2018-06-25 18:31:33 +08:00
CApp = CApp + ' Pcd = %s ; // From DSC Default Value %s \n ' % ( Value , Pcd . DefaultFromDSC . get ( TAB_DEFAULT , {}) . get ( TAB_DEFAULT_STORES_DEFAULT , Pcd . DefaultValue ) if Pcd . DefaultFromDSC else Pcd . DefaultValue )
2018-11-07 17:18:34 +08:00
elif IsArray :
2019-05-09 17:19:56 +08:00
#
# Use memcpy() to copy value into field
#
if Pcd . IsArray ():
pcdarraysize = Pcd . PcdArraySize ()
if "{CODE(" in pcddefaultvalue :
if Pcd . Capacity [ - 1 ] != "-1" :
2022-08-30 18:20:54 +08:00
CApp = CApp + '__STATIC_ASSERT(sizeof( %s _ %s _ %s _ %s _Value) <= %d * sizeof( %s ), "Pcd %s . %s Value in Dsc exceed the array capability %s "); // From %s \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName , pcdarraysize , Pcd . BaseDatumType , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . DatumType , valuefrom )
2019-05-09 17:19:56 +08:00
CApp = CApp + ' PcdArraySize = sizeof( %s _ %s _ %s _ %s _Value); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName )
CApp = CApp + ' memcpy (Pcd, %s _ %s _ %s _ %s _Value, PcdArraySize); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName )
else :
if Pcd . Capacity [ - 1 ] != "-1" :
2022-08-30 18:20:54 +08:00
CApp = CApp + '__STATIC_ASSERT( %d <= %d * sizeof( %s ), "Pcd %s . %s Value in Dsc exceed the array capability %s "); // From %s \n ' % ( ValueSize , pcdarraysize , Pcd . BaseDatumType , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . DatumType , valuefrom )
2019-05-09 17:19:56 +08:00
CApp = CApp + ' PcdArraySize = %d ; \n ' % ValueSize
CApp = CApp + ' Value = %s ; // From DSC Default Value %s \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ), Pcd . DefaultFromDSC . get ( TAB_DEFAULT , {}) . get ( TAB_DEFAULT_STORES_DEFAULT , Pcd . DefaultValue ) if Pcd . DefaultFromDSC else Pcd . DefaultValue )
CApp = CApp + ' memcpy (Pcd, Value, PcdArraySize); \n '
2018-11-07 17:18:34 +08:00
else :
2019-05-09 17:19:56 +08:00
if "{CODE(" in pcddefaultvalue :
CApp = CApp + ' PcdArraySize = %d < sizeof( %s ) * %d ? %d : sizeof( %s ) * %d ; \n ' % ( ValueSize , Pcd . BaseDatumType , pcdarraysize , ValueSize , Pcd . BaseDatumType , pcdarraysize )
CApp = CApp + ' memcpy (Pcd, & %s _ %s _ %s _ %s _Value, PcdArraySize); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName )
else :
CApp = CApp + ' Value = %s ; // From DSC Default Value %s \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ), Pcd . DefaultFromDSC . get ( TAB_DEFAULT , {}) . get ( TAB_DEFAULT_STORES_DEFAULT , Pcd . DefaultValue ) if Pcd . DefaultFromDSC else Pcd . DefaultValue )
CApp = CApp + ' memcpy (Pcd, Value, %d ); \n ' % ( ValueSize )
2018-11-07 17:18:34 +08:00
else :
if isinstance ( Value , str ):
if "{CODE(" in Value :
2019-05-09 17:19:56 +08:00
if Pcd . IsArray () and Pcd . Capacity [ - 1 ] != "-1" :
pcdarraysize = Pcd . PcdArraySize ()
2022-08-30 18:20:54 +08:00
CApp = CApp + '__STATIC_ASSERT(sizeof( %s _ %s _ %s _ %s _Value) <= %d * sizeof( %s ), "Pcd %s . %s Value in Dsc exceed the array capability %s "); // From %s \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName , pcdarraysize , Pcd . BaseDatumType , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . DatumType , valuefrom )
2019-05-09 17:19:56 +08:00
CApp = CApp + ' PcdArraySize = sizeof( %s _ %s _ %s _ %s _Value); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName )
CApp = CApp + ' memcpy (Pcd, & %s _ %s _ %s _ %s _Value, PcdArraySize); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName )
2018-11-07 17:18:34 +08:00
else :
2018-06-25 18:31:33 +08:00
CApp = CApp + ' Pcd = %s ; // From DSC Default Value %s \n ' % ( Value , Pcd . DscRawValue . get ( SkuName , {}) . get ( DefaultStoreName ))
2018-11-07 17:18:34 +08:00
elif IsArray :
2019-05-09 17:19:56 +08:00
#
# Use memcpy() to copy value into field
#
if Pcd . IsArray ():
pcdarraysize = Pcd . PcdArraySize ()
if "{CODE(" in pcddefaultvalue :
if Pcd . Capacity [ - 1 ] != "-1" :
2022-08-30 18:20:54 +08:00
CApp = CApp + '__STATIC_ASSERT(sizeof( %s _ %s _ %s _ %s _Value) <= %d * sizeof( %s ), "Pcd %s . %s Value in Dsc exceed the array capability %s "); // From %s \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName , pcdarraysize , Pcd . BaseDatumType , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . DatumType , valuefrom )
2019-05-09 17:19:56 +08:00
CApp + ' PcdArraySize = sizeof( %s _ %s _ %s _ %s _Value); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName )
CApp = CApp + ' memcpy (Pcd, %s _ %s _ %s _ %s _Value, PcdArraySize); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName )
else :
if Pcd . Capacity [ - 1 ] != "-1" :
2022-08-30 18:20:54 +08:00
CApp = CApp + '__STATIC_ASSERT( %d <= %d * sizeof( %s ), "Pcd %s . %s Value in Dsc exceed the array capability %s "); // From %s \n ' % ( ValueSize , pcdarraysize , Pcd . BaseDatumType , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . DatumType , valuefrom )
2019-05-09 17:19:56 +08:00
CApp = CApp + ' PcdArraySize = %d ; \n ' % ValueSize
CApp = CApp + ' Value = %s ; // From DSC Default Value %s \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ), Pcd . DscRawValue . get ( TAB_DEFAULT , {}) . get ( TAB_DEFAULT_STORES_DEFAULT , Pcd . DefaultValue ) if Pcd . DefaultFromDSC else Pcd . DefaultValue )
CApp = CApp + ' memcpy (Pcd, Value, PcdArraySize); \n '
2018-11-07 17:18:34 +08:00
else :
2019-05-09 17:19:56 +08:00
if "{CODE(" in pcddefaultvalue :
CApp = CApp + ' PcdArraySize = %d < sizeof( %s ) * %d ? %d : sizeof( %s ) * %d ; \n ' % ( ValueSize , Pcd . BaseDatumType , pcdarraysize , ValueSize , Pcd . BaseDatumType , pcdarraysize )
CApp = CApp + ' memcpy (Pcd, & %s _ %s _ %s _ %s _Value, PcdArraySize); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName )
else :
CApp = CApp + ' Value = %s ; // From DSC Default Value %s \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ), Pcd . DscRawValue . get ( SkuName , {}) . get ( DefaultStoreName ))
CApp = CApp + ' memcpy (Pcd, Value, %d ); \n ' % ( ValueSize )
2018-11-07 17:18:34 +08:00
inheritvalue = inherit_OverrideValues . get ( DefaultStoreName )
if not inheritvalue :
inheritvalue = []
for index in inheritvalue :
FieldList = inheritvalue [ index ]
if not FieldList :
2018-02-28 13:59:21 +08:00
continue
2018-06-25 18:31:33 +08:00
if ( SkuName , DefaultStoreName ) == ( TAB_DEFAULT , TAB_DEFAULT_STORES_DEFAULT ) or (( ( SkuName , '' ) not in Pcd . ValueChain ) and ( ( SkuName , DefaultStoreName ) not in Pcd . ValueChain )):
2018-02-28 13:59:21 +08:00
for FieldName in FieldList :
2018-11-07 17:18:34 +08:00
indicator = self . GetIndicator ( index , FieldName , Pcd )
2019-01-11 02:39:47 +08:00
IsArray = _IsFieldValueAnArray ( FieldList [ FieldName ][ 0 ])
2018-02-28 13:59:21 +08:00
if IsArray :
try :
2018-10-18 17:46:40 +08:00
FieldList [ FieldName ][ 0 ] = ValueExpressionEx ( FieldList [ FieldName ][ 0 ], TAB_VOID , self . _GuidDict )( True )
2018-02-28 13:59:21 +08:00
except BadExpression :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " %
( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName )), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ]))
try :
2018-10-18 17:46:40 +08:00
Value , ValueSize = ParseFieldValue ( FieldList [ FieldName ][ 0 ])
2018-02-28 13:59:21 +08:00
except Exception :
2018-06-25 18:31:33 +08:00
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " % ( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName )), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ]))
2018-02-28 13:59:21 +08:00
if isinstance ( Value , str ):
CApp = CApp + ' Pcd-> %s = %s ; // From %s Line %d Value %s \n ' % ( FieldName , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
elif IsArray :
#
# Use memcpy() to copy value into field
#
2018-11-07 17:18:34 +08:00
CApp = CApp + ' FieldSize = __FIELD_SIZE( %s , %s ); \n ' % ( Pcd . BaseDatumType , FieldName )
2018-04-14 04:51:29 +08:00
CApp = CApp + ' Value = %s ; // From %s Line %d Value %s \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2019-02-14 16:48:03 +08:00
CApp = CApp + ' __STATIC_ASSERT((__FIELD_SIZE( %s , %s ) >= %d ) || (__FIELD_SIZE( %s , %s ) == 0), "Input buffer exceeds the buffer array"); // From %s Line %d Value %s \n ' % ( Pcd . BaseDatumType , FieldName , ValueSize , Pcd . BaseDatumType , FieldName , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2018-11-07 17:18:34 +08:00
CApp = CApp + ' memcpy (& %s , Value, (FieldSize > 0 && FieldSize < %d ) ? FieldSize : %d ); \n ' % ( indicator , ValueSize , ValueSize )
2018-02-28 13:59:20 +08:00
else :
2018-09-04 17:26:11 +08:00
if '[' in FieldName and ']' in FieldName :
Index = int ( FieldName . split ( '[' )[ 1 ] . split ( ']' )[ 0 ])
CApp = CApp + ' __STATIC_ASSERT(( %d < __ARRAY_SIZE(Pcd-> %s )) || (__ARRAY_SIZE(Pcd-> %s ) == 0), "array index exceeds the array number"); // From %s Line %d Index of %s \n ' % ( Index , FieldName . split ( '[' )[ 0 ], FieldName . split ( '[' )[ 0 ], FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldName )
2018-02-28 13:59:21 +08:00
if ValueSize > 4 :
2018-11-07 17:18:34 +08:00
CApp = CApp + ' %s = %d ULL; // From %s Line %d Value %s \n ' % ( indicator , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2018-02-28 13:59:21 +08:00
else :
2018-11-07 17:18:34 +08:00
CApp = CApp + ' %s = %d ; // From %s Line %d Value %s \n ' % ( indicator , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2018-02-28 13:59:20 +08:00
CApp = CApp + "} \n "
return CApp
2018-04-14 04:51:29 +08:00
@staticmethod
2018-06-25 18:31:33 +08:00
def GenerateInitValueStatement ( Pcd , SkuName , DefaultStoreName ):
CApp = ' Assign_ %s _ %s _ %s _ %s _Value(Pcd); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , SkuName , DefaultStoreName )
2018-02-28 13:59:20 +08:00
return CApp
2018-04-14 04:51:29 +08:00
2018-06-25 18:31:33 +08:00
def GenerateCommandLineValue ( self , Pcd ):
2018-03-02 18:11:13 +08:00
CApp = "// Value in CommandLine \n "
2018-11-07 17:18:34 +08:00
CApp = CApp + "void Assign_ %s _ %s _CommandLine_Value( %s *Pcd){ \n " % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . BaseDatumType )
2018-03-02 18:11:13 +08:00
CApp = CApp + ' UINT32 FieldSize; \n '
CApp = CApp + ' CHAR8 *Value; \n '
pcddefaultvalue = Pcd . PcdValueFromComm
2018-06-25 18:31:33 +08:00
for FieldList in [ pcddefaultvalue , Pcd . PcdFieldValueFromComm ]:
2018-03-02 18:11:13 +08:00
if not FieldList :
continue
if pcddefaultvalue and FieldList == pcddefaultvalue :
2019-01-11 02:39:47 +08:00
IsArray = _IsFieldValueAnArray ( FieldList )
2018-03-02 18:11:13 +08:00
if IsArray :
try :
2018-04-11 09:14:05 -07:00
FieldList = ValueExpressionEx ( FieldList , TAB_VOID )( True )
2018-03-02 18:11:13 +08:00
except BadExpression :
2018-03-08 13:56:21 +08:00
EdkLogger . error ( "Build" , FORMAT_INVALID , "Invalid value format for %s . %s , from Command: %s " %
2018-03-02 18:11:13 +08:00
( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldList ))
Value , ValueSize = ParseFieldValue ( FieldList )
if isinstance ( Value , str ):
CApp = CApp + ' Pcd = %s ; // From Command Line \n ' % ( Value )
elif IsArray :
#
# Use memcpy() to copy value into field
#
2018-04-14 04:51:29 +08:00
CApp = CApp + ' Value = %s ; // From Command Line. \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ))
2018-03-02 18:11:13 +08:00
CApp = CApp + ' memcpy (Pcd, Value, %d ); \n ' % ( ValueSize )
continue
for FieldName in FieldList :
2019-01-11 02:39:47 +08:00
IsArray = _IsFieldValueAnArray ( FieldList [ FieldName ][ 0 ])
2018-03-02 18:11:13 +08:00
if IsArray :
try :
2018-04-11 09:14:05 -07:00
FieldList [ FieldName ][ 0 ] = ValueExpressionEx ( FieldList [ FieldName ][ 0 ], TAB_VOID , self . _GuidDict )( True )
2018-03-02 18:11:13 +08:00
except BadExpression :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " %
( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName )), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ]))
except :
2018-06-25 18:31:26 +08:00
print ( "error" )
2018-03-02 18:11:13 +08:00
try :
Value , ValueSize = ParseFieldValue ( FieldList [ FieldName ][ 0 ])
except Exception :
2018-06-25 18:31:33 +08:00
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " % ( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName )), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ]))
2018-03-02 18:11:13 +08:00
if isinstance ( Value , str ):
CApp = CApp + ' Pcd-> %s = %s ; // From %s Line %d Value %s \n ' % ( FieldName , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
elif IsArray :
#
# Use memcpy() to copy value into field
#
2018-11-07 17:18:34 +08:00
CApp = CApp + ' FieldSize = __FIELD_SIZE( %s , %s ); \n ' % ( Pcd . BaseDatumType , FieldName )
2018-04-14 04:51:29 +08:00
CApp = CApp + ' Value = %s ; // From %s Line %d Value %s \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2019-02-14 16:48:03 +08:00
CApp = CApp + ' __STATIC_ASSERT((__FIELD_SIZE( %s , %s ) >= %d ) || (__FIELD_SIZE( %s , %s ) == 0), "Input buffer exceeds the buffer array"); // From %s Line %d Value %s \n ' % ( Pcd . BaseDatumType , FieldName , ValueSize , Pcd . BaseDatumType , FieldName , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2018-03-02 18:11:13 +08:00
CApp = CApp + ' memcpy (&Pcd-> %s , Value, (FieldSize > 0 && FieldSize < %d ) ? FieldSize : %d ); \n ' % ( FieldName , ValueSize , ValueSize )
else :
2018-10-22 16:23:18 +08:00
if '[' in FieldName and ']' in FieldName :
Index = int ( FieldName . split ( '[' )[ 1 ] . split ( ']' )[ 0 ])
CApp = CApp + ' __STATIC_ASSERT(( %d < __ARRAY_SIZE(Pcd-> %s )) || (__ARRAY_SIZE(Pcd-> %s ) == 0), "array index exceeds the array number"); // From %s Line %d Index of %s \n ' % ( Index , FieldName . split ( '[' )[ 0 ], FieldName . split ( '[' )[ 0 ], FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldName )
2018-03-02 18:11:13 +08:00
if ValueSize > 4 :
CApp = CApp + ' Pcd-> %s = %d ULL; // From %s Line %d Value %s \n ' % ( FieldName , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
else :
CApp = CApp + ' Pcd-> %s = %d ; // From %s Line %d Value %s \n ' % ( FieldName , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
CApp = CApp + "} \n "
return CApp
2018-04-14 04:51:29 +08:00
2020-11-04 11:01:39 +08:00
def GenerateModuleScopeValue ( self , Pcd ):
CApp = "// Value in Dsc Module scope \n "
for ModuleGuid in Pcd . PcdFiledValueFromDscComponent :
CApp = CApp + "void Assign_ %s _ %s _ %s _Value( %s *Pcd){ \n " % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , ModuleGuid , Pcd . BaseDatumType )
CApp = CApp + ' UINT32 FieldSize; \n '
CApp = CApp + ' CHAR8 *Value; \n '
pcddefaultvalue , file_path , lineNo = Pcd . PcdValueFromComponents . get ( ModuleGuid ,( None , None , None ))
if pcddefaultvalue :
IsArray = _IsFieldValueAnArray ( pcddefaultvalue )
if IsArray :
try :
FieldList = ValueExpressionEx ( pcddefaultvalue , TAB_VOID )( True )
except BadExpression :
EdkLogger . error ( "Build" , FORMAT_INVALID , "Invalid value format for %s . %s , from %s Line %s : %s " %
( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , file_path , lineNo , FieldList ))
Value , ValueSize = ParseFieldValue ( FieldList )
if isinstance ( Value , str ):
CApp = CApp + ' Pcd = %s ; // From %s Line %s \n ' % ( Value , file_path , lineNo )
elif IsArray :
#
# Use memcpy() to copy value into field
#
CApp = CApp + ' Value = %s ; // From %s Line %s . \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ), file_path , lineNo )
CApp = CApp + ' memcpy (Pcd, Value, %d ); \n ' % ( ValueSize )
PcdFiledValue = Pcd . PcdFiledValueFromDscComponent . get ( ModuleGuid )
for index in PcdFiledValue :
FieldList = PcdFiledValue [ index ]
if not FieldList :
continue
for FieldName in FieldList :
IsArray = _IsFieldValueAnArray ( FieldList [ FieldName ][ 0 ])
if IsArray :
try :
FieldList [ FieldName ][ 0 ] = ValueExpressionEx ( FieldList [ FieldName ][ 0 ], TAB_VOID , self . _GuidDict )( True )
except BadExpression :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " %
( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName )), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ]))
except :
print ( "error" )
try :
Value , ValueSize = ParseFieldValue ( FieldList [ FieldName ][ 0 ])
except Exception :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " % ( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName )), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ]))
if isinstance ( Value , str ):
CApp = CApp + ' Pcd-> %s = %s ; // From %s Line %d Value %s \n ' % ( FieldName , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
elif IsArray :
#
# Use memcpy() to copy value into field
#
CApp = CApp + ' FieldSize = __FIELD_SIZE( %s , %s ); \n ' % ( Pcd . BaseDatumType , FieldName )
CApp = CApp + ' Value = %s ; // From %s Line %d Value %s \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
CApp = CApp + ' __STATIC_ASSERT((__FIELD_SIZE( %s , %s ) >= %d ) || (__FIELD_SIZE( %s , %s ) == 0), "Input buffer exceeds the buffer array"); // From %s Line %d Value %s \n ' % ( Pcd . BaseDatumType , FieldName , ValueSize , Pcd . BaseDatumType , FieldName , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
CApp = CApp + ' memcpy (&Pcd-> %s , Value, (FieldSize > 0 && FieldSize < %d ) ? FieldSize : %d ); \n ' % ( FieldName , ValueSize , ValueSize )
else :
if '[' in FieldName and ']' in FieldName :
Index = int ( FieldName . split ( '[' )[ 1 ] . split ( ']' )[ 0 ])
CApp = CApp + ' __STATIC_ASSERT(( %d < __ARRAY_SIZE(Pcd-> %s )) || (__ARRAY_SIZE(Pcd-> %s ) == 0), "array index exceeds the array number"); // From %s Line %d Index of %s \n ' % ( Index , FieldName . split ( '[' )[ 0 ], FieldName . split ( '[' )[ 0 ], FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldName )
if ValueSize > 4 :
CApp = CApp + ' Pcd-> %s = %d ULL; // From %s Line %d Value %s \n ' % ( FieldName , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
else :
CApp = CApp + ' Pcd-> %s = %d ; // From %s Line %d Value %s \n ' % ( FieldName , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
CApp = CApp + "} \n "
return CApp
2018-04-14 04:51:29 +08:00
@staticmethod
def GenerateCommandLineValueStatement ( Pcd ):
2018-03-02 18:11:13 +08:00
CApp = ' Assign_ %s _ %s _CommandLine_Value(Pcd); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
return CApp
2018-06-22 17:14:13 +08:00
def GenerateFdfValue ( self , Pcd ):
CApp = "// Value in Fdf \n "
2018-11-07 17:18:34 +08:00
CApp = CApp + "void Assign_ %s _ %s _Fdf_Value( %s *Pcd){ \n " % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . BaseDatumType )
2018-06-22 17:14:13 +08:00
CApp = CApp + ' UINT32 FieldSize; \n '
CApp = CApp + ' CHAR8 *Value; \n '
pcddefaultvalue = Pcd . PcdValueFromFdf
for FieldList in [ pcddefaultvalue , Pcd . PcdFieldValueFromFdf ]:
if not FieldList :
continue
if pcddefaultvalue and FieldList == pcddefaultvalue :
2019-01-11 02:39:47 +08:00
IsArray = _IsFieldValueAnArray ( FieldList )
2018-06-22 17:14:13 +08:00
if IsArray :
try :
FieldList = ValueExpressionEx ( FieldList , TAB_VOID )( True )
except BadExpression :
EdkLogger . error ( "Build" , FORMAT_INVALID , "Invalid value format for %s . %s , from Fdf: %s " %
( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldList ))
Value , ValueSize = ParseFieldValue ( FieldList )
if isinstance ( Value , str ):
CApp = CApp + ' Pcd = %s ; // From Fdf \n ' % ( Value )
elif IsArray :
#
# Use memcpy() to copy value into field
#
CApp = CApp + ' Value = %s ; // From Fdf . \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ))
CApp = CApp + ' memcpy (Pcd, Value, %d ); \n ' % ( ValueSize )
continue
for FieldName in FieldList :
2019-01-11 02:39:47 +08:00
IsArray = _IsFieldValueAnArray ( FieldList [ FieldName ][ 0 ])
2018-06-22 17:14:13 +08:00
if IsArray :
try :
FieldList [ FieldName ][ 0 ] = ValueExpressionEx ( FieldList [ FieldName ][ 0 ], TAB_VOID , self . _GuidDict )( True )
except BadExpression :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " %
( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName )), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ]))
except :
print ( "error" )
try :
Value , ValueSize = ParseFieldValue ( FieldList [ FieldName ][ 0 ])
except Exception :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid value format for %s . From %s Line %d " % ( "." . join (( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , FieldName )), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ]))
if isinstance ( Value , str ):
CApp = CApp + ' Pcd-> %s = %s ; // From %s Line %d Value %s \n ' % ( FieldName , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
elif IsArray :
#
# Use memcpy() to copy value into field
#
2018-11-07 17:18:34 +08:00
CApp = CApp + ' FieldSize = __FIELD_SIZE( %s , %s ); \n ' % ( Pcd . BaseDatumType , FieldName )
2018-06-22 17:14:13 +08:00
CApp = CApp + ' Value = %s ; // From %s Line %d Value %s \n ' % ( DscBuildData . IntToCString ( Value , ValueSize ), FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2019-02-14 16:48:03 +08:00
CApp = CApp + ' __STATIC_ASSERT((__FIELD_SIZE( %s , %s ) >= %d ) || (__FIELD_SIZE( %s , %s ) == 0), "Input buffer exceeds the buffer array"); // From %s Line %d Value %s \n ' % ( Pcd . BaseDatumType , FieldName , ValueSize , Pcd . BaseDatumType , FieldName , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
2018-06-22 17:14:13 +08:00
CApp = CApp + ' memcpy (&Pcd-> %s , Value, (FieldSize > 0 && FieldSize < %d ) ? FieldSize : %d ); \n ' % ( FieldName , ValueSize , ValueSize )
else :
2018-10-22 16:23:18 +08:00
if '[' in FieldName and ']' in FieldName :
Index = int ( FieldName . split ( '[' )[ 1 ] . split ( ']' )[ 0 ])
CApp = CApp + ' __STATIC_ASSERT(( %d < __ARRAY_SIZE(Pcd-> %s )) || (__ARRAY_SIZE(Pcd-> %s ) == 0), "array index exceeds the array number"); // From %s Line %d Index of %s \n ' % ( Index , FieldName . split ( '[' )[ 0 ], FieldName . split ( '[' )[ 0 ], FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldName )
2018-06-22 17:14:13 +08:00
if ValueSize > 4 :
CApp = CApp + ' Pcd-> %s = %d ULL; // From %s Line %d Value %s \n ' % ( FieldName , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
else :
CApp = CApp + ' Pcd-> %s = %d ; // From %s Line %s Value %s \n ' % ( FieldName , Value , FieldList [ FieldName ][ 1 ], FieldList [ FieldName ][ 2 ], FieldList [ FieldName ][ 0 ])
CApp = CApp + "} \n "
return CApp
@staticmethod
def GenerateFdfValueStatement ( Pcd ):
CApp = ' Assign_ %s _ %s _Fdf_Value(Pcd); \n ' % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
return CApp
2018-04-14 04:51:29 +08:00
2020-11-04 11:01:39 +08:00
@staticmethod
def GenerateModuleValueStatement ( module_guid , Pcd ):
CApp = " Assign_ %s _ %s _ %s _Value(Pcd); \n " % ( Pcd . TokenSpaceGuidCName , Pcd . TokenCName , module_guid )
return CApp
def GenerateModuleScopeInitializeFunc ( self , SkuName , Pcd , InitByteValue , CApp ):
for module_guid in Pcd . PcdFiledValueFromDscComponent :
CApp = CApp + 'void \n '
CApp = CApp + 'Initialize_ %s _ %s _ %s _ %s ( \n ' % ( module_guid , TAB_DEFAULT_STORES_DEFAULT , Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
CApp = CApp + ' void \n '
CApp = CApp + ' ) \n '
CApp = CApp + '{ \n '
CApp = CApp + ' UINT32 Size; \n '
CApp = CApp + ' UINT32 FieldSize; \n '
CApp = CApp + ' CHAR8 *Value; \n '
CApp = CApp + ' UINT32 OriginalSize; \n '
CApp = CApp + ' VOID *OriginalPcd; \n '
CApp = CApp + ' %s *Pcd; // From %s Line %d \n ' % ( Pcd . BaseDatumType , Pcd . PkgPath , Pcd . PcdDefineLineNo )
CApp = CApp + ' \n '
PcdDefaultValue = StringToArray ( Pcd . DefaultValueFromDec . strip ())
InitByteValue += ' %s . %s . %s . %s | %s | %s \n ' % ( module_guid , TAB_DEFAULT_STORES_DEFAULT , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . DatumType , PcdDefaultValue )
#
# Get current PCD value and size
#
CApp = CApp + ' OriginalPcd = PcdGetPtr ( %s , %s , %s , %s , &OriginalSize); \n ' % ( module_guid , TAB_DEFAULT_STORES_DEFAULT , Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
#
# Determine the size of the PCD. For simple structures, sizeof(TYPE) provides
# the correct value. For structures with a flexible array member, the flexible
# array member is detected, and the size is based on the highest index used with
# the flexible array member. The flexible array member must be the last field
# in a structure. The size formula for this case is:
# OFFSET_OF(FlexbleArrayField) + sizeof(FlexibleArray[0]) * (HighestIndex + 1)
#
CApp = CApp + DscBuildData . GenerateSizeStatments ( Pcd , SkuName , TAB_DEFAULT_STORES_DEFAULT )
if Pcd . IsArray () and Pcd . Capacity [ - 1 ] != "-1" :
CApp = CApp + ' OriginalSize = OriginalSize < sizeof( %s ) * %d ? OriginalSize:sizeof( %s ) * %d ; \n ' % ( Pcd . BaseDatumType , Pcd . PcdArraySize (), Pcd . BaseDatumType , Pcd . PcdArraySize ())
CApp = CApp + ' Size = sizeof( %s ) * %d ; \n ' % ( Pcd . BaseDatumType , Pcd . PcdArraySize ())
#
# Allocate and zero buffer for the PCD
# Must handle cases where current value is smaller, larger, or same size
# Always keep that larger one as the current size
#
CApp = CApp + ' Size = (OriginalSize > Size ? OriginalSize : Size); \n '
CApp = CApp + ' Pcd = ( %s *)malloc (Size); \n ' % ( Pcd . BaseDatumType ,)
CApp = CApp + ' memset (Pcd, 0, Size); \n '
#
# Copy current PCD value into allocated buffer.
#
CApp = CApp + ' memcpy (Pcd, OriginalPcd, OriginalSize); \n '
#
# Assign field values in PCD
#
CApp = CApp + DscBuildData . GenerateDefaultValueAssignStatement ( Pcd )
CApp = CApp + "// SkuName: %s , DefaultStoreName: STANDARD \n " % self . SkuIdMgr . SystemSkuId
CApp = CApp + DscBuildData . GenerateInitValueStatement ( Pcd , self . SkuIdMgr . SystemSkuId , TAB_DEFAULT_STORES_DEFAULT )
CApp = CApp + DscBuildData . GenerateModuleValueStatement ( module_guid , Pcd )
CApp = CApp + DscBuildData . GenerateFdfValueStatement ( Pcd )
CApp = CApp + DscBuildData . GenerateCommandLineValueStatement ( Pcd )
#
# Set new PCD value and size
#
CApp = CApp + ' PcdSetPtr ( %s , %s , %s , %s , Size, (void *)Pcd); \n ' % ( module_guid , TAB_DEFAULT_STORES_DEFAULT , Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
#
# Free PCD
#
CApp = CApp + ' free (Pcd); \n '
CApp = CApp + '} \n '
CApp = CApp + ' \n '
return InitByteValue , CApp
2018-02-28 13:59:21 +08:00
def GenerateInitializeFunc ( self , SkuName , DefaultStore , Pcd , InitByteValue , CApp ):
2018-11-07 17:18:34 +08:00
OverrideValues = { DefaultStore :{}}
2017-11-24 14:30:11 +08:00
if Pcd . SkuOverrideValues :
OverrideValues = Pcd . SkuOverrideValues [ SkuName ]
2018-09-04 14:13:18 +08:00
if not OverrideValues :
OverrideValues = { TAB_DEFAULT_STORES_DEFAULT : Pcd . DefaultValues }
2018-04-10 22:20:06 +08:00
for DefaultStoreName in OverrideValues :
2017-12-22 20:46:15 +08:00
CApp = CApp + 'void \n '
CApp = CApp + 'Initialize_ %s _ %s _ %s _ %s ( \n ' % ( SkuName , DefaultStoreName , Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
CApp = CApp + ' void \n '
CApp = CApp + ' ) \n '
CApp = CApp + '{ \n '
CApp = CApp + ' UINT32 Size; \n '
CApp = CApp + ' UINT32 FieldSize; \n '
2017-12-15 12:12:58 +08:00
CApp = CApp + ' CHAR8 *Value; \n '
2017-12-22 20:46:15 +08:00
CApp = CApp + ' UINT32 OriginalSize; \n '
CApp = CApp + ' VOID *OriginalPcd; \n '
2018-11-07 17:18:34 +08:00
CApp = CApp + ' %s *Pcd; // From %s Line %d \n ' % ( Pcd . BaseDatumType , Pcd . PkgPath , Pcd . PcdDefineLineNo )
2017-12-22 20:46:15 +08:00
CApp = CApp + ' \n '
2017-12-22 20:14:29 +08:00
2018-11-07 17:18:34 +08:00
PcdDefaultValue = StringToArray ( Pcd . DefaultValueFromDec . strip ())
2017-12-22 20:14:29 +08:00
2018-12-15 00:15:21 +08:00
InitByteValue += ' %s . %s . %s . %s | %s | %s \n ' % ( SkuName , DefaultStoreName , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Pcd . DatumType , PcdDefaultValue )
2017-11-24 14:30:11 +08:00
2017-12-22 20:46:15 +08:00
#
# Get current PCD value and size
#
CApp = CApp + ' OriginalPcd = PcdGetPtr ( %s , %s , %s , %s , &OriginalSize); \n ' % ( SkuName , DefaultStoreName , Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
2017-11-24 14:30:11 +08:00
2017-12-22 20:46:15 +08:00
#
# Determine the size of the PCD. For simple structures, sizeof(TYPE) provides
# the correct value. For structures with a flexible array member, the flexible
# array member is detected, and the size is based on the highest index used with
# the flexible array member. The flexible array member must be the last field
# in a structure. The size formula for this case is:
# OFFSET_OF(FlexbleArrayField) + sizeof(FlexibleArray[0]) * (HighestIndex + 1)
#
2018-12-24 18:24:46 +08:00
CApp = CApp + DscBuildData . GenerateSizeStatments ( Pcd , SkuName , DefaultStoreName )
2019-05-09 17:19:56 +08:00
if Pcd . IsArray () and Pcd . Capacity [ - 1 ] != "-1" :
CApp = CApp + ' OriginalSize = OriginalSize < sizeof( %s ) * %d ? OriginalSize:sizeof( %s ) * %d ; \n ' % ( Pcd . BaseDatumType , Pcd . PcdArraySize (), Pcd . BaseDatumType , Pcd . PcdArraySize ())
CApp = CApp + ' Size = sizeof( %s ) * %d ; \n ' % ( Pcd . BaseDatumType , Pcd . PcdArraySize ())
2017-11-24 14:30:11 +08:00
2017-12-22 20:46:15 +08:00
#
# Allocate and zero buffer for the PCD
# Must handle cases where current value is smaller, larger, or same size
# Always keep that larger one as the current size
#
CApp = CApp + ' Size = (OriginalSize > Size ? OriginalSize : Size); \n '
2018-11-07 17:18:34 +08:00
CApp = CApp + ' Pcd = ( %s *)malloc (Size); \n ' % ( Pcd . BaseDatumType ,)
2017-12-22 20:46:15 +08:00
CApp = CApp + ' memset (Pcd, 0, Size); \n '
2017-11-24 14:30:11 +08:00
2017-12-22 20:46:15 +08:00
#
# Copy current PCD value into allocated buffer.
#
CApp = CApp + ' memcpy (Pcd, OriginalPcd, OriginalSize); \n '
#
# Assign field values in PCD
#
2018-04-14 04:51:29 +08:00
CApp = CApp + DscBuildData . GenerateDefaultValueAssignStatement ( Pcd )
2018-02-28 13:59:21 +08:00
if Pcd . Type not in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_FIXED_AT_BUILD ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_PATCHABLE_IN_MODULE ]]:
for skuname in self . SkuIdMgr . GetSkuChain ( SkuName ):
2018-04-11 07:17:20 +08:00
storeset = [ DefaultStoreName ] if DefaultStoreName == TAB_DEFAULT_STORES_DEFAULT else [ TAB_DEFAULT_STORES_DEFAULT , DefaultStoreName ]
2018-02-28 13:59:21 +08:00
for defaultstorenameitem in storeset :
CApp = CApp + "// SkuName: %s , DefaultStoreName: %s \n " % ( skuname , defaultstorenameitem )
2018-06-25 18:31:33 +08:00
CApp = CApp + DscBuildData . GenerateInitValueStatement ( Pcd , skuname , defaultstorenameitem )
2018-02-28 13:59:21 +08:00
if skuname == SkuName :
break
else :
2018-03-02 18:11:14 +08:00
CApp = CApp + "// SkuName: %s , DefaultStoreName: STANDARD \n " % self . SkuIdMgr . SystemSkuId
2018-06-25 18:31:33 +08:00
CApp = CApp + DscBuildData . GenerateInitValueStatement ( Pcd , self . SkuIdMgr . SystemSkuId , TAB_DEFAULT_STORES_DEFAULT )
2018-06-22 17:14:13 +08:00
CApp = CApp + DscBuildData . GenerateFdfValueStatement ( Pcd )
2018-04-14 04:51:29 +08:00
CApp = CApp + DscBuildData . GenerateCommandLineValueStatement ( Pcd )
2017-12-22 20:46:15 +08:00
#
# Set new PCD value and size
#
2018-11-07 17:18:34 +08:00
CApp = CApp + ' PcdSetPtr ( %s , %s , %s , %s , Size, (void *)Pcd); \n ' % ( SkuName , DefaultStoreName , Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
2017-12-22 20:46:15 +08:00
#
# Free PCD
#
CApp = CApp + ' free (Pcd); \n '
CApp = CApp + '} \n '
CApp = CApp + ' \n '
2017-11-24 14:30:11 +08:00
return InitByteValue , CApp
2018-11-07 17:18:34 +08:00
def GenerateArrayAssignment ( self , Pcd ):
CApp = ""
if not Pcd :
return CApp
Demesion = ""
for d in Pcd . Capacity :
2018-12-15 00:15:21 +08:00
Demesion += "[]"
2018-11-07 17:18:34 +08:00
Value = Pcd . DefaultValueFromDec
if "{CODE(" in Pcd . DefaultValueFromDec :
realvalue = Pcd . DefaultValueFromDec . strip ()[ 6 : - 2 ] # "{CODE(").rstrip(")}"
2018-12-24 18:24:46 +08:00
CApp += "static %s %s _ %s _INIT_Value %s = %s ; \n " % ( Pcd . BaseDatumType , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Demesion , realvalue )
2018-11-07 17:18:34 +08:00
2018-12-15 00:15:21 +08:00
if Pcd . Type in PCD_DYNAMIC_TYPE_SET | PCD_DYNAMIC_EX_TYPE_SET :
for skuname in Pcd . SkuInfoList :
skuinfo = Pcd . SkuInfoList [ skuname ]
if skuinfo . VariableName :
for defaultstore in skuinfo . DefaultStoreDict :
2018-12-24 18:24:46 +08:00
pcddscrawdefaultvalue = self . GetPcdDscRawDefaultValue ( Pcd , skuname , defaultstore )
if pcddscrawdefaultvalue :
2019-02-19 21:29:49 +08:00
Value = skuinfo . DefaultStoreDict [ defaultstore ]
2018-12-24 18:24:46 +08:00
if "{CODE(" in Value :
realvalue = Value . strip ()[ 6 : - 2 ] # "{CODE(").rstrip(")}"
CApp += "static %s %s _ %s _ %s _ %s _Value %s = %s ; \n " % ( Pcd . BaseDatumType , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , skuname , defaultstore , Demesion , realvalue )
else :
pcddscrawdefaultvalue = self . GetPcdDscRawDefaultValue ( Pcd , skuname , TAB_DEFAULT_STORES_DEFAULT )
if pcddscrawdefaultvalue :
Value = skuinfo . DefaultValue
2018-12-15 00:15:21 +08:00
if "{CODE(" in Value :
realvalue = Value . strip ()[ 6 : - 2 ] # "{CODE(").rstrip(")}"
2018-12-24 18:24:46 +08:00
CApp += "static %s %s _ %s _ %s _ %s _Value %s = %s ; \n " % ( Pcd . BaseDatumType , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , skuname , TAB_DEFAULT_STORES_DEFAULT , Demesion , realvalue )
2018-12-15 00:15:21 +08:00
else :
2018-12-24 18:24:46 +08:00
pcddscrawdefaultvalue = self . GetPcdDscRawDefaultValue ( Pcd , TAB_DEFAULT , TAB_DEFAULT_STORES_DEFAULT )
if pcddscrawdefaultvalue :
if "{CODE(" in Pcd . DefaultValue :
realvalue = Pcd . DefaultValue . strip ()[ 6 : - 2 ] # "{CODE(").rstrip(")}"
CApp += "static %s %s _ %s _DEFAULT_STANDARD_Value %s = %s ; \n " % ( Pcd . BaseDatumType , Pcd . TokenSpaceGuidCName , Pcd . TokenCName , Demesion , realvalue )
2018-11-07 17:18:34 +08:00
return CApp
2018-12-24 18:24:46 +08:00
2018-09-04 14:13:18 +08:00
def SkuOverrideValuesEmpty ( self , OverrideValues ):
if not OverrideValues :
return True
for key in OverrideValues :
if OverrideValues [ key ]:
return False
return True
2017-11-24 14:30:11 +08:00
2018-11-02 13:56:38 +08:00
def ParseCCFlags ( self , ccflag ):
ccflags = set ()
2018-12-07 10:39:52 +08:00
ccflaglist = ccflag . split ( " " )
i = 0
while i < len ( ccflaglist ):
item = ccflaglist [ i ] . strip ()
if item in ( r "/D" , r "/U" , "-D" , "-U" ):
ccflags . add ( " " . join (( ccflaglist [ i ], ccflaglist [ i + 1 ])))
i = i + 1
elif item . startswith (( r "/D" , r "/U" , "-D" , "-U" )):
ccflags . add ( item )
i += 1
2018-11-02 13:56:38 +08:00
return ccflags
2024-02-07 09:20:35 -08:00
def GetStructurePcdSet ( self , OutputValueFile ):
if not os . path . isfile ( OutputValueFile ):
EdkLogger . error ( "GetStructurePcdSet" , FILE_NOT_FOUND , "Output.txt doesn't exist" , ExtraData = OutputValueFile )
return []
File = open ( OutputValueFile , 'r' )
FileBuffer = File . readlines ()
File . close ()
#start update structure pcd final value
StructurePcdSet = []
for Pcd in FileBuffer :
PcdValue = Pcd . split ( '|' )
PcdInfo = PcdValue [ 0 ] . split ( '.' )
StructurePcdSet . append (( PcdInfo [ 0 ], PcdInfo [ 1 ], PcdInfo [ 2 ], PcdInfo [ 3 ], PcdValue [ 2 ] . strip ()))
return StructurePcdSet
def GetBuildOptionsValueList ( self ):
CC_FLAGS = LinuxCFLAGS
2025-06-06 16:04:29 -07:00
if sys . platform == "win32" and not self . _MingwBaseToolsBuild :
2024-02-07 09:20:35 -08:00
CC_FLAGS = WindowsCFLAGS
BuildOptions = OrderedDict ()
for Options in self . BuildOptions :
if Options [ 2 ] != EDKII_NAME :
continue
Family = Options [ 0 ]
if Family and Family != self . ToolChainFamily :
continue
Target , Tag , Arch , Tool , Attr = Options [ 1 ] . split ( "_" )
if Tool != 'CC' :
continue
if Attr != "FLAGS" :
continue
if Target == TAB_STAR or Target == self . _Target :
if Tag == TAB_STAR or Tag == self . _Toolchain :
if 'COMMON' not in BuildOptions :
BuildOptions [ 'COMMON' ] = set ()
if Arch == TAB_STAR :
BuildOptions [ 'COMMON' ] |= self . ParseCCFlags ( self . BuildOptions [ Options ])
if Arch in self . SupArchList :
if Arch not in BuildOptions :
BuildOptions [ Arch ] = set ()
BuildOptions [ Arch ] |= self . ParseCCFlags ( self . BuildOptions [ Options ])
if BuildOptions :
ArchBuildOptions = { arch : flags for arch , flags in BuildOptions . items () if arch != 'COMMON' }
if len ( ArchBuildOptions . keys ()) == 1 :
BuildOptions [ 'COMMON' ] |= ( list ( ArchBuildOptions . values ())[ 0 ])
elif len ( ArchBuildOptions . keys ()) > 1 :
CommonBuildOptions = reduce ( lambda x , y : x & y , ArchBuildOptions . values ())
BuildOptions [ 'COMMON' ] |= CommonBuildOptions
ValueList = [ item for item in BuildOptions [ 'COMMON' ] if item . startswith (( r "/U" , "-U" ))]
ValueList . extend ([ item for item in BuildOptions [ 'COMMON' ] if item . startswith (( r "/D" , "-D" ))])
CC_FLAGS += " " . join ( ValueList )
return CC_FLAGS
2017-11-24 14:30:11 +08:00
def GenerateByteArrayValue ( self , StructuredPcds ):
#
# Generate/Compile/Run C application to determine if there are any flexible array members
#
if not StructuredPcds :
return
2024-02-07 09:20:35 -08:00
StructuredPcdsData = {}
StoredStructuredPcdObjectPaths = {}
SkipPcdValueInit = False
CC_FLAGS = self . GetBuildOptionsValueList ()
for PcdName in StructuredPcds :
Pcd = StructuredPcds [ PcdName ]
TokenSpaceGuidCName = Pcd . TokenSpaceGuidCName
TokenCName = Pcd . TokenCName
# Create a key using TokenSpaceGuidCName and TokenCName
StructuredPcdsData [ f " { TokenSpaceGuidCName } _ { TokenCName } " ] = {
"DefaultValueFromDec" : Pcd . DefaultValueFromDec ,
"DefaultValues" : Pcd . DefaultValues ,
"PcdFieldValueFromComm" : Pcd . PcdFieldValueFromComm ,
"PcdFieldValueFromFdf" : Pcd . PcdFieldValueFromFdf ,
"DefaultFromDSC" : Pcd . DefaultFromDSC ,
"PcdFiledValueFromDscComponent" : Pcd . PcdFiledValueFromDscComponent
}
# Store the CC Flags
StructuredPcdsData [ "CC_FLAGS" ] = CC_FLAGS
#
# If the output path doesn't exists then create it
#
if not os . path . exists ( self . OutputPath ):
os . makedirs ( self . OutputPath )
StructuredPcdsDataPath = os . path . join ( self . OutputPath , self . _Arch , StructuredPcdsDataName )
PcdRecordOutputValueFile = os . path . join ( self . OutputPath , self . _Arch , 'Output.txt' )
if not os . path . exists ( os . path . dirname ( StructuredPcdsDataPath )):
os . makedirs ( os . path . dirname ( StructuredPcdsDataPath ))
#
# Check if the StructuredPcdsData.json exists or not
# if exits then it might be a incremental build then check if the StructuredPcdsData has been changed or not.
# if changed then proceed further, if not changed then return the stored data from earlier build
#
if os . path . isfile ( StructuredPcdsDataPath ):
with open ( StructuredPcdsDataPath , 'r' ) as file :
StoredStructuredPcdsData = json . load ( file )
# OBJECTS will have the modified time, which needs to be checked later
StoredStructuredPcdObjectPaths = StoredStructuredPcdsData . pop ( "OBJECTS" , {})
if StructuredPcdsData == StoredStructuredPcdsData :
SkipPcdValueInit = True
for filename , file_mtime in StoredStructuredPcdObjectPaths . items ():
f_mtime = os . path . getmtime ( filename )
#
# check if the include_file are modified or not,
# if modified then generate the PcdValueInit
#
if f_mtime != file_mtime :
SkipPcdValueInit = False
break
if SkipPcdValueInit :
return self . GetStructurePcdSet ( PcdRecordOutputValueFile )
2017-11-24 14:30:11 +08:00
InitByteValue = ""
CApp = PcdMainCHeader
2018-03-16 17:40:00 +08:00
IncludeFiles = set ()
2017-11-24 14:30:11 +08:00
for PcdName in StructuredPcds :
Pcd = StructuredPcds [ PcdName ]
2018-01-29 14:09:36 +08:00
for IncludeFile in Pcd . StructuredPcdIncludeFile :
2018-04-20 23:51:32 +08:00
if IncludeFile not in IncludeFiles :
2018-03-16 17:40:00 +08:00
IncludeFiles . add ( IncludeFile )
2018-01-29 14:09:36 +08:00
CApp = CApp + '#include < %s > \n ' % ( IncludeFile )
2017-11-24 14:30:11 +08:00
CApp = CApp + ' \n '
2018-11-07 17:18:34 +08:00
for Pcd in StructuredPcds . values ():
CApp = CApp + self . GenerateArrayAssignment ( Pcd )
2020-09-04 22:30:28 +08:00
for PcdName in sorted ( StructuredPcds . keys ()):
2017-11-24 14:30:11 +08:00
Pcd = StructuredPcds [ PcdName ]
2020-11-04 11:01:39 +08:00
#create void void Cal_tocken_cname_Size functions
2018-02-28 13:59:20 +08:00
CApp = CApp + self . GenerateSizeFunction ( Pcd )
2020-11-04 11:01:39 +08:00
#create void Assign_ functions
# From DEC
2018-02-28 13:59:20 +08:00
CApp = CApp + self . GenerateDefaultValueAssignFunction ( Pcd )
2020-11-04 11:01:39 +08:00
# From Fdf
2018-06-22 17:14:13 +08:00
CApp = CApp + self . GenerateFdfValue ( Pcd )
2020-11-04 11:01:39 +08:00
# From CommandLine
2018-03-02 18:11:13 +08:00
CApp = CApp + self . GenerateCommandLineValue ( Pcd )
2020-11-04 11:01:39 +08:00
# From Dsc Global setting
2018-09-04 14:13:18 +08:00
if self . SkuOverrideValuesEmpty ( Pcd . SkuOverrideValues ) or Pcd . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_FIXED_AT_BUILD ],
2018-02-28 13:59:21 +08:00
self . _PCD_TYPE_STRING_ [ MODEL_PCD_PATCHABLE_IN_MODULE ]]:
2018-06-25 18:31:33 +08:00
CApp = CApp + self . GenerateInitValueFunction ( Pcd , self . SkuIdMgr . SystemSkuId , TAB_DEFAULT_STORES_DEFAULT )
2018-02-28 13:59:21 +08:00
else :
for SkuName in self . SkuIdMgr . SkuOverrideOrder ():
if SkuName not in Pcd . SkuOverrideValues :
continue
for DefaultStoreName in Pcd . SkuOverrideValues [ SkuName ]:
2018-06-25 18:31:33 +08:00
CApp = CApp + self . GenerateInitValueFunction ( Pcd , SkuName , DefaultStoreName )
2020-11-04 11:01:39 +08:00
# From Dsc module scope setting
CApp = CApp + self . GenerateModuleScopeValue ( Pcd )
#create Initialize_ functions
2018-09-04 14:13:18 +08:00
if self . SkuOverrideValuesEmpty ( Pcd . SkuOverrideValues ) or Pcd . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_FIXED_AT_BUILD ],
2018-02-28 13:59:19 +08:00
self . _PCD_TYPE_STRING_ [ MODEL_PCD_PATCHABLE_IN_MODULE ]]:
2018-04-11 07:17:20 +08:00
InitByteValue , CApp = self . GenerateInitializeFunc ( self . SkuIdMgr . SystemSkuId , TAB_DEFAULT_STORES_DEFAULT , Pcd , InitByteValue , CApp )
2020-11-04 11:01:39 +08:00
InitByteValue , CApp = self . GenerateModuleScopeInitializeFunc ( self . SkuIdMgr . SystemSkuId , Pcd , InitByteValue , CApp )
2017-11-24 14:30:11 +08:00
else :
2017-12-22 20:53:01 +08:00
for SkuName in self . SkuIdMgr . SkuOverrideOrder ():
if SkuName not in Pcd . SkuOverrideValues :
continue
2017-11-24 14:30:11 +08:00
for DefaultStoreName in Pcd . DefaultStoreName :
Pcd = StructuredPcds [ PcdName ]
InitByteValue , CApp = self . GenerateInitializeFunc ( SkuName , DefaultStoreName , Pcd , InitByteValue , CApp )
CApp = CApp + 'VOID \n '
CApp = CApp + 'PcdEntryPoint( \n '
CApp = CApp + ' VOID \n '
CApp = CApp + ' ) \n '
CApp = CApp + '{ \n '
for Pcd in StructuredPcds . values ():
2018-09-04 14:13:18 +08:00
if self . SkuOverrideValuesEmpty ( Pcd . SkuOverrideValues ) or Pcd . Type in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_FIXED_AT_BUILD ], self . _PCD_TYPE_STRING_ [ MODEL_PCD_PATCHABLE_IN_MODULE ]]:
2018-04-11 07:17:20 +08:00
CApp = CApp + ' Initialize_ %s _ %s _ %s _ %s (); \n ' % ( self . SkuIdMgr . SystemSkuId , TAB_DEFAULT_STORES_DEFAULT , Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
2020-11-04 11:01:39 +08:00
for ModuleGuid in Pcd . PcdFiledValueFromDscComponent :
CApp += " Initialize_ %s _ %s _ %s _ %s (); \n " % ( ModuleGuid , TAB_DEFAULT_STORES_DEFAULT , Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
2017-11-24 14:30:11 +08:00
else :
2017-12-22 20:53:01 +08:00
for SkuName in self . SkuIdMgr . SkuOverrideOrder ():
2018-09-04 15:51:05 +08:00
if SkuName not in self . SkuIdMgr . AvailableSkuIdSet :
2017-12-22 20:53:01 +08:00
continue
2017-12-22 20:46:15 +08:00
for DefaultStoreName in Pcd . SkuOverrideValues [ SkuName ]:
2017-11-24 14:30:11 +08:00
CApp = CApp + ' Initialize_ %s _ %s _ %s _ %s (); \n ' % ( SkuName , DefaultStoreName , Pcd . TokenSpaceGuidCName , Pcd . TokenCName )
CApp = CApp + '} \n '
CApp = CApp + PcdMainCEntry + ' \n '
CAppBaseFileName = os . path . join ( self . OutputPath , PcdValueInitName )
2018-02-28 13:59:19 +08:00
SaveFileOnChange ( CAppBaseFileName + '.c' , CApp , False )
2017-11-24 14:30:11 +08:00
2020-11-04 11:01:39 +08:00
# start generating makefile
2017-11-24 14:30:11 +08:00
MakeApp = PcdMakefileHeader
2025-06-06 16:04:29 -07:00
if sys . platform == "win32" and not self . _MingwBaseToolsBuild :
2023-12-29 00:47:39 +08:00
MakeApp = MakeApp + 'APPFILE = %s \\ %s .exe \n ' % ( self . OutputPath , PcdValueInitName ) + 'APPNAME = %s \n ' % ( PcdValueInitName ) + 'OBJECTS = %s \\ %s .obj %s .obj \n ' % ( self . OutputPath , PcdValueInitName , os . path . join ( self . OutputPath , PcdValueCommonName )) + 'INC = '
2017-11-24 14:30:11 +08:00
else :
2025-06-06 16:04:29 -07:00
AppSuffix = '.exe' if sys . platform == "win32" else ''
2017-11-24 14:30:11 +08:00
MakeApp = MakeApp + PcdGccMakefile
2026-02-11 10:00:05 -08:00
MakeApp = MakeApp + 'APPFILE = %s%s%s%s \n ' % ( self . OutputPath , os . sep , PcdValueInitName , AppSuffix ) + 'APPNAME = %s \n ' % ( PcdValueInitName ) + 'OBJECTS = %s / %s .o %s .o \n ' % ( self . OutputPath , PcdValueInitName , os . path . join ( self . OutputPath , PcdValueCommonName )) + \
2025-06-06 16:04:29 -07:00
'include $(MAKEROOT)/Makefiles/app.makefile \n ' + 'TOOL_INCLUDE +='
2017-11-24 14:30:11 +08:00
2018-03-16 17:40:00 +08:00
IncSearchList = []
2018-09-25 13:20:46 +08:00
PlatformInc = OrderedDict ()
2017-11-24 14:30:11 +08:00
for Cache in self . _Bdb . _CACHE_ . values ():
if Cache . MetaFile . Ext . lower () != '.dec' :
continue
if Cache . Includes :
if str ( Cache . MetaFile . Path ) not in PlatformInc :
2018-03-22 23:22:06 +08:00
PlatformInc [ str ( Cache . MetaFile . Path )] = []
PlatformInc [ str ( Cache . MetaFile . Path )] . append ( os . path . dirname ( Cache . MetaFile . Path ))
PlatformInc [ str ( Cache . MetaFile . Path )] . extend ( Cache . CommonIncludes )
2017-11-24 14:30:11 +08:00
PcdDependDEC = []
for Pcd in StructuredPcds . values ():
for PackageDec in Pcd . PackageDecs :
Package = os . path . normpath ( mws . join ( GlobalData . gWorkspace , PackageDec ))
if not os . path . exists ( Package ):
EdkLogger . error ( 'Build' , RESOURCE_NOT_AVAILABLE , "The dependent Package %s of PCD %s . %s is not exist." % ( PackageDec , Pcd . TokenSpaceGuidCName , Pcd . TokenCName ))
if Package not in PcdDependDEC :
PcdDependDEC . append ( Package )
if PlatformInc and PcdDependDEC :
for pkg in PcdDependDEC :
if pkg in PlatformInc :
for inc in PlatformInc [ pkg ]:
2019-11-20 17:12:51 -08:00
#
# Get list of files in potential -I include path
#
FileList = os . listdir ( str ( inc ))
#
# Skip -I include path if one of the include files required
# by PcdValueInit.c are present in the include paths from
# the DEC file. PcdValueInit.c must use the standard include
# files from the host compiler.
#
if 'stdio.h' in FileList :
continue
if 'stdlib.h' in FileList :
continue
if 'string.h' in FileList :
continue
2017-11-24 14:30:11 +08:00
MakeApp += '-I' + str ( inc ) + ' '
2018-03-16 17:40:00 +08:00
IncSearchList . append ( inc )
2017-11-24 14:30:11 +08:00
MakeApp = MakeApp + ' \n '
2017-12-26 13:16:17 +08:00
MakeApp += CC_FLAGS
2025-06-06 16:04:29 -07:00
if sys . platform == "win32" and not self . _MingwBaseToolsBuild :
2017-11-24 14:30:11 +08:00
MakeApp = MakeApp + PcdMakefileEnd
2018-10-22 11:24:13 +08:00
MakeApp = MakeApp + AppTarget % ( """ \t copy $(APPLICATION) $(APPFILE) /y """ )
else :
2025-06-06 16:04:29 -07:00
AppSuffix = '.exe' if sys . platform == "win32" else ''
MakeApp = MakeApp + AppTarget % ( """ \t $(CP) $(APPLICATION) %s $(APPFILE)""" % ( AppSuffix ))
2018-03-16 17:40:00 +08:00
MakeApp = MakeApp + ' \n '
IncludeFileFullPaths = []
for includefile in IncludeFiles :
for includepath in IncSearchList :
2018-06-25 18:31:33 +08:00
includefullpath = os . path . join ( str ( includepath ), includefile )
2018-03-16 17:40:00 +08:00
if os . path . exists ( includefullpath ):
IncludeFileFullPaths . append ( os . path . normpath ( includefullpath ))
break
SearchPathList = []
2020-02-07 07:07:12 +08:00
SearchPathList . append ( os . path . normpath ( mws . join ( GlobalData . gGlobalDefines [ "EDK_TOOLS_PATH" ], "BaseTools/Source/C/Include" )))
SearchPathList . append ( os . path . normpath ( mws . join ( GlobalData . gGlobalDefines [ "EDK_TOOLS_PATH" ], "BaseTools/Source/C/Common" )))
2018-04-28 06:32:54 +08:00
SearchPathList . extend ( str ( item ) for item in IncSearchList )
2018-06-25 18:31:33 +08:00
IncFileList = GetDependencyList ( IncludeFileFullPaths , SearchPathList )
2024-02-07 09:20:35 -08:00
StructuredPcdsData [ "OBJECTS" ] = {}
2018-03-16 17:40:00 +08:00
for include_file in IncFileList :
2024-02-07 09:20:35 -08:00
StructuredPcdsData [ "OBJECTS" ][ include_file ] = os . path . getmtime ( include_file )
2018-03-16 17:40:00 +08:00
MakeApp += "$(OBJECTS) : %s \n " % include_file
2020-03-11 17:51:21 +08:00
if sys . platform == "win32" :
2024-02-06 12:32:34 +05:30
PcdValueCommonPath = os . path . normpath ( mws . join ( GlobalData . gGlobalDefines [ "EDK_TOOLS_PATH" ], "Source \\ C \\ Common \\ PcdValueCommon.c" ))
2023-12-29 00:47:39 +08:00
MakeApp = MakeApp + ' %s \\ PcdValueCommon.c : %s \n ' % ( self . OutputPath , PcdValueCommonPath )
2020-03-11 17:51:21 +08:00
MakeApp = MakeApp + ' \t copy /y %s $@ \n ' % ( PcdValueCommonPath )
else :
PcdValueCommonPath = os . path . normpath ( mws . join ( GlobalData . gGlobalDefines [ "EDK_TOOLS_PATH" ], "Source/C/Common/PcdValueCommon.c" ))
MakeApp = MakeApp + ' %s /PcdValueCommon.c : %s \n ' % ( self . OutputPath , PcdValueCommonPath )
2022-07-08 21:10:00 +08:00
MakeApp = MakeApp + ' \t cp -p -f %s %s /PcdValueCommon.c \n ' % ( PcdValueCommonPath , self . OutputPath )
2017-11-24 14:30:11 +08:00
MakeFileName = os . path . join ( self . OutputPath , 'Makefile' )
2018-03-16 17:40:00 +08:00
MakeApp += "$(OBJECTS) : %s \n " % MakeFileName
2018-02-28 13:59:19 +08:00
SaveFileOnChange ( MakeFileName , MakeApp , False )
2017-11-24 14:30:11 +08:00
2020-11-04 11:01:39 +08:00
# start generating input file
2017-11-24 14:30:11 +08:00
InputValueFile = os . path . join ( self . OutputPath , 'Input.txt' )
OutputValueFile = os . path . join ( self . OutputPath , 'Output.txt' )
2018-02-28 13:59:19 +08:00
SaveFileOnChange ( InputValueFile , InitByteValue , False )
2017-11-24 14:30:11 +08:00
2018-10-22 11:24:13 +08:00
Dest_PcdValueInitExe = PcdValueInitName
2017-11-24 14:30:11 +08:00
if not sys . platform == "win32" :
2018-10-22 11:24:13 +08:00
Dest_PcdValueInitExe = os . path . join ( self . OutputPath , PcdValueInitName )
2018-01-31 17:32:01 +08:00
else :
2018-10-22 11:24:13 +08:00
Dest_PcdValueInitExe = os . path . join ( self . OutputPath , PcdValueInitName ) + ".exe"
2020-11-04 11:01:39 +08:00
#start building the structure pcd value tool
2018-03-16 17:40:00 +08:00
Messages = ''
2025-06-06 16:04:29 -07:00
if sys . platform == "win32" and not self . _MingwBaseToolsBuild :
2018-03-16 17:40:00 +08:00
MakeCommand = 'nmake -f %s ' % ( MakeFileName )
2018-04-14 04:51:29 +08:00
returncode , StdOut , StdErr = DscBuildData . ExecuteCommand ( MakeCommand )
2018-03-16 17:40:00 +08:00
Messages = StdOut
else :
2025-06-06 16:04:29 -07:00
if sys . platform == "win32" and self . _MingwBaseToolsBuild :
if shutil . which ( 'mingw32-make.exe' ) is not None :
MakeCommand = 'mingw32-make -f %s ' % ( MakeFileName )
else :
if self . _Toolchain in ( 'CLANGPDB' , 'CLANGDWARF' ) and 'CLANG_HOST_BIN' in os . environ :
MakeCommand = ' %s make -f %s ' % ( os . environ . get ( 'CLANG_HOST_BIN' ), MakeFileName )
else :
MakeCommand = 'make -f %s ' % ( MakeFileName )
else :
MakeCommand = 'make -f %s ' % ( MakeFileName )
2018-04-14 04:51:29 +08:00
returncode , StdOut , StdErr = DscBuildData . ExecuteCommand ( MakeCommand )
2018-03-16 17:40:00 +08:00
Messages = StdErr
2018-10-22 11:24:13 +08:00
2020-02-07 07:07:12 +08:00
EdkLogger . verbose ( ' %s \n %s \n %s ' % ( MakeCommand , StdOut , StdErr ))
2018-03-16 17:40:00 +08:00
Messages = Messages . split ( ' \n ' )
MessageGroup = []
2018-06-27 18:07:55 +08:00
if returncode != 0 :
2018-03-16 17:40:00 +08:00
CAppBaseFileName = os . path . join ( self . OutputPath , PcdValueInitName )
File = open ( CAppBaseFileName + '.c' , 'r' )
FileData = File . readlines ()
File . close ()
for Message in Messages :
if " error" in Message or "warning" in Message :
2020-02-07 07:07:12 +08:00
try :
FileInfo = Message . strip () . split ( '(' )
if len ( FileInfo ) > 1 :
FileName = FileInfo [ 0 ]
FileLine = FileInfo [ 1 ] . split ( ')' )[ 0 ]
else :
FileInfo = Message . strip () . split ( ':' )
if len ( FileInfo ) < 2 :
continue
FileName = FileInfo [ 0 ]
FileLine = FileInfo [ 1 ]
except :
continue
if "PcdValueInit.c" not in FileName :
continue
2018-03-16 17:40:00 +08:00
if FileLine . isdigit ():
error_line = FileData [ int ( FileLine ) - 1 ]
if r "//" in error_line :
2018-06-25 18:31:33 +08:00
c_line , dsc_line = error_line . split ( r "//" )
2018-03-16 17:40:00 +08:00
else :
dsc_line = error_line
message_itmes = Message . split ( ":" )
Index = 0
if "PcdValueInit.c" not in Message :
if not MessageGroup :
MessageGroup . append ( Message )
break
else :
for item in message_itmes :
if "PcdValueInit.c" in item :
Index = message_itmes . index ( item )
message_itmes [ Index ] = dsc_line . strip ()
break
MessageGroup . append ( ":" . join ( message_itmes [ Index :]) . strip ())
continue
else :
MessageGroup . append ( Message )
if MessageGroup :
EdkLogger . error ( "build" , PCD_STRUCTURE_PCD_ERROR , " \n " . join ( MessageGroup ) )
2018-02-28 13:59:19 +08:00
else :
2020-02-07 07:07:12 +08:00
EdkLogger . error ( 'Build' , COMMAND_FAILURE , 'Can not execute command: %s \n %s \n %s ' % ( MakeCommand , StdOut , StdErr ))
2018-03-16 17:40:00 +08:00
2020-11-04 11:01:39 +08:00
#start executing the structure pcd value tool
2018-10-22 11:24:13 +08:00
if DscBuildData . NeedUpdateOutput ( OutputValueFile , Dest_PcdValueInitExe , InputValueFile ):
Command = Dest_PcdValueInitExe + ' -i %s -o %s ' % ( InputValueFile , OutputValueFile )
2018-04-14 04:51:29 +08:00
returncode , StdOut , StdErr = DscBuildData . ExecuteCommand ( Command )
2020-02-07 07:07:12 +08:00
EdkLogger . verbose ( ' %s \n %s \n %s ' % ( Command , StdOut , StdErr ))
2018-06-25 18:31:27 +08:00
if returncode != 0 :
2022-01-21 07:58:24 +08:00
EdkLogger . warn ( 'Build' , COMMAND_FAILURE , 'Can not collect output from command: %s \n %s \n %s \n ' % ( Command , StdOut , StdErr ))
2018-02-28 13:59:19 +08:00
2024-02-07 09:20:35 -08:00
#
# In 1st build create the StructuredPcdsData.json
# update the record as PCD Input has been changed if its incremental build
#
with open ( StructuredPcdsDataPath , 'w' ) as file :
json . dump ( StructuredPcdsData , file , indent = 2 )
2017-11-24 14:30:11 +08:00
2024-02-07 09:20:35 -08:00
# Copy update output file for each Arch
shutil . copyfile ( OutputValueFile , PcdRecordOutputValueFile )
#start update structure pcd final value
return self . GetStructurePcdSet ( OutputValueFile )
2017-11-24 14:30:11 +08:00
2018-04-14 04:51:29 +08:00
@staticmethod
def NeedUpdateOutput ( OutputFile , ValueCFile , StructureInput ):
2018-02-28 13:59:19 +08:00
if not os . path . exists ( OutputFile ):
return True
if os . stat ( OutputFile ) . st_mtime <= os . stat ( ValueCFile ) . st_mtime :
return True
if os . stat ( OutputFile ) . st_mtime <= os . stat ( StructureInput ) . st_mtime :
return True
return False
2017-11-24 14:30:11 +08:00
## Retrieve dynamic PCD settings
#
# @param Type PCD type
#
# @retval a dict object contains settings of given PCD type
#
def _GetDynamicPcd ( self , Type ):
2018-04-04 05:03:09 +08:00
Pcds = OrderedDict ()
2017-11-24 14:30:11 +08:00
#
# tdict is a special dict kind of type, used for selecting correct
# PCD settings for certain ARCH and SKU
#
PcdDict = tdict ( True , 4 )
PcdList = []
# Find out all possible PCD candidates for self._Arch
RecordList = self . _RawData [ Type , self . _Arch ]
2017-12-22 20:46:15 +08:00
AvailableSkuIdSet = copy . copy ( self . SkuIds )
2017-11-24 14:30:11 +08:00
2018-06-25 18:31:33 +08:00
for TokenSpaceGuid , PcdCName , Setting , Arch , SkuName , Dummy3 , Dummy4 , Dummy5 in RecordList :
2017-12-22 20:04:04 +08:00
SkuName = SkuName . upper ()
2018-04-16 21:52:13 +08:00
SkuName = TAB_DEFAULT if SkuName == TAB_COMMON else SkuName
2017-11-24 14:30:11 +08:00
if SkuName not in AvailableSkuIdSet :
2017-12-22 20:04:04 +08:00
EdkLogger . error ( 'build' , PARAMETER_INVALID , 'Sku %s is not defined in [SkuIds] section' % SkuName ,
File = self . MetaFile , Line = Dummy5 )
2019-04-26 10:29:58 +08:00
if "." not in TokenSpaceGuid and "[" not in PcdCName and ( PcdCName , TokenSpaceGuid , SkuName , Dummy5 ) not in PcdList :
2018-01-31 17:32:01 +08:00
PcdList . append (( PcdCName , TokenSpaceGuid , SkuName , Dummy5 ))
2017-11-24 14:30:11 +08:00
PcdDict [ Arch , SkuName , PcdCName , TokenSpaceGuid ] = Setting
# Remove redundant PCD candidates, per the ARCH and SKU
for PcdCName , TokenSpaceGuid , SkuName , Dummy4 in PcdList :
Setting = PcdDict [ self . _Arch , SkuName , PcdCName , TokenSpaceGuid ]
2018-03-27 04:25:43 +08:00
if Setting is None :
2017-11-24 14:30:11 +08:00
continue
PcdValue , DatumType , MaxDatumSize = self . _ValidatePcd ( PcdCName , TokenSpaceGuid , Setting , Type , Dummy4 )
2018-08-03 15:46:20 +08:00
if MaxDatumSize :
if int ( MaxDatumSize , 0 ) > 0xFFFF :
EdkLogger . error ( 'build' , FORMAT_INVALID , "The size value must not exceed the maximum value of 0xFFFF (UINT16) for %s ." % "." . join (( TokenSpaceGuid , PcdCName )),
File = self . MetaFile , Line = Dummy4 )
if int ( MaxDatumSize , 0 ) < 0 :
EdkLogger . error ( 'build' , FORMAT_INVALID , "The size value can't be set to negative value for %s ." % "." . join (( TokenSpaceGuid , PcdCName )),
File = self . MetaFile , Line = Dummy4 )
2017-12-22 20:46:15 +08:00
SkuInfo = SkuInfoClass ( SkuName , self . SkuIds [ SkuName ][ 0 ], '' , '' , '' , '' , '' , PcdValue )
2018-04-10 22:20:06 +08:00
if ( PcdCName , TokenSpaceGuid ) in Pcds :
2017-11-24 14:30:11 +08:00
pcdObject = Pcds [ PcdCName , TokenSpaceGuid ]
pcdObject . SkuInfoList [ SkuName ] = SkuInfo
if MaxDatumSize . strip ():
CurrentMaxSize = int ( MaxDatumSize . strip (), 0 )
else :
CurrentMaxSize = 0
if pcdObject . MaxDatumSize :
PcdMaxSize = int ( pcdObject . MaxDatumSize , 0 )
else :
PcdMaxSize = 0
if CurrentMaxSize > PcdMaxSize :
pcdObject . MaxDatumSize = str ( CurrentMaxSize )
else :
Pcds [ PcdCName , TokenSpaceGuid ] = PcdClassObject (
PcdCName ,
TokenSpaceGuid ,
self . _PCD_TYPE_STRING_ [ Type ],
DatumType ,
PcdValue ,
'' ,
MaxDatumSize ,
2018-09-25 13:20:46 +08:00
OrderedDict ({ SkuName : SkuInfo }),
2017-11-24 14:30:11 +08:00
False ,
None ,
IsDsc = True )
2018-09-04 14:13:18 +08:00
if SkuName not in Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValue :
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValue [ SkuName ] = {}
2019-05-09 17:19:56 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValueInfo [ SkuName ] = {}
2018-09-04 14:13:18 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValue [ SkuName ][ TAB_DEFAULT_STORES_DEFAULT ] = PcdValue
2019-05-09 17:19:56 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValueInfo [ SkuName ][ TAB_DEFAULT_STORES_DEFAULT ] = ( self . MetaFile . File , Dummy4 )
2018-09-04 14:13:18 +08:00
2017-11-24 14:30:11 +08:00
for pcd in Pcds . values ():
pcdDecObject = self . _DecPcds [ pcd . TokenCName , pcd . TokenSpaceGuidCName ]
2017-12-22 20:07:54 +08:00
# Only fix the value while no value provided in DSC file.
for sku in pcd . SkuInfoList . values ():
2018-04-13 08:02:10 +08:00
if not sku . DefaultValue :
2017-12-22 20:07:54 +08:00
sku . DefaultValue = pcdDecObject . DefaultValue
2018-04-16 21:52:13 +08:00
if TAB_DEFAULT not in pcd . SkuInfoList and TAB_COMMON not in pcd . SkuInfoList :
2017-11-24 14:30:11 +08:00
valuefromDec = pcdDecObject . DefaultValue
2018-04-16 21:52:13 +08:00
SkuInfo = SkuInfoClass ( TAB_DEFAULT , '0' , '' , '' , '' , '' , '' , valuefromDec )
pcd . SkuInfoList [ TAB_DEFAULT ] = SkuInfo
elif TAB_DEFAULT not in pcd . SkuInfoList and TAB_COMMON in pcd . SkuInfoList :
pcd . SkuInfoList [ TAB_DEFAULT ] = pcd . SkuInfoList [ TAB_COMMON ]
del pcd . SkuInfoList [ TAB_COMMON ]
elif TAB_DEFAULT in pcd . SkuInfoList and TAB_COMMON in pcd . SkuInfoList :
del pcd . SkuInfoList [ TAB_COMMON ]
2017-12-01 22:00:07 +08:00
2019-01-28 15:06:30 +08:00
list ( map ( self . FilterSkuSettings , Pcds . values ()))
2017-11-24 14:30:11 +08:00
return Pcds
2017-12-01 22:00:07 +08:00
def FilterSkuSettings ( self , PcdObj ):
if self . SkuIdMgr . SkuUsageType == self . SkuIdMgr . SINGLE :
2018-04-16 21:52:13 +08:00
if TAB_DEFAULT in PcdObj . SkuInfoList and self . SkuIdMgr . SystemSkuId not in PcdObj . SkuInfoList :
PcdObj . SkuInfoList [ self . SkuIdMgr . SystemSkuId ] = PcdObj . SkuInfoList [ TAB_DEFAULT ]
PcdObj . SkuInfoList = { TAB_DEFAULT : PcdObj . SkuInfoList [ self . SkuIdMgr . SystemSkuId ]}
PcdObj . SkuInfoList [ TAB_DEFAULT ] . SkuIdName = TAB_DEFAULT
PcdObj . SkuInfoList [ TAB_DEFAULT ] . SkuId = '0'
2017-12-01 22:00:07 +08:00
elif self . SkuIdMgr . SkuUsageType == self . SkuIdMgr . DEFAULT :
2018-04-16 21:52:13 +08:00
PcdObj . SkuInfoList = { TAB_DEFAULT : PcdObj . SkuInfoList [ TAB_DEFAULT ]}
2017-12-01 22:00:07 +08:00
return PcdObj
2018-04-14 04:51:29 +08:00
@staticmethod
def CompareVarAttr ( Attr1 , Attr2 ):
2017-11-24 14:30:11 +08:00
if not Attr1 or not Attr2 : # for empty string
return True
Attr1s = [ attr . strip () for attr in Attr1 . split ( "," )]
Attr1Set = set ( Attr1s )
Attr2s = [ attr . strip () for attr in Attr2 . split ( "," )]
Attr2Set = set ( Attr2s )
if Attr2Set == Attr1Set :
return True
else :
return False
2018-04-14 04:51:29 +08:00
2018-06-25 18:31:33 +08:00
def CompletePcdValues ( self , PcdSet ):
2018-09-25 13:20:46 +08:00
Pcds = OrderedDict ()
2017-12-22 20:46:15 +08:00
DefaultStoreObj = DefaultStore ( self . _GetDefaultStores ())
2018-06-25 18:31:33 +08:00
SkuIds = { skuname : skuid for skuname , skuid in self . SkuIdMgr . AvailableSkuIdSet . items () if skuname != TAB_COMMON }
2018-04-28 06:32:52 +08:00
DefaultStores = set ( storename for pcdobj in PcdSet . values () for skuobj in pcdobj . SkuInfoList . values () for storename in skuobj . DefaultStoreDict )
2017-12-22 20:46:15 +08:00
for PcdCName , TokenSpaceGuid in PcdSet :
PcdObj = PcdSet [( PcdCName , TokenSpaceGuid )]
2018-09-04 14:13:18 +08:00
2017-12-22 20:46:15 +08:00
if PcdObj . Type not in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_DEFAULT ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_VPD ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_DEFAULT ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ],
self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_VPD ]]:
Pcds [ PcdCName , TokenSpaceGuid ] = PcdObj
continue
PcdType = PcdObj . Type
if PcdType in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ], self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ]]:
for skuid in PcdObj . SkuInfoList :
skuobj = PcdObj . SkuInfoList [ skuid ]
2018-04-28 06:32:54 +08:00
mindefaultstorename = DefaultStoreObj . GetMin ( set ( defaultstorename for defaultstorename in skuobj . DefaultStoreDict ))
2017-12-22 20:46:15 +08:00
for defaultstorename in DefaultStores :
if defaultstorename not in skuobj . DefaultStoreDict :
2018-12-09 21:44:13 +08:00
skuobj . DefaultStoreDict [ defaultstorename ] = skuobj . DefaultStoreDict [ mindefaultstorename ]
2017-12-22 20:46:15 +08:00
skuobj . HiiDefaultValue = skuobj . DefaultStoreDict [ mindefaultstorename ]
2018-06-25 18:31:33 +08:00
for skuname , skuid in SkuIds . items ():
2017-12-22 20:04:04 +08:00
if skuname not in PcdObj . SkuInfoList :
nextskuid = self . SkuIdMgr . GetNextSkuId ( skuname )
2017-12-22 20:46:15 +08:00
while nextskuid not in PcdObj . SkuInfoList :
nextskuid = self . SkuIdMgr . GetNextSkuId ( nextskuid )
2017-12-22 20:04:04 +08:00
PcdObj . SkuInfoList [ skuname ] = copy . deepcopy ( PcdObj . SkuInfoList [ nextskuid ])
PcdObj . SkuInfoList [ skuname ] . SkuId = skuid
PcdObj . SkuInfoList [ skuname ] . SkuIdName = skuname
2017-12-22 20:46:15 +08:00
if PcdType in [ self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_HII ], self . _PCD_TYPE_STRING_ [ MODEL_PCD_DYNAMIC_EX_HII ]]:
2019-01-28 15:06:30 +08:00
PcdObj . DefaultValue = list ( PcdObj . SkuInfoList . values ())[ 0 ] . HiiDefaultValue if self . SkuIdMgr . SkuUsageType == self . SkuIdMgr . SINGLE else PcdObj . SkuInfoList [ TAB_DEFAULT ] . HiiDefaultValue
2017-12-22 20:46:15 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] = PcdObj
return Pcds
2017-11-24 14:30:11 +08:00
## Retrieve dynamic HII PCD settings
#
# @param Type PCD type
#
# @retval a dict object contains settings of given PCD type
#
def _GetDynamicHiiPcd ( self , Type ):
VariableAttrs = {}
2018-04-04 05:03:09 +08:00
Pcds = OrderedDict ()
2018-09-04 14:59:39 +08:00
UserDefinedDefaultStores = []
2017-11-24 14:30:11 +08:00
#
# tdict is a special dict kind of type, used for selecting correct
# PCD settings for certain ARCH and SKU
#
2017-12-22 20:46:15 +08:00
PcdDict = tdict ( True , 5 )
2019-04-26 10:29:58 +08:00
PcdList = []
2017-11-24 14:30:11 +08:00
RecordList = self . _RawData [ Type , self . _Arch ]
# Find out all possible PCD candidates for self._Arch
2017-12-22 20:46:15 +08:00
AvailableSkuIdSet = copy . copy ( self . SkuIds )
2017-12-22 20:04:04 +08:00
DefaultStoresDefine = self . _GetDefaultStores ()
2017-11-24 14:30:11 +08:00
2018-06-25 18:31:33 +08:00
for TokenSpaceGuid , PcdCName , Setting , Arch , SkuName , DefaultStore , Dummy4 , Dummy5 in RecordList :
2017-12-22 20:04:04 +08:00
SkuName = SkuName . upper ()
2018-04-16 21:52:13 +08:00
SkuName = TAB_DEFAULT if SkuName == TAB_COMMON else SkuName
2017-12-22 20:04:04 +08:00
DefaultStore = DefaultStore . upper ()
2018-04-16 21:52:13 +08:00
if DefaultStore == TAB_COMMON :
2018-04-11 07:17:20 +08:00
DefaultStore = TAB_DEFAULT_STORES_DEFAULT
2018-09-04 14:59:39 +08:00
else :
#The end user define [DefaultStores] and [SKUID_IDENTIFIER.Menufacturing] in DSC
UserDefinedDefaultStores . append (( PcdCName , TokenSpaceGuid ))
2017-11-24 14:30:11 +08:00
if SkuName not in AvailableSkuIdSet :
2017-12-22 20:04:04 +08:00
EdkLogger . error ( 'build' , PARAMETER_INVALID , 'Sku %s is not defined in [SkuIds] section' % SkuName ,
File = self . MetaFile , Line = Dummy5 )
if DefaultStore not in DefaultStoresDefine :
EdkLogger . error ( 'build' , PARAMETER_INVALID , 'DefaultStores %s is not defined in [DefaultStores] section' % DefaultStore ,
File = self . MetaFile , Line = Dummy5 )
2019-04-26 10:29:58 +08:00
if "." not in TokenSpaceGuid and "[" not in PcdCName and ( PcdCName , TokenSpaceGuid , SkuName , DefaultStore , Dummy5 ) not in PcdList :
PcdList . append (( PcdCName , TokenSpaceGuid , SkuName , DefaultStore , Dummy5 ))
2018-06-25 18:31:33 +08:00
PcdDict [ Arch , SkuName , PcdCName , TokenSpaceGuid , DefaultStore ] = Setting
2017-11-24 14:30:11 +08:00
# Remove redundant PCD candidates, per the ARCH and SKU
2019-09-05 17:45:10 +08:00
for index ,( PcdCName , TokenSpaceGuid , SkuName , DefaultStore , Dummy4 ) in enumerate ( PcdList ):
2017-11-24 14:30:11 +08:00
2018-06-25 18:31:33 +08:00
Setting = PcdDict [ self . _Arch , SkuName , PcdCName , TokenSpaceGuid , DefaultStore ]
2018-03-27 04:25:43 +08:00
if Setting is None :
2017-11-24 14:30:11 +08:00
continue
VariableName , VariableGuid , VariableOffset , DefaultValue , VarAttribute = self . _ValidatePcd ( PcdCName , TokenSpaceGuid , Setting , Type , Dummy4 )
rt , Msg = VariableAttributes . ValidateVarAttributes ( VarAttribute )
if not rt :
EdkLogger . error ( "build" , PCD_VARIABLE_ATTRIBUTES_ERROR , "Variable attributes settings for %s is incorrect. \n %s " % ( "." . join (( TokenSpaceGuid , PcdCName )), Msg ),
ExtraData = "[ %s ]" % VarAttribute )
ExceedMax = False
FormatCorrect = True
if VariableOffset . isdigit ():
if int ( VariableOffset , 10 ) > 0xFFFF :
ExceedMax = True
2018-04-20 23:51:24 +08:00
elif variablePattern . match ( VariableOffset ):
2017-11-24 14:30:11 +08:00
if int ( VariableOffset , 16 ) > 0xFFFF :
ExceedMax = True
# For Offset written in "A.B"
elif VariableOffset . find ( '.' ) > - 1 :
VariableOffsetList = VariableOffset . split ( "." )
if not ( len ( VariableOffsetList ) == 2
and IsValidWord ( VariableOffsetList [ 0 ])
and IsValidWord ( VariableOffsetList [ 1 ])):
FormatCorrect = False
else :
FormatCorrect = False
if not FormatCorrect :
EdkLogger . error ( 'Build' , FORMAT_INVALID , "Invalid syntax or format of the variable offset value is incorrect for %s ." % "." . join (( TokenSpaceGuid , PcdCName )))
if ExceedMax :
EdkLogger . error ( 'Build' , OPTION_VALUE_INVALID , "The variable offset value must not exceed the maximum value of 0xFFFF (UINT16) for %s ." % "." . join (( TokenSpaceGuid , PcdCName )))
if ( VariableName , VariableGuid ) not in VariableAttrs :
VariableAttrs [( VariableName , VariableGuid )] = VarAttribute
else :
2018-04-14 04:51:29 +08:00
if not DscBuildData . CompareVarAttr ( VariableAttrs [( VariableName , VariableGuid )], VarAttribute ):
2017-11-24 14:30:11 +08:00
EdkLogger . error ( 'Build' , PCD_VARIABLE_ATTRIBUTES_CONFLICT_ERROR , "The variable %s . %s for DynamicHii PCDs has conflicting attributes [ %s ] and [ %s ] " % ( VariableGuid , VariableName , VarAttribute , VariableAttrs [( VariableName , VariableGuid )]))
pcdDecObject = self . _DecPcds [ PcdCName , TokenSpaceGuid ]
2018-04-10 22:20:06 +08:00
if ( PcdCName , TokenSpaceGuid ) in Pcds :
2017-11-24 14:30:11 +08:00
pcdObject = Pcds [ PcdCName , TokenSpaceGuid ]
2017-12-22 20:46:15 +08:00
if SkuName in pcdObject . SkuInfoList :
Skuitem = pcdObject . SkuInfoList [ SkuName ]
Skuitem . DefaultStoreDict . update ({ DefaultStore : DefaultValue })
else :
2018-06-25 18:31:33 +08:00
SkuInfo = SkuInfoClass ( SkuName , self . SkuIds [ SkuName ][ 0 ], VariableName , VariableGuid , VariableOffset , DefaultValue , VariableAttribute = VarAttribute , DefaultStore = { DefaultStore : DefaultValue })
2017-12-22 20:46:15 +08:00
pcdObject . SkuInfoList [ SkuName ] = SkuInfo
2017-11-24 14:30:11 +08:00
else :
2018-06-25 18:31:33 +08:00
SkuInfo = SkuInfoClass ( SkuName , self . SkuIds [ SkuName ][ 0 ], VariableName , VariableGuid , VariableOffset , DefaultValue , VariableAttribute = VarAttribute , DefaultStore = { DefaultStore : DefaultValue })
2018-09-04 14:59:39 +08:00
PcdClassObj = PcdClassObject (
2017-11-24 14:30:11 +08:00
PcdCName ,
TokenSpaceGuid ,
self . _PCD_TYPE_STRING_ [ Type ],
'' ,
DefaultValue ,
'' ,
'' ,
2018-09-25 13:20:46 +08:00
OrderedDict ({ SkuName : SkuInfo }),
2017-11-24 14:30:11 +08:00
False ,
None ,
pcdDecObject . validateranges ,
pcdDecObject . validlists ,
pcdDecObject . expressions ,
IsDsc = True )
2018-09-04 14:59:39 +08:00
if ( PcdCName , TokenSpaceGuid ) in UserDefinedDefaultStores :
PcdClassObj . UserDefinedDefaultStoresFlag = True
Pcds [ PcdCName , TokenSpaceGuid ] = PcdClassObj
2017-11-24 14:30:11 +08:00
2019-09-05 17:45:10 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . CustomAttribute [ 'DscPosition' ] = index
2018-09-04 14:13:18 +08:00
if SkuName not in Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValue :
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValue [ SkuName ] = {}
2019-05-09 17:19:56 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValueInfo [ SkuName ] = {}
2018-09-04 14:13:18 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValue [ SkuName ][ DefaultStore ] = DefaultValue
2019-05-09 17:19:56 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValueInfo [ SkuName ][ DefaultStore ] = ( self . MetaFile . File , Dummy4 )
2017-11-24 14:30:11 +08:00
for pcd in Pcds . values ():
pcdDecObject = self . _DecPcds [ pcd . TokenCName , pcd . TokenSpaceGuidCName ]
2018-02-06 15:20:46 +08:00
pcd . DatumType = pcdDecObject . DatumType
2017-11-24 14:30:11 +08:00
# Only fix the value while no value provided in DSC file.
for sku in pcd . SkuInfoList . values ():
2018-03-27 04:25:43 +08:00
if ( sku . HiiDefaultValue == "" or sku . HiiDefaultValue is None ):
2017-11-24 14:30:11 +08:00
sku . HiiDefaultValue = pcdDecObject . DefaultValue
2018-02-06 15:20:46 +08:00
for default_store in sku . DefaultStoreDict :
sku . DefaultStoreDict [ default_store ] = pcdDecObject . DefaultValue
pcd . DefaultValue = pcdDecObject . DefaultValue
2018-04-16 21:52:13 +08:00
if TAB_DEFAULT not in pcd . SkuInfoList and TAB_COMMON not in pcd . SkuInfoList :
2019-01-28 15:06:30 +08:00
SkuInfoObj = list ( pcd . SkuInfoList . values ())[ 0 ]
2017-11-24 14:30:11 +08:00
valuefromDec = pcdDecObject . DefaultValue
2018-06-25 18:31:33 +08:00
SkuInfo = SkuInfoClass ( TAB_DEFAULT , '0' , SkuInfoObj . VariableName , SkuInfoObj . VariableGuid , SkuInfoObj . VariableOffset , valuefromDec , VariableAttribute = SkuInfoObj . VariableAttribute , DefaultStore = { DefaultStore : valuefromDec })
2018-04-16 21:52:13 +08:00
pcd . SkuInfoList [ TAB_DEFAULT ] = SkuInfo
elif TAB_DEFAULT not in pcd . SkuInfoList and TAB_COMMON in pcd . SkuInfoList :
pcd . SkuInfoList [ TAB_DEFAULT ] = pcd . SkuInfoList [ TAB_COMMON ]
del pcd . SkuInfoList [ TAB_COMMON ]
elif TAB_DEFAULT in pcd . SkuInfoList and TAB_COMMON in pcd . SkuInfoList :
del pcd . SkuInfoList [ TAB_COMMON ]
2017-11-24 14:30:11 +08:00
if pcd . MaxDatumSize . strip ():
MaxSize = int ( pcd . MaxDatumSize , 0 )
else :
MaxSize = 0
2018-04-11 09:14:05 -07:00
if pcd . DatumType not in TAB_PCD_NUMERIC_TYPES :
2017-12-22 20:04:04 +08:00
for ( _ , skuobj ) in pcd . SkuInfoList . items ():
2017-11-24 14:30:11 +08:00
datalen = 0
2017-12-22 20:14:29 +08:00
skuobj . HiiDefaultValue = StringToArray ( skuobj . HiiDefaultValue )
datalen = len ( skuobj . HiiDefaultValue . split ( "," ))
2017-11-24 14:30:11 +08:00
if datalen > MaxSize :
MaxSize = datalen
2017-12-22 20:14:29 +08:00
for defaultst in skuobj . DefaultStoreDict :
skuobj . DefaultStoreDict [ defaultst ] = StringToArray ( skuobj . DefaultStoreDict [ defaultst ])
pcd . DefaultValue = StringToArray ( pcd . DefaultValue )
2017-11-24 14:30:11 +08:00
pcd . MaxDatumSize = str ( MaxSize )
2018-04-14 04:51:29 +08:00
rt , invalidhii = DscBuildData . CheckVariableNameAssignment ( Pcds )
2017-12-22 20:04:04 +08:00
if not rt :
invalidpcd = "," . join ( invalidhii )
EdkLogger . error ( 'build' , PCD_VARIABLE_INFO_ERROR , Message = 'The same HII PCD must map to the same EFI variable for all SKUs' , File = self . MetaFile , ExtraData = invalidpcd )
2017-12-01 22:00:07 +08:00
2019-01-28 15:06:30 +08:00
list ( map ( self . FilterSkuSettings , Pcds . values ()))
2017-12-01 22:00:07 +08:00
2017-11-24 14:30:11 +08:00
return Pcds
2018-04-14 04:51:29 +08:00
@staticmethod
def CheckVariableNameAssignment ( Pcds ):
2017-12-22 20:04:04 +08:00
invalidhii = []
for pcdname in Pcds :
pcd = Pcds [ pcdname ]
2018-06-25 18:31:33 +08:00
varnameset = set ( sku . VariableName for ( skuid , sku ) in pcd . SkuInfoList . items ())
2017-12-22 20:04:04 +08:00
if len ( varnameset ) > 1 :
2018-06-25 18:31:33 +08:00
invalidhii . append ( "." . join (( pcdname [ 1 ], pcdname [ 0 ])))
2017-12-22 20:04:04 +08:00
if len ( invalidhii ):
2018-06-25 18:31:33 +08:00
return False , invalidhii
2017-12-22 20:04:04 +08:00
else :
return True , []
2017-11-24 14:30:11 +08:00
## Retrieve dynamic VPD PCD settings
#
# @param Type PCD type
#
# @retval a dict object contains settings of given PCD type
#
def _GetDynamicVpdPcd ( self , Type ):
2018-04-04 05:03:09 +08:00
Pcds = OrderedDict ()
2017-11-24 14:30:11 +08:00
#
# tdict is a special dict kind of type, used for selecting correct
# PCD settings for certain ARCH and SKU
#
PcdDict = tdict ( True , 4 )
PcdList = []
# Find out all possible PCD candidates for self._Arch
RecordList = self . _RawData [ Type , self . _Arch ]
2017-12-22 20:46:15 +08:00
AvailableSkuIdSet = copy . copy ( self . SkuIds )
2017-11-24 14:30:11 +08:00
2018-06-25 18:31:33 +08:00
for TokenSpaceGuid , PcdCName , Setting , Arch , SkuName , Dummy3 , Dummy4 , Dummy5 in RecordList :
2017-12-22 20:04:04 +08:00
SkuName = SkuName . upper ()
2018-04-16 21:52:13 +08:00
SkuName = TAB_DEFAULT if SkuName == TAB_COMMON else SkuName
2017-11-24 14:30:11 +08:00
if SkuName not in AvailableSkuIdSet :
2017-12-22 20:04:04 +08:00
EdkLogger . error ( 'build' , PARAMETER_INVALID , 'Sku %s is not defined in [SkuIds] section' % SkuName ,
File = self . MetaFile , Line = Dummy5 )
2019-04-26 10:29:58 +08:00
if "." not in TokenSpaceGuid and "[" not in PcdCName and ( PcdCName , TokenSpaceGuid , SkuName , Dummy5 ) not in PcdList :
2018-01-31 17:32:01 +08:00
PcdList . append (( PcdCName , TokenSpaceGuid , SkuName , Dummy5 ))
2017-11-24 14:30:11 +08:00
PcdDict [ Arch , SkuName , PcdCName , TokenSpaceGuid ] = Setting
# Remove redundant PCD candidates, per the ARCH and SKU
for PcdCName , TokenSpaceGuid , SkuName , Dummy4 in PcdList :
Setting = PcdDict [ self . _Arch , SkuName , PcdCName , TokenSpaceGuid ]
2018-03-27 04:25:43 +08:00
if Setting is None :
2017-11-24 14:30:11 +08:00
continue
#
# For the VOID* type, it can have optional data of MaxDatumSize and InitialValue
# For the Integer & Boolean type, the optional data can only be InitialValue.
# At this point, we put all the data into the PcdClssObject for we don't know the PCD's datumtype
# until the DEC parser has been called.
#
VpdOffset , MaxDatumSize , InitialValue = self . _ValidatePcd ( PcdCName , TokenSpaceGuid , Setting , Type , Dummy4 )
2018-08-03 15:46:20 +08:00
if MaxDatumSize :
if int ( MaxDatumSize , 0 ) > 0xFFFF :
EdkLogger . error ( 'build' , FORMAT_INVALID , "The size value must not exceed the maximum value of 0xFFFF (UINT16) for %s ." % "." . join (( TokenSpaceGuid , PcdCName )),
File = self . MetaFile , Line = Dummy4 )
if int ( MaxDatumSize , 0 ) < 0 :
EdkLogger . error ( 'build' , FORMAT_INVALID , "The size value can't be set to negative value for %s ." % "." . join (( TokenSpaceGuid , PcdCName )),
File = self . MetaFile , Line = Dummy4 )
2017-12-22 20:46:15 +08:00
SkuInfo = SkuInfoClass ( SkuName , self . SkuIds [ SkuName ][ 0 ], '' , '' , '' , '' , VpdOffset , InitialValue )
2018-04-10 22:20:06 +08:00
if ( PcdCName , TokenSpaceGuid ) in Pcds :
2017-11-24 14:30:11 +08:00
pcdObject = Pcds [ PcdCName , TokenSpaceGuid ]
pcdObject . SkuInfoList [ SkuName ] = SkuInfo
if MaxDatumSize . strip ():
CurrentMaxSize = int ( MaxDatumSize . strip (), 0 )
else :
CurrentMaxSize = 0
if pcdObject . MaxDatumSize :
PcdMaxSize = int ( pcdObject . MaxDatumSize , 0 )
else :
PcdMaxSize = 0
if CurrentMaxSize > PcdMaxSize :
pcdObject . MaxDatumSize = str ( CurrentMaxSize )
else :
Pcds [ PcdCName , TokenSpaceGuid ] = PcdClassObject (
PcdCName ,
TokenSpaceGuid ,
self . _PCD_TYPE_STRING_ [ Type ],
'' ,
InitialValue ,
'' ,
MaxDatumSize ,
2018-09-25 13:20:46 +08:00
OrderedDict ({ SkuName : SkuInfo }),
2017-11-24 14:30:11 +08:00
False ,
None ,
IsDsc = True )
2018-09-04 14:13:18 +08:00
if SkuName not in Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValue :
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValue [ SkuName ] = {}
2019-05-09 17:19:56 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValueInfo [ SkuName ] = {}
2018-09-04 14:13:18 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValue [ SkuName ][ TAB_DEFAULT_STORES_DEFAULT ] = InitialValue
2019-05-09 17:19:56 +08:00
Pcds [ PcdCName , TokenSpaceGuid ] . DscRawValueInfo [ SkuName ][ TAB_DEFAULT_STORES_DEFAULT ] = ( self . MetaFile . File , Dummy4 )
2017-11-24 14:30:11 +08:00
for pcd in Pcds . values ():
pcdDecObject = self . _DecPcds [ pcd . TokenCName , pcd . TokenSpaceGuidCName ]
2018-02-07 10:01:59 +08:00
pcd . DatumType = pcdDecObject . DatumType
2017-12-22 20:07:54 +08:00
# Only fix the value while no value provided in DSC file.
for sku in pcd . SkuInfoList . values ():
2018-04-13 08:02:10 +08:00
if not sku . DefaultValue :
2017-12-22 20:07:54 +08:00
sku . DefaultValue = pcdDecObject . DefaultValue
2018-04-16 21:52:13 +08:00
if TAB_DEFAULT not in pcd . SkuInfoList and TAB_COMMON not in pcd . SkuInfoList :
2019-01-28 15:06:30 +08:00
SkuInfoObj = list ( pcd . SkuInfoList . values ())[ 0 ]
2017-11-24 14:30:11 +08:00
valuefromDec = pcdDecObject . DefaultValue
2018-04-16 21:52:13 +08:00
SkuInfo = SkuInfoClass ( TAB_DEFAULT , '0' , '' , '' , '' , '' , SkuInfoObj . VpdOffset , valuefromDec )
pcd . SkuInfoList [ TAB_DEFAULT ] = SkuInfo
elif TAB_DEFAULT not in pcd . SkuInfoList and TAB_COMMON in pcd . SkuInfoList :
pcd . SkuInfoList [ TAB_DEFAULT ] = pcd . SkuInfoList [ TAB_COMMON ]
del pcd . SkuInfoList [ TAB_COMMON ]
elif TAB_DEFAULT in pcd . SkuInfoList and TAB_COMMON in pcd . SkuInfoList :
del pcd . SkuInfoList [ TAB_COMMON ]
2017-11-24 14:30:11 +08:00
2018-10-18 10:42:34 +08:00
#For the same one VOID* pcd, if the default value type of one SKU is "Unicode string",
#the other SKUs are "OtherVOID*"(ASCII string or byte array),Then convert "Unicode string" to "byte array".
for pcd in Pcds . values ():
PcdValueTypeSet = set ()
for sku in pcd . SkuInfoList . values ():
PcdValueTypeSet . add ( "UnicodeString" if sku . DefaultValue . startswith (( 'L"' , "L'" )) else "OtherVOID*" )
if len ( PcdValueTypeSet ) > 1 :
for sku in pcd . SkuInfoList . values ():
sku . DefaultValue = StringToArray ( sku . DefaultValue ) if sku . DefaultValue . startswith (( 'L"' , "L'" )) else sku . DefaultValue
2017-12-01 22:00:07 +08:00
2019-01-28 15:06:30 +08:00
list ( map ( self . FilterSkuSettings , Pcds . values ()))
2017-11-24 14:30:11 +08:00
return Pcds
2018-09-11 06:18:05 +08:00
@property
def ToolChainFamily ( self ):
2018-08-25 00:33:17 +08:00
self . _ToolChainFamily = TAB_COMPILER_MSFT
2020-01-10 16:29:45 +08:00
TargetObj = TargetTxtDict ()
TargetTxt = TargetObj . Target
2021-09-23 16:59:03 +08:00
BuildConfigurationFile = os . path . normpath ( os . path . join ( GlobalData . gConfDirectory , gDefaultTargetTxtFile ))
2017-12-26 13:16:17 +08:00
if os . path . isfile ( BuildConfigurationFile ) == True :
ToolDefinitionFile = TargetTxt . TargetTxtDictionary [ DataType . TAB_TAT_DEFINES_TOOL_CHAIN_CONF ]
if ToolDefinitionFile == '' :
2021-09-23 16:59:03 +08:00
ToolDefinitionFile = os . path . normpath ( mws . join ( self . WorkspaceDir , 'Conf' , gDefaultToolsDefFile ))
2017-12-26 13:16:17 +08:00
if os . path . isfile ( ToolDefinitionFile ) == True :
2020-01-10 16:29:45 +08:00
ToolDefObj = ToolDefDict (( os . path . join ( os . getenv ( "WORKSPACE" ), "Conf" )))
ToolDefinition = ToolDefObj . ToolDef . ToolsDefTxtDatabase
2017-12-26 13:16:17 +08:00
if TAB_TOD_DEFINES_FAMILY not in ToolDefinition \
or self . _Toolchain not in ToolDefinition [ TAB_TOD_DEFINES_FAMILY ] \
or not ToolDefinition [ TAB_TOD_DEFINES_FAMILY ][ self . _Toolchain ]:
2018-08-25 00:33:17 +08:00
self . _ToolChainFamily = TAB_COMPILER_MSFT
2017-12-26 13:16:17 +08:00
else :
self . _ToolChainFamily = ToolDefinition [ TAB_TOD_DEFINES_FAMILY ][ self . _Toolchain ]
return self . _ToolChainFamily
2017-12-26 11:33:33 +08:00
@property
def DecPcds ( self ):
2018-03-27 04:25:43 +08:00
if self . _DecPcds is None :
2017-12-26 11:33:33 +08:00
FdfInfList = []
if GlobalData . gFdfParser :
FdfInfList = GlobalData . gFdfParser . Profile . InfList
PkgSet = set ()
for Inf in FdfInfList :
ModuleFile = PathClass ( NormPath ( Inf ), GlobalData . gWorkspace , Arch = self . _Arch )
if ModuleFile in self . _Modules :
continue
ModuleData = self . _Bdb [ ModuleFile , self . _Arch , self . _Target , self . _Toolchain ]
PkgSet . update ( ModuleData . Packages )
2019-11-14 09:27:42 +08:00
if self . Packages :
PkgSet . update ( self . Packages )
2018-06-25 18:31:33 +08:00
self . _DecPcds , self . _GuidDict = GetDeclaredPcd ( self , self . _Bdb , self . _Arch , self . _Target , self . _Toolchain , PkgSet )
2018-10-16 16:10:24 +08:00
self . _GuidDict . update ( GlobalData . gPlatformPcds )
2017-12-26 11:33:33 +08:00
return self . _DecPcds