Coverage Report

Created: 2019-07-24 05:18

/Users/buildslave/jenkins/workspace/clang-stage2-coverage-R/llvm/lib/Transforms/Scalar/Reg2Mem.cpp
Line
Count
Source (jump to first uncovered line)
1
//===- Reg2Mem.cpp - Convert registers to allocas -------------------------===//
2
//
3
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4
// See https://llvm.org/LICENSE.txt for license information.
5
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6
//
7
//===----------------------------------------------------------------------===//
8
//
9
// This file demotes all registers to memory references.  It is intended to be
10
// the inverse of PromoteMemoryToRegister.  By converting to loads, the only
11
// values live across basic blocks are allocas and loads before phi nodes.
12
// It is intended that this should make CFG hacking much easier.
13
// To make later hacking easier, the entry block is split into two, such that
14
// all introduced allocas and nothing else are in the entry block.
15
//
16
//===----------------------------------------------------------------------===//
17
18
#include "llvm/ADT/Statistic.h"
19
#include "llvm/Transforms/Utils/Local.h"
20
#include "llvm/IR/BasicBlock.h"
21
#include "llvm/IR/CFG.h"
22
#include "llvm/IR/Function.h"
23
#include "llvm/IR/Instructions.h"
24
#include "llvm/IR/LLVMContext.h"
25
#include "llvm/IR/Module.h"
26
#include "llvm/Pass.h"
27
#include "llvm/Transforms/Scalar.h"
28
#include "llvm/Transforms/Utils.h"
29
#include <list>
30
using namespace llvm;
31
32
#define DEBUG_TYPE "reg2mem"
33
34
STATISTIC(NumRegsDemoted, "Number of registers demoted");
35
STATISTIC(NumPhisDemoted, "Number of phi-nodes demoted");
36
37
namespace {
38
  struct RegToMem : public FunctionPass {
39
    static char ID; // Pass identification, replacement for typeid
40
1
    RegToMem() : FunctionPass(ID) {
41
1
      initializeRegToMemPass(*PassRegistry::getPassRegistry());
42
1
    }
43
44
1
    void getAnalysisUsage(AnalysisUsage &AU) const override {
45
1
      AU.addRequiredID(BreakCriticalEdgesID);
46
1
      AU.addPreservedID(BreakCriticalEdgesID);
47
1
    }
48
49
29
    bool valueEscapes(const Instruction *Inst) const {
50
29
      const BasicBlock *BB = Inst->getParent();
51
29
      for (const User *U : Inst->users()) {
52
2
        const Instruction *UI = cast<Instruction>(U);
53
2
        if (UI->getParent() != BB || 
isa<PHINode>(UI)0
)
54
2
          return true;
55
2
      }
56
29
      
return false27
;
57
29
    }
58
59
    bool runOnFunction(Function &F) override;
60
  };
61
}
62
63
char RegToMem::ID = 0;
64
36.0k
INITIALIZE_PASS_BEGIN(RegToMem, "reg2mem", "Demote all values to stack slots",
65
36.0k
                false, false)
66
36.0k
INITIALIZE_PASS_DEPENDENCY(BreakCriticalEdges)
67
36.0k
INITIALIZE_PASS_END(RegToMem, "reg2mem", "Demote all values to stack slots",
68
                false, false)
69
70
1
bool RegToMem::runOnFunction(Function &F) {
71
1
  if (F.isDeclaration() || skipFunction(F))
72
0
    return false;
73
1
74
1
  // Insert all new allocas into entry block.
75
1
  BasicBlock *BBEntry = &F.getEntryBlock();
76
1
  assert(pred_empty(BBEntry) &&
77
1
         "Entry block to function must not have predecessors!");
78
1
79
1
  // Find first non-alloca instruction and create insertion point. This is
80
1
  // safe if block is well-formed: it always have terminator, otherwise
81
1
  // we'll get and assertion.
82
1
  BasicBlock::iterator I = BBEntry->begin();
83
1
  while (isa<AllocaInst>(I)) 
++I0
;
84
1
85
1
  CastInst *AllocaInsertionPoint = new BitCastInst(
86
1
      Constant::getNullValue(Type::getInt32Ty(F.getContext())),
87
1
      Type::getInt32Ty(F.getContext()), "reg2mem alloca point", &*I);
88
1
89
1
  // Find the escaped instructions. But don't create stack slots for
90
1
  // allocas in entry block.
91
1
  std::list<Instruction*> WorkList;
92
1
  for (BasicBlock &ibb : F)
93
49
    
for (BasicBlock::iterator iib = ibb.begin(), iie = ibb.end(); 20
iib != iie;
94
29
         ++iib) {
95
29
      if (!(isa<AllocaInst>(iib) && 
iib->getParent() == BBEntry0
) &&
96
29
          valueEscapes(&*iib)) {
97
2
        WorkList.push_front(&*iib);
98
2
      }
99
29
    }
100
1
101
1
  // Demote escaped instructions
102
1
  NumRegsDemoted += WorkList.size();
103
1
  for (Instruction *ilb : WorkList)
104
2
    DemoteRegToStack(*ilb, false, AllocaInsertionPoint);
105
1
106
1
  WorkList.clear();
107
1
108
1
  // Find all phi's
109
1
  for (BasicBlock &ibb : F)
110
55
    
for (BasicBlock::iterator iib = ibb.begin(), iie = ibb.end(); 20
iib != iie;
111
35
         ++iib)
112
35
      if (isa<PHINode>(iib))
113
2
        WorkList.push_front(&*iib);
114
1
115
1
  // Demote phi nodes
116
1
  NumPhisDemoted += WorkList.size();
117
1
  for (Instruction *ilb : WorkList)
118
2
    DemotePHIToStack(cast<PHINode>(ilb), AllocaInsertionPoint);
119
1
120
1
  return true;
121
1
}
122
123
124
// createDemoteRegisterToMemory - Provide an entry point to create this pass.
125
char &llvm::DemoteRegisterToMemoryID = RegToMem::ID;
126
0
FunctionPass *llvm::createDemoteRegisterToMemoryPass() {
127
0
  return new RegToMem();
128
0
}