Module: sip-router
Branch: ser_core_cvs
Commit: f9276a5b4875a1e3ecda29d50013725642cc8af2
URL:
http://git.sip-router.org/cgi-bin/gitweb.cgi/sip-router/?a=commit;h=f9276a5…
Author: Andrei Pelinescu-Onciul <andrei(a)iptel.org>
Committer: Andrei Pelinescu-Onciul <andrei(a)iptel.org>
Date: Fri Jul 17 13:37:11 2009 +0000
core: config parser listen if names fix
If no quotes were used in listen=x, it was assumed that x was an
ip or a valid hostname (each domain part starts with a letter,
numbers and '_' are not allowed as first chars). However this
assumption failed when interface names were used, e.g. eth0.1 is a
valid interface name, but listen=eth0.1 resulted in error (it
worked only if quotes were used, e.g. listen="eth0.1").
---
cfg.lex | 41 +++++++++++++++++++++++++++++------------
cfg.y | 38 +++++++++++++++++++++++++++++++++++---
2 files changed, 64 insertions(+), 15 deletions(-)
diff --git a/cfg.lex b/cfg.lex
index 13225ab..2c9ab8f 100644
--- a/cfg.lex
+++ b/cfg.lex
@@ -112,6 +112,7 @@
int line=1;
int column=1;
int startcolumn=1;
+ char* yy_number_str=0; /* str correspondent for the current NUMBER token */
static char* addchar(struct str_buf *, char);
static char* addstr(struct str_buf *, char*, int);
@@ -403,6 +404,7 @@ LETTER [a-zA-Z]
DIGIT [0-9]
ALPHANUM {LETTER}|{DIGIT}|[_]
ID {LETTER}{ALPHANUM}*
+NUM_ID {ALPHANUM}+
HEX [0-9a-fA-F]
HEXNUMBER 0x{HEX}+
OCTNUMBER 0[0-7]+
@@ -784,10 +786,14 @@ EAT_ABLE [\ \t\b\r]
<SELECT>{DOT} { count(); return DOT; }
<SELECT>{LBRACK} { count(); return LBRACK; }
<SELECT>{RBRACK} { count(); return RBRACK; }
-<SELECT>{DECNUMBER} { count(); yylval.intval=atoi(yytext);return NUMBER; }
-<SELECT>{HEXNUMBER} { count(); yylval.intval=(int)strtol(yytext, 0, 16); return
NUMBER; }
-<SELECT>{OCTNUMBER} { count(); yylval.intval=(int)strtol(yytext, 0, 8); return
NUMBER; }
-<SELECT>{BINNUMBER} { count(); yylval.intval=(int)strtol(yytext, 0, 2); return
NUMBER; }
+<SELECT>{DECNUMBER} { count(); yylval.intval=atoi(yytext);
+ yy_number_str=yytext; return NUMBER; }
+<SELECT>{HEXNUMBER} { count(); yylval.intval=(int)strtol(yytext, 0, 16);
+ yy_number_str=yytext; return NUMBER; }
+<SELECT>{OCTNUMBER} { count(); yylval.intval=(int)strtol(yytext, 0, 8);
+ yy_number_str=yytext; return NUMBER; }
+<SELECT>{BINNUMBER} { count(); yylval.intval=(int)strtol(yytext, 0, 2);
+ yy_number_str=yytext; return NUMBER; }
<INITIAL>{ATTR_MARK} { count(); state = ATTR_S; BEGIN(ATTR); return ATTR_MARK;
}
@@ -804,7 +810,8 @@ EAT_ABLE [\ \t\b\r]
<ATTR>{LBRACK} { count(); return LBRACK; }
<ATTR>{RBRACK} { count(); return RBRACK; }
<ATTR>{STAR} { count(); return STAR; }
-<ATTR>{DECNUMBER} { count(); yylval.intval=atoi(yytext);return NUMBER; }
+<ATTR>{DECNUMBER} { count(); yylval.intval=atoi(yytext);
+ yy_number_str=yytext; return NUMBER; }
<ATTR>{ID} { count(); addstr(&s_buf, yytext, yyleng);
yylval.strval=s_buf.s;
memset(&s_buf, 0, sizeof(s_buf));
@@ -814,26 +821,32 @@ EAT_ABLE [\ \t\b\r]
}
<INITIAL>{IPV6ADDR} { count(); yylval.strval=yytext; return IPV6ADDR; }
-<INITIAL>{DECNUMBER} { count(); yylval.intval=atoi(yytext);return NUMBER; }
+<INITIAL>{DECNUMBER} { count(); yylval.intval=atoi(yytext);
+ yy_number_str=yytext; return NUMBER; }
<INITIAL>{HEXNUMBER} { count(); yylval.intval=(int)strtol(yytext, 0, 16);
- return NUMBER; }
+ yy_number_str=yytext; return NUMBER; }
<INITIAL>{OCTNUMBER} { count(); yylval.intval=(int)strtol(yytext, 0, 8);
return NUMBER; }
-<INITIAL>{BINNUMBER} { count(); yylval.intval=(int)strtol(yytext, 0, 2); return
NUMBER; }
-<INITIAL>{YES} { count(); yylval.intval=1; return NUMBER; }
-<INITIAL>{NO} { count(); yylval.intval=0; return NUMBER; }
+<INITIAL>{BINNUMBER} { count(); yylval.intval=(int)strtol(yytext, 0, 2);
+ yy_number_str=yytext; return NUMBER; }
+<INITIAL>{YES} { count(); yylval.intval=1;
+ yy_number_str=yytext; return NUMBER; }
+<INITIAL>{NO} { count(); yylval.intval=0;
+ yy_number_str=yytext; return NUMBER; }
<INITIAL>{TCP} { count(); return TCP; }
<INITIAL>{UDP} { count(); return UDP; }
<INITIAL>{TLS} { count(); return TLS; }
<INITIAL>{SCTP} { count(); return SCTP; }
-<INITIAL>{INET} { count(); yylval.intval=AF_INET; return NUMBER; }
+<INITIAL>{INET} { count(); yylval.intval=AF_INET;
+ yy_number_str=yytext; return NUMBER; }
<INITIAL>{INET6} { count();
#ifdef USE_IPV6
yylval.intval=AF_INET6;
#else
yylval.intval=-1; /* no match*/
#endif
- return NUMBER; }
+ yy_number_str=yytext;
+ return NUMBER; }
<INITIAL>{SSLv23} { count(); yylval.strval=yytext; return SSLv23; }
<INITIAL>{SSLv2} { count(); yylval.strval=yytext; return SSLv2; }
<INITIAL>{SSLv3} { count(); yylval.strval=yytext; return SSLv3; }
@@ -907,6 +920,10 @@ EAT_ABLE [\ \t\b\r]
yylval.strval=s_buf.s;
memset(&s_buf, 0, sizeof(s_buf));
return ID; }
+<INITIAL>{NUM_ID} { count(); addstr(&s_buf, yytext, yyleng);
+ yylval.strval=s_buf.s;
+ memset(&s_buf, 0, sizeof(s_buf));
+ return NUM_ID; }
<SELECT>. { unput(yytext[0]); state = INITIAL_S; BEGIN(INITIAL); } /*
Rescan the token in INITIAL state */
diff --git a/cfg.y b/cfg.y
index 389b0cd..85eb9f7 100644
--- a/cfg.y
+++ b/cfg.y
@@ -180,6 +180,9 @@
extern int yylex();
+/* safer then using yytext which can be array or pointer */
+extern char* yy_number_str;
+
static void yyerror(char* s);
static char* tmp;
static int i_tmp;
@@ -477,6 +480,7 @@ static void free_socket_id_lst(struct socket_id* i);
/* values */
%token <intval> NUMBER
%token <strval> ID
+%token <strval> NUM_ID
%token <strval> STRING
%token <strval> IPV6ADDR
@@ -501,7 +505,7 @@ static void free_socket_id_lst(struct socket_id* i);
%type <action> action actions cmd fcmd if_cmd stm exp_stm assign_action
%type <ipaddr> ipv4 ipv6 ipv6addr ip
%type <ipnet> ipnet
-%type <strval> host
+%type <strval> host host_or_if host_if_id
%type <strval> listen_id
%type <name_l> listen_id_lst
%type <name_l> listen_id2
@@ -582,7 +586,7 @@ listen_id:
strncpy($$, $1, strlen($1)+1);
}
}
- | host {
+ | host_or_if {
if ($1){
$$=pkg_malloc(strlen($1)+1);
if ($$==0) {
@@ -1920,10 +1924,37 @@ host:
}
pkg_free($1);
}
- pkg_free($3);
}
| host DOT error { $$=0; pkg_free($1); yyerror("invalid hostname"); }
;
+
+host_if_id: ID
+ | NUM_ID
+ | NUMBER { $$=yy_number_str /* text version */; }
+ ;
+
+host_or_if:
+ host_if_id { $$=$1; }
+ | host_or_if host_sep host_if_id {
+ if ($1){
+ $$=(char*)pkg_malloc(strlen($1)+1+strlen($3)+1);
+ if ($$==0) {
+ LOG(L_CRIT, "ERROR: cfg. parser: memory allocation"
+ " failure while parsing host/interface name\n");
+ } else {
+ memcpy($$, $1, strlen($1));
+ $$[strlen($1)]=*$2;
+ memcpy($$+strlen($1)+1, $3, strlen($3));
+ $$[strlen($1)+1+strlen($3)]=0;
+ }
+ pkg_free($1);
+ }
+ }
+ | host_or_if host_sep error { $$=0; pkg_free($1);
+ yyerror("invalid host or interface name"); }
+ ;
+
+
/* filtered cmd */
fcmd:
cmd {
@@ -2561,6 +2592,7 @@ func_param:
extern int line;
extern int column;
extern int startcolumn;
+
static void warn(char* s)
{
LOG(L_WARN, "cfg. warning: (%d,%d-%d): %s\n", line, startcolumn,