On Tue, Jan 17, 2012 at 10:12 AM, Julian Foad
> I (Julian Foad) wrote:
>> I think merge_reintegrate_tests.py 19 demonstrates it better than 1000 words so
>> I'll leave it at that for today.
> For people who'd like to follow along without having to apply and run the patch, that test does:
> Rev A A_COPY
> 02 |--cp-->X # every X is a commit
> 3~6 X |
> 07 | X
> 08 | |->X # side-branch 'BRANCH_DEV1'
> 09 | | X
> 10 | X<-|
> 11 X |
> 12 |->X | # side-branch 'TRUNK_DEV1'
> 13 | X |
> 14 X<-| |
> | |
> 15 |--mrg->X # 'merge ^/A A_COPY'
> | |
> 16 | X
> 17 | |->X # side-branch 'BRANCH_DEV2'
> 18 | | X
> 19 | X<-|
> 20 X |
> 21 |->X | # side-branch 'TRUNK_DEV2'
> 22 | X |
> 23 X<-| |
> | |
> 24 X<-mrg--| # 'merge --reintegrate ^/A_COPY A'
> | | # no keep-alive dance here
> 25 | X
> 26 | |->X # side-branch 'BRANCH_DEV3'
> 27 | | X
> 28 | X<-|
> 29 X |
> 30 |->X |
> 31 | X |
> 32 X<-| | # side-branch 'TRUNK_DEV3'
> | |
> WC |--mrg->X # 'merge ^/A A_COPY'
I think I understand now. Your patch works fine when the only cyclic
merges are done via reintegrate (i.e. r24).
When you said this though,
"However, if change A:40 had instead been a different merge into A,
let's say from C, it is still possible that merge might have brought
along some new mergeinfo describing merges from B, because of the way
mergeinfo is propagated from branch to branch. Therefore, if we find
that change A:40 adds new mergeinfo about merges from B, we cannot
simply say that A:40 describes a reintegrate merge from B. We need to
look more closely. That's what I'm currently working on."
I thought you were going to tackle more complex reflective merge
cases, such as this example:
|\ ^ |
| \ | |
| \ reintegrate |
| V | |
| A_COPY_2-----------------r9---r10--- |
| ^ sync merge
| / |
| cherry-pick merge of r8 |
V / V
As your patch stands, the above use-case causes some serious problems.
(The attached patch is an update of yours with a new
merge_reintegrate.py test #20, which demonstrates the above use case)
Here is the mergeinfo right before the final sync merge:
>svn pl -vR
Properties on 'A':
Properties on 'A_COPY_2':
Now perform the sync merge, your patch skips r11 because the naive
view of the mergeinfo change in that rev makes it look reflective. So
the change made in r10 on the A_COPY_2 branch, which should be applied
to A_COPY, is not:
>svn merge ^^/A A_COPY
DBG: merge.c:8464: r1:11 mi added:
DBG: merge.c:8464: r6:11 mi added:
DBG: merge.c:8464: r8:11 mi added:
DBG: merge.c:8464: r9:11 mi added:
DBG: merge.c:8464: r10:11 mi added:
DBG: merge.c:8633: Skipping reflective revision r11
Oops, there goes r10
--- Merging r2 through r10 into 'A_COPY':
--- Recording mergeinfo for merge of r2 through r11 into 'A_COPY':
Definitely not what the user intended I think. Worse, if the user
doesn't catch it and commits the sync merge...
>svn ci -m "Sync merge from /A to A_COPY"
Transmitting file data ....
Committed revision 12.
...and then reintegrates A_COPY to A, then the change from r10 is
actually removed from A:
>svn up -q
>svn merge ^^/A_COPY A --reintegrate
--- Merging differences between repository URLs into 'A':
--- Recording mergeinfo for merge between repository URLs into 'A':
>svn diff A\D\H\chi
--- A/D/H/chi (revision 12)
+++ A/D/H/chi (working copy)
@@ -1 +1 @@
-Branch 2 edit. <--- edit made in r10
+This is the file 'chi'.
Again, probably not what was intended.
> and the tail output for the last merge is:
> DBG: merge.c:8464: r23:24 mi added:
> DBG: /A_COPY:2-23
> DBG: merge.c:8633: Skipping reflective revision r24
> --- Merging r15 through r23 into 'A_COPY':
> A A_COPY/TrunkFix2
> A A_COPY/NewViaTRUNK_DEV2
> G A_COPY
> --- Merging r25 through r32 into 'A_COPY':
> A A_COPY/TrunkFix3
> A A_COPY/NewViaTRUNK_DEV3
> G A_COPY
> --- Recording mergeinfo for merge of r15 through r32 into 'A_COPY':
> G A_COPY
> mergeinfo on 'A':
> mergeinfo on 'A_COPY_at_BASE':
> mergeinfo on 'A_COPY' (working version):
> - Julian
Received on 2012-01-18 01:40:05 CET