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

Re: svn commit: r28561 - in branches/issue-2897/subversion: libsvn_client tests/cmdline

From: Kamesh Jayachandran <kamesh_at_collab.net>
Date: Mon, 07 Jan 2008 21:57:25 +0530

Hi David,

Responding to items that I did not in my earlier response.

>> + apr_pool_t *subpool = svn_pool_create(merge_b->pool);
>> + SVN_ERR(svn_io_temp_dir(&temp_dir, subpool));
>> +
>> + if (merge_b->merge_options)
>> + SVN_ERR(svn_diff_file_options_parse(options,
>> + merge_b->merge_options, subpool));
>> + else
>> + options = svn_diff_file_options_create(subpool);
>> + for (i = 0; i < merge_b->reflected_ranges->nelts; i++)
>>
>
> Loop without iterpool.
>

Fixed in r28711.
> Also, um. I might be paranoid, but I'm not really comfortable with
> you overwriting "older" like this. I'd rather this function just make
> a series of temporary files and return the last filename to
> reflective_merge_file_changed. There's nothing guaranteeing that
> "older" might not be something that some other part of the program
> cares about. Just figuring out what context this function can be
> called in is non-trivial; specifically, "older" gets its value from
> the diff callback file_changed call, and I notice that in
> libsvn_wc/diff.c(file_diff) it can get called with "older" equal to
> the text base path! Maybe this code path can't ever reach the merge
> code, but I'm still not comfortable with this...
>
Will fix it in subsequent commit.

