1#!/bin/sh 2# 3# Copyright (c) 2005 Junio C Hamano 4# 5 6. git-sh-setup|| die "Not a git archive" 7 8LF=' 9' 10 11usage () { 12 die "git-merge [-n] [-s <strategy>]... <merge-message> <head> <remote>+" 13} 14 15# all_strategies='resolve recursive stupid octopus' 16 17all_strategies='recursive octopus resolve stupid' 18default_strategies='resolve octopus' 19use_strategies= 20 21dropsave() { 22rm-f --"$GIT_DIR/MERGE_HEAD""$GIT_DIR/MERGE_MSG" \ 23"$GIT_DIR/MERGE_SAVE"||exit1 24} 25 26savestate() { 27# Stash away any local modifications. 28 git-diff-index -r -z --name-only$head| 29cpio-0 -o>"$GIR_DIR/MERGE_SAVE" 30} 31 32restorestate() { 33iftest -f"$GIT_DIR/MERGE_SAVE" 34then 35 git reset--hard$head 36cpio-iuv<"$GIT_DIR/MERGE_SAVE" 37 git-update-index --refresh>/dev/null 38fi 39} 40 41summary() { 42case"$no_summary"in 43'') 44 git-diff-tree -p -M$head"$1"| 45 git-apply --stat --summary 46;; 47esac 48} 49 50while case"$#"in0)break;;esac 51do 52case"$1"in 53-n|--n|--no|--no-|--no-s|--no-su|--no-sum|--no-summ|\ 54--no-summa|--no-summar|--no-summary) 55 no_summary=t ;; 56-s=*|--s=*|--st=*|--str=*|--stra=*|--strat=*|--strate=*|\ 57--strateg=*|--strategy=*|\ 58-s|--s|--st|--str|--stra|--strat|--strate|--strateg|--strategy) 59case"$#,$1"in 60*,*=*) 61 strategy=`expr "$1" : '-[^=]*=\(.*\)'`;; 621,*) 63 usage ;; 64*) 65 strategy="$2" 66shift;; 67esac 68case"$all_strategies"in 69*"$strategy"*) 70 use_strategies="$use_strategies$strategy";; 71*) 72 die "available strategies are:$all_strategies";; 73esac 74;; 75-*) usage ;; 76*)break;; 77esac 78shift 79done 80 81case"$use_strategies"in 82'') 83 use_strategies=$default_strategies 84;; 85esac 86test"$#"-le2&& usage ;# we need at least two heads. 87 88merge_msg="$1" 89shift 90head_arg="$1" 91head=$(git-rev-parse --verify "$1"^0)|| usage 92shift 93 94# All the rest are remote heads 95for remote 96do 97 git-rev-parse --verify"$remote"^0>/dev/null || 98 die "$remote- not something we can merge" 99done 100 101common=$(git-show-branch --merge-base $head "$@") 102echo"$head">"$GIT_DIR/ORIG_HEAD" 103 104case"$#,$common"in 105*,'') 106 die "Unable to find common commit between$head_argand $*" 107;; 1081,"$1") 109# If head can reach all the merge then we are up to date. 110# but first the most common case of merging one remote 111echo"Already up-to-date. Yeeah!" 112 dropsave 113exit0 114;; 1151,"$head") 116# Again the most common case of merging one remote. 117echo"Updating from$headto$1." 118 git-update-index --refresh2>/dev/null 119 git-read-tree -u -m$head"$1"&& 120 new_head=$(git-rev-parse --verify "$1^0")&& 121 git-update-ref HEAD "$new_head""$head"||exit1 122 summary "$1" 123 dropsave 124exit0 125;; 1261,*) 127# We are not doing octopus and not fast forward. Need a 128# real merge. 129;; 130*) 131# An octopus. If we can reach all the remote we are up to date. 132 up_to_date=t 133for remote 134do 135 common_one=$(git-merge-base $head $remote) 136iftest"$common_one"!="$remote" 137then 138 up_to_date=f 139break 140fi 141done 142iftest"$up_to_date"= t 143then 144echo"Already up-to-date. Yeeah!" 145 dropsave 146exit0 147fi 148;; 149esac 150 151# At this point, we need a real merge. No matter what strategy 152# we use, it would operate on the index, possibly affecting the 153# working tree, and when resolved cleanly, have the desired tree 154# in the index -- this means that the index must be in sync with 155# the $head commit. The strategies are responsible to ensure this. 156 157case"$use_strategies"in 158?*' '?*) 159# Stash away the local changes so that we can try more than one. 160 savestate 161 single_strategy=no 162;; 163*) 164rm-f"$GIT_DIR/MERGE_SAVE" 165 single_strategy=yes 166;; 167esac 168 169result_tree= best_cnt=-1 best_strategy= wt_strategy= 170for strategy in$use_strategies 171do 172test"$wt_strategy"=''|| { 173echo"Rewinding the tree to pristine..." 174 restorestate 175} 176case"$single_strategy"in 177 no) 178echo"Trying merge strategy$strategy..." 179;; 180esac 181 182# Remember which strategy left the state in the working tree 183 wt_strategy=$strategy 184 185 git-merge-$strategy $common--"$head_arg""$@"|| { 186 187# The backend exits with 1 when conflicts are left to be resolved, 188# with 2 when it does not handle the given merge at all. 189 190exit=$? 191iftest"$exit"-eq1 192then 193 cnt=`{ 194 git-diff-files --name-only 195 git-ls-files --unmerged 196 } | wc -l` 197iftest$best_cnt-le0-o$cnt-le$best_cnt 198then 199 best_strategy=$strategy 200 best_cnt=$cnt 201fi 202fi 203continue 204} 205 206# Automerge succeeded. 207 result_tree=$(git-write-tree)&&break 208done 209 210# If we have a resulting tree, that means the strategy module 211# auto resolved the merge cleanly. 212iftest''!="$result_tree" 213then 214 parents="-p$head" 215for remote 216do 217 parents="$parents-p$remote" 218done 219 result_commit=$(echo "$merge_msg" | git-commit-tree $result_tree $parents)||exit 220echo"Committed merge$result_commit, made by$wt_strategy." 221 git-update-ref HEAD $result_commit $head 222 summary $result_commit 223 dropsave 224exit0 225fi 226 227# Pick the result from the best strategy and have the user fix it up. 228case"$best_strategy"in 229'') 230 restorestate 231 die "No merge strategy handled the merge." 232;; 233"$wt_strategy") 234# We already have its result in the working tree. 235;; 236*) 237echo"Rewinding the tree to pristine..." 238 restorestate 239echo"Using the$best_strategyto prepare resolving by hand." 240 git-merge-$best_strategy $common--"$head_arg""$@" 241;; 242esac 243for remote 244do 245echo$remote 246done>"$GIT_DIR/MERGE_HEAD" 247echo$merge_msg>"$GIT_DIR/MERGE_MSG" 248 249die "Automatic merge failed; fix up by hand"