1'use strict'; 2const common = require('../common'); 3const assert = require('assert'); 4const vm = require('vm'); 5const spawnSync = require('child_process').spawnSync; 6 7function getSource(tag) { 8 return `(function ${tag}() { return '${tag}'; })`; 9} 10 11function produce(source, count) { 12 if (!count) 13 count = 1; 14 15 const out = spawnSync(process.execPath, [ '-e', ` 16 'use strict'; 17 const assert = require('assert'); 18 const vm = require('vm'); 19 20 var data; 21 for (var i = 0; i < ${count}; i++) { 22 var script = new vm.Script(process.argv[1], { 23 produceCachedData: true 24 }); 25 26 assert(!script.cachedDataProduced || script.cachedData instanceof Buffer); 27 28 if (script.cachedDataProduced) 29 data = script.cachedData.toString('base64'); 30 } 31 console.log(data); 32 `, source]); 33 34 assert.strictEqual(out.status, 0, String(out.stderr)); 35 36 return Buffer.from(out.stdout.toString(), 'base64'); 37} 38 39function testProduceConsume() { 40 const source = getSource('original'); 41 42 const data = produce(source); 43 44 for (const cachedData of common.getArrayBufferViews(data)) { 45 // It should consume code cache 46 const script = new vm.Script(source, { 47 cachedData 48 }); 49 assert(!script.cachedDataRejected); 50 assert.strictEqual(script.runInThisContext()(), 'original'); 51 } 52} 53testProduceConsume(); 54 55function testProduceMultiple() { 56 const source = getSource('original'); 57 58 produce(source, 3); 59} 60testProduceMultiple(); 61 62function testRejectInvalid() { 63 const source = getSource('invalid'); 64 65 const data = produce(source); 66 67 // It should reject invalid code cache 68 const script = new vm.Script(getSource('invalid_1'), { 69 cachedData: data 70 }); 71 assert(script.cachedDataRejected); 72 assert.strictEqual(script.runInThisContext()(), 'invalid_1'); 73} 74testRejectInvalid(); 75 76function testRejectSlice() { 77 const source = getSource('slice'); 78 79 const data = produce(source).slice(4); 80 81 const script = new vm.Script(source, { 82 cachedData: data 83 }); 84 assert(script.cachedDataRejected); 85} 86testRejectSlice(); 87 88// It should throw on non-Buffer cachedData 89assert.throws(() => { 90 new vm.Script('function abc() {}', { 91 cachedData: 'ohai' 92 }); 93}, { 94 code: 'ERR_INVALID_ARG_TYPE', 95 name: 'TypeError', 96 message: /must be an instance of Buffer, TypedArray, or DataView/ 97}); 98