From 7b6d91daee5cac6402186ff224c3af39d79f4a0e Mon Sep 17 00:00:00 2001 From: Christoph Hellwig Date: Sat, 7 Aug 2010 18:20:39 +0200 Subject: block: unify flags for struct bio and struct request Remove the current bio flags and reuse the request flags for the bio, too. This allows to more easily trace the type of I/O from the filesystem down to the block driver. There were two flags in the bio that were missing in the requests: BIO_RW_UNPLUG and BIO_RW_AHEAD. Also I've renamed two request flags that had a superflous RW in them. Note that the flags are in bio.h despite having the REQ_ name - as blkdev.h includes bio.h that is the only way to go for now. Signed-off-by: Christoph Hellwig Signed-off-by: Jens Axboe --- drivers/block/drbd/drbd_actlog.c | 8 ++++---- drivers/block/drbd/drbd_main.c | 6 +++--- drivers/block/drbd/drbd_receiver.c | 22 +++++++++++----------- drivers/block/drbd/drbd_req.c | 2 +- 4 files changed, 19 insertions(+), 19 deletions(-) (limited to 'drivers/block/drbd') diff --git a/drivers/block/drbd/drbd_actlog.c b/drivers/block/drbd/drbd_actlog.c index df01899..9400845 100644 --- a/drivers/block/drbd/drbd_actlog.c +++ b/drivers/block/drbd/drbd_actlog.c @@ -79,8 +79,8 @@ static int _drbd_md_sync_page_io(struct drbd_conf *mdev, md_io.error = 0; if ((rw & WRITE) && !test_bit(MD_NO_BARRIER, &mdev->flags)) - rw |= (1 << BIO_RW_BARRIER); - rw |= ((1<bi_rw & REQ_HARDBARRIER) && !ok)) { /* Try again with no barrier */ dev_warn(DEV, "Barriers not supported on meta data device - disabling\n"); set_bit(MD_NO_BARRIER, &mdev->flags); - rw &= ~(1 << BIO_RW_BARRIER); + rw &= ~REQ_HARDBARRIER; bio_put(bio); goto retry; } diff --git a/drivers/block/drbd/drbd_main.c b/drivers/block/drbd/drbd_main.c index 7258c95..e2ab13d 100644 --- a/drivers/block/drbd/drbd_main.c +++ b/drivers/block/drbd/drbd_main.c @@ -2425,15 +2425,15 @@ int drbd_send_dblock(struct drbd_conf *mdev, struct drbd_request *req) /* NOTE: no need to check if barriers supported here as we would * not pass the test in make_request_common in that case */ - if (bio_rw_flagged(req->master_bio, BIO_RW_BARRIER)) { + if (req->master_bio->bi_rw & REQ_HARDBARRIER) { dev_err(DEV, "ASSERT FAILED would have set DP_HARDBARRIER\n"); /* dp_flags |= DP_HARDBARRIER; */ } - if (bio_rw_flagged(req->master_bio, BIO_RW_SYNCIO)) + if (req->master_bio->bi_rw & REQ_SYNC) dp_flags |= DP_RW_SYNC; /* for now handle SYNCIO and UNPLUG * as if they still were one and the same flag */ - if (bio_rw_flagged(req->master_bio, BIO_RW_UNPLUG)) + if (req->master_bio->bi_rw & REQ_UNPLUG) dp_flags |= DP_RW_SYNC; if (mdev->state.conn >= C_SYNC_SOURCE && mdev->state.conn <= C_PAUSED_SYNC_T) diff --git a/drivers/block/drbd/drbd_receiver.c b/drivers/block/drbd/drbd_receiver.c index dff4870..cba1deb 100644 --- a/drivers/block/drbd/drbd_receiver.c +++ b/drivers/block/drbd/drbd_receiver.c @@ -1180,7 +1180,7 @@ next_bio: bio->bi_sector = sector; bio->bi_bdev = mdev->ldev->backing_bdev; /* we special case some flags in the multi-bio case, see below - * (BIO_RW_UNPLUG, BIO_RW_BARRIER) */ + * (REQ_UNPLUG, REQ_HARDBARRIER) */ bio->bi_rw = rw; bio->bi_private = e; bio->bi_end_io = drbd_endio_sec; @@ -1209,16 +1209,16 @@ next_bio: bios = bios->bi_next; bio->bi_next = NULL; - /* strip off BIO_RW_UNPLUG unless it is the last bio */ + /* strip off REQ_UNPLUG unless it is the last bio */ if (bios) - bio->bi_rw &= ~(1<bi_rw &= ~REQ_UNPLUG; drbd_generic_make_request(mdev, fault_type, bio); - /* strip off BIO_RW_BARRIER, + /* strip off REQ_HARDBARRIER, * unless it is the first or last bio */ if (bios && bios->bi_next) - bios->bi_rw &= ~(1<bi_rw &= ~REQ_HARDBARRIER; } while (bios); maybe_kick_lo(mdev); return 0; @@ -1233,7 +1233,7 @@ fail: } /** - * w_e_reissue() - Worker callback; Resubmit a bio, without BIO_RW_BARRIER set + * w_e_reissue() - Worker callback; Resubmit a bio, without REQ_HARDBARRIER set * @mdev: DRBD device. * @w: work object. * @cancel: The connection will be closed anyways (unused in this callback) @@ -1245,7 +1245,7 @@ int w_e_reissue(struct drbd_conf *mdev, struct drbd_work *w, int cancel) __relea (and DE_BARRIER_IN_NEXT_EPOCH_ISSUED in the previous Epoch) so that we can finish that epoch in drbd_may_finish_epoch(). That is necessary if we already have a long chain of Epochs, before - we realize that BIO_RW_BARRIER is actually not supported */ + we realize that REQ_HARDBARRIER is actually not supported */ /* As long as the -ENOTSUPP on the barrier is reported immediately that will never trigger. If it is reported late, we will just @@ -1824,14 +1824,14 @@ static int receive_Data(struct drbd_conf *mdev, struct p_header *h) epoch = list_entry(e->epoch->list.prev, struct drbd_epoch, list); if (epoch == e->epoch) { set_bit(DE_CONTAINS_A_BARRIER, &e->epoch->flags); - rw |= (1<flags |= EE_IS_BARRIER; } else { if (atomic_read(&epoch->epoch_size) > 1 || !test_bit(DE_CONTAINS_A_BARRIER, &epoch->flags)) { set_bit(DE_BARRIER_IN_NEXT_EPOCH_ISSUED, &epoch->flags); set_bit(DE_CONTAINS_A_BARRIER, &e->epoch->flags); - rw |= (1<flags |= EE_IS_BARRIER; } } @@ -1841,10 +1841,10 @@ static int receive_Data(struct drbd_conf *mdev, struct p_header *h) dp_flags = be32_to_cpu(p->dp_flags); if (dp_flags & DP_HARDBARRIER) { dev_err(DEV, "ASSERT FAILED would have submitted barrier request\n"); - /* rw |= (1<flags |= EE_MAY_SET_IN_SYNC; diff --git a/drivers/block/drbd/drbd_req.c b/drivers/block/drbd/drbd_req.c index 654f1ef..f761d98 100644 --- a/drivers/block/drbd/drbd_req.c +++ b/drivers/block/drbd/drbd_req.c @@ -997,7 +997,7 @@ int drbd_make_request_26(struct request_queue *q, struct bio *bio) * because of those XXX, this is not yet enabled, * i.e. in drbd_init_set_defaults we set the NO_BARRIER_SUPP bit. */ - if (unlikely(bio_rw_flagged(bio, BIO_RW_BARRIER) && test_bit(NO_BARRIER_SUPP, &mdev->flags))) { + if (unlikely(bio->bi_rw & REQ_HARDBARRIER) && test_bit(NO_BARRIER_SUPP, &mdev->flags)) { /* dev_warn(DEV, "Rejecting barrier request as underlying device does not support\n"); */ bio_endio(bio, -EOPNOTSUPP); return 0; -- cgit v1.1 From 6e9624b8caec290d28b4c6d9ec75749df6372b87 Mon Sep 17 00:00:00 2001 From: Arnd Bergmann Date: Sat, 7 Aug 2010 18:25:34 +0200 Subject: block: push down BKL into .open and .release The open and release block_device_operations are currently called with the BKL held. In order to change that, we must first make sure that all drivers that currently rely on this have no regressions. This blindly pushes the BKL into all .open and .release operations for all block drivers to prepare for the next step. The drivers can subsequently replace the BKL with their own locks or remove it completely when it can be shown that it is not needed. The functions blkdev_get and blkdev_put are the only remaining users of the big kernel lock in the block layer, besides a few uses in the ioctl code, none of which need to serialize with blkdev_{get,put}. Most of these two functions is also under the protection of bdev->bd_mutex, including the actual calls to ->open and ->release, and the common code does not access any global data structures that need the BKL. Signed-off-by: Arnd Bergmann Acked-by: Christoph Hellwig Signed-off-by: Jens Axboe --- drivers/block/drbd/drbd_main.c | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'drivers/block/drbd') diff --git a/drivers/block/drbd/drbd_main.c b/drivers/block/drbd/drbd_main.c index e2ab13d..d2b6764 100644 --- a/drivers/block/drbd/drbd_main.c +++ b/drivers/block/drbd/drbd_main.c @@ -2604,6 +2604,7 @@ static int drbd_open(struct block_device *bdev, fmode_t mode) unsigned long flags; int rv = 0; + lock_kernel(); spin_lock_irqsave(&mdev->req_lock, flags); /* to have a stable mdev->state.role * and no race with updating open_cnt */ @@ -2618,6 +2619,7 @@ static int drbd_open(struct block_device *bdev, fmode_t mode) if (!rv) mdev->open_cnt++; spin_unlock_irqrestore(&mdev->req_lock, flags); + unlock_kernel(); return rv; } @@ -2625,7 +2627,9 @@ static int drbd_open(struct block_device *bdev, fmode_t mode) static int drbd_release(struct gendisk *gd, fmode_t mode) { struct drbd_conf *mdev = gd->private_data; + lock_kernel(); mdev->open_cnt--; + unlock_kernel(); return 0; } -- cgit v1.1 From 6710a5760355be8f2e51682f41b0d3fc76550309 Mon Sep 17 00:00:00 2001 From: Philipp Reisner Date: Mon, 19 Jul 2010 15:04:57 +0200 Subject: drbd: Disable delay probes for the upcomming release Signed-off-by: Philipp Reisner Signed-off-by: Lars Ellenberg Cc: stable@kernel.org Signed-off-by: Jens Axboe --- drivers/block/drbd/drbd_main.c | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) (limited to 'drivers/block/drbd') diff --git a/drivers/block/drbd/drbd_main.c b/drivers/block/drbd/drbd_main.c index d2b6764..0c1e84a 100644 --- a/drivers/block/drbd/drbd_main.c +++ b/drivers/block/drbd/drbd_main.c @@ -2371,11 +2371,7 @@ static int _drbd_send_zc_ee(struct drbd_conf *mdev, struct drbd_epoch_entry *e) static void consider_delay_probes(struct drbd_conf *mdev) { - if (mdev->state.conn != C_SYNC_SOURCE || mdev->agreed_pro_version < 93) - return; - - if (mdev->dp_volume_last + mdev->sync_conf.dp_volume * 2 < mdev->send_cnt) - drbd_send_delay_probes(mdev); + return; } static int w_delay_probes(struct drbd_conf *mdev, struct drbd_work *w, int cancel) -- cgit v1.1 From 85f4cc17a62c3ac9edeaf120cdae7261df458053 Mon Sep 17 00:00:00 2001 From: Philipp Reisner Date: Tue, 29 Jun 2010 17:35:34 +0200 Subject: drbd: Initialize all members of sync_conf to their defaults [Bugz 315] Signed-off-by: Philipp Reisner Signed-off-by: Lars Ellenberg Cc: stable@kernel.org Signed-off-by: Jens Axboe --- drivers/block/drbd/drbd_main.c | 21 ++++++++++++++++++--- 1 file changed, 18 insertions(+), 3 deletions(-) (limited to 'drivers/block/drbd') diff --git a/drivers/block/drbd/drbd_main.c b/drivers/block/drbd/drbd_main.c index 0c1e84a..668f063 100644 --- a/drivers/block/drbd/drbd_main.c +++ b/drivers/block/drbd/drbd_main.c @@ -2660,9 +2660,24 @@ static void drbd_unplug_fn(struct request_queue *q) static void drbd_set_defaults(struct drbd_conf *mdev) { - mdev->sync_conf.after = DRBD_AFTER_DEF; - mdev->sync_conf.rate = DRBD_RATE_DEF; - mdev->sync_conf.al_extents = DRBD_AL_EXTENTS_DEF; + /* This way we get a compile error when sync_conf grows, + and we forgot to initialize it here */ + mdev->sync_conf = (struct syncer_conf) { + /* .rate = */ DRBD_RATE_DEF, + /* .after = */ DRBD_AFTER_DEF, + /* .al_extents = */ DRBD_AL_EXTENTS_DEF, + /* .dp_volume = */ DRBD_DP_VOLUME_DEF, + /* .dp_interval = */ DRBD_DP_INTERVAL_DEF, + /* .throttle_th = */ DRBD_RS_THROTTLE_TH_DEF, + /* .hold_off_th = */ DRBD_RS_HOLD_OFF_TH_DEF, + /* .verify_alg = */ {}, 0, + /* .cpu_mask = */ {}, 0, + /* .csums_alg = */ {}, 0, + /* .use_rle = */ 0 + }; + + /* Have to use that way, because the layout differs between + big endian and little endian */ mdev->state = (union drbd_state) { { .role = R_SECONDARY, .peer = R_UNKNOWN, -- cgit v1.1 From e7f52dfb4f378ea1bbfd4476f4e8ba42f5fb332c Mon Sep 17 00:00:00 2001 From: Lars Ellenberg Date: Tue, 3 Aug 2010 20:20:20 +0200 Subject: drbd: revert "delay probes", feature is being re-implemented differently It was a now abandoned attempt to throttle resync bandwidth based on the delay it causes on the bulk data socket. It has no userbase yet, and has been disabled by 9173465ccb51c09cc3102a10af93e9f469a0af6f already. This removes the now unused code. The basic feature, namely using up "idle" bandwith of network and disk IO subsystem, with minimal impact to application IO, is being reimplemented differently. Signed-off-by: Philipp Reisner Signed-off-by: Lars Ellenberg Signed-off-by: Jens Axboe --- drivers/block/drbd/drbd_int.h | 16 +----- drivers/block/drbd/drbd_main.c | 75 ------------------------ drivers/block/drbd/drbd_nl.c | 4 -- drivers/block/drbd/drbd_proc.c | 19 +------ drivers/block/drbd/drbd_receiver.c | 113 ++++++------------------------------- drivers/block/drbd/drbd_worker.c | 15 +---- 6 files changed, 22 insertions(+), 220 deletions(-) (limited to 'drivers/block/drbd') diff --git a/drivers/block/drbd/drbd_int.h b/drivers/block/drbd/drbd_int.h index 485ed8c..352441b 100644 --- a/drivers/block/drbd/drbd_int.h +++ b/drivers/block/drbd/drbd_int.h @@ -550,12 +550,6 @@ struct p_delay_probe { u32 offset; /* usecs the probe got sent after the reference time point */ } __packed; -struct delay_probe { - struct list_head list; - unsigned int seq_num; - struct timeval time; -}; - /* DCBP: Drbd Compressed Bitmap Packet ... */ static inline enum drbd_bitmap_code DCBP_get_code(struct p_compressed_bm *p) @@ -942,11 +936,9 @@ struct drbd_conf { unsigned int ko_count; struct drbd_work resync_work, unplug_work, - md_sync_work, - delay_probe_work; + md_sync_work; struct timer_list resync_timer; struct timer_list md_sync_timer; - struct timer_list delay_probe_timer; /* Used after attach while negotiating new disk state. */ union drbd_state new_state_tmp; @@ -1062,12 +1054,6 @@ struct drbd_conf { u64 ed_uuid; /* UUID of the exposed data */ struct mutex state_mutex; char congestion_reason; /* Why we where congested... */ - struct list_head delay_probes; /* protected by peer_seq_lock */ - int data_delay; /* Delay of packets on the data-sock behind meta-sock */ - unsigned int delay_seq; /* To generate sequence numbers of delay probes */ - struct timeval dps_time; /* delay-probes-start-time */ - unsigned int dp_volume_last; /* send_cnt of last delay probe */ - int c_sync_rate; /* current resync rate after delay_probe magic */ }; static inline struct drbd_conf *minor_to_mdev(unsigned int minor) diff --git a/drivers/block/drbd/drbd_main.c b/drivers/block/drbd/drbd_main.c index 668f063..fa650dd 100644 --- a/drivers/block/drbd/drbd_main.c +++ b/drivers/block/drbd/drbd_main.c @@ -2184,43 +2184,6 @@ int drbd_send_ov_request(struct drbd_conf *mdev, sector_t sector, int size) return ok; } -static int drbd_send_delay_probe(struct drbd_conf *mdev, struct drbd_socket *ds) -{ - struct p_delay_probe dp; - int offset, ok = 0; - struct timeval now; - - mutex_lock(&ds->mutex); - if (likely(ds->socket)) { - do_gettimeofday(&now); - offset = now.tv_usec - mdev->dps_time.tv_usec + - (now.tv_sec - mdev->dps_time.tv_sec) * 1000000; - dp.seq_num = cpu_to_be32(mdev->delay_seq); - dp.offset = cpu_to_be32(offset); - - ok = _drbd_send_cmd(mdev, ds->socket, P_DELAY_PROBE, - (struct p_header *)&dp, sizeof(dp), 0); - } - mutex_unlock(&ds->mutex); - - return ok; -} - -static int drbd_send_delay_probes(struct drbd_conf *mdev) -{ - int ok; - - mdev->delay_seq++; - do_gettimeofday(&mdev->dps_time); - ok = drbd_send_delay_probe(mdev, &mdev->meta); - ok = ok && drbd_send_delay_probe(mdev, &mdev->data); - - mdev->dp_volume_last = mdev->send_cnt; - mod_timer(&mdev->delay_probe_timer, jiffies + mdev->sync_conf.dp_interval * HZ / 10); - - return ok; -} - /* called on sndtimeo * returns FALSE if we should retry, * TRUE if we think connection is dead @@ -2369,27 +2332,6 @@ static int _drbd_send_zc_ee(struct drbd_conf *mdev, struct drbd_epoch_entry *e) return 1; } -static void consider_delay_probes(struct drbd_conf *mdev) -{ - return; -} - -static int w_delay_probes(struct drbd_conf *mdev, struct drbd_work *w, int cancel) -{ - if (!cancel && mdev->state.conn == C_SYNC_SOURCE) - drbd_send_delay_probes(mdev); - - return 1; -} - -static void delay_probe_timer_fn(unsigned long data) -{ - struct drbd_conf *mdev = (struct drbd_conf *) data; - - if (list_empty(&mdev->delay_probe_work.list)) - drbd_queue_work(&mdev->data.work, &mdev->delay_probe_work); -} - /* Used to send write requests * R_PRIMARY -> Peer (P_DATA) */ @@ -2453,9 +2395,6 @@ int drbd_send_dblock(struct drbd_conf *mdev, struct drbd_request *req) drbd_put_data_sock(mdev); - if (ok) - consider_delay_probes(mdev); - return ok; } @@ -2502,9 +2441,6 @@ int drbd_send_block(struct drbd_conf *mdev, enum drbd_packets cmd, drbd_put_data_sock(mdev); - if (ok) - consider_delay_probes(mdev); - return ok; } @@ -2666,10 +2602,6 @@ static void drbd_set_defaults(struct drbd_conf *mdev) /* .rate = */ DRBD_RATE_DEF, /* .after = */ DRBD_AFTER_DEF, /* .al_extents = */ DRBD_AL_EXTENTS_DEF, - /* .dp_volume = */ DRBD_DP_VOLUME_DEF, - /* .dp_interval = */ DRBD_DP_INTERVAL_DEF, - /* .throttle_th = */ DRBD_RS_THROTTLE_TH_DEF, - /* .hold_off_th = */ DRBD_RS_HOLD_OFF_TH_DEF, /* .verify_alg = */ {}, 0, /* .cpu_mask = */ {}, 0, /* .csums_alg = */ {}, 0, @@ -2736,24 +2668,17 @@ void drbd_init_set_defaults(struct drbd_conf *mdev) INIT_LIST_HEAD(&mdev->unplug_work.list); INIT_LIST_HEAD(&mdev->md_sync_work.list); INIT_LIST_HEAD(&mdev->bm_io_work.w.list); - INIT_LIST_HEAD(&mdev->delay_probes); - INIT_LIST_HEAD(&mdev->delay_probe_work.list); mdev->resync_work.cb = w_resync_inactive; mdev->unplug_work.cb = w_send_write_hint; mdev->md_sync_work.cb = w_md_sync; mdev->bm_io_work.w.cb = w_bitmap_io; - mdev->delay_probe_work.cb = w_delay_probes; init_timer(&mdev->resync_timer); init_timer(&mdev->md_sync_timer); - init_timer(&mdev->delay_probe_timer); mdev->resync_timer.function = resync_timer_fn; mdev->resync_timer.data = (unsigned long) mdev; mdev->md_sync_timer.function = md_sync_timer_fn; mdev->md_sync_timer.data = (unsigned long) mdev; - mdev->delay_probe_timer.function = delay_probe_timer_fn; - mdev->delay_probe_timer.data = (unsigned long) mdev; - init_waitqueue_head(&mdev->misc_wait); init_waitqueue_head(&mdev->state_wait); diff --git a/drivers/block/drbd/drbd_nl.c b/drivers/block/drbd/drbd_nl.c index 2151f18..73131c5 100644 --- a/drivers/block/drbd/drbd_nl.c +++ b/drivers/block/drbd/drbd_nl.c @@ -1557,10 +1557,6 @@ static int drbd_nl_syncer_conf(struct drbd_conf *mdev, struct drbd_nl_cfg_req *n sc.rate = DRBD_RATE_DEF; sc.after = DRBD_AFTER_DEF; sc.al_extents = DRBD_AL_EXTENTS_DEF; - sc.dp_volume = DRBD_DP_VOLUME_DEF; - sc.dp_interval = DRBD_DP_INTERVAL_DEF; - sc.throttle_th = DRBD_RS_THROTTLE_TH_DEF; - sc.hold_off_th = DRBD_RS_HOLD_OFF_TH_DEF; } else memcpy(&sc, &mdev->sync_conf, sizeof(struct syncer_conf)); diff --git a/drivers/block/drbd/drbd_proc.c b/drivers/block/drbd/drbd_proc.c index d0f1767..be3374b 100644 --- a/drivers/block/drbd/drbd_proc.c +++ b/drivers/block/drbd/drbd_proc.c @@ -73,21 +73,14 @@ static void drbd_syncer_progress(struct drbd_conf *mdev, struct seq_file *seq) seq_printf(seq, "sync'ed:%3u.%u%% ", res / 10, res % 10); /* if more than 1 GB display in MB */ if (mdev->rs_total > 0x100000L) - seq_printf(seq, "(%lu/%lu)M", + seq_printf(seq, "(%lu/%lu)M\n\t", (unsigned long) Bit2KB(rs_left >> 10), (unsigned long) Bit2KB(mdev->rs_total >> 10)); else - seq_printf(seq, "(%lu/%lu)K", + seq_printf(seq, "(%lu/%lu)K\n\t", (unsigned long) Bit2KB(rs_left), (unsigned long) Bit2KB(mdev->rs_total)); - if (mdev->state.conn == C_SYNC_TARGET) - seq_printf(seq, " queue_delay: %d.%d ms\n\t", - mdev->data_delay / 1000, - (mdev->data_delay % 1000) / 100); - else if (mdev->state.conn == C_SYNC_SOURCE) - seq_printf(seq, " delay_probe: %u\n\t", mdev->delay_seq); - /* see drivers/md/md.c * We do not want to overflow, so the order of operands and * the * 100 / 100 trick are important. We do a +1 to be @@ -135,14 +128,6 @@ static void drbd_syncer_progress(struct drbd_conf *mdev, struct seq_file *seq) else seq_printf(seq, " (%ld)", dbdt); - if (mdev->state.conn == C_SYNC_TARGET) { - if (mdev->c_sync_rate > 1000) - seq_printf(seq, " want: %d,%03d", - mdev->c_sync_rate / 1000, mdev->c_sync_rate % 1000); - else - seq_printf(seq, " want: %d", mdev->c_sync_rate); - } - seq_printf(seq, " K/sec\n"); } diff --git a/drivers/block/drbd/drbd_receiver.c b/drivers/block/drbd/drbd_receiver.c index cba1deb..20abef5 100644 --- a/drivers/block/drbd/drbd_receiver.c +++ b/drivers/block/drbd/drbd_receiver.c @@ -3555,14 +3555,15 @@ static int receive_bitmap(struct drbd_conf *mdev, struct p_header *h) return ok; } -static int receive_skip(struct drbd_conf *mdev, struct p_header *h) +static int receive_skip_(struct drbd_conf *mdev, struct p_header *h, int silent) { /* TODO zero copy sink :) */ static char sink[128]; int size, want, r; - dev_warn(DEV, "skipping unknown optional packet type %d, l: %d!\n", - h->command, h->length); + if (!silent) + dev_warn(DEV, "skipping unknown optional packet type %d, l: %d!\n", + h->command, h->length); size = h->length; while (size > 0) { @@ -3574,101 +3575,25 @@ static int receive_skip(struct drbd_conf *mdev, struct p_header *h) return size == 0; } -static int receive_UnplugRemote(struct drbd_conf *mdev, struct p_header *h) -{ - if (mdev->state.disk >= D_INCONSISTENT) - drbd_kick_lo(mdev); - - /* Make sure we've acked all the TCP data associated - * with the data requests being unplugged */ - drbd_tcp_quickack(mdev->data.socket); - - return TRUE; -} - -static void timeval_sub_us(struct timeval* tv, unsigned int us) +static int receive_skip(struct drbd_conf *mdev, struct p_header *h) { - tv->tv_sec -= us / 1000000; - us = us % 1000000; - if (tv->tv_usec > us) { - tv->tv_usec += 1000000; - tv->tv_sec--; - } - tv->tv_usec -= us; + return receive_skip_(mdev, h, 0); } -static void got_delay_probe(struct drbd_conf *mdev, int from, struct p_delay_probe *p) +static int receive_skip_silent(struct drbd_conf *mdev, struct p_header *h) { - struct delay_probe *dp; - struct list_head *le; - struct timeval now; - int seq_num; - int offset; - int data_delay; - - seq_num = be32_to_cpu(p->seq_num); - offset = be32_to_cpu(p->offset); - - spin_lock(&mdev->peer_seq_lock); - if (!list_empty(&mdev->delay_probes)) { - if (from == USE_DATA_SOCKET) - le = mdev->delay_probes.next; - else - le = mdev->delay_probes.prev; - - dp = list_entry(le, struct delay_probe, list); - - if (dp->seq_num == seq_num) { - list_del(le); - spin_unlock(&mdev->peer_seq_lock); - do_gettimeofday(&now); - timeval_sub_us(&now, offset); - data_delay = - now.tv_usec - dp->time.tv_usec + - (now.tv_sec - dp->time.tv_sec) * 1000000; - - if (data_delay > 0) - mdev->data_delay = data_delay; - - kfree(dp); - return; - } - - if (dp->seq_num > seq_num) { - spin_unlock(&mdev->peer_seq_lock); - dev_warn(DEV, "Previous allocation failure of struct delay_probe?\n"); - return; /* Do not alloca a struct delay_probe.... */ - } - } - spin_unlock(&mdev->peer_seq_lock); - - dp = kmalloc(sizeof(struct delay_probe), GFP_NOIO); - if (!dp) { - dev_warn(DEV, "Failed to allocate a struct delay_probe, do not worry.\n"); - return; - } - - dp->seq_num = seq_num; - do_gettimeofday(&dp->time); - timeval_sub_us(&dp->time, offset); - - spin_lock(&mdev->peer_seq_lock); - if (from == USE_DATA_SOCKET) - list_add(&dp->list, &mdev->delay_probes); - else - list_add_tail(&dp->list, &mdev->delay_probes); - spin_unlock(&mdev->peer_seq_lock); + return receive_skip_(mdev, h, 1); } -static int receive_delay_probe(struct drbd_conf *mdev, struct p_header *h) +static int receive_UnplugRemote(struct drbd_conf *mdev, struct p_header *h) { - struct p_delay_probe *p = (struct p_delay_probe *)h; + if (mdev->state.disk >= D_INCONSISTENT) + drbd_kick_lo(mdev); - ERR_IF(h->length != (sizeof(*p)-sizeof(*h))) return FALSE; - if (drbd_recv(mdev, h->payload, h->length) != h->length) - return FALSE; + /* Make sure we've acked all the TCP data associated + * with the data requests being unplugged */ + drbd_tcp_quickack(mdev->data.socket); - got_delay_probe(mdev, USE_DATA_SOCKET, p); return TRUE; } @@ -3695,7 +3620,7 @@ static drbd_cmd_handler_f drbd_default_handler[] = { [P_OV_REQUEST] = receive_DataRequest, [P_OV_REPLY] = receive_DataRequest, [P_CSUM_RS_REQUEST] = receive_DataRequest, - [P_DELAY_PROBE] = receive_delay_probe, + [P_DELAY_PROBE] = receive_skip_silent, /* anything missing from this table is in * the asender_tbl, see get_asender_cmd */ [P_MAX_CMD] = NULL, @@ -4472,11 +4397,9 @@ static int got_OVResult(struct drbd_conf *mdev, struct p_header *h) return TRUE; } -static int got_delay_probe_m(struct drbd_conf *mdev, struct p_header *h) +static int got_something_to_ignore_m(struct drbd_conf *mdev, struct p_header *h) { - struct p_delay_probe *p = (struct p_delay_probe *)h; - - got_delay_probe(mdev, USE_META_SOCKET, p); + /* IGNORE */ return TRUE; } @@ -4504,7 +4427,7 @@ static struct asender_cmd *get_asender_cmd(int cmd) [P_BARRIER_ACK] = { sizeof(struct p_barrier_ack), got_BarrierAck }, [P_STATE_CHG_REPLY] = { sizeof(struct p_req_state_reply), got_RqSReply }, [P_RS_IS_IN_SYNC] = { sizeof(struct p_block_ack), got_IsInSync }, - [P_DELAY_PROBE] = { sizeof(struct p_delay_probe), got_delay_probe_m }, + [P_DELAY_PROBE] = { sizeof(struct p_delay_probe), got_something_to_ignore_m }, [P_MAX_CMD] = { 0, NULL }, }; if (cmd > P_MAX_CMD || asender_tbl[cmd].process == NULL) diff --git a/drivers/block/drbd/drbd_worker.c b/drivers/block/drbd/drbd_worker.c index b623cee..ca4a16c 100644 --- a/drivers/block/drbd/drbd_worker.c +++ b/drivers/block/drbd/drbd_worker.c @@ -424,18 +424,6 @@ void resync_timer_fn(unsigned long data) drbd_queue_work(&mdev->data.work, &mdev->resync_work); } -static int calc_resync_rate(struct drbd_conf *mdev) -{ - int d = mdev->data_delay / 1000; /* us -> ms */ - int td = mdev->sync_conf.throttle_th * 100; /* 0.1s -> ms */ - int hd = mdev->sync_conf.hold_off_th * 100; /* 0.1s -> ms */ - int cr = mdev->sync_conf.rate; - - return d <= td ? cr : - d >= hd ? 0 : - cr + (cr * (td - d) / (hd - td)); -} - int w_make_resync_request(struct drbd_conf *mdev, struct drbd_work *w, int cancel) { @@ -473,8 +461,7 @@ int w_make_resync_request(struct drbd_conf *mdev, max_segment_size = mdev->agreed_pro_version < 94 ? queue_max_segment_size(mdev->rq_queue) : DRBD_MAX_SEGMENT_SIZE; - mdev->c_sync_rate = calc_resync_rate(mdev); - number = SLEEP_TIME * mdev->c_sync_rate / ((BM_BLOCK_SIZE / 1024) * HZ); + number = SLEEP_TIME * mdev->sync_conf.rate / ((BM_BLOCK_SIZE / 1024) * HZ); pe = atomic_read(&mdev->rs_pending_cnt); mutex_lock(&mdev->data.mutex); -- cgit v1.1