gawk: Extension Mechanism Outline

 
 16.3 How It Works at a High Level
 =================================
 
 Communication between 'gawk' and an extension is two-way.  First, when
 an extension is loaded, 'gawk' passes it a pointer to a 'struct' whose
 
 [image src="api-figure1.png" alt="Loading the extension" text="                          API
                          Struct
                          +---+
                          |   |
                          +---+
          +---------------|   |
          |               +---+      dl_load(api_p, id);
          |               |   |  ___________________ 
          |               +---+                     |
          |     +---------|   |  __________________ |
          |     |         +---+                    ||
          |     |         |   |                    ||
          |     |         +---+                    ||
          |     |     +---|   |                    ||
          |     |     |   +---+                  \\ || /
          |     |     |                           \\  /
          v     v     v                            \\/
 +-------+-+---+-+---+-+------------------+--------------------+
 |       |x|   |x|   |x|                  |OOOOOOOOOOOOOOOOOOOO|
 |       |x|   |x|   |x|                  |OOOOOOOOOOOOOOOOOOOO|
 |       |x|   |x|   |x|                  |OOOOOOOOOOOOOOOOOOOO|
 +-------+-+---+-+---+-+------------------+--------------------+
 
     gawk Main Program Address Space              Extension"]
 
 Figure 16.1: Loading the extension
 
    The extension can call functions inside 'gawk' through these function
 pointers, at runtime, without needing (link-time) access to 'gawk''s
 symbols.  One of these function pointers is to a function for
 
 [image src="api-figure2.png" alt="Registering a new Function" text="            register_ext_func({ \"chdir\", do_chdir, 1 });
 
             +--------------------------------------------+
             |                                            |
             V                                            |
 +-------+-+---+-+---+-+------------------+--------------+-+---+
 |       |x|   |x|   |x|                  |OOOOOOOOOOOOOO|X|OOO|
 |       |x|   |x|   |x|                  |OOOOOOOOOOOOOO|X|OOO|
 |       |x|   |x|   |x|                  |OOOOOOOOOOOOOO|X|OOO|
 +-------+-+---+-+---+-+------------------+--------------+-+---+
 
     gawk Main Program Address Space              Extension"]
 
 Figure 16.2: Registering a new function
 
    In the other direction, the extension registers its new functions
 with 'gawk' by passing function pointers to the functions that provide
 the new feature ('do_chdir()', for example).  'gawk' associates the
 function pointer with a name and can then call it, using a defined
 
 [image src="api-figure3.png" alt="Calling the new function" text="    BEGIN {
         chdir(\"/path\")                             (*fnptr)(1);
     }
             +--------------------------------------------+
             |                                            |
             |                                            V
 +-------+-+---+-+---+-+------------------+--------------+-+---+
 |       |x|   |x|   |x|                  |OOOOOOOOOOOOOO|X|OOO|
 |       |x|   |x|   |x|                  |OOOOOOOOOOOOOO|X|OOO|
 |       |x|   |x|   |x|                  |OOOOOOOOOOOOOO|X|OOO|
 +-------+-+---+-+---+-+------------------+--------------+-+---+
 
     gawk Main Program Address Space              Extension"]
 
 Figure 16.3: Calling the new function
 
    The 'do_XXX()' function, in turn, then uses the function pointers in
 the API 'struct' to do its work, such as updating variables or arrays,
 printing messages, setting 'ERRNO', and so on.
 
    Convenience macros make calling through the function pointers look
 like regular function calls so that extension code is quite readable and
 understandable.
 
    Although all of this sounds somewhat complicated, the result is that
 extension code is quite straightforward to write and to read.  You can
 see this in the sample extension 'filefuncs.c' (SeeExtension
 Example) and also in the 'testext.c' code for testing the APIs.
 
    Some other bits and pieces:
 
    * The API provides access to 'gawk''s 'do_XXX' values, reflecting
      command-line options, like 'do_lint', 'do_profiling', and so on
      (SeeExtension API Variables).  These are informational: an
      extension cannot affect their values inside 'gawk'.  In addition,
      attempting to assign to them produces a compile-time error.
 
    * The API also provides major and minor version numbers, so that an
      extension can check if the 'gawk' it is loaded with supports the
      facilities it was compiled with.  (Version mismatches "shouldn't"
      happen, but we all know how _that_ goes.)  SeeExtension
      Versioning for details.