The data contained in this repository can be downloaded to your computer using one of several clients.
Please see the documentation of your version control software client for more information.

Please select the desired protocol below to get the URL.

This URL has Read-Only access.

Statistics
| Branch: | Revision:

main_repo / deps / v8 / src / bootstrapper.cc @ f230a1cf

History | View | Annotate | Download (106 KB)

1
// Copyright 2012 the V8 project authors. All rights reserved.
2
// Redistribution and use in source and binary forms, with or without
3
// modification, are permitted provided that the following conditions are
4
// met:
5
//
6
//     * Redistributions of source code must retain the above copyright
7
//       notice, this list of conditions and the following disclaimer.
8
//     * Redistributions in binary form must reproduce the above
9
//       copyright notice, this list of conditions and the following
10
//       disclaimer in the documentation and/or other materials provided
11
//       with the distribution.
12
//     * Neither the name of Google Inc. nor the names of its
13
//       contributors may be used to endorse or promote products derived
14
//       from this software without specific prior written permission.
15
//
16
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
17
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
18
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
19
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
20
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27

    
28
#include "v8.h"
29

    
30
#include "accessors.h"
31
#include "api.h"
32
#include "bootstrapper.h"
33
#include "compiler.h"
34
#include "debug.h"
35
#include "execution.h"
36
#include "global-handles.h"
37
#include "isolate-inl.h"
38
#include "macro-assembler.h"
39
#include "natives.h"
40
#include "objects-visiting.h"
41
#include "platform.h"
42
#include "snapshot.h"
43
#include "extensions/externalize-string-extension.h"
44
#include "extensions/gc-extension.h"
45
#include "extensions/statistics-extension.h"
46
#include "code-stubs.h"
47

    
48
namespace v8 {
49
namespace internal {
50

    
51

    
52
NativesExternalStringResource::NativesExternalStringResource(
53
    Bootstrapper* bootstrapper,
54
    const char* source,
55
    size_t length)
56
    : data_(source), length_(length) {
57
  if (bootstrapper->delete_these_non_arrays_on_tear_down_ == NULL) {
58
    bootstrapper->delete_these_non_arrays_on_tear_down_ = new List<char*>(2);
59
  }
60
  // The resources are small objects and we only make a fixed number of
61
  // them, but let's clean them up on exit for neatness.
62
  bootstrapper->delete_these_non_arrays_on_tear_down_->
63
      Add(reinterpret_cast<char*>(this));
64
}
65

    
66

    
67
Bootstrapper::Bootstrapper(Isolate* isolate)
68
    : isolate_(isolate),
69
      nesting_(0),
70
      extensions_cache_(Script::TYPE_EXTENSION),
71
      delete_these_non_arrays_on_tear_down_(NULL),
72
      delete_these_arrays_on_tear_down_(NULL) {
73
}
74

    
75

    
76
Handle<String> Bootstrapper::NativesSourceLookup(int index) {
77
  ASSERT(0 <= index && index < Natives::GetBuiltinsCount());
78
  Heap* heap = isolate_->heap();
79
  if (heap->natives_source_cache()->get(index)->IsUndefined()) {
80
    // We can use external strings for the natives.
81
    Vector<const char> source = Natives::GetRawScriptSource(index);
82
    NativesExternalStringResource* resource =
83
        new NativesExternalStringResource(this,
84
                                          source.start(),
85
                                          source.length());
86
    Handle<String> source_code =
87
        isolate_->factory()->NewExternalStringFromAscii(resource);
88
    heap->natives_source_cache()->set(index, *source_code);
89
  }
90
  Handle<Object> cached_source(heap->natives_source_cache()->get(index),
91
                               isolate_);
92
  return Handle<String>::cast(cached_source);
93
}
94

    
95

    
96
void Bootstrapper::Initialize(bool create_heap_objects) {
97
  extensions_cache_.Initialize(isolate_, create_heap_objects);
98
}
99

    
100

    
101
void Bootstrapper::InitializeOncePerProcess() {
102
  GCExtension::Register();
103
  ExternalizeStringExtension::Register();
104
  StatisticsExtension::Register();
105
}
106

    
107

    
108
char* Bootstrapper::AllocateAutoDeletedArray(int bytes) {
109
  char* memory = new char[bytes];
110
  if (memory != NULL) {
111
    if (delete_these_arrays_on_tear_down_ == NULL) {
112
      delete_these_arrays_on_tear_down_ = new List<char*>(2);
113
    }
114
    delete_these_arrays_on_tear_down_->Add(memory);
115
  }
116
  return memory;
117
}
118

    
119

    
120
void Bootstrapper::TearDown() {
121
  if (delete_these_non_arrays_on_tear_down_ != NULL) {
122
    int len = delete_these_non_arrays_on_tear_down_->length();
123
    ASSERT(len < 20);  // Don't use this mechanism for unbounded allocations.
124
    for (int i = 0; i < len; i++) {
125
      delete delete_these_non_arrays_on_tear_down_->at(i);
126
      delete_these_non_arrays_on_tear_down_->at(i) = NULL;
127
    }
128
    delete delete_these_non_arrays_on_tear_down_;
129
    delete_these_non_arrays_on_tear_down_ = NULL;
130
  }
131

    
132
  if (delete_these_arrays_on_tear_down_ != NULL) {
133
    int len = delete_these_arrays_on_tear_down_->length();
134
    ASSERT(len < 1000);  // Don't use this mechanism for unbounded allocations.
135
    for (int i = 0; i < len; i++) {
136
      delete[] delete_these_arrays_on_tear_down_->at(i);
137
      delete_these_arrays_on_tear_down_->at(i) = NULL;
138
    }
139
    delete delete_these_arrays_on_tear_down_;
140
    delete_these_arrays_on_tear_down_ = NULL;
141
  }
142

    
143
  extensions_cache_.Initialize(isolate_, false);  // Yes, symmetrical
144
}
145

    
146

    
147
class Genesis BASE_EMBEDDED {
148
 public:
149
  Genesis(Isolate* isolate,
150
          Handle<Object> global_object,
151
          v8::Handle<v8::ObjectTemplate> global_template,
152
          v8::ExtensionConfiguration* extensions);
153
  ~Genesis() { }
154

    
155
  Isolate* isolate() const { return isolate_; }
156
  Factory* factory() const { return isolate_->factory(); }
157
  Heap* heap() const { return isolate_->heap(); }
158

    
159
  Handle<Context> result() { return result_; }
160

    
161
 private:
162
  Handle<Context> native_context() { return native_context_; }
163

    
164
  // Creates some basic objects. Used for creating a context from scratch.
165
  void CreateRoots();
166
  // Creates the empty function.  Used for creating a context from scratch.
167
  Handle<JSFunction> CreateEmptyFunction(Isolate* isolate);
168
  // Creates the ThrowTypeError function. ECMA 5th Ed. 13.2.3
169
  Handle<JSFunction> GetThrowTypeErrorFunction();
170

    
171
  void CreateStrictModeFunctionMaps(Handle<JSFunction> empty);
172

    
173
  // Make the "arguments" and "caller" properties throw a TypeError on access.
174
  void PoisonArgumentsAndCaller(Handle<Map> map);
175

    
176
  // Creates the global objects using the global and the template passed in
177
  // through the API.  We call this regardless of whether we are building a
178
  // context from scratch or using a deserialized one from the partial snapshot
179
  // but in the latter case we don't use the objects it produces directly, as
180
  // we have to used the deserialized ones that are linked together with the
181
  // rest of the context snapshot.
182
  Handle<JSGlobalProxy> CreateNewGlobals(
183
      v8::Handle<v8::ObjectTemplate> global_template,
184
      Handle<Object> global_object,
185
      Handle<GlobalObject>* global_proxy_out);
186
  // Hooks the given global proxy into the context.  If the context was created
187
  // by deserialization then this will unhook the global proxy that was
188
  // deserialized, leaving the GC to pick it up.
189
  void HookUpGlobalProxy(Handle<GlobalObject> inner_global,
190
                         Handle<JSGlobalProxy> global_proxy);
191
  // Similarly, we want to use the inner global that has been created by the
192
  // templates passed through the API.  The inner global from the snapshot is
193
  // detached from the other objects in the snapshot.
194
  void HookUpInnerGlobal(Handle<GlobalObject> inner_global);
195
  // New context initialization.  Used for creating a context from scratch.
196
  void InitializeGlobal(Handle<GlobalObject> inner_global,
197
                        Handle<JSFunction> empty_function);
198
  void InitializeExperimentalGlobal();
199
  // Installs the contents of the native .js files on the global objects.
200
  // Used for creating a context from scratch.
201
  void InstallNativeFunctions();
202
  void InstallExperimentalNativeFunctions();
203
  Handle<JSFunction> InstallInternalArray(Handle<JSBuiltinsObject> builtins,
204
                                          const char* name,
205
                                          ElementsKind elements_kind);
206
  bool InstallNatives();
207

    
208
  Handle<JSFunction> InstallTypedArray(const char* name,
209
      ElementsKind elementsKind);
210
  bool InstallExperimentalNatives();
211
  void InstallBuiltinFunctionIds();
212
  void InstallJSFunctionResultCaches();
213
  void InitializeNormalizedMapCaches();
214

    
215
  enum ExtensionTraversalState {
216
    UNVISITED, VISITED, INSTALLED
217
  };
218

    
219
  class ExtensionStates {
220
   public:
221
    ExtensionStates();
222
    ExtensionTraversalState get_state(RegisteredExtension* extension);
223
    void set_state(RegisteredExtension* extension,
224
                   ExtensionTraversalState state);
225
   private:
226
    HashMap map_;
227
    DISALLOW_COPY_AND_ASSIGN(ExtensionStates);
228
  };
229

    
230
  // Used both for deserialized and from-scratch contexts to add the extensions
231
  // provided.
232
  static bool InstallExtensions(Handle<Context> native_context,
233
                                v8::ExtensionConfiguration* extensions);
234
  static bool InstallExtension(Isolate* isolate,
235
                               const char* name,
236
                               ExtensionStates* extension_states);
237
  static bool InstallExtension(Isolate* isolate,
238
                               v8::RegisteredExtension* current,
239
                               ExtensionStates* extension_states);
240
  static void InstallSpecialObjects(Handle<Context> native_context);
241
  bool InstallJSBuiltins(Handle<JSBuiltinsObject> builtins);
242
  bool ConfigureApiObject(Handle<JSObject> object,
243
                          Handle<ObjectTemplateInfo> object_template);
244
  bool ConfigureGlobalObjects(v8::Handle<v8::ObjectTemplate> global_template);
245

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

    
253
  enum PrototypePropertyMode {
254
    DONT_ADD_PROTOTYPE,
255
    ADD_READONLY_PROTOTYPE,
256
    ADD_WRITEABLE_PROTOTYPE
257
  };
258

    
259
  Handle<Map> CreateFunctionMap(PrototypePropertyMode prototype_mode);
260

    
261
  void SetFunctionInstanceDescriptor(Handle<Map> map,
262
                                     PrototypePropertyMode prototypeMode);
263
  void MakeFunctionInstancePrototypeWritable();
264

    
265
  Handle<Map> CreateStrictModeFunctionMap(
266
      PrototypePropertyMode prototype_mode,
267
      Handle<JSFunction> empty_function);
268

    
269
  void SetStrictFunctionInstanceDescriptor(Handle<Map> map,
270
                                           PrototypePropertyMode propertyMode);
271

    
272
  static bool CompileBuiltin(Isolate* isolate, int index);
273
  static bool CompileExperimentalBuiltin(Isolate* isolate, int index);
274
  static bool CompileNative(Isolate* isolate,
275
                            Vector<const char> name,
276
                            Handle<String> source);
277
  static bool CompileScriptCached(Isolate* isolate,
278
                                  Vector<const char> name,
279
                                  Handle<String> source,
280
                                  SourceCodeCache* cache,
281
                                  v8::Extension* extension,
282
                                  Handle<Context> top_context,
283
                                  bool use_runtime_context);
284

    
285
  Isolate* isolate_;
286
  Handle<Context> result_;
287
  Handle<Context> native_context_;
288

    
289
  // Function maps. Function maps are created initially with a read only
290
  // prototype for the processing of JS builtins. Later the function maps are
291
  // replaced in order to make prototype writable. These are the final, writable
292
  // prototype, maps.
293
  Handle<Map> function_map_writable_prototype_;
294
  Handle<Map> strict_mode_function_map_writable_prototype_;
295
  Handle<JSFunction> throw_type_error_function;
296

    
297
  BootstrapperActive active_;
298
  friend class Bootstrapper;
299
};
300

    
301

    
302
void Bootstrapper::Iterate(ObjectVisitor* v) {
303
  extensions_cache_.Iterate(v);
304
  v->Synchronize(VisitorSynchronization::kExtensions);
305
}
306

    
307

    
308
Handle<Context> Bootstrapper::CreateEnvironment(
309
    Handle<Object> global_object,
310
    v8::Handle<v8::ObjectTemplate> global_template,
311
    v8::ExtensionConfiguration* extensions) {
312
  HandleScope scope(isolate_);
313
  Genesis genesis(isolate_, global_object, global_template, extensions);
314
  Handle<Context> env = genesis.result();
315
  if (env.is_null() || !InstallExtensions(env, extensions)) {
316
    return Handle<Context>();
317
  }
318
  return scope.CloseAndEscape(env);
319
}
320

    
321

    
322
static void SetObjectPrototype(Handle<JSObject> object, Handle<Object> proto) {
323
  // object.__proto__ = proto;
324
  Factory* factory = object->GetIsolate()->factory();
325
  Handle<Map> old_to_map = Handle<Map>(object->map());
326
  Handle<Map> new_to_map = factory->CopyMap(old_to_map);
327
  new_to_map->set_prototype(*proto);
328
  object->set_map(*new_to_map);
329
}
330

    
331

    
332
void Bootstrapper::DetachGlobal(Handle<Context> env) {
333
  Factory* factory = env->GetIsolate()->factory();
334
  Handle<JSGlobalProxy> global_proxy(JSGlobalProxy::cast(env->global_proxy()));
335
  global_proxy->set_native_context(*factory->null_value());
336
  SetObjectPrototype(global_proxy, factory->null_value());
337
  env->set_global_proxy(env->global_object());
338
  env->global_object()->set_global_receiver(env->global_object());
339
}
340

    
341

    
342
void Bootstrapper::ReattachGlobal(Handle<Context> env,
343
                                  Handle<JSGlobalProxy> global_proxy) {
344
  env->global_object()->set_global_receiver(*global_proxy);
345
  env->set_global_proxy(*global_proxy);
346
  SetObjectPrototype(global_proxy, Handle<JSObject>(env->global_object()));
347
  global_proxy->set_native_context(*env);
348
}
349

    
350

    
351
static Handle<JSFunction> InstallFunction(Handle<JSObject> target,
352
                                          const char* name,
353
                                          InstanceType type,
354
                                          int instance_size,
355
                                          Handle<JSObject> prototype,
356
                                          Builtins::Name call,
357
                                          bool install_initial_map,
358
                                          bool set_instance_class_name) {
359
  Isolate* isolate = target->GetIsolate();
360
  Factory* factory = isolate->factory();
361
  Handle<String> internalized_name = factory->InternalizeUtf8String(name);
362
  Handle<Code> call_code = Handle<Code>(isolate->builtins()->builtin(call));
363
  Handle<JSFunction> function = prototype.is_null() ?
364
    factory->NewFunctionWithoutPrototype(internalized_name, call_code) :
365
    factory->NewFunctionWithPrototype(internalized_name,
366
                                      type,
367
                                      instance_size,
368
                                      prototype,
369
                                      call_code,
370
                                      install_initial_map);
371
  PropertyAttributes attributes;
372
  if (target->IsJSBuiltinsObject()) {
373
    attributes =
374
        static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY);
375
  } else {
376
    attributes = DONT_ENUM;
377
  }
378
  CHECK_NOT_EMPTY_HANDLE(isolate,
379
                         JSObject::SetLocalPropertyIgnoreAttributes(
380
                             target, internalized_name, function, attributes));
381
  if (set_instance_class_name) {
382
    function->shared()->set_instance_class_name(*internalized_name);
383
  }
384
  function->shared()->set_native(true);
385
  return function;
386
}
387

    
388

    
389
void Genesis::SetFunctionInstanceDescriptor(
390
    Handle<Map> map, PrototypePropertyMode prototypeMode) {
391
  int size = (prototypeMode == DONT_ADD_PROTOTYPE) ? 4 : 5;
392
  Handle<DescriptorArray> descriptors(factory()->NewDescriptorArray(0, size));
393
  DescriptorArray::WhitenessWitness witness(*descriptors);
394

    
395
  Handle<Foreign> length(factory()->NewForeign(&Accessors::FunctionLength));
396
  Handle<Foreign> name(factory()->NewForeign(&Accessors::FunctionName));
397
  Handle<Foreign> args(factory()->NewForeign(&Accessors::FunctionArguments));
398
  Handle<Foreign> caller(factory()->NewForeign(&Accessors::FunctionCaller));
399
  Handle<Foreign> prototype;
400
  if (prototypeMode != DONT_ADD_PROTOTYPE) {
401
    prototype = factory()->NewForeign(&Accessors::FunctionPrototype);
402
  }
403
  PropertyAttributes attribs = static_cast<PropertyAttributes>(
404
      DONT_ENUM | DONT_DELETE | READ_ONLY);
405
  map->set_instance_descriptors(*descriptors);
406

    
407
  {  // Add length.
408
    CallbacksDescriptor d(*factory()->length_string(), *length, attribs);
409
    map->AppendDescriptor(&d, witness);
410
  }
411
  {  // Add name.
412
    CallbacksDescriptor d(*factory()->name_string(), *name, attribs);
413
    map->AppendDescriptor(&d, witness);
414
  }
415
  {  // Add arguments.
416
    CallbacksDescriptor d(*factory()->arguments_string(), *args, attribs);
417
    map->AppendDescriptor(&d, witness);
418
  }
419
  {  // Add caller.
420
    CallbacksDescriptor d(*factory()->caller_string(), *caller, attribs);
421
    map->AppendDescriptor(&d, witness);
422
  }
423
  if (prototypeMode != DONT_ADD_PROTOTYPE) {
424
    // Add prototype.
425
    if (prototypeMode == ADD_WRITEABLE_PROTOTYPE) {
426
      attribs = static_cast<PropertyAttributes>(attribs & ~READ_ONLY);
427
    }
428
    CallbacksDescriptor d(*factory()->prototype_string(), *prototype, attribs);
429
    map->AppendDescriptor(&d, witness);
430
  }
431
}
432

    
433

    
434
Handle<Map> Genesis::CreateFunctionMap(PrototypePropertyMode prototype_mode) {
435
  Handle<Map> map = factory()->NewMap(JS_FUNCTION_TYPE, JSFunction::kSize);
436
  SetFunctionInstanceDescriptor(map, prototype_mode);
437
  map->set_function_with_prototype(prototype_mode != DONT_ADD_PROTOTYPE);
438
  return map;
439
}
440

    
441

    
442
Handle<JSFunction> Genesis::CreateEmptyFunction(Isolate* isolate) {
443
  // Allocate the map for function instances. Maps are allocated first and their
444
  // prototypes patched later, once empty function is created.
445

    
446
  // Functions with this map will not have a 'prototype' property, and
447
  // can not be used as constructors.
448
  Handle<Map> function_without_prototype_map =
449
      CreateFunctionMap(DONT_ADD_PROTOTYPE);
450
  native_context()->set_function_without_prototype_map(
451
      *function_without_prototype_map);
452

    
453
  // Allocate the function map. This map is temporary, used only for processing
454
  // of builtins.
455
  // Later the map is replaced with writable prototype map, allocated below.
456
  Handle<Map> function_map = CreateFunctionMap(ADD_READONLY_PROTOTYPE);
457
  native_context()->set_function_map(*function_map);
458

    
459
  // The final map for functions. Writeable prototype.
460
  // This map is installed in MakeFunctionInstancePrototypeWritable.
461
  function_map_writable_prototype_ = CreateFunctionMap(ADD_WRITEABLE_PROTOTYPE);
462

    
463
  Factory* factory = isolate->factory();
464

    
465
  Handle<String> object_name = factory->Object_string();
466

    
467
  {  // --- O b j e c t ---
468
    Handle<JSFunction> object_fun =
469
        factory->NewFunction(object_name, factory->null_value());
470
    Handle<Map> object_function_map =
471
        factory->NewMap(JS_OBJECT_TYPE, JSObject::kHeaderSize);
472
    object_fun->set_initial_map(*object_function_map);
473
    object_function_map->set_constructor(*object_fun);
474

    
475
    native_context()->set_object_function(*object_fun);
476

    
477
    // Allocate a new prototype for the object function.
478
    Handle<JSObject> prototype = factory->NewJSObject(
479
        isolate->object_function(),
480
        TENURED);
481

    
482
    native_context()->set_initial_object_prototype(*prototype);
483
    // For bootstrapping set the array prototype to be the same as the object
484
    // prototype, otherwise the missing initial_array_prototype will cause
485
    // assertions during startup.
486
    native_context()->set_initial_array_prototype(*prototype);
487
    Accessors::FunctionSetPrototype(object_fun, prototype);
488
  }
489

    
490
  // Allocate the empty function as the prototype for function ECMAScript
491
  // 262 15.3.4.
492
  Handle<String> empty_string =
493
      factory->InternalizeOneByteString(STATIC_ASCII_VECTOR("Empty"));
494
  Handle<JSFunction> empty_function =
495
      factory->NewFunctionWithoutPrototype(empty_string, CLASSIC_MODE);
496

    
497
  // --- E m p t y ---
498
  Handle<Code> code =
499
      Handle<Code>(isolate->builtins()->builtin(
500
          Builtins::kEmptyFunction));
501
  empty_function->set_code(*code);
502
  empty_function->shared()->set_code(*code);
503
  Handle<String> source =
504
      factory->NewStringFromOneByte(STATIC_ASCII_VECTOR("() {}"));
505
  Handle<Script> script = factory->NewScript(source);
506
  script->set_type(Smi::FromInt(Script::TYPE_NATIVE));
507
  empty_function->shared()->set_script(*script);
508
  empty_function->shared()->set_start_position(0);
509
  empty_function->shared()->set_end_position(source->length());
510
  empty_function->shared()->DontAdaptArguments();
511

    
512
  // Set prototypes for the function maps.
513
  native_context()->function_map()->set_prototype(*empty_function);
514
  native_context()->function_without_prototype_map()->
515
      set_prototype(*empty_function);
516
  function_map_writable_prototype_->set_prototype(*empty_function);
517

    
518
  // Allocate the function map first and then patch the prototype later
519
  Handle<Map> empty_function_map = CreateFunctionMap(DONT_ADD_PROTOTYPE);
520
  empty_function_map->set_prototype(
521
      native_context()->object_function()->prototype());
522
  empty_function->set_map(*empty_function_map);
523
  return empty_function;
524
}
525

    
526

    
527
void Genesis::SetStrictFunctionInstanceDescriptor(
528
    Handle<Map> map, PrototypePropertyMode prototypeMode) {
529
  int size = (prototypeMode == DONT_ADD_PROTOTYPE) ? 4 : 5;
530
  Handle<DescriptorArray> descriptors(factory()->NewDescriptorArray(0, size));
531
  DescriptorArray::WhitenessWitness witness(*descriptors);
532

    
533
  Handle<Foreign> length(factory()->NewForeign(&Accessors::FunctionLength));
534
  Handle<Foreign> name(factory()->NewForeign(&Accessors::FunctionName));
535
  Handle<AccessorPair> arguments(factory()->NewAccessorPair());
536
  Handle<AccessorPair> caller(factory()->NewAccessorPair());
537
  Handle<Foreign> prototype;
538
  if (prototypeMode != DONT_ADD_PROTOTYPE) {
539
    prototype = factory()->NewForeign(&Accessors::FunctionPrototype);
540
  }
541
  PropertyAttributes rw_attribs =
542
      static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE);
543
  PropertyAttributes ro_attribs =
544
      static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY);
