You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@subversion.apache.org by rh...@apache.org on 2015/03/05 21:34:36 UTC

svn commit: r1664476 - in /subversion/trunk/subversion/libsvn_wc: wc-queries.sql wc.h wc_db_wcroot.c

Author: rhuijben
Date: Thu Mar  5 20:34:35 2015
New Revision: 1664476

URL: http://svn.apache.org/r1664476
Log:
Remove a db transaction on opening wc.db, and at the same time
also verify if the sqlite_stat1 table exists on opening a db
from svn_wc__db_wcroot_parse_local_abspath().

If the table exists we try to add the table, but ignore
errors to avoid problems when the database is read only
(This last part will need verification on other platforms)

* subversion/libsvn_wc/wc-queries.sql
  (STMT_HAVE_STAT1_TABLE): New statement.

* subversion/libsvn_wc/wc.h
  (SVN_WC__ENSURE_STAT1_TABLE): New define.

* subversion/libsvn_wc/wc_db_wcroot.c
  (svn_wc__db_pdh_create_wcroot): Only read format from db when requested
    by caller, instead of always when we open the db.
  (verify_stats_table,
   fetch_db_info): New function.
  (svn_wc__db_wcroot_parse_local_abspath): Update caller.

Modified:
    subversion/trunk/subversion/libsvn_wc/wc-queries.sql
    subversion/trunk/subversion/libsvn_wc/wc.h
    subversion/trunk/subversion/libsvn_wc/wc_db_wcroot.c

Modified: subversion/trunk/subversion/libsvn_wc/wc-queries.sql
URL: http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_wc/wc-queries.sql?rev=1664476&r1=1664475&r2=1664476&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_wc/wc-queries.sql (original)
+++ subversion/trunk/subversion/libsvn_wc/wc-queries.sql Thu Mar  5 20:34:35 2015
@@ -1781,6 +1781,10 @@ WHERE wc_id = ?1
   AND op_depth = 0
   AND (inherited_props not null)
 
+-- STMT_HAVE_STAT1_TABLE
+SELECT 1 FROM sqlite_stat1
+LIMIT 1
+
 /* ------------------------------------------------------------------------- */
 
 /* Grab all the statements related to the schema.  */

Modified: subversion/trunk/subversion/libsvn_wc/wc.h
URL: http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_wc/wc.h?rev=1664476&r1=1664475&r2=1664476&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_wc/wc.h (original)
+++ subversion/trunk/subversion/libsvn_wc/wc.h Thu Mar  5 20:34:35 2015
@@ -190,6 +190,10 @@ extern "C" {
 /* A version < this has no work queue (see workqueue.h).  */
 #define SVN_WC__HAS_WORK_QUEUE 13
 
+/* While we still have this DB version we should verify if there is
+   sqlite_stat1 table on opening */
+#define SVN_WC__ENSURE_STAT1_TABLE 31
+
 /* Return a string indicating the released version (or versions) of
  * Subversion that used WC format number WC_FORMAT, or some other
  * suitable string if no released version used WC_FORMAT.

Modified: subversion/trunk/subversion/libsvn_wc/wc_db_wcroot.c
URL: http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_wc/wc_db_wcroot.c?rev=1664476&r1=1664475&r2=1664476&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_wc/wc_db_wcroot.c (original)
+++ subversion/trunk/subversion/libsvn_wc/wc_db_wcroot.c Thu Mar  5 20:34:35 2015
@@ -304,7 +304,7 @@ svn_wc__db_pdh_create_wcroot(svn_wc__db_
                              apr_pool_t *result_pool,
                              apr_pool_t *scratch_pool)
 {
-  if (sdb != NULL)
+  if (sdb && format == FORMAT_FROM_SDB)
     SVN_ERR(svn_sqlite__read_schema_version(&format, sdb, scratch_pool));
 
   /* If we construct a wcroot, then we better have a format.  */
@@ -456,6 +456,56 @@ read_link_target(const char **link_targe
   return SVN_NO_ERROR;
 }
 
+/* Verify if the sqlite_stat1 table exists and if not tries to add
+   this table (but ignores errors on adding the schema) */
+static svn_error_t *
+verify_stats_table(svn_sqlite__db_t *sdb,
+                   int format,
+                   apr_pool_t *scratch_pool)
+{
+  svn_sqlite__stmt_t *stmt;
+  svn_boolean_t have_row;
+
+  if (format != SVN_WC__ENSURE_STAT1_TABLE)
+    return SVN_NO_ERROR;
+
+  SVN_ERR(svn_sqlite__get_statement(&stmt, sdb,
+                                    STMT_HAVE_STAT1_TABLE));
+  SVN_ERR(svn_sqlite__step(&have_row, stmt));
+  SVN_ERR(svn_sqlite__reset(stmt));
+
+  if (!have_row)
+    {
+      svn_error_clear(
+          svn_wc__db_install_schema_statistics(sdb, scratch_pool));
+    }
+
+  return SVN_NO_ERROR;
+}
+
+/* Sqlite transaction helper for opening the db in
+   svn_wc__db_wcroot_parse_local_abspath() to avoid multiple
+   db operations that each obtain and release a lock */
+static svn_error_t *
+fetch_sdb_info(apr_int64_t *wc_id,
+               int *format,
+               svn_sqlite__db_t *sdb,
+               apr_pool_t *scratch_pool)
+{
+  *wc_id = -1;
+  *format = -1;
+
+  SVN_SQLITE__WITH_LOCK4(
+        svn_wc__db_util_fetch_wc_id(wc_id, sdb, scratch_pool),
+        svn_sqlite__read_schema_version(format, sdb, scratch_pool),
+        verify_stats_table(sdb, *format, scratch_pool),
+        SVN_NO_ERROR,
+        sdb);
+
+  return SVN_NO_ERROR;
+}
+
+
 svn_error_t *
 svn_wc__db_wcroot_parse_local_abspath(svn_wc__db_wcroot_t **wcroot,
                                       const char **local_relpath,
@@ -696,9 +746,10 @@ try_symlink_as_dir:
       /* We finally found the database. Construct a wcroot_t for it.  */
 
       apr_int64_t wc_id;
+      int format;
       svn_error_t *err;
 
-      err = svn_wc__db_util_fetch_wc_id(&wc_id, sdb, scratch_pool);
+      err = fetch_sdb_info(&wc_id, &format, sdb, scratch_pool);
       if (err)
         {
           if (err->apr_err == SVN_ERR_WC_CORRUPT)
@@ -717,7 +768,7 @@ try_symlink_as_dir:
                                         symlink_wcroot_abspath
                                           ? symlink_wcroot_abspath
                                           : local_abspath),
-                            sdb, wc_id, FORMAT_FROM_SDB,
+                            sdb, wc_id, format,
                             db->verify_format,
                             db->state_pool, scratch_pool);
       if (err && (err->apr_err == SVN_ERR_WC_UNSUPPORTED_FORMAT ||