1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120
|
/*========================== begin_copyright_notice ============================
Copyright (C) 2018-2021 Intel Corporation
SPDX-License-Identifier: MIT
============================= end_copyright_notice ===========================*/
#include "Compiler/Optimizer/OpenCLPasses/WIFuncs/WIFuncsAnalysis.hpp"
#include "FoldKnownWorkGroupSizes.h"
#include "Compiler/IGCPassSupport.h"
#include "Compiler/CodeGenPublic.h"
#include "Compiler/MetaDataApi/MetaDataApi.h"
#include "LLVMWarningsPush.hpp"
#include "llvm/IR/Function.h"
#include <llvm/IR/InstVisitor.h>
#include "LLVMWarningsPop.hpp"
#include "common/igc_regkeys.hpp"
using namespace llvm;
using namespace IGC;
using namespace IGCMD;
namespace IGC
{
class FoldKnownWorkGroupSizes : public llvm::FunctionPass, public llvm::InstVisitor<FoldKnownWorkGroupSizes>
{
private:
CodeGenContext* ctx = nullptr;
bool RequirePayloadHeader = true;
public:
static char ID;
FoldKnownWorkGroupSizes() : FunctionPass(ID) {}
bool runOnFunction(llvm::Function& F) override;
void visitCallInst(llvm::CallInst& I);
llvm::StringRef getPassName() const override {
return "FoldKnownWorkGroupSizes";
}
void getAnalysisUsage(llvm::AnalysisUsage& AU) const override
{
AU.addRequired<IGC::CodeGenContextWrapper>();
}
};
bool m_changed = false;
char FoldKnownWorkGroupSizes::ID = 0;
#define PASS_FLAG "igc-fold-workgroup-sizes"
#define PASS_DESCRIPTION "Fold global offset and enqueued local sizes"
#define PASS_CFG_ONLY false
#define PASS_ANALYSIS false
IGC_INITIALIZE_PASS_BEGIN(FoldKnownWorkGroupSizes, PASS_FLAG, PASS_DESCRIPTION, PASS_CFG_ONLY, PASS_ANALYSIS)
IGC_INITIALIZE_PASS_END(FoldKnownWorkGroupSizes, PASS_FLAG, PASS_DESCRIPTION, PASS_CFG_ONLY, PASS_ANALYSIS)
}
bool FoldKnownWorkGroupSizes::runOnFunction(Function& F)
{
ctx = getAnalysis<CodeGenContextWrapper>().getCodeGenContext();
RequirePayloadHeader = ctx->m_DriverInfo.RequirePayloadHeader();
visit(F);
return m_changed;
}
void FoldKnownWorkGroupSizes::visitCallInst(llvm::CallInst& I)
{
Function* function = I.getParent()->getParent();
Module* module = function->getParent();
Function* calledFunction = I.getCalledFunction();
if (calledFunction == nullptr)
{
return;
}
StringRef funcName = calledFunction->getName();
if (funcName.equals(WIFuncsAnalysis::GET_GLOBAL_OFFSET) &&
ctx->getModuleMetaData()->compOpt.replaceGlobalOffsetsByZero)
{
if (calledFunction->getReturnType() == Type::getInt32Ty(module->getContext()))
{
ConstantInt* IntZero = ConstantInt::get(Type::getInt32Ty(module->getContext()), 0);
I.replaceAllUsesWith(IntZero);
if (!RequirePayloadHeader)
I.eraseFromParent();
m_changed = true;
}
}
else if (funcName.equals(WIFuncsAnalysis::GET_ENQUEUED_LOCAL_SIZE))
{
auto Dims = IGCMetaDataHelper::getThreadGroupDims(
*ctx->getMetaDataUtils(),
I.getFunction());
if (!Dims)
return;
IRBuilder<> IRB(&I);
auto* CV = ConstantDataVector::get(I.getContext(), *Dims);
auto* Dim = I.getArgOperand(0);
auto* EE = IRB.CreateExtractElement(CV, Dim, "enqueuedLocalSize");
I.replaceAllUsesWith(EE);
// TODO: erase when patch token is not required
//I.eraseFromParent();
m_changed = true;
}
}
namespace IGC
{
llvm::FunctionPass* CreateFoldKnownWorkGroupSizes()
{
return new FoldKnownWorkGroupSizes();
}
}
|