545
  map->set_instance_descriptors(*descriptors);
546

    
547
  {  // Add length.
548
    CallbacksDescriptor d(*factory()->length_string(), *length, ro_attribs);
549
    map->AppendDescriptor(&d, witness);
550
  }
551
  {  // Add name.
552
    CallbacksDescriptor d(*factory()->name_string(), *name, rw_attribs);
553
    map->AppendDescriptor(&d, witness);
554
  }
555
  {  // Add arguments.
556
    CallbacksDescriptor d(*factory()->arguments_string(), *arguments,
557
                          rw_attribs);
558
    map->AppendDescriptor(&d, witness);
559
  }
560
  {  // Add caller.
561
    CallbacksDescriptor d(*factory()->caller_string(), *caller, rw_attribs);
562
    map->AppendDescriptor(&d, witness);
563
  }
564
  if (prototypeMode != DONT_ADD_PROTOTYPE) {
565
    // Add prototype.
566
    PropertyAttributes attribs =
567
        prototypeMode == ADD_WRITEABLE_PROTOTYPE ? rw_attribs : ro_attribs;
568
    CallbacksDescriptor d(*factory()->prototype_string(), *prototype, attribs);
569
    map->AppendDescriptor(&d, witness);
570
  }
571
}
572

    
573

    
574
// ECMAScript 5th Edition, 13.2.3
575
Handle<JSFunction> Genesis::GetThrowTypeErrorFunction() {
576
  if (throw_type_error_function.is_null()) {
577
    Handle<String> name = factory()->InternalizeOneByteString(
578
        STATIC_ASCII_VECTOR("ThrowTypeError"));
579
    throw_type_error_function =
580
      factory()->NewFunctionWithoutPrototype(name, CLASSIC_MODE);
581
    Handle<Code> code(isolate()->builtins()->builtin(
582
        Builtins::kStrictModePoisonPill));
583
    throw_type_error_function->set_map(
584
        native_context()->function_map());
585
    throw_type_error_function->set_code(*code);
586
    throw_type_error_function->shared()->set_code(*code);
587
    throw_type_error_function->shared()->DontAdaptArguments();
588

    
589
    JSObject::PreventExtensions(throw_type_error_function);
590
  }
591
  return throw_type_error_function;
592
}
593

    
594

    
595
Handle<Map> Genesis::CreateStrictModeFunctionMap(
596
    PrototypePropertyMode prototype_mode,
597
    Handle<JSFunction> empty_function) {
598
  Handle<Map> map = factory()->NewMap(JS_FUNCTION_TYPE, JSFunction::kSize);
599
  SetStrictFunctionInstanceDescriptor(map, prototype_mode);
600
  map->set_function_with_prototype(prototype_mode != DONT_ADD_PROTOTYPE);
601
  map->set_prototype(*empty_function);
602
  return map;
603
}
604

    
605

    
606
void Genesis::CreateStrictModeFunctionMaps(Handle<JSFunction> empty) {
607
  // Allocate map for the prototype-less strict mode instances.
608
  Handle<Map> strict_mode_function_without_prototype_map =
609
      CreateStrictModeFunctionMap(DONT_ADD_PROTOTYPE, empty);
610
  native_context()->set_strict_mode_function_without_prototype_map(
611
      *strict_mode_function_without_prototype_map);
612

    
613
  // Allocate map for the strict mode functions. This map is temporary, used
614
  // only for processing of builtins.
615
  // Later the map is replaced with writable prototype map, allocated below.
616
  Handle<Map> strict_mode_function_map =
617
      CreateStrictModeFunctionMap(ADD_READONLY_PROTOTYPE, empty);
618
  native_context()->set_strict_mode_function_map(
619
      *strict_mode_function_map);
620

    
621
  // The final map for the strict mode functions. Writeable prototype.
622
  // This map is installed in MakeFunctionInstancePrototypeWritable.
623
  strict_mode_function_map_writable_prototype_ =
624
      CreateStrictModeFunctionMap(ADD_WRITEABLE_PROTOTYPE, empty);
625

    
626
  // Complete the callbacks.
627
  PoisonArgumentsAndCaller(strict_mode_function_without_prototype_map);
628
  PoisonArgumentsAndCaller(strict_mode_function_map);
629
  PoisonArgumentsAndCaller(strict_mode_function_map_writable_prototype_);
630
}
631

    
632

    
633
static void SetAccessors(Handle<Map> map,
634
                         Handle<String> name,
635
                         Handle<JSFunction> func) {
636
  DescriptorArray* descs = map->instance_descriptors();
637
  int number = descs->SearchWithCache(*name, *map);
638
  AccessorPair* accessors = AccessorPair::cast(descs->GetValue(number));
639
  accessors->set_getter(*func);
640
  accessors->set_setter(*func);
641
}
642

    
643

    
644
void Genesis::PoisonArgumentsAndCaller(Handle<Map> map) {
645
  SetAccessors(map, factory()->arguments_string(), GetThrowTypeErrorFunction());
646
  SetAccessors(map, factory()->caller_string(), GetThrowTypeErrorFunction());
647
}
648

    
649

    
650
static void AddToWeakNativeContextList(Context* context) {
651
  ASSERT(context->IsNativeContext());
652
  Heap* heap = context->GetIsolate()->heap();
653
#ifdef DEBUG
654
  { // NOLINT
655
    ASSERT(context->get(Context::NEXT_CONTEXT_LINK)->IsUndefined());
656
    // Check that context is not in the list yet.
657
    for (Object* current = heap->native_contexts_list();
658
         !current->IsUndefined();
659
         current = Context::cast(current)->get(Context::NEXT_CONTEXT_LINK)) {
660
      ASSERT(current != context);
661
    }
662
  }
663
#endif
664
  context->set(Context::NEXT_CONTEXT_LINK, heap->native_contexts_list());
665
  heap->set_native_contexts_list(context);
666
}
667

    
668

    
669
void Genesis::CreateRoots() {
670
  // Allocate the native context FixedArray first and then patch the
671
  // closure and extension object later (we need the empty function
672
  // and the global object, but in order to create those, we need the
673
  // native context).
674
  native_context_ = factory()->NewNativeContext();
675
  AddToWeakNativeContextList(*native_context());
676
  isolate()->set_context(*native_context());
677

    
678
  // Allocate the message listeners object.
679
  {
680
    v8::NeanderArray listeners;
681
    native_context()->set_message_listeners(*listeners.value());
682
  }
683
}
684

    
685

    
686
Handle<JSGlobalProxy> Genesis::CreateNewGlobals(
687
    v8::Handle<v8::ObjectTemplate> global_template,
688
    Handle<Object> global_object,
689
    Handle<GlobalObject>* inner_global_out) {
690
  // The argument global_template aka data is an ObjectTemplateInfo.
691
  // It has a constructor pointer that points at global_constructor which is a
692
  // FunctionTemplateInfo.
693
  // The global_constructor is used to create or reinitialize the global_proxy.
694
  // The global_constructor also has a prototype_template pointer that points at
695
  // js_global_template which is an ObjectTemplateInfo.
696
  // That in turn has a constructor pointer that points at
697
  // js_global_constructor which is a FunctionTemplateInfo.
698
  // js_global_constructor is used to make js_global_function
699
  // js_global_function is used to make the new inner_global.
700
  //
701
  // --- G l o b a l ---
702
  // Step 1: Create a fresh inner JSGlobalObject.
703
  Handle<JSFunction> js_global_function;
704
  Handle<ObjectTemplateInfo> js_global_template;
705
  if (!global_template.IsEmpty()) {
706
    // Get prototype template of the global_template.
707
    Handle<ObjectTemplateInfo> data =
708
        v8::Utils::OpenHandle(*global_template);
709
    Handle<FunctionTemplateInfo> global_constructor =
710
        Handle<FunctionTemplateInfo>(
711
            FunctionTemplateInfo::cast(data->constructor()));
712
    Handle<Object> proto_template(global_constructor->prototype_template(),
713
                                  isolate());
714
    if (!proto_template->IsUndefined()) {
715
      js_global_template =
716
          Handle<ObjectTemplateInfo>::cast(proto_template);
717
    }
718
  }
719

    
720
  if (js_global_template.is_null()) {
721
    Handle<String> name = Handle<String>(heap()->empty_string());
722
    Handle<Code> code = Handle<Code>(isolate()->builtins()->builtin(
723
        Builtins::kIllegal));
724
    js_global_function =
725
        factory()->NewFunction(name, JS_GLOBAL_OBJECT_TYPE,
726
                               JSGlobalObject::kSize, code, true);
727
    // Change the constructor property of the prototype of the
728
    // hidden global function to refer to the Object function.
729
    Handle<JSObject> prototype =
730
        Handle<JSObject>(
731
            JSObject::cast(js_global_function->instance_prototype()));
732
    CHECK_NOT_EMPTY_HANDLE(isolate(),
733
                           JSObject::SetLocalPropertyIgnoreAttributes(
734
                               prototype, factory()->constructor_string(),
735
                               isolate()->object_function(), NONE));
736
  } else {
737
    Handle<FunctionTemplateInfo> js_global_constructor(
738
        FunctionTemplateInfo::cast(js_global_template->constructor()));
739
    js_global_function =
740
        factory()->CreateApiFunction(js_global_constructor,
741
                                     factory()->InnerGlobalObject);
742
  }
743

    
744
  js_global_function->initial_map()->set_is_hidden_prototype();
745
  js_global_function->initial_map()->set_dictionary_map(true);
746
  Handle<GlobalObject> inner_global =
747
      factory()->NewGlobalObject(js_global_function);
748
  if (inner_global_out != NULL) {
749
    *inner_global_out = inner_global;
750
  }
751

    
752
  // Step 2: create or re-initialize the global proxy object.
753
  Handle<JSFunction> global_proxy_function;
754
  if (global_template.IsEmpty()) {
755
    Handle<String> name = Handle<String>(heap()->empty_string());
756
    Handle<Code> code = Handle<Code>(isolate()->builtins()->builtin(
757
        Builtins::kIllegal));
758
    global_proxy_function =
759
        factory()->NewFunction(name, JS_GLOBAL_PROXY_TYPE,
760
                               JSGlobalProxy::kSize, code, true);
761
  } else {
762
    Handle<ObjectTemplateInfo> data =
763
        v8::Utils::OpenHandle(*global_template);
764
    Handle<FunctionTemplateInfo> global_constructor(
765
            FunctionTemplateInfo::cast(data->constructor()));
766
    global_proxy_function =
767
        factory()->CreateApiFunction(global_constructor,
768
                                     factory()->OuterGlobalObject);
769
  }
770

    
771
  Handle<String> global_name = factory()->InternalizeOneByteString(
772
      STATIC_ASCII_VECTOR("global"));
773
  global_proxy_function->shared()->set_instance_class_name(*global_name);
774
  global_proxy_function->initial_map()->set_is_access_check_needed(true);
775

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

    
779
  if (global_object.location() != NULL) {
780
    ASSERT(global_object->IsJSGlobalProxy());
781
    return ReinitializeJSGlobalProxy(
782
        global_proxy_function,
783
        Handle<JSGlobalProxy>::cast(global_object));
784
  } else {
785
    return Handle<JSGlobalProxy>::cast(
786
        factory()->NewJSObject(global_proxy_function, TENURED));
787
  }
788
}
789

    
790

    
791
void Genesis::HookUpGlobalProxy(Handle<GlobalObject> inner_global,
792
                                Handle<JSGlobalProxy> global_proxy) {
793
  // Set the native context for the global object.
794
  inner_global->set_native_context(*native_context());
795
  inner_global->set_global_context(*native_context());
796
  inner_global->set_global_receiver(*global_proxy);
797
  global_proxy->set_native_context(*native_context());
798
  native_context()->set_global_proxy(*global_proxy);
799
}
800

    
801

    
802
void Genesis::HookUpInnerGlobal(Handle<GlobalObject> inner_global) {
803
  Handle<GlobalObject> inner_global_from_snapshot(
804
      GlobalObject::cast(native_context()->extension()));
805
  Handle<JSBuiltinsObject> builtins_global(native_context()->builtins());
806
  native_context()->set_extension(*inner_global);
807
  native_context()->set_global_object(*inner_global);
808
  native_context()->set_security_token(*inner_global);
809
  static const PropertyAttributes attributes =
810
      static_cast<PropertyAttributes>(READ_ONLY | DONT_DELETE);
811
  ForceSetProperty(builtins_global,
812
                   factory()->InternalizeOneByteString(
813
                       STATIC_ASCII_VECTOR("global")),
814
                   inner_global,
815
                   attributes);
816
  // Set up the reference from the global object to the builtins object.
817
  JSGlobalObject::cast(*inner_global)->set_builtins(*builtins_global);
818
  TransferNamedProperties(inner_global_from_snapshot, inner_global);
819
  TransferIndexedProperties(inner_global_from_snapshot, inner_global);
820
}
821

    
822

    
823
// This is only called if we are not using snapshots.  The equivalent
824
// work in the snapshot case is done in HookUpInnerGlobal.
825
void Genesis::InitializeGlobal(Handle<GlobalObject> inner_global,
826
                               Handle<JSFunction> empty_function) {
827
  // --- N a t i v e   C o n t e x t ---
828
  // Use the empty function as closure (no scope info).
829
  native_context()->set_closure(*empty_function);
830
  native_context()->set_previous(NULL);
831
  // Set extension and global object.
832
  native_context()->set_extension(*inner_global);
833
  native_context()->set_global_object(*inner_global);
834
  // Security setup: Set the security token of the global object to
835
  // its the inner global. This makes the security check between two
836
  // different contexts fail by default even in case of global
837
  // object reinitialization.
838
  native_context()->set_security_token(*inner_global);
839

    
840
  Isolate* isolate = inner_global->GetIsolate();
841
  Factory* factory = isolate->factory();
842
  Heap* heap = isolate->heap();
843

    
844
  Handle<String> object_name = factory->Object_string();
845
  CHECK_NOT_EMPTY_HANDLE(isolate,
846
                         JSObject::SetLocalPropertyIgnoreAttributes(
847
                             inner_global, object_name,
848
                             isolate->object_function(), DONT_ENUM));
849

    
850
  Handle<JSObject> global = Handle<JSObject>(native_context()->global_object());
851

    
852
  // Install global Function object
853
  InstallFunction(global, "Function", JS_FUNCTION_TYPE, JSFunction::kSize,
854
                  empty_function, Builtins::kIllegal, true, true);
855

    
856
  {  // --- A r r a y ---
857
    Handle<JSFunction> array_function =
858
        InstallFunction(global, "Array", JS_ARRAY_TYPE, JSArray::kSize,
859
                        isolate->initial_object_prototype(),
860
                        Builtins::kArrayCode, true, true);
861
    array_function->shared()->DontAdaptArguments();
862
    array_function->shared()->set_function_data(Smi::FromInt(kArrayCode));
863

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

    
868
    Handle<Map> initial_map(array_function->initial_map());
869

    
870
    // This assert protects an optimization in
871
    // HGraphBuilder::JSArrayBuilder::EmitMapCode()
872
    ASSERT(initial_map->elements_kind() == GetInitialFastElementsKind());
873

    
874
    Handle<DescriptorArray> array_descriptors(
875
        factory->NewDescriptorArray(0, 1));
876
    DescriptorArray::WhitenessWitness witness(*array_descriptors);
877

    
878
    Handle<Foreign> array_length(factory->NewForeign(&Accessors::ArrayLength));
879
    PropertyAttributes attribs = static_cast<PropertyAttributes>(
880
        DONT_ENUM | DONT_DELETE);
881
    initial_map->set_instance_descriptors(*array_descriptors);
882

    
883
    {  // Add length.
884
      CallbacksDescriptor d(*factory->length_string(), *array_length, attribs);
885
      array_function->initial_map()->AppendDescriptor(&d, witness);
886
    }
887

    
888
    // array_function is used internally. JS code creating array object should
889
    // search for the 'Array' property on the global object and use that one
890
    // as the constructor. 'Array' property on a global object can be
891
    // overwritten by JS code.
892
    native_context()->set_array_function(*array_function);
893

    
894
    // Cache the array maps, needed by ArrayConstructorStub
895
    CacheInitialJSArrayMaps(native_context(), initial_map);
896
    ArrayConstructorStub array_constructor_stub(isolate);
897
    Handle<Code> code = array_constructor_stub.GetCode(isolate);
898
    array_function->shared()->set_construct_stub(*code);
899
  }
900

    
901
  {  // --- N u m b e r ---
902
    Handle<JSFunction> number_fun =
903
        InstallFunction(global, "Number", JS_VALUE_TYPE, JSValue::kSize,
904
                        isolate->initial_object_prototype(),
905
                        Builtins::kIllegal, true, true);
906
    native_context()->set_number_function(*number_fun);
907
  }
908

    
909
  {  // --- B o o l e a n ---
910
    Handle<JSFunction> boolean_fun =
911
        InstallFunction(global, "Boolean", JS_VALUE_TYPE, JSValue::kSize,
912
                        isolate->initial_object_prototype(),
913
                        Builtins::kIllegal, true, true);
914
    native_context()->set_boolean_function(*boolean_fun);
915
  }
916

    
917
  {  // --- S t r i n g ---
918
    Handle<JSFunction> string_fun =
919
        InstallFunction(global, "String", JS_VALUE_TYPE, JSValue::kSize,
920
                        isolate->initial_object_prototype(),
921
                        Builtins::kIllegal, true, true);
922
    string_fun->shared()->set_construct_stub(
923
        isolate->builtins()->builtin(Builtins::kStringConstructCode));
924
    native_context()->set_string_function(*string_fun);
925

    
926
    Handle<Map> string_map =
927
        Handle<Map>(native_context()->string_function()->initial_map());
928
    Handle<DescriptorArray> string_descriptors(
929
        factory->NewDescriptorArray(0, 1));
930
    DescriptorArray::WhitenessWitness witness(*string_descriptors);
931

    
932
    Handle<Foreign> string_length(
933
        factory->NewForeign(&Accessors::StringLength));
934
    PropertyAttributes attribs = static_cast<PropertyAttributes>(
935
        DONT_ENUM | DONT_DELETE | READ_ONLY);
936
    string_map->set_instance_descriptors(*string_descriptors);
937

    
938
    {  // Add length.
939
      CallbacksDescriptor d(*factory->length_string(), *string_length, attribs);
940
      string_map->AppendDescriptor(&d, witness);
941
    }
942
  }
943

    
944
  {  // --- D a t e ---
945
    // Builtin functions for Date.prototype.
946
    Handle<JSFunction> date_fun =
947
        InstallFunction(global, "Date", JS_DATE_TYPE, JSDate::kSize,
948
                        isolate->initial_object_prototype(),
949
                        Builtins::kIllegal, true, true);
950

    
951
    native_context()->set_date_function(*date_fun);
952
  }
953

    
954

    
955
  {  // -- R e g E x p
956
    // Builtin functions for RegExp.prototype.
957
    Handle<JSFunction> regexp_fun =
958
        InstallFunction(global, "RegExp", JS_REGEXP_TYPE, JSRegExp::kSize,
959
                        isolate->initial_object_prototype(),
960
                        Builtins::kIllegal, true, true);
961
    native_context()->set_regexp_function(*regexp_fun);
962

    
963
    ASSERT(regexp_fun->has_initial_map());
964
    Handle<Map> initial_map(regexp_fun->initial_map());
965

    
966
    ASSERT_EQ(0, initial_map->inobject_properties());
967

    
968
    PropertyAttributes final =
969
        static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY);
970
    Handle<DescriptorArray> descriptors = factory->NewDescriptorArray(0, 5);
971
    DescriptorArray::WhitenessWitness witness(*descriptors);
972
    initial_map->set_instance_descriptors(*descriptors);
973

    
974
    {
975
      // ECMA-262, section 15.10.7.1.
976
      FieldDescriptor field(heap->source_string(),
977
                            JSRegExp::kSourceFieldIndex,
978
                            final,
979
                            Representation::Tagged());
980
      initial_map->AppendDescriptor(&field, witness);
981
    }
982
    {
983
      // ECMA-262, section 15.10.7.2.
984
      FieldDescriptor field(heap->global_string(),
985
                            JSRegExp::kGlobalFieldIndex,
986
                            final,
987
                            Representation::Tagged());
988
      initial_map->AppendDescriptor(&field, witness);
989
    }
990
    {
991
      // ECMA-262, section 15.10.7.3.
992
      FieldDescriptor field(heap->ignore_case_string(),
993
                            JSRegExp::kIgnoreCaseFieldIndex,
994
                            final,
995
                            Representation::Tagged());
996
      initial_map->AppendDescriptor(&field, witness);
997
    }
998
    {
999
      // ECMA-262, section 15.10.7.4.
1000
      FieldDescriptor field(heap->multiline_string(),
1001
                            JSRegExp::kMultilineFieldIndex,
1002
                            final,
1003
                            Representation::Tagged());
1004
      initial_map->AppendDescriptor(&field, witness);
1005
    }
1006
    {
1007
      // ECMA-262, section 15.10.7.5.
1008
      PropertyAttributes writable =
1009
          static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE);
1010
      FieldDescriptor field(heap->last_index_string(),
1011
                            JSRegExp::kLastIndexFieldIndex,
1012
                            writable,
1013
                            Representation::Tagged());
1014
      initial_map->AppendDescriptor(&field, witness);
1015
    }
