Index: llvm/docs/AMDGPUUsage.rst =================================================================== --- llvm/docs/AMDGPUUsage.rst +++ llvm/docs/AMDGPUUsage.rst @@ -637,7 +637,8 @@ - ``ET_DYN`` ``e_machine`` ``EM_AMDGPU`` ``e_entry`` 0 - ``e_flags`` See :ref:`amdgpu-elf-header-e_flags-table` + ``e_flags`` See :ref:`amdgpu-elf-header-e_flags-table-01` + and :ref:`amdgpu-elf-header-e_flags-table-2` ========================== =============================== .. @@ -645,18 +646,18 @@ .. table:: AMDGPU ELF Header Enumeration Values :name: amdgpu-elf-header-enumeration-values-table - =============================== ===== + =============================== ====== Name Value - =============================== ===== + =============================== ====== ``EM_AMDGPU`` 224 ``ELFOSABI_NONE`` 0 ``ELFOSABI_AMDGPU_HSA`` 64 ``ELFOSABI_AMDGPU_PAL`` 65 ``ELFOSABI_AMDGPU_MESA3D`` 66 - ``ELFABIVERSION_AMDGPU_HSA`` 1 + ``ELFABIVERSION_AMDGPU_HSA`` 1 or 2 ``ELFABIVERSION_AMDGPU_PAL`` 0 ``ELFABIVERSION_AMDGPU_MESA3D`` 0 - =============================== ===== + =============================== ====== ``e_ident[EI_CLASS]`` The ELF class is: @@ -712,7 +713,8 @@ by the ``r600`` and ``amdgcn`` architectures (see :ref:`amdgpu-processor-table`). The specific processor is specified in the ``EF_AMDGPU_MACH`` bit field of the ``e_flags`` (see - :ref:`amdgpu-elf-header-e_flags-table`). + :ref:`amdgpu-elf-header-e_flags-table-01` and + :ref:`amdgpu-elf-header-e_flags-table-2`). ``e_entry`` The entry point is 0 as the entry points for individual kernels must be @@ -721,8 +723,8 @@ ``e_flags`` The AMDGPU backend uses the following ELF header flags: - .. table:: AMDGPU ELF Header ``e_flags`` - :name: amdgpu-elf-header-e_flags-table + .. table:: AMDGPU ELF Header ``e_flags`` (``EI_ABIVERSION=0`` and ``EI_ABIVERSION=1``) + :name: amdgpu-elf-header-e_flags-table-01 ================================= ========== ============================= Name Value Description @@ -758,6 +760,31 @@ :ref:`amdgpu-target-features`. ================================= ========== ============================= + .. table:: AMDGPU ELF Header ``e_flags`` (``EI_ABIVERSION=2``) + :name: amdgpu-elf-header-e_flags-table-2 + + ================================= ========== ========================================== + Name Value Description + ================================= ========== ========================================== + **AMDGPU Processor Flag** See :ref:`amdgpu-processor-table`. + -------------------------------------------- ------------------------------------------ + ``EF_AMDGPU_MACH`` 0x000000ff AMDGPU processor selection + mask for + ``EF_AMDGPU_MACH_xxx`` values + defined in + :ref:`amdgpu-ef-amdgpu-mach-table`. + ``EF_AMDGPU_FEATURE_XNACK`` 0x00000300 XNACK selection mask for + representing 3 values: + ``EF_AMDGPU_FEATURE_XNACK_DEFAULT`` (1), + ``EF_AMDGPU_FEATURE_XNACK_OFF`` (2), + ``EF_AMDGPU_FEATURE_XNACK_ON`` (3). + ``EF_AMDGPU_FEATURE_SRAMECC`` 0x00000c00 SRAMECC selection mask for + representing 3 values: + ``EF_AMDGPU_FEATURE_SRAMECC_DEFAULT`` (1), + ``EF_AMDGPU_FEATURE_SRAMECC_OFF`` (2), + ``EF_AMDGPU_FEATURE_SRAMECC_ON`` (3). + ================================= ========== ========================================== + .. table:: AMDGPU ``EF_AMDGPU_MACH`` Values :name: amdgpu-ef-amdgpu-mach-table Index: llvm/include/llvm/BinaryFormat/ELF.h =================================================================== --- llvm/include/llvm/BinaryFormat/ELF.h +++ llvm/include/llvm/BinaryFormat/ELF.h @@ -721,6 +721,26 @@ // Indicates if the "sram-ecc" target feature is enabled for all code // contained in the object. EF_AMDGPU_SRAM_ECC = 0x200, + + // XNACK selection mask for EF_AMDGPU_FEATURE_XNACK_* values. Applicable + // to EI_OSABI=ELFOSABI_AMDGPU_HSA and EI_ABIVERSION=2. + EF_AMDGPU_FEATURE_XNACK = 0x300, + // XNACK is any/default. + EF_AMDGPU_FEATURE_XNACK_DEFAULT=0x100, + // XNACK is off. + EF_AMDGPU_FEATURE_XNACK_OFF=0x200, + // XNACK is on. + EF_AMDGPU_FEATURE_XNACK_ON=0x300, + + // SRAMECC selection mask for EF_AMDGPU_FEATURE_SRAMECC_* values. Applicable + // to EI_OSABI=ELFOSABI_AMDGPU_HSA and EI_ABIVERSION=2. + EF_AMDGPU_FEATURE_SRAMECC = 0xc00, + // SRAMECC is any/default. + EF_AMDGPU_FEATURE_SRAMECC_DEFAULT = 0x400, + // SRAMECC is off. + EF_AMDGPU_FEATURE_SRAMECC_OFF = 0x800, + // SRAMECC is on. + EF_AMDGPU_FEATURE_SRAMECC_ON = 0xc00, }; // ELF Relocation types for AMDGPU Index: llvm/lib/ObjectYAML/ELFYAML.cpp =================================================================== --- llvm/lib/ObjectYAML/ELFYAML.cpp +++ llvm/lib/ObjectYAML/ELFYAML.cpp @@ -429,8 +429,23 @@ BCaseMask(EF_AMDGPU_MACH_AMDGCN_GFX1010, EF_AMDGPU_MACH); BCaseMask(EF_AMDGPU_MACH_AMDGCN_GFX1011, EF_AMDGPU_MACH); BCaseMask(EF_AMDGPU_MACH_AMDGCN_GFX1012, EF_AMDGPU_MACH); - BCase(EF_AMDGPU_XNACK); - BCase(EF_AMDGPU_SRAM_ECC); + switch (Object->Header.ABIVersion) { + case 0: + case 1: + BCase(EF_AMDGPU_XNACK); + BCase(EF_AMDGPU_SRAM_ECC); + break; + case 2: + BCaseMask(EF_AMDGPU_FEATURE_XNACK_DEFAULT, EF_AMDGPU_FEATURE_XNACK); + BCaseMask(EF_AMDGPU_FEATURE_XNACK_OFF, EF_AMDGPU_FEATURE_XNACK); + BCaseMask(EF_AMDGPU_FEATURE_XNACK_ON, EF_AMDGPU_FEATURE_XNACK); + BCaseMask(EF_AMDGPU_FEATURE_SRAMECC_DEFAULT, EF_AMDGPU_FEATURE_SRAMECC); + BCaseMask(EF_AMDGPU_FEATURE_SRAMECC_OFF, EF_AMDGPU_FEATURE_SRAMECC); + BCaseMask(EF_AMDGPU_FEATURE_SRAMECC_ON, EF_AMDGPU_FEATURE_SRAMECC); + break; + default: + llvm_unreachable("Unsupported ABI Version"); + } break; case ELF::EM_X86_64: break; Index: llvm/lib/Target/AMDGPU/AMDGPUAsmPrinter.cpp =================================================================== --- llvm/lib/Target/AMDGPU/AMDGPUAsmPrinter.cpp +++ llvm/lib/Target/AMDGPU/AMDGPUAsmPrinter.cpp @@ -17,6 +17,7 @@ #include "AMDGPUAsmPrinter.h" #include "AMDGPU.h" +#include "AMDGPUMachineModuleInfo.h" #include "AMDGPUSubtarget.h" #include "AMDGPUTargetMachine.h" #include "MCTargetDesc/AMDGPUInstPrinter.h" @@ -129,20 +130,21 @@ } void AMDGPUAsmPrinter::emitStartOfAsmFile(Module &M) { - if (IsaInfo::hasCodeObjectV3(getGlobalSTI())) { - std::string ExpectedTarget; - raw_string_ostream ExpectedTargetOS(ExpectedTarget); - IsaInfo::streamIsaVersion(getGlobalSTI(), ExpectedTargetOS); - - getTargetStreamer()->EmitDirectiveAMDGCNTarget(ExpectedTarget); + StringRef TargetID = + MMI->getObjFileInfo().getTargetID(); + if (enableNewTargetID()) { + if (!isSubtargetInfoEquivalentToTargetID(getGlobalSTI(), TargetID)) { + report_fatal_error("Subtarget info does not match TargetID"); + } } + getTargetStreamer()->EmitDirectiveAMDGCNTarget(*getGlobalSTI(), TargetID); if (TM.getTargetTriple().getOS() != Triple::AMDHSA && TM.getTargetTriple().getOS() != Triple::AMDPAL) return; if (TM.getTargetTriple().getOS() == Triple::AMDHSA) - HSAMetadataStream->begin(M); + HSAMetadataStream->begin(M, TargetID); if (TM.getTargetTriple().getOS() == Triple::AMDPAL) getTargetStreamer()->getPALMetadata()->readFromIR(M); Index: llvm/lib/Target/AMDGPU/AMDGPUHSAMetadataStreamer.h =================================================================== --- llvm/lib/Target/AMDGPU/AMDGPUHSAMetadataStreamer.h +++ llvm/lib/Target/AMDGPU/AMDGPUHSAMetadataStreamer.h @@ -42,7 +42,7 @@ virtual bool emitTo(AMDGPUTargetStreamer &TargetStreamer) = 0; - virtual void begin(const Module &Mod) = 0; + virtual void begin(const Module &Mod, StringRef TargetID) = 0; virtual void end() = 0; @@ -77,6 +77,8 @@ void emitVersion(); + void emitTargetID(StringRef TargetID); + void emitPrintf(const Module &Mod); void emitKernelLanguage(const Function &Func, msgpack::MapDocNode Kern); @@ -111,7 +113,7 @@ bool emitTo(AMDGPUTargetStreamer &TargetStreamer) override; - void begin(const Module &Mod) override; + void begin(const Module &Mod, StringRef TargetID) override; void end() override; @@ -177,7 +179,7 @@ bool emitTo(AMDGPUTargetStreamer &TargetStreamer) override; - void begin(const Module &Mod) override; + void begin(const Module &Mod, StringRef TargetID) override; void end() override; Index: llvm/lib/Target/AMDGPU/AMDGPUHSAMetadataStreamer.cpp =================================================================== --- llvm/lib/Target/AMDGPU/AMDGPUHSAMetadataStreamer.cpp +++ llvm/lib/Target/AMDGPU/AMDGPUHSAMetadataStreamer.cpp @@ -452,7 +452,7 @@ return TargetStreamer.EmitHSAMetadata(getHSAMetadata()); } -void MetadataStreamerV2::begin(const Module &Mod) { +void MetadataStreamerV2::begin(const Module &Mod, StringRef TargetID) { emitVersion(); emitPrintf(Mod); } @@ -662,6 +662,11 @@ getRootMetadata("amdhsa.version") = Version; } +void MetadataStreamerV3::emitTargetID(StringRef TargetID) { + getRootMetadata("amdhsa.target") = + HSAMetadataDoc->getNode(TargetID, /*Copy=*/true); +} + void MetadataStreamerV3::emitPrintf(const Module &Mod) { auto Node = Mod.getNamedMetadata("llvm.printf.fmts"); if (!Node) @@ -922,8 +927,10 @@ return TargetStreamer.EmitHSAMetadata(*HSAMetadataDoc, true); } -void MetadataStreamerV3::begin(const Module &Mod) { +void MetadataStreamerV3::begin(const Module &Mod, StringRef TargetID) { emitVersion(); + if (enableNewTargetID()) + emitTargetID(TargetID); emitPrintf(Mod); getRootMetadata("amdhsa.kernels") = HSAMetadataDoc->getArrayNode(); } Index: llvm/lib/Target/AMDGPU/AMDGPUMachineModuleInfo.h =================================================================== --- llvm/lib/Target/AMDGPU/AMDGPUMachineModuleInfo.h +++ llvm/lib/Target/AMDGPU/AMDGPUMachineModuleInfo.h @@ -46,6 +46,12 @@ /// Single thread synchronization scope ID (single address space). SyncScope::ID SingleThreadOneAddressSpaceSSID; + // Target identification string syntax can be found here: + // https://llvm.org/docs/AMDGPUUsage.html#code-object-target-identification + + /// Target identification string. + std::string TargetID; + /// In AMDGPU target synchronization scopes are inclusive, meaning a /// larger synchronization scope is inclusive of a smaller synchronization /// scope. @@ -138,6 +144,11 @@ return AIO.getValue() >= BIO.getValue() && (IsAOneAddressSpace == IsBOneAddressSpace || !IsAOneAddressSpace); } + + /// \returns Target identification string. + StringRef getTargetID() const { + return TargetID; + } }; } // end namespace llvm Index: llvm/lib/Target/AMDGPU/AMDGPUMachineModuleInfo.cpp =================================================================== --- llvm/lib/Target/AMDGPU/AMDGPUMachineModuleInfo.cpp +++ llvm/lib/Target/AMDGPU/AMDGPUMachineModuleInfo.cpp @@ -14,6 +14,8 @@ #include "AMDGPUMachineModuleInfo.h" #include "llvm/IR/Module.h" +#include "llvm/Target/TargetMachine.h" +#include "llvm/Support/TargetParser.h" namespace llvm { @@ -33,6 +35,39 @@ CTX.getOrInsertSyncScopeID("wavefront-one-as"); SingleThreadOneAddressSpaceSSID = CTX.getOrInsertSyncScopeID("singlethread-one-as"); + + if (MMI.getTarget().getTargetTriple().getArch() != Triple::amdgcn) { + return; + } + + SmallVector ModuleFlags; + MMI.getModule()->getModuleFlagsMetadata(ModuleFlags); + for (const auto &MFE : ModuleFlags) { + if (MFE.Behavior != Module::MergeTargetId) { + continue; + } + + assert(MFE.Key->getString().equals("target-id")); + TargetID = cast(MFE.Val)->getString().str(); + } + if (TargetID.empty()) { + auto TargetTriple = MMI.getTarget().getTargetTriple(); + auto CPU = MMI.getTarget().getTargetCPU(); + auto Version = AMDGPU::getIsaVersion(CPU); + + raw_string_ostream ConstructedTargetIDOStr(TargetID); + ConstructedTargetIDOStr << TargetTriple.getArchName() << '-' + << TargetTriple.getVendorName() << '-' + << TargetTriple.getOSName() << '-' + << TargetTriple.getEnvironmentName() << '-'; + if (Version.Major >= 9) { + ConstructedTargetIDOStr << CPU; + } else { + ConstructedTargetIDOStr << "gfx" << Version.Major << Version.Minor + << Version.Stepping; + } + ConstructedTargetIDOStr.flush(); + } } } // end namespace llvm Index: llvm/lib/Target/AMDGPU/AsmParser/AMDGPUAsmParser.cpp =================================================================== --- llvm/lib/Target/AMDGPU/AsmParser/AMDGPUAsmParser.cpp +++ llvm/lib/Target/AMDGPU/AsmParser/AMDGPUAsmParser.cpp @@ -3754,22 +3754,28 @@ if (getSTI().getTargetTriple().getArch() != Triple::amdgcn) return TokError("directive only supported for amdgcn architecture"); - std::string Target; + std::string TargetID; SMLoc TargetStart = getTok().getLoc(); - if (getParser().parseEscapedString(Target)) + if (getParser().parseEscapedString(TargetID)) return true; SMRange TargetRange = SMRange(TargetStart, getTok().getLoc()); - std::string ExpectedTarget; - raw_string_ostream ExpectedTargetOS(ExpectedTarget); - IsaInfo::streamIsaVersion(&getSTI(), ExpectedTargetOS); + if (!enableNewTargetID()) { + std::string ExpectedTargetIDStr; + raw_string_ostream ExpectedTargetIDOStr(ExpectedTargetIDStr); + IsaInfo::streamIsaVersion(&getSTI(), ExpectedTargetIDOStr); - if (Target != ExpectedTargetOS.str()) - return getParser().Error(TargetRange.Start, "target must match options", - TargetRange); + if (TargetID != ExpectedTargetIDOStr.str()) + return getParser().Error(TargetRange.Start, "target must match options", + TargetRange); + } else { + if (!isSubtargetInfoEquivalentToTargetID(&getSTI(), TargetID)) + return getParser().Error(TargetRange.Start, "target must match options", + TargetRange); + } - getTargetStreamer().EmitDirectiveAMDGCNTarget(Target); + getTargetStreamer().EmitDirectiveAMDGCNTarget(getSTI(), TargetID); return false; } Index: llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUAsmBackend.cpp =================================================================== --- llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUAsmBackend.cpp +++ llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUAsmBackend.cpp @@ -237,7 +237,11 @@ const MCSubtargetInfo &STI, const MCRegisterInfo &MRI, const MCTargetOptions &Options) { + uint8_t ABIVersion = 0; + if (IsaInfo::hasCodeObjectV3(&STI)) { + ABIVersion = enableNewTargetID() ? 2 : 1; + } + // Use 64-bit ELF for amdgcn - return new ELFAMDGPUAsmBackend(T, STI.getTargetTriple(), - IsaInfo::hasCodeObjectV3(&STI) ? 1 : 0); + return new ELFAMDGPUAsmBackend(T, STI.getTargetTriple(), ABIVersion); } Index: llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUTargetStreamer.h =================================================================== --- llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUTargetStreamer.h +++ llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUTargetStreamer.h @@ -39,7 +39,8 @@ AMDGPUPALMetadata *getPALMetadata() { return &PALMetadata; } - virtual void EmitDirectiveAMDGCNTarget(StringRef Target) = 0; + virtual void EmitDirectiveAMDGCNTarget(const MCSubtargetInfo &STI, + StringRef TargetID = "") = 0; virtual void EmitDirectiveHSACodeObjectVersion(uint32_t Major, uint32_t Minor) = 0; @@ -97,7 +98,8 @@ void finish() override; - void EmitDirectiveAMDGCNTarget(StringRef Target) override; + void EmitDirectiveAMDGCNTarget(const MCSubtargetInfo &STI, + StringRef TargetID = "") override; void EmitDirectiveHSACodeObjectVersion(uint32_t Major, uint32_t Minor) override; @@ -133,7 +135,7 @@ class AMDGPUTargetELFStreamer final : public AMDGPUTargetStreamer { MCStreamer &Streamer; - Triple::OSType Os; + const MCSubtargetInfo &STI; void EmitNote(StringRef Name, const MCExpr *DescSize, unsigned NoteType, function_ref EmitDesc); @@ -145,7 +147,8 @@ void finish() override; - void EmitDirectiveAMDGCNTarget(StringRef Target) override; + void EmitDirectiveAMDGCNTarget(const MCSubtargetInfo &STI, + StringRef TargetID = "") override; void EmitDirectiveHSACodeObjectVersion(uint32_t Major, uint32_t Minor) override; Index: llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUTargetStreamer.cpp =================================================================== --- llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUTargetStreamer.cpp +++ llvm/lib/Target/AMDGPU/MCTargetDesc/AMDGPUTargetStreamer.cpp @@ -170,8 +170,23 @@ OS << S; } -void AMDGPUTargetAsmStreamer::EmitDirectiveAMDGCNTarget(StringRef Target) { - OS << "\t.amdgcn_target \"" << Target << "\"\n"; +void AMDGPUTargetAsmStreamer::EmitDirectiveAMDGCNTarget( + const MCSubtargetInfo &STI, StringRef TargetID) { + if (!IsaInfo::hasCodeObjectV3(&STI)) { + // V2 does not have TargetID concept. + return; + } + if (!enableNewTargetID()) { + // V3 + Original TargetID. + std::string ConstructedTargetIDStr; + raw_string_ostream ConstructedTargetIDOStr(ConstructedTargetIDStr); + IsaInfo::streamIsaVersion(&STI, ConstructedTargetIDOStr); + OS << "\t.amdgcn_target \"" << ConstructedTargetIDStr << "\"\n"; + return; + } + + // V3 + New TargetID. + OS << "\t.amdgcn_target \"" << TargetID << "\"\n"; } void AMDGPUTargetAsmStreamer::EmitDirectiveHSACodeObjectVersion( @@ -395,20 +410,30 @@ AMDGPUTargetELFStreamer::AMDGPUTargetELFStreamer(MCStreamer &S, const MCSubtargetInfo &STI) - : AMDGPUTargetStreamer(S), Streamer(S), Os(STI.getTargetTriple().getOS()) { + : AMDGPUTargetStreamer(S), Streamer(S), STI(STI) { MCAssembler &MCA = getStreamer().getAssembler(); unsigned EFlags = MCA.getELFHeaderEFlags(); EFlags &= ~ELF::EF_AMDGPU_MACH; EFlags |= getElfMach(STI.getCPU()); - EFlags &= ~ELF::EF_AMDGPU_XNACK; - if (AMDGPU::hasXNACK(STI)) - EFlags |= ELF::EF_AMDGPU_XNACK; - - EFlags &= ~ELF::EF_AMDGPU_SRAM_ECC; - if (AMDGPU::hasSRAMECC(STI)) - EFlags |= ELF::EF_AMDGPU_SRAM_ECC; + if (!enableNewTargetID()) { + // V2, V3 + Original TargetID. + EFlags &= ~ELF::EF_AMDGPU_XNACK; + if (AMDGPU::hasXNACK(STI)) + EFlags |= ELF::EF_AMDGPU_XNACK; + + EFlags &= ~ELF::EF_AMDGPU_SRAM_ECC; + if (AMDGPU::hasSRAMECC(STI)) + EFlags |= ELF::EF_AMDGPU_SRAM_ECC; + } else { + // V3 + New TargetID. + EFlags &= ~ELF::EF_AMDGPU_FEATURE_XNACK; + EFlags |= ELF::EF_AMDGPU_FEATURE_XNACK_DEFAULT; + + EFlags &= ~ELF::EF_AMDGPU_FEATURE_SRAMECC; + EFlags |= ELF::EF_AMDGPU_FEATURE_SRAMECC_DEFAULT; + } MCA.setELFHeaderEFlags(EFlags); } @@ -441,7 +466,7 @@ unsigned NoteFlags = 0; // TODO Apparently, this is currently needed for OpenCL as mentioned in // https://reviews.llvm.org/D74995 - if (Os == Triple::AMDHSA) + if (STI.getTargetTriple().getOS() == Triple::AMDHSA) NoteFlags = ELF::SHF_ALLOC; S.PushSection(); @@ -457,7 +482,34 @@ S.PopSection(); } -void AMDGPUTargetELFStreamer::EmitDirectiveAMDGCNTarget(StringRef Target) {} +void AMDGPUTargetELFStreamer::EmitDirectiveAMDGCNTarget( + const MCSubtargetInfo &STI, StringRef TargetID) { + if (!IsaInfo::hasCodeObjectV3(&STI)) { + // V2 is setup in the constructor. + return; + } + if (!enableNewTargetID()) { + // V3 + Original TargetID is setup in the constructor. + return; + } + + MCAssembler &MCA = getStreamer().getAssembler(); + unsigned EFlags = MCA.getELFHeaderEFlags(); + + // V3 + New TargetID (default is already setup in the constructor). + if (auto XNACK = getXnackFromTargetID(TargetID)) { + EFlags &= ~ELF::EF_AMDGPU_FEATURE_XNACK; + EFlags |= XNACK.getValue() ? ELF::EF_AMDGPU_FEATURE_XNACK_ON + : ELF::EF_AMDGPU_FEATURE_XNACK_OFF; + } + if (auto SRAMECC = getSramEccFromTargetID(TargetID)) { + EFlags &= ~ELF::EF_AMDGPU_FEATURE_SRAMECC; + EFlags |= SRAMECC.getValue() ? ELF::EF_AMDGPU_FEATURE_SRAMECC_ON + : ELF::EF_AMDGPU_FEATURE_SRAMECC_OFF; + } + + MCA.setELFHeaderEFlags(EFlags); +} void AMDGPUTargetELFStreamer::EmitDirectiveHSACodeObjectVersion( uint32_t Major, uint32_t Minor) { Index: llvm/lib/Target/AMDGPU/Utils/AMDGPUBaseInfo.h =================================================================== --- llvm/lib/Target/AMDGPU/Utils/AMDGPUBaseInfo.h +++ llvm/lib/Target/AMDGPU/Utils/AMDGPUBaseInfo.h @@ -36,6 +36,23 @@ namespace AMDGPU { +/// \returns True if new target identification string is enabled, false +/// otherwise. +bool enableNewTargetID(); + +/// \returns None for "default", false for "off", true for "on". +Optional getFeatureFromTargetID(StringRef TargetID, StringRef Feature); + +/// \returns None for "default", false for "off", true for "on". +Optional getXnackFromTargetID(StringRef TargetID); + +/// \returns None for "default", false for "off", true for "on". +Optional getSramEccFromTargetID(StringRef TargetID); + +/// \returns True if \p STI is equivalent to \p TargetID, false otherwise. +bool isSubtargetInfoEquivalentToTargetID(const MCSubtargetInfo *STI, + StringRef TargetID); + struct GcnBufferFormatInfo { unsigned Format; unsigned BitsPerComp; Index: llvm/lib/Target/AMDGPU/Utils/AMDGPUBaseInfo.cpp =================================================================== --- llvm/lib/Target/AMDGPU/Utils/AMDGPUBaseInfo.cpp +++ llvm/lib/Target/AMDGPU/Utils/AMDGPUBaseInfo.cpp @@ -32,6 +32,7 @@ #include "llvm/MC/MCSubtargetInfo.h" #include "llvm/MC/SubtargetFeature.h" #include "llvm/Support/Casting.h" +#include "llvm/Support/CommandLine.h" #include "llvm/Support/ErrorHandling.h" #include "llvm/Support/MathExtras.h" #include @@ -48,6 +49,11 @@ #undef GET_INSTRMAP_INFO #undef GET_INSTRINFO_NAMED_OPS +static llvm::cl::opt EnableNewTargetID( + "amdgcn-new-target-id", + llvm::cl::desc("Use New Target ID"), + llvm::cl::init(false)); + namespace { /// \returns Bit mask for given bit \p Shift and bit \p Width. @@ -103,6 +109,73 @@ namespace AMDGPU { +bool enableNewTargetID() { + return EnableNewTargetID; +} + +Optional getFeatureFromTargetID(StringRef TargetID, StringRef Feature) { + SmallVector TargetIDSplit; + TargetID.split(TargetIDSplit, ':'); + + Optional FeatureStatus; + for (const auto &FeatureString : TargetIDSplit) { + if (FeatureString.startswith(Feature)) { + if (FeatureString.endswith("+")) { + FeatureStatus = true; + } else if (FeatureString.endswith("-")) { + FeatureStatus = false; + } else { + llvm_unreachable("Malformed feature string"); + } + } + } + return FeatureStatus; +} + +Optional getXnackFromTargetID(StringRef TargetID) { + return getFeatureFromTargetID(TargetID, "xnack"); +} + +Optional getSramEccFromTargetID(StringRef TargetID) { + return getFeatureFromTargetID(TargetID, "sramecc"); +} + +bool isSubtargetInfoEquivalentToTargetID(const MCSubtargetInfo *STI, + StringRef TargetID) { + auto TargetTriple = STI->getTargetTriple(); + auto CPU = STI->getCPU(); + auto Version = AMDGPU::getIsaVersion(CPU); + + std::string ConstructedTargetIDStr; + raw_string_ostream ConstructedTargetIDOStr(ConstructedTargetIDStr); + ConstructedTargetIDOStr << TargetTriple.getArchName() << '-' + << TargetTriple.getVendorName() << '-' + << TargetTriple.getOSName() << '-' + << TargetTriple.getEnvironmentName() << '-'; + if (Version.Major >= 9) { + ConstructedTargetIDOStr << CPU; + } else { + ConstructedTargetIDOStr << "gfx" << Version.Major << Version.Minor + << Version.Stepping; + } + ConstructedTargetIDOStr.flush(); + + if (!TargetID.startswith(ConstructedTargetIDStr)) { + return false; + } + if (auto XNACK = getXnackFromTargetID(TargetID)) { + if (XNACK.getValue() != hasXNACK(*STI)) { + return false; + } + } + if (auto SRAMECC = getSramEccFromTargetID(TargetID)) { + if (SRAMECC.getValue() != hasSRAMECC(*STI)) { + return false; + } + } + return true; +} + #define GET_MIMGBaseOpcodesTable_IMPL #define GET_MIMGDimInfoTable_IMPL #define GET_MIMGInfoTable_IMPL Index: llvm/test/CodeGen/AMDGPU/tid-incompatible-sti-1.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/AMDGPU/tid-incompatible-sti-1.ll @@ -0,0 +1,11 @@ +; RUN: not --crash llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 --amdgcn-new-target-id < %s 2>&1 | FileCheck %s + +; CHECK: Subtarget info does not match TargetID + +define amdgpu_kernel void @empty() { +entry: + ret void +} + +!0 = !{ i32 8, !"target-id", !"amdgcn-amd-amdhsa--gfx803" } +!llvm.module.flags = !{ !0 } Index: llvm/test/CodeGen/AMDGPU/tid-incompatible-sti-2.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/AMDGPU/tid-incompatible-sti-2.ll @@ -0,0 +1,11 @@ +; RUN: not --crash llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 --amdgcn-new-target-id < %s 2>&1 | FileCheck %s + +; CHECK: Subtarget info does not match TargetID + +define amdgpu_kernel void @empty() { +entry: + ret void +} + +!0 = !{ i32 8, !"target-id", !"amdgcn-amd-amdhsa--gfx900:xnack+:sramecc+" } +!llvm.module.flags = !{ !0 } Index: llvm/test/CodeGen/AMDGPU/tid-none.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/AMDGPU/tid-none.ll @@ -0,0 +1,15 @@ +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 --amdgcn-new-target-id < %s | FileCheck --check-prefixes=ASM %s +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 --amdgcn-new-target-id -filetype=obj < %s | llvm-readobj --file-headers - | FileCheck --check-prefixes=ELF %s + +; ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900" +; ASM: amdhsa.target: amdgcn-amd-amdhsa--gfx900 +; ELF: Flags [ (0x52C) +; ELF: EF_AMDGPU_FEATURE_SRAMECC_DEFAULT (0x400) +; ELF: EF_AMDGPU_FEATURE_XNACK_DEFAULT (0x100) +; ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +; ELF: ] + +define amdgpu_kernel void @empty() { +entry: + ret void +} Index: llvm/test/CodeGen/AMDGPU/tid-xnack-default-sramecc-default.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/AMDGPU/tid-xnack-default-sramecc-default.ll @@ -0,0 +1,18 @@ +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 --amdgcn-new-target-id < %s | FileCheck --check-prefixes=ASM %s +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 --amdgcn-new-target-id -filetype=obj < %s | llvm-readobj --file-headers - | FileCheck --check-prefixes=ELF %s + +; ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900" +; ASM: amdhsa.target: amdgcn-amd-amdhsa--gfx900 +; ELF: Flags [ (0x52C) +; ELF: EF_AMDGPU_FEATURE_SRAMECC_DEFAULT (0x400) +; ELF: EF_AMDGPU_FEATURE_XNACK_DEFAULT (0x100) +; ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +; ELF: ] + +define amdgpu_kernel void @empty() { +entry: + ret void +} + +!0 = !{ i32 8, !"target-id", !"amdgcn-amd-amdhsa--gfx900" } +!llvm.module.flags = !{ !0 } Index: llvm/test/CodeGen/AMDGPU/tid-xnack-default-sramecc-off.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/AMDGPU/tid-xnack-default-sramecc-off.ll @@ -0,0 +1,18 @@ +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=-sram-ecc --amdgcn-new-target-id < %s | FileCheck --check-prefixes=ASM %s +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=-sram-ecc --amdgcn-new-target-id -filetype=obj < %s | llvm-readobj --file-headers - | FileCheck --check-prefixes=ELF %s + +; ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:sramecc-" +; ASM: amdhsa.target: 'amdgcn-amd-amdhsa--gfx900:sramecc-' +; ELF: Flags [ (0x92C) +; ELF: EF_AMDGPU_FEATURE_SRAMECC_OFF (0x800) +; ELF: EF_AMDGPU_FEATURE_XNACK_DEFAULT (0x100) +; ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +; ELF: ] + +define amdgpu_kernel void @empty() { +entry: + ret void +} + +!0 = !{ i32 8, !"target-id", !"amdgcn-amd-amdhsa--gfx900:sramecc-" } +!llvm.module.flags = !{ !0 } Index: llvm/test/CodeGen/AMDGPU/tid-xnack-default-sramecc-on.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/AMDGPU/tid-xnack-default-sramecc-on.ll @@ -0,0 +1,18 @@ +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=+sram-ecc --amdgcn-new-target-id < %s | FileCheck --check-prefixes=ASM %s +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=+sram-ecc --amdgcn-new-target-id -filetype=obj < %s | llvm-readobj --file-headers - | FileCheck --check-prefixes=ELF %s + +; ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:sramecc+" +; ASM: amdhsa.target: 'amdgcn-amd-amdhsa--gfx900:sramecc+' +; ELF: Flags [ (0xD2C) +; ELF: EF_AMDGPU_FEATURE_SRAMECC_ON (0xC00) +; ELF: EF_AMDGPU_FEATURE_XNACK_DEFAULT (0x100) +; ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +; ELF: ] + +define amdgpu_kernel void @empty() { +entry: + ret void +} + +!0 = !{ i32 8, !"target-id", !"amdgcn-amd-amdhsa--gfx900:sramecc+" } +!llvm.module.flags = !{ !0 } Index: llvm/test/CodeGen/AMDGPU/tid-xnack-off-sramecc-default.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/AMDGPU/tid-xnack-off-sramecc-default.ll @@ -0,0 +1,18 @@ +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=-xnack --amdgcn-new-target-id < %s | FileCheck --check-prefixes=ASM %s +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=-xnack --amdgcn-new-target-id -filetype=obj < %s | llvm-readobj --file-headers - | FileCheck --check-prefixes=ELF %s + +; ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack-" +; ASM: amdhsa.target: 'amdgcn-amd-amdhsa--gfx900:xnack-' +; ELF: Flags [ (0x62C) +; ELF: EF_AMDGPU_FEATURE_SRAMECC_DEFAULT (0x400) +; ELF: EF_AMDGPU_FEATURE_XNACK_OFF (0x200) +; ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +; ELF: ] + +define amdgpu_kernel void @empty() { +entry: + ret void +} + +!0 = !{ i32 8, !"target-id", !"amdgcn-amd-amdhsa--gfx900:xnack-" } +!llvm.module.flags = !{ !0 } Index: llvm/test/CodeGen/AMDGPU/tid-xnack-off-sramecc-off.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/AMDGPU/tid-xnack-off-sramecc-off.ll @@ -0,0 +1,18 @@ +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=-xnack,-sram-ecc --amdgcn-new-target-id < %s | FileCheck --check-prefixes=ASM %s +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=-xnack,-sram-ecc --amdgcn-new-target-id -filetype=obj < %s | llvm-readobj --file-headers - | FileCheck --check-prefixes=ELF %s + +; ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack-:sramecc-" +; ASM: amdhsa.target: 'amdgcn-amd-amdhsa--gfx900:xnack-:sramecc-' +; ELF: Flags [ (0xA2C) +; ELF: EF_AMDGPU_FEATURE_SRAMECC_OFF (0x800) +; ELF: EF_AMDGPU_FEATURE_XNACK_OFF (0x200) +; ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +; ELF: ] + +define amdgpu_kernel void @empty() { +entry: + ret void +} + +!0 = !{ i32 8, !"target-id", !"amdgcn-amd-amdhsa--gfx900:xnack-:sramecc-" } +!llvm.module.flags = !{ !0 } Index: llvm/test/CodeGen/AMDGPU/tid-xnack-off-sramecc-on.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/AMDGPU/tid-xnack-off-sramecc-on.ll @@ -0,0 +1,18 @@ +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=-xnack,+sram-ecc --amdgcn-new-target-id < %s | FileCheck --check-prefixes=ASM %s +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=-xnack,+sram-ecc --amdgcn-new-target-id -filetype=obj < %s | llvm-readobj --file-headers - | FileCheck --check-prefixes=ELF %s + +; ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack-:sramecc+" +; ASM: amdhsa.target: 'amdgcn-amd-amdhsa--gfx900:xnack-:sramecc+' +; ELF: Flags [ (0xE2C) +; ELF: EF_AMDGPU_FEATURE_SRAMECC_ON (0xC00) +; ELF: EF_AMDGPU_FEATURE_XNACK_OFF (0x200) +; ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +; ELF: ] + +define amdgpu_kernel void @empty() { +entry: + ret void +} + +!0 = !{ i32 8, !"target-id", !"amdgcn-amd-amdhsa--gfx900:xnack-:sramecc+" } +!llvm.module.flags = !{ !0 } Index: llvm/test/CodeGen/AMDGPU/tid-xnack-on-sramecc-default.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/AMDGPU/tid-xnack-on-sramecc-default.ll @@ -0,0 +1,18 @@ +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=+xnack --amdgcn-new-target-id < %s | FileCheck --check-prefixes=ASM %s +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=+xnack --amdgcn-new-target-id -filetype=obj < %s | llvm-readobj --file-headers - | FileCheck --check-prefixes=ELF %s + +; ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack+" +; ASM: amdhsa.target: 'amdgcn-amd-amdhsa--gfx900:xnack+' +; ELF: Flags [ (0x72C) +; ELF: EF_AMDGPU_FEATURE_SRAMECC_DEFAULT (0x400) +; ELF: EF_AMDGPU_FEATURE_XNACK_ON (0x300) +; ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +; ELF: ] + +define amdgpu_kernel void @empty() { +entry: + ret void +} + +!0 = !{ i32 8, !"target-id", !"amdgcn-amd-amdhsa--gfx900:xnack+" } +!llvm.module.flags = !{ !0 } Index: llvm/test/CodeGen/AMDGPU/tid-xnack-on-sramecc-off.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/AMDGPU/tid-xnack-on-sramecc-off.ll @@ -0,0 +1,18 @@ +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=+xnack,-sram-ecc --amdgcn-new-target-id < %s | FileCheck --check-prefixes=ASM %s +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=+xnack,-sram-ecc --amdgcn-new-target-id -filetype=obj < %s | llvm-readobj --file-headers - | FileCheck --check-prefixes=ELF %s + +; ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack+:sramecc-" +; ASM: amdhsa.target: 'amdgcn-amd-amdhsa--gfx900:xnack+:sramecc-' +; ELF: Flags [ (0xB2C) +; ELF: EF_AMDGPU_FEATURE_SRAMECC_OFF (0x800) +; ELF: EF_AMDGPU_FEATURE_XNACK_ON (0x300) +; ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +; ELF: ] + +define amdgpu_kernel void @empty() { +entry: + ret void +} + +!0 = !{ i32 8, !"target-id", !"amdgcn-amd-amdhsa--gfx900:xnack+:sramecc-" } +!llvm.module.flags = !{ !0 } Index: llvm/test/CodeGen/AMDGPU/tid-xnack-on-sramecc-on.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/AMDGPU/tid-xnack-on-sramecc-on.ll @@ -0,0 +1,18 @@ +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=+xnack,+sram-ecc --amdgcn-new-target-id < %s | FileCheck --check-prefixes=ASM %s +; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=gfx900 -mattr=+xnack,+sram-ecc --amdgcn-new-target-id -filetype=obj < %s | llvm-readobj --file-headers - | FileCheck --check-prefixes=ELF %s + +; ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack+:sramecc+" +; ASM: amdhsa.target: 'amdgcn-amd-amdhsa--gfx900:xnack+:sramecc+' +; ELF: Flags [ (0xF2C) +; ELF: EF_AMDGPU_FEATURE_SRAMECC_ON (0xC00) +; ELF: EF_AMDGPU_FEATURE_XNACK_ON (0x300) +; ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +; ELF: ] + +define amdgpu_kernel void @empty() { +entry: + ret void +} + +!0 = !{ i32 8, !"target-id", !"amdgcn-amd-amdhsa--gfx900:xnack+:sramecc+" } +!llvm.module.flags = !{ !0 } Index: llvm/test/MC/AMDGPU/tid-incompatible-sti-1.s =================================================================== --- /dev/null +++ llvm/test/MC/AMDGPU/tid-incompatible-sti-1.s @@ -0,0 +1,6 @@ +// RUN: not llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --amdgcn-new-target-id %s 2>&1 | FileCheck %s + +// CHECK: error: target must match options + +.amdgcn_target "amdgcn-amd-amdhsa--gfx803" +.text Index: llvm/test/MC/AMDGPU/tid-incompatible-sti-2.s =================================================================== --- /dev/null +++ llvm/test/MC/AMDGPU/tid-incompatible-sti-2.s @@ -0,0 +1,6 @@ +// RUN: not llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --amdgcn-new-target-id %s 2>&1 | FileCheck %s + +// CHECK: error: target must match options + +.amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack+:sramecc+" +.text Index: llvm/test/MC/AMDGPU/tid-none.s =================================================================== --- /dev/null +++ llvm/test/MC/AMDGPU/tid-none.s @@ -0,0 +1,11 @@ +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --amdgcn-new-target-id %s | FileCheck --check-prefixes=ASM %s +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --amdgcn-new-target-id -filetype=obj %s | llvm-readobj --file-headers - |FileCheck --check-prefixes=ELF %s + +// ASM-NOT: .amdgcn_target +// ELF: Flags [ (0x52C) +// ELF: EF_AMDGPU_FEATURE_SRAMECC_DEFAULT (0x400) +// ELF: EF_AMDGPU_FEATURE_XNACK_DEFAULT (0x100) +// ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +// ELF: ] + +.text Index: llvm/test/MC/AMDGPU/tid-xnack-default-sramecc-default.s =================================================================== --- /dev/null +++ llvm/test/MC/AMDGPU/tid-xnack-default-sramecc-default.s @@ -0,0 +1,12 @@ +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --amdgcn-new-target-id %s | FileCheck --check-prefixes=ASM %s +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --amdgcn-new-target-id -filetype=obj %s | llvm-readobj --file-headers - |FileCheck --check-prefixes=ELF %s + +// ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900" +// ELF: Flags [ (0x52C) +// ELF: EF_AMDGPU_FEATURE_SRAMECC_DEFAULT (0x400) +// ELF: EF_AMDGPU_FEATURE_XNACK_DEFAULT (0x100) +// ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +// ELF: ] + +.amdgcn_target "amdgcn-amd-amdhsa--gfx900" +.text Index: llvm/test/MC/AMDGPU/tid-xnack-default-sramecc-off.s =================================================================== --- /dev/null +++ llvm/test/MC/AMDGPU/tid-xnack-default-sramecc-off.s @@ -0,0 +1,12 @@ +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=-sram-ecc --amdgcn-new-target-id %s | FileCheck --check-prefixes=ASM %s +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=-sram-ecc --amdgcn-new-target-id -filetype=obj %s | llvm-readobj --file-headers - |FileCheck --check-prefixes=ELF %s + +// ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:sramecc-" +// ELF: Flags [ (0x92C) +// ELF: EF_AMDGPU_FEATURE_SRAMECC_OFF (0x800) +// ELF: EF_AMDGPU_FEATURE_XNACK_DEFAULT (0x100) +// ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +// ELF: ] + +.amdgcn_target "amdgcn-amd-amdhsa--gfx900:sramecc-" +.text Index: llvm/test/MC/AMDGPU/tid-xnack-default-sramecc-on.s =================================================================== --- /dev/null +++ llvm/test/MC/AMDGPU/tid-xnack-default-sramecc-on.s @@ -0,0 +1,12 @@ +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=+sram-ecc --amdgcn-new-target-id %s | FileCheck --check-prefixes=ASM %s +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=+sram-ecc --amdgcn-new-target-id -filetype=obj %s | llvm-readobj --file-headers - |FileCheck --check-prefixes=ELF %s + +// ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:sramecc+" +// ELF: Flags [ (0xD2C) +// ELF: EF_AMDGPU_FEATURE_SRAMECC_ON (0xC00) +// ELF: EF_AMDGPU_FEATURE_XNACK_DEFAULT (0x100) +// ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +// ELF: ] + +.amdgcn_target "amdgcn-amd-amdhsa--gfx900:sramecc+" +.text Index: llvm/test/MC/AMDGPU/tid-xnack-off-sramecc-default.s =================================================================== --- /dev/null +++ llvm/test/MC/AMDGPU/tid-xnack-off-sramecc-default.s @@ -0,0 +1,12 @@ +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=-xnack --amdgcn-new-target-id %s | FileCheck --check-prefixes=ASM %s +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=-xnack --amdgcn-new-target-id -filetype=obj %s | llvm-readobj --file-headers - |FileCheck --check-prefixes=ELF %s + +// ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack-" +// ELF: Flags [ (0x62C) +// ELF: EF_AMDGPU_FEATURE_SRAMECC_DEFAULT (0x400) +// ELF: EF_AMDGPU_FEATURE_XNACK_OFF (0x200) +// ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +// ELF: ] + +.amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack-" +.text Index: llvm/test/MC/AMDGPU/tid-xnack-off-sramecc-off.s =================================================================== --- /dev/null +++ llvm/test/MC/AMDGPU/tid-xnack-off-sramecc-off.s @@ -0,0 +1,12 @@ +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=-xnack,-sram-ecc --amdgcn-new-target-id %s | FileCheck --check-prefixes=ASM %s +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=-xnack,-sram-ecc --amdgcn-new-target-id -filetype=obj %s | llvm-readobj --file-headers - |FileCheck --check-prefixes=ELF %s + +// ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack-:sramecc-" +// ELF: Flags [ (0xA2C) +// ELF: EF_AMDGPU_FEATURE_SRAMECC_OFF (0x800) +// ELF: EF_AMDGPU_FEATURE_XNACK_OFF (0x200) +// ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +// ELF: ] + +.amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack-:sramecc-" +.text Index: llvm/test/MC/AMDGPU/tid-xnack-off-sramecc-on.s =================================================================== --- /dev/null +++ llvm/test/MC/AMDGPU/tid-xnack-off-sramecc-on.s @@ -0,0 +1,12 @@ +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=-xnack,+sram-ecc --amdgcn-new-target-id %s | FileCheck --check-prefixes=ASM %s +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=-xnack,+sram-ecc --amdgcn-new-target-id -filetype=obj %s | llvm-readobj --file-headers - |FileCheck --check-prefixes=ELF %s + +// ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack-:sramecc+" +// ELF: Flags [ (0xE2C) +// ELF: EF_AMDGPU_FEATURE_SRAMECC_ON (0xC00) +// ELF: EF_AMDGPU_FEATURE_XNACK_OFF (0x200) +// ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +// ELF: ] + +.amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack-:sramecc+" +.text Index: llvm/test/MC/AMDGPU/tid-xnack-on-sramecc-default.s =================================================================== --- /dev/null +++ llvm/test/MC/AMDGPU/tid-xnack-on-sramecc-default.s @@ -0,0 +1,12 @@ +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=+xnack --amdgcn-new-target-id %s | FileCheck --check-prefixes=ASM %s +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=+xnack --amdgcn-new-target-id -filetype=obj %s | llvm-readobj --file-headers - |FileCheck --check-prefixes=ELF %s + +// ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack+" +// ELF: Flags [ (0x72C) +// ELF: EF_AMDGPU_FEATURE_SRAMECC_DEFAULT (0x400) +// ELF: EF_AMDGPU_FEATURE_XNACK_ON (0x300) +// ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +// ELF: ] + +.amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack+" +.text Index: llvm/test/MC/AMDGPU/tid-xnack-on-sramecc-off.s =================================================================== --- /dev/null +++ llvm/test/MC/AMDGPU/tid-xnack-on-sramecc-off.s @@ -0,0 +1,12 @@ +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=+xnack,-sram-ecc --amdgcn-new-target-id %s | FileCheck --check-prefixes=ASM %s +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=+xnack,-sram-ecc --amdgcn-new-target-id -filetype=obj %s | llvm-readobj --file-headers - |FileCheck --check-prefixes=ELF %s + +// ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack+:sramecc-" +// ELF: Flags [ (0xB2C) +// ELF: EF_AMDGPU_FEATURE_SRAMECC_OFF (0x800) +// ELF: EF_AMDGPU_FEATURE_XNACK_ON (0x300) +// ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +// ELF: ] + +.amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack+:sramecc-" +.text Index: llvm/test/MC/AMDGPU/tid-xnack-on-sramecc-on.s =================================================================== --- /dev/null +++ llvm/test/MC/AMDGPU/tid-xnack-on-sramecc-on.s @@ -0,0 +1,12 @@ +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=+xnack,+sram-ecc --amdgcn-new-target-id %s | FileCheck --check-prefixes=ASM %s +// RUN: llvm-mc --triple=amdgcn-amd-amdhsa -mcpu=gfx900 --mattr=+xnack,+sram-ecc --amdgcn-new-target-id -filetype=obj %s | llvm-readobj --file-headers - |FileCheck --check-prefixes=ELF %s + +// ASM: .amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack+:sramecc+" +// ELF: Flags [ (0xF2C) +// ELF: EF_AMDGPU_FEATURE_SRAMECC_ON (0xC00) +// ELF: EF_AMDGPU_FEATURE_XNACK_ON (0x300) +// ELF: EF_AMDGPU_MACH_AMDGCN_GFX900 (0x2C) +// ELF: ] + +.amdgcn_target "amdgcn-amd-amdhsa--gfx900:xnack+:sramecc+" +.text Index: llvm/tools/llvm-readobj/ELFDumper.cpp =================================================================== --- llvm/tools/llvm-readobj/ELFDumper.cpp +++ llvm/tools/llvm-readobj/ELFDumper.cpp @@ -1759,7 +1759,7 @@ ENUM_ENT(EF_MIPS_ARCH_64R6, "mips64r6") }; -static const EnumEntry ElfHeaderAMDGPUFlags[] = { +static const EnumEntry ElfHeaderAMDGPUFlagsABIVersion01[] = { LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_NONE), LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_R600), LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_R630), @@ -1801,6 +1801,52 @@ LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_SRAM_ECC) }; +static const EnumEntry ElfHeaderAMDGPUFlagsABIVersion2[] = { + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_NONE), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_R600), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_R630), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_RS880), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_RV670), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_RV710), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_RV730), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_RV770), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_CEDAR), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_CYPRESS), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_JUNIPER), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_REDWOOD), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_SUMO), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_BARTS), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_CAICOS), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_CAYMAN), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_R600_TURKS), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX600), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX601), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX700), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX701), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX702), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX703), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX704), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX801), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX802), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX803), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX810), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX900), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX902), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX904), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX906), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX908), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX909), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX1010), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX1011), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_MACH_AMDGCN_GFX1012), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_FEATURE_XNACK_DEFAULT), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_FEATURE_XNACK_OFF), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_FEATURE_XNACK_ON), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_FEATURE_SRAMECC_DEFAULT), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_FEATURE_SRAMECC_OFF), + LLVM_READOBJ_ENUM_ENT(ELF, EF_AMDGPU_FEATURE_SRAMECC_ON), +}; + static const EnumEntry ElfHeaderRISCVFlags[] = { ENUM_ENT(EF_RISCV_RVC, "RVC"), ENUM_ENT(EF_RISCV_FLOAT_ABI_SINGLE, "single-float ABI"), @@ -5942,9 +5988,19 @@ W.printFlags("Flags", E->e_flags, makeArrayRef(ElfHeaderMipsFlags), unsigned(ELF::EF_MIPS_ARCH), unsigned(ELF::EF_MIPS_ABI), unsigned(ELF::EF_MIPS_MACH)); - else if (E->e_machine == EM_AMDGPU) - W.printFlags("Flags", E->e_flags, makeArrayRef(ElfHeaderAMDGPUFlags), - unsigned(ELF::EF_AMDGPU_MACH)); + else if (E->e_machine == EM_AMDGPU) { + if (E->e_ident[EI_ABIVERSION] == 0 || E->e_ident[EI_ABIVERSION] == 1) { + W.printFlags("Flags", E->e_flags, + makeArrayRef(ElfHeaderAMDGPUFlagsABIVersion01), + unsigned(ELF::EF_AMDGPU_MACH)); + } else if (E->e_ident[EI_ABIVERSION] == 2) { + W.printFlags("Flags", E->e_flags, + makeArrayRef(ElfHeaderAMDGPUFlagsABIVersion2), + unsigned(ELF::EF_AMDGPU_MACH), + unsigned(ELF::EF_AMDGPU_FEATURE_XNACK), + unsigned(ELF::EF_AMDGPU_FEATURE_SRAMECC)); + } + } else if (E->e_machine == EM_RISCV) W.printFlags("Flags", E->e_flags, makeArrayRef(ElfHeaderRISCVFlags)); else