OLD | NEW |
1 //===- subzero/src/IceInst.h - High-level instructions ----------*- C++ -*-===// | 1 //===- subzero/src/IceInst.h - High-level instructions ----------*- C++ -*-===// |
2 // | 2 // |
3 // The Subzero Code Generator | 3 // The Subzero Code Generator |
4 // | 4 // |
5 // This file is distributed under the University of Illinois Open Source | 5 // This file is distributed under the University of Illinois Open Source |
6 // License. See LICENSE.TXT for details. | 6 // License. See LICENSE.TXT for details. |
7 // | 7 // |
8 //===----------------------------------------------------------------------===// | 8 //===----------------------------------------------------------------------===// |
9 // | 9 // |
10 // This file declares the Inst class and its target-independent | 10 // This file declares the Inst class and its target-independent |
(...skipping 147 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
158 // operand can contain 0 or 1 Variable (and target-specific operands | 158 // operand can contain 0 or 1 Variable (and target-specific operands |
159 // could contain more than 1 Variable). All the variables in an | 159 // could contain more than 1 Variable). All the variables in an |
160 // instruction are conceptually flattened and each variable is | 160 // instruction are conceptually flattened and each variable is |
161 // mapped to one bit position of the LiveRangesEnded bit vector. | 161 // mapped to one bit position of the LiveRangesEnded bit vector. |
162 // Only the first CHAR_BIT * sizeof(LREndedBits) variables are | 162 // Only the first CHAR_BIT * sizeof(LREndedBits) variables are |
163 // tracked this way. | 163 // tracked this way. |
164 typedef uint32_t LREndedBits; // only first 32 src operands tracked, sorry | 164 typedef uint32_t LREndedBits; // only first 32 src operands tracked, sorry |
165 LREndedBits LiveRangesEnded; | 165 LREndedBits LiveRangesEnded; |
166 | 166 |
167 private: | 167 private: |
168 Inst(const Inst &) LLVM_DELETED_FUNCTION; | 168 Inst(const Inst &) = delete; |
169 Inst &operator=(const Inst &) LLVM_DELETED_FUNCTION; | 169 Inst &operator=(const Inst &) = delete; |
170 }; | 170 }; |
171 | 171 |
172 class InstHighLevel : public Inst { | 172 class InstHighLevel : public Inst { |
173 InstHighLevel(const InstHighLevel &) LLVM_DELETED_FUNCTION; | 173 InstHighLevel(const InstHighLevel &) = delete; |
174 InstHighLevel &operator=(const InstHighLevel &) LLVM_DELETED_FUNCTION; | 174 InstHighLevel &operator=(const InstHighLevel &) = delete; |
175 | 175 |
176 protected: | 176 protected: |
177 InstHighLevel(Cfg *Func, InstKind Kind, SizeT MaxSrcs, Variable *Dest) | 177 InstHighLevel(Cfg *Func, InstKind Kind, SizeT MaxSrcs, Variable *Dest) |
178 : Inst(Func, Kind, MaxSrcs, Dest) {} | 178 : Inst(Func, Kind, MaxSrcs, Dest) {} |
179 void emit(const Cfg * /*Func*/) const override { | 179 void emit(const Cfg * /*Func*/) const override { |
180 llvm_unreachable("emit() called on a non-lowered instruction"); | 180 llvm_unreachable("emit() called on a non-lowered instruction"); |
181 } | 181 } |
182 void emitIAS(const Cfg * /*Func*/) const override { | 182 void emitIAS(const Cfg * /*Func*/) const override { |
183 llvm_unreachable("emitIAS() called on a non-lowered instruction"); | 183 llvm_unreachable("emitIAS() called on a non-lowered instruction"); |
184 } | 184 } |
(...skipping 11 matching lines...) Expand all Loading... |
196 InstAlloca(Func, ByteCount, AlignInBytes, Dest); | 196 InstAlloca(Func, ByteCount, AlignInBytes, Dest); |
197 } | 197 } |
198 uint32_t getAlignInBytes() const { return AlignInBytes; } | 198 uint32_t getAlignInBytes() const { return AlignInBytes; } |
199 Operand *getSizeInBytes() const { return getSrc(0); } | 199 Operand *getSizeInBytes() const { return getSrc(0); } |
200 void dump(const Cfg *Func) const override; | 200 void dump(const Cfg *Func) const override; |
201 static bool classof(const Inst *Inst) { return Inst->getKind() == Alloca; } | 201 static bool classof(const Inst *Inst) { return Inst->getKind() == Alloca; } |
202 | 202 |
203 private: | 203 private: |
204 InstAlloca(Cfg *Func, Operand *ByteCount, uint32_t AlignInBytes, | 204 InstAlloca(Cfg *Func, Operand *ByteCount, uint32_t AlignInBytes, |
205 Variable *Dest); | 205 Variable *Dest); |
206 InstAlloca(const InstAlloca &) LLVM_DELETED_FUNCTION; | 206 InstAlloca(const InstAlloca &) = delete; |
207 InstAlloca &operator=(const InstAlloca &) LLVM_DELETED_FUNCTION; | 207 InstAlloca &operator=(const InstAlloca &) = delete; |
208 ~InstAlloca() override {} | 208 ~InstAlloca() override {} |
209 const uint32_t AlignInBytes; | 209 const uint32_t AlignInBytes; |
210 }; | 210 }; |
211 | 211 |
212 // Binary arithmetic instruction. The source operands are captured in | 212 // Binary arithmetic instruction. The source operands are captured in |
213 // getSrc(0) and getSrc(1). | 213 // getSrc(0) and getSrc(1). |
214 class InstArithmetic : public InstHighLevel { | 214 class InstArithmetic : public InstHighLevel { |
215 public: | 215 public: |
216 enum OpKind { | 216 enum OpKind { |
217 #define X(tag, str, commutative) tag, | 217 #define X(tag, str, commutative) tag, |
(...skipping 11 matching lines...) Expand all Loading... |
229 static const char *getOpName(OpKind Op); | 229 static const char *getOpName(OpKind Op); |
230 bool isCommutative() const; | 230 bool isCommutative() const; |
231 void dump(const Cfg *Func) const override; | 231 void dump(const Cfg *Func) const override; |
232 static bool classof(const Inst *Inst) { | 232 static bool classof(const Inst *Inst) { |
233 return Inst->getKind() == Arithmetic; | 233 return Inst->getKind() == Arithmetic; |
234 } | 234 } |
235 | 235 |
236 private: | 236 private: |
237 InstArithmetic(Cfg *Func, OpKind Op, Variable *Dest, Operand *Source1, | 237 InstArithmetic(Cfg *Func, OpKind Op, Variable *Dest, Operand *Source1, |
238 Operand *Source2); | 238 Operand *Source2); |
239 InstArithmetic(const InstArithmetic &) LLVM_DELETED_FUNCTION; | 239 InstArithmetic(const InstArithmetic &) = delete; |
240 InstArithmetic &operator=(const InstArithmetic &) LLVM_DELETED_FUNCTION; | 240 InstArithmetic &operator=(const InstArithmetic &) = delete; |
241 ~InstArithmetic() override {} | 241 ~InstArithmetic() override {} |
242 | 242 |
243 const OpKind Op; | 243 const OpKind Op; |
244 }; | 244 }; |
245 | 245 |
246 // Assignment instruction. The source operand is captured in | 246 // Assignment instruction. The source operand is captured in |
247 // getSrc(0). This is not part of the LLVM bitcode, but is a useful | 247 // getSrc(0). This is not part of the LLVM bitcode, but is a useful |
248 // abstraction for some of the lowering. E.g., if Phi instruction | 248 // abstraction for some of the lowering. E.g., if Phi instruction |
249 // lowering happens before target lowering, or for representing an | 249 // lowering happens before target lowering, or for representing an |
250 // Inttoptr instruction, or as an intermediate step for lowering a | 250 // Inttoptr instruction, or as an intermediate step for lowering a |
251 // Load instruction. | 251 // Load instruction. |
252 class InstAssign : public InstHighLevel { | 252 class InstAssign : public InstHighLevel { |
253 public: | 253 public: |
254 static InstAssign *create(Cfg *Func, Variable *Dest, Operand *Source) { | 254 static InstAssign *create(Cfg *Func, Variable *Dest, Operand *Source) { |
255 return new (Func->allocateInst<InstAssign>()) | 255 return new (Func->allocateInst<InstAssign>()) |
256 InstAssign(Func, Dest, Source); | 256 InstAssign(Func, Dest, Source); |
257 } | 257 } |
258 bool isSimpleAssign() const override { return true; } | 258 bool isSimpleAssign() const override { return true; } |
259 void dump(const Cfg *Func) const override; | 259 void dump(const Cfg *Func) const override; |
260 static bool classof(const Inst *Inst) { return Inst->getKind() == Assign; } | 260 static bool classof(const Inst *Inst) { return Inst->getKind() == Assign; } |
261 | 261 |
262 private: | 262 private: |
263 InstAssign(Cfg *Func, Variable *Dest, Operand *Source); | 263 InstAssign(Cfg *Func, Variable *Dest, Operand *Source); |
264 InstAssign(const InstAssign &) LLVM_DELETED_FUNCTION; | 264 InstAssign(const InstAssign &) = delete; |
265 InstAssign &operator=(const InstAssign &) LLVM_DELETED_FUNCTION; | 265 InstAssign &operator=(const InstAssign &) = delete; |
266 ~InstAssign() override {} | 266 ~InstAssign() override {} |
267 }; | 267 }; |
268 | 268 |
269 // Branch instruction. This represents both conditional and | 269 // Branch instruction. This represents both conditional and |
270 // unconditional branches. | 270 // unconditional branches. |
271 class InstBr : public InstHighLevel { | 271 class InstBr : public InstHighLevel { |
272 public: | 272 public: |
273 // Create a conditional branch. If TargetTrue==TargetFalse, it is | 273 // Create a conditional branch. If TargetTrue==TargetFalse, it is |
274 // optimized to an unconditional branch. | 274 // optimized to an unconditional branch. |
275 static InstBr *create(Cfg *Func, Operand *Source, CfgNode *TargetTrue, | 275 static InstBr *create(Cfg *Func, Operand *Source, CfgNode *TargetTrue, |
(...skipping 18 matching lines...) Expand all Loading... |
294 } | 294 } |
295 NodeList getTerminatorEdges() const override; | 295 NodeList getTerminatorEdges() const override; |
296 void dump(const Cfg *Func) const override; | 296 void dump(const Cfg *Func) const override; |
297 static bool classof(const Inst *Inst) { return Inst->getKind() == Br; } | 297 static bool classof(const Inst *Inst) { return Inst->getKind() == Br; } |
298 | 298 |
299 private: | 299 private: |
300 // Conditional branch | 300 // Conditional branch |
301 InstBr(Cfg *Func, Operand *Source, CfgNode *TargetTrue, CfgNode *TargetFalse); | 301 InstBr(Cfg *Func, Operand *Source, CfgNode *TargetTrue, CfgNode *TargetFalse); |
302 // Unconditional branch | 302 // Unconditional branch |
303 InstBr(Cfg *Func, CfgNode *Target); | 303 InstBr(Cfg *Func, CfgNode *Target); |
304 InstBr(const InstBr &) LLVM_DELETED_FUNCTION; | 304 InstBr(const InstBr &) = delete; |
305 InstBr &operator=(const InstBr &) LLVM_DELETED_FUNCTION; | 305 InstBr &operator=(const InstBr &) = delete; |
306 ~InstBr() override {} | 306 ~InstBr() override {} |
307 | 307 |
308 CfgNode *const TargetFalse; // Doubles as unconditional branch target | 308 CfgNode *const TargetFalse; // Doubles as unconditional branch target |
309 CfgNode *const TargetTrue; // NULL if unconditional branch | 309 CfgNode *const TargetTrue; // NULL if unconditional branch |
310 }; | 310 }; |
311 | 311 |
312 // Call instruction. The call target is captured as getSrc(0), and | 312 // Call instruction. The call target is captured as getSrc(0), and |
313 // arg I is captured as getSrc(I+1). | 313 // arg I is captured as getSrc(I+1). |
314 class InstCall : public InstHighLevel { | 314 class InstCall : public InstHighLevel { |
315 public: | 315 public: |
(...skipping 20 matching lines...) Expand all Loading... |
336 InstCall(Cfg *Func, SizeT NumArgs, Variable *Dest, Operand *CallTarget, | 336 InstCall(Cfg *Func, SizeT NumArgs, Variable *Dest, Operand *CallTarget, |
337 bool HasTailCall, bool HasSideEff, InstKind Kind) | 337 bool HasTailCall, bool HasSideEff, InstKind Kind) |
338 : InstHighLevel(Func, Kind, NumArgs + 1, Dest), HasTailCall(HasTailCall) { | 338 : InstHighLevel(Func, Kind, NumArgs + 1, Dest), HasTailCall(HasTailCall) { |
339 HasSideEffects = HasSideEff; | 339 HasSideEffects = HasSideEff; |
340 addSource(CallTarget); | 340 addSource(CallTarget); |
341 } | 341 } |
342 ~InstCall() override {} | 342 ~InstCall() override {} |
343 | 343 |
344 private: | 344 private: |
345 bool HasTailCall; | 345 bool HasTailCall; |
346 InstCall(const InstCall &) LLVM_DELETED_FUNCTION; | 346 InstCall(const InstCall &) = delete; |
347 InstCall &operator=(const InstCall &) LLVM_DELETED_FUNCTION; | 347 InstCall &operator=(const InstCall &) = delete; |
348 }; | 348 }; |
349 | 349 |
350 // Cast instruction (a.k.a. conversion operation). | 350 // Cast instruction (a.k.a. conversion operation). |
351 class InstCast : public InstHighLevel { | 351 class InstCast : public InstHighLevel { |
352 public: | 352 public: |
353 enum OpKind { | 353 enum OpKind { |
354 #define X(tag, str) tag, | 354 #define X(tag, str) tag, |
355 ICEINSTCAST_TABLE | 355 ICEINSTCAST_TABLE |
356 #undef X | 356 #undef X |
357 _num | 357 _num |
358 }; | 358 }; |
359 | 359 |
360 static InstCast *create(Cfg *Func, OpKind CastKind, Variable *Dest, | 360 static InstCast *create(Cfg *Func, OpKind CastKind, Variable *Dest, |
361 Operand *Source) { | 361 Operand *Source) { |
362 return new (Func->allocateInst<InstCast>()) | 362 return new (Func->allocateInst<InstCast>()) |
363 InstCast(Func, CastKind, Dest, Source); | 363 InstCast(Func, CastKind, Dest, Source); |
364 } | 364 } |
365 OpKind getCastKind() const { return CastKind; } | 365 OpKind getCastKind() const { return CastKind; } |
366 void dump(const Cfg *Func) const override; | 366 void dump(const Cfg *Func) const override; |
367 static bool classof(const Inst *Inst) { return Inst->getKind() == Cast; } | 367 static bool classof(const Inst *Inst) { return Inst->getKind() == Cast; } |
368 | 368 |
369 private: | 369 private: |
370 InstCast(Cfg *Func, OpKind CastKind, Variable *Dest, Operand *Source); | 370 InstCast(Cfg *Func, OpKind CastKind, Variable *Dest, Operand *Source); |
371 InstCast(const InstCast &) LLVM_DELETED_FUNCTION; | 371 InstCast(const InstCast &) = delete; |
372 InstCast &operator=(const InstCast &) LLVM_DELETED_FUNCTION; | 372 InstCast &operator=(const InstCast &) = delete; |
373 ~InstCast() override {} | 373 ~InstCast() override {} |
374 const OpKind CastKind; | 374 const OpKind CastKind; |
375 }; | 375 }; |
376 | 376 |
377 // ExtractElement instruction. | 377 // ExtractElement instruction. |
378 class InstExtractElement : public InstHighLevel { | 378 class InstExtractElement : public InstHighLevel { |
379 public: | 379 public: |
380 static InstExtractElement *create(Cfg *Func, Variable *Dest, Operand *Source1, | 380 static InstExtractElement *create(Cfg *Func, Variable *Dest, Operand *Source1, |
381 Operand *Source2) { | 381 Operand *Source2) { |
382 return new (Func->allocateInst<InstExtractElement>()) | 382 return new (Func->allocateInst<InstExtractElement>()) |
383 InstExtractElement(Func, Dest, Source1, Source2); | 383 InstExtractElement(Func, Dest, Source1, Source2); |
384 } | 384 } |
385 | 385 |
386 void dump(const Cfg *Func) const override; | 386 void dump(const Cfg *Func) const override; |
387 static bool classof(const Inst *Inst) { | 387 static bool classof(const Inst *Inst) { |
388 return Inst->getKind() == ExtractElement; | 388 return Inst->getKind() == ExtractElement; |
389 } | 389 } |
390 | 390 |
391 private: | 391 private: |
392 InstExtractElement(Cfg *Func, Variable *Dest, Operand *Source1, | 392 InstExtractElement(Cfg *Func, Variable *Dest, Operand *Source1, |
393 Operand *Source2); | 393 Operand *Source2); |
394 InstExtractElement(const InstExtractElement &) LLVM_DELETED_FUNCTION; | 394 InstExtractElement(const InstExtractElement &) = delete; |
395 InstExtractElement & | 395 InstExtractElement &operator=(const InstExtractElement &) = delete; |
396 operator=(const InstExtractElement &) LLVM_DELETED_FUNCTION; | |
397 ~InstExtractElement() override {} | 396 ~InstExtractElement() override {} |
398 }; | 397 }; |
399 | 398 |
400 // Floating-point comparison instruction. The source operands are | 399 // Floating-point comparison instruction. The source operands are |
401 // captured in getSrc(0) and getSrc(1). | 400 // captured in getSrc(0) and getSrc(1). |
402 class InstFcmp : public InstHighLevel { | 401 class InstFcmp : public InstHighLevel { |
403 public: | 402 public: |
404 enum FCond { | 403 enum FCond { |
405 #define X(tag, str) tag, | 404 #define X(tag, str) tag, |
406 ICEINSTFCMP_TABLE | 405 ICEINSTFCMP_TABLE |
407 #undef X | 406 #undef X |
408 _num | 407 _num |
409 }; | 408 }; |
410 | 409 |
411 static InstFcmp *create(Cfg *Func, FCond Condition, Variable *Dest, | 410 static InstFcmp *create(Cfg *Func, FCond Condition, Variable *Dest, |
412 Operand *Source1, Operand *Source2) { | 411 Operand *Source1, Operand *Source2) { |
413 return new (Func->allocateInst<InstFcmp>()) | 412 return new (Func->allocateInst<InstFcmp>()) |
414 InstFcmp(Func, Condition, Dest, Source1, Source2); | 413 InstFcmp(Func, Condition, Dest, Source1, Source2); |
415 } | 414 } |
416 FCond getCondition() const { return Condition; } | 415 FCond getCondition() const { return Condition; } |
417 void dump(const Cfg *Func) const override; | 416 void dump(const Cfg *Func) const override; |
418 static bool classof(const Inst *Inst) { return Inst->getKind() == Fcmp; } | 417 static bool classof(const Inst *Inst) { return Inst->getKind() == Fcmp; } |
419 | 418 |
420 private: | 419 private: |
421 InstFcmp(Cfg *Func, FCond Condition, Variable *Dest, Operand *Source1, | 420 InstFcmp(Cfg *Func, FCond Condition, Variable *Dest, Operand *Source1, |
422 Operand *Source2); | 421 Operand *Source2); |
423 InstFcmp(const InstFcmp &) LLVM_DELETED_FUNCTION; | 422 InstFcmp(const InstFcmp &) = delete; |
424 InstFcmp &operator=(const InstFcmp &) LLVM_DELETED_FUNCTION; | 423 InstFcmp &operator=(const InstFcmp &) = delete; |
425 ~InstFcmp() override {} | 424 ~InstFcmp() override {} |
426 const FCond Condition; | 425 const FCond Condition; |
427 }; | 426 }; |
428 | 427 |
429 // Integer comparison instruction. The source operands are captured | 428 // Integer comparison instruction. The source operands are captured |
430 // in getSrc(0) and getSrc(1). | 429 // in getSrc(0) and getSrc(1). |
431 class InstIcmp : public InstHighLevel { | 430 class InstIcmp : public InstHighLevel { |
432 public: | 431 public: |
433 enum ICond { | 432 enum ICond { |
434 #define X(tag, str) tag, | 433 #define X(tag, str) tag, |
435 ICEINSTICMP_TABLE | 434 ICEINSTICMP_TABLE |
436 #undef X | 435 #undef X |
437 _num | 436 _num |
438 }; | 437 }; |
439 | 438 |
440 static InstIcmp *create(Cfg *Func, ICond Condition, Variable *Dest, | 439 static InstIcmp *create(Cfg *Func, ICond Condition, Variable *Dest, |
441 Operand *Source1, Operand *Source2) { | 440 Operand *Source1, Operand *Source2) { |
442 return new (Func->allocateInst<InstIcmp>()) | 441 return new (Func->allocateInst<InstIcmp>()) |
443 InstIcmp(Func, Condition, Dest, Source1, Source2); | 442 InstIcmp(Func, Condition, Dest, Source1, Source2); |
444 } | 443 } |
445 ICond getCondition() const { return Condition; } | 444 ICond getCondition() const { return Condition; } |
446 void dump(const Cfg *Func) const override; | 445 void dump(const Cfg *Func) const override; |
447 static bool classof(const Inst *Inst) { return Inst->getKind() == Icmp; } | 446 static bool classof(const Inst *Inst) { return Inst->getKind() == Icmp; } |
448 | 447 |
449 private: | 448 private: |
450 InstIcmp(Cfg *Func, ICond Condition, Variable *Dest, Operand *Source1, | 449 InstIcmp(Cfg *Func, ICond Condition, Variable *Dest, Operand *Source1, |
451 Operand *Source2); | 450 Operand *Source2); |
452 InstIcmp(const InstIcmp &) LLVM_DELETED_FUNCTION; | 451 InstIcmp(const InstIcmp &) = delete; |
453 InstIcmp &operator=(const InstIcmp &) LLVM_DELETED_FUNCTION; | 452 InstIcmp &operator=(const InstIcmp &) = delete; |
454 ~InstIcmp() override {} | 453 ~InstIcmp() override {} |
455 const ICond Condition; | 454 const ICond Condition; |
456 }; | 455 }; |
457 | 456 |
458 // InsertElement instruction. | 457 // InsertElement instruction. |
459 class InstInsertElement : public InstHighLevel { | 458 class InstInsertElement : public InstHighLevel { |
460 public: | 459 public: |
461 static InstInsertElement *create(Cfg *Func, Variable *Dest, Operand *Source1, | 460 static InstInsertElement *create(Cfg *Func, Variable *Dest, Operand *Source1, |
462 Operand *Source2, Operand *Source3) { | 461 Operand *Source2, Operand *Source3) { |
463 return new (Func->allocateInst<InstInsertElement>()) | 462 return new (Func->allocateInst<InstInsertElement>()) |
464 InstInsertElement(Func, Dest, Source1, Source2, Source3); | 463 InstInsertElement(Func, Dest, Source1, Source2, Source3); |
465 } | 464 } |
466 | 465 |
467 void dump(const Cfg *Func) const override; | 466 void dump(const Cfg *Func) const override; |
468 static bool classof(const Inst *Inst) { | 467 static bool classof(const Inst *Inst) { |
469 return Inst->getKind() == InsertElement; | 468 return Inst->getKind() == InsertElement; |
470 } | 469 } |
471 | 470 |
472 private: | 471 private: |
473 InstInsertElement(Cfg *Func, Variable *Dest, Operand *Source1, | 472 InstInsertElement(Cfg *Func, Variable *Dest, Operand *Source1, |
474 Operand *Source2, Operand *Source3); | 473 Operand *Source2, Operand *Source3); |
475 InstInsertElement(const InstInsertElement &) LLVM_DELETED_FUNCTION; | 474 InstInsertElement(const InstInsertElement &) = delete; |
476 InstInsertElement &operator=(const InstInsertElement &) LLVM_DELETED_FUNCTION; | 475 InstInsertElement &operator=(const InstInsertElement &) = delete; |
477 ~InstInsertElement() override {} | 476 ~InstInsertElement() override {} |
478 }; | 477 }; |
479 | 478 |
480 // Call to an intrinsic function. The call target is captured as getSrc(0), | 479 // Call to an intrinsic function. The call target is captured as getSrc(0), |
481 // and arg I is captured as getSrc(I+1). | 480 // and arg I is captured as getSrc(I+1). |
482 class InstIntrinsicCall : public InstCall { | 481 class InstIntrinsicCall : public InstCall { |
483 public: | 482 public: |
484 static InstIntrinsicCall *create(Cfg *Func, SizeT NumArgs, Variable *Dest, | 483 static InstIntrinsicCall *create(Cfg *Func, SizeT NumArgs, Variable *Dest, |
485 Operand *CallTarget, | 484 Operand *CallTarget, |
486 const Intrinsics::IntrinsicInfo &Info) { | 485 const Intrinsics::IntrinsicInfo &Info) { |
487 return new (Func->allocateInst<InstIntrinsicCall>()) | 486 return new (Func->allocateInst<InstIntrinsicCall>()) |
488 InstIntrinsicCall(Func, NumArgs, Dest, CallTarget, Info); | 487 InstIntrinsicCall(Func, NumArgs, Dest, CallTarget, Info); |
489 } | 488 } |
490 static bool classof(const Inst *Inst) { | 489 static bool classof(const Inst *Inst) { |
491 return Inst->getKind() == IntrinsicCall; | 490 return Inst->getKind() == IntrinsicCall; |
492 } | 491 } |
493 | 492 |
494 Intrinsics::IntrinsicInfo getIntrinsicInfo() const { return Info; } | 493 Intrinsics::IntrinsicInfo getIntrinsicInfo() const { return Info; } |
495 | 494 |
496 private: | 495 private: |
497 InstIntrinsicCall(Cfg *Func, SizeT NumArgs, Variable *Dest, | 496 InstIntrinsicCall(Cfg *Func, SizeT NumArgs, Variable *Dest, |
498 Operand *CallTarget, const Intrinsics::IntrinsicInfo &Info) | 497 Operand *CallTarget, const Intrinsics::IntrinsicInfo &Info) |
499 : InstCall(Func, NumArgs, Dest, CallTarget, false, Info.HasSideEffects, | 498 : InstCall(Func, NumArgs, Dest, CallTarget, false, Info.HasSideEffects, |
500 Inst::IntrinsicCall), | 499 Inst::IntrinsicCall), |
501 Info(Info) {} | 500 Info(Info) {} |
502 InstIntrinsicCall(const InstIntrinsicCall &) LLVM_DELETED_FUNCTION; | 501 InstIntrinsicCall(const InstIntrinsicCall &) = delete; |
503 InstIntrinsicCall &operator=(const InstIntrinsicCall &) LLVM_DELETED_FUNCTION; | 502 InstIntrinsicCall &operator=(const InstIntrinsicCall &) = delete; |
504 ~InstIntrinsicCall() override {} | 503 ~InstIntrinsicCall() override {} |
505 const Intrinsics::IntrinsicInfo Info; | 504 const Intrinsics::IntrinsicInfo Info; |
506 }; | 505 }; |
507 | 506 |
508 // Load instruction. The source address is captured in getSrc(0). | 507 // Load instruction. The source address is captured in getSrc(0). |
509 class InstLoad : public InstHighLevel { | 508 class InstLoad : public InstHighLevel { |
510 public: | 509 public: |
511 static InstLoad *create(Cfg *Func, Variable *Dest, Operand *SourceAddr, | 510 static InstLoad *create(Cfg *Func, Variable *Dest, Operand *SourceAddr, |
512 uint32_t Align = 1) { | 511 uint32_t Align = 1) { |
513 // TODO(kschimpf) Stop ignoring alignment specification. | 512 // TODO(kschimpf) Stop ignoring alignment specification. |
514 (void)Align; | 513 (void)Align; |
515 return new (Func->allocateInst<InstLoad>()) | 514 return new (Func->allocateInst<InstLoad>()) |
516 InstLoad(Func, Dest, SourceAddr); | 515 InstLoad(Func, Dest, SourceAddr); |
517 } | 516 } |
518 Operand *getSourceAddress() const { return getSrc(0); } | 517 Operand *getSourceAddress() const { return getSrc(0); } |
519 void dump(const Cfg *Func) const override; | 518 void dump(const Cfg *Func) const override; |
520 static bool classof(const Inst *Inst) { return Inst->getKind() == Load; } | 519 static bool classof(const Inst *Inst) { return Inst->getKind() == Load; } |
521 | 520 |
522 private: | 521 private: |
523 InstLoad(Cfg *Func, Variable *Dest, Operand *SourceAddr); | 522 InstLoad(Cfg *Func, Variable *Dest, Operand *SourceAddr); |
524 InstLoad(const InstLoad &) LLVM_DELETED_FUNCTION; | 523 InstLoad(const InstLoad &) = delete; |
525 InstLoad &operator=(const InstLoad &) LLVM_DELETED_FUNCTION; | 524 InstLoad &operator=(const InstLoad &) = delete; |
526 ~InstLoad() override {} | 525 ~InstLoad() override {} |
527 }; | 526 }; |
528 | 527 |
529 // Phi instruction. For incoming edge I, the node is Labels[I] and | 528 // Phi instruction. For incoming edge I, the node is Labels[I] and |
530 // the Phi source operand is getSrc(I). | 529 // the Phi source operand is getSrc(I). |
531 class InstPhi : public InstHighLevel { | 530 class InstPhi : public InstHighLevel { |
532 public: | 531 public: |
533 static InstPhi *create(Cfg *Func, SizeT MaxSrcs, Variable *Dest) { | 532 static InstPhi *create(Cfg *Func, SizeT MaxSrcs, Variable *Dest) { |
534 return new (Func->allocateInst<InstPhi>()) InstPhi(Func, MaxSrcs, Dest); | 533 return new (Func->allocateInst<InstPhi>()) InstPhi(Func, MaxSrcs, Dest); |
535 } | 534 } |
536 void addArgument(Operand *Source, CfgNode *Label); | 535 void addArgument(Operand *Source, CfgNode *Label); |
537 Operand *getOperandForTarget(CfgNode *Target) const; | 536 Operand *getOperandForTarget(CfgNode *Target) const; |
538 void livenessPhiOperand(llvm::BitVector &Live, CfgNode *Target, | 537 void livenessPhiOperand(llvm::BitVector &Live, CfgNode *Target, |
539 Liveness *Liveness); | 538 Liveness *Liveness); |
540 Inst *lower(Cfg *Func); | 539 Inst *lower(Cfg *Func); |
541 void dump(const Cfg *Func) const override; | 540 void dump(const Cfg *Func) const override; |
542 static bool classof(const Inst *Inst) { return Inst->getKind() == Phi; } | 541 static bool classof(const Inst *Inst) { return Inst->getKind() == Phi; } |
543 | 542 |
544 private: | 543 private: |
545 InstPhi(Cfg *Func, SizeT MaxSrcs, Variable *Dest); | 544 InstPhi(Cfg *Func, SizeT MaxSrcs, Variable *Dest); |
546 InstPhi(const InstPhi &) LLVM_DELETED_FUNCTION; | 545 InstPhi(const InstPhi &) = delete; |
547 InstPhi &operator=(const InstPhi &) LLVM_DELETED_FUNCTION; | 546 InstPhi &operator=(const InstPhi &) = delete; |
548 void destroy(Cfg *Func) override { | 547 void destroy(Cfg *Func) override { |
549 Func->deallocateArrayOf<CfgNode *>(Labels); | 548 Func->deallocateArrayOf<CfgNode *>(Labels); |
550 Inst::destroy(Func); | 549 Inst::destroy(Func); |
551 } | 550 } |
552 ~InstPhi() override {} | 551 ~InstPhi() override {} |
553 | 552 |
554 // Labels[] duplicates the InEdges[] information in the enclosing | 553 // Labels[] duplicates the InEdges[] information in the enclosing |
555 // CfgNode, but the Phi instruction is created before InEdges[] | 554 // CfgNode, but the Phi instruction is created before InEdges[] |
556 // is available, so it's more complicated to share the list. | 555 // is available, so it's more complicated to share the list. |
557 CfgNode **Labels; | 556 CfgNode **Labels; |
(...skipping 11 matching lines...) Expand all Loading... |
569 Operand *getRetValue() const { | 568 Operand *getRetValue() const { |
570 assert(hasRetValue()); | 569 assert(hasRetValue()); |
571 return getSrc(0); | 570 return getSrc(0); |
572 } | 571 } |
573 NodeList getTerminatorEdges() const override { return NodeList(); } | 572 NodeList getTerminatorEdges() const override { return NodeList(); } |
574 void dump(const Cfg *Func) const override; | 573 void dump(const Cfg *Func) const override; |
575 static bool classof(const Inst *Inst) { return Inst->getKind() == Ret; } | 574 static bool classof(const Inst *Inst) { return Inst->getKind() == Ret; } |
576 | 575 |
577 private: | 576 private: |
578 InstRet(Cfg *Func, Operand *RetValue); | 577 InstRet(Cfg *Func, Operand *RetValue); |
579 InstRet(const InstRet &) LLVM_DELETED_FUNCTION; | 578 InstRet(const InstRet &) = delete; |
580 InstRet &operator=(const InstRet &) LLVM_DELETED_FUNCTION; | 579 InstRet &operator=(const InstRet &) = delete; |
581 ~InstRet() override {} | 580 ~InstRet() override {} |
582 }; | 581 }; |
583 | 582 |
584 // Select instruction. The condition, true, and false operands are captured. | 583 // Select instruction. The condition, true, and false operands are captured. |
585 class InstSelect : public InstHighLevel { | 584 class InstSelect : public InstHighLevel { |
586 public: | 585 public: |
587 static InstSelect *create(Cfg *Func, Variable *Dest, Operand *Condition, | 586 static InstSelect *create(Cfg *Func, Variable *Dest, Operand *Condition, |
588 Operand *SourceTrue, Operand *SourceFalse) { | 587 Operand *SourceTrue, Operand *SourceFalse) { |
589 return new (Func->allocateInst<InstSelect>()) | 588 return new (Func->allocateInst<InstSelect>()) |
590 InstSelect(Func, Dest, Condition, SourceTrue, SourceFalse); | 589 InstSelect(Func, Dest, Condition, SourceTrue, SourceFalse); |
591 } | 590 } |
592 Operand *getCondition() const { return getSrc(0); } | 591 Operand *getCondition() const { return getSrc(0); } |
593 Operand *getTrueOperand() const { return getSrc(1); } | 592 Operand *getTrueOperand() const { return getSrc(1); } |
594 Operand *getFalseOperand() const { return getSrc(2); } | 593 Operand *getFalseOperand() const { return getSrc(2); } |
595 void dump(const Cfg *Func) const override; | 594 void dump(const Cfg *Func) const override; |
596 static bool classof(const Inst *Inst) { return Inst->getKind() == Select; } | 595 static bool classof(const Inst *Inst) { return Inst->getKind() == Select; } |
597 | 596 |
598 private: | 597 private: |
599 InstSelect(Cfg *Func, Variable *Dest, Operand *Condition, Operand *Source1, | 598 InstSelect(Cfg *Func, Variable *Dest, Operand *Condition, Operand *Source1, |
600 Operand *Source2); | 599 Operand *Source2); |
601 InstSelect(const InstSelect &) LLVM_DELETED_FUNCTION; | 600 InstSelect(const InstSelect &) = delete; |
602 InstSelect &operator=(const InstSelect &) LLVM_DELETED_FUNCTION; | 601 InstSelect &operator=(const InstSelect &) = delete; |
603 ~InstSelect() override {} | 602 ~InstSelect() override {} |
604 }; | 603 }; |
605 | 604 |
606 // Store instruction. The address operand is captured, along with the | 605 // Store instruction. The address operand is captured, along with the |
607 // data operand to be stored into the address. | 606 // data operand to be stored into the address. |
608 class InstStore : public InstHighLevel { | 607 class InstStore : public InstHighLevel { |
609 public: | 608 public: |
610 static InstStore *create(Cfg *Func, Operand *Data, Operand *Addr, | 609 static InstStore *create(Cfg *Func, Operand *Data, Operand *Addr, |
611 uint32_t align = 1) { | 610 uint32_t align = 1) { |
612 // TODO(kschimpf) Stop ignoring alignment specification. | 611 // TODO(kschimpf) Stop ignoring alignment specification. |
613 (void)align; | 612 (void)align; |
614 return new (Func->allocateInst<InstStore>()) InstStore(Func, Data, Addr); | 613 return new (Func->allocateInst<InstStore>()) InstStore(Func, Data, Addr); |
615 } | 614 } |
616 Operand *getAddr() const { return getSrc(1); } | 615 Operand *getAddr() const { return getSrc(1); } |
617 Operand *getData() const { return getSrc(0); } | 616 Operand *getData() const { return getSrc(0); } |
618 void dump(const Cfg *Func) const override; | 617 void dump(const Cfg *Func) const override; |
619 static bool classof(const Inst *Inst) { return Inst->getKind() == Store; } | 618 static bool classof(const Inst *Inst) { return Inst->getKind() == Store; } |
620 | 619 |
621 private: | 620 private: |
622 InstStore(Cfg *Func, Operand *Data, Operand *Addr); | 621 InstStore(Cfg *Func, Operand *Data, Operand *Addr); |
623 InstStore(const InstStore &) LLVM_DELETED_FUNCTION; | 622 InstStore(const InstStore &) = delete; |
624 InstStore &operator=(const InstStore &) LLVM_DELETED_FUNCTION; | 623 InstStore &operator=(const InstStore &) = delete; |
625 ~InstStore() override {} | 624 ~InstStore() override {} |
626 }; | 625 }; |
627 | 626 |
628 // Switch instruction. The single source operand is captured as | 627 // Switch instruction. The single source operand is captured as |
629 // getSrc(0). | 628 // getSrc(0). |
630 class InstSwitch : public InstHighLevel { | 629 class InstSwitch : public InstHighLevel { |
631 public: | 630 public: |
632 static InstSwitch *create(Cfg *Func, SizeT NumCases, Operand *Source, | 631 static InstSwitch *create(Cfg *Func, SizeT NumCases, Operand *Source, |
633 CfgNode *LabelDefault) { | 632 CfgNode *LabelDefault) { |
634 return new (Func->allocateInst<InstSwitch>()) | 633 return new (Func->allocateInst<InstSwitch>()) |
(...skipping 10 matching lines...) Expand all Loading... |
645 assert(I < NumCases); | 644 assert(I < NumCases); |
646 return Labels[I]; | 645 return Labels[I]; |
647 } | 646 } |
648 void addBranch(SizeT CaseIndex, uint64_t Value, CfgNode *Label); | 647 void addBranch(SizeT CaseIndex, uint64_t Value, CfgNode *Label); |
649 NodeList getTerminatorEdges() const override; | 648 NodeList getTerminatorEdges() const override; |
650 void dump(const Cfg *Func) const override; | 649 void dump(const Cfg *Func) const override; |
651 static bool classof(const Inst *Inst) { return Inst->getKind() == Switch; } | 650 static bool classof(const Inst *Inst) { return Inst->getKind() == Switch; } |
652 | 651 |
653 private: | 652 private: |
654 InstSwitch(Cfg *Func, SizeT NumCases, Operand *Source, CfgNode *LabelDefault); | 653 InstSwitch(Cfg *Func, SizeT NumCases, Operand *Source, CfgNode *LabelDefault); |
655 InstSwitch(const InstSwitch &) LLVM_DELETED_FUNCTION; | 654 InstSwitch(const InstSwitch &) = delete; |
656 InstSwitch &operator=(const InstSwitch &) LLVM_DELETED_FUNCTION; | 655 InstSwitch &operator=(const InstSwitch &) = delete; |
657 void destroy(Cfg *Func) override { | 656 void destroy(Cfg *Func) override { |
658 Func->deallocateArrayOf<uint64_t>(Values); | 657 Func->deallocateArrayOf<uint64_t>(Values); |
659 Func->deallocateArrayOf<CfgNode *>(Labels); | 658 Func->deallocateArrayOf<CfgNode *>(Labels); |
660 Inst::destroy(Func); | 659 Inst::destroy(Func); |
661 } | 660 } |
662 ~InstSwitch() override {} | 661 ~InstSwitch() override {} |
663 | 662 |
664 CfgNode *LabelDefault; | 663 CfgNode *LabelDefault; |
665 SizeT NumCases; // not including the default case | 664 SizeT NumCases; // not including the default case |
666 uint64_t *Values; // size is NumCases | 665 uint64_t *Values; // size is NumCases |
667 CfgNode **Labels; // size is NumCases | 666 CfgNode **Labels; // size is NumCases |
668 }; | 667 }; |
669 | 668 |
670 // Unreachable instruction. This is a terminator instruction with no | 669 // Unreachable instruction. This is a terminator instruction with no |
671 // operands. | 670 // operands. |
672 class InstUnreachable : public InstHighLevel { | 671 class InstUnreachable : public InstHighLevel { |
673 public: | 672 public: |
674 static InstUnreachable *create(Cfg *Func) { | 673 static InstUnreachable *create(Cfg *Func) { |
675 return new (Func->allocateInst<InstUnreachable>()) InstUnreachable(Func); | 674 return new (Func->allocateInst<InstUnreachable>()) InstUnreachable(Func); |
676 } | 675 } |
677 NodeList getTerminatorEdges() const override { return NodeList(); } | 676 NodeList getTerminatorEdges() const override { return NodeList(); } |
678 void dump(const Cfg *Func) const override; | 677 void dump(const Cfg *Func) const override; |
679 static bool classof(const Inst *Inst) { | 678 static bool classof(const Inst *Inst) { |
680 return Inst->getKind() == Unreachable; | 679 return Inst->getKind() == Unreachable; |
681 } | 680 } |
682 | 681 |
683 private: | 682 private: |
684 InstUnreachable(Cfg *Func); | 683 InstUnreachable(Cfg *Func); |
685 InstUnreachable(const InstUnreachable &) LLVM_DELETED_FUNCTION; | 684 InstUnreachable(const InstUnreachable &) = delete; |
686 InstUnreachable &operator=(const InstUnreachable &) LLVM_DELETED_FUNCTION; | 685 InstUnreachable &operator=(const InstUnreachable &) = delete; |
687 ~InstUnreachable() override {} | 686 ~InstUnreachable() override {} |
688 }; | 687 }; |
689 | 688 |
690 // FakeDef instruction. This creates a fake definition of a variable, | 689 // FakeDef instruction. This creates a fake definition of a variable, |
691 // which is how we represent the case when an instruction produces | 690 // which is how we represent the case when an instruction produces |
692 // multiple results. This doesn't happen with high-level ICE | 691 // multiple results. This doesn't happen with high-level ICE |
693 // instructions, but might with lowered instructions. For example, | 692 // instructions, but might with lowered instructions. For example, |
694 // this would be a way to represent condition flags being modified by | 693 // this would be a way to represent condition flags being modified by |
695 // an instruction. | 694 // an instruction. |
696 // | 695 // |
697 // It's generally useful to set the optional source operand to be the | 696 // It's generally useful to set the optional source operand to be the |
698 // dest variable of the instruction that actually produces the FakeDef | 697 // dest variable of the instruction that actually produces the FakeDef |
699 // dest. Otherwise, the original instruction could be dead-code | 698 // dest. Otherwise, the original instruction could be dead-code |
700 // eliminated if its dest operand is unused, and therefore the FakeDef | 699 // eliminated if its dest operand is unused, and therefore the FakeDef |
701 // dest wouldn't be properly initialized. | 700 // dest wouldn't be properly initialized. |
702 class InstFakeDef : public InstHighLevel { | 701 class InstFakeDef : public InstHighLevel { |
703 public: | 702 public: |
704 static InstFakeDef *create(Cfg *Func, Variable *Dest, Variable *Src = NULL) { | 703 static InstFakeDef *create(Cfg *Func, Variable *Dest, Variable *Src = NULL) { |
705 return new (Func->allocateInst<InstFakeDef>()) InstFakeDef(Func, Dest, Src); | 704 return new (Func->allocateInst<InstFakeDef>()) InstFakeDef(Func, Dest, Src); |
706 } | 705 } |
707 void emit(const Cfg *Func) const override; | 706 void emit(const Cfg *Func) const override; |
708 void emitIAS(const Cfg *Func) const override { emit(Func); } | 707 void emitIAS(const Cfg *Func) const override { emit(Func); } |
709 void dump(const Cfg *Func) const override; | 708 void dump(const Cfg *Func) const override; |
710 static bool classof(const Inst *Inst) { return Inst->getKind() == FakeDef; } | 709 static bool classof(const Inst *Inst) { return Inst->getKind() == FakeDef; } |
711 | 710 |
712 private: | 711 private: |
713 InstFakeDef(Cfg *Func, Variable *Dest, Variable *Src); | 712 InstFakeDef(Cfg *Func, Variable *Dest, Variable *Src); |
714 InstFakeDef(const InstFakeDef &) LLVM_DELETED_FUNCTION; | 713 InstFakeDef(const InstFakeDef &) = delete; |
715 InstFakeDef &operator=(const InstFakeDef &) LLVM_DELETED_FUNCTION; | 714 InstFakeDef &operator=(const InstFakeDef &) = delete; |
716 ~InstFakeDef() override {} | 715 ~InstFakeDef() override {} |
717 }; | 716 }; |
718 | 717 |
719 // FakeUse instruction. This creates a fake use of a variable, to | 718 // FakeUse instruction. This creates a fake use of a variable, to |
720 // keep the instruction that produces that variable from being | 719 // keep the instruction that produces that variable from being |
721 // dead-code eliminated. This is useful in a variety of lowering | 720 // dead-code eliminated. This is useful in a variety of lowering |
722 // situations. The FakeUse instruction has no dest, so it can itself | 721 // situations. The FakeUse instruction has no dest, so it can itself |
723 // never be dead-code eliminated. | 722 // never be dead-code eliminated. |
724 class InstFakeUse : public InstHighLevel { | 723 class InstFakeUse : public InstHighLevel { |
725 public: | 724 public: |
726 static InstFakeUse *create(Cfg *Func, Variable *Src) { | 725 static InstFakeUse *create(Cfg *Func, Variable *Src) { |
727 return new (Func->allocateInst<InstFakeUse>()) InstFakeUse(Func, Src); | 726 return new (Func->allocateInst<InstFakeUse>()) InstFakeUse(Func, Src); |
728 } | 727 } |
729 void emit(const Cfg *Func) const override; | 728 void emit(const Cfg *Func) const override; |
730 void emitIAS(const Cfg *Func) const override { emit(Func); } | 729 void emitIAS(const Cfg *Func) const override { emit(Func); } |
731 void dump(const Cfg *Func) const override; | 730 void dump(const Cfg *Func) const override; |
732 static bool classof(const Inst *Inst) { return Inst->getKind() == FakeUse; } | 731 static bool classof(const Inst *Inst) { return Inst->getKind() == FakeUse; } |
733 | 732 |
734 private: | 733 private: |
735 InstFakeUse(Cfg *Func, Variable *Src); | 734 InstFakeUse(Cfg *Func, Variable *Src); |
736 InstFakeUse(const InstFakeUse &) LLVM_DELETED_FUNCTION; | 735 InstFakeUse(const InstFakeUse &) = delete; |
737 InstFakeUse &operator=(const InstFakeUse &) LLVM_DELETED_FUNCTION; | 736 InstFakeUse &operator=(const InstFakeUse &) = delete; |
738 ~InstFakeUse() override {} | 737 ~InstFakeUse() override {} |
739 }; | 738 }; |
740 | 739 |
741 // FakeKill instruction. This "kills" a set of variables by adding a | 740 // FakeKill instruction. This "kills" a set of variables by adding a |
742 // trivial live range at this instruction to each variable. The | 741 // trivial live range at this instruction to each variable. The |
743 // primary use is to indicate that scratch registers are killed after | 742 // primary use is to indicate that scratch registers are killed after |
744 // a call, so that the register allocator won't assign a scratch | 743 // a call, so that the register allocator won't assign a scratch |
745 // register to a variable whose live range spans a call. | 744 // register to a variable whose live range spans a call. |
746 // | 745 // |
747 // The FakeKill instruction also holds a pointer to the instruction | 746 // The FakeKill instruction also holds a pointer to the instruction |
748 // that kills the set of variables, so that if that linked instruction | 747 // that kills the set of variables, so that if that linked instruction |
749 // gets dead-code eliminated, the FakeKill instruction will as well. | 748 // gets dead-code eliminated, the FakeKill instruction will as well. |
750 class InstFakeKill : public InstHighLevel { | 749 class InstFakeKill : public InstHighLevel { |
751 public: | 750 public: |
752 static InstFakeKill *create(Cfg *Func, const VarList &KilledRegs, | 751 static InstFakeKill *create(Cfg *Func, const VarList &KilledRegs, |
753 const Inst *Linked) { | 752 const Inst *Linked) { |
754 return new (Func->allocateInst<InstFakeKill>()) | 753 return new (Func->allocateInst<InstFakeKill>()) |
755 InstFakeKill(Func, KilledRegs, Linked); | 754 InstFakeKill(Func, KilledRegs, Linked); |
756 } | 755 } |
757 const Inst *getLinked() const { return Linked; } | 756 const Inst *getLinked() const { return Linked; } |
758 void emit(const Cfg *Func) const override; | 757 void emit(const Cfg *Func) const override; |
759 void emitIAS(const Cfg *Func) const override { emit(Func); } | 758 void emitIAS(const Cfg *Func) const override { emit(Func); } |
760 void dump(const Cfg *Func) const override; | 759 void dump(const Cfg *Func) const override; |
761 static bool classof(const Inst *Inst) { return Inst->getKind() == FakeKill; } | 760 static bool classof(const Inst *Inst) { return Inst->getKind() == FakeKill; } |
762 | 761 |
763 private: | 762 private: |
764 InstFakeKill(Cfg *Func, const VarList &KilledRegs, const Inst *Linked); | 763 InstFakeKill(Cfg *Func, const VarList &KilledRegs, const Inst *Linked); |
765 InstFakeKill(const InstFakeKill &) LLVM_DELETED_FUNCTION; | 764 InstFakeKill(const InstFakeKill &) = delete; |
766 InstFakeKill &operator=(const InstFakeKill &) LLVM_DELETED_FUNCTION; | 765 InstFakeKill &operator=(const InstFakeKill &) = delete; |
767 ~InstFakeKill() override {} | 766 ~InstFakeKill() override {} |
768 | 767 |
769 // This instruction is ignored if Linked->isDeleted() is true. | 768 // This instruction is ignored if Linked->isDeleted() is true. |
770 const Inst *Linked; | 769 const Inst *Linked; |
771 }; | 770 }; |
772 | 771 |
773 // The Target instruction is the base class for all target-specific | 772 // The Target instruction is the base class for all target-specific |
774 // instructions. | 773 // instructions. |
775 class InstTarget : public Inst { | 774 class InstTarget : public Inst { |
776 InstTarget(const InstTarget &) LLVM_DELETED_FUNCTION; | 775 InstTarget(const InstTarget &) = delete; |
777 InstTarget &operator=(const InstTarget &) LLVM_DELETED_FUNCTION; | 776 InstTarget &operator=(const InstTarget &) = delete; |
778 | 777 |
779 public: | 778 public: |
780 uint32_t getEmitInstCount() const override { return 1; } | 779 uint32_t getEmitInstCount() const override { return 1; } |
781 void dump(const Cfg *Func) const override; | 780 void dump(const Cfg *Func) const override; |
782 static bool classof(const Inst *Inst) { return Inst->getKind() >= Target; } | 781 static bool classof(const Inst *Inst) { return Inst->getKind() >= Target; } |
783 | 782 |
784 protected: | 783 protected: |
785 InstTarget(Cfg *Func, InstKind Kind, SizeT MaxSrcs, Variable *Dest) | 784 InstTarget(Cfg *Func, InstKind Kind, SizeT MaxSrcs, Variable *Dest) |
786 : Inst(Func, Kind, MaxSrcs, Dest) { | 785 : Inst(Func, Kind, MaxSrcs, Dest) { |
787 assert(Kind >= Target); | 786 assert(Kind >= Target); |
788 } | 787 } |
789 void emitIAS(const Cfg *Func) const override { emit(Func); } | 788 void emitIAS(const Cfg *Func) const override { emit(Func); } |
790 ~InstTarget() override {} | 789 ~InstTarget() override {} |
791 }; | 790 }; |
792 | 791 |
793 } // end of namespace Ice | 792 } // end of namespace Ice |
794 | 793 |
795 #endif // SUBZERO_SRC_ICEINST_H | 794 #endif // SUBZERO_SRC_ICEINST_H |
OLD | NEW |