>> /* A svn_wc_diff_callbacks2_t function. */
>> static svn_error_t *
>> +reflective_merge_file_added(svn_wc_adm_access_t *adm_access,
>> + svn_wc_notify_state_t *content_state,
>> + svn_wc_notify_state_t *prop_state,
>> + const char *mine,
>> + const char *older,
>> + const char *yours,
>> + svn_revnum_t rev1,
>> + svn_revnum_t rev2,
>> + const char *mimetype1,
>> + const char *mimetype2,
>> + const apr_array_header_t *prop_changes,
>> + apr_hash_t *original_props,
>> + void *baton)
>> +{
>> + merge_cmd_baton_t *merge_b = baton;
>> + svn_node_kind_t kind;
>> +
>> + SVN_ERR(svn_io_check_path(mine, &kind, merge_b->pool));
>>
>
> I don't really get what this implementation is doing. Is it basically
> "the same as the normal merge_file_added, except if the file is
> already there then nothing happens and it's OK"? Why?
>

It was a faulty implementation, corrected at r28768.
>> +reflective_merge_file_deleted(svn_wc_adm_access_t *adm_access,
>> + svn_wc_notify_state_t *state,
>> + const char *mine,
>> + const char *older,
>> + const char *yours,
>> + const char *mimetype1,
>> + const char *mimetype2,
>> + apr_hash_t *original_props,
>> + void *baton)
>> +{
>> + merge_cmd_baton_t *merge_b = baton;
>> + svn_node_kind_t kind;
>> + SVN_ERR(svn_io_check_path(mine, &kind, merge_b->pool));
>> + if (kind == svn_node_file)
>> + SVN_ERR(merge_file_deleted(adm_access, state, mine, older, yours,
>> + mimetype1, mimetype2, original_props, baton));
>>
>
> Similarly here. Maybe just a comment somewhere explaining the point
> of the reflective callbacks might help...
>
>

It is also faulty will correct in subsequent commit.

>> static svn_error_t *
>> +reflective_merge_dir_added(svn_wc_adm_access_t *adm_access,
>> + svn_wc_notify_state_t *state,
>> + const char *path,
>> + svn_revnum_t rev,
>> + void *baton)
>> +{
>> + merge_cmd_baton_t *merge_b = baton;
>> + svn_node_kind_t kind;
>> + SVN_ERR(svn_io_check_path(path, &kind, merge_b->pool));
>> + if (kind == svn_node_none)
>> + SVN_ERR(merge_dir_added(adm_access, state, path, rev, baton));
>>
>
> Yup, still don't get it :)
>

It was a faulty implementation, corrected at r28768.
>>
>> +/* A svn_wc_diff_callbacks2_t function. */
>> +static svn_error_t *
>> +reflective_merge_dir_deleted(svn_wc_adm_access_t *adm_access,
>> + svn_wc_notify_state_t *state,
>> + const char *path,
>> + void *baton)
>> +{
>> + merge_cmd_baton_t *merge_b = baton;
>> + svn_node_kind_t kind;
>> + SVN_ERR(svn_io_check_path(path, &kind, merge_b->pool));
>> + if (kind == svn_node_dir)
>> + SVN_ERR(merge_dir_deleted(adm_access, state, path, baton));
>>
>
> ... and still :)
>

It is also faulty, will correct in subsequent commit.
>
>> +static const svn_wc_diff_callbacks2_t
>> +reflective_merge_callbacks =
>> + {
>> + reflective_merge_file_changed,
>> + reflective_merge_file_added,
>> + reflective_merge_file_deleted,
>> + reflective_merge_dir_added,
>> + reflective_merge_dir_deleted,
>> + merge_props_changed
>>
>
> Hmm, why no reflective props changed?
>

Except 'svn:mergeinfo' props rest of the properties are treated like
binary ones and hence no-contextual merging and hence *no* 'extract and
apply non-reflective changes'.

>
>> + };
>>
>> /*-----------------------------------------------------------------------*/
>>
>> @@ -1091,12 +1308,15 @@ notification_receiver(void *baton, const
>> && notify_b->merge_b->target_has_dummy_merge_range))
>> {
>> svn_wc_notify_t *notify_merge_begin;
>> + svn_client__remaining_range_info_t *range_info;
>> notify_merge_begin =
>> svn_wc_create_notify(child->path,
>> svn_wc_notify_merge_begin, pool);
>> - notify_merge_begin->merge_range =
>> - APR_ARRAY_IDX(child->remaining_ranges, 0,
>> - svn_merge_range_t *);
>> + range_info =
>> + APR_ARRAY_IDX(child->remaining_ranges, 0,
>> + svn_client__remaining_range_info_t *);
>> + notify_merge_begin->merge_range = range_info->range;
>> +
>> if (notify_b->wrapped_func)
>> (*notify_b->wrapped_func)(notify_b->wrapped_baton,
>> notify_merge_begin, pool);
>> @@ -1170,6 +1390,12 @@ notification_receiver(void *baton, const
>>
>> NOTE: This should only be called when honoring mergeinfo.
>>
>> + *REFLECTIVE_RANGELIST will be populated with commits post merge from
>> + target on source within revision1:revision2.
>> +
>>
>
> Again, what are the types of the array elements? It's confusing to
> call an array a "rangelist" since that already means something.
>

IIUC We mean rangelist as list a.k.a apr_array and all rangelist's value
type being 'svn_merge_range_t *'.

Updated doc string to state the array value types at r28769.

>
>> + *REFLECTED_RANGES_LIST will be populated with merge ranges that are
>> + merged from target to source within revision1:revision2.
>> +
>>
>
> Ditto. And state that they match up with the previous one?
>
>

Fixed in r28770.
>> @@ -1231,13 +1457,13 @@ filter_reflected_revisions(apr_array_hea
>> drive_merge_report_editor()'s application of the editor to the WC
>> -- by subtracting revisions which have already been merged from
>> MERGEINFO_PATH into the working copy from the requested range(s)
>> - REQUESTED_MERGE, and storing what's left in REMAINING_RANGES.
>> + REQUESTED_MERGE, and storing what's left in RANGES_TO_MERGE.
>> TARGET_MERGEINFO may be NULL.
>>
>> NOTE: This should only be called when honoring mergeinfo.
>> */
>> static svn_error_t *
>> -filter_merged_revisions(apr_array_header_t **remaining_ranges,
>> +filter_merged_revisions(apr_array_header_t **ranges_to_merge,
>> const char *mergeinfo_path,
>> apr_hash_t *target_mergeinfo,
>> apr_hash_t *implicit_mergeinfo,
>> @@ -1265,20 +1491,20 @@ filter_merged_revisions(apr_array_header
>> revert to work properly. */
>> requested_merge = svn_rangelist_dup(requested_merge, pool);
>> SVN_ERR(svn_rangelist_reverse(requested_merge, pool));
>> - SVN_ERR(svn_rangelist_intersect(remaining_ranges,
>> + SVN_ERR(svn_rangelist_intersect(ranges_to_merge,
>> target_rangelist,
>> requested_merge, pool));
>> - SVN_ERR(svn_rangelist_reverse(*remaining_ranges, pool));
>> + SVN_ERR(svn_rangelist_reverse(*ranges_to_merge, pool));
>> }
>> else
>> {
>> - *remaining_ranges =
>> + *ranges_to_merge =
>> apr_array_make(pool, 1, sizeof(svn_merge_range_t *));
>> }
>> }
>> else
>> {
>> - *remaining_ranges = requested_merge;
>> + *ranges_to_merge = requested_merge;
>>
>> /* ### TODO: Which evil shall we choose?
>> ###
>> @@ -1312,7 +1538,7 @@ filter_merged_revisions(apr_array_header
>> #endif
>>
>> if (target_rangelist)
>> - SVN_ERR(svn_rangelist_remove(remaining_ranges, target_rangelist,
>> + SVN_ERR(svn_rangelist_remove(ranges_to_merge, target_rangelist,
>> requested_merge, FALSE, pool));
>> }
>> return SVN_NO_ERROR;
>> @@ -1345,14 +1571,23 @@ calculate_remaining_ranges(apr_array_hea
>> apr_pool_t *pool)
>> {
>> apr_array_header_t *requested_rangelist;
>> + apr_array_header_t *reflected_ranges_list = NULL;
>> + apr_array_header_t *reflective_rangelist = NULL;
>> + apr_array_header_t *ranges_to_merge;
>> + svn_merge_range_t *range = NULL, *reflective_range = NULL;
>> + apr_array_header_t *reflected_ranges;
>> const char *old_url;
>> const char *mergeinfo_path;
>> + int i = 0, j = 0;
>> const char *primary_url = (revision1 < revision2) ? url2 : url1;
>>
>> /* Determine which of the requested ranges to consider merging... */
>> SVN_ERR(svn_ra_get_session_url(ra_session, &old_url, pool));
>> SVN_ERR(svn_ra_reparent(ra_session, source_root_url, pool));
>> - SVN_ERR(filter_reflected_revisions(&requested_rangelist, source_root_url,
>> + SVN_ERR(filter_reflected_revisions(&requested_rangelist,
>> + &reflected_ranges_list,
>> + &reflective_rangelist,
>> + source_root_url,
>> url1, revision1, url2, revision2,
>> inheritable, entry->url,
>> ra_session, ctx, pool));
>> @@ -1363,10 +1598,64 @@ calculate_remaining_ranges(apr_array_hea
>> SVN_ERR(svn_client__path_relative_to_root(&mergeinfo_path, primary_url,
>> source_root_url, TRUE,
>> ra_session, NULL, pool));
>> - SVN_ERR(filter_merged_revisions(remaining_ranges, mergeinfo_path,
>> + SVN_ERR(filter_merged_revisions(&ranges_to_merge, mergeinfo_path,
>> target_mergeinfo, implicit_mergeinfo,
>> requested_rangelist,
>> (revision1 > revision2), entry, pool));
>> +
>> + *remaining_ranges =
>> + apr_array_make(pool, 0,
>> + sizeof(svn_client__remaining_range_info_t *));
>> + /* populate remaining_ranges list. */
>> + while (TRUE)
>> + {
>>
>
> I *think* youc an safely move the declarations of range and
> reflective_range and reflected_reanges to here, which would be more
> clear. (Having the top-level declarations include
> requested_rangelist, reflected_ranges_list, reflective_rangelist,
> ranges_to_mege, range, reflective_range, and reflected_ranges is a
> little overwhelming!)
>
>

requested_rangelist, reflected_ranges_list, reflective_rangelist,
ranges_to_merge need to be having the scope as they have now,
I will look at other variables closely and fix them in subsequent commit if needed.

>> + APR_ARRAY_PUSH(*remaining_ranges,
>> + svn_client__remaining_range_info_t *) = range_info;
>> + range = NULL;
>> + reflective_range = NULL;
>>
>
> (And remove these NULLings.)
>

They are needed!, or else we would have wrong results in subsequent
WHILE iteration.

>> + default_start = range_info->range->start;
>> + /* ### We handle reflective_merges only if target has such
>> + * reflective merges. We should do for childs in
>> + * children_with_mergeinfo too, but that would be complex
>> + * enough to handle.
>> + */
>>
>
> I don't really follow what this comment means.
>
Suppose we have a working copy of url $URL/trunk.
If some directory 'src' under '/trunk' has a reflective commit, we are
not handling that as of today in issue-2897 branch, implementing that
would be too complex I believe. In other words we honour reflections
only at url from the given working copy merge target.

>> + SVN_ERR(svn_client__get_diff_editor(target_wcpath, adm_access,
>> + callbacks, merge_b, depth,
>> + merge_b->dry_run, merge_b->ra_session2,
>> + default_start, notification_receiver,
>> + notify_b, merge_b->ctx->cancel_func,
>> + merge_b->ctx->cancel_baton, &diff_editor,
>> + &diff_edit_baton, pool));
>>
>
> Not sure why you reflowed this; it's hard to see what the change was.
>

Sorry about that.

>> Index: branches/issue-2897/subversion/libsvn_client/mergeinfo.h
>> ===================================================================
>> --- branches/issue-2897/subversion/libsvn_client/mergeinfo.h (revision 28560)
>> +++ branches/issue-2897/subversion/libsvn_client/mergeinfo.h (revision 28561)
>> @@ -23,6 +23,14 @@
>> /*** Data Structures ***/
>>
>>
>> +typedef struct svn_client__remaining_range_info_t {
>> + /* Subset of requested merge range. */
>> + svn_merge_range_t *range;
>> + /* If reflected_ranges is not NULL then above 'range' is a
>> + reflective range of it. */
>> + apr_array_header_t *reflected_ranges;
>>
>
> Document the type of the elements. And I can't really parse the
> comment there. Do you mean that these are the ranges reflected in
> 'range', or something?
>
>

Yes. Fixed the doc with array element types at r28772.

Thanks again for your kind review.

With regards
Kamesh Jayachandran

---------------------------------------------------------------------
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-07 17:27:38 CET

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

This site is subject to the Apache Privacy Policy and the Apache Public Forum Archive Policy.