llvm.org GIT mirror llvm / 18ebd48
[stackprotector] Refactor the StackProtector pass from a single .cpp file into StackProtector.h and StackProtector.cpp. No functionality change. Future patches will add analysis which will be used in other passes (PEI, StackSlot). The end goal is to support ssp-strong stack layout rules. WIP. Differential Revision: http://llvm-reviews.chandlerc.com/D1521 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@191570 91177308-0d34-0410-b5e6-96231b3b80d8 Josh Magee 7 years ago
2 changed file(s) with 98 addition(s) and 70 deletion(s). Raw diff Collapse all Expand all
0 //===-- StackProtector.h - Stack Protector Insertion ----------------------===//
1 //
2 // The LLVM Compiler Infrastructure
3 //
4 // This file is distributed under the University of Illinois Open Source
5 // License. See LICENSE.TXT for details.
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This pass inserts stack protectors into functions which need them. A variable
10 // with a random value in it is stored onto the stack before the local variables
11 // are allocated. Upon exiting the block, the stored value is checked. If it's
12 // changed, then there was some sort of violation and the program aborts.
13 //
14 //===----------------------------------------------------------------------===//
15
16 #ifndef LLVM_CODEGEN_STACKPROTECTOR_H
17 #define LLVM_CODEGEN_STACKPROTECTOR_H
18
19 #include "llvm/ADT/SmallPtrSet.h"
20 #include "llvm/ADT/Triple.h"
21 #include "llvm/Pass.h"
22 #include "llvm/Target/TargetLowering.h"
23
24 namespace llvm {
25 class DominatorTree;
26 class Function;
27 class Module;
28 class PHINode;
29
30 class StackProtector : public FunctionPass {
31 const TargetMachine *TM;
32
33 /// TLI - Keep a pointer of a TargetLowering to consult for determining
34 /// target type sizes.
35 const TargetLoweringBase *TLI;
36 const Triple Trip;
37
38 Function *F;
39 Module *M;
40
41 DominatorTree *DT;
42
43 /// \brief The minimum size of buffers that will receive stack smashing
44 /// protection when -fstack-protection is used.
45 unsigned SSPBufferSize;
46
47 /// VisitedPHIs - The set of PHI nodes visited when determining
48 /// if a variable's reference has been taken. This set
49 /// is maintained to ensure we don't visit the same PHI node multiple
50 /// times.
51 SmallPtrSet VisitedPHIs;
52
53 /// InsertStackProtectors - Insert code into the prologue and epilogue of
54 /// the function.
55 ///
56 /// - The prologue code loads and stores the stack guard onto the stack.
57 /// - The epilogue checks the value stored in the prologue against the
58 /// original value. It calls __stack_chk_fail if they differ.
59 bool InsertStackProtectors();
60
61 /// CreateFailBB - Create a basic block to jump to when the stack protector
62 /// check fails.
63 BasicBlock *CreateFailBB();
64
65 /// ContainsProtectableArray - Check whether the type either is an array or
66 /// contains an array of sufficient size so that we need stack protectors
67 /// for it.
68 bool ContainsProtectableArray(Type *Ty, bool Strong = false,
69 bool InStruct = false) const;
70
71 /// \brief Check whether a stack allocation has its address taken.
72 bool HasAddressTaken(const Instruction *AI);
73
74 /// RequiresStackProtector - Check whether or not this function needs a
75 /// stack protector based upon the stack protector level.
76 bool RequiresStackProtector();
77 public:
78 static char ID; // Pass identification, replacement for typeid.
79 StackProtector() : FunctionPass(ID), TM(0), TLI(0), SSPBufferSize(0) {
80 initializeStackProtectorPass(*PassRegistry::getPassRegistry());
81 }
82 StackProtector(const TargetMachine *TM)
83 : FunctionPass(ID), TM(TM), TLI(0), Trip(TM->getTargetTriple()),
84 SSPBufferSize(8) {
85 initializeStackProtectorPass(*PassRegistry::getPassRegistry());
86 }
87
88 virtual void getAnalysisUsage(AnalysisUsage &AU) const {
89 AU.addPreserved();
90 }
91
92 virtual bool runOnFunction(Function &Fn);
93 };
94 } // end namespace llvm
95
96 #endif // LLVM_CODEGEN_STACKPROTECTOR_H
1414 //===----------------------------------------------------------------------===//
1515
1616 #define DEBUG_TYPE "stack-protector"
17 #include "llvm/CodeGen/StackProtector.h"
1718 #include "llvm/CodeGen/Analysis.h"
1819 #include "llvm/CodeGen/Passes.h"
1920 #include "llvm/ADT/SmallPtrSet.h"
2021 #include "llvm/ADT/Statistic.h"
21 #include "llvm/ADT/Triple.h"
2222 #include "llvm/Analysis/Dominators.h"
2323 #include "llvm/Analysis/ValueTracking.h"
2424 #include "llvm/IR/Attributes.h"
3333 #include "llvm/IR/IntrinsicInst.h"
3434 #include "llvm/IR/Intrinsics.h"
3535 #include "llvm/IR/Module.h"
36 #include "llvm/Pass.h"
3736 #include "llvm/Support/CommandLine.h"
38 #include "llvm/Target/TargetLowering.h"
3937 #include
4038 using namespace llvm;
4139
4644 static cl::opt
4745 EnableSelectionDAGSP("enable-selectiondag-sp", cl::init(true),
4846 cl::Hidden);
49
50 namespace {
51 class StackProtector : public FunctionPass {
52 const TargetMachine *TM;
53
54 /// TLI - Keep a pointer of a TargetLowering to consult for determining
55 /// target type sizes.
56 const TargetLoweringBase *TLI;
57 const Triple Trip;
58
59 Function *F;
60 Module *M;
61
62 DominatorTree *DT;
63
64 /// \brief The minimum size of buffers that will receive stack smashing
65 /// protection when -fstack-protection is used.
66 unsigned SSPBufferSize;
67
68 /// VisitedPHIs - The set of PHI nodes visited when determining
69 /// if a variable's reference has been taken. This set
70 /// is maintained to ensure we don't visit the same PHI node multiple
71 /// times.
72 SmallPtrSet VisitedPHIs;
73
74 /// InsertStackProtectors - Insert code into the prologue and epilogue of
75 /// the function.
76 ///
77 /// - The prologue code loads and stores the stack guard onto the stack.
78 /// - The epilogue checks the value stored in the prologue against the
79 /// original value. It calls __stack_chk_fail if they differ.
80 bool InsertStackProtectors();
81
82 /// CreateFailBB - Create a basic block to jump to when the stack protector
83 /// check fails.
84 BasicBlock *CreateFailBB();
85
86 /// ContainsProtectableArray - Check whether the type either is an array or
87 /// contains an array of sufficient size so that we need stack protectors
88 /// for it.
89 bool ContainsProtectableArray(Type *Ty, bool Strong = false,
90 bool InStruct = false) const;
91
92 /// \brief Check whether a stack allocation has its address taken.
93 bool HasAddressTaken(const Instruction *AI);
94
95 /// RequiresStackProtector - Check whether or not this function needs a
96 /// stack protector based upon the stack protector level.
97 bool RequiresStackProtector();
98 public:
99 static char ID; // Pass identification, replacement for typeid.
100 StackProtector() : FunctionPass(ID), TM(0), TLI(0), SSPBufferSize(0) {
101 initializeStackProtectorPass(*PassRegistry::getPassRegistry());
102 }
103 StackProtector(const TargetMachine *TM)
104 : FunctionPass(ID), TM(TM), TLI(0), Trip(TM->getTargetTriple()),
105 SSPBufferSize(8) {
106 initializeStackProtectorPass(*PassRegistry::getPassRegistry());
107 }
108
109 virtual void getAnalysisUsage(AnalysisUsage &AU) const {
110 AU.addPreserved();
111 }
112
113 virtual bool runOnFunction(Function &Fn);
114 };
115 } // end anonymous namespace
11647
11748 char StackProtector::ID = 0;
11849 INITIALIZE_PASS(StackProtector, "stack-protector",