prepack
Version:
Execute a JS bundle, serialize global state and side effects to a snapshot that can be quickly restored.
115 lines (90 loc) • 4.45 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.default = _default;
var _index = require("../domains/index.js");
var _index2 = require("../values/index.js");
var _singletons = require("../singletons.js");
var _index3 = require("../methods/index.js");
var _invariant = _interopRequireDefault(require("../invariant.js"));
var _errors = require("../errors.js");
var _types = require("@babel/types");
var _generator = require("../utils/generator.js");
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
/**
* Copyright (c) 2017-present, Facebook, Inc.
* All rights reserved.
*
* This source code is licensed under the BSD-style license found in the
* LICENSE file in the root directory of this source tree. An additional grant
* of patent rights can be found in the PATENTS file in the same directory.
*/
function _default(ast, strictCode, env, realm) {
// ECMA262 12.3.3.1 We just implement this method inline since it's only called here.
// 1. Return ? EvaluateNew(NewExpression, empty).
// ECMA262 2.3.3.1.1
let constructProduction = ast.callee;
let args = ast.arguments; // These steps not necessary due to our AST representation.
// 1. Assert: constructProduction is either a NewExpression or a MemberExpression.
// 2. Assert: arguments is either empty or an Arguments production.
// 3. Let ref be the result of evaluating constructProduction.
let ref = env.evaluate(constructProduction, strictCode); // 4. Let constructor be ? GetValue(ref).
let constructor = _singletons.Environment.GetValue(realm, ref);
let argsList; // 5. If arguments is empty, let argList be a new empty List.
if (!args.length) {
argsList = [];
} else {
// 6. Else,
// a. Let argList be ArgumentListEvaluation of arguments.
argsList = (0, _index3.ArgumentListEvaluation)(realm, strictCode, env, args); // BabelNodeNewExpression needs updating
// This step not necessary since we propagate completions with exceptions.
// b. ReturnIfAbrupt(argList).
}
let previousLoc = realm.setNextExecutionContextLocation(ast.loc);
try {
// If we are in pure scope, attempt to recover from creating the construct if
// it fails by creating a temporal abstract
if (realm.isInPureScope()) {
return tryToEvaluateConstructOrLeaveAsAbstract(constructor, argsList, strictCode, realm);
} else {
return createConstruct(constructor, argsList, realm);
}
} finally {
realm.setNextExecutionContextLocation(previousLoc);
}
}
function tryToEvaluateConstructOrLeaveAsAbstract(constructor, argsList, strictCode, realm) {
let effects;
try {
effects = realm.evaluateForEffects(() => createConstruct(constructor, argsList, realm), undefined, "tryToEvaluateConstructOrLeaveAsAbstract");
} catch (error) {
// if a FatalError occurs when constructing the constructor
// then try and recover and create an abstract for this construct
if (error instanceof _errors.FatalError) {
// we need to leak all the arguments and the constructor
_singletons.Leak.value(realm, constructor);
for (let arg of argsList) {
_singletons.Leak.value(realm, arg);
}
let abstractValue = realm.evaluateWithPossibleThrowCompletion(() => _index2.AbstractValue.createTemporalFromBuildFunction(realm, _index2.ObjectValue, [constructor, ...argsList], (0, _generator.createOperationDescriptor)("NEW_EXPRESSION")), _index.TypesDomain.topVal, _index.ValuesDomain.topVal);
(0, _invariant.default)(abstractValue instanceof _index2.AbstractObjectValue);
return abstractValue;
} else {
throw error;
}
}
realm.applyEffects(effects);
let completion = realm.returnOrThrowCompletion(effects.result);
(0, _invariant.default)(completion instanceof _index2.ObjectValue || completion instanceof _index2.AbstractObjectValue);
return completion;
}
function createConstruct(constructor, argsList, realm) {
// 7. If IsConstructor(constructor) is false, throw a TypeError exception.
if ((0, _index3.IsConstructor)(realm, constructor) === false) {
throw realm.createErrorThrowCompletion(realm.intrinsics.TypeError);
}
(0, _invariant.default)(constructor instanceof _index2.ObjectValue); // 8. Return ? Construct(constructor, argList).
return (0, _index3.Construct)(realm, constructor, argsList);
}
//# sourceMappingURL=NewExpression.js.map