You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@subversion.apache.org by Kamesh Jayachandran <ka...@collab.net> on 2007/10/26 07:16:53 UTC

Input needed in solving issue 2897.

Hi All,

Summary: Filter 'Target Reflective Merges on Merge Source', while 
merging to Target from merge source.

Consider the following situation
* Create feature branch '/fb' from '/trunk' (results in rX)
* Do some commits on '/fb'  (rP, rQ, rR)
* merge '/trunk' to '/fb'(merge few revs rX:Y(current HEAD), commit 
results in rZ).
* Do some more commits on '/fb'  (rS, rT)
* merge '/fb' back to '/trunk'.

Expected behaviour of last merge:
merge *only* 'rP, rQ, rR, rS, rT' from '/fb' to 'trunk', ie it should 
exclude rZ as it is reflective merges from '/trunk' itself.

Actual behaviour of last merge:
Currently this behaviour is broken (issue 2897 just deals with it.), it 
merges only rS and rT alone (that is it negates 'rX:Y' from rX:HEAD and 
gives rS and rT, remember rX<rP, rQ, rR <rY)

What to fix: We should fix this negation logic to negate the 'commit rev 
rZ' rather than what got merged(rX:Y).

We discussed few possible fixes in issue 2897 and finally we came up 
with the following finding/proposal.

Current limitation in backend mergeinfo storage:
----------------------------------------------------------------------
We have sqlite table 'mergeinfo' which has the tokenized merge revisions 
for each path
for each 'merge+commit'. This information is ambiguous, consider the 
following case.

In r50 you merged -r12 from '/trunk' to '/fb'.(Puts one record on 
mergeinfo for
this path.)
In r53 you merged -r15 from '/trunk' to '/fb'.(Puts two records on 
mergeinfo for
this path.)
In r56 you merged -r18 from '/trunk' to '/fb'.(Puts three records on 
mergeinfo
for this path.)

In this particular case r12 merge would appear 3 times, which record to 
consider to
decide when the merge has occured?
Take the least revision(commit revision)?, No What if we reverted r12 from
'/trunk' to '/fb' on r51, Remember we don't record reverse merges and 
merge back the same on r52.

Proposal to fix this issue
--------------------------------
Change the table structure of 'mergeinfo_changed'(today it is 2 coulum 
table of commit_rev, merge_target) almost same as that of mergeinfo and
record the merge range that is getting added(as we are not recording the 
revert independently !) in this commit. After all 'mergeinfo_changed' 
means 'only changes'.

2)We need a ra API 'svn_ra_get_merge_commit_revs(apr_array_header_t
**commit_rev_list, const char* mergefrom, const char* mergeto,
apr_array_header_t *merge_rangelist)

In our context 'mergefrom' -> '/trunk' (target)
'mergeto' -> '/fb'(source)

This API will give us 'commit_rev_list' a list of reflective revisions on
'mergeto' from 'mergefrom' for the merge_rangelist.

3)We can use this 'svn_ra_get_merge_commit_revs' in libsvn_client to 
negate the commit revs.

Any thoughts are welcome!

With regards
Kamesh Jayachandran


P.S: issue 2837 seem to encompass this functionality too, though it can 
be reduced to 'identify local edits in a merge from actual merge 
itself', which is a much complex problem that our current design can not 
solve.

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@subversion.tigris.org
For additional commands, e-mail: dev-help@subversion.tigris.org

RE: Input needed in solving issue 2897.

Posted by Kamesh Jayachandran <ka...@collab.net>.
 
>Kamesh Jayachandran <ka...@collab.net> writes:
>> What I am proposing is let us use 'mergeinfo' for full-text
>> mergeinfo(which we already do), 'mergeinfo_changed' as 'delta
>> mergeinfo' may be we can rename those tables to reflect this intent.

>+1, and I pledge to review the change(s).

Thanks.

>(I think *theoretically*, we could do it without this schema tweak,
>right?  But the performance would not be good, and the code would have
>to be a lot more complex.)

