1 /*========================== begin_copyright_notice ============================
2 
3 Copyright (C) 2017-2021 Intel Corporation
4 
5 SPDX-License-Identifier: MIT
6 
7 ============================= end_copyright_notice ===========================*/
8 
9 #include "Compiler/CISACodeGen/PositionDepAnalysis.hpp"
10 #include "GenISAIntrinsics/GenIntrinsicInst.h"
11 #include "Compiler/CodeGenPublic.h"
12 #include "Compiler/IGCPassSupport.h"
13 using namespace IGC;
14 using namespace llvm;
15 
16 char PositionDepAnalysis::ID = 0;
17 #define PASS_FLAG "PositionDepAnalysis"
18 #define PASS_DESCRIPTION "Pos"
19 #define PASS_CFG_ONLY true
20 #define PASS_ANALYSIS true
21 IGC_INITIALIZE_PASS_BEGIN(PositionDepAnalysis, PASS_FLAG, PASS_DESCRIPTION, PASS_CFG_ONLY, PASS_ANALYSIS)
22 IGC_INITIALIZE_PASS_DEPENDENCY(WIAnalysis)
23 IGC_INITIALIZE_PASS_DEPENDENCY(DominatorTreeWrapperPass)
24 IGC_INITIALIZE_PASS_DEPENDENCY(LoopInfoWrapperPass)
25 IGC_INITIALIZE_PASS_DEPENDENCY(MetaDataUtilsWrapper)
26 IGC_INITIALIZE_PASS_END(PositionDepAnalysis, PASS_FLAG, PASS_DESCRIPTION, PASS_CFG_ONLY, PASS_ANALYSIS)
27 
28 namespace IGC
29 {
30 
31 
PositionDepAnalysis()32     PositionDepAnalysis::PositionDepAnalysis() : FunctionPass(ID)
33     {
34         initializePositionDepAnalysisPass(*PassRegistry::getPassRegistry());
35     }
36 
runOnFunction(llvm::Function & F)37     bool PositionDepAnalysis::runOnFunction(llvm::Function& F)
38     {
39         CodeGenContext* ctx = getAnalysis<CodeGenContextWrapper>().getCodeGenContext();
40         if (ctx->type == ShaderType::VERTEX_SHADER && ctx->m_DriverInfo.PreventZFighting())
41         {
42             visit(F);
43         }
44         return false;
45     }
46 
visitCallInst(CallInst & I)47     void PositionDepAnalysis::visitCallInst(CallInst& I)
48     {
49         if (GenIntrinsicInst * intr = dyn_cast<GenIntrinsicInst>(&I))
50         {
51             if (intr->getIntrinsicID() == GenISAIntrinsic::GenISA_URBWrite)
52             {
53                 if (ConstantInt * index = dyn_cast<ConstantInt>(intr->getOperand(0)))
54                 {
55                     // position is written at offset 0 or 1
56                     if (index->isZero() || index->isOne())
57                     {
58                         unsigned int baseSourceIndex = index->isZero() ? 6 : 2;
59                         for (unsigned int i = 0; i < 4; i++)
60                         {
61                             if (Instruction * instDep = dyn_cast<Instruction>(intr->getOperand(baseSourceIndex + i)))
62                             {
63                                 UpdateDependency(instDep);
64                             }
65                         }
66                     }
67                 }
68             }
69         }
70     }
71 
UpdateDependency(Instruction * inst)72     void PositionDepAnalysis::UpdateDependency(Instruction* inst)
73     {
74         auto it = m_PositionDep.insert(inst);
75         if (it.second)
76         {
77             for (unsigned int i = 0; i < inst->getNumOperands(); ++i)
78             {
79                 if (Instruction * srcInst = dyn_cast<Instruction>(inst->getOperand(i)))
80                 {
81                     UpdateDependency(srcInst);
82                 }
83             }
84         }
85     }
PositionDependsOnInst(Instruction * inst)86     bool PositionDepAnalysis::PositionDependsOnInst(Instruction* inst)
87     {
88         return m_PositionDep.find(inst) != m_PositionDep.end();
89     }
90 
91 
92 
93 
94 }
95