bootstrapper.cc 242 KB
Newer Older
1 2 3
// Copyright 2014 the V8 project authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
4

5
#include "src/bootstrapper.h"
6

7
#include "src/accessors.h"
8
#include "src/api-natives.h"
9
#include "src/api.h"
10
#include "src/base/ieee754.h"
11
#include "src/code-stubs.h"
12
#include "src/compiler.h"
13
#include "src/debug/debug.h"
14 15 16
#include "src/extensions/externalize-string-extension.h"
#include "src/extensions/free-buffer-extension.h"
#include "src/extensions/gc-extension.h"
17
#include "src/extensions/ignition-statistics-extension.h"
18 19
#include "src/extensions/statistics-extension.h"
#include "src/extensions/trigger-failure-extension.h"
20
#include "src/heap/heap.h"
21
#include "src/isolate-inl.h"
22
#include "src/objects/js-regexp.h"
23 24
#include "src/snapshot/natives.h"
#include "src/snapshot/snapshot.h"
25 26
#include "src/wasm/wasm-js.h"

27 28 29
#if V8_INTL_SUPPORT
#include "src/objects/intl-objects.h"
#endif  // V8_INTL_SUPPORT
30

31 32
namespace v8 {
namespace internal {
33

34
void SourceCodeCache::Initialize(Isolate* isolate, bool create_heap_objects) {
35
  cache_ = create_heap_objects ? isolate->heap()->empty_fixed_array() : nullptr;
36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68
}

bool SourceCodeCache::Lookup(Vector<const char> name,
                             Handle<SharedFunctionInfo>* handle) {
  for (int i = 0; i < cache_->length(); i += 2) {
    SeqOneByteString* str = SeqOneByteString::cast(cache_->get(i));
    if (str->IsUtf8EqualTo(name)) {
      *handle = Handle<SharedFunctionInfo>(
          SharedFunctionInfo::cast(cache_->get(i + 1)));
      return true;
    }
  }
  return false;
}

void SourceCodeCache::Add(Vector<const char> name,
                          Handle<SharedFunctionInfo> shared) {
  Isolate* isolate = shared->GetIsolate();
  Factory* factory = isolate->factory();
  HandleScope scope(isolate);
  int length = cache_->length();
  Handle<FixedArray> new_array = factory->NewFixedArray(length + 2, TENURED);
  cache_->CopyTo(0, *new_array, 0, cache_->length());
  cache_ = *new_array;
  Handle<String> str =
      factory->NewStringFromOneByte(Vector<const uint8_t>::cast(name), TENURED)
          .ToHandleChecked();
  DCHECK(!str.is_null());
  cache_->set(length, *str);
  cache_->set(length + 1, *shared);
  Script::cast(shared->script())->set_type(type_);
}

69 70 71
Bootstrapper::Bootstrapper(Isolate* isolate)
    : isolate_(isolate),
      nesting_(0),
72
      extensions_cache_(Script::TYPE_EXTENSION) {}
73

74 75 76 77 78 79 80 81
Handle<String> Bootstrapper::GetNativeSource(NativeType type, int index) {
  NativesExternalStringResource* resource =
      new NativesExternalStringResource(type, index);
  Handle<ExternalOneByteString> source_code =
      isolate_->factory()->NewNativeSourceString(resource);
  isolate_->heap()->RegisterExternalString(*source_code);
  DCHECK(source_code->is_short());
  return source_code;
82 83 84
}

void Bootstrapper::Initialize(bool create_heap_objects) {
85
  extensions_cache_.Initialize(isolate_, create_heap_objects);
86 87 88
}


89
static const char* GCFunctionName() {
90 91
  bool flag_given =
      FLAG_expose_gc_as != nullptr && strlen(FLAG_expose_gc_as) != 0;
92 93 94
  return flag_given ? FLAG_expose_gc_as : "gc";
}

95 96 97 98 99 100
v8::Extension* Bootstrapper::free_buffer_extension_ = nullptr;
v8::Extension* Bootstrapper::gc_extension_ = nullptr;
v8::Extension* Bootstrapper::externalize_string_extension_ = nullptr;
v8::Extension* Bootstrapper::statistics_extension_ = nullptr;
v8::Extension* Bootstrapper::trigger_failure_extension_ = nullptr;
v8::Extension* Bootstrapper::ignition_statistics_extension_ = nullptr;
101

102
void Bootstrapper::InitializeOncePerProcess() {
103 104 105 106 107 108 109 110 111 112
  free_buffer_extension_ = new FreeBufferExtension;
  v8::RegisterExtension(free_buffer_extension_);
  gc_extension_ = new GCExtension(GCFunctionName());
  v8::RegisterExtension(gc_extension_);
  externalize_string_extension_ = new ExternalizeStringExtension;
  v8::RegisterExtension(externalize_string_extension_);
  statistics_extension_ = new StatisticsExtension;
  v8::RegisterExtension(statistics_extension_);
  trigger_failure_extension_ = new TriggerFailureExtension;
  v8::RegisterExtension(trigger_failure_extension_);
113 114
  ignition_statistics_extension_ = new IgnitionStatisticsExtension;
  v8::RegisterExtension(ignition_statistics_extension_);
115 116 117 118 119
}


void Bootstrapper::TearDownExtensions() {
  delete free_buffer_extension_;
120
  free_buffer_extension_ = nullptr;
121
  delete gc_extension_;
122
  gc_extension_ = nullptr;
123
  delete externalize_string_extension_;
124
  externalize_string_extension_ = nullptr;
125
  delete statistics_extension_;
126
  statistics_extension_ = nullptr;
127
  delete trigger_failure_extension_;
128
  trigger_failure_extension_ = nullptr;
129
  delete ignition_statistics_extension_;
130
  ignition_statistics_extension_ = nullptr;
131 132
}

133
void Bootstrapper::TearDown() {
134
  extensions_cache_.Initialize(isolate_, false);  // Yes, symmetrical
135 136 137 138 139
}


class Genesis BASE_EMBEDDED {
 public:
140 141
  Genesis(Isolate* isolate, MaybeHandle<JSGlobalProxy> maybe_global_proxy,
          v8::Local<v8::ObjectTemplate> global_proxy_template,
142
          size_t context_snapshot_index,
143
          v8::DeserializeEmbedderFieldsCallback embedder_fields_deserializer,
144
          GlobalContextType context_type);
145 146
  Genesis(Isolate* isolate, MaybeHandle<JSGlobalProxy> maybe_global_proxy,
          v8::Local<v8::ObjectTemplate> global_proxy_template);
147
  ~Genesis() { }
148

149 150
  Isolate* isolate() const { return isolate_; }
  Factory* factory() const { return isolate_->factory(); }
151
  Builtins* builtins() const { return isolate_->builtins(); }
152 153
  Heap* heap() const { return isolate_->heap(); }

154
  Handle<Context> result() { return result_; }
155

156 157
  Handle<JSGlobalProxy> global_proxy() { return global_proxy_; }

158
 private:
159
  Handle<Context> native_context() { return native_context_; }
160

161 162 163
  // Creates some basic objects. Used for creating a context from scratch.
  void CreateRoots();
  // Creates the empty function.  Used for creating a context from scratch.
164
  Handle<JSFunction> CreateEmptyFunction(Isolate* isolate);
165 166 167
  // Returns the %ThrowTypeError% intrinsic function.
  // See ES#sec-%throwtypeerror% for details.
  Handle<JSFunction> GetThrowTypeErrorIntrinsic();
168

169
  void CreateSloppyModeFunctionMaps(Handle<JSFunction> empty);
170
  void CreateStrictModeFunctionMaps(Handle<JSFunction> empty);
171
  void CreateObjectFunction(Handle<JSFunction> empty);
172
  void CreateIteratorMaps(Handle<JSFunction> empty);
173
  void CreateAsyncIteratorMaps(Handle<JSFunction> empty);
174
  void CreateAsyncFunctionMaps(Handle<JSFunction> empty);
175
  void CreateJSProxyMaps();
176 177

  // Make the "arguments" and "caller" properties throw a TypeError on access.
178
  void AddRestrictedFunctionProperties(Handle<JSFunction> empty);
179

180 181
  // Creates the global objects using the global proxy and the template passed
  // in through the API.  We call this regardless of whether we are building a
182 183
  // context from scratch or using a deserialized one from the partial snapshot
  // but in the latter case we don't use the objects it produces directly, as
184 185 186
  // we have to use the deserialized ones that are linked together with the
  // rest of the context snapshot. At the end we link the global proxy and the
  // context to each other.
187
  Handle<JSGlobalObject> CreateNewGlobals(
188
      v8::Local<v8::ObjectTemplate> global_proxy_template,
189
      Handle<JSGlobalProxy> global_proxy);
190 191 192
  // Similarly, we want to use the global that has been created by the templates
  // passed through the API.  The global from the snapshot is detached from the
  // other objects in the snapshot.
193
  void HookUpGlobalObject(Handle<JSGlobalObject> global_object);
194 195 196
  // Hooks the given global proxy into the context in the case we do not
  // replace the global object from the deserialized native context.
  void HookUpGlobalProxy(Handle<JSGlobalProxy> global_proxy);
197 198 199 200
  // The native context has a ScriptContextTable that store declarative bindings
  // made in script scopes.  Add a "this" binding to that table pointing to the
  // global proxy.
  void InstallGlobalThisBinding();
201
  // New context initialization.  Used for creating a context from scratch.
202
  void InitializeGlobal(Handle<JSGlobalObject> global_object,
203
                        Handle<JSFunction> empty_function,
204
                        GlobalContextType context_type);
205
  void InitializeExperimentalGlobal();
206
  // Depending on the situation, expose and/or get rid of the utils object.
207
  void ConfigureUtilsObject(GlobalContextType context_type);
208 209 210 211

#define DECLARE_FEATURE_INITIALIZATION(id, descr) \
  void InitializeGlobal_##id();

212 213 214
  HARMONY_INPROGRESS(DECLARE_FEATURE_INITIALIZATION)
  HARMONY_STAGED(DECLARE_FEATURE_INITIALIZATION)
  HARMONY_SHIPPING(DECLARE_FEATURE_INITIALIZATION)
215 216
#undef DECLARE_FEATURE_INITIALIZATION

217 218 219 220
  Handle<JSFunction> CreateArrayBuffer(Handle<String> name,
                                       Builtins::Name call_byteLength,
                                       BuiltinFunctionId byteLength_id,
                                       Builtins::Name call_slice);
221
  Handle<JSFunction> InstallInternalArray(Handle<JSObject> target,
222 223
                                          const char* name,
                                          ElementsKind elements_kind);
224
  bool InstallNatives(GlobalContextType context_type);
225

226 227
  void InstallTypedArray(const char* name, ElementsKind elements_kind,
                         Handle<JSFunction>* fun);
228
  bool InstallExtraNatives();
229
  bool InstallExperimentalExtraNatives();
230
  bool InstallDebuggerNatives();
231
  void InstallBuiltinFunctionIds();
binji's avatar
binji committed
232
  void InstallExperimentalBuiltinFunctionIds();
233
  void InitializeNormalizedMapCaches();
234

235 236 237 238 239
  enum ExtensionTraversalState {
    UNVISITED, VISITED, INSTALLED
  };

  class ExtensionStates {
240
   public:
241 242 243 244
    ExtensionStates();
    ExtensionTraversalState get_state(RegisteredExtension* extension);
    void set_state(RegisteredExtension* extension,
                   ExtensionTraversalState state);
245
   private:
lpy's avatar
lpy committed
246
    base::HashMap map_;
247
    DISALLOW_COPY_AND_ASSIGN(ExtensionStates);
248 249
  };

250 251
  // Used both for deserialized and from-scratch contexts to add the extensions
  // provided.
252
  static bool InstallExtensions(Handle<Context> native_context,
253
                                v8::ExtensionConfiguration* extensions);
254 255 256 257 258
  static bool InstallAutoExtensions(Isolate* isolate,
                                    ExtensionStates* extension_states);
  static bool InstallRequestedExtensions(Isolate* isolate,
                                         v8::ExtensionConfiguration* extensions,
                                         ExtensionStates* extension_states);
259 260
  static bool InstallExtension(Isolate* isolate,
                               const char* name,
261
                               ExtensionStates* extension_states);
262 263
  static bool InstallExtension(Isolate* isolate,
                               v8::RegisteredExtension* current,
264
                               ExtensionStates* extension_states);
265
  static bool InstallSpecialObjects(Handle<Context> native_context);
266 267
  bool ConfigureApiObject(Handle<JSObject> object,
                          Handle<ObjectTemplateInfo> object_template);
268
  bool ConfigureGlobalObjects(
269
      v8::Local<v8::ObjectTemplate> global_proxy_template);
270 271 272 273 274 275 276 277

  // Migrates all properties from the 'from' object to the 'to'
  // object and overrides the prototype in 'to' with the one from
  // 'from'.
  void TransferObject(Handle<JSObject> from, Handle<JSObject> to);
  void TransferNamedProperties(Handle<JSObject> from, Handle<JSObject> to);
  void TransferIndexedProperties(Handle<JSObject> from, Handle<JSObject> to);

278 279
  static bool CallUtilsFunction(Isolate* isolate, const char* name);

280
  static bool CompileExtension(Isolate* isolate, v8::Extension* extension);
281

282
  Isolate* isolate_;
283
  Handle<Context> result_;
284
  Handle<Context> native_context_;
285
  Handle<JSGlobalProxy> global_proxy_;
286

287 288 289 290
  // Temporary function maps needed only during bootstrapping.
  Handle<Map> strict_function_with_home_object_map_;
  Handle<Map> strict_function_with_name_and_home_object_map_;

291 292
  // %ThrowTypeError%. See ES#sec-%throwtypeerror% for details.
  Handle<JSFunction> restricted_properties_thrower_;
293

294 295
  BootstrapperActive active_;
  friend class Bootstrapper;
296 297
};

298
void Bootstrapper::Iterate(RootVisitor* v) {
299
  extensions_cache_.Iterate(v);
300
  v->Synchronize(VisitorSynchronization::kExtensions);
301 302 303
}

Handle<Context> Bootstrapper::CreateEnvironment(
304
    MaybeHandle<JSGlobalProxy> maybe_global_proxy,
305
    v8::Local<v8::ObjectTemplate> global_proxy_template,
306
    v8::ExtensionConfiguration* extensions, size_t context_snapshot_index,
307
    v8::DeserializeEmbedderFieldsCallback embedder_fields_deserializer,
308
    GlobalContextType context_type) {
309
  HandleScope scope(isolate_);
310 311 312 313 314 315
  Genesis genesis(isolate_, maybe_global_proxy, global_proxy_template,
                  context_snapshot_index, embedder_fields_deserializer,
                  context_type);
  Handle<Context> env = genesis.result();
  if (env.is_null() || !InstallExtensions(env, extensions)) {
    return Handle<Context>();
316
  }
317
  return scope.CloseAndEscape(env);
318 319
}

320 321 322 323
Handle<JSGlobalProxy> Bootstrapper::NewRemoteContext(
    MaybeHandle<JSGlobalProxy> maybe_global_proxy,
    v8::Local<v8::ObjectTemplate> global_proxy_template) {
  HandleScope scope(isolate_);
324 325 326
  Genesis genesis(isolate_, maybe_global_proxy, global_proxy_template);
  Handle<JSGlobalProxy> global_proxy = genesis.global_proxy();
  if (global_proxy.is_null()) return Handle<JSGlobalProxy>();
327 328
  return scope.CloseAndEscape(global_proxy);
}
329

330
void Bootstrapper::DetachGlobal(Handle<Context> env) {
331 332 333
  Isolate* isolate = env->GetIsolate();
  isolate->counters()->errors_thrown_per_context()->AddSample(
      env->GetErrorsThrown());
334

335
  Heap* heap = isolate->heap();
336
  Handle<JSGlobalProxy> global_proxy(JSGlobalProxy::cast(env->global_proxy()));
337 338 339
  global_proxy->set_native_context(heap->null_value());
  JSObject::ForceSetPrototype(global_proxy, isolate->factory()->null_value());
  global_proxy->map()->SetConstructor(heap->null_value());
340 341 342
  if (FLAG_track_detached_contexts) {
    env->GetIsolate()->AddDetachedContext(env);
  }
343 344
}

345 346
namespace {

347
// Non-construct case.
348
V8_NOINLINE Handle<SharedFunctionInfo> SimpleCreateSharedFunctionInfo(
349 350 351 352 353
    Isolate* isolate, Builtins::Name builtin_id, Handle<String> name, int len) {
  Handle<Code> code = isolate->builtins()->builtin_handle(builtin_id);
  const bool kNotConstructor = false;
  Handle<SharedFunctionInfo> shared = isolate->factory()->NewSharedFunctionInfo(
      name, code, kNotConstructor, kNormalFunction, builtin_id);
354 355 356 357 358 359
  shared->set_internal_formal_parameter_count(len);
  shared->set_length(len);
  return shared;
}

// Construct case.
360
V8_NOINLINE Handle<SharedFunctionInfo> SimpleCreateSharedFunctionInfo(
361
    Isolate* isolate, Builtins::Name builtin_id, Handle<String> name,
362
    Handle<String> instance_class_name, int len) {
363 364 365 366
  Handle<Code> code = isolate->builtins()->builtin_handle(builtin_id);
  const bool kIsConstructor = true;
  Handle<SharedFunctionInfo> shared = isolate->factory()->NewSharedFunctionInfo(
      name, code, kIsConstructor, kNormalFunction, builtin_id);
367 368 369 370 371 372 373
  shared->SetConstructStub(*BUILTIN_CODE(isolate, JSBuiltinsConstructStub));
  shared->set_instance_class_name(*instance_class_name);
  shared->set_internal_formal_parameter_count(len);
  shared->set_length(len);
  return shared;
}

374 375 376 377 378
V8_NOINLINE void InstallFunction(Handle<JSObject> target,
                                 Handle<Name> property_name,
                                 Handle<JSFunction> function,
                                 Handle<String> function_name,
                                 PropertyAttributes attributes = DONT_ENUM) {
379 380 381 382
  JSObject::AddProperty(target, property_name, function, attributes);
  if (target->IsJSGlobalObject()) {
    function->shared()->set_instance_class_name(*function_name);
  }
383 384
}

385 386 387
V8_NOINLINE void InstallFunction(Handle<JSObject> target,
                                 Handle<JSFunction> function, Handle<Name> name,
                                 PropertyAttributes attributes = DONT_ENUM) {
388 389 390 391
  Handle<String> name_string = Name::ToFunctionName(name).ToHandleChecked();
  InstallFunction(target, name, function, name_string, attributes);
}

392 393
V8_NOINLINE Handle<JSFunction> CreateFunction(
    Isolate* isolate, Handle<String> name, InstanceType type, int instance_size,
394
    int inobject_properties, MaybeHandle<Object> maybe_prototype,
395 396
    Builtins::Name builtin_id) {
  Handle<Code> code(isolate->builtins()->builtin(builtin_id));
397
  Handle<Object> prototype;
398 399 400 401 402 403 404 405 406 407 408 409
  Handle<JSFunction> result;

  if (maybe_prototype.ToHandle(&prototype)) {
    NewFunctionArgs args = NewFunctionArgs::ForBuiltinWithPrototype(
        name, code, prototype, type, instance_size, inobject_properties,
        builtin_id, IMMUTABLE);

    result = isolate->factory()->NewFunction(args);
  } else {
    NewFunctionArgs args = NewFunctionArgs::ForBuiltinWithoutPrototype(
        name, code, builtin_id, LanguageMode::kStrict);
    result = isolate->factory()->NewFunction(args);
410
  }
411

412 413
  result->shared()->set_native(true);
  return result;
414 415
}

416 417
V8_NOINLINE Handle<JSFunction> InstallFunction(
    Handle<JSObject> target, Handle<Name> name, InstanceType type,
418 419
    int instance_size, int inobject_properties,
    MaybeHandle<Object> maybe_prototype, Builtins::Name call,
420
    PropertyAttributes attributes) {
421
  Handle<String> name_string = Name::ToFunctionName(name).ToHandleChecked();
422
  Handle<JSFunction> function =
423
      CreateFunction(target->GetIsolate(), name_string, type, instance_size,
424
                     inobject_properties, maybe_prototype, call);
425 426
  InstallFunction(target, name, function, name_string, attributes);
  return function;
427 428
}

429 430
V8_NOINLINE Handle<JSFunction> InstallFunction(
    Handle<JSObject> target, const char* name, InstanceType type,
431 432
    int instance_size, int inobject_properties,
    MaybeHandle<Object> maybe_prototype, Builtins::Name call) {
433
  Factory* const factory = target->GetIsolate()->factory();
yangguo's avatar
yangguo committed
434
  PropertyAttributes attributes = DONT_ENUM;
435
  return InstallFunction(target, factory->InternalizeUtf8String(name), type,
436 437
                         instance_size, inobject_properties, maybe_prototype,
                         call, attributes);
438 439
}

440 441 442 443
V8_NOINLINE Handle<JSFunction> SimpleCreateFunction(Isolate* isolate,
                                                    Handle<String> name,
                                                    Builtins::Name call,
                                                    int len, bool adapt) {
444
  Handle<JSFunction> fun =
445
      CreateFunction(isolate, name, JS_OBJECT_TYPE, JSObject::kHeaderSize, 0,
446 447 448 449 450 451 452 453 454
                     MaybeHandle<JSObject>(), call);
  if (adapt) {
    fun->shared()->set_internal_formal_parameter_count(len);
  } else {
    fun->shared()->DontAdaptArguments();
  }
  fun->shared()->set_length(len);
  return fun;
}
455

456
V8_NOINLINE Handle<JSFunction> SimpleInstallFunction(
457 458 459 460
    Handle<JSObject> base, Handle<Name> property_name,
    Handle<String> function_name, Builtins::Name call, int len, bool adapt,
    PropertyAttributes attrs = DONT_ENUM,
    BuiltinFunctionId id = kInvalidBuiltinFunctionId) {
461
  Handle<JSFunction> fun =
462
      SimpleCreateFunction(base->GetIsolate(), function_name, call, len, adapt);
463 464 465
  if (id != kInvalidBuiltinFunctionId) {
    fun->shared()->set_builtin_function_id(id);
  }
466 467 468 469
  InstallFunction(base, fun, property_name, attrs);
  return fun;
}

470
V8_NOINLINE Handle<JSFunction> SimpleInstallFunction(
471 472 473 474
    Handle<JSObject> base, Handle<String> name, Builtins::Name call, int len,
    bool adapt, PropertyAttributes attrs = DONT_ENUM,
    BuiltinFunctionId id = kInvalidBuiltinFunctionId) {
  return SimpleInstallFunction(base, name, name, call, len, adapt, attrs, id);
475 476
}

477
V8_NOINLINE Handle<JSFunction> SimpleInstallFunction(
478 479 480 481 482
    Handle<JSObject> base, Handle<Name> property_name,
    const char* function_name, Builtins::Name call, int len, bool adapt,
    PropertyAttributes attrs = DONT_ENUM,
    BuiltinFunctionId id = kInvalidBuiltinFunctionId) {
  Factory* const factory = base->GetIsolate()->factory();
483 484 485 486
  // Function name does not have to be internalized.
  return SimpleInstallFunction(
      base, property_name, factory->NewStringFromAsciiChecked(function_name),
      call, len, adapt, attrs, id);
487 488
}

489
V8_NOINLINE Handle<JSFunction> SimpleInstallFunction(
490 491 492
    Handle<JSObject> base, const char* name, Builtins::Name call, int len,
    bool adapt, PropertyAttributes attrs = DONT_ENUM,
    BuiltinFunctionId id = kInvalidBuiltinFunctionId) {
493
  Factory* const factory = base->GetIsolate()->factory();
494 495
  // Although function name does not have to be internalized the property name
  // will be internalized during property addition anyway, so do it here now.
496
  return SimpleInstallFunction(base, factory->InternalizeUtf8String(name), call,
497
                               len, adapt, attrs, id);
498 499
}

500 501 502 503 504
V8_NOINLINE Handle<JSFunction> SimpleInstallFunction(Handle<JSObject> base,
                                                     const char* name,
                                                     Builtins::Name call,
                                                     int len, bool adapt,
                                                     BuiltinFunctionId id) {
505
  return SimpleInstallFunction(base, name, call, len, adapt, DONT_ENUM, id);
506 507
}

508 509 510 511 512
V8_NOINLINE void SimpleInstallGetterSetter(Handle<JSObject> base,
                                           Handle<String> name,
                                           Builtins::Name call_getter,
                                           Builtins::Name call_setter,
                                           PropertyAttributes attribs) {
513 514 515 516 517 518
  Isolate* const isolate = base->GetIsolate();

  Handle<String> getter_name =
      Name::ToFunctionName(name, isolate->factory()->get_string())
          .ToHandleChecked();
  Handle<JSFunction> getter =
519
      SimpleCreateFunction(isolate, getter_name, call_getter, 0, true);
520 521 522 523 524

  Handle<String> setter_name =
      Name::ToFunctionName(name, isolate->factory()->set_string())
          .ToHandleChecked();
  Handle<JSFunction> setter =
525
      SimpleCreateFunction(isolate, setter_name, call_setter, 1, true);
526 527 528 529

  JSObject::DefineAccessor(base, name, getter, setter, attribs).Check();
}

530
V8_NOINLINE Handle<JSFunction> SimpleInstallGetter(Handle<JSObject> base,
531
                                                   Handle<Name> name,
532 533 534
                                                   Handle<Name> property_name,
                                                   Builtins::Name call,
                                                   bool adapt) {
535
  Isolate* const isolate = base->GetIsolate();
536 537

  Handle<String> getter_name =
538 539
      Name::ToFunctionName(name, isolate->factory()->get_string())
          .ToHandleChecked();
540 541 542 543 544 545 546 547 548 549 550
  Handle<JSFunction> getter =
      SimpleCreateFunction(isolate, getter_name, call, 0, adapt);

  Handle<Object> setter = isolate->factory()->undefined_value();

  JSObject::DefineAccessor(base, property_name, getter, setter, DONT_ENUM)
      .Check();

  return getter;
}

551
V8_NOINLINE Handle<JSFunction> SimpleInstallGetter(Handle<JSObject> base,
552
                                                   Handle<Name> name,
553 554
                                                   Builtins::Name call,
                                                   bool adapt) {
555
  return SimpleInstallGetter(base, name, name, call, adapt);
556 557
}

558
V8_NOINLINE Handle<JSFunction> SimpleInstallGetter(Handle<JSObject> base,
559
                                                   Handle<Name> name,
560 561 562
                                                   Builtins::Name call,
                                                   bool adapt,
                                                   BuiltinFunctionId id) {
563 564 565 566 567
  Handle<JSFunction> fun = SimpleInstallGetter(base, name, call, adapt);
  fun->shared()->set_builtin_function_id(id);
  return fun;
}

568 569
V8_NOINLINE void InstallConstant(Isolate* isolate, Handle<JSObject> holder,
                                 const char* name, Handle<Object> value) {
570 571 572 573 574
  JSObject::AddProperty(
      holder, isolate->factory()->NewStringFromAsciiChecked(name), value,
      static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY));
}

575
V8_NOINLINE void InstallSpeciesGetter(Handle<JSFunction> constructor) {
576 577 578 579 580 581 582 583
  Factory* factory = constructor->GetIsolate()->factory();
  // TODO(adamk): We should be able to share a SharedFunctionInfo
  // between all these JSFunctins.
  SimpleInstallGetter(constructor, factory->symbol_species_string(),
                      factory->species_symbol(), Builtins::kReturnReceiver,
                      true);
}

584
}  // namespace
585

586
Handle<JSFunction> Genesis::CreateEmptyFunction(Isolate* isolate) {
587 588
  Factory* factory = isolate->factory();

589
  // Allocate the function map first and then patch the prototype later.
590 591
  Handle<Map> empty_function_map = factory->CreateSloppyFunctionMap(
      FUNCTION_WITHOUT_PROTOTYPE, MaybeHandle<JSFunction>());
592
  empty_function_map->set_is_prototype_map(true);
593
  DCHECK(!empty_function_map->is_dictionary_map());
594

595 596
  // Allocate the empty function as the prototype for function according to
  // ES#sec-properties-of-the-function-prototype-object
597
  Handle<Code> code(BUILTIN_CODE(isolate, EmptyFunction));
598 599 600 601
  NewFunctionArgs args =
      NewFunctionArgs::ForBuiltin(factory->empty_string(), code,
                                  empty_function_map, Builtins::kEmptyFunction);
  Handle<JSFunction> empty_function = factory->NewFunction(args);
602

603
  // --- E m p t y ---
604
  Handle<String> source = factory->NewStringFromStaticChars("() {}");
605
  Handle<Script> script = factory->NewScript(source);
606
  script->set_type(Script::TYPE_NATIVE);
607 608
  Handle<FixedArray> infos = factory->NewFixedArray(2);
  script->set_shared_function_infos(*infos);
609 610
  empty_function->shared()->set_start_position(0);
  empty_function->shared()->set_end_position(source->length());
611
  empty_function->shared()->set_function_literal_id(1);
612
  empty_function->shared()->DontAdaptArguments();
613
  SharedFunctionInfo::SetScript(handle(empty_function->shared()), script);
614

615 616
  return empty_function;
}
617

618 619
void Genesis::CreateSloppyModeFunctionMaps(Handle<JSFunction> empty) {
  Factory* factory = isolate_->factory();
620 621
  Handle<Map> map;

622 623 624
  //
  // Allocate maps for sloppy functions without prototype.
  //
625 626
  map = factory->CreateSloppyFunctionMap(FUNCTION_WITHOUT_PROTOTYPE, empty);
  native_context()->set_sloppy_function_without_prototype_map(*map);
627

628 629 630
  //
  // Allocate maps for sloppy functions with readonly prototype.
  //
631 632 633 634
  map =
      factory->CreateSloppyFunctionMap(FUNCTION_WITH_READONLY_PROTOTYPE, empty);
  native_context()->set_sloppy_function_with_readonly_prototype_map(*map);

635 636 637
  //
  // Allocate maps for sloppy functions with writable prototype.
  //
638 639 640
  map = factory->CreateSloppyFunctionMap(FUNCTION_WITH_WRITEABLE_PROTOTYPE,
                                         empty);
  native_context()->set_sloppy_function_map(*map);
641 642 643 644

  map = factory->CreateSloppyFunctionMap(
      FUNCTION_WITH_NAME_AND_WRITEABLE_PROTOTYPE, empty);
  native_context()->set_sloppy_function_with_name_map(*map);
645
}
646

647 648 649 650 651
Handle<JSFunction> Genesis::GetThrowTypeErrorIntrinsic() {
  if (!restricted_properties_thrower_.is_null()) {
    return restricted_properties_thrower_;
  }
  Handle<String> name(factory()->empty_string());
652
  Handle<Code> code = BUILTIN_CODE(isolate(), StrictPoisonPillThrower);
653 654 655
  NewFunctionArgs args = NewFunctionArgs::ForBuiltinWithoutPrototype(
      name, code, Builtins::kStrictPoisonPillThrower, i::LanguageMode::kStrict);
  Handle<JSFunction> function = factory()->NewFunction(args);
656 657 658
  function->shared()->DontAdaptArguments();

  // %ThrowTypeError% must not have a name property.
neis's avatar
neis committed
659
  if (JSReceiver::DeleteProperty(function, factory()->name_string())
660
          .IsNothing()) {
neis's avatar
neis committed
661
    DCHECK(false);
662
  }
663 664

  // length needs to be non configurable.
665 666
  Handle<Object> value(Smi::FromInt(function->shared()->GetLength()),
                       isolate());
667 668 669 670 671
  JSObject::SetOwnPropertyIgnoreAttributes(
      function, factory()->length_string(), value,
      static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY))
      .Assert();

672
  if (JSObject::PreventExtensions(function, kThrowOnError).IsNothing()) {
673
    DCHECK(false);
674
  }
675

676 677
  JSObject::MigrateSlowToFast(function, 0, "Bootstrapping");

678
  restricted_properties_thrower_ = function;
679 680 681
  return function;
}

682
void Genesis::CreateStrictModeFunctionMaps(Handle<JSFunction> empty) {
683 684 685
  Factory* factory = isolate_->factory();
  Handle<Map> map;

686 687 688
  //
  // Allocate maps for strict functions without prototype.
  //
689 690 691
  map = factory->CreateStrictFunctionMap(FUNCTION_WITHOUT_PROTOTYPE, empty);
  native_context()->set_strict_function_without_prototype_map(*map);

692 693 694 695 696 697 698 699 700 701 702 703 704
  map = factory->CreateStrictFunctionMap(METHOD_WITH_NAME, empty);
  native_context()->set_method_with_name_map(*map);

  map = factory->CreateStrictFunctionMap(METHOD_WITH_HOME_OBJECT, empty);
  native_context()->set_method_with_home_object_map(*map);

  map =
      factory->CreateStrictFunctionMap(METHOD_WITH_NAME_AND_HOME_OBJECT, empty);
  native_context()->set_method_with_name_and_home_object_map(*map);

  //
  // Allocate maps for strict functions with writable prototype.
  //
705 706 707 708
  map = factory->CreateStrictFunctionMap(FUNCTION_WITH_WRITEABLE_PROTOTYPE,
                                         empty);
  native_context()->set_strict_function_map(*map);

709 710 711 712 713 714 715 716 717 718 719 720 721
  map = factory->CreateStrictFunctionMap(
      FUNCTION_WITH_NAME_AND_WRITEABLE_PROTOTYPE, empty);
  native_context()->set_strict_function_with_name_map(*map);

  strict_function_with_home_object_map_ = factory->CreateStrictFunctionMap(
      FUNCTION_WITH_HOME_OBJECT_AND_WRITEABLE_PROTOTYPE, empty);
  strict_function_with_name_and_home_object_map_ =
      factory->CreateStrictFunctionMap(
          FUNCTION_WITH_NAME_AND_HOME_OBJECT_AND_WRITEABLE_PROTOTYPE, empty);

  //
  // Allocate maps for strict functions with readonly prototype.
  //
722 723 724 725
  map =
      factory->CreateStrictFunctionMap(FUNCTION_WITH_READONLY_PROTOTYPE, empty);
  native_context()->set_strict_function_with_readonly_prototype_map(*map);

726 727 728
  //
  // Allocate map for class functions.
  //
729 730
  map = factory->CreateClassFunctionMap(empty);
  native_context()->set_class_function_map(*map);
731

732 733 734
  // Now that the strict mode function map is available, set up the
  // restricted "arguments" and "caller" getters.
  AddRestrictedFunctionProperties(empty);
735 736
}

