1#!/bin/sh 2# 3# This is included in commands that either have to be run from the toplevel 4# of the repository, or with GIT_DIR environment variable properly. 5# If the GIT_DIR does not look like the right correct git-repository, 6# it dies. 7 8# Having this variable in your environment would break scripts because 9# you would cause "cd" to be taken to unexpected places. If you 10# like CDPATH, define it for your interactive shell sessions without 11# exporting it. 12# But we protect ourselves from such a user mistake nevertheless. 13unset CDPATH 14 15# Similarly for IFS, but some shells (e.g. FreeBSD 7.2) are buggy and 16# do not equate an unset IFS with IFS with the default, so here is 17# an explicit SP HT LF. 18IFS=' 19' 20 21git_broken_path_fix () { 22case":$PATH:"in 23*:$1:*) : ok ;; 24*) 25 PATH=$( 26 SANE_TOOL_PATH="$1" 27 IFS=: path= sep= 28set x $PATH 29shift 30for elem 31do 32case"$SANE_TOOL_PATH:$elem"in 33(?*:/bin | ?*:/usr/bin) 34 path="$path$sep$SANE_TOOL_PATH" 35 sep=: 36 SANE_TOOL_PATH= 37esac 38 path="$path$sep$elem" 39 sep=: 40done 41echo"$path" 42) 43;; 44esac 45} 46 47# @@BROKEN_PATH_FIX@@ 48 49die () { 50 die_with_status 1"$@" 51} 52 53die_with_status () { 54 status=$1 55shift 56printf>&2'%s\n'"$*" 57exit"$status" 58} 59 60GIT_QUIET= 61 62say () { 63iftest -z"$GIT_QUIET" 64then 65printf'%s\n'"$*" 66fi 67} 68 69iftest -n"$OPTIONS_SPEC";then 70 usage() { 71"$0"-h 72exit1 73} 74 75 parseopt_extra= 76[-n"$OPTIONS_KEEPDASHDASH"] && 77 parseopt_extra="--keep-dashdash" 78 79eval"$( 80 echo "$OPTIONS_SPEC" | 81 git rev-parse --parseopt$parseopt_extra-- "$@" || 82 echo exit $? 83 )" 84else 85 dashless=$(basename "$0" | sed -e 's/-/ /') 86 usage() { 87 die "usage:$dashless$USAGE" 88} 89 90if[-z"$LONG_USAGE"] 91then 92 LONG_USAGE="usage:$dashless$USAGE" 93else 94 LONG_USAGE="usage:$dashless$USAGE 95 96$LONG_USAGE" 97fi 98 99case"$1"in 100-h) 101echo"$LONG_USAGE" 102exit 103esac 104fi 105 106set_reflog_action() { 107if[-z"${GIT_REFLOG_ACTION:+set}"] 108then 109 GIT_REFLOG_ACTION="$*" 110export GIT_REFLOG_ACTION 111fi 112} 113 114git_editor() { 115iftest -z"${GIT_EDITOR:+set}" 116then 117 GIT_EDITOR="$(git var GIT_EDITOR)"||return $? 118fi 119 120eval"$GIT_EDITOR"'"$@"' 121} 122 123git_pager() { 124iftest -t1 125then 126 GIT_PAGER=$(git var GIT_PAGER) 127else 128 GIT_PAGER=cat 129fi 130:${LESS=-FRSX} 131export LESS 132 133eval"$GIT_PAGER"'"$@"' 134} 135 136sane_grep () { 137 GREP_OPTIONS= LC_ALL=C grep"$@" 138} 139 140sane_egrep () { 141 GREP_OPTIONS= LC_ALL=C egrep"$@" 142} 143 144is_bare_repository () { 145 git rev-parse --is-bare-repository 146} 147 148cd_to_toplevel () { 149 cdup=$(git rev-parse --show-toplevel)&& 150cd"$cdup"|| { 151echo>&2"Cannot chdir to$cdup, the toplevel of the working tree" 152exit1 153} 154} 155 156require_work_tree_exists () { 157iftest"z$(git rev-parse --is-bare-repository)"!= zfalse 158then 159 die "fatal:$0cannot be used without a working tree." 160fi 161} 162 163require_work_tree () { 164test"$(git rev-parse --is-inside-work-tree 2>/dev/null)"= true || 165 die "fatal:$0cannot be used without a working tree." 166} 167 168require_clean_work_tree () { 169 git rev-parse --verify HEAD >/dev/null ||exit1 170 git update-index -q --ignore-submodules --refresh 171 err=0 172 173if! git diff-files --quiet --ignore-submodules 174then 175echo>&2"Cannot$1: You have unstaged changes." 176 err=1 177fi 178 179if! git diff-index --cached --quiet --ignore-submodules HEAD -- 180then 181if[$err=0] 182then 183echo>&2"Cannot$1: Your index contains uncommitted changes." 184else 185echo>&2"Additionally, your index contains uncommitted changes." 186fi 187 err=1 188fi 189 190if[$err=1] 191then 192test -n"$2"&&echo>&2"$2" 193exit1 194fi 195} 196 197# Generate a sed script to parse identities from a commit. 198# 199# Reads the commit from stdin, which should be in raw format (e.g., from 200# cat-file or "--pretty=raw"). 201# 202# The first argument specifies the ident line to parse (e.g., "author"), and 203# the second specifies the environment variable to put it in (e.g., "AUTHOR" 204# for "GIT_AUTHOR_*"). Multiple pairs can be given to parse author and 205# committer. 206pick_ident_script () { 207whiletest$#-gt0 208do 209 lid=$1;shift 210 uid=$1;shift 211printf'%s'" 212 /^$lid/{ 213 s/'/'\\\\''/g 214 h 215 s/^$lid"'\([^<]*\) <[^>]*> .*$/\1/'" 216 s/.*/GIT_${uid}_NAME='&'/p 217 218 g 219 s/^$lid"'[^<]* <\([^>]*\)> .*$/\1/'" 220 s/.*/GIT_${uid}_EMAIL='&'/p 221 222 g 223 s/^$lid"'[^<]* <[^>]*> \(.*\)$/@\1/'" 224 s/.*/GIT_${uid}_DATE='&'/p 225 } 226 " 227done 228echo'/^$/q' 229} 230 231# Create a pick-script as above and feed it to sed. Stdout is suitable for 232# feeding to eval. 233parse_ident_from_commit () { 234 LANG=C LC_ALL=C sed-ne"$(pick_ident_script "$@")" 235} 236 237# Parse the author from a commit given as an argument. Stdout is suitable for 238# feeding to eval to set the usual GIT_* ident variables. 239get_author_ident_from_commit () { 240 encoding=$(git config i18n.commitencoding || echo UTF-8) 241 git show -s --pretty=raw --encoding="$encoding""$1"--| 242 parse_ident_from_commit author AUTHOR 243} 244 245# Clear repo-local GIT_* environment variables. Useful when switching to 246# another repository (e.g. when entering a submodule). See also the env 247# list in git_connect() 248clear_local_git_env() { 249unset$(git rev-parse --local-env-vars) 250} 251 252# Generate a virtual base file for a two-file merge. Uses git apply to 253# remove lines from $1 that are not in $2, leaving only common lines. 254create_virtual_base() { 255 sz0=$(wc -c <"$1") 256 @@DIFF@@ -u -La/"$1"-Lb/"$1""$1""$2"| git apply --no-add 257 sz1=$(wc -c <"$1") 258 259# If we do not have enough common material, it is not 260# worth trying two-file merge using common subsections. 261expr$sz0 \<$sz1 \*2>/dev/null || : >"$1" 262} 263 264 265# Platform specific tweaks to work around some commands 266case$(uname -s)in 267*MINGW*) 268# Windows has its own (incompatible) sort and find 269sort() { 270/usr/bin/sort"$@" 271} 272find() { 273/usr/bin/find"$@" 274} 275# git sees Windows-style pwd 276pwd() { 277builtin pwd -W 278} 279 is_absolute_path () { 280case"$1"in 281[/\\]* | [A-Za-z]:*) 282return0;; 283esac 284return1 285} 286;; 287*) 288 is_absolute_path () { 289case"$1"in 290/*) 291return0;; 292esac 293return1 294} 295esac 296 297# Make sure we are in a valid repository of a vintage we understand, 298# if we require to be in a git repository. 299iftest -z"$NONGIT_OK" 300then 301 GIT_DIR=$(git rev-parse --git-dir)||exit 302if[-z"$SUBDIRECTORY_OK"] 303then 304test -z"$(git rev-parse --show-cdup)"|| { 305exit=$? 306echo>&2"You need to run this command from the toplevel of the working tree." 307exit$exit 308} 309fi 310test -n"$GIT_DIR"&& GIT_DIR=$(cd "$GIT_DIR" && pwd)|| { 311echo>&2"Unable to determine absolute path of git directory" 312exit1 313} 314:${GIT_OBJECT_DIRECTORY="$GIT_DIR/objects"} 315fi 316 317peel_committish () { 318case"$1"in 319:/*) 320 peeltmp=$(git rev-parse --verify "$1")&& 321 git rev-parse --verify"${peeltmp}^0" 322;; 323*) 324 git rev-parse --verify"${1}^0" 325;; 326esac 327}