File:  [ELWIX - Embedded LightWeight unIX -] / embedaddon / bird / doc / prog-3.html
Revision 1.1.1.1 (vendor branch): download - view: text, annotated - select for diffs - revision graph
Tue Aug 22 12:33:54 2017 UTC (6 years, 10 months ago) by misho
Branches: bird, MAIN
CVS tags: v1_6_8p3, v1_6_3p0, v1_6_3, HEAD
bird 1.6.3

    1: <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN">
    2: <HTML>
    3: <HEAD>
    4:  <META NAME="GENERATOR" CONTENT="LinuxDoc-Tools 1.0.9">
    5:  <TITLE>BIRD Programmer's Documentation: Configuration</TITLE>
    6:  <LINK HREF="prog-4.html" REL=next>
    7:  <LINK HREF="prog-2.html" REL=previous>
    8:  <LINK HREF="prog.html#toc3" REL=contents>
    9: </HEAD>
   10: <BODY>
   11: <A HREF="prog-4.html">Next</A>
   12: <A HREF="prog-2.html">Previous</A>
   13: <A HREF="prog.html#toc3">Contents</A>
   14: <HR>
   15: <H2><A NAME="s3">3.</A> <A HREF="prog.html#toc3">Configuration</A></H2>
   16: 
   17: <H2><A NAME="ss3.1">3.1</A> <A HREF="prog.html#toc3.1">Configuration manager</A>
   18: </H2>
   19: 
   20: <P>
   21: <P>Configuration of BIRD is complex, yet straightforward. There are three
   22: modules taking care of the configuration: config manager (which takes care
   23: of storage of the config information and controls switching between configs),
   24: lexical analyzer and parser.
   25: <P>The configuration manager stores each config as a <I>config</I> structure
   26: accompanied by a linear pool from which all information associated
   27: with the config and pointed to by the <I>config</I> structure is allocated.
   28: <P>There can exist up to four different configurations at one time: an active
   29: one (pointed to by <B>config</B>), configuration we are just switching from
   30: (<B>old_config</B>), one queued for the next reconfiguration (<B>future_config</B>; if
   31: there is one and the user wants to reconfigure once again, we just free the
   32: previous queued config and replace it with the new one) and finally a config
   33: being parsed (<B>new_config</B>). The stored <B>old_config</B> is also used for undo
   34: reconfiguration, which works in a similar way. Reconfiguration could also
   35: have timeout (using <B>config_timer</B>) and undo is automatically called if the
   36: new configuration is not confirmed later. The new config (<B>new_config</B>) and
   37: associated linear pool (<B>cfg_mem</B>) is non-NULL only during parsing.
   38: <P>Loading of new configuration is very simple: just call <B>config_alloc()</B> to get
   39: a new <I>config</I> structure, then use <B>config_parse()</B> to parse a configuration
   40: file and fill all fields of the structure and finally ask the config manager
   41: to switch to the new config by calling <B>config_commit()</B>.
   42: <P>CLI commands are parsed in a very similar way -- there is also a stripped-down
   43: <I>config</I> structure associated with them and they are lex-ed and parsed by the
   44: same functions, only a special fake token is prepended before the command
   45: text to make the parser recognize only the rules corresponding to CLI commands.
   46: <P>
   47: <P><HR><H3>Function</H3>
   48: <P><I>struct config *</I>
   49: <B>config_alloc</B>
   50: (<I>const byte *</I> <B>name</B>) --     allocate a new configuration
   51: <P>
   52: <H3>Arguments</H3>
   53: <P>
   54: <DL>
   55: <DT><I>const byte *</I> <B>name</B><DD><P>name of the config
   56: </DL>
   57: <H3>Description</H3>
   58: <P>This function creates new <I>config</I> structure, attaches a resource
   59: pool and a linear memory pool to it and makes it available for
   60: further use. Returns a pointer to the structure.
   61: 
   62: 
   63: <HR><H3>Function</H3>
   64: <P><I>int</I>
   65: <B>config_parse</B>
   66: (<I>struct config *</I> <B>c</B>) --     parse a configuration
   67: <P>
   68: <H3>Arguments</H3>
   69: <P>
   70: <DL>
   71: <DT><I>struct config *</I> <B>c</B><DD><P>configuration
   72: </DL>
   73: <H3>Description</H3>
   74: <P><B>config_parse()</B> reads input by calling a hook function pointed to
   75: by <B>cf_read_hook</B> and parses it according to the configuration
   76: grammar. It also calls all the preconfig and postconfig hooks
   77: before, resp. after parsing.
   78: <H3>Result</H3>
   79: <P>1 if the config has been parsed successfully, 0 if any
   80: error has occurred (such as anybody calling <B>cf_error()</B>) and
   81: the <B>err_msg</B> field has been set to the error message.
   82: 
   83: 
   84: <HR><H3>Function</H3>
   85: <P><I>int</I>
   86: <B>cli_parse</B>
   87: (<I>struct config *</I> <B>c</B>) --     parse a CLI command
   88: <P>
   89: <H3>Arguments</H3>
   90: <P>
   91: <DL>
   92: <DT><I>struct config *</I> <B>c</B><DD><P>temporary config structure
   93: </DL>
   94: <H3>Description</H3>
   95: <P><B>cli_parse()</B> is similar to <B>config_parse()</B>, but instead of a configuration,
   96: it parses a CLI command. See the CLI module for more information.
   97: 
   98: 
   99: <HR><H3>Function</H3>
  100: <P><I>void</I>
  101: <B>config_free</B>
  102: (<I>struct config *</I> <B>c</B>) --     free a configuration
  103: <P>
  104: <H3>Arguments</H3>
  105: <P>
  106: <DL>
  107: <DT><I>struct config *</I> <B>c</B><DD><P>configuration to be freed
  108: </DL>
  109: <H3>Description</H3>
  110: <P>This function takes a <I>config</I> structure and frees all resources
  111: associated with it.
  112: 
  113: 
  114: <HR><H3>Function</H3>
  115: <P><I>int</I>
  116: <B>config_commit</B>
  117: (<I>struct config *</I> <B>c</B>, <I>int</I> <B>type</B>, <I>int</I> <B>timeout</B>) --     commit a configuration
  118: <P>
  119: <H3>Arguments</H3>
  120: <P>
  121: <DL>
  122: <DT><I>struct config *</I> <B>c</B><DD><P>new configuration
  123: <DT><I>int</I> <B>type</B><DD><P>type of reconfiguration (RECONFIG_SOFT or RECONFIG_HARD)
  124: <DT><I>int</I> <B>timeout</B><DD><P>timeout for undo (or 0 for no timeout)
  125: </DL>
  126: <H3>Description</H3>
  127: <P>When a configuration is parsed and prepared for use, the
  128: <B>config_commit()</B> function starts the process of reconfiguration.
  129: It checks whether there is already a reconfiguration in progress
  130: in which case it just queues the new config for later processing.
  131: Else it notifies all modules about the new configuration by calling
  132: their <B>commit()</B> functions which can either accept it immediately
  133: or call <B>config_add_obstacle()</B> to report that they need some time
  134: to complete the reconfiguration. After all such obstacles are removed
  135: using <B>config_del_obstacle()</B>, the old configuration is freed and
  136: everything runs according to the new one.
  137: <P>When <B>timeout</B> is nonzero, the undo timer is activated with given
  138: timeout. The timer is deactivated when <B>config_commit()</B>,
  139: <B>config_confirm()</B> or <B>config_undo()</B> is called.
  140: <H3>Result</H3>
  141: <P><I>CONF_DONE</I> if the configuration has been accepted immediately,
  142: <I>CONF_PROGRESS</I> if it will take some time to switch to it, <I>CONF_QUEUED</I>
  143: if it's been queued due to another reconfiguration being in progress now
  144: or <I>CONF_SHUTDOWN</I> if BIRD is in shutdown mode and no new configurations
  145: are accepted.
  146: 
  147: 
  148: <HR><H3>Function</H3>
  149: <P><I>int</I>
  150: <B>config_confirm</B>
  151: (<B>void</B>) --     confirm a commited configuration
  152: <P>
  153: <H3>Description</H3>
  154: <P>
  155: <P>When the undo timer is activated by <B>config_commit()</B> with nonzero timeout,
  156: this function can be used to deactivate it and therefore confirm
  157: the current configuration.
  158: <H3>Result</H3>
  159: <P><I>CONF_CONFIRM</I> when the current configuration is confirmed,
  160: <I>CONF_NONE</I> when there is nothing to confirm (i.e. undo timer is not active).
  161: 
  162: 
  163: <HR><H3>Function</H3>
  164: <P><I>int</I>
  165: <B>config_undo</B>
  166: (<B>void</B>) --     undo a configuration
  167: <P>
  168: <H3>Description</H3>
  169: <P>
  170: <P>Function <B>config_undo()</B> can be used to change the current
  171: configuration back to stored <I>old_config</I>. If no reconfiguration is
  172: running, this stored configuration is commited in the same way as a
  173: new configuration in <B>config_commit()</B>. If there is already a
  174: reconfiguration in progress and no next reconfiguration is
  175: scheduled, then the undo is scheduled for later processing as
  176: usual, but if another reconfiguration is already scheduled, then
  177: such reconfiguration is removed instead (i.e. undo is applied on
  178: the last commit that scheduled it).
  179: <H3>Result</H3>
  180: <P><I>CONF_DONE</I> if the configuration has been accepted immediately,
  181: <I>CONF_PROGRESS</I> if it will take some time to switch to it, <I>CONF_QUEUED</I>
  182: if it's been queued due to another reconfiguration being in progress now,
  183: <I>CONF_UNQUEUED</I> if a scheduled reconfiguration is removed, <I>CONF_NOTHING</I>
  184: if there is no relevant configuration to undo (the previous config request
  185: was <B>config_undo()</B> too)  or <I>CONF_SHUTDOWN</I> if BIRD is in shutdown mode and
  186: no new configuration changes  are accepted.
  187: 
  188: 
  189: <HR><H3>Function</H3>
  190: <P><I>void</I>
  191: <B>order_shutdown</B>
  192: (<B>void</B>) --     order BIRD shutdown
  193: <P>
  194: <H3>Description</H3>
  195: <P>
  196: <P>This function initiates shutdown of BIRD. It's accomplished by asking
  197: for switching to an empty configuration.
  198: 
  199: 
  200: <HR><H3>Function</H3>
  201: <P><I>void</I>
  202: <B>cf_error</B>
  203: (<I>char *</I> <B>msg</B>, <I>...</I> <B>...</B>) --     report a configuration error
  204: <P>
  205: <H3>Arguments</H3>
  206: <P>
  207: <DL>
  208: <DT><I>char *</I> <B>msg</B><DD><P>printf-like format string
  209: <DT><I>...</I> <B>...</B><DD><P>variable arguments
  210: </DL>
  211: <H3>Description</H3>
  212: <P><B>cf_error()</B> can be called during execution of <B>config_parse()</B>, that is
  213: from the parser, a preconfig hook or a postconfig hook, to report an
  214: error in the configuration.
  215: 
  216: 
  217: <HR><H3>Function</H3>
  218: <P><I>char *</I>
  219: <B>cfg_strdup</B>
  220: (<I>const char *</I> <B>c</B>) --     copy a string to config memory
  221: <P>
  222: <H3>Arguments</H3>
  223: <P>
  224: <DL>
  225: <DT><I>const char *</I> <B>c</B><DD><P>string to copy
  226: </DL>
  227: <H3>Description</H3>
  228: <P><B>cfg_strdup()</B> creates a new copy of the string in the memory
  229: pool associated with the configuration being currently parsed.
  230: It's often used when a string literal occurs in the configuration
  231: and we want to preserve it for further use.
  232: 
  233: <H2><A NAME="ss3.2">3.2</A> <A HREF="prog.html#toc3.2">Lexical analyzer</A>
  234: </H2>
  235: 
  236: <P>
  237: <P>The lexical analyzer used for configuration files and CLI commands
  238: is generated using the <CODE>flex</CODE> tool accompanied by a couple of
  239: functions maintaining the hash tables containing information about
  240: symbols and keywords.
  241: <P>Each symbol is represented by a <I>symbol</I> structure containing name
  242: of the symbol, its lexical scope, symbol class (<I>SYM_PROTO</I> for a
  243: name of a protocol, <I>SYM_CONSTANT</I> for a constant etc.) and class
  244: dependent data.  When an unknown symbol is encountered, it's
  245: automatically added to the symbol table with class <I>SYM_VOID</I>.
  246: <P>The keyword tables are generated from the grammar templates
  247: using the <CODE>gen_keywords.m4</CODE> script.
  248: <P>
  249: <P><HR><H3>Function</H3>
  250: <P><I>void</I>
  251: <B>cf_lex_unwind</B>
  252: (<B>void</B>) --     unwind lexer state during error
  253: <P>
  254: <H3>Lexical analyzer</H3>
  255: <P>
  256: <P><B>cf_lex_unwind()</B> frees the internal state on IFS stack when the lexical
  257: analyzer is terminated by <B>cf_error()</B>.
  258: 
  259: 
  260: <HR><H3>Function</H3>
  261: <P><I>struct symbol *</I>
  262: <B>cf_find_symbol</B>
  263: (<I>struct config *</I> <B>cfg</B>, <I>byte *</I> <B>c</B>) --     find a symbol by name
  264: <P>
  265: <H3>Arguments</H3>
  266: <P>
  267: <DL>
  268: <DT><I>struct config *</I> <B>cfg</B><DD><P>specificed config
  269: <DT><I>byte *</I> <B>c</B><DD><P>symbol name
  270: </DL>
  271: <H3>Description</H3>
  272: <P>This functions searches the symbol table in the config <B>cfg</B> for a symbol of
  273: given name. First it examines the current scope, then the second recent one
  274: and so on until it either finds the symbol and returns a pointer to its
  275: <I>symbol</I> structure or reaches the end of the scope chain and returns <I>NULL</I> to
  276: signify no match.
  277: 
  278: 
  279: <HR><H3>Function</H3>
  280: <P><I>struct symbol *</I>
  281: <B>cf_get_symbol</B>
  282: (<I>byte *</I> <B>c</B>) --     get a symbol by name
  283: <P>
  284: <H3>Arguments</H3>
  285: <P>
  286: <DL>
  287: <DT><I>byte *</I> <B>c</B><DD><P>symbol name
  288: </DL>
  289: <H3>Description</H3>
  290: <P>This functions searches the symbol table of the currently parsed config
  291: (<B>new_config</B>) for a symbol of given name. It returns either the already
  292: existing symbol or a newly allocated undefined (<I>SYM_VOID</I>) symbol if no
  293: existing symbol is found.
  294: 
  295: 
  296: <HR><H3>Function</H3>
  297: <P><I>struct symbol *</I>
  298: <B>cf_define_symbol</B>
  299: (<I>struct symbol *</I> <B>sym</B>, <I>int</I> <B>type</B>, <I>void *</I> <B>def</B>) --     define meaning of a symbol
  300: <P>
  301: <H3>Arguments</H3>
  302: <P>
  303: <DL>
  304: <DT><I>struct symbol *</I> <B>sym</B><DD><P>symbol to be defined
  305: <DT><I>int</I> <B>type</B><DD><P>symbol class to assign
  306: <DT><I>void *</I> <B>def</B><DD><P>class dependent data
  307: </DL>
  308: <H3>Description</H3>
  309: <P>Defines new meaning of a symbol. If the symbol is an undefined
  310: one (<I>SYM_VOID</I>), it's just re-defined to the new type. If it's defined
  311: in different scope, a new symbol in current scope is created and the
  312: meaning is assigned to it. If it's already defined in the current scope,
  313: an error is reported via <B>cf_error()</B>.
  314: <H3>Result</H3>
  315: <P>Pointer to the newly defined symbol. If we are in the top-level
  316: scope, it's the same <B>sym</B> as passed to the function.
  317: 
  318: 
  319: <HR><H3>Function</H3>
  320: <P><I>void</I>
  321: <B>cf_lex_init</B>
  322: (<I>int</I> <B>is_cli</B>, <I>struct config *</I> <B>c</B>) --     initialize the lexer
  323: <P>
  324: <H3>Arguments</H3>
  325: <P>
  326: <DL>
  327: <DT><I>int</I> <B>is_cli</B><DD><P>true if we're going to parse CLI command, false for configuration
  328: <DT><I>struct config *</I> <B>c</B><DD><P>configuration structure
  329: </DL>
  330: <H3>Description</H3>
  331: <P><B>cf_lex_init()</B> initializes the lexical analyzer and prepares it for
  332: parsing of a new input.
  333: 
  334: 
  335: <HR><H3>Function</H3>
  336: <P><I>void</I>
  337: <B>cf_push_scope</B>
  338: (<I>struct symbol *</I> <B>sym</B>) --     enter new scope
  339: <P>
  340: <H3>Arguments</H3>
  341: <P>
  342: <DL>
  343: <DT><I>struct symbol *</I> <B>sym</B><DD><P>symbol representing scope name
  344: </DL>
  345: <H3>Description</H3>
  346: <P>If we want to enter a new scope to process declarations inside
  347: a nested block, we can just call <B>cf_push_scope()</B> to push a new
  348: scope onto the scope stack which will cause all new symbols to be
  349: defined in this scope and all existing symbols to be sought for
  350: in all scopes stored on the stack.
  351: 
  352: 
  353: <HR><H3>Function</H3>
  354: <P><I>void</I>
  355: <B>cf_pop_scope</B>
  356: (<B>void</B>) --     leave a scope
  357: <P>
  358: <H3>Description</H3>
  359: <P>
  360: <P><B>cf_pop_scope()</B> pops the topmost scope from the scope stack,
  361: leaving all its symbols in the symbol table, but making them
  362: invisible to the rest of the config.
  363: 
  364: 
  365: <HR><H3>Function</H3>
  366: <P><I>char *</I>
  367: <B>cf_symbol_class_name</B>
  368: (<I>struct symbol *</I> <B>sym</B>) --     get name of a symbol class
  369: <P>
  370: <H3>Arguments</H3>
  371: <P>
  372: <DL>
  373: <DT><I>struct symbol *</I> <B>sym</B><DD><P>symbol
  374: </DL>
  375: <H3>Description</H3>
  376: <P>This function returns a string representing the class
  377: of the given symbol.
  378: 
  379: <H2><A NAME="ss3.3">3.3</A> <A HREF="prog.html#toc3.3">Parser</A>
  380: </H2>
  381: 
  382: <P>
  383: <P>Both the configuration and CLI commands are analyzed using a syntax
  384: driven parser generated by the <CODE>bison</CODE> tool from a grammar which
  385: is constructed from information gathered from grammar snippets by
  386: the <CODE>gen_parser.m4</CODE> script.
  387: <P>Grammar snippets are files (usually with extension <CODE>.Y</CODE>) contributed
  388: by various BIRD modules in order to provide information about syntax of their
  389: configuration and their CLI commands. Each snipped consists of several
  390: sections, each of them starting with a special keyword: <CODE>CF_HDR</CODE> for
  391: a list of <CODE>#include</CODE> directives needed by the C code, <CODE>CF_DEFINES</CODE>
  392: for a list of C declarations, <CODE>CF_DECLS</CODE> for <CODE>bison</CODE> declarations
  393: including keyword definitions specified as <CODE>CF_KEYWORDS</CODE>, <CODE>CF_GRAMMAR</CODE>
  394: for the grammar rules, <CODE>CF_CODE</CODE> for auxiliary C code and finally
  395: <CODE>CF_END</CODE> at the end of the snippet.
  396: <P>To create references between the snippets, it's possible to define
  397: multi-part rules by utilizing the <CODE>CF_ADDTO</CODE> macro which adds a new
  398: alternative to a multi-part rule.
  399: <P>CLI commands are defined using a <CODE>CF_CLI</CODE> macro. Its parameters are:
  400: the list of keywords determining the command, the list of parameters,
  401: help text for the parameters and help text for the command.
  402: <P>Values of <CODE>enum</CODE> filter types can be defined using <CODE>CF_ENUM</CODE> with
  403: the following parameters: name of filter type, prefix common for all
  404: literals of this type and names of all the possible values.
  405: <P>
  406: <P>
  407: <HR>
  408: <A HREF="prog-4.html">Next</A>
  409: <A HREF="prog-2.html">Previous</A>
  410: <A HREF="prog.html#toc3">Contents</A>
  411: </BODY>
  412: </HTML>

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>