* [staging/LoongArch RESEND PATCH v1 13/33] BaseTools: BaseTools changes for LoongArch platform. @ 2022-02-09 6:54 Chao Li 2022-04-08 6:25 ` [edk2-devel] " Abner Chang 0 siblings, 1 reply; 3+ messages in thread From: Chao Li @ 2022-02-09 6:54 UTC (permalink / raw) To: devel; +Cc: Bob Feng, Liming Gao, Yuwei Chen, Baoqi Zhang C code changes for building EDK2 LoongArch platform. Cc: Bob Feng <bob.c.feng@intel.com> Cc: Liming Gao <gaoliming@byosoft.com.cn> Cc: Yuwei Chen <yuwei.chen@intel.com> Signed-off-by: Chao Li <lichao@loongson.cn> Co-authored-by: Baoqi Zhang <zhangbaoqi@loongson.cn> --- BaseTools/Source/C/Common/BasePeCoff.c | 15 +- BaseTools/Source/C/Common/PeCoffLoaderEx.c | 76 +++++++++ BaseTools/Source/C/GenFv/GenFvInternalLib.c | 128 ++++++++++++++- BaseTools/Source/C/GenFw/Elf64Convert.c | 153 +++++++++++++++++- BaseTools/Source/C/GenFw/elf_common.h | 58 +++++++ .../C/Include/IndustryStandard/PeImage.h | 57 ++++--- 6 files changed, 454 insertions(+), 33 deletions(-) diff --git a/BaseTools/Source/C/Common/BasePeCoff.c b/BaseTools/Source/C/Common/BasePeCoff.c index 62fbb2985c..30400d1341 100644 --- a/BaseTools/Source/C/Common/BasePeCoff.c +++ b/BaseTools/Source/C/Common/BasePeCoff.c @@ -5,6 +5,7 @@ Copyright (c) 2004 - 2018, Intel Corporation. All rights reserved.<BR> Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> Portions Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights reserved.<BR> +Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All rights reserved.<BR> SPDX-License-Identifier: BSD-2-Clause-Patent **/ @@ -68,6 +69,14 @@ PeCoffLoaderRelocateRiscVImage ( IN UINT64 Adjust ); +RETURN_STATUS +PeCoffLoaderRelocateLoongArch64Image ( + IN UINT16 *Reloc, + IN OUT CHAR8 *Fixup, + IN OUT CHAR8 **FixupData, + IN UINT64 Adjust + ); + STATIC RETURN_STATUS PeCoffLoaderGetPeHeader ( @@ -184,7 +193,8 @@ Returns: ImageContext->Machine != EFI_IMAGE_MACHINE_ARMT && \ ImageContext->Machine != EFI_IMAGE_MACHINE_EBC && \ ImageContext->Machine != EFI_IMAGE_MACHINE_AARCH64 && \ - ImageContext->Machine != EFI_IMAGE_MACHINE_RISCV64) { + ImageContext->Machine != EFI_IMAGE_MACHINE_RISCV64 && \ + ImageContext->Machine != EFI_IMAGE_MACHINE_LOONGARCH64) { if (ImageContext->Machine == IMAGE_FILE_MACHINE_ARM) { // // There are two types of ARM images. Pure ARM and ARM/Thumb. @@ -815,6 +825,9 @@ Returns: case EFI_IMAGE_MACHINE_RISCV64: Status = PeCoffLoaderRelocateRiscVImage (Reloc, Fixup, &FixupData, Adjust); break; + case EFI_IMAGE_MACHINE_LOONGARCH64: + Status = PeCoffLoaderRelocateLoongArch64Image (Reloc, Fixup, &FixupData, Adjust); + break; default: Status = RETURN_UNSUPPORTED; break; diff --git a/BaseTools/Source/C/Common/PeCoffLoaderEx.c b/BaseTools/Source/C/Common/PeCoffLoaderEx.c index 799f282970..b50ce8bdef 100644 --- a/BaseTools/Source/C/Common/PeCoffLoaderEx.c +++ b/BaseTools/Source/C/Common/PeCoffLoaderEx.c @@ -4,6 +4,7 @@ IA32 and X64 Specific relocation fixups Copyright (c) 2004 - 2018, Intel Corporation. All rights reserved.<BR> Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights reserved.<BR> +Copyright (c) 2022, Loongson Technology Corporation Limited. All rights reserved.<BR> SPDX-License-Identifier: BSD-2-Clause-Patent --*/ @@ -332,3 +333,78 @@ PeCoffLoaderRelocateArmImage ( return RETURN_SUCCESS; } + +/** + Performs a LoongArch specific relocation fixup. + + @param Reloc Pointer to the relocation record. + @param Fixup Pointer to the address to fix up. + @param FixupData Pointer to a buffer to log the fixups. + @param Adjust The offset to adjust the fixup. + + @return Status code. +**/ +RETURN_STATUS +PeCoffLoaderRelocateLoongArch64Image ( + IN UINT16 *Reloc, + IN OUT CHAR8 *Fixup, + IN OUT CHAR8 **FixupData, + IN UINT64 Adjust + ) +{ + UINT8 RelocType; + UINT64 Value = 0; + UINT64 Tmp1 = 0; + UINT64 Tmp2 = 0; + + RelocType = ((*Reloc) >> 12); + + switch (RelocType) { + case EFI_IMAGE_REL_BASED_LOONGARCH64_MARK_LA: + /* The next four instructions are used to load a 64 bit address, we change it together*/ + Value = (*(UINT32*)Fixup & 0x1ffffe0) << 7 | /* lu12i.w 20bits from bit5 */ + (*((UINT32*)Fixup + 1) & 0x3ffc00) >> 10; /* ori 12bits from bit10 */ + Tmp1 = *((UINT32*)Fixup + 2) & 0x1ffffe0; /* lu32i.d 20bits from bit5 */ + Tmp2 = *((UINT32*)Fixup + 3) & 0x3ffc00; /* lu52i.d 12bits from bit10 */ + Value = Value | (Tmp1 << 27) | (Tmp2 << 42); + + Value += Adjust; + + *(UINT32*)Fixup = (*(UINT32*)Fixup & ~0x1ffffe0) | (((Value >> 12) & 0xfffff) << 5); + if (*FixupData != NULL) { + *FixupData = ALIGN_POINTER (*FixupData, sizeof (UINT32)); + *(UINT32 *) (*FixupData) = *(UINT32*)Fixup; + *FixupData = *FixupData + sizeof (UINT32); + } + + Fixup += sizeof(UINT32); + *(UINT32*)Fixup = (*(UINT32*)Fixup & ~0x3ffc00) | ((Value & 0xfff) << 10); + if (*FixupData != NULL) { + *FixupData = ALIGN_POINTER (*FixupData, sizeof (UINT32)); + *(UINT32 *) (*FixupData) = *(UINT32*)Fixup; + *FixupData = *FixupData + sizeof (UINT32); + } + + Fixup += sizeof(UINT32); + *(UINT32*)Fixup = (*(UINT32*)Fixup & ~0x1ffffe0) | (((Value >> 32) & 0xfffff) << 5); + if (*FixupData != NULL) { + *FixupData = ALIGN_POINTER (*FixupData, sizeof (UINT32)); + *(UINT32 *) (*FixupData) = *(UINT32*)Fixup; + *FixupData = *FixupData + sizeof (UINT32); + } + + Fixup += sizeof(UINT32); + *(UINT32*)Fixup = (*(UINT32*)Fixup & ~0x3ffc00) | (((Value >> 52) & 0xfff) << 10); + if (*FixupData != NULL) { + *FixupData = ALIGN_POINTER (*FixupData, sizeof (UINT32)); + *(UINT32 *) (*FixupData) = *(UINT32*)Fixup; + *FixupData = *FixupData + sizeof (UINT32); + } + break; + default: + Error (NULL, 0, 3000, "", "PeCoffLoaderRelocateLoongArch64Image: Fixup[0x%x] Adjust[0x%llx] *Reloc[0x%x], type[0x%x].", *(UINT32*)Fixup, Adjust, *Reloc, RelocType); + return RETURN_UNSUPPORTED; + } + + return RETURN_SUCCESS; +} diff --git a/BaseTools/Source/C/GenFv/GenFvInternalLib.c b/BaseTools/Source/C/GenFv/GenFvInternalLib.c index d650a527a5..9c518b3609 100644 --- a/BaseTools/Source/C/GenFv/GenFvInternalLib.c +++ b/BaseTools/Source/C/GenFv/GenFvInternalLib.c @@ -5,6 +5,7 @@ Copyright (c) 2004 - 2018, Intel Corporation. All rights reserved.<BR> Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> Portions Copyright (c) 2016 HP Development Company, L.P.<BR> Portions Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights reserved.<BR> +Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All rights reserved.<BR> SPDX-License-Identifier: BSD-2-Clause-Patent **/ @@ -57,6 +58,7 @@ SPDX-License-Identifier: BSD-2-Clause-Patent BOOLEAN mArm = FALSE; BOOLEAN mRiscV = FALSE; +BOOLEAN mLoongArch = FALSE; STATIC UINT32 MaxFfsAlignment = 0; BOOLEAN VtfFileFlag = FALSE; @@ -2416,6 +2418,102 @@ Returns: return EFI_SUCCESS; } +EFI_STATUS +UpdateLoongArchResetVectorIfNeeded ( + IN MEMORY_FILE *FvImage, + IN FV_INFO *FvInfo + ) +/*++ + +Routine Description: + This parses the FV looking for SEC and patches that address into the + beginning of the FV header. + + For LoongArch ISA, the reset vector is at 0x1c000000. + + We relocate it to SecCoreEntry and copy the ResetVector code to the + beginning of the FV. + +Arguments: + FvImage Memory file for the FV memory image + FvInfo Information read from INF file. + +Returns: + + EFI_SUCCESS Function Completed successfully. + EFI_ABORTED Error encountered. + EFI_INVALID_PARAMETER A required parameter was NULL. + EFI_NOT_FOUND PEI Core file not found. + +--*/ +{ + EFI_STATUS Status; + EFI_FILE_SECTION_POINTER SecPe32; + BOOLEAN UpdateVectorSec = FALSE; + UINT16 MachineType = 0; + EFI_PHYSICAL_ADDRESS SecCoreEntryAddress = 0; + + // + // Verify input parameters + // + if (FvImage == NULL || FvInfo == NULL) { + return EFI_INVALID_PARAMETER; + } + + // + // Locate an SEC Core instance and if found extract the machine type and entry point address + // + Status = FindCorePeSection(FvImage->FileImage, FvInfo->Size, EFI_FV_FILETYPE_SECURITY_CORE, &SecPe32); + if (!EFI_ERROR(Status)) { + + Status = GetCoreMachineType(SecPe32, &MachineType); + if (EFI_ERROR(Status)) { + Error(NULL, 0, 3000, "Invalid", "Could not get the PE32 machine type for SEC Core."); + return EFI_ABORTED; + } + + Status = GetCoreEntryPointAddress(FvImage->FileImage, FvInfo, SecPe32, &SecCoreEntryAddress); + if (EFI_ERROR(Status)) { + Error(NULL, 0, 3000, "Invalid", "Could not get the PE32 entry point address for SEC Core."); + return EFI_ABORTED; + } + + UpdateVectorSec = TRUE; + } + + if (!UpdateVectorSec) + return EFI_SUCCESS; + + if (MachineType == EFI_IMAGE_MACHINE_LOONGARCH64) { + UINT32 ResetVector[3]; + UINT32 InstrStack; + + memset(ResetVector, 0, sizeof (ResetVector)); + + /* if we found an SEC core entry point then generate a branch instruction */ + if (UpdateVectorSec) { + VerboseMsg("UpdateLoongArchResetVectorIfNeeded updating LOONGARCH64 SEC vector"); + + InstrStack = (SecCoreEntryAddress >> 12) & 0xfffff; + ResetVector[0] = 0x14000001 | (InstrStack << 5); /* lu12i.w ra si20 */ + + InstrStack = (SecCoreEntryAddress & 0x0fff); + ResetVector[1] = 0x03800021 | (InstrStack << 10); /* ori ra, ra, ui12 */ + ResetVector[2] = 0x4c000021; /* jirl ra, ra, 0 */ + } + + // + // Copy to the beginning of the FV + // + memcpy(FvImage->FileImage, ResetVector, sizeof (ResetVector)); + } else { + Error(NULL, 0, 3000, "Invalid", "Unknown machine type"); + return EFI_ABORTED; + } + + return EFI_SUCCESS; +} + EFI_STATUS GetPe32Info ( IN UINT8 *Pe32, @@ -2509,7 +2607,7 @@ Returns: // if ((*MachineType != EFI_IMAGE_MACHINE_IA32) && (*MachineType != EFI_IMAGE_MACHINE_X64) && (*MachineType != EFI_IMAGE_MACHINE_EBC) && (*MachineType != EFI_IMAGE_MACHINE_ARMT) && (*MachineType != EFI_IMAGE_MACHINE_AARCH64) && - (*MachineType != EFI_IMAGE_MACHINE_RISCV64)) { + (*MachineType != EFI_IMAGE_MACHINE_RISCV64) && (*MachineType != EFI_IMAGE_MACHINE_LOONGARCH64)) { Error (NULL, 0, 3000, "Invalid", "Unrecognized machine type in the PE32 file."); return EFI_UNSUPPORTED; } @@ -2953,7 +3051,7 @@ Returns: goto Finish; } - if (!mArm && !mRiscV) { + if (!mArm && !mRiscV && !mLoongArch) { // // Update reset vector (SALE_ENTRY for IPF) // Now for IA32 and IA64 platform, the fv which has bsf file must have the @@ -3004,6 +3102,19 @@ Returns: FvHeader->Checksum = CalculateChecksum16 ((UINT16 *) FvHeader, FvHeader->HeaderLength / sizeof (UINT16)); } + if (mLoongArch) { + Status = UpdateLoongArchResetVectorIfNeeded (&FvImageMemoryFile, &mFvDataInfo); + if (EFI_ERROR (Status)) { + Error (NULL, 0, 3000, "Invalid", "Could not update the reset vector."); + goto Finish; + } + // + // Update Checksum for FvHeader + // + FvHeader->Checksum = 0; + FvHeader->Checksum = CalculateChecksum16 ((UINT16 *) FvHeader, FvHeader->HeaderLength / sizeof (UINT16)); + } + // // Update FV Alignment attribute to the largest alignment of all the FFS files in the FV // @@ -3450,6 +3561,11 @@ Returns: VerboseMsg("Located ARM/AArch64 SEC/PEI core in child FV"); mArm = TRUE; } + // machine type is LOONGARCH64, set a flag so LOONGARCH64 reset vector procesing occurs + if ((MachineType == EFI_IMAGE_MACHINE_LOONGARCH64)) { + VerboseMsg("Located LOONGARCH64 SEC core in child FV"); + mLoongArch = TRUE; + } } // @@ -3608,6 +3724,10 @@ Returns: mRiscV = TRUE; } + if ( (ImageContext.Machine == EFI_IMAGE_MACHINE_LOONGARCH64) ) { + mLoongArch = TRUE; + } + // // Keep Image Context for PE image in FV // @@ -3885,6 +4005,10 @@ Returns: mArm = TRUE; } + if ( (ImageContext.Machine == EFI_IMAGE_MACHINE_LOONGARCH64) ) { + mLoongArch = TRUE; + } + // // Keep Image Context for TE image in FV // diff --git a/BaseTools/Source/C/GenFw/Elf64Convert.c b/BaseTools/Source/C/GenFw/Elf64Convert.c index 0bb3ead228..b66aadfd6c 100644 --- a/BaseTools/Source/C/GenFw/Elf64Convert.c +++ b/BaseTools/Source/C/GenFw/Elf64Convert.c @@ -4,6 +4,7 @@ Elf64 convert solution Copyright (c) 2010 - 2021, Intel Corporation. All rights reserved.<BR> Portions copyright (c) 2013-2014, ARM Ltd. All rights reserved.<BR> Portions Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights reserved.<BR> +Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All rights reserved.<BR> SPDX-License-Identifier: BSD-2-Clause-Patent @@ -163,7 +164,7 @@ InitializeElf64 ( 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))) { + if (!((mEhdr->e_machine == EM_X86_64) || (mEhdr->e_machine == EM_AARCH64) || (mEhdr->e_machine == EM_RISCV64) || (mEhdr->e_machine == EM_LOONGARCH64))) { Warning (NULL, 0, 3000, "Unsupported", "ELF e_machine is not Elf64 machine."); } if (mEhdr->e_version != EV_CURRENT) { @@ -730,6 +731,7 @@ ScanSections64 ( case EM_X86_64: case EM_AARCH64: case EM_RISCV64: + case EM_LOONGARCH64: mCoffOffset += sizeof (EFI_IMAGE_NT_HEADERS64); break; default: @@ -943,6 +945,10 @@ ScanSections64 ( NtHdr->Pe32Plus.FileHeader.Machine = EFI_IMAGE_MACHINE_RISCV64; NtHdr->Pe32Plus.OptionalHeader.Magic = EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC; break; + case EM_LOONGARCH64: + NtHdr->Pe32Plus.FileHeader.Machine = EFI_IMAGE_MACHINE_LOONGARCH64; + NtHdr->Pe32Plus.OptionalHeader.Magic = EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC; + break; default: VerboseMsg ("%s unknown e_machine type. Assume X64", (UINTN)mEhdr->e_machine); @@ -1149,10 +1155,10 @@ WriteSections64 ( } // - // Skip error on EM_RISCV64 becasue no symble name is built - // from RISC-V toolchain. + // Skip error on EM_RISCV64 and EM_LOONGARCH64 becasue no symble name is built + // from RISC-V and LoongArch toolchain. // - if (mEhdr->e_machine != EM_RISCV64) { + if ((mEhdr->e_machine != EM_RISCV64) && (mEhdr->e_machine != EM_LOONGARCH64)) { 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.", @@ -1417,6 +1423,74 @@ WriteSections64 ( // Write section for RISC-V 64 architecture. // WriteSectionRiscV64 (Rel, Targ, SymShdr, Sym); + } else if (mEhdr->e_machine == EM_LOONGARCH64) { + switch (ELF_R_TYPE(Rel->r_info)) { + + 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: + // + // These types are not used or do not need to fix the offsets. + // + break; + default: + Error (NULL, 0, 3000, "Invalid", "WriteSections64(): %s unsupported ELF EM_LOONGARCH64 relocation 0x%x.", mInImageName, (unsigned) ELF64_R_TYPE(Rel->r_info)); + } } else { Error (NULL, 0, 3000, "Invalid", "Not a supported machine type"); } @@ -1647,6 +1721,77 @@ WriteRelocations64 ( 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_LOONGARCH64) { + 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: + // + // 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_LOONGARCH64 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); } diff --git a/BaseTools/Source/C/GenFw/elf_common.h b/BaseTools/Source/C/GenFw/elf_common.h index b67f59e7a0..34c8748f39 100644 --- a/BaseTools/Source/C/GenFw/elf_common.h +++ b/BaseTools/Source/C/GenFw/elf_common.h @@ -4,6 +4,7 @@ Ported ELF include files from FreeBSD Copyright (c) 2009 - 2010, Apple Inc. All rights reserved.<BR> Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> Portion Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights reserved.<BR> +Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All rights reserved.<BR> SPDX-License-Identifier: BSD-2-Clause-Patent @@ -181,6 +182,7 @@ typedef struct { #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_LOONGARCH64 258 /* LoongArch 64-bit Architecture */ /* Non-standard or deprecated. */ #define EM_486 6 /* Intel i486. */ @@ -1042,4 +1044,60 @@ typedef struct { #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 #endif /* !_SYS_ELF_COMMON_H_ */ diff --git a/BaseTools/Source/C/Include/IndustryStandard/PeImage.h b/BaseTools/Source/C/Include/IndustryStandard/PeImage.h index f17b8ee19b..80961e5576 100644 --- a/BaseTools/Source/C/Include/IndustryStandard/PeImage.h +++ b/BaseTools/Source/C/Include/IndustryStandard/PeImage.h @@ -7,6 +7,7 @@ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR> Portions copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights reserved.<BR> + Copyright (c) 2022, Loongson Technology Corporation Limited. All rights reserved.<BR> SPDX-License-Identifier: BSD-2-Clause-Patent @@ -36,23 +37,25 @@ // // PE32+ Machine type for EFI images // -#define IMAGE_FILE_MACHINE_I386 0x014c -#define IMAGE_FILE_MACHINE_EBC 0x0EBC -#define IMAGE_FILE_MACHINE_X64 0x8664 -#define IMAGE_FILE_MACHINE_ARM 0x01c0 // Thumb only -#define IMAGE_FILE_MACHINE_ARMT 0x01c2 // 32bit Mixed ARM and Thumb/Thumb 2 Little Endian -#define IMAGE_FILE_MACHINE_ARM64 0xAA64 // 64bit ARM Architecture, Little Endian -#define IMAGE_FILE_MACHINE_RISCV64 0x5064 // 64bit RISC-V ISA +#define IMAGE_FILE_MACHINE_I386 0x014c +#define IMAGE_FILE_MACHINE_EBC 0x0EBC +#define IMAGE_FILE_MACHINE_X64 0x8664 +#define IMAGE_FILE_MACHINE_ARM 0x01c0 // Thumb only +#define IMAGE_FILE_MACHINE_ARMT 0x01c2 // 32bit Mixed ARM and Thumb/Thumb 2 Little Endian +#define IMAGE_FILE_MACHINE_ARM64 0xAA64 // 64bit ARM Architecture, Little Endian +#define IMAGE_FILE_MACHINE_RISCV64 0x5064 // 64bit RISC-V ISA +#define IMAGE_FILE_MACHINE_LOONGARCH64 0x6264 // 64bit LoongArch Architecture // // Support old names for backward compatible // -#define EFI_IMAGE_MACHINE_IA32 IMAGE_FILE_MACHINE_I386 -#define EFI_IMAGE_MACHINE_EBC IMAGE_FILE_MACHINE_EBC -#define EFI_IMAGE_MACHINE_X64 IMAGE_FILE_MACHINE_X64 -#define EFI_IMAGE_MACHINE_ARMT IMAGE_FILE_MACHINE_ARMT -#define EFI_IMAGE_MACHINE_AARCH64 IMAGE_FILE_MACHINE_ARM64 -#define EFI_IMAGE_MACHINE_RISCV64 IMAGE_FILE_MACHINE_RISCV64 +#define EFI_IMAGE_MACHINE_IA32 IMAGE_FILE_MACHINE_I386 +#define EFI_IMAGE_MACHINE_EBC IMAGE_FILE_MACHINE_EBC +#define EFI_IMAGE_MACHINE_X64 IMAGE_FILE_MACHINE_X64 +#define EFI_IMAGE_MACHINE_ARMT IMAGE_FILE_MACHINE_ARMT +#define EFI_IMAGE_MACHINE_AARCH64 IMAGE_FILE_MACHINE_ARM64 +#define EFI_IMAGE_MACHINE_RISCV64 IMAGE_FILE_MACHINE_RISCV64 +#define EFI_IMAGE_MACHINE_LOONGARCH64 IMAGE_FILE_MACHINE_LOONGARCH64 #define EFI_IMAGE_DOS_SIGNATURE 0x5A4D // MZ #define EFI_IMAGE_OS2_SIGNATURE 0x454E // NE @@ -500,19 +503,21 @@ typedef struct { // // Based relocation types. // -#define EFI_IMAGE_REL_BASED_ABSOLUTE 0 -#define EFI_IMAGE_REL_BASED_HIGH 1 -#define EFI_IMAGE_REL_BASED_LOW 2 -#define EFI_IMAGE_REL_BASED_HIGHLOW 3 -#define EFI_IMAGE_REL_BASED_HIGHADJ 4 -#define EFI_IMAGE_REL_BASED_MIPS_JMPADDR 5 -#define EFI_IMAGE_REL_BASED_ARM_MOV32A 5 -#define EFI_IMAGE_REL_BASED_RISCV_HI20 5 -#define EFI_IMAGE_REL_BASED_ARM_MOV32T 7 -#define EFI_IMAGE_REL_BASED_RISCV_LOW12I 7 -#define EFI_IMAGE_REL_BASED_RISCV_LOW12S 8 -#define EFI_IMAGE_REL_BASED_IA64_IMM64 9 -#define EFI_IMAGE_REL_BASED_DIR64 10 +#define EFI_IMAGE_REL_BASED_ABSOLUTE 0 +#define EFI_IMAGE_REL_BASED_HIGH 1 +#define EFI_IMAGE_REL_BASED_LOW 2 +#define EFI_IMAGE_REL_BASED_HIGHLOW 3 +#define EFI_IMAGE_REL_BASED_HIGHADJ 4 +#define EFI_IMAGE_REL_BASED_MIPS_JMPADDR 5 +#define EFI_IMAGE_REL_BASED_ARM_MOV32A 5 +#define EFI_IMAGE_REL_BASED_RISCV_HI20 5 +#define EFI_IMAGE_REL_BASED_ARM_MOV32T 7 +#define EFI_IMAGE_REL_BASED_RISCV_LOW12I 7 +#define EFI_IMAGE_REL_BASED_RISCV_LOW12S 8 +#define EFI_IMAGE_REL_BASED_LOONGARCH32_MARK_LA 8 +#define EFI_IMAGE_REL_BASED_LOONGARCH64_MARK_LA 8 +#define EFI_IMAGE_REL_BASED_IA64_IMM64 9 +#define EFI_IMAGE_REL_BASED_DIR64 10 /// -- 2.27.0 ^ permalink raw reply related [flat|nested] 3+ messages in thread
* Re: [edk2-devel] [staging/LoongArch RESEND PATCH v1 13/33] BaseTools: BaseTools changes for LoongArch platform. 2022-02-09 6:54 [staging/LoongArch RESEND PATCH v1 13/33] BaseTools: BaseTools changes for LoongArch platform Chao Li @ 2022-04-08 6:25 ` Abner Chang 2022-04-12 9:36 ` Chao Li 0 siblings, 1 reply; 3+ messages in thread From: Abner Chang @ 2022-04-08 6:25 UTC (permalink / raw) To: devel@edk2.groups.io, lichao@loongson.cn Cc: Bob Feng, Liming Gao, Yuwei Chen, Baoqi Zhang > -----Original Message----- > From: devel@edk2.groups.io <devel@edk2.groups.io> On Behalf Of Chao Li > Sent: Wednesday, February 9, 2022 2:55 PM > To: devel@edk2.groups.io > Cc: Bob Feng <bob.c.feng@intel.com>; Liming Gao > <gaoliming@byosoft.com.cn>; Yuwei Chen <yuwei.chen@intel.com>; Baoqi > Zhang <zhangbaoqi@loongson.cn> > Subject: [edk2-devel] [staging/LoongArch RESEND PATCH v1 13/33] > BaseTools: BaseTools changes for LoongArch platform. > > C code changes for building EDK2 LoongArch platform. > > Cc: Bob Feng <bob.c.feng@intel.com> > Cc: Liming Gao <gaoliming@byosoft.com.cn> > Cc: Yuwei Chen <yuwei.chen@intel.com> > > Signed-off-by: Chao Li <lichao@loongson.cn> > Co-authored-by: Baoqi Zhang <zhangbaoqi@loongson.cn> > --- > BaseTools/Source/C/Common/BasePeCoff.c | 15 +- > BaseTools/Source/C/Common/PeCoffLoaderEx.c | 76 +++++++++ > BaseTools/Source/C/GenFv/GenFvInternalLib.c | 128 ++++++++++++++- > BaseTools/Source/C/GenFw/Elf64Convert.c | 153 +++++++++++++++++- > BaseTools/Source/C/GenFw/elf_common.h | 58 +++++++ > .../C/Include/IndustryStandard/PeImage.h | 57 ++++--- > 6 files changed, 454 insertions(+), 33 deletions(-) > > diff --git a/BaseTools/Source/C/Common/BasePeCoff.c > b/BaseTools/Source/C/Common/BasePeCoff.c > index 62fbb2985c..30400d1341 100644 > --- a/BaseTools/Source/C/Common/BasePeCoff.c > +++ b/BaseTools/Source/C/Common/BasePeCoff.c > @@ -5,6 +5,7 @@ > Copyright (c) 2004 - 2018, Intel Corporation. All rights reserved.<BR> > Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> > Portions Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All > rights reserved.<BR> > +Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All > rights reserved.<BR> > SPDX-License-Identifier: BSD-2-Clause-Patent > > **/ > @@ -68,6 +69,14 @@ PeCoffLoaderRelocateRiscVImage ( > IN UINT64 Adjust > ); > > +RETURN_STATUS > +PeCoffLoaderRelocateLoongArch64Image ( > + IN UINT16 *Reloc, > + IN OUT CHAR8 *Fixup, > + IN OUT CHAR8 **FixupData, > + IN UINT64 Adjust > + ); > + > STATIC > RETURN_STATUS > PeCoffLoaderGetPeHeader ( > @@ -184,7 +193,8 @@ Returns: > ImageContext->Machine != EFI_IMAGE_MACHINE_ARMT && \ > ImageContext->Machine != EFI_IMAGE_MACHINE_EBC && \ > ImageContext->Machine != EFI_IMAGE_MACHINE_AARCH64 && \ > - ImageContext->Machine != EFI_IMAGE_MACHINE_RISCV64) { > + ImageContext->Machine != EFI_IMAGE_MACHINE_RISCV64 && \ > + ImageContext->Machine != EFI_IMAGE_MACHINE_LOONGARCH64) { > if (ImageContext->Machine == IMAGE_FILE_MACHINE_ARM) { > // > // There are two types of ARM images. Pure ARM and ARM/Thumb. > @@ -815,6 +825,9 @@ Returns: > case EFI_IMAGE_MACHINE_RISCV64: > Status = PeCoffLoaderRelocateRiscVImage (Reloc, Fixup, &FixupData, > Adjust); > break; > + case EFI_IMAGE_MACHINE_LOONGARCH64: > + Status = PeCoffLoaderRelocateLoongArch64Image (Reloc, Fixup, > &FixupData, Adjust); > + break; > default: > Status = RETURN_UNSUPPORTED; > break; > diff --git a/BaseTools/Source/C/Common/PeCoffLoaderEx.c > b/BaseTools/Source/C/Common/PeCoffLoaderEx.c > index 799f282970..b50ce8bdef 100644 > --- a/BaseTools/Source/C/Common/PeCoffLoaderEx.c > +++ b/BaseTools/Source/C/Common/PeCoffLoaderEx.c > @@ -4,6 +4,7 @@ IA32 and X64 Specific relocation fixups > Copyright (c) 2004 - 2018, Intel Corporation. All rights reserved.<BR> > Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> > Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights > reserved.<BR> > +Copyright (c) 2022, Loongson Technology Corporation Limited. All rights > reserved.<BR> > SPDX-License-Identifier: BSD-2-Clause-Patent > > --*/ > @@ -332,3 +333,78 @@ PeCoffLoaderRelocateArmImage ( > > return RETURN_SUCCESS; > } > + > +/** > + Performs a LoongArch specific relocation fixup. > + > + @param Reloc Pointer to the relocation record. > + @param Fixup Pointer to the address to fix up. > + @param FixupData Pointer to a buffer to log the fixups. > + @param Adjust The offset to adjust the fixup. > + > + @return Status code. > +**/ > +RETURN_STATUS > +PeCoffLoaderRelocateLoongArch64Image ( > + IN UINT16 *Reloc, > + IN OUT CHAR8 *Fixup, > + IN OUT CHAR8 **FixupData, > + IN UINT64 Adjust > + ) > +{ > + UINT8 RelocType; > + UINT64 Value = 0; > + UINT64 Tmp1 = 0; > + UINT64 Tmp2 = 0; > + > + RelocType = ((*Reloc) >> 12); > + > + switch (RelocType) { > + case EFI_IMAGE_REL_BASED_LOONGARCH64_MARK_LA: > + /* The next four instructions are used to load a 64 bit address, we > change it together*/ > + Value = (*(UINT32*)Fixup & 0x1ffffe0) << 7 | /* lu12i.w 20bits from > bit5 */ Please use double back slash for the comment in the function. So the comment in the entire file look consistent. This applied to the changes in this patch. > + (*((UINT32*)Fixup + 1) & 0x3ffc00) >> 10; /* ori 12bits from bit10 */ > + Tmp1 = *((UINT32*)Fixup + 2) & 0x1ffffe0; /* lu32i.d 20bits from bit5 > */ > + Tmp2 = *((UINT32*)Fixup + 3) & 0x3ffc00; /* lu52i.d 12bits from > bit10 */ > + Value = Value | (Tmp1 << 27) | (Tmp2 << 42); > + > + Value += Adjust; > + > + *(UINT32*)Fixup = (*(UINT32*)Fixup & ~0x1ffffe0) | (((Value >> 12) & > 0xfffff) << 5); > + if (*FixupData != NULL) { > + *FixupData = ALIGN_POINTER (*FixupData, sizeof (UINT32)); > + *(UINT32 *) (*FixupData) = *(UINT32*)Fixup; > + *FixupData = *FixupData + sizeof (UINT32); > + } > + > + Fixup += sizeof(UINT32); > + *(UINT32*)Fixup = (*(UINT32*)Fixup & ~0x3ffc00) | ((Value & 0xfff) << > 10); > + if (*FixupData != NULL) { > + *FixupData = ALIGN_POINTER (*FixupData, sizeof (UINT32)); > + *(UINT32 *) (*FixupData) = *(UINT32*)Fixup; > + *FixupData = *FixupData + sizeof (UINT32); > + } > + > + Fixup += sizeof(UINT32); > + *(UINT32*)Fixup = (*(UINT32*)Fixup & ~0x1ffffe0) | (((Value >> 32) & > 0xfffff) << 5); > + if (*FixupData != NULL) { > + *FixupData = ALIGN_POINTER (*FixupData, sizeof (UINT32)); > + *(UINT32 *) (*FixupData) = *(UINT32*)Fixup; > + *FixupData = *FixupData + sizeof (UINT32); > + } > + > + Fixup += sizeof(UINT32); > + *(UINT32*)Fixup = (*(UINT32*)Fixup & ~0x3ffc00) | (((Value >> 52) & > 0xfff) << 10); > + if (*FixupData != NULL) { > + *FixupData = ALIGN_POINTER (*FixupData, sizeof (UINT32)); > + *(UINT32 *) (*FixupData) = *(UINT32*)Fixup; > + *FixupData = *FixupData + sizeof (UINT32); > + } > + break; > + default: > + Error (NULL, 0, 3000, "", "PeCoffLoaderRelocateLoongArch64Image: > Fixup[0x%x] Adjust[0x%llx] *Reloc[0x%x], type[0x%x].", *(UINT32*)Fixup, > Adjust, *Reloc, RelocType); > + return RETURN_UNSUPPORTED; > + } > + > + return RETURN_SUCCESS; > +} > diff --git a/BaseTools/Source/C/GenFv/GenFvInternalLib.c > b/BaseTools/Source/C/GenFv/GenFvInternalLib.c > index d650a527a5..9c518b3609 100644 > --- a/BaseTools/Source/C/GenFv/GenFvInternalLib.c > +++ b/BaseTools/Source/C/GenFv/GenFvInternalLib.c > @@ -5,6 +5,7 @@ Copyright (c) 2004 - 2018, Intel Corporation. All rights > reserved.<BR> > Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> > Portions Copyright (c) 2016 HP Development Company, L.P.<BR> > Portions Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All > rights reserved.<BR> > +Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All > rights reserved.<BR> > SPDX-License-Identifier: BSD-2-Clause-Patent > > **/ > @@ -57,6 +58,7 @@ SPDX-License-Identifier: BSD-2-Clause-Patent > > BOOLEAN mArm = FALSE; > BOOLEAN mRiscV = FALSE; > +BOOLEAN mLoongArch = FALSE; > STATIC UINT32 MaxFfsAlignment = 0; > BOOLEAN VtfFileFlag = FALSE; > > @@ -2416,6 +2418,102 @@ Returns: > return EFI_SUCCESS; > } > > +EFI_STATUS > +UpdateLoongArchResetVectorIfNeeded ( > + IN MEMORY_FILE *FvImage, > + IN FV_INFO *FvInfo > + ) > +/*++ > + > +Routine Description: > + This parses the FV looking for SEC and patches that address into the > + beginning of the FV header. > + > + For LoongArch ISA, the reset vector is at 0x1c000000. > + > + We relocate it to SecCoreEntry and copy the ResetVector code to the > + beginning of the FV. > + > +Arguments: > + FvImage Memory file for the FV memory image > + FvInfo Information read from INF file. > + > +Returns: > + > + EFI_SUCCESS Function Completed successfully. > + EFI_ABORTED Error encountered. > + EFI_INVALID_PARAMETER A required parameter was NULL. > + EFI_NOT_FOUND PEI Core file not found. > + > +--*/ > +{ > + EFI_STATUS Status; > + EFI_FILE_SECTION_POINTER SecPe32; > + BOOLEAN UpdateVectorSec = FALSE; > + UINT16 MachineType = 0; > + EFI_PHYSICAL_ADDRESS SecCoreEntryAddress = 0; > + > + // > + // Verify input parameters > + // > + if (FvImage == NULL || FvInfo == NULL) { > + return EFI_INVALID_PARAMETER; > + } > + > + // > + // Locate an SEC Core instance and if found extract the machine type and > entry point address > + // > + Status = FindCorePeSection(FvImage->FileImage, FvInfo->Size, > EFI_FV_FILETYPE_SECURITY_CORE, &SecPe32); > + if (!EFI_ERROR(Status)) { > + > + Status = GetCoreMachineType(SecPe32, &MachineType); > + if (EFI_ERROR(Status)) { > + Error(NULL, 0, 3000, "Invalid", "Could not get the PE32 machine type for > SEC Core."); > + return EFI_ABORTED; > + } > + > + Status = GetCoreEntryPointAddress(FvImage->FileImage, FvInfo, > SecPe32, &SecCoreEntryAddress); > + if (EFI_ERROR(Status)) { > + Error(NULL, 0, 3000, "Invalid", "Could not get the PE32 entry point > address for SEC Core."); > + return EFI_ABORTED; > + } > + > + UpdateVectorSec = TRUE; > + } > + > + if (!UpdateVectorSec) > + return EFI_SUCCESS; > + > + if (MachineType == EFI_IMAGE_MACHINE_LOONGARCH64) { > + UINT32 ResetVector[3]; > + UINT32 InstrStack; > + > + memset(ResetVector, 0, sizeof (ResetVector)); > + > + /* if we found an SEC core entry point then generate a branch instruction > */ > + if (UpdateVectorSec) { > + VerboseMsg("UpdateLoongArchResetVectorIfNeeded updating > LOONGARCH64 SEC vector"); > + > + InstrStack = (SecCoreEntryAddress >> 12) & 0xfffff; > + ResetVector[0] = 0x14000001 | (InstrStack << 5); /* lu12i.w ra si20 */ > + > + InstrStack = (SecCoreEntryAddress & 0x0fff); > + ResetVector[1] = 0x03800021 | (InstrStack << 10); /* ori ra, ra, ui12 */ > + ResetVector[2] = 0x4c000021; /* jirl ra, ra, 0 */ > + } > + > + // > + // Copy to the beginning of the FV > + // > + memcpy(FvImage->FileImage, ResetVector, sizeof (ResetVector)); > + } else { > + Error(NULL, 0, 3000, "Invalid", "Unknown machine type"); > + return EFI_ABORTED; > + } > + > + return EFI_SUCCESS; > +} > + > EFI_STATUS > GetPe32Info ( > IN UINT8 *Pe32, > @@ -2509,7 +2607,7 @@ Returns: > // > if ((*MachineType != EFI_IMAGE_MACHINE_IA32) && (*MachineType != > EFI_IMAGE_MACHINE_X64) && (*MachineType != > EFI_IMAGE_MACHINE_EBC) && > (*MachineType != EFI_IMAGE_MACHINE_ARMT) && (*MachineType != > EFI_IMAGE_MACHINE_AARCH64) && > - (*MachineType != EFI_IMAGE_MACHINE_RISCV64)) { > + (*MachineType != EFI_IMAGE_MACHINE_RISCV64) && > (*MachineType != EFI_IMAGE_MACHINE_LOONGARCH64)) { > Error (NULL, 0, 3000, "Invalid", "Unrecognized machine type in the PE32 > file."); > return EFI_UNSUPPORTED; > } > @@ -2953,7 +3051,7 @@ Returns: > goto Finish; > } > > - if (!mArm && !mRiscV) { > + if (!mArm && !mRiscV && !mLoongArch) { > // > // Update reset vector (SALE_ENTRY for IPF) > // Now for IA32 and IA64 platform, the fv which has bsf file must have the > @@ -3004,6 +3102,19 @@ Returns: > FvHeader->Checksum = CalculateChecksum16 ((UINT16 *) FvHeader, > FvHeader->HeaderLength / sizeof (UINT16)); > } > > + if (mLoongArch) { > + Status = UpdateLoongArchResetVectorIfNeeded (&FvImageMemoryFile, > &mFvDataInfo); > + if (EFI_ERROR (Status)) { > + Error (NULL, 0, 3000, "Invalid", "Could not update the reset vector."); > + goto Finish; > + } > + // > + // Update Checksum for FvHeader > + // > + FvHeader->Checksum = 0; > + FvHeader->Checksum = CalculateChecksum16 ((UINT16 *) FvHeader, > FvHeader->HeaderLength / sizeof (UINT16)); > + } > + > // > // Update FV Alignment attribute to the largest alignment of all the FFS files > in the FV > // > @@ -3450,6 +3561,11 @@ Returns: > VerboseMsg("Located ARM/AArch64 SEC/PEI core in child FV"); > mArm = TRUE; > } > + // machine type is LOONGARCH64, set a flag so LOONGARCH64 reset > vector procesing occurs > + if ((MachineType == EFI_IMAGE_MACHINE_LOONGARCH64)) { > + VerboseMsg("Located LOONGARCH64 SEC core in child FV"); > + mLoongArch = TRUE; > + } > } > > // > @@ -3608,6 +3724,10 @@ Returns: > mRiscV = TRUE; > } > > + if ( (ImageContext.Machine == EFI_IMAGE_MACHINE_LOONGARCH64) ) { > + mLoongArch = TRUE; > + } > + > // > // Keep Image Context for PE image in FV > // > @@ -3885,6 +4005,10 @@ Returns: > mArm = TRUE; > } > > + if ( (ImageContext.Machine == EFI_IMAGE_MACHINE_LOONGARCH64) ) { > + mLoongArch = TRUE; > + } > + > // > // Keep Image Context for TE image in FV > // > diff --git a/BaseTools/Source/C/GenFw/Elf64Convert.c > b/BaseTools/Source/C/GenFw/Elf64Convert.c > index 0bb3ead228..b66aadfd6c 100644 > --- a/BaseTools/Source/C/GenFw/Elf64Convert.c > +++ b/BaseTools/Source/C/GenFw/Elf64Convert.c > @@ -4,6 +4,7 @@ Elf64 convert solution > Copyright (c) 2010 - 2021, Intel Corporation. All rights reserved.<BR> > Portions copyright (c) 2013-2014, ARM Ltd. All rights reserved.<BR> > Portions Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All > rights reserved.<BR> > +Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All > rights reserved.<BR> > > SPDX-License-Identifier: BSD-2-Clause-Patent > > @@ -163,7 +164,7 @@ InitializeElf64 ( > 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))) { > + if (!((mEhdr->e_machine == EM_X86_64) || (mEhdr->e_machine == > EM_AARCH64) || (mEhdr->e_machine == EM_RISCV64) || (mEhdr- > >e_machine == EM_LOONGARCH64))) { > Warning (NULL, 0, 3000, "Unsupported", "ELF e_machine is not Elf64 > machine."); > } > if (mEhdr->e_version != EV_CURRENT) { > @@ -730,6 +731,7 @@ ScanSections64 ( > case EM_X86_64: > case EM_AARCH64: > case EM_RISCV64: > + case EM_LOONGARCH64: > mCoffOffset += sizeof (EFI_IMAGE_NT_HEADERS64); > break; > default: > @@ -943,6 +945,10 @@ ScanSections64 ( > NtHdr->Pe32Plus.FileHeader.Machine = EFI_IMAGE_MACHINE_RISCV64; > NtHdr->Pe32Plus.OptionalHeader.Magic = > EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC; > break; > + case EM_LOONGARCH64: > + NtHdr->Pe32Plus.FileHeader.Machine = > EFI_IMAGE_MACHINE_LOONGARCH64; > + NtHdr->Pe32Plus.OptionalHeader.Magic = > EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC; > + break; > > default: > VerboseMsg ("%s unknown e_machine type. Assume X64", > (UINTN)mEhdr->e_machine); > @@ -1149,10 +1155,10 @@ WriteSections64 ( > } > > // > - // Skip error on EM_RISCV64 becasue no symble name is built > - // from RISC-V toolchain. > + // Skip error on EM_RISCV64 and EM_LOONGARCH64 becasue no > symble name is built > + // from RISC-V and LoongArch toolchain. > // > - if (mEhdr->e_machine != EM_RISCV64) { > + if ((mEhdr->e_machine != EM_RISCV64) && (mEhdr->e_machine != > EM_LOONGARCH64)) { > 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.", > @@ -1417,6 +1423,74 @@ WriteSections64 ( > // Write section for RISC-V 64 architecture. > // > WriteSectionRiscV64 (Rel, Targ, SymShdr, Sym); > + } else if (mEhdr->e_machine == EM_LOONGARCH64) { > + switch (ELF_R_TYPE(Rel->r_info)) { > + > + 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: > + // > + // These types are not used or do not need to fix the offsets. > + // > + break; > + default: > + Error (NULL, 0, 3000, "Invalid", "WriteSections64(): %s unsupported > ELF EM_LOONGARCH64 relocation 0x%x.", mInImageName, (unsigned) > ELF64_R_TYPE(Rel->r_info)); > + } > } else { > Error (NULL, 0, 3000, "Invalid", "Not a supported machine type"); > } > @@ -1647,6 +1721,77 @@ WriteRelocations64 ( > 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_LOONGARCH64) { > + 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: > + // > + // 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_LOONGARCH64 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); > } > diff --git a/BaseTools/Source/C/GenFw/elf_common.h > b/BaseTools/Source/C/GenFw/elf_common.h > index b67f59e7a0..34c8748f39 100644 > --- a/BaseTools/Source/C/GenFw/elf_common.h > +++ b/BaseTools/Source/C/GenFw/elf_common.h > @@ -4,6 +4,7 @@ Ported ELF include files from FreeBSD > Copyright (c) 2009 - 2010, Apple Inc. All rights reserved.<BR> > Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> > Portion Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All > rights reserved.<BR> > +Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All > rights reserved.<BR> > SPDX-License-Identifier: BSD-2-Clause-Patent > > > @@ -181,6 +182,7 @@ typedef struct { > #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_LOONGARCH64 258 /* LoongArch 64-bit Architecture */ Do you have 32-bit LOONGARCH that also requires a value in spec? Abner > > /* Non-standard or deprecated. */ > #define EM_486 6 /* Intel i486. */ > @@ -1042,4 +1044,60 @@ typedef struct { > #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 > #endif /* !_SYS_ELF_COMMON_H_ */ > diff --git a/BaseTools/Source/C/Include/IndustryStandard/PeImage.h > b/BaseTools/Source/C/Include/IndustryStandard/PeImage.h > index f17b8ee19b..80961e5576 100644 > --- a/BaseTools/Source/C/Include/IndustryStandard/PeImage.h > +++ b/BaseTools/Source/C/Include/IndustryStandard/PeImage.h > @@ -7,6 +7,7 @@ > Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR> > Portions copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> > Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights > reserved.<BR> > + Copyright (c) 2022, Loongson Technology Corporation Limited. All rights > reserved.<BR> > > SPDX-License-Identifier: BSD-2-Clause-Patent > > @@ -36,23 +37,25 @@ > // > // PE32+ Machine type for EFI images > // > -#define IMAGE_FILE_MACHINE_I386 0x014c > -#define IMAGE_FILE_MACHINE_EBC 0x0EBC > -#define IMAGE_FILE_MACHINE_X64 0x8664 > -#define IMAGE_FILE_MACHINE_ARM 0x01c0 // Thumb only > -#define IMAGE_FILE_MACHINE_ARMT 0x01c2 // 32bit Mixed ARM and > Thumb/Thumb 2 Little Endian > -#define IMAGE_FILE_MACHINE_ARM64 0xAA64 // 64bit ARM > Architecture, Little Endian > -#define IMAGE_FILE_MACHINE_RISCV64 0x5064 // 64bit RISC-V ISA > +#define IMAGE_FILE_MACHINE_I386 0x014c > +#define IMAGE_FILE_MACHINE_EBC 0x0EBC > +#define IMAGE_FILE_MACHINE_X64 0x8664 > +#define IMAGE_FILE_MACHINE_ARM 0x01c0 // Thumb only > +#define IMAGE_FILE_MACHINE_ARMT 0x01c2 // 32bit Mixed ARM and > Thumb/Thumb 2 Little Endian > +#define IMAGE_FILE_MACHINE_ARM64 0xAA64 // 64bit ARM > Architecture, Little Endian > +#define IMAGE_FILE_MACHINE_RISCV64 0x5064 // 64bit RISC-V ISA > +#define IMAGE_FILE_MACHINE_LOONGARCH64 0x6264 // 64bit LoongArch > Architecture > > // > // Support old names for backward compatible > // > -#define EFI_IMAGE_MACHINE_IA32 IMAGE_FILE_MACHINE_I386 > -#define EFI_IMAGE_MACHINE_EBC IMAGE_FILE_MACHINE_EBC > -#define EFI_IMAGE_MACHINE_X64 IMAGE_FILE_MACHINE_X64 > -#define EFI_IMAGE_MACHINE_ARMT IMAGE_FILE_MACHINE_ARMT > -#define EFI_IMAGE_MACHINE_AARCH64 IMAGE_FILE_MACHINE_ARM64 > -#define EFI_IMAGE_MACHINE_RISCV64 IMAGE_FILE_MACHINE_RISCV64 > +#define EFI_IMAGE_MACHINE_IA32 IMAGE_FILE_MACHINE_I386 > +#define EFI_IMAGE_MACHINE_EBC IMAGE_FILE_MACHINE_EBC > +#define EFI_IMAGE_MACHINE_X64 IMAGE_FILE_MACHINE_X64 > +#define EFI_IMAGE_MACHINE_ARMT IMAGE_FILE_MACHINE_ARMT > +#define EFI_IMAGE_MACHINE_AARCH64 > IMAGE_FILE_MACHINE_ARM64 > +#define EFI_IMAGE_MACHINE_RISCV64 IMAGE_FILE_MACHINE_RISCV64 > +#define EFI_IMAGE_MACHINE_LOONGARCH64 > IMAGE_FILE_MACHINE_LOONGARCH64 > > #define EFI_IMAGE_DOS_SIGNATURE 0x5A4D // MZ > #define EFI_IMAGE_OS2_SIGNATURE 0x454E // NE > @@ -500,19 +503,21 @@ typedef struct { > // > // Based relocation types. > // > -#define EFI_IMAGE_REL_BASED_ABSOLUTE 0 > -#define EFI_IMAGE_REL_BASED_HIGH 1 > -#define EFI_IMAGE_REL_BASED_LOW 2 > -#define EFI_IMAGE_REL_BASED_HIGHLOW 3 > -#define EFI_IMAGE_REL_BASED_HIGHADJ 4 > -#define EFI_IMAGE_REL_BASED_MIPS_JMPADDR 5 > -#define EFI_IMAGE_REL_BASED_ARM_MOV32A 5 > -#define EFI_IMAGE_REL_BASED_RISCV_HI20 5 > -#define EFI_IMAGE_REL_BASED_ARM_MOV32T 7 > -#define EFI_IMAGE_REL_BASED_RISCV_LOW12I 7 > -#define EFI_IMAGE_REL_BASED_RISCV_LOW12S 8 > -#define EFI_IMAGE_REL_BASED_IA64_IMM64 9 > -#define EFI_IMAGE_REL_BASED_DIR64 10 > +#define EFI_IMAGE_REL_BASED_ABSOLUTE 0 > +#define EFI_IMAGE_REL_BASED_HIGH 1 > +#define EFI_IMAGE_REL_BASED_LOW 2 > +#define EFI_IMAGE_REL_BASED_HIGHLOW 3 > +#define EFI_IMAGE_REL_BASED_HIGHADJ 4 > +#define EFI_IMAGE_REL_BASED_MIPS_JMPADDR 5 > +#define EFI_IMAGE_REL_BASED_ARM_MOV32A 5 > +#define EFI_IMAGE_REL_BASED_RISCV_HI20 5 > +#define EFI_IMAGE_REL_BASED_ARM_MOV32T 7 > +#define EFI_IMAGE_REL_BASED_RISCV_LOW12I 7 > +#define EFI_IMAGE_REL_BASED_RISCV_LOW12S 8 > +#define EFI_IMAGE_REL_BASED_LOONGARCH32_MARK_LA 8 > +#define EFI_IMAGE_REL_BASED_LOONGARCH64_MARK_LA 8 > +#define EFI_IMAGE_REL_BASED_IA64_IMM64 9 > +#define EFI_IMAGE_REL_BASED_DIR64 10 > > > /// > -- > 2.27.0 > > > > > ^ permalink raw reply [flat|nested] 3+ messages in thread
* Re: [edk2-devel] [staging/LoongArch RESEND PATCH v1 13/33] BaseTools: BaseTools changes for LoongArch platform. 2022-04-08 6:25 ` [edk2-devel] " Abner Chang @ 2022-04-12 9:36 ` Chao Li 0 siblings, 0 replies; 3+ messages in thread From: Chao Li @ 2022-04-12 9:36 UTC (permalink / raw) To: "Chang, Abner (HPS SW/FW Technologist)" Cc: "devel@edk2.groups.io", Bob Feng, Liming Gao, Yuwei Chen, Baoqi Zhang [-- Attachment #1: Type: text/plain, Size: 28736 bytes --] Hi Anber, Please check my reply in the mail. -- Thanks, Chao ------------------------ On 4月 8 2022, at 2:25 下午, "Chang, Abner (HPS SW/FW Technologist)" <abner.chang@hpe.com> wrote: > > > > -----Original Message----- > > From: devel@edk2.groups.io <devel@edk2.groups.io> On Behalf Of Chao Li > > Sent: Wednesday, February 9, 2022 2:55 PM > > To: devel@edk2.groups.io > > Cc: Bob Feng <bob.c.feng@intel.com>; Liming Gao > > <gaoliming@byosoft.com.cn>; Yuwei Chen <yuwei.chen@intel.com>; Baoqi > > Zhang <zhangbaoqi@loongson.cn> > > Subject: [edk2-devel] [staging/LoongArch RESEND PATCH v1 13/33] > > BaseTools: BaseTools changes for LoongArch platform. > > > > C code changes for building EDK2 LoongArch platform. > > > > Cc: Bob Feng <bob.c.feng@intel.com> > > Cc: Liming Gao <gaoliming@byosoft.com.cn> > > Cc: Yuwei Chen <yuwei.chen@intel.com> > > > > Signed-off-by: Chao Li <lichao@loongson.cn> > > Co-authored-by: Baoqi Zhang <zhangbaoqi@loongson.cn> > > --- > > BaseTools/Source/C/Common/BasePeCoff.c | 15 +- > > BaseTools/Source/C/Common/PeCoffLoaderEx.c | 76 +++++++++ > > BaseTools/Source/C/GenFv/GenFvInternalLib.c | 128 ++++++++++++++- > > BaseTools/Source/C/GenFw/Elf64Convert.c | 153 +++++++++++++++++- > > BaseTools/Source/C/GenFw/elf_common.h | 58 +++++++ > > .../C/Include/IndustryStandard/PeImage.h | 57 ++++--- > > 6 files changed, 454 insertions(+), 33 deletions(-) > > > > diff --git a/BaseTools/Source/C/Common/BasePeCoff.c > > b/BaseTools/Source/C/Common/BasePeCoff.c > > index 62fbb2985c..30400d1341 100644 > > --- a/BaseTools/Source/C/Common/BasePeCoff.c > > +++ b/BaseTools/Source/C/Common/BasePeCoff.c > > @@ -5,6 +5,7 @@ > > Copyright (c) 2004 - 2018, Intel Corporation. All rights reserved.<BR> > > Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> > > Portions Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All > > rights reserved.<BR> > > +Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All > > rights reserved.<BR> > > SPDX-License-Identifier: BSD-2-Clause-Patent > > > > **/ > > @@ -68,6 +69,14 @@ PeCoffLoaderRelocateRiscVImage ( > > IN UINT64 Adjust > > ); > > > > +RETURN_STATUS > > +PeCoffLoaderRelocateLoongArch64Image ( > > + IN UINT16 *Reloc, > > + IN OUT CHAR8 *Fixup, > > + IN OUT CHAR8 **FixupData, > > + IN UINT64 Adjust > > + ); > > + > > STATIC > > RETURN_STATUS > > PeCoffLoaderGetPeHeader ( > > @@ -184,7 +193,8 @@ Returns: > > ImageContext->Machine != EFI_IMAGE_MACHINE_ARMT && \ > > ImageContext->Machine != EFI_IMAGE_MACHINE_EBC && \ > > ImageContext->Machine != EFI_IMAGE_MACHINE_AARCH64 && \ > > - ImageContext->Machine != EFI_IMAGE_MACHINE_RISCV64) { > > + ImageContext->Machine != EFI_IMAGE_MACHINE_RISCV64 && \ > > + ImageContext->Machine != EFI_IMAGE_MACHINE_LOONGARCH64) { > > if (ImageContext->Machine == IMAGE_FILE_MACHINE_ARM) { > > // > > // There are two types of ARM images. Pure ARM and ARM/Thumb. > > @@ -815,6 +825,9 @@ Returns: > > case EFI_IMAGE_MACHINE_RISCV64: > > Status = PeCoffLoaderRelocateRiscVImage (Reloc, Fixup, &FixupData, > > Adjust); > > break; > > + case EFI_IMAGE_MACHINE_LOONGARCH64: > > + Status = PeCoffLoaderRelocateLoongArch64Image (Reloc, Fixup, > > &FixupData, Adjust); > > + break; > > default: > > Status = RETURN_UNSUPPORTED; > > break; > > diff --git a/BaseTools/Source/C/Common/PeCoffLoaderEx.c > > b/BaseTools/Source/C/Common/PeCoffLoaderEx.c > > index 799f282970..b50ce8bdef 100644 > > --- a/BaseTools/Source/C/Common/PeCoffLoaderEx.c > > +++ b/BaseTools/Source/C/Common/PeCoffLoaderEx.c > > @@ -4,6 +4,7 @@ IA32 and X64 Specific relocation fixups > > Copyright (c) 2004 - 2018, Intel Corporation. All rights reserved.<BR> > > Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> > > Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights > > reserved.<BR> > > +Copyright (c) 2022, Loongson Technology Corporation Limited. All rights > > reserved.<BR> > > SPDX-License-Identifier: BSD-2-Clause-Patent > > > > --*/ > > @@ -332,3 +333,78 @@ PeCoffLoaderRelocateArmImage ( > > > > return RETURN_SUCCESS; > > } > > + > > +/** > > + Performs a LoongArch specific relocation fixup. > > + > > + @param Reloc Pointer to the relocation record. > > + @param Fixup Pointer to the address to fix up. > > + @param FixupData Pointer to a buffer to log the fixups. > > + @param Adjust The offset to adjust the fixup. > > + > > + @return Status code. > > +**/ > > +RETURN_STATUS > > +PeCoffLoaderRelocateLoongArch64Image ( > > + IN UINT16 *Reloc, > > + IN OUT CHAR8 *Fixup, > > + IN OUT CHAR8 **FixupData, > > + IN UINT64 Adjust > > + ) > > +{ > > + UINT8 RelocType; > > + UINT64 Value = 0; > > + UINT64 Tmp1 = 0; > > + UINT64 Tmp2 = 0; > > + > > + RelocType = ((*Reloc) >> 12); > > + > > + switch (RelocType) { > > + case EFI_IMAGE_REL_BASED_LOONGARCH64_MARK_LA: > > + /* The next four instructions are used to load a 64 bit address, we > > change it together*/ > > + Value = (*(UINT32*)Fixup & 0x1ffffe0) << 7 | /* lu12i.w 20bits from > > bit5 */ > Please use double back slash for the comment in the function. So the comment in the entire file look consistent. This applied to the changes in this patch. > Chao: Okay, I will revise it in the next version. > + (*((UINT32*)Fixup + 1) & 0x3ffc00) >> 10; /* ori 12bits from bit10 */ > + Tmp1 = *((UINT32*)Fixup + 2) & 0x1ffffe0; /* lu32i.d 20bits from bit5 > */ > + Tmp2 = *((UINT32*)Fixup + 3) & 0x3ffc00; /* lu52i.d 12bits from > bit10 */ > + Value = Value | (Tmp1 << 27) | (Tmp2 << 42); > + > + Value += Adjust; > + > + *(UINT32*)Fixup = (*(UINT32*)Fixup & ~0x1ffffe0) | (((Value >> 12) & > 0xfffff) << 5); > + if (*FixupData != NULL) { > + *FixupData = ALIGN_POINTER (*FixupData, sizeof (UINT32)); > + *(UINT32 *) (*FixupData) = *(UINT32*)Fixup; > + *FixupData = *FixupData + sizeof (UINT32); > + } > + > + Fixup += sizeof(UINT32); > + *(UINT32*)Fixup = (*(UINT32*)Fixup & ~0x3ffc00) | ((Value & 0xfff) << > 10); > + if (*FixupData != NULL) { > + *FixupData = ALIGN_POINTER (*FixupData, sizeof (UINT32)); > + *(UINT32 *) (*FixupData) = *(UINT32*)Fixup; > + *FixupData = *FixupData + sizeof (UINT32); > + } > + > + Fixup += sizeof(UINT32); > + *(UINT32*)Fixup = (*(UINT32*)Fixup & ~0x1ffffe0) | (((Value >> 32) & > 0xfffff) << 5); > + if (*FixupData != NULL) { > + *FixupData = ALIGN_POINTER (*FixupData, sizeof (UINT32)); > + *(UINT32 *) (*FixupData) = *(UINT32*)Fixup; > + *FixupData = *FixupData + sizeof (UINT32); > + } > + > + Fixup += sizeof(UINT32); > + *(UINT32*)Fixup = (*(UINT32*)Fixup & ~0x3ffc00) | (((Value >> 52) & > 0xfff) << 10); > + if (*FixupData != NULL) { > + *FixupData = ALIGN_POINTER (*FixupData, sizeof (UINT32)); > + *(UINT32 *) (*FixupData) = *(UINT32*)Fixup; > + *FixupData = *FixupData + sizeof (UINT32); > + } > + break; > + default: > + Error (NULL, 0, 3000, "", "PeCoffLoaderRelocateLoongArch64Image: > Fixup[0x%x] Adjust[0x%llx] *Reloc[0x%x], type[0x%x].", *(UINT32*)Fixup, > Adjust, *Reloc, RelocType); > + return RETURN_UNSUPPORTED; > + } > + > + return RETURN_SUCCESS; > +} > diff --git a/BaseTools/Source/C/GenFv/GenFvInternalLib.c > b/BaseTools/Source/C/GenFv/GenFvInternalLib.c > index d650a527a5..9c518b3609 100644 > --- a/BaseTools/Source/C/GenFv/GenFvInternalLib.c > +++ b/BaseTools/Source/C/GenFv/GenFvInternalLib.c > @@ -5,6 +5,7 @@ Copyright (c) 2004 - 2018, Intel Corporation. All rights > reserved.<BR> > Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> > Portions Copyright (c) 2016 HP Development Company, L.P.<BR> > Portions Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All > rights reserved.<BR> > +Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All > rights reserved.<BR> > SPDX-License-Identifier: BSD-2-Clause-Patent > > **/ > @@ -57,6 +58,7 @@ SPDX-License-Identifier: BSD-2-Clause-Patent > > BOOLEAN mArm = FALSE; > BOOLEAN mRiscV = FALSE; > +BOOLEAN mLoongArch = FALSE; > STATIC UINT32 MaxFfsAlignment = 0; > BOOLEAN VtfFileFlag = FALSE; > > @@ -2416,6 +2418,102 @@ Returns: > return EFI_SUCCESS; > } > > +EFI_STATUS > +UpdateLoongArchResetVectorIfNeeded ( > + IN MEMORY_FILE *FvImage, > + IN FV_INFO *FvInfo > + ) > +/*++ > + > +Routine Description: > + This parses the FV looking for SEC and patches that address into the > + beginning of the FV header. > + > + For LoongArch ISA, the reset vector is at 0x1c000000. > + > + We relocate it to SecCoreEntry and copy the ResetVector code to the > + beginning of the FV. > + > +Arguments: > + FvImage Memory file for the FV memory image > + FvInfo Information read from INF file. > + > +Returns: > + > + EFI_SUCCESS Function Completed successfully. > + EFI_ABORTED Error encountered. > + EFI_INVALID_PARAMETER A required parameter was NULL. > + EFI_NOT_FOUND PEI Core file not found. > + > +--*/ > +{ > + EFI_STATUS Status; > + EFI_FILE_SECTION_POINTER SecPe32; > + BOOLEAN UpdateVectorSec = FALSE; > + UINT16 MachineType = 0; > + EFI_PHYSICAL_ADDRESS SecCoreEntryAddress = 0; > + > + // > + // Verify input parameters > + // > + if (FvImage == NULL || FvInfo == NULL) { > + return EFI_INVALID_PARAMETER; > + } > + > + // > + // Locate an SEC Core instance and if found extract the machine type and > entry point address > + // > + Status = FindCorePeSection(FvImage->FileImage, FvInfo->Size, > EFI_FV_FILETYPE_SECURITY_CORE, &SecPe32); > + if (!EFI_ERROR(Status)) { > + > + Status = GetCoreMachineType(SecPe32, &MachineType); > + if (EFI_ERROR(Status)) { > + Error(NULL, 0, 3000, "Invalid", "Could not get the PE32 machine type for > SEC Core."); > + return EFI_ABORTED; > + } > + > + Status = GetCoreEntryPointAddress(FvImage->FileImage, FvInfo, > SecPe32, &SecCoreEntryAddress); > + if (EFI_ERROR(Status)) { > + Error(NULL, 0, 3000, "Invalid", "Could not get the PE32 entry point > address for SEC Core."); > + return EFI_ABORTED; > + } > + > + UpdateVectorSec = TRUE; > + } > + > + if (!UpdateVectorSec) > + return EFI_SUCCESS; > + > + if (MachineType == EFI_IMAGE_MACHINE_LOONGARCH64) { > + UINT32 ResetVector[3]; > + UINT32 InstrStack; > + > + memset(ResetVector, 0, sizeof (ResetVector)); > + > + /* if we found an SEC core entry point then generate a branch instruction > */ > + if (UpdateVectorSec) { > + VerboseMsg("UpdateLoongArchResetVectorIfNeeded updating > LOONGARCH64 SEC vector"); > + > + InstrStack = (SecCoreEntryAddress >> 12) & 0xfffff; > + ResetVector[0] = 0x14000001 | (InstrStack << 5); /* lu12i.w ra si20 */ > + > + InstrStack = (SecCoreEntryAddress & 0x0fff); > + ResetVector[1] = 0x03800021 | (InstrStack << 10); /* ori ra, ra, ui12 */ > + ResetVector[2] = 0x4c000021; /* jirl ra, ra, 0 */ > + } > + > + // > + // Copy to the beginning of the FV > + // > + memcpy(FvImage->FileImage, ResetVector, sizeof (ResetVector)); > + } else { > + Error(NULL, 0, 3000, "Invalid", "Unknown machine type"); > + return EFI_ABORTED; > + } > + > + return EFI_SUCCESS; > +} > + > EFI_STATUS > GetPe32Info ( > IN UINT8 *Pe32, > @@ -2509,7 +2607,7 @@ Returns: > // > if ((*MachineType != EFI_IMAGE_MACHINE_IA32) && (*MachineType != > EFI_IMAGE_MACHINE_X64) && (*MachineType != > EFI_IMAGE_MACHINE_EBC) && > (*MachineType != EFI_IMAGE_MACHINE_ARMT) && (*MachineType != > EFI_IMAGE_MACHINE_AARCH64) && > - (*MachineType != EFI_IMAGE_MACHINE_RISCV64)) { > + (*MachineType != EFI_IMAGE_MACHINE_RISCV64) && > (*MachineType != EFI_IMAGE_MACHINE_LOONGARCH64)) { > Error (NULL, 0, 3000, "Invalid", "Unrecognized machine type in the PE32 > file."); > return EFI_UNSUPPORTED; > } > @@ -2953,7 +3051,7 @@ Returns: > goto Finish; > } > > - if (!mArm && !mRiscV) { > + if (!mArm && !mRiscV && !mLoongArch) { > // > // Update reset vector (SALE_ENTRY for IPF) > // Now for IA32 and IA64 platform, the fv which has bsf file must have the > @@ -3004,6 +3102,19 @@ Returns: > FvHeader->Checksum = CalculateChecksum16 ((UINT16 *) FvHeader, > FvHeader->HeaderLength / sizeof (UINT16)); > } > > + if (mLoongArch) { > + Status = UpdateLoongArchResetVectorIfNeeded (&FvImageMemoryFile, > &mFvDataInfo); > + if (EFI_ERROR (Status)) { > + Error (NULL, 0, 3000, "Invalid", "Could not update the reset vector."); > + goto Finish; > + } > + // > + // Update Checksum for FvHeader > + // > + FvHeader->Checksum = 0; > + FvHeader->Checksum = CalculateChecksum16 ((UINT16 *) FvHeader, > FvHeader->HeaderLength / sizeof (UINT16)); > + } > + > // > // Update FV Alignment attribute to the largest alignment of all the FFS files > in the FV > // > @@ -3450,6 +3561,11 @@ Returns: > VerboseMsg("Located ARM/AArch64 SEC/PEI core in child FV"); > mArm = TRUE; > } > + // machine type is LOONGARCH64, set a flag so LOONGARCH64 reset > vector procesing occurs > + if ((MachineType == EFI_IMAGE_MACHINE_LOONGARCH64)) { > + VerboseMsg("Located LOONGARCH64 SEC core in child FV"); > + mLoongArch = TRUE; > + } > } > > // > @@ -3608,6 +3724,10 @@ Returns: > mRiscV = TRUE; > } > > + if ( (ImageContext.Machine == EFI_IMAGE_MACHINE_LOONGARCH64) ) { > + mLoongArch = TRUE; > + } > + > // > // Keep Image Context for PE image in FV > // > @@ -3885,6 +4005,10 @@ Returns: > mArm = TRUE; > } > > + if ( (ImageContext.Machine == EFI_IMAGE_MACHINE_LOONGARCH64) ) { > + mLoongArch = TRUE; > + } > + > // > // Keep Image Context for TE image in FV > // > diff --git a/BaseTools/Source/C/GenFw/Elf64Convert.c > b/BaseTools/Source/C/GenFw/Elf64Convert.c > index 0bb3ead228..b66aadfd6c 100644 > --- a/BaseTools/Source/C/GenFw/Elf64Convert.c > +++ b/BaseTools/Source/C/GenFw/Elf64Convert.c > @@ -4,6 +4,7 @@ Elf64 convert solution > Copyright (c) 2010 - 2021, Intel Corporation. All rights reserved.<BR> > Portions copyright (c) 2013-2014, ARM Ltd. All rights reserved.<BR> > Portions Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All > rights reserved.<BR> > +Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All > rights reserved.<BR> > > SPDX-License-Identifier: BSD-2-Clause-Patent > > @@ -163,7 +164,7 @@ InitializeElf64 ( > 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))) { > + if (!((mEhdr->e_machine == EM_X86_64) || (mEhdr->e_machine == > EM_AARCH64) || (mEhdr->e_machine == EM_RISCV64) || (mEhdr- > >e_machine == EM_LOONGARCH64))) { > Warning (NULL, 0, 3000, "Unsupported", "ELF e_machine is not Elf64 > machine."); > } > if (mEhdr->e_version != EV_CURRENT) { > @@ -730,6 +731,7 @@ ScanSections64 ( > case EM_X86_64: > case EM_AARCH64: > case EM_RISCV64: > + case EM_LOONGARCH64: > mCoffOffset += sizeof (EFI_IMAGE_NT_HEADERS64); > break; > default: > @@ -943,6 +945,10 @@ ScanSections64 ( > NtHdr->Pe32Plus.FileHeader.Machine = EFI_IMAGE_MACHINE_RISCV64; > NtHdr->Pe32Plus.OptionalHeader.Magic = > EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC; > break; > + case EM_LOONGARCH64: > + NtHdr->Pe32Plus.FileHeader.Machine = > EFI_IMAGE_MACHINE_LOONGARCH64; > + NtHdr->Pe32Plus.OptionalHeader.Magic = > EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC; > + break; > > default: > VerboseMsg ("%s unknown e_machine type. Assume X64", > (UINTN)mEhdr->e_machine); > @@ -1149,10 +1155,10 @@ WriteSections64 ( > } > > // > - // Skip error on EM_RISCV64 becasue no symble name is built > - // from RISC-V toolchain. > + // Skip error on EM_RISCV64 and EM_LOONGARCH64 becasue no > symble name is built > + // from RISC-V and LoongArch toolchain. > // > - if (mEhdr->e_machine != EM_RISCV64) { > + if ((mEhdr->e_machine != EM_RISCV64) && (mEhdr->e_machine != > EM_LOONGARCH64)) { > 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.", > @@ -1417,6 +1423,74 @@ WriteSections64 ( > // Write section for RISC-V 64 architecture. > // > WriteSectionRiscV64 (Rel, Targ, SymShdr, Sym); > + } else if (mEhdr->e_machine == EM_LOONGARCH64) { > + switch (ELF_R_TYPE(Rel->r_info)) { > + > + 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: > + // > + // These types are not used or do not need to fix the offsets. > + // > + break; > + default: > + Error (NULL, 0, 3000, "Invalid", "WriteSections64(): %s unsupported > ELF EM_LOONGARCH64 relocation 0x%x.", mInImageName, (unsigned) > ELF64_R_TYPE(Rel->r_info)); > + } > } else { > Error (NULL, 0, 3000, "Invalid", "Not a supported machine type"); > } > @@ -1647,6 +1721,77 @@ WriteRelocations64 ( > 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_LOONGARCH64) { > + 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: > + // > + // 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_LOONGARCH64 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); > } > diff --git a/BaseTools/Source/C/GenFw/elf_common.h > b/BaseTools/Source/C/GenFw/elf_common.h > index b67f59e7a0..34c8748f39 100644 > --- a/BaseTools/Source/C/GenFw/elf_common.h > +++ b/BaseTools/Source/C/GenFw/elf_common.h > @@ -4,6 +4,7 @@ Ported ELF include files from FreeBSD > Copyright (c) 2009 - 2010, Apple Inc. All rights reserved.<BR> > Portions Copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> > Portion Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All > rights reserved.<BR> > +Portions Copyright (c) 2022, Loongson Technology Corporation Limited. All > rights reserved.<BR> > SPDX-License-Identifier: BSD-2-Clause-Patent > > > @@ -181,6 +182,7 @@ typedef struct { > #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_LOONGARCH64 258 /* LoongArch 64-bit Architecture */ Do you have 32-bit LOONGARCH that also requires a value in spec? Abner Chao: I fact we only applied one value in Binutils that 258. I have been modified this on our internal repo. Next version, I will have it sync ed to our internal repo content, it should be: #define EM_LOONGARCH 258 /* LoongArch Architecture */ > > /* Non-standard or deprecated. */ > #define EM_486 6 /* Intel i486. */ > @@ -1042,4 +1044,60 @@ typedef struct { > #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 > #endif /* !_SYS_ELF_COMMON_H_ */ > diff --git a/BaseTools/Source/C/Include/IndustryStandard/PeImage.h > b/BaseTools/Source/C/Include/IndustryStandard/PeImage.h > index f17b8ee19b..80961e5576 100644 > --- a/BaseTools/Source/C/Include/IndustryStandard/PeImage.h > +++ b/BaseTools/Source/C/Include/IndustryStandard/PeImage.h > @@ -7,6 +7,7 @@ > Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR> > Portions copyright (c) 2011 - 2013, ARM Ltd. All rights reserved.<BR> > Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights > reserved.<BR> > + Copyright (c) 2022, Loongson Technology Corporation Limited. All rights > reserved.<BR> > > SPDX-License-Identifier: BSD-2-Clause-Patent > > @@ -36,23 +37,25 @@ > // > // PE32+ Machine type for EFI images > // > -#define IMAGE_FILE_MACHINE_I386 0x014c > -#define IMAGE_FILE_MACHINE_EBC 0x0EBC > -#define IMAGE_FILE_MACHINE_X64 0x8664 > -#define IMAGE_FILE_MACHINE_ARM 0x01c0 // Thumb only > -#define IMAGE_FILE_MACHINE_ARMT 0x01c2 // 32bit Mixed ARM and > Thumb/Thumb 2 Little Endian > -#define IMAGE_FILE_MACHINE_ARM64 0xAA64 // 64bit ARM > Architecture, Little Endian > -#define IMAGE_FILE_MACHINE_RISCV64 0x5064 // 64bit RISC-V ISA > +#define IMAGE_FILE_MACHINE_I386 0x014c > +#define IMAGE_FILE_MACHINE_EBC 0x0EBC > +#define IMAGE_FILE_MACHINE_X64 0x8664 > +#define IMAGE_FILE_MACHINE_ARM 0x01c0 // Thumb only > +#define IMAGE_FILE_MACHINE_ARMT 0x01c2 // 32bit Mixed ARM and > Thumb/Thumb 2 Little Endian > +#define IMAGE_FILE_MACHINE_ARM64 0xAA64 // 64bit ARM > Architecture, Little Endian > +#define IMAGE_FILE_MACHINE_RISCV64 0x5064 // 64bit RISC-V ISA > +#define IMAGE_FILE_MACHINE_LOONGARCH64 0x6264 // 64bit LoongArch > Architecture > > // > // Support old names for backward compatible > // > -#define EFI_IMAGE_MACHINE_IA32 IMAGE_FILE_MACHINE_I386 > -#define EFI_IMAGE_MACHINE_EBC IMAGE_FILE_MACHINE_EBC > -#define EFI_IMAGE_MACHINE_X64 IMAGE_FILE_MACHINE_X64 > -#define EFI_IMAGE_MACHINE_ARMT IMAGE_FILE_MACHINE_ARMT > -#define EFI_IMAGE_MACHINE_AARCH64 IMAGE_FILE_MACHINE_ARM64 > -#define EFI_IMAGE_MACHINE_RISCV64 IMAGE_FILE_MACHINE_RISCV64 > +#define EFI_IMAGE_MACHINE_IA32 IMAGE_FILE_MACHINE_I386 > +#define EFI_IMAGE_MACHINE_EBC IMAGE_FILE_MACHINE_EBC > +#define EFI_IMAGE_MACHINE_X64 IMAGE_FILE_MACHINE_X64 > +#define EFI_IMAGE_MACHINE_ARMT IMAGE_FILE_MACHINE_ARMT > +#define EFI_IMAGE_MACHINE_AARCH64 > IMAGE_FILE_MACHINE_ARM64 > +#define EFI_IMAGE_MACHINE_RISCV64 IMAGE_FILE_MACHINE_RISCV64 > +#define EFI_IMAGE_MACHINE_LOONGARCH64 > IMAGE_FILE_MACHINE_LOONGARCH64 > > #define EFI_IMAGE_DOS_SIGNATURE 0x5A4D // MZ > #define EFI_IMAGE_OS2_SIGNATURE 0x454E // NE > @@ -500,19 +503,21 @@ typedef struct { > // > // Based relocation types. > // > -#define EFI_IMAGE_REL_BASED_ABSOLUTE 0 > -#define EFI_IMAGE_REL_BASED_HIGH 1 > -#define EFI_IMAGE_REL_BASED_LOW 2 > -#define EFI_IMAGE_REL_BASED_HIGHLOW 3 > -#define EFI_IMAGE_REL_BASED_HIGHADJ 4 > -#define EFI_IMAGE_REL_BASED_MIPS_JMPADDR 5 > -#define EFI_IMAGE_REL_BASED_ARM_MOV32A 5 > -#define EFI_IMAGE_REL_BASED_RISCV_HI20 5 > -#define EFI_IMAGE_REL_BASED_ARM_MOV32T 7 > -#define EFI_IMAGE_REL_BASED_RISCV_LOW12I 7 > -#define EFI_IMAGE_REL_BASED_RISCV_LOW12S 8 > -#define EFI_IMAGE_REL_BASED_IA64_IMM64 9 > -#define EFI_IMAGE_REL_BASED_DIR64 10 > +#define EFI_IMAGE_REL_BASED_ABSOLUTE 0 > +#define EFI_IMAGE_REL_BASED_HIGH 1 > +#define EFI_IMAGE_REL_BASED_LOW 2 > +#define EFI_IMAGE_REL_BASED_HIGHLOW 3 > +#define EFI_IMAGE_REL_BASED_HIGHADJ 4 > +#define EFI_IMAGE_REL_BASED_MIPS_JMPADDR 5 > +#define EFI_IMAGE_REL_BASED_ARM_MOV32A 5 > +#define EFI_IMAGE_REL_BASED_RISCV_HI20 5 > +#define EFI_IMAGE_REL_BASED_ARM_MOV32T 7 > +#define EFI_IMAGE_REL_BASED_RISCV_LOW12I 7 > +#define EFI_IMAGE_REL_BASED_RISCV_LOW12S 8 > +#define EFI_IMAGE_REL_BASED_LOONGARCH32_MARK_LA 8 > +#define EFI_IMAGE_REL_BASED_LOONGARCH64_MARK_LA 8 > +#define EFI_IMAGE_REL_BASED_IA64_IMM64 9 > +#define EFI_IMAGE_REL_BASED_DIR64 10 > > > /// > -- > 2.27.0 > > > > > [-- Attachment #2: Type: text/html, Size: 39885 bytes --] ^ permalink raw reply [flat|nested] 3+ messages in thread
end of thread, other threads:[~2022-04-12 9:36 UTC | newest] Thread overview: 3+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2022-02-09 6:54 [staging/LoongArch RESEND PATCH v1 13/33] BaseTools: BaseTools changes for LoongArch platform Chao Li 2022-04-08 6:25 ` [edk2-devel] " Abner Chang 2022-04-12 9:36 ` Chao Li
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox