ClearBlue
CBAccessPath.h
1 /*
2  * This file defines a full access path used in cb-check
3  *
4  * Created on: May 26, 2016
5  * Author: Zhou Jinguo
6  */
7 
8 #ifndef IR_SEG_CBAccessPath_H
9 #define IR_SEG_CBAccessPath_H
10 
11 #include <llvm/IR/Value.h>
12 
13 #include "Platform/Arch/CBTypes.h"
14 #include "Utils/ADT/kvec.h"
15 
16 using namespace llvm;
17 
18 // This class defines the access path for SEG Nodes
19 // Currently used for pseudo-inputs and pseudo outputs of function
20 // Note: Offsets are stored in a reverse way for better efficiency
21 // For example arg2->4->8->0 is abstracted as base_ptr=arg2, offsets=[0,8,4]
22 class CBAccessPath {
23  friend class SEGSerializer;
24  friend class SEGHash;
25 
26 private:
27  kvec<pp_offset_t> offsets;
28  Value *base_ptr;
29 
30  bool is_base_ptr_from_return;
31 
32 public:
33  CBAccessPath() {
34  base_ptr = nullptr;
35  is_base_ptr_from_return = false;
36  }
37  ~CBAccessPath() {}
38 
39  // Adding one level to the Access Path
40  // e.g. arg->8 => base_ptr->offset->8 where arg is base_ptr->offset
41  void add_level(Value *base_ptr, pp_offset_t offset,
42  bool is_from_return = false) {
43  this->base_ptr = base_ptr;
44  offsets.push_back(offset);
45  this->is_base_ptr_from_return = is_from_return;
46  }
47 
48  // Adding one level to the Access Path
49  // e.g. arg->8 => base_ptr->(8-offset) where arg points to base_ptr->offset
50  void reset_cur_level(Value *base_ptr, pp_offset_t offset,
51  bool is_from_return = false) {
52  if (!offsets.empty()) {
53  this->base_ptr = base_ptr;
54  offsets.back() -= offset;
55  this->is_base_ptr_from_return = is_from_return;
56  }
57  }
58 
59  // reset the Assess Path as a direct access to base_ptr
60  void reset(Value *base_ptr, bool is_from_return = false) {
61  offsets.clear();
62  this->base_ptr = base_ptr;
63  this->is_base_ptr_from_return = is_from_return;
64  }
65 
66  // reset the Assess Path as to the argument access path
67  void reset(const CBAccessPath &ap) {
68  offsets.clear();
69  offsets.push_back(ap.offsets);
70  this->base_ptr = ap.base_ptr;
71  this->is_base_ptr_from_return = ap.is_base_ptr_from_return;
72  }
73 
74  int get_depth() const { return offsets.size(); }
75 
76  pp_offset_t get_offset(int idx) const {
77  // The offset is added in a reversed way, i.e. arg->0->4->8 is stored as
78  // [8,4,0] This is because that push_back() is much faster than push_frount
79  return offsets[get_depth() - idx - 1];
80  }
81 
82  Value *get_base_ptr() const { return base_ptr; }
83 
84  // return true if the ap roots from function return
85  bool is_from_return() const { return is_base_ptr_from_return; }
86 };
87 
88 #endif /* IR_SEG_CBAccessPath_H */
CBAccessPath
Definition: CBAccessPath.h:22