## @file
# Create makefile for MS nmake and GNU make
#
# Copyright (c) 2007 - 2021, Intel Corporation. All rights reserved.<BR>
# Copyright (c) 2020 - 2021, Arm Limited. All rights reserved.<BR>
# SPDX-License-Identifier: BSD-2-Clause-Patent
#

## Import Modules
#
from __future__ import absolute_import
import Common.LongFilePathOs as os
import sys
import string
import re
import os.path as path
from Common.LongFilePathSupport import OpenLongFilePath as open
from Common.MultipleWorkspace import MultipleWorkspace as mws
from Common.BuildToolError import *
from Common.Misc import *
from Common.StringUtils import *
from .BuildEngine import *
import Common.GlobalData as GlobalData
from collections import OrderedDict
from Common.DataType import TAB_COMPILER_MSFT

## Regular expression for finding header file inclusions
gIncludePattern = re.compile(r"^[ \t]*[#%]?[ \t]*include(?:[ \t]*(?:\\(?:\r\n|\r|\n))*[ \t]*)*(?:\(?[\"<]?[ \t]*)([-\w.\\/() \t]+)(?:[ \t]*[\">]?\)?)", re.MULTILINE | re.UNICODE | re.IGNORECASE)

## Regular expression for matching macro used in header file inclusion
gMacroPattern = re.compile("([_A-Z][_A-Z0-9]*)[ \t]*\((.+)\)", re.UNICODE)

gIsFileMap = {}

## pattern for include style in Edk.x code
gProtocolDefinition = "Protocol/%(HeaderKey)s/%(HeaderKey)s.h"
gGuidDefinition = "Guid/%(HeaderKey)s/%(HeaderKey)s.h"
gArchProtocolDefinition = "ArchProtocol/%(HeaderKey)s/%(HeaderKey)s.h"
gPpiDefinition = "Ppi/%(HeaderKey)s/%(HeaderKey)s.h"
gIncludeMacroConversion = {
  "EFI_PROTOCOL_DEFINITION"         :   gProtocolDefinition,
  "EFI_GUID_DEFINITION"             :   gGuidDefinition,
  "EFI_ARCH_PROTOCOL_DEFINITION"    :   gArchProtocolDefinition,
  "EFI_PROTOCOL_PRODUCER"           :   gProtocolDefinition,
  "EFI_PROTOCOL_CONSUMER"           :   gProtocolDefinition,
  "EFI_PROTOCOL_DEPENDENCY"         :   gProtocolDefinition,
  "EFI_ARCH_PROTOCOL_PRODUCER"      :   gArchProtocolDefinition,
  "EFI_ARCH_PROTOCOL_CONSUMER"      :   gArchProtocolDefinition,
  "EFI_ARCH_PROTOCOL_DEPENDENCY"    :   gArchProtocolDefinition,
  "EFI_PPI_DEFINITION"              :   gPpiDefinition,
  "EFI_PPI_PRODUCER"                :   gPpiDefinition,
  "EFI_PPI_CONSUMER"                :   gPpiDefinition,
  "EFI_PPI_DEPENDENCY"              :   gPpiDefinition,
}

NMAKE_FILETYPE = "nmake"
GMAKE_FILETYPE = "gmake"
WIN32_PLATFORM = "win32"
POSIX_PLATFORM = "posix"

## BuildFile class
#
#  This base class encapsules build file and its generation. It uses template to generate
#  the content of build file. The content of build file will be got from AutoGen objects.
#
class BuildFile(object):
    ## template used to generate the build file (i.e. makefile if using make)
    _TEMPLATE_ = TemplateString('')

    _DEFAULT_FILE_NAME_ = "Makefile"

    ## default file name for each type of build file
    _FILE_NAME_ = {
        NMAKE_FILETYPE :   "Makefile",
        GMAKE_FILETYPE :   "GNUmakefile"
    }

    # Get Makefile name.
    def getMakefileName(self):
        if not self._FileType:
            return self._DEFAULT_FILE_NAME_
        else:
            return self._FILE_NAME_[self._FileType]

    ## Fixed header string for makefile
    _MAKEFILE_HEADER = '''#
# DO NOT EDIT
# This file is auto-generated by build utility
#
# Module Name:
#
#   %s
#
# Abstract:
#
#   Auto-generated makefile for building modules, libraries or platform
#
    '''

    ## Header string for each type of build file
    _FILE_HEADER_ = {
        NMAKE_FILETYPE :   _MAKEFILE_HEADER % _FILE_NAME_[NMAKE_FILETYPE],
        GMAKE_FILETYPE :   _MAKEFILE_HEADER % _FILE_NAME_[GMAKE_FILETYPE]
    }

    ## shell commands which can be used in build file in the form of macro
    #   $(CP)     copy file command
    #   $(MV)     move file command
    #   $(RM)     remove file command
    #   $(MD)     create dir command
    #   $(RD)     remove dir command
    #
    _SHELL_CMD_ = {
        WIN32_PLATFORM : {
            "CP"    :   "copy /y",
            "MV"    :   "move /y",
            "RM"    :   "del /f /q",
            "MD"    :   "mkdir",
            "RD"    :   "rmdir /s /q",
        },

        POSIX_PLATFORM : {
            "CP"    :   "cp -f",
            "MV"    :   "mv -f",
            "RM"    :   "rm -f",
            "MD"    :   "mkdir -p",
            "RD"    :   "rm -r -f",
        }
    }

    ## directory separator
    _SEP_ = {
        WIN32_PLATFORM :   "\\",
        POSIX_PLATFORM :   "/"
    }

    ## directory creation template
    _MD_TEMPLATE_ = {
        WIN32_PLATFORM :   'if not exist %(dir)s $(MD) %(dir)s',
        POSIX_PLATFORM :   "$(MD) %(dir)s"
    }

    ## directory removal template
    _RD_TEMPLATE_ = {
        WIN32_PLATFORM :   'if exist %(dir)s $(RD) %(dir)s',
        POSIX_PLATFORM :   "$(RD) %(dir)s"
    }
    ## cp if exist
    _CP_TEMPLATE_ = {
        WIN32_PLATFORM :   'if exist %(Src)s $(CP) %(Src)s %(Dst)s',
        POSIX_PLATFORM :   "test -f %(Src)s && $(CP) %(Src)s %(Dst)s"
    }

    _CD_TEMPLATE_ = {
        WIN32_PLATFORM :   'if exist %(dir)s cd %(dir)s',
        POSIX_PLATFORM :   "test -e %(dir)s && cd %(dir)s"
    }

    _MAKE_TEMPLATE_ = {
        WIN32_PLATFORM :   'if exist %(file)s "$(MAKE)" $(MAKE_FLAGS) -f %(file)s',
        POSIX_PLATFORM :   'test -e %(file)s && "$(MAKE)" $(MAKE_FLAGS) -f %(file)s'
    }

    _INCLUDE_CMD_ = {
        NMAKE_FILETYPE :   '!INCLUDE',
        GMAKE_FILETYPE :   "include"
    }

    _INC_FLAG_ = {TAB_COMPILER_MSFT : "/I", "GCC" : "-I", "INTEL" : "-I", "NASM" : "-I"}

    ## Constructor of BuildFile
    #
    #   @param  AutoGenObject   Object of AutoGen class
    #
    def __init__(self, AutoGenObject):
        self._AutoGenObject = AutoGenObject

        MakePath = AutoGenObject.BuildOption.get('MAKE', {}).get('PATH')
        if not MakePath:
            MakePath = AutoGenObject.ToolDefinition.get('MAKE', {}).get('PATH')
        if "nmake" in MakePath:
            self._FileType = NMAKE_FILETYPE
        else:
            self._FileType = GMAKE_FILETYPE

        if sys.platform == "win32":
            self._Platform = WIN32_PLATFORM
        else:
            self._Platform = POSIX_PLATFORM

    ## Create build file.
    #
    #  Only nmake and gmake are supported.
    #
    #  @retval TRUE     The build file is created or re-created successfully.
    #  @retval FALSE    The build file exists and is the same as the one to be generated.
    #
    def Generate(self):
        FileContent = self._TEMPLATE_.Replace(self._TemplateDict)
        FileName = self.getMakefileName()
        if not os.path.exists(os.path.join(self._AutoGenObject.MakeFileDir, "deps.txt")):
            with open(os.path.join(self._AutoGenObject.MakeFileDir, "deps.txt"),"w+") as fd:
                fd.write("")
        if not os.path.exists(os.path.join(self._AutoGenObject.MakeFileDir, "dependency")):
            with open(os.path.join(self._AutoGenObject.MakeFileDir, "dependency"),"w+") as fd:
                fd.write("")
        if not os.path.exists(os.path.join(self._AutoGenObject.MakeFileDir, "deps_target")):
            with open(os.path.join(self._AutoGenObject.MakeFileDir, "deps_target"),"w+") as fd:
                fd.write("")
        return SaveFileOnChange(os.path.join(self._AutoGenObject.MakeFileDir, FileName), FileContent, False)

    ## Return a list of directory creation command string
    #
    #   @param      DirList     The list of directory to be created
    #
    #   @retval     list        The directory creation command list
    #
    def GetCreateDirectoryCommand(self, DirList):
        return [self._MD_TEMPLATE_[self._Platform] % {'dir':Dir} for Dir in DirList]

    ## Return a list of directory removal command string
    #
    #   @param      DirList     The list of directory to be removed
    #
    #   @retval     list        The directory removal command list
    #
    def GetRemoveDirectoryCommand(self, DirList):
        return [self._RD_TEMPLATE_[self._Platform] % {'dir':Dir} for Dir in DirList]

    def PlaceMacro(self, Path, MacroDefinitions=None):
        if Path.startswith("$("):
            return Path
        else:
            if MacroDefinitions is None:
                MacroDefinitions = {}
            PathLength = len(Path)
            for MacroName in MacroDefinitions:
                MacroValue = MacroDefinitions[MacroName]
                MacroValueLength = len(MacroValue)
                if MacroValueLength == 0:
                    continue
                if MacroValueLength <= PathLength and Path.startswith(MacroValue):
                    Path = "$(%s)%s" % (MacroName, Path[MacroValueLength:])
                    break
            return Path

