|
15 | 15 | #include "llvm/CodeGen/CostTable.h" |
16 | 16 | #include "llvm/CodeGen/TargetLowering.h" |
17 | 17 | #include "llvm/IR/Constants.h" |
18 | | -#include "llvm/IR/IntrinsicInst.h" |
19 | 18 | #include "llvm/IR/Intrinsics.h" |
20 | 19 | #include "llvm/IR/IntrinsicsNVPTX.h" |
21 | 20 | #include "llvm/IR/Value.h" |
22 | 21 | #include "llvm/Support/Casting.h" |
23 | | -#include "llvm/Support/ErrorHandling.h" |
24 | 22 | #include "llvm/Transforms/InstCombine/InstCombiner.h" |
25 | 23 | #include <optional> |
26 | 24 | using namespace llvm; |
@@ -119,8 +117,7 @@ bool NVPTXTTIImpl::isSourceOfDivergence(const Value *V) { |
119 | 117 | } |
120 | 118 |
|
121 | 119 | // Convert NVVM intrinsics to target-generic LLVM code where possible. |
122 | | -static Instruction *convertNvvmIntrinsicToLlvm(InstCombiner &IC, |
123 | | - IntrinsicInst *II) { |
| 120 | +static Instruction *simplifyNvvmIntrinsic(IntrinsicInst *II, InstCombiner &IC) { |
124 | 121 | // Each NVVM intrinsic we can simplify can be replaced with one of: |
125 | 122 | // |
126 | 123 | // * an LLVM intrinsic, |
@@ -416,65 +413,11 @@ static Instruction *convertNvvmIntrinsicToLlvm(InstCombiner &IC, |
416 | 413 | llvm_unreachable("All SpecialCase enumerators should be handled in switch."); |
417 | 414 | } |
418 | 415 |
|
419 | | -// Returns an instruction pointer (may be nullptr if we do not know the answer). |
420 | | -// Returns nullopt if `II` is not one of the `isspacep` intrinsics. |
421 | | -static std::optional<Instruction *> |
422 | | -handleSpaceCheckIntrinsics(InstCombiner &IC, IntrinsicInst &II) { |
423 | | - Value *Op0 = II.getArgOperand(0); |
424 | | - // Returns true/false when we know the answer, nullopt otherwise. |
425 | | - auto CheckASMatch = [](unsigned IID, unsigned AS) -> std::optional<bool> { |
426 | | - if (AS == NVPTXAS::ADDRESS_SPACE_GENERIC || |
427 | | - AS == NVPTXAS::ADDRESS_SPACE_PARAM) |
428 | | - return std::nullopt; // Got to check at run-time. |
429 | | - switch (IID) { |
430 | | - case Intrinsic::nvvm_isspacep_global: |
431 | | - return AS == NVPTXAS::ADDRESS_SPACE_GLOBAL; |
432 | | - case Intrinsic::nvvm_isspacep_local: |
433 | | - return AS == NVPTXAS::ADDRESS_SPACE_LOCAL; |
434 | | - case Intrinsic::nvvm_isspacep_shared: |
435 | | - return AS == NVPTXAS::ADDRESS_SPACE_SHARED; |
436 | | - case Intrinsic::nvvm_isspacep_shared_cluster: |
437 | | - // We can't tell shared from shared_cluster at compile time from AS alone, |
438 | | - // but it can't be either is AS is not shared. |
439 | | - return AS == NVPTXAS::ADDRESS_SPACE_SHARED ? std::nullopt |
440 | | - : std::optional{false}; |
441 | | - case Intrinsic::nvvm_isspacep_const: |
442 | | - return AS == NVPTXAS::ADDRESS_SPACE_CONST; |
443 | | - default: |
444 | | - llvm_unreachable("Unexpected intrinsic"); |
445 | | - } |
446 | | - }; |
447 | | - |
448 | | - switch (auto IID = II.getIntrinsicID()) { |
449 | | - case Intrinsic::nvvm_isspacep_global: |
450 | | - case Intrinsic::nvvm_isspacep_local: |
451 | | - case Intrinsic::nvvm_isspacep_shared: |
452 | | - case Intrinsic::nvvm_isspacep_shared_cluster: |
453 | | - case Intrinsic::nvvm_isspacep_const: { |
454 | | - auto *Ty = II.getType(); |
455 | | - unsigned AS = Op0->getType()->getPointerAddressSpace(); |
456 | | - // Peek through ASC to generic AS. |
457 | | - // TODO: we could dig deeper through both ASCs and GEPs. |
458 | | - if (AS == NVPTXAS::ADDRESS_SPACE_GENERIC) |
459 | | - if (auto *ASCO = dyn_cast<AddrSpaceCastOperator>(Op0)) |
460 | | - AS = ASCO->getOperand(0)->getType()->getPointerAddressSpace(); |
461 | | - |
462 | | - if (std::optional<bool> Answer = CheckASMatch(IID, AS)) |
463 | | - return IC.replaceInstUsesWith(II, ConstantInt::get(Ty, *Answer)); |
464 | | - return nullptr; // Don't know the answer, got to check at run time. |
465 | | - } |
466 | | - default: |
467 | | - return std::nullopt; |
468 | | - } |
469 | | -} |
470 | | - |
471 | 416 | std::optional<Instruction *> |
472 | 417 | NVPTXTTIImpl::instCombineIntrinsic(InstCombiner &IC, IntrinsicInst &II) const { |
473 | | - if (std::optional<Instruction *> I = handleSpaceCheckIntrinsics(IC, II)) |
474 | | - return *I; |
475 | | - if (Instruction *I = convertNvvmIntrinsicToLlvm(IC, &II)) |
| 418 | + if (Instruction *I = simplifyNvvmIntrinsic(&II, IC)) { |
476 | 419 | return I; |
477 | | - |
| 420 | + } |
478 | 421 | return std::nullopt; |
479 | 422 | } |
480 | 423 |
|
|
0 commit comments