Author: rhuijben
Date: Mon Nov 26 18:40:17 2012
New Revision: 1413774
URL: http://svn.apache.org/viewvc?rev=1413774&view=rev
Log:
Make svn_wc__db_get_children_with_cached_iprops() properly check the target
itself when handling a recursive request. Also return the repository relative
path instead of a dummy value to allow further optimizations in callers.
* subversion/include/private/svn_wc_private.h
(svn_wc__get_cached_iprop_children): Update documentation.
* subversion/libsvn_wc/wc-queries.sql
(STMT_SELECT_INODES): Rename to ...
(STMT_SELECT_IPROPS_NODE): ... this.
(STMT_SELECT_INODES_RECURSIVE): Rename to ...
(STMT_SELECT_IPROPS_RECURSIVE): ... this and update comment.
(STMT_SELECT_IPROPS_CHILDREN): New query.
* subversion/libsvn_wc/wc_db.c
(get_children_with_cached_baton_t): New struct.
(get_children_with_cached_iprops): Implement svn_wc__db_txn_callback_t.
Fix queries and optimize the code path for depth files and immediates.
(svn_wc__db_get_children_with_cached_iprops): Update caller.
* subversion/libsvn_wc/wc_db.h
(svn_wc__db_get_children_with_cached_iprops): Update documentation.
Modified:
subversion/trunk/subversion/include/private/svn_wc_private.h
subversion/trunk/subversion/libsvn_wc/wc-queries.sql
subversion/trunk/subversion/libsvn_wc/wc_db.c
subversion/trunk/subversion/libsvn_wc/wc_db.h
Modified: subversion/trunk/subversion/include/private/svn_wc_private.h
URL:
http://svn.apache.org/viewvc/subversion/trunk/subversion/include/private/svn_wc_private.h?rev=1413774&r1=1413773&r2=1413774&view=diff
==============================================================================
--- subversion/trunk/subversion/include/private/svn_wc_private.h (original)
+++ subversion/trunk/subversion/include/private/svn_wc_private.h Mon Nov 26
18:40:17 2012
@@ -887,9 +887,11 @@ svn_wc__prop_retrieve_recursive(apr_hash
/**
* Set @a *iprops_paths to a hash mapping const char * absolute working
- * copy paths to the same for each path in the working copy at or below
- * @a local_abspath, limited by @a depth, that has cached inherited
- * properties for the base node of the path. Allocate @a *iprop_paths
+ * copy paths to the nodes repository root relative path for each path
+ * in the working copy at or below @a local_abspath, limited by @a depth,
+ * that has cached inherited properties for the base node of the path.
+ *
+ * Allocate @a *iprop_paths
* in @a result_pool. Use @a scratch_pool for temporary allocations.
*/
svn_error_t *
Modified: subversion/trunk/subversion/libsvn_wc/wc-queries.sql
URL:
http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_wc/wc-queries.sql?rev=1413774&r1=1413773&r2=1413774&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_wc/wc-queries.sql (original)
+++ subversion/trunk/subversion/libsvn_wc/wc-queries.sql Mon Nov 26 18:40:17
2012
@@ -1444,22 +1444,29 @@ SET inherited_props = ?3
WHERE (wc_id = ?1 AND local_relpath = ?2 AND op_depth = 0)
/* Select a single path if its base node has cached inherited properties. */
--- STMT_SELECT_INODES
-SELECT local_relpath FROM nodes
+-- STMT_SELECT_IPROPS_NODE
+SELECT local_relpath, repos_path FROM nodes
WHERE wc_id = ?1
AND local_relpath = ?2
AND op_depth = 0
AND (inherited_props not null)
-/* Select all paths whose base nodes at or below a given path, which
+/* Select all paths whose base nodes are below a given path, which
have cached inherited properties. */
--- STMT_SELECT_INODES_RECURSIVE
-SELECT local_relpath FROM nodes
+-- STMT_SELECT_IPROPS_RECURSIVE
+SELECT local_relpath, repos_path FROM nodes
WHERE wc_id = ?1
AND IS_STRICT_DESCENDANT_OF(local_relpath, ?2)
AND op_depth = 0
AND (inherited_props not null)
+-- STMT_SELECT_IPROPS_CHILDREN
+SELECT local_relpath, repos_path FROM nodes
+WHERE wc_id = ?1
+ AND parent_relpath = ?2
+ AND op_depth = 0
+ AND (inherited_props not null)
+
/* ------------------------------------------------------------------------- */
/* Grab all the statements related to the schema. */
Modified: subversion/trunk/subversion/libsvn_wc/wc_db.c
URL:
http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_wc/wc_db.c?rev=1413774&r1=1413773&r2=1413774&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_wc/wc_db.c (original)
+++ subversion/trunk/subversion/libsvn_wc/wc_db.c Mon Nov 26 18:40:17 2012
@@ -9060,37 +9060,60 @@ svn_wc__db_read_cached_iprops(apr_array_
return SVN_NO_ERROR;
}
-/* Recursive body of svn_wc__db_get_children_with_cached_iprops. */
+/* Baton for get_children_with_cached_iprops */
+struct get_children_with_cached_baton_t
+{
+ svn_depth_t depth;
+ apr_hash_t *iprop_paths;
+ apr_pool_t *result_pool;
+};
+
+/* Implements svn_wc__db_txn_callback_t for
+ svn_wc__db_get_children_with_cached_iprops. */
static svn_error_t *
-get_children_with_cached_iprops(apr_hash_t *iprop_paths,
- svn_depth_t depth,
- const char *local_abspath,
- svn_wc__db_t *db,
- apr_pool_t *result_pool,
+get_children_with_cached_iprops(void *baton,
+ svn_wc__db_wcroot_t *wcroot,
+ const char *local_relpath,
apr_pool_t *scratch_pool)
{
- svn_wc__db_wcroot_t *wcroot;
- const char *local_relpath;
+ struct get_children_with_cached_baton_t *cwcb = baton;
svn_sqlite__stmt_t *stmt;
svn_boolean_t have_row;
+ apr_hash_t *iprop_paths = cwcb->iprop_paths;
+ apr_pool_t *result_pool = cwcb->result_pool;
- SVN_ERR_ASSERT(svn_dirent_is_absolute(local_abspath));
+ /* First check if LOCAL_RELPATH itself has iprops */
+ SVN_ERR(svn_sqlite__get_statement(&stmt, wcroot->sdb,
+ STMT_SELECT_IPROPS_NODE));
+ SVN_ERR(svn_sqlite__bindf(stmt, "is", wcroot->wc_id, local_relpath));
+ SVN_ERR(svn_sqlite__step(&have_row, stmt));
- SVN_ERR(svn_wc__db_wcroot_parse_local_abspath(&wcroot, &local_relpath, db,
- local_abspath, scratch_pool,
- scratch_pool));
- VERIFY_USABLE_WCROOT(wcroot);
- if (depth == svn_depth_empty
- || depth == svn_depth_files
- || depth == svn_depth_immediates)
+ if (have_row)
+ {
+ const char *relpath_with_cache = svn_sqlite__column_text(stmt, 0,
+ NULL);
+ const char *abspath_with_cache = svn_dirent_join(wcroot->abspath,
+ relpath_with_cache,
+ result_pool);
+ apr_hash_set(iprop_paths, abspath_with_cache, APR_HASH_KEY_STRING,
+ svn_sqlite__column_text(stmt, 1, result_pool));
+ }
+ SVN_ERR(svn_sqlite__reset(stmt));
+
+ if (cwcb->depth == svn_depth_empty)
+ return SVN_NO_ERROR;
+
+ /* Now fetch information for children or all descendants */
+ if (cwcb->depth == svn_depth_files
+ || cwcb->depth == svn_depth_immediates)
{
SVN_ERR(svn_sqlite__get_statement(&stmt, wcroot->sdb,
- STMT_SELECT_INODES));
+ STMT_SELECT_IPROPS_CHILDREN));
}
else /* Default to svn_depth_infinity. */
{
SVN_ERR(svn_sqlite__get_statement(&stmt, wcroot->sdb,
- STMT_SELECT_INODES_RECURSIVE));
+ STMT_SELECT_IPROPS_RECURSIVE));
}
SVN_ERR(svn_sqlite__bindf(stmt, "is", wcroot->wc_id, local_relpath));
@@ -9104,46 +9127,50 @@ get_children_with_cached_iprops(apr_hash
relpath_with_cache,
result_pool);
apr_hash_set(iprop_paths, abspath_with_cache, APR_HASH_KEY_STRING,
- abspath_with_cache);
+ svn_sqlite__column_text(stmt, 1, result_pool));
SVN_ERR(svn_sqlite__step(&have_row, stmt));
}
SVN_ERR(svn_sqlite__reset(stmt));
- if (depth == svn_depth_files || depth == svn_depth_immediates)
+ /* For depth files we should filter non files */
+ if (cwcb->depth == svn_depth_files)
{
- const apr_array_header_t *rel_children;
- int i;
+ apr_hash_index_t *hi;
apr_pool_t *iterpool = svn_pool_create(scratch_pool);
- SVN_ERR(svn_wc__db_read_children_of_working_node(&rel_children,
- db, local_abspath,
- scratch_pool,
- scratch_pool));
- for (i = 0; i < rel_children->nelts; i++)
- {
- const char *child_abspath;
+ for (hi = apr_hash_first(scratch_pool, iprop_paths);
+ hi;
+ hi = apr_hash_next(hi))
+ {
+ const char *child_abspath = svn__apr_hash_index_key(hi);
+ const char *child_relpath;
+ svn_kind_t child_kind;
svn_pool_clear(iterpool);
- child_abspath = svn_dirent_join(
- local_abspath, APR_ARRAY_IDX(rel_children, i, const char *),
- iterpool);
- if (depth == svn_depth_files)
- {
- svn_kind_t child_kind;
+ child_relpath = svn_dirent_is_child(local_relpath, child_abspath,
+ NULL);
- SVN_ERR(svn_wc__db_read_kind(&child_kind, db, child_abspath,
- FALSE, FALSE, iterpool));
- if (child_kind != svn_kind_file)
- continue;
+ if (! child_relpath)
+ {
+ continue; /* local_relpath itself */
}
- SVN_ERR(get_children_with_cached_iprops(iprop_paths,
- svn_depth_empty,
- child_abspath, db,
- result_pool,
- iterpool));
+ SVN_ERR(svn_wc__db_base_get_info_internal(NULL, &child_kind, NULL,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL,
+ wcroot, child_relpath,
+ scratch_pool,
+ scratch_pool));
+
+ /* Filter if not a file */
+ if (child_kind != svn_kind_file)
+ {
+ apr_hash_set(iprop_paths, child_abspath, APR_HASH_KEY_STRING,
+ NULL);
+ }
}
svn_pool_destroy(iterpool);
@@ -9160,10 +9187,26 @@ svn_wc__db_get_children_with_cached_ipro
apr_pool_t *result_pool,
apr_pool_t *scratch_pool)
{
- *iprop_paths = apr_hash_make(result_pool);
- SVN_ERR(get_children_with_cached_iprops(*iprop_paths, depth,
- local_abspath, db, result_pool,
- scratch_pool));
+ svn_wc__db_wcroot_t *wcroot;
+ const char *local_relpath;
+ struct get_children_with_cached_baton_t cwcb;
+
+ SVN_ERR_ASSERT(svn_dirent_is_absolute(local_abspath));
+
+ SVN_ERR(svn_wc__db_wcroot_parse_local_abspath(&wcroot, &local_relpath, db,
+ local_abspath, scratch_pool,
+ scratch_pool));
+ VERIFY_USABLE_WCROOT(wcroot);
+
+ cwcb.iprop_paths = apr_hash_make(result_pool);
+ cwcb.depth = depth;
+ cwcb.result_pool = result_pool;
+
+ SVN_ERR(svn_wc__db_with_txn(wcroot, local_relpath,
+ get_children_with_cached_iprops, &cwcb,
+ scratch_pool));
+
+ *iprop_paths = cwcb.iprop_paths;
return SVN_NO_ERROR;
}
Modified: subversion/trunk/subversion/libsvn_wc/wc_db.h
URL:
http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_wc/wc_db.h?rev=1413774&r1=1413773&r2=1413774&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_wc/wc_db.h (original)
+++ subversion/trunk/subversion/libsvn_wc/wc_db.h Mon Nov 26 18:40:17 2012
@@ -2116,9 +2116,11 @@ svn_wc__db_read_cached_iprops(apr_array_
/* Find BASE nodes with cached inherited properties.
Set *IPROPS_PATHS to a hash mapping const char * absolute working copy
- paths to the same for each path in the working copy at or below
- LOCAL_ABSPATH, limited by DEPTH, that has cached inherited properties
- for the BASE node of the path. Allocate *IPROP_PATHS in RESULT_POOL.
+ paths to the repos_relpath of the path for each path in the working copy
+ at or below LOCAL_ABSPATH, limited by DEPTH, that has cached inherited
+ properties for the BASE node of the path.
+
+ Allocate *IPROP_PATHS in RESULT_POOL.
Use SCRATCH_POOL for temporary allocations. */
svn_error_t *
svn_wc__db_get_children_with_cached_iprops(apr_hash_t **iprop_paths,