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