## ModuleMakefile class
#
#  This class encapsules makefie and its generation for module. It uses template to generate
#  the content of makefile. The content of makefile will be got from ModuleAutoGen object.
#
class ModuleMakefile(BuildFile):
    ## template used to generate the makefile for module
    _TEMPLATE_ = TemplateString('''\
${makefile_header}

#
# Platform Macro Definition
#
PLATFORM_NAME = ${platform_name}
PLATFORM_GUID = ${platform_guid}
PLATFORM_VERSION = ${platform_version}
PLATFORM_RELATIVE_DIR = ${platform_relative_directory}
PLATFORM_DIR = ${platform_dir}
PLATFORM_OUTPUT_DIR = ${platform_output_directory}

#
# Module Macro Definition
#
MODULE_NAME = ${module_name}
MODULE_GUID = ${module_guid}
MODULE_NAME_GUID = ${module_name_guid}
MODULE_VERSION = ${module_version}
MODULE_TYPE = ${module_type}
MODULE_FILE = ${module_file}
MODULE_FILE_BASE_NAME = ${module_file_base_name}
BASE_NAME = $(MODULE_NAME)
MODULE_RELATIVE_DIR = ${module_relative_directory}
PACKAGE_RELATIVE_DIR = ${package_relative_directory}
MODULE_DIR = ${module_dir}
FFS_OUTPUT_DIR = ${ffs_output_directory}

MODULE_ENTRY_POINT = ${module_entry_point}
ARCH_ENTRY_POINT = ${arch_entry_point}
IMAGE_ENTRY_POINT = ${image_entry_point}

${BEGIN}${module_extra_defines}
${END}
#
# Build Configuration Macro Definition
#
ARCH = ${architecture}
TOOLCHAIN = ${toolchain_tag}
TOOLCHAIN_TAG = ${toolchain_tag}
TARGET = ${build_target}

#
# Build Directory Macro Definition
#
# PLATFORM_BUILD_DIR = ${platform_build_directory}
BUILD_DIR = ${platform_build_directory}
BIN_DIR = $(BUILD_DIR)${separator}${architecture}
LIB_DIR = $(BIN_DIR)
MODULE_BUILD_DIR = ${module_build_directory}
OUTPUT_DIR = ${module_output_directory}
DEBUG_DIR = ${module_debug_directory}
DEST_DIR_OUTPUT = $(OUTPUT_DIR)
DEST_DIR_DEBUG = $(DEBUG_DIR)

#
# Shell Command Macro
#
${BEGIN}${shell_command_code} = ${shell_command}
${END}

#
# Tools definitions specific to this module
#
${BEGIN}${module_tool_definitions}
${END}
MAKE_FILE = ${makefile_path}

#
# Build Macro
#
${BEGIN}${file_macro}
${END}

#
# Overridable Target Macro Definitions
#
FORCE_REBUILD = force_build
INIT_TARGET = init
PCH_TARGET =
BC_TARGET = ${BEGIN}${backward_compatible_target} ${END}
CODA_TARGET = ${BEGIN}${remaining_build_target} \\
              ${END}

#
# Default target, which will build dependent libraries in addition to source files
#

all: mbuild


#
# Target used when called from platform makefile, which will bypass the build of dependent libraries
#

pbuild: $(INIT_TARGET) $(BC_TARGET) $(PCH_TARGET) $(CODA_TARGET)

#
# ModuleTarget
#

mbuild: $(INIT_TARGET) $(BC_TARGET) gen_libs $(PCH_TARGET) $(CODA_TARGET)

#
# Build Target used in multi-thread build mode, which will bypass the init and gen_libs targets
#

tbuild: $(BC_TARGET) $(PCH_TARGET) $(CODA_TARGET)

#
# Phony target which is used to force executing commands for a target
#
force_build:
\t-@

#
# Target to update the FD
#

fds: mbuild gen_fds

#
# Initialization target: print build information and create necessary directories
#
init: info dirs

info:
\t-@echo Building ... $(MODULE_DIR)${separator}$(MODULE_FILE) [$(ARCH)]

dirs:
${BEGIN}\t-@${create_directory_command}\n${END}

strdefs:
\t-@$(CP) $(DEBUG_DIR)${separator}AutoGen.h $(DEBUG_DIR)${separator}$(MODULE_NAME)StrDefs.h

#
# GenLibsTarget
#
gen_libs:
\t${BEGIN}@"$(MAKE)" $(MAKE_FLAGS) -f ${dependent_library_build_directory}${separator}${makefile_name}
\t${END}@cd $(MODULE_BUILD_DIR)

#
# Build Flash Device Image
#
gen_fds:
\t@"$(MAKE)" $(MAKE_FLAGS) -f $(BUILD_DIR)${separator}${makefile_name} fds
\t@cd $(MODULE_BUILD_DIR)

${INCLUDETAG}

#
# Individual Object Build Targets
#
${BEGIN}${file_build_target}
${END}

#
# clean all intermediate files
#
clean:
\t${BEGIN}${clean_command}
\t${END}\t$(RM) AutoGenTimeStamp

#
# clean all generated files
#
cleanall:
${BEGIN}\t${cleanall_command}
${END}\t$(RM) *.pdb *.idb > NUL 2>&1
\t$(RM) $(BIN_DIR)${separator}$(MODULE_NAME).efi
\t$(RM) AutoGenTimeStamp

#
# clean all dependent libraries built
#
cleanlib:
\t${BEGIN}-@${library_build_command} cleanall
\t${END}@cd $(MODULE_BUILD_DIR)\n\n''')

    _FILE_MACRO_TEMPLATE = TemplateString("${macro_name} = ${BEGIN} \\\n    ${source_file}${END}\n")
    _BUILD_TARGET_TEMPLATE = TemplateString("${BEGIN}${target} : ${deps}\n${END}\t${cmd}\n")

    ## Constructor of ModuleMakefile
    #
    #   @param  ModuleAutoGen   Object of ModuleAutoGen class
    #
    def __init__(self, ModuleAutoGen):
        BuildFile.__init__(self, ModuleAutoGen)
        self.PlatformInfo = self._AutoGenObject.PlatformInfo

        self.ResultFileList = []
        self.IntermediateDirectoryList = ["$(DEBUG_DIR)", "$(OUTPUT_DIR)"]

        self.FileBuildTargetList = []       # [(src, target string)]
        self.BuildTargetList = []           # [target string]
        self.PendingBuildTargetList = []    # [FileBuildRule objects]
        self.CommonFileDependency = []
        self.FileListMacros = {}
        self.ListFileMacros = {}
        self.ObjTargetDict = OrderedDict()
        self.FileCache = {}
        self.LibraryBuildCommandList = []
        self.LibraryFileList = []
        self.LibraryMakefileList = []
        self.LibraryBuildDirectoryList = []
        self.SystemLibraryList = []
        self.Macros = OrderedDict()
        self.Macros["OUTPUT_DIR"      ] = self._AutoGenObject.Macros["OUTPUT_DIR"]
        self.Macros["DEBUG_DIR"       ] = self._AutoGenObject.Macros["DEBUG_DIR"]
        self.Macros["MODULE_BUILD_DIR"] = self._AutoGenObject.Macros["MODULE_BUILD_DIR"]
        self.Macros["BIN_DIR"         ] = self._AutoGenObject.Macros["BIN_DIR"]
        self.Macros["BUILD_DIR"       ] = self._AutoGenObject.Macros["BUILD_DIR"]
        self.Macros["WORKSPACE"       ] = self._AutoGenObject.Macros["WORKSPACE"]
        self.Macros["FFS_OUTPUT_DIR"  ] = self._AutoGenObject.Macros["FFS_OUTPUT_DIR"]
        self.GenFfsList                 = ModuleAutoGen.GenFfsList
        self.MacroList = ['FFS_OUTPUT_DIR', 'MODULE_GUID', 'OUTPUT_DIR']
        self.FfsOutputFileList = []
        self.DependencyHeaderFileSet = set()

    # Compose a dict object containing information used to do replacement in template
    @property
    def _TemplateDict(self):
        MyAgo = self._AutoGenObject
        Separator = self._SEP_[self._Platform]

        # break build if no source files and binary files are found
        if len(MyAgo.SourceFileList) == 0 and len(MyAgo.BinaryFileList) == 0:
            EdkLogger.error("build", AUTOGEN_ERROR, "No files to be built in module [%s, %s, %s]"
                            % (MyAgo.BuildTarget, MyAgo.ToolChain, MyAgo.Arch),
                            ExtraData="[%s]" % str(MyAgo))

        # convert dependent libraries to build command
        self.ProcessDependentLibrary()
        if len(MyAgo.Module.ModuleEntryPointList) > 0:
            ModuleEntryPoint = MyAgo.Module.ModuleEntryPointList[0]
        else:
            ModuleEntryPoint = "_ModuleEntryPoint"

        ArchEntryPoint = ModuleEntryPoint

        if MyAgo.Arch == "EBC":
            # EBC compiler always use "EfiStart" as entry point. Only applies to EdkII modules
            ImageEntryPoint = "EfiStart"
        else:
            # EdkII modules always use "_ModuleEntryPoint" as entry point
            ImageEntryPoint = "_ModuleEntryPoint"

        for k, v in MyAgo.Module.Defines.items():
            if k not in MyAgo.Macros:
                MyAgo.Macros[k] = v

        if 'MODULE_ENTRY_POINT' not in MyAgo.Macros:
            MyAgo.Macros['MODULE_ENTRY_POINT'] = ModuleEntryPoint
        if 'ARCH_ENTRY_POINT' not in MyAgo.Macros:
            MyAgo.Macros['ARCH_ENTRY_POINT'] = ArchEntryPoint
        if 'IMAGE_ENTRY_POINT' not in MyAgo.Macros:
            MyAgo.Macros['IMAGE_ENTRY_POINT'] = ImageEntryPoint

        PCI_COMPRESS_Flag = False
        for k, v in MyAgo.Module.Defines.items():
            if 'PCI_COMPRESS' == k and 'TRUE' == v:
                PCI_COMPRESS_Flag = True

        # tools definitions
        ToolsDef = []
        IncPrefix = self._INC_FLAG_[MyAgo.ToolChainFamily]
        for Tool in sorted(list(MyAgo.BuildOption)):
            Appended = False
            for Attr in sorted(list(MyAgo.BuildOption[Tool])):
                Value = MyAgo.BuildOption[Tool][Attr]
                if Attr == "FAMILY":
                    continue
                elif Attr == "PATH":
                    ToolsDef.append("%s = %s" % (Tool, Value))
                    Appended = True
                else:
                    # Don't generate MAKE_FLAGS in makefile. It's put in environment variable.
                    if Tool == "MAKE":
                        continue
                    # Remove duplicated include path, if any
                    if Attr == "FLAGS":
                        Value = RemoveDupOption(Value, IncPrefix, MyAgo.IncludePathList)
                        if Tool == "OPTROM" and PCI_COMPRESS_Flag:
                            ValueList = Value.split()
                            if ValueList:
                                for i, v in enumerate(ValueList):
                                    if '-e' == v:
                                        ValueList[i] = '-ec'
                                Value = ' '.join(ValueList)

                    ToolsDef.append("%s_%s = %s" % (Tool, Attr, Value))
                    Appended = True
            if Appended:
                ToolsDef.append("")

        # generate the Response file and Response flag
        RespDict = self.CommandExceedLimit()
        RespFileList = os.path.join(MyAgo.OutputDir, 'respfilelist.txt')
        if RespDict:
            RespFileListContent = ''
            for Resp in RespDict:
                RespFile = os.path.join(MyAgo.OutputDir, str(Resp).lower() + '.txt')
                StrList = RespDict[Resp].split(' ')
                UnexpandMacro = []
                NewStr = []
                for Str in StrList:
                    if '$' in Str or '-MMD' in Str or '-MF' in Str:
                        UnexpandMacro.append(Str)
                    else:
                        NewStr.append(Str)
                UnexpandMacroStr = ' '.join(UnexpandMacro)
                NewRespStr = ' '.join(NewStr)
                SaveFileOnChange(RespFile, NewRespStr, False)
                ToolsDef.append("%s = %s" % (Resp, UnexpandMacroStr + ' @' + RespFile))
                RespFileListContent += '@' + RespFile + TAB_LINE_BREAK
                RespFileListContent += NewRespStr + TAB_LINE_BREAK
            SaveFileOnChange(RespFileList, RespFileListContent, False)
        else:
            if os.path.exists(RespFileList):
                os.remove(RespFileList)

        # convert source files and binary files to build targets
        self.ResultFileList = [str(T.Target) for T in MyAgo.CodaTargetList]
        if len(self.ResultFileList) == 0 and len(MyAgo.SourceFileList) != 0:
            EdkLogger.error("build", AUTOGEN_ERROR, "Nothing to build",
                            ExtraData="[%s]" % str(MyAgo))

        self.ProcessBuildTargetList(MyAgo.OutputDir, ToolsDef)
        self.ParserGenerateFfsCmd()

        # Generate macros used to represent input files
        FileMacroList = [] # macro name = file list
        for FileListMacro in self.FileListMacros:
            FileMacro = self._FILE_MACRO_TEMPLATE.Replace(
                                                    {
                                                        "macro_name"  : FileListMacro,
                                                        "source_file" : self.FileListMacros[FileListMacro]
                                                    }
                                                    )
            FileMacroList.append(FileMacro)

        # INC_LIST is special
        FileMacro = ""
        IncludePathList = []
        for P in  MyAgo.IncludePathList:
            IncludePathList.append(IncPrefix + self.PlaceMacro(P, self.Macros))
            if FileBuildRule.INC_LIST_MACRO in self.ListFileMacros:
                self.ListFileMacros[FileBuildRule.INC_LIST_MACRO].append(IncPrefix + P)
        FileMacro += self._FILE_MACRO_TEMPLATE.Replace(
                                                {
                                                    "macro_name"   : "INC",
                                                    "source_file" : IncludePathList
                                                }
                                                )
        FileMacroList.append(FileMacro)
        # Add support when compiling .nasm source files
        IncludePathList = []
        asmsource = [item for item in MyAgo.SourceFileList if item.File.upper().endswith((".NASM",".ASM",".NASMB","S"))]
        if asmsource:
            for P in  MyAgo.IncludePathList:
                IncludePath = self._INC_FLAG_['NASM'] + self.PlaceMacro(P, self.Macros)
                if IncludePath.endswith(os.sep):
                    IncludePath = IncludePath.rstrip(os.sep)
                # When compiling .nasm files, need to add a literal backslash at each path.
                # In nmake makfiles, a trailing literal backslash must be escaped with a caret ('^').
                # It is otherwise replaced with a space (' '). This is not necessary for GNU makfefiles.
                if P == MyAgo.IncludePathList[-1] and self._Platform == WIN32_PLATFORM and self._FileType == NMAKE_FILETYPE:
                    IncludePath = ''.join([IncludePath, '^', os.sep])
                else:
                    IncludePath = os.path.join(IncludePath, '')
                IncludePathList.append(IncludePath)
            FileMacroList.append(self._FILE_MACRO_TEMPLATE.Replace({"macro_name": "NASM_INC", "source_file": IncludePathList}))

        # Generate macros used to represent files containing list of input files
        for ListFileMacro in self.ListFileMacros:
            ListFileName = os.path.join(MyAgo.OutputDir, "%s.lst" % ListFileMacro.lower()[:len(ListFileMacro) - 5])
            FileMacroList.append("%s = %s" % (ListFileMacro, ListFileName))
            SaveFileOnChange(
                ListFileName,
                "\n".join(self.ListFileMacros[ListFileMacro]),
                False
                )

        # Generate objlist used to create .obj file
        for Type in self.ObjTargetDict:
            NewLine = ' '.join(list(self.ObjTargetDict[Type]))
            FileMacroList.append("OBJLIST_%s = %s" % (list(self.ObjTargetDict.keys()).index(Type), NewLine))

        BcTargetList = []

        MakefileName = self.getMakefileName()
        LibraryMakeCommandList = []
        for D in self.LibraryBuildDirectoryList:
            Command = self._MAKE_TEMPLATE_[self._Platform] % {"file":os.path.join(D, MakefileName)}
            LibraryMakeCommandList.append(Command)

        package_rel_dir = MyAgo.SourceDir
        current_dir = self.Macros["WORKSPACE"]
        found = False
        while not found and os.sep in package_rel_dir:
            index = package_rel_dir.index(os.sep)
            current_dir = mws.join(current_dir, package_rel_dir[:index])
            if os.path.exists(current_dir):
                for fl in os.listdir(current_dir):
                    if fl.endswith('.dec'):
                        found = True
                        break
            package_rel_dir = package_rel_dir[index + 1:]

        MakefileTemplateDict = {
            "makefile_header"           : self._FILE_HEADER_[self._FileType],
            "makefile_path"             : os.path.join("$(MODULE_BUILD_DIR)", MakefileName),
            "makefile_name"             : MakefileName,
            "platform_name"             : self.PlatformInfo.Name,
            "platform_guid"             : self.PlatformInfo.Guid,
            "platform_version"          : self.PlatformInfo.Version,
            "platform_relative_directory": self.PlatformInfo.SourceDir,
            "platform_output_directory" : self.PlatformInfo.OutputDir,
            "ffs_output_directory"      : MyAgo.Macros["FFS_OUTPUT_DIR"],
            "platform_dir"              : MyAgo.Macros["PLATFORM_DIR"],

            "module_name"               : MyAgo.Name,
            "module_guid"               : MyAgo.Guid,
            "module_name_guid"          : MyAgo.UniqueBaseName,
            "module_version"            : MyAgo.Version,
            "module_type"               : MyAgo.ModuleType,
            "module_file"               : MyAgo.MetaFile.Name,
            "module_file_base_name"     : MyAgo.MetaFile.BaseName,
            "module_relative_directory" : MyAgo.SourceDir,
            "module_dir"                : mws.join (self.Macros["WORKSPACE"], MyAgo.SourceDir),
            "package_relative_directory": package_rel_dir,
            "module_extra_defines"      : ["%s = %s" % (k, v) for k, v in MyAgo.Module.Defines.items()],

            "architecture"              : MyAgo.Arch,
            "toolchain_tag"             : MyAgo.ToolChain,
            "build_target"              : MyAgo.BuildTarget,

            "platform_build_directory"  : self.PlatformInfo.BuildDir,
            "module_build_directory"    : MyAgo.BuildDir,
            "module_output_directory"   : MyAgo.OutputDir,
            "module_debug_directory"    : MyAgo.DebugDir,

            "separator"                 : Separator,
            "module_tool_definitions"   : ToolsDef,

            "shell_command_code"        : list(self._SHELL_CMD_[self._Platform].keys()),
            "shell_command"             : list(self._SHELL_CMD_[self._Platform].values()),

            "module_entry_point"        : ModuleEntryPoint,
            "image_entry_point"         : ImageEntryPoint,
            "arch_entry_point"          : ArchEntryPoint,
            "remaining_build_target"    : self.ResultFileList,
            "common_dependency_file"    : self.CommonFileDependency,
            "create_directory_command"  : self.GetCreateDirectoryCommand(self.IntermediateDirectoryList),
            "clean_command"             : self.GetRemoveDirectoryCommand(["$(OUTPUT_DIR)"]),
            "cleanall_command"          : self.GetRemoveDirectoryCommand(["$(DEBUG_DIR)", "$(OUTPUT_DIR)"]),
            "dependent_library_build_directory" : self.LibraryBuildDirectoryList,
            "library_build_command"     : LibraryMakeCommandList,
            "file_macro"                : FileMacroList,
            "file_build_target"         : self.BuildTargetList,
            "backward_compatible_target": BcTargetList,
            "INCLUDETAG"                   : "\n".join([self._INCLUDE_CMD_[self._FileType] + " " + os.path.join("$(MODULE_BUILD_DIR)","dependency"),
                                                              self._INCLUDE_CMD_[self._FileType] + " " + os.path.join("$(MODULE_BUILD_DIR)","deps_target")
                                                              ])
        }

        return MakefileTemplateDict

    def ParserGenerateFfsCmd(self):
        #Add Ffs cmd to self.BuildTargetList
        OutputFile = ''
        DepsFileList = []

        for Cmd in self.GenFfsList:
            if Cmd[2]:
                for CopyCmd in Cmd[2]:
                    Src, Dst = CopyCmd
                    Src = self.ReplaceMacro(Src)
                    Dst = self.ReplaceMacro(Dst)
                    if Dst not in self.ResultFileList:
                        self.ResultFileList.append(Dst)
                    if '%s :' %(Dst) not in self.BuildTargetList:
                        self.BuildTargetList.append("%s : %s" %(Dst,Src))
                        self.BuildTargetList.append('\t' + self._CP_TEMPLATE_[self._Platform] %{'Src': Src, 'Dst': Dst})

            FfsCmdList = Cmd[0]
            for index, Str in enumerate(FfsCmdList):
                if '-o' == Str:
                    OutputFile = FfsCmdList[index + 1]
                if '-i' == Str or "-oi" == Str:
                    if DepsFileList == []:
                        DepsFileList = [FfsCmdList[index + 1]]
                    else:
                        DepsFileList.append(FfsCmdList[index + 1])
            DepsFileString = ' '.join(DepsFileList).strip()
            if DepsFileString == '':
                continue
            OutputFile = self.ReplaceMacro(OutputFile)
            self.ResultFileList.append(OutputFile)
            DepsFileString = self.ReplaceMacro(DepsFileString)
            self.BuildTargetList.append('%s : %s' % (OutputFile, DepsFileString))
            CmdString = ' '.join(FfsCmdList).strip()
            CmdString = self.ReplaceMacro(CmdString)
            self.BuildTargetList.append('\t%s' % CmdString)

            self.ParseSecCmd(DepsFileList, Cmd[1])
            for SecOutputFile, SecDepsFile, SecCmd in self.FfsOutputFileList :
                self.BuildTargetList.append('%s : %s' % (self.ReplaceMacro(SecOutputFile), self.ReplaceMacro(SecDepsFile)))
                self.BuildTargetList.append('\t%s' % self.ReplaceMacro(SecCmd))
            self.FfsOutputFileList = []

    def ParseSecCmd(self, OutputFileList, CmdTuple):
        for OutputFile in OutputFileList:
            for SecCmdStr in CmdTuple:
                SecDepsFileList = []
                SecCmdList = SecCmdStr.split()
                CmdName = SecCmdList[0]
                for index, CmdItem in enumerate(SecCmdList):
                    if '-o' == CmdItem and OutputFile == SecCmdList[index + 1]:
                        index = index + 1
                        while index + 1 < len(SecCmdList):
                            if not SecCmdList[index+1].startswith('-'):
                                SecDepsFileList.append(SecCmdList[index + 1])
                            index = index + 1
                        if CmdName == 'Trim':
                            SecDepsFileList.append(os.path.join('$(DEBUG_DIR)', os.path.basename(OutputFile).replace('offset', 'efi')))
                        if OutputFile.endswith('.ui') or OutputFile.endswith('.ver'):
                            SecDepsFileList.append(os.path.join('$(MODULE_DIR)', '$(MODULE_FILE)'))
                        self.FfsOutputFileList.append((OutputFile, ' '.join(SecDepsFileList), SecCmdStr))
                        if len(SecDepsFileList) > 0:
                            self.ParseSecCmd(SecDepsFileList, CmdTuple)
                        break
                    else:
                        continue

    def ReplaceMacro(self, str):
        for Macro in self.MacroList:
            if self._AutoGenObject.Macros[Macro] and os.path.normcase(self._AutoGenObject.Macros[Macro]) in os.path.normcase(str):
                replace_dir = str[os.path.normcase(str).index(os.path.normcase(self._AutoGenObject.Macros[Macro])): os.path.normcase(str).index(
                    os.path.normcase(self._AutoGenObject.Macros[Macro])) + len(self._AutoGenObject.Macros[Macro])]
                str = str.replace(replace_dir, '$(' + Macro + ')')
        return str

    def CommandExceedLimit(self):
        FlagDict = {
                    'CC'    :  { 'Macro' : '$(CC_FLAGS)',    'Value' : False},
                    'PP'    :  { 'Macro' : '$(PP_FLAGS)',    'Value' : False},
                    'APP'   :  { 'Macro' : '$(APP_FLAGS)',   'Value' : False},
                    'ASLPP' :  { 'Macro' : '$(ASLPP_FLAGS)', 'Value' : False},
                    'VFRPP' :  { 'Macro' : '$(VFRPP_FLAGS)', 'Value' : False},
                    'ASM'   :  { 'Macro' : '$(ASM_FLAGS)',   'Value' : False},
                    'ASLCC' :  { 'Macro' : '$(ASLCC_FLAGS)', 'Value' : False},
                   }

        RespDict = {}
        FileTypeList = []
        IncPrefix = self._INC_FLAG_[self._AutoGenObject.ToolChainFamily]

        # base on the source files to decide the file type
        for File in self._AutoGenObject.SourceFileList:
            for type in self._AutoGenObject.FileTypes:
                if File in self._AutoGenObject.FileTypes[type]:
                    if type not in FileTypeList:
                        FileTypeList.append(type)

        # calculate the command-line length
        if FileTypeList:
            for type in FileTypeList:
                BuildTargets = self._AutoGenObject.BuildRules[type].BuildTargets
                for Target in BuildTargets:
                    CommandList = BuildTargets[Target].Commands
                    for SingleCommand in CommandList:
                        Tool = ''
                        SingleCommandLength = len(SingleCommand)
                        SingleCommandList = SingleCommand.split()
                        if len(SingleCommandList) > 0:
                            for Flag in FlagDict:
                                if '$('+ Flag +')' in SingleCommandList[0]:
                                    Tool = Flag
                                    break
                        if Tool:
                            if 'PATH' not in self._AutoGenObject.BuildOption[Tool]:
                                EdkLogger.error("build", AUTOGEN_ERROR, "%s_PATH doesn't exist in %s ToolChain and %s Arch." %(Tool, self._AutoGenObject.ToolChain, self._AutoGenObject.Arch), ExtraData="[%s]" % str(self._AutoGenObject))
                            SingleCommandLength += len(self._AutoGenObject.BuildOption[Tool]['PATH'])
                            for item in SingleCommandList[1:]:
                                if FlagDict[Tool]['Macro'] in item:
                                    if 'FLAGS' not in self._AutoGenObject.BuildOption[Tool]:
                                        EdkLogger.error("build", AUTOGEN_ERROR, "%s_FLAGS doesn't exist in %s ToolChain and %s Arch." %(Tool, self._AutoGenObject.ToolChain, self._AutoGenObject.Arch), ExtraData="[%s]" % str(self._AutoGenObject))
                                    Str = self._AutoGenObject.BuildOption[Tool]['FLAGS']
                                    for Option in self._AutoGenObject.BuildOption:
                                        for Attr in self._AutoGenObject.BuildOption[Option]:
                                            if Str.find(Option + '_' + Attr) != -1:
                                                Str = Str.replace('$(' + Option + '_' + Attr + ')', self._AutoGenObject.BuildOption[Option][Attr])
                                    while(Str.find('$(') != -1):
                                        for macro in self._AutoGenObject.Macros:
                                            MacroName = '$('+ macro + ')'
                                            if (Str.find(MacroName) != -1):
                                                Str = Str.replace(MacroName, self._AutoGenObject.Macros[macro])
                                                break
                                        else:
                                            break
                                    SingleCommandLength += len(Str)
                                elif '$(INC)' in item:
                                    SingleCommandLength += self._AutoGenObject.IncludePathLength + len(IncPrefix) * len(self._AutoGenObject.IncludePathList)
                                elif item.find('$(') != -1:
                                    Str = item
                                    for Option in self._AutoGenObject.BuildOption:
                                        for Attr in self._AutoGenObject.BuildOption[Option]:
                                            if Str.find(Option + '_' + Attr) != -1:
                                                Str = Str.replace('$(' + Option + '_' + Attr + ')', self._AutoGenObject.BuildOption[Option][Attr])
                                    while(Str.find('$(') != -1):
                                        for macro in self._AutoGenObject.Macros:
                                            MacroName = '$('+ macro + ')'
                                            if (Str.find(MacroName) != -1):
                                                Str = Str.replace(MacroName, self._AutoGenObject.Macros[macro])
                                                break
                                        else:
                                            break
                                    SingleCommandLength += len(Str)

                            if SingleCommandLength > GlobalData.gCommandMaxLength:
                                FlagDict[Tool]['Value'] = True

                # generate the response file content by combine the FLAGS and INC
                for Flag in FlagDict:
                    if FlagDict[Flag]['Value']:
                        Key = Flag + '_RESP'
                        RespMacro = FlagDict[Flag]['Macro'].replace('FLAGS', 'RESP')
                        Value = self._AutoGenObject.BuildOption[Flag]['FLAGS']
                        for inc in self._AutoGenObject.IncludePathList:
                            Value += ' ' + IncPrefix + inc
                        for Option in self._AutoGenObject.BuildOption:
                            for Attr in self._AutoGenObject.BuildOption[Option]:
                                if Value.find(Option + '_' + Attr) != -1:
                                    Value = Value.replace('$(' + Option + '_' + Attr + ')', self._AutoGenObject.BuildOption[Option][Attr])
                        while (Value.find('$(') != -1):
                            for macro in self._AutoGenObject.Macros:
                                MacroName = '$('+ macro + ')'
                                if (Value.find(MacroName) != -1):
                                    Value = Value.replace(MacroName, self._AutoGenObject.Macros[macro])
                                    break
                            else:
                                break

                        if self._AutoGenObject.ToolChainFamily == 'GCC':
                            RespDict[Key] = Value.replace('\\', '/')
                        else:
                            RespDict[Key] = Value
                        for Target in BuildTargets:
                            for i, SingleCommand in enumerate(BuildTargets[Target].Commands):
                                if FlagDict[Flag]['Macro'] in SingleCommand:
                                    BuildTargets[Target].Commands[i] = SingleCommand.replace('$(INC)', '').replace(FlagDict[Flag]['Macro'], RespMacro)
        return RespDict

    def ProcessBuildTargetList(self, RespFile, ToolsDef):
        #
        # Search dependency file list for each source file
        #
        ForceIncludedFile = []
        for File in self._AutoGenObject.AutoGenFileList:
            if File.Ext == '.h':
                ForceIncludedFile.append(File)
        SourceFileList = []
        OutPutFileList = []
        for Target in self._AutoGenObject.IntroTargetList:
            SourceFileList.extend(Target.Inputs)
            OutPutFileList.extend(Target.Outputs)

        if OutPutFileList:
            for Item in OutPutFileList:
                if Item in SourceFileList:
                    SourceFileList.remove(Item)

        FileDependencyDict = {item:ForceIncludedFile for item in SourceFileList}

        for Dependency in FileDependencyDict.values():
            self.DependencyHeaderFileSet.update(set(Dependency))

        # Get a set of unique package includes from MetaFile
        parentMetaFileIncludes = set()
        for aInclude in self._AutoGenObject.PackageIncludePathList:
            aIncludeName = str(aInclude)
            parentMetaFileIncludes.add(aIncludeName.lower())

        # Check if header files are listed in metafile
        # Get a set of unique module header source files from MetaFile
        headerFilesInMetaFileSet = set()
        for aFile in self._AutoGenObject.SourceFileList:
            aFileName = str(aFile)
            if not aFileName.endswith('.h'):
                continue
            headerFilesInMetaFileSet.add(aFileName.lower())

        # Get a set of unique module autogen files
        localAutoGenFileSet = set()
        for aFile in self._AutoGenObject.AutoGenFileList:
            localAutoGenFileSet.add(str(aFile).lower())

        # Get a set of unique module dependency header files
        # Exclude autogen files and files not in the source directory
        # and files that are under the package include list
        headerFileDependencySet = set()
        localSourceDir = str(self._AutoGenObject.SourceDir).lower()
        for Dependency in FileDependencyDict.values():
            for aFile in Dependency:
                aFileName = str(aFile).lower()
                # Exclude non-header files
                if not aFileName.endswith('.h'):
                    continue
                # Exclude autogen files
                if aFileName in localAutoGenFileSet:
                    continue
                # Exclude include out of local scope
                if localSourceDir not in aFileName:
                    continue
                # Exclude files covered by package includes
                pathNeeded = True
                for aIncludePath in parentMetaFileIncludes:
                    if aIncludePath in aFileName:
                        pathNeeded = False
                        break
                if not pathNeeded:
                    continue
                # Keep the file to be checked
                headerFileDependencySet.add(aFileName)

        # Check if a module dependency header file is missing from the module's MetaFile
        for aFile in headerFileDependencySet:
            if aFile in headerFilesInMetaFileSet:
                continue
            if GlobalData.gUseHashCache:
                GlobalData.gModuleBuildTracking[self._AutoGenObject] = 'FAIL_METAFILE'
            EdkLogger.warn("build","Module MetaFile [Sources] is missing local header!",
                        ExtraData = "Local Header: " + aFile + " not found in " + self._AutoGenObject.MetaFile.Path
                        )

        for File,Dependency in FileDependencyDict.items():
            if not Dependency:
                continue

            self._AutoGenObject.AutoGenDepSet |= set(Dependency)

        CmdSumDict = {}
        CmdTargetDict = {}
        CmdCppDict = {}
        DependencyDict = FileDependencyDict.copy()

        # Convert target description object to target string in makefile
        if self._AutoGenObject.BuildRuleFamily == TAB_COMPILER_MSFT and TAB_C_CODE_FILE in self._AutoGenObject.Targets:
            for T in self._AutoGenObject.Targets[TAB_C_CODE_FILE]:
                NewFile = self.PlaceMacro(str(T), self.Macros)
                if not self.ObjTargetDict.get(T.Target.SubDir):
                    self.ObjTargetDict[T.Target.SubDir] = set()
                self.ObjTargetDict[T.Target.SubDir].add(NewFile)
        for Type in self._AutoGenObject.Targets:
            resp_file_number = 0
            for T in self._AutoGenObject.Targets[Type]:
                # Generate related macros if needed
                if T.GenFileListMacro and T.FileListMacro not in self.FileListMacros:
                    self.FileListMacros[T.FileListMacro] = []
                if T.GenListFile and T.ListFileMacro not in self.ListFileMacros:
                    self.ListFileMacros[T.ListFileMacro] = []
                if T.GenIncListFile and T.IncListFileMacro not in self.ListFileMacros:
                    self.ListFileMacros[T.IncListFileMacro] = []

                Deps = []
                CCodeDeps = []
                # Add force-dependencies
                for Dep in T.Dependencies:
                    Deps.append(self.PlaceMacro(str(Dep), self.Macros))
                    if Dep != '$(MAKE_FILE)':
                        CCodeDeps.append(self.PlaceMacro(str(Dep), self.Macros))
                # Add inclusion-dependencies
                if len(T.Inputs) == 1 and T.Inputs[0] in FileDependencyDict:
                    for F in FileDependencyDict[T.Inputs[0]]:
                        Deps.append(self.PlaceMacro(str(F), self.Macros))
                # Add source-dependencies
                for F in T.Inputs:
                    NewFile = self.PlaceMacro(str(F), self.Macros)
                    # In order to use file list macro as dependency
                    if T.GenListFile:
                        # gnu tools need forward slash path separator, even on Windows
                        self.ListFileMacros[T.ListFileMacro].append(str(F).replace ('\\', '/'))
                        self.FileListMacros[T.FileListMacro].append(NewFile)
                    elif T.GenFileListMacro:
                        self.FileListMacros[T.FileListMacro].append(NewFile)
                    else:
                        Deps.append(NewFile)
                for key in self.FileListMacros:
                    self.FileListMacros[key].sort()
                # Use file list macro as dependency
                if T.GenFileListMacro:
                    Deps.append("$(%s)" % T.FileListMacro)
                    if Type in [TAB_OBJECT_FILE, TAB_STATIC_LIBRARY]:
                        Deps.append("$(%s)" % T.ListFileMacro)

                if self._AutoGenObject.BuildRuleFamily == TAB_COMPILER_MSFT and Type == TAB_C_CODE_FILE:
                    T, CmdTarget, CmdTargetDict, CmdCppDict = self.ParserCCodeFile(T, Type, CmdSumDict, CmdTargetDict,
                                                                                   CmdCppDict, DependencyDict, RespFile,
                                                                                   ToolsDef, resp_file_number)
                    resp_file_number += 1
                    TargetDict = {"target": self.PlaceMacro(T.Target.Path, self.Macros), "cmd": "\n\t".join(T.Commands),"deps": CCodeDeps}
                    CmdLine = self._BUILD_TARGET_TEMPLATE.Replace(TargetDict).rstrip().replace('\t$(OBJLIST', '$(OBJLIST')
                    if T.Commands:
                        CmdLine = '%s%s' %(CmdLine, TAB_LINE_BREAK)
                    if CCodeDeps or CmdLine:
                        self.BuildTargetList.append(CmdLine)
                else:
                    TargetDict = {"target": self.PlaceMacro(T.Target.Path, self.Macros), "cmd": "\n\t".join(T.Commands),"deps": Deps}
                    self.BuildTargetList.append(self._BUILD_TARGET_TEMPLATE.Replace(TargetDict))

                    # Add a Makefile rule for targets generating multiple files.
                    # The main output is a prerequisite for the other output files.
                    for i in T.Outputs[1:]:
                        AnnexeTargetDict = {"target": self.PlaceMacro(i.Path, self.Macros), "cmd": "", "deps": self.PlaceMacro(T.Target.Path, self.Macros)}
                        self.BuildTargetList.append(self._BUILD_TARGET_TEMPLATE.Replace(AnnexeTargetDict))

    def ParserCCodeFile(self, T, Type, CmdSumDict, CmdTargetDict, CmdCppDict, DependencyDict, RespFile, ToolsDef,
                            resp_file_number):
        SaveFilePath = os.path.join(RespFile, "cc_resp_%s.txt" % resp_file_number)
        if not CmdSumDict:
            for item in self._AutoGenObject.Targets[Type]:
                CmdSumDict[item.Target.SubDir] = item.Target.BaseName
                for CppPath in item.Inputs:
                    Path = self.PlaceMacro(CppPath.Path, self.Macros)
                    if CmdCppDict.get(item.Target.SubDir):
                        CmdCppDict[item.Target.SubDir].append(Path)
                    else:
                        CmdCppDict[item.Target.SubDir] = ['$(MAKE_FILE)', Path]
                    if CppPath.Path in DependencyDict:
                        for Temp in DependencyDict[CppPath.Path]:
                            try:
                                Path = self.PlaceMacro(Temp.Path, self.Macros)
                            except:
                                continue
                            if Path not in (self.CommonFileDependency + CmdCppDict[item.Target.SubDir]):
                                CmdCppDict[item.Target.SubDir].append(Path)
        if T.Commands:
            CommandList = T.Commands[:]
            for Item in CommandList[:]:
                SingleCommandList = Item.split()
                if len(SingleCommandList) > 0 and self.CheckCCCmd(SingleCommandList):
                    for Temp in SingleCommandList:
                        if Temp.startswith('/Fo'):
                            CmdSign = '%s%s' % (Temp.rsplit(TAB_SLASH, 1)[0], TAB_SLASH)
                            break
                    else:
                        continue
                    if CmdSign not in list(CmdTargetDict.keys()):
                        cmd = Item.replace(Temp, CmdSign)
                        if SingleCommandList[-1] in cmd:
                            CmdTargetDict[CmdSign] = [cmd.replace(SingleCommandList[-1], "").rstrip(), SingleCommandList[-1]]
                    else:
                        # CmdTargetDict[CmdSign] = "%s %s" % (CmdTargetDict[CmdSign], SingleCommandList[-1])
                        CmdTargetDict[CmdSign].append(SingleCommandList[-1])
                    Index = CommandList.index(Item)
                    CommandList.pop(Index)
                    if SingleCommandList[-1].endswith("%s%s.c" % (TAB_SLASH, CmdSumDict[CmdSign[3:].rsplit(TAB_SLASH, 1)[0]])):
                        Cpplist = CmdCppDict[T.Target.SubDir]
                        Cpplist.insert(0, '$(OBJLIST_%d): ' % list(self.ObjTargetDict.keys()).index(T.Target.SubDir))
                        source_files = CmdTargetDict[CmdSign][1:]
                        source_files.insert(0, " ")
                        if len(source_files)>2:
                            SaveFileOnChange(SaveFilePath, " ".join(source_files), False)
                            T.Commands[Index] = '%s\n\t%s $(cc_resp_%s)' % (
                            ' \\\n\t'.join(Cpplist), CmdTargetDict[CmdSign][0], resp_file_number)
                            ToolsDef.append("cc_resp_%s = @%s" % (resp_file_number, SaveFilePath))

                        elif len(source_files)<=2 and len(" ".join(CmdTargetDict[CmdSign][:2]))>GlobalData.gCommandMaxLength:
                            SaveFileOnChange(SaveFilePath, " ".join(source_files), False)
                            T.Commands[Index] = '%s\n\t%s $(cc_resp_%s)' % (
                                ' \\\n\t'.join(Cpplist), CmdTargetDict[CmdSign][0], resp_file_number)
                            ToolsDef.append("cc_resp_%s = @%s" % (resp_file_number, SaveFilePath))

                        else:
                            T.Commands[Index] = '%s\n\t%s' % (' \\\n\t'.join(Cpplist), " ".join(CmdTargetDict[CmdSign]))
                    else:
                        T.Commands.pop(Index)
        return T, CmdSumDict, CmdTargetDict, CmdCppDict

    def CheckCCCmd(self, CommandList):
        for cmd in CommandList:
            if '$(CC)' in cmd:
                return True
        return False
    ## For creating makefile targets for dependent libraries
    def ProcessDependentLibrary(self):
        for LibraryAutoGen in self._AutoGenObject.LibraryAutoGenList:
            if not LibraryAutoGen.IsBinaryModule:
                self.LibraryBuildDirectoryList.append(self.PlaceMacro(LibraryAutoGen.BuildDir, self.Macros))

    ## Return a list containing source file's dependencies
    #
    #   @param      FileList        The list of source files
    #   @param      ForceInculeList The list of files which will be included forcely
    #   @param      SearchPathList  The list of search path
    #
    #   @retval     dict            The mapping between source file path and its dependencies
    #
    def GetFileDependency(self, FileList, ForceInculeList, SearchPathList):
        Dependency = {}
        for F in FileList:
            Dependency[F] = GetDependencyList(self._AutoGenObject, self.FileCache, F, ForceInculeList, SearchPathList)
        return Dependency


