1'use strict'; 2 3const { 4 Error, 5 ObjectDefineProperty, 6 ObjectGetOwnPropertyDescriptor, 7 ObjectSetPrototypeOf, 8 SafeArrayIterator, 9 SafeSet, 10} = primordials; 11 12const binding = internalBinding('mksnapshot'); 13const { BuiltinModule: { normalizeRequirableId } } = require('internal/bootstrap/realm'); 14const { 15 compileSerializeMain, 16} = binding; 17 18const { 19 getOptionValue, 20} = require('internal/options'); 21 22const { 23 readFileSync, 24} = require('fs'); 25 26const supportedModules = new SafeSet(new SafeArrayIterator([ 27 // '_http_agent', 28 // '_http_client', 29 // '_http_common', 30 // '_http_incoming', 31 // '_http_outgoing', 32 // '_http_server', 33 '_stream_duplex', 34 '_stream_passthrough', 35 '_stream_readable', 36 '_stream_transform', 37 '_stream_wrap', 38 '_stream_writable', 39 // '_tls_common', 40 // '_tls_wrap', 41 'assert', 42 'assert/strict', 43 // 'async_hooks', 44 'buffer', 45 // 'child_process', 46 // 'cluster', 47 'console', 48 'constants', 49 'crypto', 50 // 'dgram', 51 // 'diagnostics_channel', 52 'dns', 53 // 'dns/promises', 54 // 'domain', 55 'events', 56 'fs', 57 'fs/promises', 58 // 'http', 59 // 'http2', 60 // 'https', 61 // 'inspector', 62 // 'module', 63 // 'net', 64 'os', 65 'path', 66 'path/posix', 67 'path/win32', 68 // 'perf_hooks', 69 'process', 70 'punycode', 71 'querystring', 72 // 'readline', 73 // 'repl', 74 'stream', 75 'stream/promises', 76 'string_decoder', 77 'sys', 78 'timers', 79 'timers/promises', 80 // 'tls', 81 // 'trace_events', 82 // 'tty', 83 'url', 84 'util', 85 'util/types', 86 'v8', 87 // 'vm', 88 // 'worker_threads', 89 'zlib', 90])); 91 92const warnedModules = new SafeSet(); 93function supportedInUserSnapshot(id) { 94 return supportedModules.has(id); 95} 96 97function requireForUserSnapshot(id) { 98 const normalizedId = normalizeRequirableId(id); 99 if (!normalizedId) { 100 // eslint-disable-next-line no-restricted-syntax 101 const err = new Error( 102 `Cannot find module '${id}'. `, 103 ); 104 err.code = 'MODULE_NOT_FOUND'; 105 throw err; 106 } 107 if (!supportedInUserSnapshot(normalizedId)) { 108 if (!warnedModules.has(normalizedId)) { 109 process.emitWarning( 110 `built-in module ${id} is not yet supported in user snapshots`); 111 warnedModules.add(normalizedId); 112 } 113 } 114 115 return require(normalizedId); 116} 117 118function main() { 119 const { 120 prepareMainThreadExecution, 121 } = require('internal/process/pre_execution'); 122 123 prepareMainThreadExecution(true, false); 124 125 const file = process.argv[1]; 126 const path = require('path'); 127 const filename = path.resolve(file); 128 const dirname = path.dirname(filename); 129 const source = readFileSync(file, 'utf-8'); 130 const serializeMainFunction = compileSerializeMain(filename, source); 131 132 const { 133 initializeCallbacks, 134 namespace: { 135 addSerializeCallback, 136 addDeserializeCallback, 137 }, 138 } = require('internal/v8/startup_snapshot'); 139 initializeCallbacks(); 140 141 let stackTraceLimitDesc; 142 addDeserializeCallback(() => { 143 if (stackTraceLimitDesc !== undefined) { 144 ObjectDefineProperty(Error, 'stackTraceLimit', stackTraceLimitDesc); 145 } 146 }); 147 148 if (getOptionValue('--inspect-brk')) { 149 internalBinding('inspector').callAndPauseOnStart( 150 serializeMainFunction, undefined, 151 requireForUserSnapshot, filename, dirname); 152 } else { 153 serializeMainFunction(requireForUserSnapshot, filename, dirname); 154 } 155 156 addSerializeCallback(() => { 157 stackTraceLimitDesc = ObjectGetOwnPropertyDescriptor(Error, 'stackTraceLimit'); 158 159 if (stackTraceLimitDesc !== undefined) { 160 // We want to use null-prototype objects to not rely on globally mutable 161 // %Object.prototype%. 162 ObjectSetPrototypeOf(stackTraceLimitDesc, null); 163 process._rawDebug('Deleting Error.stackTraceLimit from the snapshot. ' + 164 'It will be re-installed after deserialization'); 165 delete Error.stackTraceLimit; 166 } 167 }); 168} 169 170main(); 171