touched up code a little
This commit is contained in:
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* $Id: Awk.cpp 212 2009-06-25 07:39:27Z hyunghwan.chung $
|
||||
* $Id: Awk.cpp 220 2009-07-01 13:14:39Z hyunghwan.chung $
|
||||
*
|
||||
Copyright 2006-2009 Chung, Hyung-Hwan.
|
||||
|
||||
@ -226,7 +226,7 @@ void Awk::Argument::clear ()
|
||||
this->str.ptr = QSE_NULL;
|
||||
this->str.len = 0;
|
||||
}
|
||||
else if (QSE_AWK_VAL_TYPE(this->val) == QSE_AWK_VAL_MAP)
|
||||
else if (this->val->type == QSE_AWK_VAL_MAP)
|
||||
{
|
||||
QSE_ASSERT (this->run != QSE_NULL);
|
||||
|
||||
@ -241,7 +241,7 @@ void Awk::Argument::clear ()
|
||||
|
||||
if (this->str.ptr != QSE_NULL)
|
||||
{
|
||||
if (QSE_AWK_VAL_TYPE(this->val) != QSE_AWK_VAL_STR)
|
||||
if (this->val->type != QSE_AWK_VAL_STR)
|
||||
{
|
||||
awk_t* awk = this->run->awk->awk;
|
||||
qse_awk_free (awk, this->str.ptr);
|
||||
@ -315,7 +315,7 @@ int Awk::Argument::init (val_t* v)
|
||||
qse_awk_rtx_refupval (this->run->run, v);
|
||||
this->val = v;
|
||||
|
||||
if (QSE_AWK_VAL_TYPE(v) == QSE_AWK_VAL_STR)
|
||||
if (v->type == QSE_AWK_VAL_STR)
|
||||
{
|
||||
int n = qse_awk_rtx_valtonum (
|
||||
this->run->run, v, &this->inum, &this->rnum);
|
||||
@ -334,7 +334,7 @@ int Awk::Argument::init (val_t* v)
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (QSE_AWK_VAL_TYPE(v) == QSE_AWK_VAL_INT)
|
||||
else if (v->type == QSE_AWK_VAL_INT)
|
||||
{
|
||||
this->inum = ((qse_awk_val_int_t*)v)->val;
|
||||
this->rnum = (qse_real_t)((qse_awk_val_int_t*)v)->val;
|
||||
@ -343,7 +343,7 @@ int Awk::Argument::init (val_t* v)
|
||||
this->run->run, v, &this->str.len);
|
||||
if (this->str.ptr != QSE_NULL) return 0;
|
||||
}
|
||||
else if (QSE_AWK_VAL_TYPE(v) == QSE_AWK_VAL_REAL)
|
||||
else if (v->type == QSE_AWK_VAL_REAL)
|
||||
{
|
||||
this->inum = (qse_long_t)((qse_awk_val_real_t*)v)->val;
|
||||
this->rnum = ((qse_awk_val_real_t*)v)->val;
|
||||
@ -352,7 +352,7 @@ int Awk::Argument::init (val_t* v)
|
||||
this->run->run, v, &this->str.len);
|
||||
if (this->str.ptr != QSE_NULL) return 0;
|
||||
}
|
||||
else if (QSE_AWK_VAL_TYPE(v) == QSE_AWK_VAL_NIL)
|
||||
else if (v->type == QSE_AWK_VAL_NIL)
|
||||
{
|
||||
this->inum = 0;
|
||||
this->rnum = 0.0;
|
||||
@ -361,7 +361,7 @@ int Awk::Argument::init (val_t* v)
|
||||
this->run->run, v, &this->str.len);
|
||||
if (this->str.ptr != QSE_NULL) return 0;
|
||||
}
|
||||
else if (QSE_AWK_VAL_TYPE(v) == QSE_AWK_VAL_MAP)
|
||||
else if (v->type == QSE_AWK_VAL_MAP)
|
||||
{
|
||||
this->inum = 0;
|
||||
this->rnum = 0.0;
|
||||
@ -412,7 +412,7 @@ const Awk::char_t* Awk::Argument::toStr (size_t* len) const
|
||||
{
|
||||
|
||||
if (this->val != QSE_NULL &&
|
||||
QSE_AWK_VAL_TYPE(this->val) == QSE_AWK_VAL_MAP)
|
||||
this->val->type == QSE_AWK_VAL_MAP)
|
||||
{
|
||||
*len = 0;
|
||||
return QSE_T("");
|
||||
@ -432,7 +432,7 @@ const Awk::char_t* Awk::Argument::toStr (size_t* len) const
|
||||
bool Awk::Argument::isIndexed () const
|
||||
{
|
||||
if (this->val == QSE_NULL) return false;
|
||||
return QSE_AWK_VAL_TYPE(this->val) == QSE_AWK_VAL_MAP;
|
||||
return this->val->type == QSE_AWK_VAL_MAP;
|
||||
}
|
||||
|
||||
int Awk::Argument::getIndexed (const char_t* idxptr, Awk::Argument& val) const
|
||||
@ -448,7 +448,7 @@ int Awk::Argument::getIndexed (
|
||||
// not initialized yet. val is just nil. not an error
|
||||
if (this->val == QSE_NULL) return 0;
|
||||
// not a map. val is just nil. not an error
|
||||
if (QSE_AWK_VAL_TYPE(this->val) != QSE_AWK_VAL_MAP) return 0;
|
||||
if (this->val->type != QSE_AWK_VAL_MAP) return 0;
|
||||
|
||||
// get the value from the map.
|
||||
qse_awk_val_map_t* m = (qse_awk_val_map_t*)this->val;
|
||||
@ -469,7 +469,7 @@ int Awk::Argument::getIndexed (long_t idx, Argument& val) const
|
||||
if (this->val == QSE_NULL) return 0;
|
||||
|
||||
// not a map. val is just nil. not an error
|
||||
if (QSE_AWK_VAL_TYPE(this->val) != QSE_AWK_VAL_MAP) return 0;
|
||||
if (this->val->type != QSE_AWK_VAL_MAP) return 0;
|
||||
|
||||
char_t ri[128];
|
||||
|
||||
@ -510,7 +510,7 @@ int Awk::Argument::getFirstIndex (Awk::Argument& val) const
|
||||
val.clear ();
|
||||
|
||||
if (this->val == QSE_NULL) return -1;
|
||||
if (QSE_AWK_VAL_TYPE(this->val) != QSE_AWK_VAL_MAP) return -1;
|
||||
if (this->val->type != QSE_AWK_VAL_MAP) return -1;
|
||||
|
||||
qse_size_t buckno;
|
||||
qse_awk_val_map_t* m = (qse_awk_val_map_t*)this->val;
|
||||
@ -533,7 +533,7 @@ int Awk::Argument::getNextIndex (Awk::Argument& val) const
|
||||
val.clear ();
|
||||
|
||||
if (this->val == QSE_NULL) return -1;
|
||||
if (QSE_AWK_VAL_TYPE(this->val) != QSE_AWK_VAL_MAP) return -1;
|
||||
if (this->val->type != QSE_AWK_VAL_MAP) return -1;
|
||||
|
||||
qse_awk_val_map_t* m = (qse_awk_val_map_t*)this->val;
|
||||
|
||||
@ -624,7 +624,7 @@ int Awk::Return::set (const char_t* ptr, size_t len)
|
||||
bool Awk::Return::isIndexed () const
|
||||
{
|
||||
if (this->val == QSE_NULL) return false;
|
||||
return QSE_AWK_VAL_TYPE(this->val) == QSE_AWK_VAL_MAP;
|
||||
return this->val->type == QSE_AWK_VAL_MAP;
|
||||
}
|
||||
|
||||
int Awk::Return::setIndexed (const char_t* idx, size_t iln, long_t v)
|
||||
@ -639,7 +639,7 @@ int Awk::Return::setIndexed (const char_t* idx, size_t iln, long_t v)
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (QSE_AWK_VAL_TYPE(this->val) != QSE_AWK_VAL_MAP)
|
||||
if (this->val->type != QSE_AWK_VAL_MAP)
|
||||
{
|
||||
qse_awk_val_t* x = qse_awk_rtx_makemapval (this->run->run);
|
||||
if (x == QSE_NULL) return -1;
|
||||
@ -702,7 +702,7 @@ int Awk::Return::setIndexed (const char_t* idx, size_t iln, real_t v)
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (QSE_AWK_VAL_TYPE(this->val) != QSE_AWK_VAL_MAP)
|
||||
if (this->val->type != QSE_AWK_VAL_MAP)
|
||||
{
|
||||
qse_awk_val_t* x = qse_awk_rtx_makemapval (this->run->run);
|
||||
if (x == QSE_NULL) return -1;
|
||||
@ -765,7 +765,7 @@ int Awk::Return::setIndexed (const char_t* idx, size_t iln, const char_t* str, s
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (QSE_AWK_VAL_TYPE(this->val) != QSE_AWK_VAL_MAP)
|
||||
if (this->val->type != QSE_AWK_VAL_MAP)
|
||||
{
|
||||
qse_awk_val_t* x = qse_awk_rtx_makemapval (this->run->run);
|
||||
if (x == QSE_NULL) return -1;
|
||||
@ -1078,6 +1078,10 @@ Awk::Awk () throw (): awk (QSE_NULL), functionMap (QSE_NULL),
|
||||
|
||||
{
|
||||
this->errmsg[0] = QSE_T('\0');
|
||||
|
||||
this->runarg.ptr = QSE_NULL;
|
||||
this->runarg.len = 0;
|
||||
this->runarg.capa = 0;
|
||||
}
|
||||
|
||||
Awk::operator Awk::awk_t* () const
|
||||
@ -1234,6 +1238,8 @@ int Awk::open ()
|
||||
|
||||
void Awk::close ()
|
||||
{
|
||||
clearArguments ();
|
||||
|
||||
if (functionMap != QSE_NULL)
|
||||
{
|
||||
qse_map_close (functionMap);
|
||||
@ -1345,14 +1351,12 @@ int Awk::parse ()
|
||||
return n;
|
||||
}
|
||||
|
||||
int Awk::run (const char_t** args, size_t nargs)
|
||||
int Awk::loop ()
|
||||
{
|
||||
QSE_ASSERT (awk != QSE_NULL);
|
||||
|
||||
size_t i;
|
||||
qse_awk_rio_t rio;
|
||||
qse_awk_rcb_t rcb;
|
||||
qse_xstr_t* runarg = QSE_NULL;
|
||||
|
||||
// note that the run field is set below after qse_awk_rtx_open() is
|
||||
// executed.
|
||||
@ -1365,44 +1369,15 @@ int Awk::run (const char_t** args, size_t nargs)
|
||||
if (runCallback)
|
||||
{
|
||||
QSE_MEMSET (&rcb, 0, QSE_SIZEOF(rcb));
|
||||
// TODO: deprecate onRunStart and onRunEnd
|
||||
rcb.on_loop_enter = onRunEnter;
|
||||
rcb.on_loop_exit = onRunExit;
|
||||
rcb.on_statement = onRunStatement;
|
||||
rcb.data = &runctx;
|
||||
}
|
||||
|
||||
if (nargs > 0)
|
||||
{
|
||||
runarg = (qse_xstr_t*) qse_awk_alloc (
|
||||
awk, QSE_SIZEOF(qse_xstr_t)*(nargs+1));
|
||||
|
||||
if (runarg == QSE_NULL)
|
||||
{
|
||||
setError (ERR_NOMEM);
|
||||
return -1;
|
||||
}
|
||||
|
||||
for (i = 0; i < nargs; i++)
|
||||
{
|
||||
runarg[i].len = qse_strlen (args[i]);
|
||||
runarg[i].ptr = qse_awk_strxdup (awk, args[i], runarg[i].len);
|
||||
if (runarg[i].ptr == QSE_NULL)
|
||||
{
|
||||
while (i > 0) qse_awk_free (awk, runarg[--i].ptr);
|
||||
qse_awk_free (awk, runarg);
|
||||
setError (ERR_NOMEM);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
runarg[i].ptr = QSE_NULL;
|
||||
runarg[i].len = 0;
|
||||
rcb.on_loop_enter = onLoopEnter;
|
||||
rcb.on_loop_exit = onLoopExit;
|
||||
rcb.on_statement = onStatement;
|
||||
rcb.udd = &runctx;
|
||||
}
|
||||
|
||||
int n = 0;
|
||||
rtx_t* rtx = qse_awk_rtx_open (
|
||||
awk, QSE_SIZEOF(rxtn_t), &rio, (qse_cstr_t*)runarg);
|
||||
awk, QSE_SIZEOF(rxtn_t), &rio, (qse_cstr_t*)runarg.ptr);
|
||||
if (rtx == QSE_NULL)
|
||||
{
|
||||
retrieveError();
|
||||
@ -1421,13 +1396,6 @@ int Awk::run (const char_t** args, size_t nargs)
|
||||
qse_awk_rtx_close (rtx);
|
||||
}
|
||||
|
||||
if (nargs > 0)
|
||||
{
|
||||
QSE_ASSERT (runarg != QSE_NULL);
|
||||
while (i > 0) qse_awk_free (awk, runarg[--i].ptr);
|
||||
qse_awk_free (awk, runarg);
|
||||
}
|
||||
|
||||
return n;
|
||||
}
|
||||
|
||||
@ -1447,7 +1415,7 @@ int Awk::dispatchFunction (Run* run, const char_t* name, size_t len)
|
||||
pair = qse_map_search (functionMap, name, len);
|
||||
if (pair == QSE_NULL)
|
||||
{
|
||||
run->setError (ERR_FUNNONE, 0, name, len);
|
||||
run->setError (ERR_FUNNF, 0, name, len);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@ -1496,6 +1464,60 @@ int Awk::dispatchFunction (Run* run, const char_t* name, size_t len)
|
||||
return 0;
|
||||
}
|
||||
|
||||
int Awk::addArgument (const char_t* arg, size_t len)
|
||||
{
|
||||
QSE_ASSERT (awk != QSE_NULL);
|
||||
|
||||
if (runarg.len >= runarg.capa)
|
||||
{
|
||||
qse_xstr_t* ptr;
|
||||
size_t capa = runarg.capa;
|
||||
|
||||
capa += 64;
|
||||
ptr = (qse_xstr_t*) qse_awk_realloc (
|
||||
awk, runarg.ptr, QSE_SIZEOF(qse_xstr_t)*(capa+1));
|
||||
if (ptr == QSE_NULL)
|
||||
{
|
||||
setError (ERR_NOMEM);
|
||||
return -1;
|
||||
}
|
||||
|
||||
runarg.ptr = ptr;
|
||||
runarg.capa = capa;
|
||||
}
|
||||
|
||||
runarg.ptr[runarg.len].len = len;
|
||||
runarg.ptr[runarg.len].ptr = qse_awk_strxdup (awk, arg, len);
|
||||
if (runarg.ptr[runarg.len].ptr == QSE_NULL)
|
||||
{
|
||||
setError (ERR_NOMEM);
|
||||
return -1;
|
||||
}
|
||||
|
||||
runarg.len++;
|
||||
runarg.ptr[runarg.len].len = 0;
|
||||
runarg.ptr[runarg.len].ptr = QSE_NULL;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int Awk::addArgument (const char_t* arg)
|
||||
{
|
||||
return addArgument (arg, qse_strlen(arg));
|
||||
}
|
||||
|
||||
void Awk::clearArguments ()
|
||||
{
|
||||
if (runarg.ptr != QSE_NULL)
|
||||
{
|
||||
QSE_ASSERT (awk != QSE_NULL);
|
||||
qse_awk_free (awk, runarg.ptr);
|
||||
runarg.ptr = QSE_NULL;
|
||||
runarg.len = 0;
|
||||
runarg.capa = 0;
|
||||
}
|
||||
}
|
||||
|
||||
int Awk::addGlobal (const char_t* name)
|
||||
{
|
||||
QSE_ASSERT (awk != QSE_NULL);
|
||||
@ -1579,16 +1601,16 @@ void Awk::disableRunCallback ()
|
||||
runCallback = false;
|
||||
}
|
||||
|
||||
bool Awk::onRunEnter (Run& run)
|
||||
bool Awk::onLoopEnter (Run& run)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
void Awk::onRunExit (Run& run, const Argument& ret)
|
||||
void Awk::onLoopExit (Run& run, const Argument& ret)
|
||||
{
|
||||
}
|
||||
|
||||
void Awk::onRunStatement (Run& run, size_t line)
|
||||
void Awk::onStatement (Run& run, size_t line)
|
||||
{
|
||||
}
|
||||
|
||||
@ -1742,26 +1764,26 @@ void Awk::freeFunctionMapValue (map_t* map, void* dptr, size_t dlen)
|
||||
qse_awk_free (awk->awk, dptr);
|
||||
}
|
||||
|
||||
int Awk::onRunEnter (rtx_t* run, void* data)
|
||||
int Awk::onLoopEnter (rtx_t* run, void* data)
|
||||
{
|
||||
Run* r = (Run*)data;
|
||||
return r->awk->onRunEnter(*r)? 0: -1;
|
||||
return r->awk->onLoopEnter(*r)? 0: -1;
|
||||
}
|
||||
|
||||
void Awk::onRunExit (rtx_t* run, val_t* ret, void* data)
|
||||
void Awk::onLoopExit (rtx_t* run, val_t* ret, void* data)
|
||||
{
|
||||
Run* r = (Run*)data;
|
||||
|
||||
Argument x (r);
|
||||
if (x.init (ret) == -1)
|
||||
qse_awk_rtx_seterrnum (r->run, (errnum_t)ERR_NOMEM);
|
||||
else r->awk->onRunExit (*r, x);
|
||||
else r->awk->onLoopExit (*r, x);
|
||||
}
|
||||
|
||||
void Awk::onRunStatement (rtx_t* run, size_t line, void* data)
|
||||
void Awk::onStatement (rtx_t* run, size_t line, void* data)
|
||||
{
|
||||
Run* r = (Run*)data;
|
||||
r->awk->onRunStatement (*r, line);
|
||||
r->awk->onStatement (*r, line);
|
||||
}
|
||||
|
||||
Awk::real_t Awk::pow (awk_t* awk, real_t x, real_t y)
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* $Id: StdAwk.cpp 195 2009-06-10 13:18:25Z hyunghwan.chung $
|
||||
* $Id: StdAwk.cpp 220 2009-07-01 13:14:39Z hyunghwan.chung $
|
||||
*
|
||||
Copyright 2006-2009 Chung, Hyung-Hwan.
|
||||
|
||||
@ -65,19 +65,13 @@ int StdAwk::open ()
|
||||
ADDFNC (QSE_T("srand"), 0, 1, &StdAwk::srand);
|
||||
ADDFNC (QSE_T("system"), 1, 1, &StdAwk::system);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int StdAwk::run (const char_t** args, size_t nargs)
|
||||
{
|
||||
qse_ntime_t now;
|
||||
|
||||
if (qse_gettime(&now) == -1) this->seed = 0;
|
||||
else this->seed = (unsigned int)now;
|
||||
|
||||
::srand (this->seed);
|
||||
|
||||
return Awk::run (args, nargs);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int StdAwk::sin (Run& run, Return& ret, const Argument* args, size_t nargs,
|
||||
@ -391,6 +385,346 @@ int StdAwk::flushFile (File& io)
|
||||
return qse_fio_flush ((qse_fio_t*)io.getHandle());
|
||||
}
|
||||
|
||||
#if 0
|
||||
// console io handlers
|
||||
int StdAwk::openConsole (Console& io)
|
||||
{
|
||||
qse_sio_t* fp;
|
||||
Console::Mode mode = io.getMode();
|
||||
|
||||
switch (mode)
|
||||
{
|
||||
case Console::READ:
|
||||
{
|
||||
if (runarg.ptr == QSE_NULL)
|
||||
{
|
||||
io.setHandle (qse_sio_in);
|
||||
return 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
qse_sio_t* sio;
|
||||
const qse_char_t* file;
|
||||
qse_awk_val_t* argv;
|
||||
qse_map_t* map;
|
||||
qse_map_pair_t* pair;
|
||||
qse_char_t ibuf[128];
|
||||
qse_size_t ibuflen;
|
||||
qse_awk_val_t* v;
|
||||
qse_awk_rtx_valtostr_out_t out;
|
||||
|
||||
nextfile:
|
||||
file = runarg.ptr[runarg_index];
|
||||
|
||||
if (file == QSE_NULL)
|
||||
{
|
||||
/* no more input file */
|
||||
|
||||
if (runarg_count == 0)
|
||||
{
|
||||
/* all ARGVs are empty strings.
|
||||
* so no console files were opened.
|
||||
* open the standard input here.
|
||||
*
|
||||
* 'BEGIN { ARGV[1]=""; ARGV[2]=""; }
|
||||
* { print $0; }' file1 file2
|
||||
*/
|
||||
io.setHandle (qse_sio_in);
|
||||
runarg_count++;
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* handle special case when ARGV[x] has been altered.
|
||||
* so from here down, the file name gotten from
|
||||
* rxtn->c.in.files is not important and is overridden
|
||||
* from ARGV.
|
||||
* 'BEGIN { ARGV[1]="file3"; }
|
||||
* { print $0; }' file1 file2
|
||||
*/
|
||||
argv = qse_awk_rtx_getgbl (rtx, QSE_AWK_GBL_ARGV);
|
||||
QSE_ASSERT (argv != QSE_NULL);
|
||||
QSE_ASSERT (argv->type == QSE_AWK_VAL_MAP);
|
||||
|
||||
map = ((qse_awk_val_map_t*)argv)->map;
|
||||
QSE_ASSERT (map != QSE_NULL);
|
||||
|
||||
ibuflen = qse_awk_longtostr (
|
||||
rtx->awk, rxtn->c.in.index + 1, 10, QSE_NULL,
|
||||
ibuf, QSE_COUNTOF(ibuf));
|
||||
|
||||
pair = qse_map_search (map, ibuf, ibuflen);
|
||||
QSE_ASSERT (pair != QSE_NULL);
|
||||
|
||||
v = QSE_MAP_VPTR(pair);
|
||||
QSE_ASSERT (v != QSE_NULL);
|
||||
|
||||
out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP;
|
||||
if (qse_awk_rtx_valtostr (rtx, v, &out) == QSE_NULL) return -1;
|
||||
|
||||
if (out.u.cpldup.len == 0)
|
||||
{
|
||||
/* the name is empty */
|
||||
qse_awk_rtx_free (rtx, out.u.cpldup.ptr);
|
||||
rxtn->c.in.index++;
|
||||
goto nextfile;
|
||||
}
|
||||
|
||||
if (qse_strlen(out.u.cpldup.ptr) < out.u.cpldup.len)
|
||||
{
|
||||
/* the name contains one or more '\0' */
|
||||
qse_cstr_t errarg;
|
||||
|
||||
errarg.ptr = out.u.cpldup.ptr;
|
||||
/* use this length not to contains '\0'
|
||||
* in an error message */
|
||||
errarg.len = qse_strlen(out.u.cpldup.ptr);
|
||||
|
||||
qse_awk_rtx_seterror (
|
||||
rtx, QSE_AWK_EIONMNL, 0, &errarg);
|
||||
|
||||
qse_awk_rtx_free (rtx, out.u.cpldup.ptr);
|
||||
return -1;
|
||||
}
|
||||
|
||||
file = out.u.cpldup.ptr;
|
||||
|
||||
if (file[0] == QSE_T('-') && file[1] == QSE_T('\0'))
|
||||
{
|
||||
/* special file name '-' */
|
||||
sio = qse_sio_in;
|
||||
}
|
||||
else
|
||||
{
|
||||
sio = qse_sio_open (
|
||||
rtx->awk->mmgr, 0, file, QSE_SIO_READ);
|
||||
if (sio == QSE_NULL)
|
||||
{
|
||||
qse_cstr_t errarg;
|
||||
|
||||
errarg.ptr = file;
|
||||
errarg.len = qse_strlen(file);
|
||||
|
||||
qse_awk_rtx_seterror (
|
||||
rtx, QSE_AWK_EOPEN, 0, &errarg);
|
||||
|
||||
qse_awk_rtx_free (rtx, out.u.cpldup.ptr);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
if (qse_awk_rtx_setfilename (
|
||||
rtx, file, qse_strlen(file)) == -1)
|
||||
{
|
||||
if (sio != qse_sio_in) qse_sio_close (sio);
|
||||
qse_awk_rtx_free (rtx, out.u.cpldup.ptr);
|
||||
return -1;
|
||||
}
|
||||
|
||||
qse_awk_rtx_free (rtx, out.u.cpldup.ptr);
|
||||
riod->handle = sio;
|
||||
|
||||
/* increment the counter of files successfully opened */
|
||||
rxtn->c.in.count++;
|
||||
}
|
||||
|
||||
rxtn->c.in.index++;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
case Console::WRITE:
|
||||
break;
|
||||
}
|
||||
|
||||
#if 0
|
||||
FILE* fp = QSE_NULL;
|
||||
const char_t* fn = QSE_NULL;
|
||||
|
||||
switch (mode)
|
||||
{
|
||||
case StdAwk::Console::READ:
|
||||
|
||||
if (numConInFiles == 0) fp = stdin;
|
||||
else
|
||||
{
|
||||
fn = conInFile[0];
|
||||
fp = qse_fopen (fn, QSE_T("r"));
|
||||
}
|
||||
break;
|
||||
|
||||
case StdAwk::Console::WRITE:
|
||||
|
||||
if (numConOutFiles == 0) fp = stdout;
|
||||
else
|
||||
{
|
||||
fn = conOutFile[0];
|
||||
fp = qse_fopen (fn, QSE_T("w"));
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
if (fp == NULL) return -1;
|
||||
|
||||
ConTrack* t = (ConTrack*)
|
||||
qse_awk_alloc (awk, QSE_SIZEOF(ConTrack));
|
||||
if (t == QSE_NULL)
|
||||
{
|
||||
if (fp != stdin && fp != stdout) fclose (fp);
|
||||
return -1;
|
||||
}
|
||||
|
||||
t->handle = fp;
|
||||
t->nextConIdx = 1;
|
||||
|
||||
if (fn != QSE_NULL)
|
||||
{
|
||||
if (io.setFileName(fn) == -1)
|
||||
{
|
||||
if (fp != stdin && fp != stdout) fclose (fp);
|
||||
qse_awk_free (awk, t);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
io.setHandle (t);
|
||||
return 1;
|
||||
#endif
|
||||
}
|
||||
|
||||
int StdAwk::closeConsole (Console& io)
|
||||
{
|
||||
ConTrack* t = (ConTrack*)io.getHandle();
|
||||
FILE* fp = t->handle;
|
||||
|
||||
if (fp == stdout || fp == stderr) fflush (fp);
|
||||
if (fp != stdin && fp != stdout && fp != stderr) fclose (fp);
|
||||
|
||||
qse_awk_free (awk, t);
|
||||
return 0;
|
||||
}
|
||||
|
||||
ssize_t StdAwk::readConsole (Console& io, char_t* buf, size_t len)
|
||||
{
|
||||
ConTrack* t = (ConTrack*)io.getHandle();
|
||||
FILE* fp = t->handle;
|
||||
ssize_t n = 0;
|
||||
|
||||
while (n < (ssize_t)len)
|
||||
{
|
||||
qse_cint_t c = qse_fgetc (fp);
|
||||
if (c == QSE_CHAR_EOF)
|
||||
{
|
||||
if (qse_ferror(fp)) return -1;
|
||||
if (t->nextConIdx >= numConInFiles) break;
|
||||
|
||||
const char_t* fn = conInFile[t->nextConIdx];
|
||||
FILE* nfp = qse_fopen (fn, QSE_T("r"));
|
||||
if (nfp == QSE_NULL) return -1;
|
||||
|
||||
if (io.setFileName(fn) == -1 || io.setFNR(0) == -1)
|
||||
{
|
||||
fclose (nfp);
|
||||
return -1;
|
||||
}
|
||||
|
||||
fclose (fp);
|
||||
fp = nfp;
|
||||
t->nextConIdx++;
|
||||
t->handle = fp;
|
||||
|
||||
if (n == 0) continue;
|
||||
else break;
|
||||
}
|
||||
|
||||
buf[n++] = c;
|
||||
if (c == QSE_T('\n')) break;
|
||||
}
|
||||
|
||||
return n;
|
||||
}
|
||||
|
||||
ssize_t StdAwk::writeConsole (Console& io, const char_t* buf, size_t len)
|
||||
{
|
||||
ConTrack* t = (ConTrack*)io.getHandle();
|
||||
FILE* fp = t->handle;
|
||||
size_t left = len;
|
||||
|
||||
while (left > 0)
|
||||
{
|
||||
if (*buf == QSE_T('\0'))
|
||||
{
|
||||
if (qse_fputc(*buf,fp) == QSE_CHAR_EOF) return -1;
|
||||
left -= 1; buf += 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
int chunk = (left > QSE_TYPE_MAX(int))? QSE_TYPE_MAX(int): (int)left;
|
||||
int n = qse_fprintf (fp, QSE_T("%.*s"), chunk, buf);
|
||||
if (n < 0 || n > chunk) return -1;
|
||||
left -= n; buf += n;
|
||||
}
|
||||
}
|
||||
|
||||
return len;
|
||||
}
|
||||
|
||||
int StdAwk::flushConsole (Console& io)
|
||||
{
|
||||
ConTrack* t = (ConTrack*)io.getHandle();
|
||||
FILE* fp = t->handle;
|
||||
return ::fflush (fp);
|
||||
}
|
||||
|
||||
int StdAwk::nextConsole (Console& io)
|
||||
{
|
||||
StdAwk::Console::Mode mode = io.getMode();
|
||||
|
||||
ConTrack* t = (ConTrack*)io.getHandle();
|
||||
FILE* ofp = t->handle;
|
||||
FILE* nfp = QSE_NULL;
|
||||
const char_t* fn = QSE_NULL;
|
||||
|
||||
switch (mode)
|
||||
{
|
||||
case StdAwk::Console::READ:
|
||||
|
||||
if (t->nextConIdx >= numConInFiles) return 0;
|
||||
fn = conInFile[t->nextConIdx];
|
||||
nfp = qse_fopen (fn, QSE_T("r"));
|
||||
break;
|
||||
|
||||
case StdAwk::Console::WRITE:
|
||||
|
||||
if (t->nextConIdx >= numConOutFiles) return 0;
|
||||
fn = conOutFile[t->nextConIdx];
|
||||
nfp = qse_fopen (fn, QSE_T("w"));
|
||||
break;
|
||||
}
|
||||
|
||||
if (nfp == QSE_NULL) return -1;
|
||||
|
||||
if (fn != QSE_NULL)
|
||||
{
|
||||
if (io.setFileName (fn) == -1)
|
||||
{
|
||||
fclose (nfp);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
fclose (ofp);
|
||||
|
||||
t->nextConIdx++;
|
||||
t->handle = nfp;
|
||||
|
||||
return 1;
|
||||
}
|
||||
#endif
|
||||
|
||||
// memory allocation primitives
|
||||
void* StdAwk::allocMem (size_t n) throw ()
|
||||
{
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* $Id: err.c 214 2009-06-27 02:50:54Z hyunghwan.chung $
|
||||
* $Id: err.c 220 2009-07-01 13:14:39Z hyunghwan.chung $
|
||||
*
|
||||
Copyright 2006-2009 Chung, Hyung-Hwan.
|
||||
|
||||
@ -29,17 +29,9 @@ const qse_char_t* qse_awk_dflerrstr (qse_awk_t* awk, qse_awk_errnum_t errnum)
|
||||
QSE_T("insufficient memory"),
|
||||
QSE_T("not supported"),
|
||||
QSE_T("operation not allowed"),
|
||||
QSE_T("no such device"),
|
||||
QSE_T("no space left on device"),
|
||||
QSE_T("too many open files"),
|
||||
QSE_T("too many links"),
|
||||
QSE_T("resource temporarily unavailable"),
|
||||
QSE_T("'${0}' not existing"),
|
||||
QSE_T("'${0}' not found"),
|
||||
QSE_T("'${0}' already exists"),
|
||||
QSE_T("file or data too big"),
|
||||
QSE_T("system too busy"),
|
||||
QSE_T("is a directory"),
|
||||
QSE_T("IO error"),
|
||||
QSE_T("I/O error"),
|
||||
|
||||
QSE_T("cannot open '${0}'"),
|
||||
QSE_T("cannot read '${0}'"),
|
||||
@ -49,43 +41,43 @@ const qse_char_t* qse_awk_dflerrstr (qse_awk_t* awk, qse_awk_errnum_t errnum)
|
||||
QSE_T("internal error that should never have happened"),
|
||||
QSE_T("general runtime error"),
|
||||
QSE_T("block nested too deeply"),
|
||||
QSE_T("expressio nested too deeply"),
|
||||
QSE_T("expression nested too deeply"),
|
||||
|
||||
QSE_T("cannot open source input"),
|
||||
QSE_T("cannot close source input"),
|
||||
QSE_T("cannot read source input"),
|
||||
QSE_T("failed to open source input"),
|
||||
QSE_T("failed to close source input"),
|
||||
QSE_T("failed to read source input"),
|
||||
|
||||
QSE_T("cannot open source output"),
|
||||
QSE_T("cannot close source output"),
|
||||
QSE_T("cannot write source output"),
|
||||
QSE_T("failed to open source output"),
|
||||
QSE_T("failed to close source output"),
|
||||
QSE_T("failed to write source output"),
|
||||
|
||||
QSE_T("invalid character '${0}'"),
|
||||
QSE_T("invalid digit '${0}'"),
|
||||
QSE_T("cannot unget character"),
|
||||
QSE_T("failed to unget character"),
|
||||
|
||||
QSE_T("unexpected end of source"),
|
||||
QSE_T("a comment not closed properly"),
|
||||
QSE_T("a string or a regular expression not closed"),
|
||||
QSE_T("unexpected end of a regular expression"),
|
||||
QSE_T("a left brace expected in place of '${0}'"),
|
||||
QSE_T("a left parenthesis expected in place of '${0}'"),
|
||||
QSE_T("a right parenthesis expected in place of '${0}'"),
|
||||
QSE_T("a right bracket expected in place of '${0}'"),
|
||||
QSE_T("a comma expected in place of '${0}'"),
|
||||
QSE_T("a semicolon expected in place of '${0}'"),
|
||||
QSE_T("a colon expected in place of '${0}'"),
|
||||
QSE_T("comment not closed properly"),
|
||||
QSE_T("string or regular expression not closed"),
|
||||
QSE_T("unexpected end of regular expression"),
|
||||
QSE_T("left brace expected in place of '${0}'"),
|
||||
QSE_T("left parenthesis expected in place of '${0}'"),
|
||||
QSE_T("right parenthesis expected in place of '${0}'"),
|
||||
QSE_T("right bracket expected in place of '${0}'"),
|
||||
QSE_T("comma expected in place of '${0}'"),
|
||||
QSE_T("semicolon expected in place of '${0}'"),
|
||||
QSE_T("colon expected in place of '${0}'"),
|
||||
QSE_T("statement not ending with a semicolon"),
|
||||
QSE_T("'in' expected in place of '${0}'"),
|
||||
QSE_T("right-hand side of the 'in' operator not a variable"),
|
||||
QSE_T("right-hand side of 'in' not a variable"),
|
||||
QSE_T("invalid expression"),
|
||||
|
||||
QSE_T("keyword 'function' expected in place of '${0}'"),
|
||||
QSE_T("keyword 'while' expected in place of '${0}'"),
|
||||
QSE_T("'function' expected in place of '${0}'"),
|
||||
QSE_T("'while' expected in place of '${0}'"),
|
||||
QSE_T("invalid assignment statement"),
|
||||
QSE_T("an identifier expected in place of '${0}'"),
|
||||
QSE_T("identifier expected in place of '${0}'"),
|
||||
QSE_T("'${0}' not a valid function name"),
|
||||
QSE_T("BEGIN not followed by a left bracket on the same line"),
|
||||
QSE_T("END not followed by a left bracket on the same line"),
|
||||
QSE_T("BEGIN not followed by left bracket on the same line"),
|
||||
QSE_T("END not followed by left bracket on the same line"),
|
||||
QSE_T("duplicate BEGIN"),
|
||||
QSE_T("duplicate END"),
|
||||
QSE_T("keyword '${0}' redefined"),
|
||||
@ -105,15 +97,15 @@ const qse_char_t* qse_awk_dflerrstr (qse_awk_t* awk, qse_awk_errnum_t errnum)
|
||||
QSE_T("too many global variables"),
|
||||
QSE_T("too many local variables"),
|
||||
QSE_T("too many parameters"),
|
||||
QSE_T("delete statement not followed by a normal variable"),
|
||||
QSE_T("reset statement not followed by a normal variable"),
|
||||
QSE_T("break statement outside a loop"),
|
||||
QSE_T("continue statement outside a loop"),
|
||||
QSE_T("next statement illegal in the BEGIN block"),
|
||||
QSE_T("next statement illegal in the END block"),
|
||||
QSE_T("nextfile statement illegal in the BEGIN block"),
|
||||
QSE_T("nextfile statement illegal in the END block"),
|
||||
QSE_T("printf not followed by any arguments"),
|
||||
QSE_T("'delete' not followed by variable"),
|
||||
QSE_T("'reset' not followed by variable"),
|
||||
QSE_T("'break' outside a loop"),
|
||||
QSE_T("'continue' outside a loop"),
|
||||
QSE_T("'next' illegal in the BEGIN block"),
|
||||
QSE_T("'next' illegal in the END block"),
|
||||
QSE_T("'nextfile' illegal in the BEGIN block"),
|
||||
QSE_T("'nextfile' illegal in the END block"),
|
||||
QSE_T("'printf' not followed by argument"),
|
||||
QSE_T("both prefix and postfix increment/decrement operator present"),
|
||||
|
||||
QSE_T("divide by zero"),
|
||||
@ -133,21 +125,21 @@ const qse_char_t* qse_awk_dflerrstr (qse_awk_t* awk, qse_awk_errnum_t errnum)
|
||||
QSE_T("a positional value cannot be assigned a map"),
|
||||
QSE_T("map '${0}' not assignable with a scalar"),
|
||||
QSE_T("cannot change a scalar value to a map"),
|
||||
QSE_T("a map is not allowed"),
|
||||
QSE_T("map not allowed"),
|
||||
QSE_T("invalid value type"),
|
||||
QSE_T("delete statement called with a wrong target"),
|
||||
QSE_T("reset statement called with a wrong target"),
|
||||
QSE_T("next statement called from the BEGIN block"),
|
||||
QSE_T("next statement called from the END block"),
|
||||
QSE_T("nextfile statement called from the BEGIN block"),
|
||||
QSE_T("nextfile statement called from the END block"),
|
||||
QSE_T("'delete' called with wrong target"),
|
||||
QSE_T("'reset' called with wrong target"),
|
||||
QSE_T("'next' called from BEGIN block"),
|
||||
QSE_T("'next' called from END block"),
|
||||
QSE_T("'nextfile' called from BEGIN block"),
|
||||
QSE_T("'nextfile' called from END block"),
|
||||
QSE_T("wrong implementation of intrinsic function handler"),
|
||||
QSE_T("intrinsic function handler returned an error"),
|
||||
QSE_T("wrong implementation of user-defined io handler"),
|
||||
QSE_T("IO handler returned an error"),
|
||||
QSE_T("no such IO name found"),
|
||||
QSE_T("IO name empty"),
|
||||
QSE_T("IO name '${0}' containing a null character"),
|
||||
QSE_T("I/O handler returned an error"),
|
||||
QSE_T("no such I/O name found"),
|
||||
QSE_T("I/O name empty"),
|
||||
QSE_T("I/O name '${0}' containing '\\0'"),
|
||||
QSE_T("not sufficient arguments to formatting sequence"),
|
||||
QSE_T("recursion detected in format conversion"),
|
||||
QSE_T("invalid character in CONVFMT"),
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* $Id: misc.c 219 2009-06-30 13:14:39Z hyunghwan.chung $
|
||||
* $Id: misc.c 220 2009-07-01 13:14:39Z hyunghwan.chung $
|
||||
*
|
||||
Copyright 2006-2009 Chung, Hyung-Hwan.
|
||||
|
||||
@ -23,6 +23,11 @@ void* qse_awk_alloc (qse_awk_t* awk, qse_size_t size)
|
||||
return QSE_AWK_ALLOC (awk, size);
|
||||
}
|
||||
|
||||
void* qse_awk_realloc (qse_awk_t* awk, void* ptr, qse_size_t size)
|
||||
{
|
||||
return QSE_AWK_REALLOC (awk, ptr, size);
|
||||
}
|
||||
|
||||
void qse_awk_free (qse_awk_t* awk, void* ptr)
|
||||
{
|
||||
QSE_AWK_FREE (awk, ptr);
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* $Id: parse.c 218 2009-06-29 10:17:39Z hyunghwan.chung $
|
||||
* $Id: parse.c 220 2009-07-01 13:14:39Z hyunghwan.chung $
|
||||
*
|
||||
Copyright 2006-2009 Chung, Hyung-Hwan.
|
||||
|
||||
@ -553,7 +553,7 @@ static int parse (qse_awk_t* awk)
|
||||
QSE_MAP_KPTR(p), QSE_MAP_KLEN(p)) == QSE_NULL)
|
||||
{
|
||||
/* TODO: set better error no & line */
|
||||
SETERRARG (awk, QSE_AWK_EFUNNONE,
|
||||
SETERRARG (awk, QSE_AWK_EFUNNF,
|
||||
*(qse_size_t*)QSE_MAP_VPTR(p),
|
||||
QSE_MAP_KPTR(p),
|
||||
QSE_MAP_KLEN(p));
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* $Id: run.c 213 2009-06-26 13:05:19Z hyunghwan.chung $
|
||||
* $Id: run.c 220 2009-07-01 13:14:39Z hyunghwan.chung $
|
||||
*
|
||||
Copyright 2006-2009 Chung, Hyung-Hwan.
|
||||
|
||||
@ -1322,7 +1322,7 @@ static int run_bpae_loop (qse_awk_rtx_t* rtx)
|
||||
if (rtx->rcb.on_loop_enter != QSE_NULL)
|
||||
{
|
||||
qse_awk_rtx_seterrnum (rtx, QSE_AWK_ENOERR);
|
||||
ret = rtx->rcb.on_loop_enter (rtx, rtx->rcb.data);
|
||||
ret = rtx->rcb.on_loop_enter (rtx, rtx->rcb.udd);
|
||||
if (ret <= -1)
|
||||
{
|
||||
if (rtx->errinf.num == QSE_AWK_ENOMEM)
|
||||
@ -1426,7 +1426,7 @@ static int run_bpae_loop (qse_awk_rtx_t* rtx)
|
||||
/* we call the on_exit handler regardless of ret.
|
||||
* the return value passed is the global return value
|
||||
* in the stack. */
|
||||
rtx->rcb.on_loop_exit (rtx, v, rtx->rcb.data);
|
||||
rtx->rcb.on_loop_exit (rtx, v, rtx->rcb.udd);
|
||||
}
|
||||
|
||||
/* end the life of the global return value */
|
||||
@ -1498,7 +1498,7 @@ qse_awk_val_t* qse_awk_rtx_call (
|
||||
errarg.ptr = call.what.fun.name.ptr;
|
||||
errarg.len = call.what.fun.name.len;
|
||||
|
||||
qse_awk_rtx_seterror (rtx, QSE_AWK_EFUNNONE, 0, &errarg);
|
||||
qse_awk_rtx_seterror (rtx, QSE_AWK_EFUNNF, 0, &errarg);
|
||||
return QSE_NULL;
|
||||
}
|
||||
|
||||
@ -1542,17 +1542,6 @@ qse_awk_val_t* qse_awk_rtx_call (
|
||||
qse_awk_rtx_refupval (rtx, v);
|
||||
}
|
||||
|
||||
#if 0
|
||||
if (rtx->rcb.on_loop_exit != QSE_NULL)
|
||||
{
|
||||
rtx->rcb.on_loop_exit (
|
||||
rtx,
|
||||
((v == QSE_NULL)? qse_awk_val_nil: v),
|
||||
rtx->rcb.data
|
||||
);
|
||||
}
|
||||
#endif
|
||||
|
||||
/* return the return value with its reference count at least 1.
|
||||
* the caller of this function should count down its reference. */
|
||||
return v;
|
||||
@ -1844,7 +1833,7 @@ static int run_block0 (qse_awk_rtx_t* run, qse_awk_nde_blk_t* nde)
|
||||
if ((rtx)->rcb.on_statement != QSE_NULL) \
|
||||
{ \
|
||||
(rtx)->rcb.on_statement ( \
|
||||
rtx, (nde)->line, (rtx)->rcb.data); \
|
||||
rtx, (nde)->line, (rtx)->rcb.udd); \
|
||||
}
|
||||
|
||||
static int run_statement (qse_awk_rtx_t* run, qse_awk_nde_t* nde)
|
||||
@ -5520,7 +5509,7 @@ static qse_awk_val_t* eval_fun_ex (
|
||||
errarg.len = call->what.fun.name.len,
|
||||
|
||||
qse_awk_rtx_seterror (run,
|
||||
QSE_AWK_EFUNNONE, nde->line, &errarg);
|
||||
QSE_AWK_EFUNNF, nde->line, &errarg);
|
||||
return QSE_NULL;
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user