## CustomMakefile class
#
#  This class encapsules makefie and its generation for module. It uses template to generate
#  the content of makefile. The content of makefile will be got from ModuleAutoGen object.
#
class CustomMakefile(BuildFile):
    ## template used to generate the makefile for module with custom makefile
    _TEMPLATE_ = TemplateString('''\
${makefile_header}

#
# Platform Macro Definition
#
PLATFORM_NAME = ${platform_name}
PLATFORM_GUID = ${platform_guid}
PLATFORM_VERSION = ${platform_version}
PLATFORM_RELATIVE_DIR = ${platform_relative_directory}
PLATFORM_DIR = ${platform_dir}
PLATFORM_OUTPUT_DIR = ${platform_output_directory}

#
# Module Macro Definition
#
MODULE_NAME = ${module_name}
MODULE_GUID = ${module_guid}
MODULE_NAME_GUID = ${module_name_guid}
MODULE_VERSION = ${module_version}
MODULE_TYPE = ${module_type}
MODULE_FILE = ${module_file}
MODULE_FILE_BASE_NAME = ${module_file_base_name}
BASE_NAME = $(MODULE_NAME)
MODULE_RELATIVE_DIR = ${module_relative_directory}
MODULE_DIR = ${module_dir}

#
# Build Configuration Macro Definition
#
ARCH = ${architecture}
TOOLCHAIN = ${toolchain_tag}
TOOLCHAIN_TAG = ${toolchain_tag}
TARGET = ${build_target}

#
# Build Directory Macro Definition
#
# PLATFORM_BUILD_DIR = ${platform_build_directory}
BUILD_DIR = ${platform_build_directory}
BIN_DIR = $(BUILD_DIR)${separator}${architecture}
LIB_DIR = $(BIN_DIR)
MODULE_BUILD_DIR = ${module_build_directory}
OUTPUT_DIR = ${module_output_directory}
DEBUG_DIR = ${module_debug_directory}
DEST_DIR_OUTPUT = $(OUTPUT_DIR)
DEST_DIR_DEBUG = $(DEBUG_DIR)

#
# Tools definitions specific to this module
#
${BEGIN}${module_tool_definitions}
${END}
MAKE_FILE = ${makefile_path}

#
# Shell Command Macro
#
${BEGIN}${shell_command_code} = ${shell_command}
${END}

${custom_makefile_content}

#
# Target used when called from platform makefile, which will bypass the build of dependent libraries
#

pbuild: init all


#
# ModuleTarget
#

mbuild: init all

#
# Build Target used in multi-thread build mode, which no init target is needed
#

tbuild: all

#
# Initialization target: print build information and create necessary directories
#
init:
\t-@echo Building ... $(MODULE_DIR)${separator}$(MODULE_FILE) [$(ARCH)]
${BEGIN}\t-@${create_directory_command}\n${END}\

''')

    ## Constructor of CustomMakefile
    #
    #   @param  ModuleAutoGen   Object of ModuleAutoGen class
    #
    def __init__(self, ModuleAutoGen):
        BuildFile.__init__(self, ModuleAutoGen)
        self.PlatformInfo = self._AutoGenObject.PlatformInfo
        self.IntermediateDirectoryList = ["$(DEBUG_DIR)", "$(OUTPUT_DIR)"]
        self.DependencyHeaderFileSet = set()

    # Compose a dict object containing information used to do replacement in template
    @property
    def _TemplateDict(self):
        Separator = self._SEP_[self._Platform]
        MyAgo = self._AutoGenObject
        if self._FileType not in MyAgo.CustomMakefile:
            EdkLogger.error('build', OPTION_NOT_SUPPORTED, "No custom makefile for %s" % self._FileType,
                            ExtraData="[%s]" % str(MyAgo))
        MakefilePath = mws.join(
                                MyAgo.WorkspaceDir,
                                MyAgo.CustomMakefile[self._FileType]
                                )
        try:
            CustomMakefile = open(MakefilePath, 'r').read()
        except:
            EdkLogger.error('build', FILE_OPEN_FAILURE, File=str(MyAgo),
                            ExtraData=MyAgo.CustomMakefile[self._FileType])

        # tools definitions
        ToolsDef = []
        for Tool in MyAgo.BuildOption:
            # Don't generate MAKE_FLAGS in makefile. It's put in environment variable.
            if Tool == "MAKE":
                continue
            for Attr in MyAgo.BuildOption[Tool]:
                if Attr == "FAMILY":
                    continue
                elif Attr == "PATH":
                    ToolsDef.append("%s = %s" % (Tool, MyAgo.BuildOption[Tool][Attr]))
                else:
                    ToolsDef.append("%s_%s = %s" % (Tool, Attr, MyAgo.BuildOption[Tool][Attr]))
            ToolsDef.append("")

        MakefileName = self.getMakefileName()
        MakefileTemplateDict = {
            "makefile_header"           : self._FILE_HEADER_[self._FileType],
            "makefile_path"             : os.path.join("$(MODULE_BUILD_DIR)", MakefileName),
            "platform_name"             : self.PlatformInfo.Name,
            "platform_guid"             : self.PlatformInfo.Guid,
            "platform_version"          : self.PlatformInfo.Version,
            "platform_relative_directory": self.PlatformInfo.SourceDir,
            "platform_output_directory" : self.PlatformInfo.OutputDir,
            "platform_dir"              : MyAgo.Macros["PLATFORM_DIR"],

            "module_name"               : MyAgo.Name,
            "module_guid"               : MyAgo.Guid,
            "module_name_guid"          : MyAgo.UniqueBaseName,
            "module_version"            : MyAgo.Version,
            "module_type"               : MyAgo.ModuleType,
            "module_file"               : MyAgo.MetaFile,
            "module_file_base_name"     : MyAgo.MetaFile.BaseName,
            "module_relative_directory" : MyAgo.SourceDir,
            "module_dir"                : mws.join (MyAgo.WorkspaceDir, MyAgo.SourceDir),

            "architecture"              : MyAgo.Arch,
            "toolchain_tag"             : MyAgo.ToolChain,
            "build_target"              : MyAgo.BuildTarget,

            "platform_build_directory"  : self.PlatformInfo.BuildDir,
            "module_build_directory"    : MyAgo.BuildDir,
            "module_output_directory"   : MyAgo.OutputDir,
            "module_debug_directory"    : MyAgo.DebugDir,

            "separator"                 : Separator,
            "module_tool_definitions"   : ToolsDef,

            "shell_command_code"        : list(self._SHELL_CMD_[self._Platform].keys()),
            "shell_command"             : list(self._SHELL_CMD_[self._Platform].values()),

            "create_directory_command"  : self.GetCreateDirectoryCommand(self.IntermediateDirectoryList),
            "custom_makefile_content"   : CustomMakefile
        }

        return MakefileTemplateDict