1016

    
1017
    initial_map->set_inobject_properties(5);
1018
    initial_map->set_pre_allocated_property_fields(5);
1019
    initial_map->set_unused_property_fields(0);
1020
    initial_map->set_instance_size(
1021
        initial_map->instance_size() + 5 * kPointerSize);
1022
    initial_map->set_visitor_id(StaticVisitorBase::GetVisitorId(*initial_map));
1023

    
1024
    // RegExp prototype object is itself a RegExp.
1025
    Handle<Map> proto_map = factory->CopyMap(initial_map);
1026
    proto_map->set_prototype(native_context()->initial_object_prototype());
1027
    Handle<JSObject> proto = factory->NewJSObjectFromMap(proto_map);
1028
    proto->InObjectPropertyAtPut(JSRegExp::kSourceFieldIndex,
1029
                                 heap->query_colon_string());
1030
    proto->InObjectPropertyAtPut(JSRegExp::kGlobalFieldIndex,
1031
                                 heap->false_value());
1032
    proto->InObjectPropertyAtPut(JSRegExp::kIgnoreCaseFieldIndex,
1033
                                 heap->false_value());
1034
    proto->InObjectPropertyAtPut(JSRegExp::kMultilineFieldIndex,
1035
                                 heap->false_value());
1036
    proto->InObjectPropertyAtPut(JSRegExp::kLastIndexFieldIndex,
1037
                                 Smi::FromInt(0),
1038
                                 SKIP_WRITE_BARRIER);  // It's a Smi.
