]> git.neil.brown.name Git - history.git/commitdiff
[PATCH] pcmcia: BUG() if clients are kept too long
authorDominik Brodowski <linux@dominikbrodowski.de>
Tue, 11 Jan 2005 11:23:56 +0000 (03:23 -0800)
committerLinus Torvalds <torvalds@ppc970.osdl.org>
Tue, 11 Jan 2005 11:23:56 +0000 (03:23 -0800)
BUG if the socket's list of clients is not empty on shutdown and/or removal.

Signed-off-by: Dominik Brodowski <linux@brodo.de>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
drivers/pcmcia/cs.c
drivers/pcmcia/ds.c

index d8564ac9a95bc6836e80fbae2aafd9319b1de272..b93ec422c78aade7b23e99f2558567a94a31d8fa 100644 (file)
@@ -198,13 +198,8 @@ EXPORT_SYMBOL(pcmcia_put_socket);
 static void pcmcia_release_socket(struct class_device *class_dev)
 {
        struct pcmcia_socket *socket = class_get_devdata(class_dev);
-       client_t *client;
 
-       while (socket->clients) {
-               client = socket->clients;
-               socket->clients = socket->clients->next;
-               kfree(client);
-       }
+       BUG_ON(socket->clients);
 
        complete(&socket->socket_released);
 }
@@ -357,8 +352,6 @@ static void free_regions(memory_handle_t *list)
 
 static void shutdown_socket(struct pcmcia_socket *s)
 {
-    client_t **c;
-    
     cs_dbg(s, 1, "shutdown_socket\n");
 
     /* Blank out the socket state */
@@ -376,15 +369,7 @@ static void shutdown_socket(struct pcmcia_socket *s)
        kfree(s->config);
        s->config = NULL;
     }
-    for (c = &s->clients; *c; ) {
-       if ((*c)->state & CLIENT_UNBOUND) {
-           client_t *d = *c;
-           *c = (*c)->next;
-           kfree(d);
-       } else {
-           c = &((*c)->next);
-       }
-    }
+    BUG_ON(s->clients);
     free_regions(&s->a_region);
     free_regions(&s->c_region);
 
index c06e903882b17616a460c1927a3f66d607b4084f..059f02471b627d2611e5e51bf2fd46997f2a9d30 100644 (file)
@@ -907,15 +907,13 @@ int pcmcia_deregister_client(client_handle_t handle)
        s = SOCKET(handle);
        ds_dbg(1, "deregister_client(%p)\n", handle);
 
-       if (handle->state &
-           (CLIENT_IRQ_REQ|CLIENT_IO_REQ|CLIENT_CONFIG_LOCKED))
-               return CS_IN_USE;
+       if (handle->state & (CLIENT_IRQ_REQ|CLIENT_IO_REQ|CLIENT_CONFIG_LOCKED))
+               goto warn_out;
        for (i = 0; i < MAX_WIN; i++)
                if (handle->state & CLIENT_WIN_REQ(i))
-                       return CS_IN_USE;
+                       goto warn_out;
 
-       if ((handle->state & CLIENT_STALE) ||
-           (handle->Attributes & INFO_MASTER_CLIENT)) {
+       if (handle->state & CLIENT_STALE) {
                spin_lock_irqsave(&s->lock, flags);
                client = &s->clients;
                while ((*client) && ((*client) != handle))
@@ -934,6 +932,9 @@ int pcmcia_deregister_client(client_handle_t handle)
        }
 
        return CS_SUCCESS;
+ warn_out:
+       printk(KERN_WARNING "ds: deregister_client was called too early.\n");
+       return CS_IN_USE;
 } /* deregister_client */
 EXPORT_SYMBOL(pcmcia_deregister_client);