Yes, it would make the code very complex.

>This proposal includes the new API you described in
>http://subversion.tigris.org/issues/show_bug.cgi?id=2897#desc20,
>right?

Yes, but the API is not complete yet so its name/signature would change a lot from what has been described as tentative in the desc20 of issue 2897.

Thanks,

With regards
Kamesh Jayachandran

Re: Input needed in solving issue 2897.

Posted by Karl Fogel <kf...@red-bean.com>.
Kamesh Jayachandran <ka...@collab.net> writes:
> What I am proposing is let us use 'mergeinfo' for full-text
> mergeinfo(which we already do), 'mergeinfo_changed' as 'delta
> mergeinfo' may be we can rename those tables to reflect this intent.

+1, and I pledge to review the change(s).  Storing this information in
both tables will make the merge selection process much easier.

(I think *theoretically*, we could do it without this schema tweak,
right?  But the performance would not be good, and the code would have
to be a lot more complex.)

This proposal includes the new API you described in
http://subversion.tigris.org/issues/show_bug.cgi?id=2897#desc20,
right?

We're a bit hampered by the time-zone cycle here, unfortunately.  I'll
try to be as responsive as I can, but basically you're awake when I'm
asleep and vice versa.

-Karl

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@subversion.tigris.org
For additional commands, e-mail: dev-help@subversion.tigris.org

Re: Input needed in solving issue 2897.

Posted by Kamesh Jayachandran <ka...@collab.net>.
> Thanks.
>
> I'm looking at the table definitions in mergeinfo-sqlite-index.c and
> trying map the above to what I see there.  Let's take your first commit:
>
>    > Let us say you have '/trunk:12' on '/fb', It puts one record
>    > ('/trunk', '/fb', 11, 12, 1)
>
> That produces a row like this in mergeinfo_changed:
>
>    revision == 50  /* revision in which r12 was merged from trunk to fb */
>    path == '/fb'
>
> And a row like this in 'mergeinfo':
>
>    revision == 50
>    mergedfrom == '/trunk'
>    mergedto == '/fb'
>    mergedrevstart == 11
>    mergedrevend == 12
>    inheritable == 1
>
> Is that right so far?
>   

Yes.

> Now when we go to the next commit...
>
>    > Now next commit has '/trunk:12,18' on '/fb', It puts two records
>    > ('/trunk', '/fb', 11, 12, 1) ('/trunk', '/fb', 17, 18, 1) one for
>    > each merge range+path record.
>
> That produces a row like this in mergeinfo_changed:
>
>    revision == 56  /* revision in which r18 was merged from trunk to fb */
>    path == '/fb'
>
> And a row like this in 'mergeinfo':
>
>    revision == 56
>    mergedfrom == '/trunk'
>    mergedto == '/fb'
>    mergedrevstart == 17
>    mergedrevend == 18
>    inheritable == 1
>
> Now, my question is, do we also put in a new row for the r12
> mergeinfo?  That is, do we add a new row saying
>
>     (56, '/trunk', '/fb', 11, 12, 1)
>
> even though we already have a row from before that says
>
>     (50, '/trunk', '/fb', 11, 12, 1)
>
> ?
>
>   

Yes. we put again (56, '/trunk', '/fb', 11, 12, 1). Without this 
redundancy it would be difficult to combine records in this table, as 
records may be for totally different nodes in the history just having 
the same name.


