144a14a6aSChris Bieneman //===- DirectXTargetMachine.cpp - DirectX Target Implementation -*- C++ -*-===// 244a14a6aSChris Bieneman // 344a14a6aSChris Bieneman // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 444a14a6aSChris Bieneman // See https://llvm.org/LICENSE.txt for license information. 544a14a6aSChris Bieneman // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 644a14a6aSChris Bieneman // 744a14a6aSChris Bieneman //===----------------------------------------------------------------------===// 844a14a6aSChris Bieneman /// 944a14a6aSChris Bieneman /// \file 1044a14a6aSChris Bieneman /// This file contains DirectX target initializer. 1144a14a6aSChris Bieneman /// 1244a14a6aSChris Bieneman //===----------------------------------------------------------------------===// 1344a14a6aSChris Bieneman 1444a14a6aSChris Bieneman #include "DirectXTargetMachine.h" 151bc9b67bSMatt Arsenault #include "DXILDataScalarization.h" 165ac624c8SFarzon Lotfi #include "DXILFlattenArrays.h" 1781ee3855SJustin Bogner #include "DXILIntrinsicExpansion.h" 1881ee3855SJustin Bogner #include "DXILOpLowering.h" 1981ee3855SJustin Bogner #include "DXILPrettyPrinter.h" 200fca76d5SJustin Bogner #include "DXILResourceAccess.h" 2122018555SXiang Li #include "DXILResourceAnalysis.h" 222b2afb25SChris Bieneman #include "DXILShaderFlags.h" 2381ee3855SJustin Bogner #include "DXILTranslateMetadata.h" 24f2526c1aSChris Bieneman #include "DXILWriter/DXILWriterPass.h" 256599fdabSChris Bieneman #include "DirectX.h" 2644a14a6aSChris Bieneman #include "DirectXSubtarget.h" 2744a14a6aSChris Bieneman #include "DirectXTargetTransformInfo.h" 2844a14a6aSChris Bieneman #include "TargetInfo/DirectXTargetInfo.h" 292af61e62SChris Bieneman #include "llvm/CodeGen/MachineModuleInfo.h" 3044a14a6aSChris Bieneman #include "llvm/CodeGen/Passes.h" 3144a14a6aSChris Bieneman #include "llvm/CodeGen/TargetPassConfig.h" 328f0cd7c1SXiang Li #include "llvm/IR/IRPrintingPasses.h" 3344a14a6aSChris Bieneman #include "llvm/IR/LegacyPassManager.h" 34c05e29bfSFarzon Lotfi #include "llvm/InitializePasses.h" 352af61e62SChris Bieneman #include "llvm/MC/MCSectionDXContainer.h" 3644a14a6aSChris Bieneman #include "llvm/MC/SectionKind.h" 3744a14a6aSChris Bieneman #include "llvm/MC/TargetRegistry.h" 3822018555SXiang Li #include "llvm/Passes/PassBuilder.h" 3944a14a6aSChris Bieneman #include "llvm/Support/CodeGen.h" 4044a14a6aSChris Bieneman #include "llvm/Support/Compiler.h" 4144a14a6aSChris Bieneman #include "llvm/Support/ErrorHandling.h" 4244a14a6aSChris Bieneman #include "llvm/Target/TargetLoweringObjectFile.h" 43c05e29bfSFarzon Lotfi #include "llvm/Transforms/Scalar/Scalarizer.h" 448c7c20f0SKrzysztof Parzyszek #include <optional> 4544a14a6aSChris Bieneman 4644a14a6aSChris Bieneman using namespace llvm; 4744a14a6aSChris Bieneman 4844a14a6aSChris Bieneman extern "C" LLVM_EXTERNAL_VISIBILITY void LLVMInitializeDirectXTarget() { 4944a14a6aSChris Bieneman RegisterTargetMachine<DirectXTargetMachine> X(getTheDirectXTarget()); 506599fdabSChris Bieneman auto *PR = PassRegistry::getPassRegistry(); 51de1a97dbSFarzon Lotfi initializeDXILIntrinsicExpansionLegacyPass(*PR); 52324bdd66SFarzon Lotfi initializeDXILDataScalarizationLegacyPass(*PR); 535ac624c8SFarzon Lotfi initializeDXILFlattenArraysLegacyPass(*PR); 54c05e29bfSFarzon Lotfi initializeScalarizerLegacyPassPass(*PR); 556599fdabSChris Bieneman initializeDXILPrepareModulePass(*PR); 56d401a993SChris Bieneman initializeEmbedDXILPassPass(*PR); 57e3becfacSXiang Li initializeWriteDXILPassPass(*PR); 5872017fcfSJustin Bogner initializeDXContainerGlobalsPass(*PR); 5985285be9SXiang Li initializeDXILOpLoweringLegacyPass(*PR); 600fca76d5SJustin Bogner initializeDXILResourceAccessLegacyPass(*PR); 6181ee3855SJustin Bogner initializeDXILTranslateMetadataLegacyPass(*PR); 621c5f6cfcSJustin Bogner initializeDXILResourceMDWrapperPass(*PR); 636e05c8dfSChris Bieneman initializeShaderFlagsAnalysisWrapperPass(*PR); 64db279c72SHelena Kotas initializeDXILFinalizeLinkageLegacyPass(*PR); 6544a14a6aSChris Bieneman } 6644a14a6aSChris Bieneman 6744a14a6aSChris Bieneman class DXILTargetObjectFile : public TargetLoweringObjectFile { 6844a14a6aSChris Bieneman public: 6944a14a6aSChris Bieneman DXILTargetObjectFile() = default; 7044a14a6aSChris Bieneman 7144a14a6aSChris Bieneman MCSection *getExplicitSectionGlobal(const GlobalObject *GO, SectionKind Kind, 7244a14a6aSChris Bieneman const TargetMachine &TM) const override { 732af61e62SChris Bieneman return getContext().getDXContainerSection(GO->getSection(), Kind); 7444a14a6aSChris Bieneman } 7544a14a6aSChris Bieneman 7644a14a6aSChris Bieneman protected: 7744a14a6aSChris Bieneman MCSection *SelectSectionForGlobal(const GlobalObject *GO, SectionKind Kind, 7844a14a6aSChris Bieneman const TargetMachine &TM) const override { 7944a14a6aSChris Bieneman llvm_unreachable("Not supported!"); 8044a14a6aSChris Bieneman } 8144a14a6aSChris Bieneman }; 8244a14a6aSChris Bieneman 8344a14a6aSChris Bieneman class DirectXPassConfig : public TargetPassConfig { 8444a14a6aSChris Bieneman public: 8544a14a6aSChris Bieneman DirectXPassConfig(DirectXTargetMachine &TM, PassManagerBase &PM) 8644a14a6aSChris Bieneman : TargetPassConfig(TM, PM) {} 8744a14a6aSChris Bieneman 8844a14a6aSChris Bieneman DirectXTargetMachine &getDirectXTargetMachine() const { 8944a14a6aSChris Bieneman return getTM<DirectXTargetMachine>(); 9044a14a6aSChris Bieneman } 9144a14a6aSChris Bieneman 9244a14a6aSChris Bieneman FunctionPass *createTargetRegisterAllocator(bool) override { return nullptr; } 9320f7f9b7SXiang Li void addCodeGenPrepare() override { 9493d2a2caSJustin Bogner addPass(createDXILFinalizeLinkageLegacyPass()); 95de1a97dbSFarzon Lotfi addPass(createDXILIntrinsicExpansionLegacyPass()); 96324bdd66SFarzon Lotfi addPass(createDXILDataScalarizationLegacyPass()); 970fca76d5SJustin Bogner addPass(createDXILFlattenArraysLegacyPass()); 980fca76d5SJustin Bogner addPass(createDXILResourceAccessLegacyPass()); 99c05e29bfSFarzon Lotfi ScalarizerPassOptions DxilScalarOptions; 100c05e29bfSFarzon Lotfi DxilScalarOptions.ScalarizeLoadStore = true; 101c05e29bfSFarzon Lotfi addPass(createScalarizerPass(DxilScalarOptions)); 10281ee3855SJustin Bogner addPass(createDXILTranslateMetadataLegacyPass()); 103*bfd05102SJustin Bogner addPass(createDXILOpLoweringLegacyPass()); 1045e9dd882SXiang Li addPass(createDXILPrepareModulePass()); 10520f7f9b7SXiang Li } 10644a14a6aSChris Bieneman }; 10744a14a6aSChris Bieneman 10844a14a6aSChris Bieneman DirectXTargetMachine::DirectXTargetMachine(const Target &T, const Triple &TT, 10944a14a6aSChris Bieneman StringRef CPU, StringRef FS, 11044a14a6aSChris Bieneman const TargetOptions &Options, 111bac97427SFangrui Song std::optional<Reloc::Model> RM, 1128c7c20f0SKrzysztof Parzyszek std::optional<CodeModel::Model> CM, 1130a1aa6cdSArthur Eubanks CodeGenOptLevel OL, bool JIT) 114eec21cceSMatin Raayai : CodeGenTargetMachineImpl( 115bb3f5e1fSMatin Raayai T, 11644a14a6aSChris Bieneman "e-m:e-p:32:32-i1:32-i8:8-i16:16-i32:32-i64:64-f16:16-" 11744a14a6aSChris Bieneman "f32:32-f64:64-n8:16:32:64", 118bb3f5e1fSMatin Raayai TT, CPU, FS, Options, Reloc::Static, CodeModel::Small, OL), 11944a14a6aSChris Bieneman TLOF(std::make_unique<DXILTargetObjectFile>()), 1202af61e62SChris Bieneman Subtarget(std::make_unique<DirectXSubtarget>(TT, CPU, FS, *this)) { 1212af61e62SChris Bieneman initAsmInfo(); 1222af61e62SChris Bieneman } 12344a14a6aSChris Bieneman 12444a14a6aSChris Bieneman DirectXTargetMachine::~DirectXTargetMachine() {} 12544a14a6aSChris Bieneman 1265cd0ba30SNikita Popov void DirectXTargetMachine::registerPassBuilderCallbacks(PassBuilder &PB) { 12776fdb590Spaperchalice #define GET_PASS_REGISTRY "DirectXPassRegistry.def" 12876fdb590Spaperchalice #include "llvm/Passes/TargetPassRegistry.inc" 12922018555SXiang Li } 13022018555SXiang Li 13144a14a6aSChris Bieneman bool DirectXTargetMachine::addPassesToEmitFile( 13244a14a6aSChris Bieneman PassManagerBase &PM, raw_pwrite_stream &Out, raw_pwrite_stream *DwoOut, 13344a14a6aSChris Bieneman CodeGenFileType FileType, bool DisableVerify, 13444a14a6aSChris Bieneman MachineModuleInfoWrapperPass *MMIWP) { 13520f7f9b7SXiang Li TargetPassConfig *PassConfig = createPassConfig(PM); 13620f7f9b7SXiang Li PassConfig->addCodeGenPrepare(); 13720f7f9b7SXiang Li 1382af61e62SChris Bieneman switch (FileType) { 1390a1aa6cdSArthur Eubanks case CodeGenFileType::AssemblyFile: 14081ee3855SJustin Bogner PM.add(createDXILPrettyPrinterLegacyPass(Out)); 14144a14a6aSChris Bieneman PM.add(createPrintModulePass(Out, "", true)); 14244a14a6aSChris Bieneman break; 1430a1aa6cdSArthur Eubanks case CodeGenFileType::ObjectFile: 1442af61e62SChris Bieneman if (TargetPassConfig::willCompleteCodeGenPipeline()) { 14572017fcfSJustin Bogner PM.add(createDXILEmbedderPass()); 14672017fcfSJustin Bogner // We embed the other DXContainer globals after embedding DXIL so that the 14772017fcfSJustin Bogner // globals don't pollute the DXIL. 14872017fcfSJustin Bogner PM.add(createDXContainerGlobalsPass()); 14972017fcfSJustin Bogner 1502af61e62SChris Bieneman if (!MMIWP) 1512af61e62SChris Bieneman MMIWP = new MachineModuleInfoWrapperPass(this); 1522af61e62SChris Bieneman PM.add(MMIWP); 1532af61e62SChris Bieneman if (addAsmPrinter(PM, Out, DwoOut, FileType, 1542af61e62SChris Bieneman MMIWP->getMMI().getContext())) 1552af61e62SChris Bieneman return true; 1562af61e62SChris Bieneman } else 157f2526c1aSChris Bieneman PM.add(createDXILWriterPass(Out)); 15844a14a6aSChris Bieneman break; 1590a1aa6cdSArthur Eubanks case CodeGenFileType::Null: 16044a14a6aSChris Bieneman break; 16144a14a6aSChris Bieneman } 16244a14a6aSChris Bieneman return false; 16344a14a6aSChris Bieneman } 16444a14a6aSChris Bieneman 16544a14a6aSChris Bieneman bool DirectXTargetMachine::addPassesToEmitMC(PassManagerBase &PM, 16644a14a6aSChris Bieneman MCContext *&Ctx, 16744a14a6aSChris Bieneman raw_pwrite_stream &Out, 16844a14a6aSChris Bieneman bool DisableVerify) { 16944a14a6aSChris Bieneman return true; 17044a14a6aSChris Bieneman } 17144a14a6aSChris Bieneman 17244a14a6aSChris Bieneman TargetPassConfig *DirectXTargetMachine::createPassConfig(PassManagerBase &PM) { 17344a14a6aSChris Bieneman return new DirectXPassConfig(*this, PM); 17444a14a6aSChris Bieneman } 17544a14a6aSChris Bieneman 17644a14a6aSChris Bieneman const DirectXSubtarget * 17744a14a6aSChris Bieneman DirectXTargetMachine::getSubtargetImpl(const Function &) const { 17844a14a6aSChris Bieneman return Subtarget.get(); 17944a14a6aSChris Bieneman } 18044a14a6aSChris Bieneman 18144a14a6aSChris Bieneman TargetTransformInfo 18244a14a6aSChris Bieneman DirectXTargetMachine::getTargetTransformInfo(const Function &F) const { 18344a14a6aSChris Bieneman return TargetTransformInfo(DirectXTTIImpl(this, F)); 18444a14a6aSChris Bieneman } 18544a14a6aSChris Bieneman 18644a14a6aSChris Bieneman DirectXTargetLowering::DirectXTargetLowering(const DirectXTargetMachine &TM, 18744a14a6aSChris Bieneman const DirectXSubtarget &STI) 18844a14a6aSChris Bieneman : TargetLowering(TM) {} 189