diff --git a/src/node_file-inl.h b/src/node_file-inl.h index e0fc86bedc741d..ebd97c1c8c5251 100644 --- a/src/node_file-inl.h +++ b/src/node_file-inl.h @@ -209,13 +209,7 @@ FSReqPromise::FSReqPromise(BindingData* binding_data, v8::Local obj, bool use_bigint) : FSReqBase( - binding_data, obj, AsyncWrap::PROVIDER_FSREQPROMISE, use_bigint), - stats_field_array_( - env()->isolate(), - static_cast(FsStatsOffset::kFsStatsFieldsNumber)), - statfs_field_array_( - env()->isolate(), - static_cast(FsStatFsOffset::kFsStatFsFieldsNumber)) {} + binding_data, obj, AsyncWrap::PROVIDER_FSREQPROMISE, use_bigint) {} template void FSReqPromise::Reject(v8::Local reject) { @@ -253,14 +247,24 @@ void FSReqPromise::Resolve(v8::Local value) { template void FSReqPromise::ResolveStat(const uv_stat_t* stat) { - FillStatsArray(&stats_field_array_, stat); - Resolve(stats_field_array_.GetJSArray()); + if (!stats_field_array_.has_value()) { + stats_field_array_.emplace( + env()->isolate(), + static_cast(FsStatsOffset::kFsStatsFieldsNumber)); + } + FillStatsArray(&stats_field_array_.value(), stat); + Resolve(stats_field_array_->GetJSArray()); } template void FSReqPromise::ResolveStatFs(const uv_statfs_t* stat) { - FillStatFsArray(&statfs_field_array_, stat); - Resolve(statfs_field_array_.GetJSArray()); + if (!statfs_field_array_.has_value()) { + statfs_field_array_.emplace( + env()->isolate(), + static_cast(FsStatFsOffset::kFsStatFsFieldsNumber)); + } + FillStatFsArray(&statfs_field_array_.value(), stat); + Resolve(statfs_field_array_->GetJSArray()); } template @@ -280,8 +284,12 @@ void FSReqPromise::SetReturnValue( template void FSReqPromise::MemoryInfo(MemoryTracker* tracker) const { FSReqBase::MemoryInfo(tracker); - tracker->TrackField("stats_field_array", stats_field_array_); - tracker->TrackField("statfs_field_array", statfs_field_array_); + if (stats_field_array_.has_value()) { + tracker->TrackField("stats_field_array", stats_field_array_.value()); + } + if (statfs_field_array_.has_value()) { + tracker->TrackField("statfs_field_array", statfs_field_array_.value()); + } } FSReqBase* GetReqWrap(const v8::FunctionCallbackInfo& args, diff --git a/src/node_file.h b/src/node_file.h index 17f3b4203c8edd..fab01a4c17b808 100644 --- a/src/node_file.h +++ b/src/node_file.h @@ -266,8 +266,11 @@ class FSReqPromise final : public FSReqBase { bool use_bigint); bool finished_ = false; - AliasedBufferT stats_field_array_; - AliasedBufferT statfs_field_array_; + // Constructed lazily in ResolveStat()/ResolveStatFs(): most operations + // never resolve with stats, and eagerly allocating the backing stores + // for every request is a significant per-request cost. + std::optional stats_field_array_; + std::optional statfs_field_array_; }; class FSReqAfterScope final {