Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

[ANNOUNCEMENT] QSEAWK

23 views
Skip to first unread message

Hyung-Hwan Chung

unread,
Dec 14, 2009, 8:02:08 AM12/14/09
to
Dear all,

Let me announce the availability of an open source project containing
an AWK interpreter. http://qse.googlecode.com

QSE is a code library that implements various Unix utilities in an
embeddable
form and provides a set of APIs to embed them into an application. The
APIs
have been designed to be flexible enough to access various aspects of
an
embedding application and an embedded object from each other. By
embedding
a Unix utility into an application, a developer is relieved of
problems
caused by interacting with external programs and can have tighter
control
over it. Currently the library contains the following utilities:

- AWK Interpreter
- CUT Text Cutter
- SED Stream Editor

QSEAWK is an embeddable AWK interpreter and is a part of the QSE
library.
The interpreter implements the language described in the book
The AWK Proramming Language (http://cm.bell-labs.com/cm/cs/awkbook/)
with extensions. Its design focuses on building a flexible and robust
embedding API with minimal platform dependency. An embedding
application
is capable of:
- adding new global variables and functions.
- getting and set the value of a global variable.
- calling a function with or without parameters and getting its return
value.
- customizing I/O handlers for file, pipe, console I/O.
- creating multiple interpreters independent of each other.
- running a single script with different I/O streams independently.
- changing language features by setting options.
- and more

Embedding an interpreter typically involves the following steps:
- open a new interpreter
- parse in a source script
- open a new runtime context
- execute pattern-action blocks or call a function
- close the runtime context
- close the interpter

The code example below demonstrates the steps in C. It executes the
one liner
BEGIN { print "hello, world" }.

------------------------------------------------------------------------------
#include <qse/awk/std.h>
#include <qse/cmn/stdio.h>

#define FAIL(msg) do { qse_printf(QSE_T("ERR: %s\n"),msg); goto
oops; } while(0)

int main ()
{
qse_awk_t* awk = QSE_NULL;
qse_awk_rtx_t* rtx = QSE_NULL;
qse_awk_val_t* retv;
qse_awk_parsestd_in_t psin;
int ret = -1;

awk = qse_awk_openstd (0); /* open a new interpreter */
if (!awk) FAIL ("cannot open awk");

/* parse the hello world script from a string */
psin.type = QSE_AWK_PARSESTD_CP;
psin.u.cp = QSE_T("BEGIN { print \"hello, world\" }");
if (qse_awk_parsestd (awk, &psin, QSE_NULL) <= -1)
FAIL (qse_awk_geterrmsg(awk));

rtx = qse_awk_rtx_openstd ( /* open a runtime context */
awk, 0, /* no extension */
QSE_T("hello"), /* ARGV[0] */
QSE_NULL, /* stdin */
QSE_NULL /* stdout */
);
if (!rtx) FAIL (qse_awk_geterrmsg(awk));

retv = qse_awk_rtx_loop (rtx); /* exeucte pattern-action
blocks */
if (!retv) FAIL (qse_awk_rtx_geterrmsg(rtx));

qse_awk_rtx_refdownval (rtx, retv); /* destroy the return
value */
ret = 0;

oops:
if (rtx) qse_awk_rtx_close (rtx); /* close the runtime context
*/
if (awk) qse_awk_close (awk); /* close the interpreter */
return ret;
}
------------------------------------------------------------------------------

Things can get simpler when you use C++ API. Note that the C++ API
supports just a single
runtime context for each interpreter.

------------------------------------------------------------------------------
#include <qse/awk/StdAwk.hpp>
#include <iostream>

#ifdef QSE_CHAR_IS_MCHAR
# define xcout std::cout
#else
# define xcout std::wcout
#endif

struct MyAwk: public QSE::StdAwk { ~MyAwk () { QSE::StdAwk::close
(); } };

#define FAIL(awk) do { \
xcout << QSE_T("ERR: ") << awk.getErrorMessage() << std::endl;
\
return -1; \
} while (0)

int main (int argc, char* argv[])
{
MyAwk awk;

// open a new interpreter
if (awk.open () <= -1) FAIL (awk);

// set ARGV[0]
if (awk.addArgument (QSE_T("hello")) <= -1) FAIL (awk);

// parse the source script string
MyAwk::SourceString in(QSE_T("BEGIN { print \"hello, world
\" }"));
if (awk.parse (in, MyAwk::Source::NONE) == QSE_NULL) FAIL
(awk);

// execute the BEGIN, pattern-action, END blocks.
MyAwk::Value r;
if (awk.loop (&r) <= -1) FAIL (awk);

return 0;
}
------------------------------------------------------------------------------

See more samples and the standalone interpreter included in the source
tree.

PROJECT URL:
http://qse.googlecode.com/

LICENSE:
GNU Lesser General Public License version 3

AUTHOR:
Chung, Hyung-Hwan <hyunghw...@gmail.com>

I welcome any feedback, bug reports, or comments. Your help is always
appreciated.

Regards,
Chung, Hyung-Hwan.

0 new messages