From b70020aceb48b4ecf1ddce0145aed80b9f6bd915 Mon Sep 17 00:00:00 2001 From: Anna Henningsen Date: Mon, 21 Jul 2025 18:17:45 +0200 Subject: [PATCH 1/2] src: use C++20 `consteval` for `FastStringKey` This makes it easier to avoid unintentional mis-usage of the API. --- src/util-inl.h | 9 ++++++++- src/util.h | 8 +++++++- 2 files changed, 15 insertions(+), 2 deletions(-) diff --git a/src/util-inl.h b/src/util-inl.h index 3493732471fd95..778cc57537a966 100644 --- a/src/util-inl.h +++ b/src/util-inl.h @@ -618,7 +618,14 @@ constexpr bool FastStringKey::operator==(const FastStringKey& other) const { return name_ == other.name_; } -constexpr FastStringKey::FastStringKey(std::string_view name) +consteval FastStringKey::FastStringKey(std::string_view name) + : FastStringKey(name, 0) {} + +constexpr FastStringKey FastStringKey::AllowDynamic(std::string_view name) { + return FastStringKey(name, 0); +} + +constexpr FastStringKey::FastStringKey(std::string_view name, int dummy) : name_(name), cached_hash_(HashImpl(name)) {} constexpr std::string_view FastStringKey::as_string_view() const { diff --git a/src/util.h b/src/util.h index 5d4be8c90ade86..0719f7370fe64a 100644 --- a/src/util.h +++ b/src/util.h @@ -822,7 +822,11 @@ class PersistentToLocal { // computations. class FastStringKey { public: - constexpr explicit FastStringKey(std::string_view name); + // consteval ensures that the argument is a compile-time constant. + consteval explicit FastStringKey(std::string_view name); + // passing something that is not a compile-time constant needs explicit + // opt-in via this helper, as it defeats the purpose of FastStringKey. + static constexpr FastStringKey AllowDynamic(std::string_view name); struct Hash { constexpr size_t operator()(const FastStringKey& key) const; @@ -832,6 +836,8 @@ class FastStringKey { constexpr std::string_view as_string_view() const; private: + constexpr explicit FastStringKey(std::string_view name, int dummy); + static constexpr size_t HashImpl(std::string_view str); const std::string_view name_; From b8f684714834ac6e53cd986b3ea190a4cbf9a112 Mon Sep 17 00:00:00 2001 From: Anna Henningsen Date: Mon, 21 Jul 2025 18:18:44 +0200 Subject: [PATCH 2/2] src: use `FastStringKey` for `TrackV8FastApiCall` This is the exact intended use case of `FastStringKey`. --- src/node_debug.cc | 10 ++++++---- src/node_debug.h | 9 +++++---- 2 files changed, 11 insertions(+), 8 deletions(-) diff --git a/src/node_debug.cc b/src/node_debug.cc index 0f254b1fbfe820..bb0e11747e418c 100644 --- a/src/node_debug.cc +++ b/src/node_debug.cc @@ -23,13 +23,14 @@ using v8::Number; using v8::Object; using v8::Value; -thread_local std::unordered_map v8_fast_api_call_counts; +thread_local std::unordered_map + v8_fast_api_call_counts; -void TrackV8FastApiCall(std::string_view key) { +void TrackV8FastApiCall(FastStringKey key) { v8_fast_api_call_counts[key]++; } -int GetV8FastApiCallCount(std::string_view key) { +int GetV8FastApiCallCount(FastStringKey key) { return v8_fast_api_call_counts[key]; } @@ -40,7 +41,8 @@ void GetV8FastApiCallCount(const FunctionCallbackInfo& args) { return; } Utf8Value utf8_key(env->isolate(), args[0]); - args.GetReturnValue().Set(GetV8FastApiCallCount(utf8_key.ToStringView())); + args.GetReturnValue().Set(GetV8FastApiCallCount( + FastStringKey::AllowDynamic(utf8_key.ToStringView()))); } void SlowIsEven(const FunctionCallbackInfo& args) { diff --git a/src/node_debug.h b/src/node_debug.h index f42aeb8ba01162..32fbf21c813366 100644 --- a/src/node_debug.h +++ b/src/node_debug.h @@ -3,17 +3,18 @@ #if defined(NODE_WANT_INTERNALS) && NODE_WANT_INTERNALS #ifdef DEBUG -#include +#include "util.h" #endif // DEBUG namespace node { namespace debug { #ifdef DEBUG -void TrackV8FastApiCall(std::string_view key); -int GetV8FastApiCallCount(std::string_view key); +void TrackV8FastApiCall(FastStringKey key); +int GetV8FastApiCallCount(FastStringKey key); -#define TRACK_V8_FAST_API_CALL(key) node::debug::TrackV8FastApiCall(key) +#define TRACK_V8_FAST_API_CALL(key) \ + node::debug::TrackV8FastApiCall(FastStringKey(key)) #else // !DEBUG #define TRACK_V8_FAST_API_CALL(key) #endif // DEBUG