737 738 739 740
void Genesis::CreateObjectFunction(Handle<JSFunction> empty_function) {
  Factory* factory = isolate_->factory();

  // --- O b j e c t ---
741 742 743
  int inobject_properties = JSObject::kInitialGlobalObjectUnusedPropertiesCount;
  int instance_size =
      JSObject::kHeaderSize + kPointerSize * inobject_properties;
744

745 746
  Handle<JSFunction> object_fun = CreateFunction(
      isolate_, factory->Object_string(), JS_OBJECT_TYPE, instance_size,
747
      inobject_properties, factory->null_value(), Builtins::kObjectConstructor);
748 749
  object_fun->shared()->set_length(1);
  object_fun->shared()->DontAdaptArguments();
750
  object_fun->shared()->SetConstructStub(
751
      *BUILTIN_CODE(isolate_, ObjectConstructor_ConstructStub));
752 753 754 755 756 757 758 759 760 761 762 763 764 765 766 767 768 769 770 771 772 773 774 775 776 777 778 779 780 781 782 783 784 785 786 787 788 789 790 791 792 793 794
  native_context()->set_object_function(*object_fun);

  {
    // Finish setting up Object function's initial map.
    Map* initial_map = object_fun->initial_map();
    initial_map->set_elements_kind(HOLEY_ELEMENTS);
  }

  // Allocate a new prototype for the object function.
  Handle<JSObject> object_function_prototype =
      factory->NewFunctionPrototype(object_fun);

  Handle<Map> map = Map::Copy(handle(object_function_prototype->map()),
                              "EmptyObjectPrototype");
  map->set_is_prototype_map(true);
  // Ban re-setting Object.prototype.__proto__ to prevent Proxy security bug
  map->set_immutable_proto(true);
  object_function_prototype->set_map(*map);

  // Complete setting up empty function.
  {
    Handle<Map> empty_function_map(empty_function->map(), isolate_);
    Map::SetPrototype(empty_function_map, object_function_prototype);
  }

  native_context()->set_initial_object_prototype(*object_function_prototype);
  JSFunction::SetPrototype(object_fun, object_function_prototype);

  {
    // Set up slow map for Object.create(null) instances without in-object
    // properties.
    Handle<Map> map(object_fun->initial_map(), isolate_);
    map = Map::CopyInitialMapNormalized(map);
    Map::SetPrototype(map, factory->null_value());
    native_context()->set_slow_object_with_null_prototype_map(*map);

    // Set up slow map for literals with too many properties.
    map = Map::Copy(map, "slow_object_with_object_prototype_map");
    Map::SetPrototype(map, object_function_prototype);
    native_context()->set_slow_object_with_object_prototype_map(*map);
  }
}

795 796 797 798 799 800
namespace {

Handle<Map> CreateNonConstructorMap(Handle<Map> source_map,
                                    Handle<JSObject> prototype,
                                    const char* reason) {
  Handle<Map> map = Map::Copy(source_map, reason);
801 802 803
  // Ensure the resulting map has prototype slot (it is necessary for storing
  // inital map even when the prototype property is not required).
  if (!map->has_prototype_slot()) {
804 805 806
    // Re-set the unused property fields after changing the instance size.
    // TODO(ulan): Do not change instance size after map creation.
    int unused_property_fields = map->UnusedPropertyFields();
807 808
    map->set_instance_size(map->instance_size() + kPointerSize);
    map->set_has_prototype_slot(true);
809
    map->SetInObjectUnusedPropertyFields(unused_property_fields);
810
  }
811 812 813 814 815 816 817
  map->set_is_constructor(false);
  Map::SetPrototype(map, prototype);
  return map;
}

}  // namespace

818
void Genesis::CreateIteratorMaps(Handle<JSFunction> empty) {
819 820 821
  // Create iterator-related meta-objects.
  Handle<JSObject> iterator_prototype =
      factory()->NewJSObject(isolate()->object_function(), TENURED);
822

823 824 825
  SimpleInstallFunction(iterator_prototype, factory()->iterator_symbol(),
                        "[Symbol.iterator]", Builtins::kReturnReceiver, 0,
                        true);
826 827
  native_context()->set_initial_iterator_prototype(*iterator_prototype);

828 829
  Handle<JSObject> generator_object_prototype =
      factory()->NewJSObject(isolate()->object_function(), TENURED);
830 831
  native_context()->set_initial_generator_prototype(
      *generator_object_prototype);
832
  JSObject::ForceSetPrototype(generator_object_prototype, iterator_prototype);
833 834
  Handle<JSObject> generator_function_prototype =
      factory()->NewJSObject(isolate()->object_function(), TENURED);
835
  JSObject::ForceSetPrototype(generator_function_prototype, empty);
836

837 838 839 840
  JSObject::AddProperty(
      generator_function_prototype, factory()->to_string_tag_symbol(),
      factory()->NewStringFromAsciiChecked("GeneratorFunction"),
      static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
841
  JSObject::AddProperty(generator_function_prototype,
842
                        factory()->prototype_string(),
843 844 845
                        generator_object_prototype,
                        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

846 847 848 849 850 851 852 853 854
  JSObject::AddProperty(generator_object_prototype,
                        factory()->constructor_string(),
                        generator_function_prototype,
                        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
  JSObject::AddProperty(generator_object_prototype,
                        factory()->to_string_tag_symbol(),
                        factory()->NewStringFromAsciiChecked("Generator"),
                        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
  SimpleInstallFunction(generator_object_prototype, "next",
855
                        Builtins::kGeneratorPrototypeNext, 1, false);
856
  SimpleInstallFunction(generator_object_prototype, "return",
857
                        Builtins::kGeneratorPrototypeReturn, 1, false);
858
  SimpleInstallFunction(generator_object_prototype, "throw",
859
                        Builtins::kGeneratorPrototypeThrow, 1, false);
860

861 862
  // Internal version of generator_prototype_next, flagged as non-native such
  // that it doesn't show up in Error traces.
863 864
  Handle<JSFunction> generator_next_internal =
      SimpleCreateFunction(isolate(), factory()->next_string(),
865
                           Builtins::kGeneratorPrototypeNext, 1, false);
866
  generator_next_internal->shared()->set_native(false);
867 868
  native_context()->set_generator_next_internal(*generator_next_internal);

869 870 871 872 873
  // Create maps for generator functions and their prototypes.  Store those
  // maps in the native context. The "prototype" property descriptor is
  // writable, non-enumerable, and non-configurable (as per ES6 draft
  // 04-14-15, section 25.2.4.3).
  // Generator functions do not have "caller" or "arguments" accessors.
874 875 876 877 878 879 880 881 882 883 884 885 886 887 888 889 890 891 892 893
  Handle<Map> map;
  map = CreateNonConstructorMap(isolate()->strict_function_map(),
                                generator_function_prototype,
                                "GeneratorFunction");
  native_context()->set_generator_function_map(*map);

  map = CreateNonConstructorMap(isolate()->strict_function_with_name_map(),
                                generator_function_prototype,
                                "GeneratorFunction with name");
  native_context()->set_generator_function_with_name_map(*map);

  map = CreateNonConstructorMap(strict_function_with_home_object_map_,
                                generator_function_prototype,
                                "GeneratorFunction with home object");
  native_context()->set_generator_function_with_home_object_map(*map);

  map = CreateNonConstructorMap(strict_function_with_name_and_home_object_map_,
                                generator_function_prototype,
                                "GeneratorFunction with name and home object");
  native_context()->set_generator_function_with_name_and_home_object_map(*map);
894 895 896 897 898 899 900 901

  Handle<JSFunction> object_function(native_context()->object_function());
  Handle<Map> generator_object_prototype_map = Map::Create(isolate(), 0);
  Map::SetPrototype(generator_object_prototype_map, generator_object_prototype);
  native_context()->set_generator_object_prototype_map(
      *generator_object_prototype_map);
}

902
void Genesis::CreateAsyncIteratorMaps(Handle<JSFunction> empty) {
903 904 905 906 907
  // %AsyncIteratorPrototype%
  // proposal-async-iteration/#sec-asynciteratorprototype
  Handle<JSObject> async_iterator_prototype =
      factory()->NewJSObject(isolate()->object_function(), TENURED);

908 909 910
  SimpleInstallFunction(
      async_iterator_prototype, factory()->async_iterator_symbol(),
      "[Symbol.asyncIterator]", Builtins::kReturnReceiver, 0, true);
911 912 913 914 915 916 917 918 919 920 921 922 923 924 925 926 927 928 929 930 931 932 933 934 935 936 937 938 939

  // %AsyncFromSyncIteratorPrototype%
  // proposal-async-iteration/#sec-%asyncfromsynciteratorprototype%-object
  Handle<JSObject> async_from_sync_iterator_prototype =
      factory()->NewJSObject(isolate()->object_function(), TENURED);
  SimpleInstallFunction(async_from_sync_iterator_prototype,
                        factory()->next_string(),
                        Builtins::kAsyncFromSyncIteratorPrototypeNext, 1, true);
  SimpleInstallFunction(
      async_from_sync_iterator_prototype, factory()->return_string(),
      Builtins::kAsyncFromSyncIteratorPrototypeReturn, 1, true);
  SimpleInstallFunction(
      async_from_sync_iterator_prototype, factory()->throw_string(),
      Builtins::kAsyncFromSyncIteratorPrototypeThrow, 1, true);

  JSObject::AddProperty(
      async_from_sync_iterator_prototype, factory()->to_string_tag_symbol(),
      factory()->NewStringFromAsciiChecked("Async-from-Sync Iterator"),
      static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

  JSObject::ForceSetPrototype(async_from_sync_iterator_prototype,
                              async_iterator_prototype);

  Handle<Map> async_from_sync_iterator_map = factory()->NewMap(
      JS_ASYNC_FROM_SYNC_ITERATOR_TYPE, JSAsyncFromSyncIterator::kSize);
  Map::SetPrototype(async_from_sync_iterator_map,
                    async_from_sync_iterator_prototype);
  native_context()->set_async_from_sync_iterator_map(
      *async_from_sync_iterator_map);
940 941 942 943 944 945 946 947 948 949 950 951 952 953 954 955 956 957 958 959 960 961 962 963 964 965 966 967 968

  // Async Generators
  Handle<String> AsyncGeneratorFunction_string =
      factory()->NewStringFromAsciiChecked("AsyncGeneratorFunction", TENURED);

  Handle<JSObject> async_generator_object_prototype =
      factory()->NewJSObject(isolate()->object_function(), TENURED);
  Handle<JSObject> async_generator_function_prototype =
      factory()->NewJSObject(isolate()->object_function(), TENURED);

  // %AsyncGenerator% / %AsyncGeneratorFunction%.prototype
  JSObject::ForceSetPrototype(async_generator_function_prototype, empty);

  // The value of AsyncGeneratorFunction.prototype.prototype is the
  //     %AsyncGeneratorPrototype% intrinsic object.
  // This property has the attributes
  //     { [[Writable]]: false, [[Enumerable]]: false, [[Configurable]]: true }.
  JSObject::AddProperty(async_generator_function_prototype,
                        factory()->prototype_string(),
                        async_generator_object_prototype,
                        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
  JSObject::AddProperty(async_generator_function_prototype,
                        factory()->to_string_tag_symbol(),
                        AsyncGeneratorFunction_string,
                        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

  // %AsyncGeneratorPrototype%
  JSObject::ForceSetPrototype(async_generator_object_prototype,
                              async_iterator_prototype);
969 970
  native_context()->set_initial_async_generator_prototype(
      *async_generator_object_prototype);
971 972 973 974 975 976

  JSObject::AddProperty(async_generator_object_prototype,
                        factory()->to_string_tag_symbol(),
                        factory()->NewStringFromAsciiChecked("AsyncGenerator"),
                        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
  SimpleInstallFunction(async_generator_object_prototype, "next",
977
                        Builtins::kAsyncGeneratorPrototypeNext, 1, false);
978
  SimpleInstallFunction(async_generator_object_prototype, "return",
979
                        Builtins::kAsyncGeneratorPrototypeReturn, 1, false);
980
  SimpleInstallFunction(async_generator_object_prototype, "throw",
981
                        Builtins::kAsyncGeneratorPrototypeThrow, 1, false);
982 983 984 985 986 987

  // Create maps for generator functions and their prototypes.  Store those
  // maps in the native context. The "prototype" property descriptor is
  // writable, non-enumerable, and non-configurable (as per ES6 draft
  // 04-14-15, section 25.2.4.3).
  // Async Generator functions do not have "caller" or "arguments" accessors.
988 989 990 991 992 993 994 995 996 997 998 999 1000 1001 1002 1003 1004 1005 1006 1007 1008 1009
  Handle<Map> map;
  map = CreateNonConstructorMap(isolate()->strict_function_map(),
                                async_generator_function_prototype,
                                "AsyncGeneratorFunction");
  native_context()->set_async_generator_function_map(*map);

  map = CreateNonConstructorMap(isolate()->strict_function_with_name_map(),
                                async_generator_function_prototype,
                                "AsyncGeneratorFunction with name");
  native_context()->set_async_generator_function_with_name_map(*map);

  map = CreateNonConstructorMap(strict_function_with_home_object_map_,
                                async_generator_function_prototype,
                                "AsyncGeneratorFunction with home object");
  native_context()->set_async_generator_function_with_home_object_map(*map);

  map = CreateNonConstructorMap(
      strict_function_with_name_and_home_object_map_,
      async_generator_function_prototype,
      "AsyncGeneratorFunction with name and home object");
  native_context()->set_async_generator_function_with_name_and_home_object_map(
      *map);
1010 1011 1012 1013 1014 1015 1016

  Handle<JSFunction> object_function(native_context()->object_function());
  Handle<Map> async_generator_object_prototype_map = Map::Create(isolate(), 0);
  Map::SetPrototype(async_generator_object_prototype_map,
                    async_generator_object_prototype);
  native_context()->set_async_generator_object_prototype_map(
      *async_generator_object_prototype_map);
1017 1018
}

1019 1020 1021 1022
void Genesis::CreateAsyncFunctionMaps(Handle<JSFunction> empty) {
  // %AsyncFunctionPrototype% intrinsic
  Handle<JSObject> async_function_prototype =
      factory()->NewJSObject(isolate()->object_function(), TENURED);
1023
  JSObject::ForceSetPrototype(async_function_prototype, empty);
1024 1025 1026 1027 1028 1029

  JSObject::AddProperty(async_function_prototype,
                        factory()->to_string_tag_symbol(),
                        factory()->NewStringFromAsciiChecked("AsyncFunction"),
                        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

1030 1031 1032 1033 1034 1035 1036 1037 1038 1039 1040 1041 1042 1043 1044 1045 1046 1047 1048 1049
  Handle<Map> map;
  map = CreateNonConstructorMap(
      isolate()->strict_function_without_prototype_map(),
      async_function_prototype, "AsyncFunction");
  native_context()->set_async_function_map(*map);

  map = CreateNonConstructorMap(isolate()->method_with_name_map(),
                                async_function_prototype,
                                "AsyncFunction with name");
  native_context()->set_async_function_with_name_map(*map);

  map = CreateNonConstructorMap(isolate()->method_with_home_object_map(),
                                async_function_prototype,
                                "AsyncFunction with home object");
  native_context()->set_async_function_with_home_object_map(*map);

  map = CreateNonConstructorMap(
      isolate()->method_with_name_and_home_object_map(),
      async_function_prototype, "AsyncFunction with name and home object");
  native_context()->set_async_function_with_name_and_home_object_map(*map);
1050 1051
}

1052
void Genesis::CreateJSProxyMaps() {
1053
  // Allocate maps for all Proxy types.
1054 1055 1056
  // Next to the default proxy, we need maps indicating callable and
  // constructable proxies.
  Handle<Map> proxy_map =
1057
      factory()->NewMap(JS_PROXY_TYPE, JSProxy::kSize, PACKED_ELEMENTS);
1058
  proxy_map->set_dictionary_map(true);
1059
  proxy_map->set_may_have_interesting_symbols(true);
1060 1061 1062 1063 1064 1065 1066 1067 1068 1069 1070 1071
  native_context()->set_proxy_map(*proxy_map);

  Handle<Map> proxy_callable_map = Map::Copy(proxy_map, "callable Proxy");
  proxy_callable_map->set_is_callable();
  native_context()->set_proxy_callable_map(*proxy_callable_map);
  proxy_callable_map->SetConstructor(native_context()->function_function());

  Handle<Map> proxy_constructor_map =
      Map::Copy(proxy_callable_map, "constructor Proxy");
  proxy_constructor_map->set_is_constructor(true);
  native_context()->set_proxy_constructor_map(*proxy_constructor_map);
}
1072

1073 1074 1075 1076
namespace {
void ReplaceAccessors(Handle<Map> map, Handle<String> name,
                      PropertyAttributes attributes,
                      Handle<AccessorPair> accessor_pair) {
1077
  DescriptorArray* descriptors = map->instance_descriptors();
1078
  int idx = descriptors->SearchWithCache(map->GetIsolate(), *name, *map);
1079 1080
  Descriptor d = Descriptor::AccessorConstant(name, accessor_pair, attributes);
  descriptors->Replace(idx, &d);
1081
}
1082
}  // namespace
1083

1084
void Genesis::AddRestrictedFunctionProperties(Handle<JSFunction> empty) {
1085
  PropertyAttributes rw_attribs = static_cast<PropertyAttributes>(DONT_ENUM);
1086
  Handle<JSFunction> thrower = GetThrowTypeErrorIntrinsic();
1087 1088 1089 1090
  Handle<AccessorPair> accessors = factory()->NewAccessorPair();
  accessors->set_getter(*thrower);
  accessors->set_setter(*thrower);

1091
  Handle<Map> map(empty->map());
1092 1093
  ReplaceAccessors(map, factory()->arguments_string(), rw_attribs, accessors);
  ReplaceAccessors(map, factory()->caller_string(), rw_attribs, accessors);
1094 1095 1096
}


1097
static void AddToWeakNativeContextList(Context* context) {
1098
  DCHECK(context->IsNativeContext());
1099 1100
  Isolate* isolate = context->GetIsolate();
  Heap* heap = isolate->heap();
1101 1102
#ifdef DEBUG
  { // NOLINT
1103
    DCHECK(context->next_context_link()->IsUndefined(isolate));
1104
    // Check that context is not in the list yet.
1105
    for (Object* current = heap->native_contexts_list();
1106
         !current->IsUndefined(isolate);
1107
         current = Context::cast(current)->next_context_link()) {
1108
      DCHECK(current != context);
1109 1110 1111
    }
  }
#endif
1112 1113
  context->set(Context::NEXT_CONTEXT_LINK, heap->native_contexts_list(),
               UPDATE_WEAK_WRITE_BARRIER);
1114
  heap->set_native_contexts_list(context);
1115 1116 1117
}


1118
void Genesis::CreateRoots() {
1119
  // Allocate the native context FixedArray first and then patch the
1120 1121
  // closure and extension object later (we need the empty function
  // and the global object, but in order to create those, we need the
1122
  // native context).
1123 1124
  native_context_ = factory()->NewNativeContext();
  AddToWeakNativeContextList(*native_context());
1125
  isolate()->set_context(*native_context());
1126

1127 1128
  // Allocate the message listeners object.
  {
1129 1130
    Handle<TemplateList> list = TemplateList::New(isolate(), 1);
    native_context()->set_message_listeners(*list);
1131 1132
  }
}
1133 1134


1135 1136 1137 1138 1139 1140 1141 1142 1143 1144 1145 1146 1147 1148 1149 1150 1151 1152
void Genesis::InstallGlobalThisBinding() {
  Handle<ScriptContextTable> script_contexts(
      native_context()->script_context_table());
  Handle<ScopeInfo> scope_info = ScopeInfo::CreateGlobalThisBinding(isolate());
  Handle<JSFunction> closure(native_context()->closure());
  Handle<Context> context = factory()->NewScriptContext(closure, scope_info);

  // Go ahead and hook it up while we're at it.
  int slot = scope_info->ReceiverContextSlotIndex();
  DCHECK_EQ(slot, Context::MIN_CONTEXT_SLOTS);
  context->set(slot, native_context()->global_proxy());

  Handle<ScriptContextTable> new_script_contexts =
      ScriptContextTable::Extend(script_contexts, context);
  native_context()->set_script_context_table(*new_script_contexts);
}


1153
Handle<JSGlobalObject> Genesis::CreateNewGlobals(
1154
    v8::Local<v8::ObjectTemplate> global_proxy_template,
1155
    Handle<JSGlobalProxy> global_proxy) {
1156
  // The argument global_proxy_template aka data is an ObjectTemplateInfo.
1157 1158
  // It has a constructor pointer that points at global_constructor which is a
  // FunctionTemplateInfo.
1159
  // The global_proxy_constructor is used to (re)initialize the
1160 1161 1162
  // global_proxy. The global_proxy_constructor also has a prototype_template
  // pointer that points at js_global_object_template which is an
  // ObjectTemplateInfo.
1163
  // That in turn has a constructor pointer that points at
1164 1165 1166
  // js_global_object_constructor which is a FunctionTemplateInfo.
  // js_global_object_constructor is used to make js_global_object_function
  // js_global_object_function is used to make the new global_object.
1167 1168
  //
  // --- G l o b a l ---
1169 1170 1171 1172 1173
  // Step 1: Create a fresh JSGlobalObject.
  Handle<JSFunction> js_global_object_function;
  Handle<ObjectTemplateInfo> js_global_object_template;
  if (!global_proxy_template.IsEmpty()) {
    // Get prototype template of the global_proxy_template.
1174
    Handle<ObjectTemplateInfo> data =
1175
        v8::Utils::OpenHandle(*global_proxy_template);
1176 1177 1178
    Handle<FunctionTemplateInfo> global_constructor =
        Handle<FunctionTemplateInfo>(
            FunctionTemplateInfo::cast(data->constructor()));
1179 1180
    Handle<Object> proto_template(global_constructor->prototype_template(),
                                  isolate());
1181
    if (!proto_template->IsUndefined(isolate())) {
1182
      js_global_object_template =
1183
          Handle<ObjectTemplateInfo>::cast(proto_template);
1184
    }
1185
  }
1186

1187
  if (js_global_object_template.is_null()) {
1188
    Handle<String> name(factory()->empty_string());
1189
    Handle<Code> code = BUILTIN_CODE(isolate(), Illegal);
1190 1191
    Handle<JSObject> prototype =
        factory()->NewFunctionPrototype(isolate()->object_function());
1192 1193 1194 1195
    NewFunctionArgs args = NewFunctionArgs::ForBuiltinWithPrototype(
        name, code, prototype, JS_GLOBAL_OBJECT_TYPE, JSGlobalObject::kSize, 0,
        Builtins::kIllegal, MUTABLE);
    js_global_object_function = factory()->NewFunction(args);
1196 1197 1198 1199 1200 1201 1202
#ifdef DEBUG
    LookupIterator it(prototype, factory()->constructor_string(),
                      LookupIterator::OWN_SKIP_INTERCEPTOR);
    Handle<Object> value = Object::GetProperty(&it).ToHandleChecked();
    DCHECK(it.IsFound());
    DCHECK_EQ(*isolate()->object_function(), *value);
#endif
1203
  } else {
1204 1205
    Handle<FunctionTemplateInfo> js_global_object_constructor(
        FunctionTemplateInfo::cast(js_global_object_template->constructor()));
1206
    js_global_object_function = ApiNatives::CreateApiFunction(
1207 1208
        isolate(), js_global_object_constructor, factory()->the_hole_value(),
        ApiNatives::GlobalObjectType);
1209
  }
1210

1211
  js_global_object_function->initial_map()->set_is_prototype_map(true);
1212
  js_global_object_function->initial_map()->set_dictionary_map(true);
1213 1214
  js_global_object_function->initial_map()->set_may_have_interesting_symbols(
      true);
1215 1216
  Handle<JSGlobalObject> global_object =
      factory()->NewJSGlobalObject(js_global_object_function);
1217

1218
  // Step 2: (re)initialize the global proxy object.
1219
  Handle<JSFunction> global_proxy_function;
1220
  if (global_proxy_template.IsEmpty()) {
1221
    Handle<String> name(factory()->empty_string());
1222
    Handle<Code> code = BUILTIN_CODE(isolate(), Illegal);
1223 1224 1225 1226 1227
    NewFunctionArgs args = NewFunctionArgs::ForBuiltinWithPrototype(
        name, code, factory()->the_hole_value(), JS_GLOBAL_PROXY_TYPE,
        JSGlobalProxy::SizeWithEmbedderFields(0), 0, Builtins::kIllegal,
        MUTABLE);
    global_proxy_function = factory()->NewFunction(args);
1228 1229
  } else {
    Handle<ObjectTemplateInfo> data =
1230
        v8::Utils::OpenHandle(*global_proxy_template);
1231 1232
    Handle<FunctionTemplateInfo> global_constructor(
            FunctionTemplateInfo::cast(data->constructor()));
1233
    global_proxy_function = ApiNatives::CreateApiFunction(
1234 1235
        isolate(), global_constructor, factory()->the_hole_value(),
        ApiNatives::GlobalProxyType);
1236
  }
1237
  Handle<String> global_name = factory()->global_string();
1238 1239
  global_proxy_function->shared()->set_instance_class_name(*global_name);
  global_proxy_function->initial_map()->set_is_access_check_needed(true);
1240
  global_proxy_function->initial_map()->set_has_hidden_prototype(true);
1241
  global_proxy_function->initial_map()->set_may_have_interesting_symbols(true);
1242
  native_context()->set_global_proxy_function(*global_proxy_function);
1243 1244 1245 1246

  // Set global_proxy.__proto__ to js_global after ConfigureGlobalObjects
  // Return the global proxy.

1247
  factory()->ReinitializeJSGlobalProxy(global_proxy, global_proxy_function);
1248

1249
  // Set the native context for the global object.
1250 1251
  global_object->set_native_context(*native_context());
  global_object->set_global_proxy(*global_proxy);
1252
  // Set the native context of the global proxy.
1253
  global_proxy->set_native_context(*native_context());
1254 1255 1256
  // Set the global proxy of the native context. If the native context has been
  // deserialized, the global proxy is already correctly set up by the
  // deserializer. Otherwise it's undefined.
1257 1258 1259
  DCHECK(native_context()
             ->get(Context::GLOBAL_PROXY_INDEX)
             ->IsUndefined(isolate()) ||
1260
         native_context()->global_proxy() == *global_proxy);
1261
  native_context()->set_global_proxy(*global_proxy);
1262 1263

  return global_object;
1264 1265
}

1266 1267 1268 1269 1270 1271 1272 1273 1274 1275 1276 1277
void Genesis::HookUpGlobalProxy(Handle<JSGlobalProxy> global_proxy) {
  // Re-initialize the global proxy with the global proxy function from the
  // snapshot, and then set up the link to the native context.
  Handle<JSFunction> global_proxy_function(
      native_context()->global_proxy_function());
  factory()->ReinitializeJSGlobalProxy(global_proxy, global_proxy_function);
  Handle<JSObject> global_object(
      JSObject::cast(native_context()->global_object()));
  JSObject::ForceSetPrototype(global_proxy, global_object);
  global_proxy->set_native_context(*native_context());
  DCHECK(native_context()->global_proxy() == *global_proxy);
}
1278

1279
void Genesis::HookUpGlobalObject(Handle<JSGlobalObject> global_object) {
1280 1281
  Handle<JSGlobalObject> global_object_from_snapshot(
      JSGlobalObject::cast(native_context()->extension()));
1282 1283
  native_context()->set_extension(*global_object);
  native_context()->set_security_token(*global_object);
1284

1285 1286
  TransferNamedProperties(global_object_from_snapshot, global_object);
  TransferIndexedProperties(global_object_from_snapshot, global_object);
1287 1288
}

1289 1290 1291 1292 1293 1294 1295 1296 1297
static void InstallWithIntrinsicDefaultProto(Isolate* isolate,
                                             Handle<JSFunction> function,
                                             int context_index) {
  Handle<Smi> index(Smi::FromInt(context_index), isolate);
  JSObject::AddProperty(
      function, isolate->factory()->native_context_index_symbol(), index, NONE);
  isolate->native_context()->set(context_index, *function);
}

jgruber's avatar
jgruber committed
1298 1299 1300 1301
static void InstallError(Isolate* isolate, Handle<JSObject> global,
                         Handle<String> name, int context_index) {
  Factory* factory = isolate->factory();

1302
  Handle<JSFunction> error_fun = InstallFunction(
1303
      global, name, JS_ERROR_TYPE, JSObject::kHeaderSize, 0,
1304
      factory->the_hole_value(), Builtins::kErrorConstructor, DONT_ENUM);
jgruber's avatar
jgruber committed
1305 1306
  error_fun->shared()->set_instance_class_name(*factory->Error_string());
  error_fun->shared()->DontAdaptArguments();
1307
  error_fun->shared()->SetConstructStub(
1308
      *BUILTIN_CODE(isolate, ErrorConstructor));
jgruber's avatar
jgruber committed
1309 1310 1311
  error_fun->shared()->set_length(1);

  if (context_index == Context::ERROR_FUNCTION_INDEX) {
1312 1313
    SimpleInstallFunction(error_fun, "captureStackTrace",
                          Builtins::kErrorCaptureStackTrace, 2, false);
jgruber's avatar
jgruber committed
1314 1315 1316 1317 1318
  }

  InstallWithIntrinsicDefaultProto(isolate, error_fun, context_index);

  {
1319 1320
    // Setup %XXXErrorPrototype%.
    Handle<JSObject> prototype(JSObject::cast(error_fun->instance_prototype()));
jgruber's avatar
jgruber committed
1321 1322 1323 1324 1325

    JSObject::AddProperty(prototype, factory->name_string(), name, DONT_ENUM);
    JSObject::AddProperty(prototype, factory->message_string(),
                          factory->empty_string(), DONT_ENUM);

1326 1327 1328 1329 1330
    if (context_index == Context::ERROR_FUNCTION_INDEX) {
      Handle<JSFunction> to_string_fun =
          SimpleInstallFunction(prototype, factory->toString_string(),
                                Builtins::kErrorPrototypeToString, 0, true);
      isolate->native_context()->set_error_to_string(*to_string_fun);
1331
      isolate->native_context()->set_initial_error_prototype(*prototype);
1332 1333 1334 1335 1336
    } else {
      DCHECK(isolate->native_context()->error_to_string()->IsJSFunction());

      InstallFunction(prototype, isolate->error_to_string(),
                      factory->toString_string(), DONT_ENUM);
jgruber's avatar
jgruber committed
1337 1338 1339

      Handle<JSFunction> global_error = isolate->error_function();
      CHECK(JSReceiver::SetPrototype(error_fun, global_error, false,
1340
                                     kThrowOnError)
jgruber's avatar
jgruber committed
1341 1342 1343
                .FromMaybe(false));
      CHECK(JSReceiver::SetPrototype(prototype,
                                     handle(global_error->prototype(), isolate),
1344
                                     false, kThrowOnError)
jgruber's avatar
jgruber committed
1345 1346 1347 1348 1349 1350 1351 1352
                .FromMaybe(false));
    }
  }

  Handle<Map> initial_map(error_fun->initial_map());
  Map::EnsureDescriptorSlack(initial_map, 1);

  {
1353
    Handle<AccessorInfo> info = factory->error_stack_accessor();
1354 1355
    Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                info, DONT_ENUM);
jgruber's avatar
jgruber committed
1356 1357 1358
    initial_map->AppendDescriptor(&d);
  }
}
1359

1360 1361
namespace {

1362 1363 1364 1365 1366 1367 1368 1369
void InstallMakeError(Isolate* isolate, int builtin_id, int context_index) {
  Handle<Code> code(isolate->builtins()->builtin(builtin_id));
  NewFunctionArgs args = NewFunctionArgs::ForBuiltinWithPrototype(
      isolate->factory()->empty_string(), code,
      isolate->factory()->the_hole_value(), JS_OBJECT_TYPE,
      JSObject::kHeaderSize, 0, builtin_id, MUTABLE);

  Handle<JSFunction> function = isolate->factory()->NewFunction(args);
1370 1371 1372 1373
  function->shared()->DontAdaptArguments();
  isolate->native_context()->set(context_index, *function);
}

1374 1375
}  // namespace

1376
// This is only called if we are not using snapshots.  The equivalent
1377
// work in the snapshot case is done in HookUpGlobalObject.
1378
void Genesis::InitializeGlobal(Handle<JSGlobalObject> global_object,
1379
                               Handle<JSFunction> empty_function,
1380
                               GlobalContextType context_type) {
1381
  // --- N a t i v e   C o n t e x t ---
1382
  // Use the empty function as closure (no scope info).
1383
  native_context()->set_closure(*empty_function);
1384
  native_context()->set_previous(nullptr);
1385
  // Set extension and global object.
1386 1387 1388 1389 1390 1391 1392
  native_context()->set_extension(*global_object);
  // Security setup: Set the security token of the native context to the global
  // object. This makes the security check between two different contexts fail
  // by default even in case of global object reinitialization.
  native_context()->set_security_token(*global_object);

  Isolate* isolate = global_object->GetIsolate();
1393 1394
  Factory* factory = isolate->factory();

1395 1396 1397
  Handle<ScriptContextTable> script_context_table =
      factory->NewScriptContextTable();
  native_context()->set_script_context_table(*script_context_table);
1398
  InstallGlobalThisBinding();
1399

1400 1401 1402 1403 1404
  {  // --- O b j e c t ---
    Handle<String> object_name = factory->Object_string();
    Handle<JSFunction> object_function = isolate->object_function();
    JSObject::AddProperty(global_object, object_name, object_function,
                          DONT_ENUM);
1405

1406 1407
    SimpleInstallFunction(object_function, factory->assign_string(),
                          Builtins::kObjectAssign, 2, false);
1408 1409
    SimpleInstallFunction(object_function, "getOwnPropertyDescriptor",
                          Builtins::kObjectGetOwnPropertyDescriptor, 2, false);
1410 1411 1412
    SimpleInstallFunction(object_function,
                          factory->getOwnPropertyDescriptors_string(),
                          Builtins::kObjectGetOwnPropertyDescriptors, 1, false);
1413 1414
    SimpleInstallFunction(object_function, "getOwnPropertyNames",
                          Builtins::kObjectGetOwnPropertyNames, 1, false);
1415 1416
    SimpleInstallFunction(object_function, "getOwnPropertySymbols",
                          Builtins::kObjectGetOwnPropertySymbols, 1, false);
1417 1418 1419 1420 1421 1422 1423
    SimpleInstallFunction(object_function, "is",
                          Builtins::kObjectIs, 2, true);
    SimpleInstallFunction(object_function, "preventExtensions",
                          Builtins::kObjectPreventExtensions, 1, false);
    SimpleInstallFunction(object_function, "seal",
                          Builtins::kObjectSeal, 1, false);

1424 1425
    Handle<JSFunction> object_create =
        SimpleInstallFunction(object_function, factory->create_string(),
1426
                              Builtins::kObjectCreate, 2, false);
1427 1428
    native_context()->set_object_create(*object_create);

1429 1430 1431 1432 1433 1434 1435 1436 1437 1438
    Handle<JSFunction> object_define_properties = SimpleInstallFunction(
        object_function, "defineProperties",
        Builtins::kObjectDefineProperties, 2, true);
    native_context()->set_object_define_properties(*object_define_properties);

    Handle<JSFunction> object_define_property = SimpleInstallFunction(
        object_function, factory->defineProperty_string(),
        Builtins::kObjectDefineProperty, 3, true);
    native_context()->set_object_define_property(*object_define_property);

1439 1440
    SimpleInstallFunction(object_function, "freeze", Builtins::kObjectFreeze, 1,
                          false);
1441 1442 1443 1444 1445

    Handle<JSFunction> object_get_prototype_of = SimpleInstallFunction(
        object_function, "getPrototypeOf", Builtins::kObjectGetPrototypeOf,
        1, false);
    native_context()->set_object_get_prototype_of(*object_get_prototype_of);
1446 1447
    SimpleInstallFunction(object_function, "setPrototypeOf",
                          Builtins::kObjectSetPrototypeOf, 2, false);
1448 1449 1450 1451

    Handle<JSFunction> object_is_extensible = SimpleInstallFunction(
        object_function, "isExtensible", Builtins::kObjectIsExtensible,
        1, false);
1452
    native_context()->set_object_is_extensible(*object_is_extensible);
1453

1454 1455 1456
    Handle<JSFunction> object_is_frozen = SimpleInstallFunction(
        object_function, "isFrozen", Builtins::kObjectIsFrozen, 1, false);
    native_context()->set_object_is_frozen(*object_is_frozen);
1457

1458 1459 1460
    Handle<JSFunction> object_is_sealed = SimpleInstallFunction(
        object_function, "isSealed", Builtins::kObjectIsSealed, 1, false);
    native_context()->set_object_is_sealed(*object_is_sealed);
1461

1462
    Handle<JSFunction> object_keys = SimpleInstallFunction(
1463
        object_function, "keys", Builtins::kObjectKeys, 1, true);
1464
    native_context()->set_object_keys(*object_keys);
1465 1466 1467 1468
    SimpleInstallFunction(object_function, factory->entries_string(),
                          Builtins::kObjectEntries, 1, false);
    SimpleInstallFunction(object_function, factory->values_string(),
                          Builtins::kObjectValues, 1, false);
1469

1470 1471 1472 1473 1474 1475
    SimpleInstallFunction(isolate->initial_object_prototype(),
                          "__defineGetter__", Builtins::kObjectDefineGetter, 2,
                          true);
    SimpleInstallFunction(isolate->initial_object_prototype(),
                          "__defineSetter__", Builtins::kObjectDefineSetter, 2,
                          true);
1476
    SimpleInstallFunction(isolate->initial_object_prototype(), "hasOwnProperty",
1477
                          Builtins::kObjectPrototypeHasOwnProperty, 1, true);
1478 1479 1480 1481 1482 1483
    SimpleInstallFunction(isolate->initial_object_prototype(),
                          "__lookupGetter__", Builtins::kObjectLookupGetter, 1,
                          true);
    SimpleInstallFunction(isolate->initial_object_prototype(),
                          "__lookupSetter__", Builtins::kObjectLookupSetter, 1,
                          true);
1484 1485
    SimpleInstallFunction(isolate->initial_object_prototype(), "isPrototypeOf",
                          Builtins::kObjectPrototypeIsPrototypeOf, 1, true);
1486 1487 1488
    SimpleInstallFunction(
        isolate->initial_object_prototype(), "propertyIsEnumerable",
        Builtins::kObjectPrototypePropertyIsEnumerable, 1, false);
1489 1490
    Handle<JSFunction> object_to_string = SimpleInstallFunction(
        isolate->initial_object_prototype(), factory->toString_string(),
1491
        Builtins::kObjectPrototypeToString, 0, true);
1492
    native_context()->set_object_to_string(*object_to_string);
1493 1494 1495 1496
    Handle<JSFunction> object_value_of = SimpleInstallFunction(
        isolate->initial_object_prototype(), "valueOf",
        Builtins::kObjectPrototypeValueOf, 0, true);
    native_context()->set_object_value_of(*object_value_of);
1497 1498 1499 1500 1501

    SimpleInstallGetterSetter(isolate->initial_object_prototype(),
                              factory->proto_string(),
                              Builtins::kObjectPrototypeGetProto,
                              Builtins::kObjectPrototypeSetProto, DONT_ENUM);
1502
  }
1503

1504
  Handle<JSObject> global(native_context()->global_object());
1505

ishell's avatar
ishell committed
1506
  {  // --- F u n c t i o n ---
1507
    Handle<JSFunction> prototype = empty_function;
1508
    Handle<JSFunction> function_fun = InstallFunction(
1509
        global, "Function", JS_FUNCTION_TYPE, JSFunction::kSizeWithPrototype, 0,
1510
        prototype, Builtins::kFunctionConstructor);
1511 1512
    // Function instances are sloppy by default.
    function_fun->set_prototype_or_initial_map(*isolate->sloppy_function_map());
1513
    function_fun->shared()->DontAdaptArguments();
1514 1515
    function_fun->shared()->SetConstructStub(
        *BUILTIN_CODE(isolate, FunctionConstructor));
1516 1517
    function_fun->shared()->set_length(1);
    InstallWithIntrinsicDefaultProto(isolate, function_fun,
1518
                                     Context::FUNCTION_FUNCTION_INDEX);
ishell's avatar
ishell committed
1519

1520
    // Setup the methods on the %FunctionPrototype%.
1521 1522
    JSObject::AddProperty(prototype, factory->constructor_string(),
                          function_fun, DONT_ENUM);
1523 1524
    SimpleInstallFunction(prototype, factory->apply_string(),
                          Builtins::kFunctionPrototypeApply, 2, false);
1525 1526
    SimpleInstallFunction(prototype, factory->bind_string(),
                          Builtins::kFastFunctionPrototypeBind, 1, false);
1527 1528 1529 1530 1531
    SimpleInstallFunction(prototype, factory->call_string(),
                          Builtins::kFunctionPrototypeCall, 1, false);
    SimpleInstallFunction(prototype, factory->toString_string(),
                          Builtins::kFunctionPrototypeToString, 0, false);

1532
    // Install the @@hasInstance function.
1533 1534 1535 1536 1537
    Handle<JSFunction> has_instance = SimpleInstallFunction(
        prototype, factory->has_instance_symbol(), "[Symbol.hasInstance]",
        Builtins::kFunctionPrototypeHasInstance, 1, true,
        static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY),
        kFunctionHasInstance);
1538
    native_context()->set_function_has_instance(*has_instance);
1539

1540 1541 1542
    // Complete setting up function maps.
    {
      isolate->sloppy_function_map()->SetConstructor(*function_fun);
1543
      isolate->sloppy_function_with_name_map()->SetConstructor(*function_fun);
1544 1545 1546 1547
      isolate->sloppy_function_with_readonly_prototype_map()->SetConstructor(
          *function_fun);

      isolate->strict_function_map()->SetConstructor(*function_fun);
1548 1549 1550 1551
      isolate->strict_function_with_name_map()->SetConstructor(*function_fun);
      strict_function_with_home_object_map_->SetConstructor(*function_fun);
      strict_function_with_name_and_home_object_map_->SetConstructor(
          *function_fun);
1552 1553
      isolate->strict_function_with_readonly_prototype_map()->SetConstructor(
          *function_fun);
1554

1555 1556
      isolate->class_function_map()->SetConstructor(*function_fun);
    }
1557
  }
1558

1559
  {  // --- A s y n c F r o m S y n c I t e r a t o r
1560 1561 1562
    Handle<SharedFunctionInfo> info = SimpleCreateSharedFunctionInfo(
        isolate, Builtins::kAsyncIteratorValueUnwrap, factory->empty_string(),
        1);
1563 1564 1565
    native_context()->set_async_iterator_value_unwrap_shared_fun(*info);
  }

1566 1567 1568
  {  // --- A s y n c G e n e r a t o r ---
    Handle<JSFunction> await_caught =
        SimpleCreateFunction(isolate, factory->empty_string(),
1569
                             Builtins::kAsyncGeneratorAwaitCaught, 1, false);
1570
    native_context()->set_async_generator_await_caught(*await_caught);
1571 1572 1573

    Handle<JSFunction> await_uncaught =
        SimpleCreateFunction(isolate, factory->empty_string(),
1574
                             Builtins::kAsyncGeneratorAwaitUncaught, 1, false);
1575
    native_context()->set_async_generator_await_uncaught(*await_uncaught);
1576

1577 1578 1579
    Handle<SharedFunctionInfo> info = SimpleCreateSharedFunctionInfo(
        isolate, Builtins::kAsyncGeneratorAwaitResolveClosure,
        factory->empty_string(), 1);
1580 1581
    native_context()->set_async_generator_await_resolve_shared_fun(*info);

1582 1583 1584
    info = SimpleCreateSharedFunctionInfo(
        isolate, Builtins::kAsyncGeneratorAwaitRejectClosure,
        factory->empty_string(), 1);
1585
    native_context()->set_async_generator_await_reject_shared_fun(*info);
1586

1587 1588 1589
    info = SimpleCreateSharedFunctionInfo(
        isolate, Builtins::kAsyncGeneratorYieldResolveClosure,
        factory->empty_string(), 1);
1590 1591
    native_context()->set_async_generator_yield_resolve_shared_fun(*info);

1592 1593 1594
    info = SimpleCreateSharedFunctionInfo(
        isolate, Builtins::kAsyncGeneratorReturnResolveClosure,
        factory->empty_string(), 1);
1595 1596
    native_context()->set_async_generator_return_resolve_shared_fun(*info);

1597 1598 1599
    info = SimpleCreateSharedFunctionInfo(
        isolate, Builtins::kAsyncGeneratorReturnClosedResolveClosure,
        factory->empty_string(), 1);
1600 1601 1602
    native_context()->set_async_generator_return_closed_resolve_shared_fun(
        *info);

1603 1604 1605
    info = SimpleCreateSharedFunctionInfo(
        isolate, Builtins::kAsyncGeneratorReturnClosedRejectClosure,
        factory->empty_string(), 1);
1606 1607
    native_context()->set_async_generator_return_closed_reject_shared_fun(
        *info);
1608 1609
  }

1610
  {  // --- A r r a y ---
1611
    Handle<JSFunction> array_function = InstallFunction(
1612
        global, "Array", JS_ARRAY_TYPE, JSArray::kSize, 0,
1613
        isolate->initial_object_prototype(), Builtins::kArrayConstructor);
1614
    array_function->shared()->DontAdaptArguments();
1615
    array_function->shared()->set_builtin_function_id(kArrayConstructor);
1616 1617 1618 1619

    // This seems a bit hackish, but we need to make sure Array.length
    // is 1.
    array_function->shared()->set_length(1);
1620

1621
    Handle<Map> initial_map(array_function->initial_map());
1622 1623 1624

    // This assert protects an optimization in
    // HGraphBuilder::JSArrayBuilder::EmitMapCode()
1625
    DCHECK(initial_map->elements_kind() == GetInitialFastElementsKind());
1626
    Map::EnsureDescriptorSlack(initial_map, 1);
1627

1628 1629 1630 1631
    PropertyAttributes attribs = static_cast<PropertyAttributes>(
        DONT_ENUM | DONT_DELETE);

    {  // Add length.
1632 1633
      Descriptor d = Descriptor::AccessorConstant(
          factory->length_string(), factory->array_length_accessor(), attribs);
1634
      initial_map->AppendDescriptor(&d);
1635
    }
1636

1637 1638
    InstallWithIntrinsicDefaultProto(isolate, array_function,
                                     Context::ARRAY_FUNCTION_INDEX);
1639
    InstallSpeciesGetter(array_function);
1640

1641 1642 1643
    // Cache the array maps, needed by ArrayConstructorStub
    CacheInitialJSArrayMaps(native_context(), initial_map);
    ArrayConstructorStub array_constructor_stub(isolate);
1644
    Handle<Code> code = array_constructor_stub.GetCode();
1645
    array_function->shared()->SetConstructStub(*code);
1646

1647
    // Set up %ArrayPrototype%.
1648 1649 1650
    // The %ArrayPrototype% has TERMINAL_FAST_ELEMENTS_KIND in order to ensure
    // that constant functions stay constant after turning prototype to setup
    // mode and back when constant field tracking is enabled.
1651
    Handle<JSArray> proto =
1652
        factory->NewJSArray(0, TERMINAL_FAST_ELEMENTS_KIND, TENURED);
1653 1654
    JSFunction::SetPrototype(array_function, proto);
    native_context()->set_initial_array_prototype(*proto);
1655

1656
    Handle<JSFunction> is_arraylike = SimpleInstallFunction(
1657
        array_function, "isArray", Builtins::kArrayIsArray, 1, true);
1658
    native_context()->set_is_arraylike(*is_arraylike);
1659 1660 1661 1662 1663 1664 1665 1666 1667

    JSObject::AddProperty(proto, factory->constructor_string(), array_function,
                          DONT_ENUM);

    SimpleInstallFunction(proto, "concat", Builtins::kArrayConcat, 1, false);
    SimpleInstallFunction(proto, "pop", Builtins::kFastArrayPop, 0, false);
    SimpleInstallFunction(proto, "push", Builtins::kFastArrayPush, 1, false);
    SimpleInstallFunction(proto, "shift", Builtins::kFastArrayShift, 0, false);
    SimpleInstallFunction(proto, "unshift", Builtins::kArrayUnshift, 1, false);
1668 1669 1670 1671 1672 1673
    if (FLAG_enable_experimental_builtins) {
      SimpleInstallFunction(proto, "slice", Builtins::kFastArraySlice, 2,
                            false);
    } else {
      SimpleInstallFunction(proto, "slice", Builtins::kArraySlice, 2, false);
    }
1674 1675 1676 1677 1678 1679 1680 1681 1682
    SimpleInstallFunction(proto, "splice", Builtins::kArraySplice, 2, false);
    SimpleInstallFunction(proto, "includes", Builtins::kArrayIncludes, 1,
                          false);
    SimpleInstallFunction(proto, "indexOf", Builtins::kArrayIndexOf, 1, false);
    SimpleInstallFunction(proto, "keys", Builtins::kArrayPrototypeKeys, 0, true,
                          kArrayKeys);
    SimpleInstallFunction(proto, "entries", Builtins::kArrayPrototypeEntries, 0,
                          true, kArrayEntries);
    SimpleInstallFunction(proto, factory->iterator_symbol(), "values",
1683
                          Builtins::kArrayPrototypeValues, 0, true, DONT_ENUM,
1684 1685 1686 1687 1688 1689 1690 1691 1692
                          kArrayValues);
    SimpleInstallFunction(proto, "forEach", Builtins::kArrayForEach, 1, false);
    SimpleInstallFunction(proto, "filter", Builtins::kArrayFilter, 1, false);
    SimpleInstallFunction(proto, "map", Builtins::kArrayMap, 1, false);
    SimpleInstallFunction(proto, "every", Builtins::kArrayEvery, 1, false);
    SimpleInstallFunction(proto, "some", Builtins::kArraySome, 1, false);
    SimpleInstallFunction(proto, "reduce", Builtins::kArrayReduce, 1, false);
    SimpleInstallFunction(proto, "reduceRight", Builtins::kArrayReduceRight, 1,
                          false);
1693 1694
  }

1695 1696 1697 1698 1699 1700 1701 1702 1703 1704 1705 1706 1707
  {  // --- A r r a y I t e r a t o r ---
    Handle<JSObject> iterator_prototype(
        native_context()->initial_iterator_prototype());

    Handle<JSObject> array_iterator_prototype =
        factory->NewJSObject(isolate->object_function(), TENURED);
    JSObject::ForceSetPrototype(array_iterator_prototype, iterator_prototype);

    JSObject::AddProperty(
        array_iterator_prototype, factory->to_string_tag_symbol(),
        factory->ArrayIterator_string(),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

1708 1709 1710
    SimpleInstallFunction(array_iterator_prototype, "next",
                          Builtins::kArrayIteratorPrototypeNext, 0, true,
                          kArrayIteratorNext);
1711 1712 1713

    Handle<JSFunction> array_iterator_function = CreateFunction(
        isolate, factory->ArrayIterator_string(),
1714
        JS_FAST_ARRAY_VALUE_ITERATOR_TYPE, JSArrayIterator::kSize, 0,
1715
        array_iterator_prototype, Builtins::kIllegal);
1716
    array_iterator_function->shared()->set_native(false);
1717 1718 1719
    array_iterator_function->shared()->set_instance_class_name(
        isolate->heap()->ArrayIterator_string());

1720 1721 1722 1723 1724
    native_context()->set_initial_array_iterator_prototype(
        *array_iterator_prototype);
    native_context()->set_initial_array_iterator_prototype_map(
        array_iterator_prototype->map());

1725 1726 1727 1728 1729 1730 1731 1732 1733 1734 1735 1736 1737 1738 1739 1740 1741 1742 1743 1744 1745 1746 1747 1748 1749 1750 1751 1752 1753 1754 1755 1756 1757 1758 1759 1760 1761 1762 1763 1764 1765 1766 1767 1768 1769 1770 1771 1772 1773 1774 1775 1776 1777 1778
    Handle<Map> initial_map(array_iterator_function->initial_map(), isolate);

#define ARRAY_ITERATOR_LIST(V)                                              \
  V(TYPED_ARRAY, KEY, typed_array, key)                                     \
  V(FAST_ARRAY, KEY, fast_array, key)                                       \
  V(GENERIC_ARRAY, KEY, array, key)                                         \
  V(UINT8_ARRAY, KEY_VALUE, uint8_array, key_value)                         \
  V(INT8_ARRAY, KEY_VALUE, int8_array, key_value)                           \
  V(UINT16_ARRAY, KEY_VALUE, uint16_array, key_value)                       \
  V(INT16_ARRAY, KEY_VALUE, int16_array, key_value)                         \
  V(UINT32_ARRAY, KEY_VALUE, uint32_array, key_value)                       \
  V(INT32_ARRAY, KEY_VALUE, int32_array, key_value)                         \
  V(FLOAT32_ARRAY, KEY_VALUE, float32_array, key_value)                     \
  V(FLOAT64_ARRAY, KEY_VALUE, float64_array, key_value)                     \
  V(UINT8_CLAMPED_ARRAY, KEY_VALUE, uint8_clamped_array, key_value)         \
  V(FAST_SMI_ARRAY, KEY_VALUE, fast_smi_array, key_value)                   \
  V(FAST_HOLEY_SMI_ARRAY, KEY_VALUE, fast_holey_smi_array, key_value)       \
  V(FAST_ARRAY, KEY_VALUE, fast_array, key_value)                           \
  V(FAST_HOLEY_ARRAY, KEY_VALUE, fast_holey_array, key_value)               \
  V(FAST_DOUBLE_ARRAY, KEY_VALUE, fast_double_array, key_value)             \
  V(FAST_HOLEY_DOUBLE_ARRAY, KEY_VALUE, fast_holey_double_array, key_value) \
  V(GENERIC_ARRAY, KEY_VALUE, array, key_value)                             \
  V(UINT8_ARRAY, VALUE, uint8_array, value)                                 \
  V(INT8_ARRAY, VALUE, int8_array, value)                                   \
  V(UINT16_ARRAY, VALUE, uint16_array, value)                               \
  V(INT16_ARRAY, VALUE, int16_array, value)                                 \
  V(UINT32_ARRAY, VALUE, uint32_array, value)                               \
  V(INT32_ARRAY, VALUE, int32_array, value)                                 \
  V(FLOAT32_ARRAY, VALUE, float32_array, value)                             \
  V(FLOAT64_ARRAY, VALUE, float64_array, value)                             \
  V(UINT8_CLAMPED_ARRAY, VALUE, uint8_clamped_array, value)                 \
  V(FAST_SMI_ARRAY, VALUE, fast_smi_array, value)                           \
  V(FAST_HOLEY_SMI_ARRAY, VALUE, fast_holey_smi_array, value)               \
  V(FAST_ARRAY, VALUE, fast_array, value)                                   \
  V(FAST_HOLEY_ARRAY, VALUE, fast_holey_array, value)                       \
  V(FAST_DOUBLE_ARRAY, VALUE, fast_double_array, value)                     \
  V(FAST_HOLEY_DOUBLE_ARRAY, VALUE, fast_holey_double_array, value)         \
  V(GENERIC_ARRAY, VALUE, array, value)

#define CREATE_ARRAY_ITERATOR_MAP(PREFIX, SUFFIX, prefix, suffix)           \
  do {                                                                      \
    const InstanceType type = JS_##PREFIX##_##SUFFIX##_ITERATOR_TYPE;       \
    Handle<Map> map =                                                       \
        Map::Copy(initial_map, "JS_" #PREFIX "_" #SUFFIX "_ITERATOR_TYPE"); \
    map->set_instance_type(type);                                           \
    native_context()->set_##prefix##_##suffix##_iterator_map(*map);         \
  } while (0);

    ARRAY_ITERATOR_LIST(CREATE_ARRAY_ITERATOR_MAP)

#undef CREATE_ARRAY_ITERATOR_MAP
#undef ARRAY_ITERATOR_LIST
  }

1779
  {  // --- N u m b e r ---
1780
    Handle<JSFunction> number_fun = InstallFunction(
1781
        global, "Number", JS_VALUE_TYPE, JSValue::kSize, 0,
1782 1783
        isolate->initial_object_prototype(), Builtins::kNumberConstructor);
    number_fun->shared()->DontAdaptArguments();
1784
    number_fun->shared()->SetConstructStub(
1785
        *BUILTIN_CODE(isolate, NumberConstructor_ConstructStub));
1786
    number_fun->shared()->set_length(1);
1787 1788
    InstallWithIntrinsicDefaultProto(isolate, number_fun,
                                     Context::NUMBER_FUNCTION_INDEX);
1789 1790 1791 1792

    // Create the %NumberPrototype%
    Handle<JSValue> prototype =
        Handle<JSValue>::cast(factory->NewJSObject(number_fun, TENURED));
1793
    prototype->set_value(Smi::kZero);
1794
    JSFunction::SetPrototype(number_fun, prototype);
1795 1796 1797 1798 1799 1800 1801 1802 1803 1804 1805 1806 1807 1808 1809 1810 1811

    // Install the "constructor" property on the {prototype}.
    JSObject::AddProperty(prototype, factory->constructor_string(), number_fun,
                          DONT_ENUM);

    // Install the Number.prototype methods.
    SimpleInstallFunction(prototype, "toExponential",
                          Builtins::kNumberPrototypeToExponential, 1, false);
    SimpleInstallFunction(prototype, "toFixed",
                          Builtins::kNumberPrototypeToFixed, 1, false);
    SimpleInstallFunction(prototype, "toPrecision",
                          Builtins::kNumberPrototypeToPrecision, 1, false);
    SimpleInstallFunction(prototype, "toString",
                          Builtins::kNumberPrototypeToString, 1, false);
    SimpleInstallFunction(prototype, "valueOf",
                          Builtins::kNumberPrototypeValueOf, 0, true);

1812
    // Install Intl fallback functions.
1813 1814
    SimpleInstallFunction(prototype, "toLocaleString",
                          Builtins::kNumberPrototypeToLocaleString, 0, false);
1815 1816 1817 1818 1819 1820 1821 1822 1823

    // Install the Number functions.
    SimpleInstallFunction(number_fun, "isFinite", Builtins::kNumberIsFinite, 1,
                          true);
    SimpleInstallFunction(number_fun, "isInteger", Builtins::kNumberIsInteger,
                          1, true);
    SimpleInstallFunction(number_fun, "isNaN", Builtins::kNumberIsNaN, 1, true);
    SimpleInstallFunction(number_fun, "isSafeInteger",
                          Builtins::kNumberIsSafeInteger, 1, true);
1824 1825 1826 1827 1828 1829 1830

    // Install Number.parseFloat and Global.parseFloat.
    Handle<JSFunction> parse_float_fun = SimpleInstallFunction(
        number_fun, "parseFloat", Builtins::kNumberParseFloat, 1, true);
    JSObject::AddProperty(global_object,
                          factory->NewStringFromAsciiChecked("parseFloat"),
                          parse_float_fun, DONT_ENUM);
1831 1832 1833 1834 1835 1836 1837

    // Install Number.parseInt and Global.parseInt.
    Handle<JSFunction> parse_int_fun = SimpleInstallFunction(
        number_fun, "parseInt", Builtins::kNumberParseInt, 2, true);
    JSObject::AddProperty(global_object,
                          factory->NewStringFromAsciiChecked("parseInt"),
                          parse_int_fun, DONT_ENUM);
1838 1839 1840 1841 1842 1843 1844 1845 1846 1847 1848 1849 1850 1851 1852 1853 1854 1855 1856 1857 1858 1859 1860 1861 1862 1863 1864 1865 1866 1867 1868 1869 1870 1871 1872 1873 1874 1875 1876 1877 1878 1879 1880 1881 1882 1883 1884 1885 1886 1887 1888 1889 1890 1891 1892

    // Install Number constants
    double kMaxValue = 1.7976931348623157e+308;
    double kMinValue = 5e-324;

    double kMaxSafeInt = 9007199254740991;
    double kMinSafeInt = -9007199254740991;
    double kEPS = 2.220446049250313e-16;

    Handle<Object> infinity = factory->infinity_value();
    Handle<Object> nan = factory->nan_value();
    Handle<String> nan_name = factory->NewStringFromAsciiChecked("NaN");

    JSObject::AddProperty(
        number_fun, factory->NewStringFromAsciiChecked("MAX_VALUE"),
        factory->NewNumber(kMaxValue),
        static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY));
    JSObject::AddProperty(
        number_fun, factory->NewStringFromAsciiChecked("MIN_VALUE"),
        factory->NewNumber(kMinValue),
        static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY));
    JSObject::AddProperty(
        number_fun, nan_name, nan,
        static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY));
    JSObject::AddProperty(
        number_fun, factory->NewStringFromAsciiChecked("NEGATIVE_INFINITY"),
        factory->NewNumber(-V8_INFINITY),
        static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY));
    JSObject::AddProperty(
        number_fun, factory->NewStringFromAsciiChecked("POSITIVE_INFINITY"),
        infinity,
        static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY));
    JSObject::AddProperty(
        number_fun, factory->NewStringFromAsciiChecked("MAX_SAFE_INTEGER"),
        factory->NewNumber(kMaxSafeInt),
        static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY));
    JSObject::AddProperty(
        number_fun, factory->NewStringFromAsciiChecked("MIN_SAFE_INTEGER"),
        factory->NewNumber(kMinSafeInt),
        static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY));
    JSObject::AddProperty(
        number_fun, factory->NewStringFromAsciiChecked("EPSILON"),
        factory->NewNumber(kEPS),
        static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY));

    JSObject::AddProperty(
        global, factory->NewStringFromAsciiChecked("Infinity"), infinity,
        static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY));
    JSObject::AddProperty(
        global, nan_name, nan,
        static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY));
    JSObject::AddProperty(
        global, factory->NewStringFromAsciiChecked("undefined"),
        factory->undefined_value(),
        static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY));
