[DRBD-cvs] drbd by lars; stacking queue limits should work now

drbd-user@lists.linbit.com drbd-user@lists.linbit.com
Tue, 27 Jan 2004 16:51:41 +0100 (CET)


DRBD CVS committal

Author  : lars
Module  : drbd

Dir     : drbd/drbd


Modified Files:
      Tag: rel-0_7-branch
	drbd_actlog.c drbd_compat_wrappers.h drbd_fs.c drbd_int.h 
	drbd_main.c drbd_receiver.c drbd_req-2.4.c 


Log Message:
stacking queue limits should work now


===================================================================
RCS file: /var/lib/cvs/drbd/drbd/drbd/Attic/drbd_actlog.c,v
retrieving revision 1.1.2.64
retrieving revision 1.1.2.65
diff -u -3 -r1.1.2.64 -r1.1.2.65
--- drbd_actlog.c	27 Jan 2004 11:36:32 -0000	1.1.2.64
+++ drbd_actlog.c	27 Jan 2004 15:51:36 -0000	1.1.2.65
@@ -28,8 +28,6 @@
 #include "drbd.h"
 #include "drbd_int.h"
 
-#define AL_EXTENT_SIZE_B 22             // One extent represents 4M Storage
-#define AL_EXTENT_SIZE (1<<AL_EXTENT_SIZE_B)
 #define AL_EXTENTS_PT 61
 
 /* This is what I like so much about the linux kernel:
===================================================================
RCS file: /var/lib/cvs/drbd/drbd/drbd/Attic/drbd_compat_wrappers.h,v
retrieving revision 1.1.2.13
retrieving revision 1.1.2.14
diff -u -3 -r1.1.2.13 -r1.1.2.14
--- drbd_compat_wrappers.h	27 Jan 2004 11:36:32 -0000	1.1.2.13
+++ drbd_compat_wrappers.h	27 Jan 2004 15:51:36 -0000	1.1.2.14
@@ -291,6 +291,9 @@
 extern int drbd_dio_end_sec        (struct bio *bio, unsigned int bytes_done, int error);
 extern int drbd_dio_end            (struct bio *bio, unsigned int bytes_done, int error);
 
+// we should not accept bios crossing our extent boundaries!
+extern int drbd_merge_bvec_fn(request_queue_t *q, struct bio *bio, struct bio_vec *bv);
+
 /* Returns the number of 512 byte sectors of the lower level device */
 static inline unsigned long drbd_get_lo_capacity(drbd_dev *mdev)
 {
@@ -379,21 +382,17 @@
 #ifdef CONFIG_HIGHMEM
 /*
  * I don't know why there is no bvec_kmap, only bvec_kmap_irq ...
- * If for some reason it is intentional, and MUST be irq save,
- * I introduce a very bad bug right here and now.
  *
- * Most likely it is only due to performance:
+ * we do a sock_recvmsg into the target buffer,
+ * so we obviously cannot use the bvec_kmap_irq variant.	-lge
+ *
+ * Most likely it is only due to performance anyways:
   * kmap_atomic/kunmap_atomic is significantly faster than kmap/kunmap because
   * no global lock is needed and because the kmap code must perform a global TLB
   * invalidation when the kmap pool wraps.
   *
   * However when holding an atomic kmap is is not legal to sleep, so atomic
   * kmaps are appropriate for short, tight code paths only.
- *
- * So in the long run we may prefer to move to bio_kmap_irq, and either ignore
- * the compatibility with 2.4, or provide something similar there.
- *
- *	-lge
  */
 static inline char *drbd_bio_kmap(struct bio *bio)
 {
===================================================================
RCS file: /var/lib/cvs/drbd/drbd/drbd/drbd_fs.c,v
retrieving revision 1.28.2.55
retrieving revision 1.28.2.56
diff -u -3 -r1.28.2.55 -r1.28.2.56
--- drbd_fs.c	27 Jan 2004 11:36:32 -0000	1.28.2.55
+++ drbd_fs.c	27 Jan 2004 15:51:36 -0000	1.28.2.56
@@ -285,6 +285,26 @@
 	mdev->read_cnt = 0;
 	mdev->writ_cnt = 0;
 
+// FIXME unclutter the code again ;)
+/*
+ * Returns the minimum that is _not_ zero, unless both are zero.
+ */
+#define min_not_zero(l, r) (l == 0) ? r : ((r == 0) ? l : min(l, r))
+ONLY_IN_26({
+	request_queue_t * const q = mdev->rq_queue;
+	request_queue_t * const b = bdev->bd_disk->queue;
+
+	q->max_sectors = min_not_zero(PAGE_SIZE >> 9, b->max_sectors);
+	q->max_phys_segments = 1;
+	q->max_hw_segments   = 1;
+	q->max_segment_size  = min(PAGE_SIZE,b->max_segment_size);
+	q->hardsect_size     = max(512,b->hardsect_size);
+	q->seg_boundary_mask = b->seg_boundary_mask;
+	q->merge_bvec_fn     = drbd_merge_bvec_fn;
+	D_ASSERT(q->hardsect_size <= PAGE_SIZE); // or we are really screwed ;-)
+})
+#undef min_not_zero
+
 	drbd_md_read(mdev);
 	drbd_determin_dev_size(mdev);
 	drbd_read_bm(mdev);
@@ -331,6 +351,7 @@
 	struct ioctl_get_config cn;
 
 #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0)
+	//WORK_HERE
 #warning "FIXME make 26 clean, maybe move to compat layer?"
 #else
 	cn.lower_device_major=MAJOR(mdev->lo_device);
===================================================================
RCS file: /var/lib/cvs/drbd/drbd/drbd/drbd_int.h,v
retrieving revision 1.58.2.108
retrieving revision 1.58.2.109
diff -u -3 -r1.58.2.108 -r1.58.2.109
--- drbd_int.h	27 Jan 2004 09:22:13 -0000	1.58.2.108
+++ drbd_int.h	27 Jan 2004 15:51:36 -0000	1.58.2.109
@@ -584,6 +584,10 @@
 	spinlock_t bm_lock;
 };
 
+// activity log
+#define AL_EXTENT_SIZE_B 22             // One extent represents 4M Storage
+#define AL_EXTENT_SIZE (1<<AL_EXTENT_SIZE_B)
+// resync bitmap
 #define BM_EXTENT_SIZE_B 24       // One extent represents 16M Storage
 #define BM_EXTENT_SIZE (1<<BM_EXTENT_SIZE_B)
 
===================================================================
RCS file: /var/lib/cvs/drbd/drbd/drbd/drbd_main.c,v
retrieving revision 1.73.2.114
retrieving revision 1.73.2.115
diff -u -3 -r1.73.2.114 -r1.73.2.115
--- drbd_main.c	27 Jan 2004 09:22:13 -0000	1.73.2.114
+++ drbd_main.c	27 Jan 2004 15:51:36 -0000	1.73.2.115
@@ -863,6 +863,7 @@
 		 */
 		/* THINK
 		 * do we need to block DRBD_SIG if sock == &meta.socket ??
+		 * otherwise wake_asender() might interrupt some send_*Ack !
 		 */
 		rv = sock_sendmsg(sock, &msg, iov.iov_len );
 		if (rv == -EAGAIN) {
@@ -1171,6 +1172,8 @@
 			}
 			if (*q) blk_put_queue(*q);
 			*q = NULL;
+
+			if (mdev->this_bdev) bd_release(mdev->this_bdev);
 )
 
 			tl_cleanup(mdev);