## PlatformMakefile class
#
#  This class encapsules makefie and its generation for platform. It uses
# template to generate the content of makefile. The content of makefile will be
# got from PlatformAutoGen object.
#
class PlatformMakefile(BuildFile):
    ## template used to generate the makefile for platform
    _TEMPLATE_ = TemplateString('''\
${makefile_header}

#
# Platform Macro Definition
#
PLATFORM_NAME = ${platform_name}
PLATFORM_GUID = ${platform_guid}
PLATFORM_VERSION = ${platform_version}
PLATFORM_FILE = ${platform_file}
PLATFORM_DIR = ${platform_dir}
PLATFORM_OUTPUT_DIR = ${platform_output_directory}

#
# Build Configuration Macro Definition
#
TOOLCHAIN = ${toolchain_tag}
TOOLCHAIN_TAG = ${toolchain_tag}
TARGET = ${build_target}

#
# Build Directory Macro Definition
#
BUILD_DIR = ${platform_build_directory}
FV_DIR = ${platform_build_directory}${separator}FV

#
# Shell Command Macro
#
${BEGIN}${shell_command_code} = ${shell_command}
${END}

MAKE = ${make_path}
MAKE_FILE = ${makefile_path}

#
# Default target
#
all: init build_libraries build_modules

#
# Initialization target: print build information and create necessary directories
#
init:
\t-@echo Building ... $(PLATFORM_FILE) [${build_architecture_list}]
\t${BEGIN}-@${create_directory_command}
\t${END}
#
# library build target
#
libraries: init build_libraries

#
# module build target
#
modules: init build_libraries build_modules

#
# Build all libraries:
#
build_libraries:
${BEGIN}\t@"$(MAKE)" $(MAKE_FLAGS) -f ${library_makefile_list} pbuild
${END}\t@cd $(BUILD_DIR)

#
# Build all modules:
#
build_modules:
${BEGIN}\t@"$(MAKE)" $(MAKE_FLAGS) -f ${module_makefile_list} pbuild
${END}\t@cd $(BUILD_DIR)

#
# Clean intermediate files
#
clean:
\t${BEGIN}-@${library_build_command} clean
\t${END}${BEGIN}-@${module_build_command} clean
\t${END}@cd $(BUILD_DIR)

#
# Clean all generated files except to makefile
#
cleanall:
${BEGIN}\t${cleanall_command}
${END}

#
# Clean all library files
#
cleanlib:
\t${BEGIN}-@${library_build_command} cleanall
\t${END}@cd $(BUILD_DIR)\n
''')

    ## Constructor of PlatformMakefile
    #
    #   @param  ModuleAutoGen   Object of PlatformAutoGen class
    #
    def __init__(self, PlatformAutoGen):
        BuildFile.__init__(self, PlatformAutoGen)
        self.ModuleBuildCommandList = []
        self.ModuleMakefileList = []
        self.IntermediateDirectoryList = []
        self.ModuleBuildDirectoryList = []
        self.LibraryBuildDirectoryList = []
        self.LibraryMakeCommandList = []
        self.DependencyHeaderFileSet = set()

    # Compose a dict object containing information used to do replacement in template
    @property
    def _TemplateDict(self):
        Separator = self._SEP_[self._Platform]

        MyAgo = self._AutoGenObject
        if "MAKE" not in MyAgo.ToolDefinition or "PATH" not in MyAgo.ToolDefinition["MAKE"]:
            EdkLogger.error("build", OPTION_MISSING, "No MAKE command defined. Please check your tools_def.txt!",
                            ExtraData="[%s]" % str(MyAgo))

        self.IntermediateDirectoryList = ["$(BUILD_DIR)"]
        self.ModuleBuildDirectoryList = self.GetModuleBuildDirectoryList()
        self.LibraryBuildDirectoryList = self.GetLibraryBuildDirectoryList()

        MakefileName = self.getMakefileName()
        LibraryMakefileList = []
        LibraryMakeCommandList = []
        for D in self.LibraryBuildDirectoryList:
            D = self.PlaceMacro(D, {"BUILD_DIR":MyAgo.BuildDir})
            Makefile = os.path.join(D, MakefileName)
            Command = self._MAKE_TEMPLATE_[self._Platform] % {"file":Makefile}
            LibraryMakefileList.append(Makefile)
            LibraryMakeCommandList.append(Command)
        self.LibraryMakeCommandList = LibraryMakeCommandList

        ModuleMakefileList = []
        ModuleMakeCommandList = []
        for D in self.ModuleBuildDirectoryList:
            D = self.PlaceMacro(D, {"BUILD_DIR":MyAgo.BuildDir})
            Makefile = os.path.join(D, MakefileName)
            Command = self._MAKE_TEMPLATE_[self._Platform] % {"file":Makefile}
            ModuleMakefileList.append(Makefile)
            ModuleMakeCommandList.append(Command)

        MakefileTemplateDict = {
            "makefile_header"           : self._FILE_HEADER_[self._FileType],
            "makefile_path"             : os.path.join("$(BUILD_DIR)", MakefileName),
            "make_path"                 : MyAgo.ToolDefinition["MAKE"]["PATH"],
            "makefile_name"             : MakefileName,
            "platform_name"             : MyAgo.Name,
            "platform_guid"             : MyAgo.Guid,
            "platform_version"          : MyAgo.Version,
            "platform_file"             : MyAgo.MetaFile,
            "platform_relative_directory": MyAgo.SourceDir,
            "platform_output_directory" : MyAgo.OutputDir,
            "platform_build_directory"  : MyAgo.BuildDir,
            "platform_dir"              : MyAgo.Macros["PLATFORM_DIR"],

            "toolchain_tag"             : MyAgo.ToolChain,
            "build_target"              : MyAgo.BuildTarget,
            "shell_command_code"        : list(self._SHELL_CMD_[self._Platform].keys()),
            "shell_command"             : list(self._SHELL_CMD_[self._Platform].values()),
            "build_architecture_list"   : MyAgo.Arch,
            "architecture"              : MyAgo.Arch,
            "separator"                 : Separator,
            "create_directory_command"  : self.GetCreateDirectoryCommand(self.IntermediateDirectoryList),
            "cleanall_command"          : self.GetRemoveDirectoryCommand(self.IntermediateDirectoryList),
            "library_makefile_list"     : LibraryMakefileList,
            "module_makefile_list"      : ModuleMakefileList,
            "library_build_command"     : LibraryMakeCommandList,
            "module_build_command"      : ModuleMakeCommandList,
        }

        return MakefileTemplateDict

    ## Get the root directory list for intermediate files of all modules build
    #
    #   @retval     list    The list of directory
    #
    def GetModuleBuildDirectoryList(self):
        DirList = []
        for ModuleAutoGen in self._AutoGenObject.ModuleAutoGenList:
            if not ModuleAutoGen.IsBinaryModule:
                DirList.append(os.path.join(self._AutoGenObject.BuildDir, ModuleAutoGen.BuildDir))
        return DirList

    ## Get the root directory list for intermediate files of all libraries build
    #
    #   @retval     list    The list of directory
    #
    def GetLibraryBuildDirectoryList(self):
        DirList = []
        for LibraryAutoGen in self._AutoGenObject.LibraryAutoGenList:
            if not LibraryAutoGen.IsBinaryModule:
                DirList.append(os.path.join(self._AutoGenObject.BuildDir, LibraryAutoGen.BuildDir))
        return DirList

