about summary refs log tree commit diff
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2023-11-29 02:45:36 +0000
committerbors <bors@rust-lang.org>2023-11-29 02:45:36 +0000
commitf440b5f0ea042cb2087a36631b20878f9847ee28 (patch)
treecf204a92b3b76b64caf3fa66661373e473792da0
parentb1e56deadaf4b08cd591feaa1a1283348298427d (diff)
parent1487bd6a174f813967ffff6b3334b4fe296f1f30 (diff)
downloadrust-f440b5f0ea042cb2087a36631b20878f9847ee28.tar.gz
rust-f440b5f0ea042cb2087a36631b20878f9847ee28.zip
Auto merge of #118348 - Mark-Simulacrum:feature-code-size, r=compiler-errors
Cut code size for feature hashing

This locally cuts ~32 kB of .text instructions.

This isn't really a clear win in terms of readability. IMO the code size benefits are worth it (even if they're not necessarily present in the x86_64 hyperoptimized build, I expect them to translate similarly to other platforms). Ultimately there's lots of "small ish" low hanging fruit like this that I'm seeing that seems worth tackling to me, and could translate into larger wins in aggregate.
-rw-r--r--compiler/rustc_feature/src/unstable.rs12
-rw-r--r--compiler/rustc_query_system/src/ich/impls_syntax.rs8
2 files changed, 14 insertions, 6 deletions
diff --git a/compiler/rustc_feature/src/unstable.rs b/compiler/rustc_feature/src/unstable.rs
index e34661d5fc6..f73a286e6af 100644
--- a/compiler/rustc_feature/src/unstable.rs
+++ b/compiler/rustc_feature/src/unstable.rs
@@ -50,6 +50,8 @@ macro_rules! declare_features {
             }),+
         ];
 
+        const NUM_FEATURES: usize = UNSTABLE_FEATURES.len();
+
         /// A set of features to be used by later passes.
         #[derive(Clone, Default, Debug)]
         pub struct Features {
@@ -82,8 +84,14 @@ macro_rules! declare_features {
                 self.declared_features.insert(symbol);
             }
 
-            pub fn walk_feature_fields(&self, mut f: impl FnMut(&str, bool)) {
-                $(f(stringify!($feature), self.$feature);)+
+            /// This is intended for hashing the set of active features.
+            ///
+            /// The expectation is that this produces much smaller code than other alternatives.
+            ///
+            /// Note that the total feature count is pretty small, so this is not a huge array.
+            #[inline]
+            pub fn all_features(&self) -> [u8; NUM_FEATURES] {
+                [$(self.$feature as u8),+]
             }
 
             /// Is the given feature explicitly declared, i.e. named in a
diff --git a/compiler/rustc_query_system/src/ich/impls_syntax.rs b/compiler/rustc_query_system/src/ich/impls_syntax.rs
index 81a7eb604f5..f2387017c82 100644
--- a/compiler/rustc_query_system/src/ich/impls_syntax.rs
+++ b/compiler/rustc_query_system/src/ich/impls_syntax.rs
@@ -117,9 +117,9 @@ impl<'tcx> HashStable<StableHashingContext<'tcx>> for rustc_feature::Features {
         self.declared_lang_features.hash_stable(hcx, hasher);
         self.declared_lib_features.hash_stable(hcx, hasher);
 
-        self.walk_feature_fields(|feature_name, value| {
-            feature_name.hash_stable(hcx, hasher);
-            value.hash_stable(hcx, hasher);
-        });
+        self.all_features()[..].hash_stable(hcx, hasher);
+        for feature in rustc_feature::UNSTABLE_FEATURES.iter() {
+            feature.feature.name.hash_stable(hcx, hasher);
+        }
     }
 }