Re: MPlib: detect bye/end
luigi scarso <[email protected]>
| Newsgroups | gmane.comp.tex.metapost |
|---|---|
| Message-ID | <CAG5iGsApc0fz4bRzcxPq40M39=ydS4yc4uZSnAOdSE-JkEgwPA@mail.gmail.com> |
On Fri, Dec 9, 2016 at 11:50 AM, Nicola <[email protected]> wrote: > Hello, > when running a non-interactive MP instance, how can I detect that the last > executed command was `bye`, `end` or something that causes MetaPost to quit? > > For instance, after > > char *line = "bye." > int history = mp_execute(mp, line, strlen(line)); > > mp_rundata(mp) returns non-zero size data (it returns zero-size data if I > execute another command). > > Nicola > > -- > http://tug.org/metapost/ The effect of scanning an "end" are the following calls: mp_final_cleanup (mp); │ mp_close_files_and_terminate (mp); The last one ends with mp->finished = true; As first step mp_execute resets the streams, and if mp->finished = true then returns @ @c int mp_execute (MP mp, char *s, size_t l) { mp_reset_stream (&(mp->run_data.term_out)); mp_reset_stream (&(mp->run_data.log_out)); mp_reset_stream (&(mp->run_data.error_out)); mp_reset_stream (&(mp->run_data.ship_out)); if (mp->finished) { return mp->history; >From now whatever string is put into execute, the streams data are NULL and nothing is executed. We can execute a test string like "tracingall;tracingnone;": before and "end" this should put something into one stream, and if all the streams data are still NULL then we have already executed an "end" . Of course to execute a string we need a valid mp state . static char *tracingall = "tracingonline:=1; showstopping:=1;" "tracingcommands:=3; tracingtitles:=1; tracingequations:=1;" "tracingcapsules:=1; tracingspecs:=2; tracingchoices:=1; tracinglostchars:=1;" "tracingstats:=1; tracingoutput:=1; tracingmacros:=1; tracingrestores:=1;"; static int strlen_tracingall=240; static char *tracingnone = "tracingcommands:=0; tracingtitles:=0; tracingequations:=0;" "tracingcapsules:=0; tracingspecs:=0; tracingchoices:=0; tracinglostchars:=0;" "tracingstats:=0; tracingoutput:=0; tracingmacros:=0; tracingrestores:=0;"; static int strlen_tracingnone=206; int check_after_end_mp(MP mp) { mp_run_data *cmd_result ; int ret; ret = -1 ; if (mp==NULL) return ret; ret = 0; mp_execute(mp, tracingall, strlen_tracingall); cmd_result = mp_rundata(mp); if ( cmd_result->term_out.data == NULL && cmd_result->error_out.data == NULL && cmd_result->log_out.data == NULL && cmd_result->ship_out.data == NULL ) ret = 1; mp_execute(mp, tracingnone, strlen_tracingnone); return ret ; } MetaPost rev. 2107 has a new function mp_finished that returns mp->finished as boolean, so one can avoid the two calls of mp_execute int check_after_end_mp(MP mp) { mp_run_data *cmd_result ; int ret; ret = -1 ; if (mp==NULL) return ret; ret = 0; cmd_result = mp_rundata(mp); if ( mp_finished(mp) && cmd_result->term_out.data == NULL && cmd_result->error_out.data == NULL && cmd_result->log_out.data == NULL && cmd_result->ship_out.data == NULL ) ret = 1; return ret ; } -- luigi -- http://tug.org/metapost/