You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@subversion.apache.org by pb...@apache.org on 2011/07/19 18:33:08 UTC
svn commit: r1148436 - /subversion/trunk/subversion/libsvn_client/merge.c
Author: pburba
Date: Tue Jul 19 16:33:07 2011
New Revision: 1148436
URL: http://svn.apache.org/viewvc?rev=1148436&view=rev
Log:
Replace a function, whose sole purpose is addressing issue #3669 'inheritance
can result in mergeinfo describing nonexistent sources' with a new function
that more closely aligns with the problem we are trying to solve.
No functional change, just doing this in the name of sanity.
* subversion/libsvn_client/merge.c
(get_invalid_inherited_mergeinfo): Delete and replace with...
(remove_non_existent_inherited_mergeinfo): ...this.
(get_full_mergeinfo): Replace call to get_invalid_inherited_mergeinfo()
with remove_non_existent_inherited_mergeinfo().
Modified:
subversion/trunk/subversion/libsvn_client/merge.c
Modified: subversion/trunk/subversion/libsvn_client/merge.c
URL: http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_client/merge.c?rev=1148436&r1=1148435&r2=1148436&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_client/merge.c (original)
+++ subversion/trunk/subversion/libsvn_client/merge.c Tue Jul 19 16:33:07 2011
@@ -3174,47 +3174,45 @@ fix_deleted_subtree_ranges(const char *u
/*** Determining What Remains To Be Merged ***/
-/* Contact the repository to get the portion of a working copy path's
- inherited mergeinfo (if any) which contains non-existent mergeinfo
- sources -- see http://subversion.tigris.org/issues/show_bug.cgi?id=3669
-
- Note: This function should only be called if the server supports the
- SVN_RA_CAPABILITY_VALIDATE_INHERITED_MERGEINFO capability.
-
- Query the repository for the mergeinfo TARGET_ABSPATH inherits at its
- base revision.
-
- If no mergeinfo is inherited set *INVALID_INHERITED_MERGEINFO to NULL.
-
- If only empty mergeinfo is inherited set *INVALID_INHERITED_MERGEINFO to
- an empty hash.
-
- If non-empty mergeinfo is inherited then, if the server supports the
- SVN_RA_CAPABILITY_VALIDATE_INHERITED_MERGEINFO capability, remove all
- existing path-revisions from the inherited mergeinfo, and set
- *INVALID_INHERITED_MERGEINFO to the remainder. If all of the inherited
- inherited mergeinfo describes non-existent paths, then set
- *INVALID_INHERITED_MERGEINFO to an empty hash.
+/* Given the inherited mergeinfo INHERITED_MERGEINFO on TARGET_ABSPATH,
+ set *CORRECTED_MERGEINFO equal to INHERITED_MERGEINFO less any
+ mergeinfo TARGET_ABSPATH, at its base revision, inherits from the
+ repository. If TARGET_ABSPATH doesn't exist in the repository, or if
+ no mergeinfo or only empty mergeinfo is inherited from the repository,
+ then set *CORRECTED_MERGEINFO equal to INHERITED_MERGEINFO.
RA_SESSION is an open session that may be temporarily reparented as
needed by this function.
- RESULT_POOL is used to allocate *INVALID_INHERITED_MERGEINFO, SCRATCH_POOL
- is used for any temporary allocations. */
+ RESULT_POOL is used to allocate *CORRECTED_MERGEINFO if necessary.
+ SCRATCH_POOL is used for temporary allocations.
+
+ Note: This function should only be called if the server supports the
+ SVN_RA_CAPABILITY_VALIDATE_INHERITED_MERGEINFO capability. If the server
+ does not have that capability then this function is a no-op.
+
+ ### While this function addresses issue #3669 'inheritance can result
+ ### in mergeinfo describing nonexistent sources', it is worth noting
+ ### that issue #3756 'subtree merge can inherit invalid working
+ ### mergeinfo' is still a problem here, i.e. if TARGET_ABSPATH inherits
+ ### working mergeinfo from a working copy parent, some of the merge
+ ### sources in that mergeinfo may describe non-existent path-revs.
+ ###
+ ### See http://subversion.tigris.org/issues/show_bug.cgi?id=3669
+ ### and http://subversion.tigris.org/issues/show_bug.cgi?id=3756 */
static svn_error_t *
-get_invalid_inherited_mergeinfo(svn_mergeinfo_t *invalid_inherited_mergeinfo,
- svn_ra_session_t *ra_session,
- const char *target_abspath,
- svn_client_ctx_t *ctx,
- apr_pool_t *result_pool,
- apr_pool_t *scratch_pool)
+remove_non_existent_inherited_mergeinfo(svn_mergeinfo_t *corrected_mergeinfo,
+ svn_mergeinfo_t inherited_mergeinfo,
+ svn_ra_session_t *ra_session,
+ const char *target_abspath,
+ svn_client_ctx_t *ctx,
+ apr_pool_t *result_pool,
+ apr_pool_t *scratch_pool)
{
- svn_mergeinfo_t repos_raw_inherited;
- svn_mergeinfo_t repos_validated_inherited;
svn_revnum_t base_revision;
- /* Our starting assumptions. */
- *invalid_inherited_mergeinfo = NULL;
+ /* Our starting assumption. */
+ *corrected_mergeinfo = inherited_mergeinfo;
SVN_ERR(svn_wc__node_get_base_rev(&base_revision, ctx->wc_ctx,
target_abspath, scratch_pool));
@@ -3223,6 +3221,8 @@ get_invalid_inherited_mergeinfo(svn_merg
in the repository yet, so we're done. */
if (SVN_IS_VALID_REVNUM(base_revision))
{
+ svn_mergeinfo_t repos_raw_inherited;
+ svn_mergeinfo_t nonexistent_inherited_mergeinfo;
const char *target_url;
const char *session_url;
@@ -3232,38 +3232,66 @@ get_invalid_inherited_mergeinfo(svn_merg
SVN_ERR(svn_client__ensure_ra_session_url(&session_url, ra_session,
target_url, scratch_pool));
- /* Contact the repository to derive the portion of
- TARGET_ABSPATH's inherited mergeinfo which is non-existent
- and remove it from */
- SVN_ERR(svn_client__get_repos_mergeinfo(
- ra_session, &repos_raw_inherited, "", base_revision,
- svn_mergeinfo_inherited, TRUE,
- FALSE, scratch_pool));
+ /* Get TARGET_ABSPATH's inherited mergeinfo from the repository with
+ that most unusual of requests: We don't want the server to check
+ that the inherited merge sources actually exist. */
+ SVN_ERR(svn_client__get_repos_mergeinfo(ra_session,
+ &repos_raw_inherited, "",
+ base_revision,
+ svn_mergeinfo_inherited,
+ TRUE,
+ FALSE, /* No validation */
+ scratch_pool));
- if (repos_raw_inherited == NULL)
- {
- *invalid_inherited_mergeinfo = NULL;
- }
- else if (apr_hash_count(repos_raw_inherited) == 0)
+ if (repos_raw_inherited == NULL
+ || apr_hash_count(repos_raw_inherited) == 0)
{
- *invalid_inherited_mergeinfo = apr_hash_make(result_pool);
+ /* No mergeinfo or only empty mergeinfo was inherited. */
+ nonexistent_inherited_mergeinfo = NULL;
}
else
{
- SVN_ERR(svn_client__get_repos_mergeinfo(
- ra_session, &repos_validated_inherited, "", base_revision,
- svn_mergeinfo_inherited, TRUE,
- TRUE, scratch_pool));
- SVN_ERR(svn_mergeinfo_remove2(invalid_inherited_mergeinfo,
- repos_validated_inherited,
- repos_raw_inherited, FALSE,
- result_pool, scratch_pool));
+ /* Now ask the server for TARGET_ABSPATH's inherited mergeinfo
+ but this time request that the inherited mergeinfo be valiated
+ so it contains only existing merge sources. */
+ svn_mergeinfo_t repos_validated_inherited;
+
+ SVN_ERR(svn_client__get_repos_mergeinfo(ra_session,
+ &repos_validated_inherited,
+ "", base_revision,
+ svn_mergeinfo_inherited,
+ TRUE,
+ TRUE, /* Validated */
+ scratch_pool));
+ if (repos_validated_inherited == NULL
+ || apr_hash_count(repos_validated_inherited) == 0)
+ {
+ /* All of the inherited mergeinfo describes non-existent
+ merge sources. */
+ nonexistent_inherited_mergeinfo = repos_raw_inherited;
+ }
+ else
+ {
+ SVN_ERR(svn_mergeinfo_remove2(&nonexistent_inherited_mergeinfo,
+ repos_validated_inherited,
+ repos_raw_inherited, FALSE,
+ scratch_pool, scratch_pool));
+ }
}
/* If we needed to temporarily reparent RA_SESSION, then point it
back to its original URL. */
if (session_url)
SVN_ERR(svn_ra_reparent(ra_session, session_url, scratch_pool));
+
+ /* Remove any non-existent inherited merge sources from
+ INHERITED_MERGEINFO. */
+ if (nonexistent_inherited_mergeinfo
+ && apr_hash_count(nonexistent_inherited_mergeinfo))
+ SVN_ERR(svn_mergeinfo_remove2(corrected_mergeinfo,
+ nonexistent_inherited_mergeinfo,
+ inherited_mergeinfo, FALSE,
+ result_pool, scratch_pool));
}
return SVN_NO_ERROR;
}
@@ -3342,27 +3370,19 @@ get_full_mergeinfo(svn_mergeinfo_t *reco
If we already contacted the repository for inherited mergeinfo then
we've done all we can since svn_client__get_wc_or_repos_mergeinfo
- will request validation by default when asking the repository.
-
- ### [PTB] Issue #3756 is still a problem here, i.e. TARGET_ABSPATH
- ### inherits working mergeinfo from a working copy parent. */
+ will request validation by default when asking the repository. */
if (inherited_mergeinfo
&& validate_inherited
&& !inherited_from_repos)
{
- svn_mergeinfo_t invalid_inherited_mergeinfo;
+ SVN_ERR(remove_non_existent_inherited_mergeinfo(recorded_mergeinfo,
+ *recorded_mergeinfo,
+ ra_session,
+ target_abspath,
+ ctx,
+ scratch_pool,
+ scratch_pool));
- SVN_ERR(get_invalid_inherited_mergeinfo(
- &invalid_inherited_mergeinfo,
- ra_session, target_abspath, ctx,
- scratch_pool, scratch_pool));
-
- if (invalid_inherited_mergeinfo
- && apr_hash_count(invalid_inherited_mergeinfo))
- SVN_ERR(svn_mergeinfo_remove2(recorded_mergeinfo,
- invalid_inherited_mergeinfo,
- *recorded_mergeinfo, FALSE,
- scratch_pool, scratch_pool));
}
}