1/*
2 * udhcpc scripts
3 *
4 * Copyright 2004, Broadcom Corporation
5 * All Rights Reserved.
6 *
7 * THIS SOFTWARE IS OFFERED "AS IS", AND BROADCOM GRANTS NO WARRANTIES OF ANY
8 * KIND, EXPRESS OR IMPLIED, BY STATUTE, COMMUNICATION OR OTHERWISE. BROADCOM
9 * SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS
10 * FOR A SPECIFIC PURPOSE OR NONINFRINGEMENT CONCERNING THIS SOFTWARE.
11 *
12 * $Id: udhcpc.c,v 1.3 2009/03/03 02:39:54 james26_jang Exp $
13 */
14
15#include <stdio.h>
16#include <stdlib.h>
17#include <string.h>
18#include <net/route.h>
19#include <sys/socket.h>
20#include <netinet/in.h>
21#include <arpa/inet.h>
22#include <errno.h>
23#include <time.h>
24#include <unistd.h>
25
26#include <bcmnvram.h>
27#include <netconf.h>
28#include <shutils.h>
29#include <rc.h>
30
31char udhcpstate[8];
32
33static int
34expires(char *wan_ifname, unsigned int in)
35{
36	time_t now;
37	FILE *fp;
38	char tmp[100];
39	int unit;
40
41	if ((unit = wan_ifunit(wan_ifname)) < 0)
42		return -1;
43
44	time(&now);
45	snprintf(tmp, sizeof(tmp), "/tmp/udhcpc%d.expires", unit);
46	if (!(fp = fopen(tmp, "w"))) {
47		perror(tmp);
48		return errno;
49	}
50	fprintf(fp, "%d", (unsigned int) now + in);
51	fclose(fp);
52	return 0;
53}
54
55/*
56 * deconfig: This argument is used when udhcpc starts, and when a
57 * leases is lost. The script should put the interface in an up, but
58 * deconfigured state.
59*/
60static int
61deconfig(void)
62{
63	char *wan_ifname = safe_getenv("interface");
64	if (nvram_invmatch("wan0_proto", "l2tp"))
65		ifconfig(wan_ifname, IFUP, "0.0.0.0", NULL);
66	else	// fix hang-up issue
67		logmessage("dhcp client", "skipping resetting IP address to 0.0.0.0");
68	expires(wan_ifname, 0);
69
70	wan_down(wan_ifname);
71
72	logmessage("dhcp client", "%s: lease is lost", udhcpstate);
73	wanmessage("lost IP from server");
74	dprintf("done\n");
75	return 0;
76}
77
78/*
79 * bound: This argument is used when udhcpc moves from an unbound, to
80 * a bound state. All of the paramaters are set in enviromental
81 * variables, The script should configure the interface, and set any
82 * other relavent parameters (default gateway, dns server, etc).
83*/
84static int
85bound(void)
86{
87	char *wan_ifname = safe_getenv("interface");
88	char *value;
89	char tmp[100], prefix[] = "wanXXXXXXXXXX_";
90	int unit;
91#if 0
92	if ((unit = wan_ifunit(wan_ifname)) < 0)
93		return -1;
94
95	snprintf(prefix, sizeof(prefix), "wan%d_", unit);
96#endif
97
98	if ((unit = wan_ifunit(wan_ifname)) < 0)
99		strcpy(prefix, "wanx_");
100	else
101		snprintf(prefix, sizeof(prefix), "wan%d_", unit);
102
103	if ((value = getenv("ip")))
104		nvram_set(strcat_r(prefix, "ipaddr", tmp), trim_r(value));
105
106	if ((value = getenv("subnet")))
107		nvram_set(strcat_r(prefix, "netmask", tmp), trim_r(value));
108
109	if ((value = getenv("router")))
110		nvram_set(strcat_r(prefix, "gateway", tmp), trim_r(value));
111
112	if ((value = getenv("dns")))
113		nvram_set(strcat_r(prefix, "dns", tmp), trim_r(value));
114
115	if ((value = getenv("wins")))
116		nvram_set(strcat_r(prefix, "wins", tmp), trim_r(value));
117
118	nvram_set(strcat_r(prefix, "routes", tmp), getenv("routes"));
119	nvram_set(strcat_r(prefix, "msroutes", tmp), getenv("msroutes"));
120
121	//if ((value = getenv("hostname")))
122	//	sethostname(trim_r(value), strlen(value) + 1);
123
124	if ((value = getenv("domain")))
125		nvram_set(strcat_r(prefix, "domain", tmp), trim_r(value));
126	if ((value = getenv("lease"))) {
127		nvram_set(strcat_r(prefix, "lease", tmp), trim_r(value));
128		expires(wan_ifname, atoi(value));
129	}
130
131	ifconfig(wan_ifname, IFUP,
132			nvram_safe_get(strcat_r(prefix, "ipaddr", tmp)),
133			nvram_safe_get(strcat_r(prefix, "netmask", tmp)));
134
135	wan_up(wan_ifname);
136
137	logmessage("dhcp client", "%s IP : %s from %s",
138			udhcpstate,
139			nvram_safe_get(strcat_r(prefix, "ipaddr", tmp)),
140			nvram_safe_get(strcat_r(prefix, "gateway", tmp)));
141
142	wanmessage("");
143	dprintf("done\n");
144	return 0;
145}
146
147/*
148 * renew: This argument is used when a DHCP lease is renewed. All of
149 * the paramaters are set in enviromental variables. This argument is
150 * used when the interface is already configured, so the IP address,
151 * will not change, however, the other DHCP paramaters, such as the
152 * default gateway, subnet mask, and dns server may change.
153 */
154static int
155renew(void)
156{
157	bound();
158
159	dprintf("done\n");
160	return 0;
161}
162
163int
164udhcpc_main(int argc, char **argv)
165{
166	if(argv[1])
167		strcpy(udhcpstate, argv[1]);
168
169	if(!argv[1])
170		return EINVAL;
171	else if(strstr(argv[1], "deconfig"))
172		return deconfig();
173	else if(strstr(argv[1], "bound"))
174		return bound();
175	else if(strstr(argv[1], "renew"))
176		return renew();
177	else
178		return deconfig();
179}
180