e0226add28
Junio points out that we may need to create the path leading up the the file we merge. And we need to be more careful with the "exec"s we've done to exit on success - only do the on the last command in the pipeline, not the first one ;)
112 lines
2.4 KiB
Bash
Executable File
112 lines
2.4 KiB
Bash
Executable File
#!/bin/sh
|
|
#
|
|
# Copyright (c) Linus Torvalds, 2005
|
|
#
|
|
# This is the git per-file merge script, called with
|
|
#
|
|
# $1 - original file SHA1 (or empty)
|
|
# $2 - file in branch1 SHA1 (or empty)
|
|
# $3 - file in branch2 SHA1 (or empty)
|
|
# $4 - pathname in repository
|
|
# $5 - orignal file mode (or empty)
|
|
# $6 - file in branch1 mode (or empty)
|
|
# $7 - file in branch2 mode (or empty)
|
|
#
|
|
# Handle some trivial cases.. The _really_ trivial cases have
|
|
# been handled already by git-read-tree, but that one doesn't
|
|
# do any merges that might change the tree layout.
|
|
|
|
verify_path() {
|
|
file="$1"
|
|
dir=`dirname "$file"` &&
|
|
mkdir -p "$dir" &&
|
|
rm -f -- "$file" &&
|
|
: >"$file"
|
|
}
|
|
|
|
case "${1:-.}${2:-.}${3:-.}" in
|
|
#
|
|
# Deleted in both.
|
|
#
|
|
"$1..")
|
|
echo "WARNING: $4 is removed in both branches."
|
|
echo "WARNING: This is a potential rename conflict."
|
|
rm -f -- "$4" &&
|
|
exec git-update-cache --remove -- "$4"
|
|
;;
|
|
|
|
#
|
|
# Deleted in one and unchanged in the other.
|
|
#
|
|
"$1.$1" | "$1$1.")
|
|
echo "Removing $4"
|
|
rm -f -- "$4" &&
|
|
exec git-update-cache --remove -- "$4"
|
|
;;
|
|
|
|
#
|
|
# Added in one.
|
|
#
|
|
".$2." | "..$3" )
|
|
case "$6$7" in *7??) mode=+x;; *) mode=-x;; esac
|
|
echo "Adding $4 with perm $mode."
|
|
verify_path "$4" &&
|
|
git-cat-file blob "$2$3" >"$4" &&
|
|
chmod $mode -- "$4" &&
|
|
exec git-update-cache --add -- "$4"
|
|
;;
|
|
|
|
#
|
|
# Added in both (check for same permissions).
|
|
#
|
|
".$3$2")
|
|
if [ "$6" != "$7" ]; then
|
|
echo "ERROR: File $4 added identically in both branches,"
|
|
echo "ERROR: but permissions conflict $6->$7."
|
|
exit 1
|
|
fi
|
|
case "$6" in *7??) mode=+x;; *) mode=-x;; esac
|
|
echo "Adding $4 with perm $mode"
|
|
verify_path "$4" &&
|
|
git-cat-file blob "$2" >"$4" &&
|
|
chmod $mode -- "$4" &&
|
|
exec git-update-cache --add -- "$4"
|
|
;;
|
|
|
|
#
|
|
# Modified in both, but differently.
|
|
#
|
|
"$1$2$3")
|
|
echo "Auto-merging $4."
|
|
orig=`git-unpack-file $1`
|
|
src1=`git-unpack-file $2`
|
|
src2=`git-unpack-file $3`
|
|
|
|
verify_path "$4" &&
|
|
merge -p "$src1" "$orig" "$src2" > "$4"
|
|
ret=$?
|
|
rm -f -- "$orig" "$src1" "$src2"
|
|
|
|
if [ "$6" != "$7" ]; then
|
|
echo "ERROR: Permissions conflict: $5->$6,$7."
|
|
ret=1
|
|
fi
|
|
case "$6" in *7??) mode=+x;; *) mode=-x;; esac
|
|
chmod "$mode" "$4"
|
|
|
|
if [ $ret -ne 0 ]; then
|
|
# Reset the index to the first branch, making
|
|
# git-diff-file useful
|
|
git-update-cache --add --cacheinfo "$6" "$2" "$4"
|
|
echo "ERROR: Merge conflict in $4."
|
|
exit 1
|
|
fi
|
|
exec git-update-cache --add -- "$4"
|
|
;;
|
|
|
|
*)
|
|
echo "ERROR: $4: Not handling case $1 -> $2 -> $3"
|
|
;;
|
|
esac
|
|
exit 1
|