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