diff --git a/.gitmodules b/.gitmodules index 6f4b19310f..8186bf1de4 100644 --- a/.gitmodules +++ b/.gitmodules @@ -16,7 +16,7 @@ [submodule "BaseTools/Source/C/BrotliCompress/brotli"] path = BaseTools/Source/C/BrotliCompress/brotli url = https://github.com/google/brotli - ignore = untracked + ignore = untracked [submodule "RedfishPkg/Library/JsonLib/jansson"] path = RedfishPkg/Library/JsonLib/jansson url = https://github.com/akheron/jansson @@ -26,15 +26,18 @@ [submodule "UnitTestFrameworkPkg/Library/SubhookLib/subhook"] path = UnitTestFrameworkPkg/Library/SubhookLib/subhook url = https://github.com/Zeex/subhook.git -[submodule "MdePkg/Library/BaseFdtLib/libfdt"] - path = MdePkg/Library/BaseFdtLib/libfdt - url = https://github.com/devicetree-org/pylibfdt.git +[submodule "MdePkg/Library/BaseFdtLib/libfdt"] + path = MdePkg/Library/BaseFdtLib/libfdt + url = https://github.com/devicetree-org/pylibfdt.git [submodule "MdePkg/Library/MipiSysTLib/mipisyst"] path = MdePkg/Library/MipiSysTLib/mipisyst url = https://github.com/MIPI-Alliance/public-mipi-sys-t.git [submodule "CryptoPkg/Library/MbedTlsLib/mbedtls"] path = CryptoPkg/Library/MbedTlsLib/mbedtls url = https://github.com/ARMmbed/mbedtls -[submodule "SecurityPkg/DeviceSecurity/SpdmLib/libspdm"] - path = SecurityPkg/DeviceSecurity/SpdmLib/libspdm - url = https://github.com/DMTF/libspdm.git +[submodule "SecurityPkg/DeviceSecurity/SpdmLib/libspdm"] + path = SecurityPkg/DeviceSecurity/SpdmLib/libspdm + url = https://github.com/DMTF/libspdm.git +[submodule "OpenCorePkg"] + path = OpenCorePkg + url = https://github.com/acidanthera/OpenCorePkg.git diff --git a/.pytool/Plugin/SpellCheck/cspell.base.yaml b/.pytool/Plugin/SpellCheck/cspell.base.yaml index 92e65ec6f6..4c471aab19 100644 --- a/.pytool/Plugin/SpellCheck/cspell.base.yaml +++ b/.pytool/Plugin/SpellCheck/cspell.base.yaml @@ -106,7 +106,6 @@ "Trustzone", "Fastboot", "framebuffer", - "genfw", "TTYTERM", "miniport", "LFENCE", diff --git a/ArmVirtPkg/ArmVirt.dsc.inc b/ArmVirtPkg/ArmVirt.dsc.inc index f07a6edada..ce3941b787 100644 --- a/ArmVirtPkg/ArmVirt.dsc.inc +++ b/ArmVirtPkg/ArmVirt.dsc.inc @@ -26,12 +26,9 @@ DEFINE FD_NUM_BLOCKS = 0x300 !endif -[BuildOptions.common.EDKII.DXE_CORE,BuildOptions.common.EDKII.DXE_DRIVER,BuildOptions.common.EDKII.UEFI_DRIVER,BuildOptions.common.EDKII.UEFI_APPLICATION] - GCC:*_*_*_DLINK_FLAGS = -z common-page-size=0x1000 - [BuildOptions.common.EDKII.DXE_RUNTIME_DRIVER] - GCC:*_*_ARM_DLINK_FLAGS = -z common-page-size=0x1000 - GCC:*_*_AARCH64_DLINK_FLAGS = -z common-page-size=0x10000 + GCC:*_*_ARM_DLINK_FLAGS = -z max-page-size=0x1000 + GCC:*_*_AARCH64_DLINK_FLAGS = -z max-page-size=0x10000 [LibraryClasses.common] !if $(TARGET) == RELEASE diff --git a/BaseTools/.gitignore b/BaseTools/.gitignore index ec9c69f8b2..7bb6eea44b 100644 --- a/BaseTools/.gitignore +++ b/BaseTools/.gitignore @@ -18,4 +18,8 @@ Source/C/bin/ Source/C/libs/ Bin/Win32 Lib -BaseToolsBuild/ \ No newline at end of file +BaseToolsBuild/ +ImageTool/ImageTool +ImageTool/ImageTool32 +ImageTool/ImageTool64 +MicroTool/MicroTool diff --git a/BaseTools/BinWrappers/PosixLike/ImageTool b/BaseTools/BinWrappers/PosixLike/ImageTool new file mode 100755 index 0000000000..7c6a21ce99 --- /dev/null +++ b/BaseTools/BinWrappers/PosixLike/ImageTool @@ -0,0 +1,25 @@ +#!/usr/bin/env bash +# +# Copyright (c) 2022, Mikhail Krichanov. All rights reserved. +# SPDX-License-Identifier: BSD-3-Clause +# +full_cmd=${BASH_SOURCE:-$0} # see http://mywiki.wooledge.org/BashFAQ/028 for a discussion of why $0 is not a good choice here +dir=$(dirname "$full_cmd") +cmd=${full_cmd##*/} + +if [ -n "$WORKSPACE" ] && [ -e "$EDK_TOOLS_PATH/ImageTool" ] +then + if [ ! -e "$EDK_TOOLS_PATH/ImageTool/ImageTool" ] + then + echo "BaseTools C Tool binary was not found (ImageTool)" + echo "You may need to run:" + echo " make -C $EDK_TOOLS_PATH/ImageTool" + else + exec "$EDK_TOOLS_PATH/ImageTool/ImageTool" "$@" + fi +else + echo "Unable to find the real '$cmd' to run" + echo "This message was printed by" + echo " $0" + exit 127 +fi diff --git a/BaseTools/BinWrappers/PosixLike/MicroTool b/BaseTools/BinWrappers/PosixLike/MicroTool new file mode 100644 index 0000000000..0e22e2775d --- /dev/null +++ b/BaseTools/BinWrappers/PosixLike/MicroTool @@ -0,0 +1,25 @@ +#!/usr/bin/env bash +# +# Copyright (c) 2022, Mikhail Krichanov. All rights reserved. +# SPDX-License-Identifier: BSD-3-Clause +# +full_cmd=${BASH_SOURCE:-$0} # see http://mywiki.wooledge.org/BashFAQ/028 for a discussion of why $0 is not a good choice here +dir=$(dirname "$full_cmd") +cmd=${full_cmd##*/} + +if [ -n "$WORKSPACE" ] && [ -e "$EDK_TOOLS_PATH/MicroTool" ] +then + if [ ! -e "$EDK_TOOLS_PATH/MicroTool/MicroTool" ] + then + echo "BaseTools C Tool binary was not found (MicroTool)" + echo "You may need to run:" + echo " make -C $EDK_TOOLS_PATH/MicroTool" + else + exec "$EDK_TOOLS_PATH/MicroTool/MicroTool" "$@" + fi +else + echo "Unable to find the real '$cmd' to run" + echo "This message was printed by" + echo " $0" + exit 127 +fi diff --git a/BaseTools/BinWrappers/WindowsLike/ImageTool.bat b/BaseTools/BinWrappers/WindowsLike/ImageTool.bat new file mode 100644 index 0000000000..7e9d81741b --- /dev/null +++ b/BaseTools/BinWrappers/WindowsLike/ImageTool.bat @@ -0,0 +1,6 @@ +:: +:: Copyright (c) 2022, Mikhail Krichanov. All rights reserved. +:: SPDX-License-Identifier: BSD-3-Clause +:: +@echo off +call ImageTool.exe %* diff --git a/BaseTools/BinWrappers/WindowsLike/MicroTool.bat b/BaseTools/BinWrappers/WindowsLike/MicroTool.bat new file mode 100644 index 0000000000..ad8515c577 --- /dev/null +++ b/BaseTools/BinWrappers/WindowsLike/MicroTool.bat @@ -0,0 +1,6 @@ +:: +:: Copyright (c) 2022, Mikhail Krichanov. All rights reserved. +:: SPDX-License-Identifier: BSD-3-Clause +:: +@echo off +call MicroTool.exe %* diff --git a/BaseTools/Conf/build_rule.template b/BaseTools/Conf/build_rule.template index c523ed64e3..1428ad3588 100755 --- a/BaseTools/Conf/build_rule.template +++ b/BaseTools/Conf/build_rule.template @@ -272,7 +272,14 @@ $(RM) ${dst} "$(SLINK)" cr ${dst} $(SLINK_FLAGS) @$(OBJECT_FILES_LIST) - + + + "$(SLINK)" $(SLINK_FLAGS) ${dst} --via $(OBJECT_FILES_LIST) + + + # $(OBJECT_FILES_LIST) has wrong paths for cygwin + "$(SLINK)" $(SLINK_FLAGS) ${dst} $(OBJECT_FILES) + "$(SLINK)" $(SLINK_FLAGS) ${dst} -filelist $(OBJECT_FILES_LIST) @@ -295,12 +302,11 @@ "$(DLINK)" -o ${dst} $(DLINK_FLAGS) -Wl,--start-group,@$(STATIC_LIBRARY_FILES_LIST),--end-group $(CC_FLAGS) $(DLINK2_FLAGS) - "$(OBJCOPY)" $(OBJCOPY_FLAGS) ${dst} "$(DLINK)" $(DLINK_FLAGS) -o ${dst} $(DLINK_SPATH) -filelist $(STATIC_LIBRARY_FILES_LIST) $(DLINK2_FLAGS) - - + + [Static-Library-File.SEC.AARCH64, Static-Library-File.PEI_CORE.AARCH64, Static-Library-File.PEIM.AARCH64,Static-Library-File.SEC.ARM, Static-Library-File.PEI_CORE.ARM, Static-Library-File.PEIM.ARM] *.lib @@ -313,8 +319,6 @@ "$(DLINK)" -o ${dst} $(DLINK_FLAGS) $(DLINK_XIPFLAGS) -Wl,--start-group,@$(STATIC_LIBRARY_FILES_LIST),--end-group $(CC_FLAGS) $(CC_XIPFLAGS) $(DLINK2_FLAGS) - "$(OBJCOPY)" $(OBJCOPY_FLAGS) ${dst} - [Static-Library-File.USER_DEFINED, Static-Library-File.HOST_APPLICATION] @@ -334,8 +338,8 @@ "$(DLINK)" -o ${dst} $(DLINK_FLAGS) $(DLINK_SPATH) -filelist $(STATIC_LIBRARY_FILES_LIST) $(DLINK2_FLAGS) - - + + [Dynamic-Library-File] ?.dll @@ -345,32 +349,67 @@ $(OUTPUT_DIR)(+)$(MODULE_NAME).map - "$(GENFW)" -e $(MODULE_TYPE) -o ${dst} ${src} $(GENFW_FLAGS) + ImageTool GenImage -c PE -t $(MODULE_TYPE) -o ${dst} ${src} $(CP) ${dst} $(DEBUG_DIR) $(CP) ${dst} $(BIN_DIR)(+)$(MODULE_NAME_GUID).efi -$(CP) $(DEBUG_DIR)(+)*.map $(OUTPUT_DIR) - -$(CP) $(DEBUG_DIR)(+)*.pdb $(OUTPUT_DIR) - - $(CP) ${src} $(DEBUG_DIR)(+)$(MODULE_NAME).debug - "$(OBJCOPY)" $(OBJCOPY_STRIPFLAG) ${src} + -$(CP) $(DEBUG_DIR)(+)*.pdb $(OUTPUT_DIR) - # - #The below 2 lines are only needed for UNIXGCC tool chain, which generates PE image directly - # - -"$(OBJCOPY)" $(OBJCOPY_ADDDEBUGFLAG) ${src} - -$(CP) $(DEBUG_DIR)(+)$(MODULE_NAME).debug $(BIN_DIR)(+)$(MODULE_NAME_GUID).debug + + $(CP) ${src} $(DEBUG_DIR)(+)$(MODULE_NAME).strip + $(OBJCOPY) $(OBJCOPY_STRIPFLAG) $(DEBUG_DIR)(+)$(MODULE_NAME).strip + + ImageTool GenImage -c PE -t $(MODULE_TYPE) -o ${dst} $(DEBUG_DIR)(+)$(MODULE_NAME).strip - "$(GENFW)" -e $(MODULE_TYPE) -o ${dst} ${src} $(GENFW_FLAGS) $(CP) ${dst} $(DEBUG_DIR) $(CP) ${dst} $(BIN_DIR)(+)$(MODULE_NAME_GUID).efi -$(CP) $(DEBUG_DIR)(+)*.map $(OUTPUT_DIR) - + # tool to convert Mach-O to PE/COFF "$(MTOC)" -subsystem $(MODULE_TYPE) $(MTOC_FLAGS) ${src} $(DEBUG_DIR)(+)$(MODULE_NAME).pecoff # create symbol file for GDB debug -$(DSYMUTIL) ${src} - "$(GENFW)" -e $(MODULE_TYPE) -o ${dst} $(DEBUG_DIR)(+)$(MODULE_NAME).pecoff $(GENFW_FLAGS) + ImageTool GenImage -c PE -t $(MODULE_TYPE) -o ${dst} $(DEBUG_DIR)(+)$(MODULE_NAME).pecoff + $(CP) ${dst} $(DEBUG_DIR) + $(CP) ${dst} $(BIN_DIR)(+)$(MODULE_NAME_GUID).efi + -$(CP) $(DEBUG_DIR)(+)*.map $(OUTPUT_DIR) + +[Dynamic-Library-File.UEFI_HII] + + ?.dll + + + $(OUTPUT_DIR)(+)$(MODULE_NAME).efi + $(DEBUG_DIR)(+)$(MODULE_NAME).efi + $(OUTPUT_DIR)(+)$(MODULE_NAME).map + + + $(OUTPUT_DIR)(+)$(MODULE_NAME)hii.rc + + + ImageTool GenImage -c PE -t $(MODULE_TYPE) -h $(OUTPUT_DIR)(+)$(MODULE_NAME)hii.rc -o ${dst} ${src} + $(CP) ${dst} $(DEBUG_DIR) + $(CP) ${dst} $(BIN_DIR)(+)$(MODULE_NAME_GUID).efi + -$(CP) $(DEBUG_DIR)(+)*.map $(OUTPUT_DIR) + -$(CP) $(DEBUG_DIR)(+)*.pdb $(OUTPUT_DIR) + + + $(CP) ${src} $(DEBUG_DIR)(+)$(MODULE_NAME).strip + $(OBJCOPY) $(OBJCOPY_STRIPFLAG) $(DEBUG_DIR)(+)$(MODULE_NAME).strip + + ImageTool GenImage -c PE -t $(MODULE_TYPE) -h $(OUTPUT_DIR)(+)$(MODULE_NAME)hii.rc -o ${dst} $(DEBUG_DIR)(+)$(MODULE_NAME).strip + + $(CP) ${dst} $(DEBUG_DIR) + $(CP) ${dst} $(BIN_DIR)(+)$(MODULE_NAME_GUID).efi + -$(CP) $(DEBUG_DIR)(+)*.map $(OUTPUT_DIR) + + + # tool to convert Mach-O to PE/COFF + "$(MTOC)" -subsystem $(MODULE_TYPE) $(MTOC_FLAGS) ${src} $(DEBUG_DIR)(+)$(MODULE_NAME).pecoff + # create symbol file for GDB debug + -$(DSYMUTIL) ${src} + ImageTool GenImage -c PE -t $(MODULE_TYPE) -h $(OUTPUT_DIR)(+)$(MODULE_NAME)hii.rc -o ${dst} $(DEBUG_DIR)(+)$(MODULE_NAME).pecoff $(CP) ${dst} $(DEBUG_DIR) $(CP) ${dst} $(BIN_DIR)(+)$(MODULE_NAME_GUID).efi -$(CP) $(DEBUG_DIR)(+)*.map $(OUTPUT_DIR) @@ -404,14 +443,14 @@ Trim --asl-file --asl-deps -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.i -i $(INC_LIST) ${src} "$(ASLPP)" $(DEPS_FLAGS) $(ASLPP_FLAGS) $(INC) /I${s_path} $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.i > $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.iii - Trim --source-code -l -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.iiii $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.iii + Trim --source-code -l -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.iiii $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.iii "$(ASL)" $(ASL_FLAGS) $(ASL_OUTFLAGS)${dst} $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.iiii $(CP) $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.aml $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.amli Trim --asl-file --asl-deps -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.i -i $(INC_LIST) ${src} "$(ASLPP)" $(DEPS_FLAGS) $(ASLPP_FLAGS) $(INC) -I${s_path} $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.i > $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.iii - Trim --source-code -l -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.iiii $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.iii + Trim --source-code -l -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.iiii $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.iii "$(ASL)" $(ASL_FLAGS) $(ASL_OUTFLAGS)${dst} $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.iiii $(CP) $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.aml $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.amli @@ -438,12 +477,12 @@ "$(ASLCC)" $(DEPS_FLAGS) /Fo$(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj $(ASLCC_FLAGS) $(DEPS_FLAGS) $(INC) ${src} "$(ASLDLINK)" /OUT:$(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(ASLDLINK_FLAGS) $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj - "$(GENFW)" -o ${dst} -c $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(GENFW_FLAGS) + ImageTool GetAcpi -o ${dst} $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll "$(ASLCC)" $(DEPS_FLAGS) -c -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj $(CC_FLAGS) $(ASLCC_FLAGS) $(DEPS_FLAGS) $(INC) ${src} "$(ASLDLINK)" -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(ASLDLINK_FLAGS) $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj - "$(GENFW)" -o ${dst} -c $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(GENFW_FLAGS) + ImageTool GetAcpi -o ${dst} $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll [Acpi-Table-Code-File] @@ -458,25 +497,24 @@ "$(ASLCC)" $(DEPS_FLAGS) /Fo$(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj $(ASLCC_FLAGS) $(DEPS_FLAGS) $(INC) ${src} "$(ASLDLINK)" /OUT:$(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(ASLDLINK_FLAGS) $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj - "$(GENFW)" -o ${dst} -c $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(GENFW_FLAGS) + ImageTool GetAcpi -o ${dst} $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll "$(ASLCC)" $(DEPS_FLAGS) -c -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj $(CC_FLAGS) $(ASLCC_FLAGS) $(DEPS_FLAGS) $(INC) ${src} - "$(ASLDLINK)" -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(ASLDLINK_FLAGS) $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj - "$(GENFW)" -o ${dst} -c $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(GENFW_FLAGS) + "$(ASLDLINK)" -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(ASLDLINK_FLAGS) $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj $(CC_FLAGS) $(ASLCC_FLAGS) + ImageTool GetAcpi -o ${dst} $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll "$(ASLCC)" $(DEPS_FLAGS) -c -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj $(CC_FLAGS) $(ASLCC_FLAGS) $(DEPS_FLAGS) $(INC) ${src} "$(ASLDLINK)" /OUT:$(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(ASLDLINK_FLAGS) $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj - "$(GENFW)" -o ${dst} -c $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(GENFW_FLAGS) + ImageTool GetAcpi -o ${dst} $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll - + "$(ASLCC)" $(DEPS_FLAGS) -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj $(ASLCC_FLAGS) $(DEPS_FLAGS) $(INC) ${src} "$(ASLDLINK)" -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(ASLDLINK_FLAGS) $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj "$(MTOC)" -subsystem $(MODULE_TYPE) $(MTOC_FLAGS) $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.dll $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.pecoff - "$(GENFW)" -o ${dst} -c $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.pecoff $(GENFW_FLAGS) - - + ImageTool GetAcpi -o ${dst} $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.pecoff + [Masm16-Code-File] ?.asm16, ?.Asm16, ?.ASM16, ?.s16, ?.S16 @@ -501,7 +539,7 @@ Trim --source-code -o ${d_path}(+)${s_base}.iii ${d_path}(+)${s_base}.ii "$(ASM)" -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj $(ASM_FLAGS) $(INC) ${d_path}(+)${s_base}.iii "$(DLINK)" -o ${dst} $(DLINK_FLAGS) --start-group $(DLINK_SPATH) $(LIBS) $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj --end-group - + Trim --asm-file -o ${d_path}(+)${s_base}.i -i $(INC_LIST) ${src} "$(PP)" $(DEPS_FLAGS) $(PP_FLAGS) $(INC) ${src} > ${d_path}(+)${s_base}.ii @@ -509,7 +547,7 @@ "$(ASM)" -o $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj $(ASM_FLAGS) $(INC) ${d_path}(+)${s_base}.iii "$(SLINK)" $(SLINK_FLAGS) $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.slib $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.obj otool -t $(OUTPUT_DIR)(+)${s_dir}(+)${s_base}.slib | hex2bin.py ${dst} - + [Nasm-to-Binary-Code-File] @@ -537,7 +575,7 @@ $(OUTPUT_DIR)(+)${s_base}.mcb - "$(GENFW)" -o ${dst} -m ${src} $(GENFW_FLAGS) + MicroTool TxtToBin ${src} ${dst} [Microcode-Binary-File] @@ -550,7 +588,7 @@ $(OUTPUT_DIR)(+)$(MODULE_NAME).bin - "$(GENFW)" -o ${dst} -j $(MICROCODE_BINARY_FILES) $(GENFW_FLAGS) + MicroTool Merge ${dst} $(MICROCODE_BINARY_FILES) -$(CP) ${dst} $(BIN_DIR)(+)$(MODULE_NAME_GUID).bin [EFI-Image-File] @@ -633,19 +671,8 @@ *.hpk - - $(OUTPUT_DIR)(+)$(MODULE_NAME)hii.lib - - + $(OUTPUT_DIR)(+)$(MODULE_NAME)hii.rc - - "$(GENFW)" -o $(OUTPUT_DIR)(+)$(MODULE_NAME)hii.rc -g $(MODULE_GUID) --hiipackage $(HII_BINARY_PACKAGES) $(GENFW_FLAGS) - "$(RC)" /Fo${dst} $(OUTPUT_DIR)(+)$(MODULE_NAME)hii.rc - - - "$(GENFW)" -o $(OUTPUT_DIR)(+)$(MODULE_NAME)hii.rc -g $(MODULE_GUID) --hiibinpackage $(HII_BINARY_PACKAGES) $(GENFW_FLAGS) - "$(RC)" $(RC_FLAGS) $(OUTPUT_DIR)(+)$(MODULE_NAME)hii.rc ${dst} - - - "$(GENFW)" -o $(OUTPUT_DIR)(+)$(MODULE_NAME)hii.rc -g $(MODULE_GUID) --hiibinpackage $(HII_BINARY_PACKAGES) $(GENFW_FLAGS) + + ImageTool HiiBin $(MODULE_GUID) -o $(OUTPUT_DIR)(+)$(MODULE_NAME)hii.rc $(HII_BINARY_PACKAGES) diff --git a/BaseTools/Conf/tools_def.template b/BaseTools/Conf/tools_def.template index 54cf95dc0e..28c74c87db 100755 --- a/BaseTools/Conf/tools_def.template +++ b/BaseTools/Conf/tools_def.template @@ -25,6 +25,28 @@ IDENTIFIER = Default TOOL_CHAIN_CONF +!ifdef $(EDK2_MERGE_RODATA_INTO_TEXT) +DEFINE DLINK_SCRIPT = -Wl,--script=$(EDK_TOOLS_PATH)/Scripts/Merge.lds +DEFINE MSFT_MERGE = /MERGE:.rdata=.text +DEFINE XCODE_MERGE = -rename_section __DATA_CONST __text_const __TEXT __const -rename_section __DATA_CONST __cstring __TEXT __cstring -rename_section __DATA_CONST __ustring __TEXT __ustring -rename_section __DATA_CONST __const __TEXT __data_const +!else +DEFINE DLINK_SCRIPT = -Wl,--script=$(EDK_TOOLS_PATH)/Scripts/Base.lds +DEFINE MSFT_MERGE = +DEFINE XCODE_MERGE = +!endif + +!ifdef $(EDK2_REDUCE_FW_SIZE) +DEFINE GCC_ALIGN = -z max-page-size=0x20 +DEFINE MSFT_ALIGN = /ALIGN:32 /FILEALIGN:32 +DEFINE XCODE_ALIGN = 0x20 +DEFINE XCODE_ADDR = 0x400 +!else +DEFINE GCC_ALIGN = -z max-page-size=0x1000 +DEFINE MSFT_ALIGN = /ALIGN:4096 /FILEALIGN:4096 +DEFINE XCODE_ALIGN = 0x1000 +DEFINE XCODE_ADDR = 0x1000 +!endif + # common path macros DEFINE VS2015_BIN = ENV(VS2015_PREFIX)Vc\bin DEFINE VS2015_DLL = ENV(VS2015_PREFIX)Common7\IDE;DEF(VS2015_BIN) @@ -107,6 +129,7 @@ DEFINE MSFT_DEPS_FLAGS = /showIncludes DEFINE MSFT_ASLPP_FLAGS = /nologo /E /C /FIAutoGen.h DEFINE MSFT_ASLCC_FLAGS = /nologo /c /FIAutoGen.h /TC /Dmain=ReferenceAcpiTable DEFINE MSFT_ASLDLINK_FLAGS = /NODEFAULTLIB /ENTRY:ReferenceAcpiTable /SUBSYSTEM:CONSOLE +DEFINE MSFT_DLINK_COMMON = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER DEF(MSFT_ALIGN) DEF(MSFT_MERGE) DEFINE DTCPP_BIN = ENV(DTCPP_PREFIX)cpp DEFINE DTC_BIN = ENV(DTC_PREFIX)dtc @@ -271,7 +294,7 @@ DEFINE DTC_BIN = ENV(DTC_PREFIX)dtc *_VS2015_*_PP_FLAGS = /nologo /E /TC /FIAutoGen.h *_VS2015_*_VFRPP_FLAGS = /nologo /E /TC /DVFRCOMPILE /FI$(MODULE_NAME)StrDefs.h *_VS2015_*_DLINK2_FLAGS = -*_VS2015_*_DEPS_FLAGS = DEF(MSFT_DEPS_FLAGS) +*_VS2015_*_DEPS_FLAGS = DEF(MSFT_DEPS_FLAGS) *_VS2015_*_ASM16_PATH = DEF(VS2015_BIN)\ml.exe ################## @@ -308,13 +331,13 @@ NOOPT_VS2015_IA32_CC_FLAGS = /nologo /arch:IA32 /c /WX /GS- /W4 /Gs32768 RELEASE_VS2015_IA32_ASM_FLAGS = /nologo /c /WX /W3 /Cx /coff /Zd NOOPT_VS2015_IA32_ASM_FLAGS = /nologo /c /WX /W3 /Cx /coff /Zd /Zi - DEBUG_VS2015_IA32_NASM_FLAGS = -Ox -f win32 -g -RELEASE_VS2015_IA32_NASM_FLAGS = -Ox -f win32 -NOOPT_VS2015_IA32_NASM_FLAGS = -O0 -f win32 -g + DEBUG_VS2015_IA32_NASM_FLAGS = -Ox -f win32 -g -DRODATA_SECTION_NAME=.rdata +RELEASE_VS2015_IA32_NASM_FLAGS = -Ox -f win32 -DRODATA_SECTION_NAME=.rdata +NOOPT_VS2015_IA32_NASM_FLAGS = -O0 -f win32 -g -DRODATA_SECTION_NAME=.rdata - DEBUG_VS2015_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG -RELEASE_VS2015_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /MERGE:.rdata=.data -NOOPT_VS2015_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG + DEBUG_VS2015_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X86 /DEBUG +RELEASE_VS2015_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4254 /MACHINE:X86 +NOOPT_VS2015_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X86 /DEBUG ################## # X64 definitions @@ -338,15 +361,15 @@ NOOPT_VS2015_X64_CC_FLAGS = /nologo /c /WX /GS- /W4 /Gs32768 /D UNICODE /G DEBUG_VS2015_X64_ASM_FLAGS = /nologo /c /WX /W3 /Cx /Zd /Zi RELEASE_VS2015_X64_ASM_FLAGS = /nologo /c /WX /W3 /Cx /Zd -NOOPT_VS2015_X64_ASM_FLAGS = /nologo /c /WX /W3 /Cx /Zd /Zi +NOOPT_VS2015_X64_ASM_FLAGS = /nologo /c /WX /W3 /Cx /Zd /Zi - DEBUG_VS2015_X64_NASM_FLAGS = -Ox -f win64 -g -RELEASE_VS2015_X64_NASM_FLAGS = -Ox -f win64 -NOOPT_VS2015_X64_NASM_FLAGS = -O0 -f win64 -g + DEBUG_VS2015_X64_NASM_FLAGS = -Ox -f win64 -g -DRODATA_SECTION_NAME=.rdata +RELEASE_VS2015_X64_NASM_FLAGS = -Ox -f win64 -DRODATA_SECTION_NAME=.rdata +NOOPT_VS2015_X64_NASM_FLAGS = -O0 -f win64 -g -DRODATA_SECTION_NAME=.rdata - DEBUG_VS2015_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG -RELEASE_VS2015_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /MERGE:.rdata=.data -NOOPT_VS2015_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG + DEBUG_VS2015_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X64 /DEBUG +RELEASE_VS2015_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4254 /MACHINE:X64 +NOOPT_VS2015_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X64 /DEBUG #################################################################################### # VS2015x86 - Microsoft Visual Studio 2015 (x86) professional with Intel ASL @@ -401,13 +424,13 @@ NOOPT_VS2015x86_IA32_CC_FLAGS = /nologo /arch:IA32 /c /WX /GS- /W4 /Gs32768 RELEASE_VS2015x86_IA32_ASM_FLAGS = /nologo /c /WX /W3 /Cx /coff /Zd NOOPT_VS2015x86_IA32_ASM_FLAGS = /nologo /c /WX /W3 /Cx /coff /Zd /Zi - DEBUG_VS2015x86_IA32_NASM_FLAGS = -Ox -f win32 -g -RELEASE_VS2015x86_IA32_NASM_FLAGS = -Ox -f win32 -NOOPT_VS2015x86_IA32_NASM_FLAGS = -O0 -f win32 -g + DEBUG_VS2015x86_IA32_NASM_FLAGS = -Ox -f win32 -g -DRODATA_SECTION_NAME=.rdata +RELEASE_VS2015x86_IA32_NASM_FLAGS = -Ox -f win32 -DRODATA_SECTION_NAME=.rdata +NOOPT_VS2015x86_IA32_NASM_FLAGS = -O0 -f win32 -g -DRODATA_SECTION_NAME=.rdata - DEBUG_VS2015x86_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG -RELEASE_VS2015x86_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /MERGE:.rdata=.data -NOOPT_VS2015x86_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG + DEBUG_VS2015x86_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X86 /DEBUG +RELEASE_VS2015x86_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4254 /MACHINE:X86 +NOOPT_VS2015x86_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X86 /DEBUG ################## # X64 definitions @@ -433,13 +456,13 @@ NOOPT_VS2015x86_X64_CC_FLAGS = /nologo /c /WX /GS- /W4 /Gs32768 /D UNICODE RELEASE_VS2015x86_X64_ASM_FLAGS = /nologo /c /WX /W3 /Cx /Zd NOOPT_VS2015x86_X64_ASM_FLAGS = /nologo /c /WX /W3 /Cx /Zd /Zi - DEBUG_VS2015x86_X64_NASM_FLAGS = -Ox -f win64 -g -RELEASE_VS2015x86_X64_NASM_FLAGS = -Ox -f win64 -NOOPT_VS2015x86_X64_NASM_FLAGS = -O0 -f win64 -g + DEBUG_VS2015x86_X64_NASM_FLAGS = -Ox -f win64 -g -DRODATA_SECTION_NAME=.rdata +RELEASE_VS2015x86_X64_NASM_FLAGS = -Ox -f win64 -DRODATA_SECTION_NAME=.rdata +NOOPT_VS2015x86_X64_NASM_FLAGS = -O0 -f win64 -g -DRODATA_SECTION_NAME=.rdata - DEBUG_VS2015x86_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG -RELEASE_VS2015x86_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /MERGE:.rdata=.data -NOOPT_VS2015x86_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG + DEBUG_VS2015x86_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X64 /DEBUG +RELEASE_VS2015x86_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4254 /MACHINE:X64 +NOOPT_VS2015x86_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X64 /DEBUG #################################################################################### # VS2017 - Microsoft Visual Studio 2017 with Intel ASL @@ -492,13 +515,13 @@ NOOPT_VS2017_IA32_CC_FLAGS = /nologo /arch:IA32 /c /WX /GS- /W4 /Gs32768 /D RELEASE_VS2017_IA32_ASM_FLAGS = /nologo /c /WX /W3 /Cx /coff /Zd NOOPT_VS2017_IA32_ASM_FLAGS = /nologo /c /WX /W3 /Cx /coff /Zd /Zi - DEBUG_VS2017_IA32_NASM_FLAGS = -Ox -f win32 -g -RELEASE_VS2017_IA32_NASM_FLAGS = -Ox -f win32 -NOOPT_VS2017_IA32_NASM_FLAGS = -O0 -f win32 -g + DEBUG_VS2017_IA32_NASM_FLAGS = -Ox -f win32 -g -DRODATA_SECTION_NAME=.rdata +RELEASE_VS2017_IA32_NASM_FLAGS = -Ox -f win32 -DRODATA_SECTION_NAME=.rdata +NOOPT_VS2017_IA32_NASM_FLAGS = -O0 -f win32 -g -DRODATA_SECTION_NAME=.rdata - DEBUG_VS2017_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG -RELEASE_VS2017_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /MERGE:.rdata=.data -NOOPT_VS2017_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG + DEBUG_VS2017_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X86 /DEBUG +RELEASE_VS2017_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4254 /MACHINE:X86 +NOOPT_VS2017_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X86 /DEBUG ################## # X64 definitions @@ -522,13 +545,13 @@ NOOPT_VS2017_X64_CC_FLAGS = /nologo /c /WX /GS- /W4 /Gs32768 /D UNICODE /G RELEASE_VS2017_X64_ASM_FLAGS = /nologo /c /WX /W3 /Cx /Zd NOOPT_VS2017_X64_ASM_FLAGS = /nologo /c /WX /W3 /Cx /Zd /Zi - DEBUG_VS2017_X64_NASM_FLAGS = -Ox -f win64 -g -RELEASE_VS2017_X64_NASM_FLAGS = -Ox -f win64 -NOOPT_VS2017_X64_NASM_FLAGS = -O0 -f win64 -g + DEBUG_VS2017_X64_NASM_FLAGS = -Ox -f win64 -g -DRODATA_SECTION_NAME=.rdata +RELEASE_VS2017_X64_NASM_FLAGS = -Ox -f win64 -DRODATA_SECTION_NAME=.rdata +NOOPT_VS2017_X64_NASM_FLAGS = -O0 -f win64 -g -DRODATA_SECTION_NAME=.rdata - DEBUG_VS2017_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4281 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG -RELEASE_VS2017_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4281 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /MERGE:.rdata=.data -NOOPT_VS2017_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4281 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG + DEBUG_VS2017_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4281 /MACHINE:X64 /DEBUG +RELEASE_VS2017_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4281 /IGNORE:4254 /MACHINE:X64 +NOOPT_VS2017_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4281 /MACHINE:X64 /DEBUG ################# # ARM definitions @@ -552,9 +575,9 @@ NOOPT_VS2017_ARM_CC_FLAGS = /nologo /c /WX /GS- /W4 /Gs32768 /D UNICODE RELEASE_VS2017_ARM_ASM_FLAGS = /nologo NOOPT_VS2017_ARM_ASM_FLAGS = /nologo - DEBUG_VS2017_ARM_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:ARM /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG -RELEASE_VS2017_ARM_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /MAP /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:ARM /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /MERGE:.rdata=.data -NOOPT_VS2017_ARM_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:ARM /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG + DEBUG_VS2017_ARM_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:ARM /DEBUG +RELEASE_VS2017_ARM_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4254 /MACHINE:ARM +NOOPT_VS2017_ARM_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:ARM /DEBUG ##################### # AARCH64 definitions @@ -578,9 +601,9 @@ NOOPT_VS2017_AARCH64_CC_FLAGS = /nologo /c /WX /GS- /W4 /Gs32768 /D UNICODE RELEASE_VS2017_AARCH64_ASM_FLAGS = /nologo NOOPT_VS2017_AARCH64_ASM_FLAGS = /nologo - DEBUG_VS2017_AARCH64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:ARM64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /DRIVER /DEBUG -RELEASE_VS2017_AARCH64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /MAP /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:ARM64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /DRIVER /MERGE:.rdata=.data -NOOPT_VS2017_AARCH64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:ARM64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /DRIVER /DEBUG + DEBUG_VS2017_AARCH64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:ARM64 /DEBUG +RELEASE_VS2017_AARCH64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4254 /MACHINE:ARM64 +NOOPT_VS2017_AARCH64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:ARM64 /DEBUG #################################################################################### # VS2019 - Microsoft Visual Studio 2019 with Intel ASL @@ -633,13 +656,13 @@ NOOPT_VS2019_IA32_CC_FLAGS = /nologo /arch:IA32 /c /WX /GS- /W4 /Gs32768 /D RELEASE_VS2019_IA32_ASM_FLAGS = /nologo /c /WX /W3 /Cx /coff /Zd NOOPT_VS2019_IA32_ASM_FLAGS = /nologo /c /WX /W3 /Cx /coff /Zd /Zi - DEBUG_VS2019_IA32_NASM_FLAGS = -Ox -f win32 -g -RELEASE_VS2019_IA32_NASM_FLAGS = -Ox -f win32 -NOOPT_VS2019_IA32_NASM_FLAGS = -O0 -f win32 -g + DEBUG_VS2019_IA32_NASM_FLAGS = -Ox -f win32 -g -DRODATA_SECTION_NAME=.rdata +RELEASE_VS2019_IA32_NASM_FLAGS = -Ox -f win32 -DRODATA_SECTION_NAME=.rdata +NOOPT_VS2019_IA32_NASM_FLAGS = -O0 -f win32 -g -DRODATA_SECTION_NAME=.rdata - DEBUG_VS2019_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG -RELEASE_VS2019_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /MERGE:.rdata=.data -NOOPT_VS2019_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG + DEBUG_VS2019_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X86 /DEBUG +RELEASE_VS2019_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4254 /MACHINE:X86 +NOOPT_VS2019_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X86 /DEBUG ################## # X64 definitions @@ -663,13 +686,13 @@ NOOPT_VS2019_X64_CC_FLAGS = /nologo /c /WX /GS- /W4 /Gs32768 /D UNICODE /G RELEASE_VS2019_X64_ASM_FLAGS = /nologo /c /WX /W3 /Cx /Zd NOOPT_VS2019_X64_ASM_FLAGS = /nologo /c /WX /W3 /Cx /Zd /Zi - DEBUG_VS2019_X64_NASM_FLAGS = -Ox -f win64 -g -RELEASE_VS2019_X64_NASM_FLAGS = -Ox -f win64 -NOOPT_VS2019_X64_NASM_FLAGS = -O0 -f win64 -g + DEBUG_VS2019_X64_NASM_FLAGS = -Ox -f win64 -g -DRODATA_SECTION_NAME=.rdata +RELEASE_VS2019_X64_NASM_FLAGS = -Ox -f win64 -DRODATA_SECTION_NAME=.rdata +NOOPT_VS2019_X64_NASM_FLAGS = -O0 -f win64 -g -DRODATA_SECTION_NAME=.rdata - DEBUG_VS2019_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4281 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG -RELEASE_VS2019_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4281 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /MERGE:.rdata=.data -NOOPT_VS2019_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4281 /OPT:REF /OPT:ICF=10 /MAP /ALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG + DEBUG_VS2019_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4281 /MACHINE:X64 /DEBUG +RELEASE_VS2019_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4281 /IGNORE:4254 /MACHINE:X64 +NOOPT_VS2019_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4281 /MACHINE:X64 /DEBUG ################# # ARM definitions @@ -693,9 +716,9 @@ NOOPT_VS2019_ARM_CC_FLAGS = /nologo /c /WX /GS- /W4 /Gs32768 /D UNICODE RELEASE_VS2019_ARM_ASM_FLAGS = /nologo NOOPT_VS2019_ARM_ASM_FLAGS = /nologo - DEBUG_VS2019_ARM_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:ARM /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG -RELEASE_VS2019_ARM_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /MAP /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:ARM /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /MERGE:.rdata=.data -NOOPT_VS2019_ARM_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:ARM /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DRIVER /DEBUG + DEBUG_VS2019_ARM_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:ARM /DEBUG +RELEASE_VS2019_ARM_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4254 /MACHINE:ARM +NOOPT_VS2019_ARM_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:ARM /DEBUG ##################### # AARCH64 definitions @@ -719,42 +742,38 @@ NOOPT_VS2019_AARCH64_CC_FLAGS = /nologo /c /WX /GS- /W4 /Gs32768 /D UNICODE RELEASE_VS2019_AARCH64_ASM_FLAGS = /nologo NOOPT_VS2019_AARCH64_ASM_FLAGS = /nologo - DEBUG_VS2019_AARCH64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:ARM64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /DRIVER /DEBUG -RELEASE_VS2019_AARCH64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /MAP /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:ARM64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /DRIVER /MERGE:.rdata=.data -NOOPT_VS2019_AARCH64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /MAP /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:ARM64 /LTCG /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /DRIVER /DEBUG + DEBUG_VS2019_AARCH64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:ARM64 /DEBUG +RELEASE_VS2019_AARCH64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4254 /MACHINE:ARM64 +NOOPT_VS2019_AARCH64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:ARM64 /DEBUG #################################################################################### # GCC Common #################################################################################### *_*_*_OBJCOPY_PATH = echo -*_*_*_OBJCOPY_FLAGS = objcopy not needed for *_*_*_SYMRENAME_PATH = echo *_*_*_SYMRENAME_FLAGS = Symbol renaming not needed for -DEBUG_*_*_OBJCOPY_ADDDEBUGFLAG = --add-gnu-debuglink="$(DEBUG_DIR)/$(MODULE_NAME).debug" -RELEASE_*_*_OBJCOPY_ADDDEBUGFLAG = -NOOPT_*_*_OBJCOPY_ADDDEBUGFLAG = --add-gnu-debuglink="$(DEBUG_DIR)/$(MODULE_NAME).debug" *_*_*_OBJCOPY_STRIPFLAG = --strip-unneeded -R .eh_frame *_*_*_DTC_FLAGS = -H epapr *_*_*_DTCPP_PATH = DEF(DTCPP_BIN) *_*_*_DTC_PATH = DEF(DTC_BIN) DEFINE GCC_ALL_CC_FLAGS = -g -Os -fshort-wchar -fno-builtin -fno-strict-aliasing -Wall -Werror -Wno-array-bounds -include AutoGen.h -fno-common -DEFINE GCC_ARM_CC_FLAGS = DEF(GCC_ALL_CC_FLAGS) -mlittle-endian -mabi=aapcs -fno-short-enums -funsigned-char -ffunction-sections -fdata-sections -fomit-frame-pointer -Wno-address -mthumb -fno-pic -fno-pie +DEFINE GCC_ARM_CC_FLAGS = DEF(GCC_ALL_CC_FLAGS) -march=armv7-a -mthumb -mlittle-endian -mabi=aapcs -fno-short-enums -funsigned-char -ffunction-sections -fdata-sections -fomit-frame-pointer -Wno-address -mfloat-abi=soft -fno-pic -fno-pie DEFINE GCC_LOONGARCH64_CC_FLAGS = DEF(GCC_ALL_CC_FLAGS) -mabi=lp64d -fno-asynchronous-unwind-tables -fno-plt -Wno-address -fno-short-enums -fsigned-char -ffunction-sections -fdata-sections DEFINE GCC_ARM_CC_XIPFLAGS = -mno-unaligned-access DEFINE GCC_AARCH64_CC_FLAGS = DEF(GCC_ALL_CC_FLAGS) -mlittle-endian -fno-short-enums -fverbose-asm -funsigned-char -ffunction-sections -fdata-sections -Wno-address -fno-asynchronous-unwind-tables -fno-unwind-tables -fno-pic -fno-pie -ffixed-x18 DEFINE GCC_AARCH64_CC_XIPFLAGS = -mstrict-align -mgeneral-regs-only DEFINE GCC_RISCV64_CC_XIPFLAGS = -mstrict-align -mgeneral-regs-only DEFINE GCC_DLINK_FLAGS_COMMON = -nostdlib --pie -DEFINE GCC_DLINK2_FLAGS_COMMON = -Wl,--script=$(EDK_TOOLS_PATH)/Scripts/GccBase.lds +DEFINE GCC_DLINK2_FLAGS_COMMON = -Wl,--defsym=ALIGNED_PE_HEADER_SIZE=0x400 DEF(DLINK_SCRIPT) DEFINE GCC_IA32_X64_DLINK_COMMON = DEF(GCC_DLINK_FLAGS_COMMON) --gc-sections -DEFINE GCC_ARM_AARCH64_DLINK_COMMON= -Wl,--emit-relocs -nostdlib -Wl,--gc-sections -u $(IMAGE_ENTRY_POINT) -Wl,-e,$(IMAGE_ENTRY_POINT),-Map,$(DEST_DIR_DEBUG)/$(BASE_NAME).map +DEFINE GCC_ARM_AARCH64_DLINK_COMMON= -Wl,--emit-relocs -nostdlib -Wl,--gc-sections -u $(IMAGE_ENTRY_POINT) -Wl,-e,$(IMAGE_ENTRY_POINT),-Map,$(DEST_DIR_DEBUG)/$(BASE_NAME).map -no-pie DEFINE GCC_LOONGARCH64_DLINK_COMMON= -Wl,--emit-relocs -nostdlib -Wl,--gc-sections -u $(IMAGE_ENTRY_POINT) -Wl,-e,$(IMAGE_ENTRY_POINT),-Map,$(DEST_DIR_DEBUG)/$(BASE_NAME).map -DEFINE GCC_ARM_DLINK_FLAGS = DEF(GCC_ARM_AARCH64_DLINK_COMMON) -z common-page-size=0x20 -Wl,--pic-veneer -DEFINE GCC_AARCH64_DLINK_FLAGS = DEF(GCC_ARM_AARCH64_DLINK_COMMON) -z common-page-size=0x20 -DEFINE GCC_LOONGARCH64_DLINK_FLAGS = DEF(GCC_LOONGARCH64_DLINK_COMMON) -z common-page-size=0x20 -DEFINE GCC_ARM_AARCH64_ASLDLINK_FLAGS = -Wl,--defsym=PECOFF_HEADER_SIZE=0 DEF(GCC_DLINK2_FLAGS_COMMON) -z common-page-size=0x20 +DEFINE GCC_ARM_DLINK_FLAGS = DEF(GCC_ARM_AARCH64_DLINK_COMMON) DEF(GCC_ALIGN) -Wl,--pic-veneer +DEFINE GCC_AARCH64_DLINK_FLAGS = DEF(GCC_ARM_AARCH64_DLINK_COMMON) DEF(GCC_ALIGN) +DEFINE GCC_LOONGARCH64_DLINK_FLAGS = DEF(GCC_LOONGARCH64_DLINK_COMMON) DEF(GCC_ALIGN) +DEFINE GCC_ARM_AARCH64_ASLDLINK_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) DEF(GCC_ALIGN) DEFINE GCC_IA32_X64_ASLDLINK_FLAGS = DEF(GCC_IA32_X64_DLINK_COMMON) --entry _ReferenceAcpiTable -u $(IMAGE_ENTRY_POINT) DEFINE GCC_ARM_ASLDLINK_FLAGS = DEF(GCC_ARM_DLINK_FLAGS) -Wl,--entry,ReferenceAcpiTable -u $(IMAGE_ENTRY_POINT) DEF(GCC_ARM_AARCH64_ASLDLINK_FLAGS) DEFINE GCC_AARCH64_ASLDLINK_FLAGS = DEF(GCC_AARCH64_DLINK_FLAGS) -Wl,--entry,ReferenceAcpiTable -u $(IMAGE_ENTRY_POINT) DEF(GCC_ARM_AARCH64_ASLDLINK_FLAGS) @@ -767,45 +786,38 @@ DEFINE GCC_ASLPP_FLAGS = -x c -E -include AutoGen.h DEFINE GCC_ASLCC_FLAGS = -x c DEFINE GCC_WINDRES_FLAGS = -J rc -O coff DEFINE GCC_DTCPP_FLAGS = -E -x assembler-with-cpp -imacros AutoGen.h -nostdinc -undef -DEFINE GCC_IA32_RC_FLAGS = -I binary -O elf32-i386 -B i386 --rename-section .data=.hii -DEFINE GCC_X64_RC_FLAGS = -I binary -O elf64-x86-64 -B i386 --rename-section .data=.hii -DEFINE GCC_ARM_RC_FLAGS = -I binary -O elf32-littlearm -B arm --rename-section .data=.hii -DEFINE GCC_AARCH64_RC_FLAGS = -I binary -O elf64-littleaarch64 -B aarch64 --rename-section .data=.hii -DEFINE GCC_AARCH64_RC_BTI_FLAGS = --add-section .note.gnu.property=$(WORKSPACE)/ArmPkg/Library/GnuNoteBti.bin --set-section-flags .note.gnu.property=alloc,readonly -DEFINE GCC_RISCV64_RC_FLAGS = -I binary -O elf64-littleriscv -B riscv --rename-section .data=.hii -DEFINE GCC_LOONGARCH64_RC_FLAGS = -I binary -O elf64-loongarch -B loongarch64 --rename-section .data=.hii # GCC Build Flag for included header file list generation DEFINE GCC_DEPS_FLAGS = -MMD -MF $@.deps DEFINE GCC48_ALL_CC_FLAGS = DEF(GCC_ALL_CC_FLAGS) -ffunction-sections -fdata-sections -DSTRING_ARRAY_NAME=$(BASE_NAME)Strings -DEFINE GCC48_IA32_X64_DLINK_COMMON = -nostdlib -Wl,-n,-q,--gc-sections -z common-page-size=0x20 +DEFINE GCC48_IA32_X64_DLINK_COMMON = -nostdlib -Wl,-n,-q,--gc-sections DEF(GCC_ALIGN) DEFINE GCC48_IA32_CC_FLAGS = DEF(GCC48_ALL_CC_FLAGS) -m32 -march=i586 -malign-double -fno-stack-protector -D EFI32 -fno-asynchronous-unwind-tables -Wno-address -fno-omit-frame-pointer -DEFINE GCC48_X64_CC_FLAGS = DEF(GCC48_ALL_CC_FLAGS) -m64 -fno-stack-protector "-DEFIAPI=__attribute__((ms_abi))" -maccumulate-outgoing-args -mno-red-zone -Wno-address -mcmodel=small -fpie -fno-asynchronous-unwind-tables -Wno-address -fno-omit-frame-pointer +DEFINE GCC48_X64_CC_FLAGS = DEF(GCC48_ALL_CC_FLAGS) -m64 -fno-stack-protector "-DEFIAPI=__attribute__((ms_abi))" -maccumulate-outgoing-args -mno-red-zone -Wno-address -mcmodel=small -fpie -fno-asynchronous-unwind-tables -Wno-address -fno-omit-frame-pointer DEFINE GCC48_IA32_X64_ASLDLINK_FLAGS = DEF(GCC48_IA32_X64_DLINK_COMMON) -Wl,--entry,ReferenceAcpiTable -u ReferenceAcpiTable DEFINE GCC48_IA32_X64_DLINK_FLAGS = DEF(GCC48_IA32_X64_DLINK_COMMON) -Wl,--entry,$(IMAGE_ENTRY_POINT) -u $(IMAGE_ENTRY_POINT) -Wl,-Map,$(DEST_DIR_DEBUG)/$(BASE_NAME).map,--whole-archive -DEFINE GCC48_IA32_DLINK2_FLAGS = -Wl,--defsym=PECOFF_HEADER_SIZE=0x220 DEF(GCC_DLINK2_FLAGS_COMMON) +DEFINE GCC48_IA32_DLINK2_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) DEFINE GCC48_X64_DLINK_FLAGS = DEF(GCC48_IA32_X64_DLINK_FLAGS) -Wl,-melf_x86_64,--oformat=elf64-x86-64,-pie -DEFINE GCC48_X64_DLINK2_FLAGS = -Wl,--defsym=PECOFF_HEADER_SIZE=0x228 DEF(GCC_DLINK2_FLAGS_COMMON) +DEFINE GCC48_X64_DLINK2_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) DEFINE GCC48_ASM_FLAGS = DEF(GCC_ASM_FLAGS) -DEFINE GCC48_ARM_ASM_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_ASM_FLAGS) -mlittle-endian -DEFINE GCC48_AARCH64_ASM_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_ASM_FLAGS) -mlittle-endian -DEFINE GCC48_ARM_CC_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_ARM_CC_FLAGS) -fstack-protector -mword-relocations +DEFINE GCC48_ARM_ASM_FLAGS = DEF(GCC_ASM_FLAGS) -mlittle-endian -march=armv7-a +DEFINE GCC48_AARCH64_ASM_FLAGS = DEF(GCC_ASM_FLAGS) -mlittle-endian +DEFINE GCC48_ARM_CC_FLAGS = DEF(GCC_ARM_CC_FLAGS) -fstack-protector -mword-relocations DEFINE GCC48_ARM_CC_XIPFLAGS = DEF(GCC_ARM_CC_XIPFLAGS) -DEFINE GCC48_AARCH64_CC_FLAGS = $(PLATFORM_FLAGS) -mcmodel=large DEF(GCC_AARCH64_CC_FLAGS) +DEFINE GCC48_AARCH64_CC_FLAGS = -mcmodel=large DEF(GCC_AARCH64_CC_FLAGS) DEFINE GCC48_AARCH64_CC_XIPFLAGS = DEF(GCC_AARCH64_CC_XIPFLAGS) DEFINE GCC48_ARM_DLINK_FLAGS = DEF(GCC_ARM_DLINK_FLAGS) -Wl,--oformat=elf32-littlearm -DEFINE GCC48_ARM_DLINK2_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) -Wl,--defsym=PECOFF_HEADER_SIZE=0x220 +DEFINE GCC48_ARM_DLINK2_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) DEFINE GCC48_AARCH64_DLINK_FLAGS = DEF(GCC_AARCH64_DLINK_FLAGS) -DEFINE GCC48_AARCH64_DLINK2_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) -Wl,--defsym=PECOFF_HEADER_SIZE=0x228 +DEFINE GCC48_AARCH64_DLINK2_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) DEFINE GCC48_ARM_ASLDLINK_FLAGS = DEF(GCC_ARM_ASLDLINK_FLAGS) -Wl,--oformat=elf32-littlearm DEFINE GCC48_AARCH64_ASLDLINK_FLAGS = DEF(GCC_AARCH64_ASLDLINK_FLAGS) DEFINE GCC48_ASLCC_FLAGS = DEF(GCC_ASLCC_FLAGS) DEFINE GCC49_IA32_CC_FLAGS = DEF(GCC48_IA32_CC_FLAGS) -fno-pic -fno-pie DEFINE GCC49_X64_CC_FLAGS = DEF(GCC48_X64_CC_FLAGS) -DEFINE GCC49_IA32_X64_DLINK_COMMON = -nostdlib -Wl,-n,-q,--gc-sections -z common-page-size=0x40 -DEFINE GCC49_IA32_X64_ASLDLINK_FLAGS = DEF(GCC49_IA32_X64_DLINK_COMMON) -Wl,--defsym=PECOFF_HEADER_SIZE=0 DEF(GCC_DLINK2_FLAGS_COMMON) -Wl,--entry,ReferenceAcpiTable -u ReferenceAcpiTable +DEFINE GCC49_IA32_X64_DLINK_COMMON = -nostdlib -Wl,-n,-q,--gc-sections DEF(GCC_ALIGN) +DEFINE GCC49_IA32_X64_ASLDLINK_FLAGS = DEF(GCC49_IA32_X64_DLINK_COMMON) DEF(GCC_DLINK2_FLAGS_COMMON) -Wl,--entry,ReferenceAcpiTable -u ReferenceAcpiTable DEFINE GCC49_IA32_X64_DLINK_FLAGS = DEF(GCC49_IA32_X64_DLINK_COMMON) -Wl,--entry,$(IMAGE_ENTRY_POINT) -u $(IMAGE_ENTRY_POINT) -Wl,-Map,$(DEST_DIR_DEBUG)/$(BASE_NAME).map,--whole-archive DEFINE GCC49_IA32_DLINK2_FLAGS = DEF(GCC48_IA32_DLINK2_FLAGS) DEFINE GCC49_X64_DLINK_FLAGS = DEF(GCC49_IA32_X64_DLINK_FLAGS) -Wl,-melf_x86_64,--oformat=elf64-x86-64,-pie @@ -815,11 +827,11 @@ DEFINE GCC49_ARM_ASM_FLAGS = DEF(GCC48_ARM_ASM_FLAGS) DEFINE GCC49_AARCH64_ASM_FLAGS = DEF(GCC48_AARCH64_ASM_FLAGS) DEFINE GCC49_ARM_CC_FLAGS = DEF(GCC48_ARM_CC_FLAGS) DEFINE GCC49_ARM_CC_XIPFLAGS = DEF(GCC48_ARM_CC_XIPFLAGS) -DEFINE GCC49_AARCH64_CC_FLAGS = $(PLATFORM_FLAGS) DEF(GCC48_ALL_CC_FLAGS) DEF(GCC_AARCH64_CC_FLAGS) -mcmodel=small +DEFINE GCC49_AARCH64_CC_FLAGS = DEF(GCC48_ALL_CC_FLAGS) DEF(GCC_AARCH64_CC_FLAGS) -mcmodel=small DEFINE GCC49_AARCH64_CC_XIPFLAGS = DEF(GCC48_AARCH64_CC_XIPFLAGS) DEFINE GCC49_ARM_DLINK_FLAGS = DEF(GCC48_ARM_DLINK_FLAGS) DEFINE GCC49_ARM_DLINK2_FLAGS = DEF(GCC48_ARM_DLINK2_FLAGS) -DEFINE GCC49_AARCH64_DLINK_FLAGS = DEF(GCC48_AARCH64_DLINK_FLAGS) -z common-page-size=0x1000 +DEFINE GCC49_AARCH64_DLINK_FLAGS = DEF(GCC48_AARCH64_DLINK_FLAGS) DEF(GCC_ALIGN) DEFINE GCC49_AARCH64_DLINK2_FLAGS = DEF(GCC48_AARCH64_DLINK2_FLAGS) DEFINE GCC49_ARM_ASLDLINK_FLAGS = DEF(GCC48_ARM_ASLDLINK_FLAGS) DEFINE GCC49_AARCH64_ASLDLINK_FLAGS = DEF(GCC48_AARCH64_ASLDLINK_FLAGS) @@ -849,9 +861,9 @@ DEFINE GCC5_AARCH64_ASLDLINK_FLAGS = DEF(GCC49_AARCH64_ASLDLINK_FLAGS) DEFINE GCC5_ASLCC_FLAGS = DEF(GCC49_ASLCC_FLAGS) -fno-lto DEFINE GCC5_RISCV_ALL_CC_FLAGS = -g -fshort-wchar -fno-strict-aliasing -Wall -Werror -Wno-array-bounds -ffunction-sections -fdata-sections -include AutoGen.h -fno-common -DSTRING_ARRAY_NAME=$(BASE_NAME)Strings -msmall-data-limit=0 -DEFINE GCC5_RISCV_ALL_DLINK_COMMON = -nostdlib -Wl,-n,-q,--gc-sections -z common-page-size=0x40 +DEFINE GCC5_RISCV_ALL_DLINK_COMMON = -nostdlib -Wl,-n,-q,--gc-sections DEF(GCC_ALIGN) DEFINE GCC5_RISCV_ALL_DLINK_FLAGS = DEF(GCC5_RISCV_ALL_DLINK_COMMON) -Wl,--entry,$(IMAGE_ENTRY_POINT) -u $(IMAGE_ENTRY_POINT) -Wl,-Map,$(DEST_DIR_DEBUG)/$(BASE_NAME).map -DEFINE GCC5_RISCV_ALL_DLINK2_FLAGS = -Wl,--defsym=PECOFF_HEADER_SIZE=0x220,--script=$(EDK_TOOLS_PATH)/Scripts/GccBase.lds +DEFINE GCC5_RISCV_ALL_DLINK2_FLAGS = -Wl,--defsym=ALIGNED_PE_HEADER_SIZE=0x400 DEF(DLINK_SCRIPT) DEFINE GCC5_RISCV_ALL_ASM_FLAGS = -c -x assembler -imacros $(DEST_DIR_DEBUG)/AutoGen.h DEFINE GCC5_RISCV_ALL_CC_FLAGS_WARNING_DISABLE = -Wno-tautological-compare -Wno-pointer-compare @@ -866,7 +878,7 @@ DEFINE GCC5_RISCV64_ASM_FLAGS = DEF(GCC5_RISCV_ALL_ASM_FLAGS) -marc DEFINE GCC5_LOONGARCH64_CC_FLAGS = DEF(GCC_LOONGARCH64_CC_FLAGS) -march=loongarch64 -mno-memcpy -Werror -Wno-maybe-uninitialized -Wno-stringop-overflow -Wno-pointer-to-int-cast -no-pie -fno-stack-protector -mno-explicit-relocs DEFINE GCC5_LOONGARCH64_DLINK_FLAGS = DEF(GCC_LOONGARCH64_DLINK_FLAGS) -DEFINE GCC5_LOONGARCH64_DLINK2_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) -Wl,--defsym=PECOFF_HEADER_SIZE=0x228 +DEFINE GCC5_LOONGARCH64_DLINK2_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) DEFINE GCC5_LOONGARCH64_ASLDLINK_FLAGS = DEF(GCC_LOONGARCH64_ASLDLINK_FLAGS) DEF(GCC5_LOONGARCH64_DLINK2_FLAGS) DEFINE GCC5_LOONGARCH64_ASM_FLAGS = -x assembler-with-cpp -mabi=lp64d -march=loongarch64 -fno-builtin -c -Wall -mno-explicit-relocs DEFINE GCC5_LOONGARCH64_PP_FLAGS = -mabi=lp64d -march=loongarch64 DEF(GCC_PP_FLAGS) @@ -913,8 +925,7 @@ DEFINE GCC5_LOONGARCH64_PP_FLAGS = -mabi=lp64d -march=loongarch64 DEF( *_GCC48_IA32_DLINK_FLAGS = DEF(GCC48_IA32_X64_DLINK_FLAGS) -Wl,-m,elf_i386,--oformat=elf32-i386 *_GCC48_IA32_DLINK2_FLAGS = DEF(GCC48_IA32_DLINK2_FLAGS) *_GCC48_IA32_RC_FLAGS = DEF(GCC_IA32_RC_FLAGS) -*_GCC48_IA32_OBJCOPY_FLAGS = -*_GCC48_IA32_NASM_FLAGS = -f elf32 +*_GCC48_IA32_NASM_FLAGS = -f elf32 -DRODATA_SECTION_NAME=.rodata DEBUG_GCC48_IA32_CC_FLAGS = DEF(GCC48_IA32_CC_FLAGS) RELEASE_GCC48_IA32_CC_FLAGS = DEF(GCC48_IA32_CC_FLAGS) -Wno-unused-but-set-variable @@ -941,8 +952,7 @@ RELEASE_GCC48_IA32_CC_FLAGS = DEF(GCC48_IA32_CC_FLAGS) -Wno-unused-but-set *_GCC48_X64_DLINK_FLAGS = DEF(GCC48_X64_DLINK_FLAGS) *_GCC48_X64_DLINK2_FLAGS = DEF(GCC48_X64_DLINK2_FLAGS) *_GCC48_X64_RC_FLAGS = DEF(GCC_X64_RC_FLAGS) -*_GCC48_X64_OBJCOPY_FLAGS = -*_GCC48_X64_NASM_FLAGS = -f elf64 +*_GCC48_X64_NASM_FLAGS = -f elf64 -DRODATA_SECTION_NAME=.rodata DEBUG_GCC48_X64_CC_FLAGS = DEF(GCC48_X64_CC_FLAGS) RELEASE_GCC48_X64_CC_FLAGS = DEF(GCC48_X64_CC_FLAGS) -Wno-unused-but-set-variable @@ -968,10 +978,9 @@ RELEASE_GCC48_X64_CC_FLAGS = DEF(GCC48_X64_CC_FLAGS) -Wno-unused-but-set-v *_GCC48_ARM_DLINK_FLAGS = DEF(GCC48_ARM_DLINK_FLAGS) *_GCC48_ARM_DLINK2_FLAGS = DEF(GCC48_ARM_DLINK2_FLAGS) *_GCC48_ARM_DTCPP_FLAGS = DEF(GCC_DTCPP_FLAGS) -*_GCC48_ARM_PLATFORM_FLAGS = -march=armv7-a -*_GCC48_ARM_PP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_PP_FLAGS) +*_GCC48_ARM_PP_FLAGS = DEF(GCC_PP_FLAGS) -mthumb -march=armv7-a *_GCC48_ARM_RC_FLAGS = DEF(GCC_ARM_RC_FLAGS) -*_GCC48_ARM_VFRPP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_VFRPP_FLAGS) +*_GCC48_ARM_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) -mthumb -march=armv7-a *_GCC48_ARM_CC_XIPFLAGS = DEF(GCC48_ARM_CC_XIPFLAGS) DEBUG_GCC48_ARM_CC_FLAGS = DEF(GCC48_ARM_CC_FLAGS) -O0 @@ -998,10 +1007,9 @@ RELEASE_GCC48_ARM_CC_FLAGS = DEF(GCC48_ARM_CC_FLAGS) -Wno-unused-but-set-v *_GCC48_AARCH64_DLINK_FLAGS = DEF(GCC48_AARCH64_DLINK_FLAGS) *_GCC48_AARCH64_DLINK2_FLAGS = DEF(GCC48_AARCH64_DLINK2_FLAGS) *_GCC48_AARCH64_DTCPP_FLAGS = DEF(GCC_DTCPP_FLAGS) -*_GCC48_AARCH64_PLATFORM_FLAGS = -*_GCC48_AARCH64_PP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_PP_FLAGS) +*_GCC48_AARCH64_PP_FLAGS = DEF(GCC_PP_FLAGS) *_GCC48_AARCH64_RC_FLAGS = DEF(GCC_AARCH64_RC_FLAGS) -*_GCC48_AARCH64_VFRPP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_VFRPP_FLAGS) +*_GCC48_AARCH64_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) *_GCC48_AARCH64_CC_XIPFLAGS = DEF(GCC48_AARCH64_CC_XIPFLAGS) DEBUG_GCC48_AARCH64_CC_FLAGS = DEF(GCC48_AARCH64_CC_FLAGS) -O0 @@ -1050,8 +1058,7 @@ RELEASE_GCC48_AARCH64_CC_FLAGS = DEF(GCC48_AARCH64_CC_FLAGS) -Wno-unused-but-s *_GCC49_IA32_DLINK_FLAGS = DEF(GCC49_IA32_X64_DLINK_FLAGS) -Wl,-m,elf_i386,--oformat=elf32-i386 *_GCC49_IA32_DLINK2_FLAGS = DEF(GCC49_IA32_DLINK2_FLAGS) *_GCC49_IA32_RC_FLAGS = DEF(GCC_IA32_RC_FLAGS) -*_GCC49_IA32_OBJCOPY_FLAGS = -*_GCC49_IA32_NASM_FLAGS = -f elf32 +*_GCC49_IA32_NASM_FLAGS = -f elf32 -DRODATA_SECTION_NAME=.rodata DEBUG_GCC49_IA32_CC_FLAGS = DEF(GCC49_IA32_CC_FLAGS) RELEASE_GCC49_IA32_CC_FLAGS = DEF(GCC49_IA32_CC_FLAGS) -Wno-unused-but-set-variable -Wno-unused-const-variable @@ -1078,8 +1085,7 @@ RELEASE_GCC49_IA32_CC_FLAGS = DEF(GCC49_IA32_CC_FLAGS) -Wno-unused-but-set *_GCC49_X64_DLINK_FLAGS = DEF(GCC49_X64_DLINK_FLAGS) *_GCC49_X64_DLINK2_FLAGS = DEF(GCC49_X64_DLINK2_FLAGS) *_GCC49_X64_RC_FLAGS = DEF(GCC_X64_RC_FLAGS) -*_GCC49_X64_OBJCOPY_FLAGS = -*_GCC49_X64_NASM_FLAGS = -f elf64 +*_GCC49_X64_NASM_FLAGS = -f elf64 -DRODATA_SECTION_NAME=.rodata DEBUG_GCC49_X64_CC_FLAGS = DEF(GCC49_X64_CC_FLAGS) RELEASE_GCC49_X64_CC_FLAGS = DEF(GCC49_X64_CC_FLAGS) -Wno-unused-but-set-variable -Wno-unused-const-variable @@ -1105,10 +1111,9 @@ RELEASE_GCC49_X64_CC_FLAGS = DEF(GCC49_X64_CC_FLAGS) -Wno-unused-but-set-v *_GCC49_ARM_DLINK_FLAGS = DEF(GCC49_ARM_DLINK_FLAGS) *_GCC49_ARM_DLINK2_FLAGS = DEF(GCC49_ARM_DLINK2_FLAGS) *_GCC49_ARM_DTCPP_FLAGS = DEF(GCC_DTCPP_FLAGS) -*_GCC49_ARM_PLATFORM_FLAGS = -march=armv7-a -*_GCC49_ARM_PP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_PP_FLAGS) +*_GCC49_ARM_PP_FLAGS = DEF(GCC_PP_FLAGS) -mthumb -march=armv7-a *_GCC49_ARM_RC_FLAGS = DEF(GCC_ARM_RC_FLAGS) -*_GCC49_ARM_VFRPP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_VFRPP_FLAGS) +*_GCC49_ARM_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) -mthumb -march=armv7-a *_GCC49_ARM_CC_XIPFLAGS = DEF(GCC49_ARM_CC_XIPFLAGS) DEBUG_GCC49_ARM_CC_FLAGS = DEF(GCC49_ARM_CC_FLAGS) -O0 @@ -1134,23 +1139,22 @@ RELEASE_GCC49_ARM_CC_FLAGS = DEF(GCC49_ARM_CC_FLAGS) -Wno-unused-but-set-v *_GCC49_AARCH64_ASM_FLAGS = DEF(GCC49_AARCH64_ASM_FLAGS) *_GCC49_AARCH64_DLINK2_FLAGS = DEF(GCC49_AARCH64_DLINK2_FLAGS) *_GCC49_AARCH64_DTCPP_FLAGS = DEF(GCC_DTCPP_FLAGS) -*_GCC49_AARCH64_PLATFORM_FLAGS = -*_GCC49_AARCH64_PP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_PP_FLAGS) +*_GCC49_AARCH64_PP_FLAGS = DEF(GCC_PP_FLAGS) *_GCC49_AARCH64_RC_FLAGS = DEF(GCC_AARCH64_RC_FLAGS) -*_GCC49_AARCH64_VFRPP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_VFRPP_FLAGS) +*_GCC49_AARCH64_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) *_GCC49_AARCH64_CC_XIPFLAGS = DEF(GCC49_AARCH64_CC_XIPFLAGS) DEBUG_GCC49_AARCH64_CC_FLAGS = DEF(GCC49_AARCH64_CC_FLAGS) -O0 DEBUG_GCC49_AARCH64_DLINK_FLAGS = DEF(GCC49_AARCH64_DLINK_FLAGS) - DEBUG_GCC49_AARCH64_DLINK_XIPFLAGS = -z common-page-size=0x20 + DEBUG_GCC49_AARCH64_DLINK_XIPFLAGS = DEF(GCC_ALIGN) RELEASE_GCC49_AARCH64_CC_FLAGS = DEF(GCC49_AARCH64_CC_FLAGS) -Wno-unused-but-set-variable -Wno-unused-const-variable RELEASE_GCC49_AARCH64_DLINK_FLAGS = DEF(GCC49_AARCH64_DLINK_FLAGS) -RELEASE_GCC49_AARCH64_DLINK_XIPFLAGS = -z common-page-size=0x20 +RELEASE_GCC49_AARCH64_DLINK_XIPFLAGS = DEF(GCC_ALIGN) NOOPT_GCC49_AARCH64_CC_FLAGS = DEF(GCC49_AARCH64_CC_FLAGS) -O0 NOOPT_GCC49_AARCH64_DLINK_FLAGS = DEF(GCC49_AARCH64_DLINK_FLAGS) -O0 - NOOPT_GCC49_AARCH64_DLINK_XIPFLAGS = -z common-page-size=0x20 -O0 + NOOPT_GCC49_AARCH64_DLINK_XIPFLAGS = DEF(GCC_ALIGN) -O0 #################################################################################### # @@ -1336,9 +1340,7 @@ RELEASE_GCCNOLTO_AARCH64_DLINK_XIPFLAGS = -z common-page-size=0x20 *_GCC5_IA32_ASLDLINK_FLAGS = DEF(GCC5_IA32_X64_ASLDLINK_FLAGS) -Wl,-m,elf_i386 -no-pie *_GCC5_IA32_ASM_FLAGS = DEF(GCC5_ASM_FLAGS) -m32 -march=i386 *_GCC5_IA32_DLINK2_FLAGS = DEF(GCC5_IA32_DLINK2_FLAGS) -no-pie -*_GCC5_IA32_RC_FLAGS = DEF(GCC_IA32_RC_FLAGS) -*_GCC5_IA32_OBJCOPY_FLAGS = -*_GCC5_IA32_NASM_FLAGS = -f elf32 +*_GCC5_IA32_NASM_FLAGS = -f elf32 -DRODATA_SECTION_NAME=.rodata DEBUG_GCC5_IA32_CC_FLAGS = DEF(GCC5_IA32_CC_FLAGS) -flto DEBUG_GCC5_IA32_DLINK_FLAGS = DEF(GCC5_IA32_X64_DLINK_FLAGS) -flto -Os -Wl,-m,elf_i386,--oformat=elf32-i386 @@ -1368,9 +1370,7 @@ RELEASE_GCC5_IA32_DLINK_FLAGS = DEF(GCC5_IA32_X64_DLINK_FLAGS) -flto -Os -Wl, *_GCC5_X64_ASLDLINK_FLAGS = DEF(GCC5_IA32_X64_ASLDLINK_FLAGS) -Wl,-m,elf_x86_64 *_GCC5_X64_ASM_FLAGS = DEF(GCC5_ASM_FLAGS) -m64 *_GCC5_X64_DLINK2_FLAGS = DEF(GCC5_X64_DLINK2_FLAGS) -*_GCC5_X64_RC_FLAGS = DEF(GCC_X64_RC_FLAGS) -*_GCC5_X64_OBJCOPY_FLAGS = -*_GCC5_X64_NASM_FLAGS = -f elf64 +*_GCC5_X64_NASM_FLAGS = -f elf64 -DRODATA_SECTION_NAME=.rodata DEBUG_GCC5_X64_CC_FLAGS = DEF(GCC5_X64_CC_FLAGS) -flto -DUSING_LTO DEBUG_GCC5_X64_DLINK_FLAGS = DEF(GCC5_X64_DLINK_FLAGS) -flto -Os @@ -1384,6 +1384,7 @@ RELEASE_GCC5_X64_DLINK_FLAGS = DEF(GCC5_X64_DLINK_FLAGS) -flto -Os ################## # GCC5 ARM definitions ################## +*_GCC5_ARM_OBJCOPY_PATH = ENV(GCC5_ARM_PREFIX)objcopy *_GCC5_ARM_CC_PATH = ENV(GCC5_ARM_PREFIX)gcc *_GCC5_ARM_SLINK_PATH = ENV(GCC5_ARM_PREFIX)gcc-ar *_GCC5_ARM_DLINK_PATH = ENV(GCC5_ARM_PREFIX)gcc @@ -1400,10 +1401,8 @@ RELEASE_GCC5_X64_DLINK_FLAGS = DEF(GCC5_X64_DLINK_FLAGS) -flto -Os *_GCC5_ARM_ASM_FLAGS = DEF(GCC5_ARM_ASM_FLAGS) *_GCC5_ARM_DLINK2_FLAGS = DEF(GCC5_ARM_DLINK2_FLAGS) *_GCC5_ARM_DTCPP_FLAGS = DEF(GCC_DTCPP_FLAGS) -*_GCC5_ARM_PLATFORM_FLAGS = -march=armv7-a -mfloat-abi=soft -*_GCC5_ARM_PP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_PP_FLAGS) -*_GCC5_ARM_RC_FLAGS = DEF(GCC_ARM_RC_FLAGS) -*_GCC5_ARM_VFRPP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_VFRPP_FLAGS) +*_GCC5_ARM_PP_FLAGS = DEF(GCC_PP_FLAGS) -mthumb -march=armv7-a +*_GCC5_ARM_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) -mthumb -march=armv7-a *_GCC5_ARM_CC_XIPFLAGS = DEF(GCC5_ARM_CC_XIPFLAGS) DEBUG_GCC5_ARM_CC_FLAGS = DEF(GCC5_ARM_CC_FLAGS) -flto -Wno-unused-but-set-variable -Wno-unused-const-variable @@ -1418,6 +1417,7 @@ RELEASE_GCC5_ARM_DLINK_FLAGS = DEF(GCC5_ARM_DLINK_FLAGS) -flto -Os -L$(WORKS ################## # GCC5 AARCH64 definitions ################## +*_GCC5_AARCH64_OBJCOPY_PATH = ENV(GCC5_AARCH64_PREFIX)objcopy *_GCC5_AARCH64_CC_PATH = ENV(GCC5_AARCH64_PREFIX)gcc *_GCC5_AARCH64_SLINK_PATH = ENV(GCC5_AARCH64_PREFIX)gcc-ar *_GCC5_AARCH64_DLINK_PATH = ENV(GCC5_AARCH64_PREFIX)gcc @@ -1434,23 +1434,21 @@ RELEASE_GCC5_ARM_DLINK_FLAGS = DEF(GCC5_ARM_DLINK_FLAGS) -flto -Os -L$(WORKS *_GCC5_AARCH64_ASM_FLAGS = DEF(GCC5_AARCH64_ASM_FLAGS) *_GCC5_AARCH64_DLINK2_FLAGS = DEF(GCC5_AARCH64_DLINK2_FLAGS) *_GCC5_AARCH64_DTCPP_FLAGS = DEF(GCC_DTCPP_FLAGS) -*_GCC5_AARCH64_PLATFORM_FLAGS = -*_GCC5_AARCH64_PP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_PP_FLAGS) -*_GCC5_AARCH64_RC_FLAGS = DEF(GCC_AARCH64_RC_FLAGS) DEF(GCC_AARCH64_RC_BTI_FLAGS) -*_GCC5_AARCH64_VFRPP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_VFRPP_FLAGS) +*_GCC5_AARCH64_PP_FLAGS = DEF(GCC_PP_FLAGS) +*_GCC5_AARCH64_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) *_GCC5_AARCH64_CC_XIPFLAGS = DEF(GCC5_AARCH64_CC_XIPFLAGS) DEBUG_GCC5_AARCH64_CC_FLAGS = DEF(GCC5_AARCH64_CC_FLAGS) -flto -Wno-unused-but-set-variable -Wno-unused-const-variable DEBUG_GCC5_AARCH64_DLINK_FLAGS = DEF(GCC5_AARCH64_DLINK_FLAGS) -flto -Os -L$(WORKSPACE)/ArmPkg/Library/GccLto -llto-aarch64 -Wl,-plugin-opt=-pass-through=-llto-aarch64 -Wno-lto-type-mismatch - DEBUG_GCC5_AARCH64_DLINK_XIPFLAGS = -z common-page-size=0x20 + DEBUG_GCC5_AARCH64_DLINK_XIPFLAGS = DEF(GCC_ALIGN) RELEASE_GCC5_AARCH64_CC_FLAGS = DEF(GCC5_AARCH64_CC_FLAGS) -flto -Wno-unused-but-set-variable -Wno-unused-const-variable RELEASE_GCC5_AARCH64_DLINK_FLAGS = DEF(GCC5_AARCH64_DLINK_FLAGS) -flto -Os -L$(WORKSPACE)/ArmPkg/Library/GccLto -llto-aarch64 -Wl,-plugin-opt=-pass-through=-llto-aarch64 -Wno-lto-type-mismatch -RELEASE_GCC5_AARCH64_DLINK_XIPFLAGS = -z common-page-size=0x20 +RELEASE_GCC5_AARCH64_DLINK_XIPFLAGS = DEF(GCC_ALIGN) NOOPT_GCC5_AARCH64_CC_FLAGS = DEF(GCC5_AARCH64_CC_FLAGS) -O0 NOOPT_GCC5_AARCH64_DLINK_FLAGS = DEF(GCC5_AARCH64_DLINK_FLAGS) -O0 - NOOPT_GCC5_AARCH64_DLINK_XIPFLAGS = -z common-page-size=0x20 -O0 + NOOPT_GCC5_AARCH64_DLINK_XIPFLAGS = DEF(GCC_ALIGN) -O0 #################################################################################### # @@ -1480,8 +1478,6 @@ RELEASE_GCC5_AARCH64_DLINK_XIPFLAGS = -z common-page-size=0x20 *_GCC5_RISCV64_CC_FLAGS = DEF(GCC5_RISCV64_CC_FLAGS) -save-temps *_GCC5_RISCV64_DLINK_FLAGS = DEF(GCC5_RISCV64_DLINK_FLAGS) *_GCC5_RISCV64_DLINK2_FLAGS = DEF(GCC5_RISCV64_DLINK2_FLAGS) -*_GCC5_RISCV64_RC_FLAGS = DEF(GCC_RISCV64_RC_FLAGS) -*_GCC5_RISCV64_OBJCOPY_FLAGS = *_GCC5_RISCV64_DTCPP_FLAGS = DEF(GCC_DTCPP_FLAGS) *_GCC5_RISCV64_PP_FLAGS = DEF(GCC_PP_FLAGS) DEF(GCC5_RISCV_OPENSBI_TYPES) @@ -1505,8 +1501,6 @@ RELEASE_GCC5_AARCH64_DLINK_XIPFLAGS = -z common-page-size=0x20 *_GCC5_LOONGARCH64_ASM_FLAGS = DEF(GCC5_LOONGARCH64_ASM_FLAGS) *_GCC5_LOONGARCH64_DLINK_FLAGS = DEF(GCC5_LOONGARCH64_DLINK_FLAGS) *_GCC5_LOONGARCH64_DLINK2_FLAGS = DEF(GCC5_LOONGARCH64_DLINK2_FLAGS) -*_GCC5_LOONGARCH64_RC_FLAGS = DEF(GCC_LOONGARCH64_RC_FLAGS) -*_GCC5_LOONGARCH64_OBJCOPY_FLAGS = *_GCC5_LOONGARCH64_NASM_FLAGS = -f elf32 *_GCC5_LOONGARCH64_PP_FLAGS = DEF(GCC5_LOONGARCH64_PP_FLAGS) @@ -1553,7 +1547,6 @@ RELEASE_GCC5_LOONGARCH64_CC_FLAGS = DEF(GCC5_LOONGARCH64_CC_FLAGS) -Wno-un *_GCC_IA32_ASLDLINK_FLAGS = DEF(GCC5_IA32_X64_ASLDLINK_FLAGS) -Wl,-m,elf_i386 -no-pie *_GCC_IA32_ASM_FLAGS = DEF(GCC5_ASM_FLAGS) -m32 -march=i386 *_GCC_IA32_DLINK2_FLAGS = DEF(GCC5_IA32_DLINK2_FLAGS) -no-pie -*_GCC_IA32_RC_FLAGS = DEF(GCC_IA32_RC_FLAGS) *_GCC_IA32_OBJCOPY_FLAGS = *_GCC_IA32_NASM_FLAGS = -f elf32 @@ -1585,7 +1578,6 @@ RELEASE_GCC_IA32_DLINK_FLAGS = DEF(GCC5_IA32_X64_DLINK_FLAGS) -flto -Os -Wl,- *_GCC_X64_ASLDLINK_FLAGS = DEF(GCC5_IA32_X64_ASLDLINK_FLAGS) -Wl,-m,elf_x86_64 *_GCC_X64_ASM_FLAGS = DEF(GCC5_ASM_FLAGS) -m64 *_GCC_X64_DLINK2_FLAGS = DEF(GCC5_X64_DLINK2_FLAGS) -*_GCC_X64_RC_FLAGS = DEF(GCC_X64_RC_FLAGS) *_GCC_X64_OBJCOPY_FLAGS = *_GCC_X64_NASM_FLAGS = -f elf64 @@ -1619,7 +1611,6 @@ RELEASE_GCC_X64_DLINK_FLAGS = DEF(GCC5_X64_DLINK_FLAGS) -flto -Os *_GCC_ARM_DTCPP_FLAGS = DEF(GCC_DTCPP_FLAGS) *_GCC_ARM_PLATFORM_FLAGS = -march=armv7-a -mfloat-abi=soft *_GCC_ARM_PP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_PP_FLAGS) -*_GCC_ARM_RC_FLAGS = DEF(GCC_ARM_RC_FLAGS) *_GCC_ARM_VFRPP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_VFRPP_FLAGS) *_GCC_ARM_CC_XIPFLAGS = DEF(GCC5_ARM_CC_XIPFLAGS) @@ -1653,7 +1644,6 @@ RELEASE_GCC_ARM_DLINK_FLAGS = DEF(GCC5_ARM_DLINK_FLAGS) -flto -Os -L$(WORKSP *_GCC_AARCH64_DTCPP_FLAGS = DEF(GCC_DTCPP_FLAGS) *_GCC_AARCH64_PLATFORM_FLAGS = *_GCC_AARCH64_PP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_PP_FLAGS) -*_GCC_AARCH64_RC_FLAGS = DEF(GCC_AARCH64_RC_FLAGS) DEF(GCC_AARCH64_RC_BTI_FLAGS) *_GCC_AARCH64_VFRPP_FLAGS = $(PLATFORM_FLAGS) DEF(GCC_VFRPP_FLAGS) *_GCC_AARCH64_CC_XIPFLAGS = DEF(GCC5_AARCH64_CC_XIPFLAGS) @@ -1697,7 +1687,6 @@ RELEASE_GCC_AARCH64_DLINK_XIPFLAGS = -z common-page-size=0x20 *_GCC_RISCV64_CC_FLAGS = DEF(GCC5_RISCV64_CC_FLAGS) -save-temps *_GCC_RISCV64_DLINK_FLAGS = DEF(GCC5_RISCV64_DLINK_FLAGS) *_GCC_RISCV64_DLINK2_FLAGS = DEF(GCC5_RISCV64_DLINK2_FLAGS) -*_GCC_RISCV64_RC_FLAGS = DEF(GCC_RISCV64_RC_FLAGS) *_GCC_RISCV64_OBJCOPY_FLAGS = *_GCC_RISCV64_DTCPP_FLAGS = DEF(GCC_DTCPP_FLAGS) *_GCC_RISCV64_PP_FLAGS = DEF(GCC_PP_FLAGS) DEF(GCC5_RISCV_OPENSBI_TYPES) @@ -1722,7 +1711,6 @@ RELEASE_GCC_AARCH64_DLINK_XIPFLAGS = -z common-page-size=0x20 *_GCC_LOONGARCH64_ASM_FLAGS = DEF(GCC5_LOONGARCH64_ASM_FLAGS) *_GCC_LOONGARCH64_DLINK_FLAGS = DEF(GCC5_LOONGARCH64_DLINK_FLAGS) *_GCC_LOONGARCH64_DLINK2_FLAGS = DEF(GCC5_LOONGARCH64_DLINK2_FLAGS) -*_GCC_LOONGARCH64_RC_FLAGS = DEF(GCC_LOONGARCH64_RC_FLAGS) *_GCC_LOONGARCH64_OBJCOPY_FLAGS = *_GCC_LOONGARCH64_NASM_FLAGS = -f elf32 *_GCC_LOONGARCH64_PP_FLAGS = DEF(GCC5_LOONGARCH64_PP_FLAGS) @@ -1773,22 +1761,21 @@ DEFINE CLANGPDB_ALL_CC_FLAGS = DEF(GCC48_ALL_CC_FLAGS) DEF(CLANGPDB_WARN *_CLANGPDB_IA32_ASLCC_FLAGS = DEF(GCC_ASLCC_FLAGS) -m32 -fno-lto DEF(CLANGPDB_IA32_TARGET) *_CLANGPDB_IA32_ASM_FLAGS = DEF(GCC_ASM_FLAGS) -m32 -march=i386 DEF(CLANGPDB_IA32_TARGET) -*_CLANGPDB_IA32_OBJCOPY_FLAGS = -*_CLANGPDB_IA32_NASM_FLAGS = -f win32 +*_CLANGPDB_IA32_NASM_FLAGS = -f win32 -DRODATA_SECTION_NAME=.rdata *_CLANGPDB_IA32_PP_FLAGS = DEF(GCC_PP_FLAGS) DEF(CLANGPDB_IA32_TARGET) *_CLANGPDB_IA32_ASLPP_FLAGS = DEF(GCC_ASLPP_FLAGS) DEF(CLANGPDB_IA32_TARGET) *_CLANGPDB_IA32_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) DEF(CLANGPDB_IA32_TARGET) DEBUG_CLANGPDB_IA32_CC_FLAGS = DEF(CLANGPDB_ALL_CC_FLAGS) -m32 -Oz -flto -march=i586 DEF(CLANGPDB_IA32_TARGET) -gcodeview -malign-double -DEBUG_CLANGPDB_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /ALIGN:32 /FILEALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DEBUG:GHASH /MLLVM:-exception-model=wineh /lldmap +DEBUG_CLANGPDB_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X86 /DEBUG:GHASH /MLLVM:-exception-model=wineh /lldmap DEBUG_CLANGPDB_IA32_DLINK2_FLAGS = RELEASE_CLANGPDB_IA32_CC_FLAGS = DEF(CLANGPDB_ALL_CC_FLAGS) -m32 -Oz -flto -march=i586 DEF(CLANGPDB_IA32_TARGET) -malign-double -RELEASE_CLANGPDB_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /ALIGN:32 /FILEALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /MERGE:.rdata=.data /MLLVM:-exception-model=wineh /lldmap +RELEASE_CLANGPDB_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4254 /MACHINE:X86 /MLLVM:-exception-model=wineh /lldmap RELEASE_CLANGPDB_IA32_DLINK2_FLAGS = NOOPT_CLANGPDB_IA32_CC_FLAGS = DEF(CLANGPDB_ALL_CC_FLAGS) -m32 -O0 -march=i586 DEF(CLANGPDB_IA32_TARGET) -gcodeview -malign-double -NOOPT_CLANGPDB_IA32_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /ALIGN:32 /FILEALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /MACHINE:X86 /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DEBUG:GHASH /MLLVM:-exception-model=wineh /lldmap +NOOPT_CLANGPDB_IA32_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X86 /DEBUG:GHASH /MLLVM:-exception-model=wineh /lldmap NOOPT_CLANGPDB_IA32_DLINK2_FLAGS = ########################## @@ -1807,26 +1794,22 @@ NOOPT_CLANGPDB_IA32_DLINK2_FLAGS = *_CLANGPDB_X64_ASLCC_FLAGS = DEF(GCC_ASLCC_FLAGS) -m64 -fno-lto DEF(CLANGPDB_X64_TARGET) *_CLANGPDB_X64_ASM_FLAGS = DEF(GCC_ASM_FLAGS) -m64 DEF(CLANGPDB_X64_TARGET) -*_CLANGPDB_X64_OBJCOPY_FLAGS = -*_CLANGPDB_X64_NASM_FLAGS = -f win64 +*_CLANGPDB_X64_NASM_FLAGS = -f win64 -DRODATA_SECTION_NAME=.rdata *_CLANGPDB_X64_PP_FLAGS = DEF(GCC_PP_FLAGS) DEF(CLANGPDB_X64_TARGET) *_CLANGPDB_X64_ASLPP_FLAGS = DEF(GCC_ASLPP_FLAGS) DEF(CLANGPDB_X64_TARGET) *_CLANGPDB_X64_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) DEF(CLANGPDB_X64_TARGET) DEBUG_CLANGPDB_X64_CC_FLAGS = DEF(CLANGPDB_ALL_CC_FLAGS) -m64 "-DEFIAPI=__attribute__((ms_abi))" -mno-red-zone -mcmodel=small -Oz -flto DEF(CLANGPDB_X64_TARGET) -gcodeview -funwind-tables -DEBUG_CLANGPDB_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /ALIGN:32 /FILEALIGN:32 /Machine:X64 /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DEBUG:GHASH /MLLVM:-exception-model=wineh /lldmap +DEBUG_CLANGPDB_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X64 /DEBUG:GHASH /MLLVM:-exception-model=wineh /lldmap DEBUG_CLANGPDB_X64_DLINK2_FLAGS = -DEBUG_CLANGPDB_X64_GENFW_FLAGS = --keepexceptiontable RELEASE_CLANGPDB_X64_CC_FLAGS = DEF(CLANGPDB_ALL_CC_FLAGS) -m64 "-DEFIAPI=__attribute__((ms_abi))" -mno-red-zone -mcmodel=small -Oz -flto DEF(CLANGPDB_X64_TARGET) -fno-unwind-tables -RELEASE_CLANGPDB_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /IGNORE:4254 /OPT:REF /OPT:ICF=10 /ALIGN:32 /FILEALIGN:32 /SECTION:.xdata,D /SECTION:.pdata,D /Machine:X64 /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /MERGE:.rdata=.data /MLLVM:-exception-model=wineh /lldmap +RELEASE_CLANGPDB_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /IGNORE:4254 /MACHINE:X64 /MLLVM:-exception-model=wineh /lldmap RELEASE_CLANGPDB_X64_DLINK2_FLAGS = -RELEASE_CLANGPDB_X64_GENFW_FLAGS = NOOPT_CLANGPDB_X64_CC_FLAGS = DEF(CLANGPDB_ALL_CC_FLAGS) -m64 "-DEFIAPI=__attribute__((ms_abi))" -mno-red-zone -mcmodel=small -O0 DEF(CLANGPDB_X64_TARGET) -gcodeview -funwind-tables -NOOPT_CLANGPDB_X64_DLINK_FLAGS = /NOLOGO /NODEFAULTLIB /IGNORE:4001 /OPT:REF /OPT:ICF=10 /ALIGN:32 /FILEALIGN:32 /Machine:X64 /DLL /ENTRY:$(IMAGE_ENTRY_POINT) /SUBSYSTEM:EFI_BOOT_SERVICE_DRIVER /SAFESEH:NO /BASE:0 /DEBUG:GHASH /MLLVM:-exception-model=wineh /lldmap +NOOPT_CLANGPDB_X64_DLINK_FLAGS = DEF(MSFT_DLINK_COMMON) /MACHINE:X64 /DEBUG:GHASH /MLLVM:-exception-model=wineh /lldmap NOOPT_CLANGPDB_X64_DLINK2_FLAGS = -NOOPT_CLANGPDB_X64_GENFW_FLAGS = --keepexceptiontable #################################################################################### # @@ -1846,15 +1829,14 @@ NOOPT_CLANGPDB_X64_GENFW_FLAGS = --keepexceptiontable DEFINE CLANGDWARF_IA32_PREFIX = ENV(CLANG_BIN) DEFINE CLANGDWARF_X64_PREFIX = ENV(CLANG_BIN) +DEFINE CLANGDWARF_ARM_PREFIX = ENV(CLANG_BIN) +DEFINE CLANGDWARF_AARCH64_PREFIX = ENV(CLANG_BIN) # LLVM/CLANG doesn't support -n link option. So, it can't share the same IA32_X64_DLINK_COMMON flag. -# LLVM/CLANG doesn't support common page size. So, it can't share the same GccBase.lds script. -DEFINE CLANGDWARF_IA32_X64_DLINK_COMMON = -nostdlib -Wl,-q,--gc-sections -z max-page-size=0x40 -Wl,-z,notext -DEFINE CLANGDWARF_DLINK2_FLAGS_COMMON = -Wl,--script=$(EDK_TOOLS_PATH)/Scripts/ClangBase.lds -DEFINE CLANGDWARF_IA32_X64_ASLDLINK_FLAGS = DEF(CLANGDWARF_IA32_X64_DLINK_COMMON) -Wl,--defsym=PECOFF_HEADER_SIZE=0 DEF(CLANGDWARF_DLINK2_FLAGS_COMMON) -Wl,--entry,ReferenceAcpiTable -u ReferenceAcpiTable -DEFINE CLANGDWARF_IA32_X64_DLINK_FLAGS = DEF(CLANGDWARF_IA32_X64_DLINK_COMMON) -Wl,--entry,$(IMAGE_ENTRY_POINT) -u $(IMAGE_ENTRY_POINT) -Wl,-Map,$(DEST_DIR_DEBUG)/$(BASE_NAME).map,--whole-archive -Wl,-z,notext -DEFINE CLANGDWARF_IA32_DLINK2_FLAGS = -Wl,--defsym=PECOFF_HEADER_SIZE=0x220 DEF(CLANGDWARF_DLINK2_FLAGS_COMMON) -DEFINE CLANGDWARF_X64_DLINK2_FLAGS = -Wl,--defsym=PECOFF_HEADER_SIZE=0x228 DEF(CLANGDWARF_DLINK2_FLAGS_COMMON) +DEFINE CLANGDWARF_IA32_X64_DLINK_COMMON = -nostdlib -Wl,-q,--gc-sections DEF(GCC_ALIGN) -Wl,-z,notext,--defsym=ALIGNED_PE_HEADER_SIZE=0x400 DEF(DLINK_SCRIPT) +DEFINE CLANGDWARF_IA32_X64_ASLDLINK_FLAGS = DEF(CLANGDWARF_IA32_X64_DLINK_COMMON) -Wl,--entry,ReferenceAcpiTable -u ReferenceAcpiTable +DEFINE CLANGDWARF_IA32_X64_DLINK_FLAGS = DEF(CLANGDWARF_IA32_X64_DLINK_COMMON) -Wl,--entry,$(IMAGE_ENTRY_POINT) -u $(IMAGE_ENTRY_POINT) -Wl,-Map,$(DEST_DIR_DEBUG)/$(BASE_NAME).map,--whole-archive +DEFINE CLANGDWARF_IA32_DLINK2_FLAGS = -no-pie DEFINE CLANGDWARF_IA32_TARGET = -target i686-pc-linux-gnu DEFINE CLANGDWARF_X64_TARGET = -target x86_64-pc-linux-gnu @@ -1865,6 +1847,7 @@ DEFINE CLANGDWARF_ALL_CC_FLAGS = DEF(GCC48_ALL_CC_FLAGS) DEF(CLANGDWARF_ ########################### # CLANGDWARF IA32 definitions ########################### +*_CLANGDWARF_IA32_OBJCOPY_PATH = DEF(CLANGDWARF_IA32_PREFIX)llvm-objcopy *_CLANGDWARF_IA32_CC_PATH = DEF(CLANGDWARF_IA32_PREFIX)clang *_CLANGDWARF_IA32_SLINK_PATH = DEF(CLANGDWARF_IA32_PREFIX)llvm-ar *_CLANGDWARF_IA32_DLINK_PATH = DEF(CLANGDWARF_IA32_PREFIX)clang @@ -1879,28 +1862,27 @@ DEFINE CLANGDWARF_ALL_CC_FLAGS = DEF(GCC48_ALL_CC_FLAGS) DEF(CLANGDWARF_ *_CLANGDWARF_IA32_ASLCC_FLAGS = DEF(GCC_ASLCC_FLAGS) -m32 -fno-lto DEF(CLANGDWARF_IA32_TARGET) *_CLANGDWARF_IA32_ASLDLINK_FLAGS = DEF(CLANGDWARF_IA32_X64_ASLDLINK_FLAGS) -Wl,-m,elf_i386 -fuse-ld=lld -no-pie *_CLANGDWARF_IA32_ASM_FLAGS = DEF(GCC5_ASM_FLAGS) -m32 -march=i386 DEF(CLANGDWARF_IA32_TARGET) -*_CLANGDWARF_IA32_RC_FLAGS = DEF(GCC_IA32_RC_FLAGS) -*_CLANGDWARF_IA32_OBJCOPY_FLAGS = -*_CLANGDWARF_IA32_NASM_FLAGS = -f elf32 +*_CLANGDWARF_IA32_NASM_FLAGS = -f elf32 -DRODATA_SECTION_NAME=.rodata *_CLANGDWARF_IA32_PP_FLAGS = DEF(GCC_PP_FLAGS) DEF(CLANGDWARF_IA32_TARGET) *_CLANGDWARF_IA32_ASLPP_FLAGS = DEF(GCC_ASLPP_FLAGS) DEF(CLANGDWARF_IA32_TARGET) *_CLANGDWARF_IA32_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) DEF(CLANGDWARF_IA32_TARGET) -DEBUG_CLANGDWARF_IA32_CC_FLAGS = DEF(CLANGDWARF_ALL_CC_FLAGS) -fno-pic -fno-pie -m32 -Oz -flto -march=i586 DEF(CLANGDWARF_IA32_TARGET) -g -malign-double +DEBUG_CLANGDWARF_IA32_CC_FLAGS = DEF(CLANGDWARF_ALL_CC_FLAGS) -m32 -malign-double -Oz -flto -march=i586 DEF(CLANGDWARF_IA32_TARGET) -g -fno-pic -fno-pie DEBUG_CLANGDWARF_IA32_DLINK_FLAGS = DEF(CLANGDWARF_IA32_X64_DLINK_FLAGS) -flto -Wl,-O3 -Wl,-melf_i386 -Wl,--oformat,elf32-i386 DEBUG_CLANGDWARF_IA32_DLINK2_FLAGS = DEF(CLANGDWARF_IA32_DLINK2_FLAGS) -O3 -fuse-ld=lld -no-pie -RELEASE_CLANGDWARF_IA32_CC_FLAGS = DEF(CLANGDWARF_ALL_CC_FLAGS) -fno-pic -fno-pie -m32 -Oz -flto -march=i586 DEF(CLANGDWARF_IA32_TARGET) -malign-double +RELEASE_CLANGDWARF_IA32_CC_FLAGS = DEF(CLANGDWARF_ALL_CC_FLAGS) -m32 -malign-double -Oz -flto -march=i586 DEF(CLANGDWARF_IA32_TARGET) -fno-pic -fno-pie RELEASE_CLANGDWARF_IA32_DLINK_FLAGS = DEF(CLANGDWARF_IA32_X64_DLINK_FLAGS) -flto -Wl,-O3 -Wl,-melf_i386 -Wl,--oformat,elf32-i386 RELEASE_CLANGDWARF_IA32_DLINK2_FLAGS = DEF(CLANGDWARF_IA32_DLINK2_FLAGS) -O3 -fuse-ld=lld -no-pie -NOOPT_CLANGDWARF_IA32_CC_FLAGS = DEF(CLANGDWARF_ALL_CC_FLAGS) -fno-pic -fno-pie -m32 -O0 -march=i586 DEF(CLANGDWARF_IA32_TARGET) -g -malign-double +NOOPT_CLANGDWARF_IA32_CC_FLAGS = DEF(CLANGDWARF_ALL_CC_FLAGS) -m32 -malign-double -O0 -march=i586 DEF(CLANGDWARF_IA32_TARGET) -g -fno-pic -fno-pie NOOPT_CLANGDWARF_IA32_DLINK_FLAGS = DEF(CLANGDWARF_IA32_X64_DLINK_FLAGS) -Wl,-O0 -Wl,-melf_i386 -Wl,--oformat,elf32-i386 NOOPT_CLANGDWARF_IA32_DLINK2_FLAGS = DEF(CLANGDWARF_IA32_DLINK2_FLAGS) -O0 -fuse-ld=lld -no-pie ########################## # CLANGDWARF X64 definitions ########################## +*_CLANGDWARF_X64_OBJCOPY_PATH = DEF(CLANGDWARF_X64_PREFIX)llvm-objcopy *_CLANGDWARF_X64_CC_PATH = DEF(CLANGDWARF_X64_PREFIX)clang *_CLANGDWARF_X64_SLINK_PATH = DEF(CLANGDWARF_X64_PREFIX)llvm-ar *_CLANGDWARF_X64_DLINK_PATH = DEF(CLANGDWARF_X64_PREFIX)clang @@ -1915,31 +1897,29 @@ NOOPT_CLANGDWARF_IA32_DLINK2_FLAGS = DEF(CLANGDWARF_IA32_DLINK2_FLAGS) -O0 - *_CLANGDWARF_X64_ASLCC_FLAGS = DEF(GCC_ASLCC_FLAGS) -m64 -fno-lto DEF(CLANGDWARF_X64_TARGET) *_CLANGDWARF_X64_ASLDLINK_FLAGS = DEF(CLANGDWARF_IA32_X64_ASLDLINK_FLAGS) -Wl,-m,elf_x86_64 -fuse-ld=lld *_CLANGDWARF_X64_ASM_FLAGS = DEF(GCC5_ASM_FLAGS) -m64 DEF(CLANGDWARF_X64_TARGET) -*_CLANGDWARF_X64_RC_FLAGS = DEF(GCC_X64_RC_FLAGS) -*_CLANGDWARF_X64_OBJCOPY_FLAGS = -*_CLANGDWARF_X64_NASM_FLAGS = -f elf64 +*_CLANGDWARF_X64_NASM_FLAGS = -f elf64 -DRODATA_SECTION_NAME=.rodata *_CLANGDWARF_X64_PP_FLAGS = DEF(GCC_PP_FLAGS) DEF(CLANGDWARF_X64_TARGET) *_CLANGDWARF_X64_ASLPP_FLAGS = DEF(GCC_ASLPP_FLAGS) DEF(CLANGDWARF_X64_TARGET) *_CLANGDWARF_X64_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) DEF(CLANGDWARF_X64_TARGET) DEBUG_CLANGDWARF_X64_CC_FLAGS = DEF(CLANGDWARF_ALL_CC_FLAGS) -m64 "-DEFIAPI=__attribute__((ms_abi))" -mno-red-zone -mcmodel=small -fpie -fdirect-access-external-data -Oz -flto DEF(CLANGDWARF_X64_TARGET) -g DEBUG_CLANGDWARF_X64_DLINK_FLAGS = DEF(CLANGDWARF_IA32_X64_DLINK_FLAGS) -flto -Wl,-O3 -Wl,-melf_x86_64 -Wl,--oformat,elf64-x86-64 -Wl,-pie -mcmodel=small -Wl,--apply-dynamic-relocs -DEBUG_CLANGDWARF_X64_DLINK2_FLAGS = DEF(CLANGDWARF_X64_DLINK2_FLAGS) -O3 -fuse-ld=lld +DEBUG_CLANGDWARF_X64_DLINK2_FLAGS = -O3 -fuse-ld=lld RELEASE_CLANGDWARF_X64_CC_FLAGS = DEF(CLANGDWARF_ALL_CC_FLAGS) -m64 "-DEFIAPI=__attribute__((ms_abi))" -mno-red-zone -mcmodel=small -fpie -fdirect-access-external-data -Oz -flto DEF(CLANGDWARF_X64_TARGET) RELEASE_CLANGDWARF_X64_DLINK_FLAGS = DEF(CLANGDWARF_IA32_X64_DLINK_FLAGS) -flto -Wl,-O3 -Wl,-melf_x86_64 -Wl,--oformat,elf64-x86-64 -Wl,-pie -mcmodel=small -Wl,--apply-dynamic-relocs -RELEASE_CLANGDWARF_X64_DLINK2_FLAGS = DEF(CLANGDWARF_X64_DLINK2_FLAGS) -O3 -fuse-ld=lld +RELEASE_CLANGDWARF_X64_DLINK2_FLAGS = -O3 -fuse-ld=lld NOOPT_CLANGDWARF_X64_CC_FLAGS = DEF(CLANGDWARF_ALL_CC_FLAGS) -m64 "-DEFIAPI=__attribute__((ms_abi))" -mno-red-zone -mcmodel=small -fpie -fdirect-access-external-data -O0 DEF(CLANGDWARF_X64_TARGET) -g NOOPT_CLANGDWARF_X64_DLINK_FLAGS = DEF(CLANGDWARF_IA32_X64_DLINK_FLAGS) -Wl,-O0 -Wl,-melf_x86_64 -Wl,--oformat,elf64-x86-64 -Wl,-pie -mcmodel=small -Wl,--apply-dynamic-relocs -NOOPT_CLANGDWARF_X64_DLINK2_FLAGS = DEF(CLANGDWARF_X64_DLINK2_FLAGS) -O0 -fuse-ld=lld +NOOPT_CLANGDWARF_X64_DLINK2_FLAGS = -O0 -fuse-ld=lld ################## # CLANGDWARF ARM definitions ################## DEFINE CLANGDWARF_ARM_TARGET = -target arm-linux-gnueabi DEFINE CLANGDWARF_ARM_CC_FLAGS = DEF(GCC_ARM_CC_FLAGS) DEF(CLANGDWARF_ARM_TARGET) DEF(CLANGDWARF_WARNING_OVERRIDES) -mno-movt -DEFINE CLANGDWARF_ARM_DLINK_FLAGS = DEF(CLANGDWARF_ARM_TARGET) DEF(GCC_ARM_DLINK_FLAGS) +DEFINE CLANGDWARF_ARM_DLINK_FLAGS = DEF(CLANGDWARF_ARM_TARGET) DEF(GCC_ARM_DLINK_FLAGS) -fuse-ld=lld -Wl,--apply-dynamic-relocs,--no-pie,--no-relax *_CLANGDWARF_ARM_PP_FLAGS = DEF(GCC_PP_FLAGS) *_CLANGDWARF_ARM_ASLCC_FLAGS = DEF(GCC_ASLCC_FLAGS) @@ -1948,42 +1928,40 @@ DEFINE CLANGDWARF_ARM_DLINK_FLAGS = DEF(CLANGDWARF_ARM_TARGET) DEF(GCC_ARM_DLI *_CLANGDWARF_ARM_ASL_OUTFLAGS = DEF(IASL_OUTFLAGS) *_CLANGDWARF_ARM_DTCPP_FLAGS = DEF(GCC_DTCPP_FLAGS) -*_CLANGDWARF_ARM_CC_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_ARM_ASM_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_ARM_PP_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_ARM_VFRPP_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_ARM_ASLCC_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_ARM_ASLPP_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_ARM_DLINK_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_ARM_ASLDLINK_PATH = ENV(CLANGDWARF_BIN)clang - -*_CLANGDWARF_ARM_SLINK_PATH = ENV(CLANGDWARF_BIN)llvm-ar -*_CLANGDWARF_ARM_RC_PATH = ENV(CLANGDWARF_BIN)llvm-objcopy +*_CLANGDWARF_ARM_OBJCOPY_PATH = DEF(CLANGDWARF_ARM_PREFIX)llvm-objcopy +*_CLANGDWARF_ARM_CC_PATH = DEF(CLANGDWARF_ARM_PREFIX)clang +*_CLANGDWARF_ARM_ASM_PATH = DEF(CLANGDWARF_ARM_PREFIX)clang +*_CLANGDWARF_ARM_PP_PATH = DEF(CLANGDWARF_ARM_PREFIX)clang +*_CLANGDWARF_ARM_VFRPP_PATH = DEF(CLANGDWARF_ARM_PREFIX)clang +*_CLANGDWARF_ARM_ASLCC_PATH = DEF(CLANGDWARF_ARM_PREFIX)clang +*_CLANGDWARF_ARM_ASLPP_PATH = DEF(CLANGDWARF_ARM_PREFIX)clang +*_CLANGDWARF_ARM_DLINK_PATH = DEF(CLANGDWARF_ARM_PREFIX)clang +*_CLANGDWARF_ARM_ASLDLINK_PATH = DEF(CLANGDWARF_ARM_PREFIX)clang +*_CLANGDWARF_ARM_SLINK_PATH = DEF(CLANGDWARF_ARM_PREFIX)llvm-ar +*_CLANGDWARF_ARM_RC_PATH = DEF(CLANGDWARF_ARM_PREFIX)llvm-objcopy *_CLANGDWARF_ARM_ASLCC_FLAGS = DEF(GCC_ASLCC_FLAGS) -fno-lto -*_CLANGDWARF_ARM_ASLDLINK_FLAGS = DEF(CLANGDWARF_ARM_TARGET) DEF(GCC_ARM_ASLDLINK_FLAGS) -*_CLANGDWARF_ARM_ASM_FLAGS = DEF(GCC_ASM_FLAGS) DEF(CLANGDWARF_ARM_TARGET) $(PLATFORM_FLAGS) -Qunused-arguments -*_CLANGDWARF_ARM_DLINK2_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) -Wl,--defsym=PECOFF_HEADER_SIZE=0x220 -*_CLANGDWARF_ARM_PLATFORM_FLAGS = -march=armv7-a -*_CLANGDWARF_ARM_PP_FLAGS = DEF(GCC_PP_FLAGS) DEF(CLANGDWARF_ARM_TARGET) $(PLATFORM_FLAGS) -*_CLANGDWARF_ARM_RC_FLAGS = DEF(GCC_ARM_RC_FLAGS) -*_CLANGDWARF_ARM_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) DEF(CLANGDWARF_ARM_TARGET) $(PLATFORM_FLAGS) +*_CLANGDWARF_ARM_ASLDLINK_FLAGS = DEF(CLANGDWARF_ARM_TARGET) DEF(GCC_ARM_ASLDLINK_FLAGS) -fuse-ld=lld +*_CLANGDWARF_ARM_ASM_FLAGS = DEF(GCC_ASM_FLAGS) DEF(CLANGDWARF_ARM_TARGET) -march=armv7-a -Qunused-arguments +*_CLANGDWARF_ARM_DLINK2_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) +*_CLANGDWARF_ARM_PP_FLAGS = DEF(GCC_PP_FLAGS) DEF(CLANGDWARF_ARM_TARGET) -march=armv7-a +*_CLANGDWARF_ARM_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) DEF(CLANGDWARF_ARM_TARGET) -march=armv7-a *_CLANGDWARF_ARM_ASLPP_FLAGS = DEF(GCC_ASLPP_FLAGS) DEF(CLANGDWARF_ARM_TARGET) *_CLANGDWARF_ARM_CC_XIPFLAGS = DEF(GCC_ARM_CC_XIPFLAGS) - DEBUG_CLANGDWARF_ARM_CC_FLAGS = DEF(CLANGDWARF_ARM_CC_FLAGS) $(PLATFORM_FLAGS) -flto -O1 - DEBUG_CLANGDWARF_ARM_DLINK_FLAGS = DEF(CLANGDWARF_ARM_DLINK_FLAGS) -flto -Wl,-O1 -fuse-ld=lld -L$(WORKSPACE)/ArmPkg/Library/GccLto -llto-arm -Wl,-plugin-opt=-pass-through=-llto-arm -Wl,--no-pie,--no-relax - NOOPT_CLANGDWARF_ARM_CC_FLAGS = DEF(CLANGDWARF_ARM_CC_FLAGS) $(PLATFORM_FLAGS) -O0 - NOOPT_CLANGDWARF_ARM_DLINK_FLAGS = DEF(CLANGDWARF_ARM_DLINK_FLAGS) -fuse-ld=lld -Wl,--no-pie,--no-relax -RELEASE_CLANGDWARF_ARM_CC_FLAGS = DEF(CLANGDWARF_ARM_CC_FLAGS) $(PLATFORM_FLAGS) -flto -O3 -RELEASE_CLANGDWARF_ARM_DLINK_FLAGS = DEF(CLANGDWARF_ARM_DLINK_FLAGS) -flto -Wl,-O3 -fuse-ld=lld -L$(WORKSPACE)/ArmPkg/Library/GccLto -llto-arm -Wl,-plugin-opt=-pass-through=-llto-arm -Wl,--no-pie,--no-relax + DEBUG_CLANGDWARF_ARM_CC_FLAGS = DEF(CLANGDWARF_ARM_CC_FLAGS) -flto -O1 + DEBUG_CLANGDWARF_ARM_DLINK_FLAGS = DEF(CLANGDWARF_ARM_DLINK_FLAGS) -flto -Wl,-O1 -L$(WORKSPACE)/ArmPkg/Library/GccLto -llto-arm -Wl,-plugin-opt=-pass-through=-llto-arm + NOOPT_CLANGDWARF_ARM_CC_FLAGS = DEF(CLANGDWARF_ARM_CC_FLAGS) -O0 + NOOPT_CLANGDWARF_ARM_DLINK_FLAGS = DEF(CLANGDWARF_ARM_DLINK_FLAGS) +RELEASE_CLANGDWARF_ARM_CC_FLAGS = DEF(CLANGDWARF_ARM_CC_FLAGS) -flto -O3 +RELEASE_CLANGDWARF_ARM_DLINK_FLAGS = DEF(CLANGDWARF_ARM_DLINK_FLAGS) -flto -Wl,-O3 -L$(WORKSPACE)/ArmPkg/Library/GccLto -llto-arm -Wl,-plugin-opt=-pass-through=-llto-arm ################## # CLANGDWARF AARCH64 definitions ################## DEFINE CLANGDWARF_AARCH64_TARGET = -target aarch64-linux-gnu DEFINE CLANGDWARF_AARCH64_CC_FLAGS = DEF(GCC_AARCH64_CC_FLAGS) DEF(CLANGDWARF_AARCH64_TARGET) -mcmodel=small DEF(CLANGDWARF_WARNING_OVERRIDES) -DEFINE CLANGDWARF_AARCH64_DLINK_FLAGS = DEF(CLANGDWARF_AARCH64_TARGET) DEF(GCC_AARCH64_DLINK_FLAGS) -z common-page-size=0x1000 +DEFINE CLANGDWARF_AARCH64_DLINK_FLAGS = DEF(CLANGDWARF_AARCH64_TARGET) DEF(GCC_AARCH64_DLINK_FLAGS) DEF(GCC_ALIGN) -fuse-ld=lld -Wl,--apply-dynamic-relocs,--no-pie,--no-relax *_CLANGDWARF_AARCH64_PP_FLAGS = DEF(GCC_PP_FLAGS) *_CLANGDWARF_AARCH64_ASLCC_FLAGS = DEF(GCC_ASLCC_FLAGS) @@ -1992,37 +1970,35 @@ DEFINE CLANGDWARF_AARCH64_DLINK_FLAGS = DEF(CLANGDWARF_AARCH64_TARGET) DEF(GCC_ *_CLANGDWARF_AARCH64_ASL_OUTFLAGS = DEF(IASL_OUTFLAGS) *_CLANGDWARF_AARCH64_DTCPP_FLAGS = DEF(GCC_DTCPP_FLAGS) -*_CLANGDWARF_AARCH64_CC_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_AARCH64_ASM_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_AARCH64_PP_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_AARCH64_VFRPP_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_AARCH64_ASLCC_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_AARCH64_ASLPP_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_AARCH64_DLINK_PATH = ENV(CLANGDWARF_BIN)clang -*_CLANGDWARF_AARCH64_ASLDLINK_PATH = ENV(CLANGDWARF_BIN)clang - -*_CLANGDWARF_AARCH64_SLINK_PATH = ENV(CLANGDWARF_BIN)llvm-ar -*_CLANGDWARF_AARCH64_RC_PATH = ENV(CLANGDWARF_BIN)llvm-objcopy +*_CLANGDWARF_AARCH64_OBJCOPY_PATH = DEF(CLANGDWARF_AARCH64_PREFIX)llvm-objcopy +*_CLANGDWARF_AARCH64_CC_PATH = DEF(CLANGDWARF_AARCH64_PREFIX)clang +*_CLANGDWARF_AARCH64_ASM_PATH = DEF(CLANGDWARF_AARCH64_PREFIX)clang +*_CLANGDWARF_AARCH64_PP_PATH = DEF(CLANGDWARF_AARCH64_PREFIX)clang +*_CLANGDWARF_AARCH64_VFRPP_PATH = DEF(CLANGDWARF_AARCH64_PREFIX)clang +*_CLANGDWARF_AARCH64_ASLCC_PATH = DEF(CLANGDWARF_AARCH64_PREFIX)clang +*_CLANGDWARF_AARCH64_ASLPP_PATH = DEF(CLANGDWARF_AARCH64_PREFIX)clang +*_CLANGDWARF_AARCH64_DLINK_PATH = DEF(CLANGDWARF_AARCH64_PREFIX)clang +*_CLANGDWARF_AARCH64_ASLDLINK_PATH = DEF(CLANGDWARF_AARCH64_PREFIX)clang +*_CLANGDWARF_AARCH64_SLINK_PATH = DEF(CLANGDWARF_AARCH64_PREFIX)llvm-ar +*_CLANGDWARF_AARCH64_RC_PATH = DEF(CLANGDWARF_AARCH64_PREFIX)llvm-objcopy *_CLANGDWARF_AARCH64_ASLCC_FLAGS = DEF(GCC_ASLCC_FLAGS) -fno-lto -*_CLANGDWARF_AARCH64_ASLDLINK_FLAGS = DEF(CLANGDWARF_AARCH64_TARGET) DEF(GCC_AARCH64_ASLDLINK_FLAGS) -*_CLANGDWARF_AARCH64_ASM_FLAGS = DEF(GCC_ASM_FLAGS) DEF(CLANGDWARF_AARCH64_TARGET) $(PLATFORM_FLAGS) -Qunused-arguments -*_CLANGDWARF_AARCH64_DLINK_FLAGS = DEF(CLANGDWARF_AARCH64_TARGET) DEF(GCC_AARCH64_DLINK_FLAGS) -z common-page-size=0x1000 -*_CLANGDWARF_AARCH64_DLINK_XIPFLAGS = -z common-page-size=0x20 -*_CLANGDWARF_AARCH64_DLINK2_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) -Wl,--defsym=PECOFF_HEADER_SIZE=0x228 -*_CLANGDWARF_AARCH64_PLATFORM_FLAGS = -*_CLANGDWARF_AARCH64_PP_FLAGS = DEF(GCC_PP_FLAGS) DEF(CLANGDWARF_AARCH64_TARGET) $(PLATFORM_FLAGS) -*_CLANGDWARF_AARCH64_RC_FLAGS = DEF(GCC_AARCH64_RC_FLAGS) DEF(GCC_AARCH64_RC_BTI_FLAGS) -*_CLANGDWARF_AARCH64_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) DEF(CLANGDWARF_AARCH64_TARGET) $(PLATFORM_FLAGS) +*_CLANGDWARF_AARCH64_ASLDLINK_FLAGS = DEF(CLANGDWARF_AARCH64_TARGET) DEF(GCC_AARCH64_ASLDLINK_FLAGS) -fuse-ld=lld +*_CLANGDWARF_AARCH64_ASM_FLAGS = DEF(GCC_ASM_FLAGS) DEF(CLANGDWARF_AARCH64_TARGET) -Qunused-arguments +*_CLANGDWARF_AARCH64_DLINK_FLAGS = DEF(CLANGDWARF_AARCH64_TARGET) DEF(GCC_AARCH64_DLINK_FLAGS) DEF(GCC_ALIGN) +*_CLANGDWARF_AARCH64_DLINK_XIPFLAGS = DEF(GCC_ALIGN) +*_CLANGDWARF_AARCH64_DLINK2_FLAGS = DEF(GCC_DLINK2_FLAGS_COMMON) +*_CLANGDWARF_AARCH64_PP_FLAGS = DEF(GCC_PP_FLAGS) DEF(CLANGDWARF_AARCH64_TARGET) +*_CLANGDWARF_AARCH64_VFRPP_FLAGS = DEF(GCC_VFRPP_FLAGS) DEF(CLANGDWARF_AARCH64_TARGET) *_CLANGDWARF_AARCH64_ASLPP_FLAGS = DEF(GCC_ASLPP_FLAGS) DEF(CLANGDWARF_AARCH64_TARGET) *_CLANGDWARF_AARCH64_CC_XIPFLAGS = -mstrict-align - DEBUG_CLANGDWARF_AARCH64_CC_FLAGS = DEF(CLANGDWARF_AARCH64_CC_FLAGS) $(PLATFORM_FLAGS) -flto -O1 - DEBUG_CLANGDWARF_AARCH64_DLINK_FLAGS = DEF(CLANGDWARF_AARCH64_DLINK_FLAGS) -flto -Wl,-O1 -fuse-ld=lld -L$(WORKSPACE)/ArmPkg/Library/GccLto -llto-aarch64 -Wl,-plugin-opt=-pass-through=-llto-aarch64 -Wl,--no-pie,--no-relax - NOOPT_CLANGDWARF_AARCH64_CC_FLAGS = DEF(CLANGDWARF_AARCH64_CC_FLAGS) $(PLATFORM_FLAGS) -O0 - NOOPT_CLANGDWARF_AARCH64_DLINK_FLAGS = DEF(CLANGDWARF_AARCH64_DLINK_FLAGS) -fuse-ld=lld -Wl,--no-pie,--no-relax -RELEASE_CLANGDWARF_AARCH64_CC_FLAGS = DEF(CLANGDWARF_AARCH64_CC_FLAGS) $(PLATFORM_FLAGS) -flto -O3 -RELEASE_CLANGDWARF_AARCH64_DLINK_FLAGS = DEF(CLANGDWARF_AARCH64_DLINK_FLAGS) -flto -Wl,-O3 -fuse-ld=lld -L$(WORKSPACE)/ArmPkg/Library/GccLto -llto-aarch64 -Wl,-plugin-opt=-pass-through=-llto-aarch64 -Wl,--no-pie,--no-relax + DEBUG_CLANGDWARF_AARCH64_CC_FLAGS = DEF(CLANGDWARF_AARCH64_CC_FLAGS) -flto -O1 + DEBUG_CLANGDWARF_AARCH64_DLINK_FLAGS = DEF(CLANGDWARF_AARCH64_DLINK_FLAGS) -flto -Wl,-O1 -L$(WORKSPACE)/ArmPkg/Library/GccLto -llto-aarch64 -Wl,-plugin-opt=-pass-through=-llto-aarch64 + NOOPT_CLANGDWARF_AARCH64_CC_FLAGS = DEF(CLANGDWARF_AARCH64_CC_FLAGS) -O0 + NOOPT_CLANGDWARF_AARCH64_DLINK_FLAGS = DEF(CLANGDWARF_AARCH64_DLINK_FLAGS) +RELEASE_CLANGDWARF_AARCH64_CC_FLAGS = DEF(CLANGDWARF_AARCH64_CC_FLAGS) -flto -O3 +RELEASE_CLANGDWARF_AARCH64_DLINK_FLAGS = DEF(CLANGDWARF_AARCH64_DLINK_FLAGS) -flto -Wl,-O3 -L$(WORKSPACE)/ArmPkg/Library/GccLto -llto-aarch64 -Wl,-plugin-opt=-pass-through=-llto-aarch64 ################## # CLANGDWARF RISCV64 definitions @@ -2099,14 +2075,28 @@ RELEASE_CLANGDWARF_RISCV64_DLINK_FLAGS = DEF(CLANGDWARF_RISCV64_DLINK_FLAGS) -fl *_XCODE5_*_ASLPP_PATH = clang *_XCODE5_*_ASLDLINK_PATH = ld *_XCODE5_*_DSYMUTIL_PATH = /usr/bin/dsymutil -*_XCODE5_*_MTOC_PATH = /usr/local/bin/mtoc +*_XCODE5_*_MTOC_PATH = ENV(MTOC_PREFIX)mtoc *_XCODE5_*_DEPS_FLAGS = DEF(GCC_DEPS_FLAGS) +# +# x86_64 Preload Mach-O files index relocations relative to the first writable +# section, usually in __DATA. Merging __DATA,__const, which may have relocations +# targeting it, into __TEXT moves it in front of __DATA, yielding negative +# offsets to the relocation base address. These cannot be represented by the +# Mach-O relocation offsets, resulting in a broken binary. +# To work around this, introduce a new 0-sized segment __RO_RELOCS segment with +# RW permissions, which will make all relocations relative to the beginning of +# image. This also makes the usage of "-read_only_relocs suppress" safe, as +# relocations can now target __TEXT without triggering the same issue. +# +DEFINE XCODE5_RORELOCS_ARGS = -segprot __RO_RELOCS rw- rw- -segment_order __RO_RELOCS:__TEXT:__DATA_CONST:__DATA -rename_section __TEXT __text __RO_RELOCS __text -rename_section __RO_RELOCS __text __TEXT __text +DEFINE XCODE5_RODATA_ARGS = DEF(XCODE5_RORELOCS_ARGS) -segprot __DATA_CONST r-- r-- -rename_section __DATA __const __DATA_CONST __const -rename_section __TEXT __const __DATA_CONST __text_const -rename_section __TEXT __cstring __DATA_CONST __cstring -rename_section __TEXT __ustring __DATA_CONST __ustring + ################## # ASL definitions ################## *_XCODE5_*_ASLCC_FLAGS = -x c -save-temps -g -O0 -fshort-wchar -fno-strict-aliasing -Wall -Werror -Wno-missing-braces -c -include AutoGen.h -*_XCODE5_*_ASLDLINK_FLAGS = -e _ReferenceAcpiTable -preload -segalign 0x20 -pie -seg1addr 0x240 -read_only_relocs suppress -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map +*_XCODE5_*_ASLDLINK_FLAGS = DEF(XCODE5_RODATA_ARGS) -e _ReferenceAcpiTable -preload -segalign DEF(XCODE_ALIGN) -pie -seg1addr DEF(XCODE_ADDR) -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map *_XCODE5_*_ASLPP_FLAGS = -x c -E -include AutoGen.h *_XCODE5_*_ASL_FLAGS = *_XCODE5_*_ASL_OUTFLAGS = DEF(IASL_OUTFLAGS) @@ -2115,46 +2105,46 @@ RELEASE_CLANGDWARF_RISCV64_DLINK_FLAGS = DEF(CLANGDWARF_RISCV64_DLINK_FLAGS) -fl # MTOC definitions ################## - DEBUG_XCODE5_*_MTOC_FLAGS = -align 0x20 -d $(DEBUG_DIR)/$(MODULE_NAME).dll - NOOPT_XCODE5_*_MTOC_FLAGS = -align 0x20 -d $(DEBUG_DIR)/$(MODULE_NAME).dll -RELEASE_XCODE5_*_MTOC_FLAGS = -align 0x20 + DEBUG_XCODE5_*_MTOC_FLAGS = -align DEF(XCODE_ALIGN) -d $(DEBUG_DIR)/$(MODULE_NAME).dll -require_read_only_relocs + NOOPT_XCODE5_*_MTOC_FLAGS = -align DEF(XCODE_ALIGN) -d $(DEBUG_DIR)/$(MODULE_NAME).dll -require_read_only_relocs +RELEASE_XCODE5_*_MTOC_FLAGS = -align DEF(XCODE_ALIGN) -require_read_only_relocs #################### # IA-32 definitions #################### - DEBUG_XCODE5_IA32_DLINK_FLAGS = -arch i386 -u _$(IMAGE_ENTRY_POINT) -e _$(IMAGE_ENTRY_POINT) -preload -segalign 0x20 -pie -all_load -dead_strip -seg1addr 0x240 -read_only_relocs suppress -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map - NOOPT_XCODE5_IA32_DLINK_FLAGS = -arch i386 -u _$(IMAGE_ENTRY_POINT) -e _$(IMAGE_ENTRY_POINT) -preload -segalign 0x20 -pie -all_load -dead_strip -seg1addr 0x240 -read_only_relocs suppress -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map -RELEASE_XCODE5_IA32_DLINK_FLAGS = -arch i386 -u _$(IMAGE_ENTRY_POINT) -e _$(IMAGE_ENTRY_POINT) -preload -segalign 0x20 -pie -all_load -dead_strip -seg1addr 0x240 -read_only_relocs suppress -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map + DEBUG_XCODE5_IA32_DLINK_FLAGS = DEF(XCODE5_RODATA_ARGS) -arch i386 -u _$(IMAGE_ENTRY_POINT) -e _$(IMAGE_ENTRY_POINT) -preload -segalign DEF(XCODE_ALIGN) -pie -all_load -dead_strip -seg1addr DEF(XCODE_ADDR) -read_only_relocs suppress -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map DEF(XCODE_MERGE) + NOOPT_XCODE5_IA32_DLINK_FLAGS = DEF(XCODE5_RODATA_ARGS) -arch i386 -u _$(IMAGE_ENTRY_POINT) -e _$(IMAGE_ENTRY_POINT) -preload -segalign DEF(XCODE_ALIGN) -pie -all_load -dead_strip -seg1addr DEF(XCODE_ADDR) -read_only_relocs suppress -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map DEF(XCODE_MERGE) +RELEASE_XCODE5_IA32_DLINK_FLAGS = DEF(XCODE5_RODATA_ARGS) -arch i386 -u _$(IMAGE_ENTRY_POINT) -e _$(IMAGE_ENTRY_POINT) -preload -segalign DEF(XCODE_ALIGN) -pie -all_load -dead_strip -seg1addr DEF(XCODE_ADDR) -read_only_relocs suppress -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map DEF(XCODE_MERGE) *_XCODE5_IA32_SLINK_FLAGS = -static -o DEBUG_XCODE5_IA32_ASM_FLAGS = -arch i386 -g NOOPT_XCODE5_IA32_ASM_FLAGS = -arch i386 -g RELEASE_XCODE5_IA32_ASM_FLAGS = -arch i386 - *_XCODE5_IA32_NASM_FLAGS = -f macho32 + *_XCODE5_IA32_NASM_FLAGS = -f macho32 -DRODATA_SECTION_NAME=.rodata - DEBUG_XCODE5_IA32_CC_FLAGS = -arch i386 -c -g -Os -Wall -Werror -include AutoGen.h -funsigned-char -fno-stack-protector -fno-builtin -fshort-wchar -fasm-blocks -mdynamic-no-pic -mno-implicit-float -mms-bitfields -msoft-float -Wno-unused-parameter -Wno-missing-braces -Wno-missing-field-initializers -Wno-tautological-compare -Wno-sign-compare -Wno-varargs -ftrap-function=undefined_behavior_has_been_optimized_away_by_clang $(PLATFORM_FLAGS) -RELEASE_XCODE5_IA32_CC_FLAGS = -arch i386 -c -Os -Wall -Werror -include AutoGen.h -funsigned-char -fno-stack-protector -fno-builtin -fshort-wchar -fasm-blocks -mdynamic-no-pic -mno-implicit-float -mms-bitfields -msoft-float -Wno-unused-parameter -Wno-missing-braces -Wno-missing-field-initializers -Wno-tautological-compare -Wno-sign-compare -Wno-varargs -Wno-unused-const-variable -ftrap-function=undefined_behavior_has_been_optimized_away_by_clang $(PLATFORM_FLAGS) - NOOPT_XCODE5_IA32_CC_FLAGS = -arch i386 -c -g -O0 -Wall -Werror -include AutoGen.h -funsigned-char -fno-stack-protector -fno-builtin -fshort-wchar -fasm-blocks -mdynamic-no-pic -mno-implicit-float -mms-bitfields -msoft-float -Wno-unused-parameter -Wno-missing-braces -Wno-missing-field-initializers -Wno-tautological-compare -Wno-sign-compare -Wno-varargs -ftrap-function=undefined_behavior_has_been_optimized_away_by_clang $(PLATFORM_FLAGS) + DEBUG_XCODE5_IA32_CC_FLAGS = -arch i386 -c -g -Os -Wall -Werror -include AutoGen.h -funsigned-char -fno-stack-protector -fno-builtin -fshort-wchar -fasm-blocks -mdynamic-no-pic -mno-implicit-float -mms-bitfields -msoft-float -Wno-unused-parameter -Wno-missing-braces -Wno-missing-field-initializers -Wno-tautological-compare -Wno-sign-compare -Wno-varargs -Wno-unknown-warning-option -ftrap-function=undefined_behavior_has_been_optimized_away_by_clang +RELEASE_XCODE5_IA32_CC_FLAGS = -arch i386 -c -Os -Wall -Werror -include AutoGen.h -funsigned-char -fno-stack-protector -fno-builtin -fshort-wchar -fasm-blocks -mdynamic-no-pic -mno-implicit-float -mms-bitfields -msoft-float -Wno-unused-parameter -Wno-missing-braces -Wno-missing-field-initializers -Wno-tautological-compare -Wno-sign-compare -Wno-varargs -Wno-unknown-warning-option -Wno-unused-const-variable -ftrap-function=undefined_behavior_has_been_optimized_away_by_clang + NOOPT_XCODE5_IA32_CC_FLAGS = -arch i386 -c -g -O0 -Wall -Werror -include AutoGen.h -funsigned-char -fno-stack-protector -fno-builtin -fshort-wchar -fasm-blocks -mdynamic-no-pic -mno-implicit-float -mms-bitfields -msoft-float -Wno-unused-parameter -Wno-missing-braces -Wno-missing-field-initializers -Wno-tautological-compare -Wno-sign-compare -Wno-varargs -Wno-unknown-warning-option -ftrap-function=undefined_behavior_has_been_optimized_away_by_clang ################## # X64 definitions ################## - DEBUG_XCODE5_X64_DLINK_FLAGS = -arch x86_64 -u _$(IMAGE_ENTRY_POINT) -e _$(IMAGE_ENTRY_POINT) -preload -segalign 0x20 -pie -all_load -dead_strip -seg1addr 0x240 -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map - NOOPT_XCODE5_X64_DLINK_FLAGS = -arch x86_64 -u _$(IMAGE_ENTRY_POINT) -e _$(IMAGE_ENTRY_POINT) -preload -segalign 0x20 -pie -all_load -dead_strip -seg1addr 0x240 -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map -RELEASE_XCODE5_X64_DLINK_FLAGS = -arch x86_64 -u _$(IMAGE_ENTRY_POINT) -e _$(IMAGE_ENTRY_POINT) -preload -segalign 0x20 -pie -all_load -dead_strip -seg1addr 0x240 -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map + DEBUG_XCODE5_X64_DLINK_FLAGS = DEF(XCODE5_RODATA_ARGS) -arch x86_64 -u _$(IMAGE_ENTRY_POINT) -e _$(IMAGE_ENTRY_POINT) -preload -segalign DEF(XCODE_ALIGN) -pie -all_load -dead_strip -seg1addr DEF(XCODE_ADDR) -read_only_relocs suppress -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map DEF(XCODE_MERGE) + NOOPT_XCODE5_X64_DLINK_FLAGS = DEF(XCODE5_RODATA_ARGS) -arch x86_64 -u _$(IMAGE_ENTRY_POINT) -e _$(IMAGE_ENTRY_POINT) -preload -segalign DEF(XCODE_ALIGN) -pie -all_load -dead_strip -seg1addr DEF(XCODE_ADDR) -read_only_relocs suppress -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map DEF(XCODE_MERGE) +RELEASE_XCODE5_X64_DLINK_FLAGS = DEF(XCODE5_RODATA_ARGS) -arch x86_64 -u _$(IMAGE_ENTRY_POINT) -e _$(IMAGE_ENTRY_POINT) -preload -segalign DEF(XCODE_ALIGN) -pie -all_load -dead_strip -seg1addr DEF(XCODE_ADDR) -read_only_relocs suppress -map $(DEST_DIR_DEBUG)/$(BASE_NAME).map DEF(XCODE_MERGE) *_XCODE5_X64_SLINK_FLAGS = -static -o DEBUG_XCODE5_X64_ASM_FLAGS = -arch x86_64 -g NOOPT_XCODE5_X64_ASM_FLAGS = -arch x86_64 -g RELEASE_XCODE5_X64_ASM_FLAGS = -arch x86_64 - *_XCODE5_X64_NASM_FLAGS = -f macho64 -*_XCODE5_*_PP_FLAGS = -E -x assembler-with-cpp -include AutoGen.h -*_XCODE5_*_VFRPP_FLAGS = -x c -E -P -DVFRCOMPILE -include $(MODULE_NAME)StrDefs.h + *_XCODE5_X64_NASM_FLAGS = -f macho64 -DRODATA_SECTION_NAME=.rodata +*_XCODE5_*_PP_FLAGS = -E -x assembler-with-cpp -include AutoGen.h +*_XCODE5_*_VFRPP_FLAGS = -x c -E -P -DVFRCOMPILE -include $(MODULE_NAME)StrDefs.h - DEBUG_XCODE5_X64_CC_FLAGS = -target x86_64-pc-win32-macho -c -g -gdwarf -Os -Wall -Werror -Wextra -include AutoGen.h -funsigned-char -fno-ms-extensions -fno-stack-protector -fno-builtin -fshort-wchar -mno-implicit-float -mms-bitfields -Wno-unused-parameter -Wno-missing-braces -Wno-missing-field-initializers -Wno-tautological-compare -Wno-sign-compare -Wno-varargs -ftrap-function=undefined_behavior_has_been_optimized_away_by_clang -D NO_MSABI_VA_FUNCS $(PLATFORM_FLAGS) - NOOPT_XCODE5_X64_CC_FLAGS = -target x86_64-pc-win32-macho -c -g -gdwarf -O0 -Wall -Werror -Wextra -include AutoGen.h -funsigned-char -fno-ms-extensions -fno-stack-protector -fno-builtin -fshort-wchar -mno-implicit-float -mms-bitfields -Wno-unused-parameter -Wno-missing-braces -Wno-missing-field-initializers -Wno-tautological-compare -Wno-sign-compare -Wno-varargs -ftrap-function=undefined_behavior_has_been_optimized_away_by_clang -D NO_MSABI_VA_FUNCS $(PLATFORM_FLAGS) -RELEASE_XCODE5_X64_CC_FLAGS = -target x86_64-pc-win32-macho -c -Os -Wall -Werror -Wextra -include AutoGen.h -funsigned-char -fno-ms-extensions -fno-stack-protector -fno-builtin -fshort-wchar -mno-implicit-float -mms-bitfields -Wno-unused-parameter -Wno-missing-braces -Wno-missing-field-initializers -Wno-tautological-compare -Wno-sign-compare -Wno-varargs -Wno-unused-const-variable -ftrap-function=undefined_behavior_has_been_optimized_away_by_clang -D NO_MSABI_VA_FUNCS $(PLATFORM_FLAGS) + DEBUG_XCODE5_X64_CC_FLAGS = -target x86_64-pc-win32-macho -c -g -gdwarf -Os -Wall -Werror -Wextra -include AutoGen.h -funsigned-char -fno-ms-extensions -fno-stack-protector -fno-builtin -fshort-wchar -mno-implicit-float -mms-bitfields -Wno-unused-parameter -Wno-missing-braces -Wno-missing-field-initializers -Wno-tautological-compare -Wno-sign-compare -Wno-varargs -Wno-unknown-warning-option -ftrap-function=undefined_behavior_has_been_optimized_away_by_clang -D NO_MSABI_VA_FUNCS + NOOPT_XCODE5_X64_CC_FLAGS = -target x86_64-pc-win32-macho -c -g -gdwarf -O0 -Wall -Werror -Wextra -include AutoGen.h -funsigned-char -fno-ms-extensions -fno-stack-protector -fno-builtin -fshort-wchar -mno-implicit-float -mms-bitfields -Wno-unused-parameter -Wno-missing-braces -Wno-missing-field-initializers -Wno-tautological-compare -Wno-sign-compare -Wno-varargs -Wno-unknown-warning-option -ftrap-function=undefined_behavior_has_been_optimized_away_by_clang -D NO_MSABI_VA_FUNCS +RELEASE_XCODE5_X64_CC_FLAGS = -target x86_64-pc-win32-macho -c -Os -Wall -Werror -Wextra -include AutoGen.h -funsigned-char -fno-ms-extensions -fno-stack-protector -fno-builtin -fshort-wchar -mno-implicit-float -mms-bitfields -Wno-unused-parameter -Wno-missing-braces -Wno-missing-field-initializers -Wno-tautological-compare -Wno-sign-compare -Wno-varargs -Wno-unused-const-variable -Wno-unknown-warning-option -ftrap-function=undefined_behavior_has_been_optimized_away_by_clang -D NO_MSABI_VA_FUNCS ################# # ASM 16 linker definitions @@ -2174,12 +2164,6 @@ RELEASE_XCODE5_X64_CC_FLAGS = -target x86_64-pc-win32-macho -c -Os -W *_*_*_OPTROM_PATH = EfiRom *_*_*_OPTROM_FLAGS = -e -################## -# GenFw tool definitions -################## -*_*_*_GENFW_PATH = GenFw -*_*_*_GENFW_FLAGS = - ################## # Asl Compiler definitions ################## diff --git a/BaseTools/GNUmakefile b/BaseTools/GNUmakefile index d29f6d9c9b..fdaa7fa9ec 100644 --- a/BaseTools/GNUmakefile +++ b/BaseTools/GNUmakefile @@ -10,7 +10,7 @@ all: subdirs LANGUAGES = C Python SOURCE_SUBDIRS := $(patsubst %,Source/%,$(sort $(LANGUAGES))) -SUBDIRS := $(SOURCE_SUBDIRS) Tests +SUBDIRS := $(SOURCE_SUBDIRS) Tests ImageTool MicroTool CLEAN_SUBDIRS := $(patsubst %,%-clean,$(sort $(SUBDIRS))) .PHONY: subdirs $(SUBDIRS) diff --git a/BaseTools/ImageTool/BinEmit.c b/BaseTools/ImageTool/BinEmit.c new file mode 100644 index 0000000000..51fbb6f5a7 --- /dev/null +++ b/BaseTools/ImageTool/BinEmit.c @@ -0,0 +1,200 @@ +/** @file + Copyright (c) 2022, Mikhail Krichanov. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#include "ImageTool.h" + +static +EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY * +CreateEntry ( + IN UINT8 *HiiSectionHeader, + IN OUT UINT32 *HiiSectionOffset, + IN BOOLEAN DataIsDirectory + ) +{ + EFI_IMAGE_RESOURCE_DIRECTORY *RDir; + EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *Entry; + + assert (HiiSectionHeader != NULL); + assert (HiiSectionOffset != NULL); + + RDir = (EFI_IMAGE_RESOURCE_DIRECTORY *)(HiiSectionHeader + *HiiSectionOffset); + *HiiSectionOffset += sizeof (EFI_IMAGE_RESOURCE_DIRECTORY); + RDir->NumberOfNamedEntries = 1; + + Entry = (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *)(HiiSectionHeader + *HiiSectionOffset); + *HiiSectionOffset += sizeof (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY); + Entry->u1.s.NameIsString = 1; + + if (DataIsDirectory) { + Entry->u2.s.DataIsDirectory = 1; + Entry->u2.s.OffsetToDirectory = *HiiSectionOffset; + } + + return Entry; +} + +static +void +CreateStringEntry ( + IN OUT EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *Entry, + IN UINT8 *HiiSectionHeader, + IN OUT UINT32 *HiiSectionOffset, + IN CHAR16 *String + ) +{ + EFI_IMAGE_RESOURCE_DIRECTORY_STRING *RDStr; + + assert (Entry != NULL); + assert (HiiSectionHeader != NULL); + assert (HiiSectionOffset != NULL); + assert (String != NULL); + + Entry->u1.s.NameOffset = *HiiSectionOffset; + RDStr = (EFI_IMAGE_RESOURCE_DIRECTORY_STRING *)(HiiSectionHeader + *HiiSectionOffset); + RDStr->Length = (UINT16)StrLen (String); + memcpy (RDStr->String, String, RDStr->Length * sizeof (RDStr->String[0])); + *HiiSectionOffset += sizeof (*RDStr) + RDStr->Length * sizeof (RDStr->String[0]); +} + +GLOBAL_REMOVE_IF_UNREFERENCED CONST UINT8 mHiiResourceSectionHeaderSize = + 3 * (sizeof (EFI_IMAGE_RESOURCE_DIRECTORY) + sizeof (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY) + + sizeof (EFI_IMAGE_RESOURCE_DIRECTORY_STRING) + 3 * sizeof (CHAR16)) + sizeof (EFI_IMAGE_RESOURCE_DATA_ENTRY); + +VOID +InitializeHiiResouceSectionHeader ( + OUT UINT8 *HiiSectionHeader, + IN UINT32 HiiDataAddress, + IN UINT32 HiiDataSize + ) +{ + UINT32 HiiSectionOffset; + EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *TypeRDirEntry; + EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *NameRDirEntry; + EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *LangRDirEntry; + EFI_IMAGE_RESOURCE_DATA_ENTRY *ResourceDataEntry; + + assert (HiiSectionHeader != NULL); + + HiiSectionOffset = 0; + // + // Create Type, Name, Language entries + // + TypeRDirEntry = CreateEntry (HiiSectionHeader, &HiiSectionOffset, TRUE); + NameRDirEntry = CreateEntry (HiiSectionHeader, &HiiSectionOffset, TRUE); + LangRDirEntry = CreateEntry (HiiSectionHeader, &HiiSectionOffset, FALSE); + // + // Create string entry for Type, Name, Language + // + CreateStringEntry (TypeRDirEntry, HiiSectionHeader, &HiiSectionOffset, L"HII"); + CreateStringEntry (NameRDirEntry, HiiSectionHeader, &HiiSectionOffset, L"EFI"); + CreateStringEntry (LangRDirEntry, HiiSectionHeader, &HiiSectionOffset, L"BIN"); + // + // Create Leaf data + // + LangRDirEntry->u2.OffsetToData = HiiSectionOffset; + ResourceDataEntry = (EFI_IMAGE_RESOURCE_DATA_ENTRY *)(HiiSectionHeader + HiiSectionOffset); + HiiSectionOffset += sizeof (EFI_IMAGE_RESOURCE_DATA_ENTRY); + ResourceDataEntry->OffsetToData = HiiDataAddress + HiiSectionOffset; + ResourceDataEntry->Size = HiiDataSize; +} + +RETURN_STATUS +ConstructHii ( + IN const char *FileNames[], + IN UINT32 NumOfFiles, + IN GUID *HiiGuid, + OUT void **Hii, + OUT UINT32 *HiiSize + ) +{ + UINT8 *HiiPackageData; + UINT8 *HiiPackageDataPointer; + EFI_HII_PACKAGE_LIST_HEADER HiiPackageListHeader; + EFI_HII_PACKAGE_HEADER *HiiPackageHeader; + EFI_IFR_FORM_SET *IfrFormSet; + EFI_HII_PACKAGE_HEADER EndPackage; + UINT32 Index; + void *File; + UINT32 FileSize; + UINT8 NumberOfFormPackages; + + assert (Hii != NULL); + assert (HiiGuid != NULL); + assert (FileNames != NULL); + + NumberOfFormPackages = 0; + + EndPackage.Length = sizeof (EFI_HII_PACKAGE_HEADER); + EndPackage.Type = EFI_HII_PACKAGE_END; + + HiiPackageListHeader.PackageLength = sizeof (EFI_HII_PACKAGE_LIST_HEADER) + sizeof (EndPackage); + + for (Index = 0; Index < NumOfFiles; ++Index) { + File = UserReadFile (FileNames[Index], &FileSize); + if (File == NULL) { + fprintf (stderr, "ImageTool: Could not open %s: %s\n", FileNames[Index], strerror (errno)); + return RETURN_ABORTED; + } + + HiiPackageHeader = (EFI_HII_PACKAGE_HEADER *)File; + if (HiiPackageHeader->Type == EFI_HII_PACKAGE_FORMS) { + if (HiiPackageHeader->Length != FileSize) { + fprintf (stderr, "ImageTool: Wrong package size in HII package file %s\n", FileNames[Index]); + free (File); + return RETURN_ABORTED; + } + + if (IsZeroGuid (HiiGuid)) { + IfrFormSet = (EFI_IFR_FORM_SET *)(HiiPackageHeader + 1); + CopyGuid (HiiGuid, &IfrFormSet->Guid); + } + + ++NumberOfFormPackages; + } + + HiiPackageListHeader.PackageLength += FileSize; + free (File); + } + + if (NumberOfFormPackages > 1) { + fprintf (stderr, "ImageTool: The input HII packages contain more than one HII Form package\n"); + return RETURN_INVALID_PARAMETER; + } + + if (IsZeroGuid (HiiGuid)) { + fprintf (stderr, "ImageTool: HII package list guid is not specified\n"); + return RETURN_ABORTED; + } + + CopyGuid (&HiiPackageListHeader.PackageListGuid, HiiGuid); + + HiiPackageData = calloc (1, HiiPackageListHeader.PackageLength); + if (HiiPackageData == NULL) { + return RETURN_OUT_OF_RESOURCES; + } + + memmove (HiiPackageData, &HiiPackageListHeader, sizeof (HiiPackageListHeader)); + + HiiPackageDataPointer = HiiPackageData + sizeof (HiiPackageListHeader); + for (Index = 0; Index < NumOfFiles; ++Index) { + File = UserReadFile (FileNames[Index], &FileSize); + if (File == NULL) { + fprintf (stderr, "ImageTool: Could not open %s: %s\n", FileNames[Index], strerror (errno)); + return RETURN_ABORTED; + } + + memmove (HiiPackageDataPointer, File, FileSize); + HiiPackageDataPointer += FileSize; + + free (File); + } + + memmove (HiiPackageDataPointer, &EndPackage, sizeof (EndPackage)); + + *Hii = HiiPackageData; + *HiiSize = HiiPackageListHeader.PackageLength; + + return RETURN_SUCCESS; +} diff --git a/BaseTools/ImageTool/ElfScan.c b/BaseTools/ImageTool/ElfScan.c new file mode 100644 index 0000000000..ca2a1010b2 --- /dev/null +++ b/BaseTools/ImageTool/ElfScan.c @@ -0,0 +1,731 @@ +/** @file + Copyright (c) 2022, Mikhail Krichanov. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#include "ImageTool.h" + +#include "ElfScanCommon.h" + +#include "../../UefiPayloadPkg/PayloadLoaderPeim/ElfLib/ElfCommon.h" + +#if ELF_ARCH == 32 + +#include "../../UefiPayloadPkg/PayloadLoaderPeim/ElfLib/Elf32.h" + +#define ELFCLASS ELFCLASS32 +#define Elf_Ehdr Elf32_Ehdr +#define Elf_Shdr Elf32_Shdr +#define Elf_Sym Elf32_Sym +#define Elf_Rel Elf32_Rel +#define Elf_Rela Elf32_Rela +#define Elf_Size Elf32_Size +#define Elf_Addr Elf32_Addr +#define ELF_R_TYPE ELF32_R_TYPE +#define ELF_R_SYM ELF32_R_SYM + +#elif ELF_ARCH == 64 + +#include "../../UefiPayloadPkg/PayloadLoaderPeim/ElfLib/Elf64.h" + +#define ELFCLASS ELFCLASS64 +#define Elf_Ehdr Elf64_Ehdr +#define Elf_Shdr Elf64_Shdr +#define Elf_Sym Elf64_Sym +#define Elf_Rel Elf64_Rel +#define Elf_Rela Elf64_Rela +#define Elf_Size Elf64_Size +#define Elf_Addr Elf64_Addr +#define ELF_R_TYPE ELF64_R_TYPE +#define ELF_R_SYM ELF64_R_SYM + +#endif + +#define ELF_SUFFIX__(Name, Arch) Name##Arch +#define ELF_SUFFIX_(Name, Arch) ELF_SUFFIX__ (Name, Arch) +#define ELF_SUFFIX(Name) ELF_SUFFIX_ (Name, ELF_ARCH) + +typedef struct { + const Elf_Ehdr *Ehdr; + uint32_t Alignment; + Elf_Addr BaseAddress; + bool HasPieRelocs; +} tool_elf_scan_context; + +#if defined (_MSC_EXTENSIONS) +#define EFI_IMAGE_MACHINE_IA32 0x014C +#define EFI_IMAGE_MACHINE_X64 0x8664 +#define EFI_IMAGE_MACHINE_ARMTHUMB_MIXED 0x01C2 +#define EFI_IMAGE_MACHINE_AARCH64 0xAA64 +#endif + + +#define GetShrbyIndex ELF_SUFFIX(GetShrbyIndex) +static +Elf_Shdr * +GetShdrByIndex ( + IN const Elf_Ehdr *Ehdr, + IN UINT32 Index + ) +{ + UINTN Offset; + + assert (Index < Ehdr->e_shnum); + + Offset = (UINTN)Ehdr->e_shoff + Index * Ehdr->e_shentsize; + + return (Elf_Shdr *)((UINT8 *)Ehdr + Offset); +} + +#define GetString ELF_SUFFIX(GetString) +static +const char * +GetString ( + IN const Elf_Ehdr *Ehdr, + IN UINT32 Offset, + IN UINT32 Index + ) +{ + const Elf_Shdr *Shdr; + + if (Index == 0) { + Shdr = GetShdrByIndex (Ehdr, Ehdr->e_shstrndx); + } else { + Shdr = GetShdrByIndex (Ehdr, Index); + } + + if (Offset >= Shdr->sh_size) { + fprintf (stderr, "ImageTool: Invalid ELF string offset\n"); + return NULL; + } + + return (const char *)Ehdr + Shdr->sh_offset + Offset; +} + +#define IsShdrLoadable ELF_SUFFIX(IsShdrLoadable) +static +BOOLEAN +IsShdrLoadable ( + IN const Elf_Ehdr *Ehdr, + IN const Elf_Shdr *Shdr + ) +{ + assert (Shdr != NULL); + + return (Shdr->sh_flags & SHF_ALLOC) != 0; +} + +#define ParseElfFile ELF_SUFFIX(ParseElfFile) +static +RETURN_STATUS +ParseElfFile ( + OUT tool_elf_scan_context *Context, + IN const void *File, + IN uint32_t FileSize + ) +{ + static const unsigned char Ident[] = { + ELFMAG0, ELFMAG1, ELFMAG2, ELFMAG3, ELFCLASS, ELFDATA2LSB + }; + const Elf_Ehdr *Ehdr; + bool AlignmentSet; + Elf_Size Alignment; + bool BaseAddressSet; + Elf_Addr BaseAddress; + bool HasPieRelocs; + const Elf_Shdr *Shdr; + UINTN Offset; + UINT32 Index; + char *Last; + + assert (File != NULL || FileSize == 0); + + Ehdr = (const Elf_Ehdr *)File; + + // + // Check header + // + if ((FileSize < sizeof (*Ehdr)) + || (memcmp (Ident, Ehdr->e_ident, sizeof (Ident)) != 0)) { + return RETURN_UNSUPPORTED; + } + + if ((Ehdr->e_type != ET_EXEC) && (Ehdr->e_type != ET_DYN)) { + fprintf (stderr, "ImageTool: ELF e_type not ET_EXEC or ET_DYN\n"); + return RETURN_INCOMPATIBLE_VERSION; + } + + // + // Check section headers + // + BaseAddressSet = false; + BaseAddress = 0; + Alignment = 0; + AlignmentSet = false; + HasPieRelocs = false; + for (Index = 0; Index < Ehdr->e_shnum; ++Index) { + Offset = (UINTN)Ehdr->e_shoff + Index * Ehdr->e_shentsize; + + if (FileSize < (Offset + sizeof (*Shdr))) { + fprintf (stderr, "ImageTool: ELF section header is outside file\n"); + return RETURN_VOLUME_CORRUPTED; + } + + Shdr = (const Elf_Shdr *)((const char *)Ehdr + Offset); + + if ((Shdr->sh_type != SHT_NOBITS) + && ((FileSize < Shdr->sh_offset) || ((FileSize - Shdr->sh_offset) < Shdr->sh_size))) { + fprintf (stderr, "ImageTool: ELF section %d points outside file\n", Index); + return RETURN_VOLUME_CORRUPTED; + } + + if (Shdr->sh_link >= Ehdr->e_shnum) { + fprintf (stderr, "ImageTool: ELF %d-th section's sh_link is out of range\n", Index); + return RETURN_VOLUME_CORRUPTED; + } + + if ((Shdr->sh_type == SHT_RELA) || (Shdr->sh_type == SHT_REL)) { + if (Shdr->sh_info >= Ehdr->e_shnum) { + fprintf (stderr, "ImageTool: ELF %d-th section's sh_info is out of range\n", Index); + return RETURN_VOLUME_CORRUPTED; + } + + if (Shdr->sh_info == 0) { + HasPieRelocs = TRUE; + } + } + + if (!BaseAddressSet || Shdr->sh_addr < BaseAddress) { + BaseAddressSet = TRUE; + BaseAddress = Shdr->sh_addr; + } + + if (!IsShdrLoadable (Ehdr, Shdr)) { + continue; + } + + if (!AlignmentSet || Alignment < Shdr->sh_addralign) { + AlignmentSet = TRUE; + Alignment = Shdr->sh_addralign; + } + } + + if (Ehdr->e_shstrndx >= Ehdr->e_shnum) { + fprintf (stderr, "ImageTool: Invalid section name string table\n"); + return RETURN_VOLUME_CORRUPTED; + } + Shdr = GetShdrByIndex (Ehdr, Ehdr->e_shstrndx); + + if (Shdr->sh_type != SHT_STRTAB) { + fprintf (stderr, "ImageTool: ELF string table section has wrong type\n"); + return RETURN_VOLUME_CORRUPTED; + } + + Last = (char *)((UINT8 *)Ehdr + Shdr->sh_offset + Shdr->sh_size - 1); + if (*Last != '\0') { + fprintf (stderr, "ImageTool: ELF string table section is not NUL-terminated\n"); + return RETURN_VOLUME_CORRUPTED; + } + + if (!AlignmentSet || (!IS_POW2(Alignment)) || (Alignment > MAX_PE_ALIGNMENT)) { + fprintf (stderr, "ImageTool: Invalid section alignment\n"); + return RETURN_VOLUME_CORRUPTED; + } + + if (!BaseAddressSet || !IS_ALIGNED (BaseAddress, Alignment)) { + fprintf (stderr, "ImageTool: Invalid base address %llx\n", (unsigned long long)BaseAddress); + return RETURN_VOLUME_CORRUPTED; + } + + memset (Context, 0, sizeof (*Context)); + + Context->Ehdr = Ehdr; + Context->Alignment = (uint32_t)Alignment; + Context->BaseAddress = BaseAddress; + Context->HasPieRelocs = HasPieRelocs; + + return RETURN_SUCCESS; +} + +#define ProcessRelocSection ELF_SUFFIX(ProcessRelocSection) +static +bool +ProcessRelocSection ( + const tool_elf_scan_context *Context, + const Elf_Shdr *Shdr + ) +{ + const Elf_Ehdr *Ehdr; + bool HasPieRelocs; + const Elf_Shdr *SecShdr; + + Ehdr = Context->Ehdr; + HasPieRelocs = Context->HasPieRelocs; + // + // PIE relocations will target dummy section 0. + // + if (Shdr->sh_info != 0) { + // + // If PIE relocations exist, prefer them. + // + if (HasPieRelocs) { + return FALSE; + } + // + // Only translate relocations targetting sections that are translated. + // + SecShdr = GetShdrByIndex (Ehdr, Shdr->sh_info); + + if (!IsShdrLoadable (Ehdr, SecShdr)) { + return FALSE; + } + } else { + assert (HasPieRelocs); + } + + return TRUE; +} + +#define SetRelocs ELF_SUFFIX(SetRelocs) +static +RETURN_STATUS +SetRelocs ( + OUT image_tool_image_info_t *ImageInfo, + IN const tool_elf_scan_context *Context + ) +{ + const Elf_Ehdr *Ehdr; + Elf_Addr BaseAddress; + UINT32 Index; + const Elf_Shdr *RelShdr; + UINTN RelIdx; + const Elf_Rela *Rel; + UINT32 RelNum; + + Ehdr = Context->Ehdr; + BaseAddress = Context->BaseAddress; + + RelNum = 0; + + for (Index = 0; Index < Ehdr->e_shnum; Index++) { + RelShdr = GetShdrByIndex (Ehdr, Index); + + if ((RelShdr->sh_type != SHT_REL) && (RelShdr->sh_type != SHT_RELA)) { + continue; + } + + if (!ProcessRelocSection (Context, RelShdr)) { + continue; + } + + for (RelIdx = 0; RelIdx < RelShdr->sh_size; RelIdx += (UINTN)RelShdr->sh_entsize) { + Rel = (const Elf_Rela *)((const char *)Ehdr + RelShdr->sh_offset + RelIdx); + // + // Assume ELF virtual addresses match corresponding PE virtual adresses one to one, + // so we don't need to recalculate relocations computed by the linker at all r_offset's. + // We only need to transform ELF relocations' format into PE one. + // +#if ELF_ARCH == 64 + if (Ehdr->e_machine == EM_X86_64) { + switch (ELF_R_TYPE(Rel->r_info)) { + case R_X86_64_NONE: + break; + case R_X86_64_RELATIVE: + case R_X86_64_64: + ImageInfo->RelocInfo.Relocs[RelNum].Type = EFI_IMAGE_REL_BASED_DIR64; + ImageInfo->RelocInfo.Relocs[RelNum].Target = (uint32_t)(Rel->r_offset - BaseAddress); + ++RelNum; + + break; + case R_X86_64_32: + + ImageInfo->RelocInfo.Relocs[RelNum].Type = EFI_IMAGE_REL_BASED_HIGHLOW; + ImageInfo->RelocInfo.Relocs[RelNum].Target = (uint32_t)(Rel->r_offset - BaseAddress); + ++RelNum; + + break; + case R_X86_64_32S: + case R_X86_64_PLT32: + case R_X86_64_PC32: + break; + case R_X86_64_GOTPCREL: + case R_X86_64_GOTPCRELX: + case R_X86_64_REX_GOTPCRELX: + // + // Relocations of these types point to instructions' arguments containing + // offsets relative to RIP leading to .got entries. As sections' virtual + // addresses do not change during ELF->PE transform, we don't need to + // add them to relocations' list. But .got entries contain virtual + // addresses which must be updated. + // + // At r_offset the following value is stored: G + GOT + A - P. + // To derive .got entry address (G + GOT) compute: value - A + P. + // + // Such a method of finding relocatable .got entries can not be used, + // due to a BUG in clang compiler, which sometimes generates + // R_X86_64_REX_GOTPCRELX relocations instead of R_X86_64_PC32. + // + break; + default: + fprintf (stderr, "ImageTool: Unsupported ELF EM_X86_64 relocation 0x%llx in %s\n", ELF_R_TYPE(Rel->r_info), ImageInfo->DebugInfo.SymbolsPath); + return RETURN_INCOMPATIBLE_VERSION; + } + } else if (Ehdr->e_machine == EM_AARCH64) { + switch (ELF_R_TYPE(Rel->r_info)) { + case R_AARCH64_NONE0: + case R_AARCH64_NONE: + case R_AARCH64_LD64_GOTOFF_LO15: + case R_AARCH64_LD64_GOTPAGE_LO15: + case R_AARCH64_LD64_GOT_LO12_NC: + case R_AARCH64_ADR_GOT_PAGE: + case R_AARCH64_ADR_PREL_PG_HI21: + case R_AARCH64_ADD_ABS_LO12_NC: + case R_AARCH64_LDST8_ABS_LO12_NC: + case R_AARCH64_LDST16_ABS_LO12_NC: + case R_AARCH64_LDST32_ABS_LO12_NC: + case R_AARCH64_LDST64_ABS_LO12_NC: + case R_AARCH64_LDST128_ABS_LO12_NC: + case R_AARCH64_ADR_PREL_LO21: + case R_AARCH64_CONDBR19: + case R_AARCH64_LD_PREL_LO19: + case R_AARCH64_CALL26: + case R_AARCH64_JUMP26: + case R_AARCH64_PREL64: + case R_AARCH64_PREL32: + case R_AARCH64_PREL16: + break; + case R_AARCH64_ABS64: + case R_AARCH64_RELATIVE: + ImageInfo->RelocInfo.Relocs[RelNum].Type = EFI_IMAGE_REL_BASED_DIR64; + ImageInfo->RelocInfo.Relocs[RelNum].Target = (uint32_t)(Rel->r_offset - BaseAddress); + ++RelNum; + + break; + case R_AARCH64_ABS32: + + ImageInfo->RelocInfo.Relocs[RelNum].Type = EFI_IMAGE_REL_BASED_HIGHLOW; + ImageInfo->RelocInfo.Relocs[RelNum].Target = (uint32_t)(Rel->r_offset - BaseAddress); + ++RelNum; + + break; + default: + fprintf (stderr, "ImageTool: Unsupported ELF EM_AARCH64 relocation 0x%llx in %s\n", ELF_R_TYPE(Rel->r_info), ImageInfo->DebugInfo.SymbolsPath); + return RETURN_INCOMPATIBLE_VERSION; + } + } +#elif ELF_ARCH == 32 + if (Ehdr->e_machine == EM_386) { + switch (ELF_R_TYPE(Rel->r_info)) { + case R_386_NONE: + break; + case R_386_32: + + ImageInfo->RelocInfo.Relocs[RelNum].Type = EFI_IMAGE_REL_BASED_HIGHLOW; + ImageInfo->RelocInfo.Relocs[RelNum].Target = (Rel->r_offset - BaseAddress); + ++RelNum; + + break; + case R_386_PLT32: + case R_386_PC32: + break; + default: + fprintf (stderr, "ImageTool: Unsupported ELF EM_386 relocation 0x%x in %s\n", ELF_R_TYPE(Rel->r_info), ImageInfo->DebugInfo.SymbolsPath); + return RETURN_INCOMPATIBLE_VERSION; + } + } else if (Ehdr->e_machine == EM_ARM) { + switch (ELF32_R_TYPE(Rel->r_info)) { + case R_ARM_NONE: + case R_ARM_PC24: + case R_ARM_REL32: + case R_ARM_XPC25: + case R_ARM_THM_PC22: + case R_ARM_THM_JUMP19: + case R_ARM_CALL: + case R_ARM_JMP24: + case R_ARM_THM_JUMP24: + case R_ARM_PREL31: + case R_ARM_MOVW_PREL_NC: + case R_ARM_MOVT_PREL: + case R_ARM_THM_MOVW_PREL_NC: + case R_ARM_THM_MOVT_PREL: + case R_ARM_THM_JMP6: + case R_ARM_THM_ALU_PREL_11_0: + case R_ARM_THM_PC12: + case R_ARM_REL32_NOI: + case R_ARM_ALU_PC_G0_NC: + case R_ARM_ALU_PC_G0: + case R_ARM_ALU_PC_G1_NC: + case R_ARM_ALU_PC_G1: + case R_ARM_ALU_PC_G2: + case R_ARM_LDR_PC_G1: + case R_ARM_LDR_PC_G2: + case R_ARM_LDRS_PC_G0: + case R_ARM_LDRS_PC_G1: + case R_ARM_LDRS_PC_G2: + case R_ARM_LDC_PC_G0: + case R_ARM_LDC_PC_G1: + case R_ARM_LDC_PC_G2: + case R_ARM_THM_JUMP11: + case R_ARM_THM_JUMP8: + case R_ARM_TLS_GD32: + case R_ARM_TLS_LDM32: + case R_ARM_TLS_IE32: + break; + case R_ARM_ABS32: + + ImageInfo->RelocInfo.Relocs[RelNum].Type = EFI_IMAGE_REL_BASED_HIGHLOW; + ImageInfo->RelocInfo.Relocs[RelNum].Target = (Rel->r_offset - BaseAddress); + ++RelNum; + + break; + default: + fprintf (stderr, "ImageTool: Unsupported ELF EM_ARM relocation 0x%x in %s\n", ELF_R_TYPE(Rel->r_info), ImageInfo->DebugInfo.SymbolsPath); + return RETURN_INCOMPATIBLE_VERSION; + } + } +#endif + } + } + + ImageInfo->RelocInfo.NumRelocs = RelNum; + + return RETURN_SUCCESS; +} + +#define CreateIntermediate ELF_SUFFIX(CreateIntermediate) +static +RETURN_STATUS +CreateIntermediate ( + OUT image_tool_image_info_t *ImageInfo, + IN const tool_elf_scan_context *Context + ) +{ + const Elf_Ehdr *Ehdr; + Elf_Addr BaseAddress; + const Elf_Shdr *Shdr; + UINT32 Index; + image_tool_segment_t *Segments; + image_tool_reloc_t *Relocs; + UINT32 SIndex; + const Elf_Rel *Rel; + UINTN RIndex; + const char *Name; + UINT32 NumRelocs; + + Ehdr = Context->Ehdr; + BaseAddress = Context->BaseAddress; + + Segments = NULL; + SIndex = 0; + Relocs = NULL; + NumRelocs = 0; + + for (Index = 0; Index < Ehdr->e_shnum; ++Index) { + Shdr = GetShdrByIndex (Ehdr, Index); + + if ((Shdr->sh_type == SHT_REL) || (Shdr->sh_type == SHT_RELA)) { + if ((Shdr->sh_flags & SHF_ALLOC) != 0) { + fprintf (stderr, "ImageTool: Loadable reloc sections are unsupported\n"); + return RETURN_VOLUME_CORRUPTED; + } + + if (!ProcessRelocSection (Context, Shdr)) { + continue; + } + + for (RIndex = 0; RIndex < Shdr->sh_size; RIndex += (UINTN)Shdr->sh_entsize) { + Rel = (Elf_Rel *)((UINT8 *)Ehdr + Shdr->sh_offset + RIndex); +#if ELF_ARCH == 64 + if (Ehdr->e_machine == EM_X86_64) { + if ((ELF_R_TYPE(Rel->r_info) == R_X86_64_RELATIVE) + || (ELF_R_TYPE(Rel->r_info) == R_X86_64_64) + || (ELF_R_TYPE(Rel->r_info) == R_X86_64_32) + || (ELF_R_TYPE(Rel->r_info) == R_X86_64_GOTPCREL) + || (ELF_R_TYPE(Rel->r_info) == R_X86_64_GOTPCRELX) + || (ELF_R_TYPE(Rel->r_info) == R_X86_64_REX_GOTPCRELX)) { + ++NumRelocs; + } + } else if (Ehdr->e_machine == EM_AARCH64) { + if ((ELF_R_TYPE(Rel->r_info) == R_AARCH64_ABS64) + || (ELF_R_TYPE(Rel->r_info) == R_AARCH64_RELATIVE) + || (ELF_R_TYPE(Rel->r_info) == R_AARCH64_ABS32)) { + ++NumRelocs; + } + } +#elif ELF_ARCH == 32 + if (Ehdr->e_machine == EM_386) { + if (ELF_R_TYPE(Rel->r_info) == R_386_32) { + ++NumRelocs; + } + } else if (Ehdr->e_machine == EM_ARM) { + if (ELF_R_TYPE(Rel->r_info) == R_ARM_ABS32) { + ++NumRelocs; + } + } +#endif + } + } + + if (!IsShdrLoadable (Ehdr, Shdr)) { + continue; + } + + ++ImageInfo->SegmentInfo.NumSegments; + } + + if (ImageInfo->SegmentInfo.NumSegments == 0) { + fprintf (stderr, "ImageTool: No loadable sections\n"); + return RETURN_VOLUME_CORRUPTED; + } + + Segments = calloc (1, sizeof (*Segments) * ImageInfo->SegmentInfo.NumSegments); + if (Segments == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for Segments\n"); + return RETURN_OUT_OF_RESOURCES; + }; + + ImageInfo->SegmentInfo.Segments = Segments; + + if (NumRelocs != 0) { + Relocs = calloc (1, sizeof (*Relocs) * NumRelocs); + if (Relocs == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for Relocs\n"); + return RETURN_OUT_OF_RESOURCES; + }; + + ImageInfo->RelocInfo.Relocs = Relocs; + } + + for (Index = 0; Index < Ehdr->e_shnum; ++Index) { + Shdr = GetShdrByIndex (Ehdr, Index); + + if ((Shdr->sh_flags & SHF_ALLOC) == 0) { + continue; + } + + if (Shdr->sh_type != SHT_PROGBITS && Shdr->sh_type != SHT_NOBITS) { + fprintf (stderr, "ImageTool: Segment #%d type %x unsupported\n", Index, Shdr->sh_type); + return RETURN_VOLUME_CORRUPTED; + } + + Name = GetString (Ehdr, Shdr->sh_name, 0); + if (Name == NULL) { + return RETURN_VOLUME_CORRUPTED; + } + + Segments[SIndex].Name = calloc (1, strlen (Name) + 1); + if (Segments[SIndex].Name == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for Segment #%d Name\n", Index); + return RETURN_OUT_OF_RESOURCES; + }; + + memcpy (Segments[SIndex].Name, Name, strlen (Name)); + + Segments[SIndex].ImageAddress = (uint32_t)(Shdr->sh_addr - BaseAddress); + Segments[SIndex].ImageSize = ALIGN_VALUE ((uint32_t)Shdr->sh_size, Context->Alignment); + Segments[SIndex].Read = true; + Segments[SIndex].Write = (Shdr->sh_flags & SHF_WRITE) != 0; + Segments[SIndex].Execute = (Shdr->sh_flags & SHF_EXECINSTR) != 0; + + Segments[SIndex].Data = calloc (1, Segments[SIndex].ImageSize); + if (Segments[SIndex].Data == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for Segment #%d Data\n", Index); + return RETURN_OUT_OF_RESOURCES; + }; + + if (Shdr->sh_type == SHT_PROGBITS) { + memcpy (Segments[SIndex].Data, (const char *)Ehdr + Shdr->sh_offset, (size_t)Shdr->sh_size); + } + + ++SIndex; + } + + assert (SIndex == ImageInfo->SegmentInfo.NumSegments); + + return SetRelocs (ImageInfo, Context); +} + +#define ScanElf ELF_SUFFIX(ScanElf) +RETURN_STATUS +ScanElf ( + OUT image_tool_image_info_t *ImageInfo, + IN const void *File, + IN uint32_t FileSize, + IN const char *SymbolsPath OPTIONAL + ) +{ + RETURN_STATUS Status; + tool_elf_scan_context Context; + const Elf_Ehdr *Ehdr; + Elf_Addr BaseAddress; + + assert (ImageInfo != NULL); + assert (File != NULL || FileSize == 0); + + Status = ParseElfFile (&Context, File, FileSize); + if (RETURN_ERROR (Status)) { + return Status; + } + + Ehdr = Context.Ehdr; + BaseAddress = Context.BaseAddress; + + memset (ImageInfo, 0, sizeof (*ImageInfo)); + + ImageInfo->HeaderInfo.BaseAddress = BaseAddress; + ImageInfo->HeaderInfo.EntryPointAddress = (uint32_t)(Ehdr->e_entry - BaseAddress); + ImageInfo->HeaderInfo.IsXip = true; + ImageInfo->SegmentInfo.SegmentAlignment = (uint32_t)Context.Alignment; + ImageInfo->RelocInfo.RelocsStripped = false; + + if (SymbolsPath != NULL) { + ImageInfo->DebugInfo.SymbolsPathLen = strlen (SymbolsPath); + } else { + assert (ImageInfo->DebugInfo.SymbolsPathLen == 0); + } + + switch (Ehdr->e_machine) { +#if ELF_ARCH == 64 + case EM_X86_64: + ImageInfo->HeaderInfo.Machine = EFI_IMAGE_MACHINE_X64; + break; + case EM_AARCH64: + ImageInfo->HeaderInfo.Machine = EFI_IMAGE_MACHINE_AARCH64; + break; +#elif ELF_ARCH == 32 + case EM_386: + ImageInfo->HeaderInfo.Machine = EFI_IMAGE_MACHINE_IA32; + break; + case EM_ARM: + ImageInfo->HeaderInfo.Machine = EFI_IMAGE_MACHINE_ARMTHUMB_MIXED; + break; +#endif + default: + fprintf (stderr, "ImageTool: Unknown ELF architecture %d\n", Ehdr->e_machine); + return RETURN_INCOMPATIBLE_VERSION; + } + + ImageInfo->DebugInfo.SymbolsPath = malloc (ImageInfo->DebugInfo.SymbolsPathLen + 1); + if (ImageInfo->DebugInfo.SymbolsPath == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for Debug Data\n"); + return RETURN_OUT_OF_RESOURCES; + }; + + if (SymbolsPath != NULL) { + memmove (ImageInfo->DebugInfo.SymbolsPath, SymbolsPath, ImageInfo->DebugInfo.SymbolsPathLen + 1); + } else { + *ImageInfo->DebugInfo.SymbolsPath = '\0'; + } + + // + // There is no corresponding ELF property. + // + ImageInfo->HeaderInfo.Subsystem = 0; + + Status = CreateIntermediate (ImageInfo, &Context); + if (RETURN_ERROR (Status)) { + ToolImageDestruct (ImageInfo); + } + + return Status; +} diff --git a/BaseTools/ImageTool/ElfScan32.c b/BaseTools/ImageTool/ElfScan32.c new file mode 100644 index 0000000000..de954058b7 --- /dev/null +++ b/BaseTools/ImageTool/ElfScan32.c @@ -0,0 +1,7 @@ +/** @file + Copyright (c) 2023, Marvin Häuser. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#define ELF_ARCH 32 +#include "ElfScan.c" diff --git a/BaseTools/ImageTool/ElfScan64.c b/BaseTools/ImageTool/ElfScan64.c new file mode 100644 index 0000000000..c229cc8740 --- /dev/null +++ b/BaseTools/ImageTool/ElfScan64.c @@ -0,0 +1,7 @@ +/** @file + Copyright (c) 2023, Marvin Häuser. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#define ELF_ARCH 64 +#include "ElfScan.c" diff --git a/BaseTools/ImageTool/ElfScanCommon.c b/BaseTools/ImageTool/ElfScanCommon.c new file mode 100644 index 0000000000..167e9df36c --- /dev/null +++ b/BaseTools/ImageTool/ElfScanCommon.c @@ -0,0 +1,24 @@ +/** @file + Copyright (c) 2023, Marvin Häuser. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#include "ElfScanCommon.h" + +RETURN_STATUS +ScanElf ( + OUT image_tool_image_info_t *ImageInfo, + IN const void *File, + IN uint32_t FileSize, + IN const char *SymbolsPath OPTIONAL + ) +{ + RETURN_STATUS Status; + + Status = ScanElf64 (ImageInfo, File, FileSize, SymbolsPath); + if (Status == RETURN_UNSUPPORTED) { + Status = ScanElf32 (ImageInfo, File, FileSize, SymbolsPath); + } + + return Status; +} diff --git a/BaseTools/ImageTool/ElfScanCommon.h b/BaseTools/ImageTool/ElfScanCommon.h new file mode 100644 index 0000000000..a8b79290f7 --- /dev/null +++ b/BaseTools/ImageTool/ElfScanCommon.h @@ -0,0 +1,29 @@ +/** @file + Copyright (c) 2023, Marvin Häuser. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#ifndef ELF_SCAN_COMMON_H +#define ELF_SCAN_COMMON_H + +#include + +#include "ImageTool.h" + +RETURN_STATUS +ScanElf32 ( + OUT image_tool_image_info_t *ImageInfo, + IN const void *File, + IN uint32_t FileSize, + IN const char *SymbolsPath OPTIONAL + ); + +RETURN_STATUS +ScanElf64 ( + OUT image_tool_image_info_t *ImageInfo, + IN const void *File, + IN uint32_t FileSize, + IN const char *SymbolsPath OPTIONAL + ); + +#endif // ELF_SCAN_COMMON_H diff --git a/BaseTools/ImageTool/GNUmakefile b/BaseTools/ImageTool/GNUmakefile new file mode 100644 index 0000000000..f4e13585ef --- /dev/null +++ b/BaseTools/ImageTool/GNUmakefile @@ -0,0 +1,25 @@ +## @file +# Copyright (c) 2021, Marvin Häuser. All rights reserved. +# Copyright (c) 2022, Mikhail Krichanov. All rights reserved. +# SPDX-License-Identifier: BSD-3-Clause +## + +PROJECT = ImageTool +PRODUCT = $(PROJECT)$(INFIX)$(SUFFIX) +OBJS = $(PROJECT).o +OBJS += Image.o UefiImageScan.o PeEmit32.o PeEmit64.o PeEmitCommon.o PeScan.o ElfScan32.o ElfScan64.o ElfScanCommon.o BinEmit.o ImageToolEmit.o +OBJS += UefiImageExtraActionLib.o +OBJS += PeCoffInit.o PeCoffInfo.o PeCoffLoad.o PeCoffRelocate.o PeCoffHii.o PeCoffDebug.o PeCoffHash.o +OBJS += UefiImageLibPeCoff.o PeCoffSupport.o CommonSupport.o + +WERROR = 1 +DEBUG = 1 +SANITIZE = 0 +OC_USER = ../../OpenCorePkg +UDK_PATH = ../.. + +VPATH += ../../MdePkg/Library/BasePeCoffLib2:$\ + ../../MdePkg/Library/BaseUefiImageExtraActionLibNull:$\ + ../../MdePkg/Library/BaseUefiImageLib + +include $(OC_USER)/User/Makefile diff --git a/BaseTools/ImageTool/Image.c b/BaseTools/ImageTool/Image.c new file mode 100644 index 0000000000..699bd89242 --- /dev/null +++ b/BaseTools/ImageTool/Image.c @@ -0,0 +1,649 @@ +/** @file + Copyright (c) 2021, Marvin Häuser. All rights reserved. + Copyright (c) 2022, Mikhail Krichanov. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#include "ImageTool.h" + +static +bool +CheckToolImageSegment ( + const image_tool_segment_info_t *SegmentInfo, + const image_tool_segment_t *Segment, + uint32_t *PreviousEndAddress + ) +{ + bool Overflow; + + assert (Segment != NULL); + assert (PreviousEndAddress != NULL); + + if (!IS_ALIGNED (Segment->ImageSize, SegmentInfo->SegmentAlignment)) { + raise (); + return false; + } + + if (Segment->Write && Segment->Execute) { + raise (); + return false; + } + + // FIXME: Expand prior segment + if (Segment->ImageAddress != *PreviousEndAddress) { + raise (); + return false; + } + + Overflow = BaseOverflowAddU32 ( + Segment->ImageAddress, + Segment->ImageSize, + PreviousEndAddress + ); + if (Overflow) { + raise (); + return false; + } + + return true; +} + +static +bool +CheckToolImageSegmentInfo ( + const image_tool_segment_info_t *SegmentInfo, + uint32_t *ImageSize + ) +{ + uint32_t Index; + bool Result; + + assert (SegmentInfo != NULL); + assert (ImageSize != NULL); + + if (!IS_POW2 (SegmentInfo->SegmentAlignment)) { + raise (); + return false; + } + + if (SegmentInfo->NumSegments == 0) { + raise (); + return false; + } + + if (!IS_ALIGNED (SegmentInfo->Segments[0].ImageAddress, SegmentInfo->SegmentAlignment)) { + raise (); + return false; + } + + *ImageSize = SegmentInfo->Segments[0].ImageAddress; + for (Index = 0; Index < SegmentInfo->NumSegments; ++Index) { + Result = CheckToolImageSegment ( + SegmentInfo, + &SegmentInfo->Segments[Index], + ImageSize + ); + if (!Result) { + raise (); + return false; + } + } + + return true; +} + +static +const image_tool_segment_t * +ImageGetSegmentByAddress ( + uint32_t *Address, + uint32_t *RemainingSize, + const image_tool_segment_info_t *SegmentInfo + ) +{ + uint32_t Index; + + assert (Address != NULL); + assert (SegmentInfo != NULL); + + for (Index = 0; Index < SegmentInfo->NumSegments; ++Index) { + if ((SegmentInfo->Segments[Index].ImageAddress <= *Address) + && (*Address < SegmentInfo->Segments[Index].ImageAddress + SegmentInfo->Segments[Index].ImageSize)) { + *Address -= SegmentInfo->Segments[Index].ImageAddress; + *RemainingSize = SegmentInfo->Segments[Index].ImageSize - *Address; + return &SegmentInfo->Segments[Index]; + } + } + + return NULL; +} + +static +bool +CheckToolImageReloc ( + const image_tool_image_info_t *Image, + uint32_t ImageSize, + const image_tool_reloc_t *Reloc + ) +{ + uint32_t RelocOffset; + uint32_t RemainingSize; + const image_tool_segment_t *Segment; + uint16_t MovHigh; + uint16_t MovLow; + + assert (Image != NULL); + assert (Reloc != NULL); + + RelocOffset = Reloc->Target; + Segment = ImageGetSegmentByAddress ( + &RelocOffset, + &RemainingSize, + &Image->SegmentInfo + ); + if (Segment == NULL) { + raise (); + return false; + } + + switch (Reloc->Type) { + case EFI_IMAGE_REL_BASED_HIGHLOW: + { + if (RemainingSize < sizeof (UINT32)) { + raise (); + return false; + } + + break; + } + + case EFI_IMAGE_REL_BASED_DIR64: + { + if (RemainingSize < sizeof (UINT64)) { + raise (); + return false; + } + + break; + } + + case EFI_IMAGE_REL_BASED_ARM_MOV32T: + { + if (RemainingSize < sizeof (UINT32)) { + raise (); + return false; + } + + if (!IS_ALIGNED (Reloc->Target, ALIGNOF (UINT16))) { + raise (); + return false; + } + + MovHigh = *(const uint16_t *)&Segment->Data[RelocOffset]; + MovLow = *(const uint16_t *)&Segment->Data[RelocOffset + 2]; + if (((MovHigh & 0xFBF0U) != 0xF200U && (MovHigh & 0xFBF0U) != 0xF2C0U) || + (MovLow & 0x8000U) != 0) { + raise (); + return false; + } + + break; + } + + default: + { + raise (); + return false; + } + } + + /*if (Segment->Write) { + printf("!!! writable reloc at %x !!!\n", Reloc->Target); + }*/ + + return true; +} + +static +bool +CheckToolImageRelocInfo ( + const image_tool_image_info_t *Image, + uint32_t ImageSize + ) +{ + const image_tool_reloc_info_t *RelocInfo; + uint32_t Index; + bool Result; + + assert (Image != NULL); + + RelocInfo = &Image->RelocInfo; + + if (RelocInfo->NumRelocs == 0) { + return true; + } + + if (RelocInfo->RelocsStripped && (RelocInfo->NumRelocs > 0)) { + raise (); + return false; + } + + if (RelocInfo->NumRelocs > (MAX_UINT32 / sizeof (UINT16))) { + raise (); + return false; + } + + Result = CheckToolImageReloc (Image, ImageSize, &RelocInfo->Relocs[0]); + if (!Result) { + raise (); + return false; + } + + for (Index = 1; Index < RelocInfo->NumRelocs; ++Index) { + if (RelocInfo->Relocs[Index].Target < RelocInfo->Relocs[Index - 1].Target) { + assert (false); + return false; + } + + Result = CheckToolImageReloc (Image, ImageSize, &RelocInfo->Relocs[Index]); + if (!Result) { + raise (); + return false; + } + } + + return true; +} + +static +bool +CheckToolImageDebugInfo ( + const image_tool_debug_info_t *DebugInfo + ) +{ + assert (DebugInfo != NULL); + + if (DebugInfo->SymbolsPath != NULL) { + // FIXME: UE-only? + if (DebugInfo->SymbolsPathLen > MAX_UINT8) { + raise (); + return false; + } + } + + return true; +} + +bool +CheckToolImage ( + const image_tool_image_info_t *Image + ) +{ + bool Result; + uint32_t ImageSize; + + assert (Image != NULL); + + Result = CheckToolImageSegmentInfo (&Image->SegmentInfo, &ImageSize); + if (!Result) { + raise (); + return false; + } + + Result = CheckToolImageRelocInfo (Image, ImageSize); + if (!Result) { + raise (); + return false; + } + + Result = CheckToolImageDebugInfo (&Image->DebugInfo); + if (!Result) { + raise (); + return false; + } + + return true; +} + +void +ImageInitUnpaddedSize ( + const image_tool_image_info_t *Image + ) +{ + uint32_t Index; + image_tool_segment_t *Segment; + + for (Index = 0; Index < Image->SegmentInfo.NumSegments; ++Index) { + Segment = &Image->SegmentInfo.Segments[Index]; + Segment->UnpaddedSize = Segment->ImageSize; + + if (Image->HeaderInfo.IsXip) { + continue; + } + + for (; Segment->UnpaddedSize > 0; --Segment->UnpaddedSize) { + if (Segment->Data[Segment->UnpaddedSize - 1] != 0) { + break; + } + } + } +} + +void +ToolImageDestruct ( + image_tool_image_info_t *Image + ) +{ + uint8_t Index; + + assert (Image != NULL); + + if (Image->SegmentInfo.Segments != NULL) { + for (Index = 0; Index < Image->SegmentInfo.NumSegments; ++Index) { + free (Image->SegmentInfo.Segments[Index].Name); + free (Image->SegmentInfo.Segments[Index].Data); + } + + free (Image->SegmentInfo.Segments); + } + + free (Image->HiiInfo.Data); + free (Image->RelocInfo.Relocs); + free (Image->DebugInfo.SymbolsPath); + + memset (Image, 0, sizeof (*Image)); +} + +bool +ToolImageRelocate ( + image_tool_image_info_t *Image, + uint64_t BaseAddress + ) +{ + uint64_t Adjust; + const image_tool_reloc_t *Reloc; + uint32_t RelocOffset; + uint32_t RemainingSize; + const image_tool_segment_t *Segment; + uint32_t Index; + uint32_t RelocTarget32; + uint64_t RelocTarget64; + + Adjust = BaseAddress - Image->HeaderInfo.BaseAddress; + + if (Adjust == 0) { + return TRUE; + } + + for (Index = 0; Index < Image->RelocInfo.NumRelocs; ++Index) { + Reloc = &Image->RelocInfo.Relocs[Index]; + + RelocOffset = Reloc->Target; + Segment = ImageGetSegmentByAddress ( + &RelocOffset, + &RemainingSize, + &Image->SegmentInfo + ); + if (Segment == NULL) { + raise (); + return false; + } + + switch (Reloc->Type) { + case EFI_IMAGE_REL_BASED_HIGHLOW: + { + assert (RemainingSize >= sizeof (UINT32)); + + RelocTarget32 = ReadUnaligned32 ((CONST VOID *)&Segment->Data[RelocOffset]); + RelocTarget32 += (uint32_t)Adjust; + WriteUnaligned32 ((VOID *)&Segment->Data[RelocOffset], RelocTarget32); + break; + } + + case EFI_IMAGE_REL_BASED_DIR64: + { + assert (RemainingSize >= sizeof (UINT64)); + + RelocTarget64 = ReadUnaligned64 ((CONST VOID *)&Segment->Data[RelocOffset]); + RelocTarget64 += Adjust; + WriteUnaligned64 ((VOID *)&Segment->Data[RelocOffset], RelocTarget64); + break; + } + + case EFI_IMAGE_REL_BASED_ARM_MOV32T: + { + assert (RemainingSize >= sizeof (UINT32)); + assert (IS_ALIGNED (Reloc->Target, ALIGNOF (UINT16))); + + PeCoffThumbMovwMovtImmediateFixup (&Segment->Data[RelocOffset], Adjust); + break; + } + + default: + { + raise (); + return false; + } + } + } + + Image->HeaderInfo.BaseAddress = BaseAddress; + + return true; +} + +static +int +ToolImageRelocCompare ( + IN const void *Buffer1, + IN const void *Buffer2 + ) +{ + const image_tool_reloc_t *Reloc1; + const image_tool_reloc_t *Reloc2; + + Reloc1 = (const image_tool_reloc_t *)Buffer1; + Reloc2 = (const image_tool_reloc_t *)Buffer2; + + if (Reloc1->Target < Reloc2->Target) { + return -1; + } + + if (Reloc1->Target > Reloc2->Target) { + return 1; + } + + return 0; +} + +void +ToolImageSortRelocs ( + image_tool_image_info_t *Image + ) +{ + if (Image->RelocInfo.Relocs == NULL) { + return; + } + + qsort ( + Image->RelocInfo.Relocs, + Image->RelocInfo.NumRelocs, + sizeof (*Image->RelocInfo.Relocs), + ToolImageRelocCompare + ); +} + +bool +ToolImageCompare ( + const image_tool_image_info_t *Image1, + const image_tool_image_info_t *Image2 + ) +{ + int CmpResult; + uint32_t SegIndex; + const char *Name1; + const char *Name2; + uint32_t NameIndex; + + // + // Compare HeaderInfo. + // + + CmpResult = memcmp ( + &Image1->HeaderInfo, + &Image2->HeaderInfo, + sizeof (Image1->HeaderInfo) + ); + if (CmpResult != 0) { + raise (); + return false; + } + + // + // Compare SegmentInfo. + // UnpaddedSize is deliberately omitted, as it's implicit by the equality of + // ImageSize and Data. + // + + CmpResult = memcmp ( + &Image1->SegmentInfo, + &Image2->SegmentInfo, + OFFSET_OF (image_tool_segment_info_t, Segments) + ); + if (CmpResult != 0) { + raise (); + return false; + } + + for (SegIndex = 0; SegIndex < Image1->SegmentInfo.NumSegments; ++SegIndex) { + CmpResult = memcmp ( + &Image1->SegmentInfo.Segments[SegIndex], + &Image2->SegmentInfo.Segments[SegIndex], + OFFSET_OF (image_tool_segment_t, Name) + ); + if (CmpResult != 0) { + raise (); + return false; + } + + // + // Don't assume images generally support arbitrarily long names or names in + // general. Check prefix equiality as a best effort. + // + Name1 = Image1->SegmentInfo.Segments[SegIndex].Name; + Name2 = Image2->SegmentInfo.Segments[SegIndex].Name; + if (Name1 != NULL && Name2 != NULL) { + for ( + NameIndex = 0; + Name1[NameIndex] != '\0' && Name2[NameIndex] != '\0'; + ++NameIndex + ) { + if (Name1[NameIndex] != Name2[NameIndex]) { + raise (); + return false; + } + } + } + + CmpResult = memcmp ( + Image1->SegmentInfo.Segments[SegIndex].Data, + Image2->SegmentInfo.Segments[SegIndex].Data, + Image1->SegmentInfo.Segments[SegIndex].ImageSize + ); + if (CmpResult != 0) { + raise (); + return false; + } + } + + // + // Compare RelocInfo. + // + + CmpResult = memcmp ( + &Image1->RelocInfo, + &Image2->RelocInfo, + OFFSET_OF (image_tool_reloc_info_t, Relocs) + ); + if (CmpResult != 0) { + raise (); + return false; + } + + CmpResult = memcmp ( + Image1->RelocInfo.Relocs, + Image2->RelocInfo.Relocs, + Image1->RelocInfo.NumRelocs * sizeof (*Image1->RelocInfo.Relocs) + ); + if (CmpResult != 0) { + raise (); + return false; + } + + // + // Compare HiiInfo. + // + + CmpResult = memcmp ( + &Image1->HiiInfo, + &Image2->HiiInfo, + OFFSET_OF (image_tool_hii_info_t, Data) + ); + if (CmpResult != 0) { + raise (); + return false; + } + + CmpResult = memcmp ( + Image1->HiiInfo.Data, + Image2->HiiInfo.Data, + Image1->HiiInfo.DataSize + ); + if (CmpResult != 0) { + raise (); + return false; + } + + // + // Compare DebugInfo. + // + + CmpResult = memcmp ( + &Image1->DebugInfo, + &Image2->DebugInfo, + OFFSET_OF (image_tool_debug_info_t, SymbolsPath) + ); + if (CmpResult != 0) { + raise (); + return false; + } + + if ((Image1->DebugInfo.SymbolsPath != NULL) != (Image2->DebugInfo.SymbolsPath != NULL)) { + raise (); + return false; + } + + if (Image1->DebugInfo.SymbolsPath != NULL) { + CmpResult = strcmp ( + Image1->DebugInfo.SymbolsPath, + Image2->DebugInfo.SymbolsPath + ); + if (CmpResult != 0) { + raise (); + return false; + } + } + + return true; +} + +void +ToolImageStripRelocs ( + image_tool_image_info_t *Image + ) +{ + Image->RelocInfo.NumRelocs = 0; + free (Image->RelocInfo.Relocs); + Image->RelocInfo.Relocs = NULL; + + Image->RelocInfo.RelocsStripped = TRUE; +} diff --git a/BaseTools/ImageTool/ImageTool.c b/BaseTools/ImageTool/ImageTool.c new file mode 100644 index 0000000000..866a369a9a --- /dev/null +++ b/BaseTools/ImageTool/ImageTool.c @@ -0,0 +1,530 @@ +/** @file + Copyright (c) 2021, Marvin Häuser. All rights reserved. + Copyright (c) 2022, Mikhail Krichanov. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#include "ImageTool.h" +#include +#include +#include + +#include + +#include "ImageToolEmit.h" + +#define EFI_ACPI_1_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_VERSION 0x0 + + +static +RETURN_STATUS +HiiBin ( + IN const char *HiiName, + IN const char *Guid, + IN const char *FileNames[], + IN UINT32 NumOfFiles + ) +{ + RETURN_STATUS Status; + void *Hii; + UINT32 HiiSize; + GUID HiiGuid; + + assert (FileNames != NULL); + assert (HiiName != NULL); + assert (Guid != NULL); + + Status = AsciiStrToGuid (Guid, &HiiGuid); + if (RETURN_ERROR (Status)) { + fprintf (stderr, "ImageTool: Invalid GUID - %s\n", Guid); + return Status; + } + + Status = ConstructHii (FileNames, NumOfFiles, &HiiGuid, &Hii, &HiiSize); + if (RETURN_ERROR (Status)) { + fprintf (stderr, "ImageTool: Could not construct HiiBin\n"); + return Status; + } + + UserWriteFile (HiiName, Hii, HiiSize); + + free (Hii); + + return RETURN_SUCCESS; +} + +static +RETURN_STATUS +CheckAcpiTable ( + IN const void *AcpiTable, + IN UINT32 Length + ) +{ + const EFI_ACPI_DESCRIPTION_HEADER *AcpiHeader; + const EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE *Facs; + UINT32 ExpectedLength; + + AcpiHeader = (const EFI_ACPI_DESCRIPTION_HEADER *)AcpiTable; + + if (AcpiHeader->Length > Length) { + fprintf (stderr, "ImageTool: AcpiTable length section size\n"); + return RETURN_VOLUME_CORRUPTED; + } + + switch (AcpiHeader->Signature) { + case EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE: + switch (AcpiHeader->Revision) { + case EFI_ACPI_1_0_FIXED_ACPI_DESCRIPTION_TABLE_REVISION: + ExpectedLength = sizeof(EFI_ACPI_1_0_FIXED_ACPI_DESCRIPTION_TABLE); + break; + case EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE_REVISION: + ExpectedLength = sizeof(EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE); + break; + case EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE_REVISION: + ExpectedLength = sizeof(EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE); + break; + default: + if (AcpiHeader->Revision > EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE_REVISION) { + ExpectedLength = AcpiHeader->Length; + break; + } + fprintf (stderr, "ImageTool: FACP revision check failed\n"); + return RETURN_VOLUME_CORRUPTED; + } + + if (ExpectedLength != AcpiHeader->Length) { + fprintf (stderr, "ImageTool: FACP length check failed\n"); + return RETURN_VOLUME_CORRUPTED; + } + break; + case EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_SIGNATURE: + Facs = (const EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE *)AcpiTable; + if (Facs->Version > EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_VERSION) { + break; + } + + if ((Facs->Version != EFI_ACPI_1_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_VERSION) + && (Facs->Version != EFI_ACPI_2_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_VERSION) + && (Facs->Version != EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_VERSION)) { + fprintf (stderr, "ImageTool: FACS version check failed\n"); + return RETURN_VOLUME_CORRUPTED; + } + + if ((Facs->Length != sizeof(EFI_ACPI_1_0_FIRMWARE_ACPI_CONTROL_STRUCTURE)) + && (Facs->Length != sizeof(EFI_ACPI_2_0_FIRMWARE_ACPI_CONTROL_STRUCTURE)) + && (Facs->Length != sizeof(EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE))) { + fprintf (stderr, "ImageTool: FACS length check failed\n"); + return RETURN_VOLUME_CORRUPTED; + } + break; + case EFI_ACPI_3_0_DIFFERENTIATED_SYSTEM_DESCRIPTION_TABLE_SIGNATURE: + if (AcpiHeader->Revision > EFI_ACPI_3_0_DIFFERENTIATED_SYSTEM_DESCRIPTION_TABLE_REVISION) { + break; + } + + if (AcpiHeader->Length <= sizeof(EFI_ACPI_DESCRIPTION_HEADER)) { + fprintf (stderr, "ImageTool: DSDT length check failed\n"); + return RETURN_VOLUME_CORRUPTED; + } + break; + case EFI_ACPI_3_0_MULTIPLE_APIC_DESCRIPTION_TABLE_SIGNATURE: + if (AcpiHeader->Revision > EFI_ACPI_3_0_MULTIPLE_APIC_DESCRIPTION_TABLE_REVISION) { + break; + } + + if ((AcpiHeader->Revision != EFI_ACPI_1_0_MULTIPLE_APIC_DESCRIPTION_TABLE_REVISION) + && (AcpiHeader->Revision != EFI_ACPI_2_0_MULTIPLE_APIC_DESCRIPTION_TABLE_REVISION) + && (AcpiHeader->Revision != EFI_ACPI_3_0_MULTIPLE_APIC_DESCRIPTION_TABLE_REVISION)) { + fprintf (stderr, "ImageTool: APIC revision check failed\n"); + return RETURN_VOLUME_CORRUPTED; + } + + if (AcpiHeader->Length <= (sizeof(EFI_ACPI_DESCRIPTION_HEADER) + sizeof(UINT32) + sizeof(UINT32))) { + fprintf (stderr, "ImageTool: APIC length check failed\n"); + return RETURN_VOLUME_CORRUPTED; + } + break; + case EFI_ACPI_3_0_PCI_EXPRESS_MEMORY_MAPPED_CONFIGURATION_SPACE_BASE_ADDRESS_DESCRIPTION_TABLE_SIGNATURE: + if (AcpiHeader->Revision > EFI_ACPI_MEMORY_MAPPED_CONFIGURATION_SPACE_ACCESS_TABLE_REVISION) { + break; + } + + if (AcpiHeader->Revision != EFI_ACPI_MEMORY_MAPPED_CONFIGURATION_SPACE_ACCESS_TABLE_REVISION) { + fprintf (stderr, "ImageTool: MCFG revision check failed\n"); + return RETURN_VOLUME_CORRUPTED; + } + + if (AcpiHeader->Length <= (sizeof(EFI_ACPI_DESCRIPTION_HEADER) + sizeof(UINT64))) { + fprintf (stderr, "ImageTool: MCFG length check failed\n"); + return RETURN_VOLUME_CORRUPTED; + } + break; + default: + break; + } + + return RETURN_SUCCESS; +} + +static +RETURN_STATUS +GetAcpi ( + IN const char *PeName, + IN const char *AcpiName + ) +{ + RETURN_STATUS Status; + void *Pe; + uint32_t PeSize; + PE_COFF_LOADER_IMAGE_CONTEXT Context; + UINT16 NumberOfSections; + const EFI_IMAGE_SECTION_HEADER *Sections; + UINT16 Index; + UINT32 FileLength; + + assert (PeName != NULL); + assert (AcpiName != NULL); + + Pe = UserReadFile (PeName, &PeSize); + if (Pe == NULL) { + fprintf (stderr, "ImageTool: Could not open %s: %s\n", PeName, strerror (errno)); + return RETURN_ABORTED; + } + + Status = PeCoffInitializeContext (&Context, Pe, (UINT32)PeSize); + if (RETURN_ERROR (Status)) { + fprintf (stderr, "ImageTool: Could not initialise Context\n"); + free (Pe); + return Status; + } + + NumberOfSections = PeCoffGetSectionTable (&Context, &Sections); + for (Index = 0; Index < NumberOfSections; ++Index) { + if ((strcmp ((char *)Sections[Index].Name, ".data") == 0) + || (strcmp ((char *)Sections[Index].Name, ".sdata") == 0) + || (strcmp ((char *)Sections[Index].Name, ".rdata") == 0)) { + + if (Sections[Index].VirtualSize < Sections[Index].SizeOfRawData) { + FileLength = Sections[Index].VirtualSize; + } else { + FileLength = Sections[Index].SizeOfRawData; + } + + Status = CheckAcpiTable ((char *)Context.FileBuffer + Sections[Index].PointerToRawData, FileLength); + if (RETURN_ERROR (Status)) { + free (Pe); + return Status; + } + + UserWriteFile (AcpiName, (char *)Context.FileBuffer + Sections[Index].PointerToRawData, FileLength); + + free (Pe); + + return RETURN_SUCCESS; + } + } + + return RETURN_NOT_FOUND; +} + +static +int32_t +NameToType ( + IN const char *TypeName + ) +{ + if ((strcmp (TypeName, "BASE") == 0) + || (strcmp (TypeName, "SEC") == 0) + || (strcmp (TypeName, "SECURITY_CORE") == 0) + || (strcmp (TypeName, "PEI_CORE") == 0) + || (strcmp (TypeName, "PEIM") == 0) + || (strcmp (TypeName, "COMBINED_PEIM_DRIVER") == 0) + || (strcmp (TypeName, "PIC_PEIM") == 0) + || (strcmp (TypeName, "RELOCATABLE_PEIM") == 0) + || (strcmp (TypeName, "DXE_CORE") == 0) + || (strcmp (TypeName, "BS_DRIVER") == 0) + || (strcmp (TypeName, "DXE_DRIVER") == 0) + || (strcmp (TypeName, "DXE_SMM_DRIVER") == 0) + || (strcmp (TypeName, "UEFI_DRIVER") == 0) + || (strcmp (TypeName, "SMM_CORE") == 0) + || (strcmp (TypeName, "MM_STANDALONE") == 0) + || (strcmp (TypeName, "MM_CORE_STANDALONE") == 0)) { + return EFI_IMAGE_SUBSYSTEM_EFI_BOOT_SERVICE_DRIVER; + } + + if ((strcmp (TypeName, "UEFI_APPLICATION") == 0) + || (strcmp (TypeName, "APPLICATION") == 0)) { + return EFI_IMAGE_SUBSYSTEM_EFI_APPLICATION; + } + + if ((strcmp (TypeName, "DXE_RUNTIME_DRIVER") == 0) + || (strcmp (TypeName, "RT_DRIVER") == 0)) { + return EFI_IMAGE_SUBSYSTEM_EFI_RUNTIME_DRIVER; + } + + if ((strcmp (TypeName, "DXE_SAL_DRIVER") == 0) + || (strcmp (TypeName, "SAL_RT_DRIVER") == 0)) { + return EFI_IMAGE_SUBSYSTEM_SAL_RUNTIME_DRIVER; + } + + return -1; +} + +static +int8_t +NameToFormat ( + IN const char *FormatName + ) +{ + if (strcmp (FormatName, "PE") == 0) { + return UefiImageFormatPe; + } + + return -1; +} + +static +RETURN_STATUS +GenExecutable ( + IN const char *OutputFileName, + IN const char *InputFileName, + IN const char *FormatName, + IN const char *TypeName, + IN const char *HiiFileName, + IN const char *BaseAddress, + IN bool Strip, + IN bool FixedAddress + ) +{ + UINT32 InputFileSize; + VOID *InputFile; + int8_t Format; + int32_t Type; + UINT32 HiiFileSize; + VOID *HiiFile; + RETURN_STATUS Status; + UINT64 NewBaseAddress; + void *OutputFile; + uint32_t OutputFileSize; + + Format = -1; + if (FormatName != NULL) { + Format = NameToFormat (FormatName); + if (Format == -1) { + fprintf (stderr, "ImageTool: Unknown output format %s\n", FormatName); + return RETURN_UNSUPPORTED; + } + } + + Type = -1; + if (TypeName != NULL) { + Type = NameToType (TypeName); + if (Type == -1) { + fprintf (stderr, "ImageTool: Unknown EFI_FILETYPE = %s\n", TypeName); + return RETURN_UNSUPPORTED; + } + } + + NewBaseAddress = 0; + if (BaseAddress != NULL) { + Status = AsciiStrHexToUint64S (BaseAddress, NULL, &NewBaseAddress); + if (RETURN_ERROR (Status)) { + fprintf (stderr, "ImageTool: Could not convert ASCII string to UINT64\n"); + return Status; + } + } + + InputFile = UserReadFile (InputFileName, &InputFileSize); + if (InputFile == NULL) { + fprintf (stderr, "ImageTool: Could not open %s: %s\n", InputFileName, strerror (errno)); + return RETURN_ABORTED; + } + + HiiFile = NULL; + HiiFileSize = 0; + if (HiiFileName != NULL) { + HiiFile = UserReadFile (HiiFileName, &HiiFileSize); + if (HiiFile == NULL) { + fprintf (stderr, "ImageTool: Could not open %s: %s\n", HiiFileName, strerror (errno)); + return RETURN_ABORTED; + } + } + + OutputFile = ToolImageEmit ( + &OutputFileSize, + InputFile, + InputFileSize, + Format, + Type, + HiiFile, + HiiFileSize, + BaseAddress != NULL, + NewBaseAddress, + InputFileName, + Strip, + FixedAddress + ); + + if (OutputFile == NULL) { + free (HiiFile); + return RETURN_ABORTED; + } + + UserWriteFile (OutputFileName, OutputFile, OutputFileSize); + + free (OutputFile); + + return RETURN_SUCCESS; +} + +int main (int argc, const char *argv[]) +{ + RETURN_STATUS Status; + UINT32 NumOfFiles; + const char *OutputName; + const char *InputName; + const char *FormatName; + const char *TypeName; + const char *HiiFileName; + const char *BaseAddress; + bool Strip; + bool FixedAddress; + int ArgIndex; + + if (argc < 2) { + fprintf (stderr, "ImageTool: No command is specified\n"); + raise (); + return -1; + } + // + // The command structure must prefix all output files with "-o" and all + // following dash-less parameters must be input files due to scanning for + // these arguments by BaseTools/GenMake. + // + if (strcmp (argv[1], "GenImage") == 0) { + if (argc < 5) { + fprintf (stderr, "ImageTool: Command arguments are missing\n"); + fprintf (stderr, " Usage: ImageTool GenImage [-c Format] [-t ModuleType] [-h HiiRc] [-b BaseAddress] [-s] [-f] -o OutputFile InputFile\n"); + raise (); + return -1; + } + + OutputName = NULL; + InputName = NULL; + FormatName = NULL; + TypeName = NULL; + HiiFileName = NULL; + BaseAddress = NULL; + Strip = false; + FixedAddress = false; + for (ArgIndex = 2; ArgIndex < argc; ++ArgIndex) { + if (strcmp (argv[ArgIndex], "-o") == 0) { + ++ArgIndex; + if (ArgIndex == argc) { + fprintf (stderr, "Must specify an argument to -o\n"); + return -1; + } + + OutputName = argv[ArgIndex]; + } else if (strcmp (argv[ArgIndex], "-c") == 0) { + ++ArgIndex; + if (ArgIndex == argc) { + fprintf (stderr, "Must specify an argument to -c\n"); + return -1; + } + + FormatName = argv[ArgIndex]; + } else if (strcmp (argv[ArgIndex], "-t") == 0) { + ++ArgIndex; + if (ArgIndex == argc) { + fprintf (stderr, "Must specify an argument to -t\n"); + return -1; + } + + TypeName = argv[ArgIndex]; + } else if (strcmp (argv[ArgIndex], "-h") == 0) { + ++ArgIndex; + if (ArgIndex == argc) { + fprintf (stderr, "Must specify an argument to -h\n"); + return -1; + } + + HiiFileName = argv[ArgIndex]; + } else if (strcmp (argv[ArgIndex], "-b") == 0) { + ++ArgIndex; + if (ArgIndex == argc) { + fprintf (stderr, "Must specify an argument to -b\n"); + return -1; + } + + BaseAddress = argv[ArgIndex]; + } else if (strcmp (argv[ArgIndex], "-s") == 0) { + Strip = true; + } else if (strcmp (argv[ArgIndex], "-f") == 0) { + FixedAddress = true; + } else if (argv[ArgIndex][0] == '-') { + fprintf (stderr, "Unknown parameter %s\n", argv[ArgIndex]); + } else if (InputName == NULL) { + InputName = argv[ArgIndex]; + } else { + fprintf (stderr, "GenImage only supports one input file.\n"); + return -1; + } + } + + if (OutputName == NULL) { + fprintf (stderr, "Must provide an output file.\n"); + return -1; + } + + if (InputName == NULL) { + fprintf (stderr, "Must provide an input file.\n"); + return -1; + } + + Status = GenExecutable ( + OutputName, + InputName, + FormatName, + TypeName, + HiiFileName, + BaseAddress, + Strip, + FixedAddress + ); + if (RETURN_ERROR (Status)) { + raise (); + return -1; + } + } else if (strcmp (argv[1], "HiiBin") == 0) { + if (argc < 5 || strcmp (argv[3], "-o") != 0) { + fprintf (stderr, "ImageTool: Command arguments are missing\n"); + fprintf (stderr, " Usage: ImageTool HiiBin GUID -o OutputFile InputFile1 InputFile2 ...\n"); + raise (); + return -1; + } + + NumOfFiles = (UINT32)argc - 5U; + + Status = HiiBin (argv[4], argv[2], &argv[5], NumOfFiles); + if (RETURN_ERROR (Status)) { + raise (); + return -1; + } + } else if (strcmp (argv[1], "GetAcpi") == 0) { + if (argc != 5 || strcmp (argv[2], "-o") != 0) { + fprintf (stderr, "ImageTool: Command arguments are missing\n"); + fprintf (stderr, " Usage: ImageTool GetAcpi -o OutputFile InputFile\n"); + raise (); + return -1; + } + + Status = GetAcpi (argv[4], argv[3]); + if (RETURN_ERROR (Status)) { + raise (); + return -1; + } + } + + return 0; +} diff --git a/BaseTools/ImageTool/ImageTool.h b/BaseTools/ImageTool/ImageTool.h new file mode 100644 index 0000000000..048579a315 --- /dev/null +++ b/BaseTools/ImageTool/ImageTool.h @@ -0,0 +1,185 @@ +/** @file + Copyright (c) 2021, Marvin Häuser. All rights reserved. + Copyright (c) 2022, Mikhail Krichanov. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#ifndef IMAGE_TOOL_H +#define IMAGE_TOOL_H + +#include + +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#define MAX_PE_ALIGNMENT 0x10000 + +#define raise() assert(false) + +typedef struct { + EFI_IMAGE_DEBUG_DIRECTORY_ENTRY Dir; + EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY Nb10; + char Name[]; +} DebugData; + +#define PAGE(x) ((x) & ~4095U) +#define PAGE_OFF(x) ((x) & 4095U) + +typedef struct { + uint64_t BaseAddress; + uint32_t EntryPointAddress; + uint16_t Machine; + uint16_t Subsystem; + uint8_t IsXip; + uint8_t FixedAddress; + uint8_t Reserved[6]; +} image_tool_header_info_t; + +typedef struct { + uint32_t ImageAddress; + uint32_t ImageSize; + uint8_t Read; + uint8_t Write; + uint8_t Execute; + uint8_t Reserved[1]; + + char *Name; + uint8_t *Data; + + uint32_t UnpaddedSize; +} image_tool_segment_t; + +typedef struct { + uint32_t SegmentAlignment; + uint32_t NumSegments; + + image_tool_segment_t *Segments; +} image_tool_segment_info_t; + +typedef struct { + uint8_t Type; + uint8_t Reserved[3]; + uint32_t Target; +} image_tool_reloc_t; + +typedef struct { + uint32_t NumRelocs; + uint8_t RelocsStripped; + uint8_t Reserved[3]; + + image_tool_reloc_t *Relocs; +} image_tool_reloc_info_t; + +typedef struct { + uint32_t SymbolsPathLen; + + char *SymbolsPath; +} image_tool_debug_info_t; + +typedef struct { + uint32_t DebugDirAddress; + uint32_t DebugDirSize; +} image_tool_pe_datadir_info_t; + +typedef struct { + uint32_t DataSize; + + void *Data; +} image_tool_hii_info_t; + +typedef struct { + image_tool_header_info_t HeaderInfo; + image_tool_segment_info_t SegmentInfo; + image_tool_reloc_info_t RelocInfo; + image_tool_hii_info_t HiiInfo; + image_tool_debug_info_t DebugInfo; +} image_tool_image_info_t; + +void +ToolImageDestruct ( + image_tool_image_info_t *Image + ); + +void +ImageInitUnpaddedSize ( + const image_tool_image_info_t *Image + ); + +bool +ToolImageRelocate ( + image_tool_image_info_t *Image, + uint64_t BaseAddress + ); + +void +ToolImageSortRelocs ( + image_tool_image_info_t *Image + ); + +bool +ToolImageCompare ( + const image_tool_image_info_t *Image1, + const image_tool_image_info_t *Image2 + ); + +void +ToolImageStripRelocs ( + image_tool_image_info_t *Image + ); + +RETURN_STATUS +ToolContextConstructUefiImage ( + OUT image_tool_image_info_t *Image, + OUT INT8 *Format, + IN const void *File, + IN size_t FileSize + ); + +bool +CheckToolImage ( + const image_tool_image_info_t *Image + ); + +void * +ToolImageEmitPe ( + image_tool_image_info_t *Image, + uint32_t *FileSize, + bool Strip + ); + +RETURN_STATUS +ScanElf ( + OUT image_tool_image_info_t *ImageInfo, + IN const void *File, + IN uint32_t FileSize, + IN const char *SymbolsPath OPTIONAL + ); + +extern CONST UINT8 mHiiResourceSectionHeaderSize; + +VOID +InitializeHiiResouceSectionHeader ( + OUT UINT8 *HiiSectionHeader, + IN UINT32 HiiDataAddress, + IN UINT32 HiiDataSize + ); + +RETURN_STATUS +ConstructHii ( + IN const char *FileNames[], + IN UINT32 NumOfFiles, + IN GUID *HiiGuid, + OUT void **Hii, + OUT UINT32 *HiiSize + ); + +#endif // IMAGE_TOOL_H diff --git a/BaseTools/ImageTool/ImageToolEmit.c b/BaseTools/ImageTool/ImageToolEmit.c new file mode 100644 index 0000000000..338ac0fce2 --- /dev/null +++ b/BaseTools/ImageTool/ImageToolEmit.c @@ -0,0 +1,184 @@ +/** @file + Copyright (c) 2023, Marvin Häuser. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#include "ImageTool.h" + +#include + +#include + +#include + +#include "ImageToolEmit.h" + +static +RETURN_STATUS +ToolContextConstruct ( + OUT image_tool_image_info_t *ImageInfo, + OUT int8_t *Format, + IN const void *File, + IN uint32_t FileSize, + IN const char *SymbolsPath OPTIONAL + ) +{ + RETURN_STATUS Status; + + *Format = -1; + + Status = ToolContextConstructUefiImage ( + ImageInfo, + Format, + File, + FileSize + ); + if (Status == RETURN_UNSUPPORTED) { + Status = ScanElf (ImageInfo, File, FileSize, SymbolsPath); + } + + return Status; +} + +static +RETURN_STATUS +ValidateOutputFile ( + void *OutputFile, + uint32_t OutputFileSize, + const image_tool_image_info_t *ImageInfo + ) +{ + RETURN_STATUS Status; + bool Result; + image_tool_image_info_t OutputImageInfo; + int8_t Format; + + Status = ToolContextConstruct ( + &OutputImageInfo, + &Format, + OutputFile, + OutputFileSize, + NULL + ); + if (EFI_ERROR (Status)) { + assert (false); + return Status; + } + + Result = CheckToolImage (&OutputImageInfo); + if (!Result) { + raise (); + ToolImageDestruct (&OutputImageInfo); + return RETURN_UNSUPPORTED; + } + + Result = ToolImageCompare (&OutputImageInfo, ImageInfo); + + ToolImageDestruct (&OutputImageInfo); + + if (!Result) { + assert (false); + return RETURN_VOLUME_CORRUPTED; + } + + return RETURN_SUCCESS; +} + +void * +ToolImageEmit ( + OUT uint32_t *OutputFileSize, + IN const void *Buffer, + IN uint32_t BufferSize, + IN int8_t Format, + IN int32_t Type, + IN void *HiiFile, + IN uint32_t HiiFileSize, + IN bool Relocate, + IN uint64_t BaseAddress, + IN const char *SymbolsPath OPTIONAL, + IN bool Strip, + IN bool FixedAddress + ) +{ + RETURN_STATUS Status; + bool Success; + image_tool_image_info_t ImageInfo; + int8_t SourceFormat; + void *OutputFile; + + Status = ToolContextConstruct ( + &ImageInfo, + &SourceFormat, + Buffer, + BufferSize, + SymbolsPath + ); + + if (SymbolsPath == NULL) { + SymbolsPath = ""; + } + + if (RETURN_ERROR (Status)) { + fprintf (stderr, "ImageTool: Could not parse input file %s - %llx\n", SymbolsPath, (unsigned long long)Status); + return NULL; + } + + if (Format == -1) { + Format = SourceFormat; + if (Format == -1) { + fprintf (stderr, "ImageTool: Unknown output format of file %s\n", SymbolsPath); + ToolImageDestruct (&ImageInfo); + return NULL; + } + } + + if (Type != -1) { + ImageInfo.HeaderInfo.Subsystem = (uint16_t)Type; + } + + if (HiiFile != NULL) { + free (ImageInfo.HiiInfo.Data); + + ImageInfo.HiiInfo.Data = HiiFile; + ImageInfo.HiiInfo.DataSize = HiiFileSize; + } + + ToolImageSortRelocs (&ImageInfo); + + Success = CheckToolImage (&ImageInfo); + if (!Success) { + ToolImageDestruct (&ImageInfo); + return NULL; + } + + if (Relocate) { + Success = ToolImageRelocate (&ImageInfo, BaseAddress); + if (!Success) { + fprintf (stderr, "ImageTool: Failed to relocate input file %s\n", SymbolsPath); + ToolImageDestruct (&ImageInfo); + return NULL; + } + } + + if (FixedAddress) { + ImageInfo.HeaderInfo.FixedAddress = true; + } + + OutputFile = NULL; + if (Format == UefiImageFormatPe) { + OutputFile = ToolImageEmitPe (&ImageInfo, OutputFileSize, Strip); + } else { + assert (false); + } + + Status = ValidateOutputFile (OutputFile, *OutputFileSize, &ImageInfo); + + ToolImageDestruct (&ImageInfo); + + if (EFI_ERROR (Status)) { + assert (false); + return NULL; + } + + return OutputFile; +} diff --git a/BaseTools/ImageTool/ImageToolEmit.h b/BaseTools/ImageTool/ImageToolEmit.h new file mode 100644 index 0000000000..6bf7493f3f --- /dev/null +++ b/BaseTools/ImageTool/ImageToolEmit.h @@ -0,0 +1,29 @@ +/** @file + Copyright (c) 2023, Marvin Häuser. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#ifndef IMAGE_TOOL_EMIT_H +#define IMAGE_TOOL_EMIT_H + +#include + +#include + +void * +ToolImageEmit ( + OUT uint32_t *OutputFileSize, + IN const void *Buffer, + IN uint32_t BufferSize, + IN int8_t Format, + IN int32_t Type, + IN void *HiiFile, + IN uint32_t HiiFileSize, + IN bool Relocate, + IN uint64_t BaseAddress, + IN const char *SymbolsPath OPTIONAL, + IN bool Strip, + IN bool FixedAddress + ); + +#endif // IMAGE_TOOL_EMIT_H diff --git a/BaseTools/ImageTool/Makefile b/BaseTools/ImageTool/Makefile new file mode 100644 index 0000000000..76e9479d96 --- /dev/null +++ b/BaseTools/ImageTool/Makefile @@ -0,0 +1,108 @@ +## @file +# Windows makefile for 'ImageTool' module build. +# +# Copyright (c) 2022, Mikhail Krichanov. All rights reserved. +# SPDX-License-Identifier: BSD-3-Clause +# +!INCLUDE ..\Source\C\Makefiles\ms.common + +APP = ImageTool + +OC_USER = ..\..\OpenCorePkg +UDK_PATH = ..\.. +UDK_ARCH = $(HOST_ARCH) +OUT_DIR = .\Windows + +OV = $(UDK_PATH)\MdePkg\Library\BaseOverflowLib +PE = $(UDK_PATH)\MdePkg\Library\BasePeCoffLib2 +UA = $(UDK_PATH)\MdePkg\Library\BaseUefiImageExtraActionLibNull + +OBJECTS = ImageTool.obj Image.obj PeEmit32.obj PeEmit64.obj PeEmitCommon.obj UefiImageScan.obj PeScan.obj ElfScan32.obj ElfScan64.obj ElfScanCommon.obj BinEmit.obj ImageToolEmit.obj +OBJECTS = $(OBJECTS) {$(OV)}BaseAlignment.obj BaseBitOverflow.obj {$(UA)}UefiImageExtraActionLib.obj +OBJECTS = $(OBJECTS) {$(PE)}PeCoffInit.obj PeCoffInfo.obj PeCoffRelocate.obj PeCoffLoad.obj PeCoffHii.obj PeCoffDebug.obj PeCoffHash.obj + +BASE = $(UDK_PATH)\MdePkg\Library\BaseLib +OUT = $(UDK_PATH)\MdePkg\Library\UefiDebugLibConOut +PRIN = $(UDK_PATH)\MdePkg\Library\BasePrintLib +ERRO = $(UDK_PATH)\MdePkg\Library\BaseDebugPrintErrorLevelLib +UIMG = $(UDK_PATH)\MdePkg\Library\BaseUefiImageLib +BMPN = $(UDK_PATH)\MdeModulePkg\Library\BaseMemoryProfileLibNull +CMEM = $(UDK_PATH)\MdeModulePkg\Library\CommonMemoryAllocationLib +USER = $(OC_USER)\User\Library +OBJECTS = $(OBJECTS) {$(BASE)}SafeString.obj String.obj SwapBytes16.obj SwapBytes32.obj CpuDeadLoop.obj CheckSum.obj QuickSort.obj LinkedList.obj +OBJECTS = $(OBJECTS) {$(OUT)}DebugLib.obj {$(PRIN)}PrintLib.obj PrintLibInternal.obj {$(ERRO)}BaseDebugPrintErrorLevelLib.obj +OBJECTS = $(OBJECTS) {$(UIMG)}UefiImageLibPeCoff.obj PeCoffSupport.obj CommonSupport.obj +OBJECTS = $(OBJECTS) {$(USER)}UserFile.obj UserBaseMemoryLib.obj UserMath.obj UserPcd.obj UserMisc.obj UserGlobalVar.obj UserBootServices.obj +OBJECTS = $(OBJECTS) {$(BMPN)}BaseMemoryProfileLibNull.obj {$(CMEM)}CommonMemoryAllocationLib.obj {$(CMEM)}CommonMemoryAllocationLibEx.obj + +INC = -I . -I $(OC_USER)\User\Include -I $(OC_USER)\Include\Acidanthera +INC = $(INC) -I $(UDK_PATH)\MdePkg\Include -I $(UDK_PATH)\MdePkg\Include\Library -I $(UDK_PATH)\MdePkg\Include\$(UDK_ARCH) +INC = $(INC) -I $(UDK_PATH)\MdePkg\Library\BaseLib -I $(UDK_PATH)\MdeModulePkg\Include -I $(UDK_PATH)\UefiCpuPkg\Include +INC = $(INC) /FI $(OC_USER)\User\Include\UserPcd.h /FI $(UDK_PATH)\MdePkg\Include\Base.h /FI $(OC_USER)\User\Include\UserGlobalVar.h + +all: + -if not exist $(OUT_DIR) mkdir $(OUT_DIR) + $(MAKE) $(APP) + +$(APP) : $(OBJECTS) + -@if not exist $(BIN_PATH) mkdir $(BIN_PATH) + @cd $(OUT_DIR) + $(LD) /nologo /debug /OPT:REF /OPT:ICF=10 /incremental:no /nodefaultlib:libc.lib /out:..\$@ $(LIBS) $** + @copy /y ..\$@ $(BIN_PATH)\$@.exe + +.PHONY:clean +.PHONY:cleanall + +clean: + del /f /q $(OUT_DIR) $(APP) *.pdb > nul + +cleanall: + del /f /q $(OUT_DIR) *.pdb $(BIN_PATH)\$(APP).exe > nul + +.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(OV)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(PE)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(UA)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(BASE)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) /wd 4005 $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(BMPN)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(CMEM)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(OUT)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(PRIN)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) /wd 4005 $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(ERRO)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(UIMG)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(USER)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) /D WIN32 /wd 4754 $< -Fo$@ + @move $@ $(OUT_DIR)\ diff --git a/BaseTools/ImageTool/PeEmit.c b/BaseTools/ImageTool/PeEmit.c new file mode 100644 index 0000000000..ef4ffb30df --- /dev/null +++ b/BaseTools/ImageTool/PeEmit.c @@ -0,0 +1,1036 @@ +/** @file + Copyright (c) 2021, Marvin Häuser. All rights reserved. + Copyright (c) 2022, Mikhail Krichanov. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#include "ImageTool.h" + +#if PE_ARCH == 32 + +#define EFI_IMAGE_NT_HEADERS EFI_IMAGE_NT_HEADERS32 +#define EFI_IMAGE_NT_OPTIONAL_HDR_MAGIC EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC + +#elif PE_ARCH == 64 + +#define EFI_IMAGE_NT_HEADERS EFI_IMAGE_NT_HEADERS64 +#define EFI_IMAGE_NT_OPTIONAL_HDR_MAGIC EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC + +#endif + +#define PE_SUFFIX__(Name, Arch) Name##Arch +#define PE_SUFFIX_(Name, Arch) PE_SUFFIX__ (Name, Arch) +#define PE_SUFFIX(Name) PE_SUFFIX_ (Name, PE_ARCH) + +typedef struct { + uint8_t NumExtraSections; + uint32_t SizeOfHeaders; + uint8_t NumberOfRvaAndSizes; + uint16_t SizeOfOptionalHeader; + uint32_t SectionHeadersSize; + uint32_t ExtraSectionHeadersSize; +} image_tool_emit_pe_hdr_info_t; + +typedef struct { + const image_tool_image_info_t *Image; + EFI_IMAGE_NT_HEADERS *PeHdr; + image_tool_emit_pe_hdr_info_t HdrInfo; + uint32_t SectionsSize; + uint32_t HiiSectionAddress; + uint32_t ExtraSectionsSize; + uint32_t UnsignedFileSize; + uint32_t RelocTableSize; + uint32_t DebugTableSize; + uint32_t FileAlignment; +} image_tool_pe_emit_context_t; + +#define EmitPeGetHeaderSizes PE_SUFFIX (EmitPeGetHeaderSizes) +static +bool +EmitPeGetHeaderSizes ( + const image_tool_image_info_t *Image, + image_tool_emit_pe_hdr_info_t *HdrInfo + ) +{ + assert (Image != NULL); + assert (HdrInfo != NULL); + + if (Image->RelocInfo.NumRelocs > 0) { + HdrInfo->ExtraSectionHeadersSize += sizeof (EFI_IMAGE_SECTION_HEADER); + } + + if (Image->HiiInfo.DataSize > 0) { + HdrInfo->ExtraSectionHeadersSize += sizeof (EFI_IMAGE_SECTION_HEADER); + } + + if (Image->DebugInfo.SymbolsPath != NULL) { + HdrInfo->ExtraSectionHeadersSize += sizeof (EFI_IMAGE_SECTION_HEADER); + } + + HdrInfo->SectionHeadersSize = (uint32_t)Image->SegmentInfo.NumSegments * sizeof (EFI_IMAGE_SECTION_HEADER); + HdrInfo->NumberOfRvaAndSizes = EFI_IMAGE_NUMBER_OF_DIRECTORY_ENTRIES; + HdrInfo->SizeOfOptionalHeader = sizeof (EFI_IMAGE_NT_HEADERS) - sizeof (EFI_IMAGE_NT_HEADERS_COMMON_HDR) + + HdrInfo->NumberOfRvaAndSizes * sizeof (EFI_IMAGE_DATA_DIRECTORY); + HdrInfo->SizeOfHeaders = sizeof (EFI_IMAGE_DOS_HEADER) + sizeof (EFI_IMAGE_NT_HEADERS) + + HdrInfo->NumberOfRvaAndSizes * sizeof (EFI_IMAGE_DATA_DIRECTORY) + + HdrInfo->SectionHeadersSize + HdrInfo->ExtraSectionHeadersSize; + + return true; +} + +#define EmitPeGetSectionsSize PE_SUFFIX (EmitPeGetSectionsSize) +static +bool +EmitPeGetSectionsSize ( + const image_tool_pe_emit_context_t *Context, + uint32_t *SectionsSize + ) +{ + const image_tool_image_info_t *Image; + uint8_t Index; + uint32_t DataSize; + bool Overflow; + + assert (Context != NULL); + assert (SectionsSize != NULL); + + Image = Context->Image; + *SectionsSize = 0; + + for (Index = 0; Index < Image->SegmentInfo.NumSegments; ++Index) { + Overflow = BaseOverflowAlignUpU32 ( + Image->SegmentInfo.Segments[Index].UnpaddedSize, + Context->FileAlignment, + &DataSize + ); + if (Overflow) { + raise (); + return false; + } + + Overflow = BaseOverflowAddU32 (*SectionsSize, DataSize, SectionsSize); + if (Overflow) { + raise (); + return false; + } + } + + return true; +} + +#define EmitPeGetRelocSectionSize PE_SUFFIX (EmitPeGetRelocSectionSize) +static +bool +EmitPeGetRelocSectionSize ( + const image_tool_image_info_t *Image, + uint32_t *RelocsSize + ) +{ + uint32_t RelocTableSize; + uint32_t BlockAddress; + uint32_t BlockSize; + uint32_t Index; + uint32_t RelocAddress; + + assert (Image != NULL); + assert (RelocsSize != NULL); + + if (Image->RelocInfo.NumRelocs == 0) { + *RelocsSize = 0; + return true; + } + + assert (Image->RelocInfo.NumRelocs <= MAX_UINT32); + + RelocTableSize = 0; + BlockAddress = PAGE(Image->RelocInfo.Relocs[0].Target); + BlockSize = sizeof (EFI_IMAGE_BASE_RELOCATION_BLOCK); + + for (Index = 0; Index < Image->RelocInfo.NumRelocs; ++Index) { + RelocAddress = PAGE(Image->RelocInfo.Relocs[Index].Target); + if (RelocAddress != BlockAddress) { + BlockSize = ALIGN_VALUE (BlockSize, 4); + + RelocTableSize += BlockSize; + + BlockAddress = RelocAddress; + BlockSize = sizeof (EFI_IMAGE_BASE_RELOCATION_BLOCK); + } + + BlockSize += sizeof (UINT16); + } + + BlockSize = ALIGN_VALUE (BlockSize, 4); + RelocTableSize += BlockSize; + + *RelocsSize = RelocTableSize; + + return true; +} + +#define EmitPeGetDebugSectionSize PE_SUFFIX (EmitPeGetDebugSectionSize) +static +void +EmitPeGetDebugSectionSize ( + const image_tool_image_info_t *Image, + uint32_t *DebugSize + ) +{ + uint32_t Size; + + assert (Image != NULL); + assert (DebugSize != NULL); + + Size = 0; + if (Image->DebugInfo.SymbolsPath != NULL) { + Size = sizeof (DebugData) + Image->DebugInfo.SymbolsPathLen + 1; + } + + *DebugSize = Size; +} + +#define EmitPeGetExtraSectionsSize PE_SUFFIX (EmitPeGetExtraSectionsSize) +static +bool +EmitPeGetExtraSectionsSize ( + image_tool_pe_emit_context_t *Context, + uint32_t *SectionsSize + ) +{ + const image_tool_image_info_t *Image; + bool Result; + uint32_t AlignedRelocTableSize; + bool Overflow; + uint32_t AlignedDebugTableSize; + uint32_t AlignedHiiTableSize; + + assert (Context != NULL); + assert (SectionsSize != NULL); + + Image = Context->Image; + + Result = EmitPeGetRelocSectionSize (Image, &Context->RelocTableSize); + if (!Result) { + raise (); + return false; + } + + EmitPeGetDebugSectionSize (Image, &Context->DebugTableSize); + + Overflow = BaseOverflowAlignUpU32 ( + Context->RelocTableSize, + Context->FileAlignment, + &AlignedRelocTableSize + ); + if (Overflow) { + raise (); + return false; + } + + Overflow = BaseOverflowAlignUpU32 ( + Context->DebugTableSize, + Context->FileAlignment, + &AlignedDebugTableSize + ); + if (Overflow) { + raise (); + return false; + } + + AlignedHiiTableSize = 0; + if (Context->Image->HiiInfo.DataSize > 0) { + Overflow = BaseOverflowAddU32 ( + mHiiResourceSectionHeaderSize, + Context->Image->HiiInfo.DataSize, + &AlignedHiiTableSize + ); + + Overflow |= BaseOverflowAlignUpU32 ( + AlignedHiiTableSize, + Context->FileAlignment, + &AlignedHiiTableSize + ); + if (Overflow) { + raise (); + return false; + } + } + + Overflow = BaseOverflowAddU32 ( + AlignedRelocTableSize, + AlignedDebugTableSize, + SectionsSize + ); + if (Overflow) { + raise (); + return false; + } + + Overflow = BaseOverflowAddU32 ( + *SectionsSize, + AlignedHiiTableSize, + SectionsSize + ); + if (Overflow) { + raise (); + return false; + } + + return true; +} + +#define ToolImageEmitPeSectionHeaders PE_SUFFIX (ToolImageEmitPeSectionHeaders) +static +bool +ToolImageEmitPeSectionHeaders ( + const image_tool_pe_emit_context_t *Context, + uint8_t **Buffer, + uint32_t *BufferSize, + uint32_t AlignedHeaderSize + ) +{ + const image_tool_image_info_t *Image; + uint16_t SectionHeadersSize; + uint32_t SectionOffset; + EFI_IMAGE_SECTION_HEADER *Sections; + uint8_t Index; + + assert (Context != NULL); + assert (Buffer != NULL); + assert (BufferSize != NULL); + + Image = Context->Image; + SectionHeadersSize = (uint16_t) (Image->SegmentInfo.NumSegments * sizeof (EFI_IMAGE_SECTION_HEADER)); + SectionOffset = AlignedHeaderSize; + Sections = (void *) *Buffer; + + assert (SectionHeadersSize <= *BufferSize); + + for (Index = 0; Index < Image->SegmentInfo.NumSegments; ++Index) { + assert (Sections[Index].Characteristics == 0); + + if (Image->SegmentInfo.Segments[Index].Read) { + Sections[Index].Characteristics |= EFI_IMAGE_SCN_MEM_READ; + } + + if (Image->SegmentInfo.Segments[Index].Write) { + Sections[Index].Characteristics |= EFI_IMAGE_SCN_MEM_WRITE; + } + + if (Image->SegmentInfo.Segments[Index].Execute) { + Sections[Index].Characteristics |= EFI_IMAGE_SCN_MEM_EXECUTE | EFI_IMAGE_SCN_CNT_CODE; + } else { + Sections[Index].Characteristics |= EFI_IMAGE_SCN_CNT_INITIALIZED_DATA; + } + + Sections[Index].PointerToRawData = SectionOffset; + Sections[Index].VirtualAddress = SectionOffset; + Sections[Index].SizeOfRawData = ALIGN_VALUE (Image->SegmentInfo.Segments[Index].UnpaddedSize, Context->FileAlignment); + Sections[Index].VirtualSize = Image->SegmentInfo.Segments[Index].ImageSize; + + strncpy ( + (char *) Sections[Index].Name, + Image->SegmentInfo.Segments[Index].Name, + sizeof (Sections[Index].Name) + ); + + SectionOffset += Sections[Index].SizeOfRawData; + } + + if (Image->HeaderInfo.FixedAddress) { + for (Index = 0; Index < Image->SegmentInfo.NumSegments; ++Index) { + if ((Sections[Index].Characteristics & EFI_IMAGE_SCN_MEM_EXECUTE) == 0) { + WriteUnaligned64 ( + (VOID *)&Sections[Index].PointerToRelocations, + Image->HeaderInfo.BaseAddress + ); + break; + } + } + + if (Index == Image->SegmentInfo.NumSegments) { + raise (); + return false; + } + } + + *BufferSize -= SectionHeadersSize; + *Buffer += SectionHeadersSize; + + assert (SectionHeadersSize == Context->HdrInfo.SectionHeadersSize); + + return true; +} + +#define ToolImageEmitPeExtraSectionHeaders PE_SUFFIX (ToolImageEmitPeExtraSectionHeaders) +static +bool +ToolImageEmitPeExtraSectionHeaders ( + image_tool_pe_emit_context_t *Context, + uint8_t **Buffer, + uint32_t *BufferSize, + uint32_t AlignedHeaderSize + ) +{ + uint32_t SectionHeadersSize; + EFI_IMAGE_SECTION_HEADER *Section; + uint32_t SectionOffset; + uint32_t HiiSectionSize; + + assert (Context != NULL); + assert (Buffer != NULL); + assert (BufferSize != NULL); + + SectionHeadersSize = 0; + SectionOffset = AlignedHeaderSize + Context->SectionsSize; + + if (Context->Image->HiiInfo.DataSize > 0) { + ++Context->PeHdr->CommonHeader.FileHeader.NumberOfSections; + + assert (sizeof (EFI_IMAGE_SECTION_HEADER) <= *BufferSize); + + HiiSectionSize = mHiiResourceSectionHeaderSize + Context->Image->HiiInfo.DataSize; + + Section = (void *) *Buffer; + + strncpy ((char *)Section->Name, ".rsrc", sizeof (Section->Name)); + Section->SizeOfRawData = ALIGN_VALUE (HiiSectionSize, Context->FileAlignment); + Section->VirtualSize = ALIGN_VALUE (HiiSectionSize, Context->Image->SegmentInfo.SegmentAlignment); + Section->Characteristics = EFI_IMAGE_SCN_CNT_INITIALIZED_DATA | EFI_IMAGE_SCN_MEM_READ; + Section->PointerToRawData = SectionOffset; + Section->VirtualAddress = Section->PointerToRawData; + + Context->HiiSectionAddress = SectionOffset; + + SectionOffset += Section->SizeOfRawData; + + Context->PeHdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].Size = HiiSectionSize; + Context->PeHdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress = Section->PointerToRawData; + + *BufferSize -= sizeof (EFI_IMAGE_SECTION_HEADER); + *Buffer += sizeof (EFI_IMAGE_SECTION_HEADER); + SectionHeadersSize += sizeof (EFI_IMAGE_SECTION_HEADER); + } + + if (Context->RelocTableSize > 0) { + ++Context->PeHdr->CommonHeader.FileHeader.NumberOfSections; + + assert (sizeof (EFI_IMAGE_SECTION_HEADER) <= *BufferSize); + + Section = (void *) *Buffer; + + strncpy ((char *)Section->Name, ".reloc", sizeof (Section->Name)); + Section->SizeOfRawData = ALIGN_VALUE (Context->RelocTableSize, Context->FileAlignment); + Section->VirtualSize = Section->SizeOfRawData; + Section->Characteristics = EFI_IMAGE_SCN_CNT_INITIALIZED_DATA + | EFI_IMAGE_SCN_MEM_DISCARDABLE | EFI_IMAGE_SCN_MEM_READ; + Section->PointerToRawData = SectionOffset; + Section->VirtualAddress = Section->PointerToRawData; + + SectionOffset += Section->SizeOfRawData; + + Context->PeHdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size = Context->RelocTableSize; + Context->PeHdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress = Section->PointerToRawData; + + *BufferSize -= sizeof (EFI_IMAGE_SECTION_HEADER); + *Buffer += sizeof (EFI_IMAGE_SECTION_HEADER); + SectionHeadersSize += sizeof (EFI_IMAGE_SECTION_HEADER); + } + + if (Context->DebugTableSize > 0) { + ++Context->PeHdr->CommonHeader.FileHeader.NumberOfSections; + + assert (sizeof (EFI_IMAGE_SECTION_HEADER) <= *BufferSize); + + Section = (void *) *Buffer; + + strncpy ((char *)Section->Name, ".debug", sizeof (Section->Name)); + Section->SizeOfRawData = ALIGN_VALUE (Context->DebugTableSize, Context->FileAlignment); + Section->VirtualSize = Section->SizeOfRawData; + Section->Characteristics = EFI_IMAGE_SCN_CNT_INITIALIZED_DATA | EFI_IMAGE_SCN_MEM_READ; + Section->PointerToRawData = SectionOffset; + Section->VirtualAddress = Section->PointerToRawData; + + SectionOffset += Section->SizeOfRawData; + + Context->PeHdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size = sizeof (EFI_IMAGE_DEBUG_DIRECTORY_ENTRY); + Context->PeHdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress = Section->VirtualAddress; + + *BufferSize -= sizeof (EFI_IMAGE_SECTION_HEADER); + *Buffer += sizeof (EFI_IMAGE_SECTION_HEADER); + SectionHeadersSize += sizeof (EFI_IMAGE_SECTION_HEADER); + } + + assert (SectionHeadersSize == Context->HdrInfo.ExtraSectionHeadersSize); + assert (SectionOffset == Context->UnsignedFileSize); + + return true; +} + +#define ToolImageEmitPeHeaders PE_SUFFIX (ToolImageEmitPeHeaders) +static +bool +ToolImageEmitPeHeaders ( + image_tool_pe_emit_context_t *Context, + uint8_t **Buffer, + uint32_t *BufferSize, + uint32_t AlignedHeaderSize + ) +{ + const image_tool_image_info_t *Image; + EFI_IMAGE_DOS_HEADER *DosHdr; + EFI_IMAGE_NT_HEADERS *PePlusHdr; + bool Result; + uint32_t HeaderPadding; + + assert (Context != NULL); + assert (Buffer != NULL); + assert (BufferSize != NULL); + + assert (sizeof (EFI_IMAGE_DOS_HEADER) <= *BufferSize); + + Image = Context->Image; + DosHdr = (void *) *Buffer; + + DosHdr->e_magic = EFI_IMAGE_DOS_SIGNATURE; + DosHdr->e_lfanew = sizeof (EFI_IMAGE_DOS_HEADER); + + *BufferSize -= sizeof (EFI_IMAGE_DOS_HEADER); + *Buffer += sizeof (EFI_IMAGE_DOS_HEADER); + + assert (sizeof (EFI_IMAGE_NT_HEADERS) <= *BufferSize); + + PePlusHdr = (EFI_IMAGE_NT_HEADERS *)(VOID *) *Buffer; + + PePlusHdr->CommonHeader.Signature = EFI_IMAGE_NT_SIGNATURE; + PePlusHdr->CommonHeader.FileHeader.Machine = Image->HeaderInfo.Machine; + PePlusHdr->CommonHeader.FileHeader.NumberOfSections = (UINT16)Image->SegmentInfo.NumSegments; + PePlusHdr->CommonHeader.FileHeader.SizeOfOptionalHeader = Context->HdrInfo.SizeOfOptionalHeader; + PePlusHdr->CommonHeader.FileHeader.Characteristics = + EFI_IMAGE_FILE_EXECUTABLE_IMAGE | EFI_IMAGE_FILE_LINE_NUMS_STRIPPED | + EFI_IMAGE_FILE_LOCAL_SYMS_STRIPPED | EFI_IMAGE_FILE_LARGE_ADDRESS_AWARE; + + if (Image->RelocInfo.RelocsStripped) { + PePlusHdr->CommonHeader.FileHeader.Characteristics |= EFI_IMAGE_FILE_RELOCS_STRIPPED; + } + + PePlusHdr->Magic = EFI_IMAGE_NT_OPTIONAL_HDR_MAGIC; + PePlusHdr->AddressOfEntryPoint = Image->HeaderInfo.EntryPointAddress; + PePlusHdr->SectionAlignment = Image->SegmentInfo.SegmentAlignment; + PePlusHdr->FileAlignment = Context->FileAlignment; + PePlusHdr->SizeOfHeaders = AlignedHeaderSize; + PePlusHdr->SizeOfImage = AlignedHeaderSize; + PePlusHdr->ImageBase = (UINTN)Image->HeaderInfo.BaseAddress; + PePlusHdr->Subsystem = Image->HeaderInfo.Subsystem; + PePlusHdr->NumberOfRvaAndSizes = Context->HdrInfo.NumberOfRvaAndSizes; + + STATIC_ASSERT( + OFFSET_OF(EFI_IMAGE_NT_HEADERS, DataDirectory) == sizeof (EFI_IMAGE_NT_HEADERS), + "The following code needs to be updated to consider padding." + ); + + Context->PeHdr = PePlusHdr; + + *BufferSize -= sizeof (EFI_IMAGE_NT_HEADERS) + PePlusHdr->NumberOfRvaAndSizes * sizeof (EFI_IMAGE_DATA_DIRECTORY); + *Buffer += sizeof (EFI_IMAGE_NT_HEADERS) + PePlusHdr->NumberOfRvaAndSizes * sizeof (EFI_IMAGE_DATA_DIRECTORY); + + Result = ToolImageEmitPeSectionHeaders (Context, Buffer, BufferSize, AlignedHeaderSize); + if (!Result) { + return false; + } + + Result = ToolImageEmitPeExtraSectionHeaders (Context, Buffer, BufferSize, AlignedHeaderSize); + if (!Result) { + return false; + } + + HeaderPadding = AlignedHeaderSize - Context->HdrInfo.SizeOfHeaders; + + assert (HeaderPadding <= *BufferSize); + + *BufferSize -= HeaderPadding; + *Buffer += HeaderPadding; + + return true; +} + +#define ToolImageEmitPeSections PE_SUFFIX (ToolImageEmitPeSections) +static +bool +ToolImageEmitPeSections ( + const image_tool_pe_emit_context_t *Context, + uint8_t **Buffer, + uint32_t *BufferSize + ) +{ + const image_tool_image_info_t *Image; + uint32_t SectionsSize; + uint8_t Index; + const image_tool_segment_t *Segment; + uint32_t SectionPadding; + bool FirstCode; + +#if PE_ARCH == 32 + bool FirstData; +#endif + + assert (Context != NULL); + assert (Buffer != NULL); + assert (BufferSize != NULL); + + assert (Context->SectionsSize <= *BufferSize); + + Image = Context->Image; + SectionsSize = 0; + FirstCode = true; + +#if PE_ARCH == 32 + FirstData = true; +#endif + + for (Index = 0; Index < Image->SegmentInfo.NumSegments; ++Index) { + Segment = &Image->SegmentInfo.Segments[Index]; + + Context->PeHdr->SizeOfImage += Segment->ImageSize; + + if (Segment->Execute) { + if (FirstCode) { + Context->PeHdr->BaseOfCode = Segment->ImageAddress; + FirstCode = false; + } + } +#if PE_ARCH == 32 + else { + if (FirstData) { + Context->PeHdr->BaseOfData = Segment->ImageAddress; + FirstData = false; + } + } +#endif + + assert (Segment->UnpaddedSize <= *BufferSize); + + memmove (*Buffer, Segment->Data, Segment->UnpaddedSize); + + *BufferSize -= Segment->UnpaddedSize; + *Buffer += Segment->UnpaddedSize; + SectionsSize += Segment->UnpaddedSize; + + SectionPadding = ALIGN_VALUE_ADDEND ( + Segment->UnpaddedSize, + Context->FileAlignment + ); + + assert (SectionPadding <= *BufferSize); + + *BufferSize -= SectionPadding; + *Buffer += SectionPadding; + SectionsSize += SectionPadding; + + if (Segment->Execute) { + Context->PeHdr->BaseOfCode = MIN(Context->PeHdr->BaseOfCode, Segment->ImageAddress); + Context->PeHdr->SizeOfCode += Segment->ImageSize; + } else { +#if PE_ARCH == 32 + Context->PeHdr->BaseOfData = MIN(Context->PeHdr->BaseOfData, Segment->ImageAddress); +#endif + Context->PeHdr->SizeOfInitializedData += Segment->ImageSize; + } + } + + assert (SectionsSize == Context->SectionsSize); + + return true; +} + +#define ToolImageEmitPeRelocTable PE_SUFFIX (ToolImageEmitPeRelocTable) +static +bool +ToolImageEmitPeRelocTable ( + const image_tool_pe_emit_context_t *Context, + uint8_t **Buffer, + uint32_t *BufferSize + ) +{ + const image_tool_image_info_t *Image; + uint32_t RelocTableSize; + EFI_IMAGE_BASE_RELOCATION_BLOCK *RelocBlock; + uint32_t BlockAddress; + uint32_t BlockNumRelocs; + uint32_t Index; + uint32_t RelocAddress; + uint32_t RelocTablePadding; + + assert (Context != NULL); + assert (Buffer != NULL); + assert (BufferSize != NULL); + + if (Context->RelocTableSize == 0) { + return true; + } + + Image = Context->Image; + + Context->PeHdr->SizeOfImage += ALIGN_VALUE (Context->RelocTableSize, Image->SegmentInfo.SegmentAlignment); + + assert (Image->RelocInfo.NumRelocs > 0); + assert (Image->RelocInfo.NumRelocs <= MAX_UINT32); + + assert (sizeof (EFI_IMAGE_BASE_RELOCATION_BLOCK) <= *BufferSize); + + RelocTableSize = 0; + RelocBlock = (void *) *Buffer; + BlockAddress = PAGE(Image->RelocInfo.Relocs[0].Target); + BlockNumRelocs = 0; + + RelocBlock->VirtualAddress = BlockAddress; + RelocBlock->SizeOfBlock = sizeof (*RelocBlock); + + for (Index = 0; Index < Image->RelocInfo.NumRelocs; ++Index) { + RelocAddress = PAGE(Image->RelocInfo.Relocs[Index].Target); + if (RelocAddress != BlockAddress) { + RelocBlock->SizeOfBlock = ALIGN_VALUE (RelocBlock->SizeOfBlock, 4); + + assert (RelocBlock->SizeOfBlock <= *BufferSize); + + *BufferSize -= RelocBlock->SizeOfBlock; + *Buffer += RelocBlock->SizeOfBlock; + RelocTableSize += RelocBlock->SizeOfBlock; + + RelocBlock = (void *) *Buffer; + + BlockAddress = RelocAddress; + BlockNumRelocs = 0; + + RelocBlock->VirtualAddress = BlockAddress; + RelocBlock->SizeOfBlock = sizeof (*RelocBlock); + } + + RelocBlock->SizeOfBlock += sizeof (*RelocBlock->Relocations); + + assert (RelocBlock->SizeOfBlock <= *BufferSize); + + RelocBlock->Relocations[BlockNumRelocs] = PAGE_OFF(Image->RelocInfo.Relocs[Index].Target); + RelocBlock->Relocations[BlockNumRelocs] |= ((uint16_t)Image->RelocInfo.Relocs[Index].Type) << 12U; + + ++BlockNumRelocs; + } + + RelocBlock->SizeOfBlock = ALIGN_VALUE (RelocBlock->SizeOfBlock, 4); + + assert (RelocBlock->SizeOfBlock <= *BufferSize); + + *BufferSize -= RelocBlock->SizeOfBlock; + *Buffer += RelocBlock->SizeOfBlock; + RelocTableSize += RelocBlock->SizeOfBlock; + + assert (RelocTableSize == Context->RelocTableSize); + + RelocTablePadding = ALIGN_VALUE_ADDEND ( + RelocTableSize, + Context->FileAlignment + ); + + assert (RelocTablePadding <= *BufferSize); + + *BufferSize -= RelocTablePadding; + *Buffer += RelocTablePadding; + + return true; +} + +typedef struct { + EFI_IMAGE_DEBUG_DIRECTORY_ENTRY CodeViewDirEntry; + EFI_IMAGE_DEBUG_CODEVIEW_RSDS_ENTRY CodeViewEntry; + uint8_t PdbPath[]; +} image_tool_debug_dir_t; + +STATIC_ASSERT( + OFFSET_OF(image_tool_debug_dir_t, PdbPath) == sizeof (image_tool_debug_dir_t), + "Flexible array aliases padding." + ); + +#define ToolImageEmitPeDebugTable PE_SUFFIX (ToolImageEmitPeDebugTable) +static +bool +ToolImageEmitPeDebugTable ( + const image_tool_pe_emit_context_t *Context, + uint8_t **Buffer, + uint32_t *BufferSize + ) +{ + const image_tool_image_info_t *Image; + uint32_t DebugTablePadding; + DebugData *Data; + + assert (Context != NULL); + assert (Buffer != NULL); + assert (BufferSize != NULL); + + Image = Context->Image; + + if (Context->DebugTableSize == 0) { + return true; + } + + Context->PeHdr->SizeOfImage += ALIGN_VALUE (Context->DebugTableSize, Image->SegmentInfo.SegmentAlignment); + + assert (Image->DebugInfo.SymbolsPathLen + 1 <= Context->DebugTableSize); + assert (Context->DebugTableSize <= *BufferSize); + + Data = (DebugData *) *Buffer; + + Data->Dir.Type = EFI_IMAGE_DEBUG_TYPE_CODEVIEW; + Data->Dir.SizeOfData = sizeof (EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY) + Image->DebugInfo.SymbolsPathLen + 1; + Data->Dir.RVA = (Context->UnsignedFileSize - ALIGN_VALUE (Context->DebugTableSize, Context->FileAlignment)) + sizeof (EFI_IMAGE_DEBUG_DIRECTORY_ENTRY); + Data->Dir.FileOffset = Data->Dir.RVA; + + Data->Nb10.Signature = CODEVIEW_SIGNATURE_NB10; + memmove (Data->Name, Image->DebugInfo.SymbolsPath, Image->DebugInfo.SymbolsPathLen + 1); + + assert (sizeof (*Data) + Image->DebugInfo.SymbolsPathLen + 1 == Context->DebugTableSize); + + *BufferSize -= Context->DebugTableSize; + *Buffer += Context->DebugTableSize; + + DebugTablePadding = ALIGN_VALUE_ADDEND( + Context->DebugTableSize, + Context->FileAlignment + ); + + assert (DebugTablePadding <= *BufferSize); + + *BufferSize -= DebugTablePadding; + *Buffer += DebugTablePadding; + + return true; +} + +#define ToolImageEmitPeHiiTable PE_SUFFIX (ToolImageEmitPeHiiTable) +static +bool +ToolImageEmitPeHiiTable ( + const image_tool_pe_emit_context_t *Context, + uint8_t **Buffer, + uint32_t *BufferSize + ) +{ + const image_tool_image_info_t *Image; + uint32_t HiiTablePadding; + + assert (Context != NULL); + assert (Buffer != NULL); + assert (BufferSize != NULL); + + Image = Context->Image; + + if (Image->HiiInfo.DataSize == 0) { + return true; + } + + Context->PeHdr->SizeOfImage += ALIGN_VALUE (mHiiResourceSectionHeaderSize + Image->HiiInfo.DataSize, Image->SegmentInfo.SegmentAlignment); + + assert (mHiiResourceSectionHeaderSize <= *BufferSize); + + InitializeHiiResouceSectionHeader ( + *Buffer, + Context->HiiSectionAddress, + Context->Image->HiiInfo.DataSize + ); + + *BufferSize -= mHiiResourceSectionHeaderSize; + *Buffer += mHiiResourceSectionHeaderSize; + + assert (Image->HiiInfo.DataSize <= *BufferSize); + + memmove (*Buffer, Image->HiiInfo.Data, Image->HiiInfo.DataSize); + + *BufferSize -= Image->HiiInfo.DataSize; + *Buffer += Image->HiiInfo.DataSize; + + HiiTablePadding = ALIGN_VALUE_ADDEND( + mHiiResourceSectionHeaderSize + Image->HiiInfo.DataSize, + Context->FileAlignment + ); + + assert (HiiTablePadding <= *BufferSize); + + *BufferSize -= HiiTablePadding; + *Buffer += HiiTablePadding; + + return true; +} + +#define ToolImageEmitPeExtraSections PE_SUFFIX (ToolImageEmitPeExtraSections) +static +bool +ToolImageEmitPeExtraSections ( + const image_tool_pe_emit_context_t *Context, + uint8_t **Buffer, + uint32_t *BufferSize + ) +{ + uint32_t OldBufferSize; + bool Result; + + assert (Context != NULL); + assert (Buffer != NULL); + assert (BufferSize != NULL); + + OldBufferSize = *BufferSize; + + Result = ToolImageEmitPeHiiTable (Context, Buffer, BufferSize); + if (!Result) { + return false; + } + + Result = ToolImageEmitPeRelocTable (Context, Buffer, BufferSize); + if (!Result) { + return false; + } + + Result = ToolImageEmitPeDebugTable (Context, Buffer, BufferSize); + if (!Result) { + return false; + } + + assert ((OldBufferSize - *BufferSize) == Context->ExtraSectionsSize); + + return true; +} + +#define ToolImageEmitPe PE_SUFFIX (ToolImageEmitPe) +void * +ToolImageEmitPe ( + image_tool_image_info_t *Image, + uint32_t *FileSize + ) +{ + image_tool_pe_emit_context_t Context; + bool Result; + uint32_t AlignedHeaderSize; + bool Overflow; + uint32_t SectionsOffset; + void *FileBuffer; + uint8_t *Buffer; + uint32_t RemainingSize; + uint32_t ExpectedSize; + + assert (Image != NULL); + assert (FileSize != NULL); + + memset (&Context, 0, sizeof (Context)); + + // FIXME: Non-XIP is not well-supported right now. + Context.FileAlignment = Image->SegmentInfo.SegmentAlignment; + Image->HeaderInfo.IsXip = true; + + ImageInitUnpaddedSize (Image); + + Context.Image = Image; + + Result = EmitPeGetHeaderSizes (Image, &Context.HdrInfo); + if (!Result) { + raise (); + return NULL; + } + + Overflow = BaseOverflowAlignUpU32 ( + Context.HdrInfo.SizeOfHeaders, + Context.FileAlignment, + &AlignedHeaderSize + ); + if (Overflow) { + raise (); + return NULL; + } + + if (AlignedHeaderSize > Image->SegmentInfo.Segments[0].ImageAddress) { + raise (); + return NULL; + } + + AlignedHeaderSize = (uint32_t)Image->SegmentInfo.Segments[0].ImageAddress; + + Result = EmitPeGetSectionsSize (&Context, &Context.SectionsSize); + if (!Result) { + raise (); + return NULL; + } + + Overflow = BaseOverflowAddU32 ( + AlignedHeaderSize, + Context.SectionsSize, + &SectionsOffset + ); + if (Overflow) { + raise (); + return NULL; + } + + Result = EmitPeGetExtraSectionsSize (&Context, &Context.ExtraSectionsSize); + if (!Result) { + raise (); + return NULL; + } + + Overflow = BaseOverflowAddU32 ( + SectionsOffset, + Context.ExtraSectionsSize, + &Context.UnsignedFileSize + ); + if (Overflow) { + raise (); + return NULL; + } + + FileBuffer = calloc (1, Context.UnsignedFileSize); + if (FileBuffer == NULL) { + raise (); + return NULL; + } + + Buffer = FileBuffer; + RemainingSize = Context.UnsignedFileSize; + ExpectedSize = Context.UnsignedFileSize; + + Result = ToolImageEmitPeHeaders (&Context, &Buffer, &RemainingSize, AlignedHeaderSize); + if (!Result) { + raise (); + free (FileBuffer); + return NULL; + } + + ExpectedSize -= AlignedHeaderSize; + + assert (RemainingSize == ExpectedSize); + + Result = ToolImageEmitPeSections (&Context, &Buffer, &RemainingSize); + if (!Result) { + raise (); + free (FileBuffer); + return NULL; + } + + ExpectedSize -= Context.SectionsSize; + + assert (RemainingSize == ExpectedSize); + + Result = ToolImageEmitPeExtraSections (&Context, &Buffer, &RemainingSize); + if (!Result) { + raise (); + free (FileBuffer); + return NULL; + } + + ExpectedSize -= Context.ExtraSectionsSize; + + assert (RemainingSize == ExpectedSize); + assert (RemainingSize == 0); + + Context.PeHdr->SizeOfInitializedData += Context.ExtraSectionsSize; + + *FileSize = Context.UnsignedFileSize; + + return FileBuffer; +} diff --git a/BaseTools/ImageTool/PeEmit32.c b/BaseTools/ImageTool/PeEmit32.c new file mode 100644 index 0000000000..65da7c8f93 --- /dev/null +++ b/BaseTools/ImageTool/PeEmit32.c @@ -0,0 +1,7 @@ +/** @file + Copyright (c) 2023, Marvin Häuser. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#define PE_ARCH 32 +#include "PeEmit.c" diff --git a/BaseTools/ImageTool/PeEmit64.c b/BaseTools/ImageTool/PeEmit64.c new file mode 100644 index 0000000000..83448fc8e5 --- /dev/null +++ b/BaseTools/ImageTool/PeEmit64.c @@ -0,0 +1,7 @@ +/** @file + Copyright (c) 2023, Marvin Häuser. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#define PE_ARCH 64 +#include "PeEmit.c" diff --git a/BaseTools/ImageTool/PeEmitCommon.c b/BaseTools/ImageTool/PeEmitCommon.c new file mode 100644 index 0000000000..c136721a19 --- /dev/null +++ b/BaseTools/ImageTool/PeEmitCommon.c @@ -0,0 +1,39 @@ +/** @file + Copyright (c) 2023, Marvin Häuser. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#include "PeEmitCommon.h" + +void * +ToolImageEmitPe ( + image_tool_image_info_t *Image, + uint32_t *FileSize, + bool Strip + ) +{ + if (Strip) { + ToolImageStripRelocs (Image); + } + + switch (Image->HeaderInfo.Machine) { + case IMAGE_FILE_MACHINE_I386: + case IMAGE_FILE_MACHINE_ARMTHUMB_MIXED: + { + return ToolImageEmitPe32 (Image, FileSize); + } + + case IMAGE_FILE_MACHINE_X64: + case IMAGE_FILE_MACHINE_ARM64: + { + return ToolImageEmitPe64 (Image, FileSize); + } + + default: + { + assert (false); + } + } + + return NULL; +} diff --git a/BaseTools/ImageTool/PeEmitCommon.h b/BaseTools/ImageTool/PeEmitCommon.h new file mode 100644 index 0000000000..a65761f06f --- /dev/null +++ b/BaseTools/ImageTool/PeEmitCommon.h @@ -0,0 +1,25 @@ +/** @file + Copyright (c) 2023, Marvin Häuser. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#ifndef PE_EMIT_COMMON_H +#define PE_EMIT_COMMON_H + +#include + +#include "ImageTool.h" + +void * +ToolImageEmitPe32 ( + const image_tool_image_info_t *Image, + uint32_t *FileSize + ); + +void * +ToolImageEmitPe64 ( + const image_tool_image_info_t *Image, + uint32_t *FileSize + ); + +#endif // PE_EMIT_COMMON_H diff --git a/BaseTools/ImageTool/PeScan.c b/BaseTools/ImageTool/PeScan.c new file mode 100644 index 0000000000..8c7585a2a1 --- /dev/null +++ b/BaseTools/ImageTool/PeScan.c @@ -0,0 +1,295 @@ +/** @file + Copyright (c) 2021, Marvin Häuser. All rights reserved. + Copyright (c) 2022, Mikhail Krichanov. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#include "ImageTool.h" + +#define PE_COFF_SECT_NAME_RELOC ".reloc\0" +#define PE_COFF_SECT_NAME_RESRC ".rsrc\0\0" +#define PE_COFF_SECT_NAME_DEBUG ".debug\0" + +bool +ScanPeGetRelocInfo ( + OUT image_tool_reloc_info_t *RelocInfo, + IN PE_COFF_LOADER_IMAGE_CONTEXT *Context + ) +{ + BOOLEAN Overflow; + UINT32 RelocBlockRvaMax; + UINT32 TopOfRelocDir; + UINT32 RelocBlockRva; + const EFI_IMAGE_BASE_RELOCATION_BLOCK *RelocBlock; + UINT32 RelocBlockSize; + UINT32 SizeOfRelocs; + UINT32 NumRelocs; + UINT32 RelocIndex; + uint32_t RelocDirSize; + const char *ImageBuffer; + UINT16 RelocType; + UINT16 RelocOffset; + + assert (RelocInfo != NULL); + assert (Context != NULL); + + // FIXME: PE/COFF context access + RelocBlockRva = Context->RelocDirRva; + RelocDirSize = Context->RelocDirSize; + // + // Verify the Relocation Directory is not empty. + // + if (RelocDirSize == 0) { + return true; + } + + RelocInfo->Relocs = calloc (RelocDirSize / sizeof (UINT16), sizeof (*RelocInfo->Relocs)); + if (RelocInfo->Relocs == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for Relocs[]\n"); + return false; + } + + TopOfRelocDir = RelocBlockRva + RelocDirSize; + + RelocBlockRvaMax = TopOfRelocDir - sizeof (EFI_IMAGE_BASE_RELOCATION_BLOCK); + // + // Align TopOfRelocDir because, if the policy does not demand Relocation Block + // sizes to be aligned, the code below will manually align them. Thus, the + // end offset of the last Relocation Block must be compared to a manually + // aligned Relocation Directoriy end offset. + // + Overflow = BaseOverflowAlignUpU32 ( + TopOfRelocDir, + ALIGNOF (EFI_IMAGE_BASE_RELOCATION_BLOCK), + &TopOfRelocDir + ); + if (Overflow) { + fprintf (stderr, "ImageTool: Overflow during TopOfRelocDir calculation\n"); + return false; + } + // + // Apply all Base Relocations of the Image. + // + ImageBuffer = (char *)PeCoffLoaderGetImageAddress (Context); + while (RelocBlockRva <= RelocBlockRvaMax) { + RelocBlock = (const EFI_IMAGE_BASE_RELOCATION_BLOCK *)(const void *)(ImageBuffer + RelocBlockRva); + // + // Verify the Base Relocation Block size is well-formed. + // + Overflow = BaseOverflowSubU32 ( + RelocBlock->SizeOfBlock, + sizeof (EFI_IMAGE_BASE_RELOCATION_BLOCK), + &SizeOfRelocs + ); + if (Overflow) { + fprintf (stderr, "ImageTool: Overflow during SizeOfRelocs calculation\n"); + return false; + } + // + // Verify the Base Relocation Block is in bounds of the Relocation + // Directory. + // + if (SizeOfRelocs > RelocBlockRvaMax - RelocBlockRva) { + fprintf (stderr, "ImageTool: Base Relocation Block is out of bounds of the Relocation Directory\n"); + return false; + } + // + // This arithmetic cannot overflow because we know + // 1) RelocBlock->SizeOfBlock <= RelocMax <= TopOfRelocDir + // 2) IS_ALIGNED (TopOfRelocDir, ALIGNOF (EFI_IMAGE_BASE_RELOCATION_BLOCK)). + // + RelocBlockSize = ALIGN_VALUE ( + RelocBlock->SizeOfBlock, + ALIGNOF (EFI_IMAGE_BASE_RELOCATION_BLOCK) + ); + // + // This division is safe due to the guarantee made above. + // + NumRelocs = SizeOfRelocs / sizeof (*RelocBlock->Relocations); + // + // Process all Base Relocations of the current Block. + // + for (RelocIndex = 0; RelocIndex < NumRelocs; ++RelocIndex) { + RelocType = IMAGE_RELOC_TYPE (RelocBlock->Relocations[RelocIndex]); + RelocOffset = IMAGE_RELOC_OFFSET (RelocBlock->Relocations[RelocIndex]); + + // FIXME: Make separate functions for UE + switch (RelocType) { + case EFI_IMAGE_REL_BASED_ABSOLUTE: + continue; + case EFI_IMAGE_REL_BASED_HIGHLOW: + case EFI_IMAGE_REL_BASED_DIR64: + RelocInfo->Relocs[RelocInfo->NumRelocs].Type = (uint8_t)RelocType; + break; + default: + fprintf (stderr, "ImageTool: Unknown RelocType = 0x%x\n", RelocType); + return false; + } + + RelocInfo->Relocs[RelocInfo->NumRelocs].Target = RelocBlock->VirtualAddress + RelocOffset; + ++RelocInfo->NumRelocs; + } + // + // This arithmetic cannot overflow because it has been checked that the + // Image Base Relocation Block is in bounds of the Image buffer. + // + RelocBlockRva += RelocBlockSize; + } + // + // Verify the Relocation Directory size matches the contained data. + // + if (RelocBlockRva != TopOfRelocDir) { + fprintf (stderr, "ImageTool: Relocation Directory size does not match the contained data\n"); + return false; + } + + return true; +} + +bool +ScanPeGetSegmentInfo ( + OUT image_tool_segment_info_t *SegmentInfo, + IN PE_COFF_LOADER_IMAGE_CONTEXT *Context + ) +{ + const EFI_IMAGE_SECTION_HEADER *Section; + uint32_t NumSections; + image_tool_segment_t *ImageSegment; + const char *ImageBuffer; + uint32_t Index; + + assert (SegmentInfo != NULL); + assert (Context != NULL); + + NumSections = PeCoffGetSectionTable (Context, &Section); + + SegmentInfo->Segments = calloc (NumSections, sizeof (*SegmentInfo->Segments)); + if (SegmentInfo->Segments == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for Segments[]\n"); + return false; + } + + ImageBuffer = (char *)PeCoffLoaderGetImageAddress (Context); + + ImageSegment = SegmentInfo->Segments; + for (Index = 0; Index < NumSections; ++Index, ++Section) { + STATIC_ASSERT ( + sizeof(PE_COFF_SECT_NAME_RELOC) == sizeof(Section->Name) && + sizeof(PE_COFF_SECT_NAME_RESRC) == sizeof(Section->Name) && + sizeof(PE_COFF_SECT_NAME_DEBUG) == sizeof(Section->Name), + "Section names exceed section name bounds." + ); + + if ((Section->Characteristics & EFI_IMAGE_SCN_MEM_DISCARDABLE) == 0 + && memcmp (Section->Name, PE_COFF_SECT_NAME_RELOC, sizeof (Section->Name)) != 0 + && memcmp (Section->Name, PE_COFF_SECT_NAME_RESRC, sizeof (Section->Name)) != 0 + && memcmp (Section->Name, PE_COFF_SECT_NAME_DEBUG, sizeof (Section->Name)) != 0) { + ImageSegment->Name = calloc (1, sizeof (Section->Name)); + if (ImageSegment->Name == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for Segment Name\n"); + return false; + } + + memmove (ImageSegment->Name, Section->Name, sizeof (Section->Name)); + + ImageSegment->ImageAddress = Section->VirtualAddress; + ImageSegment->ImageSize = ALIGN_VALUE (Section->VirtualSize, SegmentInfo->SegmentAlignment); + ImageSegment->Read = (Section->Characteristics & EFI_IMAGE_SCN_MEM_READ) != 0; + ImageSegment->Write = (Section->Characteristics & EFI_IMAGE_SCN_MEM_WRITE) != 0; + ImageSegment->Execute = (Section->Characteristics & EFI_IMAGE_SCN_MEM_EXECUTE) != 0; + + ImageSegment->Data = malloc (ImageSegment->ImageSize); + if (ImageSegment->Data == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for Segment Data\n"); + free (ImageSegment->Name); + return false; + } + + memmove ( + ImageSegment->Data, + ImageBuffer + Section->VirtualAddress, + ImageSegment->ImageSize + ); + + ++SegmentInfo->NumSegments; + ++ImageSegment; + } + } + + return true; +} + +bool +ScanPeGetDebugInfo ( + OUT image_tool_debug_info_t *DebugInfo, + IN PE_COFF_LOADER_IMAGE_CONTEXT *Context + ) +{ + const CHAR8 *PdbPath; + UINT32 PdbPathSize; + RETURN_STATUS Status; + + assert (DebugInfo != NULL); + assert (Context != NULL); + + Status = PeCoffGetPdbPath (Context, &PdbPath, &PdbPathSize); + if (Status == RETURN_NOT_FOUND) { + return true; + } + if (RETURN_ERROR (Status)) { + fprintf (stderr, "ImageTool: Could not get PdbPath\n"); + return false; + } + + DebugInfo->SymbolsPath = malloc (PdbPathSize); + if (DebugInfo->SymbolsPath == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for SymbolsPath\n"); + return false; + } + + memmove (DebugInfo->SymbolsPath, PdbPath, PdbPathSize); + + assert (PdbPathSize >= 1); + assert (DebugInfo->SymbolsPath[PdbPathSize - 1] == '\0'); + + DebugInfo->SymbolsPathLen = PdbPathSize - 1; + + return true; +} + +bool +ScanPeGetHiiInfo ( + OUT image_tool_hii_info_t *HiiInfo, + IN PE_COFF_LOADER_IMAGE_CONTEXT *Context + ) +{ + UINT32 HiiRva; + UINT32 HiiSize; + RETURN_STATUS Status; + const char *ImageBuffer; + + assert (HiiInfo != NULL); + assert (Context != NULL); + + Status = PeCoffGetHiiDataRva (Context, &HiiRva, &HiiSize); + if (Status == RETURN_NOT_FOUND) { + return true; + } + if (RETURN_ERROR (Status)) { + fprintf (stderr, "ImageTool: Could not get HiiRva\n"); + return false; + } + + HiiInfo->Data = calloc (1, HiiSize); + if (HiiInfo->Data == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for HiiInfo Data\n"); + return false; + } + + ImageBuffer = (char *)PeCoffLoaderGetImageAddress (Context); + + memmove (HiiInfo->Data, ImageBuffer + HiiRva, HiiSize); + HiiInfo->DataSize = HiiSize; + + return true; +} diff --git a/BaseTools/ImageTool/PeScan.h b/BaseTools/ImageTool/PeScan.h new file mode 100644 index 0000000000..bdcf2078f8 --- /dev/null +++ b/BaseTools/ImageTool/PeScan.h @@ -0,0 +1,23 @@ +/** @file + Copyright (c) 2023, Marvin Häuser. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#ifndef PE_SCAN_H +#define PE_SCAN_H + +#include "ImageTool.h" + +bool +ScanPeGetRelocInfo ( + OUT image_tool_reloc_info_t *RelocInfo, + IN PE_COFF_LOADER_IMAGE_CONTEXT *Context + ); + +bool +ScanPeGetSegmentInfo ( + OUT image_tool_segment_info_t *SegmentInfo, + IN PE_COFF_LOADER_IMAGE_CONTEXT *Context + ); + +#endif // PE_SCAN_H diff --git a/BaseTools/ImageTool/UefiImageScan.c b/BaseTools/ImageTool/UefiImageScan.c new file mode 100644 index 0000000000..c02a62b7e9 --- /dev/null +++ b/BaseTools/ImageTool/UefiImageScan.c @@ -0,0 +1,279 @@ +/** @file + Copyright (c) 2023, Marvin Häuser. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#include "ImageTool.h" + +#include + +#include + +#include "PeScan.h" + +static +bool +ScanUefiImageGetHeaderInfo ( + OUT image_tool_header_info_t *HeaderInfo, + IN UEFI_IMAGE_LOADER_IMAGE_CONTEXT *Context + ) +{ + RETURN_STATUS Status; + UINT64 Address; + + assert (HeaderInfo != NULL); + assert (Context != NULL); + + HeaderInfo->BaseAddress = UefiImageGetPreferredAddress (Context); + HeaderInfo->EntryPointAddress = UefiImageGetEntryPointAddress (Context); + HeaderInfo->Machine = UefiImageGetMachine (Context); + HeaderInfo->Subsystem = UefiImageGetSubsystem (Context); + // FIXME: + HeaderInfo->IsXip = true; + + Status = UefiImageGetFixedAddress (Context, &Address); + if (!RETURN_ERROR (Status)) { + if (Address != HeaderInfo->BaseAddress) { + fprintf ( + stderr, + "ImageTool: Images with a fixed address different from their base address are not supported.\n" + ); + return false; + } + + HeaderInfo->FixedAddress = true; + } else if (Status != RETURN_NOT_FOUND) { + return false; + } + + return true; +} + +static +bool +ScanUefiImageGetRelocInfo ( + OUT image_tool_reloc_info_t *RelocInfo, + IN UEFI_IMAGE_LOADER_IMAGE_CONTEXT *Context + ) +{ + UINT8 FormatIndex; + + assert (RelocInfo != NULL); + assert (Context != NULL); + + FormatIndex = UefiImageGetFormat (Context); + + RelocInfo->RelocsStripped = UefiImageGetRelocsStripped (Context); + + if (FormatIndex == UefiImageFormatPe) { + return ScanPeGetRelocInfo ( + RelocInfo, + (PE_COFF_LOADER_IMAGE_CONTEXT *)Context + ); + } + + fprintf ( + stderr, + "ImageTool: Unsupported UefiImage format %u\n", + FormatIndex + ); + return false; +} + +static +bool +ScanUefiImageGetSegmentInfo ( + OUT image_tool_segment_info_t *SegmentInfo, + IN UEFI_IMAGE_LOADER_IMAGE_CONTEXT *Context + ) +{ + UINT8 FormatIndex; + + assert (SegmentInfo != NULL); + assert (Context != NULL); + + FormatIndex = UefiImageGetFormat (Context); + + SegmentInfo->SegmentAlignment = UefiImageGetSegmentAlignment (Context); + + if (FormatIndex == UefiImageFormatPe) { + return ScanPeGetSegmentInfo ( + SegmentInfo, + (PE_COFF_LOADER_IMAGE_CONTEXT *)Context + ); + } + + fprintf ( + stderr, + "ImageTool: Unsupported UefiImage format %u\n", + FormatIndex + ); + return false; +} + +bool +ScanUefiImageGetDebugInfo ( + OUT image_tool_debug_info_t *DebugInfo, + IN UEFI_IMAGE_LOADER_IMAGE_CONTEXT *Context + ) +{ + RETURN_STATUS Status; + const CHAR8 *SymbolsPath; + UINT32 SymbolsPathSize; + + assert (DebugInfo != NULL); + assert (Context != NULL); + + Status = UefiImageGetSymbolsPath (Context, &SymbolsPath, &SymbolsPathSize); + if (Status == RETURN_NOT_FOUND) { + return true; + } + if (RETURN_ERROR (Status)) { + fprintf (stderr, "ImageTool: Could not get SymbolsPath\n"); + return false; + } + + assert (SymbolsPathSize >= 1); + + DebugInfo->SymbolsPath = malloc (SymbolsPathSize + 1); + if (DebugInfo->SymbolsPath == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for SymbolsPath\n"); + return false; + } + + memmove (DebugInfo->SymbolsPath, SymbolsPath, SymbolsPathSize); + assert (DebugInfo->SymbolsPath[SymbolsPathSize - 1] == '\0'); + + DebugInfo->SymbolsPathLen = SymbolsPathSize - 1; + + return true; +} + +bool +ScanUefiImageGetHiiInfo ( + OUT image_tool_hii_info_t *HiiInfo, + IN UEFI_IMAGE_LOADER_IMAGE_CONTEXT *Context + ) +{ + RETURN_STATUS Status; + UINT32 HiiRva; + UINT32 HiiSize; + const char *ImageBuffer; + + assert (HiiInfo != NULL); + assert (Context != NULL); + + Status = UefiImageGetHiiDataRva (Context, &HiiRva, &HiiSize); + if (Status == RETURN_NOT_FOUND) { + return true; + } + if (RETURN_ERROR (Status)) { + fprintf (stderr, "ImageTool: Malformed HII data\n"); + return false; + } + + HiiInfo->Data = malloc (HiiSize); + if (HiiInfo->Data == NULL) { + fprintf (stderr, "ImageTool: Could not allocate memory for HiiInfo Data\n"); + return false; + } + + ImageBuffer = (char *)UefiImageLoaderGetImageAddress (Context); + + memmove (HiiInfo->Data, ImageBuffer + HiiRva, HiiSize); + HiiInfo->DataSize = HiiSize; + + return true; +} + +RETURN_STATUS +ToolContextConstructUefiImage ( + OUT image_tool_image_info_t *Image, + OUT int8_t *Format, + IN const void *File, + IN size_t FileSize + ) +{ + RETURN_STATUS Status; + UEFI_IMAGE_LOADER_IMAGE_CONTEXT Context; + UINT32 ImageSize; + UINT32 ImageAlignment; + UINT32 DestinationPages; + UINT32 DestinationSize; + void *Destination; + bool Success; + + assert (Image != NULL); + assert (File != NULL || FileSize == 0); + + if (FileSize > MAX_UINT32) { + fprintf (stderr, "ImageTool: FileSize is too huge\n"); + return RETURN_UNSUPPORTED; + } + + Status = UefiImageInitializeContext (&Context, File, (UINT32)FileSize); + if (RETURN_ERROR (Status)) { + return Status; + } + + *Format = (int8_t)UefiImageGetFormat (&Context); + + ImageSize = UefiImageGetImageSize (&Context); + DestinationPages = EFI_SIZE_TO_PAGES (ImageSize); + DestinationSize = EFI_PAGES_TO_SIZE (DestinationPages); + ImageAlignment = UefiImageGetSegmentAlignment (&Context); + + Destination = AllocateAlignedCodePages (DestinationPages, ImageAlignment); + if (Destination == NULL) { + fprintf (stderr, "ImageTool: Could not allocate Destination buffer\n"); + return RETURN_OUT_OF_RESOURCES; + } + + Status = UefiImageLoadImage (&Context, Destination, DestinationSize); + if (RETURN_ERROR (Status)) { + fprintf (stderr, "ImageTool: Could not Load Image\n"); + FreeAlignedPages (Destination, DestinationPages); + return RETURN_VOLUME_CORRUPTED; + } + + memset (Image, 0, sizeof (*Image)); + + Success = ScanUefiImageGetHeaderInfo (&Image->HeaderInfo, &Context); + if (!Success) { + fprintf (stderr, "ImageTool: Could not retrieve header info\n"); + FreeAlignedPages (Destination, DestinationPages); + return RETURN_VOLUME_CORRUPTED; + } + + Success = ScanUefiImageGetSegmentInfo (&Image->SegmentInfo, &Context); + if (!Success) { + fprintf (stderr, "ImageTool: Could not retrieve segment info\n"); + FreeAlignedPages (Destination, DestinationPages); + return RETURN_VOLUME_CORRUPTED; + } + + Success = ScanUefiImageGetRelocInfo (&Image->RelocInfo, &Context); + if (!Success) { + fprintf (stderr, "ImageTool: Could not retrieve reloc info\n"); + FreeAlignedPages (Destination, DestinationPages); + return RETURN_VOLUME_CORRUPTED; + } + + Success = ScanUefiImageGetHiiInfo (&Image->HiiInfo, &Context); + if (!Success) { + fprintf (stderr, "ImageTool: Could not retrieve HII info\n"); + FreeAlignedPages (Destination, DestinationPages); + return RETURN_VOLUME_CORRUPTED; + } + + Success = ScanUefiImageGetDebugInfo (&Image->DebugInfo, &Context); + if (!Success) { + fprintf (stderr, "ImageTool: Could not retrieve debug info\n"); + FreeAlignedPages (Destination, DestinationPages); + return RETURN_VOLUME_CORRUPTED; + } + + FreeAlignedPages (Destination, DestinationPages); + + return RETURN_SUCCESS; +} diff --git a/BaseTools/Makefile b/BaseTools/Makefile index 10963009e9..28fa83e4dc 100644 --- a/BaseTools/Makefile +++ b/BaseTools/Makefile @@ -9,13 +9,13 @@ !ERROR "BASE_TOOLS_PATH is not set! Please run toolsetup.bat first!" !ENDIF -SUBDIRS = $(BASE_TOOLS_PATH)\Source\C $(BASE_TOOLS_PATH)\Source\Python +SUBDIRS = $(BASE_TOOLS_PATH)\Source\C $(BASE_TOOLS_PATH)\Source\Python $(BASE_TOOLS_PATH)\ImageTool $(BASE_TOOLS_PATH)\MicroTool all: c c : - @if defined PYTHON_COMMAND $(PYTHON_COMMAND) $(BASE_TOOLS_PATH)\Source\C\Makefiles\NmakeSubdirs.py all $(BASE_TOOLS_PATH)\Source\C - @if not defined PYTHON_COMMAND $(PYTHON_HOME)\python.exe $(BASE_TOOLS_PATH)\Source\C\Makefiles\NmakeSubdirs.py all $(BASE_TOOLS_PATH)\Source\C + @if defined PYTHON_COMMAND $(PYTHON_COMMAND) $(BASE_TOOLS_PATH)\Source\C\Makefiles\NmakeSubdirs.py all $(BASE_TOOLS_PATH)\Source\C $(BASE_TOOLS_PATH)\ImageTool $(BASE_TOOLS_PATH)\MicroTool + @if not defined PYTHON_COMMAND $(PYTHON_HOME)\python.exe $(BASE_TOOLS_PATH)\Source\C\Makefiles\NmakeSubdirs.py all $(BASE_TOOLS_PATH)\Source\C $(BASE_TOOLS_PATH)\ImageTool $(BASE_TOOLS_PATH)\MicroTool subdirs: $(SUBDIRS) @@ -31,4 +31,3 @@ clean: cleanall: @if defined PYTHON_COMMAND $(PYTHON_COMMAND) $(BASE_TOOLS_PATH)\Source\C\Makefiles\NmakeSubdirs.py cleanall $(SUBDIRS) @if not defined PYTHON_COMMAND $(PYTHON_HOME)\python.exe $(BASE_TOOLS_PATH)\Source\C\Makefiles\NmakeSubdirs.py cleanall $(SUBDIRS) - diff --git a/BaseTools/MicroTool/GNUmakefile b/BaseTools/MicroTool/GNUmakefile new file mode 100644 index 0000000000..cce15c2c39 --- /dev/null +++ b/BaseTools/MicroTool/GNUmakefile @@ -0,0 +1,15 @@ +## @file +# Copyright (c) 2022, Mikhail Krichanov. All rights reserved. +# SPDX-License-Identifier: BSD-3-Clause +## + +PROJECT = MicroTool +PRODUCT = $(PROJECT)$(INFIX)$(SUFFIX) +OBJS = $(PROJECT).o + +DEBUG = 1 +SANITIZE = 0 +OC_USER = ../../OpenCorePkg +UDK_PATH = ../.. + +include $(OC_USER)/User/Makefile diff --git a/BaseTools/MicroTool/Makefile b/BaseTools/MicroTool/Makefile new file mode 100644 index 0000000000..8df029aff8 --- /dev/null +++ b/BaseTools/MicroTool/Makefile @@ -0,0 +1,84 @@ +## @file +# Windows makefile for 'MicroTool' module build. +# +# Copyright (c) 2022, Mikhail Krichanov. All rights reserved. +# SPDX-License-Identifier: BSD-3-Clause +# +!INCLUDE ..\Source\C\Makefiles\ms.common + +APP = MicroTool + +OC_USER = ..\..\OpenCorePkg +UDK_PATH = ..\.. +UDK_ARCH = $(HOST_ARCH) +OUT_DIR = .\Windows + +OBJECTS = MicroTool.obj + +BASE = $(UDK_PATH)\MdePkg\Library\BaseLib +OUT = $(UDK_PATH)\MdePkg\Library\UefiDebugLibConOut +PRIN = $(UDK_PATH)\MdePkg\Library\BasePrintLib +ERRO = $(UDK_PATH)\MdePkg\Library\BaseDebugPrintErrorLevelLib +BMPN = $(UDK_PATH)\MdeModulePkg\Library\BaseMemoryProfileLibNull +CMEM = $(UDK_PATH)\MdeModulePkg\Library\CommonMemoryAllocationLib +USER = $(OC_USER)\User\Library +OBJECTS = $(OBJECTS) {$(BASE)}SafeString.obj String.obj SwapBytes16.obj SwapBytes32.obj CpuDeadLoop.obj CheckSum.obj +OBJECTS = $(OBJECTS) {$(OUT)}DebugLib.obj {$(PRIN)}PrintLib.obj PrintLibInternal.obj {$(ERRO)}BaseDebugPrintErrorLevelLib.obj +OBJECTS = $(OBJECTS) {$(USER)}UserFile.obj UserBaseMemoryLib.obj UserMath.obj UserPcd.obj UserMisc.obj UserGlobalVar.obj UserBootServices.obj +OBJECTS = $(OBJECTS) {$(BMPN)}BaseMemoryProfileLibNull.obj {$(CMEM)}CommonMemoryAllocationLib.obj {$(CMEM)}CommonMemoryAllocationLibEx.obj + +INC = -I . -I $(OC_USER)\User\Include -I $(OC_USER)\Include\Acidanthera +INC = $(INC) -I $(UDK_PATH)\MdePkg\Include -I $(UDK_PATH)\MdePkg\Include\Library -I $(UDK_PATH)\MdePkg\Include\$(UDK_ARCH) +INC = $(INC) -I $(UDK_PATH)\MdePkg\Library\BaseLib -I $(UDK_PATH)\MdeModulePkg\Include -I $(UDK_PATH)\UefiCpuPkg\Include +INC = $(INC) /FI $(OC_USER)\User\Include\UserPcd.h /FI $(UDK_PATH)\MdePkg\Include\Base.h /FI $(OC_USER)\User\Include\UserGlobalVar.h + +all: + -@if not exist $(OUT_DIR) mkdir $(OUT_DIR) + $(MAKE) $(APP) + +$(APP) : $(OBJECTS) + -@if not exist $(BIN_PATH) mkdir $(BIN_PATH) + @cd $(OUT_DIR) + $(LD) /nologo /debug /OPT:REF /OPT:ICF=10 /incremental:no /nodefaultlib:libc.lib /out:..\$@ $(LIBS) $** + @copy /y ..\$@ $(BIN_PATH)\$@.exe + +.PHONY:clean +.PHONY:cleanall + +clean: + del /f /q $(OUT_DIR) $(APP) *.pdb > nul + +cleanall: + del /f /q $(OUT_DIR) *.pdb $(BIN_PATH)\$(APP).exe $(BIN_PATH)\$(APP).exe > nul + +.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(BASE)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) /wd 4005 $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(BMPN)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(CMEM)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(OUT)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(PRIN)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) /wd 4005 $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(ERRO)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) $< -Fo$@ + @move $@ $(OUT_DIR)\ + +{$(USER)}.c.obj : + $(CC) -c $(CFLAGS) $(INC) /D WIN32 /wd 4754 $< -Fo$@ + @move $@ $(OUT_DIR)\ diff --git a/BaseTools/MicroTool/MicroTool.c b/BaseTools/MicroTool/MicroTool.c new file mode 100644 index 0000000000..d7431317bc --- /dev/null +++ b/BaseTools/MicroTool/MicroTool.c @@ -0,0 +1,298 @@ +/** @file + Copyright (c) 2022, Mikhail Krichanov. All rights reserved. + SPDX-License-Identifier: BSD-3-Clause +**/ + +#include +#include +#include +#include + +#include + +#define DEFAULT_MC_ALIGNMENT 16 +#define DEFAULT_MC_PAD_BYTE_VALUE 0xFF + +typedef struct { + UINT32 HeaderVersion; + UINT32 PatchId; + UINT32 Date; + UINT32 CpuId; + UINT32 Checksum; + UINT32 LoaderVersion; + UINT32 PlatformId; + UINT32 DataSize; // if 0, then TotalSize = 2048, and TotalSize field is invalid + UINT32 TotalSize; // number of bytes + UINT32 Reserved[3]; +} MICROCODE_HEADER; + +static +RETURN_STATUS +TxtToBin ( + IN const char *TxtName, + IN const char *BinName + ) +{ + char *Txt; + char *TxtStart; + uint32_t TxtSize; + UINT32 *Buffer; + UINT32 *BufferStart; + UINT32 FileLength; + UINT32 Index; + MICROCODE_HEADER *Micro; + UINT32 CheckSum; + + assert (TxtName != NULL); + assert (BinName != NULL); + + Txt = (char *)UserReadFile (TxtName, &TxtSize); + if (Txt == NULL) { + fprintf (stderr, "MicroTool: Could not open %s: %s\n", TxtName, strerror (errno)); + return RETURN_ABORTED; + } + + Buffer = calloc (1, TxtSize); + if (Buffer == NULL) { + fprintf (stderr, "MicroTool: Could not allocate memory for Buffer\n"); + free (Txt); + return RETURN_OUT_OF_RESOURCES; + } + + BufferStart = Buffer; + TxtStart = Txt; + FileLength = 0; + for (Index = 0; Index < TxtSize; ++Index, ++Txt) { + // + // Skip Blank Lines and Comment Lines + // + if (isspace ((int)*Txt)) { + continue; + } + + if (*Txt == ';') { + while ((Index < TxtSize) && (*Txt != '\n')) { + ++Index; + ++Txt; + } + + if (Index == TxtSize) { + break; + } + + ++Index; + ++Txt; + } + // + // Look for + // dd 000000001h ; comment + // dd XXXXXXXX + // DD XXXXXXXXX + // DD XXXXXXXXX + // + if (((Index + 2) < TxtSize) && (tolower ((int)Txt[0]) == 'd') && (tolower ((int)Txt[1]) == 'd') && isspace ((int)Txt[2])) { + // + // Skip blanks and look for a hex digit + // + Txt += 3; + Index += 3; + while ((Index < TxtSize) && isspace ((int)*Txt)) { + ++Index; + ++Txt; + } + + if (Index == TxtSize) { + break; + } + + if (isxdigit ((int)*Txt)) { + if (sscanf (Txt, "%X", Buffer) != 1) { + fprintf (stderr, "MicroTool: Could not write into Buffer\n"); + free (TxtStart); + free (BufferStart); + return RETURN_ABORTED; + } + + while ((Index < TxtSize) && (*Txt != '\n')) { + ++Index; + ++Txt; + } + } + + ++Buffer; + FileLength += sizeof (*Buffer); + continue; + } + + fprintf (stderr, "MicroTool: Corrupted input file\n"); + break; + } + + free (TxtStart); + + if (FileLength == 0) { + fprintf (stderr, "MicroTool: No parseable data found in file %s\n", TxtName); + free (BufferStart); + return RETURN_INVALID_PARAMETER; + } + + if (FileLength < sizeof (MICROCODE_HEADER)) { + fprintf (stderr, "MicroTool: Amount of parsable data in %s is insufficient to contain a microcode header\n", TxtName); + free (BufferStart); + return RETURN_VOLUME_CORRUPTED; + } + + // + // Can't do much checking on the header because, per the spec, the + // DataSize field may be 0, which means DataSize = 2000 and TotalSize = 2K, + // and the TotalSize field is invalid (actually missing). Thus we can't + // even verify the Reserved fields are 0. + // + Micro = (MICROCODE_HEADER *)BufferStart; + if (Micro->DataSize == 0) { + Index = 2048; + } else { + Index = Micro->TotalSize; + } + + if (Index != FileLength) { + fprintf (stderr, "MicroTool: File length of %s (0x%x) does not equal expected TotalSize: 0x%04X\n", TxtName, FileLength, Index); + free (BufferStart); + return RETURN_VOLUME_CORRUPTED; + } + + // + // Checksum the contents + // + Buffer = BufferStart; + CheckSum = 0; + Index = 0; + while (Index < FileLength) { + CheckSum += *Buffer; + + ++Buffer; + Index += sizeof (*Buffer); + } + + if (CheckSum != 0) { + fprintf (stderr, "MicroTool: Checksum (0x%x) failed on file %s\n", CheckSum, TxtName); + free (BufferStart); + return RETURN_VOLUME_CORRUPTED; + } + + UserWriteFile (BinName, BufferStart, FileLength); + + free (BufferStart); + + return RETURN_SUCCESS; +} + +static +RETURN_STATUS +Merge ( + IN const char *Output, + IN const char *FileNames[], + IN UINT32 NumOfFiles + ) +{ + void *File; + uint32_t FileSize; + UINT32 Index; + UINT32 Total; + char *Buffer; + char *BufferStart; + UINT32 Addend; + + assert (Output != NULL); + assert (FileNames != NULL); + + Total = 0; + + for (Index = 0; Index < NumOfFiles; ++Index) { + File = UserReadFile (FileNames[Index], &FileSize); + if (File == NULL) { + fprintf (stderr, "MicroTool: Could not open %s: %s\n", FileNames[Index], strerror (errno)); + return RETURN_ABORTED; + } + + Total += ALIGN_VALUE (FileSize, DEFAULT_MC_ALIGNMENT); + + free (File); + } + + Buffer = calloc (1, Total); + if (Buffer == NULL) { + fprintf (stderr, "MicroTool: Could not allocate memory for Buffer\n"); + return RETURN_OUT_OF_RESOURCES; + } + + BufferStart = Buffer; + + for (Index = 0; Index < NumOfFiles; ++Index) { + File = UserReadFile (FileNames[Index], &FileSize); + if (File == NULL) { + fprintf (stderr, "MicroTool: Could not reopen %s: %s\n", FileNames[Index], strerror (errno)); + free (BufferStart); + return RETURN_ABORTED; + } + + memcpy (Buffer, File, FileSize); + Buffer += FileSize; + + Addend = ALIGN_VALUE_ADDEND (FileSize, DEFAULT_MC_ALIGNMENT); + memset (Buffer, DEFAULT_MC_PAD_BYTE_VALUE, Addend); + Buffer += Addend; + + free (File); + } + + UserWriteFile (Output, BufferStart, Total); + + free (BufferStart); + + return RETURN_SUCCESS; +} + +int main (int argc, const char *argv[]) +{ + RETURN_STATUS Status; + UINT32 NumOfFiles; + + if (argc < 2) { + fprintf (stderr, "MicroTool: No command is specified\n"); + assert (false); + return -1; + } + + if (strcmp (argv[1], "TxtToBin") == 0) { + if (argc < 4) { + fprintf (stderr, "MicroTool: Command arguments are missing\n"); + fprintf (stderr, " Usage: MicroTool TxtToBin InputFile OutputFile\n"); + assert (false); + return -1; + } + + Status = TxtToBin (argv[2], argv [3]); + if (RETURN_ERROR (Status)) { + assert (false); + return -1; + } + } else if (strcmp (argv[1], "Merge") == 0) { + if (argc < 4) { + fprintf (stderr, "MicroTool: Command arguments are missing\n"); + fprintf (stderr, " Usage: MicroTool Merge OutputFile InputFile1 InputFile2 ...\n"); + assert (false); + return -1; + } + + NumOfFiles = (UINT32)argc - 3U; + + Status = Merge (argv[2], &argv[3], NumOfFiles); + if (RETURN_ERROR (Status)) { + assert (false); + return -1; + } + } + + return 0; +} diff --git a/BaseTools/Scripts/Base.lds b/BaseTools/Scripts/Base.lds new file mode 100644 index 0000000000..8823db55c2 --- /dev/null +++ b/BaseTools/Scripts/Base.lds @@ -0,0 +1,67 @@ +/** @file + + Unified linker script for GCC, CLANG based builds + + Copyright (c) 2023, Mikhail Krichanov. All rights reserved.
+ Copyright (c) 2010 - 2021, Intel Corporation. All rights reserved.
+ Copyright (c) 2015, Linaro Ltd. All rights reserved.
+ (C) Copyright 2016 Hewlett Packard Enterprise Development LP
+ + SPDX-License-Identifier: BSD-2-Clause-Patent + +**/ + +SECTIONS { + + . = ALIGNED_PE_HEADER_SIZE; + + .text : ALIGN(CONSTANT(MAXPAGESIZE)) { + *(.text .text.* .stub .gnu.linkonce.t.*) + } + + .rodata : ALIGN(CONSTANT(MAXPAGESIZE)) { + *(.rodata .rodata.* .data.rel.ro .data.rel.ro.* .gnu.linkonce.r.*) + *(.got .got.*) + + /* + * The contents of AutoGen.c files are mostly constant from the POV of the + * program, but most of it ends up in .data or .bss by default since few of + * the variable definitions that get emitted are declared as CONST. + * Unfortunately, we cannot pull it into the .text section entirely, since + * patchable PCDs are also emitted here, but we can at least move all of the + * emitted GUIDs here. + */ + *:AutoGen.obj(.data.g*Guid) + } + + .data : ALIGN(CONSTANT(MAXPAGESIZE)) { + *(.data .data.* .gnu.linkonce.d.*) + *(.bss .bss.*) + } + + .hii : ALIGN(CONSTANT(MAXPAGESIZE)) { + KEEP (*(.hii)) + } + + .eh_frame : ALIGN(CONSTANT(MAXPAGESIZE)) { + KEEP (*(.eh_frame)) + } + + .rela (INFO) : { + *(.rela .rela.*) + } + + .build-id (INFO) : { *(.note.gnu.build-id) } + + /DISCARD/ : { + *(.note.GNU-stack) + *(.interp) + *(.dynsym) + *(.dynstr) + *(.hash .gnu.hash) + *(.comment) + *(COMMON) + *(.dynamic) + *(.ARM.exidx .ARM.exidx.*) + } +} diff --git a/BaseTools/Scripts/ClangBase.lds b/BaseTools/Scripts/ClangBase.lds deleted file mode 100644 index c7dcd2024a..0000000000 --- a/BaseTools/Scripts/ClangBase.lds +++ /dev/null @@ -1,88 +0,0 @@ -/** @file - - Unified linker script for CLANG based builds - - Copyright (c) 2010 - 2021, Intel Corporation. All rights reserved.
- Copyright (c) 2015, Linaro Ltd. All rights reserved.
- (C) Copyright 2016 Hewlett Packard Enterprise Development LP
- - SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -SECTIONS { - - /* - * The PE/COFF binary consists of DOS and PE/COFF headers, and a sequence of - * section headers adding up to PECOFF_HEADER_SIZE bytes (which differs - * between 32-bit and 64-bit builds). The actual start of the .text section - * will be rounded up based on its actual alignment. - */ - . = PECOFF_HEADER_SIZE; - - .text : ALIGN(CONSTANT(MAXPAGESIZE)) { - *(.text .text.* .stub .gnu.linkonce.t.*) - *(.rodata .rodata.* .gnu.linkonce.r.*) - *(.got .got.*) - - /* - * The contents of AutoGen.c files are mostly constant from the POV of the - * program, but most of it ends up in .data or .bss by default since few of - * the variable definitions that get emitted are declared as CONST. - * Unfortunately, we cannot pull it into the .text section entirely, since - * patchable PCDs are also emitted here, but we can at least move all of the - * emitted GUIDs here. - */ - *:AutoGen.obj(.data.g*Guid) - } - - /* - * The alignment of the .data section should be less than or equal to the - * alignment of the .text section. This ensures that the relative offset - * between these sections is the same in the ELF and the PE/COFF versions of - * this binary. - */ - .data ALIGN(ALIGNOF(.text)) : ALIGN(CONSTANT(MAXPAGESIZE)) { - *(.data .data.* .gnu.linkonce.d.*) - *(.bss .bss.*) - } - - .eh_frame ALIGN(CONSTANT(MAXPAGESIZE)) : { - KEEP (*(.eh_frame)) - } - - .rela (INFO) : { - *(.rela .rela.*) - } - - .hii : ALIGN(CONSTANT(MAXPAGESIZE)) { - KEEP (*(.hii)) - } - - .got : { - *(.got) - } - ASSERT(SIZEOF(.got) == 0, "Unexpected GOT entries detected!") - - .got.plt (INFO) : { - *(.got.plt) - } - ASSERT(SIZEOF(.got.plt) == 0 || SIZEOF(.got.plt) == 0xc || SIZEOF(.got.plt) == 0x18, "Unexpected GOT/PLT entries detected!") - - /* - * Retain the GNU build id but in a non-allocatable section so GenFw - * does not copy it into the PE/COFF image. - */ - .build-id (INFO) : { *(.note.gnu.build-id) } - - /DISCARD/ : { - *(.note.GNU-stack) - *(.gnu_debuglink) - *(.interp) - *(.dynsym) - *(.dynstr) - *(.hash .gnu.hash) - *(.comment) - *(COMMON) - } -} diff --git a/BaseTools/Scripts/GccBase.lds b/BaseTools/Scripts/GccBase.lds deleted file mode 100644 index 9f27e83bb0..0000000000 --- a/BaseTools/Scripts/GccBase.lds +++ /dev/null @@ -1,88 +0,0 @@ -/** @file - - Unified linker script for GCC based builds - - Copyright (c) 2010 - 2015, Intel Corporation. All rights reserved.
- Copyright (c) 2015, Linaro Ltd. All rights reserved.
- (C) Copyright 2016 Hewlett Packard Enterprise Development LP
- - SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -SECTIONS { - - /* - * The PE/COFF binary consists of DOS and PE/COFF headers, and a sequence of - * section headers adding up to PECOFF_HEADER_SIZE bytes (which differs - * between 32-bit and 64-bit builds). The actual start of the .text section - * will be rounded up based on its actual alignment. - */ - . = PECOFF_HEADER_SIZE; - - .text : ALIGN(CONSTANT(COMMONPAGESIZE)) { - *(.text .text.* .stub .gnu.linkonce.t.*) - *(.rodata .rodata.* .gnu.linkonce.r.*) - *(.got .got.*) - - /* - * The contents of AutoGen.c files are mostly constant from the POV of the - * program, but most of it ends up in .data or .bss by default since few of - * the variable definitions that get emitted are declared as CONST. - * Unfortunately, we cannot pull it into the .text section entirely, since - * patchable PCDs are also emitted here, but we can at least move all of the - * emitted GUIDs here. - */ - *:AutoGen.obj(.data.g*Guid) - } - - /* - * The alignment of the .data section should be less than or equal to the - * alignment of the .text section. This ensures that the relative offset - * between these sections is the same in the ELF and the PE/COFF versions of - * this binary. - */ - .data ALIGN(ALIGNOF(.text)) : ALIGN(CONSTANT(COMMONPAGESIZE)) { - *(.data .data.* .gnu.linkonce.d.*) - *(.bss .bss.*) - } - - .eh_frame ALIGN(CONSTANT(COMMONPAGESIZE)) : { - KEEP (*(.eh_frame)) - } - - .rela (INFO) : { - *(.rela .rela.*) - } - - .hii : ALIGN(CONSTANT(COMMONPAGESIZE)) { - KEEP (*(.hii)) - } - - .got : { - *(.got) - } - ASSERT(SIZEOF(.got) == 0, "Unexpected GOT entries detected!") - - .got.plt (INFO) : { - *(.got.plt) - } - ASSERT(SIZEOF(.got.plt) == 0 || SIZEOF(.got.plt) == 0xc || SIZEOF(.got.plt) == 0x18, "Unexpected GOT/PLT entries detected!") - - /* - * Retain the GNU build id but in a non-allocatable section so GenFw - * does not copy it into the PE/COFF image. - */ - .build-id (INFO) : { *(.note.gnu.build-id) } - - /DISCARD/ : { - *(.note.GNU-stack) - *(.gnu_debuglink) - *(.interp) - *(.dynsym) - *(.dynstr) - *(.dynamic) - *(.hash .gnu.hash) - *(.comment) - } -} diff --git a/BaseTools/Scripts/Merge.lds b/BaseTools/Scripts/Merge.lds new file mode 100644 index 0000000000..d9514283a9 --- /dev/null +++ b/BaseTools/Scripts/Merge.lds @@ -0,0 +1,64 @@ +/** @file + + Unified linker script for GCC, CLANG based builds + + Copyright (c) 2023, Mikhail Krichanov. All rights reserved.
+ Copyright (c) 2010 - 2021, Intel Corporation. All rights reserved.
+ Copyright (c) 2015, Linaro Ltd. All rights reserved.
+ (C) Copyright 2016 Hewlett Packard Enterprise Development LP
+ + SPDX-License-Identifier: BSD-2-Clause-Patent + +**/ + +SECTIONS { + + . = ALIGNED_PE_HEADER_SIZE; + + .text : ALIGN(CONSTANT(MAXPAGESIZE)) { + *(.text .text.* .stub .gnu.linkonce.t.*) + *(.rodata .rodata.* .data.rel.ro .data.rel.ro.* .gnu.linkonce.r.*) + *(.got .got.*) + + /* + * The contents of AutoGen.c files are mostly constant from the POV of the + * program, but most of it ends up in .data or .bss by default since few of + * the variable definitions that get emitted are declared as CONST. + * Unfortunately, we cannot pull it into the .text section entirely, since + * patchable PCDs are also emitted here, but we can at least move all of the + * emitted GUIDs here. + */ + *:AutoGen.obj(.data.g*Guid) + } + + .data : ALIGN(CONSTANT(MAXPAGESIZE)) { + *(.data .data.* .gnu.linkonce.d.*) + *(.bss .bss.*) + } + + .hii : ALIGN(CONSTANT(MAXPAGESIZE)) { + KEEP (*(.hii)) + } + + .eh_frame : ALIGN(CONSTANT(MAXPAGESIZE)) { + KEEP (*(.eh_frame)) + } + + .rela (INFO) : { + *(.rela .rela.*) + } + + .build-id (INFO) : { *(.note.gnu.build-id) } + + /DISCARD/ : { + *(.note.GNU-stack) + *(.interp) + *(.dynsym) + *(.dynstr) + *(.hash .gnu.hash) + *(.comment) + *(COMMON) + *(.dynamic) + *(.ARM.exidx .ARM.exidx.*) + } +} diff --git a/BaseTools/Source/C/GNUmakefile b/BaseTools/Source/C/GNUmakefile index 5275f657ef..362fdf202f 100644 --- a/BaseTools/Source/C/GNUmakefile +++ b/BaseTools/Source/C/GNUmakefile @@ -56,7 +56,6 @@ APPLICATIONS = \ EfiRom \ GenFfs \ GenFv \ - GenFw \ GenSec \ GenCrc32 \ LzmaCompress \ diff --git a/BaseTools/Source/C/GenFv/GenFvInternalLib.c b/BaseTools/Source/C/GenFv/GenFvInternalLib.c index ce0345705d..66398cb697 100644 --- a/BaseTools/Source/C/GenFv/GenFvInternalLib.c +++ b/BaseTools/Source/C/GenFv/GenFvInternalLib.c @@ -3463,7 +3463,7 @@ Returns: return EFI_SUCCESS; } -EFI_PHYSICAL_ADDRESS +EFI_STATUS AddPadSection ( IN OUT EFI_PHYSICAL_ADDRESS *BaseAddress, IN UINT32 Alignment, @@ -3476,14 +3476,14 @@ AddPadSection ( UINT32 FfsHeaderLength; UINT32 FfsFileLength; UINT32 PadSize; - UINTN PadAddress; + EFI_PHYSICAL_ADDRESS PadAddress; UINT8 *FfsPart; UINT32 PartSize; UINT32 Offset; EFI_FFS_INTEGRITY_CHECK *IntegrityCheck; PadAddress = ALIGN_VALUE (*BaseAddress + sizeof (EFI_COMMON_SECTION_HEADER), Alignment); - PadSize = PadAddress - *BaseAddress; + PadSize = (UINT32)(PadAddress - *BaseAddress); Offset = (UINT32)((UINTN)((*Section).Pe32Section) - (UINTN)(*FfsFile)); PartSize = GetFfsFileLength (*FfsFile) - Offset; @@ -3513,7 +3513,7 @@ AddPadSection ( ++NewSection; ZeroMem ((VOID *)NewSection, PadSize - sizeof (EFI_COMMON_SECTION_HEADER)); - *Section = (EFI_FILE_SECTION_POINTER)(EFI_PE32_SECTION *)((UINT8 *)NewSection + PadSize - sizeof (EFI_COMMON_SECTION_HEADER)); + (*Section).Pe32Section = (EFI_PE32_SECTION *)((UINT8 *)NewSection + PadSize - sizeof (EFI_COMMON_SECTION_HEADER)); CopyMem ( (UINT8 *)((*Section).Pe32Section), @@ -3947,7 +3947,7 @@ Returns: PdbPointer = FileName; } - WriteMapFile (FvMapFile, PdbPointer, *FfsFile, NewPe32BaseAddress, &OrigImageContext); + WriteMapFile (FvMapFile, PdbPointer, *FfsFile, NewPe32BaseAddress, &ImageContext); } if ((*FfsFile)->Type != EFI_FV_FILETYPE_SECURITY_CORE && diff --git a/BaseTools/Source/C/GenFw/Elf32Convert.c b/BaseTools/Source/C/GenFw/Elf32Convert.c deleted file mode 100644 index de198e58db..0000000000 --- a/BaseTools/Source/C/GenFw/Elf32Convert.c +++ /dev/null @@ -1,1170 +0,0 @@ -/** @file -Elf32 Convert solution - -Copyright (c) 2010 - 2021, Intel Corporation. All rights reserved.
-Portions copyright (c) 2013, ARM Ltd. All rights reserved.
-Portions Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights reserved.
- -SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -#ifndef __GNUC__ -#include -#include -#endif -#include -#include -#include -#include -#include -#include - -#include -#include - -#include "PeCoffLib.h" -#include "EfiUtilityMsgs.h" - -#include "GenFw.h" -#include "ElfConvert.h" -#include "Elf32Convert.h" - -STATIC -VOID -ScanSections32 ( - VOID - ); - -STATIC -BOOLEAN -WriteSections32 ( - SECTION_FILTER_TYPES FilterType - ); - -STATIC -VOID -WriteRelocations32 ( - VOID - ); - -STATIC -VOID -WriteDebug32 ( - VOID - ); - -STATIC -VOID -SetImageSize32 ( - VOID - ); - -STATIC -VOID -CleanUp32 ( - VOID - ); - -// -// Rename ELF32 structures to common names to help when porting to ELF64. -// -typedef Elf32_Shdr Elf_Shdr; -typedef Elf32_Ehdr Elf_Ehdr; -typedef Elf32_Rel Elf_Rel; -typedef Elf32_Sym Elf_Sym; -typedef Elf32_Phdr Elf_Phdr; -typedef Elf32_Dyn Elf_Dyn; -#define ELFCLASS ELFCLASS32 -#define ELF_R_TYPE(r) ELF32_R_TYPE(r) -#define ELF_R_SYM(r) ELF32_R_SYM(r) - -// -// Well known ELF structures. -// -STATIC Elf_Ehdr *mEhdr; -STATIC Elf_Shdr *mShdrBase; -STATIC Elf_Phdr *mPhdrBase; - -// -// Coff information -// -STATIC UINT32 mCoffAlignment = 0x20; - -// -// PE section alignment. -// -STATIC const UINT16 mCoffNbrSections = 4; - -// -// ELF sections to offset in Coff file. -// -STATIC UINT32 *mCoffSectionsOffset = NULL; - -// -// Offsets in COFF file -// -STATIC UINT32 mNtHdrOffset; -STATIC UINT32 mTextOffset; -STATIC UINT32 mDataOffset; -STATIC UINT32 mHiiRsrcOffset; -STATIC UINT32 mRelocOffset; -STATIC UINT32 mDebugOffset; - -// -// Initialization Function -// -BOOLEAN -InitializeElf32 ( - UINT8 *FileBuffer, - ELF_FUNCTION_TABLE *ElfFunctions - ) -{ - // - // Initialize data pointer and structures. - // - mEhdr = (Elf_Ehdr*) FileBuffer; - - // - // Check the ELF32 specific header information. - // - if (mEhdr->e_ident[EI_CLASS] != ELFCLASS32) { - Error (NULL, 0, 3000, "Unsupported", "ELF EI_DATA not ELFCLASS32"); - return FALSE; - } - if (mEhdr->e_ident[EI_DATA] != ELFDATA2LSB) { - Error (NULL, 0, 3000, "Unsupported", "ELF EI_DATA not ELFDATA2LSB"); - return FALSE; - } - if ((mEhdr->e_type != ET_EXEC) && (mEhdr->e_type != ET_DYN)) { - Error (NULL, 0, 3000, "Unsupported", "ELF e_type not ET_EXEC or ET_DYN"); - return FALSE; - } - if (!((mEhdr->e_machine == EM_386) || (mEhdr->e_machine == EM_ARM) || (mEhdr->e_machine == EM_RISCV))) { - Warning (NULL, 0, 3000, "Unsupported", "ELF e_machine is not Elf32 machine."); - } - if (mEhdr->e_version != EV_CURRENT) { - Error (NULL, 0, 3000, "Unsupported", "ELF e_version (%u) not EV_CURRENT (%d)", (unsigned) mEhdr->e_version, EV_CURRENT); - return FALSE; - } - - // - // Update section header pointers - // - mShdrBase = (Elf_Shdr *)((UINT8 *)mEhdr + mEhdr->e_shoff); - mPhdrBase = (Elf_Phdr *)((UINT8 *)mEhdr + mEhdr->e_phoff); - - // - // Create COFF Section offset buffer and zero. - // - mCoffSectionsOffset = (UINT32 *)malloc(mEhdr->e_shnum * sizeof (UINT32)); - if (mCoffSectionsOffset == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - return FALSE; - } - memset(mCoffSectionsOffset, 0, mEhdr->e_shnum * sizeof(UINT32)); - - // - // Fill in function pointers. - // - ElfFunctions->ScanSections = ScanSections32; - ElfFunctions->WriteSections = WriteSections32; - ElfFunctions->WriteRelocations = WriteRelocations32; - ElfFunctions->WriteDebug = WriteDebug32; - ElfFunctions->SetImageSize = SetImageSize32; - ElfFunctions->CleanUp = CleanUp32; - - return TRUE; -} - - -// -// Header by Index functions -// -STATIC -Elf_Shdr* -GetShdrByIndex ( - UINT32 Num - ) -{ - if (Num >= mEhdr->e_shnum) { - Error (NULL, 0, 3000, "Invalid", "GetShdrByIndex: Index %u is too high.", Num); - exit(EXIT_FAILURE); - } - - return (Elf_Shdr*)((UINT8*)mShdrBase + Num * mEhdr->e_shentsize); -} - -STATIC -Elf_Phdr* -GetPhdrByIndex ( - UINT32 num - ) -{ - if (num >= mEhdr->e_phnum) { - Error (NULL, 0, 3000, "Invalid", "GetPhdrByIndex: Index %u is too high.", num); - exit(EXIT_FAILURE); - } - - return (Elf_Phdr *)((UINT8*)mPhdrBase + num * mEhdr->e_phentsize); -} - -STATIC -UINT32 -CoffAlign ( - UINT32 Offset - ) -{ - return (Offset + mCoffAlignment - 1) & ~(mCoffAlignment - 1); -} - -STATIC -UINT32 -DebugRvaAlign ( - UINT32 Offset - ) -{ - return (Offset + 3) & ~3; -} - -// -// filter functions -// -STATIC -BOOLEAN -IsTextShdr ( - Elf_Shdr *Shdr - ) -{ - return (BOOLEAN) (((Shdr->sh_flags & (SHF_EXECINSTR | SHF_ALLOC)) == (SHF_EXECINSTR | SHF_ALLOC)) || - ((Shdr->sh_flags & (SHF_WRITE | SHF_ALLOC)) == SHF_ALLOC)); -} - -STATIC -BOOLEAN -IsHiiRsrcShdr ( - Elf_Shdr *Shdr - ) -{ - Elf_Shdr *Namedr = GetShdrByIndex(mEhdr->e_shstrndx); - - return (BOOLEAN) (strcmp((CHAR8*)mEhdr + Namedr->sh_offset + Shdr->sh_name, ELF_HII_SECTION_NAME) == 0); -} - -STATIC -BOOLEAN -IsDataShdr ( - Elf_Shdr *Shdr - ) -{ - if (IsHiiRsrcShdr(Shdr)) { - return FALSE; - } - return (BOOLEAN) (Shdr->sh_flags & (SHF_EXECINSTR | SHF_WRITE | SHF_ALLOC)) == (SHF_ALLOC | SHF_WRITE); -} - -STATIC -BOOLEAN -IsStrtabShdr ( - Elf_Shdr *Shdr - ) -{ - Elf_Shdr *Namedr = GetShdrByIndex(mEhdr->e_shstrndx); - - return (BOOLEAN) (strcmp((CHAR8*)mEhdr + Namedr->sh_offset + Shdr->sh_name, ELF_STRTAB_SECTION_NAME) == 0); -} - -STATIC -Elf_Shdr * -FindStrtabShdr ( - VOID - ) -{ - UINT32 i; - for (i = 0; i < mEhdr->e_shnum; i++) { - Elf_Shdr *shdr = GetShdrByIndex(i); - if (IsStrtabShdr(shdr)) { - return shdr; - } - } - return NULL; -} - -STATIC -const UINT8 * -GetSymName ( - Elf_Sym *Sym - ) -{ - Elf_Shdr *StrtabShdr; - UINT8 *StrtabContents; - BOOLEAN foundEnd; - UINT32 i; - - if (Sym->st_name == 0) { - return NULL; - } - - StrtabShdr = FindStrtabShdr(); - if (StrtabShdr == NULL) { - return NULL; - } - - assert(Sym->st_name < StrtabShdr->sh_size); - - StrtabContents = (UINT8*)mEhdr + StrtabShdr->sh_offset; - - foundEnd = FALSE; - for (i = Sym->st_name; (i < StrtabShdr->sh_size) && !foundEnd; i++) { - foundEnd = (BOOLEAN)(StrtabContents[i] == 0); - } - assert(foundEnd); - - return StrtabContents + Sym->st_name; -} - -// -// Elf functions interface implementation -// - -STATIC -VOID -ScanSections32 ( - VOID - ) -{ - UINT32 i; - EFI_IMAGE_DOS_HEADER *DosHdr; - EFI_IMAGE_OPTIONAL_HEADER_UNION *NtHdr; - UINT32 CoffEntry; - UINT32 SectionCount; - BOOLEAN FoundSection; - - CoffEntry = 0; - mCoffOffset = 0; - - // - // Coff file start with a DOS header. - // - mCoffOffset = sizeof(EFI_IMAGE_DOS_HEADER) + 0x40; - mNtHdrOffset = mCoffOffset; - switch (mEhdr->e_machine) { - case EM_386: - case EM_ARM: - mCoffOffset += sizeof (EFI_IMAGE_NT_HEADERS32); - break; - default: - VerboseMsg ("%u unknown e_machine type. Assume IA-32", (UINTN)mEhdr->e_machine); - mCoffOffset += sizeof (EFI_IMAGE_NT_HEADERS32); - break; - } - - mTableOffset = mCoffOffset; - mCoffOffset += mCoffNbrSections * sizeof(EFI_IMAGE_SECTION_HEADER); - - // - // Set mCoffAlignment to the maximum alignment of the input sections - // we care about - // - for (i = 0; i < mEhdr->e_shnum; i++) { - Elf_Shdr *shdr = GetShdrByIndex(i); - if (shdr->sh_addralign <= mCoffAlignment) { - continue; - } - if (IsTextShdr(shdr) || IsDataShdr(shdr) || IsHiiRsrcShdr(shdr)) { - mCoffAlignment = (UINT32)shdr->sh_addralign; - } - } - - // - // Check if mCoffAlignment is larger than MAX_COFF_ALIGNMENT - // - if (mCoffAlignment > MAX_COFF_ALIGNMENT) { - Error (NULL, 0, 3000, "Invalid", "Section alignment is larger than MAX_COFF_ALIGNMENT."); - assert (FALSE); - } - - // - // Move the PE/COFF header right before the first section. This will help us - // save space when converting to TE. - // - if (mCoffAlignment > mCoffOffset) { - mNtHdrOffset += mCoffAlignment - mCoffOffset; - mTableOffset += mCoffAlignment - mCoffOffset; - mCoffOffset = mCoffAlignment; - } - - // - // First text sections. - // - mCoffOffset = CoffAlign(mCoffOffset); - mTextOffset = mCoffOffset; - FoundSection = FALSE; - SectionCount = 0; - for (i = 0; i < mEhdr->e_shnum; i++) { - Elf_Shdr *shdr = GetShdrByIndex(i); - if (IsTextShdr(shdr)) { - if ((shdr->sh_addralign != 0) && (shdr->sh_addralign != 1)) { - // the alignment field is valid - if ((shdr->sh_addr & (shdr->sh_addralign - 1)) == 0) { - // if the section address is aligned we must align PE/COFF - mCoffOffset = (mCoffOffset + shdr->sh_addralign - 1) & ~(shdr->sh_addralign - 1); - } else { - Error (NULL, 0, 3000, "Invalid", "Section address not aligned to its own alignment."); - } - } - - /* Relocate entry. */ - if ((mEhdr->e_entry >= shdr->sh_addr) && - (mEhdr->e_entry < shdr->sh_addr + shdr->sh_size)) { - CoffEntry = mCoffOffset + mEhdr->e_entry - shdr->sh_addr; - } - - // - // Set mTextOffset with the offset of the first '.text' section - // - if (!FoundSection) { - mTextOffset = mCoffOffset; - FoundSection = TRUE; - } - - mCoffSectionsOffset[i] = mCoffOffset; - mCoffOffset += shdr->sh_size; - SectionCount ++; - } - } - - if (!FoundSection && mOutImageType != FW_ACPI_IMAGE) { - Error (NULL, 0, 3000, "Invalid", "Did not find any '.text' section."); - assert (FALSE); - } - - mDebugOffset = DebugRvaAlign(mCoffOffset); - mCoffOffset = CoffAlign(mCoffOffset); - - if (SectionCount > 1 && mOutImageType == FW_EFI_IMAGE) { - Warning (NULL, 0, 0, NULL, "Multiple sections in %s are merged into 1 text section. Source level debug might not work correctly.", mInImageName); - } - - // - // Then data sections. - // - mDataOffset = mCoffOffset; - FoundSection = FALSE; - SectionCount = 0; - for (i = 0; i < mEhdr->e_shnum; i++) { - Elf_Shdr *shdr = GetShdrByIndex(i); - if (IsDataShdr(shdr)) { - if ((shdr->sh_addralign != 0) && (shdr->sh_addralign != 1)) { - // the alignment field is valid - if ((shdr->sh_addr & (shdr->sh_addralign - 1)) == 0) { - // if the section address is aligned we must align PE/COFF - mCoffOffset = (mCoffOffset + shdr->sh_addralign - 1) & ~(shdr->sh_addralign - 1); - } else { - Error (NULL, 0, 3000, "Invalid", "Section address not aligned to its own alignment."); - } - } - - // - // Set mDataOffset with the offset of the first '.data' section - // - if (!FoundSection) { - mDataOffset = mCoffOffset; - FoundSection = TRUE; - } - - mCoffSectionsOffset[i] = mCoffOffset; - mCoffOffset += shdr->sh_size; - SectionCount ++; - } - } - - if (SectionCount > 1 && mOutImageType == FW_EFI_IMAGE) { - Warning (NULL, 0, 0, NULL, "Multiple sections in %s are merged into 1 data section. Source level debug might not work correctly.", mInImageName); - } - - // - // Make room for .debug data in .data (or .text if .data is empty) instead of - // putting it in a section of its own. This is explicitly allowed by the - // PE/COFF spec, and prevents bloat in the binary when using large values for - // section alignment. - // - if (SectionCount > 0) { - mDebugOffset = DebugRvaAlign(mCoffOffset); - } - mCoffOffset = mDebugOffset + sizeof(EFI_IMAGE_DEBUG_DIRECTORY_ENTRY) + - sizeof(EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY) + - strlen(mInImageName) + 1; - - mCoffOffset = CoffAlign(mCoffOffset); - if (SectionCount == 0) { - mDataOffset = mCoffOffset; - } - - // - // The HII resource sections. - // - mHiiRsrcOffset = mCoffOffset; - for (i = 0; i < mEhdr->e_shnum; i++) { - Elf_Shdr *shdr = GetShdrByIndex(i); - if (IsHiiRsrcShdr(shdr)) { - if ((shdr->sh_addralign != 0) && (shdr->sh_addralign != 1)) { - // the alignment field is valid - if ((shdr->sh_addr & (shdr->sh_addralign - 1)) == 0) { - // if the section address is aligned we must align PE/COFF - mCoffOffset = (mCoffOffset + shdr->sh_addralign - 1) & ~(shdr->sh_addralign - 1); - } else { - Error (NULL, 0, 3000, "Invalid", "Section address not aligned to its own alignment."); - } - } - if (shdr->sh_size != 0) { - mHiiRsrcOffset = mCoffOffset; - mCoffSectionsOffset[i] = mCoffOffset; - mCoffOffset += shdr->sh_size; - mCoffOffset = CoffAlign(mCoffOffset); - SetHiiResourceHeader ((UINT8*) mEhdr + shdr->sh_offset, mHiiRsrcOffset); - } - break; - } - } - - mRelocOffset = mCoffOffset; - - // - // Allocate base Coff file. Will be expanded later for relocations. - // - mCoffFile = (UINT8 *)malloc(mCoffOffset); - if (mCoffFile == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - } - assert (mCoffFile != NULL); - memset(mCoffFile, 0, mCoffOffset); - - // - // Fill headers. - // - DosHdr = (EFI_IMAGE_DOS_HEADER *)mCoffFile; - DosHdr->e_magic = EFI_IMAGE_DOS_SIGNATURE; - DosHdr->e_lfanew = mNtHdrOffset; - - NtHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION*)(mCoffFile + mNtHdrOffset); - - NtHdr->Pe32.Signature = EFI_IMAGE_NT_SIGNATURE; - - switch (mEhdr->e_machine) { - case EM_386: - NtHdr->Pe32.FileHeader.Machine = IMAGE_FILE_MACHINE_I386; - NtHdr->Pe32.OptionalHeader.Magic = EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC; - break; - case EM_ARM: - NtHdr->Pe32.FileHeader.Machine = IMAGE_FILE_MACHINE_ARMTHUMB_MIXED; - NtHdr->Pe32.OptionalHeader.Magic = EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC; - break; - default: - VerboseMsg ("%s unknown e_machine type %hu. Assume IA-32", mInImageName, mEhdr->e_machine); - NtHdr->Pe32.FileHeader.Machine = IMAGE_FILE_MACHINE_I386; - NtHdr->Pe32.OptionalHeader.Magic = EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC; - } - - NtHdr->Pe32.FileHeader.NumberOfSections = mCoffNbrSections; - NtHdr->Pe32.FileHeader.TimeDateStamp = (UINT32) time(NULL); - mImageTimeStamp = NtHdr->Pe32.FileHeader.TimeDateStamp; - NtHdr->Pe32.FileHeader.PointerToSymbolTable = 0; - NtHdr->Pe32.FileHeader.NumberOfSymbols = 0; - NtHdr->Pe32.FileHeader.SizeOfOptionalHeader = sizeof(NtHdr->Pe32.OptionalHeader); - NtHdr->Pe32.FileHeader.Characteristics = EFI_IMAGE_FILE_EXECUTABLE_IMAGE - | EFI_IMAGE_FILE_LINE_NUMS_STRIPPED - | EFI_IMAGE_FILE_LOCAL_SYMS_STRIPPED - | EFI_IMAGE_FILE_32BIT_MACHINE; - - NtHdr->Pe32.OptionalHeader.SizeOfCode = mDataOffset - mTextOffset; - NtHdr->Pe32.OptionalHeader.SizeOfInitializedData = mRelocOffset - mDataOffset; - NtHdr->Pe32.OptionalHeader.SizeOfUninitializedData = 0; - NtHdr->Pe32.OptionalHeader.AddressOfEntryPoint = CoffEntry; - - NtHdr->Pe32.OptionalHeader.BaseOfCode = mTextOffset; - - NtHdr->Pe32.OptionalHeader.BaseOfData = mDataOffset; - NtHdr->Pe32.OptionalHeader.ImageBase = 0; - NtHdr->Pe32.OptionalHeader.SectionAlignment = mCoffAlignment; - NtHdr->Pe32.OptionalHeader.FileAlignment = mCoffAlignment; - NtHdr->Pe32.OptionalHeader.SizeOfImage = 0; - - NtHdr->Pe32.OptionalHeader.SizeOfHeaders = mTextOffset; - NtHdr->Pe32.OptionalHeader.NumberOfRvaAndSizes = EFI_IMAGE_NUMBER_OF_DIRECTORY_ENTRIES; - - // - // Section headers. - // - if ((mDataOffset - mTextOffset) > 0) { - CreateSectionHeader (".text", mTextOffset, mDataOffset - mTextOffset, - EFI_IMAGE_SCN_CNT_CODE - | EFI_IMAGE_SCN_MEM_EXECUTE - | EFI_IMAGE_SCN_MEM_READ); - } else { - // Don't make a section of size 0. - NtHdr->Pe32.FileHeader.NumberOfSections--; - } - - if ((mHiiRsrcOffset - mDataOffset) > 0) { - CreateSectionHeader (".data", mDataOffset, mHiiRsrcOffset - mDataOffset, - EFI_IMAGE_SCN_CNT_INITIALIZED_DATA - | EFI_IMAGE_SCN_MEM_WRITE - | EFI_IMAGE_SCN_MEM_READ); - } else { - // Don't make a section of size 0. - NtHdr->Pe32.FileHeader.NumberOfSections--; - } - - if ((mRelocOffset - mHiiRsrcOffset) > 0) { - CreateSectionHeader (".rsrc", mHiiRsrcOffset, mRelocOffset - mHiiRsrcOffset, - EFI_IMAGE_SCN_CNT_INITIALIZED_DATA - | EFI_IMAGE_SCN_MEM_READ); - - NtHdr->Pe32.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].Size = mRelocOffset - mHiiRsrcOffset; - NtHdr->Pe32.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress = mHiiRsrcOffset; - } else { - // Don't make a section of size 0. - NtHdr->Pe32.FileHeader.NumberOfSections--; - } - -} - -STATIC -BOOLEAN -WriteSections32 ( - SECTION_FILTER_TYPES FilterType - ) -{ - UINT32 Idx; - Elf_Shdr *SecShdr; - UINT32 SecOffset; - BOOLEAN (*Filter)(Elf_Shdr *); - - // - // Initialize filter pointer - // - switch (FilterType) { - case SECTION_TEXT: - Filter = IsTextShdr; - break; - case SECTION_HII: - Filter = IsHiiRsrcShdr; - break; - case SECTION_DATA: - Filter = IsDataShdr; - break; - default: - return FALSE; - } - - // - // First: copy sections. - // - for (Idx = 0; Idx < mEhdr->e_shnum; Idx++) { - Elf_Shdr *Shdr = GetShdrByIndex(Idx); - if ((*Filter)(Shdr)) { - switch (Shdr->sh_type) { - case SHT_PROGBITS: - /* Copy. */ - if (Shdr->sh_offset + Shdr->sh_size > mFileBufferSize) { - return FALSE; - } - memcpy(mCoffFile + mCoffSectionsOffset[Idx], - (UINT8*)mEhdr + Shdr->sh_offset, - Shdr->sh_size); - break; - - case SHT_NOBITS: - memset(mCoffFile + mCoffSectionsOffset[Idx], 0, Shdr->sh_size); - break; - - default: - // - // Ignore for unknown section type. - // - VerboseMsg ("%s unknown section type %x. We ignore this unknown section type.", mInImageName, (unsigned)Shdr->sh_type); - break; - } - } - } - - // - // Second: apply relocations. - // - for (Idx = 0; Idx < mEhdr->e_shnum; Idx++) { - // - // Determine if this is a relocation section. - // - Elf_Shdr *RelShdr = GetShdrByIndex(Idx); - if ((RelShdr->sh_type != SHT_REL) && (RelShdr->sh_type != SHT_RELA)) { - continue; - } - - // - // Relocation section found. Now extract section information that the relocations - // apply to in the ELF data and the new COFF data. - // - SecShdr = GetShdrByIndex(RelShdr->sh_info); - SecOffset = mCoffSectionsOffset[RelShdr->sh_info]; - - // - // Only process relocations for the current filter type. - // - if (RelShdr->sh_type == SHT_REL && (*Filter)(SecShdr)) { - UINT32 RelOffset; - - // - // Determine the symbol table referenced by the relocation data. - // - Elf_Shdr *SymtabShdr = GetShdrByIndex(RelShdr->sh_link); - UINT8 *Symtab = (UINT8*)mEhdr + SymtabShdr->sh_offset; - - // - // Process all relocation entries for this section. - // - for (RelOffset = 0; RelOffset < RelShdr->sh_size; RelOffset += RelShdr->sh_entsize) { - // - // Set pointer to relocation entry - // - Elf_Rel *Rel = (Elf_Rel *)((UINT8*)mEhdr + RelShdr->sh_offset + RelOffset); - - // - // Set pointer to symbol table entry associated with the relocation entry. - // - Elf_Sym *Sym = (Elf_Sym *)(Symtab + ELF_R_SYM(Rel->r_info) * SymtabShdr->sh_entsize); - - Elf_Shdr *SymShdr; - UINT8 *Targ; - UINT16 Address; - - // - // Check section header index found in symbol table and get the section - // header location. - // - if (Sym->st_shndx == SHN_UNDEF - || Sym->st_shndx >= mEhdr->e_shnum) { - const UINT8 *SymName = GetSymName(Sym); - if (SymName == NULL) { - SymName = (const UINT8 *)""; - } - continue; - } - SymShdr = GetShdrByIndex(Sym->st_shndx); - - // - // Convert the relocation data to a pointer into the coff file. - // - // Note: - // r_offset is the virtual address of the storage unit to be relocated. - // sh_addr is the virtual address for the base of the section. - // - Targ = mCoffFile + SecOffset + (Rel->r_offset - SecShdr->sh_addr); - - // - // Determine how to handle each relocation type based on the machine type. - // - if (mEhdr->e_machine == EM_386) { - switch (ELF_R_TYPE(Rel->r_info)) { - case R_386_NONE: - break; - case R_386_32: - // - // Absolute relocation. - // Converts Targ from a absolute virtual address to the absolute - // COFF address. - // - *(UINT32 *)Targ = *(UINT32 *)Targ - SymShdr->sh_addr - + mCoffSectionsOffset[Sym->st_shndx]; - break; - case R_386_PC32: - // - // Relative relocation: Symbol - Ip + Addend - // - *(UINT32 *)Targ = *(UINT32 *)Targ - + (mCoffSectionsOffset[Sym->st_shndx] - SymShdr->sh_addr) - - (SecOffset - SecShdr->sh_addr); - break; - default: - Error (NULL, 0, 3000, "Invalid", "%s unsupported ELF EM_386 relocation 0x%x.", mInImageName, (unsigned) ELF_R_TYPE(Rel->r_info)); - } - } else if (mEhdr->e_machine == EM_ARM) { - switch (ELF32_R_TYPE(Rel->r_info)) { - case R_ARM_RBASE: - // No relocation - no action required - // break skipped - - case R_ARM_PC24: - case R_ARM_REL32: - case R_ARM_XPC25: - case R_ARM_THM_PC22: - case R_ARM_THM_JUMP19: - case R_ARM_CALL: - case R_ARM_JMP24: - case R_ARM_THM_JUMP24: - case R_ARM_PREL31: - case R_ARM_MOVW_PREL_NC: - case R_ARM_MOVT_PREL: - case R_ARM_THM_MOVW_PREL_NC: - case R_ARM_THM_MOVT_PREL: - case R_ARM_THM_JMP6: - case R_ARM_THM_ALU_PREL_11_0: - case R_ARM_THM_PC12: - case R_ARM_REL32_NOI: - case R_ARM_ALU_PC_G0_NC: - case R_ARM_ALU_PC_G0: - case R_ARM_ALU_PC_G1_NC: - case R_ARM_ALU_PC_G1: - case R_ARM_ALU_PC_G2: - case R_ARM_LDR_PC_G1: - case R_ARM_LDR_PC_G2: - case R_ARM_LDRS_PC_G0: - case R_ARM_LDRS_PC_G1: - case R_ARM_LDRS_PC_G2: - case R_ARM_LDC_PC_G0: - case R_ARM_LDC_PC_G1: - case R_ARM_LDC_PC_G2: - case R_ARM_THM_JUMP11: - case R_ARM_THM_JUMP8: - case R_ARM_TLS_GD32: - case R_ARM_TLS_LDM32: - case R_ARM_TLS_IE32: - // Thease are all PC-relative relocations and don't require modification - // GCC does not seem to have the concept of a application that just needs to get relocated. - break; - - case R_ARM_THM_MOVW_ABS_NC: - // MOVW is only lower 16-bits of the addres - Address = (UINT16)(Sym->st_value - SymShdr->sh_addr + mCoffSectionsOffset[Sym->st_shndx]); - ThumbMovtImmediatePatch ((UINT16 *)Targ, Address); - break; - - case R_ARM_THM_MOVT_ABS: - // MOVT is only upper 16-bits of the addres - Address = (UINT16)((Sym->st_value - SymShdr->sh_addr + mCoffSectionsOffset[Sym->st_shndx]) >> 16); - ThumbMovtImmediatePatch ((UINT16 *)Targ, Address); - break; - - case R_ARM_ABS32: - case R_ARM_RABS32: - // - // Absolute relocation. - // - *(UINT32 *)Targ = *(UINT32 *)Targ - SymShdr->sh_addr + mCoffSectionsOffset[Sym->st_shndx]; - break; - - default: - Error (NULL, 0, 3000, "Invalid", "WriteSections (): %s unsupported ELF EM_ARM relocation 0x%x.", mInImageName, (unsigned) ELF32_R_TYPE(Rel->r_info)); - } - } - } - } - } - - return TRUE; -} - -UINTN gMovwOffset = 0; - -STATIC -VOID -WriteRelocations32 ( - VOID - ) -{ - UINT32 Index; - EFI_IMAGE_OPTIONAL_HEADER_UNION *NtHdr; - EFI_IMAGE_DATA_DIRECTORY *Dir; - BOOLEAN FoundRelocations; - Elf_Dyn *Dyn; - Elf_Rel *Rel; - UINTN RelElementSize; - UINTN RelSize; - UINTN RelOffset; - UINTN K; - Elf32_Phdr *DynamicSegment; - - for (Index = 0, FoundRelocations = FALSE; Index < mEhdr->e_shnum; Index++) { - Elf_Shdr *RelShdr = GetShdrByIndex(Index); - if ((RelShdr->sh_type == SHT_REL) || (RelShdr->sh_type == SHT_RELA)) { - Elf_Shdr *SecShdr = GetShdrByIndex (RelShdr->sh_info); - if (IsTextShdr(SecShdr) || IsDataShdr(SecShdr)) { - UINT32 RelIdx; - - FoundRelocations = TRUE; - for (RelIdx = 0; RelIdx < RelShdr->sh_size; RelIdx += RelShdr->sh_entsize) { - Rel = (Elf_Rel *)((UINT8*)mEhdr + RelShdr->sh_offset + RelIdx); - - if (mEhdr->e_machine == EM_386) { - switch (ELF_R_TYPE(Rel->r_info)) { - case R_386_NONE: - case R_386_PC32: - // - // No fixup entry required. - // - break; - case R_386_32: - // - // Creates a relative relocation entry from the absolute entry. - // - CoffAddFixup(mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr), - EFI_IMAGE_REL_BASED_HIGHLOW); - break; - default: - Error (NULL, 0, 3000, "Invalid", "%s unsupported ELF EM_386 relocation 0x%x.", mInImageName, (unsigned) ELF_R_TYPE(Rel->r_info)); - } - } else if (mEhdr->e_machine == EM_ARM) { - switch (ELF32_R_TYPE(Rel->r_info)) { - case R_ARM_RBASE: - // No relocation - no action required - // break skipped - - case R_ARM_PC24: - case R_ARM_REL32: - case R_ARM_XPC25: - case R_ARM_THM_PC22: - case R_ARM_THM_JUMP19: - case R_ARM_CALL: - case R_ARM_JMP24: - case R_ARM_THM_JUMP24: - case R_ARM_PREL31: - case R_ARM_MOVW_PREL_NC: - case R_ARM_MOVT_PREL: - case R_ARM_THM_MOVW_PREL_NC: - case R_ARM_THM_MOVT_PREL: - case R_ARM_THM_JMP6: - case R_ARM_THM_ALU_PREL_11_0: - case R_ARM_THM_PC12: - case R_ARM_REL32_NOI: - case R_ARM_ALU_PC_G0_NC: - case R_ARM_ALU_PC_G0: - case R_ARM_ALU_PC_G1_NC: - case R_ARM_ALU_PC_G1: - case R_ARM_ALU_PC_G2: - case R_ARM_LDR_PC_G1: - case R_ARM_LDR_PC_G2: - case R_ARM_LDRS_PC_G0: - case R_ARM_LDRS_PC_G1: - case R_ARM_LDRS_PC_G2: - case R_ARM_LDC_PC_G0: - case R_ARM_LDC_PC_G1: - case R_ARM_LDC_PC_G2: - case R_ARM_THM_JUMP11: - case R_ARM_THM_JUMP8: - case R_ARM_TLS_GD32: - case R_ARM_TLS_LDM32: - case R_ARM_TLS_IE32: - // Thease are all PC-relative relocations and don't require modification - break; - - case R_ARM_THM_MOVW_ABS_NC: - CoffAddFixup ( - mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr), - EFI_IMAGE_REL_BASED_ARM_MOV32T - ); - - // PE/COFF treats MOVW/MOVT relocation as single 64-bit instruction - // Track this address so we can log an error for unsupported sequence of MOVW/MOVT - gMovwOffset = mCoffSectionsOffset[RelShdr->sh_info] + (Rel->r_offset - SecShdr->sh_addr); - break; - - case R_ARM_THM_MOVT_ABS: - if ((gMovwOffset + 4) != (mCoffSectionsOffset[RelShdr->sh_info] + (Rel->r_offset - SecShdr->sh_addr))) { - Error (NULL, 0, 3000, "Not Supported", "PE/COFF requires MOVW+MOVT instruction sequence %x +4 != %x.", gMovwOffset, mCoffSectionsOffset[RelShdr->sh_info] + (Rel->r_offset - SecShdr->sh_addr)); - } - break; - - case R_ARM_ABS32: - case R_ARM_RABS32: - CoffAddFixup ( - mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr), - EFI_IMAGE_REL_BASED_HIGHLOW - ); - break; - - default: - Error (NULL, 0, 3000, "Invalid", "WriteRelocations(): %s unsupported ELF EM_ARM relocation 0x%x.", mInImageName, (unsigned) ELF32_R_TYPE(Rel->r_info)); - } - } else { - Error (NULL, 0, 3000, "Not Supported", "This tool does not support relocations for ELF with e_machine %u (processor type).", (unsigned) mEhdr->e_machine); - } - } - } - } - } - - if (!FoundRelocations && (mEhdr->e_machine == EM_ARM)) { - /* Try again, but look for PT_DYNAMIC instead of SHT_REL */ - - for (Index = 0; Index < mEhdr->e_phnum; Index++) { - RelElementSize = 0; - RelSize = 0; - RelOffset = 0; - - DynamicSegment = GetPhdrByIndex (Index); - - if (DynamicSegment->p_type == PT_DYNAMIC) { - Dyn = (Elf32_Dyn *) ((UINT8 *)mEhdr + DynamicSegment->p_offset); - - while (Dyn->d_tag != DT_NULL) { - switch (Dyn->d_tag) { - case DT_REL: - RelOffset = Dyn->d_un.d_val; - break; - - case DT_RELSZ: - RelSize = Dyn->d_un.d_val; - break; - - case DT_RELENT: - RelElementSize = Dyn->d_un.d_val; - break; - - default: - break; - } - Dyn++; - } - if (( RelOffset == 0 ) || ( RelSize == 0 ) || ( RelElementSize == 0 )) { - Error (NULL, 0, 3000, "Invalid", "%s bad ARM dynamic relocations.", mInImageName); - } - - for (Index = 0; Index < mEhdr->e_shnum; Index++) { - Elf_Shdr *shdr = GetShdrByIndex(Index); - - // - // The PT_DYNAMIC section contains DT_REL relocations whose r_offset - // field is relative to the base of a segment (or the entire image), - // and not to the base of an ELF input section as is the case for - // SHT_REL sections. This means that we cannot fix up such relocations - // unless we cross-reference ELF sections and segments, considering - // that the output placement recorded in mCoffSectionsOffset[] is - // section based, not segment based. - // - // Fortunately, there is a simple way around this: we require that the - // in-memory layout of the ELF and PE/COFF versions of the binary is - // identical. That way, r_offset will retain its validity as a PE/COFF - // image offset, and we can record it in the COFF fixup table - // unmodified. - // - if (shdr->sh_addr != mCoffSectionsOffset[Index]) { - Error (NULL, 0, 3000, - "Invalid", "%s: PT_DYNAMIC relocations require identical ELF and PE/COFF section offsets.", - mInImageName); - } - } - - for (K = 0; K < RelSize; K += RelElementSize) { - - if (DynamicSegment->p_paddr == 0) { - // Older versions of the ARM ELF (SWS ESPC 0003 B-02) specification define DT_REL - // as an offset in the dynamic segment. p_paddr is defined to be zero for ARM tools - Rel = (Elf32_Rel *) ((UINT8 *) mEhdr + DynamicSegment->p_offset + RelOffset + K); - } else { - // This is how it reads in the generic ELF specification - Rel = (Elf32_Rel *) ((UINT8 *) mEhdr + RelOffset + K); - } - - switch (ELF32_R_TYPE (Rel->r_info)) { - case R_ARM_RBASE: - break; - - case R_ARM_RABS32: - CoffAddFixup (Rel->r_offset, EFI_IMAGE_REL_BASED_HIGHLOW); - break; - - default: - Error (NULL, 0, 3000, "Invalid", "%s bad ARM dynamic relocations, unknown type %d.", mInImageName, ELF32_R_TYPE (Rel->r_info)); - break; - } - } - break; - } - } - } - - // - // Pad by adding empty entries. - // - while (mCoffOffset & (mCoffAlignment - 1)) { - CoffAddFixupEntry(0); - } - - NtHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(mCoffFile + mNtHdrOffset); - Dir = &NtHdr->Pe32.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC]; - Dir->Size = mCoffOffset - mRelocOffset; - if (Dir->Size == 0) { - // If no relocations, null out the directory entry and don't add the .reloc section - Dir->VirtualAddress = 0; - NtHdr->Pe32.FileHeader.NumberOfSections--; - } else { - Dir->VirtualAddress = mRelocOffset; - CreateSectionHeader (".reloc", mRelocOffset, mCoffOffset - mRelocOffset, - EFI_IMAGE_SCN_CNT_INITIALIZED_DATA - | EFI_IMAGE_SCN_MEM_DISCARDABLE - | EFI_IMAGE_SCN_MEM_READ); - } - -} - -STATIC -VOID -WriteDebug32 ( - VOID - ) -{ - UINT32 Len; - EFI_IMAGE_OPTIONAL_HEADER_UNION *NtHdr; - EFI_IMAGE_DATA_DIRECTORY *DataDir; - EFI_IMAGE_DEBUG_DIRECTORY_ENTRY *Dir; - EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY *Nb10; - - Len = strlen(mInImageName) + 1; - - Dir = (EFI_IMAGE_DEBUG_DIRECTORY_ENTRY*)(mCoffFile + mDebugOffset); - Dir->Type = EFI_IMAGE_DEBUG_TYPE_CODEVIEW; - Dir->SizeOfData = sizeof(EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY) + Len; - Dir->RVA = mDebugOffset + sizeof(EFI_IMAGE_DEBUG_DIRECTORY_ENTRY); - Dir->FileOffset = mDebugOffset + sizeof(EFI_IMAGE_DEBUG_DIRECTORY_ENTRY); - - Nb10 = (EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY*)(Dir + 1); - Nb10->Signature = CODEVIEW_SIGNATURE_NB10; - strcpy ((char *)(Nb10 + 1), mInImageName); - - - NtHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(mCoffFile + mNtHdrOffset); - DataDir = &NtHdr->Pe32.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG]; - DataDir->VirtualAddress = mDebugOffset; - DataDir->Size = sizeof(EFI_IMAGE_DEBUG_DIRECTORY_ENTRY); -} - -STATIC -VOID -SetImageSize32 ( - VOID - ) -{ - EFI_IMAGE_OPTIONAL_HEADER_UNION *NtHdr; - - // - // Set image size - // - NtHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(mCoffFile + mNtHdrOffset); - NtHdr->Pe32.OptionalHeader.SizeOfImage = mCoffOffset; -} - -STATIC -VOID -CleanUp32 ( - VOID - ) -{ - if (mCoffSectionsOffset != NULL) { - free (mCoffSectionsOffset); - } -} - - diff --git a/BaseTools/Source/C/GenFw/Elf32Convert.h b/BaseTools/Source/C/GenFw/Elf32Convert.h deleted file mode 100644 index 906a4de3cc..0000000000 --- a/BaseTools/Source/C/GenFw/Elf32Convert.h +++ /dev/null @@ -1,19 +0,0 @@ -/** @file -Header file for Elf32 Convert solution - -Copyright (c) 2010 - 2018, Intel Corporation. All rights reserved.
- -SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -#ifndef _ELF_32_CONVERT_ -#define _ELF_32_CONVERT_ - -BOOLEAN -InitializeElf32 ( - UINT8 *FileBuffer, - ELF_FUNCTION_TABLE *ElfFunctions - ); - -#endif diff --git a/BaseTools/Source/C/GenFw/Elf64Convert.c b/BaseTools/Source/C/GenFw/Elf64Convert.c deleted file mode 100644 index 9d04fc612e..0000000000 --- a/BaseTools/Source/C/GenFw/Elf64Convert.c +++ /dev/null @@ -1,2432 +0,0 @@ -/** @file -Elf64 convert solution - -Copyright (c) 2010 - 2021, Intel Corporation. All rights reserved.
-Portions copyright (c) 2013-2022, ARM Ltd. All rights reserved.
-Portions Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights reserved.
-Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All rights reserved.
- -SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -#ifndef __GNUC__ -#include -#include -#endif -#include -#include -#include -#include -#include -#include - -#include -#include - -#include "PeCoffLib.h" -#include "EfiUtilityMsgs.h" - -#include "GenFw.h" -#include "ElfConvert.h" -#include "Elf64Convert.h" - -STATIC -VOID -ScanSections64 ( - VOID - ); - -STATIC -BOOLEAN -WriteSections64 ( - SECTION_FILTER_TYPES FilterType - ); - -STATIC -VOID -WriteRelocations64 ( - VOID - ); - -STATIC -VOID -WriteDebug64 ( - VOID - ); - -STATIC -VOID -WriteExport64 ( - VOID - ); - -STATIC -VOID -SetImageSize64 ( - VOID - ); - -STATIC -VOID -CleanUp64 ( - VOID - ); - -// -// Rename ELF32 structures to common names to help when porting to ELF64. -// -typedef Elf64_Shdr Elf_Shdr; -typedef Elf64_Ehdr Elf_Ehdr; -typedef Elf64_Rel Elf_Rel; -typedef Elf64_Rela Elf_Rela; -typedef Elf64_Sym Elf_Sym; -typedef Elf64_Phdr Elf_Phdr; -typedef Elf64_Dyn Elf_Dyn; -#define ELFCLASS ELFCLASS64 -#define ELF_R_TYPE(r) ELF64_R_TYPE(r) -#define ELF_R_SYM(r) ELF64_R_SYM(r) - -// -// Well known ELF structures. -// -STATIC Elf_Ehdr *mEhdr; -STATIC Elf_Shdr *mShdrBase; -STATIC Elf_Phdr *mPhdrBase; - -// -// GOT information -// -STATIC Elf_Shdr *mGOTShdr = NULL; -STATIC UINT32 mGOTShindex = 0; -STATIC UINT32 *mGOTCoffEntries = NULL; -STATIC UINT32 mGOTMaxCoffEntries = 0; -STATIC UINT32 mGOTNumCoffEntries = 0; - -// -// Coff information -// -STATIC UINT32 mCoffAlignment = 0x20; - -// -// PE section alignment. -// -STATIC UINT16 mCoffNbrSections = 4; - -// -// ELF sections to offset in Coff file. -// -STATIC UINT32 *mCoffSectionsOffset = NULL; - -// -// Offsets in COFF file -// -STATIC UINT32 mNtHdrOffset; -STATIC UINT32 mTextOffset; -STATIC UINT32 mDataOffset; -STATIC UINT32 mHiiRsrcOffset; -STATIC UINT32 mRelocOffset; -STATIC UINT32 mDebugOffset; -STATIC UINT32 mExportOffset; -// -// Used for RISC-V relocations. -// -STATIC UINT8 *mRiscVPass1Targ = NULL; -STATIC Elf_Shdr *mRiscVPass1Sym = NULL; -STATIC Elf64_Half mRiscVPass1SymSecIndex = 0; -STATIC INT32 mRiscVPass1Offset; -STATIC INT32 mRiscVPass1GotFixup; - -// -// Used for Export section. -// -STATIC UINT32 mExportSize; -STATIC UINT32 mExportRVA[PRM_MODULE_EXPORT_SYMBOL_NUM]; -STATIC UINT32 mExportSymNum; -STATIC CHAR8 mExportSymName[PRM_MODULE_EXPORT_SYMBOL_NUM][PRM_HANDLER_NAME_MAXIMUM_LENGTH]; - -// -// Initialization Function -// -BOOLEAN -InitializeElf64 ( - UINT8 *FileBuffer, - ELF_FUNCTION_TABLE *ElfFunctions - ) -{ - // - // Initialize data pointer and structures. - // - VerboseMsg ("Set EHDR"); - mEhdr = (Elf_Ehdr*) FileBuffer; - - // - // Check the ELF64 specific header information. - // - VerboseMsg ("Check ELF64 Header Information"); - if (mEhdr->e_ident[EI_CLASS] != ELFCLASS64) { - Error (NULL, 0, 3000, "Unsupported", "ELF EI_DATA not ELFCLASS64"); - return FALSE; - } - if (mEhdr->e_ident[EI_DATA] != ELFDATA2LSB) { - Error (NULL, 0, 3000, "Unsupported", "ELF EI_DATA not ELFDATA2LSB"); - return FALSE; - } - if ((mEhdr->e_type != ET_EXEC) && (mEhdr->e_type != ET_DYN)) { - Error (NULL, 0, 3000, "Unsupported", "ELF e_type not ET_EXEC or ET_DYN"); - return FALSE; - } - if (!((mEhdr->e_machine == EM_X86_64) || (mEhdr->e_machine == EM_AARCH64) || (mEhdr->e_machine == EM_RISCV64) || (mEhdr->e_machine == EM_LOONGARCH))) { - Warning (NULL, 0, 3000, "Unsupported", "ELF e_machine is not Elf64 machine."); - } - if (mEhdr->e_version != EV_CURRENT) { - Error (NULL, 0, 3000, "Unsupported", "ELF e_version (%u) not EV_CURRENT (%d)", (unsigned) mEhdr->e_version, EV_CURRENT); - return FALSE; - } - - if (mExportFlag) { - if ((mEhdr->e_machine != EM_X86_64) && (mEhdr->e_machine != EM_AARCH64)) { - Error (NULL, 0, 3000, "Unsupported", "--prm option currently only supports X64 and AArch64 archs."); - return FALSE; - } - } - - // - // Update section header pointers - // - VerboseMsg ("Update Header Pointers"); - mShdrBase = (Elf_Shdr *)((UINT8 *)mEhdr + mEhdr->e_shoff); - mPhdrBase = (Elf_Phdr *)((UINT8 *)mEhdr + mEhdr->e_phoff); - - // - // Create COFF Section offset buffer and zero. - // - VerboseMsg ("Create COFF Section Offset Buffer"); - mCoffSectionsOffset = (UINT32 *)malloc(mEhdr->e_shnum * sizeof (UINT32)); - if (mCoffSectionsOffset == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - return FALSE; - } - memset(mCoffSectionsOffset, 0, mEhdr->e_shnum * sizeof(UINT32)); - - // - // Fill in function pointers. - // - VerboseMsg ("Fill in Function Pointers"); - ElfFunctions->ScanSections = ScanSections64; - ElfFunctions->WriteSections = WriteSections64; - ElfFunctions->WriteRelocations = WriteRelocations64; - ElfFunctions->WriteDebug = WriteDebug64; - ElfFunctions->SetImageSize = SetImageSize64; - ElfFunctions->CleanUp = CleanUp64; - - if (mExportFlag) { - mCoffNbrSections ++; - ElfFunctions->WriteExport = WriteExport64; - } - - return TRUE; -} - - -// -// Header by Index functions -// -STATIC -Elf_Shdr* -GetShdrByIndex ( - UINT32 Num - ) -{ - if (Num >= mEhdr->e_shnum) { - Error (NULL, 0, 3000, "Invalid", "GetShdrByIndex: Index %u is too high.", Num); - exit(EXIT_FAILURE); - } - - return (Elf_Shdr*)((UINT8*)mShdrBase + Num * mEhdr->e_shentsize); -} - -STATIC -UINT32 -CoffAlign ( - UINT32 Offset - ) -{ - return (Offset + mCoffAlignment - 1) & ~(mCoffAlignment - 1); -} - -STATIC -UINT32 -DebugRvaAlign ( - UINT32 Offset - ) -{ - return (Offset + 3) & ~3; -} - -// -// filter functions -// -STATIC -BOOLEAN -IsTextShdr ( - Elf_Shdr *Shdr - ) -{ - return (BOOLEAN) (((Shdr->sh_flags & (SHF_EXECINSTR | SHF_ALLOC)) == (SHF_EXECINSTR | SHF_ALLOC)) || - ((Shdr->sh_flags & (SHF_WRITE | SHF_ALLOC)) == SHF_ALLOC)); -} - -STATIC -BOOLEAN -IsHiiRsrcShdr ( - Elf_Shdr *Shdr - ) -{ - Elf_Shdr *Namedr = GetShdrByIndex(mEhdr->e_shstrndx); - - return (BOOLEAN) (strcmp((CHAR8*)mEhdr + Namedr->sh_offset + Shdr->sh_name, ELF_HII_SECTION_NAME) == 0); -} - -STATIC -BOOLEAN -IsSymbolShdr ( - Elf_Shdr *Shdr - ) -{ - Elf_Shdr *Namehdr = GetShdrByIndex(mEhdr->e_shstrndx); - - return (BOOLEAN) (strcmp((CHAR8*)mEhdr + Namehdr->sh_offset + Shdr->sh_name, ELF_SYMBOL_SECTION_NAME) == 0); -} - -STATIC -BOOLEAN -IsDataShdr ( - Elf_Shdr *Shdr - ) -{ - if (IsHiiRsrcShdr(Shdr)) { - return FALSE; - } - return (BOOLEAN) (Shdr->sh_flags & (SHF_EXECINSTR | SHF_WRITE | SHF_ALLOC)) == (SHF_ALLOC | SHF_WRITE); -} - -STATIC -BOOLEAN -IsStrtabShdr ( - Elf_Shdr *Shdr - ) -{ - Elf_Shdr *Namedr = GetShdrByIndex(mEhdr->e_shstrndx); - - return (BOOLEAN) (strcmp((CHAR8*)mEhdr + Namedr->sh_offset + Shdr->sh_name, ELF_STRTAB_SECTION_NAME) == 0); -} - -STATIC -Elf_Shdr * -FindStrtabShdr ( - VOID - ) -{ - UINT32 i; - for (i = 0; i < mEhdr->e_shnum; i++) { - Elf_Shdr *shdr = GetShdrByIndex(i); - if (IsStrtabShdr(shdr)) { - return shdr; - } - } - return NULL; -} - -STATIC -const UINT8 * -GetSymName ( - Elf_Sym *Sym - ) -{ - Elf_Shdr *StrtabShdr; - UINT8 *StrtabContents; - BOOLEAN foundEnd; - UINT32 i; - - if (Sym->st_name == 0) { - return NULL; - } - - StrtabShdr = FindStrtabShdr(); - if (StrtabShdr == NULL) { - return NULL; - } - - assert(Sym->st_name < StrtabShdr->sh_size); - - StrtabContents = (UINT8*)mEhdr + StrtabShdr->sh_offset; - - foundEnd = FALSE; - for (i= Sym->st_name; (i < StrtabShdr->sh_size) && !foundEnd; i++) { - foundEnd = (BOOLEAN)(StrtabContents[i] == 0); - } - assert(foundEnd); - - return StrtabContents + Sym->st_name; -} - -// -// Get Prm Handler number and name -// -STATIC -VOID -FindPrmHandler ( - UINT64 Offset - ) -{ - PRM_MODULE_EXPORT_DESCRIPTOR_STRUCT_HEADER *PrmExport; - PRM_HANDLER_EXPORT_DESCRIPTOR_STRUCT *PrmHandler; - UINT32 HandlerNum; - - PrmExport = (PRM_MODULE_EXPORT_DESCRIPTOR_STRUCT_HEADER*)((UINT8*)mEhdr + Offset); - PrmHandler = (PRM_HANDLER_EXPORT_DESCRIPTOR_STRUCT *)(PrmExport + 1); - - for (HandlerNum = 0; HandlerNum < PrmExport->NumberPrmHandlers; HandlerNum++) { - strcpy(mExportSymName[mExportSymNum], PrmHandler->PrmHandlerName); - mExportSymNum ++; - PrmHandler += 1; - - // - // Check if PRM handler number is larger than (PRM_MODULE_EXPORT_SYMBOL_NUM - 1) - // - if (mExportSymNum >= (PRM_MODULE_EXPORT_SYMBOL_NUM - 1)) { - Error (NULL, 0, 3000, "Invalid", "FindPrmHandler: Number %u is too high.", mExportSymNum); - exit(EXIT_FAILURE); - } - } -} - -// -// Find the ELF section hosting the GOT from an ELF Rva -// of a single GOT entry. Normally, GOT is placed in -// ELF .text section, so assume once we find in which -// section the GOT is, all GOT entries are there, and -// just verify this. -// -STATIC -VOID -FindElfGOTSectionFromGOTEntryElfRva ( - Elf64_Addr GOTEntryElfRva - ) -{ - UINT32 i; - if (mGOTShdr != NULL) { - if (GOTEntryElfRva >= mGOTShdr->sh_addr && - GOTEntryElfRva < mGOTShdr->sh_addr + mGOTShdr->sh_size) { - return; - } - Error (NULL, 0, 3000, "Unsupported", "FindElfGOTSectionFromGOTEntryElfRva: GOT entries found in multiple sections."); - exit(EXIT_FAILURE); - } - for (i = 0; i < mEhdr->e_shnum; i++) { - Elf_Shdr *shdr = GetShdrByIndex(i); - if (GOTEntryElfRva >= shdr->sh_addr && - GOTEntryElfRva < shdr->sh_addr + shdr->sh_size) { - mGOTShdr = shdr; - mGOTShindex = i; - return; - } - } - Error (NULL, 0, 3000, "Invalid", "FindElfGOTSectionFromGOTEntryElfRva: ElfRva 0x%016LX for GOT entry not found in any section.", GOTEntryElfRva); - exit(EXIT_FAILURE); -} - -// -// Stores locations of GOT entries in COFF image. -// Returns TRUE if GOT entry is new. -// Simple implementation as number of GOT -// entries is expected to be low. -// - -STATIC -BOOLEAN -AccumulateCoffGOTEntries ( - UINT32 GOTCoffEntry - ) -{ - UINT32 i; - if (mGOTCoffEntries != NULL) { - for (i = 0; i < mGOTNumCoffEntries; i++) { - if (mGOTCoffEntries[i] == GOTCoffEntry) { - return FALSE; - } - } - } - if (mGOTCoffEntries == NULL) { - mGOTCoffEntries = (UINT32*)malloc(5 * sizeof *mGOTCoffEntries); - if (mGOTCoffEntries == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - } - assert (mGOTCoffEntries != NULL); - mGOTMaxCoffEntries = 5; - mGOTNumCoffEntries = 0; - } else if (mGOTNumCoffEntries == mGOTMaxCoffEntries) { - mGOTCoffEntries = (UINT32*)realloc(mGOTCoffEntries, 2 * mGOTMaxCoffEntries * sizeof *mGOTCoffEntries); - if (mGOTCoffEntries == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - } - assert (mGOTCoffEntries != NULL); - mGOTMaxCoffEntries += mGOTMaxCoffEntries; - } - mGOTCoffEntries[mGOTNumCoffEntries++] = GOTCoffEntry; - return TRUE; -} - -// -// 32-bit Unsigned integer comparator for qsort. -// -STATIC -int -UINT32Comparator ( - const void* lhs, - const void* rhs - ) -{ - if (*(const UINT32*)lhs < *(const UINT32*)rhs) { - return -1; - } - return *(const UINT32*)lhs > *(const UINT32*)rhs; -} - -// -// Emit accumulated Coff GOT entry relocations into -// Coff image. This function performs its job -// once and then releases the entry list, so -// it can safely be called multiple times. -// -STATIC -VOID -EmitGOTRelocations ( - VOID - ) -{ - UINT32 i; - if (mGOTCoffEntries == NULL) { - return; - } - // - // Emit Coff relocations with Rvas ordered. - // - qsort( - mGOTCoffEntries, - mGOTNumCoffEntries, - sizeof *mGOTCoffEntries, - UINT32Comparator); - for (i = 0; i < mGOTNumCoffEntries; i++) { - VerboseMsg ("EFI_IMAGE_REL_BASED_DIR64 Offset: 0x%08X", mGOTCoffEntries[i]); - CoffAddFixup( - mGOTCoffEntries[i], - EFI_IMAGE_REL_BASED_DIR64); - } - free(mGOTCoffEntries); - mGOTCoffEntries = NULL; - mGOTMaxCoffEntries = 0; - mGOTNumCoffEntries = 0; -} -// -// RISC-V 64 specific Elf WriteSection function. -// -STATIC -VOID -WriteSectionRiscV64 ( - Elf_Rela *Rel, - UINT8 *Targ, - Elf_Shdr *SymShdr, - Elf_Sym *Sym - ) -{ - UINT32 Value; - UINT32 Value2; - Elf64_Addr GOTEntryRva; - - switch (ELF_R_TYPE(Rel->r_info)) { - case R_RISCV_NONE: - break; - - case R_RISCV_32: - *(UINT64 *)Targ = Sym->st_value + Rel->r_addend; - break; - - case R_RISCV_64: - *(UINT64 *)Targ = Sym->st_value + Rel->r_addend; - break; - - case R_RISCV_HI20: - mRiscVPass1Targ = Targ; - mRiscVPass1Sym = SymShdr; - mRiscVPass1SymSecIndex = Sym->st_shndx; - break; - - case R_RISCV_LO12_I: - if (mRiscVPass1Sym == SymShdr && mRiscVPass1Targ != NULL && mRiscVPass1SymSecIndex == Sym->st_shndx && mRiscVPass1SymSecIndex != 0) { - Value = (UINT32)(RV_X(*(UINT32 *)mRiscVPass1Targ, 12, 20) << 12); - Value2 = (UINT32)(RV_X(*(UINT32 *)Targ, 20, 12)); - if (Value2 & (RISCV_IMM_REACH/2)) { - Value2 |= ~(RISCV_IMM_REACH-1); - } - Value += Value2; - Value = Value - (UINT32)SymShdr->sh_addr + mCoffSectionsOffset[Sym->st_shndx]; - Value2 = RISCV_CONST_HIGH_PART (Value); - *(UINT32 *)mRiscVPass1Targ = (RV_X (Value2, 12, 20) << 12) | \ - (RV_X (*(UINT32 *)mRiscVPass1Targ, 0, 12)); - *(UINT32 *)Targ = (RV_X (Value, 0, 12) << 20) | \ - (RV_X (*(UINT32 *)Targ, 0, 20)); - } - mRiscVPass1Sym = NULL; - mRiscVPass1Targ = NULL; - mRiscVPass1SymSecIndex = 0; - break; - - case R_RISCV_LO12_S: - if (mRiscVPass1Sym == SymShdr && mRiscVPass1Targ != NULL && mRiscVPass1SymSecIndex == Sym->st_shndx && mRiscVPass1SymSecIndex != 0) { - Value = (UINT32)(RV_X(*(UINT32 *)mRiscVPass1Targ, 12, 20) << 12); - Value2 = (UINT32)(RV_X(*(UINT32 *)Targ, 7, 5) | (RV_X(*(UINT32 *)Targ, 25, 7) << 5)); - if (Value2 & (RISCV_IMM_REACH/2)) { - Value2 |= ~(RISCV_IMM_REACH-1); - } - Value += Value2; - Value = Value - (UINT32)SymShdr->sh_addr + mCoffSectionsOffset[Sym->st_shndx]; - Value2 = RISCV_CONST_HIGH_PART (Value); - *(UINT32 *)mRiscVPass1Targ = (RV_X (Value2, 12, 20) << 12) | \ - (RV_X (*(UINT32 *)mRiscVPass1Targ, 0, 12)); - Value2 = *(UINT32 *)Targ & 0x01fff07f; - Value &= RISCV_IMM_REACH - 1; - *(UINT32 *)Targ = Value2 | (UINT32)(((RV_X(Value, 0, 5) << 7) | (RV_X(Value, 5, 7) << 25))); - } - mRiscVPass1Sym = NULL; - mRiscVPass1Targ = NULL; - mRiscVPass1SymSecIndex = 0; - break; - - case R_RISCV_GOT_HI20: - GOTEntryRva = (Sym->st_value - Rel->r_offset); - mRiscVPass1Offset = RV_X(GOTEntryRva, 0, 12); - Value = (UINT32)RV_X(GOTEntryRva, 12, 20); - *(UINT32 *)Targ = (Value << 12) | (RV_X(*(UINT32*)Targ, 0, 12)); - - mRiscVPass1Targ = Targ; - mRiscVPass1Sym = SymShdr; - mRiscVPass1SymSecIndex = Sym->st_shndx; - mRiscVPass1GotFixup = 1; - break; - - case R_RISCV_PCREL_HI20: - mRiscVPass1Targ = Targ; - mRiscVPass1Sym = SymShdr; - mRiscVPass1SymSecIndex = Sym->st_shndx; - - Value = (UINT32)(RV_X(*(UINT32 *)mRiscVPass1Targ, 12, 20)); - break; - - case R_RISCV_PCREL_LO12_S: - if (mRiscVPass1Targ != NULL && mRiscVPass1Sym != NULL && mRiscVPass1SymSecIndex != 0) { - int i; - Value2 = (UINT32)(RV_X(*(UINT32 *)mRiscVPass1Targ, 12, 20)); - - Value = ((UINT32)(RV_X(*(UINT32 *)Targ, 25, 7)) << 5); - Value = (Value | (UINT32)(RV_X(*(UINT32 *)Targ, 7, 5))); - - if(Value & (RISCV_IMM_REACH/2)) { - Value |= ~(RISCV_IMM_REACH-1); - } - Value = Value - (UINT32)mRiscVPass1Sym->sh_addr + mCoffSectionsOffset[mRiscVPass1SymSecIndex]; - - if(-2048 > (INT32)Value) { - i = (((INT32)Value * -1) / 4096); - Value2 -= i; - Value += 4096 * i; - if(-2048 > (INT32)Value) { - Value2 -= 1; - Value += 4096; - } - } - else if( 2047 < (INT32)Value) { - i = (Value / 4096); - Value2 += i; - Value -= 4096 * i; - if(2047 < (INT32)Value) { - Value2 += 1; - Value -= 4096; - } - } - - // Update the IMM of SD instruction - // - // |31 25|24 20|19 15|14 12 |11 7|6 0| - // |-------------------------------------------|-------| - // |imm[11:5] | rs2 | rs1 | funct3 |imm[4:0] | opcode| - // --------------------------------------------------- - - // First Zero out current IMM - *(UINT32 *)Targ &= ~0xfe000f80; - - // Update with new IMM - *(UINT32 *)Targ |= (RV_X(Value, 5, 7) << 25); - *(UINT32 *)Targ |= (RV_X(Value, 0, 5) << 7); - - // Update previous instruction - *(UINT32 *)mRiscVPass1Targ = (RV_X(Value2, 0, 20)<<12) | (RV_X(*(UINT32 *)mRiscVPass1Targ, 0, 12)); - } - mRiscVPass1Sym = NULL; - mRiscVPass1Targ = NULL; - mRiscVPass1SymSecIndex = 0; - break; - - case R_RISCV_PCREL_LO12_I: - if (mRiscVPass1Targ != NULL && mRiscVPass1Sym != NULL && mRiscVPass1SymSecIndex != 0) { - int i; - Value2 = (UINT32)(RV_X(*(UINT32 *)mRiscVPass1Targ, 12, 20)); - - if(mRiscVPass1GotFixup) { - Value = (UINT32)(mRiscVPass1Offset); - } else { - Value = (UINT32)(RV_X(*(UINT32 *)Targ, 20, 12)); - if(Value & (RISCV_IMM_REACH/2)) { - Value |= ~(RISCV_IMM_REACH-1); - } - } - Value = Value - (UINT32)mRiscVPass1Sym->sh_addr + mCoffSectionsOffset[mRiscVPass1SymSecIndex]; - - if(-2048 > (INT32)Value) { - i = (((INT32)Value * -1) / 4096); - Value2 -= i; - Value += 4096 * i; - if(-2048 > (INT32)Value) { - Value2 -= 1; - Value += 4096; - } - } - else if( 2047 < (INT32)Value) { - i = (Value / 4096); - Value2 += i; - Value -= 4096 * i; - if(2047 < (INT32)Value) { - Value2 += 1; - Value -= 4096; - } - } - - if(mRiscVPass1GotFixup) { - *(UINT32 *)Targ = (RV_X((UINT32)Value, 0, 12) << 20) - | (RV_X(*(UINT32*)Targ, 0, 20)); - // Convert LD instruction to ADDI - // - // |31 20|19 15|14 12|11 7|6 0| - // |-----------------------------------------| - // |imm[11:0] | rs1 | 011 | rd | 0000011 | LD - // ----------------------------------------- - - // |-----------------------------------------| - // |imm[11:0] | rs1 | 000 | rd | 0010011 | ADDI - // ----------------------------------------- - - // To convert, let's first reset bits 12-14 and 0-6 using ~0x707f - // Then modify the opcode to ADDI (0010011) - // All other fields will remain same. - - *(UINT32 *)Targ = ((*(UINT32 *)Targ & ~0x707f) | 0x13); - } else { - *(UINT32 *)Targ = (RV_X(Value, 0, 12) << 20) | (RV_X(*(UINT32*)Targ, 0, 20)); - } - *(UINT32 *)mRiscVPass1Targ = (RV_X(Value2, 0, 20)<<12) | (RV_X(*(UINT32 *)mRiscVPass1Targ, 0, 12)); - } - mRiscVPass1Sym = NULL; - mRiscVPass1Targ = NULL; - mRiscVPass1SymSecIndex = 0; - mRiscVPass1Offset = 0; - mRiscVPass1GotFixup = 0; - break; - - case R_RISCV_ADD64: - case R_RISCV_SUB64: - case R_RISCV_ADD32: - case R_RISCV_SUB32: - case R_RISCV_BRANCH: - case R_RISCV_JAL: - case R_RISCV_GPREL_I: - case R_RISCV_GPREL_S: - case R_RISCV_CALL: - case R_RISCV_CALL_PLT: - case R_RISCV_RVC_BRANCH: - case R_RISCV_RVC_JUMP: - case R_RISCV_RELAX: - case R_RISCV_SUB6: - case R_RISCV_SET6: - case R_RISCV_SET8: - case R_RISCV_SET16: - case R_RISCV_SET32: - break; - - default: - Error (NULL, 0, 3000, "Invalid", "WriteSections64(): %s unsupported ELF EM_RISCV64 relocation 0x%x.", mInImageName, (unsigned) ELF_R_TYPE(Rel->r_info)); - } -} - -STATIC UINT16 mDllCharacteristicsEx; - -STATIC -VOID -ParseNoteSection ( - CONST Elf_Shdr *Shdr - ) -{ - CONST Elf_Note *Note; - CONST UINT32 *Prop; - UINT32 Prop0; - UINT32 Prop2; - - Note = (Elf_Note *)((UINT8 *)mEhdr + Shdr->sh_offset); - - if ((Note->n_type == NT_GNU_PROPERTY_TYPE_0) && - (Note->n_namesz == sizeof ("GNU")) && - (strcmp ((CHAR8 *)(Note + 1), "GNU") == 0) && - (Note->n_descsz > sizeof (UINT32[2]))) { - Prop = (UINT32 *)((UINT8 *)(Note + 1) + sizeof("GNU")); - - switch (mEhdr->e_machine) { - case EM_AARCH64: - Prop0 = GNU_PROPERTY_AARCH64_FEATURE_1_AND; - Prop2 = GNU_PROPERTY_AARCH64_FEATURE_1_BTI; - break; - - case EM_X86_64: - Prop0 = GNU_PROPERTY_X86_FEATURE_1_AND; - Prop2 = GNU_PROPERTY_X86_FEATURE_1_IBT; - break; - - default: - return; - } - if ((Prop[0] == Prop0) && - (Prop[1] >= sizeof (UINT32)) && - ((Prop[2] & Prop2) != 0)) { - mDllCharacteristicsEx |= EFI_IMAGE_DLLCHARACTERISTICS_EX_FORWARD_CFI_COMPAT; - } - } -} - -// -// Elf functions interface implementation -// - -STATIC -VOID -ScanSections64 ( - VOID - ) -{ - UINT32 i; - EFI_IMAGE_DOS_HEADER *DosHdr; - EFI_IMAGE_OPTIONAL_HEADER_UNION *NtHdr; - UINT32 CoffEntry; - UINT32 SectionCount; - BOOLEAN FoundSection; - UINT32 Offset; - - CoffEntry = 0; - mCoffOffset = 0; - - // - // Coff file start with a DOS header. - // - mCoffOffset = sizeof(EFI_IMAGE_DOS_HEADER) + 0x40; - mNtHdrOffset = mCoffOffset; - switch (mEhdr->e_machine) { - case EM_X86_64: - case EM_AARCH64: - case EM_RISCV64: - case EM_LOONGARCH: - mCoffOffset += sizeof (EFI_IMAGE_NT_HEADERS64); - break; - default: - VerboseMsg ("%s unknown e_machine type %hu. Assume X64", mInImageName, mEhdr->e_machine); - mCoffOffset += sizeof (EFI_IMAGE_NT_HEADERS64); - break; - } - - mTableOffset = mCoffOffset; - mCoffOffset += mCoffNbrSections * sizeof(EFI_IMAGE_SECTION_HEADER); - - // - // Set mCoffAlignment to the maximum alignment of the input sections - // we care about - // - for (i = 0; i < mEhdr->e_shnum; i++) { - Elf_Shdr *shdr = GetShdrByIndex(i); - if (shdr->sh_addralign <= mCoffAlignment) { - continue; - } - if (IsTextShdr(shdr) || IsDataShdr(shdr) || IsHiiRsrcShdr(shdr)) { - mCoffAlignment = (UINT32)shdr->sh_addralign; - } - } - - for (i = 0; i < mEhdr->e_shnum; i++) { - Elf_Shdr *shdr = GetShdrByIndex(i); - if (shdr->sh_type == SHT_NOTE) { - ParseNoteSection (shdr); - } - } - - // - // Check if mCoffAlignment is larger than MAX_COFF_ALIGNMENT - // - if (mCoffAlignment > MAX_COFF_ALIGNMENT) { - Error (NULL, 0, 3000, "Invalid", "Section alignment is larger than MAX_COFF_ALIGNMENT."); - assert (FALSE); - } - - - // - // Move the PE/COFF header right before the first section. This will help us - // save space when converting to TE. - // - if (mCoffAlignment > mCoffOffset) { - mNtHdrOffset += mCoffAlignment - mCoffOffset; - mTableOffset += mCoffAlignment - mCoffOffset; - mCoffOffset = mCoffAlignment; - } - - // - // First text sections. - // - mCoffOffset = CoffAlign(mCoffOffset); - mTextOffset = mCoffOffset; - FoundSection = FALSE; - SectionCount = 0; - for (i = 0; i < mEhdr->e_shnum; i++) { - Elf_Shdr *shdr = GetShdrByIndex(i); - if (IsTextShdr(shdr)) { - if ((shdr->sh_addralign != 0) && (shdr->sh_addralign != 1)) { - // the alignment field is valid - if ((shdr->sh_addr & (shdr->sh_addralign - 1)) == 0) { - // if the section address is aligned we must align PE/COFF - mCoffOffset = (UINT32) ((mCoffOffset + shdr->sh_addralign - 1) & ~(shdr->sh_addralign - 1)); - } else { - Error (NULL, 0, 3000, "Invalid", "Section address not aligned to its own alignment."); - } - } - - /* Relocate entry. */ - if ((mEhdr->e_entry >= shdr->sh_addr) && - (mEhdr->e_entry < shdr->sh_addr + shdr->sh_size)) { - CoffEntry = (UINT32) (mCoffOffset + mEhdr->e_entry - shdr->sh_addr); - } - - // - // Set mTextOffset with the offset of the first '.text' section - // - if (!FoundSection) { - mTextOffset = mCoffOffset; - FoundSection = TRUE; - } - - mCoffSectionsOffset[i] = mCoffOffset; - mCoffOffset += (UINT32) shdr->sh_size; - SectionCount ++; - } - } - - if (!FoundSection && mOutImageType != FW_ACPI_IMAGE) { - Error (NULL, 0, 3000, "Invalid", "Did not find any '.text' section."); - assert (FALSE); - } - - mDebugOffset = DebugRvaAlign(mCoffOffset); - mCoffOffset = CoffAlign(mCoffOffset); - - if (SectionCount > 1 && mOutImageType == FW_EFI_IMAGE) { - Warning (NULL, 0, 0, NULL, "Multiple sections in %s are merged into 1 text section. Source level debug might not work correctly.", mInImageName); - } - - // - // Then data sections. - // - mDataOffset = mCoffOffset; - FoundSection = FALSE; - SectionCount = 0; - for (i = 0; i < mEhdr->e_shnum; i++) { - Elf_Shdr *shdr = GetShdrByIndex(i); - if (IsDataShdr(shdr)) { - if ((shdr->sh_addralign != 0) && (shdr->sh_addralign != 1)) { - // the alignment field is valid - if ((shdr->sh_addr & (shdr->sh_addralign - 1)) == 0) { - // if the section address is aligned we must align PE/COFF - mCoffOffset = (UINT32) ((mCoffOffset + shdr->sh_addralign - 1) & ~(shdr->sh_addralign - 1)); - } else { - Error (NULL, 0, 3000, "Invalid", "Section address not aligned to its own alignment."); - } - } - - // - // Set mDataOffset with the offset of the first '.data' section - // - if (!FoundSection) { - mDataOffset = mCoffOffset; - FoundSection = TRUE; - } - mCoffSectionsOffset[i] = mCoffOffset; - mCoffOffset += (UINT32) shdr->sh_size; - SectionCount ++; - } - } - - // - // Make room for .debug data in .data (or .text if .data is empty) instead of - // putting it in a section of its own. This is explicitly allowed by the - // PE/COFF spec, and prevents bloat in the binary when using large values for - // section alignment. - // - if (SectionCount > 0) { - mDebugOffset = DebugRvaAlign(mCoffOffset); - } - mCoffOffset = mDebugOffset + sizeof(EFI_IMAGE_DEBUG_DIRECTORY_ENTRY) + - sizeof(EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY) + - strlen(mInImageName) + 1; - - // - // Add more space in the .debug data region for the DllCharacteristicsEx - // field. - // - if (mDllCharacteristicsEx != 0) { - mCoffOffset = DebugRvaAlign(mCoffOffset) + - sizeof (EFI_IMAGE_DEBUG_DIRECTORY_ENTRY) + - sizeof (EFI_IMAGE_DEBUG_EX_DLLCHARACTERISTICS_ENTRY); - } - - mCoffOffset = CoffAlign(mCoffOffset); - if (SectionCount == 0) { - mDataOffset = mCoffOffset; - } - - if (SectionCount > 1 && mOutImageType == FW_EFI_IMAGE) { - Warning (NULL, 0, 0, NULL, "Multiple sections in %s are merged into 1 data section. Source level debug might not work correctly.", mInImageName); - } - - // - // The Symbol sections. - // - if (mExportFlag) { - UINT32 SymIndex; - Elf_Sym *Sym; - UINT64 SymNum; - const UINT8 *SymName; - - mExportOffset = mCoffOffset; - mExportSize = sizeof(EFI_IMAGE_EXPORT_DIRECTORY) + strlen(mInImageName) + 1; - - for (i = 0; i < mEhdr->e_shnum; i++) { - - // - // Determine if this is a symbol section. - // - Elf_Shdr *shdr = GetShdrByIndex(i); - if (!IsSymbolShdr(shdr)) { - continue; - } - - UINT8 *Symtab = (UINT8*)mEhdr + shdr->sh_offset; - SymNum = (shdr->sh_size) / (shdr->sh_entsize); - - // - // First Get PrmModuleExportDescriptor - // - for (SymIndex = 0; SymIndex < SymNum; SymIndex++) { - Sym = (Elf_Sym *)(Symtab + SymIndex * shdr->sh_entsize); - SymName = GetSymName(Sym); - if (SymName == NULL) { - continue; - } - - if (strcmp((CHAR8*)SymName, PRM_MODULE_EXPORT_DESCRIPTOR_NAME) == 0) { - // - // Find PrmHandler Number and Name - // - FindPrmHandler(Sym->st_value); - - strcpy(mExportSymName[mExportSymNum], (CHAR8*)SymName); - mExportRVA[mExportSymNum] = (UINT32)(Sym->st_value); - mExportSize += 2 * EFI_IMAGE_EXPORT_ADDR_SIZE + EFI_IMAGE_EXPORT_ORDINAL_SIZE + strlen((CHAR8 *)SymName) + 1; - mExportSymNum ++; - break; - } - } - - // - // Second Get PrmHandler - // - for (SymIndex = 0; SymIndex < SymNum; SymIndex++) { - UINT32 ExpIndex; - Sym = (Elf_Sym *)(Symtab + SymIndex * shdr->sh_entsize); - SymName = GetSymName(Sym); - if (SymName == NULL) { - continue; - } - - for (ExpIndex = 0; ExpIndex < (mExportSymNum -1); ExpIndex++) { - if (strcmp((CHAR8*)SymName, mExportSymName[ExpIndex]) != 0) { - continue; - } - mExportRVA[ExpIndex] = (UINT32)(Sym->st_value); - mExportSize += 2 * EFI_IMAGE_EXPORT_ADDR_SIZE + EFI_IMAGE_EXPORT_ORDINAL_SIZE + strlen((CHAR8 *)SymName) + 1; - } - } - - break; - } - - mCoffOffset += mExportSize; - mCoffOffset = CoffAlign(mCoffOffset); - } - - // - // The HII resource sections. - // - mHiiRsrcOffset = mCoffOffset; - for (i = 0; i < mEhdr->e_shnum; i++) { - Elf_Shdr *shdr = GetShdrByIndex(i); - if (IsHiiRsrcShdr(shdr)) { - if ((shdr->sh_addralign != 0) && (shdr->sh_addralign != 1)) { - // the alignment field is valid - if ((shdr->sh_addr & (shdr->sh_addralign - 1)) == 0) { - // if the section address is aligned we must align PE/COFF - mCoffOffset = (UINT32) ((mCoffOffset + shdr->sh_addralign - 1) & ~(shdr->sh_addralign - 1)); - } else { - Error (NULL, 0, 3000, "Invalid", "Section address not aligned to its own alignment."); - } - } - if (shdr->sh_size != 0) { - mHiiRsrcOffset = mCoffOffset; - mCoffSectionsOffset[i] = mCoffOffset; - mCoffOffset += (UINT32) shdr->sh_size; - mCoffOffset = CoffAlign(mCoffOffset); - SetHiiResourceHeader ((UINT8*) mEhdr + shdr->sh_offset, mHiiRsrcOffset); - } - break; - } - } - - mRelocOffset = mCoffOffset; - - // - // Allocate base Coff file. Will be expanded later for relocations. - // - mCoffFile = (UINT8 *)malloc(mCoffOffset); - if (mCoffFile == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - } - assert (mCoffFile != NULL); - memset(mCoffFile, 0, mCoffOffset); - - // - // Fill headers. - // - DosHdr = (EFI_IMAGE_DOS_HEADER *)mCoffFile; - DosHdr->e_magic = EFI_IMAGE_DOS_SIGNATURE; - DosHdr->e_lfanew = mNtHdrOffset; - - NtHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION*)(mCoffFile + mNtHdrOffset); - - NtHdr->Pe32Plus.Signature = EFI_IMAGE_NT_SIGNATURE; - - switch (mEhdr->e_machine) { - case EM_X86_64: - NtHdr->Pe32Plus.FileHeader.Machine = IMAGE_FILE_MACHINE_X64; - NtHdr->Pe32Plus.OptionalHeader.Magic = EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC; - break; - case EM_AARCH64: - NtHdr->Pe32Plus.FileHeader.Machine = IMAGE_FILE_MACHINE_ARM64; - NtHdr->Pe32Plus.OptionalHeader.Magic = EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC; - break; - case EM_RISCV64: - NtHdr->Pe32Plus.FileHeader.Machine = IMAGE_FILE_MACHINE_RISCV64; - NtHdr->Pe32Plus.OptionalHeader.Magic = EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC; - break; - case EM_LOONGARCH: - NtHdr->Pe32Plus.FileHeader.Machine = IMAGE_FILE_MACHINE_LOONGARCH64; - NtHdr->Pe32Plus.OptionalHeader.Magic = EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC; - break; - - default: - VerboseMsg ("%u unknown e_machine type. Assume X64", (UINTN)mEhdr->e_machine); - NtHdr->Pe32Plus.FileHeader.Machine = IMAGE_FILE_MACHINE_X64; - NtHdr->Pe32Plus.OptionalHeader.Magic = EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC; - } - - NtHdr->Pe32Plus.FileHeader.NumberOfSections = mCoffNbrSections; - NtHdr->Pe32Plus.FileHeader.TimeDateStamp = (UINT32) time(NULL); - mImageTimeStamp = NtHdr->Pe32Plus.FileHeader.TimeDateStamp; - NtHdr->Pe32Plus.FileHeader.PointerToSymbolTable = 0; - NtHdr->Pe32Plus.FileHeader.NumberOfSymbols = 0; - NtHdr->Pe32Plus.FileHeader.SizeOfOptionalHeader = sizeof(NtHdr->Pe32Plus.OptionalHeader); - NtHdr->Pe32Plus.FileHeader.Characteristics = EFI_IMAGE_FILE_EXECUTABLE_IMAGE - | EFI_IMAGE_FILE_LINE_NUMS_STRIPPED - | EFI_IMAGE_FILE_LOCAL_SYMS_STRIPPED - | EFI_IMAGE_FILE_LARGE_ADDRESS_AWARE; - - NtHdr->Pe32Plus.OptionalHeader.SizeOfCode = mDataOffset - mTextOffset; - NtHdr->Pe32Plus.OptionalHeader.SizeOfInitializedData = mRelocOffset - mDataOffset; - NtHdr->Pe32Plus.OptionalHeader.SizeOfUninitializedData = 0; - NtHdr->Pe32Plus.OptionalHeader.AddressOfEntryPoint = CoffEntry; - - NtHdr->Pe32Plus.OptionalHeader.BaseOfCode = mTextOffset; - - NtHdr->Pe32Plus.OptionalHeader.ImageBase = 0; - NtHdr->Pe32Plus.OptionalHeader.SectionAlignment = mCoffAlignment; - NtHdr->Pe32Plus.OptionalHeader.FileAlignment = mCoffAlignment; - NtHdr->Pe32Plus.OptionalHeader.SizeOfImage = 0; - - NtHdr->Pe32Plus.OptionalHeader.SizeOfHeaders = mTextOffset; - NtHdr->Pe32Plus.OptionalHeader.NumberOfRvaAndSizes = EFI_IMAGE_NUMBER_OF_DIRECTORY_ENTRIES; - - // - // Section headers. - // - if ((mDataOffset - mTextOffset) > 0) { - CreateSectionHeader (".text", mTextOffset, mDataOffset - mTextOffset, - EFI_IMAGE_SCN_CNT_CODE - | EFI_IMAGE_SCN_MEM_EXECUTE - | EFI_IMAGE_SCN_MEM_READ); - } else { - // Don't make a section of size 0. - NtHdr->Pe32Plus.FileHeader.NumberOfSections--; - } - - // - // If found symbol, add edata section between data and rsrc section - // - if(mExportFlag) { - Offset = mExportOffset; - } else { - Offset = mHiiRsrcOffset; - } - - if ((mHiiRsrcOffset - mDataOffset) > 0) { - CreateSectionHeader (".data", mDataOffset, Offset - mDataOffset, - EFI_IMAGE_SCN_CNT_INITIALIZED_DATA - | EFI_IMAGE_SCN_MEM_WRITE - | EFI_IMAGE_SCN_MEM_READ); - } else { - // Don't make a section of size 0. - NtHdr->Pe32Plus.FileHeader.NumberOfSections--; - } - - if(mExportFlag) { - if ((mHiiRsrcOffset - mExportOffset) > 0) { - CreateSectionHeader (".edata", mExportOffset, mHiiRsrcOffset - mExportOffset, - EFI_IMAGE_SCN_CNT_INITIALIZED_DATA - | EFI_IMAGE_SCN_MEM_READ); - NtHdr->Pe32Plus.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXPORT].Size = mHiiRsrcOffset - mExportOffset; - NtHdr->Pe32Plus.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress = mExportOffset; - - } else { - // Don't make a section of size 0. - NtHdr->Pe32Plus.FileHeader.NumberOfSections--; - } - } - - if ((mRelocOffset - mHiiRsrcOffset) > 0) { - CreateSectionHeader (".rsrc", mHiiRsrcOffset, mRelocOffset - mHiiRsrcOffset, - EFI_IMAGE_SCN_CNT_INITIALIZED_DATA - | EFI_IMAGE_SCN_MEM_READ); - - NtHdr->Pe32Plus.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].Size = mRelocOffset - mHiiRsrcOffset; - NtHdr->Pe32Plus.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress = mHiiRsrcOffset; - } else { - // Don't make a section of size 0. - NtHdr->Pe32Plus.FileHeader.NumberOfSections--; - } - -} - -STATIC -BOOLEAN -WriteSections64 ( - SECTION_FILTER_TYPES FilterType - ) -{ - UINT32 Idx; - Elf_Shdr *SecShdr; - UINT32 SecOffset; - BOOLEAN (*Filter)(Elf_Shdr *); - Elf64_Addr GOTEntryRva; - - // - // Initialize filter pointer - // - switch (FilterType) { - case SECTION_TEXT: - Filter = IsTextShdr; - break; - case SECTION_HII: - Filter = IsHiiRsrcShdr; - break; - case SECTION_DATA: - Filter = IsDataShdr; - break; - default: - return FALSE; - } - - // - // First: copy sections. - // - for (Idx = 0; Idx < mEhdr->e_shnum; Idx++) { - Elf_Shdr *Shdr = GetShdrByIndex(Idx); - if ((*Filter)(Shdr)) { - switch (Shdr->sh_type) { - case SHT_PROGBITS: - /* Copy. */ - if (Shdr->sh_offset + Shdr->sh_size > mFileBufferSize) { - return FALSE; - } - memcpy(mCoffFile + mCoffSectionsOffset[Idx], - (UINT8*)mEhdr + Shdr->sh_offset, - (size_t) Shdr->sh_size); - break; - - case SHT_NOBITS: - memset(mCoffFile + mCoffSectionsOffset[Idx], 0, (size_t) Shdr->sh_size); - break; - - default: - // - // Ignore for unknown section type. - // - VerboseMsg ("%s unknown section type %x. We ignore this unknown section type.", mInImageName, (unsigned)Shdr->sh_type); - break; - } - } - } - - // - // Second: apply relocations. - // - VerboseMsg ("Applying Relocations..."); - for (Idx = 0; Idx < mEhdr->e_shnum; Idx++) { - // - // Determine if this is a relocation section. - // - Elf_Shdr *RelShdr = GetShdrByIndex(Idx); - if ((RelShdr->sh_type != SHT_REL) && (RelShdr->sh_type != SHT_RELA)) { - continue; - } - - // - // If this is a ET_DYN (PIE) executable, we will encounter a dynamic SHT_RELA - // section that applies to the entire binary, and which will have its section - // index set to #0 (which is a NULL section with the SHF_ALLOC bit cleared). - // - // In the absence of GOT based relocations, - // this RELA section will contain redundant R_xxx_RELATIVE relocations, one - // for every R_xxx_xx64 relocation appearing in the per-section RELA sections. - // (i.e., .rela.text and .rela.data) - // - if (RelShdr->sh_info == 0) { - continue; - } - - // - // Relocation section found. Now extract section information that the relocations - // apply to in the ELF data and the new COFF data. - // - SecShdr = GetShdrByIndex(RelShdr->sh_info); - SecOffset = mCoffSectionsOffset[RelShdr->sh_info]; - - // - // Only process relocations for the current filter type. - // - if (RelShdr->sh_type == SHT_RELA && (*Filter)(SecShdr)) { - UINT64 RelIdx; - - // - // Determine the symbol table referenced by the relocation data. - // - Elf_Shdr *SymtabShdr = GetShdrByIndex(RelShdr->sh_link); - UINT8 *Symtab = (UINT8*)mEhdr + SymtabShdr->sh_offset; - - // - // Process all relocation entries for this section. - // - for (RelIdx = 0; RelIdx < RelShdr->sh_size; RelIdx += (UINT32) RelShdr->sh_entsize) { - - // - // Set pointer to relocation entry - // - Elf_Rela *Rel = (Elf_Rela *)((UINT8*)mEhdr + RelShdr->sh_offset + RelIdx); - - // - // Set pointer to symbol table entry associated with the relocation entry. - // - Elf_Sym *Sym = (Elf_Sym *)(Symtab + ELF_R_SYM(Rel->r_info) * SymtabShdr->sh_entsize); - - Elf_Shdr *SymShdr; - UINT8 *Targ; - - // - // The _GLOBAL_OFFSET_TABLE_ symbol is not actually an absolute symbol, - // but carries the SHN_ABS section index for historical reasons. - // It must be accompanied by a R_*_GOT_* type relocation on a - // subsequent instruction, which we handle below, specifically to avoid - // the GOT indirection, and to refer to the symbol directly. This means - // we can simply disregard direct references to the GOT symbol itself, - // as the resulting value will never be used. - // - if (Sym->st_shndx == SHN_ABS) { - const UINT8 *SymName = GetSymName (Sym); - if (strcmp ((CHAR8 *)SymName, "_GLOBAL_OFFSET_TABLE_") == 0) { - continue; - } - } - - // - // Check section header index found in symbol table and get the section - // header location. - // - if (Sym->st_shndx == SHN_UNDEF - || Sym->st_shndx >= mEhdr->e_shnum) { - const UINT8 *SymName = GetSymName(Sym); - if (SymName == NULL) { - SymName = (const UINT8 *)""; - } - - // - // Skip error on EM_RISCV64 and EM_LOONGARCH because no symbol name is built - // from RISC-V and LoongArch toolchain. - // - if ((mEhdr->e_machine != EM_RISCV64) && (mEhdr->e_machine != EM_LOONGARCH)) { - Error (NULL, 0, 3000, "Invalid", - "%s: Bad definition for symbol '%s'@%#llx or unsupported symbol type. " - "For example, absolute and undefined symbols are not supported.", - mInImageName, SymName, Sym->st_value); - - exit(EXIT_FAILURE); - } - continue; - } - SymShdr = GetShdrByIndex(Sym->st_shndx); - - // - // Convert the relocation data to a pointer into the coff file. - // - // Note: - // r_offset is the virtual address of the storage unit to be relocated. - // sh_addr is the virtual address for the base of the section. - // - // r_offset in a memory address. - // Convert it to a pointer in the coff file. - // - Targ = mCoffFile + SecOffset + (Rel->r_offset - SecShdr->sh_addr); - - // - // Determine how to handle each relocation type based on the machine type. - // - if (mEhdr->e_machine == EM_X86_64) { - switch (ELF_R_TYPE(Rel->r_info)) { - case R_X86_64_NONE: - break; - case R_X86_64_64: - // - // Absolute relocation. - // - VerboseMsg ("R_X86_64_64"); - VerboseMsg ("Offset: 0x%08X, Addend: 0x%016LX", - (UINT32)(SecOffset + (Rel->r_offset - SecShdr->sh_addr)), - *(UINT64 *)Targ); - *(UINT64 *)Targ = *(UINT64 *)Targ - SymShdr->sh_addr + mCoffSectionsOffset[Sym->st_shndx]; - VerboseMsg ("Relocation: 0x%016LX", *(UINT64*)Targ); - break; - case R_X86_64_32: - VerboseMsg ("R_X86_64_32"); - VerboseMsg ("Offset: 0x%08X, Addend: 0x%08X", - (UINT32)(SecOffset + (Rel->r_offset - SecShdr->sh_addr)), - *(UINT32 *)Targ); - *(UINT32 *)Targ = (UINT32)((UINT64)(*(UINT32 *)Targ) - SymShdr->sh_addr + mCoffSectionsOffset[Sym->st_shndx]); - VerboseMsg ("Relocation: 0x%08X", *(UINT32*)Targ); - break; - case R_X86_64_32S: - VerboseMsg ("R_X86_64_32S"); - VerboseMsg ("Offset: 0x%08X, Addend: 0x%08X", - (UINT32)(SecOffset + (Rel->r_offset - SecShdr->sh_addr)), - *(UINT32 *)Targ); - *(INT32 *)Targ = (INT32)((INT64)(*(INT32 *)Targ) - SymShdr->sh_addr + mCoffSectionsOffset[Sym->st_shndx]); - VerboseMsg ("Relocation: 0x%08X", *(UINT32*)Targ); - break; - - case R_X86_64_PLT32: - // - // Treat R_X86_64_PLT32 relocations as R_X86_64_PC32: this is - // possible since we know all code symbol references resolve to - // definitions in the same module (UEFI has no shared libraries), - // and so there is never a reason to jump via a PLT entry, - // allowing us to resolve the reference using the symbol directly. - // - VerboseMsg ("Treating R_X86_64_PLT32 as R_X86_64_PC32 ..."); - /* fall through */ - case R_X86_64_PC32: - // - // Relative relocation: Symbol - Ip + Addend - // - VerboseMsg ("R_X86_64_PC32"); - VerboseMsg ("Offset: 0x%08X, Addend: 0x%08X", - (UINT32)(SecOffset + (Rel->r_offset - SecShdr->sh_addr)), - *(UINT32 *)Targ); - *(UINT32 *)Targ = (UINT32) (*(UINT32 *)Targ - + (mCoffSectionsOffset[Sym->st_shndx] - SymShdr->sh_addr) - - (SecOffset - SecShdr->sh_addr)); - VerboseMsg ("Relocation: 0x%08X", *(UINT32 *)Targ); - break; - case R_X86_64_GOTPCREL: - case R_X86_64_GOTPCRELX: - case R_X86_64_REX_GOTPCRELX: - VerboseMsg ("R_X86_64_GOTPCREL family"); - VerboseMsg ("Offset: 0x%08X, Addend: 0x%08X", - (UINT32)(SecOffset + (Rel->r_offset - SecShdr->sh_addr)), - *(UINT32 *)Targ); - GOTEntryRva = Rel->r_offset - Rel->r_addend + *(INT32 *)Targ; - FindElfGOTSectionFromGOTEntryElfRva(GOTEntryRva); - *(UINT32 *)Targ = (UINT32) (*(UINT32 *)Targ - + (mCoffSectionsOffset[mGOTShindex] - mGOTShdr->sh_addr) - - (SecOffset - SecShdr->sh_addr)); - VerboseMsg ("Relocation: 0x%08X", *(UINT32 *)Targ); - GOTEntryRva += (mCoffSectionsOffset[mGOTShindex] - mGOTShdr->sh_addr); // ELF Rva -> COFF Rva - if (AccumulateCoffGOTEntries((UINT32)GOTEntryRva)) { - // - // Relocate GOT entry if it's the first time we run into it - // - Targ = mCoffFile + GOTEntryRva; - // - // Limitation: The following three statements assume memory - // at *Targ is valid because the section containing the GOT - // has already been copied from the ELF image to the Coff image. - // This pre-condition presently holds because the GOT is placed - // in section .text, and the ELF text sections are all copied - // prior to reaching this point. - // If the pre-condition is violated in the future, this fixup - // either needs to be deferred after the GOT section is copied - // to the Coff image, or the fixup should be performed on the - // source Elf image instead of the destination Coff image. - // - VerboseMsg ("Offset: 0x%08X, Addend: 0x%016LX", - (UINT32)GOTEntryRva, - *(UINT64 *)Targ); - *(UINT64 *)Targ = *(UINT64 *)Targ - SymShdr->sh_addr + mCoffSectionsOffset[Sym->st_shndx]; - VerboseMsg ("Relocation: 0x%016LX", *(UINT64*)Targ); - } - break; - default: - Error (NULL, 0, 3000, "Invalid", "%s unsupported ELF EM_X86_64 relocation 0x%x.", mInImageName, (unsigned) ELF_R_TYPE(Rel->r_info)); - } - } else if (mEhdr->e_machine == EM_AARCH64) { - - switch (ELF_R_TYPE(Rel->r_info)) { - INT64 Offset; - - case R_AARCH64_LD64_GOTOFF_LO15: - case R_AARCH64_LD64_GOTPAGE_LO15: - // - // Convert into an ADR instruction that refers to the symbol directly. - // - Offset = Sym->st_value - Rel->r_offset; - - *(UINT32 *)Targ &= 0x1000001f; - *(UINT32 *)Targ |= ((Offset & 0x1ffffc) << (5 - 2)) | ((Offset & 0x3) << 29); - - if (Offset < -0x100000 || Offset > 0xfffff) { - Error (NULL, 0, 3000, "Invalid", "WriteSections64(): %s failed to relax GOT based symbol reference - image is too big (>1 MiB).", - mInImageName); - break; - } - break; - - case R_AARCH64_LD64_GOT_LO12_NC: - // - // Convert into an ADD instruction - see R_AARCH64_ADR_GOT_PAGE below. - // - *(UINT32 *)Targ &= 0x3ff; - *(UINT32 *)Targ |= 0x91000000 | ((Sym->st_value & 0xfff) << 10); - break; - - case R_AARCH64_ADR_GOT_PAGE: - // - // This relocation points to the GOT entry that contains the absolute - // address of the symbol we are referring to. Since EDK2 only uses - // fully linked binaries, we can avoid the indirection, and simply - // refer to the symbol directly. This implies having to patch the - // subsequent LDR instruction (covered by a R_AARCH64_LD64_GOT_LO12_NC - // relocation) into an ADD instruction - this is handled above. - // - // In order to handle Cortex-A53 erratum #843419, the GCC toolchain - // may convert an ADRP instruction at the end of a page (0xffc - // offset) into an ADR instruction. If so, be sure to calculate the - // offset for an ADR instead of ADRP. - // - if ((*(UINT32 *)Targ & BIT31) == 0) { - // - // Calculate the offset for an ADR. - // - Offset = (Sym->st_value & ~0xfff) - Rel->r_offset; - if (Offset < -0x100000 || Offset > 0xfffff) { - Error (NULL, 0, 3000, "Invalid", "WriteSections64(): %s due to its size (> 1 MB), unable to relocate ADR.", - mInImageName); - break; - } - } else { - // - // Calculate the offset for an ADRP. - // - Offset = (Sym->st_value - (Rel->r_offset & ~0xfff)) >> 12; - } - - *(UINT32 *)Targ &= 0x9000001f; - *(UINT32 *)Targ |= ((Offset & 0x1ffffc) << (5 - 2)) | ((Offset & 0x3) << 29); - - /* fall through */ - - case R_AARCH64_ADR_PREL_PG_HI21: - // - // In order to handle Cortex-A53 erratum #843419, the LD linker may - // convert ADRP instructions into ADR instructions, but without - // updating the static relocation type, and so we may end up here - // while the instruction in question is actually ADR. So let's - // just disregard it: the section offset check we apply below to - // ADR instructions will trigger for its R_AARCH64_xxx_ABS_LO12_NC - // companion instruction as well, so it is safe to omit it here. - // - if ((*(UINT32 *)Targ & BIT31) == 0) { - break; - } - - // - // AArch64 PG_H21 relocations are typically paired with ABS_LO12 - // relocations, where a PC-relative reference with +/- 4 GB range is - // split into a relative high part and an absolute low part. Since - // the absolute low part represents the offset into a 4 KB page, we - // either have to convert the ADRP into an ADR instruction, or we - // need to use a section alignment of at least 4 KB, so that the - // binary appears at a correct offset at runtime. In any case, we - // have to make sure that the 4 KB relative offsets of both the - // section containing the reference as well as the section to which - // it refers have not been changed during PE/COFF conversion (i.e., - // in ScanSections64() above). - // - if (mCoffAlignment < 0x1000) { - // - // Attempt to convert the ADRP into an ADR instruction. - // This is only possible if the symbol is within +/- 1 MB. - // - - // Decode the ADRP instruction - Offset = (INT32)((*(UINT32 *)Targ & 0xffffe0) << 8); - Offset = (Offset << (6 - 5)) | ((*(UINT32 *)Targ & 0x60000000) >> (29 - 12)); - - // - // ADRP offset is relative to the previous page boundary, - // whereas ADR offset is relative to the instruction itself. - // So fix up the offset so it points to the page containing - // the symbol. - // - Offset -= (UINTN)(Targ - mCoffFile) & 0xfff; - - if (Offset < -0x100000 || Offset > 0xfffff) { - Error (NULL, 0, 3000, "Invalid", "WriteSections64(): %s due to its size (> 1 MB), this module requires 4 KB section alignment.", - mInImageName); - break; - } - - // Re-encode the offset as an ADR instruction - *(UINT32 *)Targ &= 0x1000001f; - *(UINT32 *)Targ |= ((Offset & 0x1ffffc) << (5 - 2)) | ((Offset & 0x3) << 29); - } - /* fall through */ - - case R_AARCH64_ADD_ABS_LO12_NC: - case R_AARCH64_LDST8_ABS_LO12_NC: - case R_AARCH64_LDST16_ABS_LO12_NC: - case R_AARCH64_LDST32_ABS_LO12_NC: - case R_AARCH64_LDST64_ABS_LO12_NC: - case R_AARCH64_LDST128_ABS_LO12_NC: - if (((SecShdr->sh_addr ^ SecOffset) & 0xfff) != 0 || - ((SymShdr->sh_addr ^ mCoffSectionsOffset[Sym->st_shndx]) & 0xfff) != 0) { - Error (NULL, 0, 3000, "Invalid", "WriteSections64(): %s AARCH64 small code model requires identical ELF and PE/COFF section offsets modulo 4 KB.", - mInImageName); - break; - } - /* fall through */ - - case R_AARCH64_ADR_PREL_LO21: - case R_AARCH64_CONDBR19: - case R_AARCH64_LD_PREL_LO19: - case R_AARCH64_CALL26: - case R_AARCH64_JUMP26: - case R_AARCH64_PREL64: - case R_AARCH64_PREL32: - case R_AARCH64_PREL16: - // - // The GCC toolchains (i.e., binutils) may corrupt section relative - // relocations when emitting relocation sections into fully linked - // binaries. More specifically, they tend to fail to take into - // account the fact that a '.rodata + XXX' relocation needs to have - // its addend recalculated once .rodata is merged into the .text - // section, and the relocation emitted into the .rela.text section. - // - // We cannot really recover from this loss of information, so the - // only workaround is to prevent having to recalculate any relative - // relocations at all, by using a linker script that ensures that - // the offset between the Place and the Symbol is the same in both - // the ELF and the PE/COFF versions of the binary. - // - if ((SymShdr->sh_addr - SecShdr->sh_addr) != - (mCoffSectionsOffset[Sym->st_shndx] - SecOffset)) { - Error (NULL, 0, 3000, "Invalid", "WriteSections64(): %s AARCH64 relative relocations require identical ELF and PE/COFF section offsets", - mInImageName); - } - break; - - // Absolute relocations. - case R_AARCH64_ABS64: - *(UINT64 *)Targ = *(UINT64 *)Targ - SymShdr->sh_addr + mCoffSectionsOffset[Sym->st_shndx]; - break; - - default: - Error (NULL, 0, 3000, "Invalid", "WriteSections64(): %s unsupported ELF EM_AARCH64 relocation 0x%x.", mInImageName, (unsigned) ELF_R_TYPE(Rel->r_info)); - } - } else if (mEhdr->e_machine == EM_RISCV64) { - // - // Write section for RISC-V 64 architecture. - // - WriteSectionRiscV64 (Rel, Targ, SymShdr, Sym); - } else if (mEhdr->e_machine == EM_LOONGARCH) { - switch (ELF_R_TYPE(Rel->r_info)) { - INT64 Offset; - INT32 Lo, Hi; - - case R_LARCH_SOP_PUSH_ABSOLUTE: - // - // Absolute relocation. - // - *(UINT64 *)Targ = *(UINT64 *)Targ - SymShdr->sh_addr + mCoffSectionsOffset[Sym->st_shndx]; - break; - - case R_LARCH_MARK_LA: - case R_LARCH_64: - case R_LARCH_NONE: - case R_LARCH_32: - case R_LARCH_RELATIVE: - case R_LARCH_COPY: - case R_LARCH_JUMP_SLOT: - case R_LARCH_TLS_DTPMOD32: - case R_LARCH_TLS_DTPMOD64: - case R_LARCH_TLS_DTPREL32: - case R_LARCH_TLS_DTPREL64: - case R_LARCH_TLS_TPREL32: - case R_LARCH_TLS_TPREL64: - case R_LARCH_IRELATIVE: - case R_LARCH_MARK_PCREL: - case R_LARCH_SOP_PUSH_PCREL: - case R_LARCH_SOP_PUSH_DUP: - case R_LARCH_SOP_PUSH_GPREL: - case R_LARCH_SOP_PUSH_TLS_TPREL: - case R_LARCH_SOP_PUSH_TLS_GOT: - case R_LARCH_SOP_PUSH_TLS_GD: - case R_LARCH_SOP_PUSH_PLT_PCREL: - case R_LARCH_SOP_ASSERT: - case R_LARCH_SOP_NOT: - case R_LARCH_SOP_SUB: - case R_LARCH_SOP_SL: - case R_LARCH_SOP_SR: - case R_LARCH_SOP_ADD: - case R_LARCH_SOP_AND: - case R_LARCH_SOP_IF_ELSE: - case R_LARCH_SOP_POP_32_S_10_5: - case R_LARCH_SOP_POP_32_U_10_12: - case R_LARCH_SOP_POP_32_S_10_12: - case R_LARCH_SOP_POP_32_S_10_16: - case R_LARCH_SOP_POP_32_S_10_16_S2: - case R_LARCH_SOP_POP_32_S_5_20: - case R_LARCH_SOP_POP_32_S_0_5_10_16_S2: - case R_LARCH_SOP_POP_32_S_0_10_10_16_S2: - case R_LARCH_SOP_POP_32_U: - case R_LARCH_ADD8: - case R_LARCH_ADD16: - case R_LARCH_ADD24: - case R_LARCH_ADD32: - case R_LARCH_ADD64: - case R_LARCH_SUB8: - case R_LARCH_SUB16: - case R_LARCH_SUB24: - case R_LARCH_SUB32: - case R_LARCH_SUB64: - case R_LARCH_GNU_VTINHERIT: - case R_LARCH_GNU_VTENTRY: - case R_LARCH_B16: - case R_LARCH_B21: - case R_LARCH_B26: - case R_LARCH_ABS_HI20: - case R_LARCH_ABS_LO12: - case R_LARCH_ABS64_LO20: - case R_LARCH_ABS64_HI12: - case R_LARCH_PCALA_LO12: - case R_LARCH_PCALA64_LO20: - case R_LARCH_PCALA64_HI12: - case R_LARCH_GOT_PC_LO12: - case R_LARCH_GOT64_PC_LO20: - case R_LARCH_GOT64_PC_HI12: - case R_LARCH_GOT64_HI20: - case R_LARCH_GOT64_LO12: - case R_LARCH_GOT64_LO20: - case R_LARCH_GOT64_HI12: - case R_LARCH_TLS_LE_HI20: - case R_LARCH_TLS_LE_LO12: - case R_LARCH_TLS_LE64_LO20: - case R_LARCH_TLS_LE64_HI12: - case R_LARCH_TLS_IE_PC_HI20: - case R_LARCH_TLS_IE_PC_LO12: - case R_LARCH_TLS_IE64_PC_LO20: - case R_LARCH_TLS_IE64_PC_HI12: - case R_LARCH_TLS_IE64_HI20: - case R_LARCH_TLS_IE64_LO12: - case R_LARCH_TLS_IE64_LO20: - case R_LARCH_TLS_IE64_HI12: - case R_LARCH_TLS_LD_PC_HI20: - case R_LARCH_TLS_LD64_HI20: - case R_LARCH_TLS_GD_PC_HI20: - case R_LARCH_TLS_GD64_HI20: - case R_LARCH_32_PCREL: - case R_LARCH_RELAX: - case R_LARCH_DELETE: - case R_LARCH_ALIGN: - case R_LARCH_PCREL20_S2: - case R_LARCH_CFA: - case R_LARCH_ADD6: - case R_LARCH_SUB6: - case R_LARCH_ADD_ULEB128: - case R_LARCH_SUB_ULEB128: - case R_LARCH_64_PCREL: - // - // These types are not used or do not require fixup. - // - break; - - case R_LARCH_GOT_PC_HI20: - Offset = Sym->st_value - (UINTN)(Targ - mCoffFile); - if (Offset < 0) { - Offset = (UINTN)(Targ - mCoffFile) - Sym->st_value; - Hi = Offset & ~0xfff; - Lo = (INT32)((Offset & 0xfff) << 20) >> 20; - if ((Lo < 0) && (Lo > -2048)) { - Hi += 0x1000; - Lo = ~(0x1000 - Lo) + 1; - } - Hi = ~Hi + 1; - Lo = ~Lo + 1; - } else { - Hi = Offset & ~0xfff; - Lo = (INT32)((Offset & 0xfff) << 20) >> 20; - if (Lo < 0) { - Hi += 0x1000; - Lo = ~(0x1000 - Lo) + 1; - } - } - // Re-encode the offset as PCADDU12I + ADDI.D(Convert LD.D) instruction - *(UINT32 *)Targ &= 0x1f; - *(UINT32 *)Targ |= 0x1c000000; - *(UINT32 *)Targ |= (((Hi >> 12) & 0xfffff) << 5); - *(UINT32 *)(Targ + 4) &= 0x3ff; - *(UINT32 *)(Targ + 4) |= 0x2c00000 | ((Lo & 0xfff) << 10); - break; - - // - // Attempt to convert instruction. - // - case R_LARCH_PCALA_HI20: - // Decode the PCALAU12I instruction and the instruction that following it. - Offset = ((INT32)((*(UINT32 *)Targ & 0x1ffffe0) << 7)); - Offset += ((INT32)((*(UINT32 *)(Targ + 4) & 0x3ffc00) << 10) >> 20); - // - // PCALA offset is relative to the previous page boundary, - // whereas PCADD offset is relative to the instruction itself. - // So fix up the offset so it points to the page containing - // the symbol. - // - Offset -= (UINTN)(Targ - mCoffFile) & 0xfff; - if (Offset < 0) { - Offset = -Offset; - Hi = Offset & ~0xfff; - Lo = (INT32)((Offset & 0xfff) << 20) >> 20; - if ((Lo < 0) && (Lo > -2048)) { - Hi += 0x1000; - Lo = ~(0x1000 - Lo) + 1; - } - Hi = ~Hi + 1; - Lo = ~Lo + 1; - } else { - Hi = Offset & ~0xfff; - Lo = (INT32)((Offset & 0xfff) << 20) >> 20; - if (Lo < 0) { - Hi += 0x1000; - Lo = ~(0x1000 - Lo) + 1; - } - } - // Convert the first instruction from PCALAU12I to PCADDU12I and re-encode the offset into them. - *(UINT32 *)Targ &= 0x1f; - *(UINT32 *)Targ |= 0x1c000000; - *(UINT32 *)Targ |= (((Hi >> 12) & 0xfffff) << 5); - *(UINT32 *)(Targ + 4) &= 0xffc003ff; - *(UINT32 *)(Targ + 4) |= (Lo & 0xfff) << 10; - break; - default: - Error (NULL, 0, 3000, "Invalid", "WriteSections64(): %s unsupported ELF EM_LOONGARCH relocation 0x%x.", mInImageName, (unsigned) ELF64_R_TYPE(Rel->r_info)); - } - } else { - Error (NULL, 0, 3000, "Invalid", "Not a supported machine type"); - } - } - } - } - - return TRUE; -} - -STATIC -VOID -WriteRelocations64 ( - VOID - ) -{ - UINT32 Index; - EFI_IMAGE_OPTIONAL_HEADER_UNION *NtHdr; - EFI_IMAGE_DATA_DIRECTORY *Dir; - UINT32 RiscVRelType; - - for (Index = 0; Index < mEhdr->e_shnum; Index++) { - Elf_Shdr *RelShdr = GetShdrByIndex(Index); - if ((RelShdr->sh_type == SHT_REL) || (RelShdr->sh_type == SHT_RELA)) { - Elf_Shdr *SecShdr = GetShdrByIndex (RelShdr->sh_info); - if (IsTextShdr(SecShdr) || IsDataShdr(SecShdr)) { - UINT64 RelIdx; - - for (RelIdx = 0; RelIdx < RelShdr->sh_size; RelIdx += RelShdr->sh_entsize) { - Elf_Rela *Rel = (Elf_Rela *)((UINT8*)mEhdr + RelShdr->sh_offset + RelIdx); - - if (mEhdr->e_machine == EM_X86_64) { - switch (ELF_R_TYPE(Rel->r_info)) { - case R_X86_64_NONE: - case R_X86_64_PC32: - case R_X86_64_PLT32: - case R_X86_64_GOTPCREL: - case R_X86_64_GOTPCRELX: - case R_X86_64_REX_GOTPCRELX: - break; - case R_X86_64_64: - VerboseMsg ("EFI_IMAGE_REL_BASED_DIR64 Offset: 0x%08llX", - mCoffSectionsOffset[RelShdr->sh_info] + (Rel->r_offset - SecShdr->sh_addr)); - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_DIR64); - break; - // - // R_X86_64_32 and R_X86_64_32S are ELF64 relocations emitted when using - // the SYSV X64 ABI small non-position-independent code model. - // R_X86_64_32 is used for unsigned 32-bit immediates with a 32-bit operand - // size. The value is either not extended, or zero-extended to 64 bits. - // R_X86_64_32S is used for either signed 32-bit non-rip-relative displacements - // or signed 32-bit immediates with a 64-bit operand size. The value is - // sign-extended to 64 bits. - // EFI_IMAGE_REL_BASED_HIGHLOW is a PE relocation that uses 32-bit arithmetic - // for rebasing an image. - // EFI PE binaries declare themselves EFI_IMAGE_FILE_LARGE_ADDRESS_AWARE and - // may load above 2GB. If an EFI PE binary with a converted R_X86_64_32S - // relocation is loaded above 2GB, the value will get sign-extended to the - // negative part of the 64-bit address space. The negative part of the 64-bit - // address space is unmapped, so accessing such an address page-faults. - // In order to support R_X86_64_32S, it is necessary to unset - // EFI_IMAGE_FILE_LARGE_ADDRESS_AWARE, and the EFI PE loader must implement - // this flag and abstain from loading such a PE binary above 2GB. - // Since this feature is not supported, support for R_X86_64_32S (and hence - // the small non-position-independent code model) is disabled. - // - // case R_X86_64_32S: - case R_X86_64_32: - VerboseMsg ("EFI_IMAGE_REL_BASED_HIGHLOW Offset: 0x%08llX", - mCoffSectionsOffset[RelShdr->sh_info] + (Rel->r_offset - SecShdr->sh_addr)); - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_HIGHLOW); - break; - default: - Error (NULL, 0, 3000, "Invalid", "%s unsupported ELF EM_X86_64 relocation 0x%x.", mInImageName, (unsigned) ELF_R_TYPE(Rel->r_info)); - } - } else if (mEhdr->e_machine == EM_AARCH64) { - - switch (ELF_R_TYPE(Rel->r_info)) { - case R_AARCH64_ADR_PREL_LO21: - case R_AARCH64_CONDBR19: - case R_AARCH64_LD_PREL_LO19: - case R_AARCH64_CALL26: - case R_AARCH64_JUMP26: - case R_AARCH64_PREL64: - case R_AARCH64_PREL32: - case R_AARCH64_PREL16: - case R_AARCH64_ADR_PREL_PG_HI21: - case R_AARCH64_ADD_ABS_LO12_NC: - case R_AARCH64_LDST8_ABS_LO12_NC: - case R_AARCH64_LDST16_ABS_LO12_NC: - case R_AARCH64_LDST32_ABS_LO12_NC: - case R_AARCH64_LDST64_ABS_LO12_NC: - case R_AARCH64_LDST128_ABS_LO12_NC: - case R_AARCH64_ADR_GOT_PAGE: - case R_AARCH64_LD64_GOT_LO12_NC: - case R_AARCH64_LD64_GOTOFF_LO15: - case R_AARCH64_LD64_GOTPAGE_LO15: - // - // No fixups are required for relative relocations, provided that - // the relative offsets between sections have been preserved in - // the ELF to PE/COFF conversion. We have already asserted that - // this is the case in WriteSections64 (). - // - break; - - case R_AARCH64_ABS64: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_DIR64); - break; - - case R_AARCH64_ABS32: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_HIGHLOW); - break; - - default: - Error (NULL, 0, 3000, "Invalid", "WriteRelocations64(): %s unsupported ELF EM_AARCH64 relocation 0x%x.", mInImageName, (unsigned) ELF_R_TYPE(Rel->r_info)); - } - } else if (mEhdr->e_machine == EM_RISCV64) { - RiscVRelType = ELF_R_TYPE(Rel->r_info); - switch (RiscVRelType) { - case R_RISCV_NONE: - break; - - case R_RISCV_32: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_HIGHLOW); - break; - - case R_RISCV_64: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_DIR64); - break; - - case R_RISCV_HI20: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_RISCV_HI20); - break; - - case R_RISCV_LO12_I: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_RISCV_LOW12I); - break; - - case R_RISCV_LO12_S: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_RISCV_LOW12S); - break; - - case R_RISCV_ADD64: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_ABSOLUTE); - break; - - case R_RISCV_SUB64: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_ABSOLUTE); - break; - - case R_RISCV_ADD32: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_ABSOLUTE); - break; - - case R_RISCV_SUB32: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_ABSOLUTE); - break; - - case R_RISCV_BRANCH: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_ABSOLUTE); - break; - - case R_RISCV_JAL: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_ABSOLUTE); - break; - - case R_RISCV_GPREL_I: - case R_RISCV_GPREL_S: - case R_RISCV_CALL: - case R_RISCV_CALL_PLT: - case R_RISCV_RVC_BRANCH: - case R_RISCV_RVC_JUMP: - case R_RISCV_RELAX: - case R_RISCV_SUB6: - case R_RISCV_SET6: - case R_RISCV_SET8: - case R_RISCV_SET16: - case R_RISCV_SET32: - case R_RISCV_PCREL_HI20: - case R_RISCV_GOT_HI20: - case R_RISCV_PCREL_LO12_I: - case R_RISCV_PCREL_LO12_S: - break; - - default: - Error (NULL, 0, 3000, "Invalid", "WriteRelocations64(): %s unsupported ELF EM_RISCV64 relocation 0x%x.", mInImageName, (unsigned) ELF_R_TYPE(Rel->r_info)); - } - } else if (mEhdr->e_machine == EM_LOONGARCH) { - switch (ELF_R_TYPE(Rel->r_info)) { - case R_LARCH_MARK_LA: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_LOONGARCH64_MARK_LA); - break; - case R_LARCH_64: - CoffAddFixup( - (UINT32) ((UINT64) mCoffSectionsOffset[RelShdr->sh_info] - + (Rel->r_offset - SecShdr->sh_addr)), - EFI_IMAGE_REL_BASED_DIR64); - break; - case R_LARCH_NONE: - case R_LARCH_32: - case R_LARCH_RELATIVE: - case R_LARCH_COPY: - case R_LARCH_JUMP_SLOT: - case R_LARCH_TLS_DTPMOD32: - case R_LARCH_TLS_DTPMOD64: - case R_LARCH_TLS_DTPREL32: - case R_LARCH_TLS_DTPREL64: - case R_LARCH_TLS_TPREL32: - case R_LARCH_TLS_TPREL64: - case R_LARCH_IRELATIVE: - case R_LARCH_MARK_PCREL: - case R_LARCH_SOP_PUSH_PCREL: - case R_LARCH_SOP_PUSH_ABSOLUTE: - case R_LARCH_SOP_PUSH_DUP: - case R_LARCH_SOP_PUSH_GPREL: - case R_LARCH_SOP_PUSH_TLS_TPREL: - case R_LARCH_SOP_PUSH_TLS_GOT: - case R_LARCH_SOP_PUSH_TLS_GD: - case R_LARCH_SOP_PUSH_PLT_PCREL: - case R_LARCH_SOP_ASSERT: - case R_LARCH_SOP_NOT: - case R_LARCH_SOP_SUB: - case R_LARCH_SOP_SL: - case R_LARCH_SOP_SR: - case R_LARCH_SOP_ADD: - case R_LARCH_SOP_AND: - case R_LARCH_SOP_IF_ELSE: - case R_LARCH_SOP_POP_32_S_10_5: - case R_LARCH_SOP_POP_32_U_10_12: - case R_LARCH_SOP_POP_32_S_10_12: - case R_LARCH_SOP_POP_32_S_10_16: - case R_LARCH_SOP_POP_32_S_10_16_S2: - case R_LARCH_SOP_POP_32_S_5_20: - case R_LARCH_SOP_POP_32_S_0_5_10_16_S2: - case R_LARCH_SOP_POP_32_S_0_10_10_16_S2: - case R_LARCH_SOP_POP_32_U: - case R_LARCH_ADD8: - case R_LARCH_ADD16: - case R_LARCH_ADD24: - case R_LARCH_ADD32: - case R_LARCH_ADD64: - case R_LARCH_SUB8: - case R_LARCH_SUB16: - case R_LARCH_SUB24: - case R_LARCH_SUB32: - case R_LARCH_SUB64: - case R_LARCH_GNU_VTINHERIT: - case R_LARCH_GNU_VTENTRY: - case R_LARCH_B16: - case R_LARCH_B21: - case R_LARCH_B26: - case R_LARCH_ABS_HI20: - case R_LARCH_ABS_LO12: - case R_LARCH_ABS64_LO20: - case R_LARCH_ABS64_HI12: - case R_LARCH_PCALA_HI20: - case R_LARCH_PCALA_LO12: - case R_LARCH_PCALA64_LO20: - case R_LARCH_PCALA64_HI12: - case R_LARCH_GOT_PC_HI20: - case R_LARCH_GOT_PC_LO12: - case R_LARCH_GOT64_PC_LO20: - case R_LARCH_GOT64_PC_HI12: - case R_LARCH_GOT64_HI20: - case R_LARCH_GOT64_LO12: - case R_LARCH_GOT64_LO20: - case R_LARCH_GOT64_HI12: - case R_LARCH_TLS_LE_HI20: - case R_LARCH_TLS_LE_LO12: - case R_LARCH_TLS_LE64_LO20: - case R_LARCH_TLS_LE64_HI12: - case R_LARCH_TLS_IE_PC_HI20: - case R_LARCH_TLS_IE_PC_LO12: - case R_LARCH_TLS_IE64_PC_LO20: - case R_LARCH_TLS_IE64_PC_HI12: - case R_LARCH_TLS_IE64_HI20: - case R_LARCH_TLS_IE64_LO12: - case R_LARCH_TLS_IE64_LO20: - case R_LARCH_TLS_IE64_HI12: - case R_LARCH_TLS_LD_PC_HI20: - case R_LARCH_TLS_LD64_HI20: - case R_LARCH_TLS_GD_PC_HI20: - case R_LARCH_TLS_GD64_HI20: - case R_LARCH_32_PCREL: - case R_LARCH_RELAX: - case R_LARCH_DELETE: - case R_LARCH_ALIGN: - case R_LARCH_PCREL20_S2: - case R_LARCH_CFA: - case R_LARCH_ADD6: - case R_LARCH_SUB6: - case R_LARCH_ADD_ULEB128: - case R_LARCH_SUB_ULEB128: - case R_LARCH_64_PCREL: - // - // These types are not used or do not require fixup in PE format files. - // - break; - default: - Error (NULL, 0, 3000, "Invalid", "WriteRelocations64(): %s unsupported ELF EM_LOONGARCH relocation 0x%x.", mInImageName, (unsigned) ELF64_R_TYPE(Rel->r_info)); - } - } else { - Error (NULL, 0, 3000, "Not Supported", "This tool does not support relocations for ELF with e_machine %u (processor type).", (unsigned) mEhdr->e_machine); - } - } - if (mEhdr->e_machine == EM_X86_64 && RelShdr->sh_info == mGOTShindex) { - // - // Tack relocations for GOT entries after other relocations for - // the section the GOT is in, as it's usually found at the end - // of the section. This is done in order to maintain Rva order - // of Coff relocations. - // - EmitGOTRelocations(); - } - } - } - } - - if (mEhdr->e_machine == EM_X86_64) { - // - // This is a safety net just in case the GOT is in a section - // with no other relocations and the first invocation of - // EmitGOTRelocations() above was skipped. This invocation - // does not maintain Rva order of Coff relocations. - // At present, with a single text section, all references to - // the GOT and the GOT itself reside in section .text, so - // if there's a GOT at all, the first invocation above - // is executed. - // - EmitGOTRelocations(); - } - // - // Pad by adding empty entries. - // - while (mCoffOffset & (mCoffAlignment - 1)) { - CoffAddFixupEntry(0); - } - - NtHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(mCoffFile + mNtHdrOffset); - Dir = &NtHdr->Pe32Plus.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC]; - Dir->Size = mCoffOffset - mRelocOffset; - if (Dir->Size == 0) { - // If no relocations, null out the directory entry and don't add the .reloc section - Dir->VirtualAddress = 0; - NtHdr->Pe32Plus.FileHeader.NumberOfSections--; - } else { - Dir->VirtualAddress = mRelocOffset; - CreateSectionHeader (".reloc", mRelocOffset, mCoffOffset - mRelocOffset, - EFI_IMAGE_SCN_CNT_INITIALIZED_DATA - | EFI_IMAGE_SCN_MEM_DISCARDABLE - | EFI_IMAGE_SCN_MEM_READ); - } -} - -STATIC -VOID -WriteDebug64 ( - VOID - ) -{ - UINT32 Len; - EFI_IMAGE_OPTIONAL_HEADER_UNION *NtHdr; - EFI_IMAGE_DATA_DIRECTORY *DataDir; - EFI_IMAGE_DEBUG_DIRECTORY_ENTRY *Dir; - EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY *Nb10; - EFI_IMAGE_DEBUG_EX_DLLCHARACTERISTICS_ENTRY *DllEntry; - - Len = strlen(mInImageName) + 1; - - NtHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(mCoffFile + mNtHdrOffset); - DataDir = &NtHdr->Pe32Plus.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG]; - DataDir->VirtualAddress = mDebugOffset; - DataDir->Size = sizeof (EFI_IMAGE_DEBUG_DIRECTORY_ENTRY); - - Dir = (EFI_IMAGE_DEBUG_DIRECTORY_ENTRY*)(mCoffFile + mDebugOffset); - - if (mDllCharacteristicsEx != 0) { - DataDir->Size += sizeof (EFI_IMAGE_DEBUG_DIRECTORY_ENTRY); - - Dir->Type = EFI_IMAGE_DEBUG_TYPE_EX_DLLCHARACTERISTICS; - Dir->SizeOfData = sizeof (EFI_IMAGE_DEBUG_EX_DLLCHARACTERISTICS_ENTRY); - Dir->FileOffset = mDebugOffset + DataDir->Size + - sizeof (EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY) + - DebugRvaAlign(Len); - Dir->RVA = Dir->FileOffset; - - DllEntry = (VOID *)(mCoffFile + Dir->FileOffset); - - DllEntry->DllCharacteristicsEx = mDllCharacteristicsEx; - - Dir++; - } - - Dir->Type = EFI_IMAGE_DEBUG_TYPE_CODEVIEW; - Dir->SizeOfData = sizeof(EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY) + Len; - Dir->RVA = mDebugOffset + DataDir->Size; - Dir->FileOffset = mDebugOffset + DataDir->Size; - - Nb10 = (EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY*)(Dir + 1); - Nb10->Signature = CODEVIEW_SIGNATURE_NB10; - strcpy ((char *)(Nb10 + 1), mInImageName); -} - -STATIC -VOID -SetImageSize64 ( - VOID - ) -{ - EFI_IMAGE_OPTIONAL_HEADER_UNION *NtHdr; - - // - // Set image size - // - NtHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(mCoffFile + mNtHdrOffset); - NtHdr->Pe32Plus.OptionalHeader.SizeOfImage = mCoffOffset; -} - -STATIC -VOID -CleanUp64 ( - VOID - ) -{ - if (mCoffSectionsOffset != NULL) { - free (mCoffSectionsOffset); - } -} - -STATIC -VOID -WriteExport64 ( - VOID - ) -{ - EFI_IMAGE_OPTIONAL_HEADER_UNION *NtHdr; - EFI_IMAGE_EXPORT_DIRECTORY *ExportDir; - EFI_IMAGE_DATA_DIRECTORY *DataDir; - UINT32 FileNameOffset; - UINT32 NameOffset; - UINT16 Index; - UINT8 *Tdata = NULL; - - ExportDir = (EFI_IMAGE_EXPORT_DIRECTORY*)(mCoffFile + mExportOffset); - ExportDir->Characteristics = 0; - ExportDir->TimeDateStamp = 0; - ExportDir->MajorVersion = 0; - ExportDir->MinorVersion =0; - ExportDir->Name = 0; - ExportDir->NumberOfFunctions = mExportSymNum; - ExportDir->NumberOfNames = mExportSymNum; - ExportDir->Base = EFI_IMAGE_EXPORT_ORDINAL_BASE; - ExportDir->AddressOfFunctions = mExportOffset + sizeof(EFI_IMAGE_EXPORT_DIRECTORY); - ExportDir->AddressOfNames = ExportDir->AddressOfFunctions + EFI_IMAGE_EXPORT_ADDR_SIZE * mExportSymNum; - ExportDir->AddressOfNameOrdinals = ExportDir->AddressOfNames + EFI_IMAGE_EXPORT_ADDR_SIZE * mExportSymNum; - - FileNameOffset = ExportDir->AddressOfNameOrdinals + EFI_IMAGE_EXPORT_ORDINAL_SIZE * mExportSymNum; - NameOffset = FileNameOffset + strlen(mInImageName) + 1; - - // Write Input image Name RVA - ExportDir->Name = FileNameOffset; - - // Write Input image Name - strcpy((char *)(mCoffFile + FileNameOffset), mInImageName); - - for (Index = 0; Index < mExportSymNum; Index++) { - // - // Write Export Address Table - // - Tdata = mCoffFile + ExportDir->AddressOfFunctions + Index * EFI_IMAGE_EXPORT_ADDR_SIZE; - *(UINT32 *)Tdata = mExportRVA[Index]; - - // - // Write Export Name Pointer Table - // - Tdata = mCoffFile + ExportDir->AddressOfNames + Index * EFI_IMAGE_EXPORT_ADDR_SIZE; - *(UINT32 *)Tdata = NameOffset; - - // - // Write Export Ordinal table - // - Tdata = mCoffFile + ExportDir->AddressOfNameOrdinals + Index * EFI_IMAGE_EXPORT_ORDINAL_SIZE; - *(UINT16 *)Tdata = Index; - - // - // Write Export Name Table - // - strcpy((char *)(mCoffFile + NameOffset), mExportSymName[Index]); - NameOffset += strlen(mExportSymName[Index]) + 1; - } - - NtHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(mCoffFile + mNtHdrOffset); - DataDir = &NtHdr->Pe32Plus.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXPORT]; - DataDir->VirtualAddress = mExportOffset; - DataDir->Size = mExportSize; - -} - diff --git a/BaseTools/Source/C/GenFw/Elf64Convert.h b/BaseTools/Source/C/GenFw/Elf64Convert.h deleted file mode 100644 index 330b2a76a7..0000000000 --- a/BaseTools/Source/C/GenFw/Elf64Convert.h +++ /dev/null @@ -1,19 +0,0 @@ -/** @file -Header file for Elf64 convert solution - -Copyright (c) 2010 - 2018, Intel Corporation. All rights reserved.
- -SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -#ifndef _ELF_64_CONVERT_ -#define _ELF_64_CONVERT_ - -BOOLEAN -InitializeElf64 ( - UINT8 *FileBuffer, - ELF_FUNCTION_TABLE *ElfFunctions - ); - -#endif diff --git a/BaseTools/Source/C/GenFw/ElfConvert.c b/BaseTools/Source/C/GenFw/ElfConvert.c deleted file mode 100644 index 3205f61494..0000000000 --- a/BaseTools/Source/C/GenFw/ElfConvert.c +++ /dev/null @@ -1,251 +0,0 @@ -/** @file -Elf convert solution - -Copyright (c) 2010 - 2018, Intel Corporation. All rights reserved.
- -SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -#ifndef __GNUC__ -#include -#include -#endif -#include -#include -#include -#include -#include -#include - -#include -#include - -#include "EfiUtilityMsgs.h" - -#include "GenFw.h" -#include "ElfConvert.h" -#include "Elf32Convert.h" -#include "Elf64Convert.h" - -// -// Result Coff file in memory. -// -UINT8 *mCoffFile = NULL; - -// -// COFF relocation data -// -EFI_IMAGE_BASE_RELOCATION *mCoffBaseRel; -UINT16 *mCoffEntryRel; - -// -// Current offset in coff file. -// -UINT32 mCoffOffset; - -// -// Offset in Coff file of headers and sections. -// -UINT32 mTableOffset; - -// -//mFileBufferSize -// -UINT32 mFileBufferSize; - -// -//***************************************************************************** -// Common ELF Functions -//***************************************************************************** -// - -VOID -CoffAddFixupEntry( - UINT16 Val - ) -{ - *mCoffEntryRel = Val; - mCoffEntryRel++; - mCoffBaseRel->SizeOfBlock += 2; - mCoffOffset += 2; -} - -VOID -CoffAddFixup( - UINT32 Offset, - UINT8 Type - ) -{ - if (mCoffBaseRel == NULL - || mCoffBaseRel->VirtualAddress != (Offset & ~0xfff)) { - if (mCoffBaseRel != NULL) { - // - // Add a null entry (is it required ?) - // - CoffAddFixupEntry (0); - - // - // Pad for alignment. - // - if (mCoffOffset % 4 != 0) - CoffAddFixupEntry (0); - } - - mCoffFile = realloc ( - mCoffFile, - mCoffOffset + sizeof(EFI_IMAGE_BASE_RELOCATION) + 2 * MAX_COFF_ALIGNMENT - ); - if (mCoffFile == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - } - assert (mCoffFile != NULL); - memset ( - mCoffFile + mCoffOffset, 0, - sizeof(EFI_IMAGE_BASE_RELOCATION) + 2 * MAX_COFF_ALIGNMENT - ); - - mCoffBaseRel = (EFI_IMAGE_BASE_RELOCATION*)(mCoffFile + mCoffOffset); - mCoffBaseRel->VirtualAddress = Offset & ~0xfff; - mCoffBaseRel->SizeOfBlock = sizeof(EFI_IMAGE_BASE_RELOCATION); - - mCoffEntryRel = (UINT16 *)(mCoffBaseRel + 1); - mCoffOffset += sizeof(EFI_IMAGE_BASE_RELOCATION); - } - - // - // Fill the entry. - // - CoffAddFixupEntry((UINT16) ((Type << 12) | (Offset & 0xfff))); -} - -VOID -CreateSectionHeader ( - const CHAR8 *Name, - UINT32 Offset, - UINT32 Size, - UINT32 Flags - ) -{ - EFI_IMAGE_SECTION_HEADER *Hdr; - Hdr = (EFI_IMAGE_SECTION_HEADER*)(mCoffFile + mTableOffset); - - strcpy((char *)Hdr->Name, Name); - Hdr->Misc.VirtualSize = Size; - Hdr->VirtualAddress = Offset; - Hdr->SizeOfRawData = Size; - Hdr->PointerToRawData = Offset; - Hdr->PointerToRelocations = 0; - Hdr->PointerToLinenumbers = 0; - Hdr->NumberOfRelocations = 0; - Hdr->NumberOfLinenumbers = 0; - Hdr->Characteristics = Flags; - - mTableOffset += sizeof (EFI_IMAGE_SECTION_HEADER); -} - -// -//***************************************************************************** -// Functions called from GenFw main code. -//***************************************************************************** -// - -INTN -IsElfHeader ( - UINT8 *FileBuffer -) -{ - return (FileBuffer[EI_MAG0] == ELFMAG0 && - FileBuffer[EI_MAG1] == ELFMAG1 && - FileBuffer[EI_MAG2] == ELFMAG2 && - FileBuffer[EI_MAG3] == ELFMAG3); -} - -BOOLEAN -ConvertElf ( - UINT8 **FileBuffer, - UINT32 *FileLength - ) -{ - ELF_FUNCTION_TABLE ElfFunctions; - UINT8 EiClass; - - mFileBufferSize = *FileLength; - // - // Determine ELF type and set function table pointer correctly. - // - VerboseMsg ("Check Elf Image Header"); - EiClass = (*FileBuffer)[EI_CLASS]; - if (EiClass == ELFCLASS32) { - if (!InitializeElf32 (*FileBuffer, &ElfFunctions)) { - return FALSE; - } - } else if (EiClass == ELFCLASS64) { - if (!InitializeElf64 (*FileBuffer, &ElfFunctions)) { - return FALSE; - } - } else { - Error (NULL, 0, 3000, "Unsupported", "ELF EI_CLASS not supported."); - return FALSE; - } - - // - // Compute sections new address. - // - VerboseMsg ("Compute sections new address."); - ElfFunctions.ScanSections (); - - // - // Write and relocate sections. - // - VerboseMsg ("Write and relocate sections."); - if (!ElfFunctions.WriteSections (SECTION_TEXT)) { - return FALSE; - } - if (!ElfFunctions.WriteSections (SECTION_DATA)) { - return FALSE; - } - if (!ElfFunctions.WriteSections (SECTION_HII)) { - return FALSE; - } - - // - // Translate and write relocations. - // - VerboseMsg ("Translate and write relocations."); - ElfFunctions.WriteRelocations (); - - // - // Write debug info. - // - VerboseMsg ("Write debug info."); - ElfFunctions.WriteDebug (); - - // - // For PRM Driver to Write export info. - // - if (mExportFlag) { - VerboseMsg ("Write export info."); - ElfFunctions.WriteExport (); - } - - // - // Make sure image size is correct before returning the new image. - // - VerboseMsg ("Set image size."); - ElfFunctions.SetImageSize (); - - // - // Replace. - // - free (*FileBuffer); - *FileBuffer = mCoffFile; - *FileLength = mCoffOffset; - - // - // Free resources used by ELF functions. - // - ElfFunctions.CleanUp (); - - return TRUE; -} diff --git a/BaseTools/Source/C/GenFw/ElfConvert.h b/BaseTools/Source/C/GenFw/ElfConvert.h deleted file mode 100644 index 6ab4605227..0000000000 --- a/BaseTools/Source/C/GenFw/ElfConvert.h +++ /dev/null @@ -1,122 +0,0 @@ -/** @file -Header file for Elf convert solution - -Copyright (c) 2010 - 2018, Intel Corporation. All rights reserved.
- -SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -#ifndef _ELF_CONVERT_H_ -#define _ELF_CONVERT_H_ - -#include "elf_common.h" -#include "elf32.h" -#include "elf64.h" - -// -// Externally defined variables -// -extern UINT32 mCoffOffset; -extern CHAR8 *mInImageName; -extern UINT32 mImageTimeStamp; -extern UINT8 *mCoffFile; -extern UINT32 mTableOffset; -extern UINT32 mOutImageType; -extern UINT32 mFileBufferSize; -extern BOOLEAN mExportFlag; - -// -// Common EFI specific data. -// -#define ELF_HII_SECTION_NAME ".hii" -#define ELF_STRTAB_SECTION_NAME ".strtab" -#define MAX_COFF_ALIGNMENT 0x10000 -#define ELF_SYMBOL_SECTION_NAME ".symtab" - -// -// Platform Runtime Mechanism (PRM) specific data. -// -#define PRM_MODULE_EXPORT_SYMBOL_NUM 256 - -// to include PRM header directly once PrmPkg is in main repo -#define PRM_HANDLER_NAME_MAXIMUM_LENGTH 128 - -#define PRM_MODULE_EXPORT_DESCRIPTOR_NAME "PrmModuleExportDescriptor" -#define PRM_MODULE_EXPORT_DESCRIPTOR_SIGNATURE SIGNATURE_64 ('P', 'R', 'M', '_', 'M', 'E', 'D', 'T') -#define PRM_MODULE_EXPORT_REVISION 0x0 - -// -// Platform Runtime Mechanism (PRM) Export Descriptor Structures -// -#pragma pack(push, 1) - -typedef struct { - EFI_GUID PrmHandlerGuid; - CHAR8 PrmHandlerName[PRM_HANDLER_NAME_MAXIMUM_LENGTH]; -} PRM_HANDLER_EXPORT_DESCRIPTOR_STRUCT; - -typedef struct { - UINT64 Signature; - UINT16 Revision; - UINT16 NumberPrmHandlers; - EFI_GUID PlatformGuid; - EFI_GUID ModuleGuid; -} PRM_MODULE_EXPORT_DESCRIPTOR_STRUCT_HEADER; - -typedef struct { - PRM_MODULE_EXPORT_DESCRIPTOR_STRUCT_HEADER Header; - PRM_HANDLER_EXPORT_DESCRIPTOR_STRUCT PrmHandlerExportDescriptors[1]; -} PRM_MODULE_EXPORT_DESCRIPTOR_STRUCT; - -#pragma pack(pop) - -// -// Filter Types -// -typedef enum { - SECTION_TEXT, - SECTION_HII, - SECTION_DATA, - SECTION_SYMBOL - -} SECTION_FILTER_TYPES; - -// -// FunctionTable -// -typedef struct { - VOID (*ScanSections) (); - BOOLEAN (*WriteSections) (SECTION_FILTER_TYPES FilterType); - VOID (*WriteRelocations) (); - VOID (*WriteDebug) (); - VOID (*WriteExport) (); - VOID (*SetImageSize) (); - VOID (*CleanUp) (); - -} ELF_FUNCTION_TABLE; - -// -// Common functions -// -VOID -CoffAddFixup ( - UINT32 Offset, - UINT8 Type - ); - -VOID -CoffAddFixupEntry ( - UINT16 Val - ); - - -VOID -CreateSectionHeader ( - const CHAR8 *Name, - UINT32 Offset, - UINT32 Size, - UINT32 Flags - ); - -#endif diff --git a/BaseTools/Source/C/GenFw/GNUmakefile b/BaseTools/Source/C/GenFw/GNUmakefile deleted file mode 100644 index 76cda7e7a3..0000000000 --- a/BaseTools/Source/C/GenFw/GNUmakefile +++ /dev/null @@ -1,23 +0,0 @@ -## @file -# GNU/Linux makefile for 'GenFw' module build. -# -# Copyright (c) 2009 - 2018, Intel Corporation. All rights reserved.
-# SPDX-License-Identifier: BSD-2-Clause-Patent -# -MAKEROOT ?= .. - -APPNAME = GenFw - -OBJECTS = GenFw.o ElfConvert.o Elf32Convert.o Elf64Convert.o - -include $(MAKEROOT)/Makefiles/app.makefile - -LIBS = -lCommon -ifeq ($(CYGWIN), CYGWIN) - LIBS += -L/lib/e2fsprogs -luuid -endif - -ifeq ($(LINUX), Linux) - LIBS += -luuid -endif - diff --git a/BaseTools/Source/C/GenFw/GenFw.c b/BaseTools/Source/C/GenFw/GenFw.c deleted file mode 100644 index bd635b375a..0000000000 --- a/BaseTools/Source/C/GenFw/GenFw.c +++ /dev/null @@ -1,3331 +0,0 @@ -/** @file -Converts a pe32+ image to an FW, Te image type, or other specific image. - -Copyright (c) 2004 - 2018, Intel Corporation. All rights reserved.
-SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -#ifndef __GNUC__ -#include -#include -#include -#include -#endif -#include -#include -#include -#include -#include - -#include -#include -#include - -// -// Acpi Table definition -// -#include -#include -#include -#include -#include - -#include "CommonLib.h" -#include "PeCoffLib.h" -#include "ParseInf.h" -#include "EfiUtilityMsgs.h" - -#include "GenFw.h" - -// -// Version of this utility -// -#define UTILITY_NAME "GenFw" -#define UTILITY_MAJOR_VERSION 0 -#define UTILITY_MINOR_VERSION 2 - -#define HII_RESOURCE_SECTION_INDEX 1 -#define HII_RESOURCE_SECTION_NAME "HII" - -#define DEFAULT_MC_PAD_BYTE_VALUE 0xFF -#define DEFAULT_MC_ALIGNMENT 16 - -#define STATUS_IGNORE 0xA -// -// Structure definition for a microcode header -// -typedef struct { - UINT32 HeaderVersion; - UINT32 PatchId; - UINT32 Date; - UINT32 CpuId; - UINT32 Checksum; - UINT32 LoaderVersion; - UINT32 PlatformId; - UINT32 DataSize; // if 0, then TotalSize = 2048, and TotalSize field is invalid - UINT32 TotalSize; // number of bytes - UINT32 Reserved[3]; -} MICROCODE_IMAGE_HEADER; - -static EFI_GUID mZeroGuid = {0x0, 0x0, 0x0, {0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0}}; - -static const char *gHiiPackageRCFileHeader[] = { - "//", - "// DO NOT EDIT -- auto-generated file", - "//", - NULL -}; - -// -// Module image information -// -CHAR8 *mInImageName; -UINT32 mImageTimeStamp = 0; -UINT32 mImageSize = 0; -UINT32 mOutImageType = FW_DUMMY_IMAGE; -BOOLEAN mIsConvertXip = FALSE; -BOOLEAN mExportFlag = FALSE; -BOOLEAN mNoNxCompat = FALSE; - -STATIC -EFI_STATUS -ZeroDebugData ( - IN OUT UINT8 *FileBuffer, - BOOLEAN ZeroDebug - ); - -STATIC -EFI_STATUS -SetStamp ( - IN OUT UINT8 *FileBuffer, - IN CHAR8 *TimeStamp - ); - -STATIC -STATUS -MicrocodeReadData ( - FILE *InFptr, - UINT32 *Data - ); - -STATIC -VOID -Version ( - VOID - ) -/*++ - -Routine Description: - - Print out version information for this utility. - -Arguments: - - None - -Returns: - - None - ---*/ -{ - fprintf (stdout, "%s Version %d.%d %s \n", UTILITY_NAME, UTILITY_MAJOR_VERSION, UTILITY_MINOR_VERSION, __BUILD_VERSION); -} - -STATIC -VOID -Usage ( - VOID - ) -/*++ - -Routine Description: - - Print Help message. - -Arguments: - - VOID - -Returns: - - None - ---*/ -{ - // - // Summary usage - // - fprintf (stdout, "\nUsage: %s [options] \n\n", UTILITY_NAME); - - // - // Copyright declaration - // - fprintf (stdout, "Copyright (c) 2007 - 2018, Intel Corporation. All rights reserved.\n\n"); - - // - // Details Option - // - fprintf (stdout, "Options:\n"); - fprintf (stdout, " -o FileName, --outputfile FileName\n\ - File will be created to store the output content.\n"); - fprintf (stdout, " -e EFI_FILETYPE, --efiImage EFI_FILETYPE\n\ - Create Efi Image. EFI_FILETYPE is one of BASE,SMM_CORE,\n\ - PEI_CORE, PEIM, DXE_CORE, DXE_DRIVER, UEFI_APPLICATION,\n\ - SEC, DXE_SAL_DRIVER, UEFI_DRIVER, DXE_RUNTIME_DRIVER,\n\ - DXE_SMM_DRIVER, SECURITY_CORE, COMBINED_PEIM_DRIVER,\n\ - MM_STANDALONE, MM_CORE_STANDALONE,\n\ - PIC_PEIM, RELOCATABLE_PEIM, BS_DRIVER, RT_DRIVER,\n\ - APPLICATION, SAL_RT_DRIVER to support all module types\n\ - It can only be used together with --keepexceptiontable,\n\ - --keepzeropending, --keepoptionalheader, -r, -o option.\n\ - It is a action option. If it is combined with other action options,\n\ - the later input action option will override the previous one.\n"); - fprintf (stdout, " -c, --acpi Create Acpi table.\n\ - It can't be combined with other action options\n\ - except for -o, -r option. It is a action option.\n\ - If it is combined with other action options, the later\n\ - input action option will override the previous one.\n"); - fprintf (stdout, " -t, --terse Create Te Image.\n\ - It can only be used together with --keepexceptiontable,\n\ - --keepzeropending, --keepoptionalheader, -r, -o option.\n\ - It is a action option. If it is combined with other action options,\n\ - the later input action option will override the previous one.\n"); - fprintf (stdout, " -u, --dump Dump TeImage Header.\n\ - It can't be combined with other action options\n\ - except for -o, -r option. It is a action option.\n\ - If it is combined with other action options, the later\n\ - input action option will override the previous one.\n"); - fprintf (stdout, " -z, --zero Zero the Debug Data Fields in the PE input image file.\n\ - It also zeros the time stamp fields.\n\ - This option can be used to compare the binary efi image.\n\ - It can't be combined with other action options\n\ - except for -o, -r option. It is a action option.\n\ - If it is combined with other action options, the later\n\ - input action option will override the previous one.\n"); - fprintf (stdout, " -b, --exe2bin Convert the input EXE to the output BIN file.\n\ - It can't be combined with other action options\n\ - except for -o, -r option. It is a action option.\n\ - If it is combined with other action options, the later\n\ - input action option will override the previous one.\n");; - fprintf (stdout, " -l, --stripped Strip off the relocation info from PE or TE image.\n\ - It can't be combined with other action options\n\ - except for -o, -r option. It is a action option.\n\ - If it is combined with other action options, the later\n\ - input action option will override the previous one.\n"); - fprintf (stdout, " -s timedate, --stamp timedate\n\ - timedate format is \"yyyy-mm-dd 00:00:00\". if timedata \n\ - is set to NOW, current system time is used. The support\n\ - date scope is 1970-01-01 00+timezone:00:00\n\ - ~ 2038-01-19 03+timezone:14:07\n\ - The scope is adjusted according to the different zones.\n\ - It can't be combined with other action options\n\ - except for -o, -r option. It is a action option.\n\ - If it is combined with other action options, the later\n\ - input action option will override the previous one.\n"); - fprintf (stdout, " -m, --mcifile Convert input microcode txt file to microcode bin file.\n\ - It can't be combined with other action options\n\ - except for -o option. It is a action option.\n\ - If it is combined with other action options, the later\n\ - input action option will override the previous one.\n"); - fprintf (stdout, " -j, --join Combine multi microcode bin files to one file.\n\ - It can be specified with -a, -p, -o option.\n\ - No other options can be combined with it.\n\ - If it is combined with other action options, the later\n\ - input action option will override the previous one.\n"); - fprintf (stdout, " -a NUM, --align NUM NUM is one HEX or DEC format alignment value.\n\ - This option is only used together with -j option.\n"); - fprintf (stdout, " -p NUM, --pad NUM NUM is one HEX or DEC format padding value.\n\ - This option is only used together with -j option.\n"); - fprintf (stdout, " --keepexceptiontable Don't clear exception table.\n\ - This option can be used together with -e or -t.\n\ - It doesn't work for other options.\n"); - fprintf (stdout, " --keepoptionalheader Don't zero PE/COFF optional header fields.\n\ - This option can be used together with -e or -t.\n\ - It doesn't work for other options.\n"); - fprintf (stdout, " --keepzeropending Don't strip zero pending of .reloc.\n\ - This option can be used together with -e or -t.\n\ - It doesn't work for other options.\n"); - fprintf (stdout, " -r, --replace Overwrite the input file with the output content.\n\ - If more input files are specified,\n\ - the last input file will be as the output file.\n"); - fprintf (stdout, " -g HiiPackageListGuid, --hiiguid HiiPackageListGuid\n\ - Guid is used to specify hii package list guid.\n\ - Its format is xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx\n\ - If not specified, the first Form FormSet guid is used.\n"); - fprintf (stdout, " --hiipackage Combine all input binary hii packages into \n\ - a single package list as the text resource data(RC).\n\ - It can't be combined with other action options\n\ - except for -o option. It is a action option.\n\ - If it is combined with other action options, the later\n\ - input action option will override the previous one.\n"); - fprintf (stdout, " --hiibinpackage Combine all input binary hii packages into \n\ - a single package list as the binary resource section.\n\ - It can't be combined with other action options\n\ - except for -o option. It is a action option.\n\ - If it is combined with other action options, the later\n\ - input action option will override the previous one.\n"); - fprintf (stdout, " --rebase NewAddress Rebase image to new base address. New address \n\ - is also set to the first none code section header.\n\ - It can't be combined with other action options\n\ - except for -o or -r option. It is a action option.\n\ - If it is combined with other action options, the later\n\ - input action option will override the previous one.\n"); - fprintf (stdout, " --address NewAddress Set new address into the first none code \n\ - section header of the input image.\n\ - It can't be combined with other action options\n\ - except for -o or -r option. It is a action option.\n\ - If it is combined with other action options, the later\n\ - input action option will override the previous one.\n"); - fprintf (stdout, " --prm Scan symbol section from ELF image and \n\ - write export table into PE-COFF.\n\ - This option can be used together with -e.\n\ - It doesn't work for other options.\n"); - fprintf (stdout, " --nonxcompat Do not set the IMAGE_DLLCHARACTERISTICS_NX_COMPAT bit \n\ - of the optional header in the PE header even if the \n\ - requirements are met.\n"); - fprintf (stdout, " -v, --verbose Turn on verbose output with informational messages.\n"); - fprintf (stdout, " -q, --quiet Disable all messages except key message and fatal error\n"); - fprintf (stdout, " -d, --debug level Enable debug messages, at input debug level.\n"); - fprintf (stdout, " --version Show program's version number and exit\n"); - fprintf (stdout, " -h, --help Show this help message and exit\n"); -} - -STATIC -STATUS -CheckAcpiTable ( - VOID *AcpiTable, - UINT32 Length - ) -/*++ - -Routine Description: - - Check Acpi Table - -Arguments: - - AcpiTable Buffer for AcpiSection - Length AcpiSection Length - -Returns: - - 0 success - non-zero otherwise - ---*/ -{ - EFI_ACPI_DESCRIPTION_HEADER *AcpiHeader; - EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE *Facs; - UINT32 ExpectedLength; - - AcpiHeader = (EFI_ACPI_DESCRIPTION_HEADER *)AcpiTable; - - // - // Generic check for AcpiTable length. - // - if (AcpiHeader->Length > Length) { - Error (NULL, 0, 3000, "Invalid", "AcpiTable length check failed.", NULL); - return STATUS_ERROR; - } - - // - // Currently, we only check must-have tables: FADT, FACS, DSDT, - // and some important tables: MADT, MCFG. - // - switch (AcpiHeader->Signature) { - - // - // "FACP" Fixed ACPI Description Table - // - case EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE: - switch (AcpiHeader->Revision) { - case EFI_ACPI_1_0_FIXED_ACPI_DESCRIPTION_TABLE_REVISION: - ExpectedLength = sizeof(EFI_ACPI_1_0_FIXED_ACPI_DESCRIPTION_TABLE); - break; - case EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE_REVISION: - ExpectedLength = sizeof(EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE); - break; - case EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE_REVISION: - ExpectedLength = sizeof(EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE); - break; - default: - if (AcpiHeader->Revision > EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE_REVISION) { - ExpectedLength = AcpiHeader->Length; - break; - } - Error (NULL, 0, 3000, "Invalid", "FACP revision check failed."); - return STATUS_ERROR; - } - if (ExpectedLength != AcpiHeader->Length) { - Error (NULL, 0, 3000, "Invalid", "FACP length check failed."); - return STATUS_ERROR; - } - break; - - // - // "FACS" Firmware ACPI Control Structure - // - case EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_SIGNATURE: - Facs = (EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE *)AcpiTable; - if (Facs->Version > EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_VERSION) { - break; - } - if ((Facs->Version != 0 /* field is reserved in ACPI 1.0 */) && - (Facs->Version != EFI_ACPI_2_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_VERSION) && - (Facs->Version != EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_VERSION)){ - Error (NULL, 0, 3000, "Invalid", "FACS version check failed."); - return STATUS_ERROR; - } - if ((Facs->Length != sizeof(EFI_ACPI_1_0_FIRMWARE_ACPI_CONTROL_STRUCTURE)) && - (Facs->Length != sizeof(EFI_ACPI_2_0_FIRMWARE_ACPI_CONTROL_STRUCTURE)) && - (Facs->Length != sizeof(EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE))) { - Error (NULL, 0, 3000, "Invalid", "FACS length check failed."); - return STATUS_ERROR; - } - break; - - // - // "DSDT" Differentiated System Description Table - // - case EFI_ACPI_3_0_DIFFERENTIATED_SYSTEM_DESCRIPTION_TABLE_SIGNATURE: - if (AcpiHeader->Revision > EFI_ACPI_3_0_DIFFERENTIATED_SYSTEM_DESCRIPTION_TABLE_REVISION) { - break; - } - if (AcpiHeader->Length <= sizeof(EFI_ACPI_DESCRIPTION_HEADER)) { - Error (NULL, 0, 3000, "Invalid", "DSDT length check failed."); - return STATUS_ERROR; - } - break; - - // - // "APIC" Multiple APIC Description Table - // - case EFI_ACPI_3_0_MULTIPLE_APIC_DESCRIPTION_TABLE_SIGNATURE: - if (AcpiHeader->Revision > EFI_ACPI_3_0_MULTIPLE_APIC_DESCRIPTION_TABLE_REVISION) { - break; - } - if ((AcpiHeader->Revision != EFI_ACPI_1_0_MULTIPLE_APIC_DESCRIPTION_TABLE_REVISION) && - (AcpiHeader->Revision != EFI_ACPI_2_0_MULTIPLE_APIC_DESCRIPTION_TABLE_REVISION) && - (AcpiHeader->Revision != EFI_ACPI_3_0_MULTIPLE_APIC_DESCRIPTION_TABLE_REVISION)) { - Error (NULL, 0, 3000, "Invalid", "APIC revision check failed."); - return STATUS_ERROR; - } - if (AcpiHeader->Length <= sizeof(EFI_ACPI_DESCRIPTION_HEADER) + sizeof(UINT32) + sizeof(UINT32)) { - Error (NULL, 0, 3000, "Invalid", "APIC length check failed."); - return STATUS_ERROR; - } - break; - - // - // "MCFG" PCI Express Memory Mapped Configuration Space Base Address Description Table - // - case EFI_ACPI_3_0_PCI_EXPRESS_MEMORY_MAPPED_CONFIGURATION_SPACE_BASE_ADDRESS_DESCRIPTION_TABLE_SIGNATURE: - if (AcpiHeader->Revision > EFI_ACPI_MEMORY_MAPPED_CONFIGURATION_SPACE_ACCESS_TABLE_REVISION) { - break; - } - if (AcpiHeader->Revision != EFI_ACPI_MEMORY_MAPPED_CONFIGURATION_SPACE_ACCESS_TABLE_REVISION) { - Error (NULL, 0, 3000, "Invalid", "MCFG revision check failed."); - return STATUS_ERROR; - } - if (AcpiHeader->Length <= sizeof(EFI_ACPI_DESCRIPTION_HEADER) + sizeof(UINT64)) { - Error (NULL, 0, 3000, "Invalid", "MCFG length check failed."); - return STATUS_ERROR; - } - break; - - // - // Other table pass check - // - default: - break; - } - - return STATUS_SUCCESS; -} - -/** - - Checks if the Pe image is nxcompat compliant. - - Must meet the following conditions: - 1. The PE is 64bit - 2. The section alignment is evenly divisible by 4k - 3. No section is writable and executable. - - @param PeHdr - The PE header - - @retval TRUE - The PE is nx compat compliant - @retval FALSE - The PE is not nx compat compliant - -**/ -STATIC -BOOLEAN -IsNxCompatCompliant ( - EFI_IMAGE_OPTIONAL_HEADER_UNION *PeHdr - ) -{ - EFI_IMAGE_SECTION_HEADER *SectionHeader; - UINT32 Index; - UINT32 Mask; - - // Must have an optional header to perform verification - if (PeHdr->Pe32.FileHeader.SizeOfOptionalHeader == 0) { - return FALSE; - } - - // Verify PE is 64 bit - if (!(PeHdr->Pe32.OptionalHeader.Magic == EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC)) { - return FALSE; - } - - // Verify Section Alignment is divisible by 4K - if (!((PeHdr->Pe32Plus.OptionalHeader.SectionAlignment % EFI_PAGE_SIZE) == 0)) { - return FALSE; - } - - // Verify sections are not Write & Execute - Mask = EFI_IMAGE_SCN_MEM_EXECUTE | EFI_IMAGE_SCN_MEM_WRITE; - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) &(PeHdr->Pe32Plus.OptionalHeader) + PeHdr->Pe32Plus.FileHeader.SizeOfOptionalHeader); - for (Index = 0; Index < PeHdr->Pe32Plus.FileHeader.NumberOfSections; Index ++, SectionHeader ++) { - if ((SectionHeader->Characteristics & Mask) == Mask) { - return FALSE; - } - } - - // Passed all requirements, return TRUE - return TRUE; -} - -VOID -SetHiiResourceHeader ( - UINT8 *HiiBinData, - UINT32 OffsetToFile - ) -{ - UINT32 Index; - EFI_IMAGE_RESOURCE_DIRECTORY *ResourceDirectory; - EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *ResourceDirectoryEntry; - EFI_IMAGE_RESOURCE_DIRECTORY_STRING *ResourceDirectoryString; - EFI_IMAGE_RESOURCE_DATA_ENTRY *ResourceDataEntry; - - // - // Fill Resource section entry - // - ResourceDirectory = (EFI_IMAGE_RESOURCE_DIRECTORY *) (HiiBinData); - ResourceDirectoryEntry = (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *) (ResourceDirectory + 1); - for (Index = 0; Index < ResourceDirectory->NumberOfNamedEntries; Index ++) { - if (ResourceDirectoryEntry->u1.s.NameIsString) { - ResourceDirectoryString = (EFI_IMAGE_RESOURCE_DIRECTORY_STRING *) (HiiBinData + ResourceDirectoryEntry->u1.s.NameOffset); - - if (ResourceDirectoryString->Length == 3 && - ResourceDirectoryString->String[0] == L'H' && - ResourceDirectoryString->String[1] == L'I' && - ResourceDirectoryString->String[2] == L'I') { - // - // Resource Type "HII" found - // - if (ResourceDirectoryEntry->u2.s.DataIsDirectory) { - // - // Move to next level - resource Name - // - ResourceDirectory = (EFI_IMAGE_RESOURCE_DIRECTORY *) (HiiBinData + ResourceDirectoryEntry->u2.s.OffsetToDirectory); - ResourceDirectoryEntry = (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *) (ResourceDirectory + 1); - - if (ResourceDirectoryEntry->u2.s.DataIsDirectory) { - // - // Move to next level - resource Language - // - ResourceDirectory = (EFI_IMAGE_RESOURCE_DIRECTORY *) (HiiBinData + ResourceDirectoryEntry->u2.s.OffsetToDirectory); - ResourceDirectoryEntry = (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *) (ResourceDirectory + 1); - } - } - - // - // Now it ought to be resource Data and update its OffsetToData value - // - if (!ResourceDirectoryEntry->u2.s.DataIsDirectory) { - ResourceDataEntry = (EFI_IMAGE_RESOURCE_DATA_ENTRY *) (HiiBinData + ResourceDirectoryEntry->u2.OffsetToData); - ResourceDataEntry->OffsetToData = ResourceDataEntry->OffsetToData + OffsetToFile; - break; - } - } - } - ResourceDirectoryEntry++; - } - - return; -} - -EFI_IMAGE_OPTIONAL_HEADER_UNION * -GetPeCoffHeader ( - void *Data - ) -{ - EFI_IMAGE_DOS_HEADER *DosHdr; - EFI_IMAGE_OPTIONAL_HEADER_UNION *PeHdr; - - // - // Read the dos & pe hdrs of the image - // - DosHdr = (EFI_IMAGE_DOS_HEADER *)Data; - if (DosHdr->e_magic != EFI_IMAGE_DOS_SIGNATURE) { - // NO DOS header, check for PE/COFF header - PeHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(Data); - if (PeHdr->Pe32.Signature != EFI_IMAGE_NT_SIGNATURE) { - return NULL; - } - } else { - - PeHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(((UINT8 *)Data) + DosHdr->e_lfanew); - if (PeHdr->Pe32.Signature != EFI_IMAGE_NT_SIGNATURE) { - return NULL; - } - } - - return PeHdr; -} - -void -PeCoffConvertImageToXip ( - UINT8 **FileBuffer, - UINT32 *FileLength - ) -{ - EFI_IMAGE_OPTIONAL_HEADER_UNION *PeHdr; - EFI_IMAGE_OPTIONAL_HEADER_UNION *NewPeHdr; - EFI_IMAGE_SECTION_HEADER *SectionHeader; - UINTN TotalNecessaryFileSize; - UINTN SectionSize; - UINT8 *XipFile; - UINT32 XipLength; - UINTN Index; - UINTN FirstSectionOffset; - BOOLEAN ConversionNeeded; - - PeHdr = GetPeCoffHeader ((void *) *FileBuffer); - if (PeHdr == NULL) { - return; - } - - if (PeHdr->Pe32.OptionalHeader.SectionAlignment != PeHdr->Pe32.OptionalHeader.FileAlignment) { - // - // The only reason to expand zero fill sections is to make them compatible with XIP images. - // If SectionAlignment is not equal to FileAlignment then it is not an XIP type image. - // - return; - } - - // - // Calculate size of XIP file, and determine if the conversion is needed. - // - ConversionNeeded = FALSE; - XipLength = 0; - FirstSectionOffset = *FileLength; - TotalNecessaryFileSize = 0; - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) &(PeHdr->Pe32.OptionalHeader) + PeHdr->Pe32.FileHeader.SizeOfOptionalHeader); - for (Index = 0; Index < PeHdr->Pe32.FileHeader.NumberOfSections; Index ++, SectionHeader ++) { - SectionSize = MAX (SectionHeader->Misc.VirtualSize, SectionHeader->SizeOfRawData); - TotalNecessaryFileSize += SectionSize; - if (SectionSize > 0) { - FirstSectionOffset = MIN (FirstSectionOffset, SectionHeader->VirtualAddress); - XipLength = MAX (XipLength, SectionHeader->VirtualAddress + SectionSize); - if (SectionHeader->VirtualAddress != SectionHeader->PointerToRawData) { - ConversionNeeded = TRUE; - } - } - if (SectionHeader->Misc.VirtualSize > SectionHeader->SizeOfRawData) { - ConversionNeeded = TRUE; - } - } - - if (FirstSectionOffset < PeHdr->Pe32.OptionalHeader.SizeOfHeaders) { - // - // If one of the sections should be loaded to an offset overlapping with - // the executable header, then it cannot be made into an XIP image. - // - VerboseMsg ("PE/COFF conversion to XIP is impossible due to overlap"); - VerboseMsg ("of section data with the executable header."); - return; - } - - if (FirstSectionOffset == *FileLength) { - // - // If we never found a section with a non-zero size, then we - // skip the conversion. - // - return; - } - - TotalNecessaryFileSize += FirstSectionOffset; - - if (!ConversionNeeded) { - return; - } - - if (XipLength > (2 * TotalNecessaryFileSize)) { - VerboseMsg ("PE/COFF conversion to XIP appears to be larger than necessary."); - VerboseMsg ("The image linking process may have left unused memory ranges."); - } - - if (PeHdr->Pe32.FileHeader.PointerToSymbolTable != 0) { - // - // This field is obsolete and should be zero - // - PeHdr->Pe32.FileHeader.PointerToSymbolTable = 0; - } - - // - // Allocate the extra space that we need to grow the image - // - XipFile = malloc (XipLength); - if (XipFile == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - return; - } - memset (XipFile, 0, XipLength); - - // - // Copy the file headers - // - memcpy (XipFile, *FileBuffer, PeHdr->Pe32.OptionalHeader.SizeOfHeaders); - - NewPeHdr = GetPeCoffHeader ((void *)XipFile); - if (NewPeHdr == NULL) { - free (XipFile); - return; - } - - // - // Copy the section data over to the appropriate XIP offsets - // - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) &(NewPeHdr->Pe32.OptionalHeader) + NewPeHdr->Pe32.FileHeader.SizeOfOptionalHeader); - for (Index = 0; Index < PeHdr->Pe32.FileHeader.NumberOfSections; Index ++, SectionHeader ++) { - if (SectionHeader->SizeOfRawData > 0) { - memcpy ( - XipFile + SectionHeader->VirtualAddress, - *FileBuffer + SectionHeader->PointerToRawData, - SectionHeader->SizeOfRawData - ); - } - // - // Make the size of raw data in section header alignment. - // - SectionSize = (SectionHeader->Misc.VirtualSize + PeHdr->Pe32.OptionalHeader.FileAlignment - 1) & (~(PeHdr->Pe32.OptionalHeader.FileAlignment - 1)); - if (SectionSize < SectionHeader->SizeOfRawData) { - SectionHeader->SizeOfRawData = SectionSize; - } - - SectionHeader->PointerToRawData = SectionHeader->VirtualAddress; - } - - free (*FileBuffer); - *FileLength = XipLength; - *FileBuffer = XipFile; - - mIsConvertXip = TRUE; -} - -UINT8 * -CreateHiiResouceSectionHeader ( - UINT32 *pSectionHeaderSize, - UINT32 HiiDataSize - ) -/*++ - -Routine Description: - - Create COFF resource section header - -Arguments: - - pSectionHeaderSize - Pointer to section header size. - HiiDataSize - Size of the total HII data in section. - -Returns: - The created section header buffer. - ---*/ -{ - UINT32 HiiSectionHeaderSize; - UINT32 HiiSectionOffset; - UINT8 *HiiSectionHeader; - EFI_IMAGE_RESOURCE_DIRECTORY *ResourceDirectory; - EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *TypeResourceDirectoryEntry; - EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *NameResourceDirectoryEntry; - EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *LanguageResourceDirectoryEntry; - EFI_IMAGE_RESOURCE_DIRECTORY_STRING *ResourceDirectoryString; - EFI_IMAGE_RESOURCE_DATA_ENTRY *ResourceDataEntry; - - // - // Calculate the total size for the resource header (include Type, Name and Language) - // then allocate memory for the resource header. - // - HiiSectionHeaderSize = 3 * (sizeof (EFI_IMAGE_RESOURCE_DIRECTORY) + sizeof (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY)) - + 3 * (sizeof (UINT16) + 3 * sizeof (CHAR16)) - + sizeof (EFI_IMAGE_RESOURCE_DATA_ENTRY); - HiiSectionHeader = malloc (HiiSectionHeaderSize); - if (HiiSectionHeader == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - return NULL; - } - memset (HiiSectionHeader, 0, HiiSectionHeaderSize); - - HiiSectionOffset = 0; - // - // Create Type entry - // - ResourceDirectory = (EFI_IMAGE_RESOURCE_DIRECTORY *) (HiiSectionHeader + HiiSectionOffset); - HiiSectionOffset += sizeof (EFI_IMAGE_RESOURCE_DIRECTORY); - ResourceDirectory->NumberOfNamedEntries = 1; - TypeResourceDirectoryEntry = (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *) (HiiSectionHeader + HiiSectionOffset); - HiiSectionOffset += sizeof (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY); - TypeResourceDirectoryEntry->u1.s.NameIsString = 1; - TypeResourceDirectoryEntry->u2.s.DataIsDirectory = 1; - TypeResourceDirectoryEntry->u2.s.OffsetToDirectory = HiiSectionOffset; - // - // Create Name entry - // - ResourceDirectory = (EFI_IMAGE_RESOURCE_DIRECTORY *) (HiiSectionHeader + HiiSectionOffset); - HiiSectionOffset += sizeof (EFI_IMAGE_RESOURCE_DIRECTORY); - ResourceDirectory->NumberOfNamedEntries = 1; - NameResourceDirectoryEntry = (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *) (HiiSectionHeader + HiiSectionOffset); - HiiSectionOffset += sizeof (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY); - NameResourceDirectoryEntry->u1.s.NameIsString = 1; - NameResourceDirectoryEntry->u2.s.DataIsDirectory = 1; - NameResourceDirectoryEntry->u2.s.OffsetToDirectory = HiiSectionOffset; - // - // Create Language entry - // - ResourceDirectory = (EFI_IMAGE_RESOURCE_DIRECTORY *) (HiiSectionHeader + HiiSectionOffset); - HiiSectionOffset += sizeof (EFI_IMAGE_RESOURCE_DIRECTORY); - ResourceDirectory->NumberOfNamedEntries = 1; - LanguageResourceDirectoryEntry = (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY *) (HiiSectionHeader + HiiSectionOffset); - HiiSectionOffset += sizeof (EFI_IMAGE_RESOURCE_DIRECTORY_ENTRY); - LanguageResourceDirectoryEntry->u1.s.NameIsString = 1; - // - // Create string entry for Type - // - TypeResourceDirectoryEntry->u1.s.NameOffset = HiiSectionOffset; - ResourceDirectoryString = (EFI_IMAGE_RESOURCE_DIRECTORY_STRING *) (HiiSectionHeader + HiiSectionOffset); - ResourceDirectoryString->Length = 3; - ResourceDirectoryString->String[0] = L'H'; - ResourceDirectoryString->String[1] = L'I'; - ResourceDirectoryString->String[2] = L'I'; - HiiSectionOffset = HiiSectionOffset + sizeof (ResourceDirectoryString->Length) + ResourceDirectoryString->Length * sizeof (ResourceDirectoryString->String[0]); - // - // Create string entry for Name - // - NameResourceDirectoryEntry->u1.s.NameOffset = HiiSectionOffset; - ResourceDirectoryString = (EFI_IMAGE_RESOURCE_DIRECTORY_STRING *) (HiiSectionHeader + HiiSectionOffset); - ResourceDirectoryString->Length = 3; - ResourceDirectoryString->String[0] = L'E'; - ResourceDirectoryString->String[1] = L'F'; - ResourceDirectoryString->String[2] = L'I'; - HiiSectionOffset = HiiSectionOffset + sizeof (ResourceDirectoryString->Length) + ResourceDirectoryString->Length * sizeof (ResourceDirectoryString->String[0]); - // - // Create string entry for Language - // - LanguageResourceDirectoryEntry->u1.s.NameOffset = HiiSectionOffset; - ResourceDirectoryString = (EFI_IMAGE_RESOURCE_DIRECTORY_STRING *) (HiiSectionHeader + HiiSectionOffset); - ResourceDirectoryString->Length = 3; - ResourceDirectoryString->String[0] = L'B'; - ResourceDirectoryString->String[1] = L'I'; - ResourceDirectoryString->String[2] = L'N'; - HiiSectionOffset = HiiSectionOffset + sizeof (ResourceDirectoryString->Length) + ResourceDirectoryString->Length * sizeof (ResourceDirectoryString->String[0]); - // - // Create Leaf data - // - LanguageResourceDirectoryEntry->u2.OffsetToData = HiiSectionOffset; - ResourceDataEntry = (EFI_IMAGE_RESOURCE_DATA_ENTRY *) (HiiSectionHeader + HiiSectionOffset); - HiiSectionOffset += sizeof (EFI_IMAGE_RESOURCE_DATA_ENTRY); - ResourceDataEntry->OffsetToData = HiiSectionOffset; - ResourceDataEntry->Size = HiiDataSize; - - *pSectionHeaderSize = HiiSectionHeaderSize; - return HiiSectionHeader; -} - -EFI_STATUS -RebaseImageRead ( - IN VOID *FileHandle, - IN UINTN FileOffset, - IN OUT UINT32 *ReadSize, - OUT VOID *Buffer - ) -/*++ - -Routine Description: - - Support routine for the PE/COFF Loader that reads a buffer from a PE/COFF file - -Arguments: - - FileHandle - The handle to the PE/COFF file - - FileOffset - The offset, in bytes, into the file to read - - ReadSize - The number of bytes to read from the file starting at FileOffset - - Buffer - A pointer to the buffer to read the data into. - -Returns: - - EFI_SUCCESS - ReadSize bytes of data were read into Buffer from the PE/COFF file starting at FileOffset - ---*/ -{ - CHAR8 *Destination8; - CHAR8 *Source8; - UINT32 Length; - - Destination8 = Buffer; - Source8 = (CHAR8 *) ((UINTN) FileHandle + FileOffset); - Length = *ReadSize; - while (Length--) { - *(Destination8++) = *(Source8++); - } - - return EFI_SUCCESS; -} - -EFI_STATUS -SetAddressToSectionHeader ( - IN CHAR8 *FileName, - IN OUT UINT8 *FileBuffer, - IN UINT64 NewPe32BaseAddress - ) -/*++ - -Routine Description: - - Set new base address into the section header of PeImage - -Arguments: - - FileName - Name of file - FileBuffer - Pointer to PeImage. - NewPe32BaseAddress - New Base Address for PE image. - -Returns: - - EFI_SUCCESS Set new base address into this image successfully. - ---*/ -{ - EFI_STATUS Status; - PE_COFF_LOADER_IMAGE_CONTEXT ImageContext; - UINTN Index; - EFI_IMAGE_OPTIONAL_HEADER_UNION *ImgHdr; - EFI_IMAGE_SECTION_HEADER *SectionHeader; - - // - // Initialize context - // - memset (&ImageContext, 0, sizeof (ImageContext)); - ImageContext.Handle = (VOID *) FileBuffer; - ImageContext.ImageRead = (PE_COFF_LOADER_READ_FILE) RebaseImageRead; - Status = PeCoffLoaderGetImageInfo (&ImageContext); - if (EFI_ERROR (Status)) { - Error (NULL, 0, 3000, "Invalid", "The input PeImage %s is not valid", FileName); - return Status; - } - - if (ImageContext.RelocationsStripped) { - Error (NULL, 0, 3000, "Invalid", "The input PeImage %s has no relocation to be fixed up", FileName); - return Status; - } - - // - // Get PeHeader pointer - // - ImgHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(FileBuffer + ImageContext.PeCoffHeaderOffset); - - // - // Get section header list - // - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ( - (UINTN) ImgHdr + - sizeof (UINT32) + - sizeof (EFI_IMAGE_FILE_HEADER) + - ImgHdr->Pe32.FileHeader.SizeOfOptionalHeader - ); - - // - // Set base address into the first section header that doesn't point to code section. - // - for (Index = 0; Index < ImgHdr->Pe32.FileHeader.NumberOfSections; Index ++, SectionHeader ++) { - if ((SectionHeader->Characteristics & EFI_IMAGE_SCN_CNT_CODE) == 0) { - *(UINT64 *) &SectionHeader->PointerToRelocations = NewPe32BaseAddress; - break; - } - } - - // - // BaseAddress is set to section header. - // - return EFI_SUCCESS; -} - -EFI_STATUS -RebaseImage ( - IN CHAR8 *FileName, - IN OUT UINT8 *FileBuffer, - IN UINT64 NewPe32BaseAddress - ) -/*++ - -Routine Description: - - Set new base address into PeImage, and fix up PeImage based on new address. - -Arguments: - - FileName - Name of file - FileBuffer - Pointer to PeImage. - NewPe32BaseAddress - New Base Address for PE image. - -Returns: - - EFI_INVALID_PARAMETER - BaseAddress is not valid. - EFI_SUCCESS - Update PeImage is correctly. - ---*/ -{ - EFI_STATUS Status; - PE_COFF_LOADER_IMAGE_CONTEXT ImageContext; - UINTN Index; - EFI_IMAGE_OPTIONAL_HEADER_UNION *ImgHdr; - UINT8 *MemoryImagePointer; - EFI_IMAGE_SECTION_HEADER *SectionHeader; - - // - // Initialize context - // - memset (&ImageContext, 0, sizeof (ImageContext)); - ImageContext.Handle = (VOID *) FileBuffer; - ImageContext.ImageRead = (PE_COFF_LOADER_READ_FILE) RebaseImageRead; - Status = PeCoffLoaderGetImageInfo (&ImageContext); - if (EFI_ERROR (Status)) { - Error (NULL, 0, 3000, "Invalid", "The input PeImage %s is not valid", FileName); - return Status; - } - - if (ImageContext.RelocationsStripped) { - Error (NULL, 0, 3000, "Invalid", "The input PeImage %s has no relocation to be fixed up", FileName); - return Status; - } - - // - // Get PeHeader pointer - // - ImgHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(FileBuffer + ImageContext.PeCoffHeaderOffset); - - // - // Load and Relocate Image Data - // - MemoryImagePointer = (UINT8 *) malloc ((UINTN) ImageContext.ImageSize + ImageContext.SectionAlignment); - if (MemoryImagePointer == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated on rebase of %s", FileName); - return EFI_OUT_OF_RESOURCES; - } - memset ((VOID *) MemoryImagePointer, 0, (UINTN) ImageContext.ImageSize + ImageContext.SectionAlignment); - ImageContext.ImageAddress = ((UINTN) MemoryImagePointer + ImageContext.SectionAlignment - 1) & (~((INT64)ImageContext.SectionAlignment - 1)); - - Status = PeCoffLoaderLoadImage (&ImageContext); - if (EFI_ERROR (Status)) { - Error (NULL, 0, 3000, "Invalid", "LocateImage() call failed on rebase of %s", FileName); - free ((VOID *) MemoryImagePointer); - return Status; - } - - ImageContext.DestinationAddress = NewPe32BaseAddress; - Status = PeCoffLoaderRelocateImage (&ImageContext); - if (EFI_ERROR (Status)) { - Error (NULL, 0, 3000, "Invalid", "RelocateImage() call failed on rebase of %s", FileName); - free ((VOID *) MemoryImagePointer); - return Status; - } - - // - // Copy Relocated data to raw image file. - // - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ( - (UINTN) ImgHdr + - sizeof (UINT32) + - sizeof (EFI_IMAGE_FILE_HEADER) + - ImgHdr->Pe32.FileHeader.SizeOfOptionalHeader - ); - - for (Index = 0; Index < ImgHdr->Pe32.FileHeader.NumberOfSections; Index ++, SectionHeader ++) { - CopyMem ( - FileBuffer + SectionHeader->PointerToRawData, - (VOID*) (UINTN) (ImageContext.ImageAddress + SectionHeader->VirtualAddress), - SectionHeader->SizeOfRawData < SectionHeader->Misc.VirtualSize ? SectionHeader->SizeOfRawData : SectionHeader->Misc.VirtualSize - ); - } - - free ((VOID *) MemoryImagePointer); - - // - // Update Image Base Address - // - if (ImgHdr->Pe32.OptionalHeader.Magic == EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC) { - ImgHdr->Pe32.OptionalHeader.ImageBase = (UINT32) NewPe32BaseAddress; - } else if (ImgHdr->Pe32Plus.OptionalHeader.Magic == EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC) { - ImgHdr->Pe32Plus.OptionalHeader.ImageBase = NewPe32BaseAddress; - } else { - Error (NULL, 0, 3000, "Invalid", "unknown PE magic signature %X in PE32 image %s", - ImgHdr->Pe32.OptionalHeader.Magic, - FileName - ); - return EFI_ABORTED; - } - - // - // Set new base address into section header - // - Status = SetAddressToSectionHeader (FileName, FileBuffer, NewPe32BaseAddress); - - return Status; -} - -int -main ( - int argc, - char *argv[] - ) -/*++ - -Routine Description: - - Main function. - -Arguments: - - argc - Number of command line parameters. - argv - Array of pointers to command line parameter strings. - -Returns: - STATUS_SUCCESS - Utility exits successfully. - STATUS_ERROR - Some error occurred during execution. - ---*/ -{ - UINT32 Type; - UINT32 InputFileNum; - CHAR8 **InputFileName; - char *OutImageName; - char *ModuleType; - CHAR8 *TimeStamp; - FILE *fpIn; - FILE *fpOut; - FILE *fpInOut; - UINT32 Data; - UINT32 *DataPointer; - UINT32 *OldDataPointer; - UINT32 CheckSum; - UINT32 Index; - UINT32 Index1; - UINT32 Index2; - UINT64 Temp64; - UINT32 MciAlignment; - UINT8 MciPadValue; - UINT32 AllignedRelocSize; - UINT8 *FileBuffer; - UINT32 FileLength; - UINT8 *OutputFileBuffer; - UINT32 OutputFileLength; - UINT8 *InputFileBuffer; - UINT32 InputFileLength; - RUNTIME_FUNCTION *RuntimeFunction; - UNWIND_INFO *UnwindInfo; - STATUS Status; - BOOLEAN ReplaceFlag; - BOOLEAN KeepExceptionTableFlag; - BOOLEAN KeepOptionalHeaderFlag; - BOOLEAN KeepZeroPendingFlag; - UINT64 LogLevel; - EFI_TE_IMAGE_HEADER TEImageHeader; - EFI_TE_IMAGE_HEADER *TeHdr; - EFI_IMAGE_SECTION_HEADER *SectionHeader; - EFI_IMAGE_DOS_HEADER *DosHdr; - EFI_IMAGE_OPTIONAL_HEADER_UNION *PeHdr; - EFI_IMAGE_OPTIONAL_HEADER32 *Optional32; - EFI_IMAGE_OPTIONAL_HEADER64 *Optional64; - EFI_IMAGE_DOS_HEADER BackupDosHdr; - MICROCODE_IMAGE_HEADER *MciHeader; - UINT8 *HiiPackageListBuffer; - UINT8 *HiiPackageDataPointer; - EFI_GUID HiiPackageListGuid; - EFI_HII_PACKAGE_LIST_HEADER HiiPackageListHeader; - EFI_HII_PACKAGE_HEADER HiiPackageHeader; - EFI_IFR_FORM_SET IfrFormSet; - UINT8 NumberOfFormPackage; - EFI_HII_PACKAGE_HEADER EndPackage; - UINT32 HiiSectionHeaderSize; - UINT8 *HiiSectionHeader; - UINT64 NewBaseAddress; - BOOLEAN NegativeAddr; - FILE *ReportFile; - CHAR8 *ReportFileName; - UINTN FileLen; - time_t InputFileTime; - time_t OutputFileTime; - struct stat Stat_Buf; - BOOLEAN ZeroDebugFlag; - - SetUtilityName (UTILITY_NAME); - - // - // Assign to fix compile warning - // - FileLen = 0; - InputFileNum = 0; - InputFileName = NULL; - mInImageName = NULL; - OutImageName = NULL; - ModuleType = NULL; - Type = 0; - Status = STATUS_SUCCESS; - FileBuffer = NULL; - fpIn = NULL; - fpOut = NULL; - fpInOut = NULL; - TimeStamp = NULL; - MciAlignment = DEFAULT_MC_ALIGNMENT; - MciPadValue = DEFAULT_MC_PAD_BYTE_VALUE; - FileLength = 0; - MciHeader = NULL; - CheckSum = 0; - ReplaceFlag = FALSE; - LogLevel = 0; - OutputFileBuffer = NULL; - OutputFileLength = 0; - InputFileBuffer = NULL; - InputFileLength = 0; - Optional32 = NULL; - Optional64 = NULL; - KeepExceptionTableFlag = FALSE; - KeepOptionalHeaderFlag = FALSE; - KeepZeroPendingFlag = FALSE; - NumberOfFormPackage = 0; - HiiPackageListBuffer = NULL; - HiiPackageDataPointer = NULL; - EndPackage.Length = sizeof (EFI_HII_PACKAGE_HEADER); - EndPackage.Type = EFI_HII_PACKAGE_END; - memset (&HiiPackageListGuid, 0, sizeof (HiiPackageListGuid)); - HiiSectionHeaderSize = 0; - HiiSectionHeader = NULL; - NewBaseAddress = 0; - NegativeAddr = FALSE; - InputFileTime = 0; - OutputFileTime = 0; - ZeroDebugFlag = FALSE; - - if (argc == 1) { - Error (NULL, 0, 1001, "Missing options", "No input options."); - Usage (); - return STATUS_ERROR; - } - - argc --; - argv ++; - - if ((stricmp (argv[0], "-h") == 0) || (stricmp (argv[0], "--help") == 0)) { - Version (); - Usage (); - return STATUS_SUCCESS; - } - - if (stricmp (argv[0], "--version") == 0) { - Version (); - return STATUS_SUCCESS; - } - - while (argc > 0) { - if ((stricmp (argv[0], "-o") == 0) || (stricmp (argv[0], "--outputfile") == 0)) { - if (argv[1] == NULL || argv[1][0] == '-') { - Error (NULL, 0, 1003, "Invalid option value", "Output file name is missing for -o option"); - goto Finish; - } - OutImageName = argv[1]; - argc -= 2; - argv += 2; - continue; - } - - if ((stricmp (argv[0], "-e") == 0) || (stricmp (argv[0], "--efiImage") == 0)) { - if (argv[1] == NULL || argv[1][0] == '-') { - Error (NULL, 0, 1003, "Invalid option value", "Module Type is missing for -o option"); - goto Finish; - } - ModuleType = argv[1]; - if (mOutImageType == FW_ZERO_DEBUG_IMAGE) { - ZeroDebugFlag = TRUE; - } - if (mOutImageType != FW_TE_IMAGE) { - mOutImageType = FW_EFI_IMAGE; - } - argc -= 2; - argv += 2; - continue; - } - - if ((stricmp (argv[0], "-l") == 0) || (stricmp (argv[0], "--stripped") == 0)) { - mOutImageType = FW_RELOC_STRIPEED_IMAGE; - argc --; - argv ++; - continue; - } - - if ((stricmp (argv[0], "-c") == 0) || (stricmp (argv[0], "--acpi") == 0)) { - mOutImageType = FW_ACPI_IMAGE; - argc --; - argv ++; - continue; - } - - if ((stricmp (argv[0], "-t") == 0) || (stricmp (argv[0], "--terse") == 0)) { - if (mOutImageType == FW_ZERO_DEBUG_IMAGE) { - ZeroDebugFlag = TRUE; - } - mOutImageType = FW_TE_IMAGE; - argc --; - argv ++; - continue; - } - - if ((stricmp (argv[0], "-u") == 0) || (stricmp (argv[0], "--dump") == 0)) { - mOutImageType = DUMP_TE_HEADER; - argc --; - argv ++; - continue; - } - - if ((stricmp (argv[0], "-b") == 0) || (stricmp (argv[0], "--exe2bin") == 0)) { - mOutImageType = FW_BIN_IMAGE; - argc --; - argv ++; - continue; - } - - if ((stricmp (argv[0], "-z") == 0) || (stricmp (argv[0], "--zero") == 0)) { - if (mOutImageType == FW_DUMMY_IMAGE) { - mOutImageType = FW_ZERO_DEBUG_IMAGE; - } - if (mOutImageType == FW_TE_IMAGE || mOutImageType == FW_EFI_IMAGE) { - ZeroDebugFlag = TRUE; - } - argc --; - argv ++; - continue; - } - - if ((stricmp (argv[0], "-s") == 0) || (stricmp (argv[0], "--stamp") == 0)) { - mOutImageType = FW_SET_STAMP_IMAGE; - if (argv[1] == NULL || argv[1][0] == '-') { - Error (NULL, 0, 1003, "Invalid option value", "time stamp is missing for -s option"); - goto Finish; - } - TimeStamp = argv[1]; - argc -= 2; - argv += 2; - continue; - } - - if ((stricmp (argv[0], "-r") == 0) || (stricmp (argv[0], "--replace") == 0)) { - ReplaceFlag = TRUE; - argc --; - argv ++; - continue; - } - - if (stricmp (argv[0], "--keepexceptiontable") == 0) { - KeepExceptionTableFlag = TRUE; - argc --; - argv ++; - continue; - } - - if (stricmp(argv[0], "--keepoptionalheader") == 0) { - KeepOptionalHeaderFlag = TRUE; - argc--; - argv++; - continue; - } - - if (stricmp (argv[0], "--keepzeropending") == 0) { - KeepZeroPendingFlag = TRUE; - argc --; - argv ++; - continue; - } - - if ((stricmp (argv[0], "-m") == 0) || (stricmp (argv[0], "--mcifile") == 0)) { - mOutImageType = FW_MCI_IMAGE; - argc --; - argv ++; - continue; - } - - if ((stricmp (argv[0], "-j") == 0) || (stricmp (argv[0], "--join") == 0)) { - mOutImageType = FW_MERGE_IMAGE; - argc --; - argv ++; - continue; - } - - if ((stricmp (argv[0], "-a") == 0) || (stricmp (argv[0], "--align") == 0)) { - if (AsciiStringToUint64 (argv[1], FALSE, &Temp64) != EFI_SUCCESS) { - Error (NULL, 0, 1003, "Invalid option value", "%s = %s", argv[0], argv[1]); - goto Finish; - } - MciAlignment = (UINT32) Temp64; - argc -= 2; - argv += 2; - continue; - } - - if ((stricmp (argv[0], "--rebase") == 0)) { - if (argv[1][0] == '-') { - NegativeAddr = TRUE; - Status = AsciiStringToUint64 (argv[1] + 1, FALSE, &Temp64); - } else { - NegativeAddr = FALSE; - Status = AsciiStringToUint64 (argv[1], FALSE, &Temp64); - } - if (Status != EFI_SUCCESS) { - Error (NULL, 0, 1003, "Invalid option value", "%s = %s", argv[0], argv[1]); - goto Finish; - } - mOutImageType = FW_REBASE_IMAGE; - NewBaseAddress = (UINT64) Temp64; - argc -= 2; - argv += 2; - continue; - } - - if ((stricmp (argv[0], "--address") == 0)) { - if (argv[1][0] == '-') { - NegativeAddr = TRUE; - Status = AsciiStringToUint64 (argv[1] + 1, FALSE, &Temp64); - } else { - NegativeAddr = FALSE; - Status = AsciiStringToUint64 (argv[1], FALSE, &Temp64); - } - if (Status != EFI_SUCCESS) { - Error (NULL, 0, 1003, "Invalid option value", "%s = %s", argv[0], argv[1]); - goto Finish; - } - mOutImageType = FW_SET_ADDRESS_IMAGE; - NewBaseAddress = (UINT64) Temp64; - argc -= 2; - argv += 2; - continue; - } - - if ((stricmp (argv[0], "-p") == 0) || (stricmp (argv[0], "--pad") == 0)) { - if (AsciiStringToUint64 (argv[1], FALSE, &Temp64) != EFI_SUCCESS) { - Error (NULL, 0, 1003, "Invalid option value", "%s = %s", argv[0], argv[1]); - goto Finish; - } - MciPadValue = (UINT8) Temp64; - argc -= 2; - argv += 2; - continue; - } - - if ((stricmp (argv[0], "-v") == 0) || (stricmp (argv[0], "--verbose") == 0)) { - SetPrintLevel (VERBOSE_LOG_LEVEL); - VerboseMsg ("Verbose output Mode Set!"); - argc --; - argv ++; - continue; - } - - if ((stricmp (argv[0], "-q") == 0) || (stricmp (argv[0], "--quiet") == 0)) { - SetPrintLevel (KEY_LOG_LEVEL); - KeyMsg ("Quiet output Mode Set!"); - argc --; - argv ++; - continue; - } - - if ((stricmp (argv[0], "-d") == 0) || (stricmp (argv[0], "--debug") == 0)) { - Status = AsciiStringToUint64 (argv[1], FALSE, &LogLevel); - if (EFI_ERROR (Status)) { - Error (NULL, 0, 1003, "Invalid option value", "%s = %s", argv[0], argv[1]); - goto Finish; - } - if (LogLevel > 9) { - Error (NULL, 0, 1003, "Invalid option value", "Debug Level range is 0-9, current input level is %d", (int) LogLevel); - goto Finish; - } - SetPrintLevel (LogLevel); - DebugMsg (NULL, 0, 9, "Debug Mode Set", "Debug Output Mode Level %s is set!", argv[1]); - argc -= 2; - argv += 2; - continue; - } - - if ((stricmp (argv[0], "-g") == 0) || (stricmp (argv[0], "--hiiguid") == 0)) { - Status = StringToGuid (argv[1], &HiiPackageListGuid); - if (EFI_ERROR (Status)) { - Error (NULL, 0, 1003, "Invalid option value", "%s = %s", argv[0], argv[1]); - goto Finish; - } - argc -= 2; - argv += 2; - continue; - } - - if (stricmp (argv[0], "--hiipackage") == 0) { - mOutImageType = FW_HII_PACKAGE_LIST_RCIMAGE; - argc --; - argv ++; - continue; - } - - if (stricmp (argv[0], "--hiibinpackage") == 0) { - mOutImageType = FW_HII_PACKAGE_LIST_BINIMAGE; - argc --; - argv ++; - continue; - } - - if (stricmp (argv[0], "--prm") == 0) { - if (stricmp (ModuleType, "DXE_RUNTIME_DRIVER") != 0 ){ - Error (NULL, 0, 1001, "Invalid", "--prm option only supports DXE RUNTIME driver."); - goto Finish; - } - - if (!mExportFlag) { - mExportFlag = TRUE; - } - argc --; - argv ++; - continue; - } - - if (stricmp (argv[0], "--nonxcompat") == 0) { - mNoNxCompat = TRUE; - argc --; - argv ++; - continue; - } - - if (argv[0][0] == '-') { - Error (NULL, 0, 1000, "Unknown option", argv[0]); - goto Finish; - } - // - // Get Input file name - // - if ((InputFileNum == 0) && (InputFileName == NULL)) { - InputFileName = (CHAR8 **) malloc (MAXIMUM_INPUT_FILE_NUM * sizeof (CHAR8 *)); - if (InputFileName == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - goto Finish; - } - - memset (InputFileName, 0, (MAXIMUM_INPUT_FILE_NUM * sizeof (CHAR8 *))); - } else if (InputFileNum % MAXIMUM_INPUT_FILE_NUM == 0) { - // - // InputFileName buffer too small, need to realloc - // - InputFileName = (CHAR8 **) realloc ( - InputFileName, - (InputFileNum + MAXIMUM_INPUT_FILE_NUM) * sizeof (CHAR8 *) - ); - - if (InputFileName == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - goto Finish; - } - - memset (&(InputFileName[InputFileNum]), 0, (MAXIMUM_INPUT_FILE_NUM * sizeof (CHAR8 *))); - } - - InputFileName [InputFileNum ++] = argv[0]; - argc --; - argv ++; - } - - VerboseMsg ("%s tool start.", UTILITY_NAME); - - if (mOutImageType == FW_DUMMY_IMAGE) { - Error (NULL, 0, 1001, "Missing option", "No create file action specified; pls specify -e, -c or -t option to create efi image, or acpi table or TeImage!"); - if (ReplaceFlag) { - Error (NULL, 0, 1001, "Missing option", "-r option is not supported as the independent option. It can be used together with other create file option specified at the above."); - } - goto Finish; - } - - // - // check input files - // - if (InputFileNum == 0) { - Error (NULL, 0, 1001, "Missing option", "Input files"); - goto Finish; - } - - // - // Combine MciBinary files to one file - // - if ((mOutImageType == FW_MERGE_IMAGE) && ReplaceFlag) { - Error (NULL, 0, 1002, "Conflicting option", "-r replace option cannot be used with -j merge files option."); - goto Finish; - } - - // - // Combine HiiBinary packages to a single package list - // - if ((mOutImageType == FW_HII_PACKAGE_LIST_RCIMAGE) && ReplaceFlag) { - Error (NULL, 0, 1002, "Conflicting option", "-r replace option cannot be used with --hiipackage merge files option."); - goto Finish; - } - - if ((mOutImageType == FW_HII_PACKAGE_LIST_BINIMAGE) && ReplaceFlag) { - Error (NULL, 0, 1002, "Conflicting option", "-r replace option cannot be used with --hiibinpackage merge files option."); - goto Finish; - } - - // - // Input image file - // - mInImageName = InputFileName [InputFileNum - 1]; - VerboseMsg ("the input file name is %s", mInImageName); - - // - // Action will be taken for the input file. - // - switch (mOutImageType) { - case FW_EFI_IMAGE: - VerboseMsg ("Create efi image on module type %s based on the input PE image.", ModuleType); - break; - case FW_TE_IMAGE: - VerboseMsg ("Create Te Image based on the input PE image."); - break; - case FW_ACPI_IMAGE: - VerboseMsg ("Get acpi table data from the input PE image."); - break; - case FW_RELOC_STRIPEED_IMAGE: - VerboseMsg ("Remove relocation section from Pe or Te image."); - break; - case FW_BIN_IMAGE: - VerboseMsg ("Convert the input EXE to the output BIN file."); - break; - case FW_ZERO_DEBUG_IMAGE: - VerboseMsg ("Zero the Debug Data Fields and Time Stamp in input PE image."); - break; - case FW_SET_STAMP_IMAGE: - VerboseMsg ("Set new time stamp %s in the input PE image.", TimeStamp); - break; - case DUMP_TE_HEADER: - VerboseMsg ("Dump the TE header information of the input TE image."); - break; - case FW_MCI_IMAGE: - VerboseMsg ("Convert input MicroCode.txt file to MicroCode.bin file."); - break; - case FW_MERGE_IMAGE: - VerboseMsg ("Combine the input multi microcode bin files to one bin file."); - break; - case FW_HII_PACKAGE_LIST_RCIMAGE: - VerboseMsg ("Combine the input multi hii bin packages to one text package list RC file."); - break; - case FW_HII_PACKAGE_LIST_BINIMAGE: - VerboseMsg ("Combine the input multi hii bin packages to one binary package list file."); - break; - case FW_REBASE_IMAGE: - VerboseMsg ("Rebase the input image to new base address."); - break; - case FW_SET_ADDRESS_IMAGE: - VerboseMsg ("Set the preferred address into the section header of the input image"); - break; - default: - break; - } - - if (ReplaceFlag) { - VerboseMsg ("Overwrite the input file with the output content."); - } - - // - // Open output file and Write image into the output file. - // - if (OutImageName != NULL) { - fpOut = fopen (LongFilePath (OutImageName), "rb"); - if (fpOut != NULL) { - // - // Get Output file time stamp - // - fstat(fileno (fpOut), &Stat_Buf); - OutputFileTime = Stat_Buf.st_mtime; - // - // Get Output file data - // - OutputFileLength = _filelength (fileno (fpOut)); - OutputFileBuffer = malloc (OutputFileLength); - if (OutputFileBuffer == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - fclose (fpOut); - fpOut = NULL; - goto Finish; - } - fread (OutputFileBuffer, 1, OutputFileLength, fpOut); - fclose (fpOut); - fpOut = NULL; - } - VerboseMsg ("Output file name is %s", OutImageName); - } else if (!ReplaceFlag && mOutImageType != DUMP_TE_HEADER) { - Error (NULL, 0, 1001, "Missing option", "output file"); - goto Finish; - } - - // - // Open input file and read file data into file buffer. - // - fpIn = fopen (LongFilePath (mInImageName), "rb"); - if (fpIn == NULL) { - Error (NULL, 0, 0001, "Error opening file", mInImageName); - goto Finish; - } - // - // Get Iutput file time stamp - // - fstat(fileno (fpIn), &Stat_Buf); - InputFileTime = Stat_Buf.st_mtime; - // - // Get Input file data - // - InputFileLength = _filelength (fileno (fpIn)); - InputFileBuffer = malloc (InputFileLength); - if (InputFileBuffer == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - fclose (fpIn); - goto Finish; - } - fread (InputFileBuffer, 1, InputFileLength, fpIn); - fclose (fpIn); - DebugMsg (NULL, 0, 9, "input file info", "the input file size is %u bytes", (unsigned) InputFileLength); - - // - // Combine multi binary HII package files. - // - if (mOutImageType == FW_HII_PACKAGE_LIST_RCIMAGE || mOutImageType == FW_HII_PACKAGE_LIST_BINIMAGE) { - // - // Open output file handle. - // - fpOut = fopen (LongFilePath (OutImageName), "wb"); - if (!fpOut) { - Error (NULL, 0, 0001, "Error opening output file", OutImageName); - goto Finish; - } - // - // Get hii package list length - // - HiiPackageListHeader.PackageLength = sizeof (EFI_HII_PACKAGE_LIST_HEADER); - for (Index = 0; Index < InputFileNum; Index ++) { - fpIn = fopen (LongFilePath (InputFileName [Index]), "rb"); - if (fpIn == NULL) { - Error (NULL, 0, 0001, "Error opening file", InputFileName [Index]); - goto Finish; - } - FileLength = _filelength (fileno (fpIn)); - fread (&HiiPackageHeader, 1, sizeof (HiiPackageHeader), fpIn); - if (HiiPackageHeader.Type == EFI_HII_PACKAGE_FORM) { - if (HiiPackageHeader.Length != FileLength) { - Error (NULL, 0, 3000, "Invalid", "The wrong package size is in HII package file %s", InputFileName [Index]); - fclose (fpIn); - goto Finish; - } - if (memcmp (&HiiPackageListGuid, &mZeroGuid, sizeof (EFI_GUID)) == 0) { - fread (&IfrFormSet, 1, sizeof (IfrFormSet), fpIn); - memcpy (&HiiPackageListGuid, &IfrFormSet.Guid, sizeof (EFI_GUID)); - } - NumberOfFormPackage ++; - } - HiiPackageListHeader.PackageLength += FileLength; - fclose (fpIn); - } - HiiPackageListHeader.PackageLength += sizeof (EndPackage); - // - // Check whether hii packages are valid - // - if (NumberOfFormPackage > 1) { - Error (NULL, 0, 3000, "Invalid", "The input hii packages contains more than one hii form package"); - goto Finish; - } - if (memcmp (&HiiPackageListGuid, &mZeroGuid, sizeof (EFI_GUID)) == 0) { - Error (NULL, 0, 3000, "Invalid", "HII package list guid is not specified!"); - goto Finish; - } - memcpy (&HiiPackageListHeader.PackageListGuid, &HiiPackageListGuid, sizeof (EFI_GUID)); - // - // read hii packages - // - HiiPackageListBuffer = malloc (HiiPackageListHeader.PackageLength); - if (HiiPackageListBuffer == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - goto Finish; - } - memcpy (HiiPackageListBuffer, &HiiPackageListHeader, sizeof (HiiPackageListHeader)); - HiiPackageDataPointer = HiiPackageListBuffer + sizeof (HiiPackageListHeader); - for (Index = 0; Index < InputFileNum; Index ++) { - fpIn = fopen (LongFilePath (InputFileName [Index]), "rb"); - if (fpIn == NULL) { - Error (NULL, 0, 0001, "Error opening file", InputFileName [Index]); - free (HiiPackageListBuffer); - goto Finish; - } - - FileLength = _filelength (fileno (fpIn)); - fread (HiiPackageDataPointer, 1, FileLength, fpIn); - fclose (fpIn); - HiiPackageDataPointer = HiiPackageDataPointer + FileLength; - } - memcpy (HiiPackageDataPointer, &EndPackage, sizeof (EndPackage)); - - // - // write the hii package into the binary package list file with the resource section header - // - if (mOutImageType == FW_HII_PACKAGE_LIST_BINIMAGE) { - // - // Create the resource section header - // - HiiSectionHeader = CreateHiiResouceSectionHeader (&HiiSectionHeaderSize, HiiPackageListHeader.PackageLength); - if (HiiSectionHeader == NULL) { - free (HiiPackageListBuffer); - goto Finish; - } - // - // Wrtie section header and HiiData into File. - // - fwrite (HiiSectionHeader, 1, HiiSectionHeaderSize, fpOut); - fwrite (HiiPackageListBuffer, 1, HiiPackageListHeader.PackageLength, fpOut); - // - // Free allocated resources. - // - free (HiiSectionHeader); - free (HiiPackageListBuffer); - // - // Done successfully - // - goto Finish; - } - - // - // write the hii package into the text package list rc file. - // - if (mOutImageType == FW_HII_PACKAGE_LIST_RCIMAGE) { - for (Index = 0; gHiiPackageRCFileHeader[Index] != NULL; Index++) { - fprintf (fpOut, "%s\n", gHiiPackageRCFileHeader[Index]); - } - fprintf (fpOut, "\n%d %s\n{", HII_RESOURCE_SECTION_INDEX, HII_RESOURCE_SECTION_NAME); - - HiiPackageDataPointer = HiiPackageListBuffer; - for (Index = 0; Index + 2 < HiiPackageListHeader.PackageLength; Index += 2) { - if (Index % 16 == 0) { - fprintf (fpOut, "\n "); - } - fprintf (fpOut, " 0x%04X,", *(UINT16 *) HiiPackageDataPointer); - HiiPackageDataPointer += 2; - } - - if (Index % 16 == 0) { - fprintf (fpOut, "\n "); - } - if ((Index + 2) == HiiPackageListHeader.PackageLength) { - fprintf (fpOut, " 0x%04X\n}\n", *(UINT16 *) HiiPackageDataPointer); - } - if ((Index + 1) == HiiPackageListHeader.PackageLength) { - fprintf (fpOut, " 0x%04X\n}\n", *(UINT8 *) HiiPackageDataPointer); - } - free (HiiPackageListBuffer); - // - // Done successfully - // - goto Finish; - } - } - - // - // Combine MciBinary files to one file - // - if (mOutImageType == FW_MERGE_IMAGE) { - // - // Open output file handle. - // - fpOut = fopen (LongFilePath (OutImageName), "wb"); - if (!fpOut) { - Error (NULL, 0, 0001, "Error opening output file", OutImageName); - goto Finish; - } - for (Index = 0; Index < InputFileNum; Index ++) { - fpIn = fopen (LongFilePath (InputFileName [Index]), "rb"); - if (!fpIn) { - Error (NULL, 0, 0001, "Error opening file", InputFileName [Index]); - goto Finish; - } - - FileLength = _filelength (fileno (fpIn)); - FileBuffer = malloc (FileLength); - if (FileBuffer == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - fclose (fpIn); - goto Finish; - } - - fread (FileBuffer, 1, FileLength, fpIn); - fclose (fpIn); - // - // write input file to out file - // - fwrite (FileBuffer, 1, FileLength, fpOut); - // - // write pad value to out file. - // - while (FileLength ++ % MciAlignment != 0) { - fwrite (&MciPadValue, 1, 1, fpOut); - } - // - // free allocated memory space - // - free (FileBuffer); - FileBuffer = NULL; - } - // - // Done successfully - // - goto Finish; - } - - // - // Convert MicroCode.txt file to MicroCode.bin file - // - if (mOutImageType == FW_MCI_IMAGE) { - fpIn = fopen (LongFilePath (mInImageName), "r"); - if (fpIn == NULL) { - Error (NULL, 0, 0001, "Error opening file", mInImageName); - goto Finish; - } - - // - // The first pass is to determine - // how much data is in the file so we can allocate a working buffer. - // - FileLength = 0; - do { - Status = MicrocodeReadData (fpIn, &Data); - if (Status == STATUS_SUCCESS) { - FileLength += sizeof (Data); - } - if (Status == STATUS_IGNORE) { - Status = STATUS_SUCCESS; - } - } while (Status == STATUS_SUCCESS); - // - // Error if no data. - // - if (FileLength == 0) { - Error (NULL, 0, 3000, "Invalid", "no parseable data found in file %s", mInImageName); - goto Finish; - } - if (FileLength < sizeof (MICROCODE_IMAGE_HEADER)) { - Error (NULL, 0, 3000, "Invalid", "amount of parseable data in %s is insufficient to contain a microcode header", mInImageName); - goto Finish; - } - - // - // Allocate a buffer for the data - // - FileBuffer = malloc (FileLength); - if (FileBuffer == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - goto Finish; - } - // - // Re-read the file, storing the data into our buffer - // - fseek (fpIn, 0, SEEK_SET); - DataPointer = (UINT32 *) FileBuffer; - OldDataPointer = DataPointer; - do { - OldDataPointer = DataPointer; - Status = MicrocodeReadData (fpIn, DataPointer++); - if (Status == STATUS_IGNORE) { - DataPointer = OldDataPointer; - Status = STATUS_SUCCESS; - } - } while (Status == STATUS_SUCCESS); - // - // close input file after read data - // - fclose (fpIn); - - // - // Can't do much checking on the header because, per the spec, the - // DataSize field may be 0, which means DataSize = 2000 and TotalSize = 2K, - // and the TotalSize field is invalid (actually missing). Thus we can't - // even verify the Reserved fields are 0. - // - MciHeader = (MICROCODE_IMAGE_HEADER *) FileBuffer; - if (MciHeader->DataSize == 0) { - Index = 2048; - } else { - Index = MciHeader->TotalSize; - } - - if (Index != FileLength) { - Error (NULL, 0, 3000, "Invalid", "file length of %s (0x%x) does not equal expected TotalSize: 0x%04X.", mInImageName, (unsigned) FileLength, (unsigned) Index); - goto Finish; - } - - // - // Checksum the contents - // - DataPointer = (UINT32 *) FileBuffer; - CheckSum = 0; - Index = 0; - while (Index < FileLength) { - CheckSum += *DataPointer; - DataPointer ++; - Index += sizeof (*DataPointer); - } - if (CheckSum != 0) { - Error (NULL, 0, 3000, "Invalid", "checksum (0x%x) failed on file %s.", (unsigned) CheckSum, mInImageName); - goto Finish; - } - // - // Open the output file and write the buffer contents - // - VerboseMsg ("the size of output file is %u bytes", (unsigned) FileLength); - goto WriteFile; - } - - // - // Open input file and read file data into file buffer. - // - FileLength = InputFileLength; - FileBuffer = malloc (FileLength); - if (FileBuffer == NULL) { - Error (NULL, 0, 4001, "Resource", "memory cannot be allocated!"); - goto Finish; - } - memcpy (FileBuffer, InputFileBuffer, InputFileLength); - - // - // Dump TeImage Header into output file. - // - if (mOutImageType == DUMP_TE_HEADER) { - memcpy (&TEImageHeader, FileBuffer, sizeof (TEImageHeader)); - if (TEImageHeader.Signature != EFI_TE_IMAGE_HEADER_SIGNATURE) { - Error (NULL, 0, 3000, "Invalid", "TE header signature of file %s is not correct.", mInImageName); - goto Finish; - } - // - // Open the output file handle. - // - if (ReplaceFlag) { - fpInOut = fopen (LongFilePath (mInImageName), "wb"); - if (fpInOut == NULL) { - Error (NULL, 0, 0001, "Error opening file", mInImageName); - goto Finish; - } - } else { - if (OutImageName != NULL) { - fpOut = fopen (LongFilePath (OutImageName), "wb"); - } else { - fpOut = stdout; - } - if (fpOut == NULL) { - Error (NULL, 0, 0001, "Error opening output file", OutImageName); - goto Finish; - } - } - if (fpInOut != NULL) { - fprintf (fpInOut, "Dump of file %s\n\n", mInImageName); - fprintf (fpInOut, "TE IMAGE HEADER VALUES\n"); - fprintf (fpInOut, "%17X machine\n", TEImageHeader.Machine); - fprintf (fpInOut, "%17X number of sections\n", TEImageHeader.NumberOfSections); - fprintf (fpInOut, "%17X subsystems\n", TEImageHeader.Subsystem); - fprintf (fpInOut, "%17X stripped size\n", TEImageHeader.StrippedSize); - fprintf (fpInOut, "%17X entry point\n", (unsigned) TEImageHeader.AddressOfEntryPoint); - fprintf (fpInOut, "%17X base of code\n", (unsigned) TEImageHeader.BaseOfCode); - fprintf (fpInOut, "%17llX image base\n", (unsigned long long)TEImageHeader.ImageBase); - fprintf (fpInOut, "%17X [%8X] RVA [size] of Base Relocation Directory\n", (unsigned) TEImageHeader.DataDirectory[0].VirtualAddress, (unsigned) TEImageHeader.DataDirectory[0].Size); - fprintf (fpInOut, "%17X [%8X] RVA [size] of Debug Directory\n", (unsigned) TEImageHeader.DataDirectory[1].VirtualAddress, (unsigned) TEImageHeader.DataDirectory[1].Size); - } - if (fpOut != NULL) { - fprintf (fpOut, "Dump of file %s\n\n", mInImageName); - fprintf (fpOut, "TE IMAGE HEADER VALUES\n"); - fprintf (fpOut, "%17X machine\n", TEImageHeader.Machine); - fprintf (fpOut, "%17X number of sections\n", TEImageHeader.NumberOfSections); - fprintf (fpOut, "%17X subsystems\n", TEImageHeader.Subsystem); - fprintf (fpOut, "%17X stripped size\n", TEImageHeader.StrippedSize); - fprintf (fpOut, "%17X entry point\n", (unsigned) TEImageHeader.AddressOfEntryPoint); - fprintf (fpOut, "%17X base of code\n", (unsigned) TEImageHeader.BaseOfCode); - fprintf (fpOut, "%17llX image base\n", (unsigned long long)TEImageHeader.ImageBase); - fprintf (fpOut, "%17X [%8X] RVA [size] of Base Relocation Directory\n", (unsigned) TEImageHeader.DataDirectory[0].VirtualAddress, (unsigned) TEImageHeader.DataDirectory[0].Size); - fprintf (fpOut, "%17X [%8X] RVA [size] of Debug Directory\n", (unsigned) TEImageHeader.DataDirectory[1].VirtualAddress, (unsigned) TEImageHeader.DataDirectory[1].Size); - } - goto Finish; - } - - // - // Following code to convert dll to efi image or te image. - // Get new image type - // - if ((mOutImageType == FW_EFI_IMAGE) || (mOutImageType == FW_TE_IMAGE)) { - if (ModuleType == NULL) { - if (mOutImageType == FW_EFI_IMAGE) { - Error (NULL, 0, 1001, "Missing option", "EFI_FILETYPE"); - goto Finish; - } else if (mOutImageType == FW_TE_IMAGE) { - // - // Default TE Image Type is Boot service driver - // - Type = EFI_IMAGE_SUBSYSTEM_EFI_BOOT_SERVICE_DRIVER; - VerboseMsg ("Efi Image subsystem type is efi boot service driver."); - } - } else { - if (stricmp (ModuleType, "BASE") == 0 || - stricmp (ModuleType, "SEC") == 0 || - stricmp (ModuleType, "SECURITY_CORE") == 0 || - stricmp (ModuleType, "PEI_CORE") == 0 || - stricmp (ModuleType, "PEIM") == 0 || - stricmp (ModuleType, "COMBINED_PEIM_DRIVER") == 0 || - stricmp (ModuleType, "PIC_PEIM") == 0 || - stricmp (ModuleType, "RELOCATABLE_PEIM") == 0 || - stricmp (ModuleType, "DXE_CORE") == 0 || - stricmp (ModuleType, "BS_DRIVER") == 0 || - stricmp (ModuleType, "DXE_DRIVER") == 0 || - stricmp (ModuleType, "DXE_SMM_DRIVER") == 0 || - stricmp (ModuleType, "UEFI_DRIVER") == 0 || - stricmp (ModuleType, "SMM_CORE") == 0 || - stricmp (ModuleType, "MM_STANDALONE") == 0 || - stricmp (ModuleType, "MM_CORE_STANDALONE") == 0) { - Type = EFI_IMAGE_SUBSYSTEM_EFI_BOOT_SERVICE_DRIVER; - VerboseMsg ("Efi Image subsystem type is efi boot service driver."); - - } else if (stricmp (ModuleType, "UEFI_APPLICATION") == 0 || - stricmp (ModuleType, "APPLICATION") == 0) { - Type = EFI_IMAGE_SUBSYSTEM_EFI_APPLICATION; - VerboseMsg ("Efi Image subsystem type is efi application."); - - } else if (stricmp (ModuleType, "DXE_RUNTIME_DRIVER") == 0 || - stricmp (ModuleType, "RT_DRIVER") == 0) { - Type = EFI_IMAGE_SUBSYSTEM_EFI_RUNTIME_DRIVER; - VerboseMsg ("Efi Image subsystem type is efi runtime driver."); - - } else if (stricmp (ModuleType, "DXE_SAL_DRIVER") == 0 || - stricmp (ModuleType, "SAL_RT_DRIVER") == 0) { - Type = EFI_IMAGE_SUBSYSTEM_SAL_RUNTIME_DRIVER; - VerboseMsg ("Efi Image subsystem type is efi sal runtime driver."); - - } else { - Error (NULL, 0, 1003, "Invalid option value", "EFI_FILETYPE = %s", ModuleType); - goto Finish; - } - } - } - - // - // Convert ELF image to PeImage - // - if (IsElfHeader(FileBuffer)) { - VerboseMsg ("Convert %s from ELF to PE/COFF.", mInImageName); - if (!ConvertElf(&FileBuffer, &FileLength)) { - Error (NULL, 0, 3000, "Invalid", "Unable to convert %s from ELF to PE/COFF.", mInImageName); - goto Finish; - } - } - - // - // Make sure File Offsets and Virtual Offsets are the same in the image so it is XIP - // XIP == eXecute In Place - // - PeCoffConvertImageToXip (&FileBuffer, &FileLength); - - // - // Remove reloc section from PE or TE image - // - if (mOutImageType == FW_RELOC_STRIPEED_IMAGE) { - // - // Check TeImage - // - TeHdr = (EFI_TE_IMAGE_HEADER *) FileBuffer; - if (TeHdr->Signature == EFI_TE_IMAGE_HEADER_SIGNATURE) { - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) (TeHdr + 1); - for (Index = 0; Index < TeHdr->NumberOfSections; Index ++, SectionHeader ++) { - if (strcmp ((char *)SectionHeader->Name, ".reloc") == 0) { - // - // Check the reloc section is in the end of image. - // - if ((SectionHeader->PointerToRawData + SectionHeader->SizeOfRawData) == - (FileLength + TeHdr->StrippedSize - sizeof (EFI_TE_IMAGE_HEADER))) { - // - // Remove .reloc section and update TeImage Header - // - FileLength = FileLength - SectionHeader->SizeOfRawData; - SectionHeader->SizeOfRawData = 0; - SectionHeader->Misc.VirtualSize = 0; - TeHdr->DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress = 0; - TeHdr->DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size = 0; - break; - } - } - } - } else { - // - // Check PE Image - // - DosHdr = (EFI_IMAGE_DOS_HEADER *) FileBuffer; - if (DosHdr->e_magic != EFI_IMAGE_DOS_SIGNATURE) { - PeHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(FileBuffer); - if (PeHdr->Pe32.Signature != EFI_IMAGE_NT_SIGNATURE) { - Error (NULL, 0, 3000, "Invalid", "TE and DOS header signatures were not found in %s image.", mInImageName); - goto Finish; - } - DosHdr = NULL; - } else { - PeHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(FileBuffer + DosHdr->e_lfanew); - if (PeHdr->Pe32.Signature != EFI_IMAGE_NT_SIGNATURE) { - Error (NULL, 0, 3000, "Invalid", "PE header signature was not found in %s image.", mInImageName); - goto Finish; - } - } - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) &(PeHdr->Pe32.OptionalHeader) + PeHdr->Pe32.FileHeader.SizeOfOptionalHeader); - for (Index = 0; Index < PeHdr->Pe32.FileHeader.NumberOfSections; Index ++, SectionHeader ++) { - if (strcmp ((char *)SectionHeader->Name, ".reloc") == 0) { - // - // Check the reloc section is in the end of image. - // - if ((SectionHeader->PointerToRawData + SectionHeader->SizeOfRawData) == FileLength) { - // - // Remove .reloc section and update PeImage Header - // - FileLength = FileLength - SectionHeader->SizeOfRawData; - - PeHdr->Pe32.FileHeader.Characteristics |= EFI_IMAGE_FILE_RELOCS_STRIPPED; - if (PeHdr->Pe32.OptionalHeader.Magic == EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC) { - Optional32 = (EFI_IMAGE_OPTIONAL_HEADER32 *)&PeHdr->Pe32.OptionalHeader; - Optional32->SizeOfImage -= SectionHeader->SizeOfRawData; - Optional32->SizeOfInitializedData -= SectionHeader->SizeOfRawData; - if (Optional32->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC) { - Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress = 0; - Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size = 0; - } - } - if (PeHdr->Pe32.OptionalHeader.Magic == EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC) { - Optional64 = (EFI_IMAGE_OPTIONAL_HEADER64 *)&PeHdr->Pe32.OptionalHeader; - Optional64->SizeOfImage -= SectionHeader->SizeOfRawData; - Optional64->SizeOfInitializedData -= SectionHeader->SizeOfRawData; - if (Optional64->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC) { - Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress = 0; - Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size = 0; - } - } - SectionHeader->Misc.VirtualSize = 0; - SectionHeader->SizeOfRawData = 0; - break; - } - } - } - } - // - // Write file - // - goto WriteFile; - } - // - // Read the dos & pe hdrs of the image - // - DosHdr = (EFI_IMAGE_DOS_HEADER *)FileBuffer; - if (DosHdr->e_magic != EFI_IMAGE_DOS_SIGNATURE) { - // NO DOS header, check for PE/COFF header - PeHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(FileBuffer); - if (PeHdr->Pe32.Signature != EFI_IMAGE_NT_SIGNATURE) { - Error (NULL, 0, 3000, "Invalid", "DOS header signature was not found in %s image.", mInImageName); - goto Finish; - } - DosHdr = NULL; - } else { - - PeHdr = (EFI_IMAGE_OPTIONAL_HEADER_UNION *)(FileBuffer + DosHdr->e_lfanew); - if (PeHdr->Pe32.Signature != EFI_IMAGE_NT_SIGNATURE) { - Error (NULL, 0, 3000, "Invalid", "PE header signature was not found in %s image.", mInImageName); - goto Finish; - } - } - - // - // Set new base address into image - // - if (mOutImageType == FW_REBASE_IMAGE || mOutImageType == FW_SET_ADDRESS_IMAGE) { - if (PeHdr->Pe32.OptionalHeader.Magic == EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC) { - if (NewBaseAddress >= 0x100000000ULL) { - Error (NULL, 0, 3000, "Invalid", "New base address is larger than 4G for 32bit PE image"); - goto Finish; - } - } - - if (NegativeAddr) { - // - // Set Base Address to a negative value. - // - NewBaseAddress = (UINT64) (0 - NewBaseAddress); - } - if (mOutImageType == FW_REBASE_IMAGE) { - Status = RebaseImage (mInImageName, FileBuffer, NewBaseAddress); - } else { - Status = SetAddressToSectionHeader (mInImageName, FileBuffer, NewBaseAddress); - } - if (EFI_ERROR (Status)) { - if (NegativeAddr) { - Error (NULL, 0, 3000, "Invalid", "Rebase/Set Image %s to Base address -0x%llx can't success", mInImageName, 0 - NewBaseAddress); - } else { - Error (NULL, 0, 3000, "Invalid", "Rebase/Set Image %s to Base address 0x%llx can't success", mInImageName, NewBaseAddress); - } - goto Finish; - } - - // - // Write file - // - goto WriteFile; - } - - // - // Extract bin data from Pe image. - // - if (mOutImageType == FW_BIN_IMAGE) { - if (FileLength < PeHdr->Pe32.OptionalHeader.SizeOfHeaders) { - Error (NULL, 0, 3000, "Invalid", "FileSize of %s is not a legal size.", mInImageName); - goto Finish; - } - // - // Output bin data from exe file - // - FileLength = FileLength - PeHdr->Pe32.OptionalHeader.SizeOfHeaders; - memmove (FileBuffer, FileBuffer + PeHdr->Pe32.OptionalHeader.SizeOfHeaders, FileLength); - VerboseMsg ("the size of output file is %u bytes", (unsigned) FileLength); - goto WriteFile; - } - - // - // Zero Debug Information of Pe Image - // - if (mOutImageType == FW_ZERO_DEBUG_IMAGE) { - Status = ZeroDebugData (FileBuffer, TRUE); - if (EFI_ERROR (Status)) { - Error (NULL, 0, 3000, "Invalid", "Zero DebugData Error status is 0x%x", (int) Status); - goto Finish; - } - - // - // Write the updated Image - // - VerboseMsg ("the size of output file is %u bytes", (unsigned) FileLength); - goto WriteFile; - } - - // - // Set Time Stamp of Pe Image - // - if (mOutImageType == FW_SET_STAMP_IMAGE) { - Status = SetStamp (FileBuffer, TimeStamp); - if (EFI_ERROR (Status)) { - goto Finish; - } - - // - // Write the updated Image - // - VerboseMsg ("the size of output file is %u bytes", (unsigned) FileLength); - goto WriteFile; - } - - // - // Extract acpi data from pe image. - // - if (mOutImageType == FW_ACPI_IMAGE) { - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) &(PeHdr->Pe32.OptionalHeader) + PeHdr->Pe32.FileHeader.SizeOfOptionalHeader); - for (Index = 0; Index < PeHdr->Pe32.FileHeader.NumberOfSections; Index ++, SectionHeader ++) { - if (strcmp ((char *)SectionHeader->Name, ".data") == 0 || strcmp ((char *)SectionHeader->Name, ".sdata") == 0) { - // - // Check Acpi Table - // - if (SectionHeader->Misc.VirtualSize < SectionHeader->SizeOfRawData) { - FileLength = SectionHeader->Misc.VirtualSize; - } else { - FileLength = SectionHeader->SizeOfRawData; - } - - if (CheckAcpiTable (FileBuffer + SectionHeader->PointerToRawData, FileLength) != STATUS_SUCCESS) { - Error (NULL, 0, 3000, "Invalid", "ACPI table check failed in %s.", mInImageName); - goto Finish; - } - - // - // Output Apci data to file - // - memmove (FileBuffer, FileBuffer + SectionHeader->PointerToRawData, FileLength); - VerboseMsg ("the size of output file is %u bytes", (unsigned) FileLength); - goto WriteFile; - } - } - Error (NULL, 0, 3000, "Invalid", "failed to get ACPI table from %s.", mInImageName); - goto Finish; - } - // - // Zero all unused fields of the DOS header - // - if (DosHdr != NULL) { - memcpy (&BackupDosHdr, DosHdr, sizeof (EFI_IMAGE_DOS_HEADER)); - memset (DosHdr, 0, sizeof (EFI_IMAGE_DOS_HEADER)); - DosHdr->e_magic = BackupDosHdr.e_magic; - DosHdr->e_lfanew = BackupDosHdr.e_lfanew; - - for (Index = sizeof (EFI_IMAGE_DOS_HEADER); Index < (UINT32 ) DosHdr->e_lfanew; Index++) { - FileBuffer[Index] = (UINT8) DosHdr->e_cp; - } - } - - // - // Initialize TeImage Header - // - memset (&TEImageHeader, 0, sizeof (EFI_TE_IMAGE_HEADER)); - TEImageHeader.Signature = EFI_TE_IMAGE_HEADER_SIGNATURE; - TEImageHeader.Machine = PeHdr->Pe32.FileHeader.Machine; - TEImageHeader.NumberOfSections = (UINT8) PeHdr->Pe32.FileHeader.NumberOfSections; - TEImageHeader.StrippedSize = (UINT16) ((UINTN) ((UINT8 *) &(PeHdr->Pe32.OptionalHeader) + PeHdr->Pe32.FileHeader.SizeOfOptionalHeader) - (UINTN) FileBuffer); - TEImageHeader.Subsystem = (UINT8) Type; - - // - // Patch the PE header - // - PeHdr->Pe32.OptionalHeader.Subsystem = (UINT16) Type; - - if (PeHdr->Pe32.OptionalHeader.Magic == EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC) { - Optional32 = (EFI_IMAGE_OPTIONAL_HEADER32 *)&PeHdr->Pe32.OptionalHeader; - if (!KeepOptionalHeaderFlag) { - Optional32->MajorOperatingSystemVersion = 0; - Optional32->MinorOperatingSystemVersion = 0; - Optional32->MajorImageVersion = 0; - Optional32->MinorImageVersion = 0; - Optional32->MajorSubsystemVersion = 0; - Optional32->MinorSubsystemVersion = 0; - Optional32->Win32VersionValue = 0; - Optional32->CheckSum = 0; - Optional32->SizeOfStackReserve = 0; - Optional32->SizeOfStackCommit = 0; - Optional32->SizeOfHeapReserve = 0; - Optional32->SizeOfHeapCommit = 0; - } - TEImageHeader.AddressOfEntryPoint = Optional32->AddressOfEntryPoint; - TEImageHeader.BaseOfCode = Optional32->BaseOfCode; - TEImageHeader.ImageBase = (UINT64) (Optional32->ImageBase); - - if (Optional32->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC) { - TEImageHeader.DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress = Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress; - TEImageHeader.DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size = Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size; - } - - if (Optional32->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_DEBUG) { - TEImageHeader.DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress = Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress; - TEImageHeader.DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_DEBUG].Size = Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size; - } - - // - // Zero .pdata section data. - // - if (!KeepExceptionTableFlag && Optional32->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION && - Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION].VirtualAddress != 0 && - Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION].Size != 0) { - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) &(PeHdr->Pe32.OptionalHeader) + PeHdr->Pe32.FileHeader.SizeOfOptionalHeader); - for (Index = 0; Index < PeHdr->Pe32.FileHeader.NumberOfSections; Index++, SectionHeader++) { - if (SectionHeader->VirtualAddress == Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION].VirtualAddress) { - // - // Zero .pdata Section data - // - memset (FileBuffer + SectionHeader->PointerToRawData, 0, SectionHeader->SizeOfRawData); - // - // Zero .pdata Section header name - // - memset (SectionHeader->Name, 0, sizeof (SectionHeader->Name)); - // - // Zero Exception Table - // - Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION].VirtualAddress = 0; - Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION].Size = 0; - DebugMsg (NULL, 0, 9, "Zero the .pdata section for PE image", NULL); - break; - } - } - } - - // - // Strip zero padding at the end of the .reloc section - // - if (!KeepZeroPendingFlag && Optional32->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC) { - if (Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size != 0) { - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) &(PeHdr->Pe32.OptionalHeader) + PeHdr->Pe32.FileHeader.SizeOfOptionalHeader); - for (Index = 0; Index < PeHdr->Pe32.FileHeader.NumberOfSections; Index++, SectionHeader++) { - // - // Look for the Section Header that starts as the same virtual address as the Base Relocation Data Directory - // - if (SectionHeader->VirtualAddress == Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress) { - SectionHeader->Misc.VirtualSize = Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size; - AllignedRelocSize = (Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size + Optional32->FileAlignment - 1) & (~(Optional32->FileAlignment - 1)); - // - // Check to see if there is zero padding at the end of the base relocations - // - if (AllignedRelocSize < SectionHeader->SizeOfRawData) { - // - // Check to see if the base relocations are at the end of the file - // - if (SectionHeader->PointerToRawData + SectionHeader->SizeOfRawData == Optional32->SizeOfImage) { - // - // All the required conditions are met to strip the zero padding of the end of the base relocations section - // - Optional32->SizeOfImage -= (SectionHeader->SizeOfRawData - AllignedRelocSize); - Optional32->SizeOfInitializedData -= (SectionHeader->SizeOfRawData - AllignedRelocSize); - SectionHeader->SizeOfRawData = AllignedRelocSize; - FileLength = Optional32->SizeOfImage; - DebugMsg (NULL, 0, 9, "Remove the zero padding bytes at the end of the base relocations", "The size of padding bytes is %u", (unsigned) (SectionHeader->SizeOfRawData - AllignedRelocSize)); - } - } - } - } - } - } - } else if (PeHdr->Pe32.OptionalHeader.Magic == EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC) { - Optional64 = (EFI_IMAGE_OPTIONAL_HEADER64 *)&PeHdr->Pe32.OptionalHeader; - if (!KeepOptionalHeaderFlag) { - Optional64->MajorOperatingSystemVersion = 0; - Optional64->MinorOperatingSystemVersion = 0; - Optional64->MajorImageVersion = 0; - Optional64->MinorImageVersion = 0; - Optional64->MajorSubsystemVersion = 0; - Optional64->MinorSubsystemVersion = 0; - Optional64->Win32VersionValue = 0; - Optional64->CheckSum = 0; - Optional64->SizeOfStackReserve = 0; - Optional64->SizeOfStackCommit = 0; - Optional64->SizeOfHeapReserve = 0; - Optional64->SizeOfHeapCommit = 0; - } - TEImageHeader.AddressOfEntryPoint = Optional64->AddressOfEntryPoint; - TEImageHeader.BaseOfCode = Optional64->BaseOfCode; - TEImageHeader.ImageBase = (UINT64) (Optional64->ImageBase); - - // Set NxCompat flag - if (IsNxCompatCompliant (PeHdr) && !mNoNxCompat) { - Optional64->DllCharacteristics |= IMAGE_DLLCHARACTERISTICS_NX_COMPAT; - } - - if (Optional64->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC) { - TEImageHeader.DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress = Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress; - TEImageHeader.DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size = Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size; - } - - if (Optional64->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_DEBUG) { - TEImageHeader.DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress = Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress; - TEImageHeader.DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_DEBUG].Size = Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size; - } - - // - // Zero the .pdata section for X64 machine and don't check the Debug Directory is empty - // For Itaninum and X64 Image, remove .pdata section. - // - if ((!KeepExceptionTableFlag && PeHdr->Pe32.FileHeader.Machine == IMAGE_FILE_MACHINE_X64)) { - if (Optional64->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION && - Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION].VirtualAddress != 0 && - Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION].Size != 0) { - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) &(PeHdr->Pe32.OptionalHeader) + PeHdr->Pe32.FileHeader.SizeOfOptionalHeader); - for (Index = 0; Index < PeHdr->Pe32.FileHeader.NumberOfSections; Index++, SectionHeader++) { - if (SectionHeader->VirtualAddress == Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION].VirtualAddress) { - // - // Zero .pdata Section header name - // - memset (SectionHeader->Name, 0, sizeof (SectionHeader->Name)); - - RuntimeFunction = (RUNTIME_FUNCTION *)(FileBuffer + SectionHeader->PointerToRawData); - for (Index1 = 0; Index1 < Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION].Size / sizeof (RUNTIME_FUNCTION); Index1++, RuntimeFunction++) { - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) &(PeHdr->Pe32.OptionalHeader) + PeHdr->Pe32.FileHeader.SizeOfOptionalHeader); - for (Index2 = 0; Index2 < PeHdr->Pe32.FileHeader.NumberOfSections; Index2++, SectionHeader++) { - if (RuntimeFunction->UnwindInfoAddress >= SectionHeader->VirtualAddress && RuntimeFunction->UnwindInfoAddress < (SectionHeader->VirtualAddress + SectionHeader->SizeOfRawData)) { - UnwindInfo = (UNWIND_INFO *)(FileBuffer + SectionHeader->PointerToRawData + (RuntimeFunction->UnwindInfoAddress - SectionHeader->VirtualAddress)); - if (UnwindInfo->Version == 1) { - memset (UnwindInfo + 1, 0, UnwindInfo->CountOfUnwindCodes * sizeof (UINT16)); - memset (UnwindInfo, 0, sizeof (UNWIND_INFO)); - } - break; - } - } - memset (RuntimeFunction, 0, sizeof (RUNTIME_FUNCTION)); - } - // - // Zero Exception Table - // - Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION].Size = 0; - Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXCEPTION].VirtualAddress = 0; - DebugMsg (NULL, 0, 9, "Zero the .pdata section if the machine type is X64 for PE32+ image", NULL); - break; - } - } - } - } - - // - // Strip zero padding at the end of the .reloc section - // - if (!KeepZeroPendingFlag && Optional64->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_DEBUG) { - if (Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size != 0) { - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) &(PeHdr->Pe32.OptionalHeader) + PeHdr->Pe32.FileHeader.SizeOfOptionalHeader); - for (Index = 0; Index < PeHdr->Pe32.FileHeader.NumberOfSections; Index++, SectionHeader++) { - // - // Look for the Section Header that starts as the same virtual address as the Base Relocation Data Directory - // - if (SectionHeader->VirtualAddress == Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress) { - SectionHeader->Misc.VirtualSize = Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size; - AllignedRelocSize = (Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size + Optional64->FileAlignment - 1) & (~(Optional64->FileAlignment - 1)); - // - // Check to see if there is zero padding at the end of the base relocations - // - if (AllignedRelocSize < SectionHeader->SizeOfRawData) { - // - // Check to see if the base relocations are at the end of the file - // - if (SectionHeader->PointerToRawData + SectionHeader->SizeOfRawData == Optional64->SizeOfImage) { - // - // All the required conditions are met to strip the zero padding of the end of the base relocations section - // - Optional64->SizeOfImage -= (SectionHeader->SizeOfRawData - AllignedRelocSize); - Optional64->SizeOfInitializedData -= (SectionHeader->SizeOfRawData - AllignedRelocSize); - SectionHeader->SizeOfRawData = AllignedRelocSize; - FileLength = Optional64->SizeOfImage; - DebugMsg (NULL, 0, 9, "Remove the zero padding bytes at the end of the base relocations", "The size of padding bytes is %u", (unsigned) (SectionHeader->SizeOfRawData - AllignedRelocSize)); - } - } - } - } - } - } - } else { - Error (NULL, 0, 3000, "Invalid", "Magic 0x%x of PeImage %s is unknown.", PeHdr->Pe32.OptionalHeader.Magic, mInImageName); - goto Finish; - } - - if (((PeHdr->Pe32.FileHeader.Characteristics & EFI_IMAGE_FILE_RELOCS_STRIPPED) == 0) && \ - (TEImageHeader.DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress == 0) && \ - (TEImageHeader.DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_BASERELOC].Size == 0)) { - // - // PeImage can be loaded into memory, but it has no relocation section. - // Fix TeImage Header to set VA of relocation data directory to not zero, the size is still zero. - // - if (Optional32 != NULL) { - TEImageHeader.DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress = Optional32->SizeOfImage - sizeof (EFI_IMAGE_BASE_RELOCATION); - } else if (Optional64 != NULL) { - TEImageHeader.DataDirectory[EFI_TE_IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress = Optional64->SizeOfImage - sizeof (EFI_IMAGE_BASE_RELOCATION); - } - } - - // - // Fill HII section data - // - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) &(PeHdr->Pe32.OptionalHeader) + PeHdr->Pe32.FileHeader.SizeOfOptionalHeader); - for (Index = 0; Index < PeHdr->Pe32.FileHeader.NumberOfSections; Index++) { - if (stricmp ((char *)SectionHeader[Index].Name, ".hii") == 0) { - // - // Update resource section header offset - // - SetHiiResourceHeader ((UINT8*) FileBuffer + SectionHeader[Index].PointerToRawData, SectionHeader[Index].VirtualAddress); - // - // Update resource section name - // - strcpy((char *) SectionHeader[Index].Name, ".rsrc"); - // - // Update resource data directory. - // - if (PeHdr->Pe32.OptionalHeader.Magic == EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC) { - Optional32 = (EFI_IMAGE_OPTIONAL_HEADER32 *)&PeHdr->Pe32.OptionalHeader; - Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress = SectionHeader[Index].VirtualAddress; - Optional32->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].Size = SectionHeader[Index].Misc.VirtualSize; - } else if (PeHdr->Pe32.OptionalHeader.Magic == EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC) { - Optional64 = (EFI_IMAGE_OPTIONAL_HEADER64 *)&PeHdr->Pe32.OptionalHeader; - Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress = SectionHeader[Index].VirtualAddress; - Optional64->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].Size = SectionHeader[Index].Misc.VirtualSize; - } - break; - } - } - - // - // Zero ExceptionTable Xdata - // - if (!KeepExceptionTableFlag) { - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) &(PeHdr->Pe32.OptionalHeader) + PeHdr->Pe32.FileHeader.SizeOfOptionalHeader); - for (Index = 0; Index < PeHdr->Pe32.FileHeader.NumberOfSections; Index++) { - if (stricmp ((char *)SectionHeader[Index].Name, ".xdata") == 0) { - // - // zero .xdata section - // - memset (FileBuffer + SectionHeader[Index].PointerToRawData, 0, SectionHeader[Index].SizeOfRawData); - DebugMsg (NULL, 0, 9, NULL, "Zero the .xdata section for PE image at Offset 0x%x and Length 0x%x", (unsigned) SectionHeader[Index].PointerToRawData, (unsigned) SectionHeader[Index].SizeOfRawData); - break; - } - } - } - - // - // Zero Time/Data field - // - ZeroDebugData (FileBuffer, ZeroDebugFlag); - - if (mOutImageType == FW_TE_IMAGE) { - if ((PeHdr->Pe32.FileHeader.NumberOfSections &~0xFF) || (Type &~0xFF)) { - // - // Pack the subsystem and NumberOfSections into 1 byte. Make sure they fit both. - // - Error (NULL, 0, 3000, "Invalid", "Image's subsystem or NumberOfSections of PeImage %s cannot be packed into 1 byte.", mInImageName); - goto Finish; - } - - if ((PeHdr->Pe32.OptionalHeader.SectionAlignment != PeHdr->Pe32.OptionalHeader.FileAlignment)) { - // - // TeImage has the same section alignment and file alignment. - // - Error (NULL, 0, 3000, "Invalid", "Section-Alignment and File-Alignment of PeImage %s do not match, they must be equal for a TeImage.", mInImageName); - goto Finish; - } - - DebugMsg (NULL, 0, 9, "TeImage Header Info", "Machine type is %X, Number of sections is %X, Stripped size is %X, EntryPoint is %X, BaseOfCode is %X, ImageBase is %llX", - TEImageHeader.Machine, TEImageHeader.NumberOfSections, TEImageHeader.StrippedSize, (unsigned) TEImageHeader.AddressOfEntryPoint, (unsigned) TEImageHeader.BaseOfCode, (unsigned long long) TEImageHeader.ImageBase); - // - // Update Image to TeImage - // - FileLength = FileLength - TEImageHeader.StrippedSize; - memmove (FileBuffer + sizeof (EFI_TE_IMAGE_HEADER), FileBuffer + TEImageHeader.StrippedSize, FileLength); - FileLength = FileLength + sizeof (EFI_TE_IMAGE_HEADER); - memcpy (FileBuffer, &TEImageHeader, sizeof (EFI_TE_IMAGE_HEADER)); - VerboseMsg ("the size of output file is %u bytes", (unsigned) (FileLength)); - } else { - - // - // Following codes are to fix the objcopy's issue: - // objcopy in binutil 2.50.18 will set PE image's charactices to "RELOC_STRIPPED" if image has no ".reloc" section - // It cause issue for EFI image which has no ".reloc" sections. - // Following codes will be removed when objcopy in binutil fix this problem for PE image. - // - if ((PeHdr->Pe32.FileHeader.Characteristics & EFI_IMAGE_FILE_RELOCS_STRIPPED) != 0) { - if (PeHdr->Pe32.OptionalHeader.Magic == EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC) { - Optional32 = (EFI_IMAGE_OPTIONAL_HEADER32 *)&PeHdr->Pe32.OptionalHeader; - if (Optional32->ImageBase == 0) { - PeHdr->Pe32.FileHeader.Characteristics &= ~EFI_IMAGE_FILE_RELOCS_STRIPPED; - } - } else if (PeHdr->Pe32.OptionalHeader.Magic == EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC) { - Optional64 = (EFI_IMAGE_OPTIONAL_HEADER64 *)&PeHdr->Pe32.OptionalHeader; - if (Optional64->ImageBase == 0) { - PeHdr->Pe32.FileHeader.Characteristics &= ~EFI_IMAGE_FILE_RELOCS_STRIPPED; - } - } - } - } - -WriteFile: - // - // Update Image to EfiImage or TE image - // - if (ReplaceFlag) { - if ((FileLength != InputFileLength) || (memcmp (FileBuffer, InputFileBuffer, FileLength) != 0)) { - // - // Update File when File is changed. - // - fpInOut = fopen (LongFilePath (mInImageName), "wb"); - if (fpInOut == NULL) { - Error (NULL, 0, 0001, "Error opening file", mInImageName); - goto Finish; - } - fwrite (FileBuffer, 1, FileLength, fpInOut); - VerboseMsg ("the size of output file is %u bytes", (unsigned) FileLength); - } - } else { - if ((OutputFileTime < InputFileTime) || (FileLength != OutputFileLength) || (memcmp (FileBuffer, OutputFileBuffer, FileLength) != 0)) { - // - // Update File when File is changed or File is old. - // - fpOut = fopen (LongFilePath (OutImageName), "wb"); - if (fpOut == NULL) { - Error (NULL, 0, 0001, "Error opening output file", OutImageName); - goto Finish; - } - fwrite (FileBuffer, 1, FileLength, fpOut); - VerboseMsg ("the size of output file is %u bytes", (unsigned) FileLength); - } - } - mImageSize = FileLength; - -Finish: - if (fpInOut != NULL) { - if (GetUtilityStatus () != STATUS_SUCCESS) { - // - // when file updates failed, original file is still recovered. - // - fwrite (InputFileBuffer, 1, InputFileLength, fpInOut); - } - // - // Write converted data into fpInOut file and close input file. - // - fclose (fpInOut); - } - - if (FileBuffer != NULL) { - free (FileBuffer); - } - - if (InputFileName != NULL) { - free (InputFileName); - } - - if (fpOut != NULL) { - // - // Write converted data into fpOut file and close output file. - // - fclose (fpOut); - if (GetUtilityStatus () != STATUS_SUCCESS) { - if (OutputFileBuffer == NULL) { - remove (OutImageName); - } else { - fpOut = fopen (LongFilePath (OutImageName), "wb"); - fwrite (OutputFileBuffer, 1, OutputFileLength, fpOut); - fclose (fpOut); - } - } - } - - if (InputFileBuffer != NULL) { - free (InputFileBuffer); - } - - if (OutputFileBuffer != NULL) { - free (OutputFileBuffer); - } - - // - // Write module size and time stamp to report file. - // - if (OutImageName != NULL) { - FileLen = strlen (OutImageName); - } - if (FileLen >= 4 && strcmp (OutImageName + (FileLen - 4), ".efi") == 0) { - ReportFileName = (CHAR8 *) malloc (FileLen + 1); - if (ReportFileName != NULL) { - strcpy (ReportFileName, OutImageName); - strcpy (ReportFileName + (FileLen - 4), ".txt"); - ReportFile = fopen (LongFilePath (ReportFileName), "w+"); - if (ReportFile != NULL) { - fprintf (ReportFile, "MODULE_SIZE = %u\n", (unsigned) mImageSize); - fprintf (ReportFile, "TIME_STAMP = %u\n", (unsigned) mImageTimeStamp); - fclose(ReportFile); - } - free (ReportFileName); - } - } - VerboseMsg ("%s tool done with return code is 0x%x.", UTILITY_NAME, GetUtilityStatus ()); - - return GetUtilityStatus (); -} - -STATIC -EFI_STATUS -ZeroDebugData ( - IN OUT UINT8 *FileBuffer, - BOOLEAN ZeroDebugFlag - ) -/*++ - -Routine Description: - - Zero debug information in PeImage. - -Arguments: - - FileBuffer - Pointer to PeImage. - ZeroDebugFlag - TRUE to zero Debug information, FALSE to only zero time/stamp - -Returns: - - EFI_ABORTED - PeImage is invalid. - EFI_SUCCESS - Zero debug data successfully. - ---*/ -{ - UINT32 Index; - UINT32 DebugDirectoryEntryRva; - UINT32 DebugDirectoryEntrySize; - UINT32 DebugDirectoryEntryFileOffset; - UINT32 ExportDirectoryEntryRva; - UINT32 ExportDirectoryEntryFileOffset; - UINT32 ResourceDirectoryEntryRva; - UINT32 ResourceDirectoryEntryFileOffset; - EFI_IMAGE_DOS_HEADER *DosHdr; - EFI_IMAGE_FILE_HEADER *FileHdr; - EFI_IMAGE_OPTIONAL_HEADER32 *Optional32Hdr; - EFI_IMAGE_OPTIONAL_HEADER64 *Optional64Hdr; - EFI_IMAGE_SECTION_HEADER *SectionHeader; - EFI_IMAGE_DEBUG_DIRECTORY_ENTRY *DebugEntry; - EFI_IMAGE_DEBUG_CODEVIEW_RSDS_ENTRY *RsdsEntry; - UINT32 *NewTimeStamp; - - // - // Init variable. - // - DebugDirectoryEntryRva = 0; - DebugDirectoryEntrySize = 0; - ExportDirectoryEntryRva = 0; - ResourceDirectoryEntryRva = 0; - DebugDirectoryEntryFileOffset = 0; - ExportDirectoryEntryFileOffset = 0; - ResourceDirectoryEntryFileOffset = 0; - DosHdr = (EFI_IMAGE_DOS_HEADER *) FileBuffer; - FileHdr = (EFI_IMAGE_FILE_HEADER *) (FileBuffer + DosHdr->e_lfanew + sizeof (UINT32)); - - - DosHdr = (EFI_IMAGE_DOS_HEADER *)FileBuffer; - if (DosHdr->e_magic != EFI_IMAGE_DOS_SIGNATURE) { - // NO DOS header, must start with PE/COFF header - FileHdr = (EFI_IMAGE_FILE_HEADER *)(FileBuffer + sizeof (UINT32)); - } else { - FileHdr = (EFI_IMAGE_FILE_HEADER *)(FileBuffer + DosHdr->e_lfanew + sizeof (UINT32)); - } - - // - // Get Debug, Export and Resource EntryTable RVA address. - // Resource Directory entry need to review. - // - Optional32Hdr = (EFI_IMAGE_OPTIONAL_HEADER32 *) ((UINT8*) FileHdr + sizeof (EFI_IMAGE_FILE_HEADER)); - Optional64Hdr = (EFI_IMAGE_OPTIONAL_HEADER64 *) ((UINT8*) FileHdr + sizeof (EFI_IMAGE_FILE_HEADER)); - if (Optional32Hdr->Magic == EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC) { - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) Optional32Hdr + FileHdr->SizeOfOptionalHeader); - if (Optional32Hdr->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_EXPORT && \ - Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXPORT].Size != 0) { - ExportDirectoryEntryRva = Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress; - } - if (Optional32Hdr->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE && \ - Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].Size != 0) { - ResourceDirectoryEntryRva = Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress; - } - if (Optional32Hdr->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_DEBUG && \ - Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size != 0) { - DebugDirectoryEntryRva = Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress; - DebugDirectoryEntrySize = Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size; - if (ZeroDebugFlag) { - Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size = 0; - Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress = 0; - } - } - } else { - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) Optional64Hdr + FileHdr->SizeOfOptionalHeader); - if (Optional64Hdr->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_EXPORT && \ - Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXPORT].Size != 0) { - ExportDirectoryEntryRva = Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress; - } - if (Optional64Hdr->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE && \ - Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].Size != 0) { - ResourceDirectoryEntryRva = Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress; - } - if (Optional64Hdr->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_DEBUG && \ - Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size != 0) { - DebugDirectoryEntryRva = Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress; - DebugDirectoryEntrySize = Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size; - if (ZeroDebugFlag) { - Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size = 0; - Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress = 0; - } - } - } - - // - // Get DirectoryEntryTable file offset. - // - for (Index = 0; Index < FileHdr->NumberOfSections; Index ++, SectionHeader ++) { - if (DebugDirectoryEntryRva >= SectionHeader->VirtualAddress && - DebugDirectoryEntryRva < SectionHeader->VirtualAddress + SectionHeader->Misc.VirtualSize) { - DebugDirectoryEntryFileOffset = - DebugDirectoryEntryRva - SectionHeader->VirtualAddress + SectionHeader->PointerToRawData; - } - if (ExportDirectoryEntryRva >= SectionHeader->VirtualAddress && - ExportDirectoryEntryRva < SectionHeader->VirtualAddress + SectionHeader->Misc.VirtualSize) { - ExportDirectoryEntryFileOffset = - ExportDirectoryEntryRva - SectionHeader->VirtualAddress + SectionHeader->PointerToRawData; - } - if (ResourceDirectoryEntryRva >= SectionHeader->VirtualAddress && - ResourceDirectoryEntryRva < SectionHeader->VirtualAddress + SectionHeader->Misc.VirtualSize) { - ResourceDirectoryEntryFileOffset = - ResourceDirectoryEntryRva - SectionHeader->VirtualAddress + SectionHeader->PointerToRawData; - } - } - - // - //Zero Debug Data and TimeStamp - // - FileHdr->TimeDateStamp = 0; - mImageTimeStamp = 0; - if (ExportDirectoryEntryFileOffset != 0) { - NewTimeStamp = (UINT32 *) (FileBuffer + ExportDirectoryEntryFileOffset + sizeof (UINT32)); - *NewTimeStamp = 0; - } - - if (ResourceDirectoryEntryFileOffset != 0) { - NewTimeStamp = (UINT32 *) (FileBuffer + ResourceDirectoryEntryFileOffset + sizeof (UINT32)); - *NewTimeStamp = 0; - } - - if (DebugDirectoryEntryFileOffset != 0) { - DebugEntry = (EFI_IMAGE_DEBUG_DIRECTORY_ENTRY *) (FileBuffer + DebugDirectoryEntryFileOffset); - Index = 0; - for (Index=0; Index < DebugDirectoryEntrySize / sizeof (EFI_IMAGE_DEBUG_DIRECTORY_ENTRY); Index ++, DebugEntry ++) { - DebugEntry->TimeDateStamp = 0; - if (mIsConvertXip) { - DebugEntry->FileOffset = DebugEntry->RVA; - } - if ((ZeroDebugFlag || DebugEntry->Type != EFI_IMAGE_DEBUG_TYPE_CODEVIEW) && - (DebugEntry->Type != EFI_IMAGE_DEBUG_TYPE_EX_DLLCHARACTERISTICS)) { - memset (FileBuffer + DebugEntry->FileOffset, 0, DebugEntry->SizeOfData); - memset (DebugEntry, 0, sizeof (EFI_IMAGE_DEBUG_DIRECTORY_ENTRY)); - } - if (DebugEntry->Type == EFI_IMAGE_DEBUG_TYPE_CODEVIEW) { - RsdsEntry = (EFI_IMAGE_DEBUG_CODEVIEW_RSDS_ENTRY *) (FileBuffer + DebugEntry->FileOffset); - if (RsdsEntry->Signature == CODEVIEW_SIGNATURE_MTOC) { - // MTOC sets DebugDirectoryEntrySize to size of the .debug section, so fix it. - if (!ZeroDebugFlag) { - if (Optional32Hdr->Magic == EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC) { - Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size = sizeof (EFI_IMAGE_DEBUG_DIRECTORY_ENTRY); - } else { - Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size = sizeof (EFI_IMAGE_DEBUG_DIRECTORY_ENTRY); - } - } - break; - } - } - } - } - - return EFI_SUCCESS; -} - -STATIC -EFI_STATUS -SetStamp ( - IN OUT UINT8 *FileBuffer, - IN CHAR8 *TimeStamp - ) -/*++ - -Routine Description: - - Set new time stamp into PeImage FileHdr and Directory table: - Debug, Export and Resource. - -Arguments: - - FileBuffer - Pointer to PeImage. - TimeStamp - Time stamp string. - -Returns: - - EFI_INVALID_PARAMETER - TimeStamp format is not recognized. - EFI_SUCCESS - Set new time stamp in this image successfully. - ---*/ -{ - struct tm stime; - struct tm *ptime; - time_t newtime; - UINT32 Index; - UINT32 DebugDirectoryEntryRva; - UINT32 DebugDirectoryEntryFileOffset; - UINT32 ExportDirectoryEntryRva; - UINT32 ExportDirectoryEntryFileOffset; - UINT32 ResourceDirectoryEntryRva; - UINT32 ResourceDirectoryEntryFileOffset; - EFI_IMAGE_DOS_HEADER *DosHdr; - EFI_IMAGE_FILE_HEADER *FileHdr; - EFI_IMAGE_OPTIONAL_HEADER32 *Optional32Hdr; - EFI_IMAGE_OPTIONAL_HEADER64 *Optional64Hdr; - EFI_IMAGE_SECTION_HEADER *SectionHeader; - UINT32 *NewTimeStamp; - - // - // Init variable. - // - DebugDirectoryEntryRva = 0; - DebugDirectoryEntryFileOffset = 0; - ExportDirectoryEntryRva = 0; - ExportDirectoryEntryFileOffset = 0; - ResourceDirectoryEntryRva = 0; - ResourceDirectoryEntryFileOffset = 0; - // - // Get time and date that will be set. - // - if (TimeStamp == NULL) { - Error (NULL, 0, 3000, "Invalid", "TimeStamp cannot be NULL."); - return EFI_INVALID_PARAMETER; - } - // - // compare the value with "NOW", if yes, current system time is set. - // - if (stricmp (TimeStamp, "NOW") == 0) { - // - // get system current time and date - // - time (&newtime); - } else { - // - // Check Time Format strictly yyyy-mm-dd 00:00:00 - // - for (Index = 0; TimeStamp[Index] != '\0' && Index < 20; Index ++) { - if (Index == 4 || Index == 7) { - if (TimeStamp[Index] == '-') { - continue; - } - } else if (Index == 13 || Index == 16) { - if (TimeStamp[Index] == ':') { - continue; - } - } else if (Index == 10 && TimeStamp[Index] == ' ') { - continue; - } else if ((TimeStamp[Index] < '0') || (TimeStamp[Index] > '9')) { - break; - } - } - - if (Index < 19 || TimeStamp[19] != '\0') { - Error (NULL, 0, 1003, "Invalid option value", "Incorrect Time \"%s\"\n Correct Format \"yyyy-mm-dd 00:00:00\"", TimeStamp); - return EFI_INVALID_PARAMETER; - } - - // - // get the date and time from TimeStamp - // - if (sscanf (TimeStamp, "%d-%d-%d %d:%d:%d", - &stime.tm_year, - &stime.tm_mon, - &stime.tm_mday, - &stime.tm_hour, - &stime.tm_min, - &stime.tm_sec - ) != 6) { - Error (NULL, 0, 1003, "Invalid option value", "Incorrect Tiem \"%s\"\n Correct Format \"yyyy-mm-dd 00:00:00\"", TimeStamp); - return EFI_INVALID_PARAMETER; - } - - // - // in struct, Month (0 - 11; Jan = 0). So decrease 1 from it - // - if (stime.tm_mon <= 0 || stime.tm_mday <=0) { - Error (NULL, 0, 3000, "Invalid", "%s Invalid date!", TimeStamp); - return EFI_INVALID_PARAMETER; - } - stime.tm_mon -= 1; - - // - // in struct, Year (current year minus 1900) - // and only the dates can be handled from Jan 1, 1970 to Jan 18, 2038 - // - // - // convert 0 -> 100 (2000), 1 -> 101 (2001), ..., 38 -> 138 (2038) - // - if (stime.tm_year >= 1970 && stime.tm_year <= 2038) { - // - // convert 1970 -> 70, 2000 -> 100, ... - // - stime.tm_year -= 1900; - } else { - Error (NULL, 0, 3000, "Invalid", "%s Invalid or unsupported datetime!", TimeStamp); - return EFI_INVALID_PARAMETER; - } - - // - // convert the date and time to time_t format - // - newtime = mktime (&stime); - if (newtime == (time_t) - 1) { - Error (NULL, 0, 3000, "Invalid", "%s Invalid or unsupported datetime!", TimeStamp); - return EFI_INVALID_PARAMETER; - } - } - - ptime = localtime (&newtime); - if (ptime != NULL) { - DebugMsg (NULL, 0, 9, "New Image Time Stamp", "%04d-%02d-%02d %02d:%02d:%02d", - ptime->tm_year + 1900, ptime->tm_mon + 1, ptime->tm_mday, ptime->tm_hour, ptime->tm_min, ptime->tm_sec); - } - // - // Set new time and data into PeImage. - // - DosHdr = (EFI_IMAGE_DOS_HEADER *)FileBuffer; - if (DosHdr->e_magic != EFI_IMAGE_DOS_SIGNATURE) { - // NO DOS header, must start with PE/COFF header - FileHdr = (EFI_IMAGE_FILE_HEADER *)(FileBuffer + sizeof (UINT32)); - } else { - FileHdr = (EFI_IMAGE_FILE_HEADER *)(FileBuffer + DosHdr->e_lfanew + sizeof (UINT32)); - } - - // - // Get Debug, Export and Resource EntryTable RVA address. - // Resource Directory entry need to review. - // - if (FileHdr->Machine == IMAGE_FILE_MACHINE_I386) { - Optional32Hdr = (EFI_IMAGE_OPTIONAL_HEADER32 *) ((UINT8*) FileHdr + sizeof (EFI_IMAGE_FILE_HEADER)); - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) Optional32Hdr + FileHdr->SizeOfOptionalHeader); - if (Optional32Hdr->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_EXPORT && \ - Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXPORT].Size != 0) { - ExportDirectoryEntryRva = Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress; - } - if (Optional32Hdr->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE && \ - Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].Size != 0) { - ResourceDirectoryEntryRva = Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress; - } - if (Optional32Hdr->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_DEBUG && \ - Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size != 0) { - DebugDirectoryEntryRva = Optional32Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress; - } - } else { - Optional64Hdr = (EFI_IMAGE_OPTIONAL_HEADER64 *) ((UINT8*) FileHdr + sizeof (EFI_IMAGE_FILE_HEADER)); - SectionHeader = (EFI_IMAGE_SECTION_HEADER *) ((UINT8 *) Optional64Hdr + FileHdr->SizeOfOptionalHeader); - if (Optional64Hdr->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_EXPORT && \ - Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXPORT].Size != 0) { - ExportDirectoryEntryRva = Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress; - } - if (Optional64Hdr->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE && \ - Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].Size != 0) { - ResourceDirectoryEntryRva = Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress; - } - if (Optional64Hdr->NumberOfRvaAndSizes > EFI_IMAGE_DIRECTORY_ENTRY_DEBUG && \ - Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].Size != 0) { - DebugDirectoryEntryRva = Optional64Hdr->DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress; - } - } - - // - // Get DirectoryEntryTable file offset. - // - for (Index = 0; Index < FileHdr->NumberOfSections; Index ++, SectionHeader ++) { - if (DebugDirectoryEntryRva >= SectionHeader->VirtualAddress && - DebugDirectoryEntryRva < SectionHeader->VirtualAddress + SectionHeader->Misc.VirtualSize) { - DebugDirectoryEntryFileOffset = - DebugDirectoryEntryRva - SectionHeader->VirtualAddress + SectionHeader->PointerToRawData; - } - if (ExportDirectoryEntryRva >= SectionHeader->VirtualAddress && - ExportDirectoryEntryRva < SectionHeader->VirtualAddress + SectionHeader->Misc.VirtualSize) { - ExportDirectoryEntryFileOffset = - ExportDirectoryEntryRva - SectionHeader->VirtualAddress + SectionHeader->PointerToRawData; - } - if (ResourceDirectoryEntryRva >= SectionHeader->VirtualAddress && - ResourceDirectoryEntryRva < SectionHeader->VirtualAddress + SectionHeader->Misc.VirtualSize) { - ResourceDirectoryEntryFileOffset = - ResourceDirectoryEntryRva - SectionHeader->VirtualAddress + SectionHeader->PointerToRawData; - } - } - - // - // Set new stamp - // - FileHdr->TimeDateStamp = (UINT32) newtime; - mImageTimeStamp = (UINT32) newtime; - if (ExportDirectoryEntryRva != 0) { - NewTimeStamp = (UINT32 *) (FileBuffer + ExportDirectoryEntryFileOffset + sizeof (UINT32)); - *NewTimeStamp = (UINT32) newtime; - } - - if (ResourceDirectoryEntryRva != 0) { - NewTimeStamp = (UINT32 *) (FileBuffer + ResourceDirectoryEntryFileOffset + sizeof (UINT32)); - *NewTimeStamp = (UINT32) newtime; - } - - if (DebugDirectoryEntryRva != 0) { - NewTimeStamp = (UINT32 *) (FileBuffer + DebugDirectoryEntryFileOffset + sizeof (UINT32)); - *NewTimeStamp = (UINT32) newtime; - } - - return EFI_SUCCESS; -} - -STATIC -STATUS -MicrocodeReadData ( - FILE *InFptr, - UINT32 *Data - ) -/*++ - -Routine Description: - Read a 32-bit microcode data value from a text file and convert to raw binary form. - -Arguments: - InFptr - file pointer to input text file - Data - pointer to where to return the data parsed - -Returns: - STATUS_SUCCESS - no errors or warnings, Data contains valid information - STATUS_ERROR - errors were encountered - ---*/ -{ - CHAR8 Line[MAX_LINE_LEN]; - CHAR8 *cptr; - int ScannedData = 0; - - Line[MAX_LINE_LEN - 1] = 0; - while (1) { - if (fgets (Line, MAX_LINE_LEN, InFptr) == NULL) { - return STATUS_ERROR; - } - // - // If it was a binary file, then it may have overwritten our null terminator - // - if (Line[MAX_LINE_LEN - 1] != 0) { - return STATUS_ERROR; - } - - // - // strip space - // - for (cptr = Line; *cptr && isspace((int)*cptr); cptr++) { - } - - // Skip Blank Lines and Comment Lines - if ((strlen(cptr) != 0) && (*cptr != ';')) { - break; - } - } - - // Look for - // dd 000000001h ; comment - // dd XXXXXXXX - // DD XXXXXXXXX - // DD XXXXXXXXX - // - if ((tolower((int)cptr[0]) == 'd') && (tolower((int)cptr[1]) == 'd') && isspace ((int)cptr[2])) { - // - // Skip blanks and look for a hex digit - // - cptr += 3; - for (; *cptr && isspace((int)*cptr); cptr++) { - } - if (isxdigit ((int)*cptr)) { - if (sscanf (cptr, "%X", &ScannedData) != 1) { - return STATUS_ERROR; - } - } - *Data = (UINT32) ScannedData; - return STATUS_SUCCESS; - } - - return STATUS_ERROR; -} diff --git a/BaseTools/Source/C/GenFw/GenFw.h b/BaseTools/Source/C/GenFw/GenFw.h deleted file mode 100644 index 469017602d..0000000000 --- a/BaseTools/Source/C/GenFw/GenFw.h +++ /dev/null @@ -1,50 +0,0 @@ -/** @file -Header file for GenFw - -Copyright (c) 2010 - 2018, Intel Corporation. All rights reserved.
- -SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -#ifndef _GEN_FW_H_ -#define _GEN_FW_H_ - -// -// Action for this tool. -// -#define FW_DUMMY_IMAGE 0 -#define FW_EFI_IMAGE 1 -#define FW_TE_IMAGE 2 -#define FW_ACPI_IMAGE 3 -#define FW_BIN_IMAGE 4 -#define FW_ZERO_DEBUG_IMAGE 5 -#define FW_SET_STAMP_IMAGE 6 -#define FW_MCI_IMAGE 7 -#define FW_MERGE_IMAGE 8 -#define FW_RELOC_STRIPEED_IMAGE 9 -#define FW_HII_PACKAGE_LIST_RCIMAGE 10 -#define FW_HII_PACKAGE_LIST_BINIMAGE 11 -#define FW_REBASE_IMAGE 12 -#define FW_SET_ADDRESS_IMAGE 13 - -#define DUMP_TE_HEADER 0x11 - -VOID -SetHiiResourceHeader ( - UINT8 *HiiBinData, - UINT32 OffsetToFile - ); - -INTN -IsElfHeader ( - UINT8 *FileBuffer - ); - -BOOLEAN -ConvertElf ( - UINT8 **FileBuffer, - UINT32 *FileLength - ); - -#endif diff --git a/BaseTools/Source/C/GenFw/Makefile b/BaseTools/Source/C/GenFw/Makefile deleted file mode 100644 index 08626c8f3a..0000000000 --- a/BaseTools/Source/C/GenFw/Makefile +++ /dev/null @@ -1,18 +0,0 @@ -## @file -# Windows makefile for 'GenFw' module build. -# -# Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.
-# SPDX-License-Identifier: BSD-2-Clause-Patent -# -!INCLUDE ..\Makefiles\ms.common - -APPNAME = GenFw - -LIBS = $(LIB_PATH)\Common.lib - -OBJECTS = GenFw.obj ElfConvert.obj Elf32Convert.obj Elf64Convert.obj - -#CFLAGS = $(CFLAGS) /nodefaultlib:libc.lib - -!INCLUDE ..\Makefiles\ms.app - diff --git a/BaseTools/Source/C/GenFw/elf32.h b/BaseTools/Source/C/GenFw/elf32.h deleted file mode 100644 index e8a56ff345..0000000000 --- a/BaseTools/Source/C/GenFw/elf32.h +++ /dev/null @@ -1,252 +0,0 @@ -/** @file -Ported ELF include files from FreeBSD - -Copyright (c) 2009 - 2010, Apple Inc. All rights reserved.
-SPDX-License-Identifier: BSD-2-Clause-Patent - - -**/ -/*- - * Copyright (c) 1996-1998 John D. Polstra. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - * $FreeBSD: src/sys/sys/elf32.h,v 1.8.14.2 2007/12/03 21:30:36 marius Exp $ - */ - -#ifndef _SYS_ELF32_H_ -#define _SYS_ELF32_H_ 1 - - -/* - * ELF definitions common to all 32-bit architectures. - */ - -typedef UINT32 Elf32_Addr; -typedef UINT16 Elf32_Half; -typedef UINT32 Elf32_Off; -typedef INT32 Elf32_Sword; -typedef UINT32 Elf32_Word; -typedef UINT64 Elf32_Lword; - -typedef Elf32_Word Elf32_Hashelt; - -/* Non-standard class-dependent datatype used for abstraction. */ -typedef Elf32_Word Elf32_Size; -typedef Elf32_Sword Elf32_Ssize; - -/* - * ELF header. - */ - -typedef struct { - unsigned char e_ident[EI_NIDENT]; /* File identification. */ - Elf32_Half e_type; /* File type. */ - Elf32_Half e_machine; /* Machine architecture. */ - Elf32_Word e_version; /* ELF format version. */ - Elf32_Addr e_entry; /* Entry point. */ - Elf32_Off e_phoff; /* Program header file offset. */ - Elf32_Off e_shoff; /* Section header file offset. */ - Elf32_Word e_flags; /* Architecture-specific flags. */ - Elf32_Half e_ehsize; /* Size of ELF header in bytes. */ - Elf32_Half e_phentsize; /* Size of program header entry. */ - Elf32_Half e_phnum; /* Number of program header entries. */ - Elf32_Half e_shentsize; /* Size of section header entry. */ - Elf32_Half e_shnum; /* Number of section header entries. */ - Elf32_Half e_shstrndx; /* Section name strings section. */ -} Elf32_Ehdr; - -/* - * Section header. - */ - -typedef struct { - Elf32_Word sh_name; /* Section name (index into the - section header string table). */ - Elf32_Word sh_type; /* Section type. */ - Elf32_Word sh_flags; /* Section flags. */ - Elf32_Addr sh_addr; /* Address in memory image. */ - Elf32_Off sh_offset; /* Offset in file. */ - Elf32_Word sh_size; /* Size in bytes. */ - Elf32_Word sh_link; /* Index of a related section. */ - Elf32_Word sh_info; /* Depends on section type. */ - Elf32_Word sh_addralign; /* Alignment in bytes. */ - Elf32_Word sh_entsize; /* Size of each entry in section. */ -} Elf32_Shdr; - -/* - * Program header. - */ - -typedef struct { - Elf32_Word p_type; /* Entry type. */ - Elf32_Off p_offset; /* File offset of contents. */ - Elf32_Addr p_vaddr; /* Virtual address in memory image. */ - Elf32_Addr p_paddr; /* Physical address (not used). */ - Elf32_Word p_filesz; /* Size of contents in file. */ - Elf32_Word p_memsz; /* Size of contents in memory. */ - Elf32_Word p_flags; /* Access permission flags. */ - Elf32_Word p_align; /* Alignment in memory and file. */ -} Elf32_Phdr; - -/* - * Dynamic structure. The ".dynamic" section contains an array of them. - */ - -typedef struct { - Elf32_Sword d_tag; /* Entry type. */ - union { - Elf32_Word d_val; /* Integer value. */ - Elf32_Addr d_ptr; /* Address value. */ - } d_un; -} Elf32_Dyn; - -/* - * Relocation entries. - */ - -/* Relocations that don't need an addend field. */ -typedef struct { - Elf32_Addr r_offset; /* Location to be relocated. */ - Elf32_Word r_info; /* Relocation type and symbol index. */ -} Elf32_Rel; - -/* Relocations that need an addend field. */ -typedef struct { - Elf32_Addr r_offset; /* Location to be relocated. */ - Elf32_Word r_info; /* Relocation type and symbol index. */ - Elf32_Sword r_addend; /* Addend. */ -} Elf32_Rela; - -/* Macros for accessing the fields of r_info. */ -#define ELF32_R_SYM(info) ((info) >> 8) -#define ELF32_R_TYPE(info) ((unsigned char)(info)) - -/* Macro for constructing r_info from field values. */ -#define ELF32_R_INFO(sym, type) (((sym) << 8) + (unsigned char)(type)) - -/* - * Note entry header - */ -typedef Elf_Note Elf32_Nhdr; - -/* - * Move entry - */ -typedef struct { - Elf32_Lword m_value; /* symbol value */ - Elf32_Word m_info; /* size + index */ - Elf32_Word m_poffset; /* symbol offset */ - Elf32_Half m_repeat; /* repeat count */ - Elf32_Half m_stride; /* stride info */ -} Elf32_Move; - -/* - * The macros compose and decompose values for Move.r_info - * - * sym = ELF32_M_SYM(M.m_info) - * size = ELF32_M_SIZE(M.m_info) - * M.m_info = ELF32_M_INFO(sym, size) - */ -#define ELF32_M_SYM(info) ((info)>>8) -#define ELF32_M_SIZE(info) ((unsigned char)(info)) -#define ELF32_M_INFO(sym, size) (((sym)<<8)+(unsigned char)(size)) - -/* - * Hardware/Software capabilities entry - */ -typedef struct { - Elf32_Word c_tag; /* how to interpret value */ - union { - Elf32_Word c_val; - Elf32_Addr c_ptr; - } c_un; -} Elf32_Cap; - -/* - * Symbol table entries. - */ - -typedef struct { - Elf32_Word st_name; /* String table index of name. */ - Elf32_Addr st_value; /* Symbol value. */ - Elf32_Word st_size; /* Size of associated object. */ - unsigned char st_info; /* Type and binding information. */ - unsigned char st_other; /* Reserved (not used). */ - Elf32_Half st_shndx; /* Section index of symbol. */ -} Elf32_Sym; - -/* Macros for accessing the fields of st_info. */ -#define ELF32_ST_BIND(info) ((info) >> 4) -#define ELF32_ST_TYPE(info) ((info) & 0xf) - -/* Macro for constructing st_info from field values. */ -#define ELF32_ST_INFO(bind, type) (((bind) << 4) + ((type) & 0xf)) - -/* Macro for accessing the fields of st_other. */ -#define ELF32_ST_VISIBILITY(oth) ((oth) & 0x3) - -/* Structures used by Sun & GNU symbol versioning. */ -typedef struct -{ - Elf32_Half vd_version; - Elf32_Half vd_flags; - Elf32_Half vd_ndx; - Elf32_Half vd_cnt; - Elf32_Word vd_hash; - Elf32_Word vd_aux; - Elf32_Word vd_next; -} Elf32_Verdef; - -typedef struct -{ - Elf32_Word vda_name; - Elf32_Word vda_next; -} Elf32_Verdaux; - -typedef struct -{ - Elf32_Half vn_version; - Elf32_Half vn_cnt; - Elf32_Word vn_file; - Elf32_Word vn_aux; - Elf32_Word vn_next; -} Elf32_Verneed; - -typedef struct -{ - Elf32_Word vna_hash; - Elf32_Half vna_flags; - Elf32_Half vna_other; - Elf32_Word vna_name; - Elf32_Word vna_next; -} Elf32_Vernaux; - -typedef Elf32_Half Elf32_Versym; - -typedef struct { - Elf32_Half si_boundto; /* direct bindings - symbol bound to */ - Elf32_Half si_flags; /* per symbol flags */ -} Elf32_Syminfo; - -#endif /* !_SYS_ELF32_H_ */ diff --git a/BaseTools/Source/C/GenFw/elf64.h b/BaseTools/Source/C/GenFw/elf64.h deleted file mode 100644 index 1ec0c2b29b..0000000000 --- a/BaseTools/Source/C/GenFw/elf64.h +++ /dev/null @@ -1,254 +0,0 @@ -/** @file -Ported ELF include files from FreeBSD - -Copyright (c) 2009 - 2010, Apple Inc. All rights reserved.
-SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ -/*- - * Copyright (c) 1996-1998 John D. Polstra. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - * $FreeBSD: src/sys/sys/elf64.h,v 1.10.14.2 2007/12/03 21:30:36 marius Exp $ - */ - -#ifndef _SYS_ELF64_H_ -#define _SYS_ELF64_H_ 1 - - -/* - * ELF definitions common to all 64-bit architectures. - */ - -typedef UINT64 Elf64_Addr; -typedef UINT16 Elf64_Half; -typedef UINT64 Elf64_Off; -typedef INT32 Elf64_Sword; -typedef INT64 Elf64_Sxword; -typedef UINT32 Elf64_Word; -typedef UINT64 Elf64_Lword; -typedef UINT64 Elf64_Xword; - -/* - * Types of dynamic symbol hash table bucket and chain elements. - * - * This is inconsistent among 64 bit architectures, so a machine dependent - * typedef is required. - */ - -typedef Elf64_Word Elf64_Hashelt; - -/* Non-standard class-dependent datatype used for abstraction. */ -typedef Elf64_Xword Elf64_Size; -typedef Elf64_Sxword Elf64_Ssize; - -/* - * ELF header. - */ - -typedef struct { - unsigned char e_ident[EI_NIDENT]; /* File identification. */ - Elf64_Half e_type; /* File type. */ - Elf64_Half e_machine; /* Machine architecture. */ - Elf64_Word e_version; /* ELF format version. */ - Elf64_Addr e_entry; /* Entry point. */ - Elf64_Off e_phoff; /* Program header file offset. */ - Elf64_Off e_shoff; /* Section header file offset. */ - Elf64_Word e_flags; /* Architecture-specific flags. */ - Elf64_Half e_ehsize; /* Size of ELF header in bytes. */ - Elf64_Half e_phentsize; /* Size of program header entry. */ - Elf64_Half e_phnum; /* Number of program header entries. */ - Elf64_Half e_shentsize; /* Size of section header entry. */ - Elf64_Half e_shnum; /* Number of section header entries. */ - Elf64_Half e_shstrndx; /* Section name strings section. */ -} Elf64_Ehdr; - -/* - * Section header. - */ - -typedef struct { - Elf64_Word sh_name; /* Section name (index into the - section header string table). */ - Elf64_Word sh_type; /* Section type. */ - Elf64_Xword sh_flags; /* Section flags. */ - Elf64_Addr sh_addr; /* Address in memory image. */ - Elf64_Off sh_offset; /* Offset in file. */ - Elf64_Xword sh_size; /* Size in bytes. */ - Elf64_Word sh_link; /* Index of a related section. */ - Elf64_Word sh_info; /* Depends on section type. */ - Elf64_Xword sh_addralign; /* Alignment in bytes. */ - Elf64_Xword sh_entsize; /* Size of each entry in section. */ -} Elf64_Shdr; - -/* - * Program header. - */ - -typedef struct { - Elf64_Word p_type; /* Entry type. */ - Elf64_Word p_flags; /* Access permission flags. */ - Elf64_Off p_offset; /* File offset of contents. */ - Elf64_Addr p_vaddr; /* Virtual address in memory image. */ - Elf64_Addr p_paddr; /* Physical address (not used). */ - Elf64_Xword p_filesz; /* Size of contents in file. */ - Elf64_Xword p_memsz; /* Size of contents in memory. */ - Elf64_Xword p_align; /* Alignment in memory and file. */ -} Elf64_Phdr; - -/* - * Dynamic structure. The ".dynamic" section contains an array of them. - */ - -typedef struct { - Elf64_Sxword d_tag; /* Entry type. */ - union { - Elf64_Xword d_val; /* Integer value. */ - Elf64_Addr d_ptr; /* Address value. */ - } d_un; -} Elf64_Dyn; - -/* - * Relocation entries. - */ - -/* Relocations that don't need an addend field. */ -typedef struct { - Elf64_Addr r_offset; /* Location to be relocated. */ - Elf64_Xword r_info; /* Relocation type and symbol index. */ -} Elf64_Rel; - -/* Relocations that need an addend field. */ -typedef struct { - Elf64_Addr r_offset; /* Location to be relocated. */ - Elf64_Xword r_info; /* Relocation type and symbol index. */ - Elf64_Sxword r_addend; /* Addend. */ -} Elf64_Rela; - -/* Macros for accessing the fields of r_info. */ -#define ELF64_R_SYM(info) ((info) >> 32) -#define ELF64_R_TYPE(info) ((info) & 0xffffffffL) - -/* Macro for constructing r_info from field values. */ -#define ELF64_R_INFO(sym, type) (((sym) << 32) + ((type) & 0xffffffffL)) - -#define ELF64_R_TYPE_DATA(info) (((Elf64_Xword)(info)<<32)>>40) -#define ELF64_R_TYPE_ID(info) (((Elf64_Xword)(info)<<56)>>56) -#define ELF64_R_TYPE_INFO(data, type) \ - (((Elf64_Xword)(data)<<8)+(Elf64_Xword)(type)) - -/* - * Note entry header - */ -typedef Elf_Note Elf64_Nhdr; - -/* - * Move entry - */ -typedef struct { - Elf64_Lword m_value; /* symbol value */ - Elf64_Xword m_info; /* size + index */ - Elf64_Xword m_poffset; /* symbol offset */ - Elf64_Half m_repeat; /* repeat count */ - Elf64_Half m_stride; /* stride info */ -} Elf64_Move; - -#define ELF64_M_SYM(info) ((info)>>8) -#define ELF64_M_SIZE(info) ((unsigned char)(info)) -#define ELF64_M_INFO(sym, size) (((sym)<<8)+(unsigned char)(size)) - -/* - * Hardware/Software capabilities entry - */ -typedef struct { - Elf64_Xword c_tag; /* how to interpret value */ - union { - Elf64_Xword c_val; - Elf64_Addr c_ptr; - } c_un; -} Elf64_Cap; - -/* - * Symbol table entries. - */ - -typedef struct { - Elf64_Word st_name; /* String table index of name. */ - unsigned char st_info; /* Type and binding information. */ - unsigned char st_other; /* Reserved (not used). */ - Elf64_Half st_shndx; /* Section index of symbol. */ - Elf64_Addr st_value; /* Symbol value. */ - Elf64_Xword st_size; /* Size of associated object. */ -} Elf64_Sym; - -/* Macros for accessing the fields of st_info. */ -#define ELF64_ST_BIND(info) ((info) >> 4) -#define ELF64_ST_TYPE(info) ((info) & 0xf) - -/* Macro for constructing st_info from field values. */ -#define ELF64_ST_INFO(bind, type) (((bind) << 4) + ((type) & 0xf)) - -/* Macro for accessing the fields of st_other. */ -#define ELF64_ST_VISIBILITY(oth) ((oth) & 0x3) - -/* Structures used by Sun & GNU-style symbol versioning. */ -typedef struct { - Elf64_Half vd_version; - Elf64_Half vd_flags; - Elf64_Half vd_ndx; - Elf64_Half vd_cnt; - Elf64_Word vd_hash; - Elf64_Word vd_aux; - Elf64_Word vd_next; -} Elf64_Verdef; - -typedef struct { - Elf64_Word vda_name; - Elf64_Word vda_next; -} Elf64_Verdaux; - -typedef struct { - Elf64_Half vn_version; - Elf64_Half vn_cnt; - Elf64_Word vn_file; - Elf64_Word vn_aux; - Elf64_Word vn_next; -} Elf64_Verneed; - -typedef struct { - Elf64_Word vna_hash; - Elf64_Half vna_flags; - Elf64_Half vna_other; - Elf64_Word vna_name; - Elf64_Word vna_next; -} Elf64_Vernaux; - -typedef Elf64_Half Elf64_Versym; - -typedef struct { - Elf64_Half si_boundto; /* direct bindings - symbol bound to */ - Elf64_Half si_flags; /* per symbol flags */ -} Elf64_Syminfo; - -#endif /* !_SYS_ELF64_H_ */ diff --git a/BaseTools/Source/C/GenFw/elf_common.h b/BaseTools/Source/C/GenFw/elf_common.h deleted file mode 100644 index e4d0cdac4f..0000000000 --- a/BaseTools/Source/C/GenFw/elf_common.h +++ /dev/null @@ -1,1159 +0,0 @@ -/** @file -Ported ELF include files from FreeBSD - -Copyright (c) 2009 - 2010, Apple Inc. All rights reserved.
-Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.
-Portion Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights reserved.
-Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All rights reserved.
-SPDX-License-Identifier: BSD-2-Clause-Patent - - -**/ -/*- - * Copyright (c) 1998 John D. Polstra. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - * $FreeBSD: src/sys/sys/elf_common.h,v 1.15.8.2 2007/12/03 21:30:36 marius Exp $ - */ - -#ifndef _SYS_ELF_COMMON_H_ -#define _SYS_ELF_COMMON_H_ 1 - -/* - * ELF definitions that are independent of architecture or word size. - */ - -/* - * Note header. The ".note" section contains an array of notes. Each - * begins with this header, aligned to a word boundary. Immediately - * following the note header is n_namesz bytes of name, padded to the - * next word boundary. Then comes n_descsz bytes of descriptor, again - * padded to a word boundary. The values of n_namesz and n_descsz do - * not include the padding. - */ - -typedef struct { - UINT32 n_namesz; /* Length of name. */ - UINT32 n_descsz; /* Length of descriptor. */ - UINT32 n_type; /* Type of this note. */ -} Elf_Note; - -#define NT_GNU_PROPERTY_TYPE_0 5 - -#define GNU_PROPERTY_X86_FEATURE_1_AND 0xc0000002 -#define GNU_PROPERTY_X86_FEATURE_1_IBT 0x1 - -#define GNU_PROPERTY_AARCH64_FEATURE_1_AND 0xc0000000 -#define GNU_PROPERTY_AARCH64_FEATURE_1_BTI 0x1 -#define GNU_PROPERTY_AARCH64_FEATURE_1_PAC 0x2 - -/* Indexes into the e_ident array. Keep synced with - http://www.sco.com/developers/gabi/latest/ch4.eheader.html */ -#define EI_MAG0 0 /* Magic number, byte 0. */ -#define EI_MAG1 1 /* Magic number, byte 1. */ -#define EI_MAG2 2 /* Magic number, byte 2. */ -#define EI_MAG3 3 /* Magic number, byte 3. */ -#define EI_CLASS 4 /* Class of machine. */ -#define EI_DATA 5 /* Data format. */ -#define EI_VERSION 6 /* ELF format version. */ -#define EI_OSABI 7 /* Operating system / ABI identification */ -#define EI_ABIVERSION 8 /* ABI version */ -#define OLD_EI_BRAND 8 /* Start of architecture identification. */ -#define EI_PAD 9 /* Start of padding (per SVR4 ABI). */ -#define EI_NIDENT 16 /* Size of e_ident array. */ - -/* Values for the magic number bytes. */ -#define ELFMAG0 0x7f -#define ELFMAG1 'E' -#define ELFMAG2 'L' -#define ELFMAG3 'F' -#define ELFMAG "\177ELF" /* magic string */ -#define SELFMAG 4 /* magic string size */ - -/* Values for e_ident[EI_VERSION] and e_version. */ -#define EV_NONE 0 -#define EV_CURRENT 1 - -/* Values for e_ident[EI_CLASS]. */ -#define ELFCLASSNONE 0 /* Unknown class. */ -#define ELFCLASS32 1 /* 32-bit architecture. */ -#define ELFCLASS64 2 /* 64-bit architecture. */ - -/* Values for e_ident[EI_DATA]. */ -#define ELFDATANONE 0 /* Unknown data format. */ -#define ELFDATA2LSB 1 /* 2's complement little-endian. */ -#define ELFDATA2MSB 2 /* 2's complement big-endian. */ - -/* Values for e_ident[EI_OSABI]. */ -#define ELFOSABI_NONE 0 /* UNIX System V ABI */ -#define ELFOSABI_HPUX 1 /* HP-UX operating system */ -#define ELFOSABI_NETBSD 2 /* NetBSD */ -#define ELFOSABI_LINUX 3 /* GNU/Linux */ -#define ELFOSABI_HURD 4 /* GNU/Hurd */ -#define ELFOSABI_86OPEN 5 /* 86Open common IA32 ABI */ -#define ELFOSABI_SOLARIS 6 /* Solaris */ -#define ELFOSABI_AIX 7 /* AIX */ -#define ELFOSABI_IRIX 8 /* IRIX */ -#define ELFOSABI_FREEBSD 9 /* FreeBSD */ -#define ELFOSABI_TRU64 10 /* TRU64 UNIX */ -#define ELFOSABI_MODESTO 11 /* Novell Modesto */ -#define ELFOSABI_OPENBSD 12 /* OpenBSD */ -#define ELFOSABI_OPENVMS 13 /* Open VMS */ -#define ELFOSABI_NSK 14 /* HP Non-Stop Kernel */ -#define ELFOSABI_ARM 97 /* ARM */ -#define ELFOSABI_STANDALONE 255 /* Standalone (embedded) application */ - -#define ELFOSABI_SYSV ELFOSABI_NONE /* symbol used in old spec */ -#define ELFOSABI_MONTEREY ELFOSABI_AIX /* Monterey */ - -/* e_ident */ -#define IS_ELF(ehdr) ((ehdr).e_ident[EI_MAG0] == ELFMAG0 && \ - (ehdr).e_ident[EI_MAG1] == ELFMAG1 && \ - (ehdr).e_ident[EI_MAG2] == ELFMAG2 && \ - (ehdr).e_ident[EI_MAG3] == ELFMAG3) - -/* Values for e_type. */ -#define ET_NONE 0 /* Unknown type. */ -#define ET_REL 1 /* Relocatable. */ -#define ET_EXEC 2 /* Executable. */ -#define ET_DYN 3 /* Shared object. */ -#define ET_CORE 4 /* Core file. */ -#define ET_LOOS 0xfe00 /* First operating system specific. */ -#define ET_HIOS 0xfeff /* Last operating system-specific. */ -#define ET_LOPROC 0xff00 /* First processor-specific. */ -#define ET_HIPROC 0xffff /* Last processor-specific. */ - -/* Values for e_machine. */ -#define EM_NONE 0 /* Unknown machine. */ -#define EM_M32 1 /* AT&T WE32100. */ -#define EM_SPARC 2 /* Sun SPARC. */ -#define EM_386 3 /* Intel i386. */ -#define EM_68K 4 /* Motorola 68000. */ -#define EM_88K 5 /* Motorola 88000. */ -#define EM_860 7 /* Intel i860. */ -#define EM_MIPS 8 /* MIPS R3000 Big-Endian only. */ -#define EM_S370 9 /* IBM System/370. */ -#define EM_MIPS_RS3_LE 10 /* MIPS R3000 Little-Endian. */ -#define EM_PARISC 15 /* HP PA-RISC. */ -#define EM_VPP500 17 /* Fujitsu VPP500. */ -#define EM_SPARC32PLUS 18 /* SPARC v8plus. */ -#define EM_960 19 /* Intel 80960. */ -#define EM_PPC 20 /* PowerPC 32-bit. */ -#define EM_PPC64 21 /* PowerPC 64-bit. */ -#define EM_S390 22 /* IBM System/390. */ -#define EM_V800 36 /* NEC V800. */ -#define EM_FR20 37 /* Fujitsu FR20. */ -#define EM_RH32 38 /* TRW RH-32. */ -#define EM_RCE 39 /* Motorola RCE. */ -#define EM_ARM 40 /* ARM. */ -#define EM_SH 42 /* Hitachi SH. */ -#define EM_SPARCV9 43 /* SPARC v9 64-bit. */ -#define EM_TRICORE 44 /* Siemens TriCore embedded processor. */ -#define EM_ARC 45 /* Argonaut RISC Core. */ -#define EM_H8_300 46 /* Hitachi H8/300. */ -#define EM_H8_300H 47 /* Hitachi H8/300H. */ -#define EM_H8S 48 /* Hitachi H8S. */ -#define EM_H8_500 49 /* Hitachi H8/500. */ -#define EM_MIPS_X 51 /* Stanford MIPS-X. */ -#define EM_COLDFIRE 52 /* Motorola ColdFire. */ -#define EM_68HC12 53 /* Motorola M68HC12. */ -#define EM_MMA 54 /* Fujitsu MMA. */ -#define EM_PCP 55 /* Siemens PCP. */ -#define EM_NCPU 56 /* Sony nCPU. */ -#define EM_NDR1 57 /* Denso NDR1 microprocessor. */ -#define EM_STARCORE 58 /* Motorola Star*Core processor. */ -#define EM_ME16 59 /* Toyota ME16 processor. */ -#define EM_ST100 60 /* STMicroelectronics ST100 processor. */ -#define EM_TINYJ 61 /* Advanced Logic Corp. TinyJ processor. */ -#define EM_X86_64 62 /* Advanced Micro Devices x86-64 */ -#define EM_AMD64 EM_X86_64 /* Advanced Micro Devices x86-64 (compat) */ -#define EM_AARCH64 183 /* ARM 64bit Architecture */ -#define EM_RISCV64 243 /* 64bit RISC-V Architecture */ -#define EM_RISCV 244 /* 32bit RISC-V Architecture */ -#define EM_LOONGARCH 258 /* LoongArch Architecture */ - -/* Non-standard or deprecated. */ -#define EM_486 6 /* Intel i486. */ -#define EM_MIPS_RS4_BE 10 /* MIPS R4000 Big-Endian */ -#define EM_ALPHA_STD 41 /* Digital Alpha (standard value). */ -#define EM_ALPHA 0x9026 /* Alpha (written in the absence of an ABI) */ - -/* Special section indexes. */ -#define SHN_UNDEF 0 /* Undefined, missing, irrelevant. */ -#define SHN_LORESERVE 0xff00 /* First of reserved range. */ -#define SHN_LOPROC 0xff00 /* First processor-specific. */ -#define SHN_HIPROC 0xff1f /* Last processor-specific. */ -#define SHN_LOOS 0xff20 /* First operating system-specific. */ -#define SHN_HIOS 0xff3f /* Last operating system-specific. */ -#define SHN_ABS 0xfff1 /* Absolute values. */ -#define SHN_COMMON 0xfff2 /* Common data. */ -#define SHN_XINDEX 0xffff /* Escape -- index stored elsewhere. */ -#define SHN_HIRESERVE 0xffff /* Last of reserved range. */ - -/* sh_type */ -#define SHT_NULL 0 /* inactive */ -#define SHT_PROGBITS 1 /* program defined information */ -#define SHT_SYMTAB 2 /* symbol table section */ -#define SHT_STRTAB 3 /* string table section */ -#define SHT_RELA 4 /* relocation section with addends */ -#define SHT_HASH 5 /* symbol hash table section */ -#define SHT_DYNAMIC 6 /* dynamic section */ -#define SHT_NOTE 7 /* note section */ -#define SHT_NOBITS 8 /* no space section */ -#define SHT_REL 9 /* relocation section - no addends */ -#define SHT_SHLIB 10 /* reserved - purpose unknown */ -#define SHT_DYNSYM 11 /* dynamic symbol table section */ -#define SHT_INIT_ARRAY 14 /* Initialization function pointers. */ -#define SHT_FINI_ARRAY 15 /* Termination function pointers. */ -#define SHT_PREINIT_ARRAY 16 /* Pre-initialization function ptrs. */ -#define SHT_GROUP 17 /* Section group. */ -#define SHT_SYMTAB_SHNDX 18 /* Section indexes (see SHN_XINDEX). */ -#define SHT_LOOS 0x60000000 /* First of OS specific semantics */ -#define SHT_LOSUNW 0x6ffffff4 -#define SHT_SUNW_dof 0x6ffffff4 -#define SHT_SUNW_cap 0x6ffffff5 -#define SHT_SUNW_SIGNATURE 0x6ffffff6 -#define SHT_SUNW_ANNOTATE 0x6ffffff7 -#define SHT_SUNW_DEBUGSTR 0x6ffffff8 -#define SHT_SUNW_DEBUG 0x6ffffff9 -#define SHT_SUNW_move 0x6ffffffa -#define SHT_SUNW_COMDAT 0x6ffffffb -#define SHT_SUNW_syminfo 0x6ffffffc -#define SHT_SUNW_verdef 0x6ffffffd -#define SHT_GNU_verdef 0x6ffffffd /* Symbol versions provided */ -#define SHT_SUNW_verneed 0x6ffffffe -#define SHT_GNU_verneed 0x6ffffffe /* Symbol versions required */ -#define SHT_SUNW_versym 0x6fffffff -#define SHT_GNU_versym 0x6fffffff /* Symbol version table */ -#define SHT_HISUNW 0x6fffffff -#define SHT_HIOS 0x6fffffff /* Last of OS specific semantics */ -#define SHT_LOPROC 0x70000000 /* reserved range for processor */ -#define SHT_AMD64_UNWIND 0x70000001 /* unwind information */ -#define SHT_HIPROC 0x7fffffff /* specific section header types */ -#define SHT_LOUSER 0x80000000 /* reserved range for application */ -#define SHT_HIUSER 0xffffffff /* specific indexes */ - -/* Flags for sh_flags. */ -#define SHF_WRITE 0x1 /* Section contains writable data. */ -#define SHF_ALLOC 0x2 /* Section occupies memory. */ -#define SHF_EXECINSTR 0x4 /* Section contains instructions. */ -#define SHF_MERGE 0x10 /* Section may be merged. */ -#define SHF_STRINGS 0x20 /* Section contains strings. */ -#define SHF_INFO_LINK 0x40 /* sh_info holds section index. */ -#define SHF_LINK_ORDER 0x80 /* Special ordering requirements. */ -#define SHF_OS_NONCONFORMING 0x100 /* OS-specific processing required. */ -#define SHF_GROUP 0x200 /* Member of section group. */ -#define SHF_TLS 0x400 /* Section contains TLS data. */ -#define SHF_MASKOS 0x0ff00000 /* OS-specific semantics. */ -#define SHF_MASKPROC 0xf0000000 /* Processor-specific semantics. */ - -/* Values for p_type. */ -#define PT_NULL 0 /* Unused entry. */ -#define PT_LOAD 1 /* Loadable segment. */ -#define PT_DYNAMIC 2 /* Dynamic linking information segment. */ -#define PT_INTERP 3 /* Pathname of interpreter. */ -#define PT_NOTE 4 /* Auxiliary information. */ -#define PT_SHLIB 5 /* Reserved (not used). */ -#define PT_PHDR 6 /* Location of program header itself. */ -#define PT_TLS 7 /* Thread local storage segment */ -#define PT_LOOS 0x60000000 /* First OS-specific. */ -#define PT_SUNW_UNWIND 0x6464e550 /* amd64 UNWIND program header */ -#define PT_GNU_EH_FRAME 0x6474e550 -#define PT_LOSUNW 0x6ffffffa -#define PT_SUNWBSS 0x6ffffffa /* Sun Specific segment */ -#define PT_SUNWSTACK 0x6ffffffb /* describes the stack segment */ -#define PT_SUNWDTRACE 0x6ffffffc /* private */ -#define PT_SUNWCAP 0x6ffffffd /* hard/soft capabilities segment */ -#define PT_HISUNW 0x6fffffff -#define PT_HIOS 0x6fffffff /* Last OS-specific. */ -#define PT_LOPROC 0x70000000 /* First processor-specific type. */ -#define PT_HIPROC 0x7fffffff /* Last processor-specific type. */ - -/* Values for p_flags. */ -#define PF_X 0x1 /* Executable. */ -#define PF_W 0x2 /* Writable. */ -#define PF_R 0x4 /* Readable. */ -#define PF_MASKOS 0x0ff00000 /* Operating system-specific. */ -#define PF_MASKPROC 0xf0000000 /* Processor-specific. */ - -/* Extended program header index. */ -#define PN_XNUM 0xffff - -/* Values for d_tag. */ -#define DT_NULL 0 /* Terminating entry. */ -#define DT_NEEDED 1 /* String table offset of a needed shared - library. */ -#define DT_PLTRELSZ 2 /* Total size in bytes of PLT relocations. */ -#define DT_PLTGOT 3 /* Processor-dependent address. */ -#define DT_HASH 4 /* Address of symbol hash table. */ -#define DT_STRTAB 5 /* Address of string table. */ -#define DT_SYMTAB 6 /* Address of symbol table. */ -#define DT_RELA 7 /* Address of ElfNN_Rela relocations. */ -#define DT_RELASZ 8 /* Total size of ElfNN_Rela relocations. */ -#define DT_RELAENT 9 /* Size of each ElfNN_Rela relocation entry. */ -#define DT_STRSZ 10 /* Size of string table. */ -#define DT_SYMENT 11 /* Size of each symbol table entry. */ -#define DT_INIT 12 /* Address of initialization function. */ -#define DT_FINI 13 /* Address of finalization function. */ -#define DT_SONAME 14 /* String table offset of shared object - name. */ -#define DT_RPATH 15 /* String table offset of library path. [sup] */ -#define DT_SYMBOLIC 16 /* Indicates "symbolic" linking. [sup] */ -#define DT_REL 17 /* Address of ElfNN_Rel relocations. */ -#define DT_RELSZ 18 /* Total size of ElfNN_Rel relocations. */ -#define DT_RELENT 19 /* Size of each ElfNN_Rel relocation. */ -#define DT_PLTREL 20 /* Type of relocation used for PLT. */ -#define DT_DEBUG 21 /* Reserved (not used). */ -#define DT_TEXTREL 22 /* Indicates there may be relocations in - non-writable segments. [sup] */ -#define DT_JMPREL 23 /* Address of PLT relocations. */ -#define DT_BIND_NOW 24 /* [sup] */ -#define DT_INIT_ARRAY 25 /* Address of the array of pointers to - initialization functions */ -#define DT_FINI_ARRAY 26 /* Address of the array of pointers to - termination functions */ -#define DT_INIT_ARRAYSZ 27 /* Size in bytes of the array of - initialization functions. */ -#define DT_FINI_ARRAYSZ 28 /* Size in bytes of the array of - terminationfunctions. */ -#define DT_RUNPATH 29 /* String table offset of a null-terminated - library search path string. */ -#define DT_FLAGS 30 /* Object specific flag values. */ -#define DT_ENCODING 32 /* Values greater than or equal to DT_ENCODING - and less than DT_LOOS follow the rules for - the interpretation of the d_un union - as follows: even == 'd_ptr', even == 'd_val' - or none */ -#define DT_PREINIT_ARRAY 32 /* Address of the array of pointers to - pre-initialization functions. */ -#define DT_PREINIT_ARRAYSZ 33 /* Size in bytes of the array of - pre-initialization functions. */ -#define DT_MAXPOSTAGS 34 /* number of positive tags */ -#define DT_LOOS 0x6000000d /* First OS-specific */ -#define DT_SUNW_AUXILIARY 0x6000000d /* symbol auxiliary name */ -#define DT_SUNW_RTLDINF 0x6000000e /* ld.so.1 info (private) */ -#define DT_SUNW_FILTER 0x6000000f /* symbol filter name */ -#define DT_SUNW_CAP 0x60000010 /* hardware/software */ -#define DT_HIOS 0x6ffff000 /* Last OS-specific */ - -/* - * DT_* entries which fall between DT_VALRNGHI & DT_VALRNGLO use the - * Dyn.d_un.d_val field of the Elf*_Dyn structure. - */ -#define DT_VALRNGLO 0x6ffffd00 -#define DT_CHECKSUM 0x6ffffdf8 /* elf checksum */ -#define DT_PLTPADSZ 0x6ffffdf9 /* pltpadding size */ -#define DT_MOVEENT 0x6ffffdfa /* move table entry size */ -#define DT_MOVESZ 0x6ffffdfb /* move table size */ -#define DT_FEATURE_1 0x6ffffdfc /* feature holder */ -#define DT_POSFLAG_1 0x6ffffdfd /* flags for DT_* entries, effecting */ - /* the following DT_* entry. */ - /* See DF_P1_* definitions */ -#define DT_SYMINSZ 0x6ffffdfe /* syminfo table size (in bytes) */ -#define DT_SYMINENT 0x6ffffdff /* syminfo entry size (in bytes) */ -#define DT_VALRNGHI 0x6ffffdff - -/* - * DT_* entries which fall between DT_ADDRRNGHI & DT_ADDRRNGLO use the - * Dyn.d_un.d_ptr field of the Elf*_Dyn structure. - * - * If any adjustment is made to the ELF object after it has been - * built, these entries will need to be adjusted. - */ -#define DT_ADDRRNGLO 0x6ffffe00 -#define DT_CONFIG 0x6ffffefa /* configuration information */ -#define DT_DEPAUDIT 0x6ffffefb /* dependency auditing */ -#define DT_AUDIT 0x6ffffefc /* object auditing */ -#define DT_PLTPAD 0x6ffffefd /* pltpadding (sparcv9) */ -#define DT_MOVETAB 0x6ffffefe /* move table */ -#define DT_SYMINFO 0x6ffffeff /* syminfo table */ -#define DT_ADDRRNGHI 0x6ffffeff - -#define DT_VERSYM 0x6ffffff0 /* Address of versym section. */ -#define DT_RELACOUNT 0x6ffffff9 /* number of RELATIVE relocations */ -#define DT_RELCOUNT 0x6ffffffa /* number of RELATIVE relocations */ -#define DT_FLAGS_1 0x6ffffffb /* state flags - see DF_1_* defs */ -#define DT_VERDEF 0x6ffffffc /* Address of verdef section. */ -#define DT_VERDEFNUM 0x6ffffffd /* Number of elems in verdef section */ -#define DT_VERNEED 0x6ffffffe /* Address of verneed section. */ -#define DT_VERNEEDNUM 0x6fffffff /* Number of elems in verneed section */ - -#define DT_LOPROC 0x70000000 /* First processor-specific type. */ -#define DT_DEPRECATED_SPARC_REGISTER 0x7000001 -#define DT_AUXILIARY 0x7ffffffd /* shared library auxiliary name */ -#define DT_USED 0x7ffffffe /* ignored - same as needed */ -#define DT_FILTER 0x7fffffff /* shared library filter name */ -#define DT_HIPROC 0x7fffffff /* Last processor-specific type. */ - -/* Values for DT_FLAGS */ -#define DF_ORIGIN 0x0001 /* Indicates that the object being loaded may - make reference to the $ORIGIN substitution - string */ -#define DF_SYMBOLIC 0x0002 /* Indicates "symbolic" linking. */ -#define DF_TEXTREL 0x0004 /* Indicates there may be relocations in - non-writable segments. */ -#define DF_BIND_NOW 0x0008 /* Indicates that the dynamic linker should - process all relocations for the object - containing this entry before transferring - control to the program. */ -#define DF_STATIC_TLS 0x0010 /* Indicates that the shared object or - executable contains code using a static - thread-local storage scheme. */ - -/* Values for n_type. Used in core files. */ -#define NT_PRSTATUS 1 /* Process status. */ -#define NT_FPREGSET 2 /* Floating point registers. */ -#define NT_PRPSINFO 3 /* Process state info. */ - -/* Symbol Binding - ELFNN_ST_BIND - st_info */ -#define STB_LOCAL 0 /* Local symbol */ -#define STB_GLOBAL 1 /* Global symbol */ -#define STB_WEAK 2 /* like global - lower precedence */ -#define STB_LOOS 10 /* Reserved range for operating system */ -#define STB_HIOS 12 /* specific semantics. */ -#define STB_LOPROC 13 /* reserved range for processor */ -#define STB_HIPROC 15 /* specific semantics. */ - -/* Symbol type - ELFNN_ST_TYPE - st_info */ -#define STT_NOTYPE 0 /* Unspecified type. */ -#define STT_OBJECT 1 /* Data object. */ -#define STT_FUNC 2 /* Function. */ -#define STT_SECTION 3 /* Section. */ -#define STT_FILE 4 /* Source file. */ -#define STT_COMMON 5 /* Uninitialized common block. */ -#define STT_TLS 6 /* TLS object. */ -#define STT_NUM 7 -#define STT_LOOS 10 /* Reserved range for operating system */ -#define STT_HIOS 12 /* specific semantics. */ -#define STT_LOPROC 13 /* reserved range for processor */ -#define STT_HIPROC 15 /* specific semantics. */ - -/* Symbol visibility - ELFNN_ST_VISIBILITY - st_other */ -#define STV_DEFAULT 0x0 /* Default visibility (see binding). */ -#define STV_INTERNAL 0x1 /* Special meaning in relocatable objects. */ -#define STV_HIDDEN 0x2 /* Not visible. */ -#define STV_PROTECTED 0x3 /* Visible but not preemptible. */ - -/* Special symbol table indexes. */ -#define STN_UNDEF 0 /* Undefined symbol index. */ - -/* Symbol versioning flags. */ -#define VER_DEF_CURRENT 1 -#define VER_DEF_IDX(x) VER_NDX(x) - -#define VER_FLG_BASE 0x01 -#define VER_FLG_WEAK 0x02 - -#define VER_NEED_CURRENT 1 -#define VER_NEED_WEAK (1u << 15) -#define VER_NEED_HIDDEN VER_NDX_HIDDEN -#define VER_NEED_IDX(x) VER_NDX(x) - -#define VER_NDX_LOCAL 0 -#define VER_NDX_GLOBAL 1 -#define VER_NDX_GIVEN 2 - -#define VER_NDX_HIDDEN (1u << 15) -#define VER_NDX(x) ((x) & ~(1u << 15)) - -#define CA_SUNW_NULL 0 -#define CA_SUNW_HW_1 1 /* first hardware capabilities entry */ -#define CA_SUNW_SF_1 2 /* first software capabilities entry */ - -/* - * Syminfo flag values - */ -#define SYMINFO_FLG_DIRECT 0x0001 /* symbol ref has direct association */ - /* to object containing defn. */ -#define SYMINFO_FLG_PASSTHRU 0x0002 /* ignored - see SYMINFO_FLG_FILTER */ -#define SYMINFO_FLG_COPY 0x0004 /* symbol is a copy-reloc */ -#define SYMINFO_FLG_LAZYLOAD 0x0008 /* object containing defn should be */ - /* lazily-loaded */ -#define SYMINFO_FLG_DIRECTBIND 0x0010 /* ref should be bound directly to */ - /* object containing defn. */ -#define SYMINFO_FLG_NOEXTDIRECT 0x0020 /* don't let an external reference */ - /* directly bind to this symbol */ -#define SYMINFO_FLG_FILTER 0x0002 /* symbol ref is associated to a */ -#define SYMINFO_FLG_AUXILIARY 0x0040 /* standard or auxiliary filter */ - -/* - * Syminfo.si_boundto values. - */ -#define SYMINFO_BT_SELF 0xffff /* symbol bound to self */ -#define SYMINFO_BT_PARENT 0xfffe /* symbol bound to parent */ -#define SYMINFO_BT_NONE 0xfffd /* no special symbol binding */ -#define SYMINFO_BT_EXTERN 0xfffc /* symbol defined as external */ -#define SYMINFO_BT_LOWRESERVE 0xff00 /* beginning of reserved entries */ - -/* - * Syminfo version values. - */ -#define SYMINFO_NONE 0 /* Syminfo version */ -#define SYMINFO_CURRENT 1 -#define SYMINFO_NUM 2 - -/* - * Relocation types. - * - * All machine architectures are defined here to allow tools on one to - * handle others. - */ - -#define R_386_NONE 0 /* No relocation. */ -#define R_386_32 1 /* Add symbol value. */ -#define R_386_PC32 2 /* Add PC-relative symbol value. */ -#define R_386_GOT32 3 /* Add PC-relative GOT offset. */ -#define R_386_PLT32 4 /* Add PC-relative PLT offset. */ -#define R_386_COPY 5 /* Copy data from shared object. */ -#define R_386_GLOB_DAT 6 /* Set GOT entry to data address. */ -#define R_386_JMP_SLOT 7 /* Set GOT entry to code address. */ -#define R_386_RELATIVE 8 /* Add load address of shared object. */ -#define R_386_GOTOFF 9 /* Add GOT-relative symbol address. */ -#define R_386_GOTPC 10 /* Add PC-relative GOT table address. */ -#define R_386_TLS_TPOFF 14 /* Negative offset in static TLS block */ -#define R_386_TLS_IE 15 /* Absolute address of GOT for -ve static TLS */ -#define R_386_TLS_GOTIE 16 /* GOT entry for negative static TLS block */ -#define R_386_TLS_LE 17 /* Negative offset relative to static TLS */ -#define R_386_TLS_GD 18 /* 32 bit offset to GOT (index,off) pair */ -#define R_386_TLS_LDM 19 /* 32 bit offset to GOT (index,zero) pair */ -#define R_386_TLS_GD_32 24 /* 32 bit offset to GOT (index,off) pair */ -#define R_386_TLS_GD_PUSH 25 /* pushl instruction for Sun ABI GD sequence */ -#define R_386_TLS_GD_CALL 26 /* call instruction for Sun ABI GD sequence */ -#define R_386_TLS_GD_POP 27 /* popl instruction for Sun ABI GD sequence */ -#define R_386_TLS_LDM_32 28 /* 32 bit offset to GOT (index,zero) pair */ -#define R_386_TLS_LDM_PUSH 29 /* pushl instruction for Sun ABI LD sequence */ -#define R_386_TLS_LDM_CALL 30 /* call instruction for Sun ABI LD sequence */ -#define R_386_TLS_LDM_POP 31 /* popl instruction for Sun ABI LD sequence */ -#define R_386_TLS_LDO_32 32 /* 32 bit offset from start of TLS block */ -#define R_386_TLS_IE_32 33 /* 32 bit offset to GOT static TLS offset entry */ -#define R_386_TLS_LE_32 34 /* 32 bit offset within static TLS block */ -#define R_386_TLS_DTPMOD32 35 /* GOT entry containing TLS index */ -#define R_386_TLS_DTPOFF32 36 /* GOT entry containing TLS offset */ -#define R_386_TLS_TPOFF32 37 /* GOT entry of -ve static TLS offset */ - -/* Null relocation */ -#define R_AARCH64_NONE 256 /* No relocation */ -/* Static AArch64 relocations */ - /* Static data relocations */ -#define R_AARCH64_ABS64 257 /* S + A */ -#define R_AARCH64_ABS32 258 /* S + A */ -#define R_AARCH64_ABS16 259 /* S + A */ -#define R_AARCH64_PREL64 260 /* S + A - P */ -#define R_AARCH64_PREL32 261 /* S + A - P */ -#define R_AARCH64_PREL16 262 /* S + A - P */ - /* Group relocations to create a 16, 32, 48, or 64 bit unsigned data value or address inline */ -#define R_AARCH64_MOVW_UABS_G0 263 /* S + A */ -#define R_AARCH64_MOVW_UABS_G0_NC 264 /* S + A */ -#define R_AARCH64_MOVW_UABS_G1 265 /* S + A */ -#define R_AARCH64_MOVW_UABS_G1_NC 266 /* S + A */ -#define R_AARCH64_MOVW_UABS_G2 267 /* S + A */ -#define R_AARCH64_MOVW_UABS_G2_NC 268 /* S + A */ -#define R_AARCH64_MOVW_UABS_G3 269 /* S + A */ - /* Group relocations to create a 16, 32, 48, or 64 bit signed data or offset value inline */ -#define R_AARCH64_MOVW_SABS_G0 270 /* S + A */ -#define R_AARCH64_MOVW_SABS_G1 271 /* S + A */ -#define R_AARCH64_MOVW_SABS_G2 272 /* S + A */ - /* Relocations to generate 19, 21 and 33 bit PC-relative addresses */ -#define R_AARCH64_LD_PREL_LO19 273 /* S + A - P */ -#define R_AARCH64_ADR_PREL_LO21 274 /* S + A - P */ -#define R_AARCH64_ADR_PREL_PG_HI21 275 /* Page(S+A) - Page(P) */ -#define R_AARCH64_ADR_PREL_PG_HI21_NC 276 /* Page(S+A) - Page(P) */ -#define R_AARCH64_ADD_ABS_LO12_NC 277 /* S + A */ -#define R_AARCH64_LDST8_ABS_LO12_NC 278 /* S + A */ -#define R_AARCH64_LDST16_ABS_LO12_NC 284 /* S + A */ -#define R_AARCH64_LDST32_ABS_LO12_NC 285 /* S + A */ -#define R_AARCH64_LDST64_ABS_LO12_NC 286 /* S + A */ -#define R_AARCH64_LDST128_ABS_LO12_NC 299 /* S + A */ - /* Relocations for control-flow instructions - all offsets are a multiple of 4 */ -#define R_AARCH64_TSTBR14 279 /* S+A-P */ -#define R_AARCH64_CONDBR19 280 /* S+A-P */ -#define R_AARCH64_JUMP26 282 /* S+A-P */ -#define R_AARCH64_CALL26 283 /* S+A-P */ - /* Group relocations to create a 16, 32, 48, or 64 bit PC-relative offset inline */ -#define R_AARCH64_MOVW_PREL_G0 287 /* S+A-P */ -#define R_AARCH64_MOVW_PREL_G0_NC 288 /* S+A-P */ -#define R_AARCH64_MOVW_PREL_G1 289 /* S+A-P */ -#define R_AARCH64_MOVW_PREL_G1_NC 290 /* S+A-P */ -#define R_AARCH64_MOVW_PREL_G2 291 /* S+A-P */ -#define R_AARCH64_MOVW_PREL_G2_NC 292 /* S+A-P */ -#define R_AARCH64_MOVW_PREL_G3 293 /* S+A-P */ - /* Group relocations to create a 16, 32, 48, or 64 bit GOT-relative offsets inline */ -#define R_AARCH64_MOVW_GOTOFF_G0 300 /* G(S)-GOT */ -#define R_AARCH64_MOVW_GOTOFF_G0_NC 301 /* G(S)-GOT */ -#define R_AARCH64_MOVW_GOTOFF_G1 302 /* G(S)-GOT */ -#define R_AARCH64_MOVW_GOTOFF_G1_NC 303 /* G(S)-GOT */ -#define R_AARCH64_MOVW_GOTOFF_G2 304 /* G(S)-GOT */ -#define R_AARCH64_MOVW_GOTOFF_G2_NC 305 /* G(S)-GOT */ -#define R_AARCH64_MOVW_GOTOFF_G3 306 /* G(S)-GOT */ - /* GOT-relative data relocations */ -#define R_AARCH64_GOTREL64 307 /* S+A-GOT */ -#define R_AARCH64_GOTREL32 308 /* S+A-GOT */ - /* GOT-relative instruction relocations */ -#define R_AARCH64_GOT_LD_PREL19 309 /* G(S)-P */ -#define R_AARCH64_LD64_GOTOFF_LO15 310 /* G(S)-GOT */ -#define R_AARCH64_ADR_GOT_PAGE 311 /* Page(G(S))-Page(P) */ -#define R_AARCH64_LD64_GOT_LO12_NC 312 /* G(S) */ -#define R_AARCH64_LD64_GOTPAGE_LO15 313 /* G(S)-Page(GOT) */ -/* Relocations for thread-local storage */ - /* General Dynamic TLS relocations */ -#define R_AARCH64_TLSGD_ADR_PREL21 512 /* G(TLSIDX(S+A)) - P */ -#define R_AARCH64_TLSGD_ADR_PAGE21 513 /* Page(G(TLSIDX(S+A))) - Page(P) */ -#define R_AARCH64_TLSGD_ADD_LO12_NC 514 /* G(TLSIDX(S+A)) */ -#define R_AARCH64_TLSGD_MOVW_G1 515 /* G(TLSIDX(S+A)) - GOT */ -#define R_AARCH64_TLSGD_MOVW_G0_NC 516 /* G(TLSIDX(S+A)) - GOT */ - /* Local Dynamic TLS relocations */ -#define R_AARCH64_TLSLD_ADR_PREL21 517 /* G(LDM(S))) - P */ -#define R_AARCH64_TLSLD_ADR_PAGE21 518 /* Page(G(LDM(S)))-Page(P) */ -#define R_AARCH64_TLSLD_ADD_LO12_NC 519 /* G(LDM(S)) */ -#define R_AARCH64_TLSLD_MOVW_G1 520 /* G(LDM(S)) - GOT */ -#define R_AARCH64_TLSLD_MOVW_G0_NC 521 /* G(LDM(S)) - GOT */ -#define R_AARCH64_TLSLD_LD_PREL19 522 /* G(LDM(S)) - P */ -#define R_AARCH64_TLSLD_MOVW_DTPREL_G2 523 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_MOVW_DTPREL_G1 524 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_MOVW_DTPREL_G1_NC 525 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_MOVW_DTPREL_G0 526 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_MOVW_DTPREL_G0_NC 527 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_ADD_DTPREL_HI12 528 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_ADD_DTPREL_LO12 529 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_ADD_DTPREL_LO12_NC 530 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_LDST8_DTPREL_LO12 531 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_LDST8_DTPREL_LO12_NC 532 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_LDST16_DTPREL_LO12 533 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_LDST16_DTPREL_LO12_NC 534 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_LDST32_DTPREL_LO12 535 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_LDST32_DTPREL_LO12_NC 536 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_LDST64_DTPREL_LO12 537 /* DTPREL(S+A) */ -#define R_AARCH64_TLSLD_LDST64_DTPREL_LO12_NC 538 /* DTPREL(S+A) */ - /* Initial Exec TLS relocations */ -#define R_AARCH64_TLSIE_MOVW_GOTTPREL_G1 539 /* G(TPREL(S+A)) - GOT */ -#define R_AARCH64_TLSIE_MOVW_GOTTPREL_G0_NC 540 /* G(TPREL(S+A)) - GOT */ -#define R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21 541 /* Page(G(TPREL(S+A))) - Page(P) */ -#define R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC 542 /* G(TPREL(S+A)) */ -#define R_AARCH64_TLSIE_LD_GOTTPREL_PREL19 543 /* G(TPREL(S+A)) - P */ - /* Local Exec TLS relocations */ -#define R_AARCH64_TLSLE_MOVW_TPREL_G2 544 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_MOVW_TPREL_G1 545 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_MOVW_TPREL_G1_NC 546 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_MOVW_TPREL_G0 547 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_MOVW_TPREL_G0_NC 548 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_ADD_TPREL_HI12 549 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_ADD_TPREL_LO12 550 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_ADD_TPREL_LO12_NC 551 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_LDST8_TPREL_LO12 552 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_LDST8_TPREL_LO12_NC 553 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_LDST16_TPREL_LO12 554 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_LDST16_TPREL_LO12_NC 555 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_LDST32_TPREL_LO12 556 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_LDST32_TPREL_LO12_NC 557 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_LDST64_TPREL_LO12 558 /* TPREL(S+A) */ -#define R_AARCH64_TLSLE_LDST64_TPREL_LO12_NC 559 /* TPREL(S+A) */ -/* Dynamic relocations */ - /* Dynamic relocations */ -#define R_AARCH64_COPY 1024 -#define R_AARCH64_GLOB_DAT 1025 /* S + A */ -#define R_AARCH64_JUMP_SLOT 1026 /* S + A */ -#define R_AARCH64_RELATIVE 1027 /* Delta(S) + A , Delta(P) + A */ -#define R_AARCH64_TLS_DTPREL64 1028 /* DTPREL(S+A) */ -#define R_AARCH64_TLS_DTPMOD64 1029 /* LDM(S) */ -#define R_AARCH64_TLS_TPREL64 1030 /* TPREL(S+A) */ -#define R_AARCH64_TLS_DTPREL32 1031 /* DTPREL(S+A) */ -#define R_AARCH64_TLS_DTPMOD32 1032 /* LDM(S) */ -#define R_AARCH64_TLS_TPREL32 1033 /* DTPREL(S+A) */ - -#define R_ALPHA_NONE 0 /* No reloc */ -#define R_ALPHA_REFLONG 1 /* Direct 32 bit */ -#define R_ALPHA_REFQUAD 2 /* Direct 64 bit */ -#define R_ALPHA_GPREL32 3 /* GP relative 32 bit */ -#define R_ALPHA_LITERAL 4 /* GP relative 16 bit w/optimization */ -#define R_ALPHA_LITUSE 5 /* Optimization hint for LITERAL */ -#define R_ALPHA_GPDISP 6 /* Add displacement to GP */ -#define R_ALPHA_BRADDR 7 /* PC+4 relative 23 bit shifted */ -#define R_ALPHA_HINT 8 /* PC+4 relative 16 bit shifted */ -#define R_ALPHA_SREL16 9 /* PC relative 16 bit */ -#define R_ALPHA_SREL32 10 /* PC relative 32 bit */ -#define R_ALPHA_SREL64 11 /* PC relative 64 bit */ -#define R_ALPHA_OP_PUSH 12 /* OP stack push */ -#define R_ALPHA_OP_STORE 13 /* OP stack pop and store */ -#define R_ALPHA_OP_PSUB 14 /* OP stack subtract */ -#define R_ALPHA_OP_PRSHIFT 15 /* OP stack right shift */ -#define R_ALPHA_GPVALUE 16 -#define R_ALPHA_GPRELHIGH 17 -#define R_ALPHA_GPRELLOW 18 -#define R_ALPHA_IMMED_GP_16 19 -#define R_ALPHA_IMMED_GP_HI32 20 -#define R_ALPHA_IMMED_SCN_HI32 21 -#define R_ALPHA_IMMED_BR_HI32 22 -#define R_ALPHA_IMMED_LO32 23 -#define R_ALPHA_COPY 24 /* Copy symbol at runtime */ -#define R_ALPHA_GLOB_DAT 25 /* Create GOT entry */ -#define R_ALPHA_JMP_SLOT 26 /* Create PLT entry */ -#define R_ALPHA_RELATIVE 27 /* Adjust by program base */ - -#define R_ARM_NONE 0 /* No relocation. */ -#define R_ARM_PC24 1 -#define R_ARM_ABS32 2 -#define R_ARM_REL32 3 -#define R_ARM_PC13 4 -#define R_ARM_ABS16 5 -#define R_ARM_ABS12 6 -#define R_ARM_THM_ABS5 7 -#define R_ARM_ABS8 8 -#define R_ARM_SBREL32 9 -#define R_ARM_THM_PC22 10 -#define R_ARM_THM_PC8 11 -#define R_ARM_AMP_VCALL9 12 -#define R_ARM_SWI24 13 -#define R_ARM_THM_SWI8 14 -#define R_ARM_XPC25 15 -#define R_ARM_THM_XPC22 16 -#define R_ARM_COPY 20 /* Copy data from shared object. */ -#define R_ARM_GLOB_DAT 21 /* Set GOT entry to data address. */ -#define R_ARM_JUMP_SLOT 22 /* Set GOT entry to code address. */ -#define R_ARM_RELATIVE 23 /* Add load address of shared object. */ -#define R_ARM_GOTOFF 24 /* Add GOT-relative symbol address. */ -#define R_ARM_GOTPC 25 /* Add PC-relative GOT table address. */ -#define R_ARM_GOT32 26 /* Add PC-relative GOT offset. */ -#define R_ARM_PLT32 27 /* Add PC-relative PLT offset. */ -#define R_ARM_CALL 28 -#define R_ARM_JMP24 29 -#define R_ARM_THM_MOVW_ABS_NC 47 -#define R_ARM_THM_MOVT_ABS 48 - -// Block of PC-relative relocations added to work around gcc putting -// object relocations in static executables. -#define R_ARM_THM_JUMP24 30 -#define R_ARM_PREL31 42 -#define R_ARM_MOVW_PREL_NC 45 -#define R_ARM_MOVT_PREL 46 -#define R_ARM_THM_MOVW_PREL_NC 49 -#define R_ARM_THM_MOVT_PREL 50 -#define R_ARM_THM_JMP6 52 -#define R_ARM_THM_ALU_PREL_11_0 53 -#define R_ARM_THM_PC12 54 -#define R_ARM_REL32_NOI 56 -#define R_ARM_ALU_PC_G0_NC 57 -#define R_ARM_ALU_PC_G0 58 -#define R_ARM_ALU_PC_G1_NC 59 -#define R_ARM_ALU_PC_G1 60 -#define R_ARM_ALU_PC_G2 61 -#define R_ARM_LDR_PC_G1 62 -#define R_ARM_LDR_PC_G2 63 -#define R_ARM_LDRS_PC_G0 64 -#define R_ARM_LDRS_PC_G1 65 -#define R_ARM_LDRS_PC_G2 66 -#define R_ARM_LDC_PC_G0 67 -#define R_ARM_LDC_PC_G1 68 -#define R_ARM_LDC_PC_G2 69 -#define R_ARM_GOT_PREL 96 -#define R_ARM_THM_JUMP11 102 -#define R_ARM_THM_JUMP8 103 -#define R_ARM_TLS_GD32 104 -#define R_ARM_TLS_LDM32 105 -#define R_ARM_TLS_IE32 107 - -#define R_ARM_THM_JUMP19 51 -#define R_ARM_GNU_VTENTRY 100 -#define R_ARM_GNU_VTINHERIT 101 -#define R_ARM_RSBREL32 250 -#define R_ARM_THM_RPC22 251 -#define R_ARM_RREL32 252 -#define R_ARM_RABS32 253 -#define R_ARM_RPC24 254 -#define R_ARM_RBASE 255 - -#define R_PPC_NONE 0 /* No relocation. */ -#define R_PPC_ADDR32 1 -#define R_PPC_ADDR24 2 -#define R_PPC_ADDR16 3 -#define R_PPC_ADDR16_LO 4 -#define R_PPC_ADDR16_HI 5 -#define R_PPC_ADDR16_HA 6 -#define R_PPC_ADDR14 7 -#define R_PPC_ADDR14_BRTAKEN 8 -#define R_PPC_ADDR14_BRNTAKEN 9 -#define R_PPC_REL24 10 -#define R_PPC_REL14 11 -#define R_PPC_REL14_BRTAKEN 12 -#define R_PPC_REL14_BRNTAKEN 13 -#define R_PPC_GOT16 14 -#define R_PPC_GOT16_LO 15 -#define R_PPC_GOT16_HI 16 -#define R_PPC_GOT16_HA 17 -#define R_PPC_PLTREL24 18 -#define R_PPC_COPY 19 -#define R_PPC_GLOB_DAT 20 -#define R_PPC_JMP_SLOT 21 -#define R_PPC_RELATIVE 22 -#define R_PPC_LOCAL24PC 23 -#define R_PPC_UADDR32 24 -#define R_PPC_UADDR16 25 -#define R_PPC_REL32 26 -#define R_PPC_PLT32 27 -#define R_PPC_PLTREL32 28 -#define R_PPC_PLT16_LO 29 -#define R_PPC_PLT16_HI 30 -#define R_PPC_PLT16_HA 31 -#define R_PPC_SDAREL16 32 -#define R_PPC_SECTOFF 33 -#define R_PPC_SECTOFF_LO 34 -#define R_PPC_SECTOFF_HI 35 -#define R_PPC_SECTOFF_HA 36 - -/* - * TLS relocations - */ -#define R_PPC_TLS 67 -#define R_PPC_DTPMOD32 68 -#define R_PPC_TPREL16 69 -#define R_PPC_TPREL16_LO 70 -#define R_PPC_TPREL16_HI 71 -#define R_PPC_TPREL16_HA 72 -#define R_PPC_TPREL32 73 -#define R_PPC_DTPREL16 74 -#define R_PPC_DTPREL16_LO 75 -#define R_PPC_DTPREL16_HI 76 -#define R_PPC_DTPREL16_HA 77 -#define R_PPC_DTPREL32 78 -#define R_PPC_GOT_TLSGD16 79 -#define R_PPC_GOT_TLSGD16_LO 80 -#define R_PPC_GOT_TLSGD16_HI 81 -#define R_PPC_GOT_TLSGD16_HA 82 -#define R_PPC_GOT_TLSLD16 83 -#define R_PPC_GOT_TLSLD16_LO 84 -#define R_PPC_GOT_TLSLD16_HI 85 -#define R_PPC_GOT_TLSLD16_HA 86 -#define R_PPC_GOT_TPREL16 87 -#define R_PPC_GOT_TPREL16_LO 88 -#define R_PPC_GOT_TPREL16_HI 89 -#define R_PPC_GOT_TPREL16_HA 90 - -/* - * The remaining relocs are from the Embedded ELF ABI, and are not in the - * SVR4 ELF ABI. - */ - -#define R_PPC_EMB_NADDR32 101 -#define R_PPC_EMB_NADDR16 102 -#define R_PPC_EMB_NADDR16_LO 103 -#define R_PPC_EMB_NADDR16_HI 104 -#define R_PPC_EMB_NADDR16_HA 105 -#define R_PPC_EMB_SDAI16 106 -#define R_PPC_EMB_SDA2I16 107 -#define R_PPC_EMB_SDA2REL 108 -#define R_PPC_EMB_SDA21 109 -#define R_PPC_EMB_MRKREF 110 -#define R_PPC_EMB_RELSEC16 111 -#define R_PPC_EMB_RELST_LO 112 -#define R_PPC_EMB_RELST_HI 113 -#define R_PPC_EMB_RELST_HA 114 -#define R_PPC_EMB_BIT_FLD 115 -#define R_PPC_EMB_RELSDA 116 - -#define R_SPARC_NONE 0 -#define R_SPARC_8 1 -#define R_SPARC_16 2 -#define R_SPARC_32 3 -#define R_SPARC_DISP8 4 -#define R_SPARC_DISP16 5 -#define R_SPARC_DISP32 6 -#define R_SPARC_WDISP30 7 -#define R_SPARC_WDISP22 8 -#define R_SPARC_HI22 9 -#define R_SPARC_22 10 -#define R_SPARC_13 11 -#define R_SPARC_LO10 12 -#define R_SPARC_GOT10 13 -#define R_SPARC_GOT13 14 -#define R_SPARC_GOT22 15 -#define R_SPARC_PC10 16 -#define R_SPARC_PC22 17 -#define R_SPARC_WPLT30 18 -#define R_SPARC_COPY 19 -#define R_SPARC_GLOB_DAT 20 -#define R_SPARC_JMP_SLOT 21 -#define R_SPARC_RELATIVE 22 -#define R_SPARC_UA32 23 -#define R_SPARC_PLT32 24 -#define R_SPARC_HIPLT22 25 -#define R_SPARC_LOPLT10 26 -#define R_SPARC_PCPLT32 27 -#define R_SPARC_PCPLT22 28 -#define R_SPARC_PCPLT10 29 -#define R_SPARC_10 30 -#define R_SPARC_11 31 -#define R_SPARC_64 32 -#define R_SPARC_OLO10 33 -#define R_SPARC_HH22 34 -#define R_SPARC_HM10 35 -#define R_SPARC_LM22 36 -#define R_SPARC_PC_HH22 37 -#define R_SPARC_PC_HM10 38 -#define R_SPARC_PC_LM22 39 -#define R_SPARC_WDISP16 40 -#define R_SPARC_WDISP19 41 -#define R_SPARC_GLOB_JMP 42 -#define R_SPARC_7 43 -#define R_SPARC_5 44 -#define R_SPARC_6 45 -#define R_SPARC_DISP64 46 -#define R_SPARC_PLT64 47 -#define R_SPARC_HIX22 48 -#define R_SPARC_LOX10 49 -#define R_SPARC_H44 50 -#define R_SPARC_M44 51 -#define R_SPARC_L44 52 -#define R_SPARC_REGISTER 53 -#define R_SPARC_UA64 54 -#define R_SPARC_UA16 55 -#define R_SPARC_TLS_GD_HI22 56 -#define R_SPARC_TLS_GD_LO10 57 -#define R_SPARC_TLS_GD_ADD 58 -#define R_SPARC_TLS_GD_CALL 59 -#define R_SPARC_TLS_LDM_HI22 60 -#define R_SPARC_TLS_LDM_LO10 61 -#define R_SPARC_TLS_LDM_ADD 62 -#define R_SPARC_TLS_LDM_CALL 63 -#define R_SPARC_TLS_LDO_HIX22 64 -#define R_SPARC_TLS_LDO_LOX10 65 -#define R_SPARC_TLS_LDO_ADD 66 -#define R_SPARC_TLS_IE_HI22 67 -#define R_SPARC_TLS_IE_LO10 68 -#define R_SPARC_TLS_IE_LD 69 -#define R_SPARC_TLS_IE_LDX 70 -#define R_SPARC_TLS_IE_ADD 71 -#define R_SPARC_TLS_LE_HIX22 72 -#define R_SPARC_TLS_LE_LOX10 73 -#define R_SPARC_TLS_DTPMOD32 74 -#define R_SPARC_TLS_DTPMOD64 75 -#define R_SPARC_TLS_DTPOFF32 76 -#define R_SPARC_TLS_DTPOFF64 77 -#define R_SPARC_TLS_TPOFF32 78 -#define R_SPARC_TLS_TPOFF64 79 - -#define R_X86_64_NONE 0 /* No relocation. */ -#define R_X86_64_64 1 /* Add 64 bit symbol value. */ -#define R_X86_64_PC32 2 /* PC-relative 32 bit signed sym value. */ -#define R_X86_64_GOT32 3 /* PC-relative 32 bit GOT offset. */ -#define R_X86_64_PLT32 4 /* PC-relative 32 bit PLT offset. */ -#define R_X86_64_COPY 5 /* Copy data from shared object. */ -#define R_X86_64_GLOB_DAT 6 /* Set GOT entry to data address. */ -#define R_X86_64_JMP_SLOT 7 /* Set GOT entry to code address. */ -#define R_X86_64_RELATIVE 8 /* Add load address of shared object. */ -#define R_X86_64_GOTPCREL 9 /* Add 32 bit signed pcrel offset to GOT. */ -#define R_X86_64_32 10 /* Add 32 bit zero extended symbol value */ -#define R_X86_64_32S 11 /* Add 32 bit sign extended symbol value */ -#define R_X86_64_16 12 /* Add 16 bit zero extended symbol value */ -#define R_X86_64_PC16 13 /* Add 16 bit signed extended pc relative symbol value */ -#define R_X86_64_8 14 /* Add 8 bit zero extended symbol value */ -#define R_X86_64_PC8 15 /* Add 8 bit signed extended pc relative symbol value */ -#define R_X86_64_DTPMOD64 16 /* ID of module containing symbol */ -#define R_X86_64_DTPOFF64 17 /* Offset in TLS block */ -#define R_X86_64_TPOFF64 18 /* Offset in static TLS block */ -#define R_X86_64_TLSGD 19 /* PC relative offset to GD GOT entry */ -#define R_X86_64_TLSLD 20 /* PC relative offset to LD GOT entry */ -#define R_X86_64_DTPOFF32 21 /* Offset in TLS block */ -#define R_X86_64_GOTTPOFF 22 /* PC relative offset to IE GOT entry */ -#define R_X86_64_TPOFF32 23 /* Offset in static TLS block */ -#define R_X86_64_PC64 24 /* PC relative 64 bit */ -#define R_X86_64_GOTOFF64 25 /* 64 bit offset to GOT */ -#define R_X86_64_GOTPC3 26 /* 32 bit signed pc relative offset to GOT */ -#define R_X86_64_GOT64 27 /* 64-bit GOT entry offset */ -#define R_X86_64_GOTPCREL64 28 /* 64-bit PC relative offset to GOT entry */ -#define R_X86_64_GOTPC64 29 /* 64-bit PC relative offset to GOT */ -#define R_X86_64_GOTPLT64 30 /* like GOT64, says PLT entry needed */ -#define R_X86_64_PLTOFF64 31 /* 64-bit GOT relative offset to PLT entry */ -#define R_X86_64_SIZE32 32 /* Size of symbol plus 32-bit addend */ -#define R_X86_64_SIZE64 33 /* Size of symbol plus 64-bit addend */ -#define R_X86_64_GOTPC32_TLSDESC 34 /* GOT offset for TLS descriptor. */ -#define R_X86_64_TLSDESC_CALL 35 /* Marker for call through TLS descriptor. */ -#define R_X86_64_TLSDESC 36 /* TLS descriptor. */ -#define R_X86_64_IRELATIVE 37 /* Adjust indirectly by program base */ -#define R_X86_64_RELATIVE64 38 /* 64-bit adjust by program base */ -#define R_X86_64_GOTPCRELX 41 /* Load from 32 bit signed pc relative offset to GOT entry without REX prefix, relaxable. */ -#define R_X86_64_REX_GOTPCRELX 42 /* Load from 32 bit signed pc relative offset to GOT entry with REX prefix, relaxable. */ - -/* - * RISC-V relocation types - */ - -/* Relocation types used by the dynamic linker */ -#define R_RISCV_NONE 0 -#define R_RISCV_32 1 -#define R_RISCV_64 2 -#define R_RISCV_RELATIVE 3 -#define R_RISCV_COPY 4 -#define R_RISCV_JUMP_SLOT 5 -#define R_RISCV_TLS_DTPMOD32 6 -#define R_RISCV_TLS_DTPMOD64 7 -#define R_RISCV_TLS_DTPREL32 8 -#define R_RISCV_TLS_DTPREL64 9 -#define R_RISCV_TLS_TPREL32 10 -#define R_RISCV_TLS_TPREL64 11 - -/* Relocation types not used by the dynamic linker */ -#define R_RISCV_BRANCH 16 -#define R_RISCV_JAL 17 -#define R_RISCV_CALL 18 -#define R_RISCV_CALL_PLT 19 -#define R_RISCV_GOT_HI20 20 -#define R_RISCV_TLS_GOT_HI20 21 -#define R_RISCV_TLS_GD_HI20 22 -#define R_RISCV_PCREL_HI20 23 -#define R_RISCV_PCREL_LO12_I 24 -#define R_RISCV_PCREL_LO12_S 25 -#define R_RISCV_HI20 26 -#define R_RISCV_LO12_I 27 -#define R_RISCV_LO12_S 28 -#define R_RISCV_TPREL_HI20 29 -#define R_RISCV_TPREL_LO12_I 30 -#define R_RISCV_TPREL_LO12_S 31 -#define R_RISCV_TPREL_ADD 32 -#define R_RISCV_ADD8 33 -#define R_RISCV_ADD16 34 -#define R_RISCV_ADD32 35 -#define R_RISCV_ADD64 36 -#define R_RISCV_SUB8 37 -#define R_RISCV_SUB16 38 -#define R_RISCV_SUB32 39 -#define R_RISCV_SUB64 40 -#define R_RISCV_GNU_VTINHERIT 41 -#define R_RISCV_GNU_VTENTRY 42 -#define R_RISCV_ALIGN 43 -#define R_RISCV_RVC_BRANCH 44 -#define R_RISCV_RVC_JUMP 45 -#define R_RISCV_RVC_LUI 46 -#define R_RISCV_GPREL_I 47 -#define R_RISCV_GPREL_S 48 -#define R_RISCV_TPREL_I 49 -#define R_RISCV_TPREL_S 50 -#define R_RISCV_RELAX 51 -#define R_RISCV_SUB6 52 -#define R_RISCV_SET6 53 -#define R_RISCV_SET8 54 -#define R_RISCV_SET16 55 -#define R_RISCV_SET32 56 - -/* - * LoongArch relocation types - */ -#define R_LARCH_NONE 0 -#define R_LARCH_32 1 -#define R_LARCH_64 2 -#define R_LARCH_RELATIVE 3 -#define R_LARCH_COPY 4 -#define R_LARCH_JUMP_SLOT 5 -#define R_LARCH_TLS_DTPMOD32 6 -#define R_LARCH_TLS_DTPMOD64 7 -#define R_LARCH_TLS_DTPREL32 8 -#define R_LARCH_TLS_DTPREL64 9 -#define R_LARCH_TLS_TPREL32 10 -#define R_LARCH_TLS_TPREL64 11 -#define R_LARCH_IRELATIVE 12 -#define R_LARCH_MARK_LA 20 -#define R_LARCH_MARK_PCREL 21 -#define R_LARCH_SOP_PUSH_PCREL 22 -#define R_LARCH_SOP_PUSH_ABSOLUTE 23 -#define R_LARCH_SOP_PUSH_DUP 24 -#define R_LARCH_SOP_PUSH_GPREL 25 -#define R_LARCH_SOP_PUSH_TLS_TPREL 26 -#define R_LARCH_SOP_PUSH_TLS_GOT 27 -#define R_LARCH_SOP_PUSH_TLS_GD 28 -#define R_LARCH_SOP_PUSH_PLT_PCREL 29 -#define R_LARCH_SOP_ASSERT 30 -#define R_LARCH_SOP_NOT 31 -#define R_LARCH_SOP_SUB 32 -#define R_LARCH_SOP_SL 33 -#define R_LARCH_SOP_SR 34 -#define R_LARCH_SOP_ADD 35 -#define R_LARCH_SOP_AND 36 -#define R_LARCH_SOP_IF_ELSE 37 -#define R_LARCH_SOP_POP_32_S_10_5 38 -#define R_LARCH_SOP_POP_32_U_10_12 39 -#define R_LARCH_SOP_POP_32_S_10_12 40 -#define R_LARCH_SOP_POP_32_S_10_16 41 -#define R_LARCH_SOP_POP_32_S_10_16_S2 42 -#define R_LARCH_SOP_POP_32_S_5_20 43 -#define R_LARCH_SOP_POP_32_S_0_5_10_16_S2 44 -#define R_LARCH_SOP_POP_32_S_0_10_10_16_S2 45 -#define R_LARCH_SOP_POP_32_U 46 -#define R_LARCH_ADD8 47 -#define R_LARCH_ADD16 48 -#define R_LARCH_ADD24 49 -#define R_LARCH_ADD32 50 -#define R_LARCH_ADD64 51 -#define R_LARCH_SUB8 52 -#define R_LARCH_SUB16 53 -#define R_LARCH_SUB24 54 -#define R_LARCH_SUB32 55 -#define R_LARCH_SUB64 56 -#define R_LARCH_GNU_VTINHERIT 57 -#define R_LARCH_GNU_VTENTRY 58 -#define R_LARCH_B16 64 -#define R_LARCH_B21 65 -#define R_LARCH_B26 66 -#define R_LARCH_ABS_HI20 67 -#define R_LARCH_ABS_LO12 68 -#define R_LARCH_ABS64_LO20 69 -#define R_LARCH_ABS64_HI12 70 -#define R_LARCH_PCALA_HI20 71 -#define R_LARCH_PCALA_LO12 72 -#define R_LARCH_PCALA64_LO20 73 -#define R_LARCH_PCALA64_HI12 74 -#define R_LARCH_GOT_PC_HI20 75 -#define R_LARCH_GOT_PC_LO12 76 -#define R_LARCH_GOT64_PC_LO20 77 -#define R_LARCH_GOT64_PC_HI12 78 -#define R_LARCH_GOT64_HI20 79 -#define R_LARCH_GOT64_LO12 80 -#define R_LARCH_GOT64_LO20 81 -#define R_LARCH_GOT64_HI12 82 -#define R_LARCH_TLS_LE_HI20 83 -#define R_LARCH_TLS_LE_LO12 84 -#define R_LARCH_TLS_LE64_LO20 85 -#define R_LARCH_TLS_LE64_HI12 86 -#define R_LARCH_TLS_IE_PC_HI20 87 -#define R_LARCH_TLS_IE_PC_LO12 88 -#define R_LARCH_TLS_IE64_PC_LO20 89 -#define R_LARCH_TLS_IE64_PC_HI12 90 -#define R_LARCH_TLS_IE64_HI20 91 -#define R_LARCH_TLS_IE64_LO12 92 -#define R_LARCH_TLS_IE64_LO20 93 -#define R_LARCH_TLS_IE64_HI12 94 -#define R_LARCH_TLS_LD_PC_HI20 95 -#define R_LARCH_TLS_LD64_HI20 96 -#define R_LARCH_TLS_GD_PC_HI20 97 -#define R_LARCH_TLS_GD64_HI20 98 -#define R_LARCH_32_PCREL 99 -#define R_LARCH_RELAX 100 -#define R_LARCH_DELETE 101 -#define R_LARCH_ALIGN 102 -#define R_LARCH_PCREL20_S2 103 -#define R_LARCH_CFA 104 -#define R_LARCH_ADD6 105 -#define R_LARCH_SUB6 106 -#define R_LARCH_ADD_ULEB128 107 -#define R_LARCH_SUB_ULEB128 108 -#define R_LARCH_64_PCREL 109 - -#endif /* !_SYS_ELF_COMMON_H_ */ diff --git a/BaseTools/Source/C/Makefile b/BaseTools/Source/C/Makefile index a376d32e22..589dc29e89 100644 --- a/BaseTools/Source/C/Makefile +++ b/BaseTools/Source/C/Makefile @@ -16,7 +16,6 @@ APPLICATIONS = \ GenCrc32 \ GenFfs \ GenFv \ - GenFw \ GenSec \ LzmaCompress \ TianoCompress \ diff --git a/BaseTools/Source/C/Makefiles/ms.app b/BaseTools/Source/C/Makefiles/ms.app index aecae37396..0e6e16474c 100644 --- a/BaseTools/Source/C/Makefiles/ms.app +++ b/BaseTools/Source/C/Makefiles/ms.app @@ -19,10 +19,9 @@ $(OBJECTS) : $(SOURCE_PATH)\Include\Common\BuildVersion.h .PHONY:cleanall clean: - del /f /q $(OBJECTS) *.pdb > nul + del /f /q *.obj *.pdb > nul cleanall: - del /f /q $(OBJECTS) $(APPLICATION) *.pdb $(BIN_PATH)\$(APPNAME).pdb > nul + del /f /q *.obj $(APPLICATION) *.pdb $(BIN_PATH)\$(APPNAME).pdb > nul !INCLUDE $(SOURCE_PATH)\Makefiles\ms.rule - diff --git a/BaseTools/Source/Python/Common/ToolDefClassObject.py b/BaseTools/Source/Python/Common/ToolDefClassObject.py index afc20a3c17..aa4d971d62 100644 --- a/BaseTools/Source/Python/Common/ToolDefClassObject.py +++ b/BaseTools/Source/Python/Common/ToolDefClassObject.py @@ -103,11 +103,32 @@ class ToolDefClassObject(object): else: EdkLogger.error("tools_def.txt parser", FILE_NOT_FOUND, ExtraData=FileName) + Branch = 0 for Index in range(len(FileContent)): Line = FileContent[Index].strip() if Line == "" or Line[0] == '#': continue + if Line.startswith("!ifdef"): + Condition = Line[6:].strip() + Reference = GlobalData.gMacroRefPattern.findall(Condition) + if Reference[0] in GlobalData.gCommandLineDefines: + Branch = 1 + else: + Branch = -1 + continue + + if Line.startswith("!else"): + Branch *= -1 + continue + + if Line.startswith("!endif"): + Branch = 0 + continue + + if Branch == -1: + continue + if Line.startswith("!include"): IncFile = Line[8:].strip() Done, IncFile = self.ExpandMacros(IncFile) diff --git a/BaseTools/Source/Python/GenFds/DataSection.py b/BaseTools/Source/Python/GenFds/DataSection.py index 5af3ee7b7f..abf75abcc7 100644 --- a/BaseTools/Source/Python/GenFds/DataSection.py +++ b/BaseTools/Source/Python/GenFds/DataSection.py @@ -94,7 +94,7 @@ class DataSection (DataSectionClassObject): StrippedFile = os.path.join(OutputPath, ModuleName + '.stripped') GenFdsGlobalVariable.GenerateFirmwareImage( StrippedFile, - [GenFdsGlobalVariable.MacroExtend(self.SectFileName, Dict)], + GenFdsGlobalVariable.MacroExtend(self.SectFileName, Dict), Strip=True, IsMakefile = IsMakefile ) diff --git a/BaseTools/Source/Python/GenFds/EfiSection.py b/BaseTools/Source/Python/GenFds/EfiSection.py index fd58391dac..cb981ef4e6 100644 --- a/BaseTools/Source/Python/GenFds/EfiSection.py +++ b/BaseTools/Source/Python/GenFds/EfiSection.py @@ -289,7 +289,7 @@ class EfiSection (EfiSectionClassObject): StrippedFile = os.path.join(OutputPath, ModuleName + '.stripped') GenFdsGlobalVariable.GenerateFirmwareImage( StrippedFile, - [File], + File, Strip=True, IsMakefile = IsMakefile ) diff --git a/BaseTools/Source/Python/GenFds/FfsInfStatement.py b/BaseTools/Source/Python/GenFds/FfsInfStatement.py index ec9713484e..ca3098394d 100644 --- a/BaseTools/Source/Python/GenFds/FfsInfStatement.py +++ b/BaseTools/Source/Python/GenFds/FfsInfStatement.py @@ -792,7 +792,7 @@ class FfsInfStatement(FfsInfStatementClassObject): StrippedFile = os.path.join(self.OutputPath, ModuleName + '.stipped') GenFdsGlobalVariable.GenerateFirmwareImage( StrippedFile, - [File], + File, Strip=True, IsMakefile=IsMakefile ) @@ -835,7 +835,7 @@ class FfsInfStatement(FfsInfStatementClassObject): StrippedFile = os.path.join(self.OutputPath, ModuleName + '.stipped') GenFdsGlobalVariable.GenerateFirmwareImage( StrippedFile, - [GenSecInputFile], + GenSecInputFile, Strip=True, IsMakefile=IsMakefile ) diff --git a/BaseTools/Source/Python/GenFds/GenFdsGlobalVariable.py b/BaseTools/Source/Python/GenFds/GenFdsGlobalVariable.py index d7668ba681..68faace90f 100644 --- a/BaseTools/Source/Python/GenFds/GenFdsGlobalVariable.py +++ b/BaseTools/Source/Python/GenFds/GenFdsGlobalVariable.py @@ -607,36 +607,17 @@ class GenFdsGlobalVariable: GenFdsGlobalVariable.CallExternalTool(Cmd, "Failed to generate FV") @staticmethod - def GenerateFirmwareImage(Output, Input, Type="efi", SubType=None, Zero=False, - Strip=False, Replace=False, TimeStamp=None, Join=False, - Align=None, Padding=None, Convert=False, IsMakefile=False): + def GenerateFirmwareImage(Output, Input, Format="Auto", Strip=False, IsMakefile=False): if not GenFdsGlobalVariable.NeedsUpdate(Output, Input) and not IsMakefile: return GenFdsGlobalVariable.DebugLogger(EdkLogger.DEBUG_5, "%s needs update because of newer %s" % (Output, Input)) - Cmd = ["GenFw"] - if Type.lower() == "te": - Cmd.append("-t") - if SubType: - Cmd += ("-e", SubType) - if TimeStamp: - Cmd += ("-s", TimeStamp) - if Align: - Cmd += ("-a", Align) - if Padding: - Cmd += ("-p", Padding) - if Zero: - Cmd.append("-z") + Cmd = ["ImageTool GenImage"] + if Format != "Auto": + Cmd += ("-c", Format) if Strip: - Cmd.append("-l") - if Replace: - Cmd.append("-r") - if Join: - Cmd.append("-j") - if Convert: - Cmd.append("-m") - Cmd += ("-o", Output) - Cmd += Input + Cmd.append("-s") + Cmd += ("-o", Output, Input) if IsMakefile: if " ".join(Cmd).strip() not in GenFdsGlobalVariable.SecCmdList: GenFdsGlobalVariable.SecCmdList.append(" ".join(Cmd).strip()) diff --git a/BaseTools/Source/Python/build/BuildReport.py b/BaseTools/Source/Python/build/BuildReport.py index 26dfe53fff..82a063b5a4 100644 --- a/BaseTools/Source/Python/build/BuildReport.py +++ b/BaseTools/Source/Python/build/BuildReport.py @@ -644,11 +644,11 @@ class ModuleReport(object): if os.path.isfile(DefaultEFIfile): Tempfile = os.path.join(OutputDir, self.ModuleName + "_hash.tmp") # rebase the efi image since its base address may not zero - cmd = ["GenFw", "--rebase", str(0), "-o", Tempfile, DefaultEFIfile] + cmd = ["ImageTool GenImage -b 0 -o", Tempfile, DefaultEFIfile] try: PopenObject = subprocess.Popen(' '.join(cmd), stdout=subprocess.PIPE, stderr=subprocess.PIPE, shell=True) except Exception as X: - EdkLogger.error("GenFw", COMMAND_FAILURE, ExtraData="%s: %s" % (str(X), cmd[0])) + EdkLogger.error("ImageTool", COMMAND_FAILURE, ExtraData="%s: %s" % (str(X), cmd[0])) EndOfProcedure = threading.Event() EndOfProcedure.clear() if PopenObject.stderr: @@ -661,7 +661,7 @@ class ModuleReport(object): if PopenObject.stderr: StdErrThread.join() if PopenObject.returncode != 0: - EdkLogger.error("GenFw", COMMAND_FAILURE, "Failed to generate firmware hash image for %s" % (DefaultEFIfile)) + EdkLogger.error("ImageTool", COMMAND_FAILURE, "Failed to generate firmware hash image for %s" % (DefaultEFIfile)) if os.path.isfile(Tempfile): self.Hash = hashlib.sha1() buf = open(Tempfile, 'rb').read() diff --git a/BaseTools/Source/Python/build/build.py b/BaseTools/Source/Python/build/build.py index 1390a62178..c47da87378 100755 --- a/BaseTools/Source/Python/build/build.py +++ b/BaseTools/Source/Python/build/build.py @@ -1522,18 +1522,18 @@ class Build(): BaseAddress = BaseAddress - ModuleInfo.Image.Size BaseAddress = AlignDown(BaseAddress, ModuleInfo.Image.SectionAlignment) # - # Update Image to new BaseAddress by GenFw tool + # Update Image to new BaseAddress by ImageTool tool # - LaunchCommand(["GenFw", "--rebase", str(BaseAddress), "-r", ModuleOutputImage], ModuleInfo.OutputDir) - LaunchCommand(["GenFw", "--rebase", str(BaseAddress), "-r", ModuleDebugImage], ModuleInfo.DebugDir) + LaunchCommand(["ImageTool", "GenImage", "-b", str(BaseAddress), "-o", ModuleOutputImage, ModuleOutputImage], ModuleInfo.OutputDir) + LaunchCommand(["ImageTool", "GenImage", "-b", str(BaseAddress), "-o", ModuleOutputImage, ModuleOutputImage], ModuleInfo.DebugDir) ## for SMM module in SMRAM, the SMRAM will be allocated from base to top. else: BaseAddress = AlignUp(BaseAddress, ModuleInfo.Image.SectionAlignment) # # Set new address to the section header only for SMM driver. # - LaunchCommand(["GenFw", "--address", str(BaseAddress), "-r", ModuleOutputImage], ModuleInfo.OutputDir) - LaunchCommand(["GenFw", "--address", str(BaseAddress), "-r", ModuleDebugImage], ModuleInfo.DebugDir) + LaunchCommand(["ImageTool", "GenImage", "-f -b", str(BaseAddress), "-o", ModuleOutputImage, ModuleOutputImage], ModuleInfo.OutputDir) + LaunchCommand(["ImageTool", "GenImage", "-f -b", str(BaseAddress), "-o", ModuleOutputImage, ModuleOutputImage], ModuleInfo.DebugDir) # # Collect function address from Map file # diff --git a/BaseTools/UserManuals/GenFds_Utility_Man_Page.rtf b/BaseTools/UserManuals/GenFds_Utility_Man_Page.rtf index 9192bb699e..eed8ba70e2 100644 --- a/BaseTools/UserManuals/GenFds_Utility_Man_Page.rtf +++ b/BaseTools/UserManuals/GenFds_Utility_Man_Page.rtf @@ -289,7 +289,7 @@ Build\\Nt32\\Debug_MyTools. ActivePlatform is C:\\work\\EdkII\\Nt32Pkg\\Nt32Pkg \par }\pard\plain \ltrpar\s2\ql \li-1440\ri0\sb400\sa60\sl-340\slmult0\keep\keepn\nowidctlpar\tx1440\wrapdefault\faauto\outlinelevel1\rin0\lin-1440\itap0 \rtlch\fcs1 \af0\afs24\alang1025 \ltrch\fcs0 \fs24\lang1033\langfe1033\loch\af41\hich\af41\dbch\af13\cgrid\langnp1033\langfenp1033 {\rtlch\fcs1 \ab\af41\afs28 \ltrch\fcs0 \b\fs28\cf17\insrsid5513321 \hich\af41\dbch\af13\loch\f41 See also \par }\pard\plain \ltrpar\ql \li0\ri0\sb200\nowidctlpar\wrapdefault\faauto\rin0\lin0\itap0 \rtlch\fcs1 \af0\afs24\alang1025 \ltrch\fcs0 \fs24\lang1033\langfe1033\loch\af41\hich\af41\dbch\af13\cgrid\langnp1033\langfenp1033 {\rtlch\fcs1 \af41\afs18 \ltrch\fcs0 -\fs18\cf1\insrsid5513321 \hich\af41\dbch\af13\loch\f41 GenFv, GenFfs, GenSection, GenFw. +\fs18\cf1\insrsid5513321 \hich\af41\dbch\af13\loch\f41 GenFv, GenFfs, GenSection. \par }\pard\plain \ltrpar\s2\ql \li-1440\ri0\sb400\sa60\sl-340\slmult0\keep\keepn\nowidctlpar\tx1440\wrapdefault\faauto\outlinelevel1\rin0\lin-1440\itap0 \rtlch\fcs1 \af0\afs24\alang1025 \ltrch\fcs0 \fs24\lang1033\langfe1033\loch\af41\hich\af41\dbch\af13\cgrid\langnp1033\langfenp1033 {\rtlch\fcs1 \ab\af41\afs28 \ltrch\fcs0 \b\fs28\cf17\insrsid5513321 \hich\af41\dbch\af13\loch\f41 License \par }\pard\plain \ltrpar\ql \li0\ri0\sb200\nowidctlpar\wrapdefault\faauto\rin0\lin0\itap0 \rtlch\fcs1 \af0\afs24\alang1025 \ltrch\fcs0 \fs24\lang1033\langfe1033\loch\af41\hich\af41\dbch\af13\cgrid\langnp1033\langfenp1033 {\rtlch\fcs1 \af41\afs18 \ltrch\fcs0 diff --git a/BaseTools/UserManuals/GenFw_Utility_Man_Page.rtf b/BaseTools/UserManuals/GenFw_Utility_Man_Page.rtf deleted file mode 100644 index ab7ba045e3..0000000000 --- a/BaseTools/UserManuals/GenFw_Utility_Man_Page.rtf +++ /dev/null @@ -1,179 +0,0 @@ -{\rtf1\ansi\ansicpg1252\deff0\nouicompat\deflang1033\deflangfe1033\deftab360{\fonttbl{\f0\fswiss\fprq2\fcharset0 Verdana;}{\f1\froman\fprq2\fcharset0 Times New Roman;}{\f2\fmodern\fprq1\fcharset0 Courier New;}{\f3\fmodern\fprq1\fcharset0 Consolas;}} -{\colortbl ;\red8\green96\blue168;\red0\green0\blue0;\red0\green127\blue127;\red128\green0\blue0;\red0\green0\blue255;} -{\stylesheet{ Normal;}{\s1 heading 1;}{\s2 heading 2;}} -{\*\generator Riched20 10.0.22621}{\*\mmathPr\mnaryLim0\mdispDef1\mwrapIndent1440 }\viewkind4\uc1 -\pard\keep\keepn\nowidctlpar\s2\li-1440\sb400\sa60\sl-340\slmult0\cf1\b\f0\fs28 Name\par - -\pard\nowidctlpar\sb200\cf2\b0\fs18 GenFw.exe \endash build a UEFI image or other image.\par - -\pard\keep\keepn\nowidctlpar\s2\li-1440\sb400\sa60\sl-340\slmult0\tx1440\cf1\b\fs28 Synopsis\par - -\pard\nowidctlpar\sb200\cf2\fs18 GenFw.exe -r | -o [-e ] [-c | -t | -l | -u | -b | -z | -s | -m | -j | --hiipackage | --hiibinpackage | --nonxcompat] [-a] [-p] \par - -\pard\nowidctlpar GenFw.exe \endash h\par -GenFw.exe --version\cf0\b0\fs24\par - -\pard\nowidctlpar\sb200\cf2\f1\fs18\par - -\pard\keep\keepn\nowidctlpar\s2\li-1440\sb400\sa60\sl-340\slmult0\cf1\b\f0\fs28 Description\par - -\pard\nowidctlpar\sb200\cf2\b0\fs18 Genfw is mainly used to process PE32 image to get the expected image data or image file. PE32 is a general-purpose image format that contains, among other information, data identifying the target environment for execution of the image. This utility can modify the standard PE32 image to create UEFI image with EFI subsystem type, PI Terse Executable image with the compact TE image header, zero its debug data or reset its time stamp. It can also extract PE32 image data to create bin file, extract PE32 image data section to create Acpi table image, or dump PI TE image header information. It can also parse the text MicroCode definition file to create the MicroCode binary image, merge (concatenate) several MicroCode binary images into a single file by pad value and alignment requirement. This tool also supports the override the input file with the output contents.\par - -\pard\keep\keepn\nowidctlpar\s2\li-1440\sb400\sa60\sl-340\slmult0\cf1\b\fs28 Options\par - -\pard\nowidctlpar\sb200\cf2\b0\fs18 If no options are specified, tool prints usage.\b\par -Filename1 [FilenameN]\par - -\pard\nowidctlpar\li360\sb200\b0 Input PE/PE32+ image, or TE image, or MicroCode Txt file, or MicroCode bin file, or hii binary packages.\par - -\pard\nowidctlpar\sb200\b -o FileName, --outputfile FileName\par - -\pard\nowidctlpar\li360\sb200\b0 The EFI image, TeImage, AcpiImage, MicroBin, hii package lists file or other modified PE image will be created.\par - -\pard\nowidctlpar\sb200\b -e EFI_FILETYPE, --efiImage EFI_FILETYPE\par - -\pard\nowidctlpar\li360\sb200\b0 Create Efi Image. EFI_FILETYPE is one of BASE, SEC, PEI_CORE, PEIM, DXE_CORE, SMM_CORE, DXE_DRIVER, UEFI_APPLICATION, DXE_SAL_DRIVER, UEFI_DRIVER, DXE_RUNTIME_DRIVER, DXE_SMM_DRIVER, SECURITY_CORE, COMBINED_PEIM_DRIVER, PIC_PEIM, RELOCATABLE_PEIM, BS_DRIVER, RT_DRIVER, APPLICATION, SAL_RT_DRIVER to support all module types.\f1\par - -\pard\nowidctlpar\sb200\b\f0 -c, --acpi\par - -\pard\nowidctlpar\fi360\sb200\b0 Create Acpi table.\par - -\pard\nowidctlpar\sb200\b -t, --terse\par - -\pard\nowidctlpar\fi360\sb200\b0 Create Te Image.\par - -\pard\nowidctlpar\sb200\b -u, --dump\par - -\pard\nowidctlpar\fi360\sb200\b0 Dump TeImage Header.\par - -\pard\nowidctlpar\sb200\b -z, --zero\par - -\pard\nowidctlpar\fi360\sb200\b0 Zero the Debug Data Fields in the PE input image file. It also zeros the time stamp fields.\f1\par - -\pard\nowidctlpar\sb200\b\f0 -b, --exe2bin\par - -\pard\nowidctlpar\fi360\sb200\b0 Convert the input EXE to the output BIN file.\par - -\pard\nowidctlpar\sb200\b -l, --stripped\par - -\pard\nowidctlpar\fi360\sb200\b0 Strip off the relocation information data from PE or TE image.\f1\par - -\pard\nowidctlpar\sb200\b\f0 -s timedate, --stamp timedate\par - -\pard\nowidctlpar\li360\sb200\b0 timedate format is \ldblquote yyyy-mm-dd 00:00:00\rdblquote . If timedata is set to \ldblquote NOW\rdblquote , current system time is used. The support date scope is 1970-1-1 8:0:0 ~ 2038-1-19 3:14:07.\f1\par - -\pard\nowidctlpar\sb200\b\f0 -m, --mcifile\par - -\pard\nowidctlpar\fi360\sb200\b0 Convert input microcode txt definition file to microcode bin file.\par - -\pard\nowidctlpar\sb200\b -j, --join\par - -\pard\nowidctlpar\fi360\sb200\b0 Merge multiple microcode bin files to one file.\par - -\pard\nowidctlpar\sb200\b -a NUM, --align NUM\par - -\pard\nowidctlpar\li360\sb200\b0 NUM is one HEX or DEC format alignment value, which is used to combine multiple microcode bin files.\par - -\pard\nowidctlpar\sb200\b -p NUM, --pad NUM\par - -\pard\nowidctlpar\li360\sb200\b0 NUM is one HEX or DEC format padding value, which is used to combine multiple microcode bin files.\par - -\pard\nowidctlpar\sb200\b --keepexceptiontable\par - -\pard\nowidctlpar\fi360\sb200\b0 Don\rquote t clear exception table.\par - -\pard\nowidctlpar\sb200\b --keepzeropending\par - -\pard\nowidctlpar\fi360\sb200\b0 Don\rquote t strip zero pending of .reloc.\par - -\pard\nowidctlpar\sb200\b -r, --replace\par - -\pard\nowidctlpar\fi360\sb200\b0 Overwrite the input file with the output content.\par - -\pard\nowidctlpar\sb200\b -g HiiPackageListGuid, --hiiguid HiiPackageListGuid\par - -\pard\nowidctlpar\fi360\sb200\b0 Guid is used to specify hii package list guid.\f1\par -\f0 Its format is xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx\par - -\pard\nowidctlpar\sb200\b --hiipackage \f1\par - -\pard\nowidctlpar\fi360\sb200\b0\f0 Combine all input binary hii packages into a single package list as the text resource data file (RC file format).\par - -\pard\nowidctlpar\sb200\b --hiibinpackage \f1\par - -\pard\nowidctlpar\fi360\sb200\b0\f0 Combine all input binary hii packages into a single package list as the binary resource section.\par - -\pard\nowidctlpar\sb200\b --nonxcompat \f1\par -\b0\f0 Do not set the IMAGE_DLLCHARACTERISTICS_NX_COMPAT bit of the optional header in the PE header even if the requirements are met.\par -\b -v, --verbose\b0\par - -\pard\nowidctlpar\fi360\sb200 Turn on verbose output with informational messages.\par - -\pard\nowidctlpar\sb200\b -d, --debug level\par -\b0\f1\tab\f0 Enable debug message with specified level.\par -\b --version\par - -\pard\nowidctlpar\fi360\sb200\b0 Show program's version number and exit\par - -\pard\nowidctlpar\sb200\b -h, --help\par - -\pard\nowidctlpar\fi360\sb200\b0 Show this help message and exit\par - -\pard\keep\keepn\nowidctlpar\s2\fi-1440\sb400\sa60\sl-340\slmult0\tx1440\cf3\b\fs28 Status codes returned\par -\trowd\trgaph10\trleft-118\trbrdrl\brdrs\brdrw10 \trbrdrt\brdrs\brdrw10 \trbrdrr\brdrs\brdrw10 \trbrdrb\brdrs\brdrw10 \trpaddl10\trpaddr10\trpaddfl3\trpaddfr3 -\clbrdrl\brdrw10\brdrs\clbrdrt\brdrw10\brdrs\clbrdrr\brdrw10\brdrs\clbrdrb\brdrw10\brdrs \cellx2852\clbrdrl\brdrw10\brdrs\clbrdrt\brdrw10\brdrs\clbrdrr\brdrw10\brdrs\clbrdrb\brdrw10\brdrs \cellx8702 -\pard\intbl\widctlpar\ri20\sb60\sa60\sl-200\slmult0\cf4\kerning2\f2\fs18 STATUS_SUCCESS\cf2\kerning0\b0\f0\fs16 \cf4\kerning2\b\f2\fs18\tab 0\cf2\cell\kerning0\b0\f0\fs16 The action was completed as requested.\kerning2\cell\row\trowd\trgaph10\trleft-118\trbrdrl\brdrs\brdrw10 \trbrdrt\brdrs\brdrw10 \trbrdrr\brdrs\brdrw10 \trbrdrb\brdrs\brdrw10 \trpaddl10\trpaddr10\trpaddfl3\trpaddfr3 -\clbrdrl\brdrw10\brdrs\clbrdrt\brdrw10\brdrs\clbrdrr\brdrw10\brdrs\clbrdrb\brdrw10\brdrs \cellx2852\clbrdrl\brdrw10\brdrs\clbrdrt\brdrw10\brdrs\clbrdrr\brdrw10\brdrs\clbrdrb\brdrw10\brdrs \cellx8702 -\pard\intbl\widctlpar\ri20\sb60\sa60\sl-200\slmult0\cf4\b\f2\fs18 STATUS_ERROR\cf2\kerning0\b0\f0\fs16 \cf4\kerning2\b\f2\fs18\tab\tab 2\cf0\kerning0\b0\f3\fs19\cell\cf2\kerning2\f0\fs16 The action failed.\cell\row -\pard\keep\keepn\nowidctlpar\s2\li-1440\sb400\sa60\sl-340\slmult0\cf1\kerning0\b\fs28 Example\par - -\pard\nowidctlpar\sb200\cf2\b0\fs18 1. Generate Efi image with the input PE image, module type and the output file name.\par -\b GenFw \endash e PEI_CORE PeiMain.dll \endash o PeiMain.efi\par -\b0 2. Generate Te image with the input PE image and the output file name.\par -\b GenFw \endash t PeiMain.dll \endash o PeiMain.te\par -\b0 3. Generate acpi table image with the input PE image and the output file name.\par -\b GenFw \endash c Facs.dll \endash o Facs.acpi\par -\b0 4. Dump TeImage Header with the input Te Image and the output file name.\par -\b GenFw \endash u PeiMain.te \endash o PeiMain.teheader\par -\b0 5. Modify PeImage by zero its debug data.\par -\b GenFw \endash z PeiMain.dll \endash o Peimain.zero\par -\b0 6. Modify PeImage by set new timestamp and override the input image without the output file name.\par -\b GenFw \endash s \ldblquote 2007-8-16 16:06:32\rdblquote PeiMain.dll \endash r\par -\b0 7. Extract bin image from PeImage.\par -\b GenFw \endash b PeiMain.dll \endash o PeiMain.bin\par -\b0 8. Generate the microcode binary file from the micro code txt file.\par -\b GenFw \endash m Mci.txt \endash o Mci.bin\par -\b0 9. Merge the multiple mci binary files to one file.\par -\b GenFw \endash j Mci.bin1 Mci.bin2 Mci.bin3 \endash a 32 \endash p 0xFF \endash o Mci.bin\par -\b0 10. Generate the text resource file (RC format) based on all input binary HII packages and their package list guid.\par -\b GenFw \endash o SampleHii.rc \endash g D49D2EB0-44D5-4621-9FD6-1A92C9109B99 \endash hiipackage SampleStr.hpk SampleVfr.hpk\f1\par -\b0\f0 11. Generate the binary resource section based on all input binary HII packages and their package list guid.\f1\par -\b\f0 GenFw \endash o SampleHii.bin \endash g D49D2EB0-44D5-4621-9FD6-1A92C9109B99 \endash hiibinpackage SampleStr.hpk SampleVfr.hpk\f1\par - -\pard\keep\keepn\nowidctlpar\s2\li-1440\sb400\sa60\sl-340\slmult0\cf1\f0\fs28 Bugs\par - -\pard\nowidctlpar\sb200\cf2\b0\fs18 No known bugs.\par -Report bugs to \cf5\revised edk2-devel@lists.01.org\cf2\revised0\deleted edk2-buildtools-devel@lists.sourceforge.net\deleted0\f1\par - -\pard\keep\keepn\nowidctlpar\s2\li-1440\sb400\sa60\sl-340\slmult0\cf1\b\f0\fs28 Files\par - -\pard\nowidctlpar\sb200\cf2\b0\fs18 None\par - -\pard\keep\keepn\nowidctlpar\s2\li-1440\sb400\sa60\sl-340\slmult0\cf1\b\fs28 See also\par - -\pard\nowidctlpar\sb200\cf2\b0\fs18 None\par - -\pard\keep\keepn\nowidctlpar\s2\li-1440\sb400\sa60\sl-340\slmult0\cf1\b\fs28 License\par - -\pard\nowidctlpar\cf2\b0\fs18 Copyright (c) 2007 - 2011, Intel Corporation. All rights reserved.\par -This program and the accompanying materials are licensed and made available \par -under the terms and conditions of the BSD License which accompanies this \par -distribution. The full text of the license may be found at\par -{{\field{\*\fldinst{HYPERLINK http://opensource.org/licenses/bsd-license.php }}{\fldrslt{http://opensource.org/licenses/bsd-license.php\ul0\cf0}}}}\f0\fs18\par -\par -THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\par - -\pard\nowidctlpar\sb200 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\par -\cf0\f1\par -} - \ No newline at end of file diff --git a/BaseTools/toolsetup.bat b/BaseTools/toolsetup.bat index 22bd0faeb9..9777e7fa70 100755 --- a/BaseTools/toolsetup.bat +++ b/BaseTools/toolsetup.bat @@ -263,7 +263,6 @@ if not exist "%EDK_TOOLS_BIN%" goto check_build_environment IF NOT EXIST "%EDK_TOOLS_BIN%\EfiRom.exe" goto check_c_tools IF NOT EXIST "%EDK_TOOLS_BIN%\GenFfs.exe" goto check_c_tools IF NOT EXIST "%EDK_TOOLS_BIN%\GenFv.exe" goto check_c_tools -IF NOT EXIST "%EDK_TOOLS_BIN%\GenFw.exe" goto check_c_tools IF NOT EXIST "%EDK_TOOLS_BIN%\GenSec.exe" goto check_c_tools IF NOT EXIST "%EDK_TOOLS_BIN%\TianoCompress.exe" goto check_c_tools IF NOT EXIST "%EDK_TOOLS_BIN%\VfrCompile.exe" goto check_c_tools diff --git a/MdePkg/Include/Library/UefiImageLib.h b/MdePkg/Include/Library/UefiImageLib.h index b0de4b317c..ecdb706fd9 100644 --- a/MdePkg/Include/Library/UefiImageLib.h +++ b/MdePkg/Include/Library/UefiImageLib.h @@ -2,6 +2,11 @@ #ifndef UEFI_IMAGE_LIB_H_ #define UEFI_IMAGE_LIB_H_ +typedef enum { + UefiImageFormatPe = 0, + UefiImageFormatMax +} UEFI_IMAGE_FORMAT; + // FIXME: Work on reasonable abstraction #ifndef UEFI_IMAGE_LOADER_IMAGE_CONTEXT #include diff --git a/MdePkg/Library/BaseCpuLib/Ia32/InitializeFpu.nasm b/MdePkg/Library/BaseCpuLib/Ia32/InitializeFpu.nasm index 5e27cc3250..3b0197a284 100644 --- a/MdePkg/Library/BaseCpuLib/Ia32/InitializeFpu.nasm +++ b/MdePkg/Library/BaseCpuLib/Ia32/InitializeFpu.nasm @@ -6,7 +6,7 @@ ;* ;------------------------------------------------------------------------------ - SECTION .rodata + SECTION RODATA_SECTION_NAME ; ; Float control word initial value: @@ -65,4 +65,3 @@ Done: pop ebx ret - diff --git a/MdePkg/Library/BaseCpuLib/X64/InitializeFpu.nasm b/MdePkg/Library/BaseCpuLib/X64/InitializeFpu.nasm index 8485b47135..22a5645abc 100644 --- a/MdePkg/Library/BaseCpuLib/X64/InitializeFpu.nasm +++ b/MdePkg/Library/BaseCpuLib/X64/InitializeFpu.nasm @@ -6,7 +6,7 @@ ;* ;------------------------------------------------------------------------------ - SECTION .rodata + SECTION RODATA_SECTION_NAME ; ; Float control word initial value: ; all exceptions masked, double-extended-precision, round-to-nearest @@ -48,4 +48,3 @@ ASM_PFX(InitializeFloatingPointUnits): ldmxcsr [mMmxControlWord] ret - diff --git a/OpenCorePkg b/OpenCorePkg new file mode 160000 index 0000000000..ca9a501490 --- /dev/null +++ b/OpenCorePkg @@ -0,0 +1 @@ +Subproject commit ca9a501490ccce20431f095182b4fb0d359d80e3 diff --git a/OvmfPkg/OvmfPkgIa32.dsc b/OvmfPkg/OvmfPkgIa32.dsc index 8200d85c01..fb0306fb25 100644 --- a/OvmfPkg/OvmfPkgIa32.dsc +++ b/OvmfPkg/OvmfPkgIa32.dsc @@ -102,20 +102,6 @@ !include NetworkPkg/NetworkBuildOptions.dsc.inc -[BuildOptions.common.EDKII.DXE_RUNTIME_DRIVER] - GCC:*_*_*_DLINK_FLAGS = -z common-page-size=0x1000 - XCODE:*_*_*_DLINK_FLAGS = -seg1addr 0x1000 -segalign 0x1000 - XCODE:*_*_*_MTOC_FLAGS = -align 0x1000 - CLANGPDB:*_*_*_DLINK_FLAGS = /ALIGN:4096 - -# Force PE/COFF sections to be aligned at 4KB boundaries to support page level -# protection of DXE_SMM_DRIVER/SMM_CORE modules -[BuildOptions.common.EDKII.DXE_SMM_DRIVER, BuildOptions.common.EDKII.SMM_CORE] - GCC:*_*_*_DLINK_FLAGS = -z common-page-size=0x1000 - XCODE:*_*_*_DLINK_FLAGS = -seg1addr 0x1000 -segalign 0x1000 - XCODE:*_*_*_MTOC_FLAGS = -align 0x1000 - CLANGPDB:*_*_*_DLINK_FLAGS = /ALIGN:4096 - ################################################################################ # # SKU Identification section - list of all SKU IDs supported by this Platform. @@ -597,14 +583,15 @@ # !if $(LEGACY_WINDOWS_LOADER) == TRUE # Allow execution of EfiLoaderData memory regions. - gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0x7FD1 + gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0xFFFFFFFFFFFFFFD1 !elseif $(LINUX_LOADER) == TRUE - # Allow execution of EfiConventionalMemory, EfiBootServicesData and EfiLoaderData memory regions. - gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0x7F41 + # Allow execution of EfiReservedMemoryType, EfiConventionalMemory, EfiBootServicesData and EfiLoaderData memory regions. + gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0xFFFFFFFFFFFFFF40 gEfiMdePkgTokenSpaceGuid.PcdImageLoaderAllowMisalignedOffset|TRUE !elseif $(WINDOWS_10_IA32) == TRUE # Allow execution of EfiReservedMemoryType, EfiConventionalMemory, EfiBootServicesData and EfiRuntimeServicesData memory regions. - gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0x7F04 + gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0xFFFFFFFFFFFFFF04 + gEfiMdeModulePkgTokenSpaceGuid.PcdImageProtectionPolicy|0x0 !endif ################################################################################ diff --git a/OvmfPkg/OvmfPkgIa32X64.dsc b/OvmfPkg/OvmfPkgIa32X64.dsc index a79da15629..506ca96d40 100644 --- a/OvmfPkg/OvmfPkgIa32X64.dsc +++ b/OvmfPkg/OvmfPkgIa32X64.dsc @@ -107,11 +107,6 @@ !include NetworkPkg/NetworkBuildOptions.dsc.inc - GCC:*_*_*_DLINK_FLAGS = -z common-page-size=0x1000 - XCODE:*_*_*_DLINK_FLAGS = -seg1addr 0x1000 -segalign 0x1000 - XCODE:*_*_*_MTOC_FLAGS = -align 0x1000 - CLANGPDB:*_*_*_DLINK_FLAGS = /FILEALIGN:4096 /ALIGN:4096 - ################################################################################ # # SKU Identification section - list of all SKU IDs supported by this Platform. @@ -603,14 +598,15 @@ # !if $(LEGACY_WINDOWS_LOADER) == TRUE # Allow execution of EfiLoaderData memory regions. - gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0x7FD1 + gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0xFFFFFFFFFFFFFFD1 !elseif $(LINUX_LOADER) == TRUE - # Allow execution of EfiConventionalMemory, EfiBootServicesData and EfiLoaderData memory regions. - gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0x7F41 + # Allow execution of EfiReservedMemoryType, EfiConventionalMemory, EfiBootServicesData and EfiLoaderData memory regions. + gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0xFFFFFFFFFFFFFF40 gEfiMdePkgTokenSpaceGuid.PcdImageLoaderAllowMisalignedOffset|TRUE !elseif $(WINDOWS_10_IA32) == TRUE # Allow execution of EfiReservedMemoryType, EfiConventionalMemory, EfiBootServicesData and EfiRuntimeServicesData memory regions. - gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0x7F04 + gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0xFFFFFFFFFFFFFF04 + gEfiMdeModulePkgTokenSpaceGuid.PcdImageProtectionPolicy|0x0 !endif ################################################################################ diff --git a/OvmfPkg/OvmfPkgIa32X64.fdf b/OvmfPkg/OvmfPkgIa32X64.fdf index 53f59e9680..5280b8bd4e 100644 --- a/OvmfPkg/OvmfPkgIa32X64.fdf +++ b/OvmfPkg/OvmfPkgIa32X64.fdf @@ -82,11 +82,11 @@ gUefiOvmfPkgTokenSpaceGuid.PcdOvmfWorkAreaBase|gUefiOvmfPkgTokenSpaceGuid.PcdOvm 0x010000|0x010000 gUefiOvmfPkgTokenSpaceGuid.PcdOvmfSecPeiTempRamBase|gUefiOvmfPkgTokenSpaceGuid.PcdOvmfSecPeiTempRamSize -0x020000|0x0E0000 +0x020000|0x100000 gUefiOvmfPkgTokenSpaceGuid.PcdOvmfPeiMemFvBase|gUefiOvmfPkgTokenSpaceGuid.PcdOvmfPeiMemFvSize FV = PEIFV -0x100000|0xE80000 +0x120000|0xE60000 gUefiOvmfPkgTokenSpaceGuid.PcdOvmfDxeMemFvBase|gUefiOvmfPkgTokenSpaceGuid.PcdOvmfDxeMemFvSize FV = DXEFV diff --git a/OvmfPkg/OvmfPkgX64.dsc b/OvmfPkg/OvmfPkgX64.dsc index b4246987e3..a5681c6931 100644 --- a/OvmfPkg/OvmfPkgX64.dsc +++ b/OvmfPkg/OvmfPkgX64.dsc @@ -119,20 +119,6 @@ !include NetworkPkg/NetworkBuildOptions.dsc.inc -[BuildOptions.common.EDKII.DXE_RUNTIME_DRIVER] - GCC:*_*_*_DLINK_FLAGS = -z common-page-size=0x1000 - XCODE:*_*_*_DLINK_FLAGS = -seg1addr 0x1000 -segalign 0x1000 - XCODE:*_*_*_MTOC_FLAGS = -align 0x1000 - CLANGPDB:*_*_*_DLINK_FLAGS = /ALIGN:4096 - -# Force PE/COFF sections to be aligned at 4KB boundaries to support page level -# protection of DXE_SMM_DRIVER/SMM_CORE modules -[BuildOptions.common.EDKII.DXE_SMM_DRIVER, BuildOptions.common.EDKII.SMM_CORE] - GCC:*_*_*_DLINK_FLAGS = -z common-page-size=0x1000 - XCODE:*_*_*_DLINK_FLAGS = -seg1addr 0x1000 -segalign 0x1000 - XCODE:*_*_*_MTOC_FLAGS = -align 0x1000 - CLANGPDB:*_*_*_DLINK_FLAGS = /ALIGN:4096 - ################################################################################ # # SKU Identification section - list of all SKU IDs supported by this Platform. @@ -597,7 +583,8 @@ gEmbeddedTokenSpaceGuid.PcdMemoryTypeEfiRuntimeServicesData|0x100 # - # TDX need 1G PageTable support + # TDX needs 1G PageTable support + # gEfiMdeModulePkgTokenSpaceGuid.PcdUse1GPageTable|TRUE # @@ -626,10 +613,10 @@ # !if $(LEGACY_WINDOWS_LOADER) == TRUE # Allow execution of EfiLoaderData memory regions. - gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0x7FD1 + gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0xFFFFFFFFFFFFFFD1 !elseif $(LINUX_LOADER) == TRUE - # Allow execution of EfiConventionalMemory, EfiBootServicesData and EfiLoaderData memory regions. - gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0x7F41 + # Allow execution of EfiReservedMemoryType, EfiConventionalMemory, EfiBootServicesData and EfiLoaderData memory regions. + gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0xFFFFFFFFFFFFFF40 gEfiMdePkgTokenSpaceGuid.PcdImageLoaderAllowMisalignedOffset|TRUE !endif diff --git a/OvmfPkg/OvmfPkgX64.fdf b/OvmfPkg/OvmfPkgX64.fdf index 4dcd6a033c..ddabe42be0 100644 --- a/OvmfPkg/OvmfPkgX64.fdf +++ b/OvmfPkg/OvmfPkgX64.fdf @@ -103,11 +103,11 @@ gUefiOvmfPkgTokenSpaceGuid.PcdOvmfSecApicPageTableBase|gUefiOvmfPkgTokenSpaceGui 0x011000|0x00F000 gUefiOvmfPkgTokenSpaceGuid.PcdOvmfSecPeiTempRamBase|gUefiOvmfPkgTokenSpaceGuid.PcdOvmfSecPeiTempRamSize -0x020000|0x0E0000 +0x020000|0x110000 gUefiOvmfPkgTokenSpaceGuid.PcdOvmfPeiMemFvBase|gUefiOvmfPkgTokenSpaceGuid.PcdOvmfPeiMemFvSize FV = PEIFV -0x100000|0xE80000 +0x130000|0xE50000 gUefiOvmfPkgTokenSpaceGuid.PcdOvmfDxeMemFvBase|gUefiOvmfPkgTokenSpaceGuid.PcdOvmfDxeMemFvSize FV = DXEFV diff --git a/UefiCpuPkg/SecCore/SecCoreNative.inf b/UefiCpuPkg/SecCore/SecCoreNative.inf index 454a3629e5..7b4e03b510 100644 --- a/UefiCpuPkg/SecCore/SecCoreNative.inf +++ b/UefiCpuPkg/SecCore/SecCoreNative.inf @@ -45,8 +45,8 @@ PcdLib DebugAgentLib CpuLib - PeCoffGetEntryPointLib - PeCoffExtraActionLib + UefiImageLib + UefiImageExtraActionLib CpuExceptionHandlerLib ReportStatusCodeLib PeiServicesLib diff --git a/UefiPayloadPkg/Library/UefiPayloadEntryMemoryAllocationLib/MemoryAllocation.c b/UefiPayloadPkg/Library/UefiPayloadMemoryAllocationLib/MemoryAllocationLib.c old mode 100644 new mode 100755 similarity index 78% rename from UefiPayloadPkg/Library/UefiPayloadEntryMemoryAllocationLib/MemoryAllocation.c rename to UefiPayloadPkg/Library/UefiPayloadMemoryAllocationLib/MemoryAllocationLib.c index 83936ae26e..59f9adbf1d --- a/UefiPayloadPkg/Library/UefiPayloadEntryMemoryAllocationLib/MemoryAllocation.c +++ b/UefiPayloadPkg/Library/UefiPayloadMemoryAllocationLib/MemoryAllocationLib.c @@ -8,7 +8,31 @@ **/ -#include "UefiPayloadEntry.h" +#include + +#include +#include +#include +#include +#include +#include + +/** + Add a new HOB to the HOB List. + + @param HobType Type of the new HOB. + @param HobLength Length of the new HOB to allocate. + + @return NULL if there is no space to create a hob. + @return The address point to the new created hob. + +**/ +VOID * +EFIAPI +CreateHob ( + IN UINT16 HobType, + IN UINT16 HobLength + ); /** Allocates one or more pages of type EfiBootServicesData. @@ -196,3 +220,28 @@ AllocateZeroPool ( return Buffer; } + +/** + Frees a buffer that was previously allocated with one of the pool allocation functions in the + Memory Allocation Library. + + Frees the buffer specified by Buffer. Buffer must have been allocated on a previous call to the + pool allocation services of the Memory Allocation Library. If it is not possible to free pool + resources, then this function will perform no actions. + + If Buffer was not allocated with a pool allocation function in the Memory Allocation Library, + then ASSERT(). + + @param Buffer The pointer to the buffer to free. + +**/ +VOID +EFIAPI +FreePool ( + IN VOID *Buffer + ) +{ + // + // PEI phase does not support to free pool, so leave it as NOP. + // +} diff --git a/UefiPayloadPkg/Library/UefiPayloadMemoryAllocationLib/UefiPayloadMemoryAllocationLib.inf b/UefiPayloadPkg/Library/UefiPayloadMemoryAllocationLib/UefiPayloadMemoryAllocationLib.inf new file mode 100755 index 0000000000..46ca835552 --- /dev/null +++ b/UefiPayloadPkg/Library/UefiPayloadMemoryAllocationLib/UefiPayloadMemoryAllocationLib.inf @@ -0,0 +1,39 @@ +## @file +# Instance of Memory Allocation Library using PEI Services. +# +# Memory Allocation Library that uses PEI Services to allocate memory. +# Free operations are ignored. +# +# Copyright (c) 2007 - 2018, Intel Corporation. All rights reserved.
+# +# SPDX-License-Identifier: BSD-2-Clause-Patent +# +# +## + +[Defines] + INF_VERSION = 0x00010005 + BASE_NAME = UefiPayloadMemoryAllocationLib + MODULE_UNI_FILE = UefiPayloadMemoryAllocationLib.uni + FILE_GUID = b694e0dc-cd4e-4b30-885b-9c164ed3e74a + MODULE_TYPE = PEIM + VERSION_STRING = 1.0 + LIBRARY_CLASS = MemoryAllocationLib|PEIM PEI_CORE SEC + + +# +# VALID_ARCHITECTURES = IA32 X64 EBC (EBC is for build only) +# + +[Sources] + MemoryAllocationLib.c + +[Packages] + MdePkg/MdePkg.dec + + +[LibraryClasses] + DebugLib + BaseMemoryLib + BaseLib + HobLib diff --git a/UefiPayloadPkg/Library/UefiPayloadMemoryAllocationLib/UefiPayloadMemoryAllocationLib.uni b/UefiPayloadPkg/Library/UefiPayloadMemoryAllocationLib/UefiPayloadMemoryAllocationLib.uni new file mode 100755 index 0000000000..0194972ecf --- /dev/null +++ b/UefiPayloadPkg/Library/UefiPayloadMemoryAllocationLib/UefiPayloadMemoryAllocationLib.uni @@ -0,0 +1,16 @@ +// /** @file +// Instance of Memory Allocation Library using PEI Services. +// +// Memory Allocation Library that uses PEI Services to allocate memory. +// Free operations are ignored. +// +// Copyright (c) 2007 - 2014, Intel Corporation. All rights reserved.
+// +// SPDX-License-Identifier: BSD-2-Clause-Patent +// +// **/ + + +#string STR_MODULE_ABSTRACT #language en-US "Instance of Memory Allocation Library for Uefi payloads" + +#string STR_MODULE_DESCRIPTION #language en-US "Memory Allocation Library that allocates memory in uefi payload implementations. Free operations are ignored." diff --git a/UefiPayloadPkg/PayloadLoaderPeim/ElfLib/ElfCommon.h b/UefiPayloadPkg/PayloadLoaderPeim/ElfLib/ElfCommon.h index 7559f229ef..aee9fd96b8 100644 --- a/UefiPayloadPkg/PayloadLoaderPeim/ElfLib/ElfCommon.h +++ b/UefiPayloadPkg/PayloadLoaderPeim/ElfLib/ElfCommon.h @@ -539,7 +539,8 @@ typedef struct { #define R_386_TLS_TPOFF32 37 /* GOT entry of -ve static TLS offset */ /* Null relocation */ -#define R_AARCH64_NONE 256 /* No relocation */ +#define R_AARCH64_NONE0 0 +#define R_AARCH64_NONE 256 /* No relocation */ /* Static AArch64 relocations */ /* Static data relocations */ #define R_AARCH64_ABS64 257 /* S + A */ @@ -735,6 +736,7 @@ typedef struct { #define R_ARM_THM_MOVW_PREL_NC 49 #define R_ARM_THM_MOVT_PREL 50 #define R_ARM_THM_JMP6 52 +#define R_ARM_THM_JUMP19 51 #define R_ARM_THM_ALU_PREL_11_0 53 #define R_ARM_THM_PC12 54 #define R_ARM_REL32_NOI 56 @@ -752,21 +754,14 @@ typedef struct { #define R_ARM_LDC_PC_G1 68 #define R_ARM_LDC_PC_G2 69 #define R_ARM_GOT_PREL 96 +#define R_ARM_GNU_VTENTRY 100 +#define R_ARM_GNU_VTINHERIT 101 #define R_ARM_THM_JUMP11 102 #define R_ARM_THM_JUMP8 103 #define R_ARM_TLS_GD32 104 #define R_ARM_TLS_LDM32 105 #define R_ARM_TLS_IE32 107 -#define R_ARM_THM_JUMP19 51 -#define R_ARM_GNU_VTENTRY 100 -#define R_ARM_GNU_VTINHERIT 101 -#define R_ARM_RSBREL32 250 -#define R_ARM_THM_RPC22 251 -#define R_ARM_RREL32 252 -#define R_ARM_RABS32 253 -#define R_ARM_RPC24 254 -#define R_ARM_RBASE 255 #define R_PPC_NONE 0/* No relocation. */ #define R_PPC_ADDR32 1 diff --git a/UefiPayloadPkg/UefiPayloadEntry/UniversalPayloadEntry.inf b/UefiPayloadPkg/UefiPayloadEntry/UniversalPayloadEntry.inf index 388dbf397e..6da276e6e1 100644 --- a/UefiPayloadPkg/UefiPayloadEntry/UniversalPayloadEntry.inf +++ b/UefiPayloadPkg/UefiPayloadEntry/UniversalPayloadEntry.inf @@ -23,7 +23,6 @@ [Sources] UniversalPayloadEntry.c LoadDxeCore.c - MemoryAllocation.c PrintHob.c AcpiTable.c @@ -53,6 +52,7 @@ HobLib CpuLib UefiImageLib + MemoryAllocationLib [Guids] gEfiMemoryTypeInformationGuid diff --git a/UefiPayloadPkg/UefiPayloadPkg.dsc b/UefiPayloadPkg/UefiPayloadPkg.dsc index d6c5c2e0e2..5bb5f5511d 100644 --- a/UefiPayloadPkg/UefiPayloadPkg.dsc +++ b/UefiPayloadPkg/UefiPayloadPkg.dsc @@ -161,13 +161,6 @@ MSFT:RELEASE_*_*_CC_FLAGS = /D MDEPKG_NDEBUG !endif -[BuildOptions.common.EDKII.DXE_RUNTIME_DRIVER] - GCC:*_*_*_DLINK_FLAGS = -z common-page-size=0x1000 - XCODE:*_*_*_DLINK_FLAGS = -seg1addr 0x1000 -segalign 0x1000 - XCODE:*_*_*_MTOC_FLAGS = -align 0x1000 - CLANGPDB:*_*_*_DLINK_FLAGS = /ALIGN:4096 - MSFT:*_*_*_DLINK_FLAGS = /ALIGN:4096 - ################################################################################ # # SKU Identification section - list of all SKU IDs supported by this Platform. @@ -348,7 +341,7 @@ !if $(MULTIPLE_DEBUG_PORT_SUPPORT) == TRUE SerialPortLib|UefiPayloadPkg/Library/BaseSerialPortLibHob/BaseSerialPortLibHob.inf !endif - MemoryAllocationLib|UefiPayloadPkg/Library/UefiPayloadEntryMemoryAllocationLib/UefiPayloadEntryMemoryAllocationLib.inf + MemoryAllocationLib|UefiPayloadPkg/Library/UefiPayloadMemoryAllocationLib/UefiPayloadMemoryAllocationLib.inf [LibraryClasses.common.DXE_CORE] DxeHobListLib|UefiPayloadPkg/Library/DxeHobListLibNull/DxeHobListLibNull.inf diff --git a/UefiPayloadPkg/UefiPayloadPkg.fdf b/UefiPayloadPkg/UefiPayloadPkg.fdf index c1b1e35f32..c961dc11b3 100644 --- a/UefiPayloadPkg/UefiPayloadPkg.fdf +++ b/UefiPayloadPkg/UefiPayloadPkg.fdf @@ -13,8 +13,8 @@ DEFINE FD_BASE = 0x00800000 DEFINE FD_BLOCK_SIZE = 0x00001000 !if $(TARGET) == "NOOPT" -DEFINE FD_SIZE = 0x00850000 -DEFINE NUM_BLOCKS = 0x850 +DEFINE FD_SIZE = 0x00A00000 +DEFINE NUM_BLOCKS = 0xA00 !else DEFINE FD_SIZE = 0x00590000