@@ -1457,16 +1460,22 @@
 void drbd_free_ll_dev(drbd_dev *mdev)
 {
 	if (mdev->lo_file) {
+NOT_IN_26(
 		blkdev_put(mdev->lo_file->f_dentry->d_inode->i_bdev,BDEV_FILE);
 		blkdev_put(mdev->md_file->f_dentry->d_inode->i_bdev,BDEV_FILE);
-		fput(mdev->lo_file);
-		fput(mdev->md_file);
-		mdev->lo_file = 0;
-NOT_IN_26(
 		mdev->lo_device = 0;
 		mdev->md_device = 0;
 )
 #warning "FIXME unset L26 members"
+ONLY_IN_26(
+		bd_release(mdev->backing_bdev);
+		bd_release(mdev->md_bdev);
+		mdev->md_bdev =
+		mdev->backing_bdev = 0;
+)
+		fput(mdev->lo_file);
+		fput(mdev->md_file);
+		mdev->lo_file = 0;
 		mdev->md_file = 0;
 	}
 }
===================================================================
RCS file: /var/lib/cvs/drbd/drbd/drbd/drbd_receiver.c,v
retrieving revision 1.97.2.98
retrieving revision 1.97.2.99
diff -u -3 -r1.97.2.98 -r1.97.2.99
--- drbd_receiver.c	27 Jan 2004 11:36:32 -0000	1.97.2.98
+++ drbd_receiver.c	27 Jan 2004 15:51:36 -0000	1.97.2.99
@@ -899,6 +899,10 @@
 	}
 
 	// Do not use data_size in the memcpy. The app read might be smaller.
