diff options
Diffstat (limited to 'contrib/llvm-project/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.cpp')
| -rw-r--r-- | contrib/llvm-project/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.cpp | 104 |
1 files changed, 93 insertions, 11 deletions
diff --git a/contrib/llvm-project/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.cpp b/contrib/llvm-project/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.cpp index 22746788607b..779036016560 100644 --- a/contrib/llvm-project/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.cpp +++ b/contrib/llvm-project/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.cpp @@ -15,6 +15,8 @@ //===----------------------------------------------------------------------===// #include "SPIRVModuleAnalysis.h" +#include "MCTargetDesc/SPIRVBaseInfo.h" +#include "MCTargetDesc/SPIRVMCTargetDesc.h" #include "SPIRV.h" #include "SPIRVSubtarget.h" #include "SPIRVTargetMachine.h" @@ -106,11 +108,18 @@ void SPIRVModuleAnalysis::setBaseInfo(const Module &M) { MAI.Mem = static_cast<SPIRV::MemoryModel::MemoryModel>(getMetadataUInt(MemMD, 1)); } else { - MAI.Mem = SPIRV::MemoryModel::OpenCL; - unsigned PtrSize = ST->getPointerSize(); - MAI.Addr = PtrSize == 32 ? SPIRV::AddressingModel::Physical32 - : PtrSize == 64 ? SPIRV::AddressingModel::Physical64 - : SPIRV::AddressingModel::Logical; + // TODO: Add support for VulkanMemoryModel. + MAI.Mem = ST->isOpenCLEnv() ? SPIRV::MemoryModel::OpenCL + : SPIRV::MemoryModel::GLSL450; + if (MAI.Mem == SPIRV::MemoryModel::OpenCL) { + unsigned PtrSize = ST->getPointerSize(); + MAI.Addr = PtrSize == 32 ? SPIRV::AddressingModel::Physical32 + : PtrSize == 64 ? SPIRV::AddressingModel::Physical64 + : SPIRV::AddressingModel::Logical; + } else { + // TODO: Add support for PhysicalStorageBufferAddress. + MAI.Addr = SPIRV::AddressingModel::Logical; + } } // Get the OpenCL version number from metadata. // TODO: support other source languages. @@ -148,9 +157,12 @@ void SPIRVModuleAnalysis::setBaseInfo(const Module &M) { MAI.Reqs.getAndAddRequirements(SPIRV::OperandCategory::AddressingModelOperand, MAI.Addr, *ST); - // TODO: check if it's required by default. - MAI.ExtInstSetMap[static_cast<unsigned>(SPIRV::InstructionSet::OpenCL_std)] = - Register::index2VirtReg(MAI.getNextID()); + if (ST->isOpenCLEnv()) { + // TODO: check if it's required by default. + MAI.ExtInstSetMap[static_cast<unsigned>( + SPIRV::InstructionSet::OpenCL_std)] = + Register::index2VirtReg(MAI.getNextID()); + } } // Collect MI which defines the register in the given machine function. @@ -494,7 +506,7 @@ void SPIRV::RequirementHandler::checkSatisfiable( for (auto Ext : AllExtensions) { if (ST.canUseExtension(Ext)) continue; - LLVM_DEBUG(dbgs() << "Extension not suported: " + LLVM_DEBUG(dbgs() << "Extension not supported: " << getSymbolicOperandMnemonic( OperandCategory::ExtensionOperand, Ext) << "\n"); @@ -513,12 +525,31 @@ void SPIRV::RequirementHandler::addAvailableCaps(const CapabilityList &ToAdd) { SPIRV::OperandCategory::CapabilityOperand, Cap)); } +void SPIRV::RequirementHandler::removeCapabilityIf( + const Capability::Capability ToRemove, + const Capability::Capability IfPresent) { + if (AllCaps.contains(IfPresent)) + AllCaps.erase(ToRemove); +} + namespace llvm { namespace SPIRV { void RequirementHandler::initAvailableCapabilities(const SPIRVSubtarget &ST) { - // TODO: Implemented for other targets other then OpenCL. - if (!ST.isOpenCLEnv()) + if (ST.isOpenCLEnv()) { + initAvailableCapabilitiesForOpenCL(ST); return; + } + + if (ST.isVulkanEnv()) { + initAvailableCapabilitiesForVulkan(ST); + return; + } + + report_fatal_error("Unimplemented environment for SPIR-V generation."); +} + +void RequirementHandler::initAvailableCapabilitiesForOpenCL( + const SPIRVSubtarget &ST) { // Add the min requirements for different OpenCL and SPIR-V versions. addAvailableCaps({Capability::Addresses, Capability::Float16Buffer, Capability::Int16, Capability::Int8, Capability::Kernel, @@ -552,8 +583,24 @@ void RequirementHandler::initAvailableCapabilities(const SPIRVSubtarget &ST) { // TODO: verify if this needs some checks. addAvailableCaps({Capability::Float16, Capability::Float64}); + // Add capabilities enabled by extensions. + for (auto Extension : ST.getAllAvailableExtensions()) { + CapabilityList EnabledCapabilities = + getCapabilitiesEnabledByExtension(Extension); + addAvailableCaps(EnabledCapabilities); + } + // TODO: add OpenCL extensions. } + +void RequirementHandler::initAvailableCapabilitiesForVulkan( + const SPIRVSubtarget &ST) { + addAvailableCaps({Capability::Shader, Capability::Linkage}); + + // Provided by Vulkan version 1.0. + addAvailableCaps({Capability::Int16, Capability::Int64, Capability::Float64}); +} + } // namespace SPIRV } // namespace llvm @@ -696,6 +743,16 @@ void addInstrRequirements(const MachineInstr &MI, break; } case SPIRV::OpBitReverse: + case SPIRV::OpBitFieldInsert: + case SPIRV::OpBitFieldSExtract: + case SPIRV::OpBitFieldUExtract: + if (!ST.canUseExtension(SPIRV::Extension::SPV_KHR_bit_instructions)) { + Reqs.addCapability(SPIRV::Capability::Shader); + break; + } + Reqs.addExtension(SPIRV::Extension::SPV_KHR_bit_instructions); + Reqs.addCapability(SPIRV::Capability::BitInstructions); + break; case SPIRV::OpTypeRuntimeArray: Reqs.addCapability(SPIRV::Capability::Shader); break; @@ -846,9 +903,22 @@ void addInstrRequirements(const MachineInstr &MI, case SPIRV::OpGroupNonUniformBallotFindMSB: Reqs.addCapability(SPIRV::Capability::GroupNonUniformBallot); break; + case SPIRV::OpAssumeTrueKHR: + case SPIRV::OpExpectKHR: + if (ST.canUseExtension(SPIRV::Extension::SPV_KHR_expect_assume)) { + Reqs.addExtension(SPIRV::Extension::SPV_KHR_expect_assume); + Reqs.addCapability(SPIRV::Capability::ExpectAssumeKHR); + } + break; default: break; } + + // If we require capability Shader, then we can remove the requirement for + // the BitInstructions capability, since Shader is a superset capability + // of BitInstructions. + Reqs.removeCapabilityIf(SPIRV::Capability::BitInstructions, + SPIRV::Capability::Shader); } static void collectReqs(const Module &M, SPIRV::ModuleAnalysisInfo &MAI, @@ -886,6 +956,11 @@ static void collectReqs(const Module &M, SPIRV::ModuleAnalysisInfo &MAI, MAI.Reqs.getAndAddRequirements( SPIRV::OperandCategory::ExecutionModeOperand, SPIRV::ExecutionMode::LocalSize, ST); + if (F.getFnAttribute("hlsl.numthreads").isValid()) { + MAI.Reqs.getAndAddRequirements( + SPIRV::OperandCategory::ExecutionModeOperand, + SPIRV::ExecutionMode::LocalSize, ST); + } if (F.getMetadata("work_group_size_hint")) MAI.Reqs.getAndAddRequirements( SPIRV::OperandCategory::ExecutionModeOperand, @@ -898,6 +973,13 @@ static void collectReqs(const Module &M, SPIRV::ModuleAnalysisInfo &MAI, MAI.Reqs.getAndAddRequirements( SPIRV::OperandCategory::ExecutionModeOperand, SPIRV::ExecutionMode::VecTypeHint, ST); + + if (F.hasOptNone() && + ST.canUseExtension(SPIRV::Extension::SPV_INTEL_optnone)) { + // Output OpCapability OptNoneINTEL. + MAI.Reqs.addExtension(SPIRV::Extension::SPV_INTEL_optnone); + MAI.Reqs.addCapability(SPIRV::Capability::OptNoneINTEL); + } } } |
