xref: /plan9/sys/src/9/boot/bootip.c (revision 6a9fc400c33447ef5e1cda7185cb4de2c8e8010e)
17dd7cddfSDavid du Colombier #include <u.h>
27dd7cddfSDavid du Colombier #include <libc.h>
37dd7cddfSDavid du Colombier #include <ip.h>
47dd7cddfSDavid du Colombier 
57dd7cddfSDavid du Colombier #include "boot.h"
67dd7cddfSDavid du Colombier 
77dd7cddfSDavid du Colombier static	uchar	fsip[IPaddrlen];
89a747e4fSDavid du Colombier 	uchar	auip[IPaddrlen];
97dd7cddfSDavid du Colombier static	char	mpoint[32];
107dd7cddfSDavid du Colombier 
117dd7cddfSDavid du Colombier static int isvalidip(uchar*);
127dd7cddfSDavid du Colombier static void netndb(char*, uchar*);
1380ee5cbfSDavid du Colombier static void netenv(char*, uchar*);
147dd7cddfSDavid du Colombier 
157dd7cddfSDavid du Colombier void
167dd7cddfSDavid du Colombier configip(void)
177dd7cddfSDavid du Colombier {
189a747e4fSDavid du Colombier 	int argc, pid;
197dd7cddfSDavid du Colombier 	char **argv, *p;
209a747e4fSDavid du Colombier 	Waitmsg *w;
217dd7cddfSDavid du Colombier 	char **arg;
227dd7cddfSDavid du Colombier 	char buf[32];
237dd7cddfSDavid du Colombier 
249a747e4fSDavid du Colombier 	fmtinstall('I', eipfmt);
259a747e4fSDavid du Colombier 	fmtinstall('M', eipfmt);
269a747e4fSDavid du Colombier 	fmtinstall('E', eipfmt);
277dd7cddfSDavid du Colombier 
287dd7cddfSDavid du Colombier 	arg = malloc((bargc+1) * sizeof(char*));
297dd7cddfSDavid du Colombier 	if(arg == nil)
309a747e4fSDavid du Colombier 		fatal("%r");
317dd7cddfSDavid du Colombier 	memmove(arg, bargv, (bargc+1) * sizeof(char*));
327dd7cddfSDavid du Colombier 
337dd7cddfSDavid du Colombier 	argc = bargc;
347dd7cddfSDavid du Colombier 	argv = arg;
357dd7cddfSDavid du Colombier 	strcpy(mpoint, "/net");
367dd7cddfSDavid du Colombier 	ARGBEGIN {
377dd7cddfSDavid du Colombier 	case 'x':
387dd7cddfSDavid du Colombier 		p = ARGF();
397dd7cddfSDavid du Colombier 		if(p != nil)
407dd7cddfSDavid du Colombier 			snprint(mpoint, sizeof(mpoint), "/net%s", p);
417dd7cddfSDavid du Colombier 		break;
427dd7cddfSDavid du Colombier 	case 'g':
437dd7cddfSDavid du Colombier 	case 'b':
447dd7cddfSDavid du Colombier 	case 'h':
457dd7cddfSDavid du Colombier 	case 'm':
467dd7cddfSDavid du Colombier 		p = ARGF();
477dd7cddfSDavid du Colombier 		USED(p);
487dd7cddfSDavid du Colombier 		break;
497dd7cddfSDavid du Colombier 	} ARGEND;
507dd7cddfSDavid du Colombier 
517dd7cddfSDavid du Colombier 	/* bind in an ip interface */
527dd7cddfSDavid du Colombier 	bind("#I", mpoint, MAFTER);
537dd7cddfSDavid du Colombier 	bind("#l0", mpoint, MAFTER);
547dd7cddfSDavid du Colombier 	bind("#l1", mpoint, MAFTER);
559a747e4fSDavid du Colombier 	bind("#l2", mpoint, MAFTER);
569a747e4fSDavid du Colombier 	bind("#l3", mpoint, MAFTER);
577dd7cddfSDavid du Colombier 
587dd7cddfSDavid du Colombier 	/* let ipconfig configure the ip interface */
597dd7cddfSDavid du Colombier 	switch(pid = fork()){
607dd7cddfSDavid du Colombier 	case -1:
619a747e4fSDavid du Colombier 		fatal("configuring ip: %r");
627dd7cddfSDavid du Colombier 	case 0:
63*6a9fc400SDavid du Colombier 		exec("/boot/ipconfig", arg);
647dd7cddfSDavid du Colombier 		fatal("execing /ipconfig");
657dd7cddfSDavid du Colombier 	default:
667dd7cddfSDavid du Colombier 		break;
677dd7cddfSDavid du Colombier 	}
687dd7cddfSDavid du Colombier 
697dd7cddfSDavid du Colombier 	/* wait for ipconfig to finish */
707dd7cddfSDavid du Colombier 	for(;;){
719a747e4fSDavid du Colombier 		w = wait();
729a747e4fSDavid du Colombier 		if(w != nil && w->pid == pid){
739a747e4fSDavid du Colombier 			if(w->msg[0] != 0)
749a747e4fSDavid du Colombier 				fatal(w->msg);
759a747e4fSDavid du Colombier 			free(w);
767dd7cddfSDavid du Colombier 			break;
779a747e4fSDavid du Colombier 		} else if(w == nil)
787dd7cddfSDavid du Colombier 			fatal("configuring ip");
799a747e4fSDavid du Colombier 		free(w);
807dd7cddfSDavid du Colombier 	}
817dd7cddfSDavid du Colombier 
827dd7cddfSDavid du Colombier 	/* if we didn't get a file and auth server, query user */
837dd7cddfSDavid du Colombier 	netndb("fs", fsip);
8480ee5cbfSDavid du Colombier 	if(!isvalidip(fsip))
8580ee5cbfSDavid du Colombier 		netenv("fs", fsip);
8680ee5cbfSDavid du Colombier 	while(!isvalidip(fsip)){
877dd7cddfSDavid du Colombier 		buf[0] = 0;
887dd7cddfSDavid du Colombier 		outin("filesystem IP address", buf, sizeof(buf));
897dd7cddfSDavid du Colombier 		parseip(fsip, buf);
907dd7cddfSDavid du Colombier 	}
9180ee5cbfSDavid du Colombier 
9280ee5cbfSDavid du Colombier 	netndb("auth", auip);
9380ee5cbfSDavid du Colombier 	if(!isvalidip(auip))
9480ee5cbfSDavid du Colombier 		netenv("auth", auip);
9580ee5cbfSDavid du Colombier 	while(!isvalidip(auip)){
967dd7cddfSDavid du Colombier 		buf[0] = 0;
977dd7cddfSDavid du Colombier 		outin("authentication server IP address", buf, sizeof(buf));
987dd7cddfSDavid du Colombier 		parseip(auip, buf);
997dd7cddfSDavid du Colombier 	}
1007dd7cddfSDavid du Colombier }
1017dd7cddfSDavid du Colombier 
1029a747e4fSDavid du Colombier static void
1039a747e4fSDavid du Colombier setauthaddr(char *proto, int port)
1047dd7cddfSDavid du Colombier {
1059a747e4fSDavid du Colombier 	char buf[128];
1067dd7cddfSDavid du Colombier 
1079a747e4fSDavid du Colombier 	snprint(buf, sizeof buf, "%s!%I!%d", proto, auip, port);
1089a747e4fSDavid du Colombier 	authaddr = strdup(buf);
1097dd7cddfSDavid du Colombier }
1107dd7cddfSDavid du Colombier 
11180ee5cbfSDavid du Colombier void
11280ee5cbfSDavid du Colombier configtcp(Method*)
11380ee5cbfSDavid du Colombier {
1149a747e4fSDavid du Colombier 	sleep(100);
1159a747e4fSDavid du Colombier 	print("t");
1169a747e4fSDavid du Colombier 	sleep(100);
11780ee5cbfSDavid du Colombier 	configip();
1189a747e4fSDavid du Colombier 	sleep(100);
1199a747e4fSDavid du Colombier 	print(".");
1209a747e4fSDavid du Colombier 	sleep(100);
1219a747e4fSDavid du Colombier 	setauthaddr("tcp", 567);
12280ee5cbfSDavid du Colombier }
12380ee5cbfSDavid du Colombier 
12480ee5cbfSDavid du Colombier int
12580ee5cbfSDavid du Colombier connecttcp(void)
12680ee5cbfSDavid du Colombier {
1279a747e4fSDavid du Colombier 	char buf[64];
12880ee5cbfSDavid du Colombier 
1299a747e4fSDavid du Colombier 	snprint(buf, sizeof buf, "tcp!%I!564", fsip);
1309a747e4fSDavid du Colombier 	return dial(buf, 0, 0, 0);
1319a747e4fSDavid du Colombier }
1329a747e4fSDavid du Colombier 
1339a747e4fSDavid du Colombier void
1349a747e4fSDavid du Colombier configil(Method*)
1359a747e4fSDavid du Colombier {
1369a747e4fSDavid du Colombier 	configip();
1373ff48bf5SDavid du Colombier 	setauthaddr("tcp", 567);
1389a747e4fSDavid du Colombier }
1399a747e4fSDavid du Colombier 
1409a747e4fSDavid du Colombier int
1419a747e4fSDavid du Colombier connectil(void)
1429a747e4fSDavid du Colombier {
1439a747e4fSDavid du Colombier 	char buf[64];
1449a747e4fSDavid du Colombier 
1459a747e4fSDavid du Colombier 	snprint(buf, sizeof buf, "il!%I!17008", fsip);
1469a747e4fSDavid du Colombier 	return dial(buf, 0, 0, 0);
14780ee5cbfSDavid du Colombier }
14880ee5cbfSDavid du Colombier 
1497dd7cddfSDavid du Colombier static int
1507dd7cddfSDavid du Colombier isvalidip(uchar *ip)
1517dd7cddfSDavid du Colombier {
1527dd7cddfSDavid du Colombier 	if(ipcmp(ip, IPnoaddr) == 0)
1537dd7cddfSDavid du Colombier 		return 0;
1547dd7cddfSDavid du Colombier 	if(ipcmp(ip, v4prefix) == 0)
1557dd7cddfSDavid du Colombier 		return 0;
1567dd7cddfSDavid du Colombier 	return 1;
1577dd7cddfSDavid du Colombier }
1587dd7cddfSDavid du Colombier 
1597dd7cddfSDavid du Colombier static void
16080ee5cbfSDavid du Colombier netenv(char *attr, uchar *ip)
16180ee5cbfSDavid du Colombier {
16280ee5cbfSDavid du Colombier 	int fd, n;
16380ee5cbfSDavid du Colombier 	char buf[128];
16480ee5cbfSDavid du Colombier 
16580ee5cbfSDavid du Colombier 	ipmove(ip, IPnoaddr);
16680ee5cbfSDavid du Colombier 	snprint(buf, sizeof(buf), "#e/%s", attr);
16780ee5cbfSDavid du Colombier 	fd = open(buf, OREAD);
16880ee5cbfSDavid du Colombier 	if(fd < 0)
16980ee5cbfSDavid du Colombier 		return;
17080ee5cbfSDavid du Colombier 
17180ee5cbfSDavid du Colombier 	n = read(fd, buf, sizeof(buf)-1);
17280ee5cbfSDavid du Colombier 	if(n <= 0)
17380ee5cbfSDavid du Colombier 		return;
17480ee5cbfSDavid du Colombier 	buf[n] = 0;
17580ee5cbfSDavid du Colombier 	parseip(ip, buf);
17680ee5cbfSDavid du Colombier }
17780ee5cbfSDavid du Colombier 
17880ee5cbfSDavid du Colombier static void
1797dd7cddfSDavid du Colombier netndb(char *attr, uchar *ip)
1807dd7cddfSDavid du Colombier {
1817dd7cddfSDavid du Colombier 	int fd, n, c;
1827dd7cddfSDavid du Colombier 	char buf[1024];
1837dd7cddfSDavid du Colombier 	char *p;
1847dd7cddfSDavid du Colombier 
1857dd7cddfSDavid du Colombier 	ipmove(ip, IPnoaddr);
1867dd7cddfSDavid du Colombier 	snprint(buf, sizeof(buf), "%s/ndb", mpoint);
1877dd7cddfSDavid du Colombier 	fd = open(buf, OREAD);
1887dd7cddfSDavid du Colombier 	if(fd < 0)
1897dd7cddfSDavid du Colombier 		return;
1907dd7cddfSDavid du Colombier 	n = read(fd, buf, sizeof(buf)-1);
1917dd7cddfSDavid du Colombier 	close(fd);
1927dd7cddfSDavid du Colombier 	if(n <= 0)
1937dd7cddfSDavid du Colombier 		return;
1947dd7cddfSDavid du Colombier 	buf[n] = 0;
1957dd7cddfSDavid du Colombier 	n = strlen(attr);
1967dd7cddfSDavid du Colombier 	for(p = buf;;){
1977dd7cddfSDavid du Colombier 		p = strstr(p, attr);
1987dd7cddfSDavid du Colombier 		if(p == nil)
1997dd7cddfSDavid du Colombier 			break;
2007dd7cddfSDavid du Colombier 		c = *(p-1);
2017dd7cddfSDavid du Colombier 		if(*(p + n) == '=' && (p == buf || c == '\n' || c == ' ' || c == '\t')){
2027dd7cddfSDavid du Colombier 			p += n+1;
2037dd7cddfSDavid du Colombier 			parseip(ip, p);
20480ee5cbfSDavid du Colombier 			return;
2057dd7cddfSDavid du Colombier 		}
2067dd7cddfSDavid du Colombier 		p++;
2077dd7cddfSDavid du Colombier 	}
20880ee5cbfSDavid du Colombier 	return;
2097dd7cddfSDavid du Colombier }
210