[tarantool-patches] [PATCH v2 7/9] sql: refactor sqlite3_reset routine

Kirill Shcherbatov kshcherbatov at tarantool.org
Wed Jan 30 11:59:14 MSK 2019


Refactored sqlite3_reset as sql_stmt_reset routine, removed
signature definition to sqliteInt.h to be visible outside of
vdbeapi.c module. We need this routine in future to reset
reusable ck constraint VDBE state before new run.

Needed for #3691
---
 src/box/sql/sqliteInt.h        | 13 ++++++++
 src/box/sql/vdbe.c             |  2 +-
 src/box/sql/vdbeapi.c          | 58 +++++++++++-----------------------
 test/sql-tap/subquery.test.lua |  2 +-
 4 files changed, 33 insertions(+), 42 deletions(-)

diff --git a/src/box/sql/sqliteInt.h b/src/box/sql/sqliteInt.h
index 68640c728..1f18d98e9 100644
--- a/src/box/sql/sqliteInt.h
+++ b/src/box/sql/sqliteInt.h
@@ -595,6 +595,19 @@ sqlite3_column_value(sqlite3_stmt *,
 int
 sqlite3_finalize(sqlite3_stmt * pStmt);
 
+/*
+ * Terminate the current execution of an SQL statement and reset
+ * it back to its starting state so that it can be reused. A
+ * success code from the prior execution is returned.
+ *
+ * This routine sets the error code and string returned by
+ * sqlite3_errcode(), sqlite3_errmsg() and sqlite3_errmsg16().
+ * @param stmt VDBE program, may be NULL.
+ * @retval SQLITE_OK on success, sql_ret_code error code.
+ */
+int
+sql_stmt_reset(struct sqlite3_stmt *stmt);
+
 int
 sqlite3_exec(sqlite3 *,	/* An open database */
 	     const char *sql,	/* SQL to be evaluated */
diff --git a/src/box/sql/vdbe.c b/src/box/sql/vdbe.c
index 4b2b45766..8d4d9ecf9 100644
--- a/src/box/sql/vdbe.c
+++ b/src/box/sql/vdbe.c
@@ -992,7 +992,7 @@ case OP_HaltIfNull: {      /* in3 */
  * automatically.
  *
  * P1 is the result code returned by sqlite3_exec(),
- * sqlite3_reset(), or sqlite3_finalize().  For a normal halt,
+ * sql_stmt_reset(), or sqlite3_finalize().  For a normal halt,
  * this should be SQLITE_OK (0).
  * For errors, it can be some other value.  If P1!=0 then P2 will
  * determine whether or not to rollback the current transaction.
diff --git a/src/box/sql/vdbeapi.c b/src/box/sql/vdbeapi.c
index 9e57af051..7ec9c4616 100644
--- a/src/box/sql/vdbeapi.c
+++ b/src/box/sql/vdbeapi.c
@@ -132,29 +132,18 @@ sqlite3_finalize(sqlite3_stmt * pStmt)
 	return rc;
 }
 
-/*
- * Terminate the current execution of an SQL statement and reset it
- * back to its starting state so that it can be reused. A success code from
- * the prior execution is returned.
- *
- * This routine sets the error code and string returned by
- * sqlite3_errcode(), sqlite3_errmsg() and sqlite3_errmsg16().
- */
 int
-sqlite3_reset(sqlite3_stmt * pStmt)
-{
-	int rc;
-	if (pStmt == 0) {
-		rc = SQLITE_OK;
-	} else {
-		Vdbe *v = (Vdbe *) pStmt;
-		sqlite3 *db = v->db;
-		checkProfileCallback(db, v);
-		rc = sqlite3VdbeReset(v);
-		sqlite3VdbeRewind(v);
-		assert((rc & (db->errMask)) == rc);
-		rc = sqlite3ApiExit(db, rc);
-	}
+sql_stmt_reset(struct sqlite3_stmt *stmt)
+{
+	if (stmt == NULL)
+		return SQLITE_OK;
+	struct Vdbe *v = (struct Vdbe *)stmt;
+	struct sqlite3 *db = v->db;
+	checkProfileCallback(db, v);
+	int rc = sqlite3VdbeReset(v);
+	sqlite3VdbeRewind(v);
+	assert((rc & (db->errMask)) == rc);
+	rc = sqlite3ApiExit(db, rc);
 	return rc;
 }
 
@@ -509,30 +498,19 @@ sqlite3Step(Vdbe * p)
 
 	assert(p);
 	if (p->magic != VDBE_MAGIC_RUN) {
-		/* We used to require that sqlite3_reset() be called before retrying
-		 * sqlite3_step() after any error or after SQLITE_DONE.  But beginning
-		 * with version 3.7.0, we changed this so that sqlite3_reset() would
-		 * be called automatically instead of throwing the SQLITE_MISUSE error.
-		 * This "automatic-reset" change is not technically an incompatibility,
-		 * since any application that receives an SQLITE_MISUSE is broken by
-		 * definition.
-		 *
-		 * Nevertheless, some published applications that were originally written
-		 * for version 3.6.23 or earlier do in fact depend on SQLITE_MISUSE
-		 * returns, and those were broken by the automatic-reset change.  As a
-		 * a work-around, the SQLITE_OMIT_AUTORESET compile-time restores the
-		 * legacy behavior of returning SQLITE_MISUSE for cases where the
-		 * previous sqlite3_step() returned something other than a SQLITE_LOCKED
-		 * or SQLITE_BUSY error.
+		/*
+		 * The sql_stmt_reset() routine would be called
+		 * automatically instead of throwing the
+		 * SQLITE_MISUSE error.
 		 */
 #ifdef SQLITE_OMIT_AUTORESET
 		if ((rc = p->rc & 0xff) == SQLITE_BUSY || rc == SQLITE_LOCKED) {
-			sqlite3_reset((sqlite3_stmt *) p);
+			sql_stmt_reset((sqlite3_stmt *) p);
 		} else {
 			return SQLITE_MISUSE_BKPT;
 		}
 #else
-		sqlite3_reset((sqlite3_stmt *) p);
+		sql_stmt_reset((sqlite3_stmt *) p);
 #endif
 	}
 
@@ -632,7 +610,7 @@ sqlite3_step(sqlite3_stmt * pStmt)
 		rc2 = rc = sqlite3Reprepare(v);
 		if (rc != SQLITE_OK)
 			break;
-		sqlite3_reset(pStmt);
+		sql_stmt_reset(pStmt);
 		if (savedPc >= 0)
 			v->doingRerun = 1;
 		assert(v->expired == 0);
diff --git a/test/sql-tap/subquery.test.lua b/test/sql-tap/subquery.test.lua
index fb9a737d1..38988dbdc 100755
--- a/test/sql-tap/subquery.test.lua
+++ b/test/sql-tap/subquery.test.lua
@@ -651,7 +651,7 @@ test:do_execsql_test(
 --------------------------------------------------------------------
 -- These tests - subquery-4.* - use the TCL statement cache to try 
 -- and expose bugs to do with re-using statements that have been 
--- passed to sqlite3_reset().
+-- passed to sql_stmt_reset().
 --
 -- One problem was that VDBE memory cells were not being initialized
 -- to NULL on the second and subsequent executions.
-- 
2.19.2





More information about the Tarantool-patches mailing list