diff --git a/README.md b/README.md index 3fabe9b..16f2c3f 100644 --- a/README.md +++ b/README.md @@ -34,7 +34,28 @@ Better choose the latest update of the interpreter. MUST USE -O2 ! pragma gcc optimize(2) seems useless when using g++ -> g++ -std=c++11 -O2 main.cpp -o main.exe +> g++ -std=c++11 -O2 main.cpp -o nasal.exe + +Or use this in linux/macOS/Unix + +> g++ -std=c++11 -O2 main.cpp -o nasal + +## How to Use? + +Input this command to use interactive interpreter mode: + +> ./nasal + +Input this command to run scripts directly: + +> ./nasal filename + +Use these commands to get some information of interpreter: + +> ./nasal -v +> ./nasal -version +> ./nasal -h +> ./nasal -help ## Parser @@ -471,7 +492,7 @@ After that, write the built-in function's name(in nasal) and the function's poin ```C++ struct FUNC_TABLE { - std::string name; + const char* name; nasal_val* (*func)(std::vector&,nasal_gc&); } builtin_func[]= { diff --git a/lib.nas b/lib.nas index c1b031d..8de85cc 100644 --- a/lib.nas +++ b/lib.nas @@ -1,28 +1,23 @@ var import=func(filename) { - __builtin_import(filename); - return nil; + return __builtin_import(filename); } -var print=func(elements...) +var print=func(elems...) { - __builtin_std_cout(elements); - return nil; + return __builtin_std_cout(elems); }; -var println=func(elements...) +var println=func(elems...) { - __builtin_std_cout(elements); - print('\n'); - return nil; + __builtin_std_cout(elems); + return print('\n'); } -var append=func(vector,elements...) +var append=func(vec,elems...) { - __builtin_push_back(vector,elements); - return nil; + return __builtin_push_back(vec,elems); } -var setsize=func(vector,size) +var setsize=func(vec,size) { - __builtin_set_size(vector,size); - return nil; + return __builtin_set_size(vec,size); } var system=func(str) { @@ -34,36 +29,35 @@ var input=func() } var sleep=func(duration) { - __builtin_sleep(duration); - return; + return __builtin_sleep(duration); } -var split=func(delimeter,string) +var split=func(deli,str) { - return __builtin_split(delimeter,string); + return __builtin_split(deli,str); } var rand=func(seed=nil) { return __builtin_rand(seed); } -var id=func(thing) +var id=func(object) { - return __builtin_get_id(thing); + return __builtin_get_id(object); } -var int=func(value) +var int=func(val) { - return __builtin_int(value); + return __builtin_int(val); } -var num=func(value) +var num=func(val) { - return __builtin_num(value); + return __builtin_num(val); } -var pop=func(vector) +var pop=func(vec) { - return __builtin_pop_back(vector); + return __builtin_pop_back(vec); } -var str=func(number) +var str=func(num) { - return __builtin_str(number); + return __builtin_str(num); } var size=func(object) { @@ -75,8 +69,7 @@ var contains=func(hash,key) } var delete=func(hash,key) { - __builtin_delete(hash,key); - return; + return __builtin_delete(hash,key); } var keys=func(hash) { @@ -88,49 +81,41 @@ var time=func(begin_time) } var die=func(str) { - __builtin_die(str); - return nil; + return __builtin_die(str); } var typeof=func(object) { return __builtin_type(object); } -var substr=func(str,begin,length) +var substr=func(str,begin,len) { - return __builtin_substr(str,begin,length); + return __builtin_substr(str,begin,len); } var streq=func(a,b) { return __builtin_streq(a,b); } -var left=func(string,length) +var left=func(str,len) { - return __builtin_left(string,length); + return __builtin_left(str,len); } -var right=func(string,length) +var right=func(str,len) { - return __builtin_right(string,length); + return __builtin_right(str,len); } var cmp=func(a,b) { return __builtin_cmp(a,b); } -var chr=func(code) #//Unlike in FG, this chr does not support Extended ASCII +var chr=func(code) { return __builtin_chr(code); } var io= { - fin:func(filename) - { - return __builtin_fin(filename); - }, - fout:func(filename,str) - { - __builtin_fout(filename,str); - return; - } + fin: func(filename){return __builtin_fin(filename);}, + fout:func(filename,str){return __builtin_fout(filename,str);} }; var bits= diff --git a/main.cpp b/main.cpp index 67a85d6..3d337d5 100644 --- a/main.cpp +++ b/main.cpp @@ -2,10 +2,10 @@ nasal_vm vm; -void help() +void help_interact() { std::cout - <<">> [\"file\"] input file name. \n" + <<">> [ ] input a file name to execute. \n" <<">> [help ] show help. \n" <<">> [clear] clear the screen. \n" <<">> [lex ] view tokens. \n" @@ -16,7 +16,25 @@ void help() <<">> [exit ] quit nasal interpreter. \n"; return; } - +void help_cmd() +{ + std::cout + <<"nasal -h -help | get help.\n" + <<"nasal -v -version | get version of nasal interpreter.\n" + <<"nasal filename | execute script file.\n"; + return; +} +void info() +{ + std::cout + <<">> Nasal interpreter ver 6.5 efficient gc test .\n" + <<">> Thanks to https://github.com/andyross/nasal\n" + <<">> Code: https://github.com/ValKmjolnir/Nasal-Interpreter\n" + <<">> Code: https://gitee.com/valkmjolnir/Nasal-Interpreter\n" + <<">> Info: http://wiki.flightgear.org/Nasal_scripting_language\n" + <<">> Input \"help\" to get help .\n"; + return; +} void logo() { std::cout @@ -27,13 +45,11 @@ void logo() <<" \\_\\ \\/ \\__,_|___/\\__,_|_|\n"; return; } - void die(const char* stage,std::string& filename) { std::cout<<">> ["<: error(s) occurred,stop.\n"; return; } - void execute(std::string& file,std::string& command) { nasal_lexer lexer; @@ -92,31 +108,21 @@ void execute(std::string& file,std::string& command) vm.clear(); return; } - -int main() +void interact() { - std::string command; - std::string file="null"; #ifdef _WIN32 // use chcp 65001 to use unicode io system("chcp 65001"); - system("cls"); -#else - int rs=system("clear");// avoid annoying warning of high version gcc/g++ #endif + std::string command,file="null"; logo(); - std::cout<<">> Nasal interpreter ver 6.5 efficient gc test .\n"; - std::cout<<">> Thanks to https://github.com/andyross/nasal\n"; - std::cout<<">> Code: https://github.com/ValKmjolnir/Nasal-Interpreter\n"; - std::cout<<">> Code: https://gitee.com/valkmjolnir/Nasal-Interpreter\n"; - std::cout<<">> Info: http://wiki.flightgear.org/Nasal_scripting_language\n"; - std::cout<<">> Input \"help\" to get help .\n"; + info(); while(1) { std::cout<<">> "; std::cin>>command; if(command=="help") - help(); + help_interact(); else if(command=="clear") { #ifdef _WIN32 @@ -128,11 +134,33 @@ int main() else if(command=="logo") logo(); else if(command=="exit") - break; + return; else if(command=="lex" || command=="ast" || command=="code" || command=="exec") execute(file,command); else file=command; } +} +int main(int argc,const char* argv[]) +{ + std::string command,file="null"; + if(argc==1) + interact(); + else if(argc==2 && (!strcmp(argv[1],"-v") || !strcmp(argv[1],"-version"))) + { + logo(); + std::cout<<"Nasal interpreter ver 6.5 efficient gc test\n"; + } + else if(argc==2 && (!strcmp(argv[1],"-h") || !strcmp(argv[1],"-help"))) + help_cmd(); + else if(argc==2) + { + file=argv[1]; + command="exec"; + execute(file,command); + return 0; + } + else + help_cmd(); return 0; } \ No newline at end of file diff --git a/nasal.h b/nasal.h index 3521492..f31c8b1 100644 --- a/nasal.h +++ b/nasal.h @@ -113,11 +113,9 @@ double str2num(const char* str) */ std::string num2str(double number) { - std::string res; - std::stringstream ss; + std::ostringstream ss; ss<>res; - return res; + return ss.str(); } #include "nasal_lexer.h" #include "nasal_ast.h" diff --git a/nasal_builtin.h b/nasal_builtin.h index 04dafe6..882d7e2 100644 --- a/nasal_builtin.h +++ b/nasal_builtin.h @@ -199,7 +199,7 @@ nasal_val* builtin_sleep(std::vector& local_scope,nasal_gc& gc) return nullptr; } // sleep in unistd.h will make this progress sleep sleep_time seconds. - sleep((unsigned long)val_addr->ptr.num); + sleep((unsigned int)val_addr->ptr.num); return gc.nil_addr; } @@ -628,9 +628,7 @@ nasal_val* builtin_contains(std::vector& local_scope,nasal_gc& gc) builtin_err("contains","\"key\" must be string"); return nullptr; } - nasal_val* ret_addr=gc.gc_alloc(vm_num); - ret_addr->ptr.num=hash_addr->ptr.hash->elems.count(*key_addr->ptr.str); - return ret_addr; + return hash_addr->ptr.hash->elems.count(*key_addr->ptr.str)?gc.one_addr:gc.zero_addr; } nasal_val* builtin_delete(std::vector& local_scope,nasal_gc& gc) { @@ -810,6 +808,24 @@ nasal_val* builtin_cmp(std::vector& local_scope,nasal_gc& gc) } nasal_val* builtin_chr(std::vector& local_scope,nasal_gc& gc) { + const char* extend[]={ + "€"," ","‚","ƒ","„","…","†","‡", + "ˆ","‰","Š","‹","Œ"," ","Ž"," ", + " ","‘","’","“","”","•","–","—", + "˜","™","š","›","œ"," ","ž","Ÿ", + " ","¡","¢","£","¤","¥","¦","§", + "¨","©","ª","«","¬"," ","®","¯", + "°","±","²","³","´","µ","¶","·", + "¸","¹","º","»","¼","½","¾","¿", + "À","Á","Â","Ã","Ä","Å","Æ","Ç", + "È","É","Ê","Ë","Ì","Í","Î","Ï", + "Ð","Ñ","Ò","Ó","Ô","Õ","Ö","×", + "Ø","Ù","Ú","Û","Ü","Ý","Þ","ß", + "à","á","â","ã","ä","å","æ","ç", + "è","é","ê","ë","ì","í","î","ï", + "ð","ñ","ò","ó","ô","õ","ö","÷", + "ø","ù","ú","û","ü","ý","þ","ÿ" + }; nasal_val* code_addr=local_scope[1]; if(code_addr->type!=vm_num) { @@ -817,7 +833,13 @@ nasal_val* builtin_chr(std::vector& local_scope,nasal_gc& gc) return nullptr; } nasal_val* ret_addr=gc.gc_alloc(vm_str); - *ret_addr->ptr.str=(char)code_addr->ptr.num; + int num=code_addr->ptr.num; + if(0<=num && num<128) + *ret_addr->ptr.str=(char)num; + else if(128<=num && num<256) + *ret_addr->ptr.str=extend[num-128]; + else + *ret_addr->ptr.str=" "; return ret_addr; } diff --git a/nasal_parse.h b/nasal_parse.h index 248e3ad..3779c4c 100644 --- a/nasal_parse.h +++ b/nasal_parse.h @@ -161,12 +161,8 @@ void nasal_parse::match(int type,std::string err_info) return; } std::string s=""; - for(int i=0;token_table[i].str;++i) - if(token_table[i].tok_type==type) - { - s=token_table[i].str; - break; - } + if(type>=tok_for)// token_table begins at tok_for + s=token_table[type-tok_for].str; switch(type) { case tok_num:die(error_line,"expected number"); break; @@ -391,8 +387,7 @@ nasal_ast nasal_parse::args_gen() match(tok_lcurve); while(tok_list[ptr].type!=tok_rcurve) { - nasal_ast tmp; - tmp=id_gen(); + nasal_ast tmp=id_gen(); match(tok_id); if(tok_list[ptr].type==tok_eq || tok_list[ptr].type==tok_ellipsis) { diff --git a/stl/lib.nas b/stl/lib.nas index c1b031d..8de85cc 100644 --- a/stl/lib.nas +++ b/stl/lib.nas @@ -1,28 +1,23 @@ var import=func(filename) { - __builtin_import(filename); - return nil; + return __builtin_import(filename); } -var print=func(elements...) +var print=func(elems...) { - __builtin_std_cout(elements); - return nil; + return __builtin_std_cout(elems); }; -var println=func(elements...) +var println=func(elems...) { - __builtin_std_cout(elements); - print('\n'); - return nil; + __builtin_std_cout(elems); + return print('\n'); } -var append=func(vector,elements...) +var append=func(vec,elems...) { - __builtin_push_back(vector,elements); - return nil; + return __builtin_push_back(vec,elems); } -var setsize=func(vector,size) +var setsize=func(vec,size) { - __builtin_set_size(vector,size); - return nil; + return __builtin_set_size(vec,size); } var system=func(str) { @@ -34,36 +29,35 @@ var input=func() } var sleep=func(duration) { - __builtin_sleep(duration); - return; + return __builtin_sleep(duration); } -var split=func(delimeter,string) +var split=func(deli,str) { - return __builtin_split(delimeter,string); + return __builtin_split(deli,str); } var rand=func(seed=nil) { return __builtin_rand(seed); } -var id=func(thing) +var id=func(object) { - return __builtin_get_id(thing); + return __builtin_get_id(object); } -var int=func(value) +var int=func(val) { - return __builtin_int(value); + return __builtin_int(val); } -var num=func(value) +var num=func(val) { - return __builtin_num(value); + return __builtin_num(val); } -var pop=func(vector) +var pop=func(vec) { - return __builtin_pop_back(vector); + return __builtin_pop_back(vec); } -var str=func(number) +var str=func(num) { - return __builtin_str(number); + return __builtin_str(num); } var size=func(object) { @@ -75,8 +69,7 @@ var contains=func(hash,key) } var delete=func(hash,key) { - __builtin_delete(hash,key); - return; + return __builtin_delete(hash,key); } var keys=func(hash) { @@ -88,49 +81,41 @@ var time=func(begin_time) } var die=func(str) { - __builtin_die(str); - return nil; + return __builtin_die(str); } var typeof=func(object) { return __builtin_type(object); } -var substr=func(str,begin,length) +var substr=func(str,begin,len) { - return __builtin_substr(str,begin,length); + return __builtin_substr(str,begin,len); } var streq=func(a,b) { return __builtin_streq(a,b); } -var left=func(string,length) +var left=func(str,len) { - return __builtin_left(string,length); + return __builtin_left(str,len); } -var right=func(string,length) +var right=func(str,len) { - return __builtin_right(string,length); + return __builtin_right(str,len); } var cmp=func(a,b) { return __builtin_cmp(a,b); } -var chr=func(code) #//Unlike in FG, this chr does not support Extended ASCII +var chr=func(code) { return __builtin_chr(code); } var io= { - fin:func(filename) - { - return __builtin_fin(filename); - }, - fout:func(filename,str) - { - __builtin_fout(filename,str); - return; - } + fin: func(filename){return __builtin_fin(filename);}, + fout:func(filename,str){return __builtin_fout(filename,str);} }; var bits= diff --git a/test/bf.nas b/test/bf.nas index 43f13e8..8b1a4b4 100644 --- a/test/bf.nas +++ b/test/bf.nas @@ -146,16 +146,13 @@ var mandelbrot= >>>]>[-]+<]]+>[-<[>>>>>>>>>]<<<<<<<<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>[-]<<<++++ +[-[->>>>>>>>>+<<<<<<<<<]>>>>>>>>>]>>>>>->>>>>>>>>>>>>>>>>>>>>>>>>>>-<<<<<<[<<<< <<<<<]]>>>]"; -var hello= -"++[>++<-]>[>++<-]>[>++<-]>[>++<-]>[>++<-]>+++++++++++++++++++++++++++++++++++++ -+++.---.+++++++..+++.<.>++++++++.--------.+++.------.--------."; var bf=func(program) { var paper=[]; setsize(paper,131072); - for(var i=0;i<131072;i+=1) - paper[i]=0; + #for(var i=0;i<131072;i+=1) + # paper[i]=0; var ptr=0; var s=program; var len=size(s); @@ -243,16 +240,10 @@ var bf=func(program) paper[ptr]=input()[0]; elsif(code[i][0]==out) print(chr(paper[ptr])); - elsif(code[i][0]==jt) - { - if(paper[ptr]) - i=code[i][1]-1; - } - elsif(code[i][0]==jf) - { - if(!paper[ptr]) - i=code[i][1]-1; - } + elsif(code[i][0]==jt and paper[ptr]) + i=code[i][1]-1; + elsif(code[i][0]==jf and !paper[ptr]) + i=code[i][1]-1; } print('\n'); return;