#!/bin/sh

# pdiff --- Print diff in a nice way

# Copyright 1998-2017 Free Software Foundation, Inc.

# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 3, or (at your option)
# any later version.

# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.

# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA
# 02110-1301, USA.

# Author: Akim Demaille <demaille@inf.enst.fr>

set -e

# Get the name of the program
program=`echo $0 | sed 's#.*/##g'`


# Local vars
a2ps=${A2PS:-a2ps}
a2ps_options=
debug=
diff_on=words
diff_prog=${DIFF:-diff}
diff_options='-u'
file=
output=
tmpdir=`mktemp -d -t pdiff.XXXXXX` || { echo "$program: Cannot create temporary dir!" >&2 ; exit 1; }
verbose=echo
wdiff_prog=${WDIFF:-wdiff}
wdiff_options='-w[wd- -x-wd] -y{wd+ -z+wd}'
# The version/usage strings
version="pdiff 0.4 (GNU a2ps 4.15.6)
Written by Akim Demaille.

Copyright (c) 1997-1999 Akim Demaille, Miguel Santana
This is free software; see the source for copying conditions.  There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."

usage="\
Usage: $program FILE1 FILE2 [-- A2PS-OPTIONS...]
Pretty print the differences between FILE1 and FILE2.

Options:
 -h, --help           display this help and exit
 -v, --version        display version information and exit
 -q, --quiet          don't print informational messages
 -l, --lines          search for line differences (\`diff')
 -w, --words          search for word differences (\`wdiff')
 -o, --output=FILE    save the output in FILE

Options for a2ps are given after \`--', for instance

    $ pdiff COPYING COPYING.LIB -- -Pdisplay

News, updates and documentation: https://www.gnu.org/software/a2ps/
Report bugs to <bug-a2ps@gnu.org>."

help="Try \`$program --help' for more information."


# Parse command line arguments.
option_without_arguments='vhsqDlw'
# Push a token among the arguments that will be used to notice when
# we ended options/arguments parsing.
arg_sep="$$--$$"
set dummy ${1+"$@"} "$arg_sep"
shift
while test "x$1" != "x$arg_sep"; do

  # Handle --option=value by splitting apart and putting back on argv.
  case "$1" in
    --*=*)
      opt=`echo "$1" | sed -e 's/=.*//'`
      val=`echo "$1" | sed -e 's/[^=]*=//'`
      shift
      set dummy "$opt" "$val" ${1+"$@"}
      shift
      ;;

    -[$option_without_arguments]?*)
      # Prefix $1 with x to avoid running `echo -na' for instance.
      opt=`echo "x$1" | sed -e 's/x-\(.\).*/-\1/'`
      rest=`echo "x$1" | sed -e 's/x-.\(.*\)/-\1/'`
      shift
      set dummy "$opt" "$rest" ${1+"$@"}
      shift
      ;;

    # This case needs to be protected so that the case `-??*' does
    # not split long options without arguments
    --*)
      ;;

    # This is an option with argument.  Split apart and put back on argv.
    -??*)
      opt=`echo "x$1" | sed -e 's/x-\(.\).*/-\1/'`
      arg=`echo "x$1" | sed -e 's/x-.\(.*\)/\1/'`
      shift
      set dummy "$opt" "$arg" ${1+"$@"}
      shift
      ;;
  esac

  # Now, handle the options.  $1 is the option *only*.  If it has an
  # argument, it is now necessarily in $2 etc.  Remember to shift
  # when fetching an argument.
  case "$1" in
    -v | --v*) echo "$version"; exit 0;;
    -h | --h*) echo "$usage"; exit 0;;
    -s|-q|--q*|--s*) verbose=: ;;
    -D | --debug) debug=: ;;
    -o|--output) shift
                 a2ps_options="$a2ps_options --output=$1" ;;
    -l|--lines) diff_on=lines;;
    -w|--words) diff_on=words;;
    -) # We are working with stdin
    set dummy "${1+"$@"}" "$1"; shift;;

    --) # What remains are not options.
      shift
      while test "x$1" != "x$arg_sep"; do
        set dummy ${1+"$@"} "$1"
        shift
	shift
      done
      break;;

    -*)
      echo "$program: Unknown or ambiguous option \`$1'." >&2
      echo "$program: Try \`--help' for more information." >&2
      exit 1;;
    *) set dummy ${1+"$@"} "$1"
       shift
       ;;
   esac
   shift
done
# Pop the token
shift


# What remains is ORIG NEW [A2PS_OPTIONS...]
if test $# -lt 2; then
 exec 1>&2
 echo "$program: not enough arguments"
 echo "$help"
 exit 1
fi

file1="$1"
shift
file2="$1"
shift

# Set the titles
a2ps_options="--left-title=$file1 --right-title=$file2 $a2ps_options"
a2ps_options="--center-title $a2ps_options"

# Use the right prologue
a2ps_options="--prolog=diff $a2ps_options"

# Give the additional arguments given by the user
a2ps_options="$@ $a2ps_options"

# Set -x now if debugging
test $debug && set -x

# Call the correct diffing program, and pipe into a2ps
case $diff_on in
  words) # Word differences
    $wdiff_prog $wdiff_options $file1 $file2	\
       | $a2ps -Ewdiff $a2ps_options || exit 1
    ;;

  lines) # Line differences
    # We need the total number of lines
    lines=`wc -l $file1 $file2 | sed -n 3p`
    lines=`set -- $lines && echo $1`
    $diff_prog $diff_options -$lines $file1 $file2	\
       | $a2ps -gEudiff $a2ps_options || exit 1
    ;;
esac

exit 0
