#!/usr/bin/env bash
#
# Undo a commit or a series of commits
# Copyright (c) Matt Porter, 2005
# Copyright (c) Petr Baudis, 2005
#
# Takes a commit ID which is the earliest commit to be
# removed from the repository. If no parameter is passed,
# it uncommits the latest commit (HEAD).

. ${COGITO_LIB}cg-Xlib

base=$(commit-id) || exit 1

commit=$(commit-id "$1") || exit 1
git-rev-list $base | grep -q $commit || \
	die "$commit: not an ancestor of HEAD"

parent=$(parent-id "$commit") || exit 1
[ "$parent" ] || die "cannot rewind behind the initial commit"


# XXX: Code duplication with cg-merge's fast-forward

echo "Rewinding $base (HEAD) -> $parent" >&2

patchfile=$(mktemp -t gituncommit.XXXXXX)
cg-diff >$patchfile
[ -s "$patchfile" ] &&
	echo "Warning: uncommitted local changes, trying to bring them backwards" >&2

git-read-tree -m "$parent" || die "$parent: bad commit"
echo "$parent" > $_git/HEAD

# Kill gone files
git-diff-tree -z -r $base $parent | grep -z '^-' | xargs -0 bash -c '
	while [ "$1" ]; do
		rm -- "$(echo "$1" | cut -f 4-)"
		shift
	done
' padding
git-checkout-cache -f -a

grep -v '^[^ @+-]' $patchfile | cg-patch
rm $patchfile

git-update-cache --refresh
