- still to do action,c
authorAndrei Pelinescu-Onciul <andrei@iptel.org>
Thu, 20 Sep 2001 17:17:26 +0000 (17:17 +0000)
committerAndrei Pelinescu-Onciul <andrei@iptel.org>
Thu, 20 Sep 2001 17:17:26 +0000 (17:17 +0000)
Makefile
cfg.y
config.h
error.h [new file with mode: 0644]
msg_parser.h
proxy.c [new file with mode: 0644]
proxy.h [new file with mode: 0644]
route.c
route.h
route_struct.c
route_struct.h

index bcc6368..c433493 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -11,8 +11,12 @@ depends= $(sources:.c=.d)
 
 NAME=sip_router
 
+
 CC=gcc
 CFLAGS=-O2
+LEX=lex
+YACC=bison
+YACC_FLAGS=-d
 # on linux and freebsd keep it empty (e.g. LIBS= )
 # on solaris add -lxnet (e.g. LIBS= -lxnet)
 LIBS=
@@ -23,12 +27,20 @@ MKDEP=gcc -M
 
 #implicit rules
 
+
 %.o:%.c $(ALLDEP)
        $(CC) $(CFLAGS) -c $< -o $@
 
 %.d: %.c
        $(MKDEP) $< >$@
 
+# normal rules
+lex.yy.c: cfg.lex $(ALLDEP)
+       $(LEX) $<
+
+cfg.tab.c: cfg.y
+       $(YACC) $(YACC_FLAGS) $<
+
 $(NAME): $(objs)
        $(CC) $(CFLAGS) $(LIBS) $(objs) -o $(NAME)
 
