Merge branch 'c_strings'

Conflicts:
	src/rpn.cpp
This commit is contained in:
louis 2015-03-01 23:33:20 +01:00
commit 14ea7d2b74
16 changed files with 779 additions and 320 deletions

259
README
View file

@ -24,39 +24,202 @@ Language extensions will soon be included:
======================================================================== ========================================================================
Here is a list of HP28s reserved words. Here is a list of HP28s reserved words.
New commands (nonexistent in RPL) are tagged with (+). New commands (nonexistent in RPL) are tagged with * in column new.
Already implemented commands are tagged with (*). Already implemented commands are tagged with * in column impl.
Tested commands are tagged with * in column tested.
GENERAL OPERATIONS category command new impl. tested
+(*), -(*), neg(*), *(*), /(*), inv(*)(+), %(*), %CH(*), ^(*),
sqrt(*)(+), sq(*)(+), test(*)(+)
GENERAL (some are 'CURSOR' commands) GENERAL + *
verbose(*)(+), std(*), fix(*), sci(*), version(*)(+), uname(*)(+) GENERAL - *
GENERAL neg *
GENERAL * *
GENERAL / *
GENERAL inv *
GENERAL % *
GENERAL %CH *
GENERAL ^ *
GENERAL sqrt * *
GENERAL sq * *
GENERAL test * *
GENERAL verbose * *
GENERAL std *
GENERAL fix *
GENERAL sci *
GENERAL version * *
GENERAL uname * *
STACK STACK drop *
drop(*), swap(*), roll, dup(*), over, dup2(*), drop2(*), rot(*), STACK swap *
list->, rolld, pick(*), dupn, dropn, depth(*), ->list, load_stack(+), STACK roll
save_stack(+) STACK dup *
STACK over
STACK dup2 *
STACK drop2 *
STACK rot *
STACK list->
STACK rolld
STACK pick *
STACK dupn
STACK dropn
STACK depth *
STACK ->list
STACK load_stack * *
STACK save_stack * *
STORE STORE
sto(*), rcl(*), purge(*), sto+, sto-, sto*, sto/, sneg, sinv, sconj, STORE sto *
erase(*)(+), vars(*)(+), include(+), load_vars(+), save_vars(+) STORE rcl *
STORE purge *
STORE sto+
STORE sto-
STORE sto*
STORE sto/
STORE sneg
STORE sinv
STORE sconj
STORE erase * *
STORE vars * *
STORE include *
STORE load_vars *
STORE save_vars *
PROGRAM(+) PROGRAM eval *
eval(*), load_prog(+), save_prog(+) PROGRAM load_prog *
PROGRAM save_prog *
ALGEBRA neg * *
ALGEBRA colct
ALGEBRA expan
ALGEBRA size
ALGEBRA form
ALGEBRA obsub
ALGEBRA exsub
ALGEBRA taylr
ALGEBRA isol
ALGEBRA quad,
ALGEBRA show
ALGEBRA obget
ALGEBRA exget
BINARY + *
BINARY - *
BINARY * *
BINARY / *
BINARY dec *
BINARY hex *
BINARY oct *
BINARY bin *
BINARY stws
BINARY rcws
BINARY rl
BINARY rr
BINARY rlb
BINARY rrb
BINARY r->b *
BINARY b->r *
BINARY sl
BINARY sr
BINARY slb
BINARY srb
BINARY asr
BINARY and
BINARY or
BINARY xor
BINARY not
STRING + *
STRING ->str *
STRING str-> *
STRING chr
STRING num
STRING ->lcd
STRING lcd->
STRING pos
STRING sub
STRING size
STRING disp
BRANCH
BRANCH if *
BRANCH then *
BRANCH else *
BRANCH end *
BRANCH start *
BRANCH for *
BRANCH next *
BRANCH step *
BRANCH ift
BRANCH ifte
BRANCH do
BRANCH until
BRANCH end
BRANCH while
BRANCH repeat
BRANCH end
TEST
TEST != *
TEST > *
TEST >= *
TEST < *
TEST <= *
TEST sf
TEST cf
TEST fs?
TEST fc?
TEST fs?c
TEST fc?c
TEST and *
TEST or *
TEST xor *
TEST not *
TEST same *
TEST == *
TEST stof
TEST rclf
TEST type
TRIG
TRIG pi * *
TRIG sin *
TRIG asin *
TRIG cos *
TRIG acos *
TRIG tan *
TRIG atan *
TRIG p→r
TRIG r→p
TRIG r→c
TRIG c→r
TRIG arg
TRIG →hms
TRIG hms→
TRIG hms+
TRIG hms-
TRIG d→r *
TRIG r→d *
LOGS
LOGS log *
LOGS alog *
LOGS ln *
LOGS exp *
LOGS lnp1
LOGS expm
LOGS sinh *
LOGS asinh *
LOGS cosh *
LOGS acosh *
LOGS tanh *
LOGS atanh *
Not yet
=======
MEMORY MEMORY
mem, menu, order, path, home, crdir, vars, clusr mem, menu, order, path, home, crdir, vars, clusr,
ALGEBRA
neg(*)(+), colct, expan, size, form, obsub, exsub, taylr, isol, quad,
show, obget, exget
BINARY
+(*), -(*), *(*), /(*), dec(*), hex(*), oct(*), bin(*), stws, rcws,
rl, rr, rlb, rrb, r->b(*), b->r(*), sl, sr, slb, srb, asr, and, or,
xor, not
STAT STAT
∑dat, ∑par, ∑+, ∑-, n∑, cl∑, sto∑, rcl∑, tot, mean, sdev, var, max∑, ∑dat, ∑par, ∑+, ∑-, n∑, cl∑, sto∑, rcl∑, tot, mean, sdev, var, max∑,
@ -65,39 +228,6 @@ STAT
PRINT PRINT
pr1, prst, prvar, prlcd, cr, trac, prstc, prusr, prmd pr1, prst, prvar, prlcd, cr, trac, prstc, prusr, prmd
STRING
+(*), ->str, str->, chr, num, ->lcd, lcd->, pos, sub, size, disp
CONTRL
sst, halt, abort, kill, wait, key, bepp, cllcd, disp, clmf, errn,
errm
BRANCH
if(*), iferr, then(*), else(*), end(*), start(*), for(*), next(*),
step(*), ift, ifte, do, until, end, while, repeat, end
TEST
!=(*), >(*), >=(*), <(*), <=(*), sf, cf, fs?, fc?, fs?c, fc?c, and(*),
or(*), xor(*), not(*), same(*), ==(*), stof, rclf, type
CATALOG
next, prev, scan, use, fetch, quit
UNITS
convert
CURSOR (some of these functions can be found in GENERAL)
ins, del, ← → ↑ ↓, std, fix, sci, eng, deg, rad, cmd, undo, last, ml,
rdx, prmd
TRIG
pi(*)(+), sin(*), asin(*), cos(*), acos(*), tan(*), atan(*), p→r, r→p,
r→c, c→r, arg, →hms, hms→, hms+, hms-, (*)d→r, (*)r→d
LOGS
log(*), alog(*), ln(*), exp(*), lnp1, expm, sinh(*), asinh(*), cosh(*),
acosh(*), tanh(*), atanh(*)
SOLV SOLV
steq, rceq, isol, quad, show, root, steq, rceq, isol, quad, show, root,
@ -105,6 +235,19 @@ PLOT
ppar, steq, rceq, pmin, pmax, indep, draw, res, axes, centr, *w, *h, ppar, steq, rceq, pmin, pmax, indep, draw, res, axes, centr, *w, *h,
sto∑, rcl∑, col∑, scl∑, drw∑, cllcd, digtiz sto∑, rcl∑, col∑, scl∑, drw∑, cllcd, digtiz
CURSOR
ins, del, ← → ↑ ↓, cmd, undo, last, ml, rdx, prmd
CONTRL
sst, halt, abort, kill, wait, key, bepp, cllcd, disp, clmf, errn,
errm
CATALOG
next, prev, scan, use, fetch, quit
UNITS
convert
CUSTOM CUSTOM
menu, custom menu, custom

