1#!/bin/sh
23
USAGE='[--mixed | --soft | --hard] [<commit-ish>]'
4. git-sh-setup
56
tmp=${GIT_DIR}/reset.$$
7trap 'rm -f $tmp-*' 0 1 2 3 15
89
update=
10reset_type=--mixed
11case "$1" in
12--mixed | --soft | --hard)
13reset_type="$1"
14shift
15;;
16-*)
17usage ;;
18esac
1920
case $# in
210) rev=HEAD ;;
221) rev=$(git-rev-parse --verify "$1") || exit ;;
23*) usage ;;
24esac
25rev=$(git-rev-parse --verify $rev^0) || exit
2627
# We need to remember the set of paths that _could_ be left
28# behind before a hard reset, so that we can remove them.
29if test "$reset_type" = "--hard"
30then
31update=-u
32fi
3334
# Soft reset does not touch the index file nor the working tree
35# at all, but requires them in a good order. Other resets reset
36# the index file to the tree object we are switching to.
37if test "$reset_type" = "--soft"
38then
39if test -f "$GIT_DIR/MERGE_HEAD" ||
40test "" != "$(git-ls-files --unmerged)"
41then
42die "Cannot do a soft reset in the middle of a merge."
43fi
44else
45git-read-tree --reset $update "$rev" || exit
46fi
4748
# Any resets update HEAD to the head being switched to.
49if orig=$(git-rev-parse --verify HEAD 2>/dev/null)
50then
51echo "$orig" >"$GIT_DIR/ORIG_HEAD"
52else
53rm -f "$GIT_DIR/ORIG_HEAD"
54fi
55git-update-ref -m "reset $reset_type $@" HEAD "$rev"
5657
case "$reset_type" in
58--hard )
59;; # Nothing else to do
60--soft )
61;; # Nothing else to do
62--mixed )
63# Report what has not been updated.
64git-update-index --refresh
65;;
66esac
6768
rm -f "$GIT_DIR/MERGE_HEAD" "$GIT_DIR/rr-cache/MERGE_RR" "$GIT_DIR/SQUASH_MSG"