Skip to content

Commit 69f5a75

Browse files
fhinkelitaloacasas
authored andcommitted
test: add vm module edge cases
Add two, admittedly contrived, examples that test edge cases of the vm module. They demonstrate that the if statements `if (maybe_rv.IsEmpty())` and `if (maybe_prop_attr.IsNothing())` in the GetterCallback and the QueryCallback are observable. Both GetterCallback and QueryCallback explicitly check the global_proxy() if a property is not found on the sandbox. In these tests, the explicit check inside the callback yields different results than deferring the check until after the callback. The check is deferred, if the callbacks do not intercept, i.e., if args.GetReturnValue().Set() is not called. PR-URL: #11265 Reviewed-By: Colin Ihrig <[email protected]> Reviewed-By: James M Snell <[email protected]> Reviewed-By: Ben Noordhuis <[email protected]>
1 parent 308df11 commit 69f5a75

File tree

2 files changed

+62
-0
lines changed

2 files changed

+62
-0
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
'use strict';
2+
require('../common');
3+
const assert = require('assert');
4+
const vm = require('vm');
5+
6+
// The QueryCallback explicitly calls GetRealNamedPropertyAttributes
7+
// on the global proxy if the property is not found on the sandbox.
8+
//
9+
// foo is not defined on the sandbox until we call CopyProperties().
10+
// In the QueryCallback, we do not find the property on the sandbox
11+
// and look up its PropertyAttributes on the global_proxy().
12+
// PropertyAttributes are always flattened to a value
13+
// descriptor.
14+
const sandbox = {};
15+
vm.createContext(sandbox);
16+
const code = `Object.defineProperty(
17+
this,
18+
'foo',
19+
{ get: function() {return 17} }
20+
);
21+
var desc = Object.getOwnPropertyDescriptor(this, 'foo');`;
22+
23+
vm.runInContext(code, sandbox);
24+
// The descriptor is flattened. We wrongly have typeof desc.value = 'number'.
25+
assert.strictEqual(typeof sandbox.desc.get, 'function');
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
'use strict';
2+
require('../common');
3+
const assert = require('assert');
4+
const vm = require('vm');
5+
6+
// This, admittedly contrived, example tests an edge cases of the vm module.
7+
//
8+
// The GetterCallback explicitly checks the global_proxy() if a property is
9+
// not found on the sandbox. In the following test, the explicit check
10+
// inside the callback yields different results than deferring the
11+
// check until after the callback. The check is deferred if the
12+
// callback does not intercept, i.e., if args.GetReturnValue().Set() is
13+
// not called.
14+
15+
// Check that the GetterCallback explicitly calls GetRealNamedProperty()
16+
// on the global proxy if the property is not found on the sandbox.
17+
//
18+
// foo is not defined on the sandbox until we call CopyProperties().
19+
// In the GetterCallback, we do not find the property on the sandbox and
20+
// get the property from the global proxy. Since the return value is
21+
// the sandbox, we replace it by
22+
// the global_proxy to keep the correct identities.
23+
//
24+
// This test case is partially inspired by
25+
// https://github.com/nodejs/node/issues/855
26+
const sandbox = {console};
27+
sandbox.document = {defaultView: sandbox};
28+
vm.createContext(sandbox);
29+
const code = `Object.defineProperty(
30+
this,
31+
'foo',
32+
{ get: function() {return document.defaultView} }
33+
);
34+
var result = foo === this;`;
35+
36+
vm.runInContext(code, sandbox);
37+
assert.strictEqual(sandbox.result, true);

0 commit comments

Comments
 (0)