LLVM  14.0.0git
GetElementPtrTypeIterator.h
Go to the documentation of this file.
1 //===- GetElementPtrTypeIterator.h ------------------------------*- C++ -*-===//
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 implements an iterator for walking through the types indexed by
10 // getelementptr instructions.
11 //
12 //===----------------------------------------------------------------------===//
13 
14 #ifndef LLVM_IR_GETELEMENTPTRTYPEITERATOR_H
15 #define LLVM_IR_GETELEMENTPTRTYPEITERATOR_H
16 
17 #include "llvm/ADT/ArrayRef.h"
18 #include "llvm/ADT/PointerUnion.h"
19 #include "llvm/IR/DerivedTypes.h"
20 #include "llvm/IR/Operator.h"
21 #include "llvm/IR/User.h"
22 #include "llvm/Support/Casting.h"
23 #include <cassert>
24 #include <cstddef>
25 #include <cstdint>
26 #include <iterator>
27 
28 namespace llvm {
29 
30 template <typename ItTy = User::const_op_iterator>
32 
33  ItTy OpIt;
35  enum : uint64_t { Unbounded = -1ull };
36  uint64_t NumElements = Unbounded;
37 
38  generic_gep_type_iterator() = default;
39 
40 public:
41  using iterator_category = std::forward_iterator_tag;
42  using value_type = Type *;
43  using difference_type = std::ptrdiff_t;
44  using pointer = value_type *;
45  using reference = value_type &;
46 
49  I.CurTy = Ty;
50  I.OpIt = It;
51  return I;
52  }
53 
56  I.OpIt = It;
57  return I;
58  }
59 
60  bool operator==(const generic_gep_type_iterator &x) const {
61  return OpIt == x.OpIt;
62  }
63 
64  bool operator!=(const generic_gep_type_iterator &x) const {
65  return !operator==(x);
66  }
67 
68  // FIXME: Make this the iterator's operator*() after the 4.0 release.
69  // operator*() had a different meaning in earlier releases, so we're
70  // temporarily not giving this iterator an operator*() to avoid a subtle
71  // semantics break.
72  Type *getIndexedType() const {
73  if (auto *T = CurTy.dyn_cast<Type *>())
74  return T;
75  return CurTy.get<StructType *>()->getTypeAtIndex(getOperand());
76  }
77 
78  Value *getOperand() const { return const_cast<Value *>(&**OpIt); }
79 
81  Type *Ty = getIndexedType();
82  if (auto *ATy = dyn_cast<ArrayType>(Ty)) {
83  CurTy = ATy->getElementType();
84  NumElements = ATy->getNumElements();
85  } else if (auto *VTy = dyn_cast<VectorType>(Ty)) {
86  CurTy = VTy->getElementType();
87  if (isa<ScalableVectorType>(VTy))
88  NumElements = Unbounded;
89  else
90  NumElements = cast<FixedVectorType>(VTy)->getNumElements();
91  } else
92  CurTy = dyn_cast<StructType>(Ty);
93  ++OpIt;
94  return *this;
95  }
96 
97  generic_gep_type_iterator operator++(int) { // Postincrement
99  ++*this;
100  return tmp;
101  }
102 
103  // All of the below API is for querying properties of the "outer type", i.e.
104  // the type that contains the indexed type. Most of the time this is just
105  // the type that was visited immediately prior to the indexed type, but for
106  // the first element this is an unbounded array of the GEP's source element
107  // type, for which there is no clearly corresponding IR type (we've
108  // historically used a pointer type as the outer type in this case, but
109  // pointers will soon lose their element type).
110  //
111  // FIXME: Most current users of this class are just interested in byte
112  // offsets (a few need to know whether the outer type is a struct because
113  // they are trying to replace a constant with a variable, which is only
114  // legal for arrays, e.g. canReplaceOperandWithVariable in SimplifyCFG.cpp);
115  // we should provide a more minimal API here that exposes not much more than
116  // that.
117 
118  bool isStruct() const { return CurTy.is<StructType *>(); }
119  bool isSequential() const { return CurTy.is<Type *>(); }
120 
121  StructType *getStructType() const { return CurTy.get<StructType *>(); }
122 
124  return CurTy.dyn_cast<StructType *>();
125  }
126 
127  bool isBoundedSequential() const {
128  return isSequential() && NumElements != Unbounded;
129  }
130 
133  return NumElements;
134  }
135 };
136 
138 
140  auto *GEPOp = cast<GEPOperator>(GEP);
142  GEPOp->getSourceElementType(),
143  GEP->op_begin() + 1);
144  }
145 
147  return gep_type_iterator::end(GEP->op_end());
148  }
149 
151  auto &GEPOp = cast<GEPOperator>(GEP);
153  GEPOp.getSourceElementType(),
154  GEP.op_begin() + 1);
155  }
156 
158  return gep_type_iterator::end(GEP.op_end());
159  }
160 
161  template<typename T>
162  inline generic_gep_type_iterator<const T *>
164  return generic_gep_type_iterator<const T *>::begin(Op0, A.begin());
165  }
166 
167  template<typename T>
168  inline generic_gep_type_iterator<const T *>
169  gep_type_end(Type * /*Op0*/, ArrayRef<T> A) {
171  }
172 
173 } // end namespace llvm
174 
175 #endif // LLVM_IR_GETELEMENTPTRTYPEITERATOR_H
llvm::generic_gep_type_iterator::operator++
generic_gep_type_iterator operator++(int)
Definition: GetElementPtrTypeIterator.h:97
llvm
---------------------— PointerInfo ------------------------------------—
Definition: AllocatorList.h:23
llvm::generic_gep_type_iterator::operator!=
bool operator!=(const generic_gep_type_iterator &x) const
Definition: GetElementPtrTypeIterator.h:64
llvm::generic_gep_type_iterator
Definition: GetElementPtrTypeIterator.h:31
llvm::generic_gep_type_iterator::operator==
bool operator==(const generic_gep_type_iterator &x) const
Definition: GetElementPtrTypeIterator.h:60
llvm::generic_gep_type_iterator::getSequentialNumElements
uint64_t getSequentialNumElements() const
Definition: GetElementPtrTypeIterator.h:131
llvm::Type
The instances of the Type class are immutable: once they are created, they are never changed.
Definition: Type.h:45
T
#define T
Definition: Mips16ISelLowering.cpp:341
Operator.h
tmp
alloca< 16 x float >, align 16 %tmp2=alloca< 16 x float >, align 16 store< 16 x float > %A,< 16 x float > *%tmp %s=bitcast< 16 x float > *%tmp to i8 *%s2=bitcast< 16 x float > *%tmp2 to i8 *call void @llvm.memcpy.i64(i8 *%s, i8 *%s2, i64 64, i32 16) %R=load< 16 x float > *%tmp2 ret< 16 x float > %R } declare void @llvm.memcpy.i64(i8 *nocapture, i8 *nocapture, i64, i32) nounwind which compiles to:_foo:subl $140, %esp movaps %xmm3, 112(%esp) movaps %xmm2, 96(%esp) movaps %xmm1, 80(%esp) movaps %xmm0, 64(%esp) movl 60(%esp), %eax movl %eax, 124(%esp) movl 56(%esp), %eax movl %eax, 120(%esp) movl 52(%esp), %eax< many many more 32-bit copies > movaps(%esp), %xmm0 movaps 16(%esp), %xmm1 movaps 32(%esp), %xmm2 movaps 48(%esp), %xmm3 addl $140, %esp ret On Nehalem, it may even be cheaper to just use movups when unaligned than to fall back to lower-granularity chunks. Implement processor-specific optimizations for parity with GCC on these processors. GCC does two optimizations:1. ix86_pad_returns inserts a noop before ret instructions if immediately preceded by a conditional branch or is the target of a jump. 2. ix86_avoid_jump_misspredicts inserts noops in cases where a 16-byte block of code contains more than 3 branches. The first one is done for all AMDs, Core2, and "Generic" The second one is done for:Atom, Pentium Pro, all AMDs, Pentium 4, Nocona, Core 2, and "Generic" Testcase:int x(int a) { return(a &0xf0)> >4 tmp
Definition: README.txt:1347
llvm::gep_type_begin
gep_type_iterator gep_type_begin(const User *GEP)
Definition: GetElementPtrTypeIterator.h:139
llvm::PointerUnion::get
T get() const
Returns the value of the specified pointer type.
Definition: PointerUnion.h:157
llvm::PointerUnion::is
bool is() const
Test if the Union currently holds the type matching T.
Definition: PointerUnion.h:147
llvm::gep_type_end
gep_type_iterator gep_type_end(const User *GEP)
Definition: GetElementPtrTypeIterator.h:146
llvm::generic_gep_type_iterator::iterator_category
std::forward_iterator_tag iterator_category
Definition: GetElementPtrTypeIterator.h:41
llvm::generic_gep_type_iterator::begin
static generic_gep_type_iterator begin(Type *Ty, ItTy It)
Definition: GetElementPtrTypeIterator.h:47
llvm::User
Definition: User.h:44
ItTy
llvm::generic_gep_type_iterator::getOperand
Value * getOperand() const
Definition: GetElementPtrTypeIterator.h:78
llvm::generic_gep_type_iterator::end
static generic_gep_type_iterator end(ItTy It)
Definition: GetElementPtrTypeIterator.h:54
llvm::generic_gep_type_iterator::operator++
generic_gep_type_iterator & operator++()
Definition: GetElementPtrTypeIterator.h:80
llvm::generic_gep_type_iterator::isBoundedSequential
bool isBoundedSequential() const
Definition: GetElementPtrTypeIterator.h:127
llvm::generic_gep_type_iterator::getStructTypeOrNull
StructType * getStructTypeOrNull() const
Definition: GetElementPtrTypeIterator.h:123
uint64_t
llvm::generic_gep_type_iterator::getStructType
StructType * getStructType() const
Definition: GetElementPtrTypeIterator.h:121
llvm::PointerUnion::dyn_cast
T dyn_cast() const
Returns the current pointer if it is of the specified pointer type, otherwise returns null.
Definition: PointerUnion.h:164
I
#define I(x, y, z)
Definition: MD5.cpp:59
ArrayRef.h
assert
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
llvm::generic_gep_type_iterator::getIndexedType
Type * getIndexedType() const
Definition: GetElementPtrTypeIterator.h:72
PointerUnion.h
llvm::ArrayRef
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition: APInt.h:32
llvm::StructType
Class to represent struct types.
Definition: DerivedTypes.h:213
llvm::generic_gep_type_iterator::isSequential
bool isSequential() const
Definition: GetElementPtrTypeIterator.h:119
llvm::PointerUnion
A discriminated union of two or more pointer types, with the discriminator in the low bit of the poin...
Definition: PointerUnion.h:119
Casting.h
x
TODO unsigned x
Definition: README.txt:10
User.h
llvm::generic_gep_type_iterator::isStruct
bool isStruct() const
Definition: GetElementPtrTypeIterator.h:118
DerivedTypes.h
llvm::generic_gep_type_iterator::difference_type
std::ptrdiff_t difference_type
Definition: GetElementPtrTypeIterator.h:43
GEP
Hexagon Common GEP
Definition: HexagonCommonGEP.cpp:172
llvm::Value
LLVM Value Representation.
Definition: Value.h:75