( merged the 0.8.3.4 changes back in 0.8.3.2)
[sip-router] / route.c
1 /*
2  * $Id$
3  *
4  * SIP routing engine
5  *
6  */
7  
8 #include <stdlib.h>
9 #include <sys/types.h>
10 #include <regex.h>
11 #include <netdb.h>
12 #include <string.h>
13 #include <sys/socket.h>
14 #include <netinet/in.h>
15 #include <arpa/inet.h>
16 #include <netdb.h>
17
18 #include "route.h"
19 #include "dprint.h"
20 #include "proxy.h"
21 #include "action.h"
22 #include "sr_module.h"
23
24 #ifdef DEBUG_DMALLOC
25 #include <dmalloc.h>
26 #endif
27
28 /* main routing script table  */
29 struct action* rlist[RT_NO];
30
31
32 static int fix_actions(struct action* a); /*fwd declaration*/
33
34
35 /* traverses an expr tree and compiles the REs where necessary) 
36  * returns: 0 for ok, <0 if errors */
37 static int fix_expr(struct expr* exp)
38 {
39         regex_t* re;
40         int ret;
41         
42         ret=E_BUG;
43         if (exp==0){
44                 LOG(L_CRIT, "BUG: fix_expr: null pointer\n");
45                 return E_BUG;
46         }
47         if (exp->type==EXP_T){
48                 switch(exp->op){
49                         case AND_OP:
50                         case OR_OP:
51                                                 if ((ret=fix_expr(exp->l.expr))!=0)
52                                                         return ret;
53                                                 ret=fix_expr(exp->r.expr);
54                                                 break;
55                         case NOT_OP:
56                                                 ret=fix_expr(exp->l.expr);
57                                                 break;
58                         default:
59                                                 LOG(L_CRIT, "BUG: fix_expr: unknown op %d\n",
60                                                                 exp->op);
61                 }
62         }else if (exp->type==ELEM_T){
63                         if (exp->op==MATCH_OP){
64                                 if (exp->subtype==STRING_ST){
65                                         re=(regex_t*)malloc(sizeof(regex_t));
66                                         if (re==0){
67                                                 LOG(L_CRIT, "ERROR: fix_expr: memory allocation"
68                                                                 " failure\n");
69                                                 return E_OUT_OF_MEM;
70                                         }
71                                         if (regcomp(re, (char*) exp->r.param,
72                                                                 REG_EXTENDED|REG_NOSUB|REG_ICASE) ){
73                                                 LOG(L_CRIT, "ERROR: fix_expr : bad re \"%s\"\n",
74                                                                         (char*) exp->r.param);
75                                                 free(re);
76                                                 return E_BAD_RE;
77                                         }
78                                         /* replace the string with the re */
79                                         free(exp->r.param);
80                                         exp->r.param=re;
81                                         exp->subtype=RE_ST;
82                                 }else if (exp->subtype!=RE_ST){
83                                         LOG(L_CRIT, "BUG: fix_expr : invalid type for match\n");
84                                         return E_BUG;
85                                 }
86                         }
87                         if (exp->l.operand==ACTION_O){
88                                 ret=fix_actions((struct action*)exp->r.param);
89                                 if (ret!=0){
90                                         LOG(L_CRIT, "ERROR: fix_expr : fix_actions error\n");
91                                         return ret;
92                                 }
93                         }
94                         ret=0;
95         }
96         return ret;
97 }
98
99
100
101 /* adds the proxies in the proxy list & resolves the hostnames */
102 /* returns 0 if ok, <0 on error */
103 static int fix_actions(struct action* a)
104 {
105         struct action *t;
106         struct proxy_l* p;
107         char *tmp;
108         int ret,r;
109         struct sr_module* mod;
110         
111         if (a==0){
112                 LOG(L_CRIT,"BUG: fix_actions: null pointer\n");
113                 return E_BUG;
114         }
115         for(t=a; t!=0; t=t->next){
116                 switch(t->type){
117                         case FORWARD_T:
118                         case SEND_T:
119                                         switch(t->p1_type){
120                                                 case NUMBER_ST:
121                                                 case IP_ST: /* for now ip_st==number_st*/
122                                                         tmp=strdup(inet_ntoa(
123                                                                                 *(struct in_addr*)&t->p1.number));
124                                                         if (tmp==0){
125                                                                 LOG(L_CRIT, "ERROR: fix_actions:"
126                                                                                 "memory allocation failure\n");
127                                                                 return E_OUT_OF_MEM;
128                                                         }
129                                                         t->p1_type=STRING_ST;
130                                                         t->p1.string=tmp;
131                                                         /* no break */
132                                                 case STRING_ST:
133                                                         p=add_proxy(t->p1.string, t->p2.number);
134                                                         if (p==0) return E_BAD_ADDRESS;
135                                                         t->p1.data=p;
136                                                         t->p1_type=PROXY_ST;
137                                                         break;
138                                                 case URIHOST_ST:
139                                                         break;
140                                                 default:
141                                                         LOG(L_CRIT, "BUG: fix_actions: invalid type"
142                                                                         "%d (should be string or number)\n",
143                                                                                 t->type);
144                                                         return E_BUG;
145                                         }
146                                         break;
147                         case IF_T:
148                                 if (t->p1_type!=EXPR_ST){
149                                         LOG(L_CRIT, "BUG: fix_actions: invalid subtype"
150                                                                 "%d for if (should be expr)\n",
151                                                                 t->p1_type);
152                                         return E_BUG;
153                                 }else if( (t->p2_type!=ACTIONS_ST)&&(t->p2_type!=NOSUBTYPE) ){
154                                         LOG(L_CRIT, "BUG: fix_actions: invalid subtype"
155                                                                 "%d for if() {...} (should be action)\n",
156                                                                 t->p2_type);
157                                         return E_BUG;
158                                 }else if( (t->p3_type!=ACTIONS_ST)&&(t->p3_type!=NOSUBTYPE) ){
159                                         LOG(L_CRIT, "BUG: fix_actions: invalid subtype"
160                                                                 "%d for if() {} else{...}(should be action)\n",
161                                                                 t->p3_type);
162                                         return E_BUG;
163                                 }
164                                 if (t->p1.data){
165                                         if ((ret=fix_expr((struct expr*)t->p1.data))<0)
166                                                 return ret;
167                                 }
168                                 if ( (t->p2_type==ACTIONS_ST)&&(t->p2.data) ){
169                                         if ((ret=fix_actions((struct action*)t->p2.data))<0)
170                                                 return ret;
171                                 }
172                                 if ( (t->p3_type==ACTIONS_ST)&&(t->p3.data) ){
173                                                 if ((ret=fix_actions((struct action*)t->p3.data))<0)
174                                                 return ret;
175                                 }
176                                 break;
177                         case MODULE_T:
178                                 if ((mod=find_module(t->p1.data, &r))!=0){
179                                         DBG("fixing %s %s\n", mod->path,
180                                                         mod->exports->cmd_names[r]);
181                                         if (mod->exports->fixup_pointers[r]){
182                                                 if (mod->exports->param_no[r]>0){
183                                                         ret=mod->exports->fixup_pointers[r](&t->p2.data,
184                                                                                                                                 1);
185                                                         t->p2_type=MODFIXUP_ST;
186                                                         if (ret<0) return ret;
187                                                 }
188                                                 if (mod->exports->param_no[r]>1){
189                                                         ret=mod->exports->fixup_pointers[r](&t->p3.data,
190                                                                                                                                 2);
191                                                         t->p3_type=MODFIXUP_ST;
192                                                         if (ret<0) return ret;
193                                                 }
194                                         }
195                                 }
196                         
197                 }
198         }
199         return 0;
200 }
201
202
203
204 /* eval_elem helping function, returns str op param */
205 static int comp_str(char* str, void* param, int op, int subtype)
206 {
207         int ret;
208         
209         ret=-1;
210         if (op==EQUAL_OP){
211                 if (subtype!=STRING_ST){
212                         LOG(L_CRIT, "BUG: comp_str: bad type %d, "
213                                         "string expected\n", subtype);
214                         goto error;
215                 }
216                 ret=(strcasecmp(str, (char*)param)==0);
217         }else if (op==MATCH_OP){
218                 if (subtype!=RE_ST){
219                         LOG(L_CRIT, "BUG: comp_str: bad type %d, "
220                                         " RE expected\n", subtype);
221                         goto error;
222                 }
223                 ret=(regexec((regex_t*)param, str, 0, 0, 0)==0);
224         }else{
225                 LOG(L_CRIT, "BUG: comp_str: unknown op %d\n", op);
226                 goto error;
227         }
228         return ret;
229         
230 error:
231         return -1;
232 }
233
234
235
236 /* eval_elem helping function, returns a op param */
237 static int comp_ip(unsigned a, void* param, int op, int subtype)
238 {
239         struct hostent* he;
240         char ** h;
241         int ret;
242
243         ret=-1;
244         switch(subtype){
245                 case NET_ST:
246                         ret=(a&((struct net*)param)->mask)==((struct net*)param)->ip;
247                         break;
248                 case STRING_ST:
249                 case RE_ST:
250                         /* 1: compare with ip2str*/
251                         ret=comp_str(inet_ntoa(*(struct in_addr*)&a), param, op,
252                                                 subtype);
253                         if (ret==1) break;
254                         /* 2: (slow) rev dns the address
255                          * and compare with all the aliases */
256                         he=gethostbyaddr((char*)&a, sizeof(a), AF_INET);
257                         if (he==0){
258                                 LOG(L_DBG, "comp_ip: could not rev_resolve %x\n", a);
259                                 ret=0;
260                         }else{
261                                 /*  compare with primayry host name */
262                                 ret=comp_str(he->h_name, param, op, subtype);
263                                 /* compare with all the aliases */
264                                 for(h=he->h_aliases; (ret!=1) && (*h); h++){
265                                         ret=comp_str(*h, param, op, subtype);
266                                 }
267                         }
268                         break;
269                 default:
270                         LOG(L_CRIT, "BUG: comp_ip: invalid type for "
271                                                 " src_ip or dst_ip (%d)\n", subtype);
272                         ret=-1;
273         }
274         return ret;
275         
276 error:
277         return -1;
278 }
279
280
281
282 /* returns: 0/1 (false/true) or -1 on error */
283 static int eval_elem(struct expr* e, struct sip_msg* msg)
284 {
285
286         int ret;
287         ret=E_BUG;
288         
289         if (e->type!=ELEM_T){
290                 LOG(L_CRIT," BUG: eval_elem: invalid type\n");
291                 goto error;
292         }
293         switch(e->l.operand){
294                 case METHOD_O:
295                                 ret=comp_str(msg->first_line.u.request.method.s, e->r.param,
296                                                                 e->op, e->subtype);
297                                 break;
298                 case URI_O:
299                                 if(msg->new_uri.s){
300                                         ret=comp_str(msg->new_uri.s, e->r.param,
301                                                                         e->op, e->subtype);
302                                 }else{
303                                         ret=comp_str(msg->first_line.u.request.uri.s, e->r.param,
304                                                                         e->op, e->subtype);
305                                 }
306                                 break;
307                 case SRCIP_O:
308                                 ret=comp_ip(msg->src_ip, e->r.param, e->op, e->subtype);
309                                 break;
310                 case DSTIP_O:
311                                 ret=comp_ip(msg->dst_ip, e->r.param, e->op, e->subtype);
312                                 break;
313                 case NUMBER_O:
314                                 ret=!(!e->r.intval); /* !! to transform it in {0,1} */
315                                 break;
316                 case ACTION_O:
317                                 ret=(run_actions( (struct action*)e->r.param, msg)>=0)?1:0;
318                                 break;
319                 default:
320                                 LOG(L_CRIT, "BUG: eval_elem: invalid operand %d\n",
321                                                         e->l.operand);
322         }
323         return ret;
324 error:
325         return -1;
326 }
327
328
329
330 /* ret= 0/1 (true/false) & -1 on error */
331 int eval_expr(struct expr* e, struct sip_msg* msg)
332 {
333         static int rec_lev=0;
334         int ret;
335         
336         rec_lev++;
337         if (rec_lev>MAX_REC_LEV){
338                 LOG(L_CRIT, "ERROR: eval_expr: too many expressions (%d)\n",
339                                 rec_lev);
340                 ret=-1;
341                 goto skip;
342         }
343         
344         if (e->type==ELEM_T){
345                 ret=eval_elem(e, msg);
346         }else if (e->type==EXP_T){
347                 switch(e->op){
348                         case AND_OP:
349                                 ret=eval_expr(e->l.expr, msg);
350                                 /* if error or false stop evaluating the rest */
351                                 if (ret!=1) break;
352                                 ret=eval_expr(e->r.expr, msg); /*ret1 is 1*/
353                                 break;
354                         case OR_OP:
355                                 ret=eval_expr(e->l.expr, msg);
356                                 /* if true or error stop evaluating the rest */
357                                 if (ret!=0) break;
358                                 ret=eval_expr(e->r.expr, msg); /* ret1 is 0 */
359                                 break;
360                         case NOT_OP:
361                                 ret=eval_expr(e->l.expr, msg);
362                                 if (ret<0) break;
363                                 ret= ! ret;
364                                 break;
365                         default:
366                                 LOG(L_CRIT, "BUG: eval_expr: unknown op %d\n", e->op);
367                                 ret=-1;
368                 }
369         }else{
370                 LOG(L_CRIT, "BUG: eval_expr: unknown type %d\n", e->type);
371                 ret=-1;
372         }
373
374 skip:
375         rec_lev--;
376         return ret;
377 }
378
379
380 /* adds an action list to head; a must be null terminated (last a->next=0))*/
381 void push(struct action* a, struct action** head)
382 {
383         struct action *t;
384         if (*head==0){
385                 *head=a;
386                 return;
387         }
388         for (t=*head; t->next;t=t->next);
389         t->next=a;
390 }
391
392
393
394
395 int add_actions(struct action* a, struct action** head)
396 {
397         int ret;
398
399         LOG(L_DBG, "add_actions: fixing actions...\n");
400         if ((ret=fix_actions(a))!=0) goto error;
401         push(a,head);
402         return 0;
403         
404 error:
405         return ret;
406 }
407
408
409
410 /* fixes all action tables */
411 /* returns 0 if ok , <0 on error */
412 int fix_rls()
413 {
414         int i,ret;
415         for(i=0;i<RT_NO;i++){
416                 if(rlist[i]){
417                         if ((ret=fix_actions(rlist[i]))!=0){
418                                 return ret;
419                         }
420                 }
421         }
422         return 0;
423 }
424
425
426 /* debug function, prints main routing table */
427 void print_rl()
428 {
429         struct action* t;
430         int i,j;
431
432         for(j=0; j<RT_NO; j++){
433                 if (rlist[j]==0){
434                         if (j==0) DBG("WARNING: the main routing table is empty\n");
435                         continue;
436                 }
437                 DBG("routing table %d:\n",j);
438                 for (t=rlist[j],i=0; t; i++, t=t->next){
439                         print_action(t);
440                 }
441                 DBG("\n");
442         }
443 }
444
445