main.c revision 1.7 1 /* $NetBSD: main.c,v 1.7 2012/11/12 18:39:00 kefren Exp $ */
2
3 /*-
4 * Copyright (c) 2010 The NetBSD Foundation, Inc.
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Mihai Chelaru <kefren (at) NetBSD.org>
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE.
30 */
31
32 #include <netinet/in.h>
33 #include <sys/stat.h>
34 #include <sys/socket.h>
35 #include <sys/select.h>
36 #include <arpa/inet.h>
37
38 #include <stdio.h>
39 #include <stdlib.h>
40 #include <strings.h>
41 #include <unistd.h>
42
43 #include "ldp.h"
44 #include "ldp_command.h"
45 #include "socketops.h"
46 #include "tlv.h"
47 #include "pdu.h"
48 #include "fsm.h"
49 #include "ldp_errors.h"
50 #include "mpls_interface.h"
51 #include "conffile.h"
52
53 extern int ls; /* TCP listening socket */
54 extern int dont_catch;
55 extern int command_port;
56 extern int command_socket;
57
58 extern int debug_f, warn_f, syslog_f;
59
60 extern struct sockaddr mplssockaddr;
61 extern struct in_addr conf_ldp_id;
62
63 void print_usage(char *myself)
64 {
65 printf("\nUsage: %s [-DdfhW] [-c config_file] [-p port]\n\n", myself);
66 }
67
68 int
69 main(int argc, char *argv[])
70 {
71 int ch, forkres, dontfork = 0, cpf;
72 char conffile[PATH_MAX + 1];
73
74 strlcpy(conffile, CONFFILE, sizeof(conffile));
75 while((ch = getopt(argc, argv, "c:dDfhp:W")) != -1)
76 switch(ch) {
77 case 'c':
78 strlcpy(conffile, optarg, sizeof(conffile));
79 break;
80 case 'D':
81 debug_f = 1;
82 break;
83 case 'd':
84 dont_catch = 1;
85 break;
86 case 'f':
87 dontfork = 1;
88 break;
89 case 'p':
90 if ((command_port = atoi(optarg)) < 1) {
91 print_usage(argv[0]);
92 return EXIT_FAILURE;
93 }
94 break;
95 case 'W':
96 warn_f = 1;
97 break;
98 case 'h':
99 default:
100 print_usage(argv[0]);
101 return EXIT_FAILURE;
102 break;
103 }
104 if (geteuid()) {
105 fatalp("You have to run this as ROOT\n");
106 return EXIT_FAILURE;
107 }
108
109 cpf = conf_parsefile(conffile);
110 if (cpf < 0 && strcmp(conffile, CONFFILE)) {
111 fatalp("Cannot parse config file: %s\n", conffile);
112 return EXIT_FAILURE;
113 } else if (cpf > 0) {
114 fatalp("Cannot parse line %d in config file\n", cpf);
115 return EXIT_FAILURE;
116 }
117
118 if (set_my_ldp_id()) {
119 fatalp("Cannot set LDP ID\n");
120 return EXIT_FAILURE;
121 }
122 if (conf_ldp_id.s_addr != 0)
123 strlcpy(my_ldp_id, inet_ntoa(conf_ldp_id), INET_ADDRSTRLEN);
124
125 if (mplssockaddr.sa_len == 0) {
126 fatalp("You need one mpls interface up and an IP "
127 "address set for it\n");
128 return EXIT_FAILURE;
129 }
130 if (mpls_start_ldp() == -1)
131 return EXIT_FAILURE;
132 if (!strcmp(LDP_ID, "0.0.0.0")) {
133 fatalp("Cannot set my LDP ID.\nAre you sure you've "
134 "got a non-loopback INET interface UP ?\n");
135 return EXIT_FAILURE;
136 }
137 init_command_sockets();
138 if ((command_socket = create_command_socket(command_port)) < 1) {
139 fatalp("Cannot create command socket\n");
140 return EXIT_FAILURE;
141 }
142 if (create_hello_sockets() != 0) {
143 fatalp("Cannot create hello socket\n");
144 return EXIT_FAILURE;
145 }
146
147 ls = create_listening_socket();
148
149 if (ls < 0) {
150 fatalp("Cannot create listening socket\n");
151 return EXIT_FAILURE;
152 }
153
154 if (dontfork == 1)
155 return the_big_loop();
156
157 forkres = fork();
158 if (forkres == 0) {
159 syslog_f = 1;
160 return the_big_loop();
161 }
162 if (forkres < 0)
163 perror("fork");
164
165 return EXIT_SUCCESS;
166 }
167