Last active
September 19, 2018 05:13
-
-
Save rpf5573/f495b6ee2fd908b0c0aa7940650fd492 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// loader.js를 실행하고 나서, node.js를 실행하는데, node.js안에서는 이렇게 함수가 호출되어있다. | |
// 즉, loader.js에서 load에 필요한 함수들을 정의한 뒤에, node.js에서 그걸 사용하면서 실제로 load를 진행한다. | |
startup(); | |
// lib/internal/bootstrap/node.js : 31 | |
function startup() { | |
// Make process.argv[1] into a full path. | |
const path = NativeModule.require('path'); | |
process.argv[1] = path.resolve(process.argv[1]); | |
// loader.js를 먼저 실행했기 때문에 node.js에서 가져와 쓸 수 있다 | |
const CJSModule = NativeModule.require('internal/modules/cjs/loader.js/loader'); | |
preloadModules(); | |
const fs = NativeModule.require('fs'); | |
const filename = CJSModule._resolveFilename(process.argv[1]); | |
const source = fs.readFileSync(filename, 'utf-8'); // 나의 index.js파일을 읽어들인다 | |
checkScriptSyntax(source, filename); // 문법 체크 | |
CJSModule.runMain(); | |
} | |
// lib/internal/modules/cjs/loader.js : 733 | |
Module.runMain = function() { | |
// argv[1] 안에 index.js가 들어있다.(아마도...) | |
Module._load(process.argv[1], null, true); | |
// Handle any nextTicks added in the first tick of the program | |
process._tickCallback(); | |
}; | |
// lib/internal/modules/cjs/loader.js : 506 | |
Module._load = function(request, parent, isMain) { | |
// Don't call updateChildren(), Module constructor already does. | |
var module = new Module(filename, parent); | |
tryModuleLoad(module, filename); | |
return module.exports; | |
}; | |
// lib/internal/modules/cjs/loader.js : 539 | |
function tryModuleLoad(module, filename) { | |
module.load(filename); | |
} | |
// lib/internal/modules/cjs/loader.js : 593 | |
Module.prototype.load = function(filename) { | |
Module._extensions[extension](this, filename); // == Module._extensions['.js'](this, filename) | |
}; | |
// lib/internal/modules/cjs/loader.js : 702 | |
Module._extensions['.js'] = function(module, filename) { | |
var content = fs.readFileSync(filename, 'utf8'); // 파일을 HardDisk에서 읽어 들여서 | |
module._compile(stripBOM(content), filename); // 컴파일! | |
}; | |
// lib/internal/modules/cjs/loader.js : 654 | |
Module.prototype._compile = function(content, filename) { | |
// create wrapper function | |
var wrapper = Module.wrap(content); | |
var compiledWrapper = vm.runInThisContext(wrapper, { | |
filename: filename, | |
lineOffset: 0, | |
displayErrors: true | |
}); | |
}; | |
// lib/internal/modules/cjs/loader.js : 125 | |
Module.wrap = function(script) { | |
return Module.wrapper[0] + script + Module.wrapper[1]; | |
}; | |
// lib/internal/modules/cjs/loader.js : 129 | |
Module.wrapper = [ | |
'(function (exports, require, module, __filename, __dirname) { ', | |
'\n});' | |
]; | |
// wrapper가 실행되면 이렇게 된다. | |
(function (exports, require, module, __filename, __dirname) { | |
// 내 index.js code가 여기에 들어간다 | |
// 이런 연유로 exports()나 require()을 내 코드에서 쓸 수 있다 | |
}); | |
// lib/vm.js : 287 | |
function runInThisContext(code, options) { | |
return createScript(code, options).runInThisContext(options); | |
} | |
// lib/vm.js : 89 | |
// Script의 public 함수 | |
runInThisContext(options) { | |
return super.runInThisContext(...args); | |
} | |
// lib/vm.js : 40 | |
// ContextifyScript가 super다 | |
class Script extends ContextifyScript { ~~ } | |
// lib/vm.js : 25 | |
const { | |
ContextifyScript, | |
makeContext, | |
isContext: _isContext, | |
compileFunction: _compileFunction | |
} = internalBinding('contextify'); | |
// src/node_contextify.cc | |
// 이렇게 등록했기 때문에 아까, javascript 단에서 super.runInThisContext()를 쓸 수 있게된것이다.( c++ 함수를 javascript에서도 쓸수있도록 연결 ) | |
env->SetProtoMethod(script_tmpl, "runInThisContext", RunInThisContext); | |
// src/node_contextify.cc | |
static void RunInThisContext(const FunctionCallbackInfo<Value>& args) { | |
Environment* env = Environment::GetCurrent(args); | |
// Javascript가상머신이 javascript코드를 실행한다 | |
EvalMachine(env, timeout, display_errors, break_on_sigint, args); | |
} | |
// src/node_contextify.cc | |
static bool EvalMachine(Environment* env, | |
const int64_t timeout, | |
const bool display_errors, | |
const bool break_on_sigint, | |
const FunctionCallbackInfo<Value>& args) { | |
Local<Script> script = unbound_script->BindToCurrentContext(); | |
result = script->Run(env->context()); | |
} | |
// 여기까지가 LoadEnvirenment ! | |
// 이 모든 과정이 끝난 다음에, node.cc로 다시 돌아간다. 그리고 event-loop를 돌린다. |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment