/[dynamips]/upstream/dynamips-0.2.6-RC2/dynamips.c
This is repository of my old source code which isn't updated any more. Go to git.rot13.org for current projects!
ViewVC logotype

Contents of /upstream/dynamips-0.2.6-RC2/dynamips.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 3 - (show annotations)
Sat Oct 6 16:05:34 2007 UTC (16 years, 5 months ago) by dpavlin
File MIME type: text/plain
File size: 24467 byte(s)
dynamips-0.2.6-RC2

1 /*
2 * Cisco 7200 (Predator) simulation platform.
3 * Copyright (c) 2005,2006 Christophe Fillot (cf@utc.fr)
4 *
5 * Many thanks to Nicolas Szalay for his patch
6 * for the command line parsing and virtual machine
7 * settings (RAM, ROM, NVRAM, ...)
8 */
9
10 #include <stdio.h>
11 #include <stdlib.h>
12 #include <unistd.h>
13 #include <string.h>
14 #include <errno.h>
15 #include <sys/types.h>
16 #include <sys/stat.h>
17 #include <sys/mman.h>
18 #include <signal.h>
19 #include <fcntl.h>
20 #include <assert.h>
21 #include <getopt.h>
22
23 #include ARCH_INC_FILE
24
25 #include "dynamips.h"
26 #include "mips64.h"
27 #include "mips64_exec.h"
28 #include "dev_c7200.h"
29 #include "dev_c3600.h"
30 #include "dev_vtty.h"
31 #include "ptask.h"
32 #include "timer.h"
33 #include "registry.h"
34 #include "hypervisor.h"
35 #include "net_io.h"
36 #include "net_io_bridge.h"
37 #include "net_io_filter.h"
38 #include "crc.h"
39 #include "atm.h"
40 #include "frame_relay.h"
41 #include "eth_switch.h"
42 #ifdef GEN_ETH
43 #include "gen_eth.h"
44 #endif
45 #ifdef PROFILE
46 #include "profiler.h"
47 #endif
48
49 /* Default name for logfile */
50 #define LOGFILE_DEFAULT_NAME "dynamips_log.txt"
51
52 /* Software version */
53 const char *sw_version = DYNAMIPS_VERSION"-"JIT_ARCH;
54
55 /* Hypervisor */
56 int hypervisor_mode = 0;
57 int hypervisor_tcp_port = 0;
58
59 /* Log file */
60 char *log_file_name = NULL;
61 FILE *log_file = NULL;
62
63 /* VM flags */
64 volatile int vm_save_state = 0;
65
66 /* Generic signal handler */
67 void signal_gen_handler(int sig)
68 {
69 switch(sig) {
70 case SIGHUP:
71 /* For future use */
72 break;
73
74 case SIGQUIT:
75 /* save VM context */
76 vm_save_state = TRUE;
77 break;
78
79 case SIGINT:
80 /* CTRL+C has been pressed */
81 if (hypervisor_mode)
82 hypervisor_stopsig();
83 else {
84 /* In theory, this shouldn't happen thanks to VTTY settings */
85 vm_instance_t *vm;
86
87 if ((vm = vm_acquire("default")) != NULL) {
88 /* Only forward ctrl-c if user has requested local terminal */
89 if (vm->vtty_con_type == VTTY_TYPE_TERM) {
90 vtty_store_ctrlc(vm->vtty_con);
91 } else {
92 vm_stop(vm);
93 }
94 vm_release(vm);
95 } else {
96 fprintf(stderr,"Error: Cannot acquire instance handle.\n");
97 }
98 }
99 break;
100
101 default:
102 fprintf(stderr,"Unhandled signal %d\n",sig);
103 }
104 }
105
106 /* Setups signals */
107 static void setup_signals(void)
108 {
109 struct sigaction act;
110
111 memset(&act,0,sizeof(act));
112 act.sa_handler = signal_gen_handler;
113 act.sa_flags = SA_RESTART;
114 sigaction(SIGHUP,&act,NULL);
115 sigaction(SIGQUIT,&act,NULL);
116 sigaction(SIGINT,&act,NULL);
117 }
118
119 /* Create general log file */
120 static void create_log_file(void)
121 {
122 /* Set the default value of the log file name */
123 if (!log_file_name) {
124 if (!(log_file_name = strdup(LOGFILE_DEFAULT_NAME))) {
125 fprintf(stderr,"Unable to set log file name.\n");
126 exit(EXIT_FAILURE);
127 }
128 }
129
130 if (!(log_file = fopen(log_file_name,"w"))) {
131 fprintf(stderr,"Unable to create log file (%s).\n",strerror(errno));
132 exit(EXIT_FAILURE);
133 }
134 }
135
136 /* Close general log file */
137 static void close_log_file(void)
138 {
139 if (log_file) fclose(log_file);
140 free(log_file_name);
141
142 log_file = NULL;
143 log_file_name = NULL;
144 }
145
146 /* Display the command line use */
147 static void show_usage(int argc,char *argv[],int platform)
148 {
149 u_int def_ram_size,def_rom_size,def_nvram_size;
150 u_int def_conf_reg,def_clock_div;
151 u_int def_disk0_size,def_disk1_size;
152 u_int def_nm_iomem_size = 0;
153
154 switch(platform) {
155 case VM_TYPE_C7200:
156 def_ram_size = C7200_DEFAULT_RAM_SIZE;
157 def_rom_size = C7200_DEFAULT_ROM_SIZE;
158 def_nvram_size = C7200_DEFAULT_NVRAM_SIZE;
159 def_conf_reg = C7200_DEFAULT_CONF_REG;
160 def_clock_div = C7200_DEFAULT_CLOCK_DIV;
161 def_disk0_size = C7200_DEFAULT_DISK0_SIZE;
162 def_disk1_size = C7200_DEFAULT_DISK1_SIZE;
163 break;
164 case VM_TYPE_C3600:
165 def_ram_size = C3600_DEFAULT_RAM_SIZE;
166 def_rom_size = C3600_DEFAULT_ROM_SIZE;
167 def_nvram_size = C3600_DEFAULT_NVRAM_SIZE;
168 def_conf_reg = C3600_DEFAULT_CONF_REG;
169 def_clock_div = C3600_DEFAULT_CLOCK_DIV;
170 def_disk0_size = C3600_DEFAULT_DISK0_SIZE;
171 def_disk1_size = C3600_DEFAULT_DISK1_SIZE;
172 def_nm_iomem_size = C3600_DEFAULT_IOMEM_SIZE;
173 break;
174 default:
175 fprintf(stderr,"show_usage: invalid platform.\n");
176 return;
177 }
178
179 printf("Usage: %s [options] <ios_image>\n\n",argv[0]);
180
181 printf("Available options:\n"
182 " -H <tcp_port> : Run in hypervisor mode\n\n"
183 " -P <platform> : Platform to emulate (7200 or 3600) "
184 "(default: 7200)\n\n"
185 " -l <log_file> : Set logging file (default is %s)\n"
186 " -j : Disable the JIT compiler, very slow\n"
187 " --exec-area <size> : Set the exec area size (default: %d Mb)\n"
188 " --idle-pc <pc> : Set the idle PC (default: disabled)\n"
189 " --timer-itv <val> : Timer IRQ interval check (default: %u)\n"
190 "\n"
191 " -i <instance> : Set instance ID\n"
192 " -r <ram_size> : Set the virtual RAM size (default: %u Mb)\n"
193 " -o <rom_size> : Set the virtual ROM size (default: %u Mb)\n"
194 " -n <nvram_size> : Set the NVRAM size (default: %d Kb)\n"
195 " -c <conf_reg> : Set the configuration register "
196 "(default: 0x%04x)\n"
197 " -m <mac_addr> : Set the MAC address of the chassis\n"
198 " (default: automatically generated)\n"
199 " -C <cfg_file> : Import an IOS configuration file "
200 "into NVRAM\n"
201 " -X : Do not use a file to simulate RAM (faster)\n"
202 " -R <rom_file> : Load an alternate ROM (default: embedded)\n"
203 " -k <clock_div> : Set the clock divisor (default: %d)\n"
204 "\n"
205 " -T <port> : Console is on TCP <port>\n"
206 " -U <si_desc> : Console in on serial interface <si_desc>\n"
207 " (default is on the terminal)\n"
208 "\n"
209 " -A <port> : AUX is on TCP <port>\n"
210 " -B <si_desc> : AUX is on serial interface <si_desc>\n"
211 " (default is no AUX port)\n"
212 "\n"
213 " --disk0 <size> : Set PCMCIA ATA disk0: size "
214 "(default: %u Mb)\n"
215 " --disk1 <size> : Set PCMCIA ATA disk1: size "
216 "(default: %u Mb)\n"
217 "\n",
218 LOGFILE_DEFAULT_NAME,MIPS_EXEC_AREA_SIZE,VM_TIMER_IRQ_CHECK_ITV,
219 def_ram_size,def_rom_size,def_nvram_size,def_conf_reg,
220 def_clock_div,def_disk0_size,def_disk1_size);
221
222 switch(platform) {
223 case VM_TYPE_C7200:
224 printf(" -t <npe_type> : Select NPE type (default: \"%s\")\n"
225 " -M <midplane> : Select Midplane (\"std\" or \"vxr\")\n"
226 " -p <pa_desc> : Define a Port Adapter\n"
227 " -s <pa_nio> : Bind a Network IO interface to a "
228 "Port Adapter\n",
229 C7200_DEFAULT_NPE_TYPE);
230 break;
231
232 case VM_TYPE_C3600:
233 printf(" -t <chassis_type> : Select Chassis type "
234 "(default: \"%s\")\n"
235 " --iomem-size <val> : IO memory (in percents, default: %u)\n"
236 " -p <nm_desc> : Define a Network Module\n"
237 " -s <nm_nio> : Bind a Network IO interface to a "
238 "Network Module\n",
239 C3600_DEFAULT_CHASSIS,def_nm_iomem_size);
240 break;
241 }
242
243 printf("\n"
244 #if DEBUG_SYM_TREE
245 " -S <sym_file> : Load a symbol file\n"
246 #endif
247 " -a <cfg_file> : Virtual ATM switch configuration file\n"
248 " -f <cfg_file> : Virtual Frame-Relay switch configuration "
249 "file\n"
250 " -E <cfg_file> : Virtual Ethernet switch configuration file\n"
251 " -b <cfg_file> : Virtual bridge configuration file\n"
252 " -e : Show network device list of the "
253 "host machine\n"
254 "\n");
255
256 printf("<si_desc> format:\n"
257 " \"device{:baudrate{:databits{:parity{:stopbits{:hwflow}}}}}}\"\n"
258 "\n");
259
260 switch(platform) {
261 case VM_TYPE_C7200:
262 printf("<pa_desc> format:\n"
263 " \"slot:pa_driver\"\n"
264 "\n");
265
266 printf("<pa_nio> format:\n"
267 " \"slot:port:netio_type{:netio_parameters}\"\n"
268 "\n");
269
270 /* Show the possible NPE drivers */
271 c7200_npe_show_drivers();
272
273 /* Show the possible PA drivers */
274 c7200_pa_show_drivers();
275 break;
276
277 case VM_TYPE_C3600:
278 printf("<nm_desc> format:\n"
279 " \"slot:nm_driver\"\n"
280 "\n");
281
282 printf("<nm_nio> format:\n"
283 " \"slot:port:netio_type{:netio_parameters}\"\n"
284 "\n");
285
286 /* Show the possible chassis types for C3600 platform */
287 c3600_chassis_show_drivers();
288
289 /* Show the possible PA drivers */
290 c3600_nm_show_drivers();
291 break;
292 }
293
294 /* Show the possible NETIO types */
295 netio_show_types();
296 }
297
298 /* Find an option in the command line */
299 static char *cli_find_option(int argc,char *argv[],char *opt)
300 {
301 int i;
302
303 for(i=1;i<argc;i++) {
304 if (!strncmp(argv[i],opt,2)) {
305 if (argv[i][2] != 0)
306 return(&argv[i][2]);
307 else {
308 if (argv[i+1] != NULL)
309 return(argv[i+1]);
310 else {
311 fprintf(stderr,"Error: option '%s': no argument specified.\n",
312 opt);
313 exit(EXIT_FAILURE);
314 }
315 }
316 }
317 }
318
319 return NULL;
320 }
321
322 /* Determine the platform (Cisco 3600, 7200). Default is Cisco 7200 */
323 static int cli_get_platform_type(int argc,char *argv[])
324 {
325 int vm_type = VM_TYPE_C7200;
326 char *str;
327
328 if ((str = cli_find_option(argc,argv,"-P"))) {
329 if (!strcmp(str,"3600"))
330 vm_type = VM_TYPE_C3600;
331 else if (!strcmp(str,"7200"))
332 vm_type = VM_TYPE_C7200;
333 else
334 fprintf(stderr,"Invalid platform type '%s'\n",str);
335 }
336
337 return(vm_type);
338 }
339
340 /* Command Line long options */
341 #define OPT_DISK0_SIZE 0x100
342 #define OPT_DISK1_SIZE 0x101
343 #define OPT_EXEC_AREA 0x102
344 #define OPT_IDLE_PC 0x103
345 #define OPT_TIMER_ITV 0x104
346 #define OPT_VM_DEBUG 0x105
347 #define OPT_IOMEM_SIZE 0x106
348
349 static struct option cmd_line_lopts[] = {
350 { "disk0" , 1, NULL, OPT_DISK0_SIZE },
351 { "disk1" , 1, NULL, OPT_DISK1_SIZE },
352 { "exec-area" , 1, NULL, OPT_EXEC_AREA },
353 { "idle-pc" , 1, NULL, OPT_IDLE_PC },
354 { "timer-itv" , 1, NULL, OPT_TIMER_ITV },
355 { "vm-debug" , 1, NULL, OPT_VM_DEBUG },
356 { "iomem-size" , 1, NULL, OPT_IOMEM_SIZE },
357 { NULL , 0, NULL, 0 },
358 };
359
360 /* Parse specific options for the Cisco 7200 platform */
361 static int cli_parse_c7200_options(vm_instance_t *vm,int option)
362 {
363 c7200_t *router;
364
365 router = VM_C7200(vm);
366
367 switch(option) {
368 /* NPE type */
369 case 't':
370 c7200_npe_set_type(router,optarg);
371 break;
372
373 /* Midplane type */
374 case 'M':
375 c7200_midplane_set_type(router,optarg);
376 break;
377
378 /* Set the base MAC address */
379 case 'm':
380 if (!c7200_midplane_set_mac_addr(router,optarg))
381 printf("MAC address set to '%s'.\n",optarg);
382 break;
383
384 /* PA settings */
385 case 'p':
386 return(c7200_cmd_pa_create(router,optarg));
387
388 /* PA NIO settings */
389 case 's':
390 return(c7200_cmd_add_nio(router,optarg));
391
392 /* Unknown option */
393 default:
394 return(-1);
395 }
396
397 return(0);
398 }
399
400 /* Parse specific options for the Cisco 3600 platform */
401 static int cli_parse_c3600_options(vm_instance_t *vm,int option)
402 {
403 c3600_t *router;
404
405 router = VM_C3600(vm);
406
407 switch(option) {
408 /* chassis type */
409 case 't':
410 c3600_chassis_set_type(router,optarg);
411 break;
412
413 /* IO memory reserved for NMs (in percents!) */
414 case OPT_IOMEM_SIZE:
415 router->nm_iomem_size = 0x8000 | atoi(optarg);
416 break;
417
418 /* NM settings */
419 case 'p':
420 return(c3600_cmd_nm_create(router,optarg));
421
422 /* NM NIO settings */
423 case 's':
424 return(c3600_cmd_add_nio(router,optarg));
425
426 /* Unknown option */
427 default:
428 return(-1);
429 }
430
431 return(0);
432 }
433
434 /* Create a router instance */
435 static vm_instance_t *cli_create_instance(char *name,int platform_type,
436 int instance_id)
437 {
438 c7200_t *c7200;
439 c3600_t *c3600;
440
441 switch(platform_type) {
442 case VM_TYPE_C7200:
443 if (!(c7200 = c7200_create_instance(name,instance_id))) {
444 fprintf(stderr,"C7200: unable to create instance!\n");
445 return NULL;
446 }
447 return(c7200->vm);
448
449 case VM_TYPE_C3600:
450 if (!(c3600 = c3600_create_instance(name,instance_id))) {
451 fprintf(stderr,"C3600: unable to create instance!\n");
452 return NULL;
453 }
454 return(c3600->vm);
455
456 default:
457 fprintf(stderr,"Unknown platform type '%d'!\n",platform_type);
458 return NULL;
459 }
460 }
461
462 /* Parse the command line */
463 static int parse_std_cmd_line(int argc,char *argv[],int *platform)
464 {
465 char *options_list =
466 "r:o:n:c:m:l:C:i:jt:p:s:k:T:U:A:B:a:f:E:b:S:R:M:eXP:N:";
467 vm_instance_t *vm;
468 int instance_id;
469 int res,option;
470 char *str;
471
472 /* Get the instance ID */
473 instance_id = 0;
474
475 /* Use the old VM file naming type */
476 vm_file_naming_type = 1;
477
478 if ((str = cli_find_option(argc,argv,"-i"))) {
479 instance_id = atoi(str);
480 printf("Instance ID set to %d.\n",instance_id);
481 }
482
483 if ((str = cli_find_option(argc,argv,"-N")))
484 vm_file_naming_type = atoi(str);
485
486 /* Get the platform type */
487 *platform = cli_get_platform_type(argc,argv);
488
489 /* Create the default instance */
490 if (!(vm = cli_create_instance("default",*platform,instance_id)))
491 exit(EXIT_FAILURE);
492
493 opterr = 0;
494
495 while((option = getopt_long(argc,argv,options_list,
496 cmd_line_lopts,NULL)) != -1)
497 {
498 switch(option)
499 {
500 /* Instance ID (already managed) */
501 case 'i':
502 break;
503
504 /* Platform (already managed) */
505 case 'P':
506 break;
507
508 /* RAM size */
509 case 'r':
510 vm->ram_size = strtol(optarg, NULL, 10);
511 printf("Virtual RAM size set to %d MB.\n",vm->ram_size);
512 break;
513
514 /* ROM size */
515 case 'o':
516 vm->rom_size = strtol(optarg, NULL, 10);
517 printf("Virtual ROM size set to %d MB.\n",vm->rom_size);
518 break;
519
520 /* NVRAM size */
521 case 'n':
522 vm->nvram_size = strtol(optarg, NULL, 10);
523 printf("NVRAM size set to %d KB.\n",vm->nvram_size);
524 break;
525
526 /* Execution area size */
527 case OPT_EXEC_AREA:
528 vm->exec_area_size = atoi(optarg);
529 break;
530
531 /* PCMCIA disk0 size */
532 case OPT_DISK0_SIZE:
533 vm->pcmcia_disk_size[0] = atoi(optarg);
534 printf("PCMCIA ATA disk0 size set to %u MB.\n",
535 vm->pcmcia_disk_size[0]);
536 break;
537
538 /* PCMCIA disk1 size */
539 case OPT_DISK1_SIZE:
540 vm->pcmcia_disk_size[1] = atoi(optarg);
541 printf("PCMCIA ATA disk1 size set to %u MB.\n",
542 vm->pcmcia_disk_size[1]);
543 break;
544
545 /* Config Register */
546 case 'c':
547 vm->conf_reg_setup = strtol(optarg, NULL, 0);
548 printf("Config. Register set to 0x%x.\n",vm->conf_reg_setup);
549 break;
550
551 /* IOS configuration file */
552 case 'C':
553 vm_ios_set_config(vm,optarg);
554 break;
555
556 /* Use physical memory to emulate RAM (no-mapped file) */
557 case 'X':
558 vm->ram_mmap = 0;
559 break;
560
561 /* Alternate ROM */
562 case 'R':
563 vm->rom_filename = optarg;
564 break;
565
566 /* Idle PC */
567 case OPT_IDLE_PC:
568 vm->idle_pc = strtoull(optarg,NULL,0);
569 printf("Idle PC set to 0x%llx.\n",vm->idle_pc);
570 break;
571
572 /* Timer IRQ check interval */
573 case OPT_TIMER_ITV:
574 vm->timer_irq_check_itv = atoi(optarg);
575 break;
576
577 /* Clock divisor */
578 case 'k':
579 vm->clock_divisor = atoi(optarg);
580
581 if (!vm->clock_divisor) {
582 fprintf(stderr,"Invalid Clock Divisor specified!\n");
583 exit(EXIT_FAILURE);
584 }
585
586 printf("Using a clock divisor of %d.\n",vm->clock_divisor);
587 break;
588
589 /* Disable JIT */
590 case 'j':
591 vm->jit_use = FALSE;
592 break;
593
594 /* VM debug level */
595 case OPT_VM_DEBUG:
596 vm->debug_level = atoi(optarg);
597 break;
598
599 /* Log file */
600 case 'l':
601 if (!(log_file_name = strdup(optarg))) {
602 fprintf(stderr,"Unable to set log file name.\n");
603 exit(EXIT_FAILURE);
604 }
605 printf("Log file: writing to %s\n",log_file_name);
606 break;
607
608 #if DEBUG_SYM_TREE
609 /* Symbol file */
610 case 'S':
611 vm->sym_filename = strdup(optarg);
612 break;
613 #endif
614
615 /* TCP server for Console Port */
616 case 'T':
617 vm->vtty_con_type = VTTY_TYPE_TCP;
618 vm->vtty_con_tcp_port = atoi(optarg);
619 break;
620
621 /* Serial interface for Console port */
622 case 'U':
623 vm->vtty_con_type = VTTY_TYPE_SERIAL;
624 if (vtty_parse_serial_option(&vm->vtty_con_serial_option,optarg)) {
625 fprintf(stderr,
626 "Invalid Console serial interface descriptor!\n");
627 exit(EXIT_FAILURE);
628 }
629 break;
630
631 /* TCP server for AUX Port */
632 case 'A':
633 vm->vtty_aux_type = VTTY_TYPE_TCP;
634 vm->vtty_aux_tcp_port = atoi(optarg);
635 break;
636
637 /* Serial interface for AUX port */
638 case 'B':
639 vm->vtty_aux_type = VTTY_TYPE_SERIAL;
640 if (vtty_parse_serial_option(&vm->vtty_aux_serial_option,optarg)) {
641 fprintf(stderr,"Invalid AUX serial interface descriptor!\n");
642 exit(EXIT_FAILURE);
643 }
644 break;
645
646 /* Virtual ATM switch */
647 case 'a':
648 if (atmsw_start(optarg) == -1)
649 exit(EXIT_FAILURE);
650 break;
651
652 /* Virtual Frame-Relay switch */
653 case 'f':
654 if (frsw_start(optarg) == -1)
655 exit(EXIT_FAILURE);
656 break;
657
658 /* Virtual Ethernet switch */
659 case 'E':
660 if (ethsw_start(optarg) == -1)
661 exit(EXIT_FAILURE);
662 break;
663
664 /* Virtual bridge */
665 case 'b':
666 if (netio_bridge_start(optarg) == -1)
667 exit(EXIT_FAILURE);
668 break;
669
670 #ifdef GEN_ETH
671 /* Ethernet device list */
672 case 'e':
673 gen_eth_show_dev_list();
674 exit(EXIT_SUCCESS);
675 #endif
676
677 /* Oops ! */
678 case '?':
679 show_usage(argc,argv,*platform);
680 exit(EXIT_FAILURE);
681
682 /* Parse options specific to the platform */
683 default:
684 res = 0;
685
686 switch(vm->type) {
687 case VM_TYPE_C7200:
688 res = cli_parse_c7200_options(vm,option);
689 break;
690 case VM_TYPE_C3600:
691 res = cli_parse_c3600_options(vm,option);
692 break;
693 }
694
695 if (res == -1)
696 exit(EXIT_FAILURE);
697 }
698 }
699
700 /* Last argument, this is the IOS filename */
701 if (optind == (argc - 1)) {
702 /* setting IOS image file */
703 vm_ios_set_image(vm,argv[optind]);
704 printf("IOS image file: %s\n\n",vm->ios_image);
705 } else {
706 /* IOS missing */
707 fprintf(stderr,"Please specify an IOS image filename\n");
708 show_usage(argc,argv,*platform);
709 exit(EXIT_FAILURE);
710 }
711
712 vm_release(vm);
713 return(0);
714 }
715
716 /*
717 * Run in hypervisor mode with a config file if the "-H" option
718 * is present in command line.
719 */
720 static int run_hypervisor(int argc,char *argv[])
721 {
722 char *options_list = "H:l:hN:";
723 int i,option;
724
725 for(i=1;i<argc;i++)
726 if (!strcmp(argv[i],"-H")) {
727 hypervisor_mode = 1;
728 break;
729 }
730
731 /* standard mode with one instance */
732 if (!hypervisor_mode)
733 return(FALSE);
734
735 opterr = 0;
736 while((option = getopt(argc,argv,options_list)) != -1) {
737 switch(option)
738 {
739 /* Hypervisor TCP port */
740 case 'H':
741 hypervisor_tcp_port = atoi(optarg);
742 break;
743
744 /* Log file */
745 case 'l':
746 if (!(log_file_name = malloc(strlen(optarg)+1))) {
747 fprintf(stderr,"Unable to set log file name.\n");
748 exit(EXIT_FAILURE);
749 }
750 strcpy(log_file_name, optarg);
751 printf("Log file: writing to %s\n",log_file_name);
752 break;
753
754 /* VM file naming type */
755 case 'N':
756 vm_file_naming_type = atoi(optarg);
757 break;
758
759 /* Oops ! */
760 case '?':
761 show_usage(argc,argv,VM_TYPE_C7200);
762 exit(EXIT_FAILURE);
763 }
764 }
765
766 return(TRUE);
767 }
768
769 /* Delete all objects */
770 void dynamips_reset(void)
771 {
772 printf("Shutdown in progress...\n");
773
774 /* Delete all C7200 and C3600 instances */
775 c7200_delete_all_instances();
776 c3600_delete_all_instances();
777
778 /* Delete ATM and Frame-Relay switches + bridges */
779 netio_bridge_delete_all();
780 atmsw_delete_all();
781 frsw_delete_all();
782 ethsw_delete_all();
783
784 /* Delete all NIO descriptors */
785 netio_delete_all();
786
787 printf("Shutdown completed.\n");
788 }
789
790 int main(int argc,char *argv[])
791 {
792 vm_instance_t *vm;
793 int platform,res;
794
795 /* Default emulation: Cisco 7200 */
796 platform = VM_TYPE_C7200;
797
798 #ifdef PROFILE
799 atexit(profiler_savestat);
800 #endif
801
802 printf("Cisco 7200 Simulation Platform (version %s)\n",sw_version);
803 printf("Copyright (c) 2005,2006 Christophe Fillot.\n\n");
804
805 /* Initialize timers */
806 timer_init();
807
808 /* Initialize object registry */
809 registry_init();
810
811 /* Initialize ATM module (for HEC checksums) */
812 atm_init();
813
814 /* Initialize CRC functions */
815 crc_init();
816
817 /* Initialize NetIO code */
818 netio_rxl_init();
819
820 /* Initialize NetIO packet filters */
821 netio_filter_load_all();
822
823 /* Initialize VTTY code */
824 vtty_init();
825
826 /* Parse standard command line */
827 if (!run_hypervisor(argc,argv))
828 parse_std_cmd_line(argc,argv,&platform);
829
830 /* Create general log file */
831 create_log_file();
832
833 /* Periodic tasks initialization */
834 if (ptask_init(0) == -1)
835 exit(EXIT_FAILURE);
836
837 /* Create instruction lookup tables */
838 mips64_jit_create_ilt();
839 mips64_exec_create_ilt();
840
841 setup_signals();
842
843 if (!hypervisor_mode) {
844 /* Initialize the default instance */
845 vm = vm_acquire("default");
846 assert(vm != NULL);
847
848 switch(platform) {
849 case VM_TYPE_C7200:
850 res = c7200_init_instance(VM_C7200(vm));
851 break;
852 case VM_TYPE_C3600:
853 res = c3600_init_instance(VM_C3600(vm));
854 break;
855 default:
856 res = -1;
857 }
858
859 if (res == -1) {
860 fprintf(stderr,"Unable to initialize router instance.\n");
861 exit(EXIT_FAILURE);
862 }
863
864 #if DEBUG_PERF_COUNTER
865 {
866 m_uint64_t prev = 0,delta;
867 while(vm->status == VM_STATUS_RUNNING) {
868 delta = vm->boot_cpu->perf_counter - prev;
869 prev = vm->boot_cpu->perf_counter;
870 printf("delta = %llu\n",delta);
871 sleep(1);
872 }
873 }
874 #else
875 /* Start instance monitoring */
876 vm_monitor(vm);
877 #endif
878
879 /* Free resources used by instance */
880 vm_release(vm);
881 } else {
882 hypervisor_tcp_server(hypervisor_tcp_port);
883 }
884
885 dynamips_reset();
886 close_log_file();
887 return(0);
888 }

  ViewVC Help
Powered by ViewVC 1.1.26