drbd: Converted drbd_free_sock() and drbd_disconnect() from mdev to tconn
authorPhilipp Reisner <philipp.reisner@linbit.com>
Tue, 8 Feb 2011 13:29:53 +0000 (14:29 +0100)
committerPhilipp Reisner <philipp.reisner@linbit.com>
Wed, 28 Sep 2011 08:33:06 +0000 (10:33 +0200)
Signed-off-by: Philipp Reisner <philipp.reisner@linbit.com>
Signed-off-by: Lars Ellenberg <lars.ellenberg@linbit.com>
drivers/block/drbd/drbd_int.h
drivers/block/drbd/drbd_main.c
drivers/block/drbd/drbd_receiver.c

index a51d0a4..a703654 100644 (file)
@@ -1165,7 +1165,7 @@ extern void tl_release(struct drbd_conf *mdev, unsigned int barrier_nr,
                       unsigned int set_size);
 extern void tl_clear(struct drbd_conf *mdev);
 extern void _tl_add_barrier(struct drbd_conf *, struct drbd_tl_epoch *);
-extern void drbd_free_sock(struct drbd_conf *mdev);
+extern void drbd_free_sock(struct drbd_tconn *tconn);
 extern int drbd_send(struct drbd_tconn *tconn, struct socket *sock,
                     void *buf, size_t size, unsigned msg_flags);
 extern int drbd_send_protocol(struct drbd_tconn *tconn);
index 3bb412c..a26ec93 100644 (file)
@@ -2430,21 +2430,21 @@ void drbd_free_bc(struct drbd_backing_dev *ldev)
        kfree(ldev);
 }
 
-void drbd_free_sock(struct drbd_conf *mdev)
+void drbd_free_sock(struct drbd_tconn *tconn)
 {
-       if (mdev->tconn->data.socket) {
-               mutex_lock(&mdev->tconn->data.mutex);
-               kernel_sock_shutdown(mdev->tconn->data.socket, SHUT_RDWR);
-               sock_release(mdev->tconn->data.socket);
-               mdev->tconn->data.socket = NULL;
-               mutex_unlock(&mdev->tconn->data.mutex);
+       if (tconn->data.socket) {
+               mutex_lock(&tconn->data.mutex);
+               kernel_sock_shutdown(tconn->data.socket, SHUT_RDWR);
+               sock_release(tconn->data.socket);
+               tconn->data.socket = NULL;
+               mutex_unlock(&tconn->data.mutex);
        }
-       if (mdev->tconn->meta.socket) {
-               mutex_lock(&mdev->tconn->meta.mutex);
-               kernel_sock_shutdown(mdev->tconn->meta.socket, SHUT_RDWR);
-               sock_release(mdev->tconn->meta.socket);
-               mdev->tconn->meta.socket = NULL;
-               mutex_unlock(&mdev->tconn->meta.mutex);
+       if (tconn->meta.socket) {
+               mutex_lock(&tconn->meta.mutex);
+               kernel_sock_shutdown(tconn->meta.socket, SHUT_RDWR);
+               sock_release(tconn->meta.socket);
+               tconn->meta.socket = NULL;
+               mutex_unlock(&tconn->meta.mutex);
        }
 }
 
@@ -2462,7 +2462,7 @@ void drbd_free_resources(struct drbd_conf *mdev)
        crypto_free_hash(mdev->tconn->integrity_r_tfm);
        mdev->tconn->integrity_r_tfm = NULL;
 
-       drbd_free_sock(mdev);
+       drbd_free_sock(mdev->tconn);
 
        __no_warn(local,
                  drbd_free_bc(mdev->ldev);
index 4c61802..2e5318f 100644 (file)
@@ -62,6 +62,7 @@ enum finish_epoch {
 
 static int drbd_do_handshake(struct drbd_tconn *tconn);
 static int drbd_do_auth(struct drbd_tconn *tconn);
+static int drbd_disconnected(int vnr, void *p, void *data);
 
 static enum finish_epoch drbd_may_finish_epoch(struct drbd_conf *, struct drbd_epoch *, enum epoch_event);
 static int e_end_block(struct drbd_conf *, struct drbd_work *, int);
@@ -3829,19 +3830,49 @@ void drbd_flush_workqueue(struct drbd_tconn *tconn)
        wait_for_completion(&barr.done);
 }
 
-static void drbd_disconnect(struct drbd_conf *mdev)
+static void drbd_disconnect(struct drbd_tconn *tconn)
 {
-       enum drbd_fencing_p fp;
        union drbd_state os, ns;
        int rv = SS_UNKNOWN_ERROR;
-       unsigned int i;
 
-       if (mdev->state.conn == C_STANDALONE)
+       if (tconn->volume0->state.conn == C_STANDALONE)
                return;
 
        /* asender does not clean up anything. it must not interfere, either */
-       drbd_thread_stop(&mdev->tconn->asender);
-       drbd_free_sock(mdev);
+       drbd_thread_stop(&tconn->asender);
+       drbd_free_sock(tconn);
+
+       idr_for_each(&tconn->volumes, drbd_disconnected, tconn);
+
+       conn_info(tconn, "Connection closed\n");
+
+       spin_lock_irq(&tconn->req_lock);
+       os = tconn->volume0->state;
+       if (os.conn >= C_UNCONNECTED) {
+               /* Do not restart in case we are C_DISCONNECTING */
+               ns.i = os.i;
+               ns.conn = C_UNCONNECTED;
+               rv = _drbd_set_state(tconn->volume0, ns, CS_VERBOSE, NULL);
+       }
+       spin_unlock_irq(&tconn->req_lock);
+
+       if (os.conn == C_DISCONNECTING) {
+               wait_event(tconn->net_cnt_wait, atomic_read(&tconn->net_cnt) == 0);
+
+               crypto_free_hash(tconn->cram_hmac_tfm);
+               tconn->cram_hmac_tfm = NULL;
+
+               kfree(tconn->net_conf);
+               tconn->net_conf = NULL;
+               drbd_request_state(tconn->volume0, NS(conn, C_STANDALONE));
+       }
+}
+
+static int drbd_disconnected(int vnr, void *p, void *data)
+{
+       struct drbd_conf *mdev = (struct drbd_conf *)p;
+       enum drbd_fencing_p fp;
+       unsigned int i;
 
        /* wait for current activity to cease. */
        spin_lock_irq(&mdev->tconn->req_lock);
@@ -3887,8 +3918,6 @@ static void drbd_disconnect(struct drbd_conf *mdev)
        if (!is_susp(mdev->state))
                tl_clear(mdev);
 
-       dev_info(DEV, "Connection closed\n");
-
        drbd_md_sync(mdev);
 
        fp = FP_DONT_CARE;
@@ -3900,27 +3929,6 @@ static void drbd_disconnect(struct drbd_conf *mdev)
        if (mdev->state.role == R_PRIMARY && fp >= FP_RESOURCE && mdev->state.pdsk >= D_UNKNOWN)
                drbd_try_outdate_peer_async(mdev);
 
-       spin_lock_irq(&mdev->tconn->req_lock);
-       os = mdev->state;
-       if (os.conn >= C_UNCONNECTED) {
-               /* Do not restart in case we are C_DISCONNECTING */
-               ns = os;
-               ns.conn = C_UNCONNECTED;
-               rv = _drbd_set_state(mdev, ns, CS_VERBOSE, NULL);
-       }
-       spin_unlock_irq(&mdev->tconn->req_lock);
-
-       if (os.conn == C_DISCONNECTING) {
-               wait_event(mdev->tconn->net_cnt_wait, atomic_read(&mdev->tconn->net_cnt) == 0);
-
-               crypto_free_hash(mdev->tconn->cram_hmac_tfm);
-               mdev->tconn->cram_hmac_tfm = NULL;
-
-               kfree(mdev->tconn->net_conf);
-               mdev->tconn->net_conf = NULL;
-               drbd_request_state(mdev, NS(conn, C_STANDALONE));
-       }
-
        /* serialize with bitmap writeout triggered by the state change,
         * if any. */
        wait_event(mdev->misc_wait, !test_bit(BITMAP_IO, &mdev->flags));
@@ -3950,6 +3958,8 @@ static void drbd_disconnect(struct drbd_conf *mdev)
        /* ok, no more ee's on the fly, it is safe to reset the epoch_size */
        atomic_set(&mdev->current_epoch->epoch_size, 0);
        D_ASSERT(list_empty(&mdev->current_epoch->list));
+
+       return 0;
 }
 
 /*
@@ -4226,7 +4236,7 @@ int drbdd_init(struct drbd_thread *thi)
        do {
                h = drbd_connect(mdev->tconn);
                if (h == 0) {
-                       drbd_disconnect(mdev);
+                       drbd_disconnect(mdev->tconn);
                        schedule_timeout_interruptible(HZ);
                }
                if (h == -1) {
@@ -4242,7 +4252,7 @@ int drbdd_init(struct drbd_thread *thi)
                }
        }
 
-       drbd_disconnect(mdev);
+       drbd_disconnect(mdev->tconn);
 
        dev_info(DEV, "receiver terminated\n");
        return 0;