"Fossies" - the Fresh Open Source Software Archive

Member "bind-9.11.23/lib/isc/include/isc/lex.h" (7 Sep 2020, 9770 Bytes) of package /linux/misc/dns/bind9/9.11.23/bind-9.11.23.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "lex.h" see the Fossies "Dox" file reference documentation.

    1 /*
    2  * Copyright (C) Internet Systems Consortium, Inc. ("ISC")
    3  *
    4  * This Source Code Form is subject to the terms of the Mozilla Public
    5  * License, v. 2.0. If a copy of the MPL was not distributed with this
    6  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
    7  *
    8  * See the COPYRIGHT file distributed with this work for additional
    9  * information regarding copyright ownership.
   10  */
   11 
   12 
   13 #ifndef ISC_LEX_H
   14 #define ISC_LEX_H 1
   15 
   16 /*****
   17  ***** Module Info
   18  *****/
   19 
   20 /*! \file isc/lex.h
   21  * \brief The "lex" module provides a lightweight tokenizer.  It can operate
   22  * on files or buffers, and can handle "include".  It is designed for
   23  * parsing of DNS master files and the BIND configuration file, but
   24  * should be general enough to tokenize other things, e.g. HTTP.
   25  *
   26  * \li MP:
   27  *  No synchronization is provided.  Clients must ensure exclusive
   28  *  access.
   29  *
   30  * \li Reliability:
   31  *  No anticipated impact.
   32  *
   33  * \li Resources:
   34  *  TBS
   35  *
   36  * \li Security:
   37  *  No anticipated impact.
   38  *
   39  * \li Standards:
   40  *  None.
   41  */
   42 
   43 /***
   44  *** Imports
   45  ***/
   46 
   47 #include <stdbool.h>
   48 #include <stdio.h>
   49 
   50 #include <isc/lang.h>
   51 #include <isc/region.h>
   52 #include <isc/types.h>
   53 
   54 ISC_LANG_BEGINDECLS
   55 
   56 /***
   57  *** Options
   58  ***/
   59 
   60 /*@{*/
   61 /*!
   62  * Various options for isc_lex_gettoken().
   63  */
   64 
   65 #define ISC_LEXOPT_EOL          0x01    /*%< Want end-of-line token. */
   66 #define ISC_LEXOPT_EOF          0x02    /*%< Want end-of-file token. */
   67 #define ISC_LEXOPT_INITIALWS        0x04    /*%< Want initial whitespace. */
   68 #define ISC_LEXOPT_NUMBER       0x08    /*%< Recognize numbers. */
   69 #define ISC_LEXOPT_QSTRING      0x10    /*%< Recognize qstrings. */
   70 /*@}*/
   71 
   72 /*@{*/
   73 /*!
   74  * The ISC_LEXOPT_DNSMULTILINE option handles the processing of '(' and ')' in
   75  * the DNS master file format.  If this option is set, then the
   76  * ISC_LEXOPT_INITIALWS and ISC_LEXOPT_EOL options will be ignored when
   77  * the paren count is > 0.  To use this option, '(' and ')' must be special
   78  * characters.
   79  */
   80 #define ISC_LEXOPT_DNSMULTILINE     0x20    /*%< Handle '(' and ')'. */
   81 #define ISC_LEXOPT_NOMORE       0x40    /*%< Want "no more" token. */
   82 
   83 #define ISC_LEXOPT_CNUMBER      0x80    /*%< Recognize octal and hex. */
   84 #define ISC_LEXOPT_ESCAPE       0x100   /*%< Recognize escapes. */
   85 #define ISC_LEXOPT_QSTRINGMULTILINE 0x200   /*%< Allow multiline "" strings */
   86 #define ISC_LEXOPT_OCTAL        0x400   /*%< Expect a octal number. */
   87 #define ISC_LEXOPT_BTEXT        0x800   /*%< Bracketed text. */
   88 /*@}*/
   89 /*@{*/
   90 /*!
   91  * Various commenting styles, which may be changed at any time with
   92  * isc_lex_setcomments().
   93  */
   94 
   95 #define ISC_LEXCOMMENT_C        0x01
   96 #define ISC_LEXCOMMENT_CPLUSPLUS    0x02
   97 #define ISC_LEXCOMMENT_SHELL        0x04
   98 #define ISC_LEXCOMMENT_DNSMASTERFILE    0x08
   99 /*@}*/
  100 
  101 /***
  102  *** Types
  103  ***/
  104 
  105 /*! Lex */
  106 
  107 typedef char isc_lexspecials_t[256];
  108 
  109 /* Tokens */
  110 
  111 typedef enum {
  112     isc_tokentype_unknown = 0,
  113     isc_tokentype_string = 1,
  114     isc_tokentype_number = 2,
  115     isc_tokentype_qstring = 3,
  116     isc_tokentype_eol = 4,
  117     isc_tokentype_eof = 5,
  118     isc_tokentype_initialws = 6,
  119     isc_tokentype_special = 7,
  120     isc_tokentype_nomore = 8,
  121     isc_tokentype_btext = 8
  122 } isc_tokentype_t;
  123 
  124 typedef union {
  125     char                as_char;
  126     unsigned long           as_ulong;
  127     isc_region_t            as_region;
  128     isc_textregion_t        as_textregion;
  129     void *              as_pointer;
  130 } isc_tokenvalue_t;
  131 
  132 typedef struct isc_token {
  133     isc_tokentype_t         type;
  134     isc_tokenvalue_t        value;
  135 } isc_token_t;
  136 
  137 /***
  138  *** Functions
  139  ***/
  140 
  141 isc_result_t
  142 isc_lex_create(isc_mem_t *mctx, size_t max_token, isc_lex_t **lexp);
  143 /*%<
  144  * Create a lexer.
  145  *
  146  * 'max_token' is a hint of the number of bytes in the largest token.
  147  *
  148  * Requires:
  149  *\li   '*lexp' is a valid lexer.
  150  *
  151  * Ensures:
  152  *\li   On success, *lexp is attached to the newly created lexer.
  153  *
  154  * Returns:
  155  *\li   #ISC_R_SUCCESS
  156  *\li   #ISC_R_NOMEMORY
  157  */
  158 
  159 void
  160 isc_lex_destroy(isc_lex_t **lexp);
  161 /*%<
  162  * Destroy the lexer.
  163  *
  164  * Requires:
  165  *\li   '*lexp' is a valid lexer.
  166  *
  167  * Ensures:
  168  *\li   *lexp == NULL
  169  */
  170 
  171 unsigned int
  172 isc_lex_getcomments(isc_lex_t *lex);
  173 /*%<
  174  * Return the current lexer commenting styles.
  175  *
  176  * Requires:
  177  *\li   'lex' is a valid lexer.
  178  *
  179  * Returns:
  180  *\li   The commenting styles which are currently allowed.
  181  */
  182 
  183 void
  184 isc_lex_setcomments(isc_lex_t *lex, unsigned int comments);
  185 /*%<
  186  * Set allowed lexer commenting styles.
  187  *
  188  * Requires:
  189  *\li   'lex' is a valid lexer.
  190  *
  191  *\li   'comments' has meaningful values.
  192  */
  193 
  194 void
  195 isc_lex_getspecials(isc_lex_t *lex, isc_lexspecials_t specials);
  196 /*%<
  197  * Put the current list of specials into 'specials'.
  198  *
  199  * Requires:
  200  *\li   'lex' is a valid lexer.
  201  */
  202 
  203 void
  204 isc_lex_setspecials(isc_lex_t *lex, isc_lexspecials_t specials);
  205 /*!<
  206  * The characters in 'specials' are returned as tokens.  Along with
  207  * whitespace, they delimit strings and numbers.
  208  *
  209  * Note:
  210  *\li   Comment processing takes precedence over special character
  211  *  recognition.
  212  *
  213  * Requires:
  214  *\li   'lex' is a valid lexer.
  215  */
  216 
  217 isc_result_t
  218 isc_lex_openfile(isc_lex_t *lex, const char *filename);
  219 /*%<
  220  * Open 'filename' and make it the current input source for 'lex'.
  221  *
  222  * Requires:
  223  *\li   'lex' is a valid lexer.
  224  *
  225  *\li   filename is a valid C string.
  226  *
  227  * Returns:
  228  *\li   #ISC_R_SUCCESS
  229  *\li   #ISC_R_NOMEMORY         Out of memory
  230  *\li   #ISC_R_NOTFOUND         File not found
  231  *\li   #ISC_R_NOPERM           No permission to open file
  232  *\li   #ISC_R_FAILURE          Couldn't open file, not sure why
  233  *\li   #ISC_R_UNEXPECTED
  234  */
  235 
  236 isc_result_t
  237 isc_lex_openstream(isc_lex_t *lex, FILE *stream);
  238 /*%<
  239  * Make 'stream' the current input source for 'lex'.
  240  *
  241  * Requires:
  242  *\li   'lex' is a valid lexer.
  243  *
  244  *\li   'stream' is a valid C stream.
  245  *
  246  * Returns:
  247  *\li   #ISC_R_SUCCESS
  248  *\li   #ISC_R_NOMEMORY         Out of memory
  249  */
  250 
  251 isc_result_t
  252 isc_lex_openbuffer(isc_lex_t *lex, isc_buffer_t *buffer);
  253 /*%<
  254  * Make 'buffer' the current input source for 'lex'.
  255  *
  256  * Requires:
  257  *\li   'lex' is a valid lexer.
  258  *
  259  *\li   'buffer' is a valid buffer.
  260  *
  261  * Returns:
  262  *\li   #ISC_R_SUCCESS
  263  *\li   #ISC_R_NOMEMORY         Out of memory
  264  */
  265 
  266 isc_result_t
  267 isc_lex_close(isc_lex_t *lex);
  268 /*%<
  269  * Close the most recently opened object (i.e. file or buffer).
  270  *
  271  * Returns:
  272  *\li   #ISC_R_SUCCESS
  273  *\li   #ISC_R_NOMORE           No more input sources
  274  */
  275 
  276 isc_result_t
  277 isc_lex_gettoken(isc_lex_t *lex, unsigned int options, isc_token_t *tokenp);
  278 /*%<
  279  * Get the next token.
  280  *
  281  * Requires:
  282  *\li   'lex' is a valid lexer.
  283  *
  284  *\li   'lex' has an input source.
  285  *
  286  *\li   'options' contains valid options.
  287  *
  288  *\li   '*tokenp' is a valid pointer.
  289  *
  290  * Returns:
  291  *\li   #ISC_R_SUCCESS
  292  *\li   #ISC_R_UNEXPECTEDEND
  293  *\li   #ISC_R_NOMEMORY
  294  *
  295  *  These two results are returned only if their corresponding lexer
  296  *  options are not set.
  297  *
  298  *\li   #ISC_R_EOF          End of input source
  299  *\li   #ISC_R_NOMORE           No more input sources
  300  */
  301 
  302 isc_result_t
  303 isc_lex_getmastertoken(isc_lex_t *lex, isc_token_t *token,
  304                isc_tokentype_t expect, bool eol);
  305 /*%<
  306  * Get the next token from a DNS master file type stream.  This is a
  307  * convenience function that sets appropriate options and handles quoted
  308  * strings and end of line correctly for master files.  It also ungets
  309  * unexpected tokens.  If `eol` is set then expect end-of-line otherwise
  310  * eol is a error.
  311  *
  312  * Requires:
  313  *\li   'lex' is a valid lexer.
  314  *
  315  *\li   'token' is a valid pointer
  316  *
  317  * Returns:
  318  *
  319  * \li  any return code from isc_lex_gettoken().
  320  */
  321 
  322 isc_result_t
  323 isc_lex_getoctaltoken(isc_lex_t *lex, isc_token_t *token, bool eol);
  324 /*%<
  325  * Get the next token from a DNS master file type stream.  This is a
  326  * convenience function that sets appropriate options and handles end
  327  * of line correctly for master files.  It also ungets unexpected tokens.
  328  * If `eol` is set then expect end-of-line otherwise eol is a error.
  329  *
  330  * Requires:
  331  *\li   'lex' is a valid lexer.
  332  *
  333  *\li   'token' is a valid pointer
  334  *
  335  * Returns:
  336  *
  337  * \li  any return code from isc_lex_gettoken().
  338  */
  339 
  340 void
  341 isc_lex_ungettoken(isc_lex_t *lex, isc_token_t *tokenp);
  342 /*%<
  343  * Unget the current token.
  344  *
  345  * Requires:
  346  *\li   'lex' is a valid lexer.
  347  *
  348  *\li   'lex' has an input source.
  349  *
  350  *\li   'tokenp' points to a valid token.
  351  *
  352  *\li   There is no ungotten token already.
  353  */
  354 
  355 void
  356 isc_lex_getlasttokentext(isc_lex_t *lex, isc_token_t *tokenp, isc_region_t *r);
  357 /*%<
  358  * Returns a region containing the text of the last token returned.
  359  *
  360  * Requires:
  361  *\li   'lex' is a valid lexer.
  362  *
  363  *\li   'lex' has an input source.
  364  *
  365  *\li   'tokenp' points to a valid token.
  366  *
  367  *\li   A token has been gotten and not ungotten.
  368  */
  369 
  370 char *
  371 isc_lex_getsourcename(isc_lex_t *lex);
  372 /*%<
  373  * Return the input source name.
  374  *
  375  * Requires:
  376  *\li   'lex' is a valid lexer.
  377  *
  378  * Returns:
  379  * \li  source name or NULL if no current source.
  380  *\li   result valid while current input source exists.
  381  */
  382 
  383 
  384 unsigned long
  385 isc_lex_getsourceline(isc_lex_t *lex);
  386 /*%<
  387  * Return the input source line number.
  388  *
  389  * Requires:
  390  *\li   'lex' is a valid lexer.
  391  *
  392  * Returns:
  393  *\li   Current line number or 0 if no current source.
  394  */
  395 
  396 isc_result_t
  397 isc_lex_setsourcename(isc_lex_t *lex, const char *name);
  398 /*%<
  399  * Assigns a new name to the input source.
  400  *
  401  * Requires:
  402  *
  403  * \li  'lex' is a valid lexer.
  404  *
  405  * Returns:
  406  * \li  #ISC_R_SUCCESS
  407  * \li  #ISC_R_NOMEMORY
  408  * \li  #ISC_R_NOTFOUND - there are no sources.
  409  */
  410 
  411 isc_result_t
  412 isc_lex_setsourceline(isc_lex_t *lex, unsigned long line);
  413 /*%<
  414  * Assigns a new line number to the input source. This can be used
  415  * when parsing a buffer that's been excerpted from the middle a file,
  416  * allowing logged messages to display the correct line number,
  417  * rather than the line number within the buffer.
  418  *
  419  * Requires:
  420  *
  421  * \li  'lex' is a valid lexer.
  422  *
  423  * Returns:
  424  * \li  #ISC_R_SUCCESS
  425  * \li  #ISC_R_NOTFOUND - there are no sources.
  426  */
  427 
  428 bool
  429 isc_lex_isfile(isc_lex_t *lex);
  430 /*%<
  431  * Return whether the current input source is a file.
  432  *
  433  * Requires:
  434  *\li   'lex' is a valid lexer.
  435  *
  436  * Returns:
  437  * \li  #true if the current input is a file,
  438  *\li   #false otherwise.
  439  */
  440 
  441 
  442 ISC_LANG_ENDDECLS
  443 
  444 #endif /* ISC_LEX_H */