change the way of calling built-in functions

change std::map to struct array,use index to call built-in functions.this may be more efficient.
This commit is contained in:
Valk Richard Li 2021-02-14 17:36:42 +08:00
parent 80683c381f
commit 78ba0641a6
3 changed files with 12 additions and 34 deletions

View File

@ -796,7 +796,6 @@ nasal_val* builtin_streq(nasal_val* local_scope_addr,nasal_gc& gc)
return ret_addr; return ret_addr;
} }
int ret=(a_addr->get_string()==b_addr->get_string()); int ret=(a_addr->get_string()==b_addr->get_string());
ret_addr->set_number((double)ret); ret_addr->set_number((double)ret);
return ret_addr; return ret_addr;
} }
@ -816,9 +815,9 @@ nasal_val* builtin_left(nasal_val* local_scope_addr,nasal_gc& gc)
} }
std::string str=string_addr->get_string(); std::string str=string_addr->get_string();
int len=(int)length_addr->get_number(); int len=(int)length_addr->get_number();
if(len < 0) len = 0; if(len<0)
len=0;
std::string tmp=str.substr(0, len); std::string tmp=str.substr(0, len);
nasal_val* ret_addr=gc.gc_alloc(vm_str); nasal_val* ret_addr=gc.gc_alloc(vm_str);
ret_addr->set_string(tmp); ret_addr->set_string(tmp);
return ret_addr; return ret_addr;
@ -840,10 +839,11 @@ nasal_val* builtin_right(nasal_val* local_scope_addr,nasal_gc& gc)
std::string str=string_addr->get_string(); std::string str=string_addr->get_string();
int len=(int)length_addr->get_number(); int len=(int)length_addr->get_number();
int srclen=str.length(); int srclen=str.length();
if (len > srclen) len = srclen; if(len>srclen)
if(len < 0) len = 0; len=srclen;
if(len<0)
len=0;
std::string tmp=str.substr(srclen-len, srclen); std::string tmp=str.substr(srclen-len, srclen);
nasal_val* ret_addr=gc.gc_alloc(vm_str); nasal_val* ret_addr=gc.gc_alloc(vm_str);
ret_addr->set_string(tmp); ret_addr->set_string(tmp);
return ret_addr; return ret_addr;
@ -862,21 +862,8 @@ nasal_val* builtin_cmp(nasal_val* local_scope_addr,nasal_gc& gc)
builtin_error_occurred("cmp","\"b\" must be string"); builtin_error_occurred("cmp","\"b\" must be string");
return NULL; return NULL;
} }
std::string a=a_addr->get_string();
std::string b=b_addr->get_string();
int alen=a.length();
int blen=b.length();
nasal_val* ret_addr=gc.gc_alloc(vm_num); nasal_val* ret_addr=gc.gc_alloc(vm_num);
for(int i=0; i<alen && i<blen; i++) ret_addr->set_number(strcmp(a_addr->get_string().data(),b_addr->get_string().data()));
{
int diff = a[i] - b[i];
if(diff)
{
ret_addr->set_number((double)diff < 0 ? -1 : 1);
return ret_addr;
}
}
ret_addr->set_number(alen == blen ? 0 : (alen < blen ? -1 : 1));
return ret_addr; return ret_addr;
} }
nasal_val* builtin_chr(nasal_val* local_scope_addr,nasal_gc& gc) nasal_val* builtin_chr(nasal_val* local_scope_addr,nasal_gc& gc)
@ -887,9 +874,7 @@ nasal_val* builtin_chr(nasal_val* local_scope_addr,nasal_gc& gc)
builtin_error_occurred("chr","\"code\" must be number"); builtin_error_occurred("chr","\"code\" must be number");
return NULL; return NULL;
} }
char chr[2]; char chr[2]={(char)code_addr->get_number(),'\0'};
chr[0] = (char)code_addr->get_number();
chr[1] = '\0';
nasal_val* ret_addr=gc.gc_alloc(vm_str); nasal_val* ret_addr=gc.gc_alloc(vm_str);
ret_addr->set_string(chr); ret_addr->set_string(chr);
return ret_addr; return ret_addr;

View File

@ -338,7 +338,7 @@ void nasal_codegen::call_id(nasal_ast& ast)
for(int i=0;builtin_func_table[i].func_pointer;++i) for(int i=0;builtin_func_table[i].func_pointer;++i)
if(builtin_func_table[i].func_name==str) if(builtin_func_table[i].func_name==str)
{ {
gen(op_builtincall,string_table[str]); gen(op_builtincall,i);
return; return;
} }
gen(op_call,string_table[str]); gen(op_call,string_table[str]);
@ -926,9 +926,9 @@ void nasal_codegen::print_op(int index)
switch(exec_code[index].op) switch(exec_code[index].op)
{ {
case op_pushnum:std::cout<<'('<<number_result_table[exec_code[index].index]<<')';break; case op_pushnum:std::cout<<'('<<number_result_table[exec_code[index].index]<<')';break;
case op_builtincall:std::cout<<'('<<builtin_func_table[exec_code[index].index].func_name<<')';break;
case op_hashapp: case op_hashapp:
case op_call: case op_call:
case op_builtincall:
case op_mcall: case op_mcall:
case op_pushstr: case op_pushstr:
case op_callh: case op_callh:

View File

@ -30,8 +30,6 @@ private:
std::vector<std::string> string_table; std::vector<std::string> string_table;
// number table // number table
std::vector<double> number_table; std::vector<double> number_table;
// builtin function address table
std::map<std::string,nasal_val* (*)(nasal_val* x,nasal_gc& vm)> builtin_func_hashmap;
void die(std::string); void die(std::string);
bool check_condition(nasal_val*); bool check_condition(nasal_val*);
void opr_nop(); void opr_nop();
@ -103,8 +101,6 @@ nasal_vm::nasal_vm()
val_stack=new nasal_val*[val_stack_MAX_DEPTH]; val_stack=new nasal_val*[val_stack_MAX_DEPTH];
val_stack_top=val_stack; val_stack_top=val_stack;
local_scope_stack.push(NULL); local_scope_stack.push(NULL);
for(int i=0;builtin_func_table[i].func_pointer;++i)
builtin_func_hashmap[builtin_func_table[i].func_name]=builtin_func_table[i].func_pointer;
return; return;
} }
nasal_vm::~nasal_vm() nasal_vm::~nasal_vm()
@ -899,11 +895,8 @@ void nasal_vm::opr_callf()
} }
void nasal_vm::opr_builtincall() void nasal_vm::opr_builtincall()
{ {
nasal_val* ret_value_addr=NULL; *(++val_stack_top)=(*builtin_func_table[exec_code[ptr].index].func_pointer)(local_scope_stack.top(),vm);
std::string val_name=string_table[exec_code[ptr].index];
ret_value_addr=(*builtin_func_hashmap[val_name])(local_scope_stack.top(),vm);
main_loop_break_mark=!builtin_die_state; main_loop_break_mark=!builtin_die_state;
*(++val_stack_top)=ret_value_addr;
return; return;
} }
void nasal_vm::opr_slicebegin() void nasal_vm::opr_slicebegin()