When rebasing two commits, A and B, if A ends up being a noop (because the change already exists on the destination branch) and B encounters a conflict, the resulting rebase state is not abortable if the destination was phase=public hg init foo cd foo hg book master touch a && hg add a && hg commit -m a hg book foo echo x > a && hg commit -m x echo y > b && hg add b && hg commit -m y hg up master echo x > a echo z > b && hg add b && hg commit -m z hg phase -p -r master hg rebase -d master -b foo hg rebase --abort Output: abort: can't abort rebase due to immutable changesets 396e50970b78 (see hg help phases for details) This can also happen when using --collapse and a conflict happens, but I don't have repro steps for it.
Bisect blames to: changeset: 16280:0806823370d8 branch: stable parent: 16278:900eee0778d1 user: Matt Mackall <mpm@selenic.com> date: Thu Mar 22 17:47:00 2012 -0500 summary: rebase: properly calculate descendant set when aborting (issue3332) We are also seeing this repro when doing something like: A->B->C->master \ X if 'hg rebase -d A -s X' encounters a conflict, it leaves 'B:-2' in the rebasestate. When rebase --abort is run, -2 resolves to C which is public, and therefore the abort fails.
Fixed by http://selenic.com/repo/hg/rev/eab2ff59481e Matt Mackall <mpm@selenic.com> rebase: continue abort without strip for immutable csets (issue3997) This causes us to simply discard the rebase state. (please test the fix)