diff --git a/cfg.y b/cfg.y
index 4845a6f..f02dc82 100644 (file)
--- a/cfg.y
+++ b/cfg.y
@@ -238,7 +238,7 @@ exp_elem:   METHOD EQUAL_T STRING   {$$= mk_elem(   EQUAL_OP, STRING_ST,
        ;
 
 net4:  ipv4 SLASH ipv4 { $$=mk_net($1, $3); } 
-       | ipv4 SLASH NUMBER {   if (($3>32)|($3<1)){
+       | ipv4 SLASH NUMBER {   if (($3>32)|($3<0)){
                                                                yyerror("invalid bit number in netmask");
                                                                $$=0;
                                                        }else{
@@ -402,8 +402,10 @@ yyerror(char* s)
                        column, s);
 }
 
+/*
 int main(int argc, char ** argv)
 {
        if (yyparse()!=0)
                fprintf(stderr, "parsing error\n");
 }
+*/
index 7468097..0ab487d 100644 (file)
--- a/config.h
+++ b/config.h
@@ -21,4 +21,8 @@
 /* default number of child processes started */
 #define CHILD_NO    8
 
+#define RT_NO 10 /* routing tables number */
+
+#define MAX_REC_LEV 100 /* maximum number of recursive calls */
+
 #endif
diff --git a/error.h b/error.h
new file mode 100644 (file)
index 0000000..f83a7c9
--- /dev/null
+++ b/error.h
@@ -0,0 +1,14 @@
+/*
+ * $Id$
+ */
+
+#ifndef error_h
+#define error_h
+
+#define E_OUT_OF_MEM  -2
+#define E_BAD_RE      -3
+#define E_BAD_ADDRESS -4
+#define E_BUG         -5
+
+
+#endif
index 340c057..dbdbfa7 100644 (file)
@@ -64,6 +64,8 @@ struct sip_msg{
        struct msg_start first_line;
        struct via_body via1;
        struct via_body via2;
+       unsigned int src_ip;
+       unsigned int dst_ip;
 };
 
 
diff --git a/proxy.c b/proxy.c
new file mode 100644 (file)
index 0000000..e9a17b8
--- /dev/null
+++ b/proxy.c
@@ -0,0 +1,143 @@
+/*
+ * $Id$
+ *
+ * proxy list & assoc. functions
+ *
+ */
+
+
+#include "proxy.h"
+#include "error.h"
+
+#include <string.h>
+
+
+struct proxy_l* proxies=0;
+
+
+
+/* searches for the proxy named 'name', on port 'port'
+   returns: pointer to proxy_l on success or 0 if not found */ 
+struct proxy_l* find_proxy(char *name, unsigned short port)
+{
+       struct proxy_l* t;
+       for(t=proxies; t; t=t->next)
+               if ((strcasecmp(t->name, name)==0) && (t->port==port))
+                       break;
+       return t;
+}
+
+
+
+/* copies a hostent structure*, returns 0 on success, <0 on error*/
+int hostent_cpy(struct hostent *dst, struct hosten* src)
+{
+       int len, r;
+
+       /* start copying the host entry.. */
+       /* copy h_name */
+       len=strlen(src->h_name)+1;
+       dst->h_name=(char*)malloc(sizeof(char) * len);
+       if (dst->h_name) strncpy(dst->h_name,src->h_name, len);
+       else{
+               ret=E_OUT_OF_MEM;
+               goto error;
+       }
+
+       /* copy h_aliases */
+       for (len=0;src->h_aliases[len];len++);
+       dst->h_aliases=(char**)malloc(sizeof(char*)*(len+1));
+       if (dst->h_aliases==0){
+               ret=E_OUT_OF_MEM;
+               free(dst->h_name);
+               goto error;
+       }
+       memset((void*)dst->h_aliases, 0, sizeof(char*) * (len+1) );
+       for (i=0;i<len;i++){
+               len2=strlen(src->h_aliases[i])+1;
+               dst->.h_aliases[i]=(char*)malloc(sizeof(char)*len2);
+               if (dst->h_aliases==0){
+                       ret=E_OUT_OF_MEM;
+                       free(dst->h_name);
+                       for(r=0; r<i; r++)      free(dst->h_aliases[r]);
+                       free(dst->h_aliases);
+                       goto error;
+               }
+               strncpy(dst->h_aliases[i], src->h_aliases[i], len2);
+       }
+       /* copy h_addr_list */
+       for (len=0;src->h_addr_list[len];len++);
+       dst->h_addr_list=(char**)malloc(sizeof(char*)*(len+1));
+       if (dst->h_addr_list==0){
+               ret=E_OUT_OF_MEM;
+               free(dst->h_name);
+               for(r=0; h_aliases[r]; r++)     free(dst->h_aliases[r]);
+               free h_aliases[r];
+               free(dst->h_aliases);
+               goto error;
+       }
+       memset((void*)dst->.h_addr_list, 0, sizeof(char*) * (len+1) );
+       for (i=0;i<len;i++){
+               dst->h_addr_list[i]=(char*)malloc(sizeof(char)*src->h_length);
+               if (dst->h_addr_list[i]==0){
+                       ret=E_OUT_OF_MEM;
+                       free(dst->h_name);
+                       for(r=0; h_aliases[r]; r++)     free(dst->h_aliases[r]);
+                       free h_aliases[r];
+                       free(dst->h_aliases);
+                       for (r=0; r<i;r++) free(dst->h_addr_list[r]);
+                       free(dst->h_addr_list);
+                       goto error;
+               }
+               memcpy(dst->h_addr_list[i], src->h_addr_list[i], src->h_length);
+       }
+
+       /* copy h_addr_type & length */
+       dst->h_addrtype=src->h_addrtype;
+       dst->host.h_length=src->h_length;
+       /*finished hostent copy */
+       
+       return 0;
+
+error:
+       LOG(L_CRIT, "ERROR: hostent_cpy: memory allocation failure\n");
+       return ret;
+}
+
+
+
+struct proxy_l* add_proxy(char* name, unsigned short port)
+{
+       proxy_l* p;
+       struct hostent he;
+       
+       if ((p=find_proxy(name, port))!=0) return p;
+       p=(struct proxy_l*) malloc(sizeof(struct proxy_l));
+       if (p==0){
+               LOG(L_CRIT, "ERROR: add_proxy: memory allocation failure\n");
+               goto error;
+       }
+       memset(p,0,sizeof(struct_proxy_l));
+       p->name=name;
+       p->port=port;
+       he=gethostbyname(name);
+       if (he==0){
+               LOG(L_CRIT, "ERROR: add_proxy: could not resolve hostname:"
+                                       " \"%s\"\n", name);
+               free(p);
+               goto error;
+       }
+       if (hostent_cpy(&(p->host), he)!=0){
+               free(p);
+               goto error;
+       }
+       p->ok=1;
+       /* add p to the proxy list */
+       p->next=proxies;
+       proxies=p;
+       return p;
+
+error:
+       return 0;
+}
+
diff --git a/proxy.h b/proxy.h
new file mode 100644 (file)
index 0000000..86690ff
--- /dev/null
+++ b/proxy.h
@@ -0,0 +1,32 @@
+/*
+ * $Id$
+ *
+ */
+
+#ifndef proxy_h
+#define proxy_h
+
+#include <netdb.h>
+
+struct proxy_l{
+       struct proxy_l* next;
+       char* name; /* original name */
+       struct hostent host; /* addresses */
+       unsigned short port;
+       unsigned short reserved; /*align*/
+       
+       /* socket ? */
+
+       int addr_idx;   /* crt. addr. idx. */
+       int ok; /* 0 on error */
+       /*statisticis*/
+       int tx;
+       int tx_bytes;
+       int errors;
+};
+
+extern struct proxy_l* proxies;
+
+
+#endif
+
diff --git a/route.c b/route.c
index cf75f49..f5a3f8c 100644 (file)
--- a/route.c
+++ b/route.c
@@ -9,20 +9,25 @@
 #include <regex.h>
 #include <netdb.h>
 #include <string.h>
+#include <sys/socket.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+#include <netdb.h>
 
 #include "route.h"
 #include "cfg_parser.h"
 #include "dprint.h"
 
 /* main routing list */
-struct route_elem* rlist=0;
+struct route_elem* rlist[RT_NO];
 
 
 
-void free_re(struct route_elem* r)
+ void free_re(struct route_elem* r)
 {
        int i;
        if (r){
+               /*
                        regfree(&(r->method));
                        regfree(&(r->uri));
                        
@@ -37,6 +42,7 @@ void free_re(struct route_elem* r)
                                        free(r->host.h_addr_list[i]);
                                free(r->host.h_addr_list);
                        }
+               */
                        free(r);
        }
 }
@@ -82,102 +88,301 @@ void clear_rlist(struct route_elem** rl)
 
 
 
-int add_rule(struct cfg_line* cl, struct route_elem** head)
+/* traverses an expr tree and compiles the REs where necessary) 
+ * returns: 0 for ok, <0 if errors */
+int fix_expr(struct expr* exp)
 {
-       
-       struct route_elem* re;
-       struct hostent * he;
+       regex_t* re;
        int ret;
-       int i,len, len2;
+       
+       if (exp==0){
+               LOG(L_CRIT, "BUG: fix_expr: null pointer\n");
+               return E_BUG;
+       }
+       if (exp->type==EXP_T){
+               switch(exp->op){
+                       case AND_OP:
+                       case OR_OP:
+                                               if ((ret=fix_expr(exp->l.expr))!=0)
+                                                       return ret;
+                                               ret=fix_expr(exp->r.expr);
+                                               break;
+                       case NOT_OP:
+                                               ret=fix_expr(exp->l.expr);
+                                               break;
+                       default:
+                                               LOG(L_CRIT, "BUG: fix_expr: unknown op %d\n",
+                                                               exp->op);
+               }
+       }else if (exp->type==ELEM_T){
+                       if (exp->op==MATCH_OP){
+                               if (exp->subtype==STRING_ST){
+                                       re=(regex_t*)malloc(sizeof(regex_t));
+                                       if (re==0){
+                                               LOG(L_CRIT, "ERROR: fix_expr: memory allocation"
+                                                               " failure\n");
+                                               return E_OUT_OF_MEM;
+                                       }
+                                       if (regcomp(re, (char*) exp->r.param,
+                                                               REG_EXTENDED|REG_NOSUB|REG_ICASE) ){
+                                               LOG(L_CRIT, "ERROR: fix_expr : bad re \"%s\"\n",
+                                                                       (char*) exp->r.param);
+                                               free(re);
+                                               return E_BAD_RE;
+                                       }
+                                       /* replace the string with the re */
+                                       free(exp->r.param);
+                                       exp->r.param=re;
+                                       exp->subtype=RE_ST;
+                               }else if (exp->subtype!=RE_ST){
+                                       LOG(L_CRIT, "BUG: fix_expr : invalid type for match\n");
+                                       return E_BUG;
+                               }
+                       }
+                       ret=0;
+       }
+       return ret;
+}
 
 
-       re=init_re();
-       if (re==0) return E_OUT_OF_MEM;
 
-       if (regcomp(&(re->method), cl->method, REG_EXTENDED|REG_NOSUB|REG_ICASE)){
-               LOG(L_CRIT, "ERROR: add_rule: bad re \"%s\"\n", cl->method);
-               ret=E_BAD_RE;
-               goto error;
-       }
-       if (regcomp(&(re->uri), cl->uri, REG_EXTENDED|REG_NOSUB|REG_ICASE) ){
-               LOG(L_CRIT, "ERROR: add_rule: bad re \"%s\"\n", cl->uri);
-               ret=E_BAD_RE;
-               goto error;
+/* adds the proxies in the proxy list & resolves the hostnames */
+int fix_actions(struct action* a)
+{
+       struct action *t;
+       struct proxy* p;
+       char *tmp;
+       
+       for(t=a; t!=0; t=t->next){
+               switch(t->type){
+                       case FORWARD_T:
+                       case SEND_T:
+                                       switch(t->p1_type){
+                                               case NUMBER_ST:
+                                                       tmp=strdup(inet_ntoa(
+                                                                               *(struct in_addr*)&t->p1.number));
+                                                       if (tmp==0){
+                                                               LOG(L_CRIT, "ERROR: fix_actions:"
+                                                                               "memory allocation failure\n");
+                                                               return E_OUT_OF_MEM;
+                                                       }
+                                                       t->p1_type=STRING_ST;
+                                                       t->p1.string=tmp;
+                                                       /* no break */
+                                               case STRING_ST:
+                                                       p=add_proxy(t->p1.string, t->p2.number);
+                                                       if (p==0) return E_BAD_ADDRESS;
+                                                       t->p1.data=p;
+                                                       t->p1_type=PROXY_ST;
+                                                       break;
+                                               default:
+                                                       LOG(L_CRIT, "BUG: fix_actions: invalid type"
+                                                                       " (should be string or number)\n");
+                                                       return E_BUG;
+                                       }
+                                       break;
+               }
        }
+       return 0;
+}
+
 
+
+/* eval_elem helping function, returns str op param */
+int comp_str(char* str, void* param, int op, int subtype)
+{
+       int ret;
        
-       he=gethostbyname(cl->address);
-       if (he==0){
-               LOG(L_CRIT, "ERROR: add_rule: cannot resolve \"%s\"\n", cl->address);
-               ret=E_BAD_ADDRESS;
+       ret=-1;
+       if (op==EQUAL_OP){
+               if (subtype!=STRING_ST){
+                       LOG(L_CRIT, "BUG: comp_str: bad type %d, "
+                                       "string expected\n", subtype);
+                       goto error;
+               }
+               ret=(strcasecmp(str, (char*)param)==0);
+       }else if (op==MATCH_OP){
+               if (subtype!=RE_ST){
+                       LOG(L_CRIT, "BUG: comp_str: bad type %d, "
+                                       " RE expected\n", subtype);
+                       goto error;
+               }
+               ret=(regexec((regex_t*)param, str, 0, 0, 0)==0);
+       }else{
+               LOG(L_CRIT, "BUG: comp_str: unknown op %d\n", op);
                goto error;
        }
+       return ret;
        
-       /* start copying the host entry.. */
-       /* copy h_name */
-       len=strlen(he->h_name)+1;
-       re->host.h_name=(char*)malloc(sizeof(char) * len);
-       if (re->host.h_name) strncpy(re->host.h_name, he->h_name, len);
-       else{
-               ret=E_OUT_OF_MEM;
-               goto error;
+error:
+       return -1;
+}
+
+
+
+/* eval_elem helping function, returns a op param */
+int comp_ip(unsigned a, void* param, int op, int subtype)
+{
+       struct hostent* he;
+       char ** h;
+       int ret;
+
+       ret=-1;
+       switch(subtype){
+               case NET_ST:
+                       ret=(a&((struct net*)param)->mask)==((struct net*)param)->ip;
+                       break;
+               case STRING_ST:
+                       /* 1: compare with ip2str*/
+                       ret=comp_str(inet_ntoa(*(struct in_addr*)&a), param, op,
+                                               subtype);
+                       if (ret==1) break;
+                       /* 2: (slow) rev dns the address
+                        * and compare with all the aliases */
+                       he=gethostbyaddr(&a, sizeof(a), AF_INET);
+                       if (he==0){
+                               LOG(L_DBG, "comp_ip: could not rev_resolve %x\n", a);
+                               ret=0;
+                       }else{
+                               /*  compare with primayry host name */
+                               ret=comp_str(he->h_name, param, op, subtype);
+                               /* compare with all the aliases */
+                               for(h=he->h_aliases; (ret!=1) && (*h); h++){
+                                       ret=comp_str(*h, param, op, subtype);
+                               }
+                       }
+                       break;
+               default:
+                       LOG(L_CRIT, "BUG: comp_ip: invalid type for "
+                                               " src_ip or dst_ip (%d)\n", subtype);
+                       ret=-1;
        }
+       return ret;
+       
+error:
+       return -1;
+}
+
 
-       /* copy h_aliases */
-       for (len=0;he->h_aliases[len];len++);
-       re->host.h_aliases=(char**)malloc(sizeof(char*)*(len+1));
-       if (re->host.h_aliases==0){
-               ret=E_OUT_OF_MEM;
+
+/* returns: 0/1 (false/true) or -1 on error */
+int eval_elem(struct expr* e, struct sip_msg* msg)
+{
+
+       int ret;
+       
+       if (e->type!=ELEM_T){
+               LOG(L_CRIT," BUG: eval_elem: invalid type\n");
                goto error;
        }
-       memset((void*)re->host.h_aliases, 0, sizeof(char*) * (len+1) );
-       for (i=0;i<len;i++){
-               len2=strlen(he->h_aliases[i])+1;
-               re->host.h_aliases[i]=(char*)malloc(sizeof(char)*len2);
-               if (re->host.h_aliases==0){
-                       ret=E_OUT_OF_MEM;
-                       goto error;
-               }
-               strncpy(re->host.h_aliases[i], he->h_aliases[i], len2);
+       switch(e->l.operand){
+               case METHOD_O:
+                               ret=comp_str(msg->first_line.u.request.method, e->r.param,
+                                                               e->op, e->subtype);
+                               break;
+               case URI_O:
+                               ret=comp_str(msg->first_line.u.request.uri, e->r.param,
+                                                               e->op, e->subtype);
+                               break;
+               case SRCIP_O:
+                               ret=comp_ip(msg->src_ip, e->r.param, e->op, e->subtype);
+                               break;
+               case DSTIP_O:
+                               ret=comp_ip(msg->dst_ip, e->r.param, e->op, e->subtype);
+                               break;
+               case DEFAULT_O:
+                               ret=1;
+                               break;
+               default:
+                               LOG(L_CRIT, "BUG: eval_elem: invalid operand %d\n",
+                                                       e->l.operand);
        }
-       /* copy h_addr_list */
-       for (len=0;he->h_addr_list[len];len++);
-       re->host.h_addr_list=(char**)malloc(sizeof(char*)*(len+1));
-       if (re->host.h_addr_list==0){
-               ret=E_OUT_OF_MEM;
-               goto error;
+       return ret;
+error:
+       return -1;
+}
+
+
+
+int eval_expr(struct expr* e, struct sip_msg* msg)
+{
+       static int rec_lev=0;
+       int ret;
+       
+       rec_lev++;
+       if (rec_lev>MAX_REC_LEV){
+               LOG(L_CRIT, "ERROR: eval_expr: too many expressions (%d)\n",
+                               rec_lev);
+               ret=-1;
+               goto skip;
        }
-       memset((void*)re->host.h_addr_list, 0, sizeof(char*) * (len+1) );
-       for (i=0;i<len;i++){
-               re->host.h_addr_list[i]=(char*)malloc(sizeof(char)*he->h_length);
-               if (re->host.h_addr_list[i]==0){
-                       ret=E_OUT_OF_MEM;
-                       goto error;
+       
+       if (e->type==ELEM_T){
+               ret=eval_elem(e, msg);
+       }else if (e->type==EXP_T){
+               switch(e->op){
+                       case AND_OP:
+                               ret=eval_expr(e->l.expr, msg);
+                               /* if error or false stop evaluating the rest */
+                               if (ret!=1) break;
+                               ret=eval_expr(e->r.expr, msg); /*ret1 is 1*/
+                               break;
+                       case OR_OP:
+                               ret=eval_expr(e->l.expr, msg);
+                               /* if true or error stop evaluating the rest */
+                               if (ret!=0) break;
+                               ret=eval_expr(e->r.expr, msg); /* ret1 is 0 */
+                               break;
+                       case NOT_OP:
+                               ret=eval_expr(e->l.expr, msg);
+                               if (ret<0) break;
+                               ret= ! ret;
+                               break;
+                       default:
+                               LOG(L_CRIT, "BUG: eval_expr: unknown op %d\n", e->op);
+                               ret=-1;
                }
-               memcpy(re->host.h_addr_list[i], he->h_addr_list[i], he->h_length);
+       }else{
+               LOG(L_CRIT, "BUG: eval_expr: unknown type %d\n", e->type);
+               ret=-1;
        }
 
-       /* copy h_addr_type & length */
-       re->host.h_addrtype=he->h_addrtype;
-       re->host.h_length=he->h_length;
-       /*finished hostent copy */
+skip:
+       rec_lev--;
+       return ret;
+}
+
+
+
 
+int add_rule(struct expr* e, struct action* a, struct route_elem** head)
+{
        
-       re->port=cl->port;
-       re->current_addr_idx=0;
-       re->ok=1;
+       struct route_elem* re;
+       struct hostent * he;
+       int ret;
+       int i,len, len2;
 
+       re=init_re();
+       if (re==0) return E_OUT_OF_MEM;
+       LOG(L_DBG, "add_rule: fixing expr...\n");
+       if ((ret=fix_expr(e))!=0) goto error;
+       LOG(L_DBG, "add_rule: fixing actions...\n");
+       if ((ret=fix_action(a))!=0) goto error;
+       re->condition=e;
+       re->actions=a;
+       
        push(re,head);
        return 0;
        
 error:
-               free_re(re);
-               return ret;
+       free_re(re);
+       return ret;
 }
 
 
 
-struct route_elem* route_match(char* method, char* uri, struct route_elem** rl)
+struct route_elem* route_match(struct sip_msg* msg, struct route_elem** rl)
 {
        struct route_elem* t;
        if (*rl==0){
@@ -185,13 +390,7 @@ struct route_elem* route_match(char* method, char* uri, struct route_elem** rl)
                return 0;
        }
        for (t=*rl; t; t=t->next){
-               if (regexec(&(t->method), method, 0, 0, 0)==0){
-                       /* we have a method mach !!! */
-                       if (regexec(&(t->uri), uri, 0, 0, 0)==0){
-                               /* we have a full match */
-                               return t;
-                       }
-               }
+               if (eval_expr(t->condition, msg)==1) return t;
        }
        /* no match :( */
        return 0;
@@ -206,26 +405,17 @@ void print_rl()
        int i,j;
 
        if (rlist==0){
-               LOG(L_INFO, "the routing table is empty\n");
+               printf("the routing table is empty\n");
                return;
        }
        
-       for (t=rlist,i=0; t; i++, t=t->next){
-               LOG(L_INFO, "%2d.to=%s ; route ok=%d\n", i,
-                               t->host.h_name, t->ok);
-               LOG(L_INFO, "   ips: ");
-               for (j=0; t->host.h_addr_list[j]; j++){
-                       LOG(L_INFO, "%d.%d.%d.%d ", 
-                               (unsigned char) t->host.h_addr_list[j][0],
-                               (unsigned char) t->host.h_addr_list[j][1],
-                           (unsigned char) t->host.h_addr_list[j][2],
-                               (unsigned char) t->host.h_addr_list[j][3]
-                                 );
-               }
-               LOG(L_INFO, "\n");
-               LOG(L_INFO, "   port:%d\n", (unsigned short)t->port);
-               LOG(L_INFO, "   Statistics: tx=%d, errors=%d, tx_bytes=%d, idx=%d\n",
-                               t->tx, t->errors, t->tx_bytes, t->current_addr_idx);
+       for (t=rlist[0],i=0; t; i++, t=t->next){
+               printf("%2d.condition: ");
+               print_expr(t->condition);
+               printf("\n  -> ");
+               print_action(t->actions);
+               printf("\n    Statistics: tx=%d, errors=%d, tx_bytes=%d\n",
+                               t->tx, t->errors, t->tx_bytes);
        }
 
 }
diff --git a/route.h b/route.h
index 980876d..966031a 100644 (file)
--- a/route.h
+++ b/route.h
@@ -9,20 +9,21 @@
 #include <regex.h>
 #include <netdb.h>
 
-#include "cfg_parser.h"
+#include "config.h"
+#include "error.h"
+#include "route_struct.h"
+#include "msg_parser.h"
+
+/*#include "cfg_parser.h" */
+
 
-#define E_OUT_OF_MEM  -2
-#define E_BAD_RE      -3
-#define E_BAD_ADDRESS -4
 
 struct route_elem{
        struct route_elem* next;
-       regex_t method;
-       regex_t uri;
-       struct hostent host;
-       int current_addr_idx;
-       short int port;
-       short int reserved; /* pad */
+
+       struct expr* condition;
+       struct action* actions;
+
        int ok; /* set to 0 if an error was found sendig a pkt*/
        /*counters*/
        int errors;
@@ -31,15 +32,16 @@ struct route_elem{
 };
 
 /* main "routing table" */
-extern struct route_elem* rlist;
+extern struct route_elem* rlist[RT_NO];
 
 
 void free_re(struct route_elem* re);
 struct route_elem* init_re();
 void push(struct route_elem* re, struct route_elem** head);
 void clear_rlist(struct route_elem** rl);
-int add_rule(struct cfg_line* cl, struct route_elem** head);
-struct route_elem* route_match(char* method, char* uri, struct route_elem** rl);void print_rl();
+int add_rule(struct expr* e, struct action* a, struct route_elem** head);
+struct route_elem* route_match(struct sip_msg* msg,struct route_elem** rl);
+void print_rl();
 
 
 
index c06d879..0bbdb0b 100644 (file)
@@ -217,6 +217,12 @@ void print_action(struct action* a)
                        case ERROR_T:
                                        printf("error(");
                                        break;
+                       case ROUTE_T:
+                                       printf("route(");
+                                       break;
+                       case EXEC_T:
+                                       printf("exec(");
+                                       break;
                        default:
                                        printf("UNKNOWN(");
                }
@@ -227,6 +233,9 @@ void print_action(struct action* a)
                        case NUMBER_ST:
                                        printf("%d",t->p1.number);
                                        break;
+                       case IP_ST:
+                                       print_ip(t->p1.data);
+                                       break;
                        default:
                                        printf("type<%d>", t->p1_type);
                }
index 2f9a417..1f8fe8f 100644 (file)
@@ -9,10 +9,10 @@
 enum { EXP_T=1, ELEM_T };
 enum { AND_OP=1, OR_OP, NOT_OP };
 enum { EQUAL_OP=10, MATCH_OP };
-enum { METHOD_O=1, URI_O, SRCIP_O, DSTIP_O };
+enum { METHOD_O=1, URI_O, SRCIP_O, DSTIP_O, DEFAULT_O };
 
 enum { FORWARD_T=1, SEND_T, DROP_T, LOG_T, ERROR_T, ROUTE_T, EXEC_T};
-enum { NOSUBTYPE=0, STRING_ST, NET_ST, NUMBER_ST, IP_ST };
+enum { NOSUBTYPE=0, STRING_ST, NET_ST, NUMBER_ST, IP_ST, RE_ST, PROXY_ST };
 
        
 struct expr{