1 // Copyright 2014 the V8 project authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #ifndef V8_BOOTSTRAPPER_H_ 6 #define V8_BOOTSTRAPPER_H_ 7 8 #include "src/factory.h" 9 10 namespace v8 { 11 namespace internal { 12 13 // A SourceCodeCache uses a FixedArray to store pairs of 14 // (OneByteString*, JSFunction*), mapping names of native code files 15 // (runtime.js, etc.) to precompiled functions. Instead of mapping 16 // names to functions it might make sense to let the JS2C tool 17 // generate an index for each native JS file. 18 class SourceCodeCache final BASE_EMBEDDED { 19 public: SourceCodeCache(Script::Type type)20 explicit SourceCodeCache(Script::Type type): type_(type), cache_(NULL) { } 21 Initialize(Isolate * isolate,bool create_heap_objects)22 void Initialize(Isolate* isolate, bool create_heap_objects) { 23 cache_ = create_heap_objects ? isolate->heap()->empty_fixed_array() : NULL; 24 } 25 Iterate(ObjectVisitor * v)26 void Iterate(ObjectVisitor* v) { 27 v->VisitPointer(bit_cast<Object**, FixedArray**>(&cache_)); 28 } 29 Lookup(Vector<const char> name,Handle<SharedFunctionInfo> * handle)30 bool Lookup(Vector<const char> name, Handle<SharedFunctionInfo>* handle) { 31 for (int i = 0; i < cache_->length(); i+=2) { 32 SeqOneByteString* str = SeqOneByteString::cast(cache_->get(i)); 33 if (str->IsUtf8EqualTo(name)) { 34 *handle = Handle<SharedFunctionInfo>( 35 SharedFunctionInfo::cast(cache_->get(i + 1))); 36 return true; 37 } 38 } 39 return false; 40 } 41 Add(Vector<const char> name,Handle<SharedFunctionInfo> shared)42 void Add(Vector<const char> name, Handle<SharedFunctionInfo> shared) { 43 Isolate* isolate = shared->GetIsolate(); 44 Factory* factory = isolate->factory(); 45 HandleScope scope(isolate); 46 int length = cache_->length(); 47 Handle<FixedArray> new_array = factory->NewFixedArray(length + 2, TENURED); 48 cache_->CopyTo(0, *new_array, 0, cache_->length()); 49 cache_ = *new_array; 50 Handle<String> str = 51 factory->NewStringFromAscii(name, TENURED).ToHandleChecked(); 52 DCHECK(!str.is_null()); 53 cache_->set(length, *str); 54 cache_->set(length + 1, *shared); 55 Script::cast(shared->script())->set_type(type_); 56 } 57 58 private: 59 Script::Type type_; 60 FixedArray* cache_; 61 DISALLOW_COPY_AND_ASSIGN(SourceCodeCache); 62 }; 63 64 enum GlobalContextType { FULL_CONTEXT, DEBUG_CONTEXT }; 65 66 // The Boostrapper is the public interface for creating a JavaScript global 67 // context. 68 class Bootstrapper final { 69 public: 70 static void InitializeOncePerProcess(); 71 static void TearDownExtensions(); 72 73 // Requires: Heap::SetUp has been called. 74 void Initialize(bool create_heap_objects); 75 void TearDown(); 76 77 // Creates a JavaScript Global Context with initial object graph. 78 // The returned value is a global handle casted to V8Environment*. 79 Handle<Context> CreateEnvironment( 80 MaybeHandle<JSGlobalProxy> maybe_global_proxy, 81 v8::Local<v8::ObjectTemplate> global_object_template, 82 v8::ExtensionConfiguration* extensions, size_t context_snapshot_index, 83 GlobalContextType context_type = FULL_CONTEXT); 84 85 Handle<JSGlobalProxy> NewRemoteContext( 86 MaybeHandle<JSGlobalProxy> maybe_global_proxy, 87 v8::Local<v8::ObjectTemplate> global_object_template); 88 89 // Detach the environment from its outer global object. 90 void DetachGlobal(Handle<Context> env); 91 92 // Traverses the pointers for memory management. 93 void Iterate(ObjectVisitor* v); 94 95 // Accessor for the native scripts source code. 96 template <class Source> 97 Handle<String> SourceLookup(int index); 98 99 // Tells whether bootstrapping is active. IsActive()100 bool IsActive() const { return nesting_ != 0; } 101 102 // Support for thread preemption. 103 static int ArchiveSpacePerThread(); 104 char* ArchiveState(char* to); 105 char* RestoreState(char* from); 106 void FreeThreadResources(); 107 108 // Used for new context creation. 109 bool InstallExtensions(Handle<Context> native_context, 110 v8::ExtensionConfiguration* extensions); 111 extensions_cache()112 SourceCodeCache* extensions_cache() { return &extensions_cache_; } 113 114 static bool CompileNative(Isolate* isolate, Vector<const char> name, 115 Handle<String> source, int argc, 116 Handle<Object> argv[], NativesFlag natives_flag); 117 static bool CompileBuiltin(Isolate* isolate, int index); 118 static bool CompileExperimentalBuiltin(Isolate* isolate, int index); 119 static bool CompileExtraBuiltin(Isolate* isolate, int index); 120 static bool CompileExperimentalExtraBuiltin(Isolate* isolate, int index); 121 122 static void ExportFromRuntime(Isolate* isolate, Handle<JSObject> container); 123 static void ExportExperimentalFromRuntime(Isolate* isolate, 124 Handle<JSObject> container); 125 126 private: 127 Isolate* isolate_; 128 typedef int NestingCounterType; 129 NestingCounterType nesting_; 130 SourceCodeCache extensions_cache_; 131 132 friend class BootstrapperActive; 133 friend class Isolate; 134 friend class NativesExternalStringResource; 135 136 explicit Bootstrapper(Isolate* isolate); 137 138 static v8::Extension* free_buffer_extension_; 139 static v8::Extension* gc_extension_; 140 static v8::Extension* externalize_string_extension_; 141 static v8::Extension* statistics_extension_; 142 static v8::Extension* trigger_failure_extension_; 143 static v8::Extension* ignition_statistics_extension_; 144 145 DISALLOW_COPY_AND_ASSIGN(Bootstrapper); 146 }; 147 148 149 class BootstrapperActive final BASE_EMBEDDED { 150 public: BootstrapperActive(Bootstrapper * bootstrapper)151 explicit BootstrapperActive(Bootstrapper* bootstrapper) 152 : bootstrapper_(bootstrapper) { 153 ++bootstrapper_->nesting_; 154 } 155 ~BootstrapperActive()156 ~BootstrapperActive() { 157 --bootstrapper_->nesting_; 158 } 159 160 private: 161 Bootstrapper* bootstrapper_; 162 163 DISALLOW_COPY_AND_ASSIGN(BootstrapperActive); 164 }; 165 166 167 class NativesExternalStringResource final 168 : public v8::String::ExternalOneByteStringResource { 169 public: NativesExternalStringResource(const char * source,size_t length)170 NativesExternalStringResource(const char* source, size_t length) 171 : data_(source), length_(length) {} data()172 const char* data() const override { return data_; } length()173 size_t length() const override { return length_; } 174 175 private: 176 const char* data_; 177 size_t length_; 178 }; 179 180 } // namespace internal 181 } // namespace v8 182 183 #endif // V8_BOOTSTRAPPER_H_ 184