diff options
author | Philipp Reisner <philipp.reisner@linbit.com> | 2011-03-29 08:01:02 -0400 |
---|---|---|
committer | Philipp Reisner <philipp.reisner@linbit.com> | 2012-11-08 10:45:05 -0500 |
commit | 8c7e16c39ffe77438906ff9d6196a80d171e9e32 (patch) | |
tree | 74ea98a800774a2ad58a01dea58b7b3499adda22 /drivers/block/drbd/drbd_state.c | |
parent | 5f082f98f5c8e7daee08505bcc4775aa82ad6d84 (diff) |
drbd: Calculate and provide ns_min to the w_after_conn_state_ch() work
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_state.c')
-rw-r--r-- | drivers/block/drbd/drbd_state.c | 42 |
1 files changed, 31 insertions, 11 deletions
diff --git a/drivers/block/drbd/drbd_state.c b/drivers/block/drbd/drbd_state.c index 8ec5574ad2ab..0ce665366d69 100644 --- a/drivers/block/drbd/drbd_state.c +++ b/drivers/block/drbd/drbd_state.c | |||
@@ -1358,6 +1358,7 @@ static void after_state_ch(struct drbd_conf *mdev, union drbd_state os, | |||
1358 | struct after_conn_state_chg_work { | 1358 | struct after_conn_state_chg_work { |
1359 | struct drbd_work w; | 1359 | struct drbd_work w; |
1360 | enum drbd_conns oc; | 1360 | enum drbd_conns oc; |
1361 | union drbd_state ns_min; | ||
1361 | union drbd_state ns_max; /* new, max state, over all mdevs */ | 1362 | union drbd_state ns_max; /* new, max state, over all mdevs */ |
1362 | enum chg_state_flags flags; | 1363 | enum chg_state_flags flags; |
1363 | }; | 1364 | }; |
@@ -1468,11 +1469,17 @@ conn_is_valid_transition(struct drbd_tconn *tconn, union drbd_state mask, union | |||
1468 | return rv; | 1469 | return rv; |
1469 | } | 1470 | } |
1470 | 1471 | ||
1471 | static union drbd_state | 1472 | void |
1472 | conn_set_state(struct drbd_tconn *tconn, union drbd_state mask, union drbd_state val, | 1473 | conn_set_state(struct drbd_tconn *tconn, union drbd_state mask, union drbd_state val, |
1473 | enum chg_state_flags flags) | 1474 | union drbd_state *pns_min, union drbd_state *pns_max, enum chg_state_flags flags) |
1474 | { | 1475 | { |
1475 | union drbd_state ns, os, ms = { }; | 1476 | union drbd_state ns, os, ns_max = { }; |
1477 | union drbd_state ns_min = { | ||
1478 | { .role = R_MASK, | ||
1479 | .peer = R_MASK, | ||
1480 | .disk = D_MASK, | ||
1481 | .pdsk = D_MASK | ||
1482 | } }; | ||
1476 | struct drbd_conf *mdev; | 1483 | struct drbd_conf *mdev; |
1477 | enum drbd_state_rv rv; | 1484 | enum drbd_state_rv rv; |
1478 | int vnr; | 1485 | int vnr; |
@@ -1492,13 +1499,26 @@ conn_set_state(struct drbd_tconn *tconn, union drbd_state mask, union drbd_state | |||
1492 | if (rv < SS_SUCCESS) | 1499 | if (rv < SS_SUCCESS) |
1493 | BUG(); | 1500 | BUG(); |
1494 | 1501 | ||
1495 | ms.role = max_role(mdev->state.role, ms.role); | 1502 | ns.i = mdev->state.i; |
1496 | ms.peer = max_role(mdev->state.peer, ms.peer); | 1503 | ns_max.role = max_role(ns.role, ns_max.role); |
1497 | ms.disk = max_t(enum drbd_disk_state, mdev->state.disk, ms.disk); | 1504 | ns_max.peer = max_role(ns.peer, ns_max.peer); |
1498 | ms.pdsk = max_t(enum drbd_disk_state, mdev->state.pdsk, ms.pdsk); | 1505 | ns_max.conn = max_t(enum drbd_conns, ns.conn, ns_max.conn); |
1506 | ns_max.disk = max_t(enum drbd_disk_state, ns.disk, ns_max.disk); | ||
1507 | ns_max.pdsk = max_t(enum drbd_disk_state, ns.pdsk, ns_max.pdsk); | ||
1508 | |||
1509 | ns_min.role = min_role(ns.role, ns_min.role); | ||
1510 | ns_min.peer = min_role(ns.peer, ns_min.peer); | ||
1511 | ns_min.conn = min_t(enum drbd_conns, ns.conn, ns_min.conn); | ||
1512 | ns_min.disk = min_t(enum drbd_disk_state, ns.disk, ns_min.disk); | ||
1513 | ns_min.pdsk = min_t(enum drbd_disk_state, ns.pdsk, ns_min.pdsk); | ||
1499 | } | 1514 | } |
1500 | 1515 | ||
1501 | return ms; | 1516 | ns_min.susp = ns_max.susp = tconn->susp; |
1517 | ns_min.susp_nod = ns_max.susp_nod = tconn->susp_nod; | ||
1518 | ns_min.susp_fen = ns_max.susp_fen = tconn->susp_fen; | ||
1519 | |||
1520 | *pns_min = ns_min; | ||
1521 | *pns_max = ns_max; | ||
1502 | } | 1522 | } |
1503 | 1523 | ||
1504 | static enum drbd_state_rv | 1524 | static enum drbd_state_rv |
@@ -1558,7 +1578,7 @@ _conn_request_state(struct drbd_tconn *tconn, union drbd_state mask, union drbd_ | |||
1558 | enum drbd_state_rv rv = SS_SUCCESS; | 1578 | enum drbd_state_rv rv = SS_SUCCESS; |
1559 | struct after_conn_state_chg_work *acscw; | 1579 | struct after_conn_state_chg_work *acscw; |
1560 | enum drbd_conns oc = tconn->cstate; | 1580 | enum drbd_conns oc = tconn->cstate; |
1561 | union drbd_state ns_max, os; | 1581 | union drbd_state ns_max, ns_min, os; |
1562 | 1582 | ||
1563 | rv = is_valid_conn_transition(oc, val.conn); | 1583 | rv = is_valid_conn_transition(oc, val.conn); |
1564 | if (rv < SS_SUCCESS) | 1584 | if (rv < SS_SUCCESS) |
@@ -1576,13 +1596,13 @@ _conn_request_state(struct drbd_tconn *tconn, union drbd_state mask, union drbd_ | |||
1576 | } | 1596 | } |
1577 | 1597 | ||
1578 | conn_old_common_state(tconn, &os, &flags); | 1598 | conn_old_common_state(tconn, &os, &flags); |
1579 | ns_max = conn_set_state(tconn, mask, val, flags); | 1599 | conn_set_state(tconn, mask, val, &ns_min, &ns_max, flags); |
1580 | ns_max.conn = val.conn; | ||
1581 | conn_pr_state_change(tconn, os, ns_max, flags); | 1600 | conn_pr_state_change(tconn, os, ns_max, flags); |
1582 | 1601 | ||
1583 | acscw = kmalloc(sizeof(*acscw), GFP_ATOMIC); | 1602 | acscw = kmalloc(sizeof(*acscw), GFP_ATOMIC); |
1584 | if (acscw) { | 1603 | if (acscw) { |
1585 | acscw->oc = os.conn; | 1604 | acscw->oc = os.conn; |
1605 | acscw->ns_min = ns_min; | ||
1586 | acscw->ns_max = ns_max; | 1606 | acscw->ns_max = ns_max; |
1587 | acscw->flags = flags; | 1607 | acscw->flags = flags; |
1588 | acscw->w.cb = w_after_conn_state_ch; | 1608 | acscw->w.cb = w_after_conn_state_ch; |