1039
    initial_map->set_prototype(*proto);
1040
    factory->SetRegExpIrregexpData(Handle<JSRegExp>::cast(proto),
1041
                                   JSRegExp::IRREGEXP, factory->empty_string(),
1042
                                   JSRegExp::Flags(0), 0);
1043
  }
1044

    
1045
  {  // -- J S O N
1046
    Handle<String> name = factory->InternalizeUtf8String("JSON");
1047
    Handle<JSFunction> cons = factory->NewFunction(name,
1048
                                                   factory->the_hole_value());
1049
    JSFunction::SetInstancePrototype(cons,
1050
        Handle<Object>(native_context()->initial_object_prototype(), isolate));
1051
    cons->SetInstanceClassName(*name);
1052
    Handle<JSObject> json_object = factory->NewJSObject(cons, TENURED);
1053
    ASSERT(json_object->IsJSObject());
1054
    CHECK_NOT_EMPTY_HANDLE(isolate,
1055
                           JSObject::SetLocalPropertyIgnoreAttributes(
1056
                                 global, name, json_object, DONT_ENUM));
1057
    native_context()->set_json_object(*json_object);
1058
  }
1059

    
1060
  { // -- A r r a y B u f f e r
1061
    Handle<JSFunction> array_buffer_fun =
1062
        InstallFunction(
1063
            global, "ArrayBuffer", JS_ARRAY_BUFFER_TYPE,
1064
            JSArrayBuffer::kSizeWithInternalFields,
1065
            isolate->initial_object_prototype(),
1066
            Builtins::kIllegal, true, true);
1067
    native_context()->set_array_buffer_fun(*array_buffer_fun);
1068
  }
1069

    
1070
  { // -- T y p e d A r r a y s
1071
    Handle<JSFunction> int8_fun = InstallTypedArray("Int8Array",
1072
        EXTERNAL_BYTE_ELEMENTS);
1073
    native_context()->set_int8_array_fun(*int8_fun);
1074
    Handle<JSFunction> uint8_fun = InstallTypedArray("Uint8Array",
1075
        EXTERNAL_UNSIGNED_BYTE_ELEMENTS);
1076
    native_context()->set_uint8_array_fun(*uint8_fun);
1077
    Handle<JSFunction> int16_fun = InstallTypedArray("Int16Array",
1078
        EXTERNAL_SHORT_ELEMENTS);
1079
    native_context()->set_int16_array_fun(*int16_fun);
1080
    Handle<JSFunction> uint16_fun = InstallTypedArray("Uint16Array",
1081
        EXTERNAL_UNSIGNED_SHORT_ELEMENTS);
1082
    native_context()->set_uint16_array_fun(*uint16_fun);
1083
    Handle<JSFunction> int32_fun = InstallTypedArray("Int32Array",
1084
        EXTERNAL_INT_ELEMENTS);
1085
    native_context()->set_int32_array_fun(*int32_fun);
1086
    Handle<JSFunction> uint32_fun = InstallTypedArray("Uint32Array",
1087
        EXTERNAL_UNSIGNED_INT_ELEMENTS);
1088
    native_context()->set_uint32_array_fun(*uint32_fun);
1089
    Handle<JSFunction> float_fun = InstallTypedArray("Float32Array",
1090
        EXTERNAL_FLOAT_ELEMENTS);
1091
    native_context()->set_float_array_fun(*float_fun);
1092
    Handle<JSFunction> double_fun = InstallTypedArray("Float64Array",
1093
        EXTERNAL_DOUBLE_ELEMENTS);
1094
    native_context()->set_double_array_fun(*double_fun);
1095
    Handle<JSFunction> uint8c_fun = InstallTypedArray("Uint8ClampedArray",
1096
        EXTERNAL_PIXEL_ELEMENTS);
1097
    native_context()->set_uint8c_array_fun(*uint8c_fun);
1098

    
1099
    Handle<JSFunction> data_view_fun =
1100
        InstallFunction(
1101
            global, "DataView", JS_DATA_VIEW_TYPE,
1102
            JSDataView::kSizeWithInternalFields,
1103
            isolate->initial_object_prototype(),
1104
            Builtins::kIllegal, true, true);
1105
    native_context()->set_data_view_fun(*data_view_fun);
1106
  }
1107

    
1108
  {  // --- arguments_boilerplate_
1109
    // Make sure we can recognize argument objects at runtime.
1110
    // This is done by introducing an anonymous function with
1111
    // class_name equals 'Arguments'.
1112
    Handle<String> arguments_string = factory->InternalizeOneByteString(
1113
        STATIC_ASCII_VECTOR("Arguments"));
1114
    Handle<Code> code = Handle<Code>(
1115
        isolate->builtins()->builtin(Builtins::kIllegal));
1116
    Handle<JSObject> prototype =
1117
        Handle<JSObject>(
1118
            JSObject::cast(native_context()->object_function()->prototype()));
1119

    
1120
    Handle<JSFunction> function =
1121
        factory->NewFunctionWithPrototype(arguments_string,
1122
                                          JS_OBJECT_TYPE,
1123
                                          JSObject::kHeaderSize,
1124
                                          prototype,
1125
                                          code,
1126
                                          false);
1127
    ASSERT(!function->has_initial_map());
1128
    function->shared()->set_instance_class_name(*arguments_string);
1129
    function->shared()->set_expected_nof_properties(2);
1130
    Handle<JSObject> result = factory->NewJSObject(function);
1131

    
1132
    native_context()->set_arguments_boilerplate(*result);
1133
    // Note: length must be added as the first property and
1134
    //       callee must be added as the second property.
1135
    CHECK_NOT_EMPTY_HANDLE(isolate,
1136
                           JSObject::SetLocalPropertyIgnoreAttributes(
1137
                               result, factory->length_string(),
1138
                               factory->undefined_value(), DONT_ENUM,
1139
                               Object::FORCE_TAGGED, FORCE_FIELD));
1140
    CHECK_NOT_EMPTY_HANDLE(isolate,
1141
                           JSObject::SetLocalPropertyIgnoreAttributes(
1142
                               result, factory->callee_string(),
1143
                               factory->undefined_value(), DONT_ENUM,
1144
                               Object::FORCE_TAGGED, FORCE_FIELD));
1145

    
1146
#ifdef DEBUG
1147
    LookupResult lookup(isolate);
1148
    result->LocalLookup(heap->callee_string(), &lookup);
1149
    ASSERT(lookup.IsField());
1150
    ASSERT(lookup.GetFieldIndex().field_index() == Heap::kArgumentsCalleeIndex);
1151

    
1152
    result->LocalLookup(heap->length_string(), &lookup);
1153
    ASSERT(lookup.IsField());
1154
    ASSERT(lookup.GetFieldIndex().field_index() == Heap::kArgumentsLengthIndex);
1155

    
1156
    ASSERT(result->map()->inobject_properties() > Heap::kArgumentsCalleeIndex);
1157
    ASSERT(result->map()->inobject_properties() > Heap::kArgumentsLengthIndex);
1158

    
1159
    // Check the state of the object.
1160
    ASSERT(result->HasFastProperties());
1161
    ASSERT(result->HasFastObjectElements());
1162
#endif
1163
  }
1164

    
1165
  {  // --- aliased_arguments_boilerplate_
1166
    // Set up a well-formed parameter map to make assertions happy.
1167
    Handle<FixedArray> elements = factory->NewFixedArray(2);
1168
    elements->set_map(heap->non_strict_arguments_elements_map());
1169
    Handle<FixedArray> array;
1170
    array = factory->NewFixedArray(0);
1171
    elements->set(0, *array);
1172
    array = factory->NewFixedArray(0);
1173
    elements->set(1, *array);
1174

    
1175
    Handle<Map> old_map(native_context()->arguments_boilerplate()->map());
1176
    Handle<Map> new_map = factory->CopyMap(old_map);
1177
    new_map->set_pre_allocated_property_fields(2);
1178
    Handle<JSObject> result = factory->NewJSObjectFromMap(new_map);
1179
    // Set elements kind after allocating the object because
1180
    // NewJSObjectFromMap assumes a fast elements map.
1181
    new_map->set_elements_kind(NON_STRICT_ARGUMENTS_ELEMENTS);
1182
    result->set_elements(*elements);
1183
    ASSERT(result->HasNonStrictArgumentsElements());
1184
    native_context()->set_aliased_arguments_boilerplate(*result);
1185
  }
1186

    
1187
  {  // --- strict mode arguments boilerplate
1188
    const PropertyAttributes attributes =
1189
      static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY);
1190

    
1191
    // Create the ThrowTypeError functions.
1192
    Handle<AccessorPair> callee = factory->NewAccessorPair();
1193
    Handle<AccessorPair> caller = factory->NewAccessorPair();
1194

    
1195
    Handle<JSFunction> throw_function =
1196
        GetThrowTypeErrorFunction();
1197

    
1198
    // Install the ThrowTypeError functions.
1199
    callee->set_getter(*throw_function);
1200
    callee->set_setter(*throw_function);
1201
    caller->set_getter(*throw_function);
1202
    caller->set_setter(*throw_function);
1203

    
1204
    // Create the map. Allocate one in-object field for length.
1205
    Handle<Map> map = factory->NewMap(JS_OBJECT_TYPE,
1206
                                      Heap::kArgumentsObjectSizeStrict);
1207
    // Create the descriptor array for the arguments object.
1208
    Handle<DescriptorArray> descriptors = factory->NewDescriptorArray(0, 3);
1209
    DescriptorArray::WhitenessWitness witness(*descriptors);
1210
    map->set_instance_descriptors(*descriptors);
1211

    
1212
    {  // length
1213
      FieldDescriptor d(
1214
          *factory->length_string(), 0, DONT_ENUM, Representation::Tagged());
1215
      map->AppendDescriptor(&d, witness);
1216
    }
1217
    {  // callee
1218
      CallbacksDescriptor d(*factory->callee_string(),
1219
                            *callee,
1220
                            attributes);
1221
      map->AppendDescriptor(&d, witness);
1222
    }
1223
    {  // caller
1224
      CallbacksDescriptor d(*factory->caller_string(),
1225
                            *caller,
1226
                            attributes);
1227
      map->AppendDescriptor(&d, witness);
1228
    }
1229

    
1230
    map->set_function_with_prototype(true);
1231
    map->set_prototype(native_context()->object_function()->prototype());
1232
    map->set_pre_allocated_property_fields(1);
1233
    map->set_inobject_properties(1);
1234

    
1235
    // Copy constructor from the non-strict arguments boilerplate.
1236
    map->set_constructor(
1237
      native_context()->arguments_boilerplate()->map()->constructor());
1238

    
1239
    // Allocate the arguments boilerplate object.
1240
    Handle<JSObject> result = factory->NewJSObjectFromMap(map);
1241
    native_context()->set_strict_mode_arguments_boilerplate(*result);
1242

    
1243
    // Add length property only for strict mode boilerplate.
1244
    CHECK_NOT_EMPTY_HANDLE(isolate,
1245
                           JSObject::SetLocalPropertyIgnoreAttributes(
1246
                               result, factory->length_string(),
1247
                               factory->undefined_value(), DONT_ENUM));
1248

    
1249
#ifdef DEBUG
1250
    LookupResult lookup(isolate);
1251
    result->LocalLookup(heap->length_string(), &lookup);
1252
    ASSERT(lookup.IsField());
1253
    ASSERT(lookup.GetFieldIndex().field_index() == Heap::kArgumentsLengthIndex);
1254

    
1255
    ASSERT(result->map()->inobject_properties() > Heap::kArgumentsLengthIndex);
1256

    
1257
    // Check the state of the object.
1258
    ASSERT(result->HasFastProperties());
1259
    ASSERT(result->HasFastObjectElements());
1260
#endif
1261
  }
1262

    
1263
  {  // --- context extension
1264
    // Create a function for the context extension objects.
1265
    Handle<Code> code = Handle<Code>(
1266
        isolate->builtins()->builtin(Builtins::kIllegal));
1267
    Handle<JSFunction> context_extension_fun =
1268
        factory->NewFunction(factory->empty_string(),
1269
                             JS_CONTEXT_EXTENSION_OBJECT_TYPE,
1270
                             JSObject::kHeaderSize,
1271
                             code,
1272
                             true);
1273

    
1274
    Handle<String> name = factory->InternalizeOneByteString(
1275
        STATIC_ASCII_VECTOR("context_extension"));
1276
    context_extension_fun->shared()->set_instance_class_name(*name);
1277
    native_context()->set_context_extension_function(*context_extension_fun);
1278
  }
1279

    
1280

    
1281
  {
1282
    // Set up the call-as-function delegate.
1283
    Handle<Code> code =
1284
        Handle<Code>(isolate->builtins()->builtin(
1285
            Builtins::kHandleApiCallAsFunction));
1286
    Handle<JSFunction> delegate =
1287
        factory->NewFunction(factory->empty_string(), JS_OBJECT_TYPE,
1288
                             JSObject::kHeaderSize, code, true);
1289
    native_context()->set_call_as_function_delegate(*delegate);
1290
    delegate->shared()->DontAdaptArguments();
1291
  }
1292

    
1293
  {
1294
    // Set up the call-as-constructor delegate.
1295
    Handle<Code> code =
1296
        Handle<Code>(isolate->builtins()->builtin(
1297
            Builtins::kHandleApiCallAsConstructor));
1298
    Handle<JSFunction> delegate =
1299
        factory->NewFunction(factory->empty_string(), JS_OBJECT_TYPE,
1300
                             JSObject::kHeaderSize, code, true);
1301
    native_context()->set_call_as_constructor_delegate(*delegate);
1302
    delegate->shared()->DontAdaptArguments();
1303
  }
1304

    
1305
  // Initialize the out of memory slot.
1306
  native_context()->set_out_of_memory(heap->false_value());
1307

    
1308
  // Initialize the embedder data slot.
1309
  Handle<FixedArray> embedder_data = factory->NewFixedArray(2);
1310
  native_context()->set_embedder_data(*embedder_data);
1311

    
1312
  // Allocate the random seed slot.
1313
  Handle<ByteArray> random_seed = factory->NewByteArray(kRandomStateSize);
1314
  native_context()->set_random_seed(*random_seed);
