aboutsummaryrefslogtreecommitdiff
path: root/llvm/utils/TableGen/CodeGenSchedule.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'llvm/utils/TableGen/CodeGenSchedule.cpp')
-rw-r--r--llvm/utils/TableGen/CodeGenSchedule.cpp47
1 files changed, 33 insertions, 14 deletions
diff --git a/llvm/utils/TableGen/CodeGenSchedule.cpp b/llvm/utils/TableGen/CodeGenSchedule.cpp
index 04219a6e54d9..54463da19821 100644
--- a/llvm/utils/TableGen/CodeGenSchedule.cpp
+++ b/llvm/utils/TableGen/CodeGenSchedule.cpp
@@ -91,10 +91,25 @@ struct InstRegexOp : public SetTheory::Operator {
PrintFatalError(Loc, "instregex requires pattern string: " +
Expr->getAsString());
StringRef Original = SI->getValue();
+ // Drop an explicit ^ anchor to not interfere with prefix search.
+ bool HadAnchor = Original.consume_front("^");
// Extract a prefix that we can binary search on.
static const char RegexMetachars[] = "()^$|*+?.[]\\{}";
auto FirstMeta = Original.find_first_of(RegexMetachars);
+ if (FirstMeta != StringRef::npos && FirstMeta > 0) {
+ // If we have a regex like ABC* we can only use AB as the prefix, as
+ // the * acts on C.
+ switch (Original[FirstMeta]) {
+ case '+':
+ case '*':
+ case '?':
+ --FirstMeta;
+ break;
+ default:
+ break;
+ }
+ }
// Look for top-level | or ?. We cannot optimize them to binary search.
if (removeParens(Original).find_first_of("|?") != std::string::npos)
@@ -106,7 +121,10 @@ struct InstRegexOp : public SetTheory::Operator {
if (!PatStr.empty()) {
// For the rest use a python-style prefix match.
std::string pat = std::string(PatStr);
- if (pat[0] != '^') {
+ // Add ^ anchor. If we had one originally, don't need the group.
+ if (HadAnchor) {
+ pat.insert(0, "^");
+ } else {
pat.insert(0, "^(");
pat.insert(pat.end(), ')');
}
@@ -118,7 +136,7 @@ struct InstRegexOp : public SetTheory::Operator {
// The generic opcodes are unsorted, handle them manually.
for (auto *Inst : Generics) {
StringRef InstName = Inst->TheDef->getName();
- if (InstName.startswith(Prefix) &&
+ if (InstName.starts_with(Prefix) &&
(!Regexpr || Regexpr->match(InstName.substr(Prefix.size())))) {
Elts.insert(Inst->TheDef);
NumMatches++;
@@ -134,7 +152,7 @@ struct InstRegexOp : public SetTheory::Operator {
}
bool operator()(StringRef LHS, const CodeGenInstruction *RHS) {
return LHS < RHS->TheDef->getName() &&
- !RHS->TheDef->getName().startswith(LHS);
+ !RHS->TheDef->getName().starts_with(LHS);
}
};
auto Range1 =
@@ -369,19 +387,20 @@ processSTIPredicate(STIPredicateFunction &Fn,
const std::pair<APInt, APInt> &LhsMasks = OpcodeMasks[LhsIdx];
const std::pair<APInt, APInt> &RhsMasks = OpcodeMasks[RhsIdx];
- auto LessThan = [](const APInt &Lhs, const APInt &Rhs) {
- unsigned LhsCountPopulation = Lhs.popcount();
- unsigned RhsCountPopulation = Rhs.popcount();
- return ((LhsCountPopulation < RhsCountPopulation) ||
- ((LhsCountPopulation == RhsCountPopulation) &&
- (Lhs.countl_zero() > Rhs.countl_zero())));
+ auto PopulationCountAndLeftBit =
+ [](const APInt &Other) -> std::pair<int, int> {
+ return std::pair<int, int>(Other.popcount(),
+ -Other.countl_zero());
};
+ auto lhsmask_first = PopulationCountAndLeftBit(LhsMasks.first);
+ auto rhsmask_first = PopulationCountAndLeftBit(RhsMasks.first);
+ if (lhsmask_first != rhsmask_first)
+ return lhsmask_first < rhsmask_first;
- if (LhsMasks.first != RhsMasks.first)
- return LessThan(LhsMasks.first, RhsMasks.first);
-
- if (LhsMasks.second != RhsMasks.second)
- return LessThan(LhsMasks.second, RhsMasks.second);
+ auto lhsmask_second = PopulationCountAndLeftBit(LhsMasks.second);
+ auto rhsmask_second = PopulationCountAndLeftBit(RhsMasks.second);
+ if (lhsmask_second != rhsmask_second)
+ return lhsmask_second < rhsmask_second;
return LhsIdx < RhsIdx;
});