version 0.9.6
[rofl0r-htun.git] / src / parse.l
blobeea0c649a087c764c506f21326e79ced0f3a0ec6
1 /* -------------------------------------------------------------------------
2  * parse.l - htun config parser
3  * Copyright (C) 2002 Moshe Jacobson <moshe@runslinux.net>, 
4  *                    Ola Nordström <ola@triblock.com>
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19  * -------------------------------------------------------------------------
20  */
21 /* $Id: parse.l,v 2.24 2003/01/24 01:20:50 jehsom Exp $ */
24 #include <stdio.h>
25 #include "common.h"
26 #include "y.tab.h" /* the generated yacc file */
28 extern config_data_t *config;
29 extern char *linehead, *textpoint;
30 int lineno = 1;
33 comment [\t ]*[#|;].*\n
34 space   [\t ]+
35 ip      (([0-2]){0,1}([0-9]){1,2}\.){3}([0-2]){0,1}([0-9]){1,2}
36 port    [1-9][0-9]{0,4}
37 file    ((\/)|(\.\/))[a-zA-Z0-9\.\/]+
38 range   [0-9]*
39 text    [a-zA-Z0-9\.\/]*
40 type    (server|client)
41 num     [1-9][0-9]*
42 ans     (yes|no)
43 user    [^\n\t :]+
44 pass    [^ \t\n]*
47     /* now we get the builtin push/pop state */
48 %option stack
49 %option yylineno
50 %s PRE_CLI PRE_SRV PRE_OPTIONS OPT
51 %x SRV CLI IP_S NUM_S ANS_S PORT_S FILE_S IPR IFN RDH USER_S PASS_S
54 <*>\n               { linehead = yytext+1; } REJECT;
55 <*>.                { textpoint = yytext; if(!linehead) linehead = textpoint; } REJECT;
56 <*>{space}          { return SPACE; }
57 <*>{comment}        { return NEWLINE; }
58 <*>(\n)             { return NEWLINE; }
59                      
60 <PRE_CLI>(\{)                   { yy_push_state(CLI); return LEFT_BRACE;}
61 <PRE_SRV>(\{)                   { yy_push_state(SRV); return LEFT_BRACE;}
62 <PRE_OPTIONS>(\{)               { yy_push_state(OPT); return LEFT_BRACE;}
64 <ANS_S>{ans}                    { yy_pop_state(); yylval.name = yytext; return ANSWER; }
66 <IP_S>{text}                    { yy_pop_state(); yylval.name = yytext; return IP; }
68 <NUM_S>{num}                    { yy_pop_state(); yylval.name = yytext; return NUM; }
70 <PORT_S>{port}                  { yy_pop_state(); yylval.name = yytext; return PORT; }
72 <FILE_S>{file}                  { yy_pop_state(); yylval.name = yytext; return FNAME; }
74 <IFN>{text}                     { yy_pop_state(); yylval.name = yytext; return IFNAME; }
76 <RDH>{text}                     { yy_pop_state(); yylval.name = yytext; return TEXT; }
78 <IPR>{ip}\/{range}              { yy_pop_state(); yylval.name = yytext; return RANGE; }
80 <USER_S>{user}                  { yy_pop_state(); yylval.name = yytext; return USER; }
82 <PASS_S>{pass}                  { yy_pop_state(); yylval.name = yytext; return PASS; }
84 <CLI>{ 
85     (\})                       { BEGIN 0; return RIGHT_BRACE; }
86     (do_routing)               { yy_push_state(ANS_S); return DO_ROUTING; }
87     (protocol)                 { yy_push_state(NUM_S); return PROTOCOL; }
89     (proxy_ip)                 { yy_push_state(IP_S); return PROXY_IP; }
90     (proxy_port)               { yy_push_state(PORT_S); return PROXY_PORT; }
91     (proxy_user)               { yy_push_state(USER_S); return PROXY_USER; }
92     (proxy_pass)               { yy_push_state(PASS_S); return PROXY_PASS; }
94     (server_ip)                { yy_push_state(IP_S); return SERVER_IP; }
95     (server_port)              { yy_push_state(PORT_S); return SERVER_PORT; }
96     (secondary_server_port)    { yy_push_state(PORT_S); return SERVER_PORT_2; }
98     (if_name)                  { yy_push_state(IFN); return ETHDEV; }
99     (iprange)                  { yy_push_state(IPR); return IP_RANGE; }
101     (connect_tries)            { yy_push_state(NUM_S); return CON_T; }
102     (reconnect_tries)          { yy_push_state(NUM_S); return RECON_T; }
103     (reconnect_sleep_sec)      { yy_push_state(NUM_S); return RECON_SLEEP; }
105     (channel_2_idle_allow)     { yy_push_state(NUM_S); return CHAN2_IDLE; }
106     (min_poll_interval_msec)   { yy_push_state(NUM_S); return MIN_POLL_INTERVAL_MSEC; }
107     (max_poll_interval)        { yy_push_state(NUM_S); return MAX_POLL_INTERVAL; }
108     (poll_backoff_rate)        { yy_push_state(NUM_S); return POLL_BACKOFF_RATE; }
109     (ack_wait)                 { yy_push_state(NUM_S); return ACKWAIT; }
112 <SRV>{
113     (\})                       { BEGIN 0; return RIGHT_BRACE; }
114     (iprange)                  { yy_push_state(IPR); return IP_RANGE; }
116     /* Aliases. It's obvious it's a server port when it's in the server * section! */
117     ((server_)?port)           { yy_push_state(PORT_S); return SERVER_PORT; }
118     
119     /* Aliases. It's obvious it's a server port when it's in the server * section! */
120     (secondary_(server_)?port) { yy_push_state(PORT_S); return SERVER_PORT_2; }
122     (max_clients)              { yy_push_state(NUM_S); return MAX_CLIENTS; }
123     (redirect_host)            { yy_push_state(RDH); return REDIR_HOST; }
124     (redirect_port)            { yy_push_state(PORT_S); return REDIR_PORT; }
126     (max_pending)              { yy_push_state(NUM_S); return MAX_PENDING; }
127     (idle_disconnect)          { yy_push_state(NUM_S); return IDLE_DISCONNECT; }
128     (clidata_timeout)          { yy_push_state(NUM_S); return CLIDATA_TIMEOUT; }
129     (min_nack_delay)           { yy_push_state(NUM_S); return MIN_NACK_DELAY; }
130     (packet_count_threshold)   { yy_push_state(NUM_S); return PKT_COUNT_THRESHOLD; }
131     (packet_max_interval)      { yy_push_state(NUM_S); return PKT_MAX_INTERVAL; }
132     (max_response_delay)       { yy_push_state(NUM_S); return MAX_RESPONSE_DELAY; }
135 <OPT>{
136     (daemonize)                { yy_push_state(ANS_S); return DEMONIZE; }
137     (debug)                    { yy_push_state(ANS_S); return TEST; }
138     (tunfile)                  { yy_push_state(FILE_S); return TUN_FILE; }
139     (logfile)                  { yy_push_state(FILE_S); return LOG_FILE; }
140     (\})                       { BEGIN 0; yylval.name = ""; return RIGHT_BRACE; }
143 (client)                        { yy_push_state(PRE_CLI); return CLIENT; }
144 (server)                        { yy_push_state(PRE_SRV); return SERVER; }
145 (options)                       { yy_push_state(PRE_OPTIONS); return OPTION; }
147 <*>(.)                          { return ERROR; }
151 config_data_t *read_config( const char *configfile )
153     FILE *fin = fopen( configfile, "r" );
155     if( fin == NULL ) {
156         fprintf(stderr, "Unable to open config file \"%s\"\n", configfile );
157         return NULL;
158     }
160     yyin = fin;
162     if((config = calloc(1, sizeof(config_data_t))) == NULL) {
163         fprintf(stderr, "Fatal: unable to malloc() space for config data.\n");
164         return NULL;
165     }
166     config->is_server = -1;
168     strncpy(config->cfgfile, configfile, PATH_MAX);
169     config->cfgfile[PATH_MAX-1] = '\0';
171     yyparse();
173     if( config->is_server == -1 ) {
174         fprintf(stderr, "Error \"server\" or \"client\" not declared in config file.\n");
175         exit(EXIT_FAILURE);
176     }
178     return config;