summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--common.sh.in6
-rw-r--r--ediff.sh.in67
2 files changed, 61 insertions, 12 deletions
diff --git a/common.sh.in b/common.sh.in
index 2488a69..54431fe 100644
--- a/common.sh.in
+++ b/common.sh.in
@@ -1,6 +1,6 @@
# begin common.sh {{{
-# Copyright (C) 2013-2014, 2016 Luke Shumaker <lukeshu@sbcglobal.net>
+# Copyright (C) 2013-2014, 2016-2017 Luke Shumaker <lukeshu@sbcglobal.net>
#
# This file is not considered part of GNU Emacs.
#
@@ -42,7 +42,9 @@ flag() {
printf -- "%s\n" "$flag"
flag=''
fi
- printf -- "%- ${_flag_indent}s%s\n" "$flag" "$(print "${@:2}")"
+ local text
+ text="$(print "${@:2}")"
+ printf -- "%- ${_flag_indent}s%s\n" "$flag" "${text//$'\n'/"$(printf -- "\n%- ${_flag_indent}s%s\n" '')"}"
}
error() {
diff --git a/ediff.sh.in b/ediff.sh.in
index 569721e..1a227bb 100644
--- a/ediff.sh.in
+++ b/ediff.sh.in
@@ -1,6 +1,6 @@
#!@bash@
-# Copyright (C) 2014, 2016 Luke Shumaker <lukeshu@sbcglobal.net>
+# Copyright (C) 2014, 2016-2017 Luke Shumaker <lukeshu@sbcglobal.net>
#
# This file is not considered part of GNU Emacs.
#
@@ -21,25 +21,56 @@ m4_include(common.sh.in)
usage() {
print 'Usage: %q [OPTIONS] FILE_A FILE_B' "$0"
- print ' or: %q -3 [OPTIONS] FILE_A FILE_B FILE_C' "$0"
+ print ' or: %q -3 [OPTIONS] FILE_A FILE_B FILE_C|FILE_ANCESTOR' "$0"
print "Use Emacs' ediff-mode to compare two files"
echo
print 'The following OPTIONS are accepted:'
emacs_usage
- flag '-3' 'Do a 3-way diff instead of 2-way'
- flag '-r, --recursive' 'Diff directories recursively'
+ flag '-r, -R REGEXP, --recursive[=REGEXP]' \
+ 'Diff directories recursively,
+excluding filenames not matching REGEXP'
+
+ flag '-3' \
+ 'Do a 3-way diff instead of 2-way
+When used in the context of a --merge,
+the 3rd file is the common ancestor between A and B'
+
+ flag '-m OUTFILE, --merge=OUTFILE' \
+ 'Merge files A and B, saving the output in OUTFILE'
}
main() {
declare -a flags=()
- declare -a files=()
- declare -i cnt=2
- declare cmd=ediff
declare mode=normal
+ # The functions that we currently make available are:
+ # (ediff FILE-A FILE-B &optional STARTUP-HOOKS)
+ # (ediff3 FILE-A FILE-B FILE-C &optional STARTUP-HOOKS)
+ # (ediff-merge FILE-A FILE-B &optional STARTUP-HOOKS MERGE-BUFFER-FILE)
+ # (ediff-merge-with-ancestor FILE-A FILE-B FILE-ANCESTOR &optional STARTUP-HOOKS MERGE-BUFFER-FILE)
+ # and their recursive equivalents:
+ # (edirs DIR1 DIR2 REGEXP)
+ # (edirs3 DIR1 DIR2 DIR3 REGEXP)
+ # (edirs-merge DIR1 DIR2 REGEXP &optional MERGE-AUTOSTORE-DIR)
+ # (edirs-merge-with-ancestor DIR1 DIR2 ANCESTOR-DIR REGEXP &optional MERGE-AUTOSTORE-DIR)
+ #
+ # This list is currently missing the "revision" commands:
+ # (ediff-revision &optional FILE STARTUP-HOOKS)
+ # (edir-revisions DIR1 REGEXP)
+ # (edir-merge-revisions DIR1 REGEXP &optional MERGE-AUTOSTORE-DIR)
+ # (edir-merge-revisions-with-ancestor DIR1 REGEXP &optional MERGE-AUTOSTORE-DIR)
+ # and the epatch command:
+ # (epatch &optional ARG PATCH-BUF)
+
+ declare cmd=ediff
+ declare -i cnt=2
+ declare -a files=()
+ declare extra=nil # STARTUP-HOOKS for cmd=ediff, REGEXP for cmd=edirs
+ declare merge=''
+
emacs_getopt_init
declare args
- if ! args="$(emacs_getopt 3r recursive "$@")"; then
+ if ! args="$(emacs_getopt rR:3m: recursive::,merge: "$@")"; then
mode=error
else
eval set -- "$args"
@@ -47,8 +78,18 @@ main() {
case "$1" in
-V|--version) shift; mode=version;;
-H|--help) shift; mode=usage;;
- -r|--recursive) shift; cmd=edirs;;
+
+ -r) shift; cmd=edirs;;
+ -R|--recursive)
+ cmd=edirs
+ [[ -z "$2" ]] || extra="$(emacs_quote "$2")"
+ shift 2
+ ;;
+
-3) shift; cnt=3;;
+
+ -m|--merge) merge="$(emacs_quote "$2")"; shift 2;;
+
--) shift; break;;
*)
if [[ $1 =~ $emacs_getopt_2 ]]; then
@@ -65,9 +106,15 @@ main() {
fi
fi
+ if [[ -z "$merge" ]]; then
+ [[ $cnt == 2 ]] || cmd+='3'
+ else
+ cmd+='-merge'
+ [[ $cnt == 2 ]] || cmd+='-with-ancestor'
+ fi
next "$mode" \
emacsclient "${flags[@]}" --eval \
- "(${cmd}${cnt#2} $(emacs_quote "${files[@]}"))"
+ "(${cmd} $(emacs_quote "${files[@]}") $extra $merge)"
}
main "$@"