[svn.haxx.se] · SVN Dev · SVN Users · SVN Org · TSVN Dev · TSVN Users · Subclipse Dev · Subclipse Users · this month's index

Re: svn commit: r29023 - trunk/subversion/libsvn_fs_base

From: David Glasser <glasser_at_davidglasser.net>
Date: Fri, 25 Jan 2008 10:46:38 -0800

On Jan 24, 2008 9:36 PM, <cmpilato_at_tigris.org> wrote:
> Author: cmpilato
> Date: Thu Jan 24 21:36:50 2008
> New Revision: 29023
>
> Log:
> Replace the SQLite-based implementation of mergeinfo indexing in
> libsvn_fs_base with a native Berkeley DB implementation. (Much of
> this was inspired by -- if not copied almost wholesale from -- the
> FSFS implementation of the same.)

>
> Modified: trunk/subversion/libsvn_fs_base/tree.c
> URL: http://svn.collab.net/viewvc/svn/trunk/subversion/libsvn_fs_base/tree.c?pathrev=29023&r1=29022&r2=29023
> ==============================================================================
> --- trunk/subversion/libsvn_fs_base/tree.c (original)
> +++ trunk/subversion/libsvn_fs_base/tree.c Thu Jan 24 21:36:50 2008
> @@ -469,6 +469,8 @@
> } parent_path_t;
>
>
> +/* Return the FS path for the parent path chain object PARENT_PATH,
> + allocated in POOL. */
> static const char *
> parent_path_path(parent_path_t *parent_path,
> apr_pool_t *pool)
> @@ -482,6 +484,25 @@
> }
>
>
> +/* Return the FS path for the parent path chain object CHILD relative
> + to its ANCESTOR in the same chain, allocated in POOL. */
> +static const char *
> +parent_path_relpath(parent_path_t *child,
> + parent_path_t *ancestor,
> + apr_pool_t *pool)
> +{
> + const char *path_so_far = "";
> + parent_path_t *this_node = child;
> + while (this_node != ancestor)
> + {
> + assert(this_node != NULL);
> + path_so_far = svn_path_join(this_node->entry, path_so_far, pool);
> + this_node = this_node->parent;
> + }
> + return path_so_far;
> +}
> +
> +
> /* Choose a copy ID inheritance method *INHERIT_P to be used in the
> event that immutable node CHILD in FS needs to be made mutable. If
> the inheritance method is copy_id_inherit_new, also return a
> @@ -1231,6 +1252,7 @@
> return SVN_NO_ERROR;
> }
>
> +
> struct change_node_prop_args {
> svn_fs_root_t *root;
> const char *path;
> @@ -1240,24 +1262,6 @@
>
>
> static svn_error_t *
> -change_txn_mergeinfo(struct change_node_prop_args *args, trail_t *trail)
> -{
> - const char *txn_id = args->root->txn;
> -
> - /* At least for single file merges, nodes which are direct
> - children of the root are received without a leading slash
> - (e.g. "/file.txt" is received as "file.txt"), so must be made
> - absolute. */
> - const char *canon_path = svn_fs__canonicalize_abspath(args->path,
> - trail->pool);
> - SVN_ERR(svn_fs_base__set_txn_mergeinfo(args->root->fs, txn_id, canon_path,
> - args->value, trail, trail->pool));
> -
> - return SVN_NO_ERROR;
> -}
> -
> -
> -static svn_error_t *
> txn_body_change_node_prop(void *baton,
> trail_t *trail)
> {
> @@ -1288,9 +1292,6 @@
> if (! proplist)
> proplist = apr_hash_make(trail->pool);
>
> - if (strcmp(args->name, SVN_PROP_MERGEINFO) == 0)
> - SVN_ERR(change_txn_mergeinfo(args, trail));
> -
> /* Set the property. */
> apr_hash_set(proplist, args->name, APR_HASH_KEY_STRING, args->value);
>
> @@ -4685,6 +4686,458 @@
> return SVN_NO_ERROR;
> }
>
> +
> +
> +/* Mergeinfo Queries */
> +
> +/* Examine directory NODE's immediately children for mergeinfo.
> +
> + For those which have explicit mergeinfo, add their mergeinfo to
> + RESULT_CATALOG (allocated in RESULT_CATALOG's pool).
> +
> + For those which don't, but sit atop trees which contain mergeinfo
> + somewhere deeper, add them to *CHILDREN_ATOP_MERGEINFO_TREES, a
> + hash mapping dirent names to dag_node_t * objects, allocated
> + from that hash's pool.
> +
> + For those which neither have explicit mergeinfo nor sit atop trees
> + which contain mergeinfo, ignore them.
> +
> + Use TRAIL->pool for temporary allocations. */
> +
> +struct get_mergeinfo_data_and_entries_baton
> +{
> + apr_hash_t *result_catalog;
> + apr_hash_t *children_atop_mergeinfo_trees;
> + dag_node_t *node;
> + const char *node_path;
> +};
> +
> +static svn_error_t *
> +txn_body_get_mergeinfo_data_and_entries(void *baton, trail_t *trail)
> +{
> + struct get_mergeinfo_data_and_entries_baton *args = baton;
> + dag_node_t *node = args->node;
> + apr_hash_t *entries;
> + apr_hash_index_t *hi;
> + apr_pool_t *iterpool = svn_pool_create(trail->pool);
> + apr_pool_t *result_pool = apr_hash_pool_get(args->result_catalog);
> + apr_pool_t *children_pool =
> + apr_hash_pool_get(args->children_atop_mergeinfo_trees);
> +
> + assert(svn_fs_base__dag_node_kind(node) == svn_node_dir);
> +
> + SVN_ERR(svn_fs_base__dag_dir_entries(&entries, node, trail, trail->pool));
> + for (hi = apr_hash_first(NULL, entries); hi; hi = apr_hash_next(hi))
> + {
> + void *val;
> + svn_fs_dirent_t *dirent;
> + const svn_fs_id_t *child_id;
> + dag_node_t *child_node;
> + svn_boolean_t has_mergeinfo;
> + apr_int64_t kid_count;
> +
> + svn_pool_clear(iterpool);
> + apr_hash_this(hi, NULL, NULL, &val);
> + dirent = val;
> + child_id = dirent->id;
> +
> + /* Get the node for this child. */
> + SVN_ERR(svn_fs_base__dag_get_node(&child_node, trail->fs, child_id,
> + trail, iterpool));
> +
> + /* Query the child node's mergeinfo stats. */
> + SVN_ERR(svn_fs_base__dag_get_mergeinfo_stats(&has_mergeinfo, &kid_count,
> + child_node, trail,
> + iterpool));
> +
> + /* If the child has mergeinfo, add it to the result catalog. */
> + if (has_mergeinfo)
> + {
> + apr_hash_t *plist, *child_mergeinfo_hash;
> + svn_string_t *pval;
> +
> + SVN_ERR(svn_fs_base__dag_get_proplist(&plist, child_node,
> + trail, iterpool));
> + pval = apr_hash_get(plist, SVN_PROP_MERGEINFO, APR_HASH_KEY_STRING);
> + if (! pval)
> + {
> + svn_string_t *id_str = svn_fs_base__id_unparse(child_id,
> + iterpool);
> + return svn_error_createf(SVN_ERR_FS_CORRUPT, NULL,
> + _("Node-revision '%s' claims to have "
> + "mergeinfo but doesn't"),
> + id_str->data);
> + }
> + SVN_ERR(svn_mergeinfo_parse(&child_mergeinfo_hash, pval->data,
> + result_pool));
> + apr_hash_set(args->result_catalog,
> + svn_path_join(args->node_path, dirent->name,
> + result_pool),
> + APR_HASH_KEY_STRING,
> + child_mergeinfo_hash);
> + }
> +
> + /* Otherwise, if the child has descendants with mergeinfo, add
> + it to the children_atop_mergeinfo_trees hash. */
> + else if (kid_count > 0)

I don't think this "else" here is correct.

> + {
> + if (svn_fs_base__dag_node_kind(child_node) != svn_node_dir)
> + {
> + svn_string_t *id_str = svn_fs_base__id_unparse(child_id,
> + iterpool);
> + return svn_error_createf(SVN_ERR_FS_CORRUPT, NULL,
> + _("Node-revision '%s' claims to sit "
> + "atop a tree containing mergeinfo "
> + "but is not a directory"),
> + id_str->data);
> + }
> + apr_hash_set(args->children_atop_mergeinfo_trees,
> + apr_pstrdup(children_pool, dirent->name),
> + APR_HASH_KEY_STRING,
> + svn_fs_base__dag_dup(child_node, children_pool));
> + }
> + }
> +
> + svn_pool_destroy(iterpool);
> + return SVN_NO_ERROR;
> +}

--dave

-- 
David Glasser | glasser@davidglasser.net | http://www.davidglasser.net/
---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe_at_subversion.tigris.org
For additional commands, e-mail: dev-help_at_subversion.tigris.org
Received on 2008-01-25 19:46:59 CET

This is an archived mail posted to the Subversion Dev mailing list.