[PATCH] vinyl: fix index.stat.txw.rows accounting on rollback to savepoint

Vladimir Davydov vdavydov.dev at gmail.com
Tue Jul 30 19:06:19 MSK 2019


We must un-account index.stat.txw.rows not only when a whole transaction
is rolled back, but also when we undo statements using a savepoint.
---
https://github.com/tarantool/tarantool/commits/dv/vy-fix-tx-stmt-accounting

 src/box/vy_tx.c          | 10 +++-----
 test/vinyl/stat.result   | 49 ++++++++++++++++++++++++++++++++++++++++
 test/vinyl/stat.test.lua | 18 +++++++++++++++
 3 files changed, 70 insertions(+), 7 deletions(-)

diff --git a/src/box/vy_tx.c b/src/box/vy_tx.c
index ca8c57ad..d0e92068 100644
--- a/src/box/vy_tx.c
+++ b/src/box/vy_tx.c
@@ -231,6 +231,7 @@ txv_new(struct vy_tx *tx, struct vy_lsm *lsm, struct vy_entry entry)
 	v->is_overwritten = false;
 	v->overwritten = NULL;
 	xm->write_set_size += tuple_size(entry.stmt);
+	vy_stmt_counter_acct_tuple(&lsm->stat.txw.count, entry.stmt);
 	return v;
 }
 
@@ -239,6 +240,7 @@ txv_delete(struct txv *v)
 {
 	struct tx_manager *xm = v->tx->xm;
 	xm->write_set_size -= tuple_size(v->entry.stmt);
+	vy_stmt_counter_unacct_tuple(&v->lsm->stat.txw.count, v->entry.stmt);
 	tuple_unref(v->entry.stmt);
 	vy_lsm_unref(v->lsm);
 	mempool_free(&xm->txv_mempool, v);
@@ -344,11 +346,8 @@ vy_tx_destroy(struct vy_tx *tx)
 	tx_manager_destroy_read_view(tx->xm, tx->read_view);
 
 	struct txv *v, *tmp;
-	stailq_foreach_entry_safe(v, tmp, &tx->log, next_in_log) {
-		vy_stmt_counter_unacct_tuple(&v->lsm->stat.txw.count,
-					     v->entry.stmt);
+	stailq_foreach_entry_safe(v, tmp, &tx->log, next_in_log)
 		txv_delete(v);
-	}
 
 	vy_tx_read_set_iter(&tx->read_set, NULL, vy_tx_read_set_free_cb, NULL);
 	rlist_del_entry(tx, in_writers);
@@ -653,8 +652,6 @@ vy_tx_handle_deferred_delete(struct vy_tx *tx, struct txv *v)
 			}
 			stailq_insert_entry(&tx->log, delete_txv, v,
 					    next_in_log);
-			vy_stmt_counter_acct_tuple(&lsm->stat.txw.count,
-						   entry.stmt);
 		}
 		if (rc != 0)
 			break;
@@ -1127,7 +1124,6 @@ vy_tx_set_entry(struct vy_tx *tx, struct vy_lsm *lsm, struct vy_entry entry)
 	write_set_insert(&tx->write_set, v);
 	tx->write_set_version++;
 	tx->write_size += tuple_size(entry.stmt);
-	vy_stmt_counter_acct_tuple(&lsm->stat.txw.count, entry.stmt);
 	stailq_add_tail_entry(&tx->log, v, next_in_log);
 	return 0;
 }
diff --git a/test/vinyl/stat.result b/test/vinyl/stat.result
index e2991d53..d35def13 100644
--- a/test/vinyl/stat.result
+++ b/test/vinyl/stat.result
@@ -1875,6 +1875,55 @@ i:stat().dumps_per_compaction -- 1
 s:drop()
 ---
 ...
+--
+-- Check that index.stat.txw.rows is unaccounted on rollback
+-- to a savepoint.
+--
+s = box.schema.space.create('test', {engine = 'vinyl'})
+---
+...
+i = s:create_index('pk')
+---
+...
+box.begin()
+---
+...
+s:insert{1}
+---
+- [1]
+...
+i:stat().txw.rows -- 1
+---
+- 1
+...
+sv = box.savepoint()
+---
+...
+s:insert{2}
+---
+- [2]
+...
+i:stat().txw.rows -- 2
+---
+- 2
+...
+box.rollback_to_savepoint(sv)
+---
+...
+i:stat().txw.rows -- 1
+---
+- 1
+...
+box.commit()
+---
+...
+i:stat().txw.rows -- 0
+---
+- 0
+...
+s:drop()
+---
+...
 test_run:cmd('switch default')
 ---
 - true
diff --git a/test/vinyl/stat.test.lua b/test/vinyl/stat.test.lua
index 4c751aad..a8657ccf 100644
--- a/test/vinyl/stat.test.lua
+++ b/test/vinyl/stat.test.lua
@@ -591,6 +591,24 @@ i:stat().dumps_per_compaction -- 1
 
 s:drop()
 
+--
+-- Check that index.stat.txw.rows is unaccounted on rollback
+-- to a savepoint.
+--
+s = box.schema.space.create('test', {engine = 'vinyl'})
+i = s:create_index('pk')
+box.begin()
+s:insert{1}
+i:stat().txw.rows -- 1
+sv = box.savepoint()
+s:insert{2}
+i:stat().txw.rows -- 2
+box.rollback_to_savepoint(sv)
+i:stat().txw.rows -- 1
+box.commit()
+i:stat().txw.rows -- 0
+s:drop()
+
 test_run:cmd('switch default')
 test_run:cmd('stop server test')
 test_run:cmd('cleanup server test')
-- 
2.20.1




More information about the Tarantool-patches mailing list