1893 1894 1895
  }

  {  // --- B o o l e a n ---
1896 1897 1898
    Handle<JSFunction> boolean_fun = InstallFunction(
        global, "Boolean", JS_VALUE_TYPE, JSValue::kSize, 0,
        isolate->initial_object_prototype(), Builtins::kBooleanConstructor);
1899
    boolean_fun->shared()->DontAdaptArguments();
1900
    boolean_fun->shared()->SetConstructStub(
1901
        *BUILTIN_CODE(isolate, BooleanConstructor_ConstructStub));
1902
    boolean_fun->shared()->set_length(1);
1903 1904
    InstallWithIntrinsicDefaultProto(isolate, boolean_fun,
                                     Context::BOOLEAN_FUNCTION_INDEX);
1905 1906 1907 1908 1909

    // Create the %BooleanPrototype%
    Handle<JSValue> prototype =
        Handle<JSValue>::cast(factory->NewJSObject(boolean_fun, TENURED));
    prototype->set_value(isolate->heap()->false_value());
1910
    JSFunction::SetPrototype(boolean_fun, prototype);
1911 1912 1913 1914 1915 1916 1917

    // Install the "constructor" property on the {prototype}.
    JSObject::AddProperty(prototype, factory->constructor_string(), boolean_fun,
                          DONT_ENUM);

    // Install the Boolean.prototype methods.
    SimpleInstallFunction(prototype, "toString",
1918
                          Builtins::kBooleanPrototypeToString, 0, true);
1919
    SimpleInstallFunction(prototype, "valueOf",
1920
                          Builtins::kBooleanPrototypeValueOf, 0, true);
1921 1922 1923
  }

  {  // --- S t r i n g ---
1924
    Handle<JSFunction> string_fun = InstallFunction(
1925
        global, "String", JS_VALUE_TYPE, JSValue::kSize, 0,
1926
        isolate->initial_object_prototype(), Builtins::kStringConstructor);
1927
    string_fun->shared()->SetConstructStub(
1928
        *BUILTIN_CODE(isolate, StringConstructor_ConstructStub));
1929 1930
    string_fun->shared()->DontAdaptArguments();
    string_fun->shared()->set_length(1);
1931 1932
    InstallWithIntrinsicDefaultProto(isolate, string_fun,
                                     Context::STRING_FUNCTION_INDEX);
1933

1934
    Handle<Map> string_map =
1935
        Handle<Map>(native_context()->string_function()->initial_map());
1936
    string_map->set_elements_kind(FAST_STRING_WRAPPER_ELEMENTS);
1937
    Map::EnsureDescriptorSlack(string_map, 1);
1938

1939 1940 1941 1942
    PropertyAttributes attribs = static_cast<PropertyAttributes>(
        DONT_ENUM | DONT_DELETE | READ_ONLY);

    {  // Add length.
1943 1944
      Descriptor d = Descriptor::AccessorConstant(
          factory->length_string(), factory->string_length_accessor(), attribs);
1945
      string_map->AppendDescriptor(&d);
1946
    }
1947

1948 1949
    // Install the String.fromCharCode function.
    SimpleInstallFunction(string_fun, "fromCharCode",
1950
                          Builtins::kStringFromCharCode, 1, false);
1951

1952 1953 1954 1955
    // Install the String.fromCodePoint function.
    SimpleInstallFunction(string_fun, "fromCodePoint",
                          Builtins::kStringFromCodePoint, 1, false);

1956 1957 1958
    // Install the String.raw function.
    SimpleInstallFunction(string_fun, "raw", Builtins::kStringRaw, 1, false);

1959 1960 1961 1962
    // Create the %StringPrototype%
    Handle<JSValue> prototype =
        Handle<JSValue>::cast(factory->NewJSObject(string_fun, TENURED));
    prototype->set_value(isolate->heap()->empty_string());
1963
    JSFunction::SetPrototype(string_fun, prototype);
1964
    native_context()->set_initial_string_prototype(*prototype);
1965 1966 1967 1968 1969 1970

    // Install the "constructor" property on the {prototype}.
    JSObject::AddProperty(prototype, factory->constructor_string(), string_fun,
                          DONT_ENUM);

    // Install the String.prototype methods.
1971 1972 1973 1974 1975 1976 1977 1978
    SimpleInstallFunction(prototype, "anchor", Builtins::kStringPrototypeAnchor,
                          1, true);
    SimpleInstallFunction(prototype, "big", Builtins::kStringPrototypeBig, 0,
                          true);
    SimpleInstallFunction(prototype, "blink", Builtins::kStringPrototypeBlink,
                          0, true);
    SimpleInstallFunction(prototype, "bold", Builtins::kStringPrototypeBold, 0,
                          true);
1979 1980 1981 1982
    SimpleInstallFunction(prototype, "charAt", Builtins::kStringPrototypeCharAt,
                          1, true);
    SimpleInstallFunction(prototype, "charCodeAt",
                          Builtins::kStringPrototypeCharCodeAt, 1, true);
1983 1984
    SimpleInstallFunction(prototype, "codePointAt",
                          Builtins::kStringPrototypeCodePointAt, 1, true);
1985 1986
    SimpleInstallFunction(prototype, "concat", Builtins::kStringPrototypeConcat,
                          1, false);
1987 1988
    SimpleInstallFunction(prototype, "endsWith",
                          Builtins::kStringPrototypeEndsWith, 1, false);
1989 1990 1991 1992 1993 1994
    SimpleInstallFunction(prototype, "fontcolor",
                          Builtins::kStringPrototypeFontcolor, 1, true);
    SimpleInstallFunction(prototype, "fontsize",
                          Builtins::kStringPrototypeFontsize, 1, true);
    SimpleInstallFunction(prototype, "fixed", Builtins::kStringPrototypeFixed,
                          0, true);
1995 1996
    SimpleInstallFunction(prototype, "includes",
                          Builtins::kStringPrototypeIncludes, 1, false);
1997 1998
    SimpleInstallFunction(prototype, "indexOf",
                          Builtins::kStringPrototypeIndexOf, 1, false);
1999 2000
    SimpleInstallFunction(prototype, "italics",
                          Builtins::kStringPrototypeItalics, 0, true);
2001 2002
    SimpleInstallFunction(prototype, "lastIndexOf",
                          Builtins::kStringPrototypeLastIndexOf, 1, false);
2003 2004
    SimpleInstallFunction(prototype, "link", Builtins::kStringPrototypeLink, 1,
                          true);
2005 2006
    SimpleInstallFunction(prototype, "localeCompare",
                          Builtins::kStringPrototypeLocaleCompare, 1, true);
2007 2008
    SimpleInstallFunction(prototype, "match", Builtins::kStringPrototypeMatch,
                          1, true);
2009
#ifdef V8_INTL_SUPPORT
2010
    SimpleInstallFunction(prototype, "normalize",
2011
                          Builtins::kStringPrototypeNormalizeIntl, 0, false);
2012
#else
2013 2014
    SimpleInstallFunction(prototype, "normalize",
                          Builtins::kStringPrototypeNormalize, 0, false);
2015
#endif  // V8_INTL_SUPPORT
2016 2017 2018 2019
    SimpleInstallFunction(prototype, "padEnd", Builtins::kStringPrototypePadEnd,
                          1, false);
    SimpleInstallFunction(prototype, "padStart",
                          Builtins::kStringPrototypePadStart, 1, false);
2020 2021
    SimpleInstallFunction(prototype, "repeat", Builtins::kStringPrototypeRepeat,
                          1, true);
2022 2023
    SimpleInstallFunction(prototype, "replace",
                          Builtins::kStringPrototypeReplace, 2, true);
2024 2025
    SimpleInstallFunction(prototype, "search", Builtins::kStringPrototypeSearch,
                          1, true);
2026 2027
    SimpleInstallFunction(prototype, "slice", Builtins::kStringPrototypeSlice,
                          2, false);
2028 2029
    SimpleInstallFunction(prototype, "small", Builtins::kStringPrototypeSmall,
                          0, true);
2030
    SimpleInstallFunction(prototype, "split", Builtins::kStringPrototypeSplit,
2031
                          2, false);
2032 2033 2034 2035
    SimpleInstallFunction(prototype, "strike", Builtins::kStringPrototypeStrike,
                          0, true);
    SimpleInstallFunction(prototype, "sub", Builtins::kStringPrototypeSub, 0,
                          true);
2036
    SimpleInstallFunction(prototype, "substr", Builtins::kStringPrototypeSubstr,
2037
                          2, false);
2038
    SimpleInstallFunction(prototype, "substring",
2039
                          Builtins::kStringPrototypeSubstring, 2, false);
2040 2041
    SimpleInstallFunction(prototype, "sup", Builtins::kStringPrototypeSup, 0,
                          true);
2042 2043
    SimpleInstallFunction(prototype, "startsWith",
                          Builtins::kStringPrototypeStartsWith, 1, false);
2044 2045
    SimpleInstallFunction(prototype, "toString",
                          Builtins::kStringPrototypeToString, 0, true);
2046 2047 2048 2049 2050 2051
    SimpleInstallFunction(prototype, "trim", Builtins::kStringPrototypeTrim, 0,
                          false);
    SimpleInstallFunction(prototype, "trimLeft",
                          Builtins::kStringPrototypeTrimLeft, 0, false);
    SimpleInstallFunction(prototype, "trimRight",
                          Builtins::kStringPrototypeTrimRight, 0, false);
2052 2053 2054 2055 2056 2057
#ifdef V8_INTL_SUPPORT
    SimpleInstallFunction(prototype, "toLowerCase",
                          Builtins::kStringPrototypeToLowerCaseIntl, 0, true);
    SimpleInstallFunction(prototype, "toUpperCase",
                          Builtins::kStringPrototypeToUpperCaseIntl, 0, false);
#else
2058 2059 2060 2061 2062 2063 2064 2065 2066 2067
    SimpleInstallFunction(prototype, "toLocaleLowerCase",
                          Builtins::kStringPrototypeToLocaleLowerCase, 0,
                          false);
    SimpleInstallFunction(prototype, "toLocaleUpperCase",
                          Builtins::kStringPrototypeToLocaleUpperCase, 0,
                          false);
    SimpleInstallFunction(prototype, "toLowerCase",
                          Builtins::kStringPrototypeToLowerCase, 0, false);
    SimpleInstallFunction(prototype, "toUpperCase",
                          Builtins::kStringPrototypeToUpperCase, 0, false);
2068
#endif
2069 2070
    SimpleInstallFunction(prototype, "valueOf",
                          Builtins::kStringPrototypeValueOf, 0, true);
2071

2072 2073 2074 2075
    SimpleInstallFunction(prototype, factory->iterator_symbol(),
                          "[Symbol.iterator]",
                          Builtins::kStringPrototypeIterator, 0, true,
                          DONT_ENUM, kStringIterator);
2076 2077 2078 2079 2080 2081 2082 2083 2084 2085 2086 2087 2088 2089 2090
  }

  {  // --- S t r i n g I t e r a t o r ---
    Handle<JSObject> iterator_prototype(
        native_context()->initial_iterator_prototype());

    Handle<JSObject> string_iterator_prototype =
        factory->NewJSObject(isolate->object_function(), TENURED);
    JSObject::ForceSetPrototype(string_iterator_prototype, iterator_prototype);

    JSObject::AddProperty(
        string_iterator_prototype, factory->to_string_tag_symbol(),
        factory->NewStringFromAsciiChecked("String Iterator"),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

2091 2092 2093
    SimpleInstallFunction(string_iterator_prototype, "next",
                          Builtins::kStringIteratorPrototypeNext, 0, true,
                          kStringIteratorNext);
2094 2095 2096

    Handle<JSFunction> string_iterator_function = CreateFunction(
        isolate, factory->NewStringFromAsciiChecked("StringIterator"),
2097
        JS_STRING_ITERATOR_TYPE, JSStringIterator::kSize, 0,
2098
        string_iterator_prototype, Builtins::kIllegal);
2099
    string_iterator_function->shared()->set_native(false);
2100 2101
    native_context()->set_string_iterator_map(
        string_iterator_function->initial_map());
2102 2103
  }

2104 2105
  {  // --- S y m b o l ---
    Handle<JSFunction> symbol_fun = InstallFunction(
2106
        global, "Symbol", JS_VALUE_TYPE, JSValue::kSize, 0,
2107
        factory->the_hole_value(), Builtins::kSymbolConstructor);
2108
    symbol_fun->shared()->SetConstructStub(
2109
        *BUILTIN_CODE(isolate, SymbolConstructor_ConstructStub));
2110
    symbol_fun->shared()->set_length(0);
2111
    symbol_fun->shared()->DontAdaptArguments();
2112
    native_context()->set_symbol_function(*symbol_fun);
2113

2114 2115 2116 2117 2118 2119 2120 2121 2122 2123 2124 2125 2126 2127 2128 2129 2130 2131 2132 2133 2134 2135 2136 2137
    // Install the Symbol.for and Symbol.keyFor functions.
    SimpleInstallFunction(symbol_fun, "for", Builtins::kSymbolFor, 1, false);
    SimpleInstallFunction(symbol_fun, "keyFor", Builtins::kSymbolKeyFor, 1,
                          false);

    // Install well-known symbols.
    InstallConstant(isolate, symbol_fun, "hasInstance",
                    factory->has_instance_symbol());
    InstallConstant(isolate, symbol_fun, "isConcatSpreadable",
                    factory->is_concat_spreadable_symbol());
    InstallConstant(isolate, symbol_fun, "iterator",
                    factory->iterator_symbol());
    InstallConstant(isolate, symbol_fun, "match", factory->match_symbol());
    InstallConstant(isolate, symbol_fun, "replace", factory->replace_symbol());
    InstallConstant(isolate, symbol_fun, "search", factory->search_symbol());
    InstallConstant(isolate, symbol_fun, "species", factory->species_symbol());
    InstallConstant(isolate, symbol_fun, "split", factory->split_symbol());
    InstallConstant(isolate, symbol_fun, "toPrimitive",
                    factory->to_primitive_symbol());
    InstallConstant(isolate, symbol_fun, "toStringTag",
                    factory->to_string_tag_symbol());
    InstallConstant(isolate, symbol_fun, "unscopables",
                    factory->unscopables_symbol());

2138 2139 2140 2141
    // Setup %SymbolPrototype%.
    Handle<JSObject> prototype(
        JSObject::cast(symbol_fun->instance_prototype()));

2142 2143 2144 2145 2146 2147 2148 2149 2150 2151 2152 2153 2154 2155 2156
    // Install the @@toStringTag property on the {prototype}.
    JSObject::AddProperty(
        prototype, factory->to_string_tag_symbol(),
        factory->NewStringFromAsciiChecked("Symbol"),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

    // Install the Symbol.prototype methods.
    SimpleInstallFunction(prototype, "toString",
                          Builtins::kSymbolPrototypeToString, 0, true);
    SimpleInstallFunction(prototype, "valueOf",
                          Builtins::kSymbolPrototypeValueOf, 0, true);

    // Install the @@toPrimitive function.
    Handle<JSFunction> to_primitive = InstallFunction(
        prototype, factory->to_primitive_symbol(), JS_OBJECT_TYPE,
2157
        JSObject::kHeaderSize, 0, MaybeHandle<JSObject>(),
2158 2159 2160 2161 2162 2163 2164 2165
        Builtins::kSymbolPrototypeToPrimitive,
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

    // Set the expected parameters for @@toPrimitive to 1; required by builtin.
    to_primitive->shared()->set_internal_formal_parameter_count(1);

    // Set the length for the function to satisfy ECMA-262.
    to_primitive->shared()->set_length(1);
2166 2167
  }

2168
  {  // --- D a t e ---
2169
    Handle<JSFunction> date_fun =
2170
        InstallFunction(global, "Date", JS_DATE_TYPE, JSDate::kSize, 0,
2171
                        factory->the_hole_value(), Builtins::kDateConstructor);
2172 2173
    InstallWithIntrinsicDefaultProto(isolate, date_fun,
                                     Context::DATE_FUNCTION_INDEX);
2174
    date_fun->shared()->SetConstructStub(
2175
        *BUILTIN_CODE(isolate, DateConstructor_ConstructStub));
2176 2177
    date_fun->shared()->set_length(7);
    date_fun->shared()->DontAdaptArguments();
2178 2179 2180 2181 2182 2183

    // Install the Date.now, Date.parse and Date.UTC functions.
    SimpleInstallFunction(date_fun, "now", Builtins::kDateNow, 0, false);
    SimpleInstallFunction(date_fun, "parse", Builtins::kDateParse, 1, false);
    SimpleInstallFunction(date_fun, "UTC", Builtins::kDateUTC, 7, false);

2184 2185
    // Setup %DatePrototype%.
    Handle<JSObject> prototype(JSObject::cast(date_fun->instance_prototype()));
2186 2187 2188 2189 2190 2191 2192 2193 2194 2195

    // Install the Date.prototype methods.
    SimpleInstallFunction(prototype, "toString",
                          Builtins::kDatePrototypeToString, 0, false);
    SimpleInstallFunction(prototype, "toDateString",
                          Builtins::kDatePrototypeToDateString, 0, false);
    SimpleInstallFunction(prototype, "toTimeString",
                          Builtins::kDatePrototypeToTimeString, 0, false);
    SimpleInstallFunction(prototype, "toISOString",
                          Builtins::kDatePrototypeToISOString, 0, false);
2196 2197 2198 2199 2200
    Handle<JSFunction> to_utc_string =
        SimpleInstallFunction(prototype, "toUTCString",
                              Builtins::kDatePrototypeToUTCString, 0, false);
    InstallFunction(prototype, to_utc_string,
                    factory->InternalizeUtf8String("toGMTString"), DONT_ENUM);
2201 2202 2203 2204 2205 2206 2207 2208 2209 2210 2211 2212 2213 2214 2215 2216 2217 2218 2219 2220 2221 2222 2223 2224 2225 2226 2227 2228 2229 2230 2231 2232 2233 2234 2235 2236 2237 2238 2239 2240 2241 2242 2243 2244 2245 2246 2247 2248 2249 2250 2251 2252 2253 2254 2255 2256 2257 2258 2259 2260 2261 2262 2263 2264 2265 2266 2267
    SimpleInstallFunction(prototype, "getDate", Builtins::kDatePrototypeGetDate,
                          0, true);
    SimpleInstallFunction(prototype, "setDate", Builtins::kDatePrototypeSetDate,
                          1, false);
    SimpleInstallFunction(prototype, "getDay", Builtins::kDatePrototypeGetDay,
                          0, true);
    SimpleInstallFunction(prototype, "getFullYear",
                          Builtins::kDatePrototypeGetFullYear, 0, true);
    SimpleInstallFunction(prototype, "setFullYear",
                          Builtins::kDatePrototypeSetFullYear, 3, false);
    SimpleInstallFunction(prototype, "getHours",
                          Builtins::kDatePrototypeGetHours, 0, true);
    SimpleInstallFunction(prototype, "setHours",
                          Builtins::kDatePrototypeSetHours, 4, false);
    SimpleInstallFunction(prototype, "getMilliseconds",
                          Builtins::kDatePrototypeGetMilliseconds, 0, true);
    SimpleInstallFunction(prototype, "setMilliseconds",
                          Builtins::kDatePrototypeSetMilliseconds, 1, false);
    SimpleInstallFunction(prototype, "getMinutes",
                          Builtins::kDatePrototypeGetMinutes, 0, true);
    SimpleInstallFunction(prototype, "setMinutes",
                          Builtins::kDatePrototypeSetMinutes, 3, false);
    SimpleInstallFunction(prototype, "getMonth",
                          Builtins::kDatePrototypeGetMonth, 0, true);
    SimpleInstallFunction(prototype, "setMonth",
                          Builtins::kDatePrototypeSetMonth, 2, false);
    SimpleInstallFunction(prototype, "getSeconds",
                          Builtins::kDatePrototypeGetSeconds, 0, true);
    SimpleInstallFunction(prototype, "setSeconds",
                          Builtins::kDatePrototypeSetSeconds, 2, false);
    SimpleInstallFunction(prototype, "getTime", Builtins::kDatePrototypeGetTime,
                          0, true);
    SimpleInstallFunction(prototype, "setTime", Builtins::kDatePrototypeSetTime,
                          1, false);
    SimpleInstallFunction(prototype, "getTimezoneOffset",
                          Builtins::kDatePrototypeGetTimezoneOffset, 0, true);
    SimpleInstallFunction(prototype, "getUTCDate",
                          Builtins::kDatePrototypeGetUTCDate, 0, true);
    SimpleInstallFunction(prototype, "setUTCDate",
                          Builtins::kDatePrototypeSetUTCDate, 1, false);
    SimpleInstallFunction(prototype, "getUTCDay",
                          Builtins::kDatePrototypeGetUTCDay, 0, true);
    SimpleInstallFunction(prototype, "getUTCFullYear",
                          Builtins::kDatePrototypeGetUTCFullYear, 0, true);
    SimpleInstallFunction(prototype, "setUTCFullYear",
                          Builtins::kDatePrototypeSetUTCFullYear, 3, false);
    SimpleInstallFunction(prototype, "getUTCHours",
                          Builtins::kDatePrototypeGetUTCHours, 0, true);
    SimpleInstallFunction(prototype, "setUTCHours",
                          Builtins::kDatePrototypeSetUTCHours, 4, false);
    SimpleInstallFunction(prototype, "getUTCMilliseconds",
                          Builtins::kDatePrototypeGetUTCMilliseconds, 0, true);
    SimpleInstallFunction(prototype, "setUTCMilliseconds",
                          Builtins::kDatePrototypeSetUTCMilliseconds, 1, false);
    SimpleInstallFunction(prototype, "getUTCMinutes",
                          Builtins::kDatePrototypeGetUTCMinutes, 0, true);
    SimpleInstallFunction(prototype, "setUTCMinutes",
                          Builtins::kDatePrototypeSetUTCMinutes, 3, false);
    SimpleInstallFunction(prototype, "getUTCMonth",
                          Builtins::kDatePrototypeGetUTCMonth, 0, true);
    SimpleInstallFunction(prototype, "setUTCMonth",
                          Builtins::kDatePrototypeSetUTCMonth, 2, false);
    SimpleInstallFunction(prototype, "getUTCSeconds",
                          Builtins::kDatePrototypeGetUTCSeconds, 0, true);
    SimpleInstallFunction(prototype, "setUTCSeconds",
                          Builtins::kDatePrototypeSetUTCSeconds, 2, false);
    SimpleInstallFunction(prototype, "valueOf", Builtins::kDatePrototypeValueOf,
2268
                          0, true);
2269 2270 2271 2272
    SimpleInstallFunction(prototype, "getYear", Builtins::kDatePrototypeGetYear,
                          0, true);
    SimpleInstallFunction(prototype, "setYear", Builtins::kDatePrototypeSetYear,
                          1, false);
2273 2274
    SimpleInstallFunction(prototype, "toJSON", Builtins::kDatePrototypeToJson,
                          1, false);
2275

2276
    // Install Intl fallback functions.
2277 2278 2279 2280 2281 2282 2283 2284 2285 2286
    SimpleInstallFunction(prototype, "toLocaleString",
                          Builtins::kDatePrototypeToString, 0, false);
    SimpleInstallFunction(prototype, "toLocaleDateString",
                          Builtins::kDatePrototypeToDateString, 0, false);
    SimpleInstallFunction(prototype, "toLocaleTimeString",
                          Builtins::kDatePrototypeToTimeString, 0, false);

    // Install the @@toPrimitive function.
    Handle<JSFunction> to_primitive = InstallFunction(
        prototype, factory->to_primitive_symbol(), JS_OBJECT_TYPE,
2287
        JSObject::kHeaderSize, 0, MaybeHandle<JSObject>(),
2288 2289 2290 2291 2292 2293 2294 2295
        Builtins::kDatePrototypeToPrimitive,
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

    // Set the expected parameters for @@toPrimitive to 1; required by builtin.
    to_primitive->shared()->set_internal_formal_parameter_count(1);

    // Set the length for the function to satisfy ECMA-262.
    to_primitive->shared()->set_length(1);
2296 2297
  }

2298
  {
2299 2300 2301
    Handle<SharedFunctionInfo> info = SimpleCreateSharedFunctionInfo(
        isolate, Builtins::kPromiseGetCapabilitiesExecutor,
        factory->empty_string(), factory->Object_string(), 2);
2302 2303 2304 2305 2306 2307
    native_context()->set_promise_get_capabilities_executor_shared_fun(*info);

    // %new_promise_capability(C, debugEvent)
    Handle<JSFunction> new_promise_capability =
        SimpleCreateFunction(isolate, factory->empty_string(),
                             Builtins::kNewPromiseCapability, 2, false);
2308
    native_context()->set_new_promise_capability(*new_promise_capability);
2309 2310
  }

2311
  {  // -- P r o m i s e
2312 2313
    Handle<JSFunction> promise_fun = InstallFunction(
        global, "Promise", JS_PROMISE_TYPE, JSPromise::kSizeWithEmbedderFields,
2314
        0, factory->the_hole_value(), Builtins::kPromiseConstructor);
2315 2316 2317 2318
    InstallWithIntrinsicDefaultProto(isolate, promise_fun,
                                     Context::PROMISE_FUNCTION_INDEX);

    Handle<SharedFunctionInfo> shared(promise_fun->shared(), isolate);
2319
    shared->SetConstructStub(*BUILTIN_CODE(isolate, JSBuiltinsConstructStub));
2320 2321 2322 2323
    shared->set_instance_class_name(isolate->heap()->Object_string());
    shared->set_internal_formal_parameter_count(1);
    shared->set_length(1);

2324 2325 2326 2327
    InstallSpeciesGetter(promise_fun);

    SimpleInstallFunction(promise_fun, "all", Builtins::kPromiseAll, 1, true);

2328 2329
    SimpleInstallFunction(promise_fun, "race", Builtins::kPromiseRace, 1, true);

2330 2331
    SimpleInstallFunction(promise_fun, "resolve",
                          Builtins::kPromiseResolveWrapper, 1, true);
2332 2333 2334 2335 2336 2337 2338

    SimpleInstallFunction(promise_fun, "reject", Builtins::kPromiseReject, 1,
                          true);

    // Setup %PromisePrototype%.
    Handle<JSObject> prototype(
        JSObject::cast(promise_fun->instance_prototype()));
2339 2340 2341 2342 2343 2344

    // Install the @@toStringTag property on the {prototype}.
    JSObject::AddProperty(
        prototype, factory->to_string_tag_symbol(), factory->Promise_string(),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

2345
    Handle<JSFunction> promise_then =
2346 2347
        SimpleInstallFunction(prototype, isolate->factory()->then_string(),
                              Builtins::kPromiseThen, 2, true);
2348
    native_context()->set_promise_then(*promise_then);
2349

2350
    Handle<JSFunction> promise_catch = SimpleInstallFunction(
2351
        prototype, "catch", Builtins::kPromiseCatch, 1, true);
2352
    native_context()->set_promise_catch(*promise_catch);
2353

2354 2355 2356 2357 2358 2359 2360 2361 2362
    // Force the Promise constructor to fast properties, so that we can use the
    // fast paths for various things like
    //
    //   x instanceof Promise
    //
    // etc. We should probably come up with a more principled approach once
    // the JavaScript builtins are gone.
    JSObject::MigrateSlowToFast(Handle<JSObject>::cast(promise_fun), 0,
                                "Bootstrapping");
2363

2364 2365 2366 2367 2368 2369 2370
    Handle<Map> prototype_map(prototype->map());
    Map::SetShouldBeFastPrototypeMap(prototype_map, true, isolate);

    // Store the initial Promise.prototype map. This is used in fast-path
    // checks. Do not alter the prototype after this point.
    native_context()->set_promise_prototype_map(*prototype_map);

2371
    {  // Internal: PromiseInternalConstructor
2372
       // Also exposed as extrasUtils.createPromise.
2373 2374
      Handle<JSFunction> function =
          SimpleCreateFunction(isolate, factory->empty_string(),
2375
                               Builtins::kPromiseInternalConstructor, 1, true);
2376
      function->shared()->set_native(false);
2377
      native_context()->set_promise_internal_constructor(*function);
2378 2379 2380 2381 2382
    }

    {  // Internal: IsPromise
      Handle<JSFunction> function = SimpleCreateFunction(
          isolate, factory->empty_string(), Builtins::kIsPromise, 1, false);
2383
      native_context()->set_is_promise(*function);
2384 2385
    }

2386
    {  // Internal: ResolvePromise
2387 2388 2389
       // Also exposed as extrasUtils.resolvePromise.
      Handle<JSFunction> function = SimpleCreateFunction(
          isolate, factory->empty_string(), Builtins::kResolvePromise, 2, true);
2390
      function->shared()->set_native(false);
2391
      native_context()->set_promise_resolve(*function);
2392 2393
    }

gsathya's avatar
gsathya committed
2394 2395
    {  // Internal: PromiseHandle
      Handle<JSFunction> function = SimpleCreateFunction(
2396
          isolate, factory->empty_string(), Builtins::kPromiseHandle, 5, false);
2397
      native_context()->set_promise_handle(*function);
gsathya's avatar
gsathya committed
2398 2399 2400 2401 2402 2403
    }

    {  // Internal: PromiseHandleReject
      Handle<JSFunction> function =
          SimpleCreateFunction(isolate, factory->empty_string(),
                               Builtins::kPromiseHandleReject, 3, false);
2404
      native_context()->set_promise_handle_reject(*function);
gsathya's avatar
gsathya committed
2405 2406
    }

2407 2408 2409 2410
    {  // Internal: InternalPromiseReject
      Handle<JSFunction> function =
          SimpleCreateFunction(isolate, factory->empty_string(),
                               Builtins::kInternalPromiseReject, 3, true);
2411
      function->shared()->set_native(false);
2412
      native_context()->set_promise_internal_reject(*function);
2413 2414
    }

2415
    {
2416 2417 2418
      Handle<SharedFunctionInfo> info = SimpleCreateSharedFunctionInfo(
          isolate, Builtins::kPromiseResolveClosure, factory->empty_string(),
          1);
2419 2420
      native_context()->set_promise_resolve_shared_fun(*info);

2421 2422
      info = SimpleCreateSharedFunctionInfo(
          isolate, Builtins::kPromiseRejectClosure, factory->empty_string(), 1);
2423 2424
      native_context()->set_promise_reject_shared_fun(*info);
    }
2425 2426

    {
2427 2428 2429
      Handle<SharedFunctionInfo> info = SimpleCreateSharedFunctionInfo(
          isolate, Builtins::kPromiseAllResolveElementClosure,
          factory->empty_string(), 1);
2430 2431
      native_context()->set_promise_all_resolve_element_shared_fun(*info);
    }
2432 2433 2434 2435 2436 2437 2438 2439 2440

    // Force the Promise constructor to fast properties, so that we can use the
    // fast paths for various things like
    //
    //   x instanceof Promise
    //
    // etc. We should probably come up with a more principled approach once
    // the JavaScript builtins are gone.
    JSObject::MigrateSlowToFast(promise_fun, 0, "Bootstrapping");
2441 2442
  }

2443 2444
  {  // -- R e g E x p
    // Builtin functions for RegExp.prototype.
2445
    Handle<JSFunction> regexp_fun = InstallFunction(
2446 2447 2448 2449
        global, "RegExp", JS_REGEXP_TYPE,
        JSRegExp::kSize + JSRegExp::kInObjectFieldCount * kPointerSize,
        JSRegExp::kInObjectFieldCount, factory->the_hole_value(),
        Builtins::kRegExpConstructor);
2450 2451
    InstallWithIntrinsicDefaultProto(isolate, regexp_fun,
                                     Context::REGEXP_FUNCTION_INDEX);
2452 2453

    Handle<SharedFunctionInfo> shared(regexp_fun->shared(), isolate);
2454
    shared->SetConstructStub(*BUILTIN_CODE(isolate, JSBuiltinsConstructStub));
2455
    shared->set_instance_class_name(isolate->heap()->RegExp_string());
2456
    shared->set_internal_formal_parameter_count(2);
2457
    shared->set_length(2);
2458

2459
    {
2460 2461 2462
      // Setup %RegExpPrototype%.
      Handle<JSObject> prototype(
          JSObject::cast(regexp_fun->instance_prototype()));
2463

2464 2465
      {
        Handle<JSFunction> fun = SimpleInstallFunction(
2466 2467
            prototype, factory->exec_string(), Builtins::kRegExpPrototypeExec,
            1, true, DONT_ENUM);
2468 2469
        native_context()->set_regexp_exec_function(*fun);
      }
2470

2471 2472
      SimpleInstallGetter(prototype, factory->dotAll_string(),
                          Builtins::kRegExpPrototypeDotAllGetter, true);
2473 2474 2475 2476 2477 2478 2479 2480 2481
      SimpleInstallGetter(prototype, factory->flags_string(),
                          Builtins::kRegExpPrototypeFlagsGetter, true);
      SimpleInstallGetter(prototype, factory->global_string(),
                          Builtins::kRegExpPrototypeGlobalGetter, true);
      SimpleInstallGetter(prototype, factory->ignoreCase_string(),
                          Builtins::kRegExpPrototypeIgnoreCaseGetter, true);
      SimpleInstallGetter(prototype, factory->multiline_string(),
                          Builtins::kRegExpPrototypeMultilineGetter, true);
      SimpleInstallGetter(prototype, factory->source_string(),
2482
                          Builtins::kRegExpPrototypeSourceGetter, true);
2483 2484 2485 2486
      SimpleInstallGetter(prototype, factory->sticky_string(),
                          Builtins::kRegExpPrototypeStickyGetter, true);
      SimpleInstallGetter(prototype, factory->unicode_string(),
                          Builtins::kRegExpPrototypeUnicodeGetter, true);
2487 2488

      SimpleInstallFunction(prototype, "compile",
2489
                            Builtins::kRegExpPrototypeCompile, 2, true,
2490 2491 2492 2493
                            DONT_ENUM);
      SimpleInstallFunction(prototype, factory->toString_string(),
                            Builtins::kRegExpPrototypeToString, 0, false,
                            DONT_ENUM);
2494
      SimpleInstallFunction(prototype, "test", Builtins::kRegExpPrototypeTest,
2495
                            1, true, DONT_ENUM);
2496

2497 2498 2499
      SimpleInstallFunction(prototype, factory->match_symbol(),
                            "[Symbol.match]", Builtins::kRegExpPrototypeMatch,
                            1, true);
2500

2501 2502 2503
      SimpleInstallFunction(prototype, factory->replace_symbol(),
                            "[Symbol.replace]",
                            Builtins::kRegExpPrototypeReplace, 2, false);
2504

2505 2506 2507
      SimpleInstallFunction(prototype, factory->search_symbol(),
                            "[Symbol.search]", Builtins::kRegExpPrototypeSearch,
                            1, true);
jgruber's avatar
jgruber committed
2508

2509 2510 2511
      SimpleInstallFunction(prototype, factory->split_symbol(),
                            "[Symbol.split]", Builtins::kRegExpPrototypeSplit,
                            2, false);
2512

2513 2514 2515
      Handle<Map> prototype_map(prototype->map());
      Map::SetShouldBeFastPrototypeMap(prototype_map, true, isolate);

2516 2517
      // Store the initial RegExp.prototype map. This is used in fast-path
      // checks. Do not alter the prototype after this point.
2518
      native_context()->set_regexp_prototype_map(*prototype_map);
2519
    }
2520

2521 2522 2523
    {
      // RegExp getters and setters.

2524
      InstallSpeciesGetter(regexp_fun);
2525 2526 2527

      // Static properties set by a successful match.

2528
      const PropertyAttributes no_enum = DONT_ENUM;
2529 2530
      SimpleInstallGetterSetter(regexp_fun, factory->input_string(),
                                Builtins::kRegExpInputGetter,
2531
                                Builtins::kRegExpInputSetter, no_enum);
2532 2533 2534 2535 2536 2537 2538 2539 2540 2541 2542 2543 2544 2545 2546 2547 2548 2549 2550 2551 2552 2553 2554 2555 2556 2557 2558 2559 2560 2561 2562 2563 2564 2565 2566 2567
      SimpleInstallGetterSetter(
          regexp_fun, factory->InternalizeUtf8String("$_"),
          Builtins::kRegExpInputGetter, Builtins::kRegExpInputSetter, no_enum);

      SimpleInstallGetterSetter(
          regexp_fun, factory->InternalizeUtf8String("lastMatch"),
          Builtins::kRegExpLastMatchGetter, Builtins::kEmptyFunction, no_enum);
      SimpleInstallGetterSetter(
          regexp_fun, factory->InternalizeUtf8String("$&"),
          Builtins::kRegExpLastMatchGetter, Builtins::kEmptyFunction, no_enum);

      SimpleInstallGetterSetter(
          regexp_fun, factory->InternalizeUtf8String("lastParen"),
          Builtins::kRegExpLastParenGetter, Builtins::kEmptyFunction, no_enum);
      SimpleInstallGetterSetter(
          regexp_fun, factory->InternalizeUtf8String("$+"),
          Builtins::kRegExpLastParenGetter, Builtins::kEmptyFunction, no_enum);

      SimpleInstallGetterSetter(regexp_fun,
                                factory->InternalizeUtf8String("leftContext"),
                                Builtins::kRegExpLeftContextGetter,
                                Builtins::kEmptyFunction, no_enum);
      SimpleInstallGetterSetter(regexp_fun,
                                factory->InternalizeUtf8String("$`"),
                                Builtins::kRegExpLeftContextGetter,
                                Builtins::kEmptyFunction, no_enum);

      SimpleInstallGetterSetter(regexp_fun,
                                factory->InternalizeUtf8String("rightContext"),
                                Builtins::kRegExpRightContextGetter,
                                Builtins::kEmptyFunction, no_enum);
      SimpleInstallGetterSetter(regexp_fun,
                                factory->InternalizeUtf8String("$'"),
                                Builtins::kRegExpRightContextGetter,
                                Builtins::kEmptyFunction, no_enum);

2568 2569 2570 2571
#define INSTALL_CAPTURE_GETTER(i)                         \
  SimpleInstallGetterSetter(                              \
      regexp_fun, factory->InternalizeUtf8String("$" #i), \
      Builtins::kRegExpCapture##i##Getter, Builtins::kEmptyFunction, no_enum)
2572 2573 2574 2575 2576 2577 2578 2579 2580 2581 2582
      INSTALL_CAPTURE_GETTER(1);
      INSTALL_CAPTURE_GETTER(2);
      INSTALL_CAPTURE_GETTER(3);
      INSTALL_CAPTURE_GETTER(4);
      INSTALL_CAPTURE_GETTER(5);
      INSTALL_CAPTURE_GETTER(6);
      INSTALL_CAPTURE_GETTER(7);
      INSTALL_CAPTURE_GETTER(8);
      INSTALL_CAPTURE_GETTER(9);
#undef INSTALL_CAPTURE_GETTER
    }
2583

2584
    DCHECK(regexp_fun->has_initial_map());
2585 2586
    Handle<Map> initial_map(regexp_fun->initial_map());

2587
    DCHECK_EQ(1, initial_map->GetInObjectProperties());
2588

2589 2590 2591 2592 2593
    Map::EnsureDescriptorSlack(initial_map, 1);

    // ECMA-262, section 15.10.7.5.
    PropertyAttributes writable =
        static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE);
2594 2595 2596 2597
    Descriptor d = Descriptor::DataField(factory->lastIndex_string(),
                                         JSRegExp::kLastIndexFieldIndex,
                                         writable, Representation::Tagged());
    initial_map->AppendDescriptor(&d);
2598

2599 2600
    {  // Internal: RegExpInternalMatch
      Handle<JSFunction> function =
2601 2602
          SimpleCreateFunction(isolate, isolate->factory()->empty_string(),
                               Builtins::kRegExpInternalMatch, 2, true);
2603
      native_context()->set(Context::REGEXP_INTERNAL_MATCH, *function);
2604
    }
2605 2606 2607 2608 2609 2610 2611

    // Create the last match info. One for external use, and one for internal
    // use when we don't want to modify the externally visible match info.
    Handle<RegExpMatchInfo> last_match_info = factory->NewRegExpMatchInfo();
    native_context()->set_regexp_last_match_info(*last_match_info);
    Handle<RegExpMatchInfo> internal_match_info = factory->NewRegExpMatchInfo();
    native_context()->set_regexp_internal_match_info(*internal_match_info);
2612 2613 2614 2615 2616 2617 2618 2619 2620

    // Force the RegExp constructor to fast properties, so that we can use the
    // fast paths for various things like
    //
    //   x instanceof RegExp
    //
    // etc. We should probably come up with a more principled approach once
    // the JavaScript builtins are gone.
    JSObject::MigrateSlowToFast(regexp_fun, 0, "Bootstrapping");
2621 2622
  }

2623
  {  // -- E r r o r
jgruber's avatar
jgruber committed
2624 2625
    InstallError(isolate, global, factory->Error_string(),
                 Context::ERROR_FUNCTION_INDEX);
2626
    InstallMakeError(isolate, Builtins::kMakeError, Context::MAKE_ERROR_INDEX);
2627 2628 2629
  }

  {  // -- E v a l E r r o r
jgruber's avatar
jgruber committed
2630 2631
    InstallError(isolate, global, factory->EvalError_string(),
                 Context::EVAL_ERROR_FUNCTION_INDEX);
2632 2633 2634
  }

  {  // -- R a n g e E r r o r
jgruber's avatar
jgruber committed
2635 2636
    InstallError(isolate, global, factory->RangeError_string(),
                 Context::RANGE_ERROR_FUNCTION_INDEX);
2637
    InstallMakeError(isolate, Builtins::kMakeRangeError,
2638
                     Context::MAKE_RANGE_ERROR_INDEX);
2639 2640 2641
  }

  {  // -- R e f e r e n c e E r r o r
jgruber's avatar
jgruber committed
2642 2643
    InstallError(isolate, global, factory->ReferenceError_string(),
                 Context::REFERENCE_ERROR_FUNCTION_INDEX);
2644 2645 2646
  }

  {  // -- S y n t a x E r r o r
jgruber's avatar
jgruber committed
2647 2648
    InstallError(isolate, global, factory->SyntaxError_string(),
                 Context::SYNTAX_ERROR_FUNCTION_INDEX);
2649
    InstallMakeError(isolate, Builtins::kMakeSyntaxError,
2650
                     Context::MAKE_SYNTAX_ERROR_INDEX);
2651 2652 2653
  }

  {  // -- T y p e E r r o r
jgruber's avatar
jgruber committed
2654 2655
    InstallError(isolate, global, factory->TypeError_string(),
                 Context::TYPE_ERROR_FUNCTION_INDEX);
2656
    InstallMakeError(isolate, Builtins::kMakeTypeError,
2657
                     Context::MAKE_TYPE_ERROR_INDEX);
2658 2659 2660
  }

  {  // -- U R I E r r o r
jgruber's avatar
jgruber committed
2661 2662
    InstallError(isolate, global, factory->URIError_string(),
                 Context::URI_ERROR_FUNCTION_INDEX);
2663
    InstallMakeError(isolate, Builtins::kMakeURIError,
2664
                     Context::MAKE_URI_ERROR_INDEX);
2665 2666
  }

2667 2668 2669 2670 2671
  {  // -- C o m p i l e E r r o r
    Handle<JSObject> dummy = factory->NewJSObject(isolate->object_function());
    InstallError(isolate, dummy, factory->CompileError_string(),
                 Context::WASM_COMPILE_ERROR_FUNCTION_INDEX);

2672 2673 2674 2675
    // -- L i n k E r r o r
    InstallError(isolate, dummy, factory->LinkError_string(),
                 Context::WASM_LINK_ERROR_FUNCTION_INDEX);

2676 2677 2678 2679 2680
    // -- R u n t i m e E r r o r
    InstallError(isolate, dummy, factory->RuntimeError_string(),
                 Context::WASM_RUNTIME_ERROR_FUNCTION_INDEX);
  }

2681 2682 2683 2684
  // Initialize the embedder data slot.
  Handle<FixedArray> embedder_data = factory->NewFixedArray(3);
  native_context()->set_embedder_data(*embedder_data);

2685
  {  // -- J S O N
2686
    Handle<String> name = factory->InternalizeUtf8String("JSON");
2687 2688
    Handle<JSObject> json_object =
        factory->NewJSObject(isolate->object_function(), TENURED);
2689
    JSObject::AddProperty(global, name, json_object, DONT_ENUM);
2690
    SimpleInstallFunction(json_object, "parse", Builtins::kJsonParse, 2, false);
2691 2692
    SimpleInstallFunction(json_object, "stringify", Builtins::kJsonStringify, 3,
                          true);
2693 2694 2695 2696
    JSObject::AddProperty(
        json_object, factory->to_string_tag_symbol(),
        factory->NewStringFromAsciiChecked("JSON"),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
2697 2698 2699 2700
  }

  {  // -- M a t h
    Handle<String> name = factory->InternalizeUtf8String("Math");
2701 2702
    Handle<JSObject> math =
        factory->NewJSObject(isolate->object_function(), TENURED);
2703
    JSObject::AddProperty(global, name, math, DONT_ENUM);
2704
    SimpleInstallFunction(math, "abs", Builtins::kMathAbs, 1, true);
2705
    SimpleInstallFunction(math, "acos", Builtins::kMathAcos, 1, true);
2706
    SimpleInstallFunction(math, "acosh", Builtins::kMathAcosh, 1, true);
2707
    SimpleInstallFunction(math, "asin", Builtins::kMathAsin, 1, true);
2708
    SimpleInstallFunction(math, "asinh", Builtins::kMathAsinh, 1, true);
2709
    SimpleInstallFunction(math, "atan", Builtins::kMathAtan, 1, true);
2710
    SimpleInstallFunction(math, "atanh", Builtins::kMathAtanh, 1, true);
2711
    SimpleInstallFunction(math, "atan2", Builtins::kMathAtan2, 2, true);
2712
    SimpleInstallFunction(math, "ceil", Builtins::kMathCeil, 1, true);
2713 2714
    SimpleInstallFunction(math, "cbrt", Builtins::kMathCbrt, 1, true);
    SimpleInstallFunction(math, "expm1", Builtins::kMathExpm1, 1, true);
2715
    SimpleInstallFunction(math, "clz32", Builtins::kMathClz32, 1, true);
2716
    SimpleInstallFunction(math, "cos", Builtins::kMathCos, 1, true);
2717
    SimpleInstallFunction(math, "cosh", Builtins::kMathCosh, 1, true);
2718
    SimpleInstallFunction(math, "exp", Builtins::kMathExp, 1, true);
2719 2720 2721
    Handle<JSFunction> math_floor =
        SimpleInstallFunction(math, "floor", Builtins::kMathFloor, 1, true);
    native_context()->set_math_floor(*math_floor);
2722
    SimpleInstallFunction(math, "fround", Builtins::kMathFround, 1, true);
2723
    SimpleInstallFunction(math, "hypot", Builtins::kMathHypot, 2, false);
2724
    SimpleInstallFunction(math, "imul", Builtins::kMathImul, 2, true);
2725
    SimpleInstallFunction(math, "log", Builtins::kMathLog, 1, true);
2726
    SimpleInstallFunction(math, "log1p", Builtins::kMathLog1p, 1, true);
2727 2728
    SimpleInstallFunction(math, "log2", Builtins::kMathLog2, 1, true);
    SimpleInstallFunction(math, "log10", Builtins::kMathLog10, 1, true);
2729 2730
    SimpleInstallFunction(math, "max", Builtins::kMathMax, 2, false);
    SimpleInstallFunction(math, "min", Builtins::kMathMin, 2, false);
2731 2732 2733
    Handle<JSFunction> math_pow =
        SimpleInstallFunction(math, "pow", Builtins::kMathPow, 2, true);
    native_context()->set_math_pow(*math_pow);
2734
    SimpleInstallFunction(math, "random", Builtins::kMathRandom, 0, true);
2735
    SimpleInstallFunction(math, "round", Builtins::kMathRound, 1, true);
2736
    SimpleInstallFunction(math, "sign", Builtins::kMathSign, 1, true);
2737
    SimpleInstallFunction(math, "sin", Builtins::kMathSin, 1, true);
2738
    SimpleInstallFunction(math, "sinh", Builtins::kMathSinh, 1, true);
2739
    SimpleInstallFunction(math, "sqrt", Builtins::kMathSqrt, 1, true);
2740
    SimpleInstallFunction(math, "tan", Builtins::kMathTan, 1, true);
2741
    SimpleInstallFunction(math, "tanh", Builtins::kMathTanh, 1, true);
2742
    SimpleInstallFunction(math, "trunc", Builtins::kMathTrunc, 1, true);
2743 2744 2745

    // Install math constants.
    double const kE = base::ieee754::exp(1.0);
2746
    double const kPI = 3.1415926535897932;
2747 2748 2749 2750 2751 2752 2753 2754 2755 2756 2757 2758 2759
    InstallConstant(isolate, math, "E", factory->NewNumber(kE));
    InstallConstant(isolate, math, "LN10",
                    factory->NewNumber(base::ieee754::log(10.0)));
    InstallConstant(isolate, math, "LN2",
                    factory->NewNumber(base::ieee754::log(2.0)));
    InstallConstant(isolate, math, "LOG10E",
                    factory->NewNumber(base::ieee754::log10(kE)));
    InstallConstant(isolate, math, "LOG2E",
                    factory->NewNumber(base::ieee754::log2(kE)));
    InstallConstant(isolate, math, "PI", factory->NewNumber(kPI));
    InstallConstant(isolate, math, "SQRT1_2",
                    factory->NewNumber(std::sqrt(0.5)));
    InstallConstant(isolate, math, "SQRT2", factory->NewNumber(std::sqrt(2.0)));
2760 2761 2762 2763
    JSObject::AddProperty(
        math, factory->to_string_tag_symbol(),
        factory->NewStringFromAsciiChecked("Math"),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
2764 2765
  }

2766 2767
  {  // -- C o n s o l e
    Handle<String> name = factory->InternalizeUtf8String("console");
2768 2769 2770 2771
    NewFunctionArgs args = NewFunctionArgs::ForFunctionWithoutCode(
        name, isolate->strict_function_map(), LanguageMode::kStrict);
    Handle<JSFunction> cons = factory->NewFunction(args);

2772
    Handle<JSObject> empty = factory->NewJSObject(isolate->object_function());
2773
    JSFunction::SetPrototype(cons, empty);
2774

2775 2776 2777
    Handle<JSObject> console = factory->NewJSObject(cons, TENURED);
    DCHECK(console->IsJSObject());
    JSObject::AddProperty(global, name, console, DONT_ENUM);
2778 2779 2780 2781 2782 2783 2784 2785 2786 2787 2788 2789 2790 2791 2792 2793 2794 2795 2796 2797
    SimpleInstallFunction(console, "debug", Builtins::kConsoleDebug, 1, false,
                          NONE);
    SimpleInstallFunction(console, "error", Builtins::kConsoleError, 1, false,
                          NONE);
    SimpleInstallFunction(console, "info", Builtins::kConsoleInfo, 1, false,
                          NONE);
    SimpleInstallFunction(console, "log", Builtins::kConsoleLog, 1, false,
                          NONE);
    SimpleInstallFunction(console, "warn", Builtins::kConsoleWarn, 1, false,
                          NONE);
    SimpleInstallFunction(console, "dir", Builtins::kConsoleDir, 1, false,
                          NONE);
    SimpleInstallFunction(console, "dirxml", Builtins::kConsoleDirXml, 1, false,
                          NONE);
    SimpleInstallFunction(console, "table", Builtins::kConsoleTable, 1, false,
                          NONE);
    SimpleInstallFunction(console, "trace", Builtins::kConsoleTrace, 1, false,
                          NONE);
    SimpleInstallFunction(console, "group", Builtins::kConsoleGroup, 1, false,
                          NONE);
2798
    SimpleInstallFunction(console, "groupCollapsed",
2799
                          Builtins::kConsoleGroupCollapsed, 1, false, NONE);
2800
    SimpleInstallFunction(console, "groupEnd", Builtins::kConsoleGroupEnd, 1,
2801 2802 2803 2804 2805
                          false, NONE);
    SimpleInstallFunction(console, "clear", Builtins::kConsoleClear, 1, false,
                          NONE);
    SimpleInstallFunction(console, "count", Builtins::kConsoleCount, 1, false,
                          NONE);
2806
    SimpleInstallFunction(console, "assert", Builtins::kFastConsoleAssert, 1,
2807
                          false, NONE);
2808
    SimpleInstallFunction(console, "markTimeline",
2809
                          Builtins::kConsoleMarkTimeline, 1, false, NONE);
2810
    SimpleInstallFunction(console, "profile", Builtins::kConsoleProfile, 1,
2811
                          false, NONE);
2812
    SimpleInstallFunction(console, "profileEnd", Builtins::kConsoleProfileEnd,
2813
                          1, false, NONE);
2814
    SimpleInstallFunction(console, "timeline", Builtins::kConsoleTimeline, 1,
2815
                          false, NONE);
2816
    SimpleInstallFunction(console, "timelineEnd", Builtins::kConsoleTimelineEnd,
2817 2818 2819
                          1, false, NONE);
    SimpleInstallFunction(console, "time", Builtins::kConsoleTime, 1, false,
                          NONE);
2820
    SimpleInstallFunction(console, "timeEnd", Builtins::kConsoleTimeEnd, 1,
2821
                          false, NONE);
2822
    SimpleInstallFunction(console, "timeStamp", Builtins::kConsoleTimeStamp, 1,
2823
                          false, NONE);
2824 2825
    SimpleInstallFunction(console, "context", Builtins::kConsoleContext, 1,
                          true, NONE);
2826 2827 2828 2829 2830 2831
    JSObject::AddProperty(
        console, factory->to_string_tag_symbol(),
        factory->NewStringFromAsciiChecked("Object"),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
  }

2832
#ifdef V8_INTL_SUPPORT
2833 2834
  {  // -- I n t l
    Handle<String> name = factory->InternalizeUtf8String("Intl");
2835 2836
    Handle<JSObject> intl =
        factory->NewJSObject(isolate->object_function(), TENURED);
2837 2838
    JSObject::AddProperty(global, name, intl, DONT_ENUM);

2839 2840
    {
      Handle<JSFunction> date_time_format_constructor = InstallFunction(
2841
          intl, "DateTimeFormat", JS_OBJECT_TYPE, DateFormat::kSize, 0,
2842 2843 2844 2845 2846 2847 2848 2849 2850 2851 2852 2853 2854 2855 2856
          factory->the_hole_value(), Builtins::kIllegal);
      native_context()->set_intl_date_time_format_function(
          *date_time_format_constructor);

      Handle<JSObject> prototype(
          JSObject::cast(date_time_format_constructor->prototype()), isolate);

      // Install the @@toStringTag property on the {prototype}.
      JSObject::AddProperty(
          prototype, factory->to_string_tag_symbol(), factory->Object_string(),
          static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
    }

    {
      Handle<JSFunction> number_format_constructor = InstallFunction(
2857
          intl, "NumberFormat", JS_OBJECT_TYPE, NumberFormat::kSize, 0,
2858 2859 2860 2861 2862 2863 2864 2865 2866 2867 2868 2869 2870 2871 2872
          factory->the_hole_value(), Builtins::kIllegal);
      native_context()->set_intl_number_format_function(
          *number_format_constructor);

      Handle<JSObject> prototype(
          JSObject::cast(number_format_constructor->prototype()), isolate);

      // Install the @@toStringTag property on the {prototype}.
      JSObject::AddProperty(
          prototype, factory->to_string_tag_symbol(), factory->Object_string(),
          static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
    }

    {
      Handle<JSFunction> collator_constructor =
2873
          InstallFunction(intl, "Collator", JS_OBJECT_TYPE, Collator::kSize, 0,
2874 2875 2876 2877 2878 2879 2880 2881 2882 2883 2884 2885 2886 2887
                          factory->the_hole_value(), Builtins::kIllegal);
      native_context()->set_intl_collator_function(*collator_constructor);

      Handle<JSObject> prototype(
          JSObject::cast(collator_constructor->prototype()), isolate);

      // Install the @@toStringTag property on the {prototype}.
      JSObject::AddProperty(
          prototype, factory->to_string_tag_symbol(), factory->Object_string(),
          static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
    }

    {
      Handle<JSFunction> v8_break_iterator_constructor = InstallFunction(
2888
          intl, "v8BreakIterator", JS_OBJECT_TYPE, V8BreakIterator::kSize, 0,
2889 2890 2891 2892 2893 2894 2895 2896 2897 2898 2899 2900
          factory->the_hole_value(), Builtins::kIllegal);
      native_context()->set_intl_v8_break_iterator_function(
          *v8_break_iterator_constructor);

      Handle<JSObject> prototype(
          JSObject::cast(v8_break_iterator_constructor->prototype()), isolate);

      // Install the @@toStringTag property on the {prototype}.
      JSObject::AddProperty(
          prototype, factory->to_string_tag_symbol(), factory->Object_string(),
          static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
    }
2901
  }
2902
#endif  // V8_INTL_SUPPORT
2903

2904
  {  // -- A r r a y B u f f e r
2905 2906 2907 2908 2909 2910
    Handle<String> name = factory->InternalizeUtf8String("ArrayBuffer");
    Handle<JSFunction> array_buffer_fun =
        CreateArrayBuffer(name, Builtins::kArrayBufferPrototypeGetByteLength,
                          BuiltinFunctionId::kArrayBufferByteLength,
                          Builtins::kArrayBufferPrototypeSlice);
    JSObject::AddProperty(global, name, array_buffer_fun, DONT_ENUM);
2911 2912
    InstallWithIntrinsicDefaultProto(isolate, array_buffer_fun,
                                     Context::ARRAY_BUFFER_FUN_INDEX);
2913
    InstallSpeciesGetter(array_buffer_fun);
2914 2915 2916 2917 2918 2919 2920

    Handle<JSFunction> array_buffer_noinit_fun = SimpleCreateFunction(
        isolate,
        factory->NewStringFromAsciiChecked(
            "arrayBufferConstructor_DoNotInitialize"),
        Builtins::kArrayBufferConstructor_DoNotInitialize, 1, false);
    native_context()->set_array_buffer_noinit_fun(*array_buffer_noinit_fun);
2921 2922
  }

2923 2924 2925 2926 2927 2928 2929 2930 2931 2932 2933 2934
  {  // -- S h a r e d A r r a y B u f f e r
    Handle<String> name = factory->InternalizeUtf8String("SharedArrayBuffer");
    Handle<JSFunction> shared_array_buffer_fun = CreateArrayBuffer(
        name, Builtins::kSharedArrayBufferPrototypeGetByteLength,
        BuiltinFunctionId::kSharedArrayBufferByteLength,
        Builtins::kSharedArrayBufferPrototypeSlice);
    InstallWithIntrinsicDefaultProto(isolate, shared_array_buffer_fun,
                                     Context::SHARED_ARRAY_BUFFER_FUN_INDEX);
    InstallSpeciesGetter(shared_array_buffer_fun);
  }

  {  // -- A t o m i c s
2935 2936
    Handle<JSObject> atomics_object =
        factory->NewJSObject(isolate->object_function(), TENURED);
2937 2938 2939 2940 2941 2942 2943 2944 2945 2946 2947 2948 2949 2950 2951 2952 2953 2954 2955 2956 2957 2958 2959 2960 2961 2962 2963
    native_context()->set_atomics_object(*atomics_object);

    SimpleInstallFunction(atomics_object, "load", Builtins::kAtomicsLoad, 2,
                          true);
    SimpleInstallFunction(atomics_object, "store", Builtins::kAtomicsStore, 3,
                          true);
    SimpleInstallFunction(atomics_object, "add", Builtins::kAtomicsAdd, 3,
                          true);
    SimpleInstallFunction(atomics_object, "sub", Builtins::kAtomicsSub, 3,
                          true);
    SimpleInstallFunction(atomics_object, "and", Builtins::kAtomicsAnd, 3,
                          true);
    SimpleInstallFunction(atomics_object, "or", Builtins::kAtomicsOr, 3, true);
    SimpleInstallFunction(atomics_object, "xor", Builtins::kAtomicsXor, 3,
                          true);
    SimpleInstallFunction(atomics_object, "exchange",
                          Builtins::kAtomicsExchange, 3, true);
    SimpleInstallFunction(atomics_object, "compareExchange",
                          Builtins::kAtomicsCompareExchange, 4, true);
    SimpleInstallFunction(atomics_object, "isLockFree",
                          Builtins::kAtomicsIsLockFree, 1, true);
    SimpleInstallFunction(atomics_object, "wait", Builtins::kAtomicsWait, 4,
                          true);
    SimpleInstallFunction(atomics_object, "wake", Builtins::kAtomicsWake, 3,
                          true);
  }

2964 2965 2966
  {  // -- T y p e d A r r a y
    Handle<JSFunction> typed_array_fun =
        CreateFunction(isolate, factory->InternalizeUtf8String("TypedArray"),
2967
                       JS_TYPED_ARRAY_TYPE, JSTypedArray::kSize, 0,
2968
                       factory->the_hole_value(), Builtins::kIllegal);
2969
    typed_array_fun->shared()->set_native(false);
2970
    InstallSpeciesGetter(typed_array_fun);
2971 2972
    native_context()->set_typed_array_function(*typed_array_fun);

2973 2974 2975 2976 2977
    // Setup %TypedArrayPrototype%.
    Handle<JSObject> prototype(
        JSObject::cast(typed_array_fun->instance_prototype()));
    native_context()->set_typed_array_prototype(*prototype);

2978 2979
    // Install the "buffer", "byteOffset", "byteLength", "length"
    // and @@toStringTag getters on the {prototype}.
2980 2981 2982 2983 2984 2985 2986 2987 2988 2989 2990
    SimpleInstallGetter(prototype, factory->buffer_string(),
                        Builtins::kTypedArrayPrototypeBuffer, false);
    SimpleInstallGetter(prototype, factory->byte_length_string(),
                        Builtins::kTypedArrayPrototypeByteLength, true,
                        kTypedArrayByteLength);
    SimpleInstallGetter(prototype, factory->byte_offset_string(),
                        Builtins::kTypedArrayPrototypeByteOffset, true,
                        kTypedArrayByteOffset);
    SimpleInstallGetter(prototype, factory->length_string(),
                        Builtins::kTypedArrayPrototypeLength, true,
                        kTypedArrayLength);
2991 2992 2993
    SimpleInstallGetter(prototype, factory->to_string_tag_symbol(),
                        Builtins::kTypedArrayPrototypeToStringTag, true,
                        kTypedArrayToStringTag);
2994 2995

    // Install "keys", "values" and "entries" methods on the {prototype}.
2996 2997 2998 2999 3000 3001 3002 3003 3004 3005
    SimpleInstallFunction(prototype, "entries",
                          Builtins::kTypedArrayPrototypeEntries, 0, true,
                          kTypedArrayEntries);

    SimpleInstallFunction(prototype, "keys", Builtins::kTypedArrayPrototypeKeys,
                          0, true, kTypedArrayKeys);

    Handle<JSFunction> values = SimpleInstallFunction(
        prototype, "values", Builtins::kTypedArrayPrototypeValues, 0, true,
        kTypedArrayValues);
3006
    JSObject::AddProperty(prototype, factory->iterator_symbol(), values,
3007
                          DONT_ENUM);
3008 3009 3010 3011

    // TODO(caitp): alphasort accessors/methods
    SimpleInstallFunction(prototype, "copyWithin",
                          Builtins::kTypedArrayPrototypeCopyWithin, 2, false);
3012 3013
    SimpleInstallFunction(prototype, "every",
                          Builtins::kTypedArrayPrototypeEvery, 1, false);
3014 3015
    SimpleInstallFunction(prototype, "fill",
                          Builtins::kTypedArrayPrototypeFill, 1, false);
3016 3017
    SimpleInstallFunction(prototype, "forEach",
                          Builtins::kTypedArrayPrototypeForEach, 1, false);
3018 3019
    SimpleInstallFunction(prototype, "includes",
                          Builtins::kTypedArrayPrototypeIncludes, 1, false);
3020 3021
    SimpleInstallFunction(prototype, "indexOf",
                          Builtins::kTypedArrayPrototypeIndexOf, 1, false);
3022 3023
    SimpleInstallFunction(prototype, "lastIndexOf",
                          Builtins::kTypedArrayPrototypeLastIndexOf, 1, false);
3024 3025
    SimpleInstallFunction(prototype, "map", Builtins::kTypedArrayPrototypeMap,
                          1, false);
3026 3027
    SimpleInstallFunction(prototype, "reverse",
                          Builtins::kTypedArrayPrototypeReverse, 0, false);
3028 3029 3030 3031
    SimpleInstallFunction(prototype, "reduce",
                          Builtins::kTypedArrayPrototypeReduce, 1, false);
    SimpleInstallFunction(prototype, "reduceRight",
                          Builtins::kTypedArrayPrototypeReduceRight, 1, false);
3032 3033
    SimpleInstallFunction(prototype, "set", Builtins::kTypedArrayPrototypeSet,
                          1, false);
3034 3035
    SimpleInstallFunction(prototype, "slice",
                          Builtins::kTypedArrayPrototypeSlice, 2, false);
3036 3037
    SimpleInstallFunction(prototype, "some", Builtins::kTypedArrayPrototypeSome,
                          1, false);
3038 3039
  }

3040
  {  // -- T y p e d A r r a y s
3041 3042 3043 3044 3045 3046
#define INSTALL_TYPED_ARRAY(Type, type, TYPE, ctype, size)             \
  {                                                                    \
    Handle<JSFunction> fun;                                            \
    InstallTypedArray(#Type "Array", TYPE##_ELEMENTS, &fun);           \
    InstallWithIntrinsicDefaultProto(isolate, fun,                     \
                                     Context::TYPE##_ARRAY_FUN_INDEX); \
3047
  }
3048 3049
    TYPED_ARRAYS(INSTALL_TYPED_ARRAY)
#undef INSTALL_TYPED_ARRAY
3050

3051 3052 3053 3054 3055
    // %typed_array_construct_by_length
    Handle<JSFunction> construct_by_length = SimpleCreateFunction(
        isolate,
        factory->NewStringFromAsciiChecked("typedArrayConstructByLength"),
        Builtins::kTypedArrayConstructByLength, 3, false);
3056
    native_context()->set_typed_array_construct_by_length(*construct_by_length);
3057 3058 3059 3060 3061 3062

    // %typed_array_construct_by_array_buffer
    Handle<JSFunction> construct_by_buffer = SimpleCreateFunction(
        isolate,
        factory->NewStringFromAsciiChecked("typedArrayConstructByArrayBuffer"),
        Builtins::kTypedArrayConstructByArrayBuffer, 5, false);
3063 3064 3065 3066 3067 3068 3069 3070 3071 3072
    native_context()->set_typed_array_construct_by_array_buffer(
        *construct_by_buffer);

    // %typed_array_construct_by_array_like
    Handle<JSFunction> construct_by_array_like = SimpleCreateFunction(
        isolate,
        factory->NewStringFromAsciiChecked("typedArrayConstructByArrayLike"),
        Builtins::kTypedArrayConstructByArrayLike, 4, false);
    native_context()->set_typed_array_construct_by_array_like(
        *construct_by_array_like);
3073
  }
3074

3075
  {  // -- D a t a V i e w
3076 3077
    Handle<JSFunction> data_view_fun = InstallFunction(
        global, "DataView", JS_DATA_VIEW_TYPE,
3078
        JSDataView::kSizeWithEmbedderFields, 0, factory->the_hole_value(),
3079
        Builtins::kDataViewConstructor);
3080 3081
    InstallWithIntrinsicDefaultProto(isolate, data_view_fun,
                                     Context::DATA_VIEW_FUN_INDEX);
3082
    data_view_fun->shared()->SetConstructStub(
3083
        *BUILTIN_CODE(isolate, DataViewConstructor_ConstructStub));
3084 3085
    data_view_fun->shared()->set_length(3);
    data_view_fun->shared()->DontAdaptArguments();
3086

3087 3088 3089 3090
    // Setup %DataViewPrototype%.
    Handle<JSObject> prototype(
        JSObject::cast(data_view_fun->instance_prototype()));

3091 3092 3093 3094 3095 3096 3097 3098 3099 3100 3101 3102 3103 3104 3105 3106 3107
    // Install the @@toStringTag property on the {prototype}.
    JSObject::AddProperty(
        prototype, factory->to_string_tag_symbol(),
        factory->NewStringFromAsciiChecked("DataView"),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

    // Install the "buffer", "byteOffset" and "byteLength" getters
    // on the {prototype}.
    SimpleInstallGetter(prototype, factory->buffer_string(),
                        Builtins::kDataViewPrototypeGetBuffer, false,
                        kDataViewBuffer);
    SimpleInstallGetter(prototype, factory->byte_length_string(),
                        Builtins::kDataViewPrototypeGetByteLength, false,
                        kDataViewByteLength);
    SimpleInstallGetter(prototype, factory->byte_offset_string(),
                        Builtins::kDataViewPrototypeGetByteOffset, false,
                        kDataViewByteOffset);
3108 3109 3110 3111 3112 3113 3114 3115 3116 3117 3118 3119 3120 3121 3122 3123 3124 3125 3126 3127 3128 3129 3130 3131 3132 3133 3134 3135 3136 3137 3138 3139 3140

    SimpleInstallFunction(prototype, "getInt8",
                          Builtins::kDataViewPrototypeGetInt8, 1, false);
    SimpleInstallFunction(prototype, "setInt8",
                          Builtins::kDataViewPrototypeSetInt8, 2, false);
    SimpleInstallFunction(prototype, "getUint8",
                          Builtins::kDataViewPrototypeGetUint8, 1, false);
    SimpleInstallFunction(prototype, "setUint8",
                          Builtins::kDataViewPrototypeSetUint8, 2, false);
    SimpleInstallFunction(prototype, "getInt16",
                          Builtins::kDataViewPrototypeGetInt16, 1, false);
    SimpleInstallFunction(prototype, "setInt16",
                          Builtins::kDataViewPrototypeSetInt16, 2, false);
    SimpleInstallFunction(prototype, "getUint16",
                          Builtins::kDataViewPrototypeGetUint16, 1, false);
    SimpleInstallFunction(prototype, "setUint16",
                          Builtins::kDataViewPrototypeSetUint16, 2, false);
    SimpleInstallFunction(prototype, "getInt32",
                          Builtins::kDataViewPrototypeGetInt32, 1, false);
    SimpleInstallFunction(prototype, "setInt32",
                          Builtins::kDataViewPrototypeSetInt32, 2, false);
    SimpleInstallFunction(prototype, "getUint32",
                          Builtins::kDataViewPrototypeGetUint32, 1, false);
    SimpleInstallFunction(prototype, "setUint32",
                          Builtins::kDataViewPrototypeSetUint32, 2, false);
    SimpleInstallFunction(prototype, "getFloat32",
                          Builtins::kDataViewPrototypeGetFloat32, 1, false);
    SimpleInstallFunction(prototype, "setFloat32",
                          Builtins::kDataViewPrototypeSetFloat32, 2, false);
    SimpleInstallFunction(prototype, "getFloat64",
                          Builtins::kDataViewPrototypeGetFloat64, 1, false);
    SimpleInstallFunction(prototype, "setFloat64",
                          Builtins::kDataViewPrototypeSetFloat64, 2, false);
3141 3142
  }

3143
  {  // -- M a p
3144 3145 3146 3147 3148 3149 3150 3151 3152 3153 3154 3155
    {
      Handle<String> index_string = isolate->factory()->zero_string();
      uint32_t field =
          StringHasher::MakeArrayIndexHash(0, index_string->length());
      index_string->set_hash_field(field);

      index_string = isolate->factory()->one_string();
      field = StringHasher::MakeArrayIndexHash(1, index_string->length());
      index_string->set_hash_field(field);
    }

    Handle<JSFunction> js_map_fun =
3156
        InstallFunction(global, "Map", JS_MAP_TYPE, JSMap::kSize, 0,
3157
                        factory->the_hole_value(), Builtins::kMapConstructor);
3158 3159
    InstallWithIntrinsicDefaultProto(isolate, js_map_fun,
                                     Context::JS_MAP_FUN_INDEX);
3160 3161

    Handle<SharedFunctionInfo> shared(js_map_fun->shared(), isolate);
3162
    shared->SetConstructStub(*BUILTIN_CODE(isolate, JSBuiltinsConstructStub));
3163
    shared->set_instance_class_name(isolate->heap()->Map_string());
3164
    shared->DontAdaptArguments();
3165 3166
    shared->set_length(0);

3167 3168 3169
    // Setup %MapPrototype%.
    Handle<JSObject> prototype(
        JSObject::cast(js_map_fun->instance_prototype()));
3170 3171 3172 3173 3174 3175

    // Install the @@toStringTag property on the {prototype}.
    JSObject::AddProperty(
        prototype, factory->to_string_tag_symbol(), factory->Map_string(),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

3176 3177
    Handle<JSFunction> map_get = SimpleInstallFunction(
        prototype, "get", Builtins::kMapPrototypeGet, 1, true);
3178
    native_context()->set_map_get(*map_get);
3179

3180 3181
    Handle<JSFunction> map_set = SimpleInstallFunction(
        prototype, "set", Builtins::kMapPrototypeSet, 2, true);
3182 3183
    native_context()->set_map_set(*map_set);

3184 3185
    Handle<JSFunction> map_has = SimpleInstallFunction(
        prototype, "has", Builtins::kMapPrototypeHas, 1, true);
3186
    native_context()->set_map_has(*map_has);
3187

3188
    Handle<JSFunction> map_delete = SimpleInstallFunction(
3189
        prototype, "delete", Builtins::kMapPrototypeDelete, 1, true);
3190 3191
    native_context()->set_map_delete(*map_delete);

3192 3193
    SimpleInstallFunction(prototype, "clear", Builtins::kMapPrototypeClear, 0,
                          true);
3194 3195 3196 3197
    Handle<JSFunction> entries = SimpleInstallFunction(
        prototype, "entries", Builtins::kMapPrototypeEntries, 0, true);
    JSObject::AddProperty(prototype, factory->iterator_symbol(), entries,
                          DONT_ENUM);
3198 3199
    SimpleInstallFunction(prototype, "forEach", Builtins::kMapPrototypeForEach,
                          1, false);
3200 3201
    SimpleInstallFunction(prototype, "keys", Builtins::kMapPrototypeKeys, 0,
                          true);
3202
    SimpleInstallGetter(prototype, factory->InternalizeUtf8String("size"),
3203 3204
                        Builtins::kMapPrototypeGetSize, true,
                        BuiltinFunctionId::kMapSize);
3205 3206
    SimpleInstallFunction(prototype, "values", Builtins::kMapPrototypeValues, 0,
                          true);
3207
    InstallSpeciesGetter(js_map_fun);
3208
  }
3209

3210
  {  // -- S e t
3211
    Handle<JSFunction> js_set_fun =
3212
        InstallFunction(global, "Set", JS_SET_TYPE, JSSet::kSize, 0,
3213
                        factory->the_hole_value(), Builtins::kSetConstructor);
3214 3215
    InstallWithIntrinsicDefaultProto(isolate, js_set_fun,
                                     Context::JS_SET_FUN_INDEX);
3216

3217
    Handle<SharedFunctionInfo> shared(js_set_fun->shared(), isolate);
3218
    shared->SetConstructStub(*BUILTIN_CODE(isolate, JSBuiltinsConstructStub));
3219
    shared->set_instance_class_name(isolate->heap()->Set_string());
3220
    shared->DontAdaptArguments();
3221 3222
    shared->set_length(0);

3223 3224 3225
    // Setup %SetPrototype%.
    Handle<JSObject> prototype(
        JSObject::cast(js_set_fun->instance_prototype()));
3226 3227 3228 3229 3230 3231

    // Install the @@toStringTag property on the {prototype}.
    JSObject::AddProperty(
        prototype, factory->to_string_tag_symbol(), factory->Set_string(),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

3232 3233
    Handle<JSFunction> set_has = SimpleInstallFunction(
        prototype, "has", Builtins::kSetPrototypeHas, 1, true);
3234
    native_context()->set_set_has(*set_has);
3235

3236 3237
    Handle<JSFunction> set_add = SimpleInstallFunction(
        prototype, "add", Builtins::kSetPrototypeAdd, 1, true);
3238 3239 3240
    native_context()->set_set_add(*set_add);

    Handle<JSFunction> set_delete = SimpleInstallFunction(
3241
        prototype, "delete", Builtins::kSetPrototypeDelete, 1, true);
3242 3243
    native_context()->set_set_delete(*set_delete);

3244 3245
    SimpleInstallFunction(prototype, "clear", Builtins::kSetPrototypeClear, 0,
                          true);
3246 3247
    SimpleInstallFunction(prototype, "entries", Builtins::kSetPrototypeEntries,
                          0, true);
3248 3249
    SimpleInstallFunction(prototype, "forEach", Builtins::kSetPrototypeForEach,
                          1, false);
3250
    SimpleInstallGetter(prototype, factory->InternalizeUtf8String("size"),
3251 3252
                        Builtins::kSetPrototypeGetSize, true,
                        BuiltinFunctionId::kSetSize);
3253 3254 3255 3256 3257
    Handle<JSFunction> values = SimpleInstallFunction(
        prototype, "values", Builtins::kSetPrototypeValues, 0, true);
    JSObject::AddProperty(prototype, factory->keys_string(), values, DONT_ENUM);
    JSObject::AddProperty(prototype, factory->iterator_symbol(), values,
                          DONT_ENUM);
3258
    InstallSpeciesGetter(js_set_fun);
3259
  }
3260

3261
  {  // -- J S M o d u l e N a m e s p a c e
3262 3263 3264
    Handle<Map> map = factory->NewMap(
        JS_MODULE_NAMESPACE_TYPE, JSModuleNamespace::kSize,
        TERMINAL_FAST_ELEMENTS_KIND, JSModuleNamespace::kInObjectFieldCount);
3265
    Map::SetPrototype(map, isolate->factory()->null_value());
3266
    Map::EnsureDescriptorSlack(map, 1);
3267 3268
    native_context()->set_js_module_namespace_map(*map);

3269 3270
    {  // Install @@toStringTag.
      PropertyAttributes attribs =
3271
          static_cast<PropertyAttributes>(DONT_DELETE | DONT_ENUM | READ_ONLY);
3272 3273 3274 3275
      Descriptor d =
          Descriptor::DataField(factory->to_string_tag_symbol(),
                                JSModuleNamespace::kToStringTagFieldIndex,
                                attribs, Representation::Tagged());
3276 3277
      map->AppendDescriptor(&d);
    }
3278 3279
  }

3280
  {  // -- I t e r a t o r R e s u l t
3281 3282
    Handle<Map> map = factory->NewMap(JS_OBJECT_TYPE, JSIteratorResult::kSize,
                                      TERMINAL_FAST_ELEMENTS_KIND, 2);
3283 3284 3285 3286
    Map::SetPrototype(map, isolate->initial_object_prototype());
    Map::EnsureDescriptorSlack(map, 2);

    {  // value
3287 3288 3289
      Descriptor d = Descriptor::DataField(factory->value_string(),
                                           JSIteratorResult::kValueIndex, NONE,
                                           Representation::Tagged());
3290 3291 3292 3293
      map->AppendDescriptor(&d);
    }

    {  // done
3294 3295 3296
      Descriptor d = Descriptor::DataField(factory->done_string(),
                                           JSIteratorResult::kDoneIndex, NONE,
                                           Representation::Tagged());
3297 3298 3299
      map->AppendDescriptor(&d);
    }

3300
    map->SetConstructor(native_context()->object_function());
3301
    native_context()->set_iterator_result_map(*map);
3302 3303
  }

3304
  {  // -- W e a k M a p
3305 3306 3307
    Handle<JSFunction> cons = InstallFunction(
        global, "WeakMap", JS_WEAK_MAP_TYPE, JSWeakMap::kSize, 0,
        factory->the_hole_value(), Builtins::kWeakMapConstructor);
3308
    InstallWithIntrinsicDefaultProto(isolate, cons,
3309
                                     Context::JS_WEAK_MAP_FUN_INDEX);
3310 3311 3312 3313 3314 3315 3316

    Handle<SharedFunctionInfo> shared(cons->shared(), isolate);
    shared->SetConstructStub(*BUILTIN_CODE(isolate, JSBuiltinsConstructStub));
    shared->set_instance_class_name(isolate->heap()->WeakMap_string());
    shared->DontAdaptArguments();
    shared->set_length(0);

3317
    // Setup %WeakMapPrototype%.
3318
    Handle<JSObject> prototype(JSObject::cast(cons->instance_prototype()));
3319

3320 3321
    SimpleInstallFunction(prototype, "delete",
                          Builtins::kWeakMapPrototypeDelete, 1, true);
3322 3323
    SimpleInstallFunction(prototype, "get", Builtins::kWeakMapGet, 1, true);
    SimpleInstallFunction(prototype, "has", Builtins::kWeakMapHas, 1, true);
3324 3325
    SimpleInstallFunction(prototype, "set", Builtins::kWeakMapPrototypeSet, 2,
                          true);
3326

3327 3328 3329 3330
    JSObject::AddProperty(
        prototype, factory->to_string_tag_symbol(),
        factory->NewStringFromAsciiChecked("WeakMap"),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
3331 3332 3333
  }

  {  // -- W e a k S e t
3334 3335 3336
    Handle<JSFunction> cons = InstallFunction(
        global, "WeakSet", JS_WEAK_SET_TYPE, JSWeakSet::kSize, 0,
        factory->the_hole_value(), Builtins::kWeakSetConstructor);
3337
    InstallWithIntrinsicDefaultProto(isolate, cons,
3338
                                     Context::JS_WEAK_SET_FUN_INDEX);
3339 3340 3341 3342 3343 3344 3345

    Handle<SharedFunctionInfo> shared(cons->shared(), isolate);
    shared->SetConstructStub(*BUILTIN_CODE(isolate, JSBuiltinsConstructStub));
    shared->set_instance_class_name(isolate->heap()->WeakSet_string());
    shared->DontAdaptArguments();
    shared->set_length(0);

3346
    // Setup %WeakSetPrototype%.
3347
    Handle<JSObject> prototype(JSObject::cast(cons->instance_prototype()));
3348

3349 3350
    SimpleInstallFunction(prototype, "delete",
                          Builtins::kWeakSetPrototypeDelete, 1, true);
3351
    SimpleInstallFunction(prototype, "has", Builtins::kWeakSetHas, 1, true);
3352 3353
    SimpleInstallFunction(prototype, "add", Builtins::kWeakSetPrototypeAdd, 1,
                          true);
3354

3355 3356 3357 3358
    JSObject::AddProperty(
        prototype, factory->to_string_tag_symbol(),
        factory->NewStringFromAsciiChecked("WeakSet"),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
3359
  }
3360

3361 3362 3363
  {  // -- P r o x y
    CreateJSProxyMaps();

3364 3365
    // Proxy function map has prototype slot for storing initial map but does
    // not have a prototype property.
3366
    Handle<Map> proxy_function_map =
3367
        Map::Copy(isolate->strict_function_without_prototype_map(), "Proxy");
3368 3369 3370
    // Re-set the unused property fields after changing the instance size.
    // TODO(ulan): Do not change instance size after map creation.
    int unused_property_fields = proxy_function_map->UnusedPropertyFields();
3371 3372
    proxy_function_map->set_instance_size(JSFunction::kSizeWithPrototype);
    proxy_function_map->set_has_prototype_slot(true);
3373
    proxy_function_map->set_is_constructor(true);
3374
    proxy_function_map->SetInObjectUnusedPropertyFields(unused_property_fields);
3375

3376
    Handle<String> name = factory->Proxy_string();
3377
    Handle<Code> code(BUILTIN_CODE(isolate, ProxyConstructor));
3378 3379 3380 3381

    NewFunctionArgs args = NewFunctionArgs::ForBuiltin(
        name, code, proxy_function_map, Builtins::kProxyConstructor);
    Handle<JSFunction> proxy_function = factory->NewFunction(args);
3382

3383 3384
    JSFunction::SetInitialMap(proxy_function, isolate->proxy_map(),
                              factory->null_value());
3385

3386
    proxy_function->shared()->SetConstructStub(
3387
        *BUILTIN_CODE(isolate, ProxyConstructor_ConstructStub));
3388 3389 3390 3391 3392 3393 3394 3395 3396 3397 3398 3399 3400 3401 3402 3403 3404 3405 3406 3407 3408 3409 3410 3411 3412 3413 3414 3415 3416 3417 3418 3419 3420 3421 3422 3423 3424 3425 3426 3427 3428 3429 3430 3431 3432 3433 3434 3435 3436 3437 3438 3439
    proxy_function->shared()->set_internal_formal_parameter_count(2);
    proxy_function->shared()->set_length(2);

    native_context()->set_proxy_function(*proxy_function);
    InstallFunction(global, name, proxy_function, factory->Object_string());
  }

  {  // -- R e f l e c t
    Handle<String> reflect_string = factory->InternalizeUtf8String("Reflect");
    Handle<JSObject> reflect =
        factory->NewJSObject(isolate->object_function(), TENURED);
    JSObject::AddProperty(global, reflect_string, reflect, DONT_ENUM);

    Handle<JSFunction> define_property =
        SimpleInstallFunction(reflect, factory->defineProperty_string(),
                              Builtins::kReflectDefineProperty, 3, true);
    native_context()->set_reflect_define_property(*define_property);

    Handle<JSFunction> delete_property =
        SimpleInstallFunction(reflect, factory->deleteProperty_string(),
                              Builtins::kReflectDeleteProperty, 2, true);
    native_context()->set_reflect_delete_property(*delete_property);

    Handle<JSFunction> apply = SimpleInstallFunction(
        reflect, factory->apply_string(), Builtins::kReflectApply, 3, false);
    native_context()->set_reflect_apply(*apply);

    Handle<JSFunction> construct =
        SimpleInstallFunction(reflect, factory->construct_string(),
                              Builtins::kReflectConstruct, 2, false);
    native_context()->set_reflect_construct(*construct);

    SimpleInstallFunction(reflect, factory->get_string(), Builtins::kReflectGet,
                          2, false);
    SimpleInstallFunction(reflect, factory->getOwnPropertyDescriptor_string(),
                          Builtins::kReflectGetOwnPropertyDescriptor, 2, true);
    SimpleInstallFunction(reflect, factory->getPrototypeOf_string(),
                          Builtins::kReflectGetPrototypeOf, 1, true);
    SimpleInstallFunction(reflect, factory->has_string(), Builtins::kReflectHas,
                          2, true);
    SimpleInstallFunction(reflect, factory->isExtensible_string(),
                          Builtins::kReflectIsExtensible, 1, true);
    SimpleInstallFunction(reflect, factory->ownKeys_string(),
                          Builtins::kReflectOwnKeys, 1, true);
    SimpleInstallFunction(reflect, factory->preventExtensions_string(),
                          Builtins::kReflectPreventExtensions, 1, true);
    SimpleInstallFunction(reflect, factory->set_string(), Builtins::kReflectSet,
                          3, false);
    SimpleInstallFunction(reflect, factory->setPrototypeOf_string(),
                          Builtins::kReflectSetPrototypeOf, 2, true);
  }

3440 3441
  {  // --- B o u n d F u n c t i o n
    Handle<Map> map =
3442 3443
        factory->NewMap(JS_BOUND_FUNCTION_TYPE, JSBoundFunction::kSize,
                        TERMINAL_FAST_ELEMENTS_KIND, 0);
3444
    map->SetConstructor(native_context()->object_function());
3445 3446 3447 3448 3449 3450 3451 3452
    map->set_is_callable();
    Map::SetPrototype(map, empty_function);

    PropertyAttributes roc_attribs =
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY);
    Map::EnsureDescriptorSlack(map, 2);

    {  // length
3453 3454 3455
      Descriptor d = Descriptor::AccessorConstant(
          factory->length_string(), factory->bound_function_length_accessor(),
          roc_attribs);
3456 3457
      map->AppendDescriptor(&d);
    }
3458

3459
    {  // name
3460 3461 3462
      Descriptor d = Descriptor::AccessorConstant(
          factory->name_string(), factory->bound_function_name_accessor(),
          roc_attribs);
3463 3464 3465 3466 3467
      map->AppendDescriptor(&d);
    }
    native_context()->set_bound_function_without_constructor_map(*map);

    map = Map::Copy(map, "IsConstructor");
3468
    map->set_is_constructor(true);
3469 3470 3471
    native_context()->set_bound_function_with_constructor_map(*map);
  }

3472
  {  // --- sloppy arguments map
3473 3474 3475
    // Make sure we can recognize argument objects at runtime.
    // This is done by introducing an anonymous function with
    // class_name equals 'Arguments'.
3476
    Handle<String> arguments_string = factory->Arguments_string();
3477
    NewFunctionArgs args = NewFunctionArgs::ForBuiltinWithPrototype(
3478
        arguments_string, BUILTIN_CODE(isolate, Illegal),
3479 3480 3481
        isolate->initial_object_prototype(), JS_ARGUMENTS_TYPE,
        JSSloppyArgumentsObject::kSize, 2, Builtins::kIllegal, MUTABLE);
    Handle<JSFunction> function = factory->NewFunction(args);
3482
    function->shared()->set_instance_class_name(*arguments_string);
3483
    Handle<Map> map(function->initial_map());
3484

3485 3486 3487 3488
    // Create the descriptor array for the arguments object.
    Map::EnsureDescriptorSlack(map, 2);

    {  // length
3489 3490
      Descriptor d = Descriptor::DataField(
          factory->length_string(), JSSloppyArgumentsObject::kLengthIndex,
3491
          DONT_ENUM, Representation::Tagged());
3492 3493 3494
      map->AppendDescriptor(&d);
    }
    {  // callee
3495 3496
      Descriptor d = Descriptor::DataField(
          factory->callee_string(), JSSloppyArgumentsObject::kCalleeIndex,
3497
          DONT_ENUM, Representation::Tagged());
3498 3499
      map->AppendDescriptor(&d);
    }
3500
    // @@iterator method is added later.
3501 3502 3503

    native_context()->set_sloppy_arguments_map(*map);

3504
    DCHECK(!map->is_dictionary_map());
3505
    DCHECK(IsObjectElementsKind(map->elements_kind()));
3506 3507
  }

3508 3509 3510 3511
  {  // --- fast and slow aliased arguments map
    Handle<Map> map = isolate->sloppy_arguments_map();
    map = Map::Copy(map, "FastAliasedArguments");
    map->set_elements_kind(FAST_SLOPPY_ARGUMENTS_ELEMENTS);
3512
    DCHECK_EQ(2, map->GetInObjectProperties());
3513 3514 3515 3516
    native_context()->set_fast_aliased_arguments_map(*map);

    map = Map::Copy(map, "SlowAliasedArguments");
    map->set_elements_kind(SLOW_SLOPPY_ARGUMENTS_ELEMENTS);
3517
    DCHECK_EQ(2, map->GetInObjectProperties());
3518
    native_context()->set_slow_aliased_arguments_map(*map);
3519 3520 3521
  }

  {  // --- strict mode arguments map
3522 3523 3524
    const PropertyAttributes attributes =
      static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY);

3525
    // Create the ThrowTypeError function.
3526
    Handle<AccessorPair> callee = factory->NewAccessorPair();
3527

3528
    Handle<JSFunction> poison = GetThrowTypeErrorIntrinsic();
3529

3530
    // Install the ThrowTypeError function.
3531 3532
    callee->set_getter(*poison);
    callee->set_setter(*poison);
3533

3534
    // Create the map. Allocate one in-object field for length.
3535
    Handle<Map> map = factory->NewMap(
3536
        JS_ARGUMENTS_TYPE, JSStrictArgumentsObject::kSize, PACKED_ELEMENTS, 1);
3537
    // Create the descriptor array for the arguments object.
3538
    Map::EnsureDescriptorSlack(map, 2);
3539

3540
    {  // length
3541 3542
      Descriptor d = Descriptor::DataField(
          factory->length_string(), JSStrictArgumentsObject::kLengthIndex,
3543
          DONT_ENUM, Representation::Tagged());
3544
      map->AppendDescriptor(&d);
3545 3546
    }
    {  // callee
3547 3548
      Descriptor d = Descriptor::AccessorConstant(factory->callee_string(),
                                                  callee, attributes);
3549
      map->AppendDescriptor(&d);
3550
    }
3551
    // @@iterator method is added later.
3552

3553 3554
    DCHECK_EQ(native_context()->object_function()->prototype(),
              *isolate->initial_object_prototype());
3555
    Map::SetPrototype(map, isolate->initial_object_prototype());
3556

3557
    // Copy constructor from the sloppy arguments boilerplate.
3558 3559
    map->SetConstructor(
        native_context()->sloppy_arguments_map()->GetConstructor());
3560

3561
    native_context()->set_strict_arguments_map(*map);
3562

3563
    DCHECK(!map->is_dictionary_map());
3564
    DCHECK(IsObjectElementsKind(map->elements_kind()));
3565 3566 3567 3568
  }

  {  // --- context extension
    // Create a function for the context extension objects.
3569 3570 3571 3572
    Handle<JSFunction> context_extension_fun =
        CreateFunction(isolate, factory->empty_string(),
                       JS_CONTEXT_EXTENSION_OBJECT_TYPE, JSObject::kHeaderSize,
                       0, factory->the_hole_value(), Builtins::kIllegal);
3573
    Handle<String> name = factory->InternalizeUtf8String("context_extension");
3574
    context_extension_fun->shared()->set_instance_class_name(*name);
3575
    native_context()->set_context_extension_function(*context_extension_fun);
3576 3577
  }

3578
  {
3579
    // Set up the call-as-function delegate.
3580 3581 3582
    Handle<JSFunction> delegate =
        SimpleCreateFunction(isolate, factory->empty_string(),
                             Builtins::kHandleApiCallAsFunction, 0, false);
3583
    native_context()->set_call_as_function_delegate(*delegate);
3584 3585 3586
  }

  {
3587
    // Set up the call-as-constructor delegate.
3588 3589 3590
    Handle<JSFunction> delegate =
        SimpleCreateFunction(isolate, factory->empty_string(),
                             Builtins::kHandleApiCallAsConstructor, 0, false);
3591
    native_context()->set_call_as_constructor_delegate(*delegate);
3592
  }
3593
}  // NOLINT(readability/fn_size)
3594

3595 3596
void Genesis::InstallTypedArray(const char* name, ElementsKind elements_kind,
                                Handle<JSFunction>* fun) {
3597
  Handle<JSObject> global = Handle<JSObject>(native_context()->global_object());
3598 3599 3600 3601 3602 3603 3604 3605

  Handle<JSObject> typed_array_prototype =
      Handle<JSObject>(isolate()->typed_array_prototype());
  Handle<JSFunction> typed_array_function =
      Handle<JSFunction>(isolate()->typed_array_function());

  Handle<JSObject> prototype =
      factory()->NewJSObject(isolate()->object_function(), TENURED);
3606
  Handle<JSFunction> result = InstallFunction(
3607
      global, name, JS_TYPED_ARRAY_TYPE, JSTypedArray::kSizeWithEmbedderFields,
3608
      0, prototype, Builtins::kIllegal);
3609
  result->initial_map()->set_elements_kind(elements_kind);
3610

3611
  CHECK(JSObject::SetPrototype(result, typed_array_function, false, kDontThrow)
3612 3613 3614
            .FromJust());

  CHECK(JSObject::SetPrototype(prototype, typed_array_prototype, false,
3615
                               kDontThrow)
3616
            .FromJust());
3617
  *fun = result;
3618 3619 3620
}


3621
void Genesis::InitializeExperimentalGlobal() {
3622
#define FEATURE_INITIALIZE_GLOBAL(id, descr) InitializeGlobal_##id();
3623

3624 3625
  HARMONY_INPROGRESS(FEATURE_INITIALIZE_GLOBAL)
  HARMONY_STAGED(FEATURE_INITIALIZE_GLOBAL)
3626
  HARMONY_SHIPPING(FEATURE_INITIALIZE_GLOBAL)
3627
#undef FEATURE_INITIALIZE_GLOBAL
3628 3629
}

3630
bool Bootstrapper::CompileBuiltin(Isolate* isolate, int index) {
3631
  Vector<const char> name = Natives::GetScriptName(index);
3632
  Handle<String> source_code =
3633
      isolate->bootstrapper()->GetNativeSource(CORE, index);
3634 3635 3636

  // We pass in extras_utils so that builtin code can set it up for later use
  // by actual extras code, compiled with CompileExtraBuiltin.
3637
  Handle<Object> global = isolate->global_object();
3638
  Handle<Object> utils = isolate->natives_utils_object();
3639 3640
  Handle<Object> extras_utils = isolate->extras_utils_object();
  Handle<Object> args[] = {global, utils, extras_utils};
3641

yangguo's avatar
yangguo committed
3642
  return Bootstrapper::CompileNative(isolate, name, source_code,
3643
                                     arraysize(args), args, NATIVES_CODE);
3644 3645 3646
}


3647
bool Bootstrapper::CompileExtraBuiltin(Isolate* isolate, int index) {
3648
  HandleScope scope(isolate);
3649 3650
  Vector<const char> name = ExtraNatives::GetScriptName(index);
  Handle<String> source_code =
3651
      isolate->bootstrapper()->GetNativeSource(EXTRAS, index);
3652
  Handle<Object> global = isolate->global_object();
3653
  Handle<Object> binding = isolate->extras_binding_object();
3654 3655
  Handle<Object> extras_utils = isolate->extras_utils_object();
  Handle<Object> args[] = {global, binding, extras_utils};
yangguo's avatar
yangguo committed
3656
  return Bootstrapper::CompileNative(isolate, name, source_code,
3657
                                     arraysize(args), args, EXTENSION_CODE);
3658 3659 3660
}


3661 3662 3663 3664 3665
bool Bootstrapper::CompileExperimentalExtraBuiltin(Isolate* isolate,
                                                   int index) {
  HandleScope scope(isolate);
  Vector<const char> name = ExperimentalExtraNatives::GetScriptName(index);
  Handle<String> source_code =
3666
      isolate->bootstrapper()->GetNativeSource(EXPERIMENTAL_EXTRAS, index);
3667 3668
  Handle<Object> global = isolate->global_object();
  Handle<Object> binding = isolate->extras_binding_object();
3669 3670
  Handle<Object> extras_utils = isolate->extras_utils_object();
  Handle<Object> args[] = {global, binding, extras_utils};
yangguo's avatar
yangguo committed
3671
  return Bootstrapper::CompileNative(isolate, name, source_code,
3672
                                     arraysize(args), args, EXTENSION_CODE);
3673 3674
}

3675 3676
bool Bootstrapper::CompileNative(Isolate* isolate, Vector<const char> name,
                                 Handle<String> source, int argc,
3677 3678
                                 Handle<Object> argv[],
                                 NativesFlag natives_flag) {
3679
  SuppressDebug compiling_natives(isolate->debug());
3680 3681 3682 3683
  // During genesis, the boilerplate for stack overflow won't work until the
  // environment has been at least partially initialized. Add a stack check
  // before entering JS code to catch overflow early.
  StackLimitCheck check(isolate);
3684
  if (check.JsHasOverflowed(kStackSpaceRequiredForCompilation * KB)) {
3685 3686 3687
    isolate->StackOverflow();
    return false;
  }
3688

3689 3690 3691 3692
  Handle<Context> context(isolate->context());

  Handle<String> script_name =
      isolate->factory()->NewStringFromUtf8(name).ToHandleChecked();
3693
  MaybeHandle<SharedFunctionInfo> maybe_function_info =
3694
      Compiler::GetSharedFunctionInfoForScript(
3695
          source, script_name, 0, 0, ScriptOriginOptions(),
3696
          MaybeHandle<Object>(), context, nullptr, nullptr,
3697 3698
          ScriptCompiler::kNoCompileOptions, ScriptCompiler::kNoCacheNoReason,
          natives_flag, MaybeHandle<FixedArray>());
3699 3700
  Handle<SharedFunctionInfo> function_info;
  if (!maybe_function_info.ToHandle(&function_info)) return false;
3701 3702 3703 3704 3705

  DCHECK(context->IsNativeContext());

  Handle<JSFunction> fun =
      isolate->factory()->NewFunctionFromSharedFunctionInfo(function_info,
3706
                                                            context);
yangguo's avatar
yangguo committed
3707
  Handle<Object> receiver = isolate->factory()->undefined_value();
3708 3709 3710

  // For non-extension scripts, run script to get the function wrapper.
  Handle<Object> wrapper;
3711 3712 3713
  if (!Execution::TryCall(isolate, fun, receiver, 0, nullptr,
                          Execution::MessageHandling::kKeepPending, nullptr)
           .ToHandle(&wrapper)) {
3714 3715 3716
    return false;
  }
  // Then run the function wrapper.
3717 3718 3719 3720
  return !Execution::TryCall(isolate, Handle<JSFunction>::cast(wrapper),
                             receiver, argc, argv,
                             Execution::MessageHandling::kKeepPending, nullptr)
              .is_null();
3721 3722 3723
}


3724 3725 3726
bool Genesis::CallUtilsFunction(Isolate* isolate, const char* name) {
  Handle<JSObject> utils =
      Handle<JSObject>::cast(isolate->natives_utils_object());
3727 3728
  Handle<String> name_string =
      isolate->factory()->NewStringFromAsciiChecked(name);
3729 3730
  Handle<Object> fun = JSObject::GetDataProperty(utils, name_string);
  Handle<Object> receiver = isolate->factory()->undefined_value();
3731
  Handle<Object> args[] = {utils};
3732 3733 3734
  return !Execution::TryCall(isolate, fun, receiver, 1, args,
                             Execution::MessageHandling::kKeepPending, nullptr)
              .is_null();
3735 3736 3737
}


3738
bool Genesis::CompileExtension(Isolate* isolate, v8::Extension* extension) {
3739 3740
  Factory* factory = isolate->factory();
  HandleScope scope(isolate);
3741
  Handle<SharedFunctionInfo> function_info;
3742

3743 3744 3745 3746 3747 3748
  Handle<String> source =
      isolate->factory()
          ->NewExternalStringFromOneByte(extension->source())
          .ToHandleChecked();
  DCHECK(source->IsOneByteRepresentation());

3749 3750
  // If we can't find the function in the cache, we compile a new
  // function and insert it into the cache.
3751 3752 3753 3754 3755 3756
  Vector<const char> name = CStrVector(extension->name());
  SourceCodeCache* cache = isolate->bootstrapper()->extensions_cache();
  Handle<Context> context(isolate->context());
  DCHECK(context->IsNativeContext());

  if (!cache->Lookup(name, &function_info)) {
3757 3758
    Handle<String> script_name =
        factory->NewStringFromUtf8(name).ToHandleChecked();
3759 3760 3761
    MaybeHandle<SharedFunctionInfo> maybe_function_info =
        Compiler::GetSharedFunctionInfoForScript(
            source, script_name, 0, 0, ScriptOriginOptions(),
3762
            MaybeHandle<Object>(), context, extension, nullptr,
3763
            ScriptCompiler::kNoCompileOptions,
3764
            ScriptCompiler::kNoCacheBecauseV8Extension, EXTENSION_CODE,
3765
            MaybeHandle<FixedArray>());
3766
    if (!maybe_function_info.ToHandle(&function_info)) return false;
3767
    cache->Add(name, function_info);
3768 3769
  }

3770
  // Set up the function context. Conceptually, we should clone the
3771 3772 3773
  // function before overwriting the context but since we're in a
  // single-threaded environment it is not strictly necessary.
  Handle<JSFunction> fun =
3774
      factory->NewFunctionFromSharedFunctionInfo(function_info, context);
3775

sgjesse@chromium.org's avatar
sgjesse@chromium.org committed
3776
  // Call function using either the runtime object or the global
3777
  // object as the receiver. Provide no parameters.
3778
  Handle<Object> receiver = isolate->global_object();
3779 3780 3781
  return !Execution::TryCall(isolate, fun, receiver, 0, nullptr,
                             Execution::MessageHandling::kKeepPending, nullptr)
              .is_null();
3782 3783 3784
}


3785 3786 3787 3788
static Handle<JSObject> ResolveBuiltinIdHolder(Handle<Context> native_context,
                                               const char* holder_expr) {
  Isolate* isolate = native_context->GetIsolate();
  Factory* factory = isolate->factory();
3789
  Handle<JSGlobalObject> global(native_context->global_object());
3790
  const char* period_pos = strchr(holder_expr, '.');
3791
  if (period_pos == nullptr) {
3792 3793 3794 3795 3796 3797
    return Handle<JSObject>::cast(
        Object::GetPropertyOrElement(
            global, factory->InternalizeUtf8String(holder_expr))
            .ToHandleChecked());
  }
  const char* inner = period_pos + 1;
3798
  DCHECK(!strchr(inner, '.'));
3799 3800 3801
  Vector<const char> property(holder_expr,
                              static_cast<int>(period_pos - holder_expr));
  Handle<String> property_string = factory->InternalizeUtf8String(property);
3802
  DCHECK(!property_string.is_null());
3803
  Handle<JSObject> object = Handle<JSObject>::cast(
3804
      JSReceiver::GetProperty(global, property_string).ToHandleChecked());
3805 3806 3807 3808 3809
  if (strcmp("prototype", inner) == 0) {
    Handle<JSFunction> function = Handle<JSFunction>::cast(object);
    return Handle<JSObject>(JSObject::cast(function->prototype()));
  }
  Handle<String> inner_string = factory->InternalizeUtf8String(inner);
3810
  DCHECK(!inner_string.is_null());
3811
  Handle<Object> value =
3812
      JSReceiver::GetProperty(object, inner_string).ToHandleChecked();
3813 3814 3815
  return Handle<JSObject>::cast(value);
}

3816
void Genesis::ConfigureUtilsObject(GlobalContextType context_type) {
3817 3818 3819 3820 3821 3822 3823 3824
  switch (context_type) {
    // We still need the utils object to find debug functions.
    case DEBUG_CONTEXT:
      return;
    // Expose the natives in global if a valid name for it is specified.
    case FULL_CONTEXT: {
      // We still need the utils object after deserialization.
      if (isolate()->serializer_enabled()) return;
3825
      if (FLAG_expose_natives_as == nullptr) break;
3826 3827 3828 3829 3830 3831 3832 3833 3834 3835 3836 3837 3838 3839 3840
      if (strlen(FLAG_expose_natives_as) == 0) break;
      HandleScope scope(isolate());
      Handle<String> natives_key =
          factory()->InternalizeUtf8String(FLAG_expose_natives_as);
      uint32_t dummy_index;
      if (natives_key->AsArrayIndex(&dummy_index)) break;
      Handle<Object> utils = isolate()->natives_utils_object();
      Handle<JSObject> global = isolate()->global_object();
      JSObject::AddProperty(global, natives_key, utils, DONT_ENUM);
      break;
    }
  }

  // The utils object can be removed for cases that reach this point.
  native_context()->set_natives_utils_object(heap()->undefined_value());
3841
  native_context()->set_extras_utils_object(heap()->undefined_value());
3842 3843 3844
}


3845 3846
void Bootstrapper::ExportFromRuntime(Isolate* isolate,
                                     Handle<JSObject> container) {
3847
  Factory* factory = isolate->factory();
3848
  HandleScope scope(isolate);
3849 3850 3851 3852
  Handle<Context> native_context = isolate->native_context();
#define EXPORT_PRIVATE_SYMBOL(NAME)                                       \
  Handle<String> NAME##_name = factory->NewStringFromAsciiChecked(#NAME); \
  JSObject::AddProperty(container, NAME##_name, factory->NAME(), NONE);
3853 3854
  PRIVATE_SYMBOL_LIST(EXPORT_PRIVATE_SYMBOL)
#undef EXPORT_PRIVATE_SYMBOL
3855

3856 3857 3858
#define EXPORT_PUBLIC_SYMBOL(NAME, DESCRIPTION)                           \
  Handle<String> NAME##_name = factory->NewStringFromAsciiChecked(#NAME); \
  JSObject::AddProperty(container, NAME##_name, factory->NAME(), NONE);
3859
  PUBLIC_SYMBOL_LIST(EXPORT_PUBLIC_SYMBOL)
3860
  WELL_KNOWN_SYMBOL_LIST(EXPORT_PUBLIC_SYMBOL)
3861 3862
#undef EXPORT_PUBLIC_SYMBOL

3863 3864
  Handle<JSObject> iterator_prototype(
      native_context->initial_iterator_prototype());
3865

3866 3867 3868
  JSObject::AddProperty(container,
                        factory->InternalizeUtf8String("IteratorPrototype"),
                        iterator_prototype, NONE);
3869 3870

  {
3871
    PrototypeIterator iter(native_context->generator_function_map());
3872 3873
    Handle<JSObject> generator_function_prototype(iter.GetCurrent<JSObject>());

3874 3875 3876
    JSObject::AddProperty(
        container, factory->InternalizeUtf8String("GeneratorFunctionPrototype"),
        generator_function_prototype, NONE);
3877

3878
    Handle<JSFunction> generator_function_function = InstallFunction(
3879
        container, "GeneratorFunction", JS_FUNCTION_TYPE,
3880
        JSFunction::kSizeWithPrototype, 0, generator_function_prototype,
3881
        Builtins::kGeneratorFunctionConstructor);
ishell's avatar
ishell committed
3882
    generator_function_function->set_prototype_or_initial_map(
3883
        native_context->generator_function_map());
3884
    generator_function_function->shared()->DontAdaptArguments();
3885
    generator_function_function->shared()->SetConstructStub(
3886
        *BUILTIN_CODE(isolate, GeneratorFunctionConstructor));
3887
    generator_function_function->shared()->set_length(1);
3888 3889 3890
    InstallWithIntrinsicDefaultProto(
        isolate, generator_function_function,
        Context::GENERATOR_FUNCTION_FUNCTION_INDEX);
ishell's avatar
ishell committed
3891

3892 3893
    JSObject::ForceSetPrototype(generator_function_function,
                                isolate->function_function());
3894 3895 3896 3897 3898
    JSObject::AddProperty(
        generator_function_prototype, factory->constructor_string(),
        generator_function_function,
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

3899
    native_context->generator_function_map()->SetConstructor(
ishell's avatar
ishell committed
3900
        *generator_function_function);
3901 3902
  }

3903 3904 3905 3906 3907
  {
    PrototypeIterator iter(native_context->async_generator_function_map());
    Handle<JSObject> async_generator_function_prototype(
        iter.GetCurrent<JSObject>());

3908 3909
    Handle<JSFunction> async_generator_function_function = InstallFunction(
        container, "AsyncGeneratorFunction", JS_FUNCTION_TYPE,
3910
        JSFunction::kSizeWithPrototype, 0, async_generator_function_prototype,
3911
        Builtins::kAsyncGeneratorFunctionConstructor);
3912 3913 3914 3915
    async_generator_function_function->set_prototype_or_initial_map(
        native_context->async_generator_function_map());
    async_generator_function_function->shared()->DontAdaptArguments();
    async_generator_function_function->shared()->SetConstructStub(
3916
        *BUILTIN_CODE(isolate, AsyncGeneratorFunctionConstructor));
3917 3918 3919 3920 3921 3922 3923 3924 3925 3926 3927 3928 3929 3930 3931 3932 3933
    async_generator_function_function->shared()->set_length(1);
    InstallWithIntrinsicDefaultProto(
        isolate, async_generator_function_function,
        Context::ASYNC_GENERATOR_FUNCTION_FUNCTION_INDEX);

    JSObject::ForceSetPrototype(async_generator_function_function,
                                isolate->function_function());

    JSObject::AddProperty(
        async_generator_function_prototype, factory->constructor_string(),
        async_generator_function_function,
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

    native_context->async_generator_function_map()->SetConstructor(
        *async_generator_function_function);
  }

3934
  {  // -- S e t I t e r a t o r
3935 3936 3937 3938 3939 3940 3941 3942 3943 3944 3945 3946
    Handle<String> name = factory->InternalizeUtf8String("Set Iterator");

    // Setup %SetIteratorPrototype%.
    Handle<JSObject> prototype =
        factory->NewJSObject(isolate->object_function(), TENURED);
    JSObject::ForceSetPrototype(prototype, iterator_prototype);

    // Install the @@toStringTag property on the {prototype}.
    JSObject::AddProperty(
        prototype, factory->to_string_tag_symbol(), name,
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

3947 3948 3949 3950 3951
    // Install the next function on the {prototype}.
    SimpleInstallFunction(prototype, "next",
                          Builtins::kSetIteratorPrototypeNext, 0, true,
                          kSetIteratorNext);

3952 3953
    // Setup SetIterator constructor.
    Handle<JSFunction> set_iterator_function =
3954
        InstallFunction(container, "SetIterator", JS_SET_VALUE_ITERATOR_TYPE,
3955
                        JSSetIterator::kSize, 0, prototype, Builtins::kIllegal);
3956
    set_iterator_function->shared()->set_native(false);
3957
    set_iterator_function->shared()->set_instance_class_name(*name);
3958 3959 3960 3961 3962 3963 3964 3965 3966 3967

    Handle<Map> set_value_iterator_map(set_iterator_function->initial_map(),
                                       isolate);
    native_context->set_set_value_iterator_map(*set_value_iterator_map);

    Handle<Map> set_key_value_iterator_map =
        Map::Copy(set_value_iterator_map, "JS_SET_KEY_VALUE_ITERATOR_TYPE");
    set_key_value_iterator_map->set_instance_type(
        JS_SET_KEY_VALUE_ITERATOR_TYPE);
    native_context->set_set_key_value_iterator_map(*set_key_value_iterator_map);
3968 3969 3970
  }

  {  // -- M a p I t e r a t o r
3971 3972 3973 3974 3975 3976 3977 3978 3979 3980 3981 3982
    Handle<String> name = factory->InternalizeUtf8String("Map Iterator");

    // Setup %MapIteratorPrototype%.
    Handle<JSObject> prototype =
        factory->NewJSObject(isolate->object_function(), TENURED);
    JSObject::ForceSetPrototype(prototype, iterator_prototype);

    // Install the @@toStringTag property on the {prototype}.
    JSObject::AddProperty(
        prototype, factory->to_string_tag_symbol(), name,
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

3983 3984 3985 3986 3987
    // Install the next function on the {prototype}.
    SimpleInstallFunction(prototype, "next",
                          Builtins::kMapIteratorPrototypeNext, 0, true,
                          kMapIteratorNext);

3988 3989
    // Setup MapIterator constructor.
    Handle<JSFunction> map_iterator_function =
3990
        InstallFunction(container, "MapIterator", JS_MAP_KEY_ITERATOR_TYPE,
3991
                        JSMapIterator::kSize, 0, prototype, Builtins::kIllegal);
3992
    map_iterator_function->shared()->set_native(false);
3993
    map_iterator_function->shared()->set_instance_class_name(*name);
3994 3995 3996 3997 3998 3999 4000 4001 4002 4003 4004 4005 4006 4007 4008

    Handle<Map> map_key_iterator_map(map_iterator_function->initial_map(),
                                     isolate);
    native_context->set_map_key_iterator_map(*map_key_iterator_map);

    Handle<Map> map_key_value_iterator_map =
        Map::Copy(map_key_iterator_map, "JS_MAP_KEY_VALUE_ITERATOR_TYPE");
    map_key_value_iterator_map->set_instance_type(
        JS_MAP_KEY_VALUE_ITERATOR_TYPE);
    native_context->set_map_key_value_iterator_map(*map_key_value_iterator_map);

    Handle<Map> map_value_iterator_map =
        Map::Copy(map_key_iterator_map, "JS_MAP_VALUE_ITERATOR_TYPE");
    map_value_iterator_map->set_instance_type(JS_MAP_VALUE_ITERATOR_TYPE);
    native_context->set_map_value_iterator_map(*map_value_iterator_map);
4009 4010 4011
  }

  {  // -- S c r i p t
4012
    Handle<String> name = factory->InternalizeUtf8String("Script");
4013
    Handle<JSFunction> script_fun = InstallFunction(
4014
        container, name, JS_VALUE_TYPE, JSValue::kSize, 0,
4015 4016
        factory->the_hole_value(), Builtins::kUnsupportedThrower, DONT_ENUM);
    script_fun->shared()->set_instance_class_name(*name);
4017 4018 4019 4020 4021 4022 4023 4024
    native_context->set_script_function(*script_fun);

    Handle<Map> script_map = Handle<Map>(script_fun->initial_map());
    Map::EnsureDescriptorSlack(script_map, 15);

    PropertyAttributes attribs =
        static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY);

4025
    {  // column_offset
4026
      Handle<AccessorInfo> info = factory->script_column_offset_accessor();
4027 4028
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4029 4030 4031
      script_map->AppendDescriptor(&d);
    }

4032
    {  // id
4033
      Handle<AccessorInfo> info = factory->script_id_accessor();
4034 4035
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4036 4037 4038
      script_map->AppendDescriptor(&d);
    }

4039
    {  // name
4040
      Handle<AccessorInfo> info = factory->script_name_accessor();
4041 4042
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4043 4044 4045
      script_map->AppendDescriptor(&d);
    }

4046
    {  // line_offset
4047
      Handle<AccessorInfo> info = factory->script_line_offset_accessor();
4048 4049
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4050 4051 4052
      script_map->AppendDescriptor(&d);
    }

4053
    {  // source
4054
      Handle<AccessorInfo> info = factory->script_source_accessor();
4055 4056
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4057 4058 4059
      script_map->AppendDescriptor(&d);
    }

4060
    {  // type
4061
      Handle<AccessorInfo> info = factory->script_type_accessor();
4062 4063
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4064 4065 4066
      script_map->AppendDescriptor(&d);
    }

4067
    {  // compilation_type
4068
      Handle<AccessorInfo> info = factory->script_compilation_type_accessor();
4069 4070
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4071 4072 4073
      script_map->AppendDescriptor(&d);
    }

4074
    {  // context_data
4075
      Handle<AccessorInfo> info = factory->script_context_data_accessor();
4076 4077
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4078 4079 4080
      script_map->AppendDescriptor(&d);
    }

4081
    {  // eval_from_script
4082
      Handle<AccessorInfo> info = factory->script_eval_from_script_accessor();
4083 4084
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4085 4086 4087
      script_map->AppendDescriptor(&d);
    }

4088 4089
    {  // eval_from_script_position
      Handle<AccessorInfo> info =
4090
          factory->script_eval_from_script_position_accessor();
4091 4092
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4093 4094 4095
      script_map->AppendDescriptor(&d);
    }

4096 4097
    {  // eval_from_function_name
      Handle<AccessorInfo> info =
4098
          factory->script_eval_from_function_name_accessor();
4099 4100
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4101 4102 4103
      script_map->AppendDescriptor(&d);
    }

4104
    {  // source_url
4105
      Handle<AccessorInfo> info = factory->script_source_url_accessor();
4106 4107
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4108 4109 4110
      script_map->AppendDescriptor(&d);
    }

4111
    {  // source_mapping_url
4112
      Handle<AccessorInfo> info = factory->script_source_mapping_url_accessor();
4113 4114
      Descriptor d = Descriptor::AccessorConstant(handle(info->name(), isolate),
                                                  info, attribs);
4115 4116
      script_map->AppendDescriptor(&d);
    }
4117 4118 4119 4120 4121 4122 4123 4124
  }

  {  // -- A s y n c F u n c t i o n
    // Builtin functions for AsyncFunction.
    PrototypeIterator iter(native_context->async_function_map());
    Handle<JSObject> async_function_prototype(iter.GetCurrent<JSObject>());

    Handle<JSFunction> async_function_constructor = InstallFunction(
4125
        container, "AsyncFunction", JS_FUNCTION_TYPE,
4126
        JSFunction::kSizeWithPrototype, 0, async_function_prototype,
4127
        Builtins::kAsyncFunctionConstructor);
4128 4129
    async_function_constructor->set_prototype_or_initial_map(
        native_context->async_function_map());
4130 4131
    async_function_constructor->shared()->DontAdaptArguments();
    async_function_constructor->shared()->SetConstructStub(
4132
        *BUILTIN_CODE(isolate, AsyncFunctionConstructor));
4133
    async_function_constructor->shared()->set_length(1);
4134
    native_context->set_async_function_constructor(*async_function_constructor);
4135 4136 4137 4138 4139 4140 4141 4142 4143 4144
    JSObject::ForceSetPrototype(async_function_constructor,
                                isolate->function_function());

    JSObject::AddProperty(
        async_function_prototype, factory->constructor_string(),
        async_function_constructor,
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

    JSFunction::SetPrototype(async_function_constructor,
                             async_function_prototype);
4145

4146
    {
4147 4148
      Handle<JSFunction> function =
          SimpleCreateFunction(isolate, factory->empty_string(),
4149
                               Builtins::kAsyncFunctionAwaitCaught, 2, false);
4150
      native_context->set_async_function_await_caught(*function);
4151
    }
4152

4153 4154 4155
    {
      Handle<JSFunction> function =
          SimpleCreateFunction(isolate, factory->empty_string(),
4156
                               Builtins::kAsyncFunctionAwaitUncaught, 2, false);
4157
      native_context->set_async_function_await_uncaught(*function);
4158
    }
4159

4160
    {
4161 4162 4163
      Handle<SharedFunctionInfo> info = SimpleCreateSharedFunctionInfo(
          isolate, Builtins::kAsyncFunctionAwaitRejectClosure,
          factory->empty_string(), 1);
4164 4165 4166 4167
      native_context->set_async_function_await_reject_shared_fun(*info);
    }

    {
4168 4169 4170
      Handle<SharedFunctionInfo> info = SimpleCreateSharedFunctionInfo(
          isolate, Builtins::kAsyncFunctionAwaitResolveClosure,
          factory->empty_string(), 1);
4171 4172 4173 4174 4175 4176 4177
      native_context->set_async_function_await_resolve_shared_fun(*info);
    }

    {
      Handle<JSFunction> function =
          SimpleCreateFunction(isolate, factory->empty_string(),
                               Builtins::kAsyncFunctionPromiseCreate, 0, false);
4178
      native_context->set_async_function_promise_create(*function);
4179 4180 4181 4182 4183 4184
    }

    {
      Handle<JSFunction> function = SimpleCreateFunction(
          isolate, factory->empty_string(),
          Builtins::kAsyncFunctionPromiseRelease, 1, false);
4185
      native_context->set_async_function_promise_release(*function);
4186
    }
4187
  }
4188 4189 4190 4191

  {  // -- C a l l S i t e
    // Builtin functions for CallSite.

4192 4193 4194 4195
    // CallSites are a special case; the constructor is for our private use
    // only, therefore we set it up as a builtin that throws. Internally, we use
    // CallSiteUtils::Construct to create CallSite objects.

4196
    Handle<JSFunction> callsite_fun = InstallFunction(
4197
        container, "CallSite", JS_OBJECT_TYPE, JSObject::kHeaderSize, 0,
4198
        factory->the_hole_value(), Builtins::kUnsupportedThrower);
4199
    callsite_fun->shared()->DontAdaptArguments();
jgruber's avatar
jgruber committed
4200 4201
    isolate->native_context()->set_callsite_function(*callsite_fun);

4202
    {
4203 4204 4205
      // Setup CallSite.prototype.
      Handle<JSObject> prototype(
          JSObject::cast(callsite_fun->instance_prototype()));
4206 4207 4208 4209 4210 4211 4212 4213 4214 4215 4216 4217 4218 4219 4220 4221 4222 4223 4224 4225 4226 4227

      struct FunctionInfo {
        const char* name;
        Builtins::Name id;
      };

      FunctionInfo infos[] = {
          {"getColumnNumber", Builtins::kCallSitePrototypeGetColumnNumber},
          {"getEvalOrigin", Builtins::kCallSitePrototypeGetEvalOrigin},
          {"getFileName", Builtins::kCallSitePrototypeGetFileName},
          {"getFunction", Builtins::kCallSitePrototypeGetFunction},
          {"getFunctionName", Builtins::kCallSitePrototypeGetFunctionName},
          {"getLineNumber", Builtins::kCallSitePrototypeGetLineNumber},
          {"getMethodName", Builtins::kCallSitePrototypeGetMethodName},
          {"getPosition", Builtins::kCallSitePrototypeGetPosition},
          {"getScriptNameOrSourceURL",
           Builtins::kCallSitePrototypeGetScriptNameOrSourceURL},
          {"getThis", Builtins::kCallSitePrototypeGetThis},
          {"getTypeName", Builtins::kCallSitePrototypeGetTypeName},
          {"isConstructor", Builtins::kCallSitePrototypeIsConstructor},
          {"isEval", Builtins::kCallSitePrototypeIsEval},
          {"isNative", Builtins::kCallSitePrototypeIsNative},
4228 4229
          {"isToplevel", Builtins::kCallSitePrototypeIsToplevel},
          {"toString", Builtins::kCallSitePrototypeToString}};
4230 4231 4232 4233 4234 4235

      PropertyAttributes attrs =
          static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY);

      Handle<JSFunction> fun;
      for (const FunctionInfo& info : infos) {
4236
        SimpleInstallFunction(prototype, info.name, info.id, 0, true, attrs);
4237 4238 4239
      }
    }
  }
4240 4241 4242 4243 4244 4245 4246 4247 4248 4249 4250

#ifdef V8_INTL_SUPPORT
  {  // I n t l  P l u r a l R u l e s
    Handle<JSObject> plural_rules_prototype =
        factory->NewJSObject(isolate->object_function(), TENURED);
    // Install the @@toStringTag property on the {prototype}.
    JSObject::AddProperty(
        plural_rules_prototype, factory->to_string_tag_symbol(),
        factory->Object_string(),
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
    Handle<JSFunction> plural_rules_constructor = InstallFunction(
4251
        container, "PluralRules", JS_OBJECT_TYPE, PluralRules::kSize, 0,
4252 4253 4254 4255 4256 4257
        plural_rules_prototype, Builtins::kIllegal);
    JSObject::AddProperty(plural_rules_prototype, factory->constructor_string(),
                          plural_rules_constructor, DONT_ENUM);
    native_context->set_intl_plural_rules_function(*plural_rules_constructor);
  }
#endif  // V8_INTL_SUPPORT
4258 4259 4260
}


4261 4262 4263
#define EMPTY_INITIALIZE_GLOBAL_FOR_FEATURE(id) \
  void Genesis::InitializeGlobal_##id() {}

4264
EMPTY_INITIALIZE_GLOBAL_FOR_FEATURE(harmony_do_expressions)
4265
EMPTY_INITIALIZE_GLOBAL_FOR_FEATURE(harmony_regexp_named_captures)
4266
EMPTY_INITIALIZE_GLOBAL_FOR_FEATURE(harmony_regexp_property)
4267
EMPTY_INITIALIZE_GLOBAL_FOR_FEATURE(harmony_function_sent)
4268
EMPTY_INITIALIZE_GLOBAL_FOR_FEATURE(harmony_function_tostring)
4269
EMPTY_INITIALIZE_GLOBAL_FOR_FEATURE(harmony_class_fields)
4270
EMPTY_INITIALIZE_GLOBAL_FOR_FEATURE(harmony_dynamic_import)
4271
EMPTY_INITIALIZE_GLOBAL_FOR_FEATURE(harmony_import_meta)
4272
EMPTY_INITIALIZE_GLOBAL_FOR_FEATURE(harmony_template_escapes)
4273
EMPTY_INITIALIZE_GLOBAL_FOR_FEATURE(harmony_restrict_constructor_return)
4274

4275 4276 4277 4278 4279 4280 4281 4282 4283 4284 4285 4286 4287
void InstallPublicSymbol(Factory* factory, Handle<Context> native_context,
                         const char* name, Handle<Symbol> value) {
  Handle<JSGlobalObject> global(
      JSGlobalObject::cast(native_context->global_object()));
  Handle<String> symbol_string = factory->InternalizeUtf8String("Symbol");
  Handle<JSObject> symbol = Handle<JSObject>::cast(
      JSObject::GetProperty(global, symbol_string).ToHandleChecked());
  Handle<String> name_string = factory->InternalizeUtf8String(name);
  PropertyAttributes attributes =
      static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY);
  JSObject::AddProperty(symbol, name_string, value, attributes);
}

binji's avatar
binji committed
4288 4289 4290
void Genesis::InitializeGlobal_harmony_sharedarraybuffer() {
  if (!FLAG_harmony_sharedarraybuffer) return;

4291
  Handle<JSGlobalObject> global(native_context()->global_object());
4292 4293 4294
  Isolate* isolate = global->GetIsolate();
  Factory* factory = isolate->factory();

4295 4296 4297 4298 4299
  {
    Handle<String> name = factory->InternalizeUtf8String("SharedArrayBuffer");
    JSObject::AddProperty(global, name, isolate->shared_array_buffer_fun(),
                          DONT_ENUM);
  }
4300

4301 4302 4303 4304 4305 4306 4307
  {
    Handle<String> name = factory->InternalizeUtf8String("Atomics");
    JSObject::AddProperty(global, name, isolate->atomics_object(), DONT_ENUM);
    JSObject::AddProperty(
        isolate->atomics_object(), factory->to_string_tag_symbol(), name,
        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
  }
binji's avatar
binji committed
4308 4309
}

4310 4311 4312 4313 4314 4315 4316 4317 4318 4319 4320 4321 4322 4323 4324 4325 4326 4327 4328 4329
void Genesis::InitializeGlobal_harmony_array_prototype_values() {
  if (!FLAG_harmony_array_prototype_values) return;
  Handle<JSFunction> array_constructor(native_context()->array_function());
  Handle<JSObject> array_prototype(
      JSObject::cast(array_constructor->instance_prototype()));
  Handle<Object> values_iterator =
      JSObject::GetProperty(array_prototype, factory()->iterator_symbol())
          .ToHandleChecked();
  DCHECK(values_iterator->IsJSFunction());
  JSObject::AddProperty(array_prototype, factory()->values_string(),
                        values_iterator, DONT_ENUM);

  Handle<Object> unscopables =
      JSObject::GetProperty(array_prototype, factory()->unscopables_symbol())
          .ToHandleChecked();
  DCHECK(unscopables->IsJSObject());
  JSObject::AddProperty(Handle<JSObject>::cast(unscopables),
                        factory()->values_string(), factory()->true_value(),
                        NONE);
}
4330

4331 4332 4333 4334 4335 4336 4337
void Genesis::InitializeGlobal_harmony_async_iteration() {
  if (!FLAG_harmony_async_iteration) return;
  Handle<JSFunction> symbol_fun(native_context()->symbol_function());
  InstallConstant(isolate(), symbol_fun, "asyncIterator",
                  factory()->async_iterator_symbol());
}

4338 4339 4340 4341 4342 4343 4344 4345 4346 4347 4348 4349 4350 4351 4352
void Genesis::InitializeGlobal_harmony_promise_finally() {
  if (!FLAG_harmony_promise_finally) return;

  Handle<JSFunction> constructor(native_context()->promise_function());
  Handle<JSObject> prototype(JSObject::cast(constructor->instance_prototype()));
  SimpleInstallFunction(prototype, "finally", Builtins::kPromiseFinally, 1,
                        true, DONT_ENUM);

  // The promise prototype map has changed because we added a property
  // to prototype, so we update the saved map.
  Handle<Map> prototype_map(prototype->map());
  Map::SetShouldBeFastPrototypeMap(prototype_map, true, isolate());
  native_context()->set_promise_prototype_map(*prototype_map);

  {
4353 4354
    Handle<SharedFunctionInfo> info = SimpleCreateSharedFunctionInfo(
        isolate(), Builtins::kPromiseThenFinally, factory()->empty_string(), 1);
4355 4356 4357 4358 4359
    info->set_native(true);
    native_context()->set_promise_then_finally_shared_fun(*info);
  }

  {
4360 4361 4362
    Handle<SharedFunctionInfo> info = SimpleCreateSharedFunctionInfo(
        isolate(), Builtins::kPromiseCatchFinally, factory()->empty_string(),
        1);
4363 4364 4365 4366 4367
    info->set_native(true);
    native_context()->set_promise_catch_finally_shared_fun(*info);
  }

  {
4368 4369 4370
    Handle<SharedFunctionInfo> info = SimpleCreateSharedFunctionInfo(
        isolate(), Builtins::kPromiseValueThunkFinally,
        factory()->empty_string(), 0);
4371 4372 4373 4374
    native_context()->set_promise_value_thunk_finally_shared_fun(*info);
  }

  {
4375 4376 4377
    Handle<SharedFunctionInfo> info = SimpleCreateSharedFunctionInfo(
        isolate(), Builtins::kPromiseThrowerFinally, factory()->empty_string(),
        0);
4378 4379 4380 4381
    native_context()->set_promise_thrower_finally_shared_fun(*info);
  }
}

4382 4383 4384
void Genesis::InitializeGlobal_harmony_bigint() {
  if (!FLAG_harmony_bigint) return;

4385
  Factory* factory = isolate()->factory();
4386
  Handle<JSGlobalObject> global(native_context()->global_object());
4387 4388 4389
  Handle<JSFunction> bigint_fun =
      InstallFunction(global, "BigInt", JS_VALUE_TYPE, JSValue::kSize, 0,
                      factory->the_hole_value(), Builtins::kBigIntConstructor);
4390 4391 4392 4393 4394 4395 4396 4397 4398 4399 4400 4401 4402 4403 4404 4405 4406 4407 4408 4409 4410 4411 4412 4413 4414 4415 4416 4417 4418 4419 4420 4421 4422 4423 4424
  bigint_fun->shared()->DontAdaptArguments();
  bigint_fun->shared()->SetConstructStub(
      *BUILTIN_CODE(isolate(), BigIntConstructor_ConstructStub));
  bigint_fun->shared()->set_length(1);
  InstallWithIntrinsicDefaultProto(isolate(), bigint_fun,
                                   Context::BIGINT_FUNCTION_INDEX);
  heap()->bigint_map()->SetConstructorFunctionIndex(
      Context::BIGINT_FUNCTION_INDEX);

  // Install the properties of the BigInt constructor.
  // parseInt(string, radix)
  SimpleInstallFunction(bigint_fun, "parseInt", Builtins::kBigIntParseInt, 2,
                        false);
  // asUintN(bits, bigint)
  SimpleInstallFunction(bigint_fun, "asUintN", Builtins::kBigIntAsUintN, 2,
                        false);
  // asIntN(bits, bigint)
  SimpleInstallFunction(bigint_fun, "asIntN", Builtins::kBigIntAsIntN, 2,
                        false);

  // Set up the %BigIntPrototype%.
  Handle<JSObject> prototype(JSObject::cast(bigint_fun->instance_prototype()));
  JSFunction::SetPrototype(bigint_fun, prototype);

  // Install the properties of the BigInt.prototype.
  // "constructor" is created implicitly by InstallFunction() above.
  // toLocaleString([reserved1 [, reserved2]])
  SimpleInstallFunction(prototype, "toLocaleString",
                        Builtins::kBigIntPrototypeToLocaleString, 0, false);
  // toString([radix])
  SimpleInstallFunction(prototype, "toString",
                        Builtins::kBigIntPrototypeToString, 0, false);
  // valueOf()
  SimpleInstallFunction(prototype, "valueOf", Builtins::kBigIntPrototypeValueOf,
                        0, false);
4425 4426 4427 4428
  // @@toStringTag
  JSObject::AddProperty(prototype, factory->to_string_tag_symbol(),
                        factory->BigInt_string(),
                        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));
4429 4430
}

4431 4432 4433 4434 4435 4436 4437 4438 4439 4440
#ifdef V8_INTL_SUPPORT

void Genesis::InitializeGlobal_harmony_number_format_to_parts() {
  if (!FLAG_harmony_number_format_to_parts) return;
  Handle<JSObject> number_format_prototype(JSObject::cast(
      native_context()->intl_number_format_function()->prototype()));
  Handle<String> name = factory()->InternalizeUtf8String("formatToParts");
  InstallFunction(number_format_prototype,
                  SimpleCreateFunction(
                      isolate(), name,
4441
                      Builtins::kNumberFormatPrototypeFormatToParts, 1, false),
4442 4443 4444
                  name);
}

4445 4446 4447 4448 4449 4450 4451 4452 4453 4454 4455 4456 4457 4458
void Genesis::InitializeGlobal_harmony_plural_rules() {
  if (!FLAG_harmony_plural_rules) return;

  Handle<JSFunction> plural_rules(
      native_context()->intl_plural_rules_function());
  Handle<JSObject> intl = Handle<JSObject>::cast(
      JSReceiver::GetProperty(
          Handle<JSReceiver>(native_context()->global_object()),
          factory()->InternalizeUtf8String("Intl"))
          .ToHandleChecked());
  JSObject::AddProperty(intl, factory()->InternalizeUtf8String("PluralRules"),
                        plural_rules, DONT_ENUM);
}

4459 4460
#endif  // V8_INTL_SUPPORT

4461 4462 4463 4464
Handle<JSFunction> Genesis::CreateArrayBuffer(Handle<String> name,
                                              Builtins::Name call_byteLength,
                                              BuiltinFunctionId byteLength_id,
                                              Builtins::Name call_slice) {
4465
  // Create the %ArrayBufferPrototype%
4466 4467 4468
  // Setup the {prototype} with the given {name} for @@toStringTag.
  Handle<JSObject> prototype =
      factory()->NewJSObject(isolate()->object_function(), TENURED);
4469
  JSObject::AddProperty(prototype, factory()->to_string_tag_symbol(), name,
4470 4471 4472 4473
                        static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY));

  // Allocate the constructor with the given {prototype}.
  Handle<JSFunction> array_buffer_fun =
4474
      CreateFunction(isolate(), name, JS_ARRAY_BUFFER_TYPE,
4475
                     JSArrayBuffer::kSizeWithEmbedderFields, 0, prototype,
4476
                     Builtins::kArrayBufferConstructor);
4477 4478 4479
  Handle<Code> code =
      BUILTIN_CODE(isolate(), ArrayBufferConstructor_ConstructStub);
  array_buffer_fun->shared()->SetConstructStub(*code);
4480 4481
  array_buffer_fun->shared()->DontAdaptArguments();
  array_buffer_fun->shared()->set_length(1);
4482
  array_buffer_fun->shared()->set_instance_class_name(*name);
4483 4484 4485 4486 4487 4488

  // Install the "constructor" property on the {prototype}.
  JSObject::AddProperty(prototype, factory()->constructor_string(),
                        array_buffer_fun, DONT_ENUM);

  SimpleInstallFunction(array_buffer_fun, factory()->isView_string(),
4489 4490
                        Builtins::kArrayBufferIsView, 1, true, DONT_ENUM,
                        kArrayBufferIsView);
4491

4492
  // Install the "byteLength" getter on the {prototype}.
4493 4494
  SimpleInstallGetter(prototype, factory()->byte_length_string(),
                      call_byteLength, false, byteLength_id);
4495

4496
  SimpleInstallFunction(prototype, "slice", call_slice, 2, true);
4497

4498 4499 4500 4501
  return array_buffer_fun;
}


4502 4503 4504
Handle<JSFunction> Genesis::InstallInternalArray(Handle<JSObject> target,
                                                 const char* name,
                                                 ElementsKind elements_kind) {
4505 4506 4507 4508 4509 4510 4511 4512
  // --- I n t e r n a l   A r r a y ---
  // An array constructor on the builtins object that works like
  // the public Array constructor, except that its prototype
  // doesn't inherit from Object.prototype.
  // To be used only for internal work by builtins. Instances
  // must not be leaked to user code.
  Handle<JSObject> prototype =
      factory()->NewJSObject(isolate()->object_function(), TENURED);
4513
  Handle<JSFunction> array_function =
4514
      InstallFunction(target, name, JS_ARRAY_TYPE, JSArray::kSize, 0, prototype,
4515
                      Builtins::kInternalArrayConstructor);
4516

4517
  InternalArrayConstructorStub internal_array_constructor_stub(isolate());
4518
  Handle<Code> code = internal_array_constructor_stub.GetCode();
4519
  array_function->shared()->SetConstructStub(*code);
4520 4521
  array_function->shared()->DontAdaptArguments();

4522
  Handle<Map> original_map(array_function->initial_map());
4523
  Handle<Map> initial_map = Map::Copy(original_map, "InternalArray");
4524
  initial_map->set_elements_kind(elements_kind);
4525
  JSFunction::SetInitialMap(array_function, initial_map, prototype);
4526 4527

  // Make "length" magic on instances.
4528
  Map::EnsureDescriptorSlack(initial_map, 1);
4529 4530 4531 4532 4533

  PropertyAttributes attribs = static_cast<PropertyAttributes>(
      DONT_ENUM | DONT_DELETE);

  {  // Add length.
4534 4535 4536
    Descriptor d = Descriptor::AccessorConstant(
        factory()->length_string(), factory()->array_length_accessor(),
        attribs);
4537
    initial_map->AppendDescriptor(&d);
4538 4539 4540 4541 4542
  }

  return array_function;
}

4543
bool Genesis::InstallNatives(GlobalContextType context_type) {
4544
  HandleScope scope(isolate());
4545

4546 4547 4548 4549 4550
  // Set up the utils object as shared container between native scripts.
  Handle<JSObject> utils = factory()->NewJSObject(isolate()->object_function());
  JSObject::NormalizeProperties(utils, CLEAR_INOBJECT_PROPERTIES, 16,
                                "utils container for native scripts");
  native_context()->set_natives_utils_object(*utils);
4551

4552 4553 4554 4555 4556 4557
  // Set up the extras utils object as a shared container between native
  // scripts and extras. (Extras consume things added there by native scripts.)
  Handle<JSObject> extras_utils =
      factory()->NewJSObject(isolate()->object_function());
  native_context()->set_extras_utils_object(*extras_utils);

4558
  InstallInternalArray(extras_utils, "InternalPackedArray", PACKED_ELEMENTS);
4559

4560 4561
  InstallFunction(extras_utils, isolate()->promise_internal_constructor(),
                  factory()->NewStringFromAsciiChecked("createPromise"));
4562 4563
  InstallFunction(extras_utils, isolate()->promise_resolve(),
                  factory()->NewStringFromAsciiChecked("resolvePromise"));
domenic's avatar
domenic committed
4564 4565
  InstallFunction(extras_utils, isolate()->is_promise(),
                  factory()->NewStringFromAsciiChecked("isPromise"));
4566

4567
  int builtin_index = Natives::GetDebuggerCount();
4568
  // Only run prologue.js at this point.
4569 4570 4571
  DCHECK_EQ(builtin_index, Natives::GetIndex("prologue"));
  if (!Bootstrapper::CompileBuiltin(isolate(), builtin_index++)) return false;

4572 4573 4574 4575 4576
  {
    // Builtin function for OpaqueReference -- a JSValue-based object,
    // that keeps its field isolated from JavaScript code. It may store
    // objects, that JavaScript code may not access.
    Handle<JSObject> prototype =
4577
        factory()->NewJSObject(isolate()->object_function(), TENURED);
4578 4579
    Handle<JSFunction> opaque_reference_fun =
        CreateFunction(isolate(), factory()->empty_string(), JS_VALUE_TYPE,
4580
                       JSValue::kSize, 0, prototype, Builtins::kIllegal);
4581
    native_context()->set_opaque_reference_function(*opaque_reference_fun);
4582
  }
4583

4584 4585 4586 4587 4588 4589
  // InternalArrays should not use Smi-Only array optimizations. There are too
  // many places in the C++ runtime code (e.g. RegEx) that assume that
  // elements in InternalArrays can be set to non-Smi values without going
  // through a common bottleneck that would make the SMI_ONLY -> FAST_ELEMENT
  // transition easy to trap. Moreover, they rarely are smi-only.
  {
4590
    HandleScope scope(isolate());
4591 4592 4593
    Handle<JSObject> utils =
        Handle<JSObject>::cast(isolate()->natives_utils_object());
    Handle<JSFunction> array_function =
4594
        InstallInternalArray(utils, "InternalArray", HOLEY_ELEMENTS);
4595
    native_context()->set_internal_array_function(*array_function);
4596 4597
  }

4598 4599 4600
  // Run the rest of the native scripts.
  while (builtin_index < Natives::GetBuiltinsCount()) {
    if (!Bootstrapper::CompileBuiltin(isolate(), builtin_index++)) return false;
4601 4602
  }

4603
  if (!CallUtilsFunction(isolate(), "PostNatives")) return false;
4604 4605 4606 4607
  auto fast_template_instantiations_cache = isolate()->factory()->NewFixedArray(
      TemplateInfo::kFastTemplateInstantiationsCacheSize);
  native_context()->set_fast_template_instantiations_cache(
      *fast_template_instantiations_cache);
4608

4609 4610
  auto slow_template_instantiations_cache =
      NumberDictionary::New(isolate(), ApiNatives::kInitialFunctionCacheSize);
4611 4612
  native_context()->set_slow_template_instantiations_cache(
      *slow_template_instantiations_cache);
4613

4614 4615
  // Store the map for the %ObjectPrototype% after the natives has been compiled
  // and the Object function has been set up.
4616 4617 4618 4619 4620 4621 4622
  {
    Handle<JSFunction> object_function(native_context()->object_function());
    DCHECK(JSObject::cast(object_function->initial_map()->prototype())
               ->HasFastProperties());
    native_context()->set_object_function_prototype_map(
        HeapObject::cast(object_function->initial_map()->prototype())->map());
  }
4623

4624
  // Store the map for the %StringPrototype% after the natives has been compiled
4625
  // and the String function has been set up.
4626
  Handle<JSFunction> string_function(native_context()->string_function());
4627 4628 4629
  JSObject* string_function_prototype =
      JSObject::cast(string_function->initial_map()->prototype());
  DCHECK(string_function_prototype->HasFastProperties());
4630
  native_context()->set_string_function_prototype_map(
4631
      string_function_prototype->map());
4632

4633 4634 4635
  Handle<JSGlobalObject> global_object =
      handle(native_context()->global_object());

4636 4637
  // Install Global.decodeURI.
  SimpleInstallFunction(global_object, "decodeURI", Builtins::kGlobalDecodeURI,
4638
                        1, false, kGlobalDecodeURI);
4639 4640 4641

  // Install Global.decodeURIComponent.
  SimpleInstallFunction(global_object, "decodeURIComponent",
4642 4643
                        Builtins::kGlobalDecodeURIComponent, 1, false,
                        kGlobalDecodeURIComponent);
4644

4645 4646
  // Install Global.encodeURI.
  SimpleInstallFunction(global_object, "encodeURI", Builtins::kGlobalEncodeURI,
4647
                        1, false, kGlobalEncodeURI);
4648 4649 4650

  // Install Global.encodeURIComponent.
  SimpleInstallFunction(global_object, "encodeURIComponent",
4651 4652
                        Builtins::kGlobalEncodeURIComponent, 1, false,
                        kGlobalEncodeURIComponent);
4653

4654 4655
  // Install Global.escape.
  SimpleInstallFunction(global_object, "escape", Builtins::kGlobalEscape, 1,
4656
                        false, kGlobalEscape);
4657 4658 4659

  // Install Global.unescape.
  SimpleInstallFunction(global_object, "unescape", Builtins::kGlobalUnescape, 1,
4660
                        false, kGlobalUnescape);
4661

4662 4663
  // Install Global.eval.
  {
4664 4665 4666
    Handle<JSFunction> eval =
        SimpleInstallFunction(global_object, factory()->eval_string(),
                              Builtins::kGlobalEval, 1, false);
4667 4668 4669
    native_context()->set_global_eval_fun(*eval);
  }

4670 4671 4672 4673 4674 4675 4676 4677
  // Install Global.isFinite
  SimpleInstallFunction(global_object, "isFinite", Builtins::kGlobalIsFinite, 1,
                        true, kGlobalIsFinite);

  // Install Global.isNaN
  SimpleInstallFunction(global_object, "isNaN", Builtins::kGlobalIsNaN, 1, true,
                        kGlobalIsNaN);

4678
  // Install Array builtin functions.
4679 4680
  {
    Handle<JSFunction> array_constructor(native_context()->array_function());
4681 4682 4683 4684 4685
    Handle<JSArray> proto(JSArray::cast(array_constructor->prototype()));

    // Verification of important array prototype properties.
    Object* length = proto->length();
    CHECK(length->IsSmi());
4686
    CHECK_EQ(Smi::ToInt(length), 0);
4687
    CHECK(proto->HasSmiOrObjectElements());
4688 4689 4690
    // This is necessary to enable fast checks for absence of elements
    // on Array.prototype and below.
    proto->set_elements(heap()->empty_fixed_array());
4691 4692 4693 4694 4695 4696 4697
  }

  // Install InternalArray.prototype.concat
  {
    Handle<JSFunction> array_constructor(
        native_context()->internal_array_function());
    Handle<JSObject> proto(JSObject::cast(array_constructor->prototype()));
4698
    SimpleInstallFunction(proto, "concat", Builtins::kArrayConcat, 1, false);
4699
  }
4700

4701 4702
  InstallBuiltinFunctionIds();

4703 4704 4705 4706 4707
  // Create a map for accessor property descriptors (a variant of JSObject
  // that predefines four properties get, set, configurable and enumerable).
  {
    // AccessorPropertyDescriptor initial map.
    Handle<Map> map =
4708 4709
        factory()->NewMap(JS_OBJECT_TYPE, JSAccessorPropertyDescriptor::kSize,
                          TERMINAL_FAST_ELEMENTS_KIND, 4);
4710 4711 4712 4713
    // Create the descriptor array for the property descriptor object.
    Map::EnsureDescriptorSlack(map, 4);

    {  // get
4714 4715 4716
      Descriptor d = Descriptor::DataField(
          factory()->get_string(), JSAccessorPropertyDescriptor::kGetIndex,
          NONE, Representation::Tagged());
4717 4718 4719
      map->AppendDescriptor(&d);
    }
    {  // set
4720 4721 4722
      Descriptor d = Descriptor::DataField(
          factory()->set_string(), JSAccessorPropertyDescriptor::kSetIndex,
          NONE, Representation::Tagged());
4723 4724 4725
      map->AppendDescriptor(&d);
    }
    {  // enumerable
4726 4727 4728 4729
      Descriptor d =
          Descriptor::DataField(factory()->enumerable_string(),
                                JSAccessorPropertyDescriptor::kEnumerableIndex,
                                NONE, Representation::Tagged());
4730 4731 4732
      map->AppendDescriptor(&d);
    }
    {  // configurable
4733 4734 4735 4736
      Descriptor d = Descriptor::DataField(
          factory()->configurable_string(),
          JSAccessorPropertyDescriptor::kConfigurableIndex, NONE,
          Representation::Tagged());
4737 4738 4739 4740
      map->AppendDescriptor(&d);
    }

    Map::SetPrototype(map, isolate()->initial_object_prototype());
4741
    map->SetConstructor(native_context()->object_function());
4742 4743 4744 4745 4746 4747 4748 4749 4750 4751

    native_context()->set_accessor_property_descriptor_map(*map);
  }

  // Create a map for data property descriptors (a variant of JSObject
  // that predefines four properties value, writable, configurable and
  // enumerable).
  {
    // DataPropertyDescriptor initial map.
    Handle<Map> map =
4752 4753
        factory()->NewMap(JS_OBJECT_TYPE, JSDataPropertyDescriptor::kSize,
                          TERMINAL_FAST_ELEMENTS_KIND, 4);
4754 4755 4756 4757
    // Create the descriptor array for the property descriptor object.
    Map::EnsureDescriptorSlack(map, 4);

    {  // value
4758 4759 4760
      Descriptor d = Descriptor::DataField(
          factory()->value_string(), JSDataPropertyDescriptor::kValueIndex,
          NONE, Representation::Tagged());
4761 4762 4763
      map->AppendDescriptor(&d);
    }
    {  // writable
4764 4765 4766 4767
      Descriptor d =
          Descriptor::DataField(factory()->writable_string(),
                                JSDataPropertyDescriptor::kWritableIndex, NONE,
                                Representation::Tagged());
4768 4769 4770
      map->AppendDescriptor(&d);
    }
    {  // enumerable
4771 4772 4773 4774
      Descriptor d =
          Descriptor::DataField(factory()->enumerable_string(),
                                JSDataPropertyDescriptor::kEnumerableIndex,
                                NONE, Representation::Tagged());
4775 4776 4777
      map->AppendDescriptor(&d);
    }
    {  // configurable
4778 4779 4780 4781
      Descriptor d =
          Descriptor::DataField(factory()->configurable_string(),
                                JSDataPropertyDescriptor::kConfigurableIndex,
                                NONE, Representation::Tagged());
4782 4783 4784 4785
      map->AppendDescriptor(&d);
    }

    Map::SetPrototype(map, isolate()->initial_object_prototype());
4786
    map->SetConstructor(native_context()->object_function());
4787 4788 4789 4790

    native_context()->set_data_property_descriptor_map(*map);
  }

4791 4792 4793 4794 4795 4796
  // Create a constructor for RegExp results (a variant of Array that
  // predefines the two properties index and match).
  {
    // RegExpResult initial map.

    // Find global.Array.prototype to inherit from.
4797
    Handle<JSFunction> array_constructor(native_context()->array_function());
4798 4799 4800 4801
    Handle<JSObject> array_prototype(
        JSObject::cast(array_constructor->instance_prototype()));

    // Add initial map.
4802 4803
    Handle<Map> initial_map = factory()->NewMap(
        JS_ARRAY_TYPE, JSRegExpResult::kSize, TERMINAL_FAST_ELEMENTS_KIND, 2);
4804
    initial_map->SetConstructor(*array_constructor);
4805 4806 4807

    // Set prototype on map.
    initial_map->set_non_instance_prototype(false);
4808
    Map::SetPrototype(initial_map, array_prototype);
4809 4810

    // Update map with length accessor from Array and add "index" and "input".
4811
    Map::EnsureDescriptorSlack(initial_map, 3);
4812

4813
    {
4814
      JSFunction* array_function = native_context()->array_function();
4815 4816
      Handle<DescriptorArray> array_descriptors(
          array_function->initial_map()->instance_descriptors());
4817
      Handle<String> length = factory()->length_string();
4818
      int old = array_descriptors->SearchWithCache(
4819
          isolate(), *length, array_function->initial_map());
4820
      DCHECK_NE(old, DescriptorArray::kNotFound);
4821
      Descriptor d = Descriptor::AccessorConstant(
4822 4823
          length, handle(array_descriptors->GetValue(old), isolate()),
          array_descriptors->GetDetails(old).attributes());
4824
      initial_map->AppendDescriptor(&d);
4825
    }
4826
    {
4827 4828 4829 4830
      Descriptor d = Descriptor::DataField(factory()->index_string(),
                                           JSRegExpResult::kIndexIndex, NONE,
                                           Representation::Tagged());
      initial_map->AppendDescriptor(&d);
4831 4832 4833
    }

    {
4834 4835 4836 4837
      Descriptor d = Descriptor::DataField(factory()->input_string(),
                                           JSRegExpResult::kInputIndex, NONE,
                                           Representation::Tagged());
      initial_map->AppendDescriptor(&d);
4838 4839
    }

4840
    native_context()->set_regexp_result_map(*initial_map);
4841 4842
  }

4843 4844 4845 4846
  // Add @@iterator method to the arguments object maps.
  {
    PropertyAttributes attribs = DONT_ENUM;
    Handle<AccessorInfo> arguments_iterator =
4847
        factory()->arguments_iterator_accessor();
4848
    {
4849 4850
      Descriptor d = Descriptor::AccessorConstant(factory()->iterator_symbol(),
                                                  arguments_iterator, attribs);
4851 4852 4853 4854 4855
      Handle<Map> map(native_context()->sloppy_arguments_map());
      Map::EnsureDescriptorSlack(map, 1);
      map->AppendDescriptor(&d);
    }
    {
4856 4857
      Descriptor d = Descriptor::AccessorConstant(factory()->iterator_symbol(),
                                                  arguments_iterator, attribs);
4858 4859 4860 4861 4862
      Handle<Map> map(native_context()->fast_aliased_arguments_map());
      Map::EnsureDescriptorSlack(map, 1);
      map->AppendDescriptor(&d);
    }
    {
4863 4864
      Descriptor d = Descriptor::AccessorConstant(factory()->iterator_symbol(),
                                                  arguments_iterator, attribs);
4865
      Handle<Map> map(native_context()->slow_aliased_arguments_map());
4866 4867 4868 4869
      Map::EnsureDescriptorSlack(map, 1);
      map->AppendDescriptor(&d);
    }
    {
4870 4871
      Descriptor d = Descriptor::AccessorConstant(factory()->iterator_symbol(),
                                                  arguments_iterator, attribs);
4872 4873 4874 4875 4876 4877
      Handle<Map> map(native_context()->strict_arguments_map());
      Map::EnsureDescriptorSlack(map, 1);
      map->AppendDescriptor(&d);
    }
  }

4878 4879 4880
  return true;
}

4881
bool Genesis::InstallExtraNatives() {
4882 4883 4884 4885 4886 4887
  HandleScope scope(isolate());

  Handle<JSObject> extras_binding =
      factory()->NewJSObject(isolate()->object_function());
  native_context()->set_extras_binding_object(*extras_binding);

4888 4889
  for (int i = ExtraNatives::GetDebuggerCount();
       i < ExtraNatives::GetBuiltinsCount(); i++) {
4890 4891 4892 4893 4894 4895 4896
    if (!Bootstrapper::CompileExtraBuiltin(isolate(), i)) return false;
  }

  return true;
}


4897 4898 4899 4900 4901 4902 4903 4904 4905 4906 4907
bool Genesis::InstallExperimentalExtraNatives() {
  for (int i = ExperimentalExtraNatives::GetDebuggerCount();
       i < ExperimentalExtraNatives::GetBuiltinsCount(); i++) {
    if (!Bootstrapper::CompileExperimentalExtraBuiltin(isolate(), i))
      return false;
  }

  return true;
}


4908 4909 4910 4911
bool Genesis::InstallDebuggerNatives() {
  for (int i = 0; i < Natives::GetDebuggerCount(); ++i) {
    if (!Bootstrapper::CompileBuiltin(isolate(), i)) return false;
  }
4912
  return true;
4913 4914 4915
}


4916 4917 4918
static void InstallBuiltinFunctionId(Handle<JSObject> holder,
                                     const char* function_name,
                                     BuiltinFunctionId id) {
4919
  Isolate* isolate = holder->GetIsolate();
4920
  Handle<Object> function_object =
4921
      JSReceiver::GetProperty(isolate, holder, function_name).ToHandleChecked();
4922
  Handle<JSFunction> function = Handle<JSFunction>::cast(function_object);
4923
  function->shared()->set_builtin_function_id(id);
4924 4925 4926
}


binji's avatar
binji committed
4927 4928 4929 4930 4931
#define INSTALL_BUILTIN_ID(holder_expr, fun_name, name) \
  { #holder_expr, #fun_name, k##name }                  \
  ,


4932
void Genesis::InstallBuiltinFunctionIds() {
4933
  HandleScope scope(isolate());
4934 4935 4936 4937 4938 4939 4940 4941 4942 4943 4944 4945 4946 4947
  struct BuiltinFunctionIds {
    const char* holder_expr;
    const char* fun_name;
    BuiltinFunctionId id;
  };

  const BuiltinFunctionIds builtins[] = {
      FUNCTIONS_WITH_ID_LIST(INSTALL_BUILTIN_ID)};

  for (const BuiltinFunctionIds& builtin : builtins) {
    Handle<JSObject> holder =
        ResolveBuiltinIdHolder(native_context(), builtin.holder_expr);
    InstallBuiltinFunctionId(holder, builtin.fun_name, builtin.id);
  }
4948 4949
}

binji's avatar
binji committed
4950 4951 4952
#undef INSTALL_BUILTIN_ID


4953
void Genesis::InitializeNormalizedMapCaches() {
4954 4955
  Handle<NormalizedMapCache> cache = NormalizedMapCache::New(isolate());
  native_context()->set_normalized_map_cache(*cache);
4956 4957 4958
}


4959
bool Bootstrapper::InstallExtensions(Handle<Context> native_context,
4960
                                     v8::ExtensionConfiguration* extensions) {
4961 4962 4963
  BootstrapperActive active(this);
  SaveContext saved_context(isolate_);
  isolate_->set_context(*native_context);
4964 4965
  return Genesis::InstallExtensions(native_context, extensions) &&
      Genesis::InstallSpecialObjects(native_context);
4966 4967 4968
}


4969
bool Genesis::InstallSpecialObjects(Handle<Context> native_context) {
4970
  Isolate* isolate = native_context->GetIsolate();
4971 4972 4973
  // Don't install extensions into the snapshot.
  if (isolate->serializer_enabled()) return true;

4974
  Factory* factory = isolate->factory();
4975
  HandleScope scope(isolate);
4976

4977
  Handle<JSObject> Error = isolate->error_function();
4978
  Handle<String> name =
4979
      factory->InternalizeOneByteString(STATIC_CHAR_VECTOR("stackTraceLimit"));
4980 4981 4982
  Handle<Smi> stack_trace_limit(Smi::FromInt(FLAG_stack_trace_limit), isolate);
  JSObject::AddProperty(Error, name, stack_trace_limit, NONE);

4983 4984 4985 4986 4987 4988 4989 4990
  if (FLAG_expose_wasm) {
    // Install the internal data structures into the isolate and expose on
    // the global object.
    WasmJs::Install(isolate, true);
  } else if (FLAG_validate_asm) {
    // Install the internal data structures only; these are needed for asm.js
    // translated to WASM to work correctly.
    WasmJs::Install(isolate, false);
4991
  }
4992

4993
  return true;
4994 4995
}

4996

4997 4998 4999 5000
static uint32_t Hash(RegisteredExtension* extension) {
  return v8::internal::ComputePointerHash(extension);
}

5001
Genesis::ExtensionStates::ExtensionStates() : map_(8) {}
5002 5003 5004

Genesis::ExtensionTraversalState Genesis::ExtensionStates::get_state(
    RegisteredExtension* extension) {
lpy's avatar
lpy committed
5005
  base::HashMap::Entry* entry = map_.Lookup(extension, Hash(extension));
5006
  if (entry == nullptr) {
5007 5008 5009 5010 5011 5012 5013 5014
    return UNVISITED;
  }
  return static_cast<ExtensionTraversalState>(
      reinterpret_cast<intptr_t>(entry->value));
}

void Genesis::ExtensionStates::set_state(RegisteredExtension* extension,
                                         ExtensionTraversalState state) {
5015
  map_.LookupOrInsert(extension, Hash(extension))->value =
5016 5017
      reinterpret_cast<void*>(static_cast<intptr_t>(state));
}
5018

5019

5020
bool Genesis::InstallExtensions(Handle<Context> native_context,
5021
                                v8::ExtensionConfiguration* extensions) {
5022
  Isolate* isolate = native_context->GetIsolate();
5023
  ExtensionStates extension_states;  // All extensions have state UNVISITED.
5024
  return InstallAutoExtensions(isolate, &extension_states) &&
5025 5026 5027 5028 5029 5030
         (!FLAG_expose_free_buffer ||
          InstallExtension(isolate, "v8/free-buffer", &extension_states)) &&
         (!FLAG_expose_gc ||
          InstallExtension(isolate, "v8/gc", &extension_states)) &&
         (!FLAG_expose_externalize_string ||
          InstallExtension(isolate, "v8/externalize", &extension_states)) &&
5031
         (!FLAG_gc_stats ||
5032 5033 5034
          InstallExtension(isolate, "v8/statistics", &extension_states)) &&
         (!FLAG_expose_trigger_failure ||
          InstallExtension(isolate, "v8/trigger-failure", &extension_states)) &&
5035
         (!FLAG_trace_ignition_dispatches ||
5036 5037 5038
          InstallExtension(isolate, "v8/ignition-statistics",
                           &extension_states)) &&
         InstallRequestedExtensions(isolate, extensions, &extension_states);
5039
}
5040

5041 5042 5043 5044

bool Genesis::InstallAutoExtensions(Isolate* isolate,
                                    ExtensionStates* extension_states) {
  for (v8::RegisteredExtension* it = v8::RegisteredExtension::first_extension();
5045
       it != nullptr; it = it->next()) {
5046 5047 5048 5049
    if (it->extension()->auto_enable() &&
        !InstallExtension(isolate, it, extension_states)) {
      return false;
    }
5050
  }
5051 5052 5053
  return true;
}

5054

5055 5056 5057
bool Genesis::InstallRequestedExtensions(Isolate* isolate,
                                         v8::ExtensionConfiguration* extensions,
                                         ExtensionStates* extension_states) {
5058
  for (const char** it = extensions->begin(); it != extensions->end(); ++it) {
5059
    if (!InstallExtension(isolate, *it, extension_states)) return false;
5060 5061 5062 5063 5064 5065 5066
  }
  return true;
}


// Installs a named extension.  This methods is unoptimized and does
// not scale well if we want to support a large number of extensions.
5067 5068
bool Genesis::InstallExtension(Isolate* isolate,
                               const char* name,
5069
                               ExtensionStates* extension_states) {
5070
  for (v8::RegisteredExtension* it = v8::RegisteredExtension::first_extension();
5071
       it != nullptr; it = it->next()) {
5072 5073 5074
    if (strcmp(name, it->extension()->name()) == 0) {
      return InstallExtension(isolate, it, extension_states);
    }
5075
  }
5076 5077 5078
  return Utils::ApiCheck(false,
                         "v8::Context::New()",
                         "Cannot find required extension");
5079 5080 5081
}


5082 5083
bool Genesis::InstallExtension(Isolate* isolate,
                               v8::RegisteredExtension* current,
5084
                               ExtensionStates* extension_states) {
5085
  HandleScope scope(isolate);
5086

5087
  if (extension_states->get_state(current) == INSTALLED) return true;
5088 5089
  // The current node has already been visited so there must be a
  // cycle in the dependency graph; fail.
5090 5091 5092
  if (!Utils::ApiCheck(extension_states->get_state(current) != VISITED,
                       "v8::Context::New()",
                       "Circular extension dependency")) {
5093 5094
    return false;
  }
5095
  DCHECK(extension_states->get_state(current) == UNVISITED);
5096
  extension_states->set_state(current, VISITED);
5097 5098 5099
  v8::Extension* extension = current->extension();
  // Install the extension's dependencies
  for (int i = 0; i < extension->dependency_count(); i++) {
5100 5101 5102
    if (!InstallExtension(isolate,
                          extension->dependencies()[i],
                          extension_states)) {
5103
      return false;
5104
    }
5105
  }
5106
  // We do not expect this to throw an exception. Change this if it does.
5107
  bool result = CompileExtension(isolate, extension);
5108
  DCHECK(isolate->has_pending_exception() != result);
5109
  if (!result) {
5110 5111 5112 5113
    // We print out the name of the extension that fail to install.
    // When an error is thrown during bootstrapping we automatically print
    // the line number at which this happened to the console in the isolate
    // error throwing functionality.
5114 5115
    base::OS::PrintError("Error installing extension '%s'.\n",
                         current->extension()->name());
5116
    isolate->clear_pending_exception();
5117
  }
5118
  extension_states->set_state(current, INSTALLED);
5119 5120 5121 5122
  return result;
}


5123
bool Genesis::ConfigureGlobalObjects(
5124
    v8::Local<v8::ObjectTemplate> global_proxy_template) {
5125
  Handle<JSObject> global_proxy(
5126
      JSObject::cast(native_context()->global_proxy()));
5127
  Handle<JSObject> global_object(
5128
      JSObject::cast(native_context()->global_object()));
5129 5130

  if (!global_proxy_template.IsEmpty()) {
feng@chromium.org's avatar
feng@chromium.org committed
5131
    // Configure the global proxy object.
5132
    Handle<ObjectTemplateInfo> global_proxy_data =
5133
        v8::Utils::OpenHandle(*global_proxy_template);
5134
    if (!ConfigureApiObject(global_proxy, global_proxy_data)) return false;
5135

5136
    // Configure the global object.
5137
    Handle<FunctionTemplateInfo> proxy_constructor(
5138
        FunctionTemplateInfo::cast(global_proxy_data->constructor()));
5139
    if (!proxy_constructor->prototype_template()->IsUndefined(isolate())) {
5140
      Handle<ObjectTemplateInfo> global_object_data(
5141
          ObjectTemplateInfo::cast(proxy_constructor->prototype_template()));
5142
      if (!ConfigureApiObject(global_object, global_object_data)) return false;
5143 5144
    }
  }
5145

5146
  JSObject::ForceSetPrototype(global_proxy, global_object);
5147

5148 5149
  native_context()->set_array_buffer_map(
      native_context()->array_buffer_fun()->initial_map());
5150 5151 5152 5153 5154 5155 5156 5157 5158 5159 5160 5161 5162 5163 5164 5165

  Handle<JSFunction> js_map_fun(native_context()->js_map_fun());
  Handle<JSFunction> js_set_fun(native_context()->js_set_fun());
  // Force the Map/Set constructor to fast properties, so that we can use the
  // fast paths for various things like
  //
  //   x instanceof Map
  //   x instanceof Set
  //
  // etc. We should probably come up with a more principled approach once
  // the JavaScript builtins are gone.
  JSObject::MigrateSlowToFast(js_map_fun, 0, "Bootstrapping");
  JSObject::MigrateSlowToFast(js_set_fun, 0, "Bootstrapping");

  native_context()->set_js_map_map(js_map_fun->initial_map());
  native_context()->set_js_set_map(js_set_fun->initial_map());
5166

5167 5168 5169
  return true;
}

feng@chromium.org's avatar
feng@chromium.org committed
5170

5171
bool Genesis::ConfigureApiObject(Handle<JSObject> object,
5172
                                 Handle<ObjectTemplateInfo> object_template) {
5173 5174
  DCHECK(!object_template.is_null());
  DCHECK(FunctionTemplateInfo::cast(object_template->constructor())
5175
             ->IsTemplateFor(object->map()));;
5176

5177
  MaybeHandle<JSObject> maybe_obj =
5178
      ApiNatives::InstantiateObject(object_template);
5179 5180
  Handle<JSObject> obj;
  if (!maybe_obj.ToHandle(&obj)) {
5181
    DCHECK(isolate()->has_pending_exception());
5182
    isolate()->clear_pending_exception();
5183 5184 5185
    return false;
  }
  TransferObject(obj, object);
5186 5187 5188 5189 5190 5191
  return true;
}


void Genesis::TransferNamedProperties(Handle<JSObject> from,
                                      Handle<JSObject> to) {
5192 5193 5194 5195 5196
  // If JSObject::AddProperty asserts due to already existing property,
  // it is likely due to both global objects sharing property name(s).
  // Merging those two global objects is impossible.
  // The global template must not create properties that already exist
  // in the snapshotted global object.
5197 5198 5199
  if (from->HasFastProperties()) {
    Handle<DescriptorArray> descs =
        Handle<DescriptorArray>(from->map()->instance_descriptors());
5200
    for (int i = 0; i < from->map()->NumberOfOwnDescriptors(); i++) {
5201
      PropertyDetails details = descs->GetDetails(i);
5202 5203
      if (details.location() == kField) {
        if (details.kind() == kData) {
5204
          HandleScope inner(isolate());
5205
          Handle<Name> key = Handle<Name>(descs->GetKey(i));
5206
          FieldIndex index = FieldIndex::ForDescriptor(from->map(), i);
5207 5208
          Handle<Object> value =
              JSObject::FastPropertyAt(from, details.representation(), index);
5209
          JSObject::AddProperty(to, key, value, details.attributes());
5210 5211 5212
        } else {
          DCHECK_EQ(kAccessor, details.kind());
          UNREACHABLE();
5213
        }
5214 5215 5216 5217

      } else {
        DCHECK_EQ(kDescriptor, details.location());
        if (details.kind() == kData) {
5218
          DCHECK(!FLAG_track_constant_fields);
5219
          HandleScope inner(isolate());
5220
          Handle<Name> key = Handle<Name>(descs->GetKey(i));
5221 5222
          Handle<Object> value(descs->GetValue(i), isolate());
          JSObject::AddProperty(to, key, value, details.attributes());
5223 5224 5225

        } else {
          DCHECK_EQ(kAccessor, details.kind());
5226
          Handle<Name> key(descs->GetKey(i));
5227 5228
          LookupIterator it(to, key, LookupIterator::OWN_SKIP_INTERCEPTOR);
          CHECK_NE(LookupIterator::ACCESS_CHECK, it.state());
5229
          // If the property is already there we skip it
5230
          if (it.IsFound()) continue;
5231
          HandleScope inner(isolate());
5232
          DCHECK(!to->HasFastProperties());
5233
          // Add to dictionary.
5234
          Handle<Object> value(descs->GetValue(i), isolate());
5235
          PropertyDetails d(kAccessor, details.attributes(),
5236
                            PropertyCellType::kMutable);
5237
          JSObject::SetNormalizedProperty(to, key, value, d);
5238 5239 5240
        }
      }
    }
5241
  } else if (from->IsJSGlobalObject()) {
5242
    // Copy all keys and values in enumeration order.
5243 5244
    Handle<GlobalDictionary> properties(
        JSGlobalObject::cast(*from)->global_dictionary());
5245 5246
    Handle<FixedArray> indices = GlobalDictionary::IterationIndices(properties);
    for (int i = 0; i < indices->length(); i++) {
jgruber's avatar
jgruber committed
5247
      int index = Smi::ToInt(indices->get(i));
5248
      // If the property is already there we skip it.
5249 5250
      Handle<PropertyCell> cell(properties->CellAt(index));
      Handle<Name> key(cell->name(), isolate());
5251 5252 5253 5254 5255 5256 5257
      LookupIterator it(to, key, LookupIterator::OWN_SKIP_INTERCEPTOR);
      CHECK_NE(LookupIterator::ACCESS_CHECK, it.state());
      if (it.IsFound()) continue;
      // Set the property.
      Handle<Object> value(cell->value(), isolate());
      if (value->IsTheHole(isolate())) continue;
      PropertyDetails details = cell->property_details();
5258
      if (details.kind() != kData) continue;
5259
      JSObject::AddProperty(to, key, value, details.attributes());
5260
    }
5261
  } else {
5262
    // Copy all keys and values in enumeration order.
5263 5264
    Handle<NameDictionary> properties =
        Handle<NameDictionary>(from->property_dictionary());
5265 5266 5267
    Handle<FixedArray> key_indices =
        NameDictionary::IterationIndices(properties);
    for (int i = 0; i < key_indices->length(); i++) {
jgruber's avatar
jgruber committed
5268
      int key_index = Smi::ToInt(key_indices->get(i));
5269 5270 5271 5272 5273 5274 5275 5276 5277 5278 5279 5280 5281 5282 5283 5284
      Object* raw_key = properties->KeyAt(key_index);
      DCHECK(properties->IsKey(isolate(), raw_key));
      DCHECK(raw_key->IsName());
      // If the property is already there we skip it.
      Handle<Name> key(Name::cast(raw_key), isolate());
      LookupIterator it(to, key, LookupIterator::OWN_SKIP_INTERCEPTOR);
      CHECK_NE(LookupIterator::ACCESS_CHECK, it.state());
      if (it.IsFound()) continue;
      // Set the property.
      Handle<Object> value =
          Handle<Object>(properties->ValueAt(key_index), isolate());
      DCHECK(!value->IsCell());
      DCHECK(!value->IsTheHole(isolate()));
      PropertyDetails details = properties->DetailsAt(key_index);
      DCHECK_EQ(kData, details.kind());
      JSObject::AddProperty(to, key, value, details.attributes());
5285 5286 5287 5288 5289 5290 5291 5292 5293 5294
    }
  }
}


void Genesis::TransferIndexedProperties(Handle<JSObject> from,
                                        Handle<JSObject> to) {
  // Cloning the elements array is sufficient.
  Handle<FixedArray> from_elements =
      Handle<FixedArray>(FixedArray::cast(from->elements()));
5295
  Handle<FixedArray> to_elements = factory()->CopyFixedArray(from_elements);
5296 5297 5298 5299 5300
  to->set_elements(*to_elements);
}


void Genesis::TransferObject(Handle<JSObject> from, Handle<JSObject> to) {
5301
  HandleScope outer(isolate());
5302

5303 5304
  DCHECK(!from->IsJSArray());
  DCHECK(!to->IsJSArray());
5305 5306 5307 5308 5309

  TransferNamedProperties(from, to);
  TransferIndexedProperties(from, to);

  // Transfer the prototype (new map is needed).
5310
  Handle<Object> proto(from->map()->prototype(), isolate());
5311
  JSObject::ForceSetPrototype(to, proto);
5312 5313
}

5314

5315 5316 5317 5318
Genesis::Genesis(
    Isolate* isolate, MaybeHandle<JSGlobalProxy> maybe_global_proxy,
    v8::Local<v8::ObjectTemplate> global_proxy_template,
    size_t context_snapshot_index,
5319
    v8::DeserializeEmbedderFieldsCallback embedder_fields_deserializer,
5320
    GlobalContextType context_type)
5321
    : isolate_(isolate), active_(isolate->bootstrapper()) {
5322
  result_ = Handle<Context>::null();
5323 5324
  global_proxy_ = Handle<JSGlobalProxy>::null();

5325 5326
  // Before creating the roots we must save the context and restore it
  // on all function exits.
5327
  SaveContext saved_context(isolate);
5328

5329 5330 5331
  // During genesis, the boilerplate for stack overflow won't work until the
  // environment has been at least partially initialized. Add a stack check
  // before entering JS code to catch overflow early.
5332
  StackLimitCheck check(isolate);
5333 5334 5335 5336
  if (check.HasOverflowed()) {
    isolate->StackOverflow();
    return;
  }
5337

5338 5339 5340 5341
  // The deserializer needs to hook up references to the global proxy.
  // Create an uninitialized global proxy now if we don't have one
  // and initialize it later in CreateNewGlobals.
  Handle<JSGlobalProxy> global_proxy;
5342
  if (!maybe_global_proxy.ToHandle(&global_proxy)) {
5343 5344 5345 5346 5347 5348 5349
    int instance_size = 0;
    if (context_snapshot_index > 0) {
      // The global proxy function to reinitialize this global proxy is in the
      // context that is yet to be deserialized. We need to prepare a global
      // proxy of the correct size.
      Object* size = isolate->heap()->serialized_global_proxy_sizes()->get(
          static_cast<int>(context_snapshot_index) - 1);
jgruber's avatar
jgruber committed
5350
      instance_size = Smi::ToInt(size);
5351
    } else {
5352
      instance_size = JSGlobalProxy::SizeWithEmbedderFields(
5353 5354 5355 5356 5357 5358
          global_proxy_template.IsEmpty()
              ? 0
              : global_proxy_template->InternalFieldCount());
    }
    global_proxy =
        isolate->factory()->NewUninitializedJSGlobalProxy(instance_size);
5359 5360
  }

5361 5362
  // We can only de-serialize a context if the isolate was initialized from
  // a snapshot. Otherwise we have to build the context from scratch.
5363
  // Also create a context from scratch to expose natives, if required by flag.
5364
  if (!isolate->initialized_from_snapshot() ||
5365
      !Snapshot::NewContextFromSnapshot(isolate, global_proxy,
5366
                                        context_snapshot_index,
5367
                                        embedder_fields_deserializer)
5368
           .ToHandle(&native_context_)) {
5369 5370 5371
    native_context_ = Handle<Context>();
  }

5372 5373 5374
  if (!native_context().is_null()) {
    AddToWeakNativeContextList(*native_context());
    isolate->set_context(*native_context());
5375
    isolate->counters()->contexts_created_by_snapshot()->Increment();
5376 5377 5378 5379 5380 5381 5382 5383 5384
    if (FLAG_trace_maps) {
      DisallowHeapAllocation no_gc;
      Handle<JSFunction> object_fun = isolate->object_function();
      Map* initial_map = object_fun->initial_map();
      LOG(isolate, MapDetails(initial_map));
      LOG(isolate, MapEvent("InitialMap", nullptr, initial_map, "Object",
                            object_fun->shared()));
      LOG(isolate, LogAllTransitions(initial_map));
    }
5385

5386
    if (context_snapshot_index == 0) {
5387 5388 5389 5390 5391
      Handle<JSGlobalObject> global_object =
          CreateNewGlobals(global_proxy_template, global_proxy);
      HookUpGlobalObject(global_object);

      if (!ConfigureGlobalObjects(global_proxy_template)) return;
5392 5393 5394
    } else {
      // The global proxy needs to be integrated into the native context.
      HookUpGlobalProxy(global_proxy);
5395
    }
5396
    DCHECK(!global_proxy->IsDetachedFrom(native_context()->global_object()));
5397
  } else {
5398 5399
    base::ElapsedTimer timer;
    if (FLAG_profile_deserialization) timer.Start();
5400
    DCHECK_EQ(0u, context_snapshot_index);
5401 5402
    // We get here if there was no context snapshot.
    CreateRoots();
5403
    Handle<JSFunction> empty_function = CreateEmptyFunction(isolate);
5404
    CreateSloppyModeFunctionMaps(empty_function);
5405
    CreateStrictModeFunctionMaps(empty_function);
5406
    CreateObjectFunction(empty_function);
5407
    CreateIteratorMaps(empty_function);
5408
    CreateAsyncIteratorMaps(empty_function);
5409
    CreateAsyncFunctionMaps(empty_function);
5410
    Handle<JSGlobalObject> global_object =
5411
        CreateNewGlobals(global_proxy_template, global_proxy);
5412
    InitializeGlobal(global_object, empty_function, context_type);
5413
    InitializeNormalizedMapCaches();
5414 5415

    if (!InstallNatives(context_type)) return;
5416 5417 5418
    if (!InstallExtraNatives()) return;
    if (!ConfigureGlobalObjects(global_proxy_template)) return;

5419
    isolate->counters()->contexts_created_from_scratch()->Increment();
5420 5421 5422 5423 5424

    if (FLAG_profile_deserialization) {
      double ms = timer.Elapsed().InMillisecondsF();
      i::PrintF("[Initializing context from scratch took %0.3f ms]\n", ms);
    }
5425
  }
5426

5427
  // Install experimental natives. Do not include them into the
5428 5429
  // snapshot as we should be able to turn them off at runtime. Re-installing
  // them after they have already been deserialized would also fail.
5430 5431 5432
  if (context_type == FULL_CONTEXT) {
    if (!isolate->serializer_enabled()) {
      InitializeExperimentalGlobal();
5433 5434 5435 5436

      if (FLAG_experimental_extras) {
        if (!InstallExperimentalExtraNatives()) return;
      }
5437 5438 5439 5440 5441 5442 5443 5444 5445

      // Store String.prototype's map again in case it has been changed by
      // experimental natives.
      Handle<JSFunction> string_function(native_context()->string_function());
      JSObject* string_function_prototype =
          JSObject::cast(string_function->initial_map()->prototype());
      DCHECK(string_function_prototype->HasFastProperties());
      native_context()->set_string_function_prototype_map(
          string_function_prototype->map());
5446
    }
5447 5448 5449 5450
  } else if (context_type == DEBUG_CONTEXT) {
    DCHECK(!isolate->serializer_enabled());
    InitializeExperimentalGlobal();
    if (!InstallDebuggerNatives()) return;
5451
  }
5452

5453 5454
  ConfigureUtilsObject(context_type);

5455 5456
  // Check that the script context table is empty except for the 'this' binding.
  // We do not need script contexts for native scripts.
5457
  DCHECK_EQ(1, native_context()->script_context_table()->used());
5458

5459
  native_context()->ResetErrorsThrown();
5460
  result_ = native_context();
5461 5462
}

5463 5464 5465 5466 5467 5468 5469 5470 5471 5472 5473 5474 5475 5476 5477 5478 5479 5480 5481 5482
Genesis::Genesis(Isolate* isolate,
                 MaybeHandle<JSGlobalProxy> maybe_global_proxy,
                 v8::Local<v8::ObjectTemplate> global_proxy_template)
    : isolate_(isolate), active_(isolate->bootstrapper()) {
  result_ = Handle<Context>::null();
  global_proxy_ = Handle<JSGlobalProxy>::null();

  // Before creating the roots we must save the context and restore it
  // on all function exits.
  SaveContext saved_context(isolate);

  // During genesis, the boilerplate for stack overflow won't work until the
  // environment has been at least partially initialized. Add a stack check
  // before entering JS code to catch overflow early.
  StackLimitCheck check(isolate);
  if (check.HasOverflowed()) {
    isolate->StackOverflow();
    return;
  }

5483
  const int proxy_size = JSGlobalProxy::SizeWithEmbedderFields(
5484 5485
      global_proxy_template->InternalFieldCount());

5486 5487
  Handle<JSGlobalProxy> global_proxy;
  if (!maybe_global_proxy.ToHandle(&global_proxy)) {
5488
    global_proxy = factory()->NewUninitializedJSGlobalProxy(proxy_size);
5489 5490
  }

5491
  // Create a remote object as the global object.
5492
  Handle<ObjectTemplateInfo> global_proxy_data =
5493
      Utils::OpenHandle(*global_proxy_template);
5494 5495
  Handle<FunctionTemplateInfo> global_constructor(
      FunctionTemplateInfo::cast(global_proxy_data->constructor()));
5496 5497 5498 5499 5500 5501 5502 5503

  Handle<ObjectTemplateInfo> global_object_template(
      ObjectTemplateInfo::cast(global_constructor->prototype_template()));
  Handle<JSObject> global_object =
      ApiNatives::InstantiateRemoteObject(
          global_object_template).ToHandleChecked();

  // (Re)initialize the global proxy object.
5504
  DCHECK_EQ(global_proxy_data->embedder_field_count(),
5505
            global_proxy_template->InternalFieldCount());
5506
  Handle<Map> global_proxy_map = isolate->factory()->NewMap(
5507
      JS_GLOBAL_PROXY_TYPE, proxy_size, HOLEY_SMI_ELEMENTS);
5508 5509
  global_proxy_map->set_is_access_check_needed(true);
  global_proxy_map->set_has_hidden_prototype(true);
5510
  global_proxy_map->set_may_have_interesting_symbols(true);
5511

5512
  // A remote global proxy has no native context.
5513
  global_proxy->set_native_context(heap()->null_value());
5514

5515 5516
  // Configure the hidden prototype chain of the global proxy.
  JSObject::ForceSetPrototype(global_proxy, global_object);
5517
  global_proxy->map()->SetConstructor(*global_constructor);
5518 5519 5520
  // TODO(dcheng): This is a hack. Why does this need to be manually called
  // here? Line 4812 should have taken care of it?
  global_proxy->map()->set_has_hidden_prototype(true);
5521 5522 5523

  global_proxy_ = global_proxy;
}
5524 5525 5526 5527 5528

// Support for thread preemption.

// Reserve space for statics needing saving and restoring.
int Bootstrapper::ArchiveSpacePerThread() {
5529
  return sizeof(NestingCounterType);
5530 5531 5532
}


5533
// Archive statics that are thread-local.
5534
char* Bootstrapper::ArchiveState(char* to) {
5535 5536 5537
  *reinterpret_cast<NestingCounterType*>(to) = nesting_;
  nesting_ = 0;
  return to + sizeof(NestingCounterType);
5538 5539 5540
}


5541
// Restore statics that are thread-local.
5542
char* Bootstrapper::RestoreState(char* from) {
5543 5544
  nesting_ = *reinterpret_cast<NestingCounterType*>(from);
  return from + sizeof(NestingCounterType);
5545 5546 5547
}


5548 5549
// Called when the top-level V8 mutex is destroyed.
void Bootstrapper::FreeThreadResources() {
5550
  DCHECK(!IsActive());
5551 5552
}

5553 5554
}  // namespace internal
}  // namespace v8