summaryrefslogtreecommitdiffstats
path: root/llvm
diff options
context:
space:
mode:
Diffstat (limited to 'llvm')
-rw-r--r--llvm/include/llvm/CodeGen/GlobalISel/LegalizerInfo.h60
-rw-r--r--llvm/lib/CodeGen/GlobalISel/LegalizeMutations.cpp7
-rw-r--r--llvm/lib/CodeGen/GlobalISel/LegalizerInfo.cpp1
-rw-r--r--llvm/lib/Target/AArch64/AArch64LegalizerInfo.cpp16
4 files changed, 73 insertions, 11 deletions
diff --git a/llvm/include/llvm/CodeGen/GlobalISel/LegalizerInfo.h b/llvm/include/llvm/CodeGen/GlobalISel/LegalizerInfo.h
index 117c791d299..af0242645a4 100644
--- a/llvm/include/llvm/CodeGen/GlobalISel/LegalizerInfo.h
+++ b/llvm/include/llvm/CodeGen/GlobalISel/LegalizerInfo.h
@@ -176,6 +176,8 @@ LegalityPredicate numElementsNotPow2(unsigned TypeIdx);
namespace LegalizeMutations {
/// Select this specific type for the given type index.
LegalizeMutation changeTo(unsigned TypeIdx, LLT Ty);
+/// Keep the same type as the given type index.
+LegalizeMutation changeTo(unsigned TypeIdx, unsigned FromTypeIdx);
/// Widen the type for the given type index to the next power of 2.
LegalizeMutation widenScalarToNextPow2(unsigned TypeIdx, unsigned Min = 0);
/// Add more elements to the type for the given type index to the next power of
@@ -235,7 +237,7 @@ class LegalizeRuleSet {
return *this;
}
/// Use the given action when the predicate is true.
- /// Action should not be an action that requires mutation.
+ /// Action should be an action that requires mutation.
LegalizeRuleSet &actionIf(LegalizeAction Action, LegalityPredicate Predicate,
LegalizeMutation Mutation) {
add({Predicate, Action, Mutation});
@@ -248,6 +250,14 @@ class LegalizeRuleSet {
using namespace LegalityPredicates;
return actionIf(Action, typeInSet(0, Types));
}
+ /// Use the given action when type index 0 is any type in the given list.
+ /// Action should be an action that requires mutation.
+ LegalizeRuleSet &actionFor(LegalizeAction Action,
+ std::initializer_list<LLT> Types,
+ LegalizeMutation Mutation) {
+ using namespace LegalityPredicates;
+ return actionIf(Action, typeInSet(0, Types), Mutation);
+ }
/// Use the given action when type indexes 0 and 1 is any type pair in the
/// given list.
/// Action should not be an action that requires mutation.
@@ -257,6 +267,15 @@ class LegalizeRuleSet {
using namespace LegalityPredicates;
return actionIf(Action, typePairInSet(0, 1, Types));
}
+ /// Use the given action when type indexes 0 and 1 is any type pair in the
+ /// given list.
+ /// Action should be an action that requires mutation.
+ LegalizeRuleSet &actionFor(LegalizeAction Action,
+ std::initializer_list<std::pair<LLT, LLT>> Types,
+ LegalizeMutation Mutation) {
+ using namespace LegalityPredicates;
+ return actionIf(Action, typePairInSet(0, 1, Types), Mutation);
+ }
/// Use the given action when type indexes 0 and 1 are both in the given list.
/// That is, the type pair is in the cartesian product of the list.
/// Action should not be an action that requires mutation.
@@ -315,6 +334,45 @@ public:
return actionForCartesianProduct(LegalizeAction::Legal, Types0, Types1);
}
+ /// The instruction is lowered.
+ LegalizeRuleSet &lower() {
+ using namespace LegalizeMutations;
+ return actionIf(LegalizeAction::Lower, always, changeTo(0, 0));
+ }
+ /// The instruction is lowered if predicate is true. Keep type index 0 as the
+ /// same type.
+ LegalizeRuleSet &lowerIf(LegalityPredicate Predicate) {
+ using namespace LegalizeMutations;
+ return actionIf(LegalizeAction::Lower, Predicate, changeTo(0, 0));
+ }
+ /// The instruction is lowered when type index 0 is any type in the given
+ /// list. Keep type index 0 as the same type.
+ LegalizeRuleSet &lowerFor(std::initializer_list<LLT> Types) {
+ using namespace LegalizeMutations;
+ return lowerFor(Types, changeTo(0, 0));
+ }
+ /// The instruction is lowered when type indexes 0 and 1 is any type pair in the
+ /// given list. Keep type index 0 as the same type.
+ LegalizeRuleSet &lowerFor(std::initializer_list<std::pair<LLT, LLT>> Types) {
+ return lowerFor(Types, LegalizeMutations::changeTo(0, 0));
+ }
+ /// The instruction is lowered when type indexes 0 and 1 is any type pair in the
+ /// given list.
+ LegalizeRuleSet &lowerFor(std::initializer_list<std::pair<LLT, LLT>> Types,
+ LegalizeMutation Mutation) {
+ return actionFor(LegalizeAction::Lower, Types, Mutation);
+ }
+ /// The instruction is lowered if predicate is true.
+ LegalizeRuleSet &lowerIf(LegalityPredicate Predicate,
+ LegalizeMutation Mutation) {
+ return actionIf(LegalizeAction::Lower, Predicate, Mutation);
+ }
+ /// The instruction is lowered when type index 0 is any type in the given list.
+ LegalizeRuleSet &lowerFor(std::initializer_list<LLT> Types,
+ LegalizeMutation Mutation) {
+ return actionFor(LegalizeAction::Lower, Types, Mutation);
+ }
+
/// Like legalIf, but for the Libcall action.
LegalizeRuleSet &libcallIf(LegalityPredicate Predicate) {
return actionIf(LegalizeAction::Libcall, Predicate);
diff --git a/llvm/lib/CodeGen/GlobalISel/LegalizeMutations.cpp b/llvm/lib/CodeGen/GlobalISel/LegalizeMutations.cpp
index 65a0c9e62be..a29b32ecdc0 100644
--- a/llvm/lib/CodeGen/GlobalISel/LegalizeMutations.cpp
+++ b/llvm/lib/CodeGen/GlobalISel/LegalizeMutations.cpp
@@ -20,6 +20,13 @@ LegalizeMutation LegalizeMutations::changeTo(unsigned TypeIdx, LLT Ty) {
[=](const LegalityQuery &Query) { return std::make_pair(TypeIdx, Ty); };
}
+LegalizeMutation LegalizeMutations::changeTo(unsigned TypeIdx,
+ unsigned FromTypeIdx) {
+ return [=](const LegalityQuery &Query) {
+ return std::make_pair(TypeIdx, Query.Types[FromTypeIdx]);
+ };
+}
+
LegalizeMutation LegalizeMutations::widenScalarToNextPow2(unsigned TypeIdx,
unsigned Min) {
return [=](const LegalityQuery &Query) {
diff --git a/llvm/lib/CodeGen/GlobalISel/LegalizerInfo.cpp b/llvm/lib/CodeGen/GlobalISel/LegalizerInfo.cpp
index 709bf353975..32fec80ec4a 100644
--- a/llvm/lib/CodeGen/GlobalISel/LegalizerInfo.cpp
+++ b/llvm/lib/CodeGen/GlobalISel/LegalizerInfo.cpp
@@ -64,6 +64,7 @@ LegalizeActionStep LegalizeRuleSet::apply(const LegalityQuery &Query) const {
DEBUG(dbgs() << ".. .. " << (unsigned)Rule.getAction() << ", "
<< Mutation.first << ", " << Mutation.second << "\n");
assert((Query.Types[Mutation.first] != Mutation.second ||
+ Rule.getAction() == Lower ||
Rule.getAction() == MoreElements ||
Rule.getAction() == FewerElements) &&
"Simple loop detected");
diff --git a/llvm/lib/Target/AArch64/AArch64LegalizerInfo.cpp b/llvm/lib/Target/AArch64/AArch64LegalizerInfo.cpp
index 083047c3814..0944b7a7231 100644
--- a/llvm/lib/Target/AArch64/AArch64LegalizerInfo.cpp
+++ b/llvm/lib/Target/AArch64/AArch64LegalizerInfo.cpp
@@ -81,14 +81,11 @@ AArch64LegalizerInfo::AArch64LegalizerInfo(const AArch64Subtarget &ST) {
.clampScalar(0, s32, s64)
.widenScalarToNextPow2(0);
- for (unsigned BinOp : {G_SREM, G_UREM})
- for (auto Ty : { s1, s8, s16, s32, s64 })
- setAction({BinOp, Ty}, Lower);
+ getActionDefinitionsBuilder({G_SREM, G_UREM})
+ .lowerFor({s1, s8, s16, s32, s64});
- for (unsigned Op : {G_SMULO, G_UMULO}) {
- setAction({Op, 0, s64}, Lower);
- setAction({Op, 1, s1}, Legal);
- }
+ getActionDefinitionsBuilder({G_SMULO, G_UMULO})
+ .lowerFor({{s64, s1}});
getActionDefinitionsBuilder({G_SMULH, G_UMULH}).legalFor({s32, s64});
@@ -242,9 +239,8 @@ AArch64LegalizerInfo::AArch64LegalizerInfo(const AArch64Subtarget &ST) {
}
if (ST.hasLSE()) {
- for (auto Ty : {s8, s16, s32, s64}) {
- setAction({G_ATOMIC_CMPXCHG_WITH_SUCCESS, Ty}, Lower);
- }
+ getActionDefinitionsBuilder(G_ATOMIC_CMPXCHG_WITH_SUCCESS)
+ .lowerFor({s8, s16, s32, s64});
getActionDefinitionsBuilder(
{G_ATOMICRMW_XCHG, G_ATOMICRMW_ADD, G_ATOMICRMW_SUB, G_ATOMICRMW_AND,
OpenPOWER on IntegriCloud