Path: blob/main/contrib/llvm-project/llvm/lib/Target/BPF/BPFTargetMachine.cpp
35294 views
//===-- BPFTargetMachine.cpp - Define TargetMachine for BPF ---------------===//1//2// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.3// See https://llvm.org/LICENSE.txt for license information.4// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception5//6//===----------------------------------------------------------------------===//7//8// Implements the info about BPF target spec.9//10//===----------------------------------------------------------------------===//1112#include "BPFTargetMachine.h"13#include "BPF.h"14#include "BPFTargetTransformInfo.h"15#include "MCTargetDesc/BPFMCAsmInfo.h"16#include "TargetInfo/BPFTargetInfo.h"17#include "llvm/CodeGen/GlobalISel/IRTranslator.h"18#include "llvm/CodeGen/GlobalISel/InstructionSelect.h"19#include "llvm/CodeGen/GlobalISel/Legalizer.h"20#include "llvm/CodeGen/GlobalISel/RegBankSelect.h"21#include "llvm/CodeGen/Passes.h"22#include "llvm/CodeGen/TargetLoweringObjectFileImpl.h"23#include "llvm/CodeGen/TargetPassConfig.h"24#include "llvm/IR/PassManager.h"25#include "llvm/InitializePasses.h"26#include "llvm/MC/TargetRegistry.h"27#include "llvm/Passes/PassBuilder.h"28#include "llvm/Support/FormattedStream.h"29#include "llvm/Target/TargetOptions.h"30#include "llvm/Transforms/Scalar.h"31#include "llvm/Transforms/Scalar/SimplifyCFG.h"32#include "llvm/Transforms/Utils/SimplifyCFGOptions.h"33#include <optional>34using namespace llvm;3536static cl::37opt<bool> DisableMIPeephole("disable-bpf-peephole", cl::Hidden,38cl::desc("Disable machine peepholes for BPF"));3940extern "C" LLVM_EXTERNAL_VISIBILITY void LLVMInitializeBPFTarget() {41// Register the target.42RegisterTargetMachine<BPFTargetMachine> X(getTheBPFleTarget());43RegisterTargetMachine<BPFTargetMachine> Y(getTheBPFbeTarget());44RegisterTargetMachine<BPFTargetMachine> Z(getTheBPFTarget());4546PassRegistry &PR = *PassRegistry::getPassRegistry();47initializeGlobalISel(PR);48initializeBPFCheckAndAdjustIRPass(PR);49initializeBPFMIPeepholePass(PR);50initializeBPFDAGToDAGISelLegacyPass(PR);51}5253// DataLayout: little or big endian54static std::string computeDataLayout(const Triple &TT) {55if (TT.getArch() == Triple::bpfeb)56return "E-m:e-p:64:64-i64:64-i128:128-n32:64-S128";57else58return "e-m:e-p:64:64-i64:64-i128:128-n32:64-S128";59}6061static Reloc::Model getEffectiveRelocModel(std::optional<Reloc::Model> RM) {62return RM.value_or(Reloc::PIC_);63}6465BPFTargetMachine::BPFTargetMachine(const Target &T, const Triple &TT,66StringRef CPU, StringRef FS,67const TargetOptions &Options,68std::optional<Reloc::Model> RM,69std::optional<CodeModel::Model> CM,70CodeGenOptLevel OL, bool JIT)71: LLVMTargetMachine(T, computeDataLayout(TT), TT, CPU, FS, Options,72getEffectiveRelocModel(RM),73getEffectiveCodeModel(CM, CodeModel::Small), OL),74TLOF(std::make_unique<TargetLoweringObjectFileELF>()),75Subtarget(TT, std::string(CPU), std::string(FS), *this) {76initAsmInfo();7778BPFMCAsmInfo *MAI =79static_cast<BPFMCAsmInfo *>(const_cast<MCAsmInfo *>(AsmInfo.get()));80MAI->setDwarfUsesRelocationsAcrossSections(!Subtarget.getUseDwarfRIS());81}8283namespace {84// BPF Code Generator Pass Configuration Options.85class BPFPassConfig : public TargetPassConfig {86public:87BPFPassConfig(BPFTargetMachine &TM, PassManagerBase &PM)88: TargetPassConfig(TM, PM) {}8990BPFTargetMachine &getBPFTargetMachine() const {91return getTM<BPFTargetMachine>();92}9394void addIRPasses() override;95bool addInstSelector() override;96void addMachineSSAOptimization() override;97void addPreEmitPass() override;9899bool addIRTranslator() override;100bool addLegalizeMachineIR() override;101bool addRegBankSelect() override;102bool addGlobalInstructionSelect() override;103};104}105106TargetPassConfig *BPFTargetMachine::createPassConfig(PassManagerBase &PM) {107return new BPFPassConfig(*this, PM);108}109110static Expected<bool> parseBPFPreserveStaticOffsetOptions(StringRef Params) {111return PassBuilder::parseSinglePassOption(Params, "allow-partial",112"BPFPreserveStaticOffsetPass");113}114115void BPFTargetMachine::registerPassBuilderCallbacks(PassBuilder &PB) {116#define GET_PASS_REGISTRY "BPFPassRegistry.def"117#include "llvm/Passes/TargetPassRegistry.inc"118119PB.registerPipelineStartEPCallback(120[=](ModulePassManager &MPM, OptimizationLevel) {121FunctionPassManager FPM;122FPM.addPass(BPFPreserveStaticOffsetPass(true));123FPM.addPass(BPFAbstractMemberAccessPass(this));124FPM.addPass(BPFPreserveDITypePass());125FPM.addPass(BPFIRPeepholePass());126MPM.addPass(createModuleToFunctionPassAdaptor(std::move(FPM)));127});128PB.registerPeepholeEPCallback([=](FunctionPassManager &FPM,129OptimizationLevel Level) {130FPM.addPass(SimplifyCFGPass(SimplifyCFGOptions().hoistCommonInsts(true)));131FPM.addPass(BPFASpaceCastSimplifyPass());132});133PB.registerScalarOptimizerLateEPCallback(134[=](FunctionPassManager &FPM, OptimizationLevel Level) {135// Run this after loop unrolling but before136// SimplifyCFGPass(... .sinkCommonInsts(true))137FPM.addPass(BPFPreserveStaticOffsetPass(false));138});139PB.registerPipelineEarlySimplificationEPCallback(140[=](ModulePassManager &MPM, OptimizationLevel) {141MPM.addPass(BPFAdjustOptPass());142});143}144145void BPFPassConfig::addIRPasses() {146addPass(createAtomicExpandLegacyPass());147addPass(createBPFCheckAndAdjustIR());148149TargetPassConfig::addIRPasses();150}151152TargetTransformInfo153BPFTargetMachine::getTargetTransformInfo(const Function &F) const {154return TargetTransformInfo(BPFTTIImpl(this, F));155}156157// Install an instruction selector pass using158// the ISelDag to gen BPF code.159bool BPFPassConfig::addInstSelector() {160addPass(createBPFISelDag(getBPFTargetMachine()));161162return false;163}164165void BPFPassConfig::addMachineSSAOptimization() {166addPass(createBPFMISimplifyPatchablePass());167168// The default implementation must be called first as we want eBPF169// Peephole ran at last.170TargetPassConfig::addMachineSSAOptimization();171172const BPFSubtarget *Subtarget = getBPFTargetMachine().getSubtargetImpl();173if (!DisableMIPeephole) {174if (Subtarget->getHasAlu32())175addPass(createBPFMIPeepholePass());176}177}178179void BPFPassConfig::addPreEmitPass() {180addPass(createBPFMIPreEmitCheckingPass());181if (getOptLevel() != CodeGenOptLevel::None)182if (!DisableMIPeephole)183addPass(createBPFMIPreEmitPeepholePass());184}185186bool BPFPassConfig::addIRTranslator() {187addPass(new IRTranslator());188return false;189}190191bool BPFPassConfig::addLegalizeMachineIR() {192addPass(new Legalizer());193return false;194}195196bool BPFPassConfig::addRegBankSelect() {197addPass(new RegBankSelect());198return false;199}200201bool BPFPassConfig::addGlobalInstructionSelect() {202addPass(new InstructionSelect(getOptLevel()));203return false;204}205206207