1#
2# bash completion support for core Git.
3#
4# Copyright (C) 2006,2007 Shawn O. Pearce <spearce@spearce.org>
5# Conceptually based on gitcompletion (http://gitweb.hawaga.org.uk/).
6# Distributed under the GNU General Public License, version 2.0.
7#
8# The contained completion routines provide support for completing:
9#
10# *) local and remote branch names
11# *) local and remote tag names
12# *) .git/remotes file names
13# *) git 'subcommands'
14# *) tree paths within 'ref:path/to/file' expressions
15# *) common --long-options
16#
17# To use these routines:
18#
19# 1) Copy this file to somewhere (e.g. ~/.git-completion.sh).
20# 2) Added the following line to your .bashrc:
21# source ~/.git-completion.sh
22#
23# 3) You may want to make sure the git executable is available
24# in your PATH before this script is sourced, as some caching
25# is performed while the script loads. If git isn't found
26# at source time then all lookups will be done on demand,
27# which may be slightly slower.
28#
29# 4) Consider changing your PS1 to also show the current branch:
30# PS1='[\u@\h \W$(__git_ps1 " (%s)")]\$ '
31#
32# The argument to __git_ps1 will be displayed only if you
33# are currently in a git repository. The %s token will be
34# the name of the current branch.
35#
36# To submit patches:
37#
38# *) Read Documentation/SubmittingPatches
39# *) Send all patches to the current maintainer:
40#
41# "Shawn O. Pearce" <spearce@spearce.org>
42#
43# *) Always CC the Git mailing list:
44#
45# git@vger.kernel.org
46#
47
48case "$COMP_WORDBREAKS" in
49*:*) : great ;;
50*) COMP_WORDBREAKS="$COMP_WORDBREAKS:"
51esac
52
53__gitdir ()
54{
55 if [ -z "$1" ]; then
56 if [ -n "$__git_dir" ]; then
57 echo "$__git_dir"
58 elif [ -d .git ]; then
59 echo .git
60 else
61 git rev-parse --git-dir 2>/dev/null
62 fi
63 elif [ -d "$1/.git" ]; then
64 echo "$1/.git"
65 else
66 echo "$1"
67 fi
68}
69
70__git_ps1 ()
71{
72 local g="$(git rev-parse --git-dir 2>/dev/null)"
73 if [ -n "$g" ]; then
74 local r
75 local b
76 if [ -d "$g/rebase-apply" ]
77 then
78 if test -f "$g/rebase-apply/rebasing"
79 then
80 r="|REBASE"
81 elif test -f "$g/rebase-apply/applying"
82 then
83 r="|AM"
84 else
85 r="|AM/REBASE"
86 fi
87 b="$(git symbolic-ref HEAD 2>/dev/null)"
88 elif [ -f "$g/rebase-merge/interactive" ]
89 then
90 r="|REBASE-i"
91 b="$(cat "$g/rebase-merge/head-name")"
92 elif [ -d "$g/rebase-merge" ]
93 then
94 r="|REBASE-m"
95 b="$(cat "$g/rebase-merge/head-name")"
96 elif [ -f "$g/MERGE_HEAD" ]
97 then
98 r="|MERGING"
99 b="$(git symbolic-ref HEAD 2>/dev/null)"
100 else
101 if [ -f "$g/BISECT_LOG" ]
102 then
103 r="|BISECTING"
104 fi
105 if ! b="$(git symbolic-ref HEAD 2>/dev/null)"
106 then
107 if ! b="$(git describe --exact-match HEAD 2>/dev/null)"
108 then
109 b="$(cut -c1-7 "$g/HEAD")..."
110 fi
111 fi
112 fi
113
114 if [ -n "$1" ]; then
115 printf "$1" "${b##refs/heads/}$r"
116 else
117 printf " (%s)" "${b##refs/heads/}$r"
118 fi
119 fi
120}
121
122__gitcomp_1 ()
123{
124 local c IFS=' '$'\t'$'\n'
125 for c in $1; do
126 case "$c$2" in
127 --*=*) printf %s$'\n' "$c$2" ;;
128 *.) printf %s$'\n' "$c$2" ;;
129 *) printf %s$'\n' "$c$2 " ;;
130 esac
131 done
132}
133
134__gitcomp ()
135{
136 local cur="${COMP_WORDS[COMP_CWORD]}"
137 if [ $# -gt 2 ]; then
138 cur="$3"
139 fi
140 case "$cur" in
141 --*=)
142 COMPREPLY=()
143 ;;
144 *)
145 local IFS=$'\n'
146 COMPREPLY=($(compgen -P "$2" \
147 -W "$(__gitcomp_1 "$1" "$4")" \
148 -- "$cur"))
149 ;;
150 esac
151}
152
153__git_heads ()
154{
155 local cmd i is_hash=y dir="$(__gitdir "$1")"
156 if [ -d "$dir" ]; then
157 for i in $(git --git-dir="$dir" \
158 for-each-ref --format='%(refname)' \
159 refs/heads ); do
160 echo "${i#refs/heads/}"
161 done
162 return
163 fi
164 for i in $(git ls-remote "$1" 2>/dev/null); do
165 case "$is_hash,$i" in
166 y,*) is_hash=n ;;
167 n,*^{}) is_hash=y ;;
168 n,refs/heads/*) is_hash=y; echo "${i#refs/heads/}" ;;
169 n,*) is_hash=y; echo "$i" ;;
170 esac
171 done
172}
173
174__git_tags ()
175{
176 local cmd i is_hash=y dir="$(__gitdir "$1")"
177 if [ -d "$dir" ]; then
178 for i in $(git --git-dir="$dir" \
179 for-each-ref --format='%(refname)' \
180 refs/tags ); do
181 echo "${i#refs/tags/}"
182 done
183 return
184 fi
185 for i in $(git ls-remote "$1" 2>/dev/null); do
186 case "$is_hash,$i" in
187 y,*) is_hash=n ;;
188 n,*^{}) is_hash=y ;;
189 n,refs/tags/*) is_hash=y; echo "${i#refs/tags/}" ;;
190 n,*) is_hash=y; echo "$i" ;;
191 esac
192 done
193}
194
195__git_refs ()
196{
197 local cmd i is_hash=y dir="$(__gitdir "$1")"
198 if [ -d "$dir" ]; then
199 if [ -e "$dir/HEAD" ]; then echo HEAD; fi
200 for i in $(git --git-dir="$dir" \
201 for-each-ref --format='%(refname)' \
202 refs/tags refs/heads refs/remotes); do
203 case "$i" in
204 refs/tags/*) echo "${i#refs/tags/}" ;;
205 refs/heads/*) echo "${i#refs/heads/}" ;;
206 refs/remotes/*) echo "${i#refs/remotes/}" ;;
207 *) echo "$i" ;;
208 esac
209 done
210 return
211 fi
212 for i in $(git ls-remote "$dir" 2>/dev/null); do
213 case "$is_hash,$i" in
214 y,*) is_hash=n ;;
215 n,*^{}) is_hash=y ;;
216 n,refs/tags/*) is_hash=y; echo "${i#refs/tags/}" ;;
217 n,refs/heads/*) is_hash=y; echo "${i#refs/heads/}" ;;
218 n,refs/remotes/*) is_hash=y; echo "${i#refs/remotes/}" ;;
219 n,*) is_hash=y; echo "$i" ;;
220 esac
221 done
222}
223
224__git_refs2 ()
225{
226 local i
227 for i in $(__git_refs "$1"); do
228 echo "$i:$i"
229 done
230}
231
232__git_refs_remotes ()
233{
234 local cmd i is_hash=y
235 for i in $(git ls-remote "$1" 2>/dev/null); do
236 case "$is_hash,$i" in
237 n,refs/heads/*)
238 is_hash=y
239 echo "$i:refs/remotes/$1/${i#refs/heads/}"
240 ;;
241 y,*) is_hash=n ;;
242 n,*^{}) is_hash=y ;;
243 n,refs/tags/*) is_hash=y;;
244 n,*) is_hash=y; ;;
245 esac
246 done
247}
248
249__git_remotes ()
250{
251 local i ngoff IFS=$'\n' d="$(__gitdir)"
252 shopt -q nullglob || ngoff=1
253 shopt -s nullglob
254 for i in "$d/remotes"/*; do
255 echo ${i#$d/remotes/}
256 done
257 [ "$ngoff" ] && shopt -u nullglob
258 for i in $(git --git-dir="$d" config --list); do
259 case "$i" in
260 remote.*.url=*)
261 i="${i#remote.}"
262 echo "${i/.url=*/}"
263 ;;
264 esac
265 done
266}
267
268__git_merge_strategies ()
269{
270 if [ -n "$__git_merge_strategylist" ]; then
271 echo "$__git_merge_strategylist"
272 return
273 fi
274 git merge -s help 2>&1 |
275 sed -n -e '/[Aa]vailable strategies are: /,/^$/{
276 s/\.$//
277 s/.*://
278 s/^[ ]*//
279 s/[ ]*$//
280 p
281 }'
282}
283__git_merge_strategylist=
284__git_merge_strategylist=$(__git_merge_strategies 2>/dev/null)
285
286__git_complete_file ()
287{
288 local pfx ls ref cur="${COMP_WORDS[COMP_CWORD]}"
289 case "$cur" in
290 ?*:*)
291 ref="${cur%%:*}"
292 cur="${cur#*:}"
293 case "$cur" in
294 ?*/*)
295 pfx="${cur%/*}"
296 cur="${cur##*/}"
297 ls="$ref:$pfx"
298 pfx="$pfx/"
299 ;;
300 *)
301 ls="$ref"
302 ;;
303 esac
304
305 case "$COMP_WORDBREAKS" in
306 *:*) : great ;;
307 *) pfx="$ref:$pfx" ;;
308 esac
309
310 local IFS=$'\n'
311 COMPREPLY=($(compgen -P "$pfx" \
312 -W "$(git --git-dir="$(__gitdir)" ls-tree "$ls" \
313 | sed '/^100... blob /{
314 s,^.* ,,
315 s,$, ,
316 }
317 /^120000 blob /{
318 s,^.* ,,
319 s,$, ,
320 }
321 /^040000 tree /{
322 s,^.* ,,
323 s,$,/,
324 }
325 s/^.* //')" \
326 -- "$cur"))
327 ;;
328 *)
329 __gitcomp "$(__git_refs)"
330 ;;
331 esac
332}
333
334__git_complete_revlist ()
335{
336 local pfx cur="${COMP_WORDS[COMP_CWORD]}"
337 case "$cur" in
338 *...*)
339 pfx="${cur%...*}..."
340 cur="${cur#*...}"
341 __gitcomp "$(__git_refs)" "$pfx" "$cur"
342 ;;
343 *..*)
344 pfx="${cur%..*}.."
345 cur="${cur#*..}"
346 __gitcomp "$(__git_refs)" "$pfx" "$cur"
347 ;;
348 *)
349 __gitcomp "$(__git_refs)"
350 ;;
351 esac
352}
353
354__git_all_commands ()
355{
356 if [ -n "$__git_all_commandlist" ]; then
357 echo "$__git_all_commandlist"
358 return
359 fi
360 local i IFS=" "$'\n'
361 for i in $(git help -a|egrep '^ ')
362 do
363 case $i in
364 *--*) : helper pattern;;
365 *) echo $i;;
366 esac
367 done
368}
369__git_all_commandlist=
370__git_all_commandlist="$(__git_all_commands 2>/dev/null)"
371
372__git_porcelain_commands ()
373{
374 if [ -n "$__git_porcelain_commandlist" ]; then
375 echo "$__git_porcelain_commandlist"
376 return
377 fi
378 local i IFS=" "$'\n'
379 for i in "help" $(__git_all_commands)
380 do
381 case $i in
382 *--*) : helper pattern;;
383 applymbox) : ask gittus;;
384 applypatch) : ask gittus;;
385 archimport) : import;;
386 cat-file) : plumbing;;
387 check-attr) : plumbing;;
388 check-ref-format) : plumbing;;
389 checkout-index) : plumbing;;
390 commit-tree) : plumbing;;
391 count-objects) : infrequent;;
392 cvsexportcommit) : export;;
393 cvsimport) : import;;
394 cvsserver) : daemon;;
395 daemon) : daemon;;
396 diff-files) : plumbing;;
397 diff-index) : plumbing;;
398 diff-tree) : plumbing;;
399 fast-import) : import;;
400 fast-export) : export;;
401 fsck-objects) : plumbing;;
402 fetch-pack) : plumbing;;
403 fmt-merge-msg) : plumbing;;
404 for-each-ref) : plumbing;;
405 hash-object) : plumbing;;
406 http-*) : transport;;
407 index-pack) : plumbing;;
408 init-db) : deprecated;;
409 local-fetch) : plumbing;;
410 lost-found) : infrequent;;
411 ls-files) : plumbing;;
412 ls-remote) : plumbing;;
413 ls-tree) : plumbing;;
414 mailinfo) : plumbing;;
415 mailsplit) : plumbing;;
416 merge-*) : plumbing;;
417 mktree) : plumbing;;
418 mktag) : plumbing;;
419 pack-objects) : plumbing;;
420 pack-redundant) : plumbing;;
421 pack-refs) : plumbing;;
422 parse-remote) : plumbing;;
423 patch-id) : plumbing;;
424 peek-remote) : plumbing;;
425 prune) : plumbing;;
426 prune-packed) : plumbing;;
427 quiltimport) : import;;
428 read-tree) : plumbing;;
429 receive-pack) : plumbing;;
430 reflog) : plumbing;;
431 repo-config) : deprecated;;
432 rerere) : plumbing;;
433 rev-list) : plumbing;;
434 rev-parse) : plumbing;;
435 runstatus) : plumbing;;
436 sh-setup) : internal;;
437 shell) : daemon;;
438 show-ref) : plumbing;;
439 send-pack) : plumbing;;
440 show-index) : plumbing;;
441 ssh-*) : transport;;
442 stripspace) : plumbing;;
443 symbolic-ref) : plumbing;;
444 tar-tree) : deprecated;;
445 unpack-file) : plumbing;;
446 unpack-objects) : plumbing;;
447 update-index) : plumbing;;
448 update-ref) : plumbing;;
449 update-server-info) : daemon;;
450 upload-archive) : plumbing;;
451 upload-pack) : plumbing;;
452 write-tree) : plumbing;;
453 var) : infrequent;;
454 verify-pack) : infrequent;;
455 verify-tag) : plumbing;;
456 *) echo $i;;
457 esac
458 done
459}
460__git_porcelain_commandlist=
461__git_porcelain_commandlist="$(__git_porcelain_commands 2>/dev/null)"
462
463__git_aliases ()
464{
465 local i IFS=$'\n'
466 for i in $(git --git-dir="$(__gitdir)" config --list); do
467 case "$i" in
468 alias.*)
469 i="${i#alias.}"
470 echo "${i/=*/}"
471 ;;
472 esac
473 done
474}
475
476__git_aliased_command ()
477{
478 local word cmdline=$(git --git-dir="$(__gitdir)" \
479 config --get "alias.$1")
480 for word in $cmdline; do
481 if [ "${word##-*}" ]; then
482 echo $word
483 return
484 fi
485 done
486}
487
488__git_find_subcommand ()
489{
490 local word subcommand c=1
491
492 while [ $c -lt $COMP_CWORD ]; do
493 word="${COMP_WORDS[c]}"
494 for subcommand in $1; do
495 if [ "$subcommand" = "$word" ]; then
496 echo "$subcommand"
497 return
498 fi
499 done
500 c=$((++c))
501 done
502}
503
504__git_has_doubledash ()
505{
506 local c=1
507 while [ $c -lt $COMP_CWORD ]; do
508 if [ "--" = "${COMP_WORDS[c]}" ]; then
509 return 0
510 fi
511 c=$((++c))
512 done
513 return 1
514}
515
516__git_whitespacelist="nowarn warn error error-all fix"
517
518_git_am ()
519{
520 local cur="${COMP_WORDS[COMP_CWORD]}" dir="$(__gitdir)"
521 if [ -d "$dir"/rebase-apply ]; then
522 __gitcomp "--skip --resolved --abort"
523 return
524 fi
525 case "$cur" in
526 --whitespace=*)
527 __gitcomp "$__git_whitespacelist" "" "${cur##--whitespace=}"
528 return
529 ;;
530 --*)
531 __gitcomp "
532 --signoff --utf8 --binary --3way --interactive
533 --whitespace=
534 "
535 return
536 esac
537 COMPREPLY=()
538}
539
540_git_apply ()
541{
542 local cur="${COMP_WORDS[COMP_CWORD]}"
543 case "$cur" in
544 --whitespace=*)
545 __gitcomp "$__git_whitespacelist" "" "${cur##--whitespace=}"
546 return
547 ;;
548 --*)
549 __gitcomp "
550 --stat --numstat --summary --check --index
551 --cached --index-info --reverse --reject --unidiff-zero
552 --apply --no-add --exclude=
553 --whitespace= --inaccurate-eof --verbose
554 "
555 return
556 esac
557 COMPREPLY=()
558}
559
560_git_add ()
561{
562 __git_has_doubledash && return
563
564 local cur="${COMP_WORDS[COMP_CWORD]}"
565 case "$cur" in
566 --*)
567 __gitcomp "
568 --interactive --refresh --patch --update --dry-run
569 --ignore-errors
570 "
571 return
572 esac
573 COMPREPLY=()
574}
575
576_git_archive ()
577{
578 local cur="${COMP_WORDS[COMP_CWORD]}"
579 case "$cur" in
580 --format=*)
581 __gitcomp "$(git archive --list)" "" "${cur##--format=}"
582 return
583 ;;
584 --remote=*)
585 __gitcomp "$(__git_remotes)" "" "${cur##--remote=}"
586 return
587 ;;
588 --*)
589 __gitcomp "
590 --format= --list --verbose
591 --prefix= --remote= --exec=
592 "
593 return
594 ;;
595 esac
596 __git_complete_file
597}
598
599_git_bisect ()
600{
601 __git_has_doubledash && return
602
603 local subcommands="start bad good skip reset visualize replay log run"
604 local subcommand="$(__git_find_subcommand "$subcommands")"
605 if [ -z "$subcommand" ]; then
606 __gitcomp "$subcommands"
607 return
608 fi
609
610 case "$subcommand" in
611 bad|good|reset|skip)
612 __gitcomp "$(__git_refs)"
613 ;;
614 *)
615 COMPREPLY=()
616 ;;
617 esac
618}
619
620_git_branch ()
621{
622 local i c=1 only_local_ref="n" has_r="n"
623
624 while [ $c -lt $COMP_CWORD ]; do
625 i="${COMP_WORDS[c]}"
626 case "$i" in
627 -d|-m) only_local_ref="y" ;;
628 -r) has_r="y" ;;
629 esac
630 c=$((++c))
631 done
632
633 case "${COMP_WORDS[COMP_CWORD]}" in
634 --*=*) COMPREPLY=() ;;
635 --*)
636 __gitcomp "
637 --color --no-color --verbose --abbrev= --no-abbrev
638 --track --no-track --contains --merged --no-merged
639 "
640 ;;
641 *)
642 if [ $only_local_ref = "y" -a $has_r = "n" ]; then
643 __gitcomp "$(__git_heads)"
644 else
645 __gitcomp "$(__git_refs)"
646 fi
647 ;;
648 esac
649}
650
651_git_bundle ()
652{
653 local cmd="${COMP_WORDS[2]}"
654 case "$COMP_CWORD" in
655 2)
656 __gitcomp "create list-heads verify unbundle"
657 ;;
658 3)
659 # looking for a file
660 ;;
661 *)
662 case "$cmd" in
663 create)
664 __git_complete_revlist
665 ;;
666 esac
667 ;;
668 esac
669}
670
671_git_checkout ()
672{
673 __git_has_doubledash && return
674
675 __gitcomp "$(__git_refs)"
676}
677
678_git_cherry ()
679{
680 __gitcomp "$(__git_refs)"
681}
682
683_git_cherry_pick ()
684{
685 local cur="${COMP_WORDS[COMP_CWORD]}"
686 case "$cur" in
687 --*)
688 __gitcomp "--edit --no-commit"
689 ;;
690 *)
691 __gitcomp "$(__git_refs)"
692 ;;
693 esac
694}
695
696_git_clean ()
697{
698 __git_has_doubledash && return
699
700 local cur="${COMP_WORDS[COMP_CWORD]}"
701 case "$cur" in
702 --*)
703 __gitcomp "--dry-run --quiet"
704 return
705 ;;
706 esac
707 COMPREPLY=()
708}
709
710_git_clone ()
711{
712 local cur="${COMP_WORDS[COMP_CWORD]}"
713 case "$cur" in
714 --*)
715 __gitcomp "
716 --local
717 --no-hardlinks
718 --shared
719 --reference
720 --quiet
721 --no-checkout
722 --bare
723 --mirror
724 --origin
725 --upload-pack
726 --template=
727 --depth
728 "
729 return
730 ;;
731 esac
732 COMPREPLY=()
733}
734
735_git_commit ()
736{
737 __git_has_doubledash && return
738
739 local cur="${COMP_WORDS[COMP_CWORD]}"
740 case "$cur" in
741 --*)
742 __gitcomp "
743 --all --author= --signoff --verify --no-verify
744 --edit --amend --include --only --interactive
745 "
746 return
747 esac
748 COMPREPLY=()
749}
750
751_git_describe ()
752{
753 local cur="${COMP_WORDS[COMP_CWORD]}"
754 case "$cur" in
755 --*)
756 __gitcomp "
757 --all --tags --contains --abbrev= --candidates=
758 --exact-match --debug --long --match --always
759 "
760 return
761 esac
762 __gitcomp "$(__git_refs)"
763}
764
765_git_diff ()
766{
767 __git_has_doubledash && return
768
769 local cur="${COMP_WORDS[COMP_CWORD]}"
770 case "$cur" in
771 --*)
772 __gitcomp "--cached --stat --numstat --shortstat --summary
773 --patch-with-stat --name-only --name-status --color
774 --no-color --color-words --no-renames --check
775 --full-index --binary --abbrev --diff-filter=
776 --find-copies-harder --pickaxe-all --pickaxe-regex
777 --text --ignore-space-at-eol --ignore-space-change
778 --ignore-all-space --exit-code --quiet --ext-diff
779 --no-ext-diff
780 --no-prefix --src-prefix= --dst-prefix=
781 --base --ours --theirs
782 "
783 return
784 ;;
785 esac
786 __git_complete_file
787}
788
789_git_fetch ()
790{
791 local cur="${COMP_WORDS[COMP_CWORD]}"
792
793 if [ "$COMP_CWORD" = 2 ]; then
794 __gitcomp "$(__git_remotes)"
795 else
796 case "$cur" in
797 *:*)
798 local pfx=""
799 case "$COMP_WORDBREAKS" in
800 *:*) : great ;;
801 *) pfx="${cur%%:*}:" ;;
802 esac
803 __gitcomp "$(__git_refs)" "$pfx" "${cur#*:}"
804 ;;
805 *)
806 __gitcomp "$(__git_refs2 "${COMP_WORDS[2]}")"
807 ;;
808 esac
809 fi
810}
811
812_git_format_patch ()
813{
814 local cur="${COMP_WORDS[COMP_CWORD]}"
815 case "$cur" in
816 --*)
817 __gitcomp "
818 --stdout --attach --thread
819 --output-directory
820 --numbered --start-number
821 --numbered-files
822 --keep-subject
823 --signoff
824 --in-reply-to=
825 --full-index --binary
826 --not --all
827 --cover-letter
828 --no-prefix --src-prefix= --dst-prefix=
829 "
830 return
831 ;;
832 esac
833 __git_complete_revlist
834}
835
836_git_gc ()
837{
838 local cur="${COMP_WORDS[COMP_CWORD]}"
839 case "$cur" in
840 --*)
841 __gitcomp "--prune --aggressive"
842 return
843 ;;
844 esac
845 COMPREPLY=()
846}
847
848_git_grep ()
849{
850 __git_has_doubledash && return
851
852 local cur="${COMP_WORDS[COMP_CWORD]}"
853 case "$cur" in
854 --*)
855 __gitcomp "
856 --cached
857 --text --ignore-case --word-regexp --invert-match
858 --full-name
859 --extended-regexp --basic-regexp --fixed-strings
860 --files-with-matches --name-only
861 --files-without-match
862 --count
863 --and --or --not --all-match
864 "
865 return
866 ;;
867 esac
868 COMPREPLY=()
869}
870
871_git_help ()
872{
873 local cur="${COMP_WORDS[COMP_CWORD]}"
874 case "$cur" in
875 --*)
876 __gitcomp "--all --info --man --web"
877 return
878 ;;
879 esac
880 __gitcomp "$(__git_all_commands)
881 attributes cli core-tutorial cvs-migration
882 diffcore gitk glossary hooks ignore modules
883 repository-layout tutorial tutorial-2
884 "
885}
886
887_git_init ()
888{
889 local cur="${COMP_WORDS[COMP_CWORD]}"
890 case "$cur" in
891 --shared=*)
892 __gitcomp "
893 false true umask group all world everybody
894 " "" "${cur##--shared=}"
895 return
896 ;;
897 --*)
898 __gitcomp "--quiet --bare --template= --shared --shared="
899 return
900 ;;
901 esac
902 COMPREPLY=()
903}
904
905_git_ls_files ()
906{
907 __git_has_doubledash && return
908
909 local cur="${COMP_WORDS[COMP_CWORD]}"
910 case "$cur" in
911 --*)
912 __gitcomp "--cached --deleted --modified --others --ignored
913 --stage --directory --no-empty-directory --unmerged
914 --killed --exclude= --exclude-from=
915 --exclude-per-directory= --exclude-standard
916 --error-unmatch --with-tree= --full-name
917 --abbrev --ignored --exclude-per-directory
918 "
919 return
920 ;;
921 esac
922 COMPREPLY=()
923}
924
925_git_ls_remote ()
926{
927 __gitcomp "$(__git_remotes)"
928}
929
930_git_ls_tree ()
931{
932 __git_complete_file
933}
934
935_git_log ()
936{
937 __git_has_doubledash && return
938
939 local cur="${COMP_WORDS[COMP_CWORD]}"
940 case "$cur" in
941 --pretty=*)
942 __gitcomp "
943 oneline short medium full fuller email raw
944 " "" "${cur##--pretty=}"
945 return
946 ;;
947 --date=*)
948 __gitcomp "
949 relative iso8601 rfc2822 short local default
950 " "" "${cur##--date=}"
951 return
952 ;;
953 --*)
954 __gitcomp "
955 --max-count= --max-age= --since= --after=
956 --min-age= --before= --until=
957 --root --topo-order --date-order --reverse
958 --no-merges --follow
959 --abbrev-commit --abbrev=
960 --relative-date --date=
961 --author= --committer= --grep=
962 --all-match
963 --pretty= --name-status --name-only --raw
964 --not --all
965 --left-right --cherry-pick
966 --graph
967 --stat --numstat --shortstat
968 --decorate --diff-filter=
969 --color-words --walk-reflogs
970 --parents --children --full-history
971 --merge
972 "
973 return
974 ;;
975 esac
976 __git_complete_revlist
977}
978
979_git_merge ()
980{
981 local cur="${COMP_WORDS[COMP_CWORD]}"
982 case "${COMP_WORDS[COMP_CWORD-1]}" in
983 -s|--strategy)
984 __gitcomp "$(__git_merge_strategies)"
985 return
986 esac
987 case "$cur" in
988 --strategy=*)
989 __gitcomp "$(__git_merge_strategies)" "" "${cur##--strategy=}"
990 return
991 ;;
992 --*)
993 __gitcomp "
994 --no-commit --no-stat --log --no-log --squash --strategy
995 "
996 return
997 esac
998 __gitcomp "$(__git_refs)"
999}
1000
1001_git_mergetool ()
1002{
1003 local cur="${COMP_WORDS[COMP_CWORD]}"
1004 case "$cur" in
1005 --tool=*)
1006 __gitcomp "
1007 kdiff3 tkdiff meld xxdiff emerge
1008 vimdiff gvimdiff ecmerge opendiff
1009 " "" "${cur##--tool=}"
1010 return
1011 ;;
1012 --*)
1013 __gitcomp "--tool="
1014 return
1015 ;;
1016 esac
1017 COMPREPLY=()
1018}
1019
1020_git_merge_base ()
1021{
1022 __gitcomp "$(__git_refs)"
1023}
1024
1025_git_mv ()
1026{
1027 local cur="${COMP_WORDS[COMP_CWORD]}"
1028 case "$cur" in
1029 --*)
1030 __gitcomp "--dry-run"
1031 return
1032 ;;
1033 esac
1034 COMPREPLY=()
1035}
1036
1037_git_name_rev ()
1038{
1039 __gitcomp "--tags --all --stdin"
1040}
1041
1042_git_pull ()
1043{
1044 local cur="${COMP_WORDS[COMP_CWORD]}"
1045
1046 if [ "$COMP_CWORD" = 2 ]; then
1047 __gitcomp "$(__git_remotes)"
1048 else
1049 __gitcomp "$(__git_refs "${COMP_WORDS[2]}")"
1050 fi
1051}
1052
1053_git_push ()
1054{
1055 local cur="${COMP_WORDS[COMP_CWORD]}"
1056
1057 if [ "$COMP_CWORD" = 2 ]; then
1058 __gitcomp "$(__git_remotes)"
1059 else
1060 case "$cur" in
1061 *:*)
1062 local pfx=""
1063 case "$COMP_WORDBREAKS" in
1064 *:*) : great ;;
1065 *) pfx="${cur%%:*}:" ;;
1066 esac
1067
1068 __gitcomp "$(__git_refs "${COMP_WORDS[2]}")" "$pfx" "${cur#*:}"
1069 ;;
1070 +*)
1071 __gitcomp "$(__git_refs)" + "${cur#+}"
1072 ;;
1073 *)
1074 __gitcomp "$(__git_refs)"
1075 ;;
1076 esac
1077 fi
1078}
1079
1080_git_rebase ()
1081{
1082 local cur="${COMP_WORDS[COMP_CWORD]}" dir="$(__gitdir)"
1083 if [ -d "$dir"/rebase-apply ] || [ -d "$dir"/rebase-merge ]; then
1084 __gitcomp "--continue --skip --abort"
1085 return
1086 fi
1087 case "${COMP_WORDS[COMP_CWORD-1]}" in
1088 -s|--strategy)
1089 __gitcomp "$(__git_merge_strategies)"
1090 return
1091 esac
1092 case "$cur" in
1093 --strategy=*)
1094 __gitcomp "$(__git_merge_strategies)" "" "${cur##--strategy=}"
1095 return
1096 ;;
1097 --*)
1098 __gitcomp "--onto --merge --strategy --interactive"
1099 return
1100 esac
1101 __gitcomp "$(__git_refs)"
1102}
1103
1104_git_send_email ()
1105{
1106 local cur="${COMP_WORDS[COMP_CWORD]}"
1107 case "$cur" in
1108 --*)
1109 __gitcomp "--bcc --cc --cc-cmd --chain-reply-to --compose
1110 --dry-run --envelope-sender --from --identity
1111 --in-reply-to --no-chain-reply-to --no-signed-off-by-cc
1112 --no-suppress-from --no-thread --quiet
1113 --signed-off-by-cc --smtp-pass --smtp-server
1114 --smtp-server-port --smtp-ssl --smtp-user --subject
1115 --suppress-cc --suppress-from --thread --to"
1116 return
1117 ;;
1118 esac
1119 COMPREPLY=()
1120}
1121
1122_git_config ()
1123{
1124 local cur="${COMP_WORDS[COMP_CWORD]}"
1125 local prv="${COMP_WORDS[COMP_CWORD-1]}"
1126 case "$prv" in
1127 branch.*.remote)
1128 __gitcomp "$(__git_remotes)"
1129 return
1130 ;;
1131 branch.*.merge)
1132 __gitcomp "$(__git_refs)"
1133 return
1134 ;;
1135 remote.*.fetch)
1136 local remote="${prv#remote.}"
1137 remote="${remote%.fetch}"
1138 __gitcomp "$(__git_refs_remotes "$remote")"
1139 return
1140 ;;
1141 remote.*.push)
1142 local remote="${prv#remote.}"
1143 remote="${remote%.push}"
1144 __gitcomp "$(git --git-dir="$(__gitdir)" \
1145 for-each-ref --format='%(refname):%(refname)' \
1146 refs/heads)"
1147 return
1148 ;;
1149 pull.twohead|pull.octopus)
1150 __gitcomp "$(__git_merge_strategies)"
1151 return
1152 ;;
1153 color.branch|color.diff|color.status)
1154 __gitcomp "always never auto"
1155 return
1156 ;;
1157 color.*.*)
1158 __gitcomp "
1159 black red green yellow blue magenta cyan white
1160 bold dim ul blink reverse
1161 "
1162 return
1163 ;;
1164 *.*)
1165 COMPREPLY=()
1166 return
1167 ;;
1168 esac
1169 case "$cur" in
1170 --*)
1171 __gitcomp "
1172 --global --system --file=
1173 --list --replace-all
1174 --get --get-all --get-regexp
1175 --add --unset --unset-all
1176 --remove-section --rename-section
1177 "
1178 return
1179 ;;
1180 branch.*.*)
1181 local pfx="${cur%.*}."
1182 cur="${cur##*.}"
1183 __gitcomp "remote merge" "$pfx" "$cur"
1184 return
1185 ;;
1186 branch.*)
1187 local pfx="${cur%.*}."
1188 cur="${cur#*.}"
1189 __gitcomp "$(__git_heads)" "$pfx" "$cur" "."
1190 return
1191 ;;
1192 remote.*.*)
1193 local pfx="${cur%.*}."
1194 cur="${cur##*.}"
1195 __gitcomp "
1196 url fetch push skipDefaultUpdate
1197 receivepack uploadpack tagopt
1198 " "$pfx" "$cur"
1199 return
1200 ;;
1201 remote.*)
1202 local pfx="${cur%.*}."
1203 cur="${cur#*.}"
1204 __gitcomp "$(__git_remotes)" "$pfx" "$cur" "."
1205 return
1206 ;;
1207 esac
1208 __gitcomp "
1209 apply.whitespace
1210 core.fileMode
1211 core.gitProxy
1212 core.ignoreStat
1213 core.preferSymlinkRefs
1214 core.logAllRefUpdates
1215 core.loosecompression
1216 core.repositoryFormatVersion
1217 core.sharedRepository
1218 core.warnAmbiguousRefs
1219 core.compression
1220 core.packedGitWindowSize
1221 core.packedGitLimit
1222 clean.requireForce
1223 color.branch
1224 color.branch.current
1225 color.branch.local
1226 color.branch.remote
1227 color.branch.plain
1228 color.diff
1229 color.diff.plain
1230 color.diff.meta
1231 color.diff.frag
1232 color.diff.old
1233 color.diff.new
1234 color.diff.commit
1235 color.diff.whitespace
1236 color.pager
1237 color.status
1238 color.status.header
1239 color.status.added
1240 color.status.changed
1241 color.status.untracked
1242 diff.renameLimit
1243 diff.renames
1244 fetch.unpackLimit
1245 format.headers
1246 format.subjectprefix
1247 gitcvs.enabled
1248 gitcvs.logfile
1249 gitcvs.allbinary
1250 gitcvs.dbname gitcvs.dbdriver gitcvs.dbuser gitcvs.dbpass
1251 gitcvs.dbtablenameprefix
1252 gc.packrefs
1253 gc.reflogexpire
1254 gc.reflogexpireunreachable
1255 gc.rerereresolved
1256 gc.rerereunresolved
1257 http.sslVerify
1258 http.sslCert
1259 http.sslKey
1260 http.sslCAInfo
1261 http.sslCAPath
1262 http.maxRequests
1263 http.lowSpeedLimit
1264 http.lowSpeedTime
1265 http.noEPSV
1266 i18n.commitEncoding
1267 i18n.logOutputEncoding
1268 log.showroot
1269 merge.tool
1270 merge.summary
1271 merge.verbosity
1272 pack.window
1273 pack.depth
1274 pack.windowMemory
1275 pack.compression
1276 pack.deltaCacheSize
1277 pack.deltaCacheLimit
1278 pull.octopus
1279 pull.twohead
1280 repack.useDeltaBaseOffset
1281 showbranch.default
1282 tar.umask
1283 transfer.unpackLimit
1284 receive.unpackLimit
1285 receive.denyNonFastForwards
1286 user.name
1287 user.email
1288 user.signingkey
1289 branch. remote.
1290 "
1291}
1292
1293_git_remote ()
1294{
1295 local subcommands="add rm show prune update"
1296 local subcommand="$(__git_find_subcommand "$subcommands")"
1297 if [ -z "$subcommand" ]; then
1298 __gitcomp "$subcommands"
1299 return
1300 fi
1301
1302 case "$subcommand" in
1303 rm|show|prune)
1304 __gitcomp "$(__git_remotes)"
1305 ;;
1306 update)
1307 local i c='' IFS=$'\n'
1308 for i in $(git --git-dir="$(__gitdir)" config --list); do
1309 case "$i" in
1310 remotes.*)
1311 i="${i#remotes.}"
1312 c="$c ${i/=*/}"
1313 ;;
1314 esac
1315 done
1316 __gitcomp "$c"
1317 ;;
1318 *)
1319 COMPREPLY=()
1320 ;;
1321 esac
1322}
1323
1324_git_reset ()
1325{
1326 __git_has_doubledash && return
1327
1328 local cur="${COMP_WORDS[COMP_CWORD]}"
1329 case "$cur" in
1330 --*)
1331 __gitcomp "--mixed --hard --soft"
1332 return
1333 ;;
1334 esac
1335 __gitcomp "$(__git_refs)"
1336}
1337
1338_git_revert ()
1339{
1340 local cur="${COMP_WORDS[COMP_CWORD]}"
1341 case "$cur" in
1342 --*)
1343 __gitcomp "--edit --mainline --no-edit --no-commit --signoff"
1344 return
1345 ;;
1346 esac
1347 __gitcomp "$(__git_refs)"
1348}
1349
1350_git_rm ()
1351{
1352 __git_has_doubledash && return
1353
1354 local cur="${COMP_WORDS[COMP_CWORD]}"
1355 case "$cur" in
1356 --*)
1357 __gitcomp "--cached --dry-run --ignore-unmatch --quiet"
1358 return
1359 ;;
1360 esac
1361 COMPREPLY=()
1362}
1363
1364_git_shortlog ()
1365{
1366 __git_has_doubledash && return
1367
1368 local cur="${COMP_WORDS[COMP_CWORD]}"
1369 case "$cur" in
1370 --*)
1371 __gitcomp "
1372 --max-count= --max-age= --since= --after=
1373 --min-age= --before= --until=
1374 --no-merges
1375 --author= --committer= --grep=
1376 --all-match
1377 --not --all
1378 --numbered --summary
1379 "
1380 return
1381 ;;
1382 esac
1383 __git_complete_revlist
1384}
1385
1386_git_show ()
1387{
1388 __git_has_doubledash && return
1389
1390 local cur="${COMP_WORDS[COMP_CWORD]}"
1391 case "$cur" in
1392 --pretty=*)
1393 __gitcomp "
1394 oneline short medium full fuller email raw
1395 " "" "${cur##--pretty=}"
1396 return
1397 ;;
1398 --*)
1399 __gitcomp "--pretty="
1400 return
1401 ;;
1402 esac
1403 __git_complete_file
1404}
1405
1406_git_show_branch ()
1407{
1408 local cur="${COMP_WORDS[COMP_CWORD]}"
1409 case "$cur" in
1410 --*)
1411 __gitcomp "
1412 --all --remotes --topo-order --current --more=
1413 --list --independent --merge-base --no-name
1414 --sha1-name --topics --reflog
1415 "
1416 return
1417 ;;
1418 esac
1419 __git_complete_revlist
1420}
1421
1422_git_stash ()
1423{
1424 local subcommands='save list show apply clear drop pop create branch'
1425 local subcommand="$(__git_find_subcommand "$subcommands")"
1426 if [ -z "$subcommand" ]; then
1427 __gitcomp "$subcommands"
1428 else
1429 local cur="${COMP_WORDS[COMP_CWORD]}"
1430 case "$subcommand,$cur" in
1431 save,--*)
1432 __gitcomp "--keep-index"
1433 ;;
1434 apply,--*)
1435 __gitcomp "--index"
1436 ;;
1437 show,--*|drop,--*|pop,--*|branch,--*)
1438 COMPREPLY=()
1439 ;;
1440 show,*|apply,*|drop,*|pop,*|branch,*)
1441 __gitcomp "$(git --git-dir="$(__gitdir)" stash list \
1442 | sed -n -e 's/:.*//p')"
1443 ;;
1444 *)
1445 COMPREPLY=()
1446 ;;
1447 esac
1448 fi
1449}
1450
1451_git_submodule ()
1452{
1453 __git_has_doubledash && return
1454
1455 local subcommands="add status init update"
1456 if [ -z "$(__git_find_subcommand "$subcommands")" ]; then
1457 local cur="${COMP_WORDS[COMP_CWORD]}"
1458 case "$cur" in
1459 --*)
1460 __gitcomp "--quiet --cached"
1461 ;;
1462 *)
1463 __gitcomp "$subcommands"
1464 ;;
1465 esac
1466 return
1467 fi
1468}
1469
1470_git_svn ()
1471{
1472 local subcommands="
1473 init fetch clone rebase dcommit log find-rev
1474 set-tree commit-diff info create-ignore propget
1475 proplist show-ignore show-externals
1476 "
1477 local subcommand="$(__git_find_subcommand "$subcommands")"
1478 if [ -z "$subcommand" ]; then
1479 __gitcomp "$subcommands"
1480 else
1481 local remote_opts="--username= --config-dir= --no-auth-cache"
1482 local fc_opts="
1483 --follow-parent --authors-file= --repack=
1484 --no-metadata --use-svm-props --use-svnsync-props
1485 --log-window-size= --no-checkout --quiet
1486 --repack-flags --user-log-author $remote_opts
1487 "
1488 local init_opts="
1489 --template= --shared= --trunk= --tags=
1490 --branches= --stdlayout --minimize-url
1491 --no-metadata --use-svm-props --use-svnsync-props
1492 --rewrite-root= $remote_opts
1493 "
1494 local cmt_opts="
1495 --edit --rmdir --find-copies-harder --copy-similarity=
1496 "
1497
1498 local cur="${COMP_WORDS[COMP_CWORD]}"
1499 case "$subcommand,$cur" in
1500 fetch,--*)
1501 __gitcomp "--revision= --fetch-all $fc_opts"
1502 ;;
1503 clone,--*)
1504 __gitcomp "--revision= $fc_opts $init_opts"
1505 ;;
1506 init,--*)
1507 __gitcomp "$init_opts"
1508 ;;
1509 dcommit,--*)
1510 __gitcomp "
1511 --merge --strategy= --verbose --dry-run
1512 --fetch-all --no-rebase $cmt_opts $fc_opts
1513 "
1514 ;;
1515 set-tree,--*)
1516 __gitcomp "--stdin $cmt_opts $fc_opts"
1517 ;;
1518 create-ignore,--*|propget,--*|proplist,--*|show-ignore,--*|\
1519 show-externals,--*)
1520 __gitcomp "--revision="
1521 ;;
1522 log,--*)
1523 __gitcomp "
1524 --limit= --revision= --verbose --incremental
1525 --oneline --show-commit --non-recursive
1526 --authors-file=
1527 "
1528 ;;
1529 rebase,--*)
1530 __gitcomp "
1531 --merge --verbose --strategy= --local
1532 --fetch-all $fc_opts
1533 "
1534 ;;
1535 commit-diff,--*)
1536 __gitcomp "--message= --file= --revision= $cmt_opts"
1537 ;;
1538 info,--*)
1539 __gitcomp "--url"
1540 ;;
1541 *)
1542 COMPREPLY=()
1543 ;;
1544 esac
1545 fi
1546}
1547
1548_git_tag ()
1549{
1550 local i c=1 f=0
1551 while [ $c -lt $COMP_CWORD ]; do
1552 i="${COMP_WORDS[c]}"
1553 case "$i" in
1554 -d|-v)
1555 __gitcomp "$(__git_tags)"
1556 return
1557 ;;
1558 -f)
1559 f=1
1560 ;;
1561 esac
1562 c=$((++c))
1563 done
1564
1565 case "${COMP_WORDS[COMP_CWORD-1]}" in
1566 -m|-F)
1567 COMPREPLY=()
1568 ;;
1569 -*|tag)
1570 if [ $f = 1 ]; then
1571 __gitcomp "$(__git_tags)"
1572 else
1573 COMPREPLY=()
1574 fi
1575 ;;
1576 *)
1577 __gitcomp "$(__git_refs)"
1578 ;;
1579 esac
1580}
1581
1582_git ()
1583{
1584 local i c=1 command __git_dir
1585
1586 while [ $c -lt $COMP_CWORD ]; do
1587 i="${COMP_WORDS[c]}"
1588 case "$i" in
1589 --git-dir=*) __git_dir="${i#--git-dir=}" ;;
1590 --bare) __git_dir="." ;;
1591 --version|-p|--paginate) ;;
1592 --help) command="help"; break ;;
1593 *) command="$i"; break ;;
1594 esac
1595 c=$((++c))
1596 done
1597
1598 if [ -z "$command" ]; then
1599 case "${COMP_WORDS[COMP_CWORD]}" in
1600 --*=*) COMPREPLY=() ;;
1601 --*) __gitcomp "
1602 --paginate
1603 --no-pager
1604 --git-dir=
1605 --bare
1606 --version
1607 --exec-path
1608 --work-tree=
1609 --help
1610 "
1611 ;;
1612 *) __gitcomp "$(__git_porcelain_commands) $(__git_aliases)" ;;
1613 esac
1614 return
1615 fi
1616
1617 local expansion=$(__git_aliased_command "$command")
1618 [ "$expansion" ] && command="$expansion"
1619
1620 case "$command" in
1621 am) _git_am ;;
1622 add) _git_add ;;
1623 apply) _git_apply ;;
1624 archive) _git_archive ;;
1625 bisect) _git_bisect ;;
1626 bundle) _git_bundle ;;
1627 branch) _git_branch ;;
1628 checkout) _git_checkout ;;
1629 cherry) _git_cherry ;;
1630 cherry-pick) _git_cherry_pick ;;
1631 clean) _git_clean ;;
1632 clone) _git_clone ;;
1633 commit) _git_commit ;;
1634 config) _git_config ;;
1635 describe) _git_describe ;;
1636 diff) _git_diff ;;
1637 fetch) _git_fetch ;;
1638 format-patch) _git_format_patch ;;
1639 gc) _git_gc ;;
1640 grep) _git_grep ;;
1641 help) _git_help ;;
1642 init) _git_init ;;
1643 log) _git_log ;;
1644 ls-files) _git_ls_files ;;
1645 ls-remote) _git_ls_remote ;;
1646 ls-tree) _git_ls_tree ;;
1647 merge) _git_merge;;
1648 mergetool) _git_mergetool;;
1649 merge-base) _git_merge_base ;;
1650 mv) _git_mv ;;
1651 name-rev) _git_name_rev ;;
1652 pull) _git_pull ;;
1653 push) _git_push ;;
1654 rebase) _git_rebase ;;
1655 remote) _git_remote ;;
1656 reset) _git_reset ;;
1657 revert) _git_revert ;;
1658 rm) _git_rm ;;
1659 send-email) _git_send_email ;;
1660 shortlog) _git_shortlog ;;
1661 show) _git_show ;;
1662 show-branch) _git_show_branch ;;
1663 stash) _git_stash ;;
1664 submodule) _git_submodule ;;
1665 svn) _git_svn ;;
1666 tag) _git_tag ;;
1667 whatchanged) _git_log ;;
1668 *) COMPREPLY=() ;;
1669 esac
1670}
1671
1672_gitk ()
1673{
1674 __git_has_doubledash && return
1675
1676 local cur="${COMP_WORDS[COMP_CWORD]}"
1677 local g="$(git rev-parse --git-dir 2>/dev/null)"
1678 local merge=""
1679 if [ -f $g/MERGE_HEAD ]; then
1680 merge="--merge"
1681 fi
1682 case "$cur" in
1683 --*)
1684 __gitcomp "--not --all $merge"
1685 return
1686 ;;
1687 esac
1688 __git_complete_revlist
1689}
1690
1691complete -o default -o nospace -F _git git
1692complete -o default -o nospace -F _gitk gitk
1693
1694# The following are necessary only for Cygwin, and only are needed
1695# when the user has tab-completed the executable name and consequently
1696# included the '.exe' suffix.
1697#
1698if [ Cygwin = "$(uname -o 2>/dev/null)" ]; then
1699complete -o default -o nospace -F _git git.exe
1700fi