## TopLevelMakefile class
#
#  This class encapsules makefie and its generation for entrance makefile. It
# uses template to generate the content of makefile. The content of makefile
# will be got from WorkspaceAutoGen object.
#
class TopLevelMakefile(BuildFile):
    ## template used to generate toplevel makefile
    _TEMPLATE_ = TemplateString('''${BEGIN}\tGenFds -f ${fdf_file} --conf=${conf_directory} -o ${platform_build_directory} -t ${toolchain_tag} -b ${build_target} -p ${active_platform} -a ${build_architecture_list} ${extra_options}${END}${BEGIN} -r ${fd} ${END}${BEGIN} -i ${fv} ${END}${BEGIN} -C ${cap} ${END}${BEGIN} -D ${macro} ${END}''')

    ## Constructor of TopLevelMakefile
    #
    #   @param  Workspace   Object of WorkspaceAutoGen class
    #
    def __init__(self, Workspace):
        BuildFile.__init__(self, Workspace)
        self.IntermediateDirectoryList = []
        self.DependencyHeaderFileSet = set()

    # Compose a dict object containing information used to do replacement in template
    @property
    def _TemplateDict(self):
        Separator = self._SEP_[self._Platform]

        # any platform autogen object is ok because we just need common information
        MyAgo = self._AutoGenObject

        if "MAKE" not in MyAgo.ToolDefinition or "PATH" not in MyAgo.ToolDefinition["MAKE"]:
            EdkLogger.error("build", OPTION_MISSING, "No MAKE command defined. Please check your tools_def.txt!",
                            ExtraData="[%s]" % str(MyAgo))

        for Arch in MyAgo.ArchList:
            self.IntermediateDirectoryList.append(Separator.join(["$(BUILD_DIR)", Arch]))
        self.IntermediateDirectoryList.append("$(FV_DIR)")

        # TRICK: for not generating GenFds call in makefile if no FDF file
        MacroList = []
        if MyAgo.FdfFile is not None and MyAgo.FdfFile != "":
            FdfFileList = [MyAgo.FdfFile]
            # macros passed to GenFds
            MacroDict = {}
            MacroDict.update(GlobalData.gGlobalDefines)
            MacroDict.update(GlobalData.gCommandLineDefines)
            for MacroName in MacroDict:
                if MacroDict[MacroName] != "":
                    MacroList.append('"%s=%s"' % (MacroName, MacroDict[MacroName].replace('\\', '\\\\')))
                else:
                    MacroList.append('"%s"' % MacroName)
        else:
            FdfFileList = []

        # pass extra common options to external program called in makefile, currently GenFds.exe
        ExtraOption = ''
        LogLevel = EdkLogger.GetLevel()
        if LogLevel == EdkLogger.VERBOSE:
            ExtraOption += " -v"
        elif LogLevel <= EdkLogger.DEBUG_9:
            ExtraOption += " -d %d" % (LogLevel - 1)
        elif LogLevel == EdkLogger.QUIET:
            ExtraOption += " -q"

        if GlobalData.gCaseInsensitive:
            ExtraOption += " -c"
        if not GlobalData.gEnableGenfdsMultiThread:
            ExtraOption += " --no-genfds-multi-thread"
        if GlobalData.gIgnoreSource:
            ExtraOption += " --ignore-sources"

        for pcd in GlobalData.BuildOptionPcd:
            if pcd[2]:
                pcdname = '.'.join(pcd[0:3])
            else:
                pcdname = '.'.join(pcd[0:2])
            if pcd[3].startswith('{'):
                ExtraOption += " --pcd " + pcdname + '=' + 'H' + '"' + pcd[3] + '"'
            else:
                ExtraOption += " --pcd " + pcdname + '=' + pcd[3]

        MakefileName = self.getMakefileName()
        SubBuildCommandList = []
        for A in MyAgo.ArchList:
            Command = self._MAKE_TEMPLATE_[self._Platform] % {"file":os.path.join("$(BUILD_DIR)", A, MakefileName)}
            SubBuildCommandList.append(Command)

        MakefileTemplateDict = {
            "makefile_header"           : self._FILE_HEADER_[self._FileType],
            "makefile_path"             : os.path.join("$(BUILD_DIR)", MakefileName),
            "make_path"                 : MyAgo.ToolDefinition["MAKE"]["PATH"],
            "platform_name"             : MyAgo.Name,
            "platform_guid"             : MyAgo.Guid,
            "platform_version"          : MyAgo.Version,
            "platform_build_directory"  : MyAgo.BuildDir,
            "conf_directory"            : GlobalData.gConfDirectory,

            "toolchain_tag"             : MyAgo.ToolChain,
            "build_target"              : MyAgo.BuildTarget,
            "shell_command_code"        : list(self._SHELL_CMD_[self._Platform].keys()),
            "shell_command"             : list(self._SHELL_CMD_[self._Platform].values()),
            'arch'                      : list(MyAgo.ArchList),
            "build_architecture_list"   : ','.join(MyAgo.ArchList),
            "separator"                 : Separator,
            "create_directory_command"  : self.GetCreateDirectoryCommand(self.IntermediateDirectoryList),
            "cleanall_command"          : self.GetRemoveDirectoryCommand(self.IntermediateDirectoryList),
            "sub_build_command"         : SubBuildCommandList,
            "fdf_file"                  : FdfFileList,
            "active_platform"           : str(MyAgo),
            "fd"                        : MyAgo.FdTargetList,
            "fv"                        : MyAgo.FvTargetList,
            "cap"                       : MyAgo.CapTargetList,
            "extra_options"             : ExtraOption,
            "macro"                     : MacroList,
        }

        return MakefileTemplateDict

    ## Get the root directory list for intermediate files of all modules build
    #
    #   @retval     list    The list of directory
    #
    def GetModuleBuildDirectoryList(self):
        DirList = []
        for ModuleAutoGen in self._AutoGenObject.ModuleAutoGenList:
            if not ModuleAutoGen.IsBinaryModule:
                DirList.append(os.path.join(self._AutoGenObject.BuildDir, ModuleAutoGen.BuildDir))
        return DirList

    ## Get the root directory list for intermediate files of all libraries build
    #
    #   @retval     list    The list of directory
    #
    def GetLibraryBuildDirectoryList(self):
        DirList = []
        for LibraryAutoGen in self._AutoGenObject.LibraryAutoGenList:
            if not LibraryAutoGen.IsBinaryModule:
                DirList.append(os.path.join(self._AutoGenObject.BuildDir, LibraryAutoGen.BuildDir))
        return DirList

