rx: Don't send packets to localhost if -rxbind set

For some platforms (SOLARIS, FBSD), shutting down the libafs client
currently involves sending a packet to localhost to wakeup the listener
thread. If rx is bound to a specific host address (the -rxbind option
was passed to afsd), this won't work, because rx won't receive packets
sent to localhost. This results in the client hanging forever when
trying to 'umount afs', until a packet is otherwise sent to the rx
socket.

To fix this, send the packet to the bound host address instead, if
-rxbind was given. Otherwise, send the packet to localhost, like before.

Introduce the small helper function rxi_GetLocalAddr() to consolidate
the logic of what address to use.

Change-Id: I26fa5194b726ed753779faa07142fec647228b44
Reviewed-on: https://gerrit.openafs.org/15906
Reviewed-by: Marcio Brito Barbosa <mbarbosa@sinenomine.net>
Reviewed-by: Michael Meffie <mmeffie@sinenomine.net>
Reviewed-by: Cheyenne Wills <cwills@sinenomine.net>
Tested-by: Andrew Deason <adeason@sinenomine.net>
This commit is contained in:
Andrew Deason 2024-11-11 16:16:33 -06:00
parent 1cb8deb64f
commit 91378d93b9
3 changed files with 24 additions and 4 deletions

View File

@ -108,8 +108,7 @@ osi_StopListener(void)
bzero(&taddr, sizeof(taddr));
taddr.sin_len = sizeof(struct sockaddr_in);
taddr.sin_family = AF_INET;
taddr.sin_port = rx_port;
taddr.sin_addr.s_addr = htonl(0x7f000001); /* no place like localhost */
rxi_GetLocalAddr(&taddr);
bzero(&dvec, sizeof(dvec));
dvec.iov_base = &c;
dvec.iov_len = 1;

View File

@ -451,8 +451,7 @@ osi_FreeSocket(osi_socket asocket)
AFS_STATCNT(osi_FreeSocket);
taddr.sin_family = AF_INET;
taddr.sin_port = rx_port;
taddr.sin_addr.s_addr = htonl(0x7f000001);
rxi_GetLocalAddr(&taddr);
dvec.iov_base = &c;
dvec.iov_len = 1;

View File

@ -9679,3 +9679,25 @@ rxi_NetSend(osi_socket socket, void *addr, struct iovec *dvec,
return ESHUTDOWN;
#endif
}
/*
* Get our local address (the address to use to send packets to ourselves). If
* rx_InitHost() was given a host to bind to, we use that host address;
* otherwise use 127.0.0.1. The port is the port we are actually bound to.
*
* @param[out] sin host/port populated with the address to use
*
* @pre rx_InitHost() called successfully
*/
void
rxi_GetLocalAddr(struct sockaddr_in *sin)
{
if (rx_host != 0) {
/* If we're bound to an address, use that address as localhost. */
sin->sin_addr.s_addr = rx_host;
} else {
/* Otherwise, use 127.0.0.1. */
sin->sin_addr.s_addr = htonl(0x7f000001);
}
sin->sin_port = rx_port;
}