From 5e75e2faa70b23750246a5e88a4f32de051e32a8 Mon Sep 17 00:00:00 2001 From: Vladimir Davydov <vdavydov.dev@gmail.com> Date: Tue, 13 Feb 2018 19:29:18 +0300 Subject: [PATCH] Make box.ctl.wait_rw check orphan state If an instance is 'orphan', it is read-only hence box.ctl.wait_rw() should block until the instance syncs, but currently it doesn't. Fix it. --- src/box/box.cc | 3 ++- test/replication/quorum.result | 37 ++++++++++++++++++++++++++++---- test/replication/quorum.test.lua | 15 +++++++++---- 3 files changed, 46 insertions(+), 9 deletions(-) diff --git a/src/box/box.cc b/src/box/box.cc index e724de3978..f055788d90 100644 --- a/src/box/box.cc +++ b/src/box/box.cc @@ -207,7 +207,7 @@ int box_wait_ro(bool ro, double timeout) { double deadline = ev_monotonic_now(loop()) + timeout; - while (is_ro != ro) { + while (box_is_ro() != ro) { if (fiber_cond_wait_deadline(&ro_cond, deadline) != 0) return -1; if (fiber_is_cancelled()) { @@ -225,6 +225,7 @@ box_clear_orphan(void) return; /* nothing to do */ is_orphan = false; + fiber_cond_broadcast(&ro_cond); /* Update the title to reflect the new status. */ title("running"); diff --git a/test/replication/quorum.result b/test/replication/quorum.result index f6e60aee93..5a29410303 100644 --- a/test/replication/quorum.result +++ b/test/replication/quorum.result @@ -32,6 +32,14 @@ box.info.status -- orphan --- - orphan ... +box.ctl.wait_rw(0.001) -- timeout +--- +- error: timed out +... +box.info.ro -- true +--- +- true +... box.space.test:replace{100} -- error --- - error: Can't modify data because this instance is in read-only mode. @@ -48,6 +56,14 @@ box.info.status -- orphan --- - orphan ... +box.ctl.wait_rw(0.001) -- timeout +--- +- error: timed out +... +box.info.ro -- true +--- +- true +... box.space.test:replace{100} -- error --- - error: Can't modify data because this instance is in read-only mode. @@ -55,11 +71,12 @@ box.space.test:replace{100} -- error box.cfg{replication_connect_quorum = 2} --- ... -fiber = require('fiber') +box.ctl.wait_rw() --- ... -while box.info.status == 'orphan' do fiber.sleep(0.001) end +box.info.ro -- false --- +- false ... box.info.status -- running --- @@ -70,6 +87,14 @@ box.info.status -- orphan --- - orphan ... +box.ctl.wait_rw(0.001) -- timeout +--- +- error: timed out +... +box.info.ro -- true +--- +- true +... box.space.test:replace{100} -- error --- - error: Can't modify data because this instance is in read-only mode. @@ -78,11 +103,12 @@ test_run:cmd('start server quorum1') --- - true ... -fiber = require('fiber') +box.ctl.wait_rw() --- ... -while box.info.status == 'orphan' do fiber.sleep(0.001) end +box.info.ro -- false --- +- false ... box.info.status -- running --- @@ -126,6 +152,9 @@ test_run:cmd('stop server quorum1') for i = 1, 10 do box.space.test:insert{i} end --- ... +fiber = require('fiber') +--- +... fiber.sleep(0.1) --- ... diff --git a/test/replication/quorum.test.lua b/test/replication/quorum.test.lua index 44c98b7b1c..192f136951 100644 --- a/test/replication/quorum.test.lua +++ b/test/replication/quorum.test.lua @@ -20,24 +20,30 @@ test_run:cmd('switch quorum2') test_run:cmd('restart server quorum2') box.info.status -- orphan +box.ctl.wait_rw(0.001) -- timeout +box.info.ro -- true box.space.test:replace{100} -- error box.cfg{replication={}} box.info.status -- running test_run:cmd('restart server quorum2') box.info.status -- orphan +box.ctl.wait_rw(0.001) -- timeout +box.info.ro -- true box.space.test:replace{100} -- error box.cfg{replication_connect_quorum = 2} -fiber = require('fiber') -while box.info.status == 'orphan' do fiber.sleep(0.001) end +box.ctl.wait_rw() +box.info.ro -- false box.info.status -- running test_run:cmd('restart server quorum2') box.info.status -- orphan +box.ctl.wait_rw(0.001) -- timeout +box.info.ro -- true box.space.test:replace{100} -- error test_run:cmd('start server quorum1') -fiber = require('fiber') -while box.info.status == 'orphan' do fiber.sleep(0.001) end +box.ctl.wait_rw() +box.info.ro -- false box.info.status -- running -- Check that the replica follows all masters. @@ -54,6 +60,7 @@ box.error.injection.set("ERRINJ_RELAY_TIMEOUT", 0.01) test_run:cmd('stop server quorum1') for i = 1, 10 do box.space.test:insert{i} end +fiber = require('fiber') fiber.sleep(0.1) test_run:cmd('start server quorum1') -- GitLab