mirror of
https://github.com/QingdaoU/Judger.git
synced 2024-12-28 07:51:42 +00:00
use popen to run libjudger.so ✨
This commit is contained in:
parent
1dce5f71e3
commit
d54b84ab58
1
.gitignore
vendored
1
.gitignore
vendored
@ -8,3 +8,4 @@ __pycache__
|
|||||||
*.pyc
|
*.pyc
|
||||||
cmake-build-debug/
|
cmake-build-debug/
|
||||||
.ycm_extra_conf.py
|
.ycm_extra_conf.py
|
||||||
|
node_modules/
|
||||||
|
@ -1,18 +0,0 @@
|
|||||||
/*-----------------
|
|
||||||
* author: Rainboy
|
|
||||||
* email: rainboylvx@qq.com
|
|
||||||
* time: 2019年 04月 24日 星期三 18:22:46 CST
|
|
||||||
* problem: online judge-_id
|
|
||||||
*----------------*/
|
|
||||||
#include <cstdio>
|
|
||||||
#include <cstring>
|
|
||||||
#include <algorithm>
|
|
||||||
#include <string>
|
|
||||||
using namespace std;
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main(){
|
|
||||||
string a("je");
|
|
||||||
return 0;
|
|
||||||
}
|
|
@ -1,36 +1,8 @@
|
|||||||
{
|
{
|
||||||
"targets": [
|
"targets": [
|
||||||
{
|
|
||||||
"target_name": "judgerlib",
|
|
||||||
"type": "static_library",
|
|
||||||
"sources": [
|
|
||||||
"../../src/child.c",
|
|
||||||
"../../src/killer.c",
|
|
||||||
"../../src/logger.c",
|
|
||||||
"../../src/runner.c",
|
|
||||||
"../../src/rules/c_cpp.c",
|
|
||||||
"../../src/rules/c_cpp_file_io.c",
|
|
||||||
"../../src/rules/general.c"
|
|
||||||
],
|
|
||||||
'include_dirs':[
|
|
||||||
"../../src",
|
|
||||||
"../../src/rules"
|
|
||||||
]
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
"target_name": "judger",
|
"target_name": "judger",
|
||||||
"sources": [ "judger.cc"],
|
"sources": [ "judger.cc"]
|
||||||
'include_dirs':[
|
|
||||||
"../../src",
|
|
||||||
"../../src/rules"
|
|
||||||
],
|
|
||||||
"libraries":[
|
|
||||||
"-L/usr/lib","-lpthread","-lseccomp"
|
|
||||||
],
|
|
||||||
|
|
||||||
"dependencies": [
|
|
||||||
"judgerlib"
|
|
||||||
]
|
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
@ -1,13 +1,17 @@
|
|||||||
#include "node.h"
|
#include "node.h"
|
||||||
#include <cstdio>
|
#include <cstdio>
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
#include <string>
|
#include <string>
|
||||||
#include "../../src/runner.h"
|
#include <cstdlib>
|
||||||
|
#include <sys/wait.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
|
||||||
|
|
||||||
namespace demo {
|
namespace demo {
|
||||||
|
|
||||||
using v8::FunctionCallbackInfo;
|
using v8::FunctionCallbackInfo;
|
||||||
using v8::Isolate;
|
using v8::Isolate;
|
||||||
|
using v8::JSON;
|
||||||
using v8::Local;
|
using v8::Local;
|
||||||
using v8::Int32;
|
using v8::Int32;
|
||||||
using v8::Array;
|
using v8::Array;
|
||||||
@ -22,14 +26,18 @@ namespace demo {
|
|||||||
using v8::Context;
|
using v8::Context;
|
||||||
|
|
||||||
/* 转成数字 */
|
/* 转成数字 */
|
||||||
long ToNumber(Isolate * isolate,Local<Object> &args,char * key,long default_val){
|
void ToNumber(Isolate * isolate,Local<Value> &args,char * key,std::string &str){
|
||||||
Local<Context> context= isolate->GetCurrentContext();
|
Local<Context> context= isolate->GetCurrentContext();
|
||||||
Local<Value> val = args->Get(context,String::NewFromUtf8(isolate,key)).ToLocalChecked();
|
Local<Value> val = args->ToObject()->Get(context,String::NewFromUtf8(isolate,key)).ToLocalChecked();
|
||||||
if(val->IsNullOrUndefined())
|
if(val->IsNullOrUndefined())
|
||||||
return default_val;
|
return ;
|
||||||
else if( val->IsNumber()){
|
else if( val->IsNumber()){
|
||||||
Local<Integer> num = val->ToInteger(context).ToLocalChecked();
|
Local<Integer> num = val->ToInteger(context).ToLocalChecked();
|
||||||
return num->Value();
|
str+=" --";
|
||||||
|
str+=std::string(key);
|
||||||
|
str+="=";
|
||||||
|
str+=std::to_string(num->Value());
|
||||||
|
return ;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
isolate->ThrowException(Exception::Error(String::NewFromUtf8(isolate,"typeof argument must be Object!")));
|
isolate->ThrowException(Exception::Error(String::NewFromUtf8(isolate,"typeof argument must be Object!")));
|
||||||
@ -37,21 +45,30 @@ namespace demo {
|
|||||||
}
|
}
|
||||||
|
|
||||||
char * _ToCharPTR(Local<Value> &val,Local<Context> &context,char * str_content){
|
char * _ToCharPTR(Local<Value> &val,Local<Context> &context,char * str_content){
|
||||||
String::Utf8Value str_val( val->ToString(context).ToLocalChecked());
|
String::Utf8Value str_val( val->ToString(context).ToLocalChecked());
|
||||||
strcpy(str_content,*str_val);
|
strcpy(str_content,*str_val);
|
||||||
return str_content;
|
return str_content;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* 转成字符串 */
|
/* 转成字符串 */
|
||||||
char * ToCStr(Isolate * isolate,Local<Object> &args,char * key,char *default_val,char *str_content){
|
void ToCStr(Isolate * isolate,Local<Value> &args,char * key,std::string &str){
|
||||||
|
|
||||||
|
char str_content[255]={0};
|
||||||
Local<Context> context= isolate->GetCurrentContext();
|
Local<Context> context= isolate->GetCurrentContext();
|
||||||
Local<Value> val= args->Get(context,String::NewFromUtf8(isolate,key)).ToLocalChecked();
|
Local<Value> val;
|
||||||
|
if(args->IsObject())
|
||||||
|
val = args->ToObject()->Get(context,String::NewFromUtf8(isolate,key)).ToLocalChecked();
|
||||||
|
else
|
||||||
|
val = args;
|
||||||
if(val->IsNullOrUndefined())
|
if(val->IsNullOrUndefined())
|
||||||
return default_val;
|
return;
|
||||||
else if(val->IsString()){
|
else if(val->IsString()){
|
||||||
_ToCharPTR(val,context,str_content);
|
_ToCharPTR(val,context,str_content);
|
||||||
return str_content;
|
str+=" --";
|
||||||
|
str+=std::string(key);
|
||||||
|
str+="=";
|
||||||
|
str+=std::string(str_content);
|
||||||
|
return ;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
char ret[100];
|
char ret[100];
|
||||||
@ -95,68 +112,55 @@ namespace demo {
|
|||||||
Isolate* isolate = args.GetIsolate();
|
Isolate* isolate = args.GetIsolate();
|
||||||
Local<Context> context= isolate->GetCurrentContext();
|
Local<Context> context= isolate->GetCurrentContext();
|
||||||
|
|
||||||
|
std::string _args = "/usr/lib/judger/libjudger.so";
|
||||||
|
|
||||||
if( !args[0]->IsObject()){
|
if( !args[0]->IsObject()){
|
||||||
isolate->ThrowException(Exception::Error(String::NewFromUtf8(isolate,"typeof argument must be Object!")));
|
isolate->ThrowException(Exception::Error(String::NewFromUtf8(isolate,"typeof argument must be Object!")));
|
||||||
}
|
}
|
||||||
|
|
||||||
Local<Object> argument = args[0]->ToObject();
|
Local<Value> argument = args[0];
|
||||||
|
|
||||||
/* 参数 */
|
|
||||||
struct config _config;
|
|
||||||
|
|
||||||
|
|
||||||
/* max_cpu_time */
|
/* max_cpu_time */
|
||||||
_config.max_cpu_time = ToNumber(isolate,argument,(char *)"max_cpu_time",UNLIMITED);
|
ToNumber(isolate,argument,(char *)"max_cpu_time",_args);
|
||||||
|
|
||||||
/* max_real_time */
|
/* max_real_time */
|
||||||
_config.max_real_time = ToNumber(isolate,argument,(char *)"max_real_time",UNLIMITED);
|
ToNumber(isolate,argument,(char *)"max_real_time",_args);
|
||||||
|
|
||||||
/* max_memory */
|
/* max_memory */
|
||||||
_config.max_memory = ToNumber(isolate,argument,(char *)"max_memory",UNLIMITED);
|
ToNumber(isolate,argument,(char *)"max_memory",_args);
|
||||||
|
|
||||||
/* memory_limit_check_only */
|
/* memory_limit_check_only */
|
||||||
_config.memory_limit_check_only =
|
ToNumber(isolate,argument,(char *)"memory_limit_check_only",_args);
|
||||||
ToNumber(isolate,argument,(char *)"memory_limit_check_only",0);
|
|
||||||
|
|
||||||
if(_config.memory_limit_check_only)
|
|
||||||
_config.memory_limit_check_only = 1;
|
|
||||||
|
|
||||||
|
|
||||||
/* max_stack */
|
/* max_stack */
|
||||||
_config.max_stack =
|
ToNumber(isolate,argument,(char *)"max_stack",_args); //默认16mb
|
||||||
ToNumber(isolate,argument,(char *)"max_stack",16*1024*1024); //默认16mb
|
|
||||||
|
|
||||||
/* max_process_number */
|
/* max_process_number */
|
||||||
_config.max_process_number =
|
ToNumber(isolate,argument,(char *)"max_process_number",_args);
|
||||||
ToNumber(isolate,argument,(char *)"max_process_number",UNLIMITED);
|
|
||||||
|
|
||||||
/* max_output_size */
|
/* max_output_size */
|
||||||
_config.max_output_size =
|
ToNumber(isolate,argument,(char *)"max_output_size",_args);
|
||||||
ToNumber(isolate,argument,(char *)"max_output_size",UNLIMITED);
|
|
||||||
|
|
||||||
/* input_path */
|
/* input_path */
|
||||||
char input_path[255];
|
ToCStr(isolate,argument,(char *)"input_path",_args);
|
||||||
_config.input_path = ToCStr(isolate,argument,(char *)"input_path",(char *)"/dev/stdin",input_path);
|
|
||||||
|
|
||||||
/* output_path */
|
/* output_path */
|
||||||
char output_path[255];
|
ToCStr(isolate,argument,(char *)"output_path",_args);
|
||||||
_config.output_path= ToCStr(isolate,argument,(char *)"output_path",(char *)"/dev/stdout",output_path);
|
|
||||||
|
|
||||||
/* error_path */
|
/* error_path */
|
||||||
char error_path[255];
|
ToCStr(isolate,argument,(char *)"error_path",_args);
|
||||||
_config.error_path= ToCStr(isolate,argument,(char *)"error_path",(char *)"/dev/stderr",error_path);
|
|
||||||
|
|
||||||
/* exe_path */
|
/* exe_path */
|
||||||
char exe_path[255];
|
ToCStr(isolate,argument,(char *)"exe_path",_args);
|
||||||
_config.exe_path = ToCStr(isolate,argument,(char *)"exe_path",(char *)"/bin/ls",exe_path);
|
|
||||||
|
|
||||||
/* args */
|
/* args */
|
||||||
_config.args[0] = _config.exe_path;
|
|
||||||
|
|
||||||
char _args[100][255];
|
Local<Value> margs= argument->ToObject()->Get(context,String::NewFromUtf8(isolate,"args")).ToLocalChecked();
|
||||||
Local<Value> margs= argument->Get(context,String::NewFromUtf8(isolate,"args")).ToLocalChecked();
|
|
||||||
if( margs->IsNullOrUndefined()){
|
if( margs->IsNullOrUndefined()){
|
||||||
_config.args[1] = NULL;
|
NULL;
|
||||||
}
|
}
|
||||||
else if( margs->IsArray()){
|
else if( margs->IsArray()){
|
||||||
Local<Array> args = margs.As<Array>();
|
Local<Array> args = margs.As<Array>();
|
||||||
@ -164,23 +168,16 @@ namespace demo {
|
|||||||
int i;
|
int i;
|
||||||
for(i=0;i<len;i++){
|
for(i=0;i<len;i++){
|
||||||
Local<Value> in = args->Get(i);
|
Local<Value> in = args->Get(i);
|
||||||
if(in->IsString()){
|
ToCStr(isolate,in,(char *)"args",_args);
|
||||||
_ToCharPTR(in,context,_args[i]);
|
|
||||||
_config.args[i+1] = _args[i];
|
|
||||||
}
|
|
||||||
else
|
|
||||||
isolate->ThrowException(Exception::Error(String::NewFromUtf8(isolate,"the content of args must be string!")));
|
|
||||||
}
|
}
|
||||||
_config.args[len+1] = NULL;
|
|
||||||
}
|
}
|
||||||
else { //not array
|
else { //not array
|
||||||
isolate->ThrowException(Exception::Error(String::NewFromUtf8(isolate,"typeof argument.args must be Array!")));
|
isolate->ThrowException(Exception::Error(String::NewFromUtf8(isolate,"args must be a list")));
|
||||||
}
|
}
|
||||||
|
|
||||||
char _env[100][255];
|
Local<Value> menv= argument->ToObject()->Get(context,String::NewFromUtf8(isolate,"env")).ToLocalChecked();
|
||||||
Local<Value> menv= argument->Get(context,String::NewFromUtf8(isolate,"env")).ToLocalChecked();
|
|
||||||
if( menv->IsNullOrUndefined()){
|
if( menv->IsNullOrUndefined()){
|
||||||
_config.env[0] = NULL;
|
NULL;
|
||||||
}
|
}
|
||||||
else if( margs->IsArray()){
|
else if( margs->IsArray()){
|
||||||
Local<Array> env = menv.As<Array>();
|
Local<Array> env = menv.As<Array>();
|
||||||
@ -188,103 +185,75 @@ namespace demo {
|
|||||||
int i;
|
int i;
|
||||||
for(i=0;i<len;i++){
|
for(i=0;i<len;i++){
|
||||||
Local<Value> in = env->Get(i);
|
Local<Value> in = env->Get(i);
|
||||||
if(in->IsString()){
|
ToCStr(isolate,in,(char *)"env",_args);
|
||||||
_ToCharPTR(in,context,_env[i]);
|
|
||||||
_config.env[i] = _env[i];
|
|
||||||
}
|
|
||||||
else
|
|
||||||
isolate->ThrowException(Exception::Error(String::NewFromUtf8(isolate,"the content of env must be string!")));
|
|
||||||
}
|
}
|
||||||
_config.env[len] = NULL;
|
|
||||||
}
|
}
|
||||||
else { //not array
|
else { //not array
|
||||||
isolate->ThrowException(Exception::Error(String::NewFromUtf8(isolate,"typeof argument.env must be Array!")));
|
isolate->ThrowException(Exception::Error(String::NewFromUtf8(isolate,"env must be a list")));
|
||||||
}
|
}
|
||||||
|
|
||||||
/* log_path */
|
/* log_path */
|
||||||
char log_path[255];
|
ToCStr(isolate,argument,(char *)"log_path",_args);
|
||||||
_config.log_path= ToCStr(isolate,argument,(char *)"log_path",(char *)"judger.log",log_path);
|
|
||||||
|
|
||||||
/* seccomp_rule_name */
|
/* seccomp_rule_name */
|
||||||
char seccomp_rule_name[255];
|
char seccomp_rule_name[255];
|
||||||
_config.seccomp_rule_name = ToCStr(isolate,argument,(char *)"seccomp_rule_name",NULL,seccomp_rule_name);
|
ToCStr(isolate,argument,(char *)"seccomp_rule_name",_args);
|
||||||
|
|
||||||
/* uid */
|
/* uid */
|
||||||
_config.uid =
|
ToNumber(isolate,argument,(char *)"uid",_args);
|
||||||
ToNumber(isolate,argument,(char *)"uid",65534);
|
|
||||||
/* gid */
|
/* gid */
|
||||||
_config.gid =
|
ToNumber(isolate,argument,(char *)"gid",_args);
|
||||||
ToNumber(isolate,argument,(char *)"gid",65534);
|
|
||||||
|
|
||||||
|
|
||||||
|
char buf[255];
|
||||||
|
FILE *_result_f;
|
||||||
|
std::string result;
|
||||||
|
if(( _result_f = popen(_args.c_str(),"r"))==NULL)
|
||||||
|
isolate->ThrowException(Exception::Error(String::NewFromUtf8(isolate,"run /usr/lib/judger/libjudger.so failed!")));
|
||||||
|
while(fgets(buf,sizeof(buf),_result_f)){
|
||||||
|
result += std::string(buf);
|
||||||
|
}
|
||||||
|
pclose(_result_f);
|
||||||
|
|
||||||
/*
|
const char *pr = result.c_str();
|
||||||
* printf("max_cpu_time %d\n",_config.max_cpu_time);
|
int len = strlen(pr);
|
||||||
* printf("max_real_time %d\n",_config.max_real_time);
|
for(len--;len>=0;len--){
|
||||||
* printf("max_memory %ld\n",_config.max_memory);
|
if( pr[len] == '{')
|
||||||
* printf("max_stack %ld\n",_config.max_stack);
|
break;
|
||||||
* printf("max_process_number %d\n",_config.max_process_number);
|
}
|
||||||
* printf("max_output_size %ld\n",_config.max_output_size);
|
|
||||||
* printf("%s\n",_config.input_path);
|
|
||||||
* printf("%s\n",_config.output_path);
|
|
||||||
* printf("%s\n",_config.error_path);
|
|
||||||
*
|
|
||||||
* int idx = 0;
|
|
||||||
* while( _config.args[idx]!= NULL){
|
|
||||||
* printf("args[%d] = %s\n",idx,_config.args[idx]);
|
|
||||||
* idx++;
|
|
||||||
* }
|
|
||||||
*
|
|
||||||
* idx = 0;
|
|
||||||
* while( _config.env[idx]!= NULL){
|
|
||||||
* printf("env[%d] = %s\n",idx,_config.env[idx]);
|
|
||||||
* idx++;
|
|
||||||
* }
|
|
||||||
*
|
|
||||||
* printf("log_path %s\n",_config.log_path);
|
|
||||||
* printf("seccomp_rule_name %s\n",_config.seccomp_rule_name);
|
|
||||||
* printf("uid %d\n",_config.uid);
|
|
||||||
* printf("gid %d\n",_config.gid);
|
|
||||||
*/
|
|
||||||
|
|
||||||
struct result _result = {0, 0, 0, 0, 0, 0, 0};
|
printf("%*.*s",len,len,pr); //输出 程序的输出
|
||||||
run(&_config, &_result);
|
|
||||||
|
|
||||||
/*
|
MaybeLocal<Value> mres = JSON::Parse(isolate,String::NewFromUtf8(isolate,pr+len));
|
||||||
*printf("{\n"
|
args.GetReturnValue().Set(mres.ToLocalChecked());
|
||||||
* " \"cpu_time\": %d,\n"
|
|
||||||
* " \"real_time\": %d,\n"
|
|
||||||
* " \"memory\": %ld,\n"
|
|
||||||
* " \"signal\": %d,\n"
|
|
||||||
* " \"exit_code\": %d,\n"
|
|
||||||
* " \"error\": %d,\n"
|
|
||||||
* " \"result\": %d\n"
|
|
||||||
* "}",
|
|
||||||
* _result.cpu_time,
|
|
||||||
* _result.real_time,
|
|
||||||
* _result.memory,
|
|
||||||
* _result.signal,
|
|
||||||
* _result.exit_code,
|
|
||||||
* _result.error,
|
|
||||||
* _result.result);
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* 返回值 */
|
|
||||||
Local<Object> result = Object::New(isolate);
|
|
||||||
result->Set(String::NewFromUtf8(isolate,"cpu_time"),Integer::New(isolate,_result.cpu_time));
|
|
||||||
result->Set(String::NewFromUtf8(isolate,"real_time"),Integer::New(isolate,_result.real_time));
|
|
||||||
result->Set(String::NewFromUtf8(isolate,"memory"),Integer::New(isolate,_result.memory));
|
|
||||||
result->Set(String::NewFromUtf8(isolate,"signal"),Integer::New(isolate,_result.signal));
|
|
||||||
result->Set(String::NewFromUtf8(isolate,"exit_code"),Integer::New(isolate,_result.exit_code));
|
|
||||||
result->Set(String::NewFromUtf8(isolate,"result"),Integer::New(isolate,_result.result));
|
|
||||||
result->Set(String::NewFromUtf8(isolate,"error"),Integer::New(isolate,_result.error));
|
|
||||||
|
|
||||||
args.GetReturnValue().Set(result);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void init(Local<Object> exports)
|
void init(Local<Object> exports)
|
||||||
{
|
{
|
||||||
|
v8::Isolate* isolate = v8::Isolate::GetCurrent();
|
||||||
NODE_SET_METHOD(exports, "run", Method);
|
NODE_SET_METHOD(exports, "run", Method);
|
||||||
|
exports->Set( String::NewFromUtf8(isolate,"UNLIMITED"),Integer::New(isolate, -1));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"VERSION"),Integer::New(isolate, 0x020101));
|
||||||
|
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"RESULT_SUCCESS"),Integer::New(isolate, 0));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"RESULT_WRONG_ANSWER"),Integer::New(isolate, -1));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"RESULT_CPU_TIME_LIMIT_EXCEEDED"),Integer::New(isolate, 1));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"RESULT_REAL_TIME_LIMIT_EXCEEDED"),Integer::New(isolate, 2));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"RESULT_MEMORY_LIMIT_EXCEEDED"),Integer::New(isolate, 3));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"RESULT_RUNTIME_ERROR"),Integer::New(isolate, 4));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"RESULT_SYSTEM_ERROR"),Integer::New(isolate, 5));
|
||||||
|
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"ERROR_INVALID_CONFIG"),Integer::New(isolate, -1));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"ERROR_FORK_FAILED"),Integer::New(isolate, -2));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"ERROR_PTHREAD_FAILED"),Integer::New(isolate, -3));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"ERROR_WAIT_FAILED"),Integer::New(isolate, -4));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"ERROR_ROOT_REQUIRED"),Integer::New(isolate, -5));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"ERROR_LOAD_SECCOMP_FAILED"),Integer::New(isolate, -6));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"ERROR_SETRLIMIT_FAILED"),Integer::New(isolate, -7));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"ERROR_DUP2_FAILED"),Integer::New(isolate, -8));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"ERROR_SETUID_FAILED"),Integer::New(isolate, -9));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"ERROR_EXECVE_FAILED"),Integer::New(isolate, -10));
|
||||||
|
exports->Set(String::NewFromUtf8(isolate,"ERROR_SPJ_ERROR"),Integer::New(isolate, -11));
|
||||||
}
|
}
|
||||||
|
|
||||||
NODE_MODULE(addon, init)
|
NODE_MODULE(addon, init)
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
"description": "judger for online system",
|
"description": "judger for online system",
|
||||||
"main": "./build/Release/judger.node",
|
"main": "./build/Release/judger.node",
|
||||||
"scripts": {
|
"scripts": {
|
||||||
|
"build":"node-gyp rebuild",
|
||||||
"test": "echo \"Error: no test specified\" && exit 1"
|
"test": "echo \"Error: no test specified\" && exit 1"
|
||||||
},
|
},
|
||||||
"author": "virusdefender,rainboy",
|
"author": "virusdefender,rainboy",
|
||||||
|
Loading…
Reference in New Issue
Block a user