1#!bash
2#
3# bash/zsh completion support for core Git.
4#
5# Copyright (C) 2006,2007 Shawn O. Pearce <spearce@spearce.org>
6# Conceptually based on gitcompletion (http://gitweb.hawaga.org.uk/).
7# Distributed under the GNU General Public License, version 2.0.
8#
9# The contained completion routines provide support for completing:
10#
11# *) local and remote branch names
12# *) local and remote tag names
13# *) .git/remotes file names
14# *) git 'subcommands'
15# *) tree paths within 'ref:path/to/file' expressions
16# *) common --long-options
17#
18# To use these routines:
19#
20# 1) Copy this file to somewhere (e.g. ~/.git-completion.sh).
21# 2) Add the following line to your .bashrc/.zshrc:
22# source ~/.git-completion.sh
23#
24# 3) Consider changing your PS1 to also show the current branch:
25# Bash: PS1='[\u@\h \W$(__git_ps1 " (%s)")]\$ '
26# ZSH: PS1='[%n@%m %c$(__git_ps1 " (%s)")]\$ '
27#
28# The argument to __git_ps1 will be displayed only if you
29# are currently in a git repository. The %s token will be
30# the name of the current branch.
31#
32# In addition, if you set GIT_PS1_SHOWDIRTYSTATE to a nonempty
33# value, unstaged (*) and staged (+) changes will be shown next
34# to the branch name. You can configure this per-repository
35# with the bash.showDirtyState variable, which defaults to true
36# once GIT_PS1_SHOWDIRTYSTATE is enabled.
37#
38# You can also see if currently something is stashed, by setting
39# GIT_PS1_SHOWSTASHSTATE to a nonempty value. If something is stashed,
40# then a '$' will be shown next to the branch name.
41#
42# If you would like to see if there're untracked files, then you can
43# set GIT_PS1_SHOWUNTRACKEDFILES to a nonempty value. If there're
44# untracked files, then a '%' will be shown next to the branch name.
45#
46# If you would like to see the difference between HEAD and its
47# upstream, set GIT_PS1_SHOWUPSTREAM="auto". A "<" indicates
48# you are behind, ">" indicates you are ahead, and "<>"
49# indicates you have diverged. You can further control
50# behaviour by setting GIT_PS1_SHOWUPSTREAM to a space-separated
51# list of values:
52# verbose show number of commits ahead/behind (+/-) upstream
53# legacy don't use the '--count' option available in recent
54# versions of git-rev-list
55# git always compare HEAD to @{upstream}
56# svn always compare HEAD to your SVN upstream
57# By default, __git_ps1 will compare HEAD to your SVN upstream
58# if it can find one, or @{upstream} otherwise. Once you have
59# set GIT_PS1_SHOWUPSTREAM, you can override it on a
60# per-repository basis by setting the bash.showUpstream config
61# variable.
62#
63
64if [[ -n ${ZSH_VERSION-} ]]; then
65 autoload -U +X bashcompinit && bashcompinit
66fi
67
68case "$COMP_WORDBREAKS" in
69*:*) : great ;;
70*) COMP_WORDBREAKS="$COMP_WORDBREAKS:"
71esac
72
73# __gitdir accepts 0 or 1 arguments (i.e., location)
74# returns location of .git repo
75__gitdir ()
76{
77 if [ -z "${1-}" ]; then
78 if [ -n "${__git_dir-}" ]; then
79 echo "$__git_dir"
80 elif [ -d .git ]; then
81 echo .git
82 else
83 git rev-parse --git-dir 2>/dev/null
84 fi
85 elif [ -d "$1/.git" ]; then
86 echo "$1/.git"
87 else
88 echo "$1"
89 fi
90}
91
92# stores the divergence from upstream in $p
93# used by GIT_PS1_SHOWUPSTREAM
94__git_ps1_show_upstream ()
95{
96 local key value
97 local svn_remote=() svn_url_pattern count n
98 local upstream=git legacy="" verbose=""
99
100 # get some config options from git-config
101 local output="$(git config -z --get-regexp '^(svn-remote\..*\.url|bash\.showupstream)$' 2>/dev/null | tr '\0\n' '\n ')"
102 while read -r key value; do
103 case "$key" in
104 bash.showupstream)
105 GIT_PS1_SHOWUPSTREAM="$value"
106 if [[ -z "${GIT_PS1_SHOWUPSTREAM}" ]]; then
107 p=""
108 return
109 fi
110 ;;
111 svn-remote.*.url)
112 svn_remote[ $((${#svn_remote[@]} + 1)) ]="$value"
113 svn_url_pattern+="\\|$value"
114 upstream=svn+git # default upstream is SVN if available, else git
115 ;;
116 esac
117 done <<< "$output"
118
119 # parse configuration values
120 for option in ${GIT_PS1_SHOWUPSTREAM}; do
121 case "$option" in
122 git|svn) upstream="$option" ;;
123 verbose) verbose=1 ;;
124 legacy) legacy=1 ;;
125 esac
126 done
127
128 # Find our upstream
129 case "$upstream" in
130 git) upstream="@{upstream}" ;;
131 svn*)
132 # get the upstream from the "git-svn-id: ..." in a commit message
133 # (git-svn uses essentially the same procedure internally)
134 local svn_upstream=($(git log --first-parent -1 \
135 --grep="^git-svn-id: \(${svn_url_pattern#??}\)" 2>/dev/null))
136 if [[ 0 -ne ${#svn_upstream[@]} ]]; then
137 svn_upstream=${svn_upstream[ ${#svn_upstream[@]} - 2 ]}
138 svn_upstream=${svn_upstream%@*}
139 local n_stop="${#svn_remote[@]}"
140 for ((n=1; n <= n_stop; n++)); do
141 svn_upstream=${svn_upstream#${svn_remote[$n]}}
142 done
143
144 if [[ -z "$svn_upstream" ]]; then
145 # default branch name for checkouts with no layout:
146 upstream=${GIT_SVN_ID:-git-svn}
147 else
148 upstream=${svn_upstream#/}
149 fi
150 elif [[ "svn+git" = "$upstream" ]]; then
151 upstream="@{upstream}"
152 fi
153 ;;
154 esac
155
156 # Find how many commits we are ahead/behind our upstream
157 if [[ -z "$legacy" ]]; then
158 count="$(git rev-list --count --left-right \
159 "$upstream"...HEAD 2>/dev/null)"
160 else
161 # produce equivalent output to --count for older versions of git
162 local commits
163 if commits="$(git rev-list --left-right "$upstream"...HEAD 2>/dev/null)"
164 then
165 local commit behind=0 ahead=0
166 for commit in $commits
167 do
168 case "$commit" in
169 "<"*) ((behind++)) ;;
170 *) ((ahead++)) ;;
171 esac
172 done
173 count="$behind $ahead"
174 else
175 count=""
176 fi
177 fi
178
179 # calculate the result
180 if [[ -z "$verbose" ]]; then
181 case "$count" in
182 "") # no upstream
183 p="" ;;
184 "0 0") # equal to upstream
185 p="=" ;;
186 "0 "*) # ahead of upstream
187 p=">" ;;
188 *" 0") # behind upstream
189 p="<" ;;
190 *) # diverged from upstream
191 p="<>" ;;
192 esac
193 else
194 case "$count" in
195 "") # no upstream
196 p="" ;;
197 "0 0") # equal to upstream
198 p=" u=" ;;
199 "0 "*) # ahead of upstream
200 p=" u+${count#0 }" ;;
201 *" 0") # behind upstream
202 p=" u-${count% 0}" ;;
203 *) # diverged from upstream
204 p=" u+${count#* }-${count% *}" ;;
205 esac
206 fi
207
208}
209
210
211# __git_ps1 accepts 0 or 1 arguments (i.e., format string)
212# returns text to add to bash PS1 prompt (includes branch name)
213__git_ps1 ()
214{
215 local g="$(__gitdir)"
216 if [ -n "$g" ]; then
217 local r=""
218 local b=""
219 if [ -f "$g/rebase-merge/interactive" ]; then
220 r="|REBASE-i"
221 b="$(cat "$g/rebase-merge/head-name")"
222 elif [ -d "$g/rebase-merge" ]; then
223 r="|REBASE-m"
224 b="$(cat "$g/rebase-merge/head-name")"
225 else
226 if [ -d "$g/rebase-apply" ]; then
227 if [ -f "$g/rebase-apply/rebasing" ]; then
228 r="|REBASE"
229 elif [ -f "$g/rebase-apply/applying" ]; then
230 r="|AM"
231 else
232 r="|AM/REBASE"
233 fi
234 elif [ -f "$g/MERGE_HEAD" ]; then
235 r="|MERGING"
236 elif [ -f "$g/CHERRY_PICK_HEAD" ]; then
237 r="|CHERRY-PICKING"
238 elif [ -f "$g/BISECT_LOG" ]; then
239 r="|BISECTING"
240 fi
241
242 b="$(git symbolic-ref HEAD 2>/dev/null)" || {
243
244 b="$(
245 case "${GIT_PS1_DESCRIBE_STYLE-}" in
246 (contains)
247 git describe --contains HEAD ;;
248 (branch)
249 git describe --contains --all HEAD ;;
250 (describe)
251 git describe HEAD ;;
252 (* | default)
253 git describe --tags --exact-match HEAD ;;
254 esac 2>/dev/null)" ||
255
256 b="$(cut -c1-7 "$g/HEAD" 2>/dev/null)..." ||
257 b="unknown"
258 b="($b)"
259 }
260 fi
261
262 local w=""
263 local i=""
264 local s=""
265 local u=""
266 local c=""
267 local p=""
268
269 if [ "true" = "$(git rev-parse --is-inside-git-dir 2>/dev/null)" ]; then
270 if [ "true" = "$(git rev-parse --is-bare-repository 2>/dev/null)" ]; then
271 c="BARE:"
272 else
273 b="GIT_DIR!"
274 fi
275 elif [ "true" = "$(git rev-parse --is-inside-work-tree 2>/dev/null)" ]; then
276 if [ -n "${GIT_PS1_SHOWDIRTYSTATE-}" ]; then
277 if [ "$(git config --bool bash.showDirtyState)" != "false" ]; then
278 git diff --no-ext-diff --quiet --exit-code || w="*"
279 if git rev-parse --quiet --verify HEAD >/dev/null; then
280 git diff-index --cached --quiet HEAD -- || i="+"
281 else
282 i="#"
283 fi
284 fi
285 fi
286 if [ -n "${GIT_PS1_SHOWSTASHSTATE-}" ]; then
287 git rev-parse --verify refs/stash >/dev/null 2>&1 && s="$"
288 fi
289
290 if [ -n "${GIT_PS1_SHOWUNTRACKEDFILES-}" ]; then
291 if [ -n "$(git ls-files --others --exclude-standard)" ]; then
292 u="%"
293 fi
294 fi
295
296 if [ -n "${GIT_PS1_SHOWUPSTREAM-}" ]; then
297 __git_ps1_show_upstream
298 fi
299 fi
300
301 local f="$w$i$s$u"
302 printf -- "${1:- (%s)}" "$c${b##refs/heads/}${f:+ $f}$r$p"
303 fi
304}
305
306# __gitcomp_1 requires 2 arguments
307__gitcomp_1 ()
308{
309 local c IFS=' '$'\t'$'\n'
310 for c in $1; do
311 case "$c$2" in
312 --*=*) printf %s$'\n' "$c$2" ;;
313 *.) printf %s$'\n' "$c$2" ;;
314 *) printf %s$'\n' "$c$2 " ;;
315 esac
316 done
317}
318
319# The following function is based on code from:
320#
321# bash_completion - programmable completion functions for bash 3.2+
322#
323# Copyright © 2006-2008, Ian Macdonald <ian@caliban.org>
324# © 2009-2010, Bash Completion Maintainers
325# <bash-completion-devel@lists.alioth.debian.org>
326#
327# This program is free software; you can redistribute it and/or modify
328# it under the terms of the GNU General Public License as published by
329# the Free Software Foundation; either version 2, or (at your option)
330# any later version.
331#
332# This program is distributed in the hope that it will be useful,
333# but WITHOUT ANY WARRANTY; without even the implied warranty of
334# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
335# GNU General Public License for more details.
336#
337# You should have received a copy of the GNU General Public License
338# along with this program; if not, write to the Free Software Foundation,
339# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
340#
341# The latest version of this software can be obtained here:
342#
343# http://bash-completion.alioth.debian.org/
344#
345# RELEASE: 2.x
346
347# This function can be used to access a tokenized list of words
348# on the command line:
349#
350# __git_reassemble_comp_words_by_ref '=:'
351# if test "${words_[cword_-1]}" = -w
352# then
353# ...
354# fi
355#
356# The argument should be a collection of characters from the list of
357# word completion separators (COMP_WORDBREAKS) to treat as ordinary
358# characters.
359#
360# This is roughly equivalent to going back in time and setting
361# COMP_WORDBREAKS to exclude those characters. The intent is to
362# make option types like --date=<type> and <rev>:<path> easy to
363# recognize by treating each shell word as a single token.
364#
365# It is best not to set COMP_WORDBREAKS directly because the value is
366# shared with other completion scripts. By the time the completion
367# function gets called, COMP_WORDS has already been populated so local
368# changes to COMP_WORDBREAKS have no effect.
369#
370# Output: words_, cword_, cur_.
371
372__git_reassemble_comp_words_by_ref()
373{
374 local exclude i j first
375 # Which word separators to exclude?
376 exclude="${1//[^$COMP_WORDBREAKS]}"
377 cword_=$COMP_CWORD
378 if [ -z "$exclude" ]; then
379 words_=("${COMP_WORDS[@]}")
380 return
381 fi
382 # List of word completion separators has shrunk;
383 # re-assemble words to complete.
384 for ((i=0, j=0; i < ${#COMP_WORDS[@]}; i++, j++)); do
385 # Append each nonempty word consisting of just
386 # word separator characters to the current word.
387 first=t
388 while
389 [ $i -gt 0 ] &&
390 [ -n "${COMP_WORDS[$i]}" ] &&
391 # word consists of excluded word separators
392 [ "${COMP_WORDS[$i]//[^$exclude]}" = "${COMP_WORDS[$i]}" ]
393 do
394 # Attach to the previous token,
395 # unless the previous token is the command name.
396 if [ $j -ge 2 ] && [ -n "$first" ]; then
397 ((j--))
398 fi
399 first=
400 words_[$j]=${words_[j]}${COMP_WORDS[i]}
401 if [ $i = $COMP_CWORD ]; then
402 cword_=$j
403 fi
404 if (($i < ${#COMP_WORDS[@]} - 1)); then
405 ((i++))
406 else
407 # Done.
408 return
409 fi
410 done
411 words_[$j]=${words_[j]}${COMP_WORDS[i]}
412 if [ $i = $COMP_CWORD ]; then
413 cword_=$j
414 fi
415 done
416}
417
418if ! type _get_comp_words_by_ref >/dev/null 2>&1; then
419if [[ -z ${ZSH_VERSION:+set} ]]; then
420_get_comp_words_by_ref ()
421{
422 local exclude cur_ words_ cword_
423 if [ "$1" = "-n" ]; then
424 exclude=$2
425 shift 2
426 fi
427 __git_reassemble_comp_words_by_ref "$exclude"
428 cur_=${words_[cword_]}
429 while [ $# -gt 0 ]; do
430 case "$1" in
431 cur)
432 cur=$cur_
433 ;;
434 prev)
435 prev=${words_[$cword_-1]}
436 ;;
437 words)
438 words=("${words_[@]}")
439 ;;
440 cword)
441 cword=$cword_
442 ;;
443 esac
444 shift
445 done
446}
447else
448_get_comp_words_by_ref ()
449{
450 while [ $# -gt 0 ]; do
451 case "$1" in
452 cur)
453 cur=${COMP_WORDS[COMP_CWORD]}
454 ;;
455 prev)
456 prev=${COMP_WORDS[COMP_CWORD-1]}
457 ;;
458 words)
459 words=("${COMP_WORDS[@]}")
460 ;;
461 cword)
462 cword=$COMP_CWORD
463 ;;
464 -n)
465 # assume COMP_WORDBREAKS is already set sanely
466 shift
467 ;;
468 esac
469 shift
470 done
471}
472fi
473fi
474
475# Generates completion reply with compgen, appending a space to possible
476# completion words, if necessary.
477# It accepts 1 to 4 arguments:
478# 1: List of possible completion words.
479# 2: A prefix to be added to each possible completion word (optional).
480# 3: Generate possible completion matches for this word (optional).
481# 4: A suffix to be appended to each possible completion word (optional).
482__gitcomp ()
483{
484 local cur_="${3-$cur}"
485
486 case "$cur_" in
487 --*=)
488 COMPREPLY=()
489 ;;
490 *)
491 local IFS=$'\n'
492 COMPREPLY=($(compgen -P "${2-}" \
493 -W "$(__gitcomp_1 "${1-}" "${4-}")" \
494 -- "$cur_"))
495 ;;
496 esac
497}
498
499# Generates completion reply with compgen from newline-separated possible
500# completion words by appending a space to all of them.
501# It accepts 1 to 4 arguments:
502# 1: List of possible completion words, separated by a single newline.
503# 2: A prefix to be added to each possible completion word (optional).
504# 3: Generate possible completion matches for this word (optional).
505# 4: A suffix to be appended to each possible completion word instead of
506# the default space (optional). If specified but empty, nothing is
507# appended.
508__gitcomp_nl ()
509{
510 local IFS=$'\n'
511 COMPREPLY=($(compgen -P "${2-}" -S "${4- }" -W "$1" -- "${3-$cur}"))
512}
513
514__git_heads ()
515{
516 local dir="$(__gitdir)"
517 if [ -d "$dir" ]; then
518 git --git-dir="$dir" for-each-ref --format='%(refname:short)' \
519 refs/heads
520 return
521 fi
522}
523
524__git_tags ()
525{
526 local dir="$(__gitdir)"
527 if [ -d "$dir" ]; then
528 git --git-dir="$dir" for-each-ref --format='%(refname:short)' \
529 refs/tags
530 return
531 fi
532}
533
534# __git_refs accepts 0, 1 (to pass to __gitdir), or 2 arguments
535# presence of 2nd argument means use the guess heuristic employed
536# by checkout for tracking branches
537__git_refs ()
538{
539 local i hash dir="$(__gitdir "${1-}")" track="${2-}"
540 local format refs
541 if [ -d "$dir" ]; then
542 case "$cur" in
543 refs|refs/*)
544 format="refname"
545 refs="${cur%/*}"
546 track=""
547 ;;
548 *)
549 for i in HEAD FETCH_HEAD ORIG_HEAD MERGE_HEAD; do
550 if [ -e "$dir/$i" ]; then echo $i; fi
551 done
552 format="refname:short"
553 refs="refs/tags refs/heads refs/remotes"
554 ;;
555 esac
556 git --git-dir="$dir" for-each-ref --format="%($format)" \
557 $refs
558 if [ -n "$track" ]; then
559 # employ the heuristic used by git checkout
560 # Try to find a remote branch that matches the completion word
561 # but only output if the branch name is unique
562 local ref entry
563 git --git-dir="$dir" for-each-ref --shell --format="ref=%(refname:short)" \
564 "refs/remotes/" | \
565 while read -r entry; do
566 eval "$entry"
567 ref="${ref#*/}"
568 if [[ "$ref" == "$cur"* ]]; then
569 echo "$ref"
570 fi
571 done | uniq -u
572 fi
573 return
574 fi
575 case "$cur" in
576 refs|refs/*)
577 git ls-remote "$dir" "$cur*" 2>/dev/null | \
578 while read -r hash i; do
579 case "$i" in
580 *^{}) ;;
581 *) echo "$i" ;;
582 esac
583 done
584 ;;
585 *)
586 git ls-remote "$dir" HEAD ORIG_HEAD 'refs/tags/*' 'refs/heads/*' 'refs/remotes/*' 2>/dev/null | \
587 while read -r hash i; do
588 case "$i" in
589 *^{}) ;;
590 refs/*) echo "${i#refs/*/}" ;;
591 *) echo "$i" ;;
592 esac
593 done
594 ;;
595 esac
596}
597
598# __git_refs2 requires 1 argument (to pass to __git_refs)
599__git_refs2 ()
600{
601 local i
602 for i in $(__git_refs "$1"); do
603 echo "$i:$i"
604 done
605}
606
607# __git_refs_remotes requires 1 argument (to pass to ls-remote)
608__git_refs_remotes ()
609{
610 local i hash
611 git ls-remote "$1" 'refs/heads/*' 2>/dev/null | \
612 while read -r hash i; do
613 echo "$i:refs/remotes/$1/${i#refs/heads/}"
614 done
615}
616
617__git_remotes ()
618{
619 local i IFS=$'\n' d="$(__gitdir)"
620 test -d "$d/remotes" && ls -1 "$d/remotes"
621 for i in $(git --git-dir="$d" config --get-regexp 'remote\..*\.url' 2>/dev/null); do
622 i="${i#remote.}"
623 echo "${i/.url*/}"
624 done
625}
626
627__git_list_merge_strategies ()
628{
629 git merge -s help 2>&1 |
630 sed -n -e '/[Aa]vailable strategies are: /,/^$/{
631 s/\.$//
632 s/.*://
633 s/^[ ]*//
634 s/[ ]*$//
635 p
636 }'
637}
638
639__git_merge_strategies=
640# 'git merge -s help' (and thus detection of the merge strategy
641# list) fails, unfortunately, if run outside of any git working
642# tree. __git_merge_strategies is set to the empty string in
643# that case, and the detection will be repeated the next time it
644# is needed.
645__git_compute_merge_strategies ()
646{
647 test -n "$__git_merge_strategies" ||
648 __git_merge_strategies=$(__git_list_merge_strategies)
649}
650
651__git_complete_revlist_file ()
652{
653 local pfx ls ref cur_="$cur"
654 case "$cur_" in
655 *..?*:*)
656 return
657 ;;
658 ?*:*)
659 ref="${cur_%%:*}"
660 cur_="${cur_#*:}"
661 case "$cur_" in
662 ?*/*)
663 pfx="${cur_%/*}"
664 cur_="${cur_##*/}"
665 ls="$ref:$pfx"
666 pfx="$pfx/"
667 ;;
668 *)
669 ls="$ref"
670 ;;
671 esac
672
673 case "$COMP_WORDBREAKS" in
674 *:*) : great ;;
675 *) pfx="$ref:$pfx" ;;
676 esac
677
678 local IFS=$'\n'
679 COMPREPLY=($(compgen -P "$pfx" \
680 -W "$(git --git-dir="$(__gitdir)" ls-tree "$ls" \
681 | sed '/^100... blob /{
682 s,^.* ,,
683 s,$, ,
684 }
685 /^120000 blob /{
686 s,^.* ,,
687 s,$, ,
688 }
689 /^040000 tree /{
690 s,^.* ,,
691 s,$,/,
692 }
693 s/^.* //')" \
694 -- "$cur_"))
695 ;;
696 *...*)
697 pfx="${cur_%...*}..."
698 cur_="${cur_#*...}"
699 __gitcomp_nl "$(__git_refs)" "$pfx" "$cur_"
700 ;;
701 *..*)
702 pfx="${cur_%..*}.."
703 cur_="${cur_#*..}"
704 __gitcomp_nl "$(__git_refs)" "$pfx" "$cur_"
705 ;;
706 *)
707 __gitcomp_nl "$(__git_refs)"
708 ;;
709 esac
710}
711
712
713__git_complete_file ()
714{
715 __git_complete_revlist_file
716}
717
718__git_complete_revlist ()
719{
720 __git_complete_revlist_file
721}
722
723__git_complete_remote_or_refspec ()
724{
725 local cur_="$cur" cmd="${words[1]}"
726 local i c=2 remote="" pfx="" lhs=1 no_complete_refspec=0
727 if [ "$cmd" = "remote" ]; then
728 ((c++))
729 fi
730 while [ $c -lt $cword ]; do
731 i="${words[c]}"
732 case "$i" in
733 --mirror) [ "$cmd" = "push" ] && no_complete_refspec=1 ;;
734 --all)
735 case "$cmd" in
736 push) no_complete_refspec=1 ;;
737 fetch)
738 COMPREPLY=()
739 return
740 ;;
741 *) ;;
742 esac
743 ;;
744 -*) ;;
745 *) remote="$i"; break ;;
746 esac
747 ((c++))
748 done
749 if [ -z "$remote" ]; then
750 __gitcomp_nl "$(__git_remotes)"
751 return
752 fi
753 if [ $no_complete_refspec = 1 ]; then
754 COMPREPLY=()
755 return
756 fi
757 [ "$remote" = "." ] && remote=
758 case "$cur_" in
759 *:*)
760 case "$COMP_WORDBREAKS" in
761 *:*) : great ;;
762 *) pfx="${cur_%%:*}:" ;;
763 esac
764 cur_="${cur_#*:}"
765 lhs=0
766 ;;
767 +*)
768 pfx="+"
769 cur_="${cur_#+}"
770 ;;
771 esac
772 case "$cmd" in
773 fetch)
774 if [ $lhs = 1 ]; then
775 __gitcomp_nl "$(__git_refs2 "$remote")" "$pfx" "$cur_"
776 else
777 __gitcomp_nl "$(__git_refs)" "$pfx" "$cur_"
778 fi
779 ;;
780 pull|remote)
781 if [ $lhs = 1 ]; then
782 __gitcomp_nl "$(__git_refs "$remote")" "$pfx" "$cur_"
783 else
784 __gitcomp_nl "$(__git_refs)" "$pfx" "$cur_"
785 fi
786 ;;
787 push)
788 if [ $lhs = 1 ]; then
789 __gitcomp_nl "$(__git_refs)" "$pfx" "$cur_"
790 else
791 __gitcomp_nl "$(__git_refs "$remote")" "$pfx" "$cur_"
792 fi
793 ;;
794 esac
795}
796
797__git_complete_strategy ()
798{
799 __git_compute_merge_strategies
800 case "$prev" in
801 -s|--strategy)
802 __gitcomp "$__git_merge_strategies"
803 return 0
804 esac
805 case "$cur" in
806 --strategy=*)
807 __gitcomp "$__git_merge_strategies" "" "${cur##--strategy=}"
808 return 0
809 ;;
810 esac
811 return 1
812}
813
814__git_list_all_commands ()
815{
816 local i IFS=" "$'\n'
817 for i in $(git help -a|egrep '^ [a-zA-Z0-9]')
818 do
819 case $i in
820 *--*) : helper pattern;;
821 *) echo $i;;
822 esac
823 done
824}
825
826__git_all_commands=
827__git_compute_all_commands ()
828{
829 test -n "$__git_all_commands" ||
830 __git_all_commands=$(__git_list_all_commands)
831}
832
833__git_list_porcelain_commands ()
834{
835 local i IFS=" "$'\n'
836 __git_compute_all_commands
837 for i in "help" $__git_all_commands
838 do
839 case $i in
840 *--*) : helper pattern;;
841 applymbox) : ask gittus;;
842 applypatch) : ask gittus;;
843 archimport) : import;;
844 cat-file) : plumbing;;
845 check-attr) : plumbing;;
846 check-ref-format) : plumbing;;
847 checkout-index) : plumbing;;
848 commit-tree) : plumbing;;
849 count-objects) : infrequent;;
850 cvsexportcommit) : export;;
851 cvsimport) : import;;
852 cvsserver) : daemon;;
853 daemon) : daemon;;
854 diff-files) : plumbing;;
855 diff-index) : plumbing;;
856 diff-tree) : plumbing;;
857 fast-import) : import;;
858 fast-export) : export;;
859 fsck-objects) : plumbing;;
860 fetch-pack) : plumbing;;
861 fmt-merge-msg) : plumbing;;
862 for-each-ref) : plumbing;;
863 hash-object) : plumbing;;
864 http-*) : transport;;
865 index-pack) : plumbing;;
866 init-db) : deprecated;;
867 local-fetch) : plumbing;;
868 lost-found) : infrequent;;
869 ls-files) : plumbing;;
870 ls-remote) : plumbing;;
871 ls-tree) : plumbing;;
872 mailinfo) : plumbing;;
873 mailsplit) : plumbing;;
874 merge-*) : plumbing;;
875 mktree) : plumbing;;
876 mktag) : plumbing;;
877 pack-objects) : plumbing;;
878 pack-redundant) : plumbing;;
879 pack-refs) : plumbing;;
880 parse-remote) : plumbing;;
881 patch-id) : plumbing;;
882 peek-remote) : plumbing;;
883 prune) : plumbing;;
884 prune-packed) : plumbing;;
885 quiltimport) : import;;
886 read-tree) : plumbing;;
887 receive-pack) : plumbing;;
888 remote-*) : transport;;
889 repo-config) : deprecated;;
890 rerere) : plumbing;;
891 rev-list) : plumbing;;
892 rev-parse) : plumbing;;
893 runstatus) : plumbing;;
894 sh-setup) : internal;;
895 shell) : daemon;;
896 show-ref) : plumbing;;
897 send-pack) : plumbing;;
898 show-index) : plumbing;;
899 ssh-*) : transport;;
900 stripspace) : plumbing;;
901 symbolic-ref) : plumbing;;
902 tar-tree) : deprecated;;
903 unpack-file) : plumbing;;
904 unpack-objects) : plumbing;;
905 update-index) : plumbing;;
906 update-ref) : plumbing;;
907 update-server-info) : daemon;;
908 upload-archive) : plumbing;;
909 upload-pack) : plumbing;;
910 write-tree) : plumbing;;
911 var) : infrequent;;
912 verify-pack) : infrequent;;
913 verify-tag) : plumbing;;
914 *) echo $i;;
915 esac
916 done
917}
918
919__git_porcelain_commands=
920__git_compute_porcelain_commands ()
921{
922 __git_compute_all_commands
923 test -n "$__git_porcelain_commands" ||
924 __git_porcelain_commands=$(__git_list_porcelain_commands)
925}
926
927__git_pretty_aliases ()
928{
929 local i IFS=$'\n'
930 for i in $(git --git-dir="$(__gitdir)" config --get-regexp "pretty\..*" 2>/dev/null); do
931 case "$i" in
932 pretty.*)
933 i="${i#pretty.}"
934 echo "${i/ */}"
935 ;;
936 esac
937 done
938}
939
940__git_aliases ()
941{
942 local i IFS=$'\n'
943 for i in $(git --git-dir="$(__gitdir)" config --get-regexp "alias\..*" 2>/dev/null); do
944 case "$i" in
945 alias.*)
946 i="${i#alias.}"
947 echo "${i/ */}"
948 ;;
949 esac
950 done
951}
952
953# __git_aliased_command requires 1 argument
954__git_aliased_command ()
955{
956 local word cmdline=$(git --git-dir="$(__gitdir)" \
957 config --get "alias.$1")
958 for word in $cmdline; do
959 case "$word" in
960 \!gitk|gitk)
961 echo "gitk"
962 return
963 ;;
964 \!*) : shell command alias ;;
965 -*) : option ;;
966 *=*) : setting env ;;
967 git) : git itself ;;
968 *)
969 echo "$word"
970 return
971 esac
972 done
973}
974
975# __git_find_on_cmdline requires 1 argument
976__git_find_on_cmdline ()
977{
978 local word subcommand c=1
979 while [ $c -lt $cword ]; do
980 word="${words[c]}"
981 for subcommand in $1; do
982 if [ "$subcommand" = "$word" ]; then
983 echo "$subcommand"
984 return
985 fi
986 done
987 ((c++))
988 done
989}
990
991__git_has_doubledash ()
992{
993 local c=1
994 while [ $c -lt $cword ]; do
995 if [ "--" = "${words[c]}" ]; then
996 return 0
997 fi
998 ((c++))
999 done
1000 return 1
1001}
1002
1003__git_whitespacelist="nowarn warn error error-all fix"
1004
1005_git_am ()
1006{
1007 local dir="$(__gitdir)"
1008 if [ -d "$dir"/rebase-apply ]; then
1009 __gitcomp "--skip --continue --resolved --abort"
1010 return
1011 fi
1012 case "$cur" in
1013 --whitespace=*)
1014 __gitcomp "$__git_whitespacelist" "" "${cur##--whitespace=}"
1015 return
1016 ;;
1017 --*)
1018 __gitcomp "
1019 --3way --committer-date-is-author-date --ignore-date
1020 --ignore-whitespace --ignore-space-change
1021 --interactive --keep --no-utf8 --signoff --utf8
1022 --whitespace= --scissors
1023 "
1024 return
1025 esac
1026 COMPREPLY=()
1027}
1028
1029_git_apply ()
1030{
1031 case "$cur" in
1032 --whitespace=*)
1033 __gitcomp "$__git_whitespacelist" "" "${cur##--whitespace=}"
1034 return
1035 ;;
1036 --*)
1037 __gitcomp "
1038 --stat --numstat --summary --check --index
1039 --cached --index-info --reverse --reject --unidiff-zero
1040 --apply --no-add --exclude=
1041 --ignore-whitespace --ignore-space-change
1042 --whitespace= --inaccurate-eof --verbose
1043 "
1044 return
1045 esac
1046 COMPREPLY=()
1047}
1048
1049_git_add ()
1050{
1051 __git_has_doubledash && return
1052
1053 case "$cur" in
1054 --*)
1055 __gitcomp "
1056 --interactive --refresh --patch --update --dry-run
1057 --ignore-errors --intent-to-add
1058 "
1059 return
1060 esac
1061 COMPREPLY=()
1062}
1063
1064_git_archive ()
1065{
1066 case "$cur" in
1067 --format=*)
1068 __gitcomp "$(git archive --list)" "" "${cur##--format=}"
1069 return
1070 ;;
1071 --remote=*)
1072 __gitcomp_nl "$(__git_remotes)" "" "${cur##--remote=}"
1073 return
1074 ;;
1075 --*)
1076 __gitcomp "
1077 --format= --list --verbose
1078 --prefix= --remote= --exec=
1079 "
1080 return
1081 ;;
1082 esac
1083 __git_complete_file
1084}
1085
1086_git_bisect ()
1087{
1088 __git_has_doubledash && return
1089
1090 local subcommands="start bad good skip reset visualize replay log run"
1091 local subcommand="$(__git_find_on_cmdline "$subcommands")"
1092 if [ -z "$subcommand" ]; then
1093 if [ -f "$(__gitdir)"/BISECT_START ]; then
1094 __gitcomp "$subcommands"
1095 else
1096 __gitcomp "replay start"
1097 fi
1098 return
1099 fi
1100
1101 case "$subcommand" in
1102 bad|good|reset|skip|start)
1103 __gitcomp_nl "$(__git_refs)"
1104 ;;
1105 *)
1106 COMPREPLY=()
1107 ;;
1108 esac
1109}
1110
1111_git_branch ()
1112{
1113 local i c=1 only_local_ref="n" has_r="n"
1114
1115 while [ $c -lt $cword ]; do
1116 i="${words[c]}"
1117 case "$i" in
1118 -d|-m) only_local_ref="y" ;;
1119 -r) has_r="y" ;;
1120 esac
1121 ((c++))
1122 done
1123
1124 case "$cur" in
1125 --*)
1126 __gitcomp "
1127 --color --no-color --verbose --abbrev= --no-abbrev
1128 --track --no-track --contains --merged --no-merged
1129 --set-upstream --edit-description --list
1130 "
1131 ;;
1132 *)
1133 if [ $only_local_ref = "y" -a $has_r = "n" ]; then
1134 __gitcomp_nl "$(__git_heads)"
1135 else
1136 __gitcomp_nl "$(__git_refs)"
1137 fi
1138 ;;
1139 esac
1140}
1141
1142_git_bundle ()
1143{
1144 local cmd="${words[2]}"
1145 case "$cword" in
1146 2)
1147 __gitcomp "create list-heads verify unbundle"
1148 ;;
1149 3)
1150 # looking for a file
1151 ;;
1152 *)
1153 case "$cmd" in
1154 create)
1155 __git_complete_revlist
1156 ;;
1157 esac
1158 ;;
1159 esac
1160}
1161
1162_git_checkout ()
1163{
1164 __git_has_doubledash && return
1165
1166 case "$cur" in
1167 --conflict=*)
1168 __gitcomp "diff3 merge" "" "${cur##--conflict=}"
1169 ;;
1170 --*)
1171 __gitcomp "
1172 --quiet --ours --theirs --track --no-track --merge
1173 --conflict= --orphan --patch
1174 "
1175 ;;
1176 *)
1177 # check if --track, --no-track, or --no-guess was specified
1178 # if so, disable DWIM mode
1179 local flags="--track --no-track --no-guess" track=1
1180 if [ -n "$(__git_find_on_cmdline "$flags")" ]; then
1181 track=''
1182 fi
1183 __gitcomp_nl "$(__git_refs '' $track)"
1184 ;;
1185 esac
1186}
1187
1188_git_cherry ()
1189{
1190 __gitcomp "$(__git_refs)"
1191}
1192
1193_git_cherry_pick ()
1194{
1195 case "$cur" in
1196 --*)
1197 __gitcomp "--edit --no-commit"
1198 ;;
1199 *)
1200 __gitcomp_nl "$(__git_refs)"
1201 ;;
1202 esac
1203}
1204
1205_git_clean ()
1206{
1207 __git_has_doubledash && return
1208
1209 case "$cur" in
1210 --*)
1211 __gitcomp "--dry-run --quiet"
1212 return
1213 ;;
1214 esac
1215 COMPREPLY=()
1216}
1217
1218_git_clone ()
1219{
1220 case "$cur" in
1221 --*)
1222 __gitcomp "
1223 --local
1224 --no-hardlinks
1225 --shared
1226 --reference
1227 --quiet
1228 --no-checkout
1229 --bare
1230 --mirror
1231 --origin
1232 --upload-pack
1233 --template=
1234 --depth
1235 "
1236 return
1237 ;;
1238 esac
1239 COMPREPLY=()
1240}
1241
1242_git_commit ()
1243{
1244 __git_has_doubledash && return
1245
1246 case "$cur" in
1247 --cleanup=*)
1248 __gitcomp "default strip verbatim whitespace
1249 " "" "${cur##--cleanup=}"
1250 return
1251 ;;
1252 --reuse-message=*|--reedit-message=*|\
1253 --fixup=*|--squash=*)
1254 __gitcomp_nl "$(__git_refs)" "" "${cur#*=}"
1255 return
1256 ;;
1257 --untracked-files=*)
1258 __gitcomp "all no normal" "" "${cur##--untracked-files=}"
1259 return
1260 ;;
1261 --*)
1262 __gitcomp "
1263 --all --author= --signoff --verify --no-verify
1264 --edit --amend --include --only --interactive
1265 --dry-run --reuse-message= --reedit-message=
1266 --reset-author --file= --message= --template=
1267 --cleanup= --untracked-files --untracked-files=
1268 --verbose --quiet --fixup= --squash=
1269 "
1270 return
1271 esac
1272 COMPREPLY=()
1273}
1274
1275_git_describe ()
1276{
1277 case "$cur" in
1278 --*)
1279 __gitcomp "
1280 --all --tags --contains --abbrev= --candidates=
1281 --exact-match --debug --long --match --always
1282 "
1283 return
1284 esac
1285 __gitcomp_nl "$(__git_refs)"
1286}
1287
1288__git_diff_common_options="--stat --numstat --shortstat --summary
1289 --patch-with-stat --name-only --name-status --color
1290 --no-color --color-words --no-renames --check
1291 --full-index --binary --abbrev --diff-filter=
1292 --find-copies-harder
1293 --text --ignore-space-at-eol --ignore-space-change
1294 --ignore-all-space --exit-code --quiet --ext-diff
1295 --no-ext-diff
1296 --no-prefix --src-prefix= --dst-prefix=
1297 --inter-hunk-context=
1298 --patience
1299 --raw
1300 --dirstat --dirstat= --dirstat-by-file
1301 --dirstat-by-file= --cumulative
1302"
1303
1304_git_diff ()
1305{
1306 __git_has_doubledash && return
1307
1308 case "$cur" in
1309 --*)
1310 __gitcomp "--cached --staged --pickaxe-all --pickaxe-regex
1311 --base --ours --theirs --no-index
1312 $__git_diff_common_options
1313 "
1314 return
1315 ;;
1316 esac
1317 __git_complete_revlist_file
1318}
1319
1320__git_mergetools_common="diffuse ecmerge emerge kdiff3 meld opendiff
1321 tkdiff vimdiff gvimdiff xxdiff araxis p4merge bc3
1322"
1323
1324_git_difftool ()
1325{
1326 __git_has_doubledash && return
1327
1328 case "$cur" in
1329 --tool=*)
1330 __gitcomp "$__git_mergetools_common kompare" "" "${cur##--tool=}"
1331 return
1332 ;;
1333 --*)
1334 __gitcomp "--cached --staged --pickaxe-all --pickaxe-regex
1335 --base --ours --theirs
1336 --no-renames --diff-filter= --find-copies-harder
1337 --relative --ignore-submodules
1338 --tool="
1339 return
1340 ;;
1341 esac
1342 __git_complete_file
1343}
1344
1345__git_fetch_options="
1346 --quiet --verbose --append --upload-pack --force --keep --depth=
1347 --tags --no-tags --all --prune --dry-run
1348"
1349
1350_git_fetch ()
1351{
1352 case "$cur" in
1353 --*)
1354 __gitcomp "$__git_fetch_options"
1355 return
1356 ;;
1357 esac
1358 __git_complete_remote_or_refspec
1359}
1360
1361_git_format_patch ()
1362{
1363 case "$cur" in
1364 --thread=*)
1365 __gitcomp "
1366 deep shallow
1367 " "" "${cur##--thread=}"
1368 return
1369 ;;
1370 --*)
1371 __gitcomp "
1372 --stdout --attach --no-attach --thread --thread=
1373 --output-directory
1374 --numbered --start-number
1375 --numbered-files
1376 --keep-subject
1377 --signoff --signature --no-signature
1378 --in-reply-to= --cc=
1379 --full-index --binary
1380 --not --all
1381 --cover-letter
1382 --no-prefix --src-prefix= --dst-prefix=
1383 --inline --suffix= --ignore-if-in-upstream
1384 --subject-prefix=
1385 "
1386 return
1387 ;;
1388 esac
1389 __git_complete_revlist
1390}
1391
1392_git_fsck ()
1393{
1394 case "$cur" in
1395 --*)
1396 __gitcomp "
1397 --tags --root --unreachable --cache --no-reflogs --full
1398 --strict --verbose --lost-found
1399 "
1400 return
1401 ;;
1402 esac
1403 COMPREPLY=()
1404}
1405
1406_git_gc ()
1407{
1408 case "$cur" in
1409 --*)
1410 __gitcomp "--prune --aggressive"
1411 return
1412 ;;
1413 esac
1414 COMPREPLY=()
1415}
1416
1417_git_gitk ()
1418{
1419 _gitk
1420}
1421
1422__git_match_ctag() {
1423 awk "/^${1////\\/}/ { print \$1 }" "$2"
1424}
1425
1426_git_grep ()
1427{
1428 __git_has_doubledash && return
1429
1430 case "$cur" in
1431 --*)
1432 __gitcomp "
1433 --cached
1434 --text --ignore-case --word-regexp --invert-match
1435 --full-name --line-number
1436 --extended-regexp --basic-regexp --fixed-strings
1437 --perl-regexp
1438 --files-with-matches --name-only
1439 --files-without-match
1440 --max-depth
1441 --count
1442 --and --or --not --all-match
1443 "
1444 return
1445 ;;
1446 esac
1447
1448 case "$cword,$prev" in
1449 2,*|*,-*)
1450 if test -r tags; then
1451 __gitcomp_nl "$(__git_match_ctag "$cur" tags)"
1452 return
1453 fi
1454 ;;
1455 esac
1456
1457 __gitcomp_nl "$(__git_refs)"
1458}
1459
1460_git_help ()
1461{
1462 case "$cur" in
1463 --*)
1464 __gitcomp "--all --info --man --web"
1465 return
1466 ;;
1467 esac
1468 __git_compute_all_commands
1469 __gitcomp "$__git_all_commands $(__git_aliases)
1470 attributes cli core-tutorial cvs-migration
1471 diffcore gitk glossary hooks ignore modules
1472 namespaces repository-layout tutorial tutorial-2
1473 workflows
1474 "
1475}
1476
1477_git_init ()
1478{
1479 case "$cur" in
1480 --shared=*)
1481 __gitcomp "
1482 false true umask group all world everybody
1483 " "" "${cur##--shared=}"
1484 return
1485 ;;
1486 --*)
1487 __gitcomp "--quiet --bare --template= --shared --shared="
1488 return
1489 ;;
1490 esac
1491 COMPREPLY=()
1492}
1493
1494_git_ls_files ()
1495{
1496 __git_has_doubledash && return
1497
1498 case "$cur" in
1499 --*)
1500 __gitcomp "--cached --deleted --modified --others --ignored
1501 --stage --directory --no-empty-directory --unmerged
1502 --killed --exclude= --exclude-from=
1503 --exclude-per-directory= --exclude-standard
1504 --error-unmatch --with-tree= --full-name
1505 --abbrev --ignored --exclude-per-directory
1506 "
1507 return
1508 ;;
1509 esac
1510 COMPREPLY=()
1511}
1512
1513_git_ls_remote ()
1514{
1515 __gitcomp_nl "$(__git_remotes)"
1516}
1517
1518_git_ls_tree ()
1519{
1520 __git_complete_file
1521}
1522
1523# Options that go well for log, shortlog and gitk
1524__git_log_common_options="
1525 --not --all
1526 --branches --tags --remotes
1527 --first-parent --merges --no-merges
1528 --max-count=
1529 --max-age= --since= --after=
1530 --min-age= --until= --before=
1531 --min-parents= --max-parents=
1532 --no-min-parents --no-max-parents
1533"
1534# Options that go well for log and gitk (not shortlog)
1535__git_log_gitk_options="
1536 --dense --sparse --full-history
1537 --simplify-merges --simplify-by-decoration
1538 --left-right --notes --no-notes
1539"
1540# Options that go well for log and shortlog (not gitk)
1541__git_log_shortlog_options="
1542 --author= --committer= --grep=
1543 --all-match
1544"
1545
1546__git_log_pretty_formats="oneline short medium full fuller email raw format:"
1547__git_log_date_formats="relative iso8601 rfc2822 short local default raw"
1548
1549_git_log ()
1550{
1551 __git_has_doubledash && return
1552
1553 local g="$(git rev-parse --git-dir 2>/dev/null)"
1554 local merge=""
1555 if [ -f "$g/MERGE_HEAD" ]; then
1556 merge="--merge"
1557 fi
1558 case "$cur" in
1559 --pretty=*|--format=*)
1560 __gitcomp "$__git_log_pretty_formats $(__git_pretty_aliases)
1561 " "" "${cur#*=}"
1562 return
1563 ;;
1564 --date=*)
1565 __gitcomp "$__git_log_date_formats" "" "${cur##--date=}"
1566 return
1567 ;;
1568 --decorate=*)
1569 __gitcomp "long short" "" "${cur##--decorate=}"
1570 return
1571 ;;
1572 --*)
1573 __gitcomp "
1574 $__git_log_common_options
1575 $__git_log_shortlog_options
1576 $__git_log_gitk_options
1577 --root --topo-order --date-order --reverse
1578 --follow --full-diff
1579 --abbrev-commit --abbrev=
1580 --relative-date --date=
1581 --pretty= --format= --oneline
1582 --cherry-pick
1583 --graph
1584 --decorate --decorate=
1585 --walk-reflogs
1586 --parents --children
1587 $merge
1588 $__git_diff_common_options
1589 --pickaxe-all --pickaxe-regex
1590 "
1591 return
1592 ;;
1593 esac
1594 __git_complete_revlist
1595}
1596
1597__git_merge_options="
1598 --no-commit --no-stat --log --no-log --squash --strategy
1599 --commit --stat --no-squash --ff --no-ff --ff-only --edit --no-edit
1600"
1601
1602_git_merge ()
1603{
1604 __git_complete_strategy && return
1605
1606 case "$cur" in
1607 --*)
1608 __gitcomp "$__git_merge_options"
1609 return
1610 esac
1611 __gitcomp_nl "$(__git_refs)"
1612}
1613
1614_git_mergetool ()
1615{
1616 case "$cur" in
1617 --tool=*)
1618 __gitcomp "$__git_mergetools_common tortoisemerge" "" "${cur##--tool=}"
1619 return
1620 ;;
1621 --*)
1622 __gitcomp "--tool="
1623 return
1624 ;;
1625 esac
1626 COMPREPLY=()
1627}
1628
1629_git_merge_base ()
1630{
1631 __gitcomp_nl "$(__git_refs)"
1632}
1633
1634_git_mv ()
1635{
1636 case "$cur" in
1637 --*)
1638 __gitcomp "--dry-run"
1639 return
1640 ;;
1641 esac
1642 COMPREPLY=()
1643}
1644
1645_git_name_rev ()
1646{
1647 __gitcomp "--tags --all --stdin"
1648}
1649
1650_git_notes ()
1651{
1652 local subcommands='add append copy edit list prune remove show'
1653 local subcommand="$(__git_find_on_cmdline "$subcommands")"
1654
1655 case "$subcommand,$cur" in
1656 ,--*)
1657 __gitcomp '--ref'
1658 ;;
1659 ,*)
1660 case "${words[cword-1]}" in
1661 --ref)
1662 __gitcomp_nl "$(__git_refs)"
1663 ;;
1664 *)
1665 __gitcomp "$subcommands --ref"
1666 ;;
1667 esac
1668 ;;
1669 add,--reuse-message=*|append,--reuse-message=*|\
1670 add,--reedit-message=*|append,--reedit-message=*)
1671 __gitcomp_nl "$(__git_refs)" "" "${cur#*=}"
1672 ;;
1673 add,--*|append,--*)
1674 __gitcomp '--file= --message= --reedit-message=
1675 --reuse-message='
1676 ;;
1677 copy,--*)
1678 __gitcomp '--stdin'
1679 ;;
1680 prune,--*)
1681 __gitcomp '--dry-run --verbose'
1682 ;;
1683 prune,*)
1684 ;;
1685 *)
1686 case "${words[cword-1]}" in
1687 -m|-F)
1688 ;;
1689 *)
1690 __gitcomp_nl "$(__git_refs)"
1691 ;;
1692 esac
1693 ;;
1694 esac
1695}
1696
1697_git_pull ()
1698{
1699 __git_complete_strategy && return
1700
1701 case "$cur" in
1702 --*)
1703 __gitcomp "
1704 --rebase --no-rebase
1705 $__git_merge_options
1706 $__git_fetch_options
1707 "
1708 return
1709 ;;
1710 esac
1711 __git_complete_remote_or_refspec
1712}
1713
1714_git_push ()
1715{
1716 case "$prev" in
1717 --repo)
1718 __gitcomp_nl "$(__git_remotes)"
1719 return
1720 esac
1721 case "$cur" in
1722 --repo=*)
1723 __gitcomp_nl "$(__git_remotes)" "" "${cur##--repo=}"
1724 return
1725 ;;
1726 --*)
1727 __gitcomp "
1728 --all --mirror --tags --dry-run --force --verbose
1729 --receive-pack= --repo= --set-upstream
1730 "
1731 return
1732 ;;
1733 esac
1734 __git_complete_remote_or_refspec
1735}
1736
1737_git_rebase ()
1738{
1739 local dir="$(__gitdir)"
1740 if [ -d "$dir"/rebase-apply ] || [ -d "$dir"/rebase-merge ]; then
1741 __gitcomp "--continue --skip --abort"
1742 return
1743 fi
1744 __git_complete_strategy && return
1745 case "$cur" in
1746 --whitespace=*)
1747 __gitcomp "$__git_whitespacelist" "" "${cur##--whitespace=}"
1748 return
1749 ;;
1750 --*)
1751 __gitcomp "
1752 --onto --merge --strategy --interactive
1753 --preserve-merges --stat --no-stat
1754 --committer-date-is-author-date --ignore-date
1755 --ignore-whitespace --whitespace=
1756 --autosquash
1757 "
1758
1759 return
1760 esac
1761 __gitcomp_nl "$(__git_refs)"
1762}
1763
1764_git_reflog ()
1765{
1766 local subcommands="show delete expire"
1767 local subcommand="$(__git_find_on_cmdline "$subcommands")"
1768
1769 if [ -z "$subcommand" ]; then
1770 __gitcomp "$subcommands"
1771 else
1772 __gitcomp_nl "$(__git_refs)"
1773 fi
1774}
1775
1776__git_send_email_confirm_options="always never auto cc compose"
1777__git_send_email_suppresscc_options="author self cc bodycc sob cccmd body all"
1778
1779_git_send_email ()
1780{
1781 case "$cur" in
1782 --confirm=*)
1783 __gitcomp "
1784 $__git_send_email_confirm_options
1785 " "" "${cur##--confirm=}"
1786 return
1787 ;;
1788 --suppress-cc=*)
1789 __gitcomp "
1790 $__git_send_email_suppresscc_options
1791 " "" "${cur##--suppress-cc=}"
1792
1793 return
1794 ;;
1795 --smtp-encryption=*)
1796 __gitcomp "ssl tls" "" "${cur##--smtp-encryption=}"
1797 return
1798 ;;
1799 --*)
1800 __gitcomp "--annotate --bcc --cc --cc-cmd --chain-reply-to
1801 --compose --confirm= --dry-run --envelope-sender
1802 --from --identity
1803 --in-reply-to --no-chain-reply-to --no-signed-off-by-cc
1804 --no-suppress-from --no-thread --quiet
1805 --signed-off-by-cc --smtp-pass --smtp-server
1806 --smtp-server-port --smtp-encryption= --smtp-user
1807 --subject --suppress-cc= --suppress-from --thread --to
1808 --validate --no-validate"
1809 return
1810 ;;
1811 esac
1812 COMPREPLY=()
1813}
1814
1815_git_stage ()
1816{
1817 _git_add
1818}
1819
1820__git_config_get_set_variables ()
1821{
1822 local prevword word config_file= c=$cword
1823 while [ $c -gt 1 ]; do
1824 word="${words[c]}"
1825 case "$word" in
1826 --global|--system|--file=*)
1827 config_file="$word"
1828 break
1829 ;;
1830 -f|--file)
1831 config_file="$word $prevword"
1832 break
1833 ;;
1834 esac
1835 prevword=$word
1836 c=$((--c))
1837 done
1838
1839 git --git-dir="$(__gitdir)" config $config_file --list 2>/dev/null |
1840 while read -r line
1841 do
1842 case "$line" in
1843 *.*=*)
1844 echo "${line/=*/}"
1845 ;;
1846 esac
1847 done
1848}
1849
1850_git_config ()
1851{
1852 case "$prev" in
1853 branch.*.remote)
1854 __gitcomp_nl "$(__git_remotes)"
1855 return
1856 ;;
1857 branch.*.merge)
1858 __gitcomp_nl "$(__git_refs)"
1859 return
1860 ;;
1861 remote.*.fetch)
1862 local remote="${prev#remote.}"
1863 remote="${remote%.fetch}"
1864 if [ -z "$cur" ]; then
1865 COMPREPLY=("refs/heads/")
1866 return
1867 fi
1868 __gitcomp_nl "$(__git_refs_remotes "$remote")"
1869 return
1870 ;;
1871 remote.*.push)
1872 local remote="${prev#remote.}"
1873 remote="${remote%.push}"
1874 __gitcomp_nl "$(git --git-dir="$(__gitdir)" \
1875 for-each-ref --format='%(refname):%(refname)' \
1876 refs/heads)"
1877 return
1878 ;;
1879 pull.twohead|pull.octopus)
1880 __git_compute_merge_strategies
1881 __gitcomp "$__git_merge_strategies"
1882 return
1883 ;;
1884 color.branch|color.diff|color.interactive|\
1885 color.showbranch|color.status|color.ui)
1886 __gitcomp "always never auto"
1887 return
1888 ;;
1889 color.pager)
1890 __gitcomp "false true"
1891 return
1892 ;;
1893 color.*.*)
1894 __gitcomp "
1895 normal black red green yellow blue magenta cyan white
1896 bold dim ul blink reverse
1897 "
1898 return
1899 ;;
1900 help.format)
1901 __gitcomp "man info web html"
1902 return
1903 ;;
1904 log.date)
1905 __gitcomp "$__git_log_date_formats"
1906 return
1907 ;;
1908 sendemail.aliasesfiletype)
1909 __gitcomp "mutt mailrc pine elm gnus"
1910 return
1911 ;;
1912 sendemail.confirm)
1913 __gitcomp "$__git_send_email_confirm_options"
1914 return
1915 ;;
1916 sendemail.suppresscc)
1917 __gitcomp "$__git_send_email_suppresscc_options"
1918 return
1919 ;;
1920 --get|--get-all|--unset|--unset-all)
1921 __gitcomp_nl "$(__git_config_get_set_variables)"
1922 return
1923 ;;
1924 *.*)
1925 COMPREPLY=()
1926 return
1927 ;;
1928 esac
1929 case "$cur" in
1930 --*)
1931 __gitcomp "
1932 --global --system --file=
1933 --list --replace-all
1934 --get --get-all --get-regexp
1935 --add --unset --unset-all
1936 --remove-section --rename-section
1937 "
1938 return
1939 ;;
1940 branch.*.*)
1941 local pfx="${cur%.*}." cur_="${cur##*.}"
1942 __gitcomp "remote merge mergeoptions rebase" "$pfx" "$cur_"
1943 return
1944 ;;
1945 branch.*)
1946 local pfx="${cur%.*}." cur_="${cur#*.}"
1947 __gitcomp_nl "$(__git_heads)" "$pfx" "$cur_" "."
1948 return
1949 ;;
1950 guitool.*.*)
1951 local pfx="${cur%.*}." cur_="${cur##*.}"
1952 __gitcomp "
1953 argprompt cmd confirm needsfile noconsole norescan
1954 prompt revprompt revunmerged title
1955 " "$pfx" "$cur_"
1956 return
1957 ;;
1958 difftool.*.*)
1959 local pfx="${cur%.*}." cur_="${cur##*.}"
1960 __gitcomp "cmd path" "$pfx" "$cur_"
1961 return
1962 ;;
1963 man.*.*)
1964 local pfx="${cur%.*}." cur_="${cur##*.}"
1965 __gitcomp "cmd path" "$pfx" "$cur_"
1966 return
1967 ;;
1968 mergetool.*.*)
1969 local pfx="${cur%.*}." cur_="${cur##*.}"
1970 __gitcomp "cmd path trustExitCode" "$pfx" "$cur_"
1971 return
1972 ;;
1973 pager.*)
1974 local pfx="${cur%.*}." cur_="${cur#*.}"
1975 __git_compute_all_commands
1976 __gitcomp_nl "$__git_all_commands" "$pfx" "$cur_"
1977 return
1978 ;;
1979 remote.*.*)
1980 local pfx="${cur%.*}." cur_="${cur##*.}"
1981 __gitcomp "
1982 url proxy fetch push mirror skipDefaultUpdate
1983 receivepack uploadpack tagopt pushurl
1984 " "$pfx" "$cur_"
1985 return
1986 ;;
1987 remote.*)
1988 local pfx="${cur%.*}." cur_="${cur#*.}"
1989 __gitcomp_nl "$(__git_remotes)" "$pfx" "$cur_" "."
1990 return
1991 ;;
1992 url.*.*)
1993 local pfx="${cur%.*}." cur_="${cur##*.}"
1994 __gitcomp "insteadOf pushInsteadOf" "$pfx" "$cur_"
1995 return
1996 ;;
1997 esac
1998 __gitcomp "
1999 add.ignoreErrors
2000 advice.commitBeforeMerge
2001 advice.detachedHead
2002 advice.implicitIdentity
2003 advice.pushNonFastForward
2004 advice.resolveConflict
2005 advice.statusHints
2006 alias.
2007 am.keepcr
2008 apply.ignorewhitespace
2009 apply.whitespace
2010 branch.autosetupmerge
2011 branch.autosetuprebase
2012 browser.
2013 clean.requireForce
2014 color.branch
2015 color.branch.current
2016 color.branch.local
2017 color.branch.plain
2018 color.branch.remote
2019 color.decorate.HEAD
2020 color.decorate.branch
2021 color.decorate.remoteBranch
2022 color.decorate.stash
2023 color.decorate.tag
2024 color.diff
2025 color.diff.commit
2026 color.diff.frag
2027 color.diff.func
2028 color.diff.meta
2029 color.diff.new
2030 color.diff.old
2031 color.diff.plain
2032 color.diff.whitespace
2033 color.grep
2034 color.grep.context
2035 color.grep.filename
2036 color.grep.function
2037 color.grep.linenumber
2038 color.grep.match
2039 color.grep.selected
2040 color.grep.separator
2041 color.interactive
2042 color.interactive.error
2043 color.interactive.header
2044 color.interactive.help
2045 color.interactive.prompt
2046 color.pager
2047 color.showbranch
2048 color.status
2049 color.status.added
2050 color.status.changed
2051 color.status.header
2052 color.status.nobranch
2053 color.status.untracked
2054 color.status.updated
2055 color.ui
2056 commit.status
2057 commit.template
2058 core.abbrev
2059 core.askpass
2060 core.attributesfile
2061 core.autocrlf
2062 core.bare
2063 core.bigFileThreshold
2064 core.compression
2065 core.createObject
2066 core.deltaBaseCacheLimit
2067 core.editor
2068 core.eol
2069 core.excludesfile
2070 core.fileMode
2071 core.fsyncobjectfiles
2072 core.gitProxy
2073 core.ignoreCygwinFSTricks
2074 core.ignoreStat
2075 core.ignorecase
2076 core.logAllRefUpdates
2077 core.loosecompression
2078 core.notesRef
2079 core.packedGitLimit
2080 core.packedGitWindowSize
2081 core.pager
2082 core.preferSymlinkRefs
2083 core.preloadindex
2084 core.quotepath
2085 core.repositoryFormatVersion
2086 core.safecrlf
2087 core.sharedRepository
2088 core.sparseCheckout
2089 core.symlinks
2090 core.trustctime
2091 core.warnAmbiguousRefs
2092 core.whitespace
2093 core.worktree
2094 diff.autorefreshindex
2095 diff.external
2096 diff.ignoreSubmodules
2097 diff.mnemonicprefix
2098 diff.noprefix
2099 diff.renameLimit
2100 diff.renames
2101 diff.suppressBlankEmpty
2102 diff.tool
2103 diff.wordRegex
2104 difftool.
2105 difftool.prompt
2106 fetch.recurseSubmodules
2107 fetch.unpackLimit
2108 format.attach
2109 format.cc
2110 format.headers
2111 format.numbered
2112 format.pretty
2113 format.signature
2114 format.signoff
2115 format.subjectprefix
2116 format.suffix
2117 format.thread
2118 format.to
2119 gc.
2120 gc.aggressiveWindow
2121 gc.auto
2122 gc.autopacklimit
2123 gc.packrefs
2124 gc.pruneexpire
2125 gc.reflogexpire
2126 gc.reflogexpireunreachable
2127 gc.rerereresolved
2128 gc.rerereunresolved
2129 gitcvs.allbinary
2130 gitcvs.commitmsgannotation
2131 gitcvs.dbTableNamePrefix
2132 gitcvs.dbdriver
2133 gitcvs.dbname
2134 gitcvs.dbpass
2135 gitcvs.dbuser
2136 gitcvs.enabled
2137 gitcvs.logfile
2138 gitcvs.usecrlfattr
2139 guitool.
2140 gui.blamehistoryctx
2141 gui.commitmsgwidth
2142 gui.copyblamethreshold
2143 gui.diffcontext
2144 gui.encoding
2145 gui.fastcopyblame
2146 gui.matchtrackingbranch
2147 gui.newbranchtemplate
2148 gui.pruneduringfetch
2149 gui.spellingdictionary
2150 gui.trustmtime
2151 help.autocorrect
2152 help.browser
2153 help.format
2154 http.lowSpeedLimit
2155 http.lowSpeedTime
2156 http.maxRequests
2157 http.minSessions
2158 http.noEPSV
2159 http.postBuffer
2160 http.proxy
2161 http.sslCAInfo
2162 http.sslCAPath
2163 http.sslCert
2164 http.sslCertPasswordProtected
2165 http.sslKey
2166 http.sslVerify
2167 http.useragent
2168 i18n.commitEncoding
2169 i18n.logOutputEncoding
2170 imap.authMethod
2171 imap.folder
2172 imap.host
2173 imap.pass
2174 imap.port
2175 imap.preformattedHTML
2176 imap.sslverify
2177 imap.tunnel
2178 imap.user
2179 init.templatedir
2180 instaweb.browser
2181 instaweb.httpd
2182 instaweb.local
2183 instaweb.modulepath
2184 instaweb.port
2185 interactive.singlekey
2186 log.date
2187 log.decorate
2188 log.showroot
2189 mailmap.file
2190 man.
2191 man.viewer
2192 merge.
2193 merge.conflictstyle
2194 merge.log
2195 merge.renameLimit
2196 merge.renormalize
2197 merge.stat
2198 merge.tool
2199 merge.verbosity
2200 mergetool.
2201 mergetool.keepBackup
2202 mergetool.keepTemporaries
2203 mergetool.prompt
2204 notes.displayRef
2205 notes.rewrite.
2206 notes.rewrite.amend
2207 notes.rewrite.rebase
2208 notes.rewriteMode
2209 notes.rewriteRef
2210 pack.compression
2211 pack.deltaCacheLimit
2212 pack.deltaCacheSize
2213 pack.depth
2214 pack.indexVersion
2215 pack.packSizeLimit
2216 pack.threads
2217 pack.window
2218 pack.windowMemory
2219 pager.
2220 pretty.
2221 pull.octopus
2222 pull.twohead
2223 push.default
2224 rebase.autosquash
2225 rebase.stat
2226 receive.autogc
2227 receive.denyCurrentBranch
2228 receive.denyDeleteCurrent
2229 receive.denyDeletes
2230 receive.denyNonFastForwards
2231 receive.fsckObjects
2232 receive.unpackLimit
2233 receive.updateserverinfo
2234 remotes.
2235 repack.usedeltabaseoffset
2236 rerere.autoupdate
2237 rerere.enabled
2238 sendemail.
2239 sendemail.aliasesfile
2240 sendemail.aliasfiletype
2241 sendemail.bcc
2242 sendemail.cc
2243 sendemail.cccmd
2244 sendemail.chainreplyto
2245 sendemail.confirm
2246 sendemail.envelopesender
2247 sendemail.from
2248 sendemail.identity
2249 sendemail.multiedit
2250 sendemail.signedoffbycc
2251 sendemail.smtpdomain
2252 sendemail.smtpencryption
2253 sendemail.smtppass
2254 sendemail.smtpserver
2255 sendemail.smtpserveroption
2256 sendemail.smtpserverport
2257 sendemail.smtpuser
2258 sendemail.suppresscc
2259 sendemail.suppressfrom
2260 sendemail.thread
2261 sendemail.to
2262 sendemail.validate
2263 showbranch.default
2264 status.relativePaths
2265 status.showUntrackedFiles
2266 status.submodulesummary
2267 submodule.
2268 tar.umask
2269 transfer.unpackLimit
2270 url.
2271 user.email
2272 user.name
2273 user.signingkey
2274 web.browser
2275 branch. remote.
2276 "
2277}
2278
2279_git_remote ()
2280{
2281 local subcommands="add rename rm set-head set-branches set-url show prune update"
2282 local subcommand="$(__git_find_on_cmdline "$subcommands")"
2283 if [ -z "$subcommand" ]; then
2284 __gitcomp "$subcommands"
2285 return
2286 fi
2287
2288 case "$subcommand" in
2289 rename|rm|set-url|show|prune)
2290 __gitcomp_nl "$(__git_remotes)"
2291 ;;
2292 set-head|set-branches)
2293 __git_complete_remote_or_refspec
2294 ;;
2295 update)
2296 local i c='' IFS=$'\n'
2297 for i in $(git --git-dir="$(__gitdir)" config --get-regexp "remotes\..*" 2>/dev/null); do
2298 i="${i#remotes.}"
2299 c="$c ${i/ */}"
2300 done
2301 __gitcomp "$c"
2302 ;;
2303 *)
2304 COMPREPLY=()
2305 ;;
2306 esac
2307}
2308
2309_git_replace ()
2310{
2311 __gitcomp_nl "$(__git_refs)"
2312}
2313
2314_git_reset ()
2315{
2316 __git_has_doubledash && return
2317
2318 case "$cur" in
2319 --*)
2320 __gitcomp "--merge --mixed --hard --soft --patch"
2321 return
2322 ;;
2323 esac
2324 __gitcomp_nl "$(__git_refs)"
2325}
2326
2327_git_revert ()
2328{
2329 case "$cur" in
2330 --*)
2331 __gitcomp "--edit --mainline --no-edit --no-commit --signoff"
2332 return
2333 ;;
2334 esac
2335 __gitcomp_nl "$(__git_refs)"
2336}
2337
2338_git_rm ()
2339{
2340 __git_has_doubledash && return
2341
2342 case "$cur" in
2343 --*)
2344 __gitcomp "--cached --dry-run --ignore-unmatch --quiet"
2345 return
2346 ;;
2347 esac
2348 COMPREPLY=()
2349}
2350
2351_git_shortlog ()
2352{
2353 __git_has_doubledash && return
2354
2355 case "$cur" in
2356 --*)
2357 __gitcomp "
2358 $__git_log_common_options
2359 $__git_log_shortlog_options
2360 --numbered --summary
2361 "
2362 return
2363 ;;
2364 esac
2365 __git_complete_revlist
2366}
2367
2368_git_show ()
2369{
2370 __git_has_doubledash && return
2371
2372 case "$cur" in
2373 --pretty=*|--format=*)
2374 __gitcomp "$__git_log_pretty_formats $(__git_pretty_aliases)
2375 " "" "${cur#*=}"
2376 return
2377 ;;
2378 --*)
2379 __gitcomp "--pretty= --format= --abbrev-commit --oneline
2380 $__git_diff_common_options
2381 "
2382 return
2383 ;;
2384 esac
2385 __git_complete_file
2386}
2387
2388_git_show_branch ()
2389{
2390 case "$cur" in
2391 --*)
2392 __gitcomp "
2393 --all --remotes --topo-order --current --more=
2394 --list --independent --merge-base --no-name
2395 --color --no-color
2396 --sha1-name --sparse --topics --reflog
2397 "
2398 return
2399 ;;
2400 esac
2401 __git_complete_revlist
2402}
2403
2404_git_stash ()
2405{
2406 local save_opts='--keep-index --no-keep-index --quiet --patch'
2407 local subcommands='save list show apply clear drop pop create branch'
2408 local subcommand="$(__git_find_on_cmdline "$subcommands")"
2409 if [ -z "$subcommand" ]; then
2410 case "$cur" in
2411 --*)
2412 __gitcomp "$save_opts"
2413 ;;
2414 *)
2415 if [ -z "$(__git_find_on_cmdline "$save_opts")" ]; then
2416 __gitcomp "$subcommands"
2417 else
2418 COMPREPLY=()
2419 fi
2420 ;;
2421 esac
2422 else
2423 case "$subcommand,$cur" in
2424 save,--*)
2425 __gitcomp "$save_opts"
2426 ;;
2427 apply,--*|pop,--*)
2428 __gitcomp "--index --quiet"
2429 ;;
2430 show,--*|drop,--*|branch,--*)
2431 COMPREPLY=()
2432 ;;
2433 show,*|apply,*|drop,*|pop,*|branch,*)
2434 __gitcomp_nl "$(git --git-dir="$(__gitdir)" stash list \
2435 | sed -n -e 's/:.*//p')"
2436 ;;
2437 *)
2438 COMPREPLY=()
2439 ;;
2440 esac
2441 fi
2442}
2443
2444_git_submodule ()
2445{
2446 __git_has_doubledash && return
2447
2448 local subcommands="add status init update summary foreach sync"
2449 if [ -z "$(__git_find_on_cmdline "$subcommands")" ]; then
2450 case "$cur" in
2451 --*)
2452 __gitcomp "--quiet --cached"
2453 ;;
2454 *)
2455 __gitcomp "$subcommands"
2456 ;;
2457 esac
2458 return
2459 fi
2460}
2461
2462_git_svn ()
2463{
2464 local subcommands="
2465 init fetch clone rebase dcommit log find-rev
2466 set-tree commit-diff info create-ignore propget
2467 proplist show-ignore show-externals branch tag blame
2468 migrate mkdirs reset gc
2469 "
2470 local subcommand="$(__git_find_on_cmdline "$subcommands")"
2471 if [ -z "$subcommand" ]; then
2472 __gitcomp "$subcommands"
2473 else
2474 local remote_opts="--username= --config-dir= --no-auth-cache"
2475 local fc_opts="
2476 --follow-parent --authors-file= --repack=
2477 --no-metadata --use-svm-props --use-svnsync-props
2478 --log-window-size= --no-checkout --quiet
2479 --repack-flags --use-log-author --localtime
2480 --ignore-paths= $remote_opts
2481 "
2482 local init_opts="
2483 --template= --shared= --trunk= --tags=
2484 --branches= --stdlayout --minimize-url
2485 --no-metadata --use-svm-props --use-svnsync-props
2486 --rewrite-root= --prefix= --use-log-author
2487 --add-author-from $remote_opts
2488 "
2489 local cmt_opts="
2490 --edit --rmdir --find-copies-harder --copy-similarity=
2491 "
2492
2493 case "$subcommand,$cur" in
2494 fetch,--*)
2495 __gitcomp "--revision= --fetch-all $fc_opts"
2496 ;;
2497 clone,--*)
2498 __gitcomp "--revision= $fc_opts $init_opts"
2499 ;;
2500 init,--*)
2501 __gitcomp "$init_opts"
2502 ;;
2503 dcommit,--*)
2504 __gitcomp "
2505 --merge --strategy= --verbose --dry-run
2506 --fetch-all --no-rebase --commit-url
2507 --revision --interactive $cmt_opts $fc_opts
2508 "
2509 ;;
2510 set-tree,--*)
2511 __gitcomp "--stdin $cmt_opts $fc_opts"
2512 ;;
2513 create-ignore,--*|propget,--*|proplist,--*|show-ignore,--*|\
2514 show-externals,--*|mkdirs,--*)
2515 __gitcomp "--revision="
2516 ;;
2517 log,--*)
2518 __gitcomp "
2519 --limit= --revision= --verbose --incremental
2520 --oneline --show-commit --non-recursive
2521 --authors-file= --color
2522 "
2523 ;;
2524 rebase,--*)
2525 __gitcomp "
2526 --merge --verbose --strategy= --local
2527 --fetch-all --dry-run $fc_opts
2528 "
2529 ;;
2530 commit-diff,--*)
2531 __gitcomp "--message= --file= --revision= $cmt_opts"
2532 ;;
2533 info,--*)
2534 __gitcomp "--url"
2535 ;;
2536 branch,--*)
2537 __gitcomp "--dry-run --message --tag"
2538 ;;
2539 tag,--*)
2540 __gitcomp "--dry-run --message"
2541 ;;
2542 blame,--*)
2543 __gitcomp "--git-format"
2544 ;;
2545 migrate,--*)
2546 __gitcomp "
2547 --config-dir= --ignore-paths= --minimize
2548 --no-auth-cache --username=
2549 "
2550 ;;
2551 reset,--*)
2552 __gitcomp "--revision= --parent"
2553 ;;
2554 *)
2555 COMPREPLY=()
2556 ;;
2557 esac
2558 fi
2559}
2560
2561_git_tag ()
2562{
2563 local i c=1 f=0
2564 while [ $c -lt $cword ]; do
2565 i="${words[c]}"
2566 case "$i" in
2567 -d|-v)
2568 __gitcomp_nl "$(__git_tags)"
2569 return
2570 ;;
2571 -f)
2572 f=1
2573 ;;
2574 esac
2575 ((c++))
2576 done
2577
2578 case "$prev" in
2579 -m|-F)
2580 COMPREPLY=()
2581 ;;
2582 -*|tag)
2583 if [ $f = 1 ]; then
2584 __gitcomp_nl "$(__git_tags)"
2585 else
2586 COMPREPLY=()
2587 fi
2588 ;;
2589 *)
2590 __gitcomp_nl "$(__git_refs)"
2591 ;;
2592 esac
2593}
2594
2595_git_whatchanged ()
2596{
2597 _git_log
2598}
2599
2600_git ()
2601{
2602 local i c=1 command __git_dir
2603
2604 if [[ -n ${ZSH_VERSION-} ]]; then
2605 emulate -L bash
2606 setopt KSH_TYPESET
2607
2608 # workaround zsh's bug that leaves 'words' as a special
2609 # variable in versions < 4.3.12
2610 typeset -h words
2611
2612 # workaround zsh's bug that quotes spaces in the COMPREPLY
2613 # array if IFS doesn't contain spaces.
2614 typeset -h IFS
2615 fi
2616
2617 local cur words cword prev
2618 _get_comp_words_by_ref -n =: cur words cword prev
2619 while [ $c -lt $cword ]; do
2620 i="${words[c]}"
2621 case "$i" in
2622 --git-dir=*) __git_dir="${i#--git-dir=}" ;;
2623 --bare) __git_dir="." ;;
2624 --version|-p|--paginate) ;;
2625 --help) command="help"; break ;;
2626 *) command="$i"; break ;;
2627 esac
2628 ((c++))
2629 done
2630
2631 if [ -z "$command" ]; then
2632 case "$cur" in
2633 --*) __gitcomp "
2634 --paginate
2635 --no-pager
2636 --git-dir=
2637 --bare
2638 --version
2639 --exec-path
2640 --html-path
2641 --work-tree=
2642 --namespace=
2643 --help
2644 "
2645 ;;
2646 *) __git_compute_porcelain_commands
2647 __gitcomp "$__git_porcelain_commands $(__git_aliases)" ;;
2648 esac
2649 return
2650 fi
2651
2652 local completion_func="_git_${command//-/_}"
2653 declare -f $completion_func >/dev/null && $completion_func && return
2654
2655 local expansion=$(__git_aliased_command "$command")
2656 if [ -n "$expansion" ]; then
2657 completion_func="_git_${expansion//-/_}"
2658 declare -f $completion_func >/dev/null && $completion_func
2659 fi
2660}
2661
2662_gitk ()
2663{
2664 if [[ -n ${ZSH_VERSION-} ]]; then
2665 emulate -L bash
2666 setopt KSH_TYPESET
2667
2668 # workaround zsh's bug that leaves 'words' as a special
2669 # variable in versions < 4.3.12
2670 typeset -h words
2671
2672 # workaround zsh's bug that quotes spaces in the COMPREPLY
2673 # array if IFS doesn't contain spaces.
2674 typeset -h IFS
2675 fi
2676
2677 local cur words cword prev
2678 _get_comp_words_by_ref -n =: cur words cword prev
2679
2680 __git_has_doubledash && return
2681
2682 local g="$(__gitdir)"
2683 local merge=""
2684 if [ -f "$g/MERGE_HEAD" ]; then
2685 merge="--merge"
2686 fi
2687 case "$cur" in
2688 --*)
2689 __gitcomp "
2690 $__git_log_common_options
2691 $__git_log_gitk_options
2692 $merge
2693 "
2694 return
2695 ;;
2696 esac
2697 __git_complete_revlist
2698}
2699
2700complete -o bashdefault -o default -o nospace -F _git git 2>/dev/null \
2701 || complete -o default -o nospace -F _git git
2702complete -o bashdefault -o default -o nospace -F _gitk gitk 2>/dev/null \
2703 || complete -o default -o nospace -F _gitk gitk
2704
2705# The following are necessary only for Cygwin, and only are needed
2706# when the user has tab-completed the executable name and consequently
2707# included the '.exe' suffix.
2708#
2709if [ Cygwin = "$(uname -o 2>/dev/null)" ]; then
2710complete -o bashdefault -o default -o nospace -F _git git.exe 2>/dev/null \
2711 || complete -o default -o nospace -F _git git.exe
2712fi