Bug 930414 - Add hook for HostResolveImportedModule r=shu

This commit is contained in:
Jon Coppeard 2015-09-23 15:47:39 +01:00
parent 84fc2ff3a5
commit f24ee6bba0
4 changed files with 74 additions and 1 deletions

View File

@ -703,7 +703,8 @@ struct JSClass {
// the beginning of every global object's slots for use by the
// application.
#define JSCLASS_GLOBAL_APPLICATION_SLOTS 5
#define JSCLASS_GLOBAL_SLOT_COUNT (JSCLASS_GLOBAL_APPLICATION_SLOTS + JSProto_LIMIT * 3 + 32)
#define JSCLASS_GLOBAL_SLOT_COUNT \
(JSCLASS_GLOBAL_APPLICATION_SLOTS + JSProto_LIMIT * 3 + 33)
#define JSCLASS_GLOBAL_FLAGS_WITH_SLOTS(n) \
(JSCLASS_IS_GLOBAL | JSCLASS_HAS_RESERVED_SLOTS(JSCLASS_GLOBAL_SLOT_COUNT + (n)))
#define JSCLASS_GLOBAL_FLAGS \

View File

@ -3105,6 +3105,29 @@ ParseModule(JSContext* cx, unsigned argc, Value* vp)
return true;
}
static bool
SetModuleResolveHook(JSContext* cx, unsigned argc, Value* vp)
{
CallArgs args = CallArgsFromVp(argc, vp);
if (args.length() != 1) {
JS_ReportErrorNumber(cx, GetErrorMessage, nullptr,
JSMSG_MORE_ARGS_NEEDED, "setModuleResolveHook", "0", "s");
return false;
}
if (!args[0].isObject() || !args[0].toObject().is<JSFunction>()) {
const char* typeName = InformalValueTypeName(args[0]);
JS_ReportError(cx, "expected hook function, got %s", typeName);
return false;
}
RootedFunction hook(cx, &args[0].toObject().as<JSFunction>());
Rooted<GlobalObject*> global(cx, cx->global());
global->setModuleResolveHook(hook);
args.rval().setUndefined();
return true;
}
static bool
Parse(JSContext* cx, unsigned argc, Value* vp)
{
@ -4667,6 +4690,12 @@ static const JSFunctionSpecWithHelp shell_functions[] = {
"parseModule(code)",
" Parses source text as a module and returns a Module object."),
JS_FN_HELP("setModuleResolveHook", SetModuleResolveHook, 1, 0,
"setModuleResolveHook(function(module, specifier) {})",
" Set the HostResolveImportedModule hook to |function|.\n"
" This hook is used to look up a previously loaded module object. It should\n"
" be implemented by the module loader."),
JS_FN_HELP("parse", Parse, 1, 0,
"parse(code)",
" Parses a string, potentially throwing."),

View File

@ -111,6 +111,7 @@ class GlobalObject : public NativeObject
INT16X8_TYPE_DESCR,
INT32X4_TYPE_DESCR,
FOR_OF_PIC_CHAIN,
MODULE_RESOLVE_HOOK,
/* Total reserved-slot count for global objects. */
RESERVED_SLOTS
@ -750,6 +751,19 @@ class GlobalObject : public NativeObject
return &forOfPIC.toObject().as<NativeObject>();
}
static NativeObject* getOrCreateForOfPICObject(JSContext* cx, Handle<GlobalObject*> global);
void setModuleResolveHook(HandleFunction hook) {
MOZ_ASSERT(hook);
setSlot(MODULE_RESOLVE_HOOK, ObjectValue(*hook));
}
JSFunction* moduleResolveHook() {
Value value = getSlotRef(MODULE_RESOLVE_HOOK);
if (value.isUndefined())
return nullptr;
return &value.toObject().as<JSFunction>();
}
};
template<>

View File

@ -21,6 +21,7 @@
#include "builtin/Intl.h"
#include "builtin/MapObject.h"
#include "builtin/ModuleObject.h"
#include "builtin/Object.h"
#include "builtin/Reflect.h"
#include "builtin/SelfHostingDefines.h"
@ -1244,6 +1245,33 @@ intrinsic_ConstructorForTypedArray(JSContext* cx, unsigned argc, Value* vp)
return true;
}
static bool
intrinsic_HostResolveImportedModule(JSContext* cx, unsigned argc, Value* vp)
{
CallArgs args = CallArgsFromVp(argc, vp);
MOZ_ASSERT(args.length() == 2);
MOZ_ASSERT(args[0].toObject().is<ModuleObject>());
MOZ_ASSERT(args[1].isString());
RootedFunction moduleResolveHook(cx, cx->global()->moduleResolveHook());
if (!moduleResolveHook) {
JS_ReportError(cx, "Module resolve hook not set");
return false;
}
RootedValue result(cx);
if (!JS_CallFunction(cx, nullptr, moduleResolveHook, args, &result))
return false;
if (!result.isObject() || !result.toObject().is<ModuleObject>()) {
JS_ReportError(cx, "Module resolve hook did not return Module object");
return false;
}
args.rval().set(result);
return true;
}
// The self-hosting global isn't initialized with the normal set of builtins.
// Instead, individual C++-implemented functions that're required by
// self-hosted code are defined as global functions. Accessing these
@ -1485,6 +1513,7 @@ static const JSFunctionSpec intrinsic_functions[] = {
JS_FN("regexp_test_no_statics", regexp_test_no_statics, 2,0),
JS_FN("regexp_construct_no_statics", regexp_construct_no_statics, 2,0),
JS_FN("HostResolveImportedModule", intrinsic_HostResolveImportedModule, 2, 0),
JS_FS_END
};