]> git.michaelhowe.org Git - packages/o/openafs.git/commitdiff
viced-client-cps-race-fix-20060220
authorJeffrey Altman <jaltman@secure-endpoints.com>
Mon, 20 Feb 2006 15:26:21 +0000 (15:26 +0000)
committerJeffrey Altman <jaltman@secure-endpoints.com>
Mon, 20 Feb 2006 15:26:21 +0000 (15:26 +0000)
remove a race condition between h_TossStuff_r and SRXAFS_FlushCPS by
changing h_ID2Client to return the client with a refcount and then
release the refCount with PutClient.

when the CPS list is non-NULL and the viceid is ANONYMOUSID be sure
to set the prlist_val to NULL if the prlist_len is being set to 0
since all of the tests are performed on prlist_val

src/viced/afsfileprocs.c
src/viced/host.c

index e38992345a5a74308cadfaa320fb8587dbe32c06..6cc477ca4a7b5e5b615f98499d1e0bf028edd666 100644 (file)
@@ -6033,7 +6033,7 @@ SRXAFS_FlushCPS(struct rx_call * acall, struct ViceIds * vids,
     for (i = 0; i < nids; i++, vd++) {
        if (!*vd)
            continue;
-       client = h_ID2Client(*vd);      /* returns client write locked, or NULL */
+       client = h_ID2Client(*vd);      /* returns write locked and refCounted, or NULL */
        if (!client)
            continue;
 
@@ -6049,6 +6049,7 @@ SRXAFS_FlushCPS(struct rx_call * acall, struct ViceIds * vids,
            client->CPS.prlist_len = 0;
        }
        ReleaseWriteLock(&client->lock);
+       PutClient(&client);
     }
 
     addr = addrs->IPAddrs_val;
index cee3ccf11eb4a21294e146cfbd7974a514ae018c..cacd65c6165a415873616a3b6d532b264cad4ebf 100644 (file)
@@ -719,10 +719,9 @@ h_TossStuff_r(register struct host *host)
            }
            /* We can't protect this without dropping the H_LOCK */
            client->CPS.prlist_len = 0;
-           if ((client->ViceId != ANONYMOUSID) && client->CPS.prlist_val) {
+           if ((client->ViceId != ANONYMOUSID) && client->CPS.prlist_val)
                free(client->CPS.prlist_val);
-               client->CPS.prlist_val = NULL;
-           }
+           client->CPS.prlist_val = NULL;
            if (client->tcon) {
                rx_SetSpecific(client->tcon, rxcon_client_key, (void *)0);
            }
@@ -1546,7 +1545,7 @@ MapName_r(char *aname, char *acell, afs_int32 * aval)
 /*MapName*/
 
 
-/* NOTE: this returns the client with a Write lock */
+/* NOTE: this returns the client with a Write lock and a refCount */
 struct client *
 h_ID2Client(afs_int32 vid)
 {
@@ -1562,9 +1561,6 @@ h_ID2Client(afs_int32 vid)
                client->refCount++;
                H_UNLOCK;
                ObtainWriteLock(&client->lock);
-               H_LOCK;
-               client->refCount--;
-               H_UNLOCK;
                return client;
            }
        }
@@ -1734,11 +1730,10 @@ h_FindClient_r(struct rx_connection *tcon)
     client->prfail = fail;
 
     if (!(client->CPS.prlist_val) || (viceid != client->ViceId)) {
-       if (client->CPS.prlist_val && (client->ViceId != ANONYMOUSID)) {
+       client->CPS.prlist_len = 0;
+       if (client->CPS.prlist_val && (client->ViceId != ANONYMOUSID))
            free(client->CPS.prlist_val);
-       }
        client->CPS.prlist_val = NULL;
-       client->CPS.prlist_len = 0;
        client->ViceId = viceid;
        client->expTime = expTime;
 
@@ -1797,10 +1792,9 @@ h_FindClient_r(struct rx_connection *tcon)
                            afs_inet_ntoa_r(rxr_HostOf(tcon), hoststr),
                            ntohs(rxr_PortOf(tcon)),
                            oldClient, oldClient->sid));
-               if ((client->ViceId != ANONYMOUSID) && client->CPS.prlist_val) {
+               if ((client->ViceId != ANONYMOUSID) && client->CPS.prlist_val)
                    free(client->CPS.prlist_val);
-                   client->CPS.prlist_val = NULL;
-               }
+               client->CPS.prlist_val = NULL;
                client->CPS.prlist_len = 0;
                if (client->tcon) {
                    rx_SetSpecific(client->tcon, rxcon_client_key, (void *)0);