From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from smtp50.i.mail.ru (smtp50.i.mail.ru [94.100.177.110]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by dev.tarantool.org (Postfix) with ESMTPS id 42D754696C5 for ; Fri, 14 Feb 2020 00:53:13 +0300 (MSK) From: sergepetrenko Date: Fri, 14 Feb 2020 00:52:58 +0300 Message-Id: In-Reply-To: References: MIME-Version: 1.0 Content-Transfer-Encoding: 8bit Subject: [Tarantool-patches] [PATCH v2 2/4] replication: check for rows to skip in applier correctly List-Id: Tarantool development patches List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: alexander.turenko@tarantool.org, v.shpilevoy@tarantool.org, kostja.osipov@gmail.com Cc: tarantool-patches@dev.tarantool.org From: Serge Petrenko Remove applier vclock initialization from replication_init(), where it is zeroed-out, and place it in the end of box_cfg_xc(), where replicaset vclock already has a meaningful value. Do not apply rows originating form the current instance if replication sync has ended. Closes #4739 --- src/box/applier.cc | 17 +++++++++++++++-- src/box/box.cc | 6 ++++++ src/box/replication.cc | 1 - 3 files changed, 21 insertions(+), 3 deletions(-) diff --git a/src/box/applier.cc b/src/box/applier.cc index ae3d281a5..e931e1595 100644 --- a/src/box/applier.cc +++ b/src/box/applier.cc @@ -731,8 +731,21 @@ applier_apply_tx(struct stailq *rows) struct latch *latch = (replica ? &replica->order_latch : &replicaset.applier.order_latch); latch_lock(latch); - if (vclock_get(&replicaset.applier.vclock, - first_row->replica_id) >= first_row->lsn) { + /* + * Skip remote rows either if one of the appliers has + * sent them to write or if the rows originate from the + * local instance and we've already synced with the + * replica. The latter is important because relay gets + * notified about WAL write before tx does, so it is + * possible that a remote instance receives our rows + * via replication before we update replicaset vclock and + * even sends these rows back to us. An attemt to apply + * such rows will lead to having entries with duplicate + * LSNs in WAL. + */ + if (vclock_get(&replicaset.applier.vclock, first_row->replica_id) >= + first_row->lsn || (first_row->replica_id == instance_id && + !box_is_orphan())) { latch_unlock(latch); return 0; } diff --git a/src/box/box.cc b/src/box/box.cc index 0290578b2..952d60ad1 100644 --- a/src/box/box.cc +++ b/src/box/box.cc @@ -2425,6 +2425,12 @@ box_cfg_xc(void) rmean_cleanup(rmean_box); + /* + * Local recovery is over so it's fine to update applier + * vclock now. + */ + vclock_copy(&replicaset.applier.vclock, &replicaset.vclock); + /* Follow replica */ replicaset_follow(); diff --git a/src/box/replication.cc b/src/box/replication.cc index e7bfa22ab..7b04573a4 100644 --- a/src/box/replication.cc +++ b/src/box/replication.cc @@ -93,7 +93,6 @@ replication_init(void) latch_create(&replicaset.applier.order_latch); vclock_create(&replicaset.applier.vclock); - vclock_copy(&replicaset.applier.vclock, &replicaset.vclock); rlist_create(&replicaset.applier.on_rollback); rlist_create(&replicaset.applier.on_commit); -- 2.20.1 (Apple Git-117)