> Okay, moving on to the third commit:
>
>    > Now next commit has '/trunk:12-13,18' on '/fb', It puts two records
>    > ('/trunk', '/fb', 11, 13, 1) ('/trunk', '/fb', 17, 18, 1) one for
>    > each merge range+path record.
>
> (Let's say that happens in r60.)  A similar questions applies: when we
> add the record...
>
>    (60, '/trunk', '/fb', 11, 13, 1)
>
> ...do we also *remove* any records like this:
>
>    (..., '/trunk', '/fb', 11, 12, 1)
>
> since they are sort of subsets of the new record?  Or do we let the
> old records remain?  I realize that doing such removals might be
> computationally intensive, so I'm really asking two questions: do we
> remove such subset records, and if not, do we at least *wish* we could
> remove them?
>   

No we won't remove any old records. Each set of records for a revision 
uniquely identify a node's mergeinfo.
Logic is simple,
Upon every commit 'fs_(fs|base) identifies the 'paths_changed' with 
'svn:mergeinfo' modified and tokenizes this fulltext mergeinfo and puts 
them as records in mergeinfo.

What I am proposing is let us use 'mergeinfo' for full-text 
mergeinfo(which we already do), 'mergeinfo_changed' as 'delta mergeinfo' 
may be we can rename those tables to reflect this intent.

>   
>   
> Thanks, that helps clarify things for me.
>
> Let me test my understanding.  The way to find out (using the current
> code) what exactly got merged in, say, r60 is to look in
> mergeinfo_changed and select on rev==60.  Suppose we get these
> results:
>
>    (60, '/some/path')
>    (60, '/some/other/path')
>    (60, '/yet/another/path')
>
> Okay, let's start with '/some/path'.  We search backwards in that
> table for the previous change to '/some/path'.  Say we find this:
>
>    (56, '/some/path')
>
> Great.  Now go to the mergeinfo table, and select every row where
>
>    (rev == 60) && (mergedto == '/some/path')
>
> Then get all the mergeinfo for 
>
>    (rev == 56) && (mergedto == '/some/path')
>
> Compute the "difference" between the two mergeinfo sets, and that is
> what was merged to '/some/path' in r60.  Repeat for '/some/other/path'
> and '/yet/another/path', of course.
>
> Is my understanding even close?  This is all guessing, based on the
> table schemas and on thinking about the problem.  I might be
> completely wrong, please don't hesitate to correct me :-).  If I am
> wrong, then I don't understand the way those two tables are used
> together in today's code.
>
>   

Your understanding is exactly correct. For the usecase of 2897 we just 
need the opposite 'which commit_rev has this merge'.

Thanks for your meticulous review.

With regards
Kamesh Jayachandran

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@subversion.tigris.org
For additional commands, e-mail: dev-help@subversion.tigris.org

Re: Input needed in solving issue 2897.

Posted by Karl Fogel <kf...@red-bean.com>.
"Kamesh Jayachandran" <ka...@collab.net> writes:
>>So my question is, immediately after rZ, does the svn:mergeinfo on /fb
>>accurately reflect exactly what has been merged in from elsewhere?  If
>>not, is there a good reason why not?
>
> Good question!. Mergeinfo on '/fb' is accurate only with respect to
> '/fb'. When someone wants to know what has been merged from '/trunk'
> to '/fb', he would get the correct answer say rX:Y. One should use
> this mergerange(rX:Y) to avoid repeated merge only if the merge is
> from '/trunk' not '/fb'. To avoid repeat merge from '/fb' one should
> use rZ.
>
> Mergeinfo === 'merge source' + 'merge range' doing a math only on
> 'merge range'(ignoring the merge source) is like comparing apples
> and oranges.

Yes, agreed -- I completely see what you mean.

(Slowly, slowly I'm beginning to understand our merge tracking
implementation.)

>>> In this particular case r12 merge would appear 3 times, which record
>>> to consider to decide when the merge has occured?
>
>>Why does r12 appear 3 times?  It was only merged once.
>
> That is the way mergeinfo is stored in sqlite database. Whenever any
> node in a commit has mergeinfo it is stored as multiple merge
> range+path records. That is full text of 'svn:mergeinfo' is divided
> in to multiple merges and stored as individual record.
>
> Let us say you have '/trunk:12' on '/fb', It puts one record
> ('/trunk', '/fb', 11, 12, 1)
>
> Now next commit has '/trunk:12,18' on '/fb', It puts two records
> ('/trunk', '/fb', 11, 12, 1) ('/trunk', '/fb', 17, 18, 1) one for
> each merge range+path record.
>
> Now next commit has '/trunk:12-13,18' on '/fb', It puts two records
> ('/trunk', '/fb', 11, 13, 1) ('/trunk', '/fb', 17, 18, 1) one for
> each merge range+path record.

Thanks.

I'm looking at the table definitions in mergeinfo-sqlite-index.c and
trying map the above to what I see there.  Let's take your first commit:

   > Let us say you have '/trunk:12' on '/fb', It puts one record
   > ('/trunk', '/fb', 11, 12, 1)

That produces a row like this in mergeinfo_changed:

   revision == 50  /* revision in which r12 was merged from trunk to fb */
   path == '/fb'

And a row like this in 'mergeinfo':

   revision == 50
   mergedfrom == '/trunk'
   mergedto == '/fb'
   mergedrevstart == 11
   mergedrevend == 12
   inheritable == 1

Is that right so far?

Now when we go to the next commit...

   > Now next commit has '/trunk:12,18' on '/fb', It puts two records
   > ('/trunk', '/fb', 11, 12, 1) ('/trunk', '/fb', 17, 18, 1) one for
   > each merge range+path record.

That produces a row like this in mergeinfo_changed:

   revision == 56  /* revision in which r18 was merged from trunk to fb */
   path == '/fb'

And a row like this in 'mergeinfo':

   revision == 56
   mergedfrom == '/trunk'
   mergedto == '/fb'
   mergedrevstart == 17
   mergedrevend == 18
   inheritable == 1

Now, my question is, do we also put in a new row for the r12
mergeinfo?  That is, do we add a new row saying

    (56, '/trunk', '/fb', 11, 12, 1)

even though we already have a row from before that says

    (50, '/trunk', '/fb', 11, 12, 1)

?

Okay, moving on to the third commit:

   > Now next commit has '/trunk:12-13,18' on '/fb', It puts two records
   > ('/trunk', '/fb', 11, 13, 1) ('/trunk', '/fb', 17, 18, 1) one for
   > each merge range+path record.

(Let's say that happens in r60.)  A similar questions applies: when we
add the record...

   (60, '/trunk', '/fb', 11, 13, 1)

...do we also *remove* any records like this:

   (..., '/trunk', '/fb', 11, 12, 1)

since they are sort of subsets of the new record?  Or do we let the
old records remain?  I realize that doing such removals might be
computationally intensive, so I'm really asking two questions: do we
remove such subset records, and if not, do we at least *wish* we could
remove them?

>>> Take the least revision(commit revision)?, No What if we reverted r12 from
>>> '/trunk' to '/fb' on r51, Remember we don't record reverse merges and
>>> merge back the same on r52.
>
>>I don't understand what the phrase "reverted r12 from '/trunk' to
>>'/fb' on r51" means.  Do you mean remove r12 from /trunk and put it
>>into /fb, all in one commit?  (But it is already in /fb...)
>
> Sorry for being unclear, I meant 'reverse merge r12 on '/fb' from
> '/trunk' and commit in r51, So this would remove 'r12' from /fb's
> mergeinfo. So sqlite record won't have 'r12' anymore. Now again you
> merge r12 to '/fb' from '/trunk', Now sqlite will have r12.

Thanks, now I understand.

>>Could you show the precise structure of the proposed new table?
>
> Current schema of 'mergeinfo_changed'
> -------------------------------------
> CREATE TABLE mergeinfo_changed (revision INTEGER NOT NULL,
>                                 path TEXT NOT NULL);
>
> revision = subsequent commit to merge.
> path = merge target.
>
> My proposed schema
> ------------------------------
> CREATE TABLE mergeinfo_changed (revision INTEGER NOT NULL,
> mergedfrom TEXT NOT NULL, mergedto TEXT NOT NULL, mergedrevstart
> INTEGER NOT NULL, mergedrevend INTEGER NOT NULL, inheritable INTEGER
> NOT NULL);
>
> *exactly same* as that of the only other table in our sqlite db 'mergeinfo'.
>
> I think coulumn names are more obvious here.

*nod*  Okay, understood.

> The difference is in the way we are going to store the records in
> 'mergeinfo_changed'.
>
> 'mergeinfo' table as ususal will have the records for all the merges
> on a node on every single merge+commit irrespective of what exactly
> been merged in this commit.(Remember 3 records for r12 in my
> original mail)

Thanks, that helps clarify things for me.

Let me test my understanding.  The way to find out (using the current
code) what exactly got merged in, say, r60 is to look in
mergeinfo_changed and select on rev==60.  Suppose we get these
results:

   (60, '/some/path')
   (60, '/some/other/path')
   (60, '/yet/another/path')

Okay, let's start with '/some/path'.  We search backwards in that
table for the previous change to '/some/path'.  Say we find this:

   (56, '/some/path')

Great.  Now go to the mergeinfo table, and select every row where

   (rev == 60) && (mergedto == '/some/path')

Then get all the mergeinfo for 

   (rev == 56) && (mergedto == '/some/path')

Compute the "difference" between the two mergeinfo sets, and that is
what was merged to '/some/path' in r60.  Repeat for '/some/other/path'
and '/yet/another/path', of course.

Is my understanding even close?  This is all guessing, based on the
table schemas and on thinking about the problem.  I might be
completely wrong, please don't hesitate to correct me :-).  If I am
wrong, then I don't understand the way those two tables are used
together in today's code.

> 'mergeinfo_changed' table will only record the merge revision ranges
> pertaining to a given commit, that way we can precisely identify the
> 'commit_revs'(a.k.a reflective merge revision rZ in my origial mail)
> for a merge.

This sounds sane to me, but I think I need to hear your response to
the above before I can be sure.

Thanks for your patience while I learn this code, Kamesh.

-Karl

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@subversion.tigris.org
For additional commands, e-mail: dev-help@subversion.tigris.org

RE: Input needed in solving issue 2897.

Posted by Kamesh Jayachandran <ka...@collab.net>.
Hi Karl,

>> Actual behaviour of last merge:
>> Currently this behaviour is broken (issue 2897 just deals with it.),
>> it merges only rS and rT alone (that is it negates 'rX:Y' from rX:HEAD
>> and gives rS and rT, remember rX<rP, rQ, rR <rY)

>In other words, because rP, rQ, and rR fall in between rX and rY, they
>are omitted as undesirable purely on numeric grounds, even though they
>were on /fb while the other stuff in rX:Y was on trunk?

Yes.

>> What to fix: We should fix this negation logic to negate the 'commit
>> rev rZ' rather than what got merged(rX:Y).

>I didn't understand that sentence, sorry.

I meant in reflective merge scenario like this we should 'negate' the commit rev resulting from the follow-up commit to merge i.e rZ.

>My understanding is that in rZ, the svn:mergeinfo on /fb would be
>changed to note all the /trunk revisions in the range rX:Y.  Call that
>set {R}.  When we merge /fb back to /trunk, nothing from {R} should be
>included.  But rP, rQ, and rR are not in {R}, since they were
>committed directly on /fb, and trunk has never seen them.

>So my question is, immediately after rZ, does the svn:mergeinfo on /fb
>accurately reflect exactly what has been merged in from elsewhere?  If
>not, is there a good reason why not?


Good question!. Mergeinfo on '/fb' is accurate only with respect to '/fb'. When someone wants to know what has been merged from '/trunk' to '/fb', he would get the correct answer say rX:Y. One should use this mergerange(rX:Y) to avoid repeated merge only if the merge is from '/trunk' not '/fb'. To avoid repeat merge from '/fb' one should use rZ.


Mergeinfo === 'merge source' + 'merge range' doing a math only on 'merge range'(ignoring the merge source) is like comparing apples and oranges.


>> In this particular case r12 merge would appear 3 times, which record
>> to consider to decide when the merge has occured?

>Why does r12 appear 3 times?  It was only merged once.

That is the way mergeinfo is stored in sqlite database. Whenever any node in a commit has mergeinfo it is stored as multiple merge range+path records. That is full text of 'svn:mergeinfo' is divided in to multiple merges and stored as individual record.

Let us say you have '/trunk:12' on '/fb', It puts one record ('/trunk', '/fb', 11, 12, 1)
Now next commit has '/trunk:12,18' on '/fb', It puts two records ('/trunk', '/fb', 11, 12, 1) ('/trunk', '/fb', 17, 18, 1) one for each merge range+path record.

Now next commit has '/trunk:12-13,18' on '/fb', It puts two records ('/trunk', '/fb', 11, 13, 1) ('/trunk', '/fb', 17, 18, 1) one for each merge range+path record.

>> Take the least revision(commit revision)?, No What if we reverted r12 from
>> '/trunk' to '/fb' on r51, Remember we don't record reverse merges and
>> merge back the same on r52.

>I don't understand what the phrase "reverted r12 from '/trunk' to
>'/fb' on r51" means.  Do you mean remove r12 from /trunk and put it
>into /fb, all in one commit?  (But it is already in /fb...)

Sorry for being unclear, I meant 'reverse merge r12 on '/fb' from '/trunk' and commit in r51, So this would remove 'r12' from /fb's mergeinfo. So sqlite record won't have 'r12' anymore. Now again you merge r12 to '/fb' from '/trunk', Now sqlite will have r12.




>Could you show the precise structure of the proposed new table?

Current schema of 'mergeinfo_changed'
-------------------------------------
CREATE TABLE mergeinfo_changed (revision INTEGER NOT NULL, path TEXT NOT NULL);

revision = subsequent commit to merge.
path = merge target.

My proposed schema
------------------------------
CREATE TABLE mergeinfo_changed (revision INTEGER NOT NULL, mergedfrom TEXT NOT NULL, mergedto TEXT NOT NULL, mergedrevstart INTEGER NOT NULL, mergedrevend INTEGER NOT NULL, inheritable INTEGER NOT NULL);

*exactly same* as that of the only other table in our sqlite db 'mergeinfo'.

I think coulumn names are more obvious here.

The difference is in the way we are going to store the records in 'mergeinfo_changed'.
'mergeinfo' table as ususal will have the records for all the merges on a node on every single merge+commit irrespective of what exactly been merged in this commit.(Remember 3 records for r12 in my original mail).

'mergeinfo_changed' table will only record the merge revision ranges pertaining to a given commit, that way we can precisely identify the 'commit_revs'(a.k.a reflective merge revision rZ in my origial mail) for a merge.

Thanks for your review.

With regards
Kamesh Jayachandran

Re: Input needed in solving issue 2897.

Posted by Karl Fogel <kf...@red-bean.com>.
Kamesh Jayachandran <ka...@collab.net> writes:
> Summary: Filter 'Target Reflective Merges on Merge Source', while
> merging to Target from merge source.
>
> Consider the following situation
> * Create feature branch '/fb' from '/trunk' (results in rX)
> * Do some commits on '/fb'  (rP, rQ, rR)
> * merge '/trunk' to '/fb'(merge few revs rX:Y(current HEAD), commit
> results in rZ).
> * Do some more commits on '/fb'  (rS, rT)
> * merge '/fb' back to '/trunk'.
>
> Expected behaviour of last merge:
> merge *only* 'rP, rQ, rR, rS, rT' from '/fb' to 'trunk', ie it should
> exclude rZ as it is reflective merges from '/trunk' itself.

Clearly, this would be the ideal behavior, yes! :-)

> Actual behaviour of last merge:
> Currently this behaviour is broken (issue 2897 just deals with it.),
> it merges only rS and rT alone (that is it negates 'rX:Y' from rX:HEAD
> and gives rS and rT, remember rX<rP, rQ, rR <rY)

In other words, because rP, rQ, and rR fall in between rX and rY, they
are omitted as undesirable purely on numeric grounds, even though they
were on /fb while the other stuff in rX:Y was on trunk?

> What to fix: We should fix this negation logic to negate the 'commit
> rev rZ' rather than what got merged(rX:Y).

I didn't understand that sentence, sorry.

My understanding is that in rZ, the svn:mergeinfo on /fb would be
changed to note all the /trunk revisions in the range rX:Y.  Call that
set {R}.  When we merge /fb back to /trunk, nothing from {R} should be
included.  But rP, rQ, and rR are not in {R}, since they were
committed directly on /fb, and trunk has never seen them.

So my question is, immediately after rZ, does the svn:mergeinfo on /fb
accurately reflect exactly what has been merged in from elsewhere?  If
not, is there a good reason why not?

> We discussed few possible fixes in issue 2897 and finally we came up
> with the following finding/proposal.
>
> Current limitation in backend mergeinfo storage:
> ----------------------------------------------------------------------
> We have sqlite table 'mergeinfo' which has the tokenized merge
> revisions for each path
> for each 'merge+commit'. This information is ambiguous, consider the
> following case.
>
> In r50 you merged -r12 from '/trunk' to '/fb'.(Puts one record on
> mergeinfo for
> this path.)
> In r53 you merged -r15 from '/trunk' to '/fb'.(Puts two records on
> mergeinfo for
> this path.)
> In r56 you merged -r18 from '/trunk' to '/fb'.(Puts three records on
> mergeinfo
> for this path.)
>
> In this particular case r12 merge would appear 3 times, which record
> to consider to decide when the merge has occured?

Why does r12 appear 3 times?  It was only merged once.

(Please remember that I'm just coming at this fresh, so I may not have
certain assumptions / understandings that you have.)

> Take the least revision(commit revision)?, No What if we reverted r12 from
> '/trunk' to '/fb' on r51, Remember we don't record reverse merges and
> merge back the same on r52.

I don't understand what the phrase "reverted r12 from '/trunk' to
'/fb' on r51" means.  Do you mean remove r12 from /trunk and put it
into /fb, all in one commit?  (But it is already in /fb...)

> Proposal to fix this issue
> --------------------------------
> Change the table structure of 'mergeinfo_changed'(today it is 2 coulum
> table of commit_rev, merge_target) almost same as that of mergeinfo
> and
> record the merge range that is getting added(as we are not recording
> the revert independently !) in this commit. After all
> mergeinfo_changed' means 'only changes'.

Could you show the precise structure of the proposed new table?  

It would also help us newcomers if you would use longer sentences,
with more context, and fewer back-references (for example, I have no
idea what "the revert" refers to in the above paragraph).  I'm having
a lot of trouble understanding exactly what's being proposed here.  I
think this is partly because there is much more knowledge in your head
than in mine.  You may have to explain things that are obvious to you,
because they are not obvious to others who haven't been deep into the
merge-tracking code :-).  Thanks.

> 2)We need a ra API 'svn_ra_get_merge_commit_revs(apr_array_header_t
> **commit_rev_list, const char* mergefrom, const char* mergeto,
> apr_array_header_t *merge_rangelist)
>
> In our context 'mergefrom' -> '/trunk' (target)
> 'mergeto' -> '/fb'(source)
>
> This API will give us 'commit_rev_list' a list of reflective revisions on
> 'mergeto' from 'mergefrom' for the merge_rangelist.
>
> 3)We can use this 'svn_ra_get_merge_commit_revs' in libsvn_client to
> negate the commit revs.
>
> Any thoughts are welcome!

I think I'll understand the rest of this proposal when I understand
the answers to my previous questions.

Thanks,
-Karl

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@subversion.tigris.org
For additional commands, e-mail: dev-help@subversion.tigris.org