41
src/debug.h Normal file
View file

@ -0,0 +1,41 @@
static void dump8(unsigned char* to_dump, unsigned long offset,
unsigned long size)
{
const int block_size = 1;
const int block_per_line = 16;
int max_line = size / block_size;
unsigned char mychar;
int i;
int j;
for (i = 0; i < max_line; i++)
{
if ((i % block_per_line) == 0)
{
if (i > 0)
{
printf(" ");
for (j = i - block_per_line; j < i; j++)
{
mychar = *(to_dump + j);
if ((mychar < 32) || (mychar >= 127))
mychar = '.';
printf("%c", mychar);
}
}
printf("\n%08lX:", offset + i * block_size);
}
printf(" %02hhX", *(to_dump + i));
}
if (i > 0)
{
printf(" ");
for (j = (i >= block_per_line) ? (i - block_per_line) : 0; j < i; j++)
{
mychar = *(to_dump + j);
if ((mychar < 32) || (mychar >= 127))
mychar = '.';
printf("%c", mychar);
}
}
printf("\n");
}

View file

@ -1,15 +1,43 @@
static bool _cut(const string& entry, vector<string>& entries) // keywords declaration
struct keyword_t
{
cmd_type_t type;
char name[24];
program_fn_t fn;
string comment;
};
static const int g_max_commands = 128;
static keyword_t _keywords[g_max_commands];
static ret_value get_fn(const char* fn_name, program_fn_t& fn, cmd_type_t& type)
{
for(unsigned int i=0; (i<sizeof(_keywords)/sizeof(_keywords[0])) && (_keywords[i].type != cmd_max); i++)
{
if ((strnlen(_keywords[i].name, sizeof(_keywords[i].name))>0)
&& (strncmp(fn_name, _keywords[i].name, sizeof(_keywords[i].name)) == 0))
{
fn = _keywords[i].fn;
type = _keywords[i].type;
return ret_ok;
}
}
return ret_unknown_err;
}
static bool _cut(const char* entry, vector<string>& entries)
{ {
string tmp; string tmp;
//TODO borner
int len = strlen(entry);
for (int i=0; i<entry.size(); i++) for (int i=0; i < len; i++)
{ {
switch(entry.at(i)) switch(entry[i])
{ {
//symbol //symbol
case '\'': case '\'':
//push prec entry if exists //push prec entry if exists
if (tmp.size()>0) if (tmp.size() > 0)
{ {
entries.push_back(tmp); entries.push_back(tmp);
tmp.clear(); tmp.clear();
@ -17,10 +45,10 @@ static bool _cut(const string& entry, vector<string>& entries)
//get symbol //get symbol
tmp='\''; tmp='\'';
i++; i++;
while((i<entry.size()) && (isalnum(entry.at(i)) || entry.at(i)=='_')) while((i < len) && (isalnum(entry[i]) || entry[i]=='_'))
tmp+=entry.at(i++); tmp += entry[i++];
if ((i<entry.size()) && entry.at(i)=='\'') if ((i < len) && entry[i] == '\'')
tmp+='\''; tmp += '\'';
entries.push_back(tmp); entries.push_back(tmp);
tmp.clear(); tmp.clear();
break; break;
@ -28,7 +56,7 @@ static bool _cut(const string& entry, vector<string>& entries)
//string //string
case '"': case '"':
//push prec entry if exists //push prec entry if exists
if (tmp.size()>0) if (tmp.size() > 0)
{ {
entries.push_back(tmp); entries.push_back(tmp);
tmp.clear(); tmp.clear();
@ -36,10 +64,10 @@ static bool _cut(const string& entry, vector<string>& entries)
//get expression //get expression
tmp='"'; tmp='"';
i++; i++;
while(i<entry.size() && entry.at(i)>=' ') while(i < len && entry[i] >= ' ')
{ {
tmp+=entry.at(i); tmp += entry[i];
if (entry.at(i++) == '"') if (entry[i++] == '"')
break; break;
} }
entries.push_back(tmp); entries.push_back(tmp);
@ -55,35 +83,37 @@ static bool _cut(const string& entry, vector<string>& entries)
tmp.clear(); tmp.clear();
} }
if (entry.substr(i, 2) == "<<") if (strncmp(&entry[i], "<<", 2) == 0)
{ {
int up = 1; int up = 1;
// found a program begin // found a program begin
i+=2; i += 2;
tmp="<< "; tmp = "<< ";
// trim leading spaces // trim leading spaces
while (i<entry.size() && (entry.at(i)==' ' || entry.at(i)=='\t')) while (i < len && (entry[i]==' ' || entry[i]=='\t'))
i++; i++;
while(i<entry.size()) while(i < len)
{ {
if (entry.substr(i, 2) == "<<") if (strncmp(&entry[i], "<<", 2) == 0)
{ {
up++; up++;
i+=2; i += 2;
tmp+=" << "; tmp += " << ";
// trim leading spaces // trim leading spaces
while (i<entry.size() && (entry.at(i)==' ' || entry.at(i)=='\t')) while (i < len && (entry[i] == ' ' || entry[i] == '\t'))
i++; i++;
} }
else if (entry.substr(i, 2) == ">>") else if (strncmp(&entry[i], ">>", 2) == 0)
{ {
up--; up--;
i+=2; i += 2;
tmp+=" >>"; tmp += " >>";
// trim trailing spaces // trim trailing spaces
while (i<entry.size() && (entry.at(i)==' ' || entry.at(i)=='\t')) while (i < len && (entry[i] == ' ' || entry[i] == '\t'))
i++; i++;
// found end // found end
if (up == 0) if (up == 0)
@ -91,7 +121,7 @@ static bool _cut(const string& entry, vector<string>& entries)
} }
else else
{ {
tmp+=entry[i]; tmp += entry[i];
i++; i++;
} }
} }
@ -114,9 +144,9 @@ static bool _cut(const string& entry, vector<string>& entries)
//other //other
default: default:
if (entry.at(i)!=' ' && entry.at(i)!='\t') if (entry[i] != ' ' && entry[i] != '\t')
{ {
tmp+=entry.at(i); tmp += entry[i];
} }
else else
{ {
@ -147,14 +177,18 @@ static bool get_keyword(const string& entry, object*& obj, unsigned int& obj_siz
{ {
if (type == cmd_keyword) if (type == cmd_keyword)
{ {
obj = new keyword(fn, (string&)entry); // allocate keyword object
obj_size = sizeof(keyword); obj_size = sizeof(keyword)+entry.size()+1;
obj = (object*)malloc(obj_size);
((keyword*)obj)->set(fn, entry.c_str(), entry.size());
ret = true; ret = true;
} }
else if (type == cmd_branch) else if (type == cmd_branch)
{ {
obj = new branch((branch_fn_t)fn, (string&)entry); // allocate branch object
obj_size = sizeof(branch); obj_size = sizeof(branch)+entry.size()+1;
obj = (object*)malloc(obj_size);
((branch*)obj)->set((branch_fn_t)fn, entry.c_str(), entry.size());
ret = true; ret = true;
} }
} }
@ -162,53 +196,147 @@ static bool get_keyword(const string& entry, object*& obj, unsigned int& obj_siz
return ret; return ret;
} }
static bool get_symbol(const string& entry, object*& obj) static bool get_symbol(const string& entry, object*& obj, unsigned int& obj_len)
{ {
bool ret = false; bool ret = false;
int len = entry.size(); int entry_len = entry.size();
if (len>1 && entry[0]=='\'')
{
int last = entry[len-1]=='\''?(len-2):(len-1);
obj = new symbol(entry.substr(1, last).c_str());
ret = true;
}
return ret;
}
static bool get_string(const string& entry, object*& obj) if (entry_len>=1 && entry[0]=='\'')
{
bool ret = false;
int len = entry.size();
if (len>1 && entry[0]=='\"')
{ {
int last = entry[len-1]=='\"'?(len-2):(len-1); // symbol entry, like 'toto'
obj = new ostring(entry.substr(1, last).c_str()); if (entry_len == 1)
ret = true; {
} // total object length
return ret; obj_len = sizeof(symbol)+1;
}
static bool get_program(const string& entry, object*& obj) // allocate object
{ obj = (symbol*)malloc(obj_len);
bool ret = false;
int len = entry.size(); //set it
if (len>=2 && entry[0]=='<' && entry[1]=='<') ((symbol*)obj)->set("", 0);
{ }
int last;
if (len>=4 && entry[len-1]=='>' && entry[len-2]=='>')
last = len-4;
else else
last = len-2; {
obj = new oprogram(entry.substr(2, last).c_str()); int naked_entry_len;
// entry length without prefix / postfix
naked_entry_len = entry[entry_len-1]=='\''?(entry_len-2):(entry_len-1);
// total object length
obj_len = sizeof(symbol)+naked_entry_len+1;
// allocate object
obj = (symbol*)malloc(obj_len);
// set it
((symbol*)obj)->set(entry.substr(1, naked_entry_len).c_str(), naked_entry_len);
}
ret = true;
}
return ret;
}
static bool get_other(const string& entry, object*& obj, unsigned int& obj_len, cmd_type_t& type)
{
bool ret = false;
int entry_len = entry.size();
if (entry_len>=1)
{
// entry which is nothing is considered as an auto-evaluated symbol
int naked_entry_len;
// entry length without prefix / postfix
naked_entry_len = entry[entry_len-1]=='\''?(entry_len-1):(entry_len);
// total object length
obj_len = sizeof(symbol)+naked_entry_len+1;
// allocate object
obj = (symbol*)malloc(obj_len);
// set it
((symbol*)obj)->set(entry.c_str(), naked_entry_len);
((symbol*)obj)->_auto_eval = true;
type = cmd_symbol;
ret = true;
}
return ret;
}
static bool get_string(const string& entry, object*& obj, unsigned int& obj_len)
{
bool ret = false;
int entry_len = entry.size();
if (entry_len>=1 && entry[0]=='"')
{
if (entry_len == 1)
{
// total object length
obj_len = sizeof(ostring)+1;
// allocate object
obj = (ostring*)malloc(obj_len);
//set it
((ostring*)obj)->set("", 0);
}
else
{
int naked_entry_len;
// entry length without prefix / postfix
naked_entry_len = entry[entry_len-1]=='"'?(entry_len-2):(entry_len-1);
// total object length
obj_len = sizeof(ostring)+naked_entry_len+1;
// allocate object
obj = (ostring*)malloc(obj_len);
// set it
((ostring*)obj)->set(entry.substr(1, naked_entry_len).c_str(), naked_entry_len);
}
ret = true;
}
return ret;
}
static bool get_program(const string& entry, object*& obj, unsigned int& obj_len)
{
bool ret = false;
int entry_len = entry.size();
if (entry_len>=2 && entry[0]=='<' && entry[1]=='<')
{
int naked_entry_len;
// entry length without prefix / postfix
if (entry_len>=4 && entry[entry_len-1]=='>' && entry[entry_len-2]=='>')
naked_entry_len = entry_len-4;
else
naked_entry_len = entry_len-2;
// total object length
obj_len = sizeof(oprogram)+naked_entry_len+1;
// allocate object
obj = (object*)malloc(obj_len);
// set it
((oprogram*)obj)->set(&entry[2], naked_entry_len);
ret = true; ret = true;
} }
return ret; return ret;
} }
static bool get_float(const string& entry, object*& obj) // care: not threadsafe
static bool get_float(const string& entry, object*& obj, unsigned int& obj_size)
{ {
stringstream token; static number new_number;
floating_t val; floating_t val;
stringstream token;
bool ret = false; bool ret = false;
token<<entry; token<<entry;
@ -216,17 +344,22 @@ static bool get_float(const string& entry, object*& obj)
if ( (!token.fail()) && (!token.bad()) ) if ( (!token.fail()) && (!token.bad()) )
{ {
obj = new number(val); new_number.set(val);
obj = &new_number;
obj_size = sizeof(number);
ret = true; ret = true;
} }
return ret; return ret;
} }
static bool get_binary(const string& entry, object*& obj) // care: not threadsafe
static bool get_binary(const string& entry, object*& obj, unsigned int& obj_size)
{ {
static binary new_binary;
integer_t val; integer_t val;
bool ret = false; bool ret = false;
if ((entry.size() >= 2) && (entry[0] == '#')) if ((entry.size() >= 2) && (entry[0] == '#'))
{ {
stringstream token; stringstream token;
@ -255,7 +388,9 @@ static bool get_binary(const string& entry, object*& obj)
token>>val; token>>val;
if(syntax && !token.fail()) if(syntax && !token.fail())
{ {
obj = new binary(val); new_binary.set(val);
obj = &new_binary;
obj_size = sizeof(binary);
ret = true; ret = true;
} }
} }
@ -263,8 +398,10 @@ static bool get_binary(const string& entry, object*& obj)
return ret; return ret;
} }
static bool get_binary_bin(const string& entry, object*& obj) // care: not threadsafe
static bool get_binary_bin(const string& entry, object*& obj, unsigned int& obj_size)
{ {
static binary new_binary;
integer_t val; integer_t val;
int len = entry.size(); int len = entry.size();
bool ret = false; bool ret = false;
@ -281,7 +418,9 @@ static bool get_binary_bin(const string& entry, object*& obj)
exponent/=2; exponent/=2;
} }
} }
obj = new binary(val); new_binary.set(val);
obj = &new_binary;
obj_size = sizeof(binary);
ret = true; ret = true;
} }
@ -292,40 +431,34 @@ static bool _obj_from_string(const string& entry, object*& obj, unsigned int& ob
{ {
bool ret = false; bool ret = false;
if (get_float(entry, obj)) if (get_float(entry, obj, obj_size))
{ {
type = cmd_number; type = cmd_number;
obj_size = sizeof(number);
ret = true; ret = true;
} }
else if (get_binary(entry, obj)) else if (get_binary(entry, obj, obj_size))
{ {
type = cmd_binary; type = cmd_binary;
obj_size = sizeof(binary);
ret = true; ret = true;
} }
else if (get_binary_bin(entry, obj)) else if (get_binary_bin(entry, obj, obj_size))
{ {
type = cmd_binary; type = cmd_binary;
obj_size = sizeof(binary);
ret = true; ret = true;
} }
else if (get_symbol(entry, obj)) else if (get_symbol(entry, obj, obj_size))
{ {
type = cmd_symbol; type = cmd_symbol;
obj_size = sizeof(symbol);
ret = true; ret = true;
} }
else if (get_string(entry, obj)) else if (get_string(entry, obj, obj_size))
{ {
type = cmd_string; type = cmd_string;
obj_size = sizeof(ostring);
ret = true; ret = true;
} }
else if (get_program(entry, obj)) else if (get_program(entry, obj, obj_size))
{ {
type = cmd_program; type = cmd_program;
obj_size = sizeof(oprogram);
ret = true; ret = true;
} }
else if (get_keyword(entry, obj, obj_size, type)) else if (get_keyword(entry, obj, obj_size, type))
@ -335,16 +468,31 @@ static bool _obj_from_string(const string& entry, object*& obj, unsigned int& ob
else else
{ {
// nothing, considered as an auto-evaluated symbol // nothing, considered as an auto-evaluated symbol
obj = new symbol((string&)entry); if (get_other(entry, obj, obj_size, type))
((symbol*)obj)->_auto_eval = true; {
obj_size = sizeof(symbol); ret = true;
type = cmd_symbol; }
ret = true;
} }
return ret; return ret;
} }
static void _delete_obj_from_string(object* obj)
{
if (obj != NULL)
{
switch (obj->_type)
{
case cmd_number:
case cmd_binary:
break;
default:
free(obj);
break;
}
}
}
static char* entry_completion_generator(const char* text, int state) static char* entry_completion_generator(const char* text, int state)
{ {
static int list_index, len, too_far; static int list_index, len, too_far;
@ -386,7 +534,7 @@ static char* entry_completion_dupstr(char* s)
return r; return r;
} }
static ret_value parse(const string& entry, program& prog) static ret_value parse(const char* entry, program& prog)
{ {
vector<string> entries; vector<string> entries;
ret_value ret = ret_ok; ret_value ret = ret_ok;
@ -403,6 +551,7 @@ static ret_value parse(const string& entry, program& prog)
if(_obj_from_string((*it), obj, obj_size, type)) if(_obj_from_string((*it), obj, obj_size, type))
{ {
prog.push_back(obj, obj_size, type); prog.push_back(obj, obj_size, type);
_delete_obj_from_string(obj);
} }
else else
{ {
@ -417,7 +566,7 @@ static ret_value parse(const string& entry, program& prog)
// interactive entry and decoding // interactive entry and decoding
static ret_value entry(program& prog) static ret_value entry(program& prog)
{ {
char *buf; char* buf;
ret_value ret; ret_value ret;
// declare completion fn (bound to '\t' by default) // declare completion fn (bound to '\t' by default)
@ -427,10 +576,8 @@ static ret_value entry(program& prog)
buf = readline(prompt); buf = readline(prompt);
if (buf != NULL) if (buf != NULL)
{ {
string entry(buf);
// parse it // parse it
ret = parse(entry, prog); ret = parse(buf, prog);
// keep history // keep history
if (buf[0]!=0) if (buf[0]!=0)

View file

@ -16,7 +16,9 @@ void plus()
//TODO really too slow //TODO really too slow
putb(getb() + getb()); putb(getb() + getb());
} }
// string //TODO
#if 0
// string
else if (IS_ARG_TYPE(0, cmd_string)) else if (IS_ARG_TYPE(0, cmd_string))
{ {
ARG_MUST_BE_OF_TYPE(1, cmd_string); ARG_MUST_BE_OF_TYPE(1, cmd_string);
@ -24,6 +26,7 @@ void plus()
_stack->pop_back(); _stack->pop_back();
*((ostring*)_stack->back())->_value += second; *((ostring*)_stack->back())->_value += second;
} }
#endif
else else
ERR_CONTEXT(ret_bad_operand_type); ERR_CONTEXT(ret_bad_operand_type);
} }

View file

@ -23,8 +23,9 @@ void rtob()
MIN_ARGUMENTS(1); MIN_ARGUMENTS(1);
ARG_MUST_BE_OF_TYPE(0, cmd_number); ARG_MUST_BE_OF_TYPE(0, cmd_number);
binary bin((integer_t)getf()); binary bin;
_stack->push_back(&bin, sizeof(binary), cmd_binary); bin.set(((integer_t)getf()));
_stack->push_back(&bin, bin.size(), cmd_binary);
} }

View file

@ -70,8 +70,9 @@ int rpn_for(branch& myobj)
myobj.farg1 = getf(); myobj.farg1 = getf();
// store symbol with first value // store symbol with first value
number num(myobj.farg1); number num;
_heap->add(*sym->_value, &num, sizeof(number), cmd_number); num.set(myobj.farg1);
_heap->add(string(sym->_value), &num, num.size(), cmd_number);
return myobj.arg1 + 1; return myobj.arg1 + 1;
} }
@ -98,7 +99,7 @@ int rpn_next(branch& myobj)
int type; int type;
symbol* var = (symbol*)seq_obj(start_or_for->arg1); symbol* var = (symbol*)seq_obj(start_or_for->arg1);
// check symbol variable is a number, then increase // check symbol variable is a number, then increase
if (_heap->get(*var->_value, obj, size, type) && (type == cmd_number)) if (_heap->get(string(var->_value), obj, size, type) && (type == cmd_number))
((number*)obj)->_value = myobj.farg1; ((number*)obj)->_value = myobj.farg1;
} }
@ -143,7 +144,7 @@ int rpn_step(branch& myobj)
int type; int type;
symbol* var = (symbol*)seq_obj(start_or_for->arg1); symbol* var = (symbol*)seq_obj(start_or_for->arg1);
// check symbol variable is a number, then increase // check symbol variable is a number, then increase
if (_heap->get(*var->_value, obj, size, type) && (type == cmd_number)) if (_heap->get(string(var->_value), obj, size, type) && (type == cmd_number))
((number*)obj)->_value = myobj.farg1; ((number*)obj)->_value = myobj.farg1;
} }

View file

@ -8,7 +8,7 @@ void eval(void)
void* obj; void* obj;
unsigned int size; unsigned int size;
int type; int type;
string& variable = *((symbol*)_stack->back())->_value; string variable(((symbol*)_stack->back())->_value);
if (_heap->get(variable, obj, size, type)) if (_heap->get(variable, obj, size, type))
{ {
_stack->pop_back(); _stack->pop_back();
@ -20,13 +20,13 @@ void eval(void)
else if (IS_ARG_TYPE(0, cmd_program)) else if (IS_ARG_TYPE(0, cmd_program))
{ {
// eval a program // eval a program
string& entry = *((oprogram*)_stack->back())->_value; string entry(((oprogram*)_stack->back())->_value);
_stack->pop_back(); _stack->pop_back();
program prog; program prog;
// make program from entry // make program from entry
if (program::parse(entry, prog) == ret_ok) if (program::parse(entry.c_str(), prog) == ret_ok)
{ {
// run it // run it
prog.run(*_stack, *_heap); prog.run(*_stack, *_heap);
@ -100,16 +100,16 @@ int inprog(branch& myobj)
// load variables // load variables
for (unsigned int i = myobj.arg1 + count_symbols; i > myobj.arg1; i--) for (unsigned int i = myobj.arg1 + count_symbols; i > myobj.arg1; i--)
{ {
_heap->add(*((symbol*)seq_obj(i))->_value, _stack->get_obj(0), _stack->get_len(0), _stack->get_type(0)); _heap->add(string(((symbol*)seq_obj(i))->_value), _stack->get_obj(0), _stack->get_len(0), _stack->get_type(0));
_stack->pop_back(); _stack->pop_back();
} }
// run the program // run the program
string& entry = *((oprogram*)seq_obj(myobj.arg1 + count_symbols + 1))->_value; string entry(((oprogram*)seq_obj(myobj.arg1 + count_symbols + 1))->_value);
program prog; program prog;
// make the program from entry // make the program from entry
if (program::parse(entry, prog) == ret_ok) if (program::parse(entry.c_str(), prog) == ret_ok)
{ {
// run it // run it
prog.run(*_stack, *_heap); prog.run(*_stack, *_heap);

View file

@ -76,6 +76,7 @@ void rot(void)
void depth(void) void depth(void)
{ {
number num((floating_t)_stack->size()); number num;
_stack->push_back(&num, sizeof(number), cmd_number); num.set((floating_t)_stack->size());
_stack->push_back(&num, num.size(), cmd_number);
} }

View file

@ -4,7 +4,8 @@ void sto(void)
MIN_ARGUMENTS(2); MIN_ARGUMENTS(2);
ARG_MUST_BE_OF_TYPE(0, cmd_symbol); ARG_MUST_BE_OF_TYPE(0, cmd_symbol);
string name = getn(); string name(((symbol*)_stack->get_obj(0))->_value);
_stack->pop_back();
_heap->add(name, _stack->get_obj(0), _stack->get_len(0), _stack->get_type(0)); _heap->add(name, _stack->get_obj(0), _stack->get_len(0), _stack->get_type(0));
_stack->pop_back(); _stack->pop_back();
} }
@ -18,7 +19,7 @@ void rcl(void)
void* obj; void* obj;
unsigned int size; unsigned int size;
int type; int type;
string& variable = *((symbol*)_stack->back())->_value; string variable(((symbol*)_stack->back())->_value);
if (_heap->get(variable, obj, size, type)) if (_heap->get(variable, obj, size, type))
{ {
_stack->pop_back(); _stack->pop_back();
@ -36,13 +37,13 @@ void auto_rcl(symbol* symb)
void* obj; void* obj;
unsigned int size; unsigned int size;
int type; int type;
if (_heap->get(*symb->_value, obj, size, type)) if (_heap->get(string(symb->_value), obj, size, type))
_stack->push_back(obj, size, type); _stack->push_back(obj, size, type);
else else
_stack->push_back(symb, sizeof(symbol), cmd_symbol); _stack->push_back(symb, symb->size(), cmd_symbol);
} }
else else
_stack->push_back(symb, sizeof(symbol), cmd_symbol); _stack->push_back(symb, symb->size(), cmd_symbol);
} }
void purge(void) void purge(void)
@ -50,8 +51,11 @@ void purge(void)
MIN_ARGUMENTS(1); MIN_ARGUMENTS(1);
ARG_MUST_BE_OF_TYPE(0, cmd_symbol); ARG_MUST_BE_OF_TYPE(0, cmd_symbol);
if (!_heap->erase(getn())) string name(((symbol*)_stack->back())->_value);
if (!_heap->erase(name))
ERR_CONTEXT(ret_unknown_variable); ERR_CONTEXT(ret_unknown_variable);
else
_stack->pop_back();
} }
void vars(void) void vars(void)

View file

@ -9,23 +9,24 @@ void instr()
((object*)_stack->back())->show(out); ((object*)_stack->back())->show(out);
_stack->pop_back(); _stack->pop_back();
ostring* str = new ostring(out.str().c_str()); ostring str;
_stack->push_back(str, sizeof(ostring), cmd_string); str.set(out.str().c_str(), out.str().size());
_stack->push_back(&str, str.size(), cmd_string);
} }
} }
void strout() void strout()
{ {
MIN_ARGUMENTS(1); MIN_ARGUMENTS(1);
ARG_MUST_BE_OF_TYPE(0, cmd_string); ARG_MUST_BE_OF_TYPE(0, cmd_string);
string& entry = *((ostring*)_stack->back())->_value; string entry(((ostring*)_stack->back())->_value);
_stack->pop_back(); _stack->pop_back();
program prog; program prog;
// make program from string in stack level 1 // make program from string in stack level 1
if (program::parse(entry, prog) == ret_ok) if (program::parse(entry.c_str(), prog) == ret_ok)
{ {
// run it // run it
prog.run(*_stack, *_heap); prog.run(*_stack, *_heap);

View file

@ -115,7 +115,7 @@ void program::test()
{ {
// parse entry and run line // parse entry and run line
program prog; program prog;
ret = program::parse(entry, prog); ret = program::parse(entry.c_str(), prog);
if (ret == ret_ok) if (ret == ret_ok)
{ {
// run it // run it

View file

@ -63,11 +63,14 @@ void eq(void)
putf(getf() == first); putf(getf() == first);
} }
break; break;
//TODO
#if 0
case cmd_symbol: case cmd_symbol:
{ {
string first = getn(); string first = getn();
putf(getn() == first); putf(getn() == first);
} }
#endif
break; break;
default: default:
_stack->pop_back(); _stack->pop_back();

View file

@ -43,11 +43,6 @@ using namespace std;
#include "stack.h" #include "stack.h"
//TODO faut-il que ces variables soient globales ?
static const char g_cursor[] = "> ";
static const string g_show_stack_separator = ":\t";
static const int g_max_commands = 128;
// //
static int g_verbose = 0; static int g_verbose = 0;
@ -106,22 +101,28 @@ typedef union
typedef int (program::*branch_fn_t)(branch&); typedef int (program::*branch_fn_t)(branch&);
// //
class object struct object
{ {
public: // object type
cmd_type_t _type;// object type cmd_type_t _type;
object(cmd_type_t type = cmd_undef):_type(type) { }
//
void show(ostream& stream = cout); void show(ostream& stream = cout);
}; } __attribute__((packed));
class number : public object struct number : public object
{ {
public:
number(floating_t value) : object(cmd_number) { _value = value; }
floating_t _value; floating_t _value;
// representation mode //
void set(floating_t value)
{
_type = cmd_number;
_value = value;
}
unsigned int size() { return sizeof(number); }
// representation mode
typedef enum { typedef enum {
std, std,
fix, fix,
@ -133,18 +134,24 @@ public:
// precision // precision
static int s_default_precision; static int s_default_precision;
static int s_current_precision; static int s_current_precision;
}; } __attribute__((packed));
number::mode_enum number::s_default_mode = number::std; number::mode_enum number::s_default_mode = number::std;
number::mode_enum number::s_mode = number::s_default_mode; number::mode_enum number::s_mode = number::s_default_mode;
int number::s_default_precision = 20; int number::s_default_precision = 20;
int number::s_current_precision = number::s_default_precision; int number::s_current_precision = number::s_default_precision;
class binary : public object struct binary : public object
{ {
public:
binary(integer_t value) : object(cmd_binary) { _value = value; }
integer_t _value; integer_t _value;
//
void set(integer_t value)
{
_type = cmd_binary;
_value = value;
}
unsigned int size() { return sizeof(binary); }
// representation mode // representation mode
typedef enum { typedef enum {
dec, dec,
@ -154,61 +161,190 @@ public:
} binary_enum; } binary_enum;
static binary_enum s_default_mode; static binary_enum s_default_mode;
static binary_enum s_mode; static binary_enum s_mode;
}; } __attribute__((packed));
binary::binary_enum binary::s_default_mode = binary::dec; binary::binary_enum binary::s_default_mode = binary::dec;
binary::binary_enum binary::s_mode = binary::s_default_mode; binary::binary_enum binary::s_mode = binary::s_default_mode;
class ostring : public object struct ostring : public object
{ {
public: //
ostring(string& value, cmd_type_t type = cmd_string) : object(type) void set(const char* value, unsigned int len)
{ {
_value = new string(value); _type = cmd_string;
} if (value != NULL)
ostring(const char* value, cmd_type_t type = cmd_string) : object(type) {
{ if (len>0)
_value = new string(value); (void)memcpy(_value, value, len);
} _value[len] = 0;
string* _value; _len = len;
}; }
else
len = 0;
}
int size() { return sizeof(ostring)+_len+1; }
class oprogram : public ostring //
{ unsigned int _len;
public: char _value[0];
oprogram(string& value, cmd_type_t type = cmd_program) : ostring(value, type) { } } __attribute__((packed));
oprogram(const char* value, cmd_type_t type = cmd_program) : ostring(value, type) { }
};
class symbol : public ostring struct oprogram : public object
{ {
public: //
symbol(string& value, cmd_type_t type = cmd_symbol) : ostring(value, type), _auto_eval(false) { } void set(const char* value, unsigned int len)
symbol(const char* value, cmd_type_t type = cmd_symbol) : ostring(value, type), _auto_eval(false) { } {
bool _auto_eval; _type = cmd_program;
}; if (value != NULL)
{
if (len>0)
(void)memcpy(_value, value, len);
_value[len] = 0;
_len = len;
}
else
len = 0;
}
int size() { return sizeof(oprogram)+_len+1; }
class keyword : public symbol //
{ unsigned int _len;
public: char _value[0];
keyword(program_fn_t fn, string& value, cmd_type_t type = cmd_keyword) : symbol(value, type) { _fn = fn; } } __attribute__((packed));
program_fn_t _fn;
};
class branch : public keyword struct symbol : public object
{ {
public: //
branch(branch_fn_t fn, string& value) : keyword(NULL, value, cmd_branch), arg1(-1), arg2(-1), arg3(-1), arg_bool(false) void set(const char* value, unsigned int len)
{ {
_type = cmd_branch; _type = cmd_symbol;
_fn = fn; _auto_eval = false;
} if (value != NULL)
// branch function {
branch_fn_t _fn; if (len>0)
// args used by cmd_branch cmds (void)memcpy(_value, value, len);
int arg1, arg2, arg3; _value[len] = 0;
floating_t farg1, farg2; _len = len;
bool arg_bool; }
}; else
len = 0;
}
int size() { return sizeof(symbol)+_len+1; }
//
bool _auto_eval;
unsigned int _len;
char _value[0];
} __attribute__((packed));
struct keyword : public object
{
//
void set(program_fn_t fn, const char* value, unsigned int len)
{
_type = cmd_keyword;
_fn = fn;
if (value != NULL)
{
if (len>0)
(void)memcpy(_value, value, len);
_value[len] = 0;
_len = len;
}
else
len = 0;
}
int size() { return sizeof(keyword)+_len+1; }
//
program_fn_t _fn;
unsigned int _len;
char _value[0];
} __attribute__((packed));
struct branch : public object
{
//
void set(branch_fn_t fn, const char* value, unsigned int len)
{
_type = cmd_branch;
_fn = fn;
arg1 = -1;
arg2 = -1;
arg3 = -1;
farg1 = 0;
farg2 = 0;
arg_bool = 0;
if (value != NULL)
{
if (len>0)
(void)memcpy(_value, value, len);
_value[len] = 0;
_len = len;
}
else
len = 0;
}
int size() { return sizeof(branch)+_len+1; }
// branch function
branch_fn_t _fn;
// args used by cmd_branch cmds
int arg1, arg2, arg3;
floating_t farg1, farg2;
bool arg_bool;
unsigned int _len;
char _value[0];
} __attribute__((packed));
void object::show(ostream& stream)
{
switch(_type)
{
case cmd_number:
stream << ((number*)this)->_value;
break;
case cmd_binary:
{
cout << "# ";
switch(((binary*)this)->s_mode)
{
case binary::dec: cout<<std::right<<std::setw(8)<<std::dec<<((binary*)this)->_value<<" d"; break;
case binary::hex: cout<<std::right<<std::setw(16)<<std::hex<<((binary*)this)->_value<<" h"; break;
case binary::oct: cout<<std::right<<std::setw(16)<<std::oct<<((binary*)this)->_value<<" o"; break;
case binary::bin:
{
string mybin;
for (int i = (int)(log((floating_t)((binary*)this)->_value) / log(2.)); i>=0; i--)
{
if (((binary*)this)->_value & (1 << i))
mybin+='1';
else
mybin+='0';
}
cout<<std::right<<std::setw(20)<<std::oct<<mybin<<" b";
}
break;
}
}
break;
case cmd_string:
stream << "\"" << ((ostring*)this)->_value << "\"";
break;
case cmd_program:
stream << "<< " << ((oprogram*)this)->_value << " >>";
break;
case cmd_symbol:
stream << "'" << ((symbol*)this)->_value << "'";
break;
case cmd_keyword:
case cmd_branch:
stream << ((keyword*)this)->_value;
break;
default:
stream << "< unknown object representation >";
break;
}
}
void object::show(ostream& stream) void object::show(ostream& stream)
{ {
@ -305,9 +441,9 @@ public:
} }
// could be an auto-evaluated symbol // could be an auto-evaluated symbol
if (type == cmd_symbol) if (type == cmd_symbol)
{ {
auto_rcl((symbol*)seq_obj(i)); auto_rcl((symbol*)seq_obj(i));
i++; i++;
} }
@ -364,7 +500,23 @@ public:
return ret; return ret;
} }
ret_value preprocess(void) bool compare_keyword(keyword* k, const char* str_to_compare, int len)
{
if (k->_len >= len)
return strncmp(k->_value, str_to_compare, len) == 0;
else
return false;
}
bool compare_branch(branch* b, const char* str_to_compare, int len)
{
if (b->_len >= len)
return strncmp(b->_value, str_to_compare, len) == 0;
else
return false;
}
ret_value preprocess(void)
{ {
// for if-then-else-end // for if-then-else-end
vector<struct if_layout_t> vlayout; vector<struct if_layout_t> vlayout;
@ -380,9 +532,9 @@ public:
if (type == cmd_keyword) if (type == cmd_keyword)
{ {
keyword* k = (keyword*)seq_obj(i); keyword* k = (keyword*)seq_obj(i);
if (k->_value->compare("end") == 0) if (compare_keyword(k, "end", 3))
{ {
int next = i + 1; int next = i + 1;
if (next >= (int)size()) if (next >= (int)size())
next = -1; next = -1;
@ -410,16 +562,16 @@ public:
else if (type == cmd_branch) else if (type == cmd_branch)
{ {
branch* k = (branch*)seq_obj(i); branch* k = (branch*)seq_obj(i);
if (k->_value->compare("if") == 0) if (compare_branch(k, "if", 2))
{ {
if_layout_t layout; if_layout_t layout;
layout.index_if = i; layout.index_if = i;
vlayout.push_back(layout); vlayout.push_back(layout);
layout_index++; layout_index++;
} }
else if (k->_value->compare("then") == 0) else if (compare_branch(k, "then", 4))
{ {
int next = i + 1; int next = i + 1;
if (next >= (int)size()) if (next >= (int)size())
next = -1; next = -1;
@ -446,9 +598,9 @@ public:
k->arg1 = next; k->arg1 = next;
k->arg3 = vlayout[layout_index].index_if; k->arg3 = vlayout[layout_index].index_if;
} }
else if (k->_value->compare("else") == 0) else if (compare_branch(k, "else", 4))
{ {
int next = i + 1; int next = i + 1;
if (next >= (int)size()) if (next >= (int)size())
next = -1; next = -1;
@ -482,16 +634,16 @@ public:
k->arg3 = vlayout[layout_index].index_if; k->arg3 = vlayout[layout_index].index_if;
((branch*)seq_obj(vlayout[layout_index].index_then))->arg2 = next;// fill branch2 (if was false) of 'then' ((branch*)seq_obj(vlayout[layout_index].index_then))->arg2 = next;// fill branch2 (if was false) of 'then'
} }
else if (k->_value->compare("start") == 0) else if (compare_branch(k, "start", 5))
{ {
vstartindex.push_back(i); vstartindex.push_back(i);
} }
else if (k->_value->compare("for") == 0) else if (compare_branch(k, "for", 3))
{ {
vstartindex.push_back(i); vstartindex.push_back(i);
k->arg1 = i + 1;// arg1 points on symbol variable k->arg1 = i + 1;// arg1 points on symbol variable
} }
else if(k->_value->compare("next") == 0) else if(compare_branch(k, "next", 4))
{ {
if (vstartindex.size() == 0) if (vstartindex.size() == 0)
{ {
@ -502,7 +654,7 @@ public:
k->arg1 = vstartindex[vstartindex.size() - 1];// fill 'next' branch1 = 'start' index k->arg1 = vstartindex[vstartindex.size() - 1];// fill 'next' branch1 = 'start' index
vstartindex.pop_back(); vstartindex.pop_back();
} }
else if (k->_value->compare("step") == 0) else if (compare_branch(k, "step", 4))
{ {
if (vstartindex.size() == 0) if (vstartindex.size() == 0)
{ {
@ -513,7 +665,7 @@ public:
k->arg1 = vstartindex[vstartindex.size() - 1];// fill 'step' branch1 = 'start' index k->arg1 = vstartindex[vstartindex.size() - 1];// fill 'step' branch1 = 'start' index
vstartindex.pop_back(); vstartindex.pop_back();
} }
else if (k->_value->compare("->") == 0) else if (compare_branch(k, "->", 2))
{ {
k->arg1 = i;// arg1 is '->' command index in program k->arg1 = i;// arg1 is '->' command index in program
} }
@ -558,31 +710,6 @@ public:
cerr<<"syntax error: "<<context<<endl; cerr<<"syntax error: "<<context<<endl;
} }
// keywords declaration
struct keyword_t
{
cmd_type_t type;
char name[24];
program_fn_t fn;
string comment;
};
static keyword_t _keywords[g_max_commands];
static ret_value get_fn(const char* fn_name, program_fn_t& fn, cmd_type_t& type)
{
for(unsigned int i=0; (i<sizeof(_keywords)/sizeof(_keywords[0])) && (_keywords[i].type != cmd_max); i++)
{
if ((strnlen(_keywords[i].name, sizeof(_keywords[i].name))>0)
&& (strncmp(fn_name, _keywords[i].name, sizeof(_keywords[i].name)) == 0))
{
fn = _keywords[i].fn;
type = _keywords[i].type;
return ret_ok;
}
}
return ret_unknown_err;
}
ret_value get_err(void) { return _err; } ret_value get_err(void) { return _err; }
#include "parse.h" #include "parse.h"
@ -625,8 +752,9 @@ private:
void putf(floating_t value) void putf(floating_t value)
{ {
/* warning, caller must check object type before */ /* warning, caller must check object type before */
number num(value); number num;
_stack->push_back(&num, sizeof(number), cmd_number); num.set(value);
_stack->push_back(&num, num.size(), cmd_number);
} }
integer_t getb() integer_t getb()
@ -640,26 +768,12 @@ private:
void putb(integer_t value) void putb(integer_t value)
{ {
/* warning, caller must check object type before */ /* warning, caller must check object type before */
binary num(value); binary num;
_stack->push_back(&num, sizeof(binary), cmd_binary); num.set(value);
_stack->push_back(&num, num.size(), cmd_binary);
} }
string getn() int stack_size()
{
/* warning, caller must check object type before */
string* a = ((symbol*)_stack->back())->_value;
_stack->pop_back();
return *a;
}
void putn(string& a)
{
/* warning, caller must check object type before */
symbol sym(a);
_stack->push_back(&sym, sizeof(symbol), cmd_symbol);
}
int stack_size()
{ {
return _stack->size(); return _stack->size();
} }
@ -748,7 +862,7 @@ int _tmain(int argc, _TCHAR* argv[])
} }
// make program // make program
ret = program::parse(entry, prog); ret = program::parse(entry.c_str(), prog);
if (ret == ret_ok) if (ret == ret_ok)
{ {
string separator = ""; string separator = "";

View file

@ -8,6 +8,8 @@
#include <map> #include <map>
using namespace std; using namespace std;
#include "debug.h"
#define ALLOC_BLOB (128*1024) #define ALLOC_BLOB (128*1024)
#define LOCAL_COPY_PLACES 3 #define LOCAL_COPY_PLACES 3
#define LOCAL_COPY_SIZE 128 #define LOCAL_COPY_SIZE 128
@ -147,6 +149,11 @@ public:
push_back(&local->blob, local->length, local->type); push_back(&local->blob, local->length, local->type);
} }
void dump(void)
{
dump8((unsigned char*)_base, 0, (unsigned long)(_current - _base));
}
private: private:
char* _base; char* _base;
char* _current; char* _current;
@ -186,13 +193,13 @@ public:
//TODO gerer les pbs de memoire //TODO gerer les pbs de memoire
blob = (struct local_var*)malloc(size + sizeof(local_var)); blob = (struct local_var*)malloc(size + sizeof(local_var));
_map[name] = blob; _map[name] = blob;
} }
else if (size != blob->length) else if (size != blob->length)
{ {
//TODO gerer les pbs de memoire //TODO gerer les pbs de memoire
blob = (struct local_var*)realloc(blob, size + sizeof(local_var)); blob = (struct local_var*)realloc(blob, size + sizeof(local_var));
_map[name] = blob; _map[name] = blob;
} }
blob->length = size; blob->length = size;
blob->type= type; blob->type= type;
memcpy(&blob->blob, obj, size); memcpy(&blob->blob, obj, size);
@ -244,12 +251,12 @@ public:
return false; return false;
} }
bool erase(const string name) bool erase(const string& name)
{ {
map<string, struct local_var*>::iterator i = _map.find(name); map<string, struct local_var*>::iterator i = _map.find(name);
if (i != _map.end()) if (i != _map.end())
{ {
free(i->second); free(i->second);
_map.erase(i->first); _map.erase(i->first);
return true; return true;
} }

View file

@ -2,6 +2,9 @@
static const char version[] = "1.4-beta"; static const char version[] = "1.4-beta";
static const char uname[] = "rpn v1.4-beta, (c) 2015 <louis@rubet.fr>"; static const char uname[] = "rpn v1.4-beta, (c) 2015 <louis@rubet.fr>";
static const char g_cursor[] = "> ";
static const string g_show_stack_separator = "> ";
// syntax // syntax
static const char* syntax[] = { static const char* syntax[] = {
"Reverse Polish Notation language, based on hewlett-Packard RPL", "Reverse Polish Notation language, based on hewlett-Packard RPL",

View file

@ -42,21 +42,11 @@ drop2
drop2 drop2
# test symbol entry 3 # test symbol entry 3
'2 3'
-> stack should be '2 3'
drop
# test symbol entry 4
'2 3
-> stack should be '2 3'
drop
# test symbol entry 5
'' ''
-> stack should be '' -> stack should be ''
drop drop
# test symbol entry 6 # test symbol entry 4
' '
-> stack should be '' -> stack should be ''
drop drop
@ -216,9 +206,9 @@ drop
drop drop
# if-then-else-end test 8 # if-then-else-end test 8
0 if then 0 if then 'ok' else 0 end else 'OK !' end 0 if then 0 if then 'ok' else 0 end else 'OK' end
-> stack size should be 1 -> stack size should be 1
-> stack should be 'OK !' -> stack should be 'OK'
drop drop
# start-next-step test 1 # start-next-step test 1