diff options
author | ss146032 <none@none> | 2006-01-09 22:51:40 -0800 |
---|---|---|
committer | ss146032 <none@none> | 2006-01-09 22:51:40 -0800 |
commit | 9f1fc992b281e57216b036e784b762829b875b4b (patch) | |
tree | 084d4b4d95d6189a9a0fd6c5a0c027d43f5b533d /usr/src/stand | |
parent | 6c740c0a708fa2f50ef147a46e4c5a9f753fe06f (diff) | |
download | illumos-gate-9f1fc992b281e57216b036e784b762829b875b4b.tar.gz |
6216419 boot-net stalls while waiting for ARP reply generated for IP outside the client's subnet....
Diffstat (limited to 'usr/src/stand')
-rw-r--r-- | usr/src/stand/lib/fs/nfs/clnt_budp.c | 30 | ||||
-rw-r--r-- | usr/src/stand/lib/fs/nfs/mount.c | 29 | ||||
-rw-r--r-- | usr/src/stand/lib/fs/nfs/rpc.c | 20 | ||||
-rw-r--r-- | usr/src/stand/lib/inet/mac.c | 17 | ||||
-rw-r--r-- | usr/src/stand/lib/tcp/tcp.c | 26 |
5 files changed, 99 insertions, 23 deletions
diff --git a/usr/src/stand/lib/fs/nfs/clnt_budp.c b/usr/src/stand/lib/fs/nfs/clnt_budp.c index bf2e895373..cfd14574ff 100644 --- a/usr/src/stand/lib/fs/nfs/clnt_budp.c +++ b/usr/src/stand/lib/fs/nfs/clnt_budp.c @@ -2,9 +2,8 @@ * CDDL HEADER START * * The contents of this file are subject to the terms of the - * Common Development and Distribution License, Version 1.0 only - * (the "License"). You may not use this file except in compliance - * with the License. + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. * * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE * or http://www.opensolaris.org/os/licensing. @@ -19,8 +18,9 @@ * * CDDL HEADER END */ + /* - * Copyright 2004 Sun Microsystems, Inc. All rights reserved. + * Copyright 2006 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ @@ -59,6 +59,9 @@ #define dprintf if (boothowto & RB_DEBUG) printf +/* retries to send RPC message when sendto fails */ +#define RPC_UDP_SEND_RETRIES 3 + extern int errno; /* @@ -244,6 +247,7 @@ clntbudp_call(cl, proc, xargs, argsp, xresults, resultsp, utimeout) int nrefreshes = 2; /* number of times to refresh cred */ struct timeval timeout; int errors; + short send_retries = RPC_UDP_SEND_RETRIES; cu = (struct cu_data *)cl->cl_private; if (cu->cu_total.tv_usec == -1) @@ -283,8 +287,24 @@ send_again: if (sendto(cu->cu_sock, cu->cu_outbuf, outlen, 0, (struct sockaddr *)&(cu->cu_raddr), cu->cu_rlen) != outlen) { + if (errno == ETIMEDOUT) { + /* + * sendto() times out probably because + * ARP times out while waiting for reply. + * We retry sending RPC message again. + */ + if (send_retries-- > 0) { + dprintf("clntbudp_call: timedout, try sending" + "RPC again\n"); + errno = 0; + goto send_again; + } + cu->cu_error.re_status = RPC_TIMEDOUT; + } else { + cu->cu_error.re_status = RPC_CANTSEND; + } cu->cu_error.re_errno = errno; - return (cu->cu_error.re_status = RPC_CANTSEND); + return (cu->cu_error.re_status); } /* diff --git a/usr/src/stand/lib/fs/nfs/mount.c b/usr/src/stand/lib/fs/nfs/mount.c index 89d5c2f71a..760aac3414 100644 --- a/usr/src/stand/lib/fs/nfs/mount.c +++ b/usr/src/stand/lib/fs/nfs/mount.c @@ -2,9 +2,8 @@ * CDDL HEADER START * * The contents of this file are subject to the terms of the - * Common Development and Distribution License, Version 1.0 only - * (the "License"). You may not use this file except in compliance - * with the License. + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. * * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE * or http://www.opensolaris.org/os/licensing. @@ -19,8 +18,9 @@ * * CDDL HEADER END */ + /* - * Copyright 2004 Sun Microsystems, Inc. All rights reserved. + * Copyright 2006 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ @@ -60,6 +60,9 @@ #include "dhcpv4.h" #include <sys/mntent.h> +/* ARP timeout in milliseconds for BOOTP/RARP */ +#define ARP_INETBOOT_TIMEOUT 1000 + struct nfs_file roothandle; /* root file handle */ static char root_hostname[SYS_NMLN]; /* server hostname */ static char my_hostname[MAXHOSTNAMELEN]; @@ -73,6 +76,7 @@ char rootopts[MAX_PATH_LEN]; static gid_t fake_gids = 1; /* fake gids list for auth_unix */ extern void set_default_filename(char *); /* boot.c */ +extern void mac_set_arp_timeout(unsigned int); /* mac.c */ /* * xdr routines used by mount. @@ -604,6 +608,23 @@ boot_nfs_mountroot(char *str) * services are local. Use DHCP if this bothers you. */ dontroute = TRUE; + /* + * We are trying to keep the ARP response + * timeout on the lower side with BOOTP/RARP. + * We are doing this for BOOTP/RARP where policy + * doesn't allow to route the packets outside + * the subnet as it has no idea about the + * netmask. By doing so, we are reducing + * ARP response timeout for any packet destined + * for outside booting clients subnet. Client can + * not expect such ARP replies and will finally + * timeout after a long delay. This would cause + * booting client to get stalled for a longer + * time. We can not avoid accepting any outside + * subnet packets accidentally destined for the + * booting client. + */ + mac_set_arp_timeout(ARP_INETBOOT_TIMEOUT); /* now that we have an IP address, turn off promiscuous mode */ (void) ipv4_setpromiscuous(FALSE); diff --git a/usr/src/stand/lib/fs/nfs/rpc.c b/usr/src/stand/lib/fs/nfs/rpc.c index 55b76fe154..db813a2d1d 100644 --- a/usr/src/stand/lib/fs/nfs/rpc.c +++ b/usr/src/stand/lib/fs/nfs/rpc.c @@ -2,9 +2,8 @@ * CDDL HEADER START * * The contents of this file are subject to the terms of the - * Common Development and Distribution License, Version 1.0 only - * (the "License"). You may not use this file except in compliance - * with the License. + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. * * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE * or http://www.opensolaris.org/os/licensing. @@ -19,8 +18,9 @@ * * CDDL HEADER END */ + /* - * Copyright 2004 Sun Microsystems, Inc. All rights reserved. + * Copyright 2006 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. * * This file contains a simple implementation of RPC. Standard XDR is @@ -348,7 +348,17 @@ brpc_call( do { if (sendto(s, trm_msg, xmit_len, flags, (struct sockaddr *)to, sizeof (struct sockaddr_in)) < 0) { - rpc_error.re_status = RPC_CANTSEND; + /* + * If errno is set to ETIMEDOUT, return + * with RPC status as RPC_TIMEDOUT. Calling + * funciton will take care of this error by + * retrying the RPC call. + */ + if (errno == ETIMEDOUT) { + rpc_error.re_status = RPC_TIMEDOUT; + } else { + rpc_error.re_status = RPC_CANTSEND; + } goto gt_error; } diff --git a/usr/src/stand/lib/inet/mac.c b/usr/src/stand/lib/inet/mac.c index 009523b5f9..a1a9f2dd59 100644 --- a/usr/src/stand/lib/inet/mac.c +++ b/usr/src/stand/lib/inet/mac.c @@ -2,9 +2,8 @@ * CDDL HEADER START * * The contents of this file are subject to the terms of the - * Common Development and Distribution License, Version 1.0 only - * (the "License"). You may not use this file except in compliance - * with the License. + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. * * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE * or http://www.opensolaris.org/os/licensing. @@ -19,8 +18,9 @@ * * CDDL HEADER END */ + /* - * Copyright 2005 Sun Microsystems, Inc. All rights reserved. + * Copyright 2006 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ @@ -71,6 +71,8 @@ struct ofw_net_types { }; #endif /* !__i386 */ +void mac_set_arp_timeout(unsigned int); + /* * given the mac type, initialize the mac interface state. */ @@ -395,6 +397,13 @@ mac_get_type(void) return (mac_state.mac_type); } +void +mac_set_arp_timeout(unsigned int timeout) +{ + mac_state.mac_arp_timeout = + timeout; +} + int mac_get_arp_timeout(void) { diff --git a/usr/src/stand/lib/tcp/tcp.c b/usr/src/stand/lib/tcp/tcp.c index c6f8afe0e8..7525ce3f83 100644 --- a/usr/src/stand/lib/tcp/tcp.c +++ b/usr/src/stand/lib/tcp/tcp.c @@ -2,9 +2,8 @@ * CDDL HEADER START * * The contents of this file are subject to the terms of the - * Common Development and Distribution License, Version 1.0 only - * (the "License"). You may not use this file except in compliance - * with the License. + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. * * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE * or http://www.opensolaris.org/os/licensing. @@ -19,8 +18,9 @@ * * CDDL HEADER END */ + /* - * Copyright 2005 Sun Microsystems, Inc. All rights reserved. + * Copyright 2006 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. * * tcp.c, Code implementing the TCP protocol. @@ -678,6 +678,16 @@ tcp_send(int sock_id, tcp_t *tcp, const void *msg, int len) return (-1); tcp_wput_data(tcp, head, sock_id); + /* + * errno should be reset here as it may be + * set to ETIMEDOUT. This may be set by + * the MAC driver in case it has timed out + * waiting for ARP reply. Any segment which + * was not transmitted because of ARP timeout + * will be retransmitted by TCP. + */ + if (errno == ETIMEDOUT) + errno = 0; return (cnt); } @@ -1398,7 +1408,13 @@ tcp_connect(int sock_id) /* Send out the SYN packet. */ ret = ipv4_tcp_output(sock_id, syn_mp); freeb(syn_mp); - if (ret < 0) { + /* + * errno ETIMEDOUT is set by the mac driver + * in case it is not able to receive ARP reply. + * TCP will retransmit this segment so we can + * ignore the ARP timeout. + */ + if ((ret < 0) && (errno != ETIMEDOUT)) { return (-1); } /* tcp_state_wait() will finish the 3 way handshake. */ |