summaryrefslogtreecommitdiff
path: root/usr/src/stand
diff options
context:
space:
mode:
authorss146032 <none@none>2006-01-09 22:51:40 -0800
committerss146032 <none@none>2006-01-09 22:51:40 -0800
commit9f1fc992b281e57216b036e784b762829b875b4b (patch)
tree084d4b4d95d6189a9a0fd6c5a0c027d43f5b533d /usr/src/stand
parent6c740c0a708fa2f50ef147a46e4c5a9f753fe06f (diff)
downloadillumos-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.c30
-rw-r--r--usr/src/stand/lib/fs/nfs/mount.c29
-rw-r--r--usr/src/stand/lib/fs/nfs/rpc.c20
-rw-r--r--usr/src/stand/lib/inet/mac.c17
-rw-r--r--usr/src/stand/lib/tcp/tcp.c26
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. */