[llvm] [MC][TargetParser] Optimize SetImpliedBits. (PR #164583)
via llvm-commits
llvm-commits at lists.llvm.org
Wed Oct 22 02:10:07 PDT 2025
llvmbot wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-llvm-mc
Author: Weng Jinrui (wjr-z)
<details>
<summary>Changes</summary>
Optimize SetImpliedBits, avoid repeated updates multiple times
---
Full diff: https://github.com/llvm/llvm-project/pull/164583.diff
2 Files Affected:
- (modified) llvm/include/llvm/TargetParser/SubtargetFeature.h (+13)
- (modified) llvm/lib/MC/MCSubtargetInfo.cpp (+26-9)
``````````diff
diff --git a/llvm/include/llvm/TargetParser/SubtargetFeature.h b/llvm/include/llvm/TargetParser/SubtargetFeature.h
index a48b18745352a..a5bf1ef72fa68 100644
--- a/llvm/include/llvm/TargetParser/SubtargetFeature.h
+++ b/llvm/include/llvm/TargetParser/SubtargetFeature.h
@@ -20,6 +20,7 @@
#include "llvm/ADT/ArrayRef.h"
#include "llvm/ADT/STLExtras.h"
#include "llvm/ADT/StringRef.h"
+#include "llvm/ADT/bit.h"
#include "llvm/Support/Compiler.h"
#include "llvm/Support/MathExtras.h"
#include <array>
@@ -151,6 +152,18 @@ class FeatureBitset {
}
return false;
}
+
+ template <typename Func>
+ constexpr void forEachBit(Func func) const {
+ for (unsigned I = 0; I < MAX_SUBTARGET_WORDS; ++I) {
+ uint64_t Word = Bits[I];
+ while (Word) {
+ unsigned Bit = llvm::countr_zero(Word);
+ Word &= Word - 1;
+ func(I * 64 + Bit);
+ }
+ }
+ }
};
/// Class used to store the subtarget bits in the tables created by tablegen.
diff --git a/llvm/lib/MC/MCSubtargetInfo.cpp b/llvm/lib/MC/MCSubtargetInfo.cpp
index 89a08327dd259..77ea1bc5aa040 100644
--- a/llvm/lib/MC/MCSubtargetInfo.cpp
+++ b/llvm/lib/MC/MCSubtargetInfo.cpp
@@ -34,15 +34,32 @@ static const T *Find(StringRef S, ArrayRef<T> A) {
}
/// For each feature that is (transitively) implied by this feature, set it.
-static
-void SetImpliedBits(FeatureBitset &Bits, const FeatureBitset &Implies,
- ArrayRef<SubtargetFeatureKV> FeatureTable) {
- // OR the Implies bits in outside the loop. This allows the Implies for CPUs
- // which might imply features not in FeatureTable to use this.
- Bits |= Implies;
- for (const SubtargetFeatureKV &FE : FeatureTable)
- if (Implies.test(FE.Value))
- SetImpliedBits(Bits, FE.Implies.getAsBitset(), FeatureTable);
+static void SetImpliedBits(FeatureBitset &Bits, const FeatureBitset &Implies,
+ ArrayRef<SubtargetFeatureKV> FeatureTable) {
+ std::array<uint16_t, MAX_SUBTARGET_FEATURES> featureMap;
+ FeatureBitset Mask;
+ uint16_t idx = 0;
+ for (const auto &FE : FeatureTable) {
+ Mask.set(FE.Value);
+ featureMap[FE.Value] = idx++;
+ }
+
+ FeatureBitset impl(Implies);
+ while (true) {
+ Bits |= impl;
+ auto newImplies = Mask & impl;
+ if (newImplies.none()) {
+ break;
+ }
+
+ Mask ^= newImplies;
+ impl = FeatureBitset();
+
+ newImplies.forEachBit([&](unsigned Bit) {
+ unsigned idx = featureMap[Bit];
+ impl |= FeatureTable[idx].Implies.getAsBitset();
+ });
+ }
}
/// For each feature that (transitively) implies this feature, clear it.
``````````
</details>
https://github.com/llvm/llvm-project/pull/164583
More information about the llvm-commits
mailing list