1*86d7f5d3SJohn Marino /*
2*86d7f5d3SJohn Marino 
3*86d7f5d3SJohn Marino This code is not copyright, and is placed in the public domain. Feel free to
4*86d7f5d3SJohn Marino use and modify. Please send modifications and/or suggestions + bug fixes to
5*86d7f5d3SJohn Marino 
6*86d7f5d3SJohn Marino         Klas Heggemann <klas@nada.kth.se>
7*86d7f5d3SJohn Marino 
8*86d7f5d3SJohn Marino */
9*86d7f5d3SJohn Marino 
10*86d7f5d3SJohn Marino /*
11*86d7f5d3SJohn Marino  * $FreeBSD: src/usr.sbin/bootparamd/bootparamd/main.c,v 1.14 2008/08/02 00:10:02 cognet Exp $
12*86d7f5d3SJohn Marino  * $DragonFly: src/usr.sbin/bootparamd/bootparamd/main.c,v 1.6 2008/09/19 18:48:33 swildner Exp $
13*86d7f5d3SJohn Marino  */
14*86d7f5d3SJohn Marino #include <ctype.h>
15*86d7f5d3SJohn Marino #include <err.h>
16*86d7f5d3SJohn Marino #include <netdb.h>
17*86d7f5d3SJohn Marino #include <stdio.h>
18*86d7f5d3SJohn Marino #include <stdlib.h>
19*86d7f5d3SJohn Marino #include <string.h>
20*86d7f5d3SJohn Marino #include <syslog.h>
21*86d7f5d3SJohn Marino #include <unistd.h>
22*86d7f5d3SJohn Marino #include <rpc/rpc.h>
23*86d7f5d3SJohn Marino #include <rpc/pmap_clnt.h>
24*86d7f5d3SJohn Marino #include <sys/ioctl.h>
25*86d7f5d3SJohn Marino #include <sys/socket.h>
26*86d7f5d3SJohn Marino #include <sys/stat.h>
27*86d7f5d3SJohn Marino #include <sys/types.h>
28*86d7f5d3SJohn Marino #include <netinet/in.h>
29*86d7f5d3SJohn Marino #include <arpa/inet.h>
30*86d7f5d3SJohn Marino #include "bootparam_prot.h"
31*86d7f5d3SJohn Marino 
32*86d7f5d3SJohn Marino int debug = 0;
33*86d7f5d3SJohn Marino int dolog = 0;
34*86d7f5d3SJohn Marino in_addr_t route_addr = -1;
35*86d7f5d3SJohn Marino struct sockaddr_in my_addr;
36*86d7f5d3SJohn Marino char *bootpfile = "/etc/bootparams";
37*86d7f5d3SJohn Marino 
38*86d7f5d3SJohn Marino extern  void bootparamprog_1();
39*86d7f5d3SJohn Marino static void usage(void);
40*86d7f5d3SJohn Marino 
41*86d7f5d3SJohn Marino int
main(int argc,char ** argv)42*86d7f5d3SJohn Marino main(int argc, char **argv)
43*86d7f5d3SJohn Marino {
44*86d7f5d3SJohn Marino 	SVCXPRT *transp;
45*86d7f5d3SJohn Marino 	struct hostent *he;
46*86d7f5d3SJohn Marino 	struct stat buf;
47*86d7f5d3SJohn Marino 	int c;
48*86d7f5d3SJohn Marino 
49*86d7f5d3SJohn Marino 	while ((c = getopt(argc, argv,"dsr:f:")) != -1)
50*86d7f5d3SJohn Marino 	  switch (c) {
51*86d7f5d3SJohn Marino 	  case 'd':
52*86d7f5d3SJohn Marino 	    debug = 1;
53*86d7f5d3SJohn Marino 	    break;
54*86d7f5d3SJohn Marino 	  case 'r':
55*86d7f5d3SJohn Marino 	      if (isdigit((unsigned char)*optarg)) {
56*86d7f5d3SJohn Marino 		route_addr = inet_addr(optarg);
57*86d7f5d3SJohn Marino 		break;
58*86d7f5d3SJohn Marino 	      } else {
59*86d7f5d3SJohn Marino 		he = gethostbyname(optarg);
60*86d7f5d3SJohn Marino 		if (he) {
61*86d7f5d3SJohn Marino 		   bcopy(he->h_addr, (char *)&route_addr, sizeof(route_addr));
62*86d7f5d3SJohn Marino 		   break;
63*86d7f5d3SJohn Marino 		} else {
64*86d7f5d3SJohn Marino 		   errx(1, "no such host %s", optarg);
65*86d7f5d3SJohn Marino 		}
66*86d7f5d3SJohn Marino 	      }
67*86d7f5d3SJohn Marino 	  case 'f':
68*86d7f5d3SJohn Marino 	    bootpfile = optarg;
69*86d7f5d3SJohn Marino 	    break;
70*86d7f5d3SJohn Marino 	  case 's':
71*86d7f5d3SJohn Marino 	    dolog = 1;
72*86d7f5d3SJohn Marino #ifndef LOG_DAEMON
73*86d7f5d3SJohn Marino 	    openlog("bootparamd", 0 , 0);
74*86d7f5d3SJohn Marino #else
75*86d7f5d3SJohn Marino 	    openlog("bootparamd", 0 , LOG_DAEMON);
76*86d7f5d3SJohn Marino 	    setlogmask(LOG_UPTO(LOG_NOTICE));
77*86d7f5d3SJohn Marino #endif
78*86d7f5d3SJohn Marino 	    break;
79*86d7f5d3SJohn Marino 	  default:
80*86d7f5d3SJohn Marino 	    usage();
81*86d7f5d3SJohn Marino 	  }
82*86d7f5d3SJohn Marino 
83*86d7f5d3SJohn Marino 	if ( stat(bootpfile, &buf ) )
84*86d7f5d3SJohn Marino 	  err(1, "%s", bootpfile);
85*86d7f5d3SJohn Marino 
86*86d7f5d3SJohn Marino 	if (route_addr == -1) {
87*86d7f5d3SJohn Marino 	  get_myaddress(&my_addr);
88*86d7f5d3SJohn Marino 	  bcopy(&my_addr.sin_addr.s_addr, &route_addr, sizeof (route_addr));
89*86d7f5d3SJohn Marino 	}
90*86d7f5d3SJohn Marino 
91*86d7f5d3SJohn Marino 	if (!debug) {
92*86d7f5d3SJohn Marino 	  if (daemon(0,0))
93*86d7f5d3SJohn Marino 	    err(1, "fork");
94*86d7f5d3SJohn Marino 	}
95*86d7f5d3SJohn Marino 
96*86d7f5d3SJohn Marino 
97*86d7f5d3SJohn Marino 	pmap_unset(BOOTPARAMPROG, BOOTPARAMVERS);
98*86d7f5d3SJohn Marino 
99*86d7f5d3SJohn Marino 	transp = svcudp_create(RPC_ANYSOCK);
100*86d7f5d3SJohn Marino 	if (transp == NULL)
101*86d7f5d3SJohn Marino 		errx(1, "cannot create udp service");
102*86d7f5d3SJohn Marino 	if (!svc_register(transp, BOOTPARAMPROG, BOOTPARAMVERS, bootparamprog_1, IPPROTO_UDP))
103*86d7f5d3SJohn Marino 		errx(1, "unable to register (BOOTPARAMPROG, BOOTPARAMVERS, udp)");
104*86d7f5d3SJohn Marino 
105*86d7f5d3SJohn Marino 	svc_run();
106*86d7f5d3SJohn Marino 	errx(1, "svc_run returned");
107*86d7f5d3SJohn Marino }
108*86d7f5d3SJohn Marino 
109*86d7f5d3SJohn Marino static void
usage(void)110*86d7f5d3SJohn Marino usage(void)
111*86d7f5d3SJohn Marino {
112*86d7f5d3SJohn Marino 	fprintf(stderr,
113*86d7f5d3SJohn Marino 		"usage: bootparamd [-d] [-s] [-r router] [-f bootparmsfile]\n");
114*86d7f5d3SJohn Marino 	exit(1);
115*86d7f5d3SJohn Marino }
116