1315
}
1316

    
1317

    
1318
Handle<JSFunction> Genesis::InstallTypedArray(
1319
    const char* name, ElementsKind elementsKind) {
1320
  Handle<JSObject> global = Handle<JSObject>(native_context()->global_object());
1321
  Handle<JSFunction> result = InstallFunction(global, name, JS_TYPED_ARRAY_TYPE,
1322
      JSTypedArray::kSize, isolate()->initial_object_prototype(),
1323
      Builtins::kIllegal, false, true);
1324

    
1325
  Handle<Map> initial_map = isolate()->factory()->NewMap(
1326
      JS_TYPED_ARRAY_TYPE, JSTypedArray::kSizeWithInternalFields, elementsKind);
1327
  result->set_initial_map(*initial_map);
1328
  initial_map->set_constructor(*result);
1329
  return result;
1330
}
1331

    
1332

    
1333
void Genesis::InitializeExperimentalGlobal() {
1334
  Handle<JSObject> global = Handle<JSObject>(native_context()->global_object());
1335

    
1336
  // TODO(mstarzinger): Move this into Genesis::InitializeGlobal once we no
1337
  // longer need to live behind flags, so functions get added to the snapshot.
1338

    
1339
  if (FLAG_harmony_symbols) {
1340
    // --- S y m b o l ---
1341
    Handle<JSFunction> symbol_fun =
1342
        InstallFunction(global, "Symbol", JS_VALUE_TYPE, JSValue::kSize,
1343
                        isolate()->initial_object_prototype(),
1344
                        Builtins::kIllegal, true, true);
1345
    native_context()->set_symbol_function(*symbol_fun);
1346
  }
1347

    
1348
  if (FLAG_harmony_collections) {
1349
    {  // -- S e t
1350
      InstallFunction(global, "Set", JS_SET_TYPE, JSSet::kSize,
1351
                      isolate()->initial_object_prototype(),
1352
                      Builtins::kIllegal, true, true);
1353
    }
1354
    {  // -- M a p
1355
      InstallFunction(global, "Map", JS_MAP_TYPE, JSMap::kSize,
1356
                      isolate()->initial_object_prototype(),
1357
                      Builtins::kIllegal, true, true);
1358
    }
1359
    {  // -- W e a k M a p
1360
      InstallFunction(global, "WeakMap", JS_WEAK_MAP_TYPE, JSWeakMap::kSize,
1361
                      isolate()->initial_object_prototype(),
1362
                      Builtins::kIllegal, true, true);
1363
    }
1364
    {  // -- W e a k S e t
1365
      InstallFunction(global, "WeakSet", JS_WEAK_SET_TYPE, JSWeakSet::kSize,
1366
                      isolate()->initial_object_prototype(),
1367
                      Builtins::kIllegal, true, true);
1368
    }
1369
  }
1370

    
1371
  if (FLAG_harmony_generators) {
1372
    // Create generator meta-objects and install them on the builtins object.
1373
    Handle<JSObject> builtins(native_context()->builtins());
1374
    Handle<JSObject> generator_object_prototype =
1375
        factory()->NewJSObject(isolate()->object_function(), TENURED);
1376
    Handle<JSFunction> generator_function_prototype =
1377
        InstallFunction(builtins, "GeneratorFunctionPrototype",
1378
                        JS_FUNCTION_TYPE, JSFunction::kHeaderSize,
1379
                        generator_object_prototype, Builtins::kIllegal,
1380
                        false, false);
1381
    InstallFunction(builtins, "GeneratorFunction",
1382
                    JS_FUNCTION_TYPE, JSFunction::kSize,
1383
                    generator_function_prototype, Builtins::kIllegal,
1384
                    false, false);
1385

    
1386
    // Create maps for generator functions and their prototypes.  Store those
1387
    // maps in the native context.
1388
    Handle<Map> function_map(native_context()->function_map());
1389
    Handle<Map> generator_function_map = factory()->CopyMap(function_map);
1390
    generator_function_map->set_prototype(*generator_function_prototype);
1391
    native_context()->set_generator_function_map(*generator_function_map);
1392

    
1393
    Handle<Map> strict_mode_function_map(
1394
        native_context()->strict_mode_function_map());
1395
    Handle<Map> strict_mode_generator_function_map = factory()->CopyMap(
1396
        strict_mode_function_map);
1397
    strict_mode_generator_function_map->set_prototype(
1398
        *generator_function_prototype);
1399
    native_context()->set_strict_mode_generator_function_map(
1400
        *strict_mode_generator_function_map);
1401

    
1402
    Handle<Map> object_map(native_context()->object_function()->initial_map());
1403
    Handle<Map> generator_object_prototype_map = factory()->CopyMap(
1404
        object_map, 0);
1405
    generator_object_prototype_map->set_prototype(
1406
        *generator_object_prototype);
1407
    native_context()->set_generator_object_prototype_map(
1408
        *generator_object_prototype_map);
1409

    
1410
    // Create a map for generator result objects.
1411
    ASSERT(object_map->inobject_properties() == 0);
1412
    STATIC_ASSERT(JSGeneratorObject::kResultPropertyCount == 2);
1413
    Handle<Map> generator_result_map = factory()->CopyMap(object_map,
1414
        JSGeneratorObject::kResultPropertyCount);
1415
    ASSERT(generator_result_map->inobject_properties() ==
1416
        JSGeneratorObject::kResultPropertyCount);
1417

    
1418
    Handle<DescriptorArray> descriptors = factory()->NewDescriptorArray(0,
1419
        JSGeneratorObject::kResultPropertyCount);
1420
    DescriptorArray::WhitenessWitness witness(*descriptors);
1421
    generator_result_map->set_instance_descriptors(*descriptors);
1422

    
1423
    Handle<String> value_string = factory()->InternalizeOneByteString(
1424
        STATIC_ASCII_VECTOR("value"));
1425
    FieldDescriptor value_descr(*value_string,
1426
                                JSGeneratorObject::kResultValuePropertyIndex,
1427
                                NONE,
1428
                                Representation::Tagged());
1429
    generator_result_map->AppendDescriptor(&value_descr, witness);
1430

    
1431
    Handle<String> done_string = factory()->InternalizeOneByteString(
1432
        STATIC_ASCII_VECTOR("done"));
1433
    FieldDescriptor done_descr(*done_string,
1434
                               JSGeneratorObject::kResultDonePropertyIndex,
1435
                               NONE,
1436
                               Representation::Tagged());
1437
    generator_result_map->AppendDescriptor(&done_descr, witness);
1438

    
1439
    generator_result_map->set_unused_property_fields(0);
1440
    ASSERT_EQ(JSGeneratorObject::kResultSize,
1441
              generator_result_map->instance_size());
1442
    native_context()->set_generator_result_map(*generator_result_map);
1443
  }
1444
}
1445

    
1446

    
1447
bool Genesis::CompileBuiltin(Isolate* isolate, int index) {
1448
  Vector<const char> name = Natives::GetScriptName(index);
1449
  Handle<String> source_code =
1450
      isolate->bootstrapper()->NativesSourceLookup(index);
1451
  return CompileNative(isolate, name, source_code);
1452
}
1453

    
1454

    
1455
bool Genesis::CompileExperimentalBuiltin(Isolate* isolate, int index) {
1456
  Vector<const char> name = ExperimentalNatives::GetScriptName(index);
1457
  Factory* factory = isolate->factory();
1458
  Handle<String> source_code =
1459
      factory->NewStringFromAscii(
1460
          ExperimentalNatives::GetRawScriptSource(index));
1461
  return CompileNative(isolate, name, source_code);
1462
}
1463

    
1464

    
1465
bool Genesis::CompileNative(Isolate* isolate,
1466
                            Vector<const char> name,
1467
                            Handle<String> source) {
1468
  HandleScope scope(isolate);
1469
#ifdef ENABLE_DEBUGGER_SUPPORT
1470
  isolate->debugger()->set_compiling_natives(true);
1471
#endif
1472
  // During genesis, the boilerplate for stack overflow won't work until the
1473
  // environment has been at least partially initialized. Add a stack check
1474
  // before entering JS code to catch overflow early.
1475
  StackLimitCheck check(isolate);
1476
  if (check.HasOverflowed()) return false;
1477

    
1478
  bool result = CompileScriptCached(isolate,
1479
                                    name,
1480
                                    source,
1481
                                    NULL,
1482
                                    NULL,
1483
                                    Handle<Context>(isolate->context()),
1484
                                    true);
1485
  ASSERT(isolate->has_pending_exception() != result);
1486
  if (!result) isolate->clear_pending_exception();
1487
#ifdef ENABLE_DEBUGGER_SUPPORT
1488
  isolate->debugger()->set_compiling_natives(false);
1489
#endif
1490
  return result;
1491
}
1492

    
1493

    
1494
bool Genesis::CompileScriptCached(Isolate* isolate,
1495
                                  Vector<const char> name,
1496
                                  Handle<String> source,
1497
                                  SourceCodeCache* cache,
1498
                                  v8::Extension* extension,
1499
                                  Handle<Context> top_context,
1500
                                  bool use_runtime_context) {
1501
  Factory* factory = isolate->factory();
1502
  HandleScope scope(isolate);
1503
  Handle<SharedFunctionInfo> function_info;
1504

    
1505
  // If we can't find the function in the cache, we compile a new
1506
  // function and insert it into the cache.
1507
  if (cache == NULL || !cache->Lookup(name, &function_info)) {
1508
    ASSERT(source->IsOneByteRepresentation());
1509
    Handle<String> script_name = factory->NewStringFromUtf8(name);
1510
    function_info = Compiler::Compile(
1511
        source,
1512
        script_name,
1513
        0,
1514
        0,
1515
        false,
1516
        top_context,
1517
        extension,
1518
        NULL,
1519
        Handle<String>::null(),
1520
        use_runtime_context ? NATIVES_CODE : NOT_NATIVES_CODE);
1521
    if (function_info.is_null()) return false;
1522
    if (cache != NULL) cache->Add(name, function_info);
1523
  }
1524

    
1525
  // Set up the function context. Conceptually, we should clone the
1526
  // function before overwriting the context but since we're in a
1527
  // single-threaded environment it is not strictly necessary.
1528
  ASSERT(top_context->IsNativeContext());
1529
  Handle<Context> context =
1530
      Handle<Context>(use_runtime_context
1531
                      ? Handle<Context>(top_context->runtime_context())
1532
                      : top_context);
1533
  Handle<JSFunction> fun =
1534
      factory->NewFunctionFromSharedFunctionInfo(function_info, context);
1535

    
1536
  // Call function using either the runtime object or the global
1537
  // object as the receiver. Provide no parameters.
1538
  Handle<Object> receiver =
1539
      Handle<Object>(use_runtime_context
1540
                     ? top_context->builtins()
1541
                     : top_context->global_object(),
1542
                     isolate);
1543
  bool has_pending_exception;
1544
  Execution::Call(isolate, fun, receiver, 0, NULL, &has_pending_exception);
1545
  if (has_pending_exception) return false;
1546
  return true;
1547
}
1548

    
1549

    
1550
#define INSTALL_NATIVE(Type, name, var)                                 \
1551
  Handle<String> var##_name =                                           \
1552
    factory()->InternalizeOneByteString(STATIC_ASCII_VECTOR(name));     \
1553
  Object* var##_native =                                                \
