Hi Yves, On Sat, 13 Aug 2022, demerphq wrote: > I keep finding myself using interactive rebase to try to find the > earliest place in a change sequence that a given commit can be placed > without conflicting with any other patch. I find myself doing that a lot, too. So much so that I wrote shell code to do that for me. The essential idea is to use the diff hunk header of the hunk that I want to stage and transmogrify it into the `-L <start>,<end>:<path>` parameter of `git log` (and yes, the `sed` call to transmogrify that is a bit hard to read). The relevant part of the code looks like this: -- snip -- sh_quote () { for arg do echo "'$(echo "$arg" | sed "s/'/'\\''/g")'" done } staged_log () { # [--upstream=<ref> | -u <ref>] upstream=not\ set while case "$1" in --upstream) shift; upstream="$1";; --upstream=*) upstream="${1#*=}";; -u) shift; upstream="$1";; -*) die "Unknown option: $1";; *) break;; esac; do shift; done test not\ set != "$upstream" || upstream="$(git rev-parse @{upstream} 2>/dev/null)" # look beyond upstream if identical to HEAD test -z "$upstream" || test 0 != $(git rev-list --count $upstream..) || upstream= diff="$(git diff --cached -U1)" cached_diff="$diff" test -n "$diff" || diff="$(git diff -U1)" test -n "$diff" || die "No changes" args="$(echo "$diff" | sed -ne '/^--- a\//{s/^-* a\/\(.*\)/'\''\1'\''/;x}' -e \ '/^@@ -/{s/^@@ -\([^, ]*\),\([^ ]*\).*/-L \1,+\2/;s/^@@ -\([^,]*\) .*/-L \1,+1/;G;s/\n/:/g;p}' | tr '\n' ' ') ${upstream:+$upstream..} $(sh_quote "$@")" eval "git log $args" revs="$(eval "git log --pretty=%H --no-patch $args")" case "$revs" in *[!0-9a-z]*) ;; # multiple revs '') # not a single rev test -z "$upstream" || staged_log -u '' ;; ?*) printf "Commit (yes/no/edit)? " read line case "$line" in [Yy]*) git commit --fixup "$revs" $(test -n "$cached_diff" || echo "-a");; [Ee]*) git commit --fixup "$revs" $(test -n "$cached_diff" || echo "-a") -se;; esac ;; esac } -- snap -- Unfortunately, the `-L <...>` code currently works reliably only for a single hunk, if I use multiple hunks, I sometimes run into assertions. To help with that, the shell code looks at the staged hunk(s), if any. Only if no changes are staged, it falls back to the unstaged diff. Ciao, Dscho