GCC Code Coverage Report
Directory: ../ Exec Total Coverage
File: /home/iojs/build/workspace/node-test-commit-linux-coverage-daily/nodes/benchmark/out/../src/node_native_module_env.cc Lines: 95 99 96.0 %
Date: 2020-07-19 22:14:24 Branches: 11 16 68.8 %

Line Branch Exec Source
1
#include "node_native_module_env.h"
2
#include "env-inl.h"
3
#include "node_external_reference.h"
4
5
namespace node {
6
namespace native_module {
7
8
using v8::Context;
9
using v8::DEFAULT;
10
using v8::Function;
11
using v8::FunctionCallbackInfo;
12
using v8::IntegrityLevel;
13
using v8::Isolate;
14
using v8::Local;
15
using v8::MaybeLocal;
16
using v8::Name;
17
using v8::None;
18
using v8::Object;
19
using v8::PropertyCallbackInfo;
20
using v8::Set;
21
using v8::SideEffectType;
22
using v8::String;
23
using v8::Value;
24
25
// TODO(joyeecheung): make these more general and put them into util.h
26
6
Local<Set> ToJsSet(Local<Context> context, const std::set<std::string>& in) {
27
6
  Isolate* isolate = context->GetIsolate();
28
6
  Local<Set> out = Set::New(isolate);
29
621
  for (auto const& x : in) {
30
1845
    out->Add(context, OneByteString(isolate, x.c_str(), x.size()))
31
        .ToLocalChecked();
32
  }
33
6
  return out;
34
}
35
36
13
bool NativeModuleEnv::Add(const char* id, const UnionBytes& source) {
37
13
  return NativeModuleLoader::GetInstance()->Add(id, source);
38
}
39
40
bool NativeModuleEnv::Exists(const char* id) {
41
  return NativeModuleLoader::GetInstance()->Exists(id);
42
}
43
44
6
Local<Object> NativeModuleEnv::GetSourceObject(Local<Context> context) {
45
6
  return NativeModuleLoader::GetInstance()->GetSourceObject(context);
46
}
47
48
390
Local<String> NativeModuleEnv::GetConfigString(Isolate* isolate) {
49
390
  return NativeModuleLoader::GetInstance()->GetConfigString(isolate);
50
}
51
52
2
void NativeModuleEnv::GetModuleCategories(
53
    Local<Name> property, const PropertyCallbackInfo<Value>& info) {
54
2
  Environment* env = Environment::GetCurrent(info);
55
2
  Isolate* isolate = env->isolate();
56
2
  Local<Context> context = env->context();
57
2
  Local<Object> result = Object::New(isolate);
58
59
  // Copy from the per-process categories
60
  std::set<std::string> cannot_be_required =
61
4
      NativeModuleLoader::GetInstance()->GetCannotBeRequired();
62
  std::set<std::string> can_be_required =
63
4
      NativeModuleLoader::GetInstance()->GetCanBeRequired();
64
65
2
  if (!env->owns_process_state()) {
66
    can_be_required.erase("trace_events");
67
    cannot_be_required.insert("trace_events");
68
  }
69
70
  result
71
4
      ->Set(context,
72
            OneByteString(isolate, "cannotBeRequired"),
73
8
            ToJsSet(context, cannot_be_required))
74
      .FromJust();
75
  result
76
4
      ->Set(context,
77
            OneByteString(isolate, "canBeRequired"),
78
8
            ToJsSet(context, can_be_required))
79
      .FromJust();
80
4
  info.GetReturnValue().Set(result);
81
2
}
82
83
1
void NativeModuleEnv::GetCacheUsage(const FunctionCallbackInfo<Value>& args) {
84
1
  Environment* env = Environment::GetCurrent(args);
85
1
  Isolate* isolate = env->isolate();
86
1
  Local<Context> context = env->context();
87
1
  Local<Object> result = Object::New(isolate);
88
  result
89
2
      ->Set(env->context(),
90
            OneByteString(isolate, "compiledWithCache"),
91
5
            ToJsSet(context, env->native_modules_with_cache))
92
      .FromJust();
93
  result
94
2
      ->Set(env->context(),
95
            OneByteString(isolate, "compiledWithoutCache"),
96
5
            ToJsSet(context, env->native_modules_without_cache))
97
      .FromJust();
98
99
  result
100
2
      ->Set(env->context(),
101
            OneByteString(isolate, "compiledInSnapshot"),
102
2
            ToV8Value(env->context(), env->native_modules_in_snapshot)
103
4
                .ToLocalChecked())
104
      .FromJust();
105
106
2
  args.GetReturnValue().Set(result);
107
1
}
108
109
384
void NativeModuleEnv::ModuleIdsGetter(Local<Name> property,
110
                                      const PropertyCallbackInfo<Value>& info) {
111
384
  Isolate* isolate = info.GetIsolate();
112
113
  std::vector<std::string> ids =
114
768
      NativeModuleLoader::GetInstance()->GetModuleIds();
115
768
  info.GetReturnValue().Set(
116
768
      ToV8Value(isolate->GetCurrentContext(), ids).ToLocalChecked());
117
384
}
118
119
384
void NativeModuleEnv::ConfigStringGetter(
120
    Local<Name> property, const PropertyCallbackInfo<Value>& info) {
121
1152
  info.GetReturnValue().Set(GetConfigString(info.GetIsolate()));
122
384
}
123
124
354129
void NativeModuleEnv::RecordResult(const char* id,
125
                                   NativeModuleLoader::Result result,
126
                                   Environment* env) {
127
354129
  if (result == NativeModuleLoader::Result::kWithCache) {
128
332830
    env->native_modules_with_cache.insert(id);
129
  } else {
130
21299
    env->native_modules_without_cache.insert(id);
131
  }
132
354128
}
133
347302
void NativeModuleEnv::CompileFunction(const FunctionCallbackInfo<Value>& args) {
134
347302
  Environment* env = Environment::GetCurrent(args);
135
1041909
  CHECK(args[0]->IsString());
136
1041908
  node::Utf8Value id_v(env->isolate(), args[0].As<String>());
137
347301
  const char* id = *id_v;
138
  NativeModuleLoader::Result result;
139
  MaybeLocal<Function> maybe =
140
      NativeModuleLoader::GetInstance()->CompileAsModule(
141
347302
          env->context(), id, &result);
142
347303
  RecordResult(id, result, env);
143
  Local<Function> fn;
144
347302
  if (maybe.ToLocal(&fn)) {
145
694606
    args.GetReturnValue().Set(fn);
146
  }
147
347303
}
148
149
// Returns Local<Function> of the compiled module if return_code_cache
150
// is false (we are only compiling the function).
151
// Otherwise return a Local<Object> containing the cache.
152
9153
MaybeLocal<Function> NativeModuleEnv::LookupAndCompile(
153
    Local<Context> context,
154
    const char* id,
155
    std::vector<Local<String>>* parameters,
156
    Environment* optional_env) {
157
  NativeModuleLoader::Result result;
158
  MaybeLocal<Function> maybe =
159
      NativeModuleLoader::GetInstance()->LookupAndCompile(
160
9153
          context, id, parameters, &result);
161
9155
  if (optional_env != nullptr) {
162
6826
    RecordResult(id, result, optional_env);
163
  }
164
9155
  return maybe;
165
}
166
167
4
void HasCachedBuiltins(const FunctionCallbackInfo<Value>& args) {
168
16
  args.GetReturnValue().Set(
169
      v8::Boolean::New(args.GetIsolate(), has_code_cache));
170
4
}
171
172
// TODO(joyeecheung): It is somewhat confusing that Class::Initialize
173
// is used to initialize to the binding, but it is the current convention.
174
// Rename this across the code base to something that makes more sense.
175
384
void NativeModuleEnv::Initialize(Local<Object> target,
176
                                 Local<Value> unused,
177
                                 Local<Context> context,
178
                                 void* priv) {
179
384
  Environment* env = Environment::GetCurrent(context);
180
181
  target
182
768
      ->SetAccessor(env->context(),
183
                    env->config_string(),
184
                    ConfigStringGetter,
185
                    nullptr,
186
                    MaybeLocal<Value>(),
187
                    DEFAULT,
188
                    None,
189
1536
                    SideEffectType::kHasNoSideEffect)
190
      .Check();
191
  target
192
768
      ->SetAccessor(env->context(),
193
                    FIXED_ONE_BYTE_STRING(env->isolate(), "moduleIds"),
194
                    ModuleIdsGetter,
195
                    nullptr,
196
                    MaybeLocal<Value>(),
197
                    DEFAULT,
198
                    None,
199
1536
                    SideEffectType::kHasNoSideEffect)
200
      .Check();
201
202
  target
203
768
      ->SetAccessor(env->context(),
204
                    FIXED_ONE_BYTE_STRING(env->isolate(), "moduleCategories"),
205
                    GetModuleCategories,
206
                    nullptr,
207
                    Local<Value>(),
208
                    DEFAULT,
209
                    None,
210
1536
                    SideEffectType::kHasNoSideEffect)
211
      .Check();
212
213
384
  env->SetMethod(target, "getCacheUsage", NativeModuleEnv::GetCacheUsage);
214
384
  env->SetMethod(target, "compileFunction", NativeModuleEnv::CompileFunction);
215
384
  env->SetMethod(target, "hasCachedBuiltins", HasCachedBuiltins);
216
  // internalBinding('native_module') should be frozen
217
768
  target->SetIntegrityLevel(context, IntegrityLevel::kFrozen).FromJust();
218
384
}
219
220
4920
void NativeModuleEnv::RegisterExternalReferences(
221
    ExternalReferenceRegistry* registry) {
222
4920
  registry->Register(ConfigStringGetter);
223
4920
  registry->Register(ModuleIdsGetter);
224
4920
  registry->Register(GetModuleCategories);
225
4920
  registry->Register(GetCacheUsage);
226
4920
  registry->Register(CompileFunction);
227
4920
  registry->Register(HasCachedBuiltins);
228
4920
}
229
230
}  // namespace native_module
231
}  // namespace node
232
233
4989
NODE_MODULE_CONTEXT_AWARE_INTERNAL(
234
    native_module, node::native_module::NativeModuleEnv::Initialize)
235

19890
NODE_MODULE_EXTERNAL_REFERENCE(
236
    native_module,
237
    node::native_module::NativeModuleEnv::RegisterExternalReferences)