]>
Commit | Line | Data |
---|---|---|
40d8cfe4 | 1 | #!/bin/sh |
45d197a4 | 2 | |
806f36d4 FK |
3 | USAGE='[--mixed | --soft | --hard] [<commit-ish>]' |
4 | . git-sh-setup | |
2f9d685c | 5 | |
6ff0b1c5 | 6 | tmp=${GIT_DIR}/reset.$$ |
45d197a4 JH |
7 | trap 'rm -f $tmp-*' 0 1 2 3 15 |
8 | ||
9 | reset_type=--mixed | |
10 | case "$1" in | |
11 | --mixed | --soft | --hard) | |
12 | reset_type="$1" | |
13 | shift | |
14 | ;; | |
2f9d685c CS |
15 | -*) |
16 | usage ;; | |
45d197a4 JH |
17 | esac |
18 | ||
2ad77e67 JH |
19 | rev=$(git-rev-parse --verify --default HEAD "$@") || exit |
20 | rev=$(git-rev-parse --verify $rev^0) || exit | |
45d197a4 JH |
21 | |
22 | # We need to remember the set of paths that _could_ be left | |
23 | # behind before a hard reset, so that we can remove them. | |
24 | if test "$reset_type" = "--hard" | |
25 | then | |
26 | { | |
27 | git-ls-files --stage -z | |
28 | git-rev-parse --verify HEAD 2>/dev/null && | |
29 | git-ls-tree -r -z HEAD | |
30 | } | perl -e ' | |
31 | use strict; | |
32 | my %seen; | |
33 | $/ = "\0"; | |
34 | while (<>) { | |
35 | chomp; | |
36 | my ($info, $path) = split(/\t/, $_); | |
37 | next if ($info =~ / tree /); | |
38 | if (!$seen{$path}) { | |
39 | $seen{$path} = 1; | |
40 | print "$path\0"; | |
41 | } | |
42 | } | |
43 | ' >$tmp-exists | |
44 | fi | |
45 | ||
46 | # Soft reset does not touch the index file nor the working tree | |
47 | # at all, but requires them in a good order. Other resets reset | |
48 | # the index file to the tree object we are switching to. | |
49 | if test "$reset_type" = "--soft" | |
50 | then | |
51 | if test -f "$GIT_DIR/MERGE_HEAD" || | |
52 | test "" != "$(git-ls-files --unmerged)" | |
32173e69 | 53 | then |
45d197a4 | 54 | die "Cannot do a soft reset in the middle of a merge." |
32173e69 | 55 | fi |
45d197a4 JH |
56 | else |
57 | git-read-tree --reset "$rev" || exit | |
58 | fi | |
59 | ||
60 | # Any resets update HEAD to the head being switched to. | |
61 | if orig=$(git-rev-parse --verify HEAD 2>/dev/null) | |
62 | then | |
63 | echo "$orig" >"$GIT_DIR/ORIG_HEAD" | |
64 | else | |
65 | rm -f "$GIT_DIR/ORIG_HEAD" | |
66 | fi | |
bf7960eb | 67 | git-update-ref HEAD "$rev" |
45d197a4 JH |
68 | |
69 | case "$reset_type" in | |
70 | --hard ) | |
71 | # Hard reset matches the working tree to that of the tree | |
72 | # being switched to. | |
215a7ad1 | 73 | git-checkout-index -f -u -q -a |
45d197a4 JH |
74 | git-ls-files --cached -z | |
75 | perl -e ' | |
76 | use strict; | |
77 | my (%keep, $fh); | |
78 | $/ = "\0"; | |
79 | while (<STDIN>) { | |
80 | chomp; | |
81 | $keep{$_} = 1; | |
82 | } | |
83 | open $fh, "<", $ARGV[0] | |
84 | or die "cannot open $ARGV[0]"; | |
85 | while (<$fh>) { | |
86 | chomp; | |
87 | if (! exists $keep{$_}) { | |
c3bc895c JH |
88 | # it is ok if this fails -- it may already |
89 | # have been culled by checkout-index. | |
90 | unlink $_; | |
772d8a3b SP |
91 | while (s|/[^/]*$||) { |
92 | rmdir($_) or last; | |
93 | } | |
45d197a4 JH |
94 | } |
95 | } | |
c3bc895c | 96 | ' $tmp-exists |
45d197a4 JH |
97 | ;; |
98 | --soft ) | |
99 | ;; # Nothing else to do | |
100 | --mixed ) | |
101 | # Report what has not been updated. | |
215a7ad1 | 102 | git-update-index --refresh |
45d197a4 JH |
103 | ;; |
104 | esac | |
105 | ||
8389b52b | 106 | rm -f "$GIT_DIR/MERGE_HEAD" "$GIT_DIR/rr-cache/MERGE_RR" |