@@ -71,96 +71,6 @@ namespace sandboxir {
7171class Function ;
7272class Context ;
7373class Instruction ;
74- class User ;
75- class Value ;
76-
77- // / Represents a Def-use/Use-def edge in SandboxIR.
78- // / NOTE: Unlike llvm::Use, this is not an integral part of the use-def chains.
79- // / It is also not uniqued and is currently passed by value, so you can have
80- // / more than one sandboxir::Use objects for the same use-def edge.
81- class Use {
82- llvm::Use *LLVMUse;
83- User *Usr;
84- Context *Ctx;
85-
86- // / Don't allow the user to create a sandboxir::Use directly.
87- Use (llvm::Use *LLVMUse, User *Usr, Context &Ctx)
88- : LLVMUse(LLVMUse), Usr(Usr), Ctx(&Ctx) {}
89- Use () : LLVMUse(nullptr ), Ctx(nullptr ) {}
90-
91- friend class Value ; // For constructor
92- friend class User ; // For constructor
93- friend class OperandUseIterator ; // For constructor
94- friend class UserUseIterator ; // For accessing members
95-
96- public:
97- operator Value *() const { return get (); }
98- Value *get () const ;
99- class User *getUser () const { return Usr; }
100- unsigned getOperandNo () const ;
101- Context *getContext () const { return Ctx; }
102- bool operator ==(const Use &Other) const {
103- assert (Ctx == Other.Ctx && " Contexts differ!" );
104- return LLVMUse == Other.LLVMUse && Usr == Other.Usr ;
105- }
106- bool operator !=(const Use &Other) const { return !(*this == Other); }
107- #ifndef NDEBUG
108- void dump (raw_ostream &OS) const ;
109- void dump () const ;
110- #endif // NDEBUG
111- };
112-
113- // / Returns the operand edge when dereferenced.
114- class OperandUseIterator {
115- Use Use;
116- // / Don't let the user create a non-empty OperandUseIterator.
117- OperandUseIterator (const class Use &Use) : Use(Use) {}
118- friend class User ; // For constructor
119- #define DEF_INSTR (ID, OPC, CLASS ) friend class CLASS ; // For constructor
120- #include " llvm/SandboxIR/SandboxIRValues.def"
121-
122- public:
123- using difference_type = std::ptrdiff_t ;
124- using value_type = sandboxir::Use;
125- using pointer = value_type *;
126- using reference = value_type &;
127- using iterator_category = std::input_iterator_tag;
128-
129- OperandUseIterator () = default ;
130- value_type operator *() const ;
131- OperandUseIterator &operator ++();
132- bool operator ==(const OperandUseIterator &Other) const {
133- return Use == Other.Use ;
134- }
135- bool operator !=(const OperandUseIterator &Other) const {
136- return !(*this == Other);
137- }
138- };
139-
140- // / Returns user edge when dereferenced.
141- class UserUseIterator {
142- Use Use;
143- // / Don't let the user create a non-empty UserUseIterator.
144- UserUseIterator (const class Use &Use) : Use(Use) {}
145- friend class Value ; // For constructor
146-
147- public:
148- using difference_type = std::ptrdiff_t ;
149- using value_type = sandboxir::Use;
150- using pointer = value_type *;
151- using reference = value_type &;
152- using iterator_category = std::input_iterator_tag;
153-
154- UserUseIterator () = default ;
155- value_type operator *() const { return Use; }
156- UserUseIterator &operator ++();
157- bool operator ==(const UserUseIterator &Other) const {
158- return Use == Other.Use ;
159- }
160- bool operator !=(const UserUseIterator &Other) const {
161- return !(*this == Other);
162- }
163- };
16474
16575// / A SandboxIR Value has users. This is the base class.
16676class Value {
@@ -213,77 +123,9 @@ class Value {
213123 virtual ~Value () = default ;
214124 ClassID getSubclassID () const { return SubclassID; }
215125
216- using use_iterator = UserUseIterator;
217- using const_use_iterator = UserUseIterator;
218-
219- use_iterator use_begin ();
220- const_use_iterator use_begin () const {
221- return const_cast <Value *>(this )->use_begin ();
222- }
223- use_iterator use_end () { return use_iterator (Use (nullptr , nullptr , Ctx)); }
224- const_use_iterator use_end () const {
225- return const_cast <Value *>(this )->use_end ();
226- }
227-
228- iterator_range<use_iterator> uses () {
229- return make_range<use_iterator>(use_begin (), use_end ());
230- }
231- iterator_range<const_use_iterator> uses () const {
232- return make_range<const_use_iterator>(use_begin (), use_end ());
233- }
234-
235- // / Helper for mapped_iterator.
236- struct UseToUser {
237- User *operator ()(const Use &Use) const { return &*Use.getUser (); }
238- };
239-
240- using user_iterator = mapped_iterator<sandboxir::UserUseIterator, UseToUser>;
241- using const_user_iterator = user_iterator;
242-
243- user_iterator user_begin ();
244- user_iterator user_end () {
245- return user_iterator (Use (nullptr , nullptr , Ctx), UseToUser ());
246- }
247- const_user_iterator user_begin () const {
248- return const_cast <Value *>(this )->user_begin ();
249- }
250- const_user_iterator user_end () const {
251- return const_cast <Value *>(this )->user_end ();
252- }
253-
254- iterator_range<user_iterator> users () {
255- return make_range<user_iterator>(user_begin (), user_end ());
256- }
257- iterator_range<const_user_iterator> users () const {
258- return make_range<const_user_iterator>(user_begin (), user_end ());
259- }
260- // / \Returns the number of user edges (not necessarily to unique users).
261- // / WARNING: This is a linear-time operation.
262- unsigned getNumUses () const ;
263- // / Return true if this value has N uses or more.
264- // / This is logically equivalent to getNumUses() >= N.
265- // / WARNING: This can be expensive, as it is linear to the number of users.
266- bool hasNUsesOrMore (unsigned Num) const {
267- unsigned Cnt = 0 ;
268- for (auto It = use_begin (), ItE = use_end (); It != ItE; ++It) {
269- if (++Cnt >= Num)
270- return true ;
271- }
272- return false ;
273- }
274- // / Return true if this Value has exactly N uses.
275- bool hasNUses (unsigned Num) const {
276- unsigned Cnt = 0 ;
277- for (auto It = use_begin (), ItE = use_end (); It != ItE; ++It) {
278- if (++Cnt > Num)
279- return false ;
280- }
281- return Cnt == Num;
282- }
283-
284126 Type *getType () const { return Val->getType (); }
285127
286- Context &getContext () const { return Ctx; }
128+ Context &getContext () const ;
287129#ifndef NDEBUG
288130 // / Should crash if there is something wrong with the instruction.
289131 virtual void verify () const = 0;
@@ -332,61 +174,9 @@ class User : public Value {
332174protected:
333175 User (ClassID ID, llvm::Value *V, Context &Ctx) : Value(ID, V, Ctx) {}
334176
335- // / \Returns the Use edge that corresponds to \p OpIdx.
336- // / Note: This is the default implementation that works for instructions that
337- // / match the underlying LLVM instruction. All others should use a different
338- // / implementation.
339- Use getOperandUseDefault (unsigned OpIdx, bool Verify) const ;
340- virtual Use getOperandUseInternal (unsigned OpIdx, bool Verify) const = 0;
341- friend class OperandUseIterator ; // for getOperandUseInternal()
342-
343- // / The default implementation works only for single-LLVMIR-instruction
344- // / Users and only if they match exactly the LLVM instruction.
345- unsigned getUseOperandNoDefault (const Use &Use) const {
346- return Use.LLVMUse ->getOperandNo ();
347- }
348- // / \Returns the operand index of \p Use.
349- virtual unsigned getUseOperandNo (const Use &Use) const = 0;
350- friend unsigned Use::getOperandNo () const ; // For getUseOperandNo()
351-
352177public:
353178 // / For isa/dyn_cast.
354179 static bool classof (const Value *From);
355- using op_iterator = OperandUseIterator;
356- using const_op_iterator = OperandUseIterator;
357- using op_range = iterator_range<op_iterator>;
358- using const_op_range = iterator_range<const_op_iterator>;
359-
360- virtual op_iterator op_begin () {
361- assert (isa<llvm::User>(Val) && " Expect User value!" );
362- return op_iterator (getOperandUseInternal (0 , /* Verify=*/ false ));
363- }
364- virtual op_iterator op_end () {
365- assert (isa<llvm::User>(Val) && " Expect User value!" );
366- return op_iterator (
367- getOperandUseInternal (getNumOperands (), /* Verify=*/ false ));
368- }
369- virtual const_op_iterator op_begin () const {
370- return const_cast <User *>(this )->op_begin ();
371- }
372- virtual const_op_iterator op_end () const {
373- return const_cast <User *>(this )->op_end ();
374- }
375-
376- op_range operands () { return make_range<op_iterator>(op_begin (), op_end ()); }
377- const_op_range operands () const {
378- return make_range<const_op_iterator>(op_begin (), op_end ());
379- }
380- Value *getOperand (unsigned OpIdx) const { return getOperandUse (OpIdx).get (); }
381- // / \Returns the operand edge for \p OpIdx. NOTE: This should also work for
382- // / OpIdx == getNumOperands(), which is used for op_end().
383- Use getOperandUse (unsigned OpIdx) const {
384- return getOperandUseInternal (OpIdx, /* Verify=*/ true );
385- }
386- virtual unsigned getNumOperands () const {
387- return isa<llvm::User>(Val) ? cast<llvm::User>(Val)->getNumOperands () : 0 ;
388- }
389-
390180#ifndef NDEBUG
391181 void verify () const override {
392182 assert (isa<llvm::User>(Val) && " Expected User!" );
@@ -405,9 +195,6 @@ class Constant : public sandboxir::User {
405195 Constant (llvm::Constant *C, sandboxir::Context &SBCtx)
406196 : sandboxir::User(ClassID::Constant, C, SBCtx) {}
407197 friend class Context ; // For constructor.
408- Use getOperandUseInternal (unsigned OpIdx, bool Verify) const final {
409- return getOperandUseDefault (OpIdx, Verify);
410- }
411198
412199public:
413200 // / For isa/dyn_cast.
@@ -416,9 +203,6 @@ class Constant : public sandboxir::User {
416203 From->getSubclassID () == ClassID::Function;
417204 }
418205 sandboxir::Context &getParent () const { return getContext (); }
419- unsigned getUseOperandNo (const Use &Use) const final {
420- return getUseOperandNoDefault (Use);
421- }
422206#ifndef NDEBUG
423207 void verify () const final {
424208 assert (isa<llvm::Constant>(Val) && " Expected Constant!" );
@@ -525,17 +309,11 @@ class OpaqueInst : public sandboxir::Instruction {
525309 OpaqueInst (ClassID SubclassID, llvm::Instruction *I, sandboxir::Context &Ctx)
526310 : sandboxir::Instruction(SubclassID, Opcode::Opaque, I, Ctx) {}
527311 friend class Context ; // For constructor.
528- Use getOperandUseInternal (unsigned OpIdx, bool Verify) const final {
529- return getOperandUseDefault (OpIdx, Verify);
530- }
531312
532313public:
533314 static bool classof (const sandboxir::Value *From) {
534315 return From->getSubclassID () == ClassID::Opaque;
535316 }
536- unsigned getUseOperandNo (const Use &Use) const final {
537- return getUseOperandNoDefault (Use);
538- }
539317 unsigned getNumOfIRInstrs () const final { return 1u ; }
540318#ifndef NDEBUG
541319 void verify () const final {
0 commit comments