renamed Awk::uponDemise() to Awk::uponClosing and added Awk::uponClearing()

This commit is contained in:
hyung-hwan 2015-03-12 06:39:16 +00:00
parent 0355e4e96e
commit 756a93ff41
6 changed files with 66 additions and 36 deletions

View File

@ -968,11 +968,19 @@ public:
void close (); void close ();
/// ///
/// The uponClose() function is called back after Awk::close() /// The uponClosing() function is called back after Awk::close()
/// has cleared most of the internal data but before destroying /// has cleared most of the internal data but before destroying
/// the underlying awk object. /// the underlying awk object. This maps to the close callback
/// of #qse_awk_ecb_t.
/// ///
virtual void uponDemise () {} virtual void uponClosing ();
///
/// The uponClearing() function is called back when Awk::close()
/// begins clearing internal data. This maps to the clear callback
/// of #qse_awk_ecb_t.
///
virtual void uponClearing ();
/// ///
/// The parse() function parses the source code read from the input /// The parse() function parses the source code read from the input

View File

@ -95,7 +95,7 @@ public:
int open (); int open ();
void close (); void close ();
void uponDemise (); void uponClosing ();
Run* parse (Source& in, Source& out); Run* parse (Source& in, Source& out);

View File

@ -923,7 +923,9 @@ struct qse_awk_mod_sym_t
/** /**
* The qse_awk_ecb_close_t type defines the callback function * The qse_awk_ecb_close_t type defines the callback function
* called when an awk object is closed. * called when an awk object is closed. The qse_awk_close() function
* calls this callback function after having called qse_awk_clear()
* but before actual closing.
*/ */
typedef void (*qse_awk_ecb_close_t) ( typedef void (*qse_awk_ecb_close_t) (
qse_awk_t* awk /**< awk */ qse_awk_t* awk /**< awk */
@ -931,7 +933,8 @@ typedef void (*qse_awk_ecb_close_t) (
/** /**
* The qse_awk_ecb_clear_t type defines the callback function * The qse_awk_ecb_clear_t type defines the callback function
* called when an awk object is cleared. * called when an awk object is cleared. The qse_awk_clear() function
* calls this calllback function before it performs actual clearing.
*/ */
typedef void (*qse_awk_ecb_clear_t) ( typedef void (*qse_awk_ecb_clear_t) (
qse_awk_t* awk /**< awk */ qse_awk_t* awk /**< awk */

View File

@ -1068,7 +1068,7 @@ void Awk::setError (errnum_t code, const cstr_t* args, const loc_t* loc)
if (awk != QSE_NULL) if (awk != QSE_NULL)
{ {
qse_awk_seterror (awk, code, args, loc); qse_awk_seterror (awk, code, args, loc);
retrieveError (); this->retrieveError ();
} }
else else
{ {
@ -1119,15 +1119,15 @@ void Awk::retrieveError (Run* run)
static void fini_xtn (qse_awk_t* awk) static void fini_xtn (qse_awk_t* awk)
{ {
xtn_t* xtn = (xtn_t*)qse_awk_getxtn(awk); xtn_t* xtn = (xtn_t*)qse_awk_getxtn(awk);
xtn->awk->uponDemise (); xtn->awk->uponClosing ();
} }
static void clear_xtn (qse_awk_t* awk) static void clear_xtn (qse_awk_t* awk)
{ {
// do nothing xtn_t* xtn = (xtn_t*)qse_awk_getxtn(awk);
xtn->awk->uponClearing ();
} }
int Awk::open () int Awk::open ()
{ {
QSE_ASSERT (this->awk == QSE_NULL); QSE_ASSERT (this->awk == QSE_NULL);
@ -1142,7 +1142,7 @@ int Awk::open ()
prm.math.mod = mod; prm.math.mod = mod;
prm.modopen = modopen; prm.modopen = modopen;
prm.modclose = modclose; prm.modclose = modclose;
prm.modsym = modsym; prm.modsym = modsym;
qse_awk_errnum_t errnum; qse_awk_errnum_t errnum;
this->awk = qse_awk_open (this->getMmgr(), QSE_SIZEOF(xtn_t), &prm, &errnum); this->awk = qse_awk_open (this->getMmgr(), QSE_SIZEOF(xtn_t), &prm, &errnum);
@ -1228,13 +1228,23 @@ void Awk::close ()
this->clearError (); this->clearError ();
} }
void Awk::uponClosing ()
{
// nothing to do
}
void Awk::uponClearing ()
{
// nothing to do
}
Awk::Run* Awk::parse (Source& in, Source& out) Awk::Run* Awk::parse (Source& in, Source& out)
{ {
QSE_ASSERT (awk != QSE_NULL); QSE_ASSERT (awk != QSE_NULL);
if (&in == &Source::NONE) if (&in == &Source::NONE)
{ {
setError (QSE_AWK_EINVAL); this->setError (QSE_AWK_EINVAL);
return QSE_NULL; return QSE_NULL;
} }
@ -1250,7 +1260,7 @@ Awk::Run* Awk::parse (Source& in, Source& out)
int n = qse_awk_parse (awk, &sio); int n = qse_awk_parse (awk, &sio);
if (n <= -1) if (n <= -1)
{ {
retrieveError (); this->retrieveError ();
return QSE_NULL; return QSE_NULL;
} }
@ -1277,7 +1287,7 @@ int Awk::loop (Value* ret)
val_t* rv = qse_awk_rtx_loop (this->runctx.rtx); val_t* rv = qse_awk_rtx_loop (this->runctx.rtx);
if (rv == QSE_NULL) if (rv == QSE_NULL)
{ {
retrieveError (&this->runctx); this->retrieveError (&this->runctx);
return -1; return -1;
} }
@ -1307,7 +1317,7 @@ int Awk::call (
if (ptr == QSE_NULL) if (ptr == QSE_NULL)
{ {
this->runctx.setError (QSE_AWK_ENOMEM); this->runctx.setError (QSE_AWK_ENOMEM);
retrieveError (&this->runctx); this->retrieveError (&this->runctx);
return -1; return -1;
} }
} }
@ -1321,7 +1331,7 @@ int Awk::call (
if (rv == QSE_NULL) if (rv == QSE_NULL)
{ {
retrieveError (&this->runctx); this->retrieveError (&this->runctx);
return -1; return -1;
} }
@ -1350,7 +1360,7 @@ int Awk::init_runctx ()
rtx_t* rtx = qse_awk_rtx_open (awk, QSE_SIZEOF(rxtn_t), &rio); rtx_t* rtx = qse_awk_rtx_open (awk, QSE_SIZEOF(rxtn_t), &rio);
if (rtx == QSE_NULL) if (rtx == QSE_NULL)
{ {
retrieveError(); this->retrieveError();
return -1; return -1;
} }
@ -1615,7 +1625,7 @@ int Awk::addArgument (const char_t* arg, size_t len)
{ {
QSE_ASSERT (awk != QSE_NULL); QSE_ASSERT (awk != QSE_NULL);
int n = runarg.add (awk, arg, len); int n = runarg.add (awk, arg, len);
if (n <= -1) setError (QSE_AWK_ENOMEM); if (n <= -1) this->setError (QSE_AWK_ENOMEM);
return n; return n;
} }
@ -1633,7 +1643,7 @@ int Awk::addGlobal (const char_t* name)
{ {
QSE_ASSERT (awk != QSE_NULL); QSE_ASSERT (awk != QSE_NULL);
int n = qse_awk_addgbl (awk, name); int n = qse_awk_addgbl (awk, name);
if (n <= -1) retrieveError (); if (n <= -1) this->retrieveError ();
return n; return n;
} }
@ -1641,7 +1651,7 @@ int Awk::deleteGlobal (const char_t* name)
{ {
QSE_ASSERT (awk != QSE_NULL); QSE_ASSERT (awk != QSE_NULL);
int n = qse_awk_delgbl (awk, name); int n = qse_awk_delgbl (awk, name);
if (n <= -1) retrieveError (); if (n <= -1) this->retrieveError ();
return n; return n;
} }
@ -1649,7 +1659,7 @@ int Awk::findGlobal (const char_t* name)
{ {
QSE_ASSERT (awk != QSE_NULL); QSE_ASSERT (awk != QSE_NULL);
int n = qse_awk_findgbl (awk, name); int n = qse_awk_findgbl (awk, name);
if (n <= -1) retrieveError (); if (n <= -1) this->retrieveError ();
return n; return n;
} }
@ -1660,12 +1670,12 @@ int Awk::setGlobal (int id, const Value& v)
if (v.run != &runctx) if (v.run != &runctx)
{ {
setError (QSE_AWK_EINVAL); this->setError (QSE_AWK_EINVAL);
return -1; return -1;
} }
int n = runctx.setGlobal (id, v); int n = runctx.setGlobal (id, v);
if (n <= -1) retrieveError (); if (n <= -1) this->retrieveError ();
return n; return n;
} }
@ -1675,7 +1685,7 @@ int Awk::getGlobal (int id, Value& v)
QSE_ASSERT (runctx.rtx != QSE_NULL); QSE_ASSERT (runctx.rtx != QSE_NULL);
int n = runctx.getGlobal (id, v); int n = runctx.getGlobal (id, v);
if (n <= -1) retrieveError (); if (n <= -1) this->retrieveError ();
return n; return n;
} }

View File

@ -138,20 +138,27 @@ void StdAwk::close ()
clearConsoleOutputs (); clearConsoleOutputs ();
// I can't call qse_awk_stdmodshutdown before Awk::close() //
// Fini and Unload functions need to be executed when modules // StdAwk called qse_awk_stdmodstartup() after Awk::open().
// are unloaded. This should be done in StdAwk::uponDemise(). // It's logical to call qse_awk_stdmodshutdown() Awk::close().
// but Awk::close() still needs to call some module's fini and
// unload functions. So it must be done in StdAwk::uponClosing()
// which is called after modules have been unloaded but while
// the underlying awk object is still alive.
//
// See StdAwk::uponClosing() below.
// //
//if (this->stdmod_up) //if (this->stdmod_up)
//{ //{
// qse_awk_stdmodshutdown (this->awk); // qse_awk_stdmodshutdown (this->awk);
// stdmod_up = false; // stdmod_up = false;
//} //}
//
Awk::close (); Awk::close ();
} }
void StdAwk::uponDemise () void StdAwk::uponClosing ()
{ {
if (this->stdmod_up) if (this->stdmod_up)
{ {
@ -159,7 +166,8 @@ void StdAwk::uponDemise ()
stdmod_up = false; stdmod_up = false;
} }
Awk::uponDemise (); // chain up
Awk::uponClosing ();
} }
StdAwk::Run* StdAwk::parse (Source& in, Source& out) StdAwk::Run* StdAwk::parse (Source& in, Source& out)
@ -207,7 +215,7 @@ int StdAwk::build_argcv (Run* run)
this->runarg.ptr[i].ptr, this->runarg.ptr[i].ptr,
this->runarg.ptr[i].len, true) <= -1) return -1; this->runarg.ptr[i].len, true) <= -1) return -1;
} }
run->setGlobal (this->gbl_argc, (int_t)this->runarg.len); run->setGlobal (this->gbl_argc, (int_t)this->runarg.len);
run->setGlobal (this->gbl_argv, argv); run->setGlobal (this->gbl_argv, argv);
return 0; return 0;
@ -251,9 +259,9 @@ int StdAwk::__build_environ (Run* run, void* envptr)
/* mbstowcsdup() may fail for invalid encoding. /* mbstowcsdup() may fail for invalid encoding.
* so setting the error code to ENOMEM may not * so setting the error code to ENOMEM may not
* be really accurate */ * be really accurate */
setError (QSE_AWK_ENOMEM); this->setError (QSE_AWK_ENOMEM);
return -1; return -1;
} }
*eq = QSE_MT('='); *eq = QSE_MT('=');
#else #else
@ -272,9 +280,9 @@ int StdAwk::__build_environ (Run* run, void* envptr)
/* mbstowcsdup() may fail for invalid encoding. /* mbstowcsdup() may fail for invalid encoding.
* so setting the error code to ENOMEM may not * so setting the error code to ENOMEM may not
* be really accurate */ * be really accurate */
setError (QSE_AWK_ENOMEM); this->setError (QSE_AWK_ENOMEM);
return -1; return -1;
} }
*eq = QSE_WT('='); *eq = QSE_WT('=');
#endif #endif
@ -302,7 +310,7 @@ int StdAwk::build_environ (Run* run)
if (qse_env_init (&env, ((Awk*)*run)->getMmgr(), 1) <= -1) if (qse_env_init (&env, ((Awk*)*run)->getMmgr(), 1) <= -1)
{ {
setError (QSE_AWK_ENOMEM); this->setError (QSE_AWK_ENOMEM);
return -1; return -1;
} }
@ -354,7 +362,7 @@ StdAwk::ioattr_t* StdAwk::find_or_make_ioattr (const char_t* ptr, size_t len)
QSE_SIZEOF(StdAwk::default_ioattr)); QSE_SIZEOF(StdAwk::default_ioattr));
if (pair == QSE_NULL) if (pair == QSE_NULL)
{ {
setError (QSE_AWK_ENOMEM); this->setError (QSE_AWK_ENOMEM);
return QSE_NULL; return QSE_NULL;
} }
} }

View File

@ -325,6 +325,7 @@ void qse_awk_clear (qse_awk_t* awk)
clear_token (&awk->ntok); clear_token (&awk->ntok);
clear_token (&awk->ptok); clear_token (&awk->ptok);
/* clear all loaded modules */
qse_rbt_walk (awk->modtab, unload_module, awk); qse_rbt_walk (awk->modtab, unload_module, awk);
qse_rbt_clear (awk->modtab); qse_rbt_clear (awk->modtab);