git/list[1] front-page[2] threads[3] people[4] search[5] about
 

Re: keeping track of where a patch begins

From
Junio C Hamano <gitster@pobox.com>
Date
Oct 21, 2009, 20:03 UTC
Message-ID
<7veiow4iqc.fsf@alter.siamese.dyndns.org>
In-Reply-To
<alpine.LFD.2.00.0910211402490.21460@xanadu.home>
Nicolas Pitre <nico@fluxnic.net> writes:
Show 14 quoted lines
> On Wed, 21 Oct 2009, E R wrote:
>
>> What solutions have you come up with to either to catch or prevent
>> this from happening? It is possible to determine what node a branch
>> started from?
>
> This can be determined by looking at the gitk output.
>
> Also 'git merge-base' can give you that node, given the main branch and 
> the topic branch.  See documentation about git-merge-base.
>
> Then if you need to move a branch to another starting node, then 'git 
> rebase' is what you need (again the git-rebase documentation is pretty 
> detailed).

That is a correct way to diagnose the mistake and recover from it, but unfortunately it is a rather weak tool to identify the mistake in the first place.

A branch in git, as Randal often used to say on #git, is an illusion---it points only at the top and does not identify the bottom.

But it does _not_ have to stay that way at the Porcelain level.

Here is a rough sketch of one possible solution. It is not fully thought out; the basic idea is probably sound but I did not try to exhaustively cover changes to various tools that are necessary to maintain the invariants this scheme requires.

 (0) Define a way to identify the bottom of a branch.  One way to do this
     is by an extra ref (e.g. refs/branchpoints/frotz).  Then the commits
     between refs/branchpoints/frotz..refs/heads/frotz identifies the
     commits on the branch.  None of the additional restrictions below
     applies when the branch does not have such bottom defined (i.e.
     created by the current git without this extension).
 (1) At branch creation, the branchpoint is noted.  E.g.
     $ git branch frotz master~4
     would internally become
     $ git update-ref refs/heads/frotz master~4
     $ git update-ref refs/branchpoints/frotz master~4
     You would also need to cover "checkout -b".
 (2) You can grow the branch naturally with "commit", "am" and "merge".
     The bottom of the branch does not have to move with these operations.
 (3) Operations that alter histories, e.g. "commit --amend", "rebase",
     "reset", while on a branch that records its bottom need to be taught
     to pay attention to not break its bottom.  Paying attention needs to
     take different forms depending on the operation; some probably will
     forbid the operation while others would automatically adjust the
     bottom.
     Examples (not exhaustive):
 (3-a) "branch -f frotz $commit"
     This moves the tip of the branch.  Unless $commit is already some
     part of the existing frotz branch, we should probably forbid it for
     simplicity, when a bottom is defined for the branch.
     We could later loosen the rule so that $commit is only required to be
     a descendant of existing bottom of the branch to support a workflow
     like this:
     $ git checkout -b frotz master~4 ;# records branchpoint
     $ edit; git add; git commit; ... ;# builds history
     $ git checkout HEAD^             ;# go back somewhere on frotz
     $ edit; git add; git commit; ... ;# builds an alternate history
     $ git show-branch HEAD frotz     ;# check progress
     $ git diff frotz HEAD            ;# is this one better?
     $ git branch -f frotz            ;# I prefer this new one better
 (3-b) "reset $commit" (with or without --hard/--soft/--mixed)
     This is similar to (3-a) above; $commit has to be a descendant of
     existing bottom.
 (3-c) "commit --amend"
     $ git checkout -b frotz master~4 ;# records branchpoint
     $ git commit --amend             ;# rewrite the bottom???
     would probably be a mistake, as the end result would make the frotz
     branch forked from master~5 with the first commit on the branch a
     fix-up to what is already in the master branch.
     However, this is a valid way to work:
     $ git checkout -b frotz master~4 ;# records branchpoint
     $ edit; git add; git commit      ;# builds history
     $ git commit --amend             ;# fix the tip
     and it does not have to do anything to the bottom.
 (3-d) "rebase"
     $ git checkout -b frotz master~4 ;# records branchpoint
     $ edit; git add; git commit; ... ;# builds history
     $ git rebase --onto master       ;# transplants the branch
     would make the "onto" commit the new bottom.  Another interesting
     thing to note is that we do not have to compute which commits to
     transplant with merge-base with the "onto" commit, because we know
     the bottom commit of the branch.
 (4) Operations that browse histories, e.g. "log", "show-branch", while on
     a branch that records its bottom can be taught to pay attention to
     the bottom.  For example, it is conceivable that
     $ git log
     $ git log -- Documentation/
     without an explicit branch name that fell back to the default HEAD
     while on branch "frotz" might be better run with an implicit bottom
     ^refs/branchpoint/frotz.

We probably could kill the other bird in the nearby thread that wants to add a description to a branch, if this scheme is fully implemented (no, I am not going to start coding right away, as this message is just a sketch of what we _could_ do), As we will fully know in what operations we need to update the branchpoint ref, we could make the refs/branchpoints/frotz an annotated tag, and store the description for the branch in that tag. Whenever we need to adjust the branchpoint, we update it while carrying the branch description message over to the new tag object.

Previous: Nicolas PitreNext: Nicolas Pitre
Message 3 of 8 in “keeping track of where a patch begins”
  1. E ROct 21, 2009
  2. Nicolas PitreOct 21, 2009
  3. Junio C HamanoOct 21, 2009
  4. Nicolas PitreOct 21, 2009
  5. Thomas RastOct 22, 2009
  6. Pascal ObryOct 30, 2009
  7. Thomas RastOct 30, 2009
  8. Jeff KingOct 26, 2009

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.