diff --git a/qse/doc/page/awk-embed.md b/qse/doc/page/awk-embed.md index a2230296..9f6fddc3 100644 --- a/qse/doc/page/awk-embed.md +++ b/qse/doc/page/awk-embed.md @@ -129,17 +129,36 @@ returned with qse_awk_rtx_getfirstmapvalitr() and qse_awk_rtx_getnextmapvalitr() \includelineno awk07.c -Global Variables ----------------- +Built-in Global Variables +-------------------------- -You can add built-in global variables with qse_awk_addgbl(). -Use qse_awk_getgbl() to get information. +QSEAWK predefines global variables such as *SUBSEP* and *ARGC*. You can add +your own built-in variables in the global scope with qse_awk_addgbl(). You +must add new variables before qse_awk_parse() or qse_awk_parsestd(). Later, +you can get the values of the global variables using qse_awk_rtx_getgbl() +with an ID returned by qse_awk_addgbl(). The IDs of the predefined global +variables are available as the ::qse_awk_gbl_id_t type values + + \includelineno awk08.c Built-in Functions ------------------ -You can add built-in functions with qse_awk_addfnc(). -On the other hand, modular built-in functions reside in a shared object. +QSEAWK predefines built-in functions like *match*. You can add your own +built-in function with qse_awk_addfnc(). The following sample shows how to add +a function named *basename* that get the base file name part of a path name. + + \includelineno awk09.c + +In the sample above, the *basename* function returns a resulting string. In +case of any implemenation errors, it would cause the runtime context to abort +with an error since it returned -1. To avoid the situation, you may change +the way basename() works by defining it to return the resulting string via +the second parameter and return 0 or -1 as a return value. For the arguements +to pass by reference, you can specify the letter *r* into the *arg.spec* field +at the argument position. + + \includelineno awk10.c Single Script over Multiple Data Streams ---------------------------------------- @@ -153,9 +172,10 @@ Creating multiple awk objects Memory Pool ----------- -Locale ------- +Writing Modules +--------------- +modular built-in functions and variables reside in a shared object. Embedding in C++ ----------------- @@ -215,10 +235,6 @@ In 0.6.X, it accepts an array of scripts. psin[1].type = QSE_AWK_PARSESTD_STR; qse_awk_parsestd (awk, psin, QSE_NULL) -### qse_awk_parsestd_t ### - -the cmgr field moved from the union member file to the outer structure. - ### 0 upon Opening ### I/O handlers can return 0 for success upon opening. @@ -237,6 +253,9 @@ I/O handlers can return 0 for success upon opening. \example awk05.c \example awk06.c \example awk07.c +\example awk08.c +\example awk09.c +\example awk10.c \example awk21.cpp \example awk22.cpp \example awk23.cpp diff --git a/qse/doc/page/sed-embed.md b/qse/doc/page/sed-embed.md index 5f71a474..31ea5e78 100644 --- a/qse/doc/page/sed-embed.md +++ b/qse/doc/page/sed-embed.md @@ -83,6 +83,11 @@ how to embed QSE::StdSed for stream editing. \includelineno sed21.cpp +The following sample shows how to inherit QSE::StdSed and and create a +customized stream editor. + + \includelineno sed22.cpp + @@ -93,3 +98,4 @@ how to embed QSE::StdSed for stream editing. \example sed02.c \example sed03.c \example sed21.cpp +\example sed22.cpp diff --git a/qse/include/qse/sed/Sed.hpp b/qse/include/qse/sed/Sed.hpp index 74a417d2..625164e4 100644 --- a/qse/include/qse/sed/Sed.hpp +++ b/qse/include/qse/sed/Sed.hpp @@ -24,11 +24,13 @@ #include #include -/** @file - * This file defines C++ classes that you can use when you create a stream - * editor. The C++ classes encapsulates the C data types and functions in - * a more object-oriented manner. - */ +/// \file +/// This file defines C++ classes that you can use when you create a stream +/// editor. The C++ classes encapsulates the C data types and functions in +/// a more object-oriented manner. +/// +/// \todo support sed tracer +/// ///////////////////////////////// QSE_BEGIN_NAMESPACE(QSE) @@ -97,7 +99,7 @@ public: void setHandle (void* handle) { this->arg->handle = handle; } /// The getName() function returns an I/O name. - /// @return #QSE_NULL for the main data stream, + /// \return #QSE_NULL for the main data stream, /// file path for explicit file stream const char_t* getName () const { return this->arg->path; } @@ -122,7 +124,7 @@ public: /// The open() function should be implemented by a subclass /// to open a stream. It can get the mode requested by calling - /// the Data::getMode() function over the I/O parameter @a io. + /// the Data::getMode() function over the I/O parameter \a io. /// /// The return value of 0 may look a bit tricky. Easygoers /// can just return 1 on success and never return 0 from open(). @@ -134,7 +136,7 @@ public: /// failure after having called close() as it cannot write /// further on EOF. /// - /// @return -1 on failure, 1 on success, + /// \return -1 on failure, 1 on success, /// 0 on success but reached EOF. virtual int open (Data& io) = 0; @@ -157,7 +159,7 @@ public: /// /// The ~Sed() function destroys a stream editor. - /// @note The close() function is not called by this destructor. + /// \note The close() function is not called by this destructor. /// To avoid resource leaks, You should call close() before /// a stream editor is destroyed if it has been initialized /// with open(). @@ -167,7 +169,7 @@ public: /// /// The open() function initializes a stream editor and makes it /// ready for subsequent use. - /// @return 0 on success, -1 on failure. + /// \return 0 on success, -1 on failure. /// int open (); @@ -178,15 +180,15 @@ public: /// /// The compile() function compiles a script from a stream - /// @a iostream. - /// @return 0 on success, -1 on failure + /// \a iostream. + /// \return 0 on success, -1 on failure /// int compile (Stream& sstream); /// /// The execute() function executes compiled commands over the I/O /// streams defined through I/O handlers - /// @return 0 on success, -1 on failure + /// \return 0 on success, -1 on failure /// int execute (Stream& iostream); @@ -205,36 +207,18 @@ public: /// /// The getTrait() function gets the current traits. - /// @return 0 or current options ORed of #trait_t enumerators. + /// \return 0 or current options ORed of #trait_t enumerators. /// int getTrait () const; /// /// The setTrait() function sets traits for a stream editor. - /// The option code @a opt is 0 or OR'ed of #trait_t enumerators. + /// The option code \a opt is 0 or OR'ed of #trait_t enumerators. /// void setTrait ( int trait ///< option code ); -#if 0 - /// - /// The getMaxDepth() function gets the maximum processing depth for - /// an operation type identified by @a id. - /// - size_t getMaxDepth ( - depth_t id ///< operation type - ) const; - - /// - /// The setMaxDepth() function gets the maximum processing depth. - /// - void setMaxDepth ( - int ids, ///< 0 or a number OR'ed of depth_t values - size_t depth ///< 0 maximum depth - ); -#endif - /// /// The getErrorMessage() function gets the description of the last /// error occurred. It returns an empty string if the stream editor @@ -276,7 +260,7 @@ public: /// /// The getConsoleLine() function returns the current line /// number from an input console. - /// @return current line number + /// \return current line number /// size_t getConsoleLine (); @@ -291,7 +275,7 @@ public: protected: /// /// The getErrorString() function returns an error formatting string - /// for the error number @a num. A subclass wishing to customize + /// for the error number \a num. A subclass wishing to customize /// an error formatting string may override this function. /// virtual const char_t* getErrorString ( diff --git a/qse/include/qse/sed/StdSed.hpp b/qse/include/qse/sed/StdSed.hpp index 38e8a147..4c10dfc7 100644 --- a/qse/include/qse/sed/StdSed.hpp +++ b/qse/include/qse/sed/StdSed.hpp @@ -25,10 +25,11 @@ #include #include -/** @file - * This file defines easier-to-use stream editor classes providing standard - * memory management and I/O handling. - */ +/// +/// @file +/// This file defines easier-to-use stream editor classes providing standard +/// memory management and I/O handling. +/// ///////////////////////////////// QSE_BEGIN_NAMESPACE(QSE) diff --git a/qse/lib/sed/Sed.cpp b/qse/lib/sed/Sed.cpp index e0f5b871..ded8c17b 100644 --- a/qse/lib/sed/Sed.cpp +++ b/qse/lib/sed/Sed.cpp @@ -90,21 +90,6 @@ void Sed::setTrait (int trait) qse_sed_setopt (sed, QSE_SED_TRAIT, &trait); } - -#if 0 -Sed::size_t Sed::getMaxDepth (depth_t id) const -{ - QSE_ASSERT (sed != QSE_NULL); - return qse_sed_getmaxdepth (sed, id); -} - -void Sed::setMaxDepth (int ids, size_t depth) -{ - QSE_ASSERT (sed != QSE_NULL); - qse_sed_setmaxdepth (sed, ids, depth); -} -#endif - const Sed::char_t* Sed::getErrorMessage () const { return (sed == QSE_NULL)? QSE_T(""): qse_sed_geterrmsg (sed); diff --git a/qse/samples/awk/Makefile.am b/qse/samples/awk/Makefile.am index 34280392..4badf93b 100644 --- a/qse/samples/awk/Makefile.am +++ b/qse/samples/awk/Makefile.am @@ -5,7 +5,7 @@ AM_CPPFLAGS = \ -I$(top_srcdir)/include \ -I$(includedir) -bin_PROGRAMS = awk01 awk02 awk03 awk04 awk05 awk06 awk07 awk09 awk11 awk15 +bin_PROGRAMS = awk01 awk02 awk03 awk04 awk05 awk06 awk07 awk08 awk09 awk10 awk11 awk12 awk15 LDFLAGS = -L../../lib/awk -L../../lib/cmn LDADD = -lqseawk -lqsecmn $(LIBM) @@ -16,16 +16,20 @@ LDADD += $(UNICOWS_LIBS) endif endif +CMNFILES = awk00.c awk00.h awk01_SOURCES = awk01.c -awk02_SOURCES = awk02.c awk00.c awk00.h -awk03_SOURCES = awk03.c awk00.c awk00.h -awk04_SOURCES = awk04.c awk00.c awk00.h -awk05_SOURCES = awk05.c awk00.c awk00.h -awk06_SOURCES = awk06.c awk00.c awk00.h -awk07_SOURCES = awk07.c awk00.c awk00.h -awk09_SOURCES = awk09.c awk00.c awk00.h -awk11_SOURCES = awk11.c awk00.c awk00.h -awk15_SOURCES = awk15.c awk00.c awk00.h +awk02_SOURCES = awk02.c $(CMNFILES) +awk03_SOURCES = awk03.c $(CMNFILES) +awk04_SOURCES = awk04.c $(CMNFILES) +awk05_SOURCES = awk05.c $(CMNFILES) +awk06_SOURCES = awk06.c $(CMNFILES) +awk07_SOURCES = awk07.c $(CMNFILES) +awk08_SOURCES = awk08.c $(CMNFILES) +awk09_SOURCES = awk09.c $(CMNFILES) +awk10_SOURCES = awk10.c $(CMNFILES) +awk11_SOURCES = awk11.c $(CMNFILES) +awk12_SOURCES = awk12.c $(CMNFILES) +awk15_SOURCES = awk15.c $(CMNFILES) if ENABLE_CXX diff --git a/qse/samples/awk/Makefile.in b/qse/samples/awk/Makefile.in index 0b899b01..97ce4d74 100644 --- a/qse/samples/awk/Makefile.in +++ b/qse/samples/awk/Makefile.in @@ -36,7 +36,8 @@ build_triplet = @build@ host_triplet = @host@ bin_PROGRAMS = awk01$(EXEEXT) awk02$(EXEEXT) awk03$(EXEEXT) \ awk04$(EXEEXT) awk05$(EXEEXT) awk06$(EXEEXT) awk07$(EXEEXT) \ - awk09$(EXEEXT) awk11$(EXEEXT) awk15$(EXEEXT) $(am__EXEEXT_1) + awk08$(EXEEXT) awk09$(EXEEXT) awk10$(EXEEXT) awk11$(EXEEXT) \ + awk12$(EXEEXT) awk15$(EXEEXT) $(am__EXEEXT_1) @WCHAR_TRUE@@WIN32_TRUE@am__append_1 = $(UNICOWS_LIBS) @ENABLE_CXX_TRUE@am__append_2 = awk21 awk22 awk23 awk24 awk25 awk26 awk27 awk28 subdir = samples/awk @@ -65,39 +66,52 @@ awk01_LDADD = $(LDADD) am__DEPENDENCIES_1 = @WCHAR_TRUE@@WIN32_TRUE@am__DEPENDENCIES_2 = $(am__DEPENDENCIES_1) awk01_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) -am_awk02_OBJECTS = awk02.$(OBJEXT) awk00.$(OBJEXT) +am__objects_1 = awk00.$(OBJEXT) +am_awk02_OBJECTS = awk02.$(OBJEXT) $(am__objects_1) awk02_OBJECTS = $(am_awk02_OBJECTS) awk02_LDADD = $(LDADD) awk02_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) -am_awk03_OBJECTS = awk03.$(OBJEXT) awk00.$(OBJEXT) +am_awk03_OBJECTS = awk03.$(OBJEXT) $(am__objects_1) awk03_OBJECTS = $(am_awk03_OBJECTS) awk03_LDADD = $(LDADD) awk03_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) -am_awk04_OBJECTS = awk04.$(OBJEXT) awk00.$(OBJEXT) +am_awk04_OBJECTS = awk04.$(OBJEXT) $(am__objects_1) awk04_OBJECTS = $(am_awk04_OBJECTS) awk04_LDADD = $(LDADD) awk04_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) -am_awk05_OBJECTS = awk05.$(OBJEXT) awk00.$(OBJEXT) +am_awk05_OBJECTS = awk05.$(OBJEXT) $(am__objects_1) awk05_OBJECTS = $(am_awk05_OBJECTS) awk05_LDADD = $(LDADD) awk05_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) -am_awk06_OBJECTS = awk06.$(OBJEXT) awk00.$(OBJEXT) +am_awk06_OBJECTS = awk06.$(OBJEXT) $(am__objects_1) awk06_OBJECTS = $(am_awk06_OBJECTS) awk06_LDADD = $(LDADD) awk06_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) -am_awk07_OBJECTS = awk07.$(OBJEXT) awk00.$(OBJEXT) +am_awk07_OBJECTS = awk07.$(OBJEXT) $(am__objects_1) awk07_OBJECTS = $(am_awk07_OBJECTS) awk07_LDADD = $(LDADD) awk07_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) -am_awk09_OBJECTS = awk09.$(OBJEXT) awk00.$(OBJEXT) +am_awk08_OBJECTS = awk08.$(OBJEXT) $(am__objects_1) +awk08_OBJECTS = $(am_awk08_OBJECTS) +awk08_LDADD = $(LDADD) +awk08_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) +am_awk09_OBJECTS = awk09.$(OBJEXT) $(am__objects_1) awk09_OBJECTS = $(am_awk09_OBJECTS) awk09_LDADD = $(LDADD) awk09_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) -am_awk11_OBJECTS = awk11.$(OBJEXT) awk00.$(OBJEXT) +am_awk10_OBJECTS = awk10.$(OBJEXT) $(am__objects_1) +awk10_OBJECTS = $(am_awk10_OBJECTS) +awk10_LDADD = $(LDADD) +awk10_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) +am_awk11_OBJECTS = awk11.$(OBJEXT) $(am__objects_1) awk11_OBJECTS = $(am_awk11_OBJECTS) awk11_LDADD = $(LDADD) awk11_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) -am_awk15_OBJECTS = awk15.$(OBJEXT) awk00.$(OBJEXT) +am_awk12_OBJECTS = awk12.$(OBJEXT) $(am__objects_1) +awk12_OBJECTS = $(am_awk12_OBJECTS) +awk12_LDADD = $(LDADD) +awk12_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) +am_awk15_OBJECTS = awk15.$(OBJEXT) $(am__objects_1) awk15_OBJECTS = $(am_awk15_OBJECTS) awk15_LDADD = $(LDADD) awk15_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_2) @@ -166,13 +180,15 @@ CXXLINK = $(LIBTOOL) --tag=CXX $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ $(LDFLAGS) -o $@ SOURCES = $(awk01_SOURCES) $(awk02_SOURCES) $(awk03_SOURCES) \ $(awk04_SOURCES) $(awk05_SOURCES) $(awk06_SOURCES) \ - $(awk07_SOURCES) $(awk09_SOURCES) $(awk11_SOURCES) \ + $(awk07_SOURCES) $(awk08_SOURCES) $(awk09_SOURCES) \ + $(awk10_SOURCES) $(awk11_SOURCES) $(awk12_SOURCES) \ $(awk15_SOURCES) $(awk21_SOURCES) $(awk22_SOURCES) \ $(awk23_SOURCES) $(awk24_SOURCES) $(awk25_SOURCES) \ $(awk26_SOURCES) $(awk27_SOURCES) $(awk28_SOURCES) DIST_SOURCES = $(awk01_SOURCES) $(awk02_SOURCES) $(awk03_SOURCES) \ $(awk04_SOURCES) $(awk05_SOURCES) $(awk06_SOURCES) \ - $(awk07_SOURCES) $(awk09_SOURCES) $(awk11_SOURCES) \ + $(awk07_SOURCES) $(awk08_SOURCES) $(awk09_SOURCES) \ + $(awk10_SOURCES) $(awk11_SOURCES) $(awk12_SOURCES) \ $(awk15_SOURCES) $(am__awk21_SOURCES_DIST) \ $(am__awk22_SOURCES_DIST) $(am__awk23_SOURCES_DIST) \ $(am__awk24_SOURCES_DIST) $(am__awk25_SOURCES_DIST) \ @@ -361,16 +377,20 @@ AM_CPPFLAGS = \ -I$(includedir) LDADD = -lqseawk -lqsecmn $(LIBM) $(am__append_1) +CMNFILES = awk00.c awk00.h awk01_SOURCES = awk01.c -awk02_SOURCES = awk02.c awk00.c awk00.h -awk03_SOURCES = awk03.c awk00.c awk00.h -awk04_SOURCES = awk04.c awk00.c awk00.h -awk05_SOURCES = awk05.c awk00.c awk00.h -awk06_SOURCES = awk06.c awk00.c awk00.h -awk07_SOURCES = awk07.c awk00.c awk00.h -awk09_SOURCES = awk09.c awk00.c awk00.h -awk11_SOURCES = awk11.c awk00.c awk00.h -awk15_SOURCES = awk15.c awk00.c awk00.h +awk02_SOURCES = awk02.c $(CMNFILES) +awk03_SOURCES = awk03.c $(CMNFILES) +awk04_SOURCES = awk04.c $(CMNFILES) +awk05_SOURCES = awk05.c $(CMNFILES) +awk06_SOURCES = awk06.c $(CMNFILES) +awk07_SOURCES = awk07.c $(CMNFILES) +awk08_SOURCES = awk08.c $(CMNFILES) +awk09_SOURCES = awk09.c $(CMNFILES) +awk10_SOURCES = awk10.c $(CMNFILES) +awk11_SOURCES = awk11.c $(CMNFILES) +awk12_SOURCES = awk12.c $(CMNFILES) +awk15_SOURCES = awk15.c $(CMNFILES) @ENABLE_CXX_TRUE@CXXLIB = -lqseawkxx -lqsecmnxx @ENABLE_CXX_TRUE@awk21_SOURCES = awk21.cpp @ENABLE_CXX_TRUE@awk22_SOURCES = awk22.cpp @@ -486,12 +506,21 @@ awk06$(EXEEXT): $(awk06_OBJECTS) $(awk06_DEPENDENCIES) $(EXTRA_awk06_DEPENDENCIE awk07$(EXEEXT): $(awk07_OBJECTS) $(awk07_DEPENDENCIES) $(EXTRA_awk07_DEPENDENCIES) @rm -f awk07$(EXEEXT) $(LINK) $(awk07_OBJECTS) $(awk07_LDADD) $(LIBS) +awk08$(EXEEXT): $(awk08_OBJECTS) $(awk08_DEPENDENCIES) $(EXTRA_awk08_DEPENDENCIES) + @rm -f awk08$(EXEEXT) + $(LINK) $(awk08_OBJECTS) $(awk08_LDADD) $(LIBS) awk09$(EXEEXT): $(awk09_OBJECTS) $(awk09_DEPENDENCIES) $(EXTRA_awk09_DEPENDENCIES) @rm -f awk09$(EXEEXT) $(LINK) $(awk09_OBJECTS) $(awk09_LDADD) $(LIBS) +awk10$(EXEEXT): $(awk10_OBJECTS) $(awk10_DEPENDENCIES) $(EXTRA_awk10_DEPENDENCIES) + @rm -f awk10$(EXEEXT) + $(LINK) $(awk10_OBJECTS) $(awk10_LDADD) $(LIBS) awk11$(EXEEXT): $(awk11_OBJECTS) $(awk11_DEPENDENCIES) $(EXTRA_awk11_DEPENDENCIES) @rm -f awk11$(EXEEXT) $(LINK) $(awk11_OBJECTS) $(awk11_LDADD) $(LIBS) +awk12$(EXEEXT): $(awk12_OBJECTS) $(awk12_DEPENDENCIES) $(EXTRA_awk12_DEPENDENCIES) + @rm -f awk12$(EXEEXT) + $(LINK) $(awk12_OBJECTS) $(awk12_LDADD) $(LIBS) awk15$(EXEEXT): $(awk15_OBJECTS) $(awk15_DEPENDENCIES) $(EXTRA_awk15_DEPENDENCIES) @rm -f awk15$(EXEEXT) $(LINK) $(awk15_OBJECTS) $(awk15_LDADD) $(LIBS) @@ -534,8 +563,11 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/awk05.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/awk06.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/awk07.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/awk08.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/awk09.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/awk10.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/awk11.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/awk12.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/awk15.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/awk21.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/awk22.Po@am__quote@ diff --git a/qse/samples/awk/awk02.c b/qse/samples/awk/awk02.c index 20d69327..710bd266 100644 --- a/qse/samples/awk/awk02.c +++ b/qse/samples/awk/awk02.c @@ -101,8 +101,7 @@ static int awk_main (int argc, qse_char_t* argv[]) /* parse a script in a string */ if (qse_awk_parsestd (awk, psin, QSE_NULL) <= -1) { - qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), - qse_awk_geterrmsg(awk)); + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); goto oops; } diff --git a/qse/samples/awk/awk03.c b/qse/samples/awk/awk03.c index d7785faf..499a6f50 100644 --- a/qse/samples/awk/awk03.c +++ b/qse/samples/awk/awk03.c @@ -109,8 +109,7 @@ static int awk_main (int argc, qse_char_t* argv[]) /* parse a script in a string */ if (qse_awk_parsestd (awk, psin, QSE_NULL) <= -1) { - qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), - qse_awk_geterrmsg(awk)); + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); goto oops; } @@ -125,8 +124,7 @@ static int awk_main (int argc, qse_char_t* argv[]) ); if (rtx == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), - qse_awk_geterrmsg(awk)); + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); goto oops; } @@ -148,19 +146,19 @@ static int awk_main (int argc, qse_char_t* argv[]) retv = qse_awk_rtx_loop (rtx); if (retv == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); goto oops; } /* decrement the reference count of the return value */ qse_awk_rtx_refdownval (rtx, retv); - ret = 0; -oops: /* the buffer is available during the runtime context is alive */ qse_printf (QSE_T("Console Output:\n================\n%.*s\n"), (int)con->conoutpos, con->conout); + ret = 0; + +oops: /* destroy the runtime context */ if (rtx) qse_awk_rtx_close (rtx); diff --git a/qse/samples/awk/awk04.c b/qse/samples/awk/awk04.c index faefa397..7eee7602 100644 --- a/qse/samples/awk/awk04.c +++ b/qse/samples/awk/awk04.c @@ -24,14 +24,14 @@ static int awk_main (int argc, qse_char_t* argv[]) qse_awk_t* awk = QSE_NULL; qse_awk_rtx_t* rtx = QSE_NULL; qse_awk_parsestd_t psin[2]; - int ret, i, opt; + int ret = -1, i, opt; /* create an awk object */ awk = qse_awk_openstd (0); if (awk == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: cannot open awk\n")); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: cannot open awk\n")); + goto oops; } /* get the awk's trait */ @@ -48,10 +48,9 @@ static int awk_main (int argc, qse_char_t* argv[]) psin[1].type = QSE_AWK_PARSESTD_NULL; /* parse a script */ - ret = qse_awk_parsestd (awk, psin, QSE_NULL); - if (ret == -1) + if (qse_awk_parsestd (awk, psin, QSE_NULL) <= -1) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); goto oops; } @@ -67,9 +66,8 @@ static int awk_main (int argc, qse_char_t* argv[]) ); if (rtx == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_geterrmsg(awk)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); + goto oops; } /* call init() initially, followed by 4 calls to main(), @@ -84,9 +82,8 @@ static int awk_main (int argc, qse_char_t* argv[]) v = qse_awk_rtx_call (rtx, fnc[i], QSE_NULL, 0); if (v == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } /* convert the return value to a string with duplication */ @@ -97,9 +94,8 @@ static int awk_main (int argc, qse_char_t* argv[]) if (str == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } /* print the return value */ @@ -109,9 +105,12 @@ static int awk_main (int argc, qse_char_t* argv[]) qse_awk_rtx_freemem (rtx, str); } + ret = 0; + oops: /* destroy a runtime context */ if (rtx) qse_awk_rtx_close (rtx); + /* destroy the awk object */ if (awk) qse_awk_close (awk); diff --git a/qse/samples/awk/awk05.c b/qse/samples/awk/awk05.c index 3dc661b9..903cb9ff 100644 --- a/qse/samples/awk/awk05.c +++ b/qse/samples/awk/awk05.c @@ -14,16 +14,16 @@ static int awk_main (int argc, qse_char_t* argv[]) qse_awk_parsestd_t psin[2]; qse_char_t* str; qse_size_t len; - qse_awk_val_t* rtv = QSE_NULL; + qse_awk_val_t* rtv; qse_awk_val_t* arg[2] = { QSE_NULL, QSE_NULL }; - int ret, i, opt; + int ret = -1, i, opt; /* create an awk object */ awk = qse_awk_openstd (0); if (awk == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: cannot open awk\n")); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: cannot open awk\n")); + goto oops; } /* get the awk's trait */ @@ -40,11 +40,9 @@ static int awk_main (int argc, qse_char_t* argv[]) psin[1].type = QSE_AWK_PARSESTD_NULL; /* parse the script */ - ret = qse_awk_parsestd (awk, psin, QSE_NULL); - if (ret == -1) + if (qse_awk_parsestd (awk, psin, QSE_NULL) <= -1) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_geterrmsg(awk)); + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); goto oops; } @@ -59,18 +57,16 @@ static int awk_main (int argc, qse_char_t* argv[]) ); if (rtx == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_geterrmsg(awk)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); + goto oops; } /* create the first argument to the pow function to call */ arg[0] = qse_awk_rtx_makeintval (rtx, 50); if (arg[0] == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } qse_awk_rtx_refupval (rtx, arg[0]); @@ -78,9 +74,8 @@ static int awk_main (int argc, qse_char_t* argv[]) arg[1] = qse_awk_rtx_makeintval (rtx, 3); if (arg[1] == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } qse_awk_rtx_refupval (rtx, arg[1]); @@ -88,9 +83,8 @@ static int awk_main (int argc, qse_char_t* argv[]) rtv = qse_awk_rtx_call (rtx, QSE_T("pow"), arg, 2); if (rtv == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } /* duplicate the return value to a string */ @@ -101,9 +95,8 @@ static int awk_main (int argc, qse_char_t* argv[]) if (str == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } qse_printf (QSE_T("[%.*s]\n"), (int)len, str); @@ -111,6 +104,8 @@ static int awk_main (int argc, qse_char_t* argv[]) /* destroy the duplicated string */ qse_awk_rtx_freemem (rtx, str); + ret = 0; + oops: /* dereference all arguments */ for (i = 0; i < QSE_COUNTOF(arg); i++) @@ -120,6 +115,7 @@ oops: /* destroy a runtime context */ if (rtx) qse_awk_rtx_close (rtx); + /* destroy the processor */ if (awk) qse_awk_close (awk); diff --git a/qse/samples/awk/awk06.c b/qse/samples/awk/awk06.c index f9eb8bbb..db9d643e 100644 --- a/qse/samples/awk/awk06.c +++ b/qse/samples/awk/awk06.c @@ -14,17 +14,17 @@ static int awk_main (int argc, qse_char_t* argv[]) qse_awk_parsestd_t psin[2]; qse_char_t* str; qse_size_t len; - qse_awk_val_t* rtv = QSE_NULL; + qse_awk_val_t* rtv; qse_awk_val_t* arg[2] = { QSE_NULL, QSE_NULL }; - int ret, i, opt; + int ret = -1, i, opt; qse_awk_fun_t* fun; /* create an awk object */ awk = qse_awk_openstd (0); if (awk == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: cannot open awk\n")); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: cannot open awk\n")); + goto oops; } /* get the awk's trait */ @@ -41,11 +41,9 @@ static int awk_main (int argc, qse_char_t* argv[]) psin[1].type = QSE_AWK_PARSESTD_NULL; /* parse the script */ - ret = qse_awk_parsestd (awk, psin, QSE_NULL); - if (ret == -1) + if (qse_awk_parsestd (awk, psin, QSE_NULL) <= -1) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_geterrmsg(awk)); + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); goto oops; } @@ -60,18 +58,16 @@ static int awk_main (int argc, qse_char_t* argv[]) ); if (rtx == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_geterrmsg(awk)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); + goto oops; } /* create the first argument to the pow function to call */ arg[0] = qse_awk_rtx_makeintval (rtx, 50); if (arg[0] == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } qse_awk_rtx_refupval (rtx, arg[0]); @@ -79,9 +75,8 @@ static int awk_main (int argc, qse_char_t* argv[]) arg[1] = qse_awk_rtx_makeintval (rtx, 3); if (arg[1] == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } qse_awk_rtx_refupval (rtx, arg[1]); @@ -89,18 +84,16 @@ static int awk_main (int argc, qse_char_t* argv[]) fun = qse_awk_rtx_findfun (rtx, QSE_T("pow")); if (fun == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } /* call the function found */ rtv = qse_awk_rtx_callfun (rtx, fun, arg, 2); if (rtv == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } /* duplicate the return value to a string */ @@ -111,9 +104,8 @@ static int awk_main (int argc, qse_char_t* argv[]) if (str == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } qse_printf (QSE_T("[%.*s]\n"), (int)len, str); @@ -121,6 +113,8 @@ static int awk_main (int argc, qse_char_t* argv[]) /* destroy the duplicated string */ qse_awk_rtx_freemem (rtx, str); + ret = 0; + oops: /* dereference all arguments */ for (i = 0; i < QSE_COUNTOF(arg); i++) @@ -130,6 +124,7 @@ oops: /* destroy a runtime context */ if (rtx) qse_awk_rtx_close (rtx); + /* destroy the processor */ if (awk) qse_awk_close (awk); diff --git a/qse/samples/awk/awk07.c b/qse/samples/awk/awk07.c index 15b432af..9ecb5d95 100644 --- a/qse/samples/awk/awk07.c +++ b/qse/samples/awk/awk07.c @@ -14,7 +14,7 @@ static int awk_main (int argc, qse_char_t* argv[]) qse_awk_parsestd_t psin[2]; qse_awk_val_t* rtv = QSE_NULL; qse_awk_val_t* arg = QSE_NULL; - int ret, opt; + int ret = -1, opt; /* this structure is passed to qse_awk_rtx_makemapvalwithdata() */ qse_awk_val_map_data_t md[] = @@ -29,8 +29,8 @@ static int awk_main (int argc, qse_char_t* argv[]) awk = qse_awk_openstd (0); if (awk == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: cannot open awk\n")); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: cannot open awk\n")); + goto oops; } /* get the awk's trait */ @@ -47,11 +47,9 @@ static int awk_main (int argc, qse_char_t* argv[]) psin[1].type = QSE_AWK_PARSESTD_NULL; /* parse the script */ - ret = qse_awk_parsestd (awk, psin, QSE_NULL); - if (ret == -1) + if (qse_awk_parsestd (awk, psin, QSE_NULL) <= -1) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_geterrmsg(awk)); + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); goto oops; } @@ -67,18 +65,16 @@ static int awk_main (int argc, qse_char_t* argv[]) ); if (rtx == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_geterrmsg(awk)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); + goto oops; } /* create a map value to pass as an argument */ arg = qse_awk_rtx_makemapvalwithdata (rtx, md); if (arg == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } qse_awk_rtx_refupval (rtx, arg); @@ -86,9 +82,8 @@ static int awk_main (int argc, qse_char_t* argv[]) rtv = qse_awk_rtx_call (rtx, QSE_T("dump"), &arg, 1); if (rtv == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } if (rtv->type == QSE_AWK_VAL_MAP) @@ -110,9 +105,8 @@ static int awk_main (int argc, qse_char_t* argv[]) rtx, QSE_AWK_VAL_MAP_ITR_VAL(iptr), &str.len); if (str.ptr == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } /* #QSE_AWK_VAL_MAP_ITR_KEY returns the key part */ @@ -136,15 +130,16 @@ static int awk_main (int argc, qse_char_t* argv[]) str.ptr = qse_awk_rtx_valtostrdup (rtx, rtv, &str.len); if (str.ptr == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); - ret = -1; goto oops; + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; } qse_printf (QSE_T("ret [%.*s]\n"), (int)str.len, str.ptr); qse_awk_rtx_freemem (rtx, str.ptr); } + ret = 0; + oops: /* clear the return value */ if (rtv) qse_awk_rtx_refdownval (rtx, rtv); diff --git a/qse/samples/awk/awk08.c b/qse/samples/awk/awk08.c new file mode 100644 index 00000000..36eebae3 --- /dev/null +++ b/qse/samples/awk/awk08.c @@ -0,0 +1,132 @@ +#include +#include +#include +#include "awk00.h" + +static const qse_char_t* src = QSE_T( + "BEGIN { G0 = 10; G1 = \"hello, world\"; G2 = sin(90); match (\"abcdefg\", /[c-f]+/); }" +); + +struct ginfo_t +{ + int g[3]; +}; + +typedef struct ginfo_t ginfo_t; + +static int awk_main (int argc, qse_char_t* argv[]) +{ + qse_awk_t* awk = QSE_NULL; + qse_awk_rtx_t* rtx = QSE_NULL; + qse_awk_parsestd_t psin[2]; + qse_char_t* str; + qse_size_t len; + qse_awk_val_t* rtv; + int ret = -1, i; + ginfo_t* ginfo; + + /* create an awk object */ + awk = qse_awk_openstd (QSE_SIZEOF(*ginfo)); + if (awk == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: cannot open awk\n")); + goto oops; + } + + /* add global variables G1, G2, and G3. store the IDs to the extension + * area. the extension area is used for demonstration. there is no special + * need to use it when adding global variables. */ + ginfo = qse_awk_getxtnstd (awk); + for (i = 0; i < QSE_COUNTOF(ginfo->g); i++) + { + qse_char_t name[] = QSE_T("GX"); + name[1] = QSE_T('0') + i; + ginfo->g[i] = qse_awk_addgbl (awk, name); + if (ginfo->g[i] <= -1) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); + goto oops; + } + } + + /* prepare an awk script to parse */ + psin[0].type = QSE_AWK_PARSESTD_STR; + psin[0].u.str.ptr = src; + psin[0].u.str.len = qse_strlen(src); + psin[1].type = QSE_AWK_PARSESTD_NULL; + + /* parse the script */ + if (qse_awk_parsestd (awk, psin, QSE_NULL) <= -1) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); + goto oops; + } + + /* create a runtime context */ + rtx = qse_awk_rtx_openstd ( + awk, + 0, + QSE_T("awk08"), + QSE_NULL, /* stdin */ + QSE_NULL, /* stdout */ + QSE_NULL /* default cmgr */ + ); + if (rtx == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); + goto oops; + } + + /* execute the script over the standard data streams */ + rtv = qse_awk_rtx_loop (rtx); + if (rtv == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; + } + + /* clear the return value */ + qse_awk_rtx_refdownval (rtx, rtv); + + /* get the values of built-in global variables + * and print them */ + for (i = 0; i < QSE_COUNTOF(ginfo->g); i++) + { + str = qse_awk_rtx_valtostrdup (rtx, qse_awk_rtx_getgbl (rtx, ginfo->g[i]), &len); + if (str == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; + } + qse_printf (QSE_T("G%d => %.*s\n"), i, (int)len, str); + qse_awk_rtx_freemem (rtx, str); + } + + /* get the value of RLENGTH and print it */ + str = qse_awk_rtx_valtostrdup (rtx, qse_awk_rtx_getgbl (rtx, QSE_AWK_GBL_RLENGTH), &len); + if (str == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; + } + qse_printf (QSE_T("RLENGTH => %.*s\n"), (int)len, str); + qse_awk_rtx_freemem (rtx, str); + + ret = 0; + +oops: + /* destroy a runtime context */ + if (rtx) qse_awk_rtx_close (rtx); + + /* destroy the processor */ + if (awk) qse_awk_close (awk); + + return ret; +} + +int qse_main (int argc, qse_achar_t* argv[]) +{ + init_awk_sample_locale (); + return qse_runmain (argc, argv, awk_main); +} + diff --git a/qse/samples/awk/awk09.c b/qse/samples/awk/awk09.c index f9645ad7..da301bbd 100644 --- a/qse/samples/awk/awk09.c +++ b/qse/samples/awk/awk09.c @@ -1,61 +1,67 @@ -/* - * $Id$ - * - Copyright 2006-2012 Chung, Hyung-Hwan. - This file is part of QSE. - - QSE is free software: you can redistribute it and/or modify - it under the terms of the GNU Lesser General Public License as - published by the Free Software Foundation, either version 3 of - the License, or (at your option) any later version. - - QSE is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with QSE. If not, see . - */ - #include +#include +#include +#include #include +#include "awk00.h" -/* this sample produces 8 text files containing multiplication chart. */ - -const qse_char_t* src = QSE_T( - "BEGIN {" - " for (i=2;i<=9;i++)" - " {" - " print \"OFILENAME:\" OFILENAME;" - " for (j=1;j<=9;j++)" - " print i \"*\" j \"=\" i * j;" - " nextofile;" - " }" - "}" +static const qse_char_t* src = QSE_T( + "BEGIN { print basename(\"/etc/passwd\"); }" ); -int main () +static int fnc_basename (qse_awk_rtx_t* rtx, const qse_awk_fnc_info_t* fi) +{ + qse_awk_val_t* a0, * rv; + qse_char_t* ptr; + qse_size_t len; + + /* note that this implementation doesn't care if the parameter + * contains a null character like "/etc/p\0asswd" */ + + /* get the value of the first parameter */ + a0 = qse_awk_rtx_getarg (rtx, 0); + if (a0->type == QSE_AWK_VAL_STR) + { + /* if it is a string value, don't duplicate the value */ + ptr = ((qse_awk_val_str_t*)a0)->val.ptr; + len = ((qse_awk_val_str_t*)a0)->val.len; + + /* make a string value with the base name */ + rv = qse_awk_rtx_makestrvalwithstr (rtx, qse_basename (ptr)); + } + else + { + /* if it is a string value, convert the value to a string + * with duplication */ + ptr = qse_awk_rtx_valtostrdup (rtx, a0, &len); + if (ptr == QSE_NULL) return -1; + + /* make a string value with the base name */ + rv = qse_awk_rtx_makestrvalwithstr (rtx, qse_basename (ptr)); + + /* free the duplicated string */ + qse_awk_rtx_freemem (rtx, ptr); + } + + if (rv == QSE_NULL) return -1; + + /* set the return value that basename() will return */ + qse_awk_rtx_setretval (rtx, rv); + + /* implemenation success */ + return 0; +} + +static int awk_main (int argc, qse_char_t* argv[]) { qse_awk_t* awk = QSE_NULL; qse_awk_rtx_t* rtx = QSE_NULL; - qse_awk_val_t* retv; qse_awk_parsestd_t psin[2]; - int ret = -1, opt; - - const qse_char_t* output_files[] = - { - QSE_T("awk09.out.2"), - QSE_T("awk09.out.3"), - QSE_T("awk09.out.4"), - QSE_T("awk09.out.5"), - QSE_T("awk09.out.6"), - QSE_T("awk09.out.7"), - QSE_T("awk09.out.8"), - QSE_T("awk09.out.9"), - QSE_NULL - }; + qse_awk_val_t* rtv; + int ret = -1; + qse_awk_fnc_spec_t spec; + /* create an awk object */ awk = qse_awk_openstd (0); if (awk == QSE_NULL) { @@ -63,51 +69,71 @@ int main () goto oops; } - qse_awk_getopt (awk, QSE_AWK_TRAIT, &opt); - opt |= QSE_AWK_EXTRAKWS; - qse_awk_setopt (awk, QSE_AWK_TRAIT, &opt); + /* add a built-in function basename() */ + qse_memset (&spec, 0, QSE_SIZEOF(spec)); + spec.arg.min = 1; /* limit the number of arguments to 1 */ + spec.arg.max = 1; + spec.impl = fnc_basename; /* specify the actual implementation */ + if (qse_awk_addfnc (awk, QSE_T("basename"), &spec) == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); + goto oops; + } + /* prepare an awk script to parse */ psin[0].type = QSE_AWK_PARSESTD_STR; psin[0].u.str.ptr = src; psin[0].u.str.len = qse_strlen(src); psin[1].type = QSE_AWK_PARSESTD_NULL; + /* parse the script */ if (qse_awk_parsestd (awk, psin, QSE_NULL) <= -1) { - qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), - qse_awk_geterrmsg(awk)); + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); goto oops; } + /* create a runtime context */ rtx = qse_awk_rtx_openstd ( awk, 0, - QSE_T("awk09"), + QSE_T("awk09"), QSE_NULL, /* stdin */ - output_files, + QSE_NULL, /* stdout */ QSE_NULL /* default cmgr */ ); if (rtx == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), - qse_awk_geterrmsg(awk)); + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); goto oops; } - retv = qse_awk_rtx_loop (rtx); - if (retv == QSE_NULL) + /* execute the script over the standard data streams */ + rtv = qse_awk_rtx_loop (rtx); + if (rtv == QSE_NULL) { - qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), - qse_awk_rtx_geterrmsg(rtx)); + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); goto oops; } - qse_awk_rtx_refdownval (rtx, retv); + /* clear the return value */ + qse_awk_rtx_refdownval (rtx, rtv); + ret = 0; oops: - if (rtx != QSE_NULL) qse_awk_rtx_close (rtx); - if (awk != QSE_NULL) qse_awk_close (awk); + /* destroy a runtime context */ + if (rtx) qse_awk_rtx_close (rtx); + + /* destroy the processor */ + if (awk) qse_awk_close (awk); + return ret; } +int qse_main (int argc, qse_achar_t* argv[]) +{ + init_awk_sample_locale (); + return qse_runmain (argc, argv, awk_main); +} + diff --git a/qse/samples/awk/awk10.c b/qse/samples/awk/awk10.c new file mode 100644 index 00000000..6b2d8dd1 --- /dev/null +++ b/qse/samples/awk/awk10.c @@ -0,0 +1,152 @@ +#include +#include +#include +#include +#include +#include "awk00.h" + +static const qse_char_t* src = QSE_T( + "BEGIN { if (basename(\"/etc/passwd\", base) <= -1) print \"ERROR\"; else print base; }" +); + +static int fnc_basename (qse_awk_rtx_t* rtx, const qse_awk_fnc_info_t* fi) +{ + qse_awk_val_t* a0, * rv = QSE_NULL; + qse_char_t* ptr; + qse_size_t len; + + /* note that this implementation doesn't care if the parameter + * contains a null character like "/etc/p\0asswd" */ + + /* get the value of the first parameter */ + a0 = qse_awk_rtx_getarg (rtx, 0); + if (a0->type == QSE_AWK_VAL_STR) + { + /* if it is a string value, don't duplicate the value */ + ptr = ((qse_awk_val_str_t*)a0)->val.ptr; + len = ((qse_awk_val_str_t*)a0)->val.len; + + /* make a string value with the base name */ + rv = qse_awk_rtx_makestrvalwithstr (rtx, qse_basename (ptr)); + } + else + { + /* if it is a string value, convert the value to a string + * with duplication */ + ptr = qse_awk_rtx_valtostrdup (rtx, a0, &len); + if (ptr) + { + /* make a string value with the base name */ + rv = qse_awk_rtx_makestrvalwithstr (rtx, qse_basename (ptr)); + + /* free the duplicated string */ + qse_awk_rtx_freemem (rtx, ptr); + } + } + + if (rv) + { + /* change the value of the second parameter passed by reference */ + qse_awk_rtx_setrefval (rtx, qse_awk_rtx_getarg (rtx, 1), rv); + + /* set the return value without error checks because + * qse_awk_rtx_makeintval() for 0 never fails */ + qse_awk_rtx_setretval (rtx, qse_awk_rtx_makeintval (rtx, 0)); + } + else + { + /* set the return value without error checks because + * qse_awk_rtx_makeintval() for -1 never fails */ + qse_awk_rtx_setretval (rtx, qse_awk_rtx_makeintval (rtx, -1)); + } + + /* implementation success */ + return 0; +} + +static int awk_main (int argc, qse_char_t* argv[]) +{ + qse_awk_t* awk = QSE_NULL; + qse_awk_rtx_t* rtx = QSE_NULL; + qse_awk_parsestd_t psin[2]; + qse_awk_val_t* rtv; + int ret = -1; + qse_awk_fnc_spec_t spec; + + /* create an awk object */ + awk = qse_awk_openstd (0); + if (awk == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: cannot open awk\n")); + goto oops; + } + + /* add a built-in function basename() */ + qse_memset (&spec, 0, QSE_SIZEOF(spec)); + spec.arg.min = 2; /* limit the number of arguments to 1 */ + spec.arg.max = 2; + spec.arg.spec = QSE_T("vr"); /* pass the second argument by reference */ + spec.impl = fnc_basename; /* specify the actual implementation */ + if (qse_awk_addfnc (awk, QSE_T("basename"), &spec) == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); + goto oops; + } + + /* prepare an awk script to parse */ + psin[0].type = QSE_AWK_PARSESTD_STR; + psin[0].u.str.ptr = src; + psin[0].u.str.len = qse_strlen(src); + psin[1].type = QSE_AWK_PARSESTD_NULL; + + /* parse the script */ + if (qse_awk_parsestd (awk, psin, QSE_NULL) <= -1) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); + goto oops; + } + + /* create a runtime context */ + rtx = qse_awk_rtx_openstd ( + awk, + 0, + QSE_T("awk10"), + QSE_NULL, /* stdin */ + QSE_NULL, /* stdout */ + QSE_NULL /* default cmgr */ + ); + if (rtx == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_geterrmsg(awk)); + goto oops; + } + + /* execute the script over the standard data streams */ + rtv = qse_awk_rtx_loop (rtx); + if (rtv == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), qse_awk_rtx_geterrmsg(rtx)); + goto oops; + } + + /* clear the return value */ + qse_awk_rtx_refdownval (rtx, rtv); + + ret = 0; + +oops: + /* destroy a runtime context */ + if (rtx) qse_awk_rtx_close (rtx); + + /* destroy the processor */ + if (awk) qse_awk_close (awk); + + return ret; +} + +int qse_main (int argc, qse_achar_t* argv[]) +{ + init_awk_sample_locale (); + return qse_runmain (argc, argv, awk_main); +} + diff --git a/qse/samples/awk/awk12.c b/qse/samples/awk/awk12.c new file mode 100644 index 00000000..2a7a3f88 --- /dev/null +++ b/qse/samples/awk/awk12.c @@ -0,0 +1,93 @@ +#include +#include + +/* this sample produces 8 text files containing multiplication chart. */ + +const qse_char_t* src = QSE_T( + "BEGIN {" + " for (i=2;i<=9;i++)" + " {" + " print \"OFILENAME:\" OFILENAME;" + " for (j=1;j<=9;j++)" + " print i \"*\" j \"=\" i * j;" + " nextofile;" + " }" + "}" +); + +int main () +{ + qse_awk_t* awk = QSE_NULL; + qse_awk_rtx_t* rtx = QSE_NULL; + qse_awk_val_t* retv; + qse_awk_parsestd_t psin[2]; + int ret = -1, opt; + + const qse_char_t* output_files[] = + { + QSE_T("awk09.out.2"), + QSE_T("awk09.out.3"), + QSE_T("awk09.out.4"), + QSE_T("awk09.out.5"), + QSE_T("awk09.out.6"), + QSE_T("awk09.out.7"), + QSE_T("awk09.out.8"), + QSE_T("awk09.out.9"), + QSE_NULL + }; + + awk = qse_awk_openstd (0); + if (awk == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: cannot open awk\n")); + goto oops; + } + + qse_awk_getopt (awk, QSE_AWK_TRAIT, &opt); + opt |= QSE_AWK_EXTRAKWS; + qse_awk_setopt (awk, QSE_AWK_TRAIT, &opt); + + psin[0].type = QSE_AWK_PARSESTD_STR; + psin[0].u.str.ptr = src; + psin[0].u.str.len = qse_strlen(src); + psin[1].type = QSE_AWK_PARSESTD_NULL; + + if (qse_awk_parsestd (awk, psin, QSE_NULL) <= -1) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), + qse_awk_geterrmsg(awk)); + goto oops; + } + + rtx = qse_awk_rtx_openstd ( + awk, + 0, + QSE_T("awk09"), + QSE_NULL, /* stdin */ + output_files, + QSE_NULL /* default cmgr */ + ); + if (rtx == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), + qse_awk_geterrmsg(awk)); + goto oops; + } + + retv = qse_awk_rtx_loop (rtx); + if (retv == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("ERROR: %s\n"), + qse_awk_rtx_geterrmsg(rtx)); + goto oops; + } + + qse_awk_rtx_refdownval (rtx, retv); + ret = 0; + +oops: + if (rtx != QSE_NULL) qse_awk_rtx_close (rtx); + if (awk != QSE_NULL) qse_awk_close (awk); + return ret; +} +