## Find dependencies for one source file
#
#  By searching recursively "#include" directive in file, find out all the
#  files needed by given source file. The dependencies will be only searched
#  in given search path list.
#
#   @param      File            The source file
#   @param      ForceInculeList The list of files which will be included forcely
#   @param      SearchPathList  The list of search path
#
#   @retval     list            The list of files the given source file depends on
#
def GetDependencyList(AutoGenObject, FileCache, File, ForceList, SearchPathList):
    EdkLogger.debug(EdkLogger.DEBUG_1, "Try to get dependency files for %s" % File)
    FileStack = [File] + ForceList
    DependencySet = set()

    if AutoGenObject.Arch not in gDependencyDatabase:
        gDependencyDatabase[AutoGenObject.Arch] = {}
    DepDb = gDependencyDatabase[AutoGenObject.Arch]

    while len(FileStack) > 0:
        F = FileStack.pop()

        FullPathDependList = []
        if F in FileCache:
            for CacheFile in FileCache[F]:
                FullPathDependList.append(CacheFile)
                if CacheFile not in DependencySet:
                    FileStack.append(CacheFile)
            DependencySet.update(FullPathDependList)
            continue

        CurrentFileDependencyList = []
        if F in DepDb:
            CurrentFileDependencyList = DepDb[F]
        else:
            try:
                Fd = open(F.Path, 'rb')
                FileContent = Fd.read()
                Fd.close()
            except BaseException as X:
                EdkLogger.error("build", FILE_OPEN_FAILURE, ExtraData=F.Path + "\n\t" + str(X))
            if len(FileContent) == 0:
                continue
            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
            IncludedFileList = gIncludePattern.findall(FileContent)

            for Inc in IncludedFileList:
                Inc = Inc.strip()
                # if there's macro used to reference header file, expand it
                HeaderList = gMacroPattern.findall(Inc)
                if len(HeaderList) == 1 and len(HeaderList[0]) == 2:
                    HeaderType = HeaderList[0][0]
                    HeaderKey = HeaderList[0][1]
                    if HeaderType in gIncludeMacroConversion:
                        Inc = gIncludeMacroConversion[HeaderType] % {"HeaderKey" : HeaderKey}
                    else:
                        # not known macro used in #include, always build the file by
                        # returning a empty dependency
                        FileCache[File] = []
                        return []
                Inc = os.path.normpath(Inc)
                CurrentFileDependencyList.append(Inc)
            DepDb[F] = CurrentFileDependencyList

        CurrentFilePath = F.Dir
        PathList = [CurrentFilePath] + SearchPathList
        for Inc in CurrentFileDependencyList:
            for SearchPath in PathList:
                FilePath = os.path.join(SearchPath, Inc)
                if FilePath in gIsFileMap:
                    if not gIsFileMap[FilePath]:
                        continue
                # If isfile is called too many times, the performance is slow down.
                elif not os.path.isfile(FilePath):
                    gIsFileMap[FilePath] = False
                    continue
                else:
                    gIsFileMap[FilePath] = True
                FilePath = PathClass(FilePath)
                FullPathDependList.append(FilePath)
                if FilePath not in DependencySet:
                    FileStack.append(FilePath)
                break
            else:
                EdkLogger.debug(EdkLogger.DEBUG_9, "%s included by %s was not found "\
                                "in any given path:\n\t%s" % (Inc, F, "\n\t".join(SearchPathList)))

        FileCache[F] = FullPathDependList
        DependencySet.update(FullPathDependList)

    DependencySet.update(ForceList)
    if File in DependencySet:
        DependencySet.remove(File)
    DependencyList = list(DependencySet)  # remove duplicate ones

    return DependencyList

# This acts like the main() function for the script, unless it is 'import'ed into another script.
if __name__ == '__main__':
    pass