1554
      native_context()->builtins()->GetPropertyNoExceptionThrown(       \
1555
           *var##_name);                                                \
1556
  native_context()->set_##var(Type::cast(var##_native));
1557

    
1558

    
1559
void Genesis::InstallNativeFunctions() {
1560
  HandleScope scope(isolate());
1561
  INSTALL_NATIVE(JSFunction, "CreateDate", create_date_fun);
1562
  INSTALL_NATIVE(JSFunction, "ToNumber", to_number_fun);
1563
  INSTALL_NATIVE(JSFunction, "ToString", to_string_fun);
1564
  INSTALL_NATIVE(JSFunction, "ToDetailString", to_detail_string_fun);
1565
  INSTALL_NATIVE(JSFunction, "ToObject", to_object_fun);
1566
  INSTALL_NATIVE(JSFunction, "ToInteger", to_integer_fun);
1567
  INSTALL_NATIVE(JSFunction, "ToUint32", to_uint32_fun);
1568
  INSTALL_NATIVE(JSFunction, "ToInt32", to_int32_fun);
1569
  INSTALL_NATIVE(JSFunction, "GlobalEval", global_eval_fun);
1570
  INSTALL_NATIVE(JSFunction, "Instantiate", instantiate_fun);
1571
  INSTALL_NATIVE(JSFunction, "ConfigureTemplateInstance",
1572
                 configure_instance_fun);
1573
  INSTALL_NATIVE(JSFunction, "GetStackTraceLine", get_stack_trace_line_fun);
1574
  INSTALL_NATIVE(JSObject, "functionCache", function_cache);
1575
  INSTALL_NATIVE(JSFunction, "ToCompletePropertyDescriptor",
1576
                 to_complete_property_descriptor);
1577
}
1578

    
1579

    
1580
void Genesis::InstallExperimentalNativeFunctions() {
1581
  if (FLAG_harmony_proxies) {
1582
    INSTALL_NATIVE(JSFunction, "DerivedHasTrap", derived_has_trap);
1583
    INSTALL_NATIVE(JSFunction, "DerivedGetTrap", derived_get_trap);
1584
    INSTALL_NATIVE(JSFunction, "DerivedSetTrap", derived_set_trap);
1585
    INSTALL_NATIVE(JSFunction, "ProxyEnumerate", proxy_enumerate);
1586
  }
1587
  if (FLAG_harmony_observation) {
1588
    INSTALL_NATIVE(JSFunction, "NotifyChange", observers_notify_change);
1589
    INSTALL_NATIVE(JSFunction, "EnqueueSpliceRecord", observers_enqueue_splice);
1590
    INSTALL_NATIVE(JSFunction, "BeginPerformSplice",
1591
                   observers_begin_perform_splice);
1592
    INSTALL_NATIVE(JSFunction, "EndPerformSplice",
1593
                   observers_end_perform_splice);
1594
    INSTALL_NATIVE(JSFunction, "DeliverChangeRecords",
1595
                   observers_deliver_changes);
1596
  }
1597
}
1598

    
1599
#undef INSTALL_NATIVE
1600

    
1601

    
1602
Handle<JSFunction> Genesis::InstallInternalArray(
1603
    Handle<JSBuiltinsObject> builtins,
1604
    const char* name,
1605
    ElementsKind elements_kind) {
1606
  // --- I n t e r n a l   A r r a y ---
1607
  // An array constructor on the builtins object that works like
1608
  // the public Array constructor, except that its prototype
1609
  // doesn't inherit from Object.prototype.
1610
  // To be used only for internal work by builtins. Instances
1611
  // must not be leaked to user code.
1612
  Handle<JSFunction> array_function =
1613
      InstallFunction(builtins,
1614
                      name,
1615
                      JS_ARRAY_TYPE,
1616
                      JSArray::kSize,
1617
                      isolate()->initial_object_prototype(),
1618
                      Builtins::kInternalArrayCode,
1619
                      true, true);
1620
  Handle<JSObject> prototype =
1621
      factory()->NewJSObject(isolate()->object_function(), TENURED);
1622
  Accessors::FunctionSetPrototype(array_function, prototype);
1623

    
1624
  InternalArrayConstructorStub internal_array_constructor_stub(isolate());
1625
  Handle<Code> code = internal_array_constructor_stub.GetCode(isolate());
1626
  array_function->shared()->set_construct_stub(*code);
1627
  array_function->shared()->DontAdaptArguments();
1628

    
1629
  Handle<Map> original_map(array_function->initial_map());
1630
  Handle<Map> initial_map = factory()->CopyMap(original_map);
1631
  initial_map->set_elements_kind(elements_kind);
1632
  array_function->set_initial_map(*initial_map);
1633

    
1634
  // Make "length" magic on instances.
1635
  Handle<DescriptorArray> array_descriptors(
1636
      factory()->NewDescriptorArray(0, 1));
1637
  DescriptorArray::WhitenessWitness witness(*array_descriptors);
1638

    
1639
  Handle<Foreign> array_length(factory()->NewForeign(
1640
      &Accessors::ArrayLength));
1641
  PropertyAttributes attribs = static_cast<PropertyAttributes>(
1642
      DONT_ENUM | DONT_DELETE);
1643
  initial_map->set_instance_descriptors(*array_descriptors);
1644

    
1645
  {  // Add length.
1646
    CallbacksDescriptor d(
1647
        *factory()->length_string(), *array_length, attribs);
1648
    array_function->initial_map()->AppendDescriptor(&d, witness);
1649
  }
1650

    
1651
  return array_function;
1652
}
1653

    
1654

    
1655
bool Genesis::InstallNatives() {
1656
  HandleScope scope(isolate());
1657

    
1658
  // Create a function for the builtins object. Allocate space for the
1659
  // JavaScript builtins, a reference to the builtins object
1660
  // (itself) and a reference to the native_context directly in the object.
1661
  Handle<Code> code = Handle<Code>(
1662
      isolate()->builtins()->builtin(Builtins::kIllegal));
1663
  Handle<JSFunction> builtins_fun =
1664
      factory()->NewFunction(factory()->empty_string(),
1665
                             JS_BUILTINS_OBJECT_TYPE,
1666
                             JSBuiltinsObject::kSize, code, true);
1667

    
1668
  Handle<String> name =
1669
      factory()->InternalizeOneByteString(STATIC_ASCII_VECTOR("builtins"));
1670
  builtins_fun->shared()->set_instance_class_name(*name);
1671
  builtins_fun->initial_map()->set_dictionary_map(true);
1672
  builtins_fun->initial_map()->set_prototype(heap()->null_value());
1673

    
1674
  // Allocate the builtins object.
1675
  Handle<JSBuiltinsObject> builtins =
1676
      Handle<JSBuiltinsObject>::cast(factory()->NewGlobalObject(builtins_fun));
1677
  builtins->set_builtins(*builtins);
1678
  builtins->set_native_context(*native_context());
1679
  builtins->set_global_context(*native_context());
1680
  builtins->set_global_receiver(*builtins);
1681

    
1682
  // Set up the 'global' properties of the builtins object. The
1683
  // 'global' property that refers to the global object is the only
1684
  // way to get from code running in the builtins context to the
1685
  // global object.
1686
  static const PropertyAttributes attributes =
1687
      static_cast<PropertyAttributes>(READ_ONLY | DONT_DELETE);
1688
  Handle<String> global_string =
1689
      factory()->InternalizeOneByteString(STATIC_ASCII_VECTOR("global"));
1690
  Handle<Object> global_obj(native_context()->global_object(), isolate());
1691
  CHECK_NOT_EMPTY_HANDLE(isolate(),
1692
                         JSObject::SetLocalPropertyIgnoreAttributes(
1693
                             builtins, global_string, global_obj, attributes));
1694

    
1695
  // Set up the reference from the global object to the builtins object.
1696
  JSGlobalObject::cast(native_context()->global_object())->
1697
      set_builtins(*builtins);
1698

    
1699
  // Create a bridge function that has context in the native context.
1700
  Handle<JSFunction> bridge =
1701
      factory()->NewFunction(factory()->empty_string(),
1702
                             factory()->undefined_value());
1703
  ASSERT(bridge->context() == *isolate()->native_context());
1704

    
1705
  // Allocate the builtins context.
1706
  Handle<Context> context =
1707
    factory()->NewFunctionContext(Context::MIN_CONTEXT_SLOTS, bridge);
1708
  context->set_global_object(*builtins);  // override builtins global object
1709

    
1710
  native_context()->set_runtime_context(*context);
1711

    
1712
  {  // -- S c r i p t
1713
    // Builtin functions for Script.
1714
    Handle<JSFunction> script_fun =
1715
        InstallFunction(builtins, "Script", JS_VALUE_TYPE, JSValue::kSize,
1716
                        isolate()->initial_object_prototype(),
1717
                        Builtins::kIllegal, false, false);
1718
    Handle<JSObject> prototype =
1719
        factory()->NewJSObject(isolate()->object_function(), TENURED);
1720
    Accessors::FunctionSetPrototype(script_fun, prototype);
1721
    native_context()->set_script_function(*script_fun);
1722

    
1723
    Handle<Map> script_map = Handle<Map>(script_fun->initial_map());
1724

    
1725
    Handle<DescriptorArray> script_descriptors(
1726
        factory()->NewDescriptorArray(0, 13));
1727
    DescriptorArray::WhitenessWitness witness(*script_descriptors);
1728

    
1729
    Handle<Foreign> script_source(
1730
        factory()->NewForeign(&Accessors::ScriptSource));
1731
    Handle<Foreign> script_name(factory()->NewForeign(&Accessors::ScriptName));
1732
    Handle<String> id_string(factory()->InternalizeOneByteString(
1733
        STATIC_ASCII_VECTOR("id")));
1734
    Handle<Foreign> script_id(factory()->NewForeign(&Accessors::ScriptId));
1735
    Handle<String> line_offset_string(
1736
        factory()->InternalizeOneByteString(
1737
            STATIC_ASCII_VECTOR("line_offset")));
1738
    Handle<Foreign> script_line_offset(
1739
        factory()->NewForeign(&Accessors::ScriptLineOffset));
1740
    Handle<String> column_offset_string(
1741
        factory()->InternalizeOneByteString(
1742
            STATIC_ASCII_VECTOR("column_offset")));
1743
    Handle<Foreign> script_column_offset(
1744
        factory()->NewForeign(&Accessors::ScriptColumnOffset));
1745
    Handle<String> data_string(factory()->InternalizeOneByteString(
1746
        STATIC_ASCII_VECTOR("data")));
1747
    Handle<Foreign> script_data(factory()->NewForeign(&Accessors::ScriptData));
1748
    Handle<String> type_string(factory()->InternalizeOneByteString(
1749
        STATIC_ASCII_VECTOR("type")));
1750
    Handle<Foreign> script_type(factory()->NewForeign(&Accessors::ScriptType));
1751
    Handle<String> compilation_type_string(
1752
        factory()->InternalizeOneByteString(
1753
            STATIC_ASCII_VECTOR("compilation_type")));
1754
    Handle<Foreign> script_compilation_type(
1755
        factory()->NewForeign(&Accessors::ScriptCompilationType));
1756
    Handle<String> line_ends_string(factory()->InternalizeOneByteString(
1757
        STATIC_ASCII_VECTOR("line_ends")));
1758
    Handle<Foreign> script_line_ends(
1759
        factory()->NewForeign(&Accessors::ScriptLineEnds));
1760
    Handle<String> context_data_string(
1761
        factory()->InternalizeOneByteString(
1762
            STATIC_ASCII_VECTOR("context_data")));
1763
    Handle<Foreign> script_context_data(
1764
        factory()->NewForeign(&Accessors::ScriptContextData));
1765
    Handle<String> eval_from_script_string(
1766
        factory()->InternalizeOneByteString(
1767
            STATIC_ASCII_VECTOR("eval_from_script")));
1768
    Handle<Foreign> script_eval_from_script(
1769
        factory()->NewForeign(&Accessors::ScriptEvalFromScript));
1770
    Handle<String> eval_from_script_position_string(
1771
        factory()->InternalizeOneByteString(
1772
            STATIC_ASCII_VECTOR("eval_from_script_position")));
1773
    Handle<Foreign> script_eval_from_script_position(
1774
        factory()->NewForeign(&Accessors::ScriptEvalFromScriptPosition));
1775
    Handle<String> eval_from_function_name_string(
1776
        factory()->InternalizeOneByteString(
1777
            STATIC_ASCII_VECTOR("eval_from_function_name")));
1778
    Handle<Foreign> script_eval_from_function_name(
1779
        factory()->NewForeign(&Accessors::ScriptEvalFromFunctionName));
1780
    PropertyAttributes attribs =
1781
        static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY);
1782
    script_map->set_instance_descriptors(*script_descriptors);
1783

    
1784
    {
1785
      CallbacksDescriptor d(
1786
          *factory()->source_string(), *script_source, attribs);
1787
      script_map->AppendDescriptor(&d, witness);
1788
    }
1789

    
1790
    {
1791
      CallbacksDescriptor d(*factory()->name_string(), *script_name, attribs);
1792
      script_map->AppendDescriptor(&d, witness);
1793
    }
1794

    
1795
    {
1796
      CallbacksDescriptor d(*id_string, *script_id, attribs);
1797
      script_map->AppendDescriptor(&d, witness);
1798
    }
1799

    
1800
    {
1801
      CallbacksDescriptor d(*line_offset_string, *script_line_offset, attribs);
1802
      script_map->AppendDescriptor(&d, witness);
1803
    }
1804

    
1805
    {
1806
      CallbacksDescriptor d(
1807
          *column_offset_string, *script_column_offset, attribs);
1808
      script_map->AppendDescriptor(&d, witness);
1809
    }
1810

    
1811
    {
1812
      CallbacksDescriptor d(*data_string, *script_data, attribs);
1813
      script_map->AppendDescriptor(&d, witness);
1814
    }
1815

    
1816
    {
1817
      CallbacksDescriptor d(*type_string, *script_type, attribs);
1818
      script_map->AppendDescriptor(&d, witness);
1819
    }
1820

    
1821
    {
1822
      CallbacksDescriptor d(
1823
          *compilation_type_string, *script_compilation_type, attribs);
1824
      script_map->AppendDescriptor(&d, witness);
1825
    }
1826

    
1827
    {
1828
      CallbacksDescriptor d(*line_ends_string, *script_line_ends, attribs);
1829
      script_map->AppendDescriptor(&d, witness);
1830
    }
1831

    
1832
    {
1833
      CallbacksDescriptor d(
1834
          *context_data_string, *script_context_data, attribs);
1835
      script_map->AppendDescriptor(&d, witness);
1836
    }
1837

    
1838
    {
1839
      CallbacksDescriptor d(
1840
          *eval_from_script_string, *script_eval_from_script, attribs);
1841
      script_map->AppendDescriptor(&d, witness);
1842
    }
1843

    
1844
    {
1845
      CallbacksDescriptor d(
1846
          *eval_from_script_position_string,
1847
          *script_eval_from_script_position,
1848
          attribs);
1849
      script_map->AppendDescriptor(&d, witness);
1850
    }
1851

    
1852
    {
1853
      CallbacksDescriptor d(
1854
          *eval_from_function_name_string,
1855
          *script_eval_from_function_name,
1856
          attribs);
1857
      script_map->AppendDescriptor(&d, witness);
1858
    }
1859

    
1860
    // Allocate the empty script.
1861
    Handle<Script> script = factory()->NewScript(factory()->empty_string());
1862
    script->set_type(Smi::FromInt(Script::TYPE_NATIVE));
1863
    heap()->public_set_empty_script(*script);
1864
  }
1865
  {
1866
    // Builtin function for OpaqueReference -- a JSValue-based object,
1867
    // that keeps its field isolated from JavaScript code. It may store
1868
    // objects, that JavaScript code may not access.
1869
    Handle<JSFunction> opaque_reference_fun =
1870
        InstallFunction(builtins, "OpaqueReference", JS_VALUE_TYPE,
1871
                        JSValue::kSize,
1872
                        isolate()->initial_object_prototype(),
1873
                        Builtins::kIllegal, false, false);
1874
    Handle<JSObject> prototype =
1875
        factory()->NewJSObject(isolate()->object_function(), TENURED);
1876
    Accessors::FunctionSetPrototype(opaque_reference_fun, prototype);
1877
    native_context()->set_opaque_reference_function(*opaque_reference_fun);
1878
  }
1879

    
1880
  // InternalArrays should not use Smi-Only array optimizations. There are too
1881
  // many places in the C++ runtime code (e.g. RegEx) that assume that
1882
  // elements in InternalArrays can be set to non-Smi values without going
1883
  // through a common bottleneck that would make the SMI_ONLY -> FAST_ELEMENT
1884
  // transition easy to trap. Moreover, they rarely are smi-only.
1885
  {
1886
    Handle<JSFunction> array_function =
1887
        InstallInternalArray(builtins, "InternalArray", FAST_HOLEY_ELEMENTS);
1888
    native_context()->set_internal_array_function(*array_function);
1889
  }
1890

    
1891
  {
1892
    InstallInternalArray(builtins, "InternalPackedArray", FAST_ELEMENTS);
1893
  }
1894

    
1895
  if (FLAG_disable_native_files) {
1896
    PrintF("Warning: Running without installed natives!\n");
1897
    return true;
1898
  }
1899

    
1900
  // Install natives.
1901
  for (int i = Natives::GetDebuggerCount();
1902
       i < Natives::GetBuiltinsCount();
1903
       i++) {
1904
    if (!CompileBuiltin(isolate(), i)) return false;
1905
    // TODO(ager): We really only need to install the JS builtin
1906
    // functions on the builtins object after compiling and running
1907
    // runtime.js.
1908
    if (!InstallJSBuiltins(builtins)) return false;
1909
  }
1910

    
1911
  InstallNativeFunctions();
1912

    
1913
  // Store the map for the string prototype after the natives has been compiled
1914
  // and the String function has been set up.
1915
  Handle<JSFunction> string_function(native_context()->string_function());
1916
  ASSERT(JSObject::cast(
1917
      string_function->initial_map()->prototype())->HasFastProperties());
1918
  native_context()->set_string_function_prototype_map(
1919
      HeapObject::cast(string_function->initial_map()->prototype())->map());
1920

    
1921
  // Install Function.prototype.call and apply.
1922
  { Handle<String> key = factory()->function_class_string();
1923
    Handle<JSFunction> function =
1924
        Handle<JSFunction>::cast(
1925
            GetProperty(isolate(), isolate()->global_object(), key));
1926
    Handle<JSObject> proto =
1927
        Handle<JSObject>(JSObject::cast(function->instance_prototype()));
1928

    
1929
    // Install the call and the apply functions.
1930
    Handle<JSFunction> call =
1931
        InstallFunction(proto, "call", JS_OBJECT_TYPE, JSObject::kHeaderSize,
1932
                        Handle<JSObject>::null(),
1933
                        Builtins::kFunctionCall,
1934
                        false, false);
1935
    Handle<JSFunction> apply =
1936
        InstallFunction(proto, "apply", JS_OBJECT_TYPE, JSObject::kHeaderSize,
1937
                        Handle<JSObject>::null(),
1938
                        Builtins::kFunctionApply,
1939
                        false, false);
1940

    
1941
    // Make sure that Function.prototype.call appears to be compiled.
1942
    // The code will never be called, but inline caching for call will
1943
    // only work if it appears to be compiled.
1944
    call->shared()->DontAdaptArguments();
1945
    ASSERT(call->is_compiled());
1946

    
1947
    // Set the expected parameters for apply to 2; required by builtin.
1948
    apply->shared()->set_formal_parameter_count(2);
1949

    
1950
    // Set the lengths for the functions to satisfy ECMA-262.
1951
    call->shared()->set_length(1);
1952
    apply->shared()->set_length(2);
1953
  }
1954

    
1955
  InstallBuiltinFunctionIds();
1956

    
1957
  // Create a constructor for RegExp results (a variant of Array that
1958
  // predefines the two properties index and match).
1959
  {
1960
    // RegExpResult initial map.
1961

    
1962
    // Find global.Array.prototype to inherit from.
1963
    Handle<JSFunction> array_constructor(native_context()->array_function());
1964
    Handle<JSObject> array_prototype(
1965
        JSObject::cast(array_constructor->instance_prototype()));
1966

    
1967
    // Add initial map.
1968
    Handle<Map> initial_map =
1969
        factory()->NewMap(JS_ARRAY_TYPE, JSRegExpResult::kSize);
1970
    initial_map->set_constructor(*array_constructor);
1971

    
1972
    // Set prototype on map.
1973
    initial_map->set_non_instance_prototype(false);
1974
    initial_map->set_prototype(*array_prototype);
1975

    
1976
    // Update map with length accessor from Array and add "index" and "input".
1977
    Handle<DescriptorArray> reresult_descriptors =
1978
        factory()->NewDescriptorArray(0, 3);
1979
    DescriptorArray::WhitenessWitness witness(*reresult_descriptors);
1980
    initial_map->set_instance_descriptors(*reresult_descriptors);
1981

    
1982
    {
1983
      JSFunction* array_function = native_context()->array_function();
1984
      Handle<DescriptorArray> array_descriptors(
1985
          array_function->initial_map()->instance_descriptors());
1986
      String* length = heap()->length_string();
1987
      int old = array_descriptors->SearchWithCache(
1988
          length, array_function->initial_map());
1989
      ASSERT(old != DescriptorArray::kNotFound);
1990
      CallbacksDescriptor desc(length,
1991
                               array_descriptors->GetValue(old),
1992
                               array_descriptors->GetDetails(old).attributes());
1993
      initial_map->AppendDescriptor(&desc, witness);
1994
    }
1995
    {
1996
      FieldDescriptor index_field(heap()->index_string(),
1997
                                  JSRegExpResult::kIndexIndex,
1998
                                  NONE,
1999
                                  Representation::Tagged());
2000
      initial_map->AppendDescriptor(&index_field, witness);
2001
    }
2002

    
2003
    {
2004
      FieldDescriptor input_field(heap()->input_string(),
2005
                                  JSRegExpResult::kInputIndex,
2006
                                  NONE,
2007
                                  Representation::Tagged());
2008
      initial_map->AppendDescriptor(&input_field, witness);
2009
    }
2010

    
2011
    initial_map->set_inobject_properties(2);
2012
    initial_map->set_pre_allocated_property_fields(2);
2013
    initial_map->set_unused_property_fields(0);
2014

    
2015
    native_context()->set_regexp_result_map(*initial_map);
2016
  }
2017

    
2018
#ifdef VERIFY_HEAP
2019
  builtins->Verify();
2020
#endif
2021

    
2022
  return true;
2023
}
2024

    
2025

    
2026
bool Genesis::InstallExperimentalNatives() {
2027
  for (int i = ExperimentalNatives::GetDebuggerCount();
2028
       i < ExperimentalNatives::GetBuiltinsCount();
2029
       i++) {
2030
    if (FLAG_harmony_symbols &&
2031
        strcmp(ExperimentalNatives::GetScriptName(i).start(),
2032
               "native symbol.js") == 0) {
2033
      if (!CompileExperimentalBuiltin(isolate(), i)) return false;
2034
    }
2035
    if (FLAG_harmony_proxies &&
2036
        strcmp(ExperimentalNatives::GetScriptName(i).start(),
2037
               "native proxy.js") == 0) {
2038
      if (!CompileExperimentalBuiltin(isolate(), i)) return false;
2039
    }
2040
    if (FLAG_harmony_collections &&
2041
        strcmp(ExperimentalNatives::GetScriptName(i).start(),
2042
               "native collection.js") == 0) {
2043
      if (!CompileExperimentalBuiltin(isolate(), i)) return false;
2044
    }
2045
    if (FLAG_harmony_observation &&
2046
        strcmp(ExperimentalNatives::GetScriptName(i).start(),
2047
               "native object-observe.js") == 0) {
2048
      if (!CompileExperimentalBuiltin(isolate(), i)) return false;
2049
    }
2050
    if (FLAG_harmony_generators &&
2051
        strcmp(ExperimentalNatives::GetScriptName(i).start(),
2052
               "native generator.js") == 0) {
2053
      if (!CompileExperimentalBuiltin(isolate(), i)) return false;
2054
    }
2055
    if (FLAG_harmony_iteration &&
2056
        strcmp(ExperimentalNatives::GetScriptName(i).start(),
2057
               "native array-iterator.js") == 0) {
2058
      if (!CompileExperimentalBuiltin(isolate(), i)) return false;
2059
    }
2060
    if (FLAG_harmony_strings &&
2061
        strcmp(ExperimentalNatives::GetScriptName(i).start(),
2062
               "native harmony-string.js") == 0) {
2063
      if (!CompileExperimentalBuiltin(isolate(), i)) return false;
2064
    }
2065
    if (FLAG_harmony_arrays &&
2066
        strcmp(ExperimentalNatives::GetScriptName(i).start(),
2067
               "native harmony-array.js") == 0) {
2068
      if (!CompileExperimentalBuiltin(isolate(), i)) return false;
2069
    }
2070
    if (FLAG_harmony_maths &&
2071
        strcmp(ExperimentalNatives::GetScriptName(i).start(),
2072
               "native harmony-math.js") == 0) {
2073
      if (!CompileExperimentalBuiltin(isolate(), i)) return false;
2074
    }
2075
  }
2076

    
2077
  InstallExperimentalNativeFunctions();
2078

    
2079
  return true;
2080
}
2081

    
2082

    
2083
static Handle<JSObject> ResolveBuiltinIdHolder(
2084
    Handle<Context> native_context,
2085
    const char* holder_expr) {
2086
  Isolate* isolate = native_context->GetIsolate();
2087
  Factory* factory = isolate->factory();
2088
  Handle<GlobalObject> global(native_context->global_object());
2089
  const char* period_pos = strchr(holder_expr, '.');
2090
  if (period_pos == NULL) {
2091
    return Handle<JSObject>::cast(GetProperty(
2092
        isolate, global, factory->InternalizeUtf8String(holder_expr)));
2093
  }
2094
  ASSERT_EQ(".prototype", period_pos);
2095
  Vector<const char> property(holder_expr,
2096
                              static_cast<int>(period_pos - holder_expr));
2097
  Handle<JSFunction> function = Handle<JSFunction>::cast(
2098
      GetProperty(isolate, global, factory->InternalizeUtf8String(property)));
2099
  return Handle<JSObject>(JSObject::cast(function->prototype()));
2100
}
2101

    
2102

    
2103
static void InstallBuiltinFunctionId(Handle<JSObject> holder,
2104
                                     const char* function_name,
2105
                                     BuiltinFunctionId id) {
2106
  Factory* factory = holder->GetIsolate()->factory();
2107
  Handle<String> name = factory->InternalizeUtf8String(function_name);
2108
  Object* function_object = holder->GetProperty(*name)->ToObjectUnchecked();
2109
  Handle<JSFunction> function(JSFunction::cast(function_object));
2110
  function->shared()->set_function_data(Smi::FromInt(id));
2111
}
2112

    
2113

    
2114
void Genesis::InstallBuiltinFunctionIds() {
2115
  HandleScope scope(isolate());
2116
#define INSTALL_BUILTIN_ID(holder_expr, fun_name, name) \
2117
  {                                                     \
2118
    Handle<JSObject> holder = ResolveBuiltinIdHolder(   \
2119
        native_context(), #holder_expr);                \
2120
    BuiltinFunctionId id = k##name;                     \
2121
    InstallBuiltinFunctionId(holder, #fun_name, id);    \
2122
  }
2123
  FUNCTIONS_WITH_ID_LIST(INSTALL_BUILTIN_ID)
2124
#undef INSTALL_BUILTIN_ID
2125
}
2126

    
2127

    
2128
// Do not forget to update macros.py with named constant
2129
// of cache id.
2130
#define JSFUNCTION_RESULT_CACHE_LIST(F) \
2131
  F(16, native_context()->regexp_function())
2132

    
2133

    
2134
static FixedArray* CreateCache(int size, Handle<JSFunction> factory_function) {
2135
  Factory* factory = factory_function->GetIsolate()->factory();
2136
  // Caches are supposed to live for a long time, allocate in old space.
2137
  int array_size = JSFunctionResultCache::kEntriesIndex + 2 * size;
2138
  // Cannot use cast as object is not fully initialized yet.
2139
  JSFunctionResultCache* cache = reinterpret_cast<JSFunctionResultCache*>(
2140
      *factory->NewFixedArrayWithHoles(array_size, TENURED));
2141
  cache->set(JSFunctionResultCache::kFactoryIndex, *factory_function);
2142
  cache->MakeZeroSize();
2143
  return cache;
2144
}
2145

    
2146

    
2147
void Genesis::InstallJSFunctionResultCaches() {
2148
  const int kNumberOfCaches = 0 +
2149
#define F(size, func) + 1
2150
    JSFUNCTION_RESULT_CACHE_LIST(F)
2151
#undef F
2152
  ;
2153

    
2154
  Handle<FixedArray> caches =
2155
      factory()->NewFixedArray(kNumberOfCaches, TENURED);
2156

    
2157
  int index = 0;
2158

    
2159
#define F(size, func) do {                                              \
2160
    FixedArray* cache = CreateCache((size), Handle<JSFunction>(func));  \
2161
    caches->set(index++, cache);                                        \
2162
  } while (false)
2163

    
2164
  JSFUNCTION_RESULT_CACHE_LIST(F);
2165

    
2166
#undef F
2167

    
2168
  native_context()->set_jsfunction_result_caches(*caches);
2169
}
2170

    
2171

    
2172
void Genesis::InitializeNormalizedMapCaches() {
2173
  Handle<FixedArray> array(
2174
      factory()->NewFixedArray(NormalizedMapCache::kEntries, TENURED));
2175
  native_context()->set_normalized_map_cache(NormalizedMapCache::cast(*array));
2176
}
2177

    
2178

    
2179
bool Bootstrapper::InstallExtensions(Handle<Context> native_context,
2180
                                     v8::ExtensionConfiguration* extensions) {
2181
  BootstrapperActive active(this);
2182
  SaveContext saved_context(isolate_);
2183
  isolate_->set_context(*native_context);
2184
  if (!Genesis::InstallExtensions(native_context, extensions)) return false;
2185
  Genesis::InstallSpecialObjects(native_context);
2186
  return true;
2187
}
2188

    
2189

    
2190
void Genesis::InstallSpecialObjects(Handle<Context> native_context) {
2191
  Isolate* isolate = native_context->GetIsolate();
2192
  Factory* factory = isolate->factory();
2193
  HandleScope scope(isolate);
2194
  Handle<JSGlobalObject> global(JSGlobalObject::cast(
2195
      native_context->global_object()));
2196
  // Expose the natives in global if a name for it is specified.
2197
  if (FLAG_expose_natives_as != NULL && strlen(FLAG_expose_natives_as) != 0) {
2198
    Handle<String> natives =
2199
        factory->InternalizeUtf8String(FLAG_expose_natives_as);
2200
    CHECK_NOT_EMPTY_HANDLE(isolate,
2201
                           JSObject::SetLocalPropertyIgnoreAttributes(
2202
                               global, natives,
2203
                               Handle<JSObject>(global->builtins()),
2204
                               DONT_ENUM));
2205
  }
2206

    
2207
  Handle<Object> Error = GetProperty(global, "Error");
2208
  if (Error->IsJSObject()) {
2209
    Handle<String> name = factory->InternalizeOneByteString(
2210
        STATIC_ASCII_VECTOR("stackTraceLimit"));
2211
    Handle<Smi> stack_trace_limit(
2212
        Smi::FromInt(FLAG_stack_trace_limit), isolate);
2213
    CHECK_NOT_EMPTY_HANDLE(isolate,
2214
                           JSObject::SetLocalPropertyIgnoreAttributes(
2215
                               Handle<JSObject>::cast(Error), name,
2216
                               stack_trace_limit, NONE));
2217
  }
2218

    
2219
#ifdef ENABLE_DEBUGGER_SUPPORT
2220
  // Expose the debug global object in global if a name for it is specified.
2221
  if (FLAG_expose_debug_as != NULL && strlen(FLAG_expose_debug_as) != 0) {
2222
    Debug* debug = isolate->debug();
2223
    // If loading fails we just bail out without installing the
2224
    // debugger but without tanking the whole context.
2225
    if (!debug->Load()) return;
2226
    // Set the security token for the debugger context to the same as
2227
    // the shell native context to allow calling between these (otherwise
2228
    // exposing debug global object doesn't make much sense).
2229
    debug->debug_context()->set_security_token(
2230
        native_context->security_token());
2231

    
2232
    Handle<String> debug_string =
2233
        factory->InternalizeUtf8String(FLAG_expose_debug_as);
2234
    Handle<Object> global_proxy(
2235
        debug->debug_context()->global_proxy(), isolate);
2236
    CHECK_NOT_EMPTY_HANDLE(isolate,
2237
                           JSObject::SetLocalPropertyIgnoreAttributes(
2238
                               global, debug_string, global_proxy, DONT_ENUM));
2239
  }
2240
#endif
2241
}
2242

    
2243

    
2244
static uint32_t Hash(RegisteredExtension* extension) {
2245
  return v8::internal::ComputePointerHash(extension);
2246
}
2247

    
2248

    
2249
static bool MatchRegisteredExtensions(void* key1, void* key2) {
2250
  return key1 == key2;
2251
}
2252

    
2253
Genesis::ExtensionStates::ExtensionStates()
2254
  : map_(MatchRegisteredExtensions, 8) { }
2255

    
2256
Genesis::ExtensionTraversalState Genesis::ExtensionStates::get_state(
2257
    RegisteredExtension* extension) {
2258
  i::HashMap::Entry* entry = map_.Lookup(extension, Hash(extension), false);
2259
  if (entry == NULL) {
2260
    return UNVISITED;
2261
  }
2262
  return static_cast<ExtensionTraversalState>(
2263
      reinterpret_cast<intptr_t>(entry->value));
2264
}
2265

    
2266
void Genesis::ExtensionStates::set_state(RegisteredExtension* extension,
2267
                                         ExtensionTraversalState state) {
2268
  map_.Lookup(extension, Hash(extension), true)->value =
2269
      reinterpret_cast<void*>(static_cast<intptr_t>(state));
2270
}
2271

    
2272
bool Genesis::InstallExtensions(Handle<Context> native_context,
2273
                                v8::ExtensionConfiguration* extensions) {
2274
  Isolate* isolate = native_context->GetIsolate();
2275
  ExtensionStates extension_states;  // All extensions have state UNVISITED.
2276
  // Install auto extensions.
2277
  v8::RegisteredExtension* current = v8::RegisteredExtension::first_extension();
2278
  while (current != NULL) {
2279
    if (current->extension()->auto_enable())
2280
      InstallExtension(isolate, current, &extension_states);
2281
    current = current->next();
2282
  }
2283

    
2284
  if (FLAG_expose_gc) InstallExtension(isolate, "v8/gc", &extension_states);
2285
  if (FLAG_expose_externalize_string) {
2286
    InstallExtension(isolate, "v8/externalize", &extension_states);
2287
  }
2288
  if (FLAG_track_gc_object_stats) {
2289
    InstallExtension(isolate, "v8/statistics", &extension_states);
2290
  }
2291

    
2292
  if (extensions == NULL) return true;
2293
  // Install required extensions
2294
  int count = v8::ImplementationUtilities::GetNameCount(extensions);
2295
  const char** names = v8::ImplementationUtilities::GetNames(extensions);
2296
  for (int i = 0; i < count; i++) {
2297
    if (!InstallExtension(isolate, names[i], &extension_states))
2298
      return false;
2299
  }
2300

    
2301
  return true;
2302
}
2303

    
2304

    
2305
// Installs a named extension.  This methods is unoptimized and does
2306
// not scale well if we want to support a large number of extensions.
2307
bool Genesis::InstallExtension(Isolate* isolate,
2308
                               const char* name,
2309
                               ExtensionStates* extension_states) {
2310
  v8::RegisteredExtension* current = v8::RegisteredExtension::first_extension();
2311
  // Loop until we find the relevant extension
2312
  while (current != NULL) {
2313
    if (strcmp(name, current->extension()->name()) == 0) break;
2314
    current = current->next();
2315
  }
2316
  // Didn't find the extension; fail.
2317
  if (current == NULL) {
2318
    v8::Utils::ReportApiFailure(
2319
        "v8::Context::New()", "Cannot find required extension");
2320
    return false;
2321
  }
2322
  return InstallExtension(isolate, current, extension_states);
2323
}
2324

    
2325

    
2326
bool Genesis::InstallExtension(Isolate* isolate,
2327
                               v8::RegisteredExtension* current,
2328
                               ExtensionStates* extension_states) {
2329
  HandleScope scope(isolate);
2330

    
2331
  if (extension_states->get_state(current) == INSTALLED) return true;
2332
  // The current node has already been visited so there must be a
2333
  // cycle in the dependency graph; fail.
2334
  if (extension_states->get_state(current) == VISITED) {
2335
    v8::Utils::ReportApiFailure(
2336
        "v8::Context::New()", "Circular extension dependency");
2337
    return false;
2338
  }
2339
  ASSERT(extension_states->get_state(current) == UNVISITED);
2340
  extension_states->set_state(current, VISITED);
2341
  v8::Extension* extension = current->extension();
2342
  // Install the extension's dependencies
2343
  for (int i = 0; i < extension->dependency_count(); i++) {
2344
    if (!InstallExtension(isolate,
2345
                          extension->dependencies()[i],
2346
                          extension_states)) {
2347
      return false;
2348
    }
2349
  }
2350
  Handle<String> source_code =
2351
      isolate->factory()->NewExternalStringFromAscii(extension->source());
2352
  bool result = CompileScriptCached(isolate,
2353
                                    CStrVector(extension->name()),
2354
                                    source_code,
2355
                                    isolate->bootstrapper()->extensions_cache(),
2356
                                    extension,
2357
                                    Handle<Context>(isolate->context()),
2358
                                    false);
2359
  ASSERT(isolate->has_pending_exception() != result);
2360
  if (!result) {
2361
    // We print out the name of the extension that fail to install.
2362
    // When an error is thrown during bootstrapping we automatically print
2363
    // the line number at which this happened to the console in the isolate
2364
    // error throwing functionality.
2365
    OS::PrintError("Error installing extension '%s'.\n",
2366
                   current->extension()->name());
2367
    isolate->clear_pending_exception();
2368
  }
2369
  extension_states->set_state(current, INSTALLED);
2370
  isolate->NotifyExtensionInstalled();
2371
  return result;
2372
}
2373

    
2374

    
2375
bool Genesis::InstallJSBuiltins(Handle<JSBuiltinsObject> builtins) {
2376
  HandleScope scope(isolate());
2377
  for (int i = 0; i < Builtins::NumberOfJavaScriptBuiltins(); i++) {
2378
    Builtins::JavaScript id = static_cast<Builtins::JavaScript>(i);
2379
    Handle<String> name =
2380
        factory()->InternalizeUtf8String(Builtins::GetName(id));
2381
    Object* function_object = builtins->GetPropertyNoExceptionThrown(*name);
2382
    Handle<JSFunction> function
2383
        = Handle<JSFunction>(JSFunction::cast(function_object));
2384
    builtins->set_javascript_builtin(id, *function);
2385
    if (!JSFunction::CompileLazy(function, CLEAR_EXCEPTION)) {
2386
      return false;
2387
    }
2388
    builtins->set_javascript_builtin_code(id, function->shared()->code());
2389
  }
2390
  return true;
2391
}
2392

    
2393

    
2394
bool Genesis::ConfigureGlobalObjects(
2395
    v8::Handle<v8::ObjectTemplate> global_proxy_template) {
2396
  Handle<JSObject> global_proxy(
2397
      JSObject::cast(native_context()->global_proxy()));
2398
  Handle<JSObject> inner_global(
2399
      JSObject::cast(native_context()->global_object()));
2400

    
2401
  if (!global_proxy_template.IsEmpty()) {
2402
    // Configure the global proxy object.
2403
    Handle<ObjectTemplateInfo> proxy_data =
2404
        v8::Utils::OpenHandle(*global_proxy_template);
2405
    if (!ConfigureApiObject(global_proxy, proxy_data)) return false;
2406

    
2407
    // Configure the inner global object.
2408
    Handle<FunctionTemplateInfo> proxy_constructor(
2409
        FunctionTemplateInfo::cast(proxy_data->constructor()));
2410
    if (!proxy_constructor->prototype_template()->IsUndefined()) {
2411
      Handle<ObjectTemplateInfo> inner_data(
2412
          ObjectTemplateInfo::cast(proxy_constructor->prototype_template()));
2413
      if (!ConfigureApiObject(inner_global, inner_data)) return false;
2414
    }
2415
  }
2416

    
2417
  SetObjectPrototype(global_proxy, inner_global);
2418

    
2419
  native_context()->set_initial_array_prototype(
2420
      JSArray::cast(native_context()->array_function()->prototype()));
2421

    
2422
  return true;
2423
}
2424

    
2425

    
2426
bool Genesis::ConfigureApiObject(Handle<JSObject> object,
2427
    Handle<ObjectTemplateInfo> object_template) {
2428
  ASSERT(!object_template.is_null());
2429
  ASSERT(object->IsInstanceOf(
2430
      FunctionTemplateInfo::cast(object_template->constructor())));
2431

    
2432
  bool pending_exception = false;
2433
  Handle<JSObject> obj =
2434
      Execution::InstantiateObject(object_template, &pending_exception);
2435
  if (pending_exception) {
2436
    ASSERT(isolate()->has_pending_exception());
2437
    isolate()->clear_pending_exception();
2438
    return false;
2439
  }
2440
  TransferObject(obj, object);
2441
  return true;
2442
}
2443

    
2444

    
2445
void Genesis::TransferNamedProperties(Handle<JSObject> from,
2446
                                      Handle<JSObject> to) {
2447
  if (from->HasFastProperties()) {
2448
    Handle<DescriptorArray> descs =
2449
        Handle<DescriptorArray>(from->map()->instance_descriptors());
2450
    for (int i = 0; i < from->map()->NumberOfOwnDescriptors(); i++) {
2451
      PropertyDetails details = descs->GetDetails(i);
2452
      switch (details.type()) {
2453
        case FIELD: {
2454
          HandleScope inner(isolate());
2455
          Handle<Name> key = Handle<Name>(descs->GetKey(i));
2456
          int index = descs->GetFieldIndex(i);
2457
          ASSERT(!descs->GetDetails(i).representation().IsDouble());
2458
          Handle<Object> value = Handle<Object>(from->RawFastPropertyAt(index),
2459
                                                isolate());
2460
          CHECK_NOT_EMPTY_HANDLE(isolate(),
2461
                                 JSObject::SetLocalPropertyIgnoreAttributes(
2462
                                     to, key, value, details.attributes()));
2463
          break;
2464
        }
2465
        case CONSTANT: {
2466
          HandleScope inner(isolate());
2467
          Handle<Name> key = Handle<Name>(descs->GetKey(i));
2468
          Handle<Object> constant(descs->GetConstant(i), isolate());
2469
          CHECK_NOT_EMPTY_HANDLE(isolate(),
2470
                                 JSObject::SetLocalPropertyIgnoreAttributes(
2471
                                     to, key, constant, details.attributes()));
2472
          break;
2473
        }
2474
        case CALLBACKS: {
2475
          LookupResult result(isolate());
2476
          to->LocalLookup(descs->GetKey(i), &result);
2477
          // If the property is already there we skip it
2478
          if (result.IsFound()) continue;
2479
          HandleScope inner(isolate());
2480
          ASSERT(!to->HasFastProperties());
2481
          // Add to dictionary.
2482
          Handle<Name> key = Handle<Name>(descs->GetKey(i));
2483
          Handle<Object> callbacks(descs->GetCallbacksObject(i), isolate());
2484
          PropertyDetails d = PropertyDetails(
2485
              details.attributes(), CALLBACKS, i + 1);
2486
          JSObject::SetNormalizedProperty(to, key, callbacks, d);
2487
          break;
2488
        }
2489
        case NORMAL:
2490
          // Do not occur since the from object has fast properties.
2491
        case HANDLER:
2492
        case INTERCEPTOR:
2493
        case TRANSITION:
2494
        case NONEXISTENT:
2495
          // No element in instance descriptors have proxy or interceptor type.
2496
          UNREACHABLE();
2497
          break;
2498
      }
2499
    }
2500
  } else {
2501
    Handle<NameDictionary> properties =
2502
        Handle<NameDictionary>(from->property_dictionary());
2503
    int capacity = properties->Capacity();
2504
    for (int i = 0; i < capacity; i++) {
2505
      Object* raw_key(properties->KeyAt(i));
2506
      if (properties->IsKey(raw_key)) {
2507
        ASSERT(raw_key->IsName());
2508
        // If the property is already there we skip it.
2509
        LookupResult result(isolate());
2510
        to->LocalLookup(Name::cast(raw_key), &result);
2511
        if (result.IsFound()) continue;
2512
        // Set the property.
2513
        Handle<Name> key = Handle<Name>(Name::cast(raw_key));
2514
        Handle<Object> value = Handle<Object>(properties->ValueAt(i),
2515
                                              isolate());
2516
        ASSERT(!value->IsCell());
2517
        if (value->IsPropertyCell()) {
2518
          value = Handle<Object>(PropertyCell::cast(*value)->value(),
2519
                                 isolate());
2520
        }
2521
        PropertyDetails details = properties->DetailsAt(i);
2522
        CHECK_NOT_EMPTY_HANDLE(isolate(),
2523
                               JSObject::SetLocalPropertyIgnoreAttributes(
2524
                                   to, key, value, details.attributes()));
2525
      }
2526
    }
2527
  }
2528
}
2529

    
2530

    
2531
void Genesis::TransferIndexedProperties(Handle<JSObject> from,
2532
                                        Handle<JSObject> to) {
2533
  // Cloning the elements array is sufficient.
2534
  Handle<FixedArray> from_elements =
2535
      Handle<FixedArray>(FixedArray::cast(from->elements()));
2536
  Handle<FixedArray> to_elements = factory()->CopyFixedArray(from_elements);
2537
  to->set_elements(*to_elements);
2538
}
2539

    
2540

    
2541
void Genesis::TransferObject(Handle<JSObject> from, Handle<JSObject> to) {
2542
  HandleScope outer(isolate());
2543

    
2544
  ASSERT(!from->IsJSArray());
2545
  ASSERT(!to->IsJSArray());
2546

    
2547
  TransferNamedProperties(from, to);
2548
  TransferIndexedProperties(from, to);
2549

    
2550
  // Transfer the prototype (new map is needed).
2551
  Handle<Map> old_to_map = Handle<Map>(to->map());
2552
  Handle<Map> new_to_map = factory()->CopyMap(old_to_map);
2553
  new_to_map->set_prototype(from->map()->prototype());
2554
  to->set_map(*new_to_map);
2555
}
2556

    
2557

    
2558
void Genesis::MakeFunctionInstancePrototypeWritable() {
2559
  // The maps with writable prototype are created in CreateEmptyFunction
2560
  // and CreateStrictModeFunctionMaps respectively. Initially the maps are
2561
  // created with read-only prototype for JS builtins processing.
2562
  ASSERT(!function_map_writable_prototype_.is_null());
2563
  ASSERT(!strict_mode_function_map_writable_prototype_.is_null());
2564

    
2565
  // Replace function instance maps to make prototype writable.
2566
  native_context()->set_function_map(*function_map_writable_prototype_);
2567
  native_context()->set_strict_mode_function_map(
2568
      *strict_mode_function_map_writable_prototype_);
2569
}
2570

    
2571

    
2572
Genesis::Genesis(Isolate* isolate,
2573
                 Handle<Object> global_object,
2574
                 v8::Handle<v8::ObjectTemplate> global_template,
2575
                 v8::ExtensionConfiguration* extensions)
2576
    : isolate_(isolate),
2577
      active_(isolate->bootstrapper()) {
2578
  result_ = Handle<Context>::null();
2579
  // If V8 cannot be initialized, just return.
2580
  if (!V8::Initialize(NULL)) return;
2581

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

    
2586
  // During genesis, the boilerplate for stack overflow won't work until the
2587
  // environment has been at least partially initialized. Add a stack check
2588
  // before entering JS code to catch overflow early.
2589
  StackLimitCheck check(isolate);
2590
  if (check.HasOverflowed()) return;
2591

    
2592
  // We can only de-serialize a context if the isolate was initialized from
2593
  // a snapshot. Otherwise we have to build the context from scratch.
2594
  if (isolate->initialized_from_snapshot()) {
2595
    native_context_ = Snapshot::NewContextFromSnapshot(isolate);
2596
  } else {
2597
    native_context_ = Handle<Context>();
2598
  }
2599

    
2600
  if (!native_context().is_null()) {
2601
    AddToWeakNativeContextList(*native_context());
2602
    isolate->set_context(*native_context());
2603
    isolate->counters()->contexts_created_by_snapshot()->Increment();
2604
    Handle<GlobalObject> inner_global;
2605
    Handle<JSGlobalProxy> global_proxy =
2606
        CreateNewGlobals(global_template,
2607
                         global_object,
2608
                         &inner_global);
2609

    
2610
    HookUpGlobalProxy(inner_global, global_proxy);
2611
    HookUpInnerGlobal(inner_global);
2612

    
2613
    if (!ConfigureGlobalObjects(global_template)) return;
2614
  } else {
2615
    // We get here if there was no context snapshot.
2616
    CreateRoots();
2617
    Handle<JSFunction> empty_function = CreateEmptyFunction(isolate);
2618
    CreateStrictModeFunctionMaps(empty_function);
2619
    Handle<GlobalObject> inner_global;
2620
    Handle<JSGlobalProxy> global_proxy =
2621
        CreateNewGlobals(global_template, global_object, &inner_global);
2622
    HookUpGlobalProxy(inner_global, global_proxy);
2623
    InitializeGlobal(inner_global, empty_function);
2624
    InstallJSFunctionResultCaches();
2625
    InitializeNormalizedMapCaches();
2626
    if (!InstallNatives()) return;
2627

    
2628
    MakeFunctionInstancePrototypeWritable();
2629

    
2630
    if (!ConfigureGlobalObjects(global_template)) return;
2631
    isolate->counters()->contexts_created_from_scratch()->Increment();
2632
  }
2633

    
2634
  // Initialize experimental globals and install experimental natives.
2635
  InitializeExperimentalGlobal();
2636
  if (!InstallExperimentalNatives()) return;
2637

    
2638
  // Initially seed the per-context random number generator
2639
  // using the per-isolate random number generator.
2640
  uint32_t* state = reinterpret_cast<uint32_t*>(
2641
      native_context()->random_seed()->GetDataStartAddress());
2642
  do {
2643
    isolate->random_number_generator()->NextBytes(state, kRandomStateSize);
2644
  } while (state[0] == 0 || state[1] == 0);
2645

    
2646
  result_ = native_context();
2647
}
2648

    
2649

    
2650
// Support for thread preemption.
2651

    
2652
// Reserve space for statics needing saving and restoring.
2653
int Bootstrapper::ArchiveSpacePerThread() {
2654
  return sizeof(NestingCounterType);
2655
}
2656

    
2657

    
2658
// Archive statics that are thread local.
2659
char* Bootstrapper::ArchiveState(char* to) {
2660
  *reinterpret_cast<NestingCounterType*>(to) = nesting_;
2661
  nesting_ = 0;
2662
  return to + sizeof(NestingCounterType);
2663
}
2664

    
2665

    
2666
// Restore statics that are thread local.
2667
char* Bootstrapper::RestoreState(char* from) {
2668
  nesting_ = *reinterpret_cast<NestingCounterType*>(from);
2669
  return from + sizeof(NestingCounterType);
2670
}
2671

    
2672

    
2673
// Called when the top-level V8 mutex is destroyed.
2674
void Bootstrapper::FreeThreadResources() {
2675
  ASSERT(!IsActive());
2676
}
2677

    
2678
} }  // namespace v8::internal