Javascript 在Duktape中,如何将JS源文件内容转换为字节码
我想知道下面描述的步骤是如何完成的:Javascript 在Duktape中,如何将JS源文件内容转换为字节码,javascript,c++,duktape,Javascript,C++,Duktape,我想知道下面描述的步骤是如何完成的: 如何将JS源文件(test.JS有两个函数,funcA()和funcB())转换为字节码 如何将生成的字节码加载到duktape并调用其中一个函数,比如funcA() 谢谢 test.js: function funcA() { print("funcA()"); } function funcB() { print("funcB()"); } main.cpp int main() { duk_context* ctx = du
function funcA() {
print("funcA()");
}
function funcB() {
print("funcB()");
}
main.cpp
int main() {
duk_context* ctx = duk_create_heap_default();
std::string byteCodeBuff; // buffer where to save the byte code;
{ // generate the bytecode from 'sourceFilePath'
const char* sourceCodeFilePath = "test.js"; // contains the JS code
// Step 1 How to 'dump' the 'sourceFilePath' to bytecode buffer ???
// get the duktape bytecode
duk_size_t bufferSize = 0;
const char* bytecode = (const char*)duk_get_buffer(ctx, -1, &bufferSize);
// save the bytecode to byteCodeBuff
byteCodeBuff.assign(bytecode,bufferSize);
duk_pop(ctx); // bytecode buffer
}
{ // load the bytecode into duktape
const size_t length = byteCodeBuff.size(); // bytecode length
const char* bytecode = &byteCodeBuff.front(); // pointer to bytecode
char* dukBuff = (char*)duk_push_fixed_buffer(ctx, length); // push a duk buffer to stack
memcpy(dukBuff, bytecode, length); // copy the bytecode to the duk buffer
// Step 2 ??? How start using the bytecode
// ??? How to invoke funcA()
// ??? How to invoke funcB()
}
duk_destroy_heap(ctx);
return 0;
}
Duktape提供了转换字节码的功能:
首先,只需加载您的文件:
// Step 1 (a):
char* sourceCode;
int sourceLen;
{ // load from file (excuse lack of error catching...)
ifstream fscript(sourceCodeFilePath,ios::in | ios::binary);
fscript.seekg(0,ios::end);
sourceLen= fscript.tellg();
buffer = new char[sourceLen];
fscript.seekg(0);
fscript.read(sourceCode,sourceLen);
}
// Step 1 (b):
// compile source code
duk_compile_lstring(ctx,0,sourceCode,sourceLen); // compiles to an ECMAScript function and puts it on the stack top
// dump the code into a buffer
duk_dump_function(ctx); // replaces the stack top function with its bytecode
// Step 2 (a):
// replaces the buffer on the stack top with the original function
duk_load_function(ctx);
// since this is a global script, it must be executed before calling the invidual functions
duk_call(ctx,0); // perhaps consider using duk_pcall() instead
// Step 2 (b):
// push the global object on the stack to get its properties
duk_push_global_object(ctx);
// obtain the function with the name "funcA" and push it on the stack
duk_get_prop_string(ctx,-1,"funcA"); // key name / global function name
duk_require_function(ctx,-1); // require this is a function before calling it
// now invoke it!
// duk_push_* arguments here
duk_call(ctx,0); // 0: number of arguments
// duk_get_* (ctx,-1); to obtain return value
// pop function return value
duk_pop(ctx);
// current stack top: global object
// get next function
duk_get_prop_string(ctx,-1,"funcB");
// require it's a function
duk_require_function(ctx,-1);
// invoke it!
duk_call(ctx,0);
// pop return and global object off stack
duk_pop_2(ctx);