restructure the diskless NFS boot code to keep track of the used
interface and the address allocated, to roll everything back if the mount fails: -put an interface pointer into "struct nfs_diskless" to have it available for cleanup, don't pass it around anymore where the "struct nfs_diskless" is already passed -add a "cleanup" function which shuts the interface down -in the protocol-specific parts, either return with "everything ready" or "completely shut down" -use common functions for interface initialization and shutdown -add a function to delete all routes associate to an interface (why is this necessary and not done by ~IFF_UP?) g/c diskless swap stuff general cleanup
This commit is contained in:
parent
4e214e9bac
commit
27098b1199
|
@ -1,4 +1,4 @@
|
|||
/* $NetBSD: nfs_boot.c,v 1.49 1998/09/13 13:49:29 christos Exp $ */
|
||||
/* $NetBSD: nfs_boot.c,v 1.50 1999/02/21 15:07:49 drochner Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1995, 1997 The NetBSD Foundation, Inc.
|
||||
|
@ -117,6 +117,7 @@ nfs_boot_init(nd, procp)
|
|||
root_device->dv_xname);
|
||||
return (ENXIO);
|
||||
}
|
||||
nd->nd_ifp = ifp;
|
||||
|
||||
error = EADDRNOTAVAIL; /* ??? */
|
||||
#if defined(NFS_BOOT_BOOTP) || defined(NFS_BOOT_DHCP)
|
||||
|
@ -126,13 +127,13 @@ nfs_boot_init(nd, procp)
|
|||
#else
|
||||
printf("nfs_boot: trying BOOTP\n");
|
||||
#endif
|
||||
error = nfs_bootdhcp(ifp, nd, procp);
|
||||
error = nfs_bootdhcp(nd, procp);
|
||||
}
|
||||
#endif
|
||||
#ifdef NFS_BOOT_BOOTPARAM
|
||||
if (error && nfs_boot_bootparam) {
|
||||
printf("nfs_boot: trying RARP (and RPC/bootparam)\n");
|
||||
error = nfs_bootparam(ifp, nd, procp);
|
||||
error = nfs_bootparam(nd, procp);
|
||||
}
|
||||
#endif
|
||||
if (error)
|
||||
|
@ -150,11 +151,171 @@ nfs_boot_init(nd, procp)
|
|||
*/
|
||||
error = nfs_boot_getfh(&nd->nd_root);
|
||||
|
||||
if (error)
|
||||
nfs_boot_cleanup(nd, procp);
|
||||
|
||||
return (error);
|
||||
}
|
||||
|
||||
int nfs_boot_setrecvtimo(so)
|
||||
struct socket *so;
|
||||
void
|
||||
nfs_boot_cleanup(nd, procp)
|
||||
struct nfs_diskless *nd;
|
||||
struct proc *procp;
|
||||
{
|
||||
|
||||
nfs_boot_deladdress(nd->nd_ifp, procp, nd->nd_myip.s_addr);
|
||||
nfs_boot_ifupdown(nd->nd_ifp, procp, 0);
|
||||
nfs_boot_flushrt(nd->nd_ifp);
|
||||
}
|
||||
|
||||
int
|
||||
nfs_boot_ifupdown(ifp, procp, up)
|
||||
struct ifnet *ifp;
|
||||
struct proc *procp;
|
||||
int up;
|
||||
{
|
||||
struct socket *so;
|
||||
struct ifreq ireq;
|
||||
int error;
|
||||
|
||||
memset(&ireq, 0, sizeof(ireq));
|
||||
memcpy(ireq.ifr_name, ifp->if_xname, IFNAMSIZ);
|
||||
|
||||
/*
|
||||
* Get a socket to use for various things in here.
|
||||
* After this, use "goto out" to cleanup and return.
|
||||
*/
|
||||
error = socreate(AF_INET, &so, SOCK_DGRAM, 0);
|
||||
if (error) {
|
||||
printf("ifupdown: socreate, error=%d\n", error);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* Bring up the interface. (just set the "up" flag)
|
||||
* Get the old interface flags and or IFF_UP into them so
|
||||
* things like media selection flags are not clobbered.
|
||||
*/
|
||||
error = ifioctl(so, SIOCGIFFLAGS, (caddr_t)&ireq, procp);
|
||||
if (error) {
|
||||
printf("ifupdown: GIFFLAGS, error=%d\n", error);
|
||||
goto out;
|
||||
}
|
||||
if (up)
|
||||
ireq.ifr_flags |= IFF_UP;
|
||||
else
|
||||
ireq.ifr_flags &= ~IFF_UP;
|
||||
error = ifioctl(so, SIOCSIFFLAGS, (caddr_t)&ireq, procp);
|
||||
if (error) {
|
||||
printf("ifupdown: SIFFLAGS, error=%d\n", error);
|
||||
goto out;
|
||||
}
|
||||
|
||||
out:
|
||||
soclose(so);
|
||||
return (error);
|
||||
}
|
||||
|
||||
int
|
||||
nfs_boot_setaddress(ifp, procp, addr, netmask, braddr)
|
||||
struct ifnet *ifp;
|
||||
struct proc *procp;
|
||||
u_int32_t addr, netmask, braddr;
|
||||
{
|
||||
struct socket *so;
|
||||
struct ifaliasreq iareq;
|
||||
struct sockaddr_in *sin;
|
||||
int error;
|
||||
|
||||
/*
|
||||
* Get a socket to use for various things in here.
|
||||
* After this, use "goto out" to cleanup and return.
|
||||
*/
|
||||
error = socreate(AF_INET, &so, SOCK_DGRAM, 0);
|
||||
if (error) {
|
||||
printf("setaddress: socreate, error=%d\n", error);
|
||||
return (error);
|
||||
}
|
||||
|
||||
memset(&iareq, 0, sizeof(iareq));
|
||||
memcpy(iareq.ifra_name, ifp->if_xname, IFNAMSIZ);
|
||||
|
||||
/* Set the I/F address */
|
||||
sin = (struct sockaddr_in *)&iareq.ifra_addr;
|
||||
sin->sin_len = sizeof(*sin);
|
||||
sin->sin_family = AF_INET;
|
||||
sin->sin_addr.s_addr = addr;
|
||||
|
||||
/* Set the netmask */
|
||||
if (netmask != INADDR_ANY) {
|
||||
sin = (struct sockaddr_in *)&iareq.ifra_mask;
|
||||
sin->sin_len = sizeof(*sin);
|
||||
sin->sin_family = AF_INET;
|
||||
sin->sin_addr.s_addr = netmask;
|
||||
} /* else leave subnetmask unspecified (len=0) */
|
||||
|
||||
/* Set the broadcast addr. */
|
||||
if (braddr != INADDR_ANY) {
|
||||
sin = (struct sockaddr_in *)&iareq.ifra_broadaddr;
|
||||
sin->sin_len = sizeof(*sin);
|
||||
sin->sin_family = AF_INET;
|
||||
sin->sin_addr.s_addr = braddr;
|
||||
} /* else leave broadcast addr unspecified (len=0) */
|
||||
|
||||
error = ifioctl(so, SIOCAIFADDR, (caddr_t)&iareq, procp);
|
||||
if (error) {
|
||||
printf("setaddress, error=%d\n", error);
|
||||
goto out;
|
||||
}
|
||||
|
||||
out:
|
||||
soclose(so);
|
||||
return (error);
|
||||
}
|
||||
|
||||
int
|
||||
nfs_boot_deladdress(ifp, procp, addr)
|
||||
struct ifnet *ifp;
|
||||
struct proc *procp;
|
||||
u_int32_t addr;
|
||||
{
|
||||
struct socket *so;
|
||||
struct ifreq ireq;
|
||||
struct sockaddr_in *sin;
|
||||
int error;
|
||||
|
||||
/*
|
||||
* Get a socket to use for various things in here.
|
||||
* After this, use "goto out" to cleanup and return.
|
||||
*/
|
||||
error = socreate(AF_INET, &so, SOCK_DGRAM, 0);
|
||||
if (error) {
|
||||
printf("deladdress: socreate, error=%d\n", error);
|
||||
return (error);
|
||||
}
|
||||
|
||||
memset(&ireq, 0, sizeof(ireq));
|
||||
memcpy(ireq.ifr_name, ifp->if_xname, IFNAMSIZ);
|
||||
|
||||
sin = (struct sockaddr_in *)&ireq.ifr_addr;
|
||||
sin->sin_len = sizeof(*sin);
|
||||
sin->sin_family = AF_INET;
|
||||
sin->sin_addr.s_addr = addr;
|
||||
|
||||
error = ifioctl(so, SIOCDIFADDR, (caddr_t)&ireq, procp);
|
||||
if (error) {
|
||||
printf("deladdress, error=%d\n", error);
|
||||
goto out;
|
||||
}
|
||||
|
||||
out:
|
||||
soclose(so);
|
||||
return (error);
|
||||
}
|
||||
|
||||
int
|
||||
nfs_boot_setrecvtimo(so)
|
||||
struct socket *so;
|
||||
{
|
||||
struct mbuf *m;
|
||||
struct timeval *tv;
|
||||
|
@ -164,11 +325,12 @@ struct socket *so;
|
|||
m->m_len = sizeof(*tv);
|
||||
tv->tv_sec = 1;
|
||||
tv->tv_usec = 0;
|
||||
return(sosetopt(so, SOL_SOCKET, SO_RCVTIMEO, m));
|
||||
return (sosetopt(so, SOL_SOCKET, SO_RCVTIMEO, m));
|
||||
}
|
||||
|
||||
int nfs_boot_enbroadcast(so)
|
||||
struct socket *so;
|
||||
int
|
||||
nfs_boot_enbroadcast(so)
|
||||
struct socket *so;
|
||||
{
|
||||
struct mbuf *m;
|
||||
int32_t *on;
|
||||
|
@ -177,12 +339,13 @@ struct socket *so;
|
|||
on = mtod(m, int32_t *);
|
||||
m->m_len = sizeof(*on);
|
||||
*on = 1;
|
||||
return(sosetopt(so, SOL_SOCKET, SO_BROADCAST, m));
|
||||
return (sosetopt(so, SOL_SOCKET, SO_BROADCAST, m));
|
||||
}
|
||||
|
||||
int nfs_boot_sobind_ipport(so, port)
|
||||
struct socket *so;
|
||||
u_int16_t port;
|
||||
int
|
||||
nfs_boot_sobind_ipport(so, port)
|
||||
struct socket *so;
|
||||
u_int16_t port;
|
||||
{
|
||||
struct mbuf *m;
|
||||
struct sockaddr_in *sin;
|
||||
|
@ -196,7 +359,7 @@ u_int16_t port;
|
|||
sin->sin_port = htons(port);
|
||||
error = sobind(so, m);
|
||||
m_freem(m);
|
||||
return(error);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -208,15 +371,15 @@ u_int16_t port;
|
|||
#define MAX_RESEND_DELAY 5 /* seconds */
|
||||
#define TOTAL_TIMEOUT 30 /* seconds */
|
||||
|
||||
int nfs_boot_sendrecv(so, nam, sndproc, snd, rcvproc, rcv,
|
||||
from_p, context)
|
||||
struct socket *so;
|
||||
struct mbuf *nam;
|
||||
int (*sndproc) __P((struct mbuf*, void*, int));
|
||||
struct mbuf *snd;
|
||||
int (*rcvproc) __P((struct mbuf*, void*));
|
||||
struct mbuf **rcv, **from_p;
|
||||
void *context;
|
||||
int
|
||||
nfs_boot_sendrecv(so, nam, sndproc, snd, rcvproc, rcv, from_p, context)
|
||||
struct socket *so;
|
||||
struct mbuf *nam;
|
||||
int (*sndproc) __P((struct mbuf*, void*, int));
|
||||
struct mbuf *snd;
|
||||
int (*rcvproc) __P((struct mbuf*, void*));
|
||||
struct mbuf **rcv, **from_p;
|
||||
void *context;
|
||||
{
|
||||
int error, rcvflg, timo, secs, waited;
|
||||
struct mbuf *m, *from;
|
||||
|
@ -234,7 +397,7 @@ void *context;
|
|||
send_again:
|
||||
waited += timo;
|
||||
if (waited >= TOTAL_TIMEOUT)
|
||||
return(ETIMEDOUT);
|
||||
return (ETIMEDOUT);
|
||||
|
||||
/* Determine new timeout. */
|
||||
if (timo < MAX_RESEND_DELAY)
|
||||
|
@ -307,7 +470,7 @@ send_again:
|
|||
}
|
||||
out:
|
||||
if (from) m_freem(from);
|
||||
return(error);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -337,13 +500,40 @@ nfs_boot_defrt(gw_ip)
|
|||
|
||||
/* add, dest, gw, mask, flags, 0 */
|
||||
error = rtrequest(RTM_ADD, &dst, &gw, &mask,
|
||||
(RTF_UP | RTF_GATEWAY | RTF_STATIC), NULL);
|
||||
(RTF_UP | RTF_GATEWAY | RTF_STATIC), NULL);
|
||||
if (error) {
|
||||
printf("nfs_boot: add route, error=%d\n", error);
|
||||
error = 0;
|
||||
}
|
||||
}
|
||||
|
||||
static int nfs_boot_delroute __P((struct radix_node *, void *));
|
||||
static int
|
||||
nfs_boot_delroute(rn, w)
|
||||
struct radix_node *rn;
|
||||
void *w;
|
||||
{
|
||||
struct rtentry *rt = (struct rtentry *)rn;
|
||||
int error;
|
||||
|
||||
if (rt->rt_ifp != (struct ifnet *)w)
|
||||
return (0);
|
||||
|
||||
error = rtrequest(RTM_DELETE, rt_key(rt), NULL, rt_mask(rt), 0, NULL);
|
||||
if (error)
|
||||
printf("nfs_boot: del route, error=%d\n", error);
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
||||
void
|
||||
nfs_boot_flushrt(ifp)
|
||||
struct ifnet *ifp;
|
||||
{
|
||||
|
||||
rn_walktree(rt_tables[AF_INET], nfs_boot_delroute, ifp);
|
||||
}
|
||||
|
||||
/*
|
||||
* Get an initial NFS file handle using Sun RPC/mountd.
|
||||
* Separate function because we used to call it twice.
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $NetBSD: nfs_bootdhcp.c,v 1.10 1999/02/12 01:38:38 thorpej Exp $ */
|
||||
/* $NetBSD: nfs_bootdhcp.c,v 1.11 1999/02/21 15:07:49 drochner Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1995, 1997 The NetBSD Foundation, Inc.
|
||||
|
@ -220,8 +220,7 @@ static const u_int8_t vm_rfc1048[4] = { 99, 130, 83, 99 };
|
|||
/* Convenience macro */
|
||||
#define INTOHL(ina) ((u_int32_t)ntohl((ina).s_addr))
|
||||
|
||||
static int bootpc_call __P((struct socket *, struct ifnet *,
|
||||
struct nfs_diskless *, struct proc *));
|
||||
static int bootpc_call __P((struct nfs_diskless *, struct proc *));
|
||||
static void bootp_extract __P((struct bootp *, int, struct nfs_diskless *));
|
||||
|
||||
/* #define DEBUG XXX */
|
||||
|
@ -237,57 +236,30 @@ static void bootp_extract __P((struct bootp *, int, struct nfs_diskless *));
|
|||
* Get our boot parameters using BOOTP.
|
||||
*/
|
||||
int
|
||||
nfs_bootdhcp(ifp, nd, procp)
|
||||
struct ifnet *ifp;
|
||||
nfs_bootdhcp(nd, procp)
|
||||
struct nfs_diskless *nd;
|
||||
struct proc *procp;
|
||||
{
|
||||
struct ifaliasreq iareq;
|
||||
struct socket *so;
|
||||
struct sockaddr_in *sin;
|
||||
struct ifnet *ifp = nd->nd_ifp;
|
||||
int error;
|
||||
|
||||
/*
|
||||
* Get a socket to use for various things in here.
|
||||
* After this, use "goto out" to cleanup and return.
|
||||
*/
|
||||
error = socreate(AF_INET, &so, SOCK_DGRAM, 0);
|
||||
if (error) {
|
||||
printf("nfs_boot: socreate, error=%d\n", error);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* Do enough of ifconfig(8) so that the chosen interface
|
||||
* can talk to the servers. Use address zero for now.
|
||||
*/
|
||||
memset(&iareq, 0, sizeof(iareq));
|
||||
memcpy(iareq.ifra_name, ifp->if_xname, IFNAMSIZ);
|
||||
/* Set the I/F address */
|
||||
sin = (struct sockaddr_in *)&iareq.ifra_addr;
|
||||
sin->sin_len = sizeof(*sin);
|
||||
sin->sin_family = AF_INET;
|
||||
sin->sin_addr.s_addr = INADDR_ANY;
|
||||
/* Leave subnetmask unspecified (len=0) */
|
||||
/* Set the broadcast addr. */
|
||||
sin = (struct sockaddr_in *)&iareq.ifra_broadaddr;
|
||||
sin->sin_len = sizeof(*sin);
|
||||
sin->sin_family = AF_INET;
|
||||
sin->sin_addr.s_addr = INADDR_BROADCAST;
|
||||
error = ifioctl(so, SIOCAIFADDR, (caddr_t)&iareq, procp);
|
||||
error = nfs_boot_setaddress(ifp, procp, INADDR_ANY, INADDR_ANY,
|
||||
INADDR_BROADCAST);
|
||||
if (error) {
|
||||
printf("nfs_boot: set ifaddr zero, error=%d\n", error);
|
||||
goto out;
|
||||
return (error);
|
||||
}
|
||||
|
||||
/* This function call does the real send/recv work. */
|
||||
error = bootpc_call(so, ifp, nd, procp);
|
||||
error = bootpc_call(nd, procp);
|
||||
|
||||
/* Get rid of the temporary (zero) IP address. */
|
||||
/*
|
||||
* XXX SIOCDIFADDR takes a "struct ifreq", which is
|
||||
* an exact subset of "struct ifaliasreq".
|
||||
*/
|
||||
(void) ifioctl(so, SIOCDIFADDR, (caddr_t)&iareq, procp);
|
||||
(void) nfs_boot_deladdress(ifp, procp, INADDR_ANY);
|
||||
|
||||
/* NOW we can test the error from bootpc_call. */
|
||||
if (error)
|
||||
goto out;
|
||||
|
@ -295,29 +267,18 @@ nfs_bootdhcp(ifp, nd, procp)
|
|||
/*
|
||||
* Do ifconfig with our real IP address and mask.
|
||||
*/
|
||||
/* I/F address */
|
||||
sin = (struct sockaddr_in *)&iareq.ifra_addr;
|
||||
sin->sin_addr = nd->nd_myip;
|
||||
/* subnetmask */
|
||||
if (nd->nd_mask.s_addr) {
|
||||
sin = (struct sockaddr_in *)&iareq.ifra_mask;
|
||||
sin->sin_len = sizeof(*sin);
|
||||
sin->sin_family = AF_INET;
|
||||
sin->sin_addr = nd->nd_mask;
|
||||
}
|
||||
/* Let ifioctl() default the broadcast address. */
|
||||
sin = (struct sockaddr_in *)&iareq.ifra_broadaddr;
|
||||
sin->sin_len = 0;
|
||||
sin->sin_family = 0;
|
||||
sin->sin_addr.s_addr = 0;
|
||||
error = ifioctl(so, SIOCAIFADDR, (caddr_t)&iareq, procp);
|
||||
error = nfs_boot_setaddress(ifp, procp, nd->nd_myip.s_addr,
|
||||
nd->nd_mask.s_addr, INADDR_ANY);
|
||||
if (error) {
|
||||
printf("nfs_boot: set ifaddr real, error=%d\n", error);
|
||||
goto out;
|
||||
}
|
||||
|
||||
out:
|
||||
soclose(so);
|
||||
if (error) {
|
||||
(void) nfs_boot_ifupdown(ifp, procp, 0);
|
||||
nfs_boot_flushrt(ifp);
|
||||
}
|
||||
return (error);
|
||||
}
|
||||
|
||||
|
@ -470,12 +431,12 @@ warn:
|
|||
}
|
||||
|
||||
static int
|
||||
bootpc_call(so, ifp, nd, procp)
|
||||
struct socket *so;
|
||||
struct ifnet *ifp;
|
||||
bootpc_call(nd, procp)
|
||||
struct nfs_diskless *nd;
|
||||
struct proc *procp;
|
||||
{
|
||||
struct socket *so;
|
||||
struct ifnet *ifp = nd->nd_ifp;
|
||||
static u_int32_t xid = ~0xFF;
|
||||
struct bootp *bootp; /* request */
|
||||
struct mbuf *m, *nam;
|
||||
|
@ -485,6 +446,12 @@ bootpc_call(so, ifp, nd, procp)
|
|||
u_char hafmt, halen;
|
||||
struct bootpcontext bpc;
|
||||
|
||||
error = socreate(AF_INET, &so, SOCK_DGRAM, 0);
|
||||
if (error) {
|
||||
printf("bootp: socreate, error=%d\n", error);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* Initialize to NULL anything that will hold an allocation,
|
||||
* and free each at the end if not null.
|
||||
|
@ -650,6 +617,7 @@ out:
|
|||
m_freem(m);
|
||||
if (nam)
|
||||
m_freem(nam);
|
||||
soclose(so);
|
||||
return (error);
|
||||
}
|
||||
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $NetBSD: nfs_bootparam.c,v 1.10 1998/09/13 13:49:29 christos Exp $ */
|
||||
/* $NetBSD: nfs_bootparam.c,v 1.11 1999/02/21 15:07:49 drochner Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1995, 1997 The NetBSD Foundation, Inc.
|
||||
|
@ -107,52 +107,28 @@ static int bp_getfile __P((struct sockaddr_in *bpsin, char *key,
|
|||
* is used for all subsequent booptaram RPCs.
|
||||
*/
|
||||
int
|
||||
nfs_bootparam(ifp, nd, procp)
|
||||
struct ifnet *ifp;
|
||||
nfs_bootparam(nd, procp)
|
||||
struct nfs_diskless *nd;
|
||||
struct proc *procp;
|
||||
{
|
||||
struct ifreq ireq;
|
||||
struct in_addr my_ip, gw_ip;
|
||||
struct ifnet *ifp = nd->nd_ifp;
|
||||
struct in_addr my_ip, arps_ip, gw_ip;
|
||||
struct sockaddr_in bp_sin;
|
||||
struct sockaddr_in *sin;
|
||||
struct socket *so;
|
||||
struct nfs_dlmount *gw_ndm;
|
||||
#if 0 /* XXX - not yet */
|
||||
struct nfs_dlmount *gw_ndm = 0;
|
||||
char *p;
|
||||
u_int32_t mask;
|
||||
#endif /* XXX */
|
||||
int error;
|
||||
|
||||
gw_ndm = 0;
|
||||
memset(&ireq, 0, sizeof(ireq));
|
||||
memcpy(ireq.ifr_name, ifp->if_xname, IFNAMSIZ);
|
||||
|
||||
/*
|
||||
* Get a socket to use for various things in here.
|
||||
* After this, use "goto out" to cleanup and return.
|
||||
*/
|
||||
error = socreate(AF_INET, &so, SOCK_DGRAM, 0);
|
||||
if (error) {
|
||||
printf("nfs_boot: socreate, error=%d\n", error);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* Bring up the interface. (just set the "up" flag)
|
||||
* Get the old interface flags and or IFF_UP into them so
|
||||
* things like media selection flags are not clobbered.
|
||||
*/
|
||||
error = ifioctl(so, SIOCGIFFLAGS, (caddr_t)&ireq, procp);
|
||||
if (error) {
|
||||
printf("nfs_boot: GIFFLAGS, error=%d\n", error);
|
||||
goto out;
|
||||
}
|
||||
ireq.ifr_flags |= IFF_UP;
|
||||
error = ifioctl(so, SIOCSIFFLAGS, (caddr_t)&ireq, procp);
|
||||
error = nfs_boot_ifupdown(ifp, procp, 1);
|
||||
if (error) {
|
||||
printf("nfs_boot: SIFFLAGS, error=%d\n", error);
|
||||
goto out;
|
||||
return (error);
|
||||
}
|
||||
|
||||
error = EADDRNOTAVAIL; /* ??? */
|
||||
|
@ -161,7 +137,7 @@ nfs_bootparam(ifp, nd, procp)
|
|||
/*
|
||||
* Do RARP for the interface address.
|
||||
*/
|
||||
error = revarpwhoami(&my_ip, ifp);
|
||||
error = revarpwhoarewe(ifp, &arps_ip, &my_ip);
|
||||
if (error) {
|
||||
printf("revarp failed, error=%d\n", error);
|
||||
goto out;
|
||||
|
@ -170,18 +146,16 @@ nfs_bootparam(ifp, nd, procp)
|
|||
#endif
|
||||
|
||||
nd->nd_myip.s_addr = my_ip.s_addr;
|
||||
printf("nfs_boot: client_addr=0x%x\n",
|
||||
(u_int32_t)ntohl(my_ip.s_addr));
|
||||
printf("nfs_boot: client_addr=0x%x (RARP from 0x%x)\n",
|
||||
(u_int32_t)ntohl(my_ip.s_addr),
|
||||
(u_int32_t)ntohl(arps_ip.s_addr));
|
||||
|
||||
/*
|
||||
* Do enough of ifconfig(8) so that the chosen interface
|
||||
* can talk to the servers. (just set the address)
|
||||
*/
|
||||
sin = (struct sockaddr_in *)&ireq.ifr_addr;
|
||||
sin->sin_len = sizeof(*sin);
|
||||
sin->sin_family = AF_INET;
|
||||
sin->sin_addr = my_ip;
|
||||
error = ifioctl(so, SIOCSIFADDR, (caddr_t)&ireq, procp);
|
||||
error = nfs_boot_setaddress(ifp, procp, my_ip.s_addr,
|
||||
INADDR_ANY, INADDR_ANY);
|
||||
if (error) {
|
||||
printf("nfs_boot: set ifaddr, error=%d\n", error);
|
||||
goto out;
|
||||
|
@ -205,7 +179,7 @@ nfs_bootparam(ifp, nd, procp)
|
|||
error = bp_whoami(sin, &my_ip, &gw_ip);
|
||||
if (error) {
|
||||
printf("nfs_boot: bootparam whoami, error=%d\n", error);
|
||||
goto out;
|
||||
goto delout;
|
||||
}
|
||||
printf("nfs_boot: server_addr=0x%x\n",
|
||||
(u_int32_t)ntohl(sin->sin_addr.s_addr));
|
||||
|
@ -218,15 +192,8 @@ nfs_bootparam(ifp, nd, procp)
|
|||
error = bp_getfile(sin, "root", &nd->nd_root);
|
||||
if (error) {
|
||||
printf("nfs_boot: bootparam get root: %d\n", error);
|
||||
goto out;
|
||||
goto delout;
|
||||
}
|
||||
#if 0
|
||||
error = bp_getfile(sin, "swap", &nd->nd_swap);
|
||||
if (error) {
|
||||
printf("nfs_boot: bootparam get swap: %d\n", error);
|
||||
error = 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef NFS_BOOT_GATEWAY
|
||||
/*
|
||||
|
@ -281,12 +248,18 @@ nfs_bootparam(ifp, nd, procp)
|
|||
printf("nfs_boot: set ifmask, error=%d\n", error);
|
||||
error = 0; /* ignore it */
|
||||
}
|
||||
#endif /* XXX */
|
||||
|
||||
out:
|
||||
if (gw_ndm)
|
||||
free(gw_ndm, M_NFSMNT);
|
||||
soclose(so);
|
||||
#endif /* XXX */
|
||||
|
||||
delout:
|
||||
if (error)
|
||||
(void) nfs_boot_deladdress(ifp, procp, my_ip.s_addr);
|
||||
out:
|
||||
if (error) {
|
||||
(void) nfs_boot_ifupdown(ifp, procp, 0);
|
||||
nfs_boot_flushrt(ifp);
|
||||
}
|
||||
return (error);
|
||||
}
|
||||
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $NetBSD: nfsdiskless.h,v 1.15 1997/09/30 20:44:35 drochner Exp $ */
|
||||
/* $NetBSD: nfsdiskless.h,v 1.16 1999/02/21 15:07:49 drochner Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1995, 1997 The NetBSD Foundation, Inc.
|
||||
|
@ -55,18 +55,23 @@ struct nfs_dlmount {
|
|||
u_char ndm_fh[NFSX_V3FHMAX]; /* The file's file handle */
|
||||
};
|
||||
struct nfs_diskless {
|
||||
/* the interface used */
|
||||
struct ifnet *nd_ifp;
|
||||
/* A collection of IP addresses, for convenience. */
|
||||
struct in_addr nd_myip; /* My IP address */
|
||||
struct in_addr nd_mask; /* My netmask */
|
||||
struct in_addr nd_gwip; /* My gateway */
|
||||
/* Information for each mount point we need. */
|
||||
struct nfs_dlmount nd_root; /* Mount info for root */
|
||||
#if 0
|
||||
struct nfs_dlmount nd_swap; /* Mount info for swap */
|
||||
#endif
|
||||
};
|
||||
|
||||
int nfs_boot_init __P((struct nfs_diskless *nd, struct proc *procp));
|
||||
void nfs_boot_cleanup __P((struct nfs_diskless *nd, struct proc *procp));
|
||||
int nfs_boot_ifupdown __P((struct ifnet *, struct proc *, int));
|
||||
int nfs_boot_setaddress __P((struct ifnet *, struct proc *,
|
||||
u_int32_t, u_int32_t, u_int32_t));
|
||||
int nfs_boot_deladdress __P((struct ifnet *, struct proc *, u_int32_t));
|
||||
void nfs_boot_flushrt __P((struct ifnet *));
|
||||
int nfs_boot_setrecvtimo __P((struct socket *));
|
||||
int nfs_boot_enbroadcast __P((struct socket *));
|
||||
int nfs_boot_sobind_ipport __P((struct socket *, u_int16_t));
|
||||
|
@ -75,6 +80,6 @@ int nfs_boot_sendrecv __P((struct socket *, struct mbuf *,
|
|||
int (*)(struct mbuf*, void*), struct mbuf**,
|
||||
struct mbuf**, void*));
|
||||
|
||||
int nfs_bootdhcp __P((struct ifnet *, struct nfs_diskless *, struct proc *));
|
||||
int nfs_bootparam __P((struct ifnet *, struct nfs_diskless *, struct proc *));
|
||||
int nfs_bootdhcp __P((struct nfs_diskless *, struct proc *));
|
||||
int nfs_bootparam __P((struct nfs_diskless *, struct proc *));
|
||||
|
||||
|
|
Loading…
Reference in New Issue