Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

git rebase fails with Unknown exit code (128) from command: git-merge-recursive

Consider the following scenario: - upstream repository with 2500 is stored in SVN - git user A imports the repository into git and commits 1 patch - git user B imports the repository into git and commits 1 patch - git user A wants to merge the patch from git user B

In this case, if user A uses git merge, then the git history will be polluted with the common svn commits (i.e. instead of 2502 commits, history will contain 2501+2501 = 5002 commits!)

If user A uses git rebase, then git history will be correct (2502 commits). This works fine in this simple scenario, but if user A and user B had not 1 but 1000 commits each then a strange complication arises: git rebase -Xours fails with the following message:

First, rewinding head to replay your work on top of it...
fatal: Could not parse object '98d7cd83de321e737b22240752cd178622d29406^'
Unknown exit code (128) from command: git-merge-recursive 98d7cd83de321e737b22240752cd178622d29406^ -- HEAD 98d7cd83de321e737b22240752cd178622d29406

You can e.g. reproduce this issue using the following github repositories:

git clone https://github.com/opentk/opentk
cd opentk
git remote add mono https://github.com/mono/opentk
git fetch mono
git checkout -b integrate
git rebase -Xours mono/rodo-consolidate-opentk

Does anyone know why this happens? Any ideas how to resolve this issue?

like image 303
The Fiddler Avatar asked Feb 21 '14 07:02

The Fiddler


People also ask

How to fix Git REBASE when merge fails?

It is possible that a merge failure will prevent this process from being completely automatic. You will have to resolve any such merge failure and run git rebase --continue. Another option is to bypass the commit that caused the merge failure with git rebase --skip.

How to avoid the merge commit in Git?

One way to avoid the merge commit is to use git rebase instead. git rebase is a very powerful feature. That being said, it is risky as well if it is not used in the right way. git rebase alters the commit history, so use it with care.

Is Git REBASE the same behavior as Git backend exit code?

From a comment in the source code of builtin/merge.c: "The backend exits with 1 when conflicts are left to be resolved, with 2 when it does not handle the given merge at all." is git rebase the same behavior? In short, no. You're going to see exit code 1 for errors, and 0 for success.

How do I remove a commit from a git repository?

One way is to open the files in a text editor and delete the parts of the code you do not want. Then use git add <file name> followed by git rebase --continue. You can skip over the conflicted commit by entering git rebase --skip, stop rebasing by running git rebase --abort in your console.


3 Answers

seems this is an issue that rarely needs to be explored. I just stumbled in this problem, and as suggested in this email, the problem really seems to be because you are trying to use a recursive strategy to a commit without parents (the master branch of another repository, for example).

In my scenario I was joining two git repositories, rebasing the master of one in the master of the other. In your case, converting and merging svn repos, so I guess this is pretty much the same scenario.

In my scenario, again, I was using strategy=recursive and strategy-option=renormalize, to ignore annoying line endings conflicts. It worked very good, although at a given time I had to issue an additional commit in the middle of the history just for the sake of discarding the line endings from committed files (which keeps as 'modified' until you commit them).

Here is my approach to overcome the issue:

  1. git rebase <branch> --strategy=recursive --strategy-option=ours
First, rewinding head to replay your work on top of it...
fatal: Could not parse object '67fceed5a80ff78ac6f9a437620323131c88cd51^'
Unknown exit code (128) from command: git-merge-recursive 67fceed5a80ff78ac6f9a437620323131c88cd51^ -- HEAD 67fceed5a80ff78ac6f9a437620323131c88cd51
  1. git cherry-pick 67fceed5a80ff78ac6f9a437620323131c88cd51 (notice, it is the hash displayed in the error message!)

  2. Resolve the conflicts (if any)

  3. git rebase --continue

From the second commit onwards, the recursive strategy will work as they all have parent (the one you just cherry-picked).

You will have a few conflicts and some needed commits to normalize codes once in a while, but you will no longer be pestered by a lot of useless line ending conflicts that just serve to confuse and make bugs in the merged code.

I consider this a bug as the recursive strategy might just assume if no parent, an 'empty' commit/working tree should be used as base for the comparisons (so everything in the commit are actual additions and no modifications).

like image 197
Avenger Avatar answered Oct 12 '22 23:10

Avenger


I had a similar issue with this error and I gave up rebase, and instead used cherry-pick to pick the changes, and it worked fine.

like image 44
ryenus Avatar answered Oct 12 '22 22:10

ryenus


One of the possible solutions is to use git gc --aggressive to remove all the links to the old commits. It helped for me.

like image 1
Dmitry Polushkin Avatar answered Oct 12 '22 21:10

Dmitry Polushkin