+	/* XXX for exactly this reason: maybe don't memcpy at all, but first
+	 * write it to disk, and only then propagate the read to upper layers?
+	 * the next app read might target the very same region!
+	 */
 	memcpy(drbd_bio_kmap(bio),drbd_bio_kmap(&e->private_bio),
 	       drbd_bio_get_size(bio));
 	drbd_bio_kunmap(bio);
===================================================================
RCS file: /var/lib/cvs/drbd/drbd/drbd/drbd_req-2.4.c,v
retrieving revision 1.33.2.46
retrieving revision 1.33.2.47
diff -u -3 -r1.33.2.46 -r1.33.2.47
--- drbd_req-2.4.c	27 Jan 2004 09:16:50 -0000	1.33.2.46
+++ drbd_req-2.4.c	27 Jan 2004 15:51:36 -0000	1.33.2.47
@@ -131,10 +131,34 @@
 	drbd_send_drequest(mdev, DataRequest, bio->b_rsector, bio->b_size,
 			   (unsigned long)pr);
 #else
+	//WORK_HERE
 #warning "FIXME make 2.6.x clean"
 #endif
 }
 
+
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
+int drbd_merge_bvec_fn(request_queue_t *q, struct bio *bio, struct bio_vec *bv)
+{
+	drbd_dev * const mdev = q->queuedata;
+	sector_t sector = bio->bi_sector;
+	int lo_max = PAGE_SIZE, max = PAGE_SIZE;
+	const unsigned long chunk_sectors = AL_EXTENT_SIZE >> 9;
+
+	D_ASSERT(bio->bi_size == 0);
+
+	if (mdev->backing_bdev) {
+		request_queue_t * const b = mdev->backing_bdev->bd_disk->queue;
+		if (b->merge_bvec_fn)
+			lo_max = b->merge_bvec_fn(b,bio,bv);
+	}
+	max = (chunk_sectors - (sector & (chunk_sectors - 1))) << 9;
+	max = min(lo_max,max);
+	// if (max < 0) max = 0; /* bio_add cannot handle a negative return */
+	return min(PAGE_SIZE,max);
+}
+#endif
+
 #if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0)
 int drbd_make_request(request_queue_t *q, int rw, struct buffer_head *bio)
 #else
@@ -208,6 +232,7 @@
 			}
 			SET_MAGIC(req);
 
+			//WORK_HERE
 			/* FIXME the drbd_make_request function will be
 			 * restructured soon.
 			 * until that is the case,
@@ -263,6 +288,7 @@
 		bio->b_rdev = mdev->lo_device;
 #else
 #warning "FIXME"
+			//WORK_HERE
 		/* I want to change it anyways so we never remap ... */
 #endif
 		return 1; // Not arranged for transfer ( but remapped :)
@@ -279,6 +305,7 @@
 		bio->b_rdev = mdev->lo_device;
 #else
 #warning "FIXME"
+			//WORK_HERE
 		/* I want to change it anyways so we never remap ... */
 #endif
 		return 1; // Not arranged for transfer ( but remapped :)