diff options
author | Jeff Darcy <jdarcy@redhat.com> | 2014-03-31 18:37:38 +0000 |
---|---|---|
committer | Jeff Darcy <jdarcy@redhat.com> | 2014-04-22 15:20:46 +0000 |
commit | 46d333783a968ab39e0beade9c7a1eec8035f8b1 (patch) | |
tree | faf1db8cb7ea7fefb0a4d8374440fa095116fef1 /xlators/cluster/nsr-server/src/all-templates.c | |
parent | acd2292f085b15c2c5c28169d11f20dca90f5ec9 (diff) |
nsr: add quorum enforcement
Change-Id: I0241f8c1ac97c80ae438e3d9f1ac492d63da9347
Signed-off-by: Jeff Darcy <jdarcy@redhat.com>
Diffstat (limited to 'xlators/cluster/nsr-server/src/all-templates.c')
-rw-r--r-- | xlators/cluster/nsr-server/src/all-templates.c | 25 |
1 files changed, 25 insertions, 0 deletions
diff --git a/xlators/cluster/nsr-server/src/all-templates.c b/xlators/cluster/nsr-server/src/all-templates.c index 2f0509a6c..fa29de7b2 100644 --- a/xlators/cluster/nsr-server/src/all-templates.c +++ b/xlators/cluster/nsr-server/src/all-templates.c @@ -59,6 +59,31 @@ nsr_$NAME$ (call_frame_t *frame, xlator_t *this, int from_leader; int from_recon; uint32_t ti = 0; + double must_be_up; + double are_up; + + /* + * Our first goal here is to avoid "split brain surprise" for users who + * specify exactly 50% with two- or three-way replication. That means + * either a more-than check against half the total replicas or an + * at-least check against half of our peers (one less). Of the two, + * only an at-least check supports the intuitive use of 100% to mean + * all replicas must be present, because "more than 100%" will never + * succeed regardless of which count we use. This leaves us with a + * slightly non-traditional definition of quorum ("at least X% of peers + * not including ourselves") but one that's useful enough to be worth + * it. + * + * Note that n_children and up_children *do* include the local + * subvolume, so we need to subtract one in each case. + */ + must_be_up = ((double)(priv->n_children - 1)) * priv->quorum_pct; + are_up = ((double)(priv->up_children - 1)) * 100.0; + if (are_up < must_be_up) { + /* Emulate the AFR client-side-quorum behavior. */ + op_errno = EROFS; + goto err; + } local = mem_get0(this->local_pool); if (!local) { |