Add the concept of a V8 extras exports object
Exposed to the extras as extrasExports (on the builtins object), on which they can put things that should be accessible from C++. Exposed to C++ through the V8 API as v8::Context::GetExtrasExportsObject(). Adding a test (in test-api.cc) required adding a simple extra, test-extra.js, which we build into the standalone builds. R=yangguo@chromium.org, jochen@chromium.org BUG= Review URL: https://codereview.chromium.org/1128113006 Cr-Commit-Position: refs/heads/master@{#28317}
This commit is contained in:
parent
297bb0ca8b
commit
ad547cea05
@ -100,6 +100,9 @@
|
||||
'msan%': '<(msan)',
|
||||
'tsan%': '<(tsan)',
|
||||
|
||||
# Add a simple extra solely for the purpose of the cctests
|
||||
'v8_extra_library_files': ['../test/cctest/test-extra.js'],
|
||||
|
||||
# .gyp files or targets should set v8_code to 1 if they build V8 specific
|
||||
# code, as opposed to external code. This variable is used to control such
|
||||
# things as the set of warnings to enable, and whether warnings are treated
|
||||
|
@ -6370,6 +6370,12 @@ class V8_EXPORT Context {
|
||||
*/
|
||||
V8_INLINE Local<Value> GetEmbedderData(int index);
|
||||
|
||||
/**
|
||||
* Gets the exports object used by V8 extras. Extra natives get a reference
|
||||
* to this object and can use it to export functionality.
|
||||
*/
|
||||
Local<Object> GetExtrasExportsObject();
|
||||
|
||||
/**
|
||||
* Sets the embedder data with the given index, growing the data as
|
||||
* needed. Note that index 0 currently has a special meaning for Chrome's
|
||||
|
@ -5492,6 +5492,14 @@ void Context::DetachGlobal() {
|
||||
}
|
||||
|
||||
|
||||
Local<v8::Object> Context::GetExtrasExportsObject() {
|
||||
i::Handle<i::Context> context = Utils::OpenHandle(this);
|
||||
i::Isolate* isolate = context->GetIsolate();
|
||||
i::Handle<i::JSObject> exports(context->extras_exports_object(), isolate);
|
||||
return Utils::ToLocal(exports);
|
||||
}
|
||||
|
||||
|
||||
void Context::AllowCodeGenerationFromStrings(bool allow) {
|
||||
i::Handle<i::Context> context = Utils::OpenHandle(this);
|
||||
i::Isolate* isolate = context->GetIsolate();
|
||||
|
@ -201,6 +201,7 @@ class Genesis BASE_EMBEDDED {
|
||||
void InitializeGlobal(Handle<GlobalObject> global_object,
|
||||
Handle<JSFunction> empty_function);
|
||||
void InitializeExperimentalGlobal();
|
||||
void InitializeExtrasExportsObject();
|
||||
// Installs the contents of the native .js files on the global objects.
|
||||
// Used for creating a context from scratch.
|
||||
void InstallNativeFunctions();
|
||||
@ -1441,6 +1442,20 @@ void Genesis::InitializeExperimentalGlobal() {
|
||||
}
|
||||
|
||||
|
||||
void Genesis::InitializeExtrasExportsObject() {
|
||||
Handle<JSObject> exports =
|
||||
factory()->NewJSObject(isolate()->object_function(), TENURED);
|
||||
|
||||
native_context()->set_extras_exports_object(*exports);
|
||||
|
||||
Handle<JSBuiltinsObject> builtins(native_context()->builtins());
|
||||
Handle<String> exports_string =
|
||||
factory()->InternalizeOneByteString(STATIC_CHAR_VECTOR("extrasExports"));
|
||||
Runtime::SetObjectProperty(isolate(), builtins, exports_string, exports,
|
||||
STRICT).Assert();
|
||||
}
|
||||
|
||||
|
||||
bool Genesis::CompileBuiltin(Isolate* isolate, int index) {
|
||||
Vector<const char> name = Natives::GetScriptName(index);
|
||||
Handle<String> source_code =
|
||||
@ -2962,6 +2977,7 @@ Genesis::Genesis(Isolate* isolate,
|
||||
// them after they have already been deserialized would also fail.
|
||||
if (!isolate->serializer_enabled()) {
|
||||
InitializeExperimentalGlobal();
|
||||
InitializeExtrasExportsObject();
|
||||
if (!InstallExperimentalNatives()) return;
|
||||
if (!InstallExtraNatives()) return;
|
||||
}
|
||||
|
@ -185,7 +185,8 @@ enum BindingFlags {
|
||||
V(MAP_ITERATOR_MAP_INDEX, Map, map_iterator_map) \
|
||||
V(SET_ITERATOR_MAP_INDEX, Map, set_iterator_map) \
|
||||
V(ARRAY_VALUES_ITERATOR_INDEX, JSFunction, array_values_iterator) \
|
||||
V(SCRIPT_CONTEXT_TABLE_INDEX, ScriptContextTable, script_context_table)
|
||||
V(SCRIPT_CONTEXT_TABLE_INDEX, ScriptContextTable, script_context_table) \
|
||||
V(EXTRAS_EXPORTS_OBJECT_INDEX, JSObject, extras_exports_object)
|
||||
|
||||
|
||||
// A table of all script contexts. Every loaded top-level script with top-level
|
||||
@ -422,6 +423,7 @@ class Context: public FixedArray {
|
||||
SCRIPT_CONTEXT_TABLE_INDEX,
|
||||
MAP_CACHE_INDEX,
|
||||
TO_LENGTH_FUN_INDEX,
|
||||
EXTRAS_EXPORTS_OBJECT_INDEX,
|
||||
|
||||
// Properties from here are treated as weak references by the full GC.
|
||||
// Scavenge treats them as strong references.
|
||||
|
@ -364,6 +364,12 @@ RUNTIME_FUNCTION(Runtime_NativeScriptsCount) {
|
||||
}
|
||||
|
||||
|
||||
RUNTIME_FUNCTION(Runtime_NativeExtrasCount) {
|
||||
DCHECK(args.length() == 0);
|
||||
return Smi::FromInt(ExtraNatives::GetBuiltinsCount());
|
||||
}
|
||||
|
||||
|
||||
// Returns V8 version as a string.
|
||||
RUNTIME_FUNCTION(Runtime_GetV8Version) {
|
||||
HandleScope scope(isolate);
|
||||
|
@ -592,6 +592,7 @@ namespace internal {
|
||||
F(Abort, 1, 1) \
|
||||
F(AbortJS, 1, 1) \
|
||||
F(NativeScriptsCount, 0, 1) \
|
||||
F(NativeExtrasCount, 0, 1) \
|
||||
F(GetV8Version, 0, 1) \
|
||||
F(DisassembleFunction, 1, 1) \
|
||||
F(TraceEnter, 0, 1) \
|
||||
|
@ -21029,3 +21029,21 @@ TEST(SealHandleScopeNested) {
|
||||
USE(obj);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
TEST(ExtrasExportsObject) {
|
||||
v8::Isolate* isolate = CcTest::isolate();
|
||||
v8::HandleScope handle_scope(isolate);
|
||||
LocalContext env;
|
||||
|
||||
// standalone.gypi ensures we include the test-extra.js file, which should
|
||||
// add the testExtraShouldReturnFive export
|
||||
v8::Local<v8::Object> exports = env->GetExtrasExportsObject();
|
||||
|
||||
auto func =
|
||||
exports->Get(v8_str("testExtraShouldReturnFive")).As<v8::Function>();
|
||||
auto undefined = v8::Undefined(isolate);
|
||||
auto result = func->Call(undefined, 0, {}).As<v8::Number>();
|
||||
|
||||
CHECK(result->Value() == 5.0);
|
||||
}
|
||||
|
11
test/cctest/test-extra.js
Normal file
11
test/cctest/test-extra.js
Normal file
@ -0,0 +1,11 @@
|
||||
// Copyright 2015 the V8 project authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
(function () {
|
||||
'use strict';
|
||||
|
||||
extrasExports.testExtraShouldReturnFive = function () {
|
||||
return 5;
|
||||
};
|
||||
})();
|
@ -66,7 +66,7 @@ for (i = 0; i < scripts.length; i++) {
|
||||
}
|
||||
|
||||
// This has to be updated if the number of native scripts change.
|
||||
assertEquals(%NativeScriptsCount(), named_native_count);
|
||||
assertEquals(%NativeScriptsCount() + %NativeExtrasCount(), named_native_count);
|
||||
// Only the 'gc' extension is loaded.
|
||||
assertEquals(1, extension_count);
|
||||
// This script and mjsunit.js has been loaded. If using d8, d8 loads
|
||||
|
Loading…
Reference in New Issue
Block a user