1 /*========================== begin_copyright_notice ============================
2
3 Copyright (C) 2017-2021 Intel Corporation
4
5 SPDX-License-Identifier: MIT
6
7 ============================= end_copyright_notice ===========================*/
8
9 #define DEBUG_TYPE "type-legalizer"
10 #include "TypeLegalizer.h"
11 #include "InstPromoter.h"
12 #include "llvmWrapper/IR/DerivedTypes.h"
13 #include "common/LLVMWarningsPush.hpp"
14 #include "llvm/Support/Debug.h"
15 #include "llvm/Support/MathExtras.h"
16 #include "llvm/Support/raw_ostream.h"
17 #include "llvmWrapper/IR/DerivedTypes.h"
18 #include "llvm/IR/Dominators.h"
19 #include "llvm/Transforms/Utils/Local.h"
20 #include "common/LLVMWarningsPop.hpp"
21 #include "Probe/Assertion.h"
22
23 using namespace llvm;
24 using namespace IGC::Legalizer;
25
promote(Instruction * I)26 bool InstPromoter::promote(Instruction* I) {
27 IRB->SetInsertPoint(&(*std::next(BasicBlock::iterator(I))));
28 IRB->SetCurrentDebugLocation(I->getDebugLoc());
29 Promoted = nullptr;
30
31 if (!visit(*I))
32 return false;
33
34 if (Promoted)
35 {
36 TL->setLegalizedValues(I, Promoted);
37 // In the case where we've only legalized the arguments to the instruction,
38 // we can go ahead and replace it with the new promoted instruction since
39 // the return types are the same.
40 if (I->getType() == Promoted->getType())
41 {
42 I->replaceAllUsesWith(Promoted);
43 }
44 else
45 {
46 // Need copy debug information for new legalized instruction
47 replaceAllDbgUsesWith(*I, *Promoted, *I, TL->getDominatorTree());
48 }
49 }
50
51 return true;
52 }
53
54 // By default, capture all missing instructions!
visitInstruction(Instruction & I)55 bool InstPromoter::visitInstruction(Instruction& I) {
56 LLVM_DEBUG(dbgs() << "PROMOTE: " << I << '\n');
57 IGC_ASSERT_EXIT_MESSAGE(0, "UNKNOWN INSTRUCTION IS BEING PROMOTED!");
58 return false;
59 }
60
61 /// Terminator instructions
62 ///
63
visitTerminatorInst(IGCLLVM::TerminatorInst & I)64 bool InstPromoter::visitTerminatorInst(IGCLLVM::TerminatorInst& I) {
65 // All terminators are handled specially.
66 return false;
67 }
68
visitSelectInst(SelectInst & I)69 bool InstPromoter::visitSelectInst(SelectInst& I) {
70
71 ValueSeq* Ops0, * Ops1;
72 std::tie(Ops0, std::ignore) = TL->getLegalizedValues(I.getOperand(1), true);
73 IGC_ASSERT(Ops0 != nullptr && Ops0->size() == 1);
74 // we should get value from Ops0 here, as next getLegalizedValues call may grow ValueMap object
75 // when inserting new pair with ValueMap.insert(e.g.when ValueMap.NumBuckets grows from 64 to 128)
76 // and previously received ValueSeq objects will become invalid.
77 Value* LHS = Ops0->front();
78
79 std::tie(Ops1, std::ignore) = TL->getLegalizedValues(I.getOperand(2), true);
80 IGC_ASSERT(Ops1 != nullptr && Ops1->size() == 1);
81 Value* RHS = Ops1->front();
82
83 Promoted = IRB->CreateSelect(I.getOperand(0), LHS, RHS,
84 Twine(I.getName(), getSuffix()));
85
86 return true;
87 }
88
visitICmpInst(ICmpInst & I)89 bool InstPromoter::visitICmpInst(ICmpInst& I)
90 {
91 bool isSigned = I.isSigned();
92
93 ValueSeq* Ops0, * Ops1;
94 std::tie(Ops0, std::ignore) = TL->getLegalizedValues(I.getOperand(0), isSigned);
95 IGC_ASSERT(Ops0 != nullptr && Ops0->size() == 1);
96 // we should get value from Ops0 here, as next getLegalizedValues call may grow ValueMap object
97 // when inserting new pair with ValueMap.insert(e.g.when ValueMap.NumBuckets grows from 64 to 128)
98 // and previously received ValueSeq objects will become invalid.
99 Value* LHS = Ops0->front();
100
101 std::tie(Ops1, std::ignore) = TL->getLegalizedValues(I.getOperand(1), isSigned);
102 IGC_ASSERT(Ops1 != nullptr && Ops1->size() == 1);
103 Value* RHS = Ops1->front();
104
105 unsigned initialWidth = I.getOperand(0)->getType()->getIntegerBitWidth();
106 unsigned finalWidth = LHS->getType()->getIntegerBitWidth();
107
108 if (!isSigned)
109 {
110 LHS = IRB->CreateAnd(LHS, (1 << initialWidth) - 1);
111 RHS = IRB->CreateAnd(RHS, (1 << initialWidth) - 1);
112 }
113 else
114 {
115 IGC_ASSERT(finalWidth >= initialWidth);
116
117 unsigned shiftAmt = finalWidth - initialWidth;
118
119 LHS = IRB->CreateShl(LHS, shiftAmt);
120 LHS = IRB->CreateAShr(LHS, shiftAmt);
121 RHS = IRB->CreateShl(RHS, shiftAmt);
122 RHS = IRB->CreateAShr(RHS, shiftAmt);
123 }
124
125 Promoted = IRB->CreateICmp(I.getPredicate(), LHS, RHS,
126 Twine(I.getName(), getSuffix()));
127
128 return true;
129 }
130
131 /// Standard binary operators
132 ///
133
visitBinaryOperator(BinaryOperator & I)134 bool InstPromoter::visitBinaryOperator(BinaryOperator& I) {
135 ValueSeq* Ops0, * Ops1;
136 std::tie(Ops0, std::ignore) = TL->getLegalizedValues(I.getOperand(0));
137 IGC_ASSERT(Ops0 != nullptr && Ops0->size() == 1);
138 // we should get value from Ops0 here, as next getLegalizedValues call may grow ValueMap object
139 // when inserting new pair with ValueMap.insert(e.g.when ValueMap.NumBuckets grows from 64 to 128)
140 // and previously received ValueSeq objects will become invalid.
141 Value* LHS = Ops0->front();
142
143 std::tie(Ops1, std::ignore) = TL->getLegalizedValues(I.getOperand(1));
144 IGC_ASSERT(Ops1 != nullptr && Ops1->size() == 1);
145 Value* RHS = Ops1->front();
146
147 switch (I.getOpcode()) {
148 case Instruction::Add:
149 case Instruction::Sub:
150 case Instruction::Mul:
151 case Instruction::And:
152 case Instruction::Or:
153 case Instruction::Xor:
154 break;
155 case Instruction::UDiv:
156 case Instruction::URem:
157 std::tie(LHS, RHS) = TL->zext(LHS, RHS, I.getType());
158 break;
159 case Instruction::SDiv:
160 case Instruction::SRem:
161 std::tie(LHS, RHS) = TL->sext(LHS, RHS, I.getType());
162 break;
163 case Instruction::Shl:
164 RHS = TL->zext(RHS, I.getType());
165 break;
166 case Instruction::LShr:
167 std::tie(LHS, RHS) = TL->zext(LHS, RHS, I.getType());
168 break;
169 case Instruction::AShr:
170 LHS = TL->sext(LHS, I.getType());
171 RHS = TL->zext(RHS, I.getType());
172 break;
173 default:
174 IGC_ASSERT_EXIT_MESSAGE(0, "UNKNOWN BINARY OPERATOR IS BEING PROMOTED!");
175 }
176
177 Promoted =
178 TL->createBinOpAsGiven(&I, LHS, RHS, Twine(I.getName(), getSuffix()));
179
180 return true;
181 }
182
183 /// Memory operators
184 ///
185
visitLoadInst(LoadInst & I)186 bool InstPromoter::visitLoadInst(LoadInst& I) {
187 Type* OrigTy = I.getType();
188
189 TypeSeq* TySeq;
190 std::tie(TySeq, std::ignore) = TL->getLegalizedTypes(OrigTy);
191 IGC_ASSERT(TySeq != nullptr && TySeq->size() == 1);
192
193 unsigned AS = I.getPointerAddressSpace();
194
195 Value* OldPtr = I.getPointerOperand();
196 Type* PromotedTy = TySeq->front();
197
198 Value* NewBasePtr =
199 IRB->CreatePointerCast(OldPtr, IRB->getInt8PtrTy(AS),
200 Twine(OldPtr->getName(), ".ptrcast"));
201
202 // Different from promotion of regular instructions, such as 'add', promotion
203 // of load is required to split the original load into small ones and
204 // concatenate them together, e.g. i56 needs splitting into loads of i32,
205 // i16, and i8. It's because, without alignment checking, out-of-bound load
206 // may be generated if the promoted type is used directly.
207
208 Value* PromotedVal = Constant::getNullValue(PromotedTy);
209 unsigned Off = 0;
210 unsigned Part = 0;
211 for (unsigned TotalLoadBits = TL->getTypeStoreSizeInBits(OrigTy),
212 ActualLoadBits = 0; TotalLoadBits != 0;
213 TotalLoadBits -= ActualLoadBits) {
214 // Get the largest integer type but not bigger than total load bits.
215 ActualLoadBits = TL->getLargestLegalIntTypeSize(TotalLoadBits);
216
217 Type* NewTy = TL->getIntNTy(ActualLoadBits);
218 Type* NewPtrTy = PointerType::get(NewTy, AS);
219
220 Value* NewPtr =
221 TL->getPointerToElt(NewBasePtr, Off, NewPtrTy,
222 Twine(NewBasePtr->getName(), ".off") + Twine(Off));
223
224 LoadInst* NewLd =
225 IRB->CreateLoad(NewPtr, Twine(I.getName(), getSuffix()) + Twine(Part));
226 TL->dupMemoryAttribute(NewLd, &I, Off);
227
228 Value* NewVal =
229 IRB->CreateZExt(NewLd, PromotedTy, Twine(NewLd->getName(), ".zext"));
230 NewVal = TL->shl(NewVal, Off << 3);
231 PromotedVal =
232 IRB->CreateOr(PromotedVal, NewVal, Twine(NewVal->getName(), ".concat"));
233
234 IGC_ASSERT_MESSAGE((ActualLoadBits & 0x7) == 0, "LEGAL INTEGER TYPE IS NOT BYTE ADDRESSABLE!");
235 Off += ActualLoadBits >> 3;
236 ++Part;
237 }
238
239 Promoted = PromotedVal;
240 return true;
241 }
242
visitStoreInst(StoreInst & I)243 bool InstPromoter::visitStoreInst(StoreInst& I) {
244 Value* OrigVal = I.getValueOperand();
245 Type* OrigTy = OrigVal->getType();
246
247 ValueSeq* ValSeq;
248 std::tie(ValSeq, std::ignore) = TL->getLegalizedValues(OrigVal);
249 IGC_ASSERT(ValSeq != nullptr && ValSeq->size() == 1);
250
251 unsigned AS = I.getPointerAddressSpace();
252
253 Value* OldPtr = I.getPointerOperand();
254 Value* PromotedVal = ValSeq->front();
255
256 Value* NewBasePtr =
257 IRB->CreatePointerCast(OldPtr, IRB->getInt8PtrTy(AS),
258 Twine(OldPtr->getName(), ".ptrcast"));
259
260 unsigned Off = 0;
261 for (unsigned TotalStoreBits = TL->getTypeStoreSizeInBits(OrigTy),
262 ActualStoreBits = 0; TotalStoreBits != 0;
263 TotalStoreBits -= ActualStoreBits) {
264
265 // Get the largest integer type but not bigger than total store bits.
266 ActualStoreBits = TL->getLargestLegalIntTypeSize(TotalStoreBits);
267
268 Type* NewTy = TL->getIntNTy(ActualStoreBits);
269 Type* NewPtrTy = PointerType::get(NewTy, AS);
270
271 Value* NewPtr =
272 TL->getPointerToElt(NewBasePtr, Off, NewPtrTy,
273 Twine(NewBasePtr->getName(), ".off") + Twine(Off));
274
275 Value* NewVal = TL->lshr(PromotedVal, Off << 3);
276 NewVal =
277 IRB->CreateTrunc(NewVal, NewTy, Twine(NewVal->getName(), ".trunc"));
278
279 StoreInst* NewSt = IRB->CreateStore(NewVal, NewPtr);
280 TL->dupMemoryAttribute(NewSt, &I, Off);
281
282 IGC_ASSERT_MESSAGE((ActualStoreBits & 0x7) == 0, "LEGAL INTEGER TYPE IS NOT BYTE ADDRESSABLE!");
283 Off += ActualStoreBits >> 3;
284 }
285
286 return true;
287 }
288
289 /// Cast operators
290
visitTruncInst(TruncInst & I)291 bool InstPromoter::visitTruncInst(TruncInst& I) {
292 ValueSeq* ValSeq; LegalizeAction ValAct;
293 std::tie(ValSeq, ValAct) = TL->getLegalizedValues(I.getOperand(0));
294
295 Value* Val = I.getOperand(0);
296 if (ValAct != Legal)
297 Val = ValSeq->front();
298
299 TypeSeq* TySeq; LegalizeAction Act;
300 std::tie(TySeq, Act) = TL->getLegalizedTypes(I.getDestTy());
301 IGC_ASSERT(Act == Legal || Act == Promote);
302
303 if (Act == Legal) {
304 if (Val->getType() == I.getType())
305 I.replaceAllUsesWith(Val);
306 else
307 I.setOperand(0, Val);
308
309 return true;
310 }
311
312 IGC_ASSERT(TySeq->size() == 1);
313
314 Type* PromotedTy = TySeq->front();
315
316 IGC_ASSERT(cast<IntegerType>(PromotedTy)->getBitWidth() <= cast<IntegerType>(Val->getType())->getBitWidth());
317
318 Promoted =
319 IRB->CreateTrunc(Val, PromotedTy, Twine(I.getName(), getSuffix()));
320
321 return true;
322 }
323
visitZExtInst(ZExtInst & I)324 bool InstPromoter::visitZExtInst(ZExtInst& I) {
325 ValueSeq* ValSeq; LegalizeAction ValAct;
326 std::tie(ValSeq, ValAct) = TL->getLegalizedValues(I.getOperand(0));
327
328 Value* Val = I.getOperand(0);
329 if (ValAct != Legal)
330 Val = ValSeq->front();
331
332 TypeSeq* TySeq; LegalizeAction Act;
333 std::tie(TySeq, Act) = TL->getLegalizedTypes(I.getDestTy());
334 IGC_ASSERT(Act == Legal || Act == Promote);
335
336 if (Act == Legal) {
337 // Reset insert position as we don't create a new instruction from the
338 // original one due to the legal return type.
339 IRB->SetInsertPoint(&I);
340
341 if (ValAct != Legal)
342 Val = TL->zext(Val, I.getSrcTy());
343
344 if (Val->getType() == I.getType())
345 I.replaceAllUsesWith(Val);
346 else
347 I.setOperand(0, Val);
348
349 return true;
350 }
351
352 IGC_ASSERT(TySeq->size() == 1);
353
354 Type* PromotedTy = TySeq->front();
355
356 IGC_ASSERT(cast<IntegerType>(PromotedTy)->getBitWidth() >= cast<IntegerType>(Val->getType())->getBitWidth());
357
358 if (ValAct != Legal)
359 Val = TL->zext(Val, I.getSrcTy());
360
361 Promoted =
362 IRB->CreateZExt(Val, PromotedTy, Twine(I.getName(), getSuffix()));
363
364 return true;
365 }
366
visitBitCastInst(BitCastInst & I)367 bool InstPromoter::visitBitCastInst(BitCastInst& I) {
368 ValueSeq* ValSeq;
369 LegalizeAction ValAct;
370 std::tie(ValSeq, ValAct) = TL->getLegalizedValues(I.getOperand(0));
371 Value* Val = I.getOperand(0);
372 if (ValAct != Legal && ValSeq != nullptr)
373 Val = ValSeq->front();
374
375 TypeSeq* TySeq;
376 LegalizeAction Act;
377 std::tie(TySeq, Act) = TL->getLegalizedTypes(I.getDestTy());
378 IGC_ASSERT(Act == Legal || Act == Promote);
379
380 // Promote bitcast i24 %0 to <3 x i8>
381 // -->
382 // %1 = bitcast i32 %0 to <4 x i8>
383 // %2 = shufflevector <4 x i8> %1, <4 x i8> zeroinitializer, <i32 0, i32 1, i32 2>
384 if (Act == Legal && ValAct == Promote && Val->getType()->isIntegerTy() &&
385 I.getType()->isVectorTy()) {
386 Type* DestTy = I.getDestTy();
387 unsigned N =
388 Val->getType()->getScalarSizeInBits() / DestTy->getScalarSizeInBits();
389 Value* BC =
390 IRB->CreateBitCast(Val, IGCLLVM::FixedVectorType::get(DestTy->getScalarType(), N));
391
392 std::vector<Constant*> Vals;
393 for (unsigned i = 0; i < (unsigned)cast<IGCLLVM::FixedVectorType>(DestTy)->getNumElements(); i++)
394 Vals.push_back(IRB->getInt32(i));
395
396 Value* Mask = ConstantVector::get(Vals);
397 Value* Zero = Constant::getNullValue(BC->getType());
398 Promoted = IRB->CreateShuffleVector(BC, Zero, Mask,
399 Twine(I.getName(), getSuffix()));
400 return true;
401 }
402
403 // Promote bitcast <3 x i8> %0 to i24
404 // -->
405 // %1 = shufflevector <3 x i8> %0, <3 x i8> zeroinitializer, <i32 0, i32 1, i32 2, i32 3>
406 // %2 = bitcast <4 x i8> %1 to i32
407 if (Act == Promote && Val->getType()->isVectorTy() &&
408 I.getType()->isIntegerTy()) {
409 Type* PromotedTy = TySeq->front();
410 unsigned N = PromotedTy->getScalarSizeInBits() /
411 Val->getType()->getScalarSizeInBits();
412 std::vector<Constant*> Vals;
413 for (unsigned i = 0; i < N; i++)
414 Vals.push_back(IRB->getInt32(i));
415
416 Value* Mask = ConstantVector::get(Vals);
417 Value* Zero = Constant::getNullValue(Val->getType());
418 Value* NewVal = IRB->CreateShuffleVector(Val, Zero, Mask,
419 Twine(I.getName(), getSuffix()));
420 Promoted = IRB->CreateBitCast(NewVal, PromotedTy);
421 return true;
422 }
423
424 // Promote bitcast with illegal src and dst both requiring to be promoted
425 // to the same type. Example:
426 //
427 // bitcast i12 %v to <3 x i4>
428 //
429 // '%v' may just be used as a promoted value, since both i12 and <3 x i4> are
430 // required to be promoted to i16 type.
431 if (Act == Promote && ValAct == Promote &&
432 Val->getType() == TySeq->front()) {
433 Promoted = Val;
434 return true;
435 }
436
437 // Unsupported legalization action.
438 return false;
439 }
440
visitExtractElementInst(ExtractElementInst & I)441 bool InstPromoter::visitExtractElementInst(ExtractElementInst& I) {
442 ValueSeq* ValSeq; LegalizeAction ValAct;
443 Value* Val = I.getOperand(0);
444 std::tie(ValSeq, ValAct) = TL->getLegalizedValues(Val);
445
446 if (ValAct != Legal)
447 Val = ValSeq->front();
448
449 TypeSeq* TySeq; LegalizeAction Act;
450 std::tie(TySeq, Act) = TL->getLegalizedTypes(I.getType());
451 IGC_ASSERT(Act == Legal || Act == Promote);
452
453 auto SetBits = [](uint64_t& Data, uint32_t From, uint32_t To) {
454 IGC_ASSERT(From < To);
455 uint64_t N = To - From;
456 uint64_t Mask = (0xFFFFFFFFFFFFFFFFu >> (64 - N));
457 Data |= (Mask << From);
458 };
459
460 if (Act == Promote && Val->getType()->isIntegerTy()) {
461 if (ConstantInt* Index = dyn_cast<ConstantInt>(I.getIndexOperand())) {
462 const uint32_t IndexImm = int_cast<uint32_t>(Index->getZExtValue());
463 const uint32_t IllegalElemTyWidth = I.getOperand(0)->getType()->getScalarSizeInBits();
464
465 // Mask preparation
466 uint64_t Mask = 0;
467 const uint32_t From = IndexImm * IllegalElemTyWidth;
468 const uint32_t To = From + IllegalElemTyWidth;
469 SetBits(Mask, From, To);
470
471 // Clear bits representing source vector elements that are not queried by
472 // extract element instruction
473 Value* And = IRB->CreateAnd(Val, Mask);
474
475 // Shift relevant bits to put sign bit on it's place
476 Type* LegalReturnTy = TySeq->front();
477 const uint32_t LegalReturnTyWidth = LegalReturnTy->getIntegerBitWidth();
478 const uint32_t CurrSignPos = To - 1;
479 const uint32_t TargetSignPos = LegalReturnTyWidth - 1;
480 Value* Shift = nullptr;
481 if (CurrSignPos == TargetSignPos) {
482 // Continue operating on 'and' instruction. Shifting is not required,
483 // since sign bit is already in place.
484 Shift = And;
485 }
486 else {
487 if (CurrSignPos < TargetSignPos) {
488 Shift = IRB->CreateShl(And, TargetSignPos - CurrSignPos);
489 }
490 else if (CurrSignPos > TargetSignPos) {
491 Shift = IRB->CreateLShr(And, CurrSignPos - TargetSignPos);
492 }
493 }
494
495 // Truncate result to a legalized type
496 Value* Trunc = IRB->CreateTrunc(Shift, LegalReturnTy);
497
498 // Shift bits back to put relevant ones at the begging of an integer
499 IGC_ASSERT(LegalReturnTyWidth > IllegalElemTyWidth);
500 Promoted = IRB->CreateAShr(Trunc, LegalReturnTyWidth - IllegalElemTyWidth);
501
502 return true;
503 }
504 else {
505 IGC_ASSERT_MESSAGE(0, "Cannot legalize extract element instruction with non-constant index!");
506 return false;
507 }
508 }
509
510 return false;
511 }
512
visitInsertElementInst(InsertElementInst & I)513 bool InstPromoter::visitInsertElementInst(InsertElementInst& I) {
514 ValueSeq* ValSeq; LegalizeAction ValAct;
515 Value* Val = I.getOperand(1);
516 std::tie(ValSeq, ValAct) = TL->getLegalizedValues(Val);
517
518 if (ValAct != Legal)
519 Val = ValSeq->front();
520
521 Value* VecVal = I.getOperand(0);
522 if (!isa<UndefValue>(VecVal)) {
523 ValueSeq* VecValSeq; LegalizeAction VecValAct;
524 std::tie(VecValSeq, VecValAct) = TL->getLegalizedValues(VecVal);
525
526 if (VecValAct != Legal)
527 VecVal = VecValSeq->front();
528 }
529
530 TypeSeq* TySeq; LegalizeAction Act;
531 std::tie(TySeq, Act) = TL->getLegalizedTypes(I.getType());
532 IGC_ASSERT(Act == Legal || Act == Promote);
533
534 if (Act == Promote && Val->getType()->isIntegerTy()) {
535 if (ConstantInt* Index = dyn_cast<ConstantInt>(I.getOperand(2))) {
536 // Extend value to be inserted to the legalized insert element return type
537 Value* ZExt = IRB->CreateZExt(Val, TySeq->front());
538
539 // Shift extended value to it's place based on index to imitate insert element behavior
540 // Note: If an insert element index is zero, we don't need to generate shl instruction.
541 const uint32_t IllegalElemTyWidth = I.getOperand(0)->getType()->getScalarSizeInBits();
542 const uint32_t IndexImm = int_cast<uint32_t>(Index->getZExtValue());
543 const uint32_t ShiftFactor = IndexImm * IllegalElemTyWidth;
544 Promoted = (IndexImm > 0) ? IRB->CreateShl(ZExt, ShiftFactor) : ZExt;
545
546 if (!isa<UndefValue>(VecVal)) {
547 // Generate 'and' instruction to merge value returned by another insert element instruction
548 // with value to be inserted.
549 IGC_ASSERT(VecVal->getType()->isIntegerTy());
550 Promoted = IRB->CreateAnd(VecVal, Promoted);
551 }
552 }
553 else {
554 IGC_ASSERT_MESSAGE(0, "Cannot legalize insert element instruction with non-constant index!");
555 return false;
556 }
557 }
558
559 return true;
560 }
561
562 /// Other operators
563
visitGenIntrinsicInst(GenIntrinsicInst & I)564 bool InstPromoter::visitGenIntrinsicInst(GenIntrinsicInst& I) {
565 IGC_ASSERT_EXIT_MESSAGE(0, "UNKNOWN GEN INSTRINSIC INSTRUCTION IS BEING PROMOTED!");
566 return false;
567 }
568
visitCallInst(CallInst & I)569 bool InstPromoter::visitCallInst(CallInst& I) {
570 if (isa<GenIntrinsicInst>(&I))
571 return visitGenIntrinsicInst(static_cast<GenIntrinsicInst&>(I));
572 IGC_ASSERT_EXIT_MESSAGE(0, "NOT IMPLEMENTED YET!");
573 return false;
574 }
575