drbd: protocol compatibility for maximum packet sizes
authorLars Ellenberg <lars.ellenberg@linbit.com>
Tue, 14 Sep 2010 13:56:29 +0000 (15:56 +0200)
committerPhilipp Reisner <philipp.reisner@linbit.com>
Thu, 14 Oct 2010 16:38:41 +0000 (18:38 +0200)
Two missing corner cases to the "maximum packet size" handshake.

Signed-off-by: Philipp Reisner <philipp.reisner@linbit.com>
Signed-off-by: Lars Ellenberg <lars.ellenberg@linbit.com>
drivers/block/drbd/drbd_nl.c
drivers/block/drbd/drbd_receiver.c

index 9ee4456..9ae33a5 100644 (file)
@@ -861,6 +861,7 @@ static int drbd_nl_disk_conf(struct drbd_conf *mdev, struct drbd_nl_cfg_req *nlp
        struct inode *inode, *inode2;
        struct lru_cache *resync_lru = NULL;
        union drbd_state ns, os;
+       unsigned int max_seg_s;
        int rv;
        int cp_discovered = 0;
        int logical_block_size;
@@ -1133,9 +1134,20 @@ static int drbd_nl_disk_conf(struct drbd_conf *mdev, struct drbd_nl_cfg_req *nlp
        mdev->read_cnt = 0;
        mdev->writ_cnt = 0;
 
-       drbd_setup_queue_param(mdev, mdev->state.conn == C_CONNECTED &&
-                              mdev->agreed_pro_version < 95 ?
-                              DRBD_MAX_SIZE_H80_PACKET : DRBD_MAX_SEGMENT_SIZE);
+       max_seg_s = DRBD_MAX_SEGMENT_SIZE;
+       if (mdev->state.conn == C_CONNECTED) {
+               /* We are Primary, Connected, and now attach a new local
+                * backing store. We must not increase the user visible maximum
+                * bio size on this device to something the peer may not be
+                * able to handle. */
+               if (mdev->agreed_pro_version < 94)
+                       max_seg_s = queue_max_segment_size(mdev->rq_queue);
+               else if (mdev->agreed_pro_version == 94)
+                       max_seg_s = DRBD_MAX_SIZE_H80_PACKET;
+               /* else: drbd 8.3.9 and later, stay with default */
+       }
+
+       drbd_setup_queue_param(mdev, max_seg_s);
 
        /* If I am currently not R_PRIMARY,
         * but meta data primary indicator is set,
index 6b69b2f..9da32ac 100644 (file)
@@ -3088,6 +3088,8 @@ static int receive_sizes(struct drbd_conf *mdev, enum drbd_packets cmd, unsigned
 
                if (mdev->agreed_pro_version < 94)
                        max_seg_s = be32_to_cpu(p->max_segment_size);
+               else if (mdev->agreed_pro_version == 94)
+                       max_seg_s = DRBD_MAX_SIZE_H80_PACKET;
                else /* drbd 8.3.8 onwards */
                        max_seg_s = DRBD_MAX_SEGMENT_SIZE;