diff options
author | Philipp Reisner <philipp.reisner@linbit.com> | 2011-02-05 11:34:11 -0500 |
---|---|---|
committer | Philipp Reisner <philipp.reisner@linbit.com> | 2011-09-28 04:26:47 -0400 |
commit | e64a32945902a178c9de9b38e0ea3290981605bc (patch) | |
tree | 3f7f18114122a7dbd55ab0b39ecf9e8203d8e5ea /drivers/block/drbd/drbd_worker.c | |
parent | 1f04af33fe7db542d75a487b8381b5a3402b7896 (diff) |
drbd: Do no sleep long in drbd_start_resync
Work items that sleep too long can cause requests to take as
long as the longest sleeping work item.
Signed-off-by: Philipp Reisner <philipp.reisner@linbit.com>
Signed-off-by: Lars Ellenberg <lars.ellenberg@linbit.com>
Diffstat (limited to 'drivers/block/drbd/drbd_worker.c')
-rw-r--r-- | drivers/block/drbd/drbd_worker.c | 58 |
1 files changed, 36 insertions, 22 deletions
diff --git a/drivers/block/drbd/drbd_worker.c b/drivers/block/drbd/drbd_worker.c index 28925d3d1a2f..a705979c71f8 100644 --- a/drivers/block/drbd/drbd_worker.c +++ b/drivers/block/drbd/drbd_worker.c | |||
@@ -1487,35 +1487,49 @@ void drbd_start_resync(struct drbd_conf *mdev, enum drbd_conns side) | |||
1487 | Ahead/Behind and SyncSource/SyncTarget */ | 1487 | Ahead/Behind and SyncSource/SyncTarget */ |
1488 | } | 1488 | } |
1489 | 1489 | ||
1490 | if (side == C_SYNC_TARGET) { | 1490 | if (!test_bit(B_RS_H_DONE, &mdev->flags)) { |
1491 | /* Since application IO was locked out during C_WF_BITMAP_T and | 1491 | if (side == C_SYNC_TARGET) { |
1492 | C_WF_SYNC_UUID we are still unmodified. Before going to C_SYNC_TARGET | 1492 | /* Since application IO was locked out during C_WF_BITMAP_T and |
1493 | we check that we might make the data inconsistent. */ | 1493 | C_WF_SYNC_UUID we are still unmodified. Before going to C_SYNC_TARGET |
1494 | r = drbd_khelper(mdev, "before-resync-target"); | 1494 | we check that we might make the data inconsistent. */ |
1495 | r = (r >> 8) & 0xff; | 1495 | r = drbd_khelper(mdev, "before-resync-target"); |
1496 | if (r > 0) { | 1496 | r = (r >> 8) & 0xff; |
1497 | dev_info(DEV, "before-resync-target handler returned %d, " | 1497 | if (r > 0) { |
1498 | "dropping connection.\n", r); | 1498 | dev_info(DEV, "before-resync-target handler returned %d, " |
1499 | drbd_force_state(mdev, NS(conn, C_DISCONNECTING)); | ||
1500 | return; | ||
1501 | } | ||
1502 | } else /* C_SYNC_SOURCE */ { | ||
1503 | r = drbd_khelper(mdev, "before-resync-source"); | ||
1504 | r = (r >> 8) & 0xff; | ||
1505 | if (r > 0) { | ||
1506 | if (r == 3) { | ||
1507 | dev_info(DEV, "before-resync-source handler returned %d, " | ||
1508 | "ignoring. Old userland tools?", r); | ||
1509 | } else { | ||
1510 | dev_info(DEV, "before-resync-source handler returned %d, " | ||
1511 | "dropping connection.\n", r); | 1499 | "dropping connection.\n", r); |
1512 | drbd_force_state(mdev, NS(conn, C_DISCONNECTING)); | 1500 | drbd_force_state(mdev, NS(conn, C_DISCONNECTING)); |
1513 | return; | 1501 | return; |
1514 | } | 1502 | } |
1503 | } else /* C_SYNC_SOURCE */ { | ||
1504 | r = drbd_khelper(mdev, "before-resync-source"); | ||
1505 | r = (r >> 8) & 0xff; | ||
1506 | if (r > 0) { | ||
1507 | if (r == 3) { | ||
1508 | dev_info(DEV, "before-resync-source handler returned %d, " | ||
1509 | "ignoring. Old userland tools?", r); | ||
1510 | } else { | ||
1511 | dev_info(DEV, "before-resync-source handler returned %d, " | ||
1512 | "dropping connection.\n", r); | ||
1513 | drbd_force_state(mdev, NS(conn, C_DISCONNECTING)); | ||
1514 | return; | ||
1515 | } | ||
1516 | } | ||
1515 | } | 1517 | } |
1516 | } | 1518 | } |
1517 | 1519 | ||
1518 | drbd_state_lock(mdev); | 1520 | if (current == mdev->tconn->worker.task) { |
1521 | /* The worker should not sleep waiting for drbd_state_lock(), | ||
1522 | that can take long */ | ||
1523 | if (test_and_set_bit(CLUSTER_ST_CHANGE, &mdev->flags)) { | ||
1524 | set_bit(B_RS_H_DONE, &mdev->flags); | ||
1525 | mdev->start_resync_timer.expires = jiffies + HZ/5; | ||
1526 | add_timer(&mdev->start_resync_timer); | ||
1527 | return; | ||
1528 | } | ||
1529 | } else { | ||
1530 | drbd_state_lock(mdev); | ||
1531 | } | ||
1532 | clear_bit(B_RS_H_DONE, &mdev->flags); | ||
1519 | 1533 | ||
1520 | if (!get_ldev_if_state(mdev, D_NEGOTIATING)) { | 1534 | if (!get_ldev_if_state(mdev, D_NEGOTIATING)) { |
1521 | drbd_state_unlock(mdev); | 1535 | drbd_state_unlock(mdev); |