blob: d1f98e07d71380df6ed4a16c68523826d744142e [file] [log] [blame]
akmhoque1771c412012-11-09 13:06:08 -06001#include <stdio.h>
2#include <string.h>
3#include <stdlib.h>
akmhoque59980a52012-08-09 12:36:09 -05004#include <unistd.h>
5#include <getopt.h>
6#include <sys/time.h>
akmhoquebfefef22012-09-26 10:09:34 -05007#include <sys/stat.h>
akmhoque59980a52012-08-09 12:36:09 -05008#include <assert.h>
akmhoque1771c412012-11-09 13:06:08 -06009#include <sys/types.h>
10#include <signal.h>
11#include <sys/socket.h>
12#include <sys/un.h>
13#include <fcntl.h>
14#include <sys/ioctl.h>
akmhoque95041802012-11-16 09:18:02 -060015#include <netinet/in.h>
16#include <netdb.h>
17#include <arpa/inet.h>
akmhoque1771c412012-11-09 13:06:08 -060018
akmhoque59980a52012-08-09 12:36:09 -050019#ifdef HAVE_CONFIG_H
20#include <config.h>
21#endif
akmhoquebfefef22012-09-26 10:09:34 -050022
akmhoque59980a52012-08-09 12:36:09 -050023#include <ccn/ccn.h>
24#include <ccn/uri.h>
25#include <ccn/keystore.h>
26#include <ccn/signing.h>
27#include <ccn/schedule.h>
28#include <ccn/hashtb.h>
29
30#include "nlsr.h"
31#include "nlsr_ndn.h"
akmhoque902d57e2012-08-17 09:24:38 -050032#include "nlsr_lsdb.h"
akmhoque53f64222012-09-05 13:57:51 -050033#include "utility.h"
akmhoque03004e62012-09-06 01:12:28 -050034#include "nlsr_npl.h"
35#include "nlsr_adl.h"
akmhoque3560cb62012-09-09 10:52:30 -050036#include "nlsr_npt.h"
37#include "nlsr_route.h"
38
39
akmhoque81c25e02012-09-10 14:50:33 -050040#define ON_ERROR_DESTROY(resval) \
41{ \
42 if ((resval) < 0) { \
43 nlsr_destroy(); \
akmhoqueffacaa82012-09-13 17:48:30 -050044 exit(1);\
akmhoque81c25e02012-09-10 14:50:33 -050045 } \
46}
47
48
49#define ON_ERROR_EXIT(resval) \
50{ \
51 if ((resval) < 0) { \
akmhoqueffacaa82012-09-13 17:48:30 -050052 exit(1); \
akmhoque81c25e02012-09-10 14:50:33 -050053 } \
54}
akmhoque59980a52012-08-09 12:36:09 -050055
56struct option longopts[] =
57{
58 { "daemon", no_argument, NULL, 'd'},
59 { "config_file", required_argument, NULL, 'f'},
akmhoque95041802012-11-16 09:18:02 -060060 { "api_port", required_argument, NULL, 'p'},
akmhoque59980a52012-08-09 12:36:09 -050061 { "help", no_argument, NULL, 'h'},
62 { 0 }
63};
64
65static int
66usage(char *progname)
67{
68
69 printf("Usage: %s [OPTIONS...]\n\
70 NDN routing....\n\
71 -d, --daemon Run in daemon mode\n\
72 -f, --config_file Specify configuration file name\n\
akmhoque95041802012-11-16 09:18:02 -060073 -p, --api_port port where api client will connect\n\
akmhoque59980a52012-08-09 12:36:09 -050074 -h, --help Display this help message\n", progname);
75
76 exit(1);
77}
78
79void ndn_rtr_gettime(const struct ccn_gettime *self, struct ccn_timeval *result)
80{
81 struct timeval now = {0};
82 gettimeofday(&now, 0);
83 result->s = now.tv_sec;
84 result->micros = now.tv_usec;
85}
86
87static struct ccn_gettime ndn_rtr_ticker = {
88 "timer",
89 &ndn_rtr_gettime,
90 1000000,
91 NULL
92};
93
akmhoqueffacaa82012-09-13 17:48:30 -050094void
95nlsr_lock(void)
96{
97 nlsr->semaphor=NLSR_LOCKED;
98}
99
100void
101nlsr_unlock(void)
102{
103 nlsr->semaphor=NLSR_UNLOCKED;
104}
akmhoque42098b12012-08-27 22:54:23 -0500105
106void
akmhoque03004e62012-09-06 01:12:28 -0500107nlsr_stop_signal_handler(int sig)
akmhoque42098b12012-08-27 22:54:23 -0500108{
akmhoque03004e62012-09-06 01:12:28 -0500109 signal(sig, SIG_IGN);
akmhoqueffacaa82012-09-13 17:48:30 -0500110 nlsr_destroy();
111 exit(0);
akmhoque59980a52012-08-09 12:36:09 -0500112}
113
akmhoquebfefef22012-09-26 10:09:34 -0500114void
115daemonize_nlsr(void)
116{
117 int ret;
118 pid_t process_id = 0;
119 pid_t sid = 0;
120 process_id = fork();
121 if (process_id < 0)
122 {
akmhoque7b791452012-10-30 11:24:56 -0500123 printf("Daemonization failed!\n");
akmhoquebfefef22012-09-26 10:09:34 -0500124 ON_ERROR_DESTROY(process_id);
125 }
126 if (process_id > 0)
127 {
128 printf("Process daemonized. Process id: %d \n", process_id);
129 ret=process_id;
130 exit(0);
131 }
132
133 umask(0);
134 sid = setsid();
135 if(sid < 0)
136 {
137 ON_ERROR_DESTROY(sid);
138 }
139
140 chdir("/");
141 close(STDIN_FILENO);
142 close(STDOUT_FILENO);
143 close(STDERR_FILENO);
144}
145
akmhoque59980a52012-08-09 12:36:09 -0500146void
147process_command_ccnneighbor(char *command)
148{
149 if(command==NULL)
150 {
akmhoque28c45022012-08-09 15:38:02 -0500151 printf(" Wrong Command Format ( ccnneighbor router_name faceX)\n");
akmhoque59980a52012-08-09 12:36:09 -0500152 return;
153 }
154 char *rem;
155 const char *sep=" \t\n";
akmhoque28c45022012-08-09 15:38:02 -0500156 char *rtr_name,*face;
akmhoque59980a52012-08-09 12:36:09 -0500157
akmhoque28c45022012-08-09 15:38:02 -0500158 rtr_name=strtok_r(command,sep,&rem);
159 if(rtr_name==NULL)
akmhoque59980a52012-08-09 12:36:09 -0500160 {
akmhoque28c45022012-08-09 15:38:02 -0500161 printf(" Wrong Command Format ( ccnneighbor router_name faceX)\n");
akmhoque59980a52012-08-09 12:36:09 -0500162 return;
163 }
164
165 face=strtok_r(NULL,sep,&rem);
166 if(face==NULL)
167 {
akmhoque28c45022012-08-09 15:38:02 -0500168 printf(" Wrong Command Format ( ccnneighbor router_name faceX)\n");
akmhoque59980a52012-08-09 12:36:09 -0500169 return;
170 }
171
akmhoque28c45022012-08-09 15:38:02 -0500172 printf("Router: %s face: %s\n",rtr_name,face);
173 int face_id;
174 int res;
175 res=sscanf(face,"face%d",&face_id);
176
177 if(res != 1 )
178 {
179 printf(" Wrong Command Format ( ccnneighbor router_name faceX) where X is integer\n");
180 return;
181 }
182
akmhoqued5152122012-09-19 06:44:23 -0500183 if ( rtr_name[strlen(rtr_name)-1] == '/' )
184 {
185 rtr_name[strlen(rtr_name)-1]='\0';
186 }
akmhoque03004e62012-09-06 01:12:28 -0500187 struct name_prefix *nbr=(struct name_prefix *)malloc(sizeof(struct name_prefix ));
188 nbr->name=(char *)malloc(strlen(rtr_name)+1);
189 memset(nbr->name,0,strlen(rtr_name)+1);
190 memcpy(nbr->name,rtr_name,strlen(rtr_name)+1);
191 nbr->length=strlen(rtr_name)+1;
192
193 add_nbr_to_adl(nbr,face_id);
194
195 free(nbr->name);
196 free(nbr);
197}
198
199void
200process_command_ccnname(char *command)
201{
202
203 if(command==NULL)
204 {
205 printf(" Wrong Command Format ( ccnname /name/prefix)\n");
206 return;
207 }
208 char *rem;
209 const char *sep=" \t\n";
210 char *name;
211 name=strtok_r(command,sep,&rem);
212 if(name==NULL)
213 {
214 printf(" Wrong Command Format ( ccnname /name/prefix/ )\n");
215 return;
216 }
217
218 printf("Name Prefix: %s \n",name);
219
akmhoqued5152122012-09-19 06:44:23 -0500220 if ( name[strlen(name)-1] == '/' )
221 name[strlen(name)-1]='\0';
222
akmhoque53f64222012-09-05 13:57:51 -0500223 struct name_prefix *np=(struct name_prefix *)malloc(sizeof(struct name_prefix ));
akmhoque03004e62012-09-06 01:12:28 -0500224 np->name=(char *)malloc(strlen(name)+1);
225 memset(np->name,0,strlen(name)+1);
226 memcpy(np->name,name,strlen(name)+1);
227 np->length=strlen(name)+1;
akmhoque386081b2012-08-10 10:53:21 -0500228
akmhoque03004e62012-09-06 01:12:28 -0500229 add_name_to_npl(np);
akmhoque28c45022012-08-09 15:38:02 -0500230
akmhoque03004e62012-09-06 01:12:28 -0500231 free(np->name);
akmhoque53f64222012-09-05 13:57:51 -0500232 free(np);
akmhoque59980a52012-08-09 12:36:09 -0500233}
234
akmhoque03004e62012-09-06 01:12:28 -0500235
236void
237process_command_router_name(char *command)
238{
239 if(command==NULL)
240 {
241 printf(" Wrong Command Format ( router-name /router/name )\n");
242 return;
243 }
244 char *rem;
245 const char *sep=" \t\n";
246 char *rtr_name;
247
248 rtr_name=strtok_r(command,sep,&rem);
249 if(rtr_name==NULL)
250 {
251 printf(" Wrong Command Format ( router-name /router/name )\n");
252 return;
253 }
254
255
akmhoqued5152122012-09-19 06:44:23 -0500256 if ( rtr_name[strlen(rtr_name)-1] == '/' )
257 rtr_name[strlen(rtr_name)-1]='\0';
258
akmhoque03004e62012-09-06 01:12:28 -0500259 nlsr->router_name=(char *)malloc(strlen(rtr_name)+1);
260 memset(nlsr->router_name,0,strlen(rtr_name)+1);
261 memcpy(nlsr->router_name,rtr_name,strlen(rtr_name)+1);
262
263
264}
265
akmhoque59980a52012-08-09 12:36:09 -0500266void
akmhoqued79438d2012-08-27 13:31:42 -0500267process_command_lsdb_synch_interval(char *command)
268{
269 if(command==NULL)
270 {
271 printf(" Wrong Command Format ( lsdb-synch-interval secs )\n");
272 return;
273 }
274 char *rem;
275 const char *sep=" \t\n";
276 char *secs;
277 long int seconds;
278
279 secs=strtok_r(command,sep,&rem);
280 if(secs==NULL)
281 {
282 printf(" Wrong Command Format ( lsdb-synch-interval secs)\n");
283 return;
284 }
285
286 seconds=atoi(secs);
akmhoqueffacaa82012-09-13 17:48:30 -0500287 if ( seconds >= 120 && seconds <= 3600 )
288 {
289 nlsr->lsdb_synch_interval=seconds;
290 }
akmhoqued79438d2012-08-27 13:31:42 -0500291
292}
293
294
295void
296process_command_interest_retry(char *command)
297{
298 if(command==NULL)
299 {
300 printf(" Wrong Command Format ( interest-retry number )\n");
301 return;
302 }
303 char *rem;
304 const char *sep=" \t\n";
akmhoqueffacaa82012-09-13 17:48:30 -0500305 char *retry;
306 long int retry_number;
akmhoqued79438d2012-08-27 13:31:42 -0500307
akmhoqueffacaa82012-09-13 17:48:30 -0500308 retry=strtok_r(command,sep,&rem);
309 if(retry==NULL)
akmhoqued79438d2012-08-27 13:31:42 -0500310 {
311 printf(" Wrong Command Format ( interest-retry number)\n");
312 return;
313 }
314
akmhoqueffacaa82012-09-13 17:48:30 -0500315 retry_number=atoi(retry);
316 if ( retry_number >= 1 && retry_number<=10 )
317 {
318 nlsr->interest_retry=retry_number;
319 }
akmhoqued79438d2012-08-27 13:31:42 -0500320
321}
322
323void
324process_command_interest_resend_time(char *command)
325{
326 if(command==NULL)
327 {
328 printf(" Wrong Command Format ( interest-resend-time secs )\n");
329 return;
330 }
331 char *rem;
332 const char *sep=" \t\n";
333 char *secs;
334 long int seconds;
335
336 secs=strtok_r(command,sep,&rem);
337 if(secs==NULL)
338 {
339 printf(" Wrong Command Format ( interest-resend-time secs)\n");
340 return;
341 }
342
343 seconds=atoi(secs);
akmhoqueffacaa82012-09-13 17:48:30 -0500344 if ( seconds <= 60 && seconds >= 1 )
345 {
346 nlsr->interest_resend_time=seconds;
347 }
akmhoqued79438d2012-08-27 13:31:42 -0500348}
349
akmhoque03004e62012-09-06 01:12:28 -0500350
akmhoqued5152122012-09-19 06:44:23 -0500351void
352process_command_lsa_refresh_time(char *command)
353{
354 if(command==NULL)
355 {
356 printf(" Wrong Command Format ( lsa-refresh-time secs )\n");
357 return;
358 }
359 char *rem;
360 const char *sep=" \t\n";
361 char *secs;
362 long int seconds;
363
364 secs=strtok_r(command,sep,&rem);
365 if(secs==NULL)
366 {
367 printf(" Wrong Command Format ( lsa-refresh-time secs)\n");
368 return;
369 }
370
371 seconds=atoi(secs);
372 if ( seconds >= 240 && seconds <= 3600 )
373 {
374 nlsr->lsa_refresh_time=seconds;
375 }
376
377}
378
379void
380process_command_router_dead_interval(char *command)
381{
382 if(command==NULL)
383 {
384 printf(" Wrong Command Format ( router-dead-interval secs )\n");
385 return;
386 }
387 char *rem;
388 const char *sep=" \t\n";
389 char *secs;
390 long int seconds;
391
392 secs=strtok_r(command,sep,&rem);
393 if(secs==NULL)
394 {
395 printf(" Wrong Command Format ( router-dead-interval secs)\n");
396 return;
397 }
398
399 seconds=atoi(secs);
400 if ( seconds >= 360 && seconds <= 5400 )
401 {
402 nlsr->router_dead_interval=seconds;
403 }
404
405}
akmhoque03004e62012-09-06 01:12:28 -0500406
akmhoqued79438d2012-08-27 13:31:42 -0500407void
akmhoque3cced642012-09-24 16:20:20 -0500408process_command_multi_path_face_num(char *command)
409{
410 if(command==NULL)
411 {
412 printf(" Wrong Command Format ( multi-path-face-num n )\n");
413 return;
414 }
415 char *rem;
416 const char *sep=" \t\n";
417 char *num;
418 long int number;
419
420 num=strtok_r(command,sep,&rem);
421 if(num==NULL)
422 {
423 printf(" Wrong Command Format ( multi-path-face-num n)\n");
424 return;
425 }
426
427 number=atoi(num);
428 if ( number >= 0 && number <= 60 )
429 {
430 nlsr->multi_path_face_num=number;
431 }
432
433}
434
435void
akmhoquebfefef22012-09-26 10:09:34 -0500436process_command_logdir(char *command)
437{
438 if(command==NULL)
439 {
440 printf(" Wrong Command Format ( logdir /path/to/logdir )\n");
441 return;
442 }
443 char *rem;
444 const char *sep=" \t\n";
445 char *dir;
446
447 dir=strtok_r(command,sep,&rem);
448 if(dir==NULL)
449 {
450 printf(" Wrong Command Format ( logdir /path/to/logdir/ )\n");
451 return;
452 }
453
454 nlsr->logDir=(char *)malloc(strlen(dir)+1);
455 memset(nlsr->logDir,0,strlen(dir)+1);
456 memcpy(nlsr->logDir,dir,strlen(dir));
457}
458
459void
akmhoque7b791452012-10-30 11:24:56 -0500460process_command_detailed_log(char *command)
461{
462 if(command==NULL)
463 {
464 printf(" Wrong Command Format ( detailed-log on/off )\n");
465 return;
466 }
467 char *rem;
468 const char *sep=" \t\n";
469 char *on_off;
470
471 on_off=strtok_r(command,sep,&rem);
472 if(on_off==NULL)
473 {
474 printf(" Wrong Command Format ( detailed-log on/off )\n");
475 return;
476 }
477
478 if ( strcmp(on_off,"ON") == 0 || strcmp(on_off,"on") == 0)
479 {
480 nlsr->detailed_logging=1;
481 }
482}
483
484void
485process_command_debug(char *command)
486{
487 if(command==NULL)
488 {
489 printf(" Wrong Command Format ( debug on/off )\n");
490 return;
491 }
492 char *rem;
493 const char *sep=" \t\n";
494 char *on_off;
495
496 on_off=strtok_r(command,sep,&rem);
497 if(on_off==NULL)
498 {
499 printf(" Wrong Command Format ( debug on/off )\n");
500 return;
501 }
502
503 if ( strcmp(on_off,"ON") == 0 || strcmp(on_off,"on") == 0 )
504 {
505 nlsr->debugging=1;
506 }
507}
508
509void
akmhoque59980a52012-08-09 12:36:09 -0500510process_conf_command(char *command)
511{
512 const char *separators=" \t\n";
513 char *remainder=NULL;
514 char *cmd_type=NULL;
515
516 if(command==NULL || strlen(command)==0 || command[0]=='!')
517 return;
518
519 cmd_type=strtok_r(command,separators,&remainder);
520
521 if(!strcmp(cmd_type,"router-name") )
522 {
523 process_command_router_name(remainder);
524 }
525 else if(!strcmp(cmd_type,"ccnneighbor") )
526 {
527 process_command_ccnneighbor(remainder);
528 }
529 else if(!strcmp(cmd_type,"ccnname") )
530 {
531 process_command_ccnname(remainder);
532 }
akmhoqued79438d2012-08-27 13:31:42 -0500533 else if(!strcmp(cmd_type,"lsdb-synch-interval") )
534 {
535 process_command_lsdb_synch_interval(remainder);
536 }
537 else if(!strcmp(cmd_type,"interest-retry") )
538 {
539 process_command_interest_retry(remainder);
540 }
541 else if(!strcmp(cmd_type,"interest-resend-time") )
542 {
543 process_command_interest_resend_time(remainder);
544 }
akmhoqued5152122012-09-19 06:44:23 -0500545 else if(!strcmp(cmd_type,"lsa-refresh-time") )
546 {
547 process_command_lsa_refresh_time(remainder);
548 }
549 else if(!strcmp(cmd_type,"router-dead-interval") )
550 {
551 process_command_router_dead_interval(remainder);
552 }
akmhoque3cced642012-09-24 16:20:20 -0500553 else if(!strcmp(cmd_type,"multi-path-face-num") )
554 {
555 process_command_multi_path_face_num(remainder);
556 }
akmhoquebfefef22012-09-26 10:09:34 -0500557 else if(!strcmp(cmd_type,"logdir") )
558 {
559 process_command_logdir(remainder);
560 }
akmhoque7b791452012-10-30 11:24:56 -0500561 else if(!strcmp(cmd_type,"detailed-log") )
562 {
563 process_command_detailed_log(remainder);
564 }
565 else if(!strcmp(cmd_type,"debug") )
566 {
567 process_command_debug(remainder);
568 }
akmhoqued5152122012-09-19 06:44:23 -0500569 else
akmhoque59980a52012-08-09 12:36:09 -0500570 {
571 printf("Wrong configuration Command %s \n",cmd_type);
572 }
573}
574
akmhoque03004e62012-09-06 01:12:28 -0500575
akmhoque59980a52012-08-09 12:36:09 -0500576int
577readConfigFile(const char *filename)
578{
579 FILE *cfg;
580 char buf[1024];
581 int len;
582
583 cfg=fopen(filename, "r");
584
585 if(cfg == NULL)
586 {
587 printf("\nConfiguration File does not exists\n");
588 exit(1);
589 }
590
591 while(fgets((char *)buf, sizeof(buf), cfg))
592 {
593 len=strlen(buf);
594 if(buf[len-1] == '\n')
595 buf[len-1]='\0';
akmhoqued5152122012-09-19 06:44:23 -0500596 if ( buf[0] != '#' && buf[0] != '!')
597 process_conf_command(buf);
akmhoque59980a52012-08-09 12:36:09 -0500598 }
599
600 fclose(cfg);
601
602 return 0;
603}
604
akmhoque562caef2012-11-09 13:29:06 -0600605char *
606process_api_client_command(char *command)
607{
608 char *msg;
609 msg=(char *)malloc(100);
610 memset(msg,100,0);
akmhoque3171d652012-11-13 11:44:33 -0600611 //strcpy(msg,"Action Carried Out for NLSR Api Client");
akmhoque562caef2012-11-09 13:29:06 -0600612
akmhoque3171d652012-11-13 11:44:33 -0600613 const char *sep=" \t\n";
614 char *rem=NULL;
615 char *cmd_type=NULL;
616 char *op_type=NULL;
617 char *name=NULL;
618 char *face=NULL;
619 int face_id;
620 int res;
621
622 op_type=strtok_r(command,sep,&rem);
623 cmd_type=strtok_r(NULL,sep,&rem);
624 name=strtok_r(NULL,sep,&rem);
625 if ( name[strlen(name)-1] == '/' )
626 name[strlen(name)-1]='\0';
627
628 struct name_prefix *np=(struct name_prefix *)malloc(sizeof(struct name_prefix ));
629 np->name=(char *)malloc(strlen(name)+1);
630 memset(np->name,0,strlen(name)+1);
631 memcpy(np->name,name,strlen(name)+1);
632 np->length=strlen(name)+1;
633
634 if ( strcmp(cmd_type,"name")!= 0 )
635 {
636 face=strtok_r(NULL,sep,&rem);
637 sscanf(face,"face%d",&face_id);
638 }
akmhoque562caef2012-11-09 13:29:06 -0600639
akmhoque3171d652012-11-13 11:44:33 -0600640 if ( strcmp(cmd_type,"name")== 0 )
641 {
642 if ( strcmp(op_type,"del") == 0 )
643 {
644 res=does_name_exist_in_npl(np);
645 if ( res == 0)
646 {
647 sprintf(msg,"Name %s does not exist !!",name);
648 }
649 else
650 {
651 long int ls_id=get_lsa_id_from_npl(np);
652 if ( ls_id != 0 )
653 {
654 make_name_lsa_invalid(np,LS_TYPE_NAME,ls_id);
655 sprintf(msg,"Name %s has been deleted and Advertised.",name);
656 }
657 else
658 {
659 sprintf(msg,"Name %s does not have an Name LSA yet !!",name);
660 }
661 }
662 }
663 else if ( strcmp(op_type,"add") == 0 )
664 {
665 res=does_name_exist_in_npl(np);
666 if ( res == 0)
667 {
668 add_name_to_npl(np);
669 build_and_install_single_name_lsa(np);
670 sprintf(msg,"Name %s has been added to advertise.",name);
671 }
672 else
673 {
674 sprintf(msg,"Name %s has already been advertised from this router !!",name);
675 }
676 }
677 }
678 else if ( strcmp(cmd_type,"neighbor") == 0 )
679 {
680 if ( strcmp(op_type,"del") == 0 )
681 {
682 res=is_neighbor(np->name);
683 if ( res == 0)
684 {
685 sprintf(msg,"Neighbor %s does not exist !!",name);
686 }
687 else
688 {
689 update_adjacent_status_to_adl(np,NBR_DOWN);
690 delete_nbr_from_adl(np);
691 if(!nlsr->is_build_adj_lsa_sheduled)
692 {
693 nlsr->event_build_adj_lsa = ccn_schedule_event(nlsr->sched, 1000, &build_and_install_adj_lsa, NULL, 0);
694 nlsr->is_build_adj_lsa_sheduled=1;
695 }
696 sprintf(msg,"Neighbor %s has been deleted from adjacency list.",name);
697 }
698 }
699 else if ( strcmp(op_type,"add") == 0 )
700 {
701 res=is_neighbor(np->name);
702 if ( res == 0 )
703 {
704 add_nbr_to_adl(np,face_id);
705 sprintf(msg,"Neighbor %s has been added to adjacency list.",name);
706 }
707 else
708 {
709 sprintf(msg,"Neighbor %s already exists in adjacency list.",name);
710 }
711 }
712 }
713
akmhoque562caef2012-11-09 13:29:06 -0600714
715 return msg;
716}
akmhoque1771c412012-11-09 13:06:08 -0600717
718int
719nlsr_api_server_poll(long int time_out_micro_sec, int ccn_fd)
720{
721 struct timeval timeout;
722 if ( time_out_micro_sec < 0 )
723 {
724 timeout.tv_sec=1;
725 timeout.tv_usec=0;
726 }
727 else
728 {
729 time_out_micro_sec=(long int)time_out_micro_sec*0.4;
730 timeout.tv_sec=time_out_micro_sec / 1000000;
731 timeout.tv_usec=time_out_micro_sec % 1000000;
732 }
733
734
735 int fd;
736 int nread;
737 int result;
738 fd_set testfds;
739 unsigned int client_len;
740 int client_sockfd;
741 char recv_buffer[1024];
742 bzero(recv_buffer,1024);
akmhoque95041802012-11-16 09:18:02 -0600743 struct sockaddr_in client_address;
akmhoque1771c412012-11-09 13:06:08 -0600744
745 testfds=nlsr->readfds;
746 result = select(FD_SETSIZE, &testfds, NULL,NULL, &timeout);
747
748 for(fd = 0; fd < FD_SETSIZE; fd++)
749 {
750 if(FD_ISSET(fd,&testfds))
751 {
752 if ( fd == ccn_fd )
753 {
754 return 0;
755 }
756 else if(fd == nlsr->nlsr_api_server_sock_fd)
757 {
758 client_len = sizeof(client_address);
759 client_sockfd = accept(nlsr->nlsr_api_server_sock_fd,(struct sockaddr *)&client_address, &client_len);
760 FD_SET(client_sockfd, &nlsr->readfds);
761 }
762 else
763 {
764
765 ioctl(fd, FIONREAD, &nread);
766 if(nread == 0)
767 {
768 close(fd);
769 FD_CLR(fd, &nlsr->readfds);
770 }
771 else
772 {
773 recv(fd, recv_buffer, 1024, 0);
774 printf("Received Data from NLSR API cleint: %s \n",recv_buffer);
akmhoque562caef2012-11-09 13:29:06 -0600775 char *msg=process_api_client_command(recv_buffer);
776 send(fd, msg, strlen(msg),0);
777 free(msg);
akmhoque1771c412012-11-09 13:06:08 -0600778 close(fd);
779 FD_CLR(fd, &nlsr->readfds);
akmhoque1771c412012-11-09 13:06:08 -0600780 }
781 }
782 }
783 }
784
785 return 0;
786}
787
akmhoque386081b2012-08-10 10:53:21 -0500788void
789nlsr_destroy( void )
790{
akmhoque7b791452012-10-30 11:24:56 -0500791 if ( nlsr->debugging )
792 {
793 printf("Freeing Allocated Memory....\n");
794 }
akmhoque9e9fc722012-09-26 14:03:25 -0500795 writeLogg(__FILE__,__FUNCTION__,__LINE__,"Freeing Allocated Memory....\n");
akmhoquefbfd0982012-09-09 20:59:03 -0500796 /* Destroying all face created by nlsr in CCND */
797 destroy_all_face_by_nlsr();
798
akmhoque386081b2012-08-10 10:53:21 -0500799 /* Destroying every hash table attached to each neighbor in ADL before destorying ADL */
akmhoque53f64222012-09-05 13:57:51 -0500800 hashtb_destroy(&nlsr->npl);
akmhoque03004e62012-09-06 01:12:28 -0500801 hashtb_destroy(&nlsr->adl);
802 hashtb_destroy(&nlsr->lsdb->name_lsdb);
803 hashtb_destroy(&nlsr->lsdb->adj_lsdb);
akmhoque29c1db52012-09-07 14:47:43 -0500804 hashtb_destroy(&nlsr->pit_alsa);
akmhoque3cced642012-09-24 16:20:20 -0500805
806 //To Do: has to destroy the face_list one by one
807
akmhoque3560cb62012-09-09 10:52:30 -0500808 hashtb_destroy(&nlsr->routing_table);
809
810
811 int i, npt_element;
812 struct npt_entry *ne;
813 struct hashtb_enumerator ee;
814 struct hashtb_enumerator *e = &ee;
815 hashtb_start(nlsr->npt, e);
816 npt_element=hashtb_n(nlsr->npt);
817 for(i=0;i<npt_element;i++)
818 {
819 ne=e->data;
akmhoque3cced642012-09-24 16:20:20 -0500820 hashtb_destroy(&ne->name_list);
821 hashtb_destroy(&ne->face_list);
akmhoque3560cb62012-09-09 10:52:30 -0500822 hashtb_next(e);
823 }
824
825 hashtb_end(e);
826 hashtb_destroy(&nlsr->npt);
827
akmhoque95041802012-11-16 09:18:02 -0600828
829 close(nlsr->nlsr_api_server_sock_fd);
830
akmhoque386081b2012-08-10 10:53:21 -0500831 ccn_schedule_destroy(&nlsr->sched);
832 ccn_destroy(&nlsr->ccn);
akmhoque03004e62012-09-06 01:12:28 -0500833
834 free(nlsr->lsdb->lsdb_version);
835 free(nlsr->lsdb);
836 free(nlsr->router_name);
akmhoque386081b2012-08-10 10:53:21 -0500837 free(nlsr);
akmhoque7b791452012-10-30 11:24:56 -0500838 if ( nlsr->debugging )
839 {
840 printf("Finished freeing allocated memory\n");
841 }
akmhoque9e9fc722012-09-26 14:03:25 -0500842 writeLogg(__FILE__,__FUNCTION__,__LINE__,"Finished freeing allocated memory\n");
akmhoque53f64222012-09-05 13:57:51 -0500843
akmhoque386081b2012-08-10 10:53:21 -0500844}
845
akmhoque03004e62012-09-06 01:12:28 -0500846
akmhoque1771c412012-11-09 13:06:08 -0600847void
848init_api_server(int ccn_fd)
849{
850 int server_sockfd;
851 int server_len;
akmhoque95041802012-11-16 09:18:02 -0600852 struct sockaddr_in server_address;
akmhoque1771c412012-11-09 13:06:08 -0600853
akmhoque95041802012-11-16 09:18:02 -0600854 //unlink("/tmp/nlsr_api_server_socket");
855 server_sockfd = socket(AF_INET, SOCK_STREAM, 0);
akmhoque1771c412012-11-09 13:06:08 -0600856
857 int flags = fcntl(server_sockfd, F_GETFL, 0);
858 fcntl(server_sockfd, F_SETFL, O_NONBLOCK|flags);
859
akmhoque95041802012-11-16 09:18:02 -0600860 //server_address.sun_family = AF_UNIX;
861 //strcpy(server_address.sun_path, "/tmp/nlsr_api_server_socket");
862
863 server_address.sin_family = AF_INET;
864 server_address.sin_addr.s_addr = inet_addr("127.0.0.1");
865 server_address.sin_port = nlsr->api_port;
866
akmhoque1771c412012-11-09 13:06:08 -0600867 server_len = sizeof(server_address);
868 bind(server_sockfd, (struct sockaddr *)&server_address, server_len);
869 listen(server_sockfd, 100);
870 FD_ZERO(&nlsr->readfds);
871 FD_SET(server_sockfd, &nlsr->readfds);
872 FD_SET(ccn_fd, &nlsr->readfds);
873 nlsr->nlsr_api_server_sock_fd=server_sockfd;
874
875}
876
akmhoque81c25e02012-09-10 14:50:33 -0500877int
akmhoque902d57e2012-08-17 09:24:38 -0500878init_nlsr(void)
akmhoque59980a52012-08-09 12:36:09 -0500879{
akmhoque03004e62012-09-06 01:12:28 -0500880 if (signal(SIGQUIT, nlsr_stop_signal_handler ) == SIG_ERR)
881 {
882 perror("SIGQUIT install error\n");
akmhoque81c25e02012-09-10 14:50:33 -0500883 return -1;
akmhoque03004e62012-09-06 01:12:28 -0500884 }
885 if (signal(SIGTERM, nlsr_stop_signal_handler ) == SIG_ERR)
886 {
887 perror("SIGTERM install error\n");
akmhoque81c25e02012-09-10 14:50:33 -0500888 return -1;
akmhoque03004e62012-09-06 01:12:28 -0500889 }
890 if (signal(SIGINT, nlsr_stop_signal_handler ) == SIG_ERR)
891 {
892 perror("SIGTERM install error\n");
akmhoque81c25e02012-09-10 14:50:33 -0500893 return -1;
akmhoque03004e62012-09-06 01:12:28 -0500894 }
akmhoque902d57e2012-08-17 09:24:38 -0500895
akmhoque59980a52012-08-09 12:36:09 -0500896 nlsr=(struct nlsr *)malloc(sizeof(struct nlsr));
akmhoque03004e62012-09-06 01:12:28 -0500897
898 struct hashtb_param param_adl = {0};
akmhoque28c45022012-08-09 15:38:02 -0500899 nlsr->adl=hashtb_create(sizeof(struct ndn_neighbor), &param_adl);
akmhoque03004e62012-09-06 01:12:28 -0500900 struct hashtb_param param_npl = {0};
akmhoque3171d652012-11-13 11:44:33 -0600901 nlsr->npl = hashtb_create(sizeof(struct name_prefix_list_entry), &param_npl);
akmhoque29c1db52012-09-07 14:47:43 -0500902 struct hashtb_param param_pit_alsa = {0};
akmhoque1ce71052012-09-13 22:51:32 -0500903 nlsr->pit_alsa = hashtb_create(sizeof(struct pending_interest), &param_pit_alsa);
akmhoque3560cb62012-09-09 10:52:30 -0500904 struct hashtb_param param_npt = {0};
905 nlsr->npt = hashtb_create(sizeof(struct npt_entry), &param_npt);
906 struct hashtb_param param_rte = {0};
907 nlsr->routing_table = hashtb_create(sizeof(struct routing_table_entry), &param_rte);
akmhoque29c1db52012-09-07 14:47:43 -0500908
akmhoque59980a52012-08-09 12:36:09 -0500909 nlsr->in_interest.p = &incoming_interest;
910 nlsr->in_content.p = &incoming_content;
akmhoque07dd8cc2012-08-16 10:23:01 -0500911
akmhoque03004e62012-09-06 01:12:28 -0500912 nlsr->lsdb=(struct linkStateDatabase *)malloc(sizeof(struct linkStateDatabase));
akmhoque07dd8cc2012-08-16 10:23:01 -0500913
akmhoque03004e62012-09-06 01:12:28 -0500914 char *time_stamp=(char *)malloc(20);
915 memset(time_stamp,0,20);
916 get_current_timestamp_micro(time_stamp);
917 nlsr->lsdb->lsdb_version=(char *)malloc(strlen(time_stamp)+1);
918 memset(nlsr->lsdb->lsdb_version,'0',strlen(time_stamp));
919 free(time_stamp);
920
921 struct hashtb_param param_adj_lsdb = {0};
akmhoquef71d9082012-08-22 12:51:53 -0400922 nlsr->lsdb->adj_lsdb = hashtb_create(sizeof(struct alsa), &param_adj_lsdb);
akmhoque03004e62012-09-06 01:12:28 -0500923 struct hashtb_param param_name_lsdb = {0};
akmhoquef71d9082012-08-22 12:51:53 -0400924 nlsr->lsdb->name_lsdb = hashtb_create(sizeof(struct nlsa), &param_name_lsdb);
akmhoque29c1db52012-09-07 14:47:43 -0500925
926
akmhoque902d57e2012-08-17 09:24:38 -0500927
akmhoque53f64222012-09-05 13:57:51 -0500928
akmhoque59980a52012-08-09 12:36:09 -0500929 nlsr->is_synch_init=1;
akmhoquec9286692012-08-16 09:57:58 -0500930 nlsr->nlsa_id=0;
akmhoqued79438d2012-08-27 13:31:42 -0500931 nlsr->adj_build_flag=0;
akmhoque53f64222012-09-05 13:57:51 -0500932 nlsr->adj_build_count=0;
933 nlsr->is_build_adj_lsa_sheduled=0;
akmhoque29c1db52012-09-07 14:47:43 -0500934 nlsr->is_send_lsdb_interest_scheduled=0;
935 nlsr->is_route_calculation_scheduled=0;
akmhoqued79438d2012-08-27 13:31:42 -0500936
akmhoque7b791452012-10-30 11:24:56 -0500937 nlsr->detailed_logging=0;
938 nlsr->debugging=0;
939
akmhoqued79438d2012-08-27 13:31:42 -0500940 nlsr->lsdb_synch_interval = LSDB_SYNCH_INTERVAL;
941 nlsr->interest_retry = INTEREST_RETRY;
942 nlsr->interest_resend_time = INTEREST_RESEND_TIME;
akmhoqueda5b6832012-09-13 22:33:55 -0500943 nlsr->lsa_refresh_time=LSA_REFRESH_TIME;
944 nlsr->router_dead_interval=ROUTER_DEAD_INTERVAL;
akmhoque3cced642012-09-24 16:20:20 -0500945 nlsr->multi_path_face_num=MULTI_PATH_FACE_NUM;
akmhoqueffacaa82012-09-13 17:48:30 -0500946 nlsr->semaphor=NLSR_UNLOCKED;
akmhoque81c25e02012-09-10 14:50:33 -0500947
akmhoque95041802012-11-16 09:18:02 -0600948 nlsr->api_port=API_PORT;
949
akmhoque81c25e02012-09-10 14:50:33 -0500950 return 0;
akmhoque902d57e2012-08-17 09:24:38 -0500951}
952
akmhoque03004e62012-09-06 01:12:28 -0500953
akmhoque902d57e2012-08-17 09:24:38 -0500954int
955main(int argc, char *argv[])
956{
akmhoque81c25e02012-09-10 14:50:33 -0500957 int res, ret;
akmhoque902d57e2012-08-17 09:24:38 -0500958 char *config_file;
akmhoquebfefef22012-09-26 10:09:34 -0500959 int daemon_mode=0;
akmhoque95041802012-11-16 09:18:02 -0600960 int port=0;
akmhoque902d57e2012-08-17 09:24:38 -0500961
akmhoquebfefef22012-09-26 10:09:34 -0500962
akmhoque81c25e02012-09-10 14:50:33 -0500963
akmhoque95041802012-11-16 09:18:02 -0600964 while ((res = getopt_long(argc, argv, "df:p:h", longopts, 0)) != -1)
akmhoque59980a52012-08-09 12:36:09 -0500965 {
966 switch (res)
967 {
968 case 'd':
akmhoquebfefef22012-09-26 10:09:34 -0500969 daemon_mode = 1;
akmhoque59980a52012-08-09 12:36:09 -0500970 break;
971 case 'f':
972 config_file = optarg;
973 break;
akmhoque95041802012-11-16 09:18:02 -0600974 case 'p':
975 port = atoi(optarg);
976 break;
akmhoque59980a52012-08-09 12:36:09 -0500977 case 'h':
978 default:
979 usage(argv[0]);
980 }
981 }
982
akmhoquebfefef22012-09-26 10:09:34 -0500983 ret=init_nlsr();
984 ON_ERROR_EXIT(ret);
akmhoque95041802012-11-16 09:18:02 -0600985
986 if ( port !=0 )
987 nlsr->api_port=port;
988
akmhoque59980a52012-08-09 12:36:09 -0500989 readConfigFile(config_file);
akmhoquebfefef22012-09-26 10:09:34 -0500990 if ( daemon_mode == 1 )
991 {
992 daemonize_nlsr();
993 }
994
995 startLogging(nlsr->logDir);
996
akmhoque59980a52012-08-09 12:36:09 -0500997 nlsr->ccn=ccn_create();
akmhoque1771c412012-11-09 13:06:08 -0600998 int ccn_fd=ccn_connect(nlsr->ccn, NULL);
999 if(ccn_fd == -1)
akmhoque03004e62012-09-06 01:12:28 -05001000 {
1001 fprintf(stderr,"Could not connect to ccnd\n");
akmhoquebfefef22012-09-26 10:09:34 -05001002 writeLogg(__FILE__,__FUNCTION__,__LINE__,"Could not connect to ccnd\n");
akmhoque81c25e02012-09-10 14:50:33 -05001003 ON_ERROR_DESTROY(-1);
akmhoque03004e62012-09-06 01:12:28 -05001004 }
akmhoque1771c412012-11-09 13:06:08 -06001005
1006 init_api_server(ccn_fd);
1007
akmhoque53f64222012-09-05 13:57:51 -05001008 struct ccn_charbuf *router_prefix;
akmhoque03004e62012-09-06 01:12:28 -05001009 router_prefix=ccn_charbuf_create();
1010 res=ccn_name_from_uri(router_prefix,nlsr->router_name);
akmhoque59980a52012-08-09 12:36:09 -05001011 if(res<0)
akmhoque03004e62012-09-06 01:12:28 -05001012 {
1013 fprintf(stderr, "Bad ccn URI: %s\n",nlsr->router_name);
akmhoquebfefef22012-09-26 10:09:34 -05001014 writeLogg(__FILE__,__FUNCTION__,__LINE__,"Bad ccn URI: %s\n",nlsr->router_name);
akmhoque81c25e02012-09-10 14:50:33 -05001015 ON_ERROR_DESTROY(res);
akmhoque03004e62012-09-06 01:12:28 -05001016 }
akmhoque59980a52012-08-09 12:36:09 -05001017
1018 ccn_name_append_str(router_prefix,"nlsr");
akmhoque03004e62012-09-06 01:12:28 -05001019 nlsr->in_interest.data=nlsr->router_name;
akmhoque59980a52012-08-09 12:36:09 -05001020 res=ccn_set_interest_filter(nlsr->ccn,router_prefix,&nlsr->in_interest);
1021 if ( res < 0 )
akmhoque03004e62012-09-06 01:12:28 -05001022 {
1023 fprintf(stderr,"Failed to register interest for router\n");
akmhoque9e9fc722012-09-26 14:03:25 -05001024 writeLogg(__FILE__,__FUNCTION__,__LINE__,"Failed to register interest for router\n");
akmhoque81c25e02012-09-10 14:50:33 -05001025 ON_ERROR_DESTROY(res);
akmhoque03004e62012-09-06 01:12:28 -05001026 }
1027 ccn_charbuf_destroy(&router_prefix);
1028
akmhoque7b791452012-10-30 11:24:56 -05001029 if ( nlsr->debugging )
1030 printf("Router Name : %s\n",nlsr->router_name);
akmhoque9e9fc722012-09-26 14:03:25 -05001031 writeLogg(__FILE__,__FUNCTION__,__LINE__,"Router Name : %s\n",nlsr->router_name);
akmhoque7b791452012-10-30 11:24:56 -05001032 if ( nlsr->debugging )
1033 printf("lsdb_version: %s\n",nlsr->lsdb->lsdb_version);
akmhoque9e9fc722012-09-26 14:03:25 -05001034 writeLogg(__FILE__,__FUNCTION__,__LINE__,"lsdb_version: %s\n",nlsr->lsdb->lsdb_version);
akmhoque59980a52012-08-09 12:36:09 -05001035
akmhoque53f64222012-09-05 13:57:51 -05001036 print_name_prefix_from_npl();
1037 print_adjacent_from_adl();
akmhoque53f64222012-09-05 13:57:51 -05001038 build_and_install_name_lsas();
1039 print_name_lsdb();
1040
1041 nlsr->sched = ccn_schedule_create(nlsr, &ndn_rtr_ticker);
akmhoque03004e62012-09-06 01:12:28 -05001042 nlsr->event_send_info_interest = ccn_schedule_event(nlsr->sched, 1, &send_info_interest, NULL, 0);
akmhoqueffacaa82012-09-13 17:48:30 -05001043 nlsr->event = ccn_schedule_event(nlsr->sched, 60000000, &refresh_lsdb, NULL, 0);
akmhoque1c9b92f2012-08-13 10:57:50 -05001044
akmhoque1771c412012-11-09 13:06:08 -06001045
akmhoque59980a52012-08-09 12:36:09 -05001046 while(1)
akmhoque29c1db52012-09-07 14:47:43 -05001047 {
akmhoqueffacaa82012-09-13 17:48:30 -05001048 if ( nlsr->semaphor == NLSR_UNLOCKED )
akmhoque29c1db52012-09-07 14:47:43 -05001049 {
akmhoqueffacaa82012-09-13 17:48:30 -05001050 if( nlsr->sched != NULL )
1051 {
akmhoque1771c412012-11-09 13:06:08 -06001052 long int micro_sec=ccn_schedule_run(nlsr->sched);
1053 res=nlsr_api_server_poll(micro_sec,ccn_fd);
1054 ON_ERROR_DESTROY(res);
akmhoqueffacaa82012-09-13 17:48:30 -05001055 }
1056 if(nlsr->ccn != NULL)
1057 {
akmhoque1771c412012-11-09 13:06:08 -06001058 res = ccn_run(nlsr->ccn, 0);
akmhoqueffacaa82012-09-13 17:48:30 -05001059 }
1060 if (!(nlsr->sched && nlsr->ccn))
1061 {
1062 break;
1063 }
akmhoque29c1db52012-09-07 14:47:43 -05001064 }
1065
akmhoque59980a52012-08-09 12:36:09 -05001066 }
akmhoque1771c412012-11-09 13:06:08 -06001067
akmhoque59980a52012-08-09 12:36:09 -05001068
akmhoque59980a52012-08-09 12:36:09 -05001069 return 0;
1070}
1071