[OpenAFS] NAT and changing ip addresses
Jim Rees
rees@umich.edu
Mon, 08 Jan 2001 16:35:21 -0500
I think most of you are missing the fundamental problem with afs and nat.
The problem isn't that the client's ip address can change (that's solvable;
see below) but that each client must be able to receive packets addressed to
it from the server to port 7001. This is ok if you only have one client
behind the nat box, but if you have more than one you have trouble.
When the nat box sees a packet originating at a client on port 7001, it sets
up a flow such that any packet addressed from the server to the nat box on
port 7001 will go to the client named in the flow. Now if you add another
client, you have two clients sending from port 7001, and the nat box doesn't
know which client to send the reply packets to. I see no solution to this
problem.
The problem of a client changing ip addresses is easier. We've been doing
this for years in disconnected afs (which I hope to incorporate into OpenAFS
at some point). Right now it's done manually but I think it could be
automated.
When a client changes ip address it must discard all state associated with
that ip address. That state consists of callbacks on the client and server,
and rx connections on the client (and maybe server). Callbacks are
discarded by calling afs_FlushVCBs(). At the end of this message I have
attached the routine we use to discard connections.
Tokens do not have to be discarded. A token does have the client's ip
address in it, but the server ignores the ip address.
afs_RemoveAllConns()
{
register int i;
register struct server *ts;
register struct conn *tc, **lc;
ObtainReadLock(&afs_xserver);
ObtainWriteLock(&afs_xconn);
for (i = 0; i < NSERVERS; i++) {
for (ts = afs_servers[i]; ts; ts = ts->next) {
for (tc = ts->conns, lc = &ts->conns; tc; tc = *lc) {
*lc = tc->next;
rx_DestroyConnection(tc->id);
osi_Free(tc, sizeof(struct conn));
} /*For each connection on the server*/
} /*For each server on chain*/
} /*For each chain*/
ReleaseWriteLock(&afs_xconn);
ReleaseReadLock(&afs_xserver);
rx_Finalize();
} /*RemoveAllConns*/