Module Name: othersrc
Committed By: agc
Date: Tue Jan 15 01:46:04 UTC 2013
Modified Files:
othersrc/external/bsd/netdiff/bin: Makefile
othersrc/external/bsd/netdiff/dist: diff_subr.c diffreg.c netdiff.h
netwdiff.1 netwdiff.c
Log Message:
Add support to netwdiff to specify the insert and delete region
character sequences from the command line via the -w, -x, -y and -z
args. The default is, as before, "[- ... -]" for deleted regions,
and "{+ ... +}" for inserted text.
With this in place, the arguments can be used to highlight word diffs
portably across shells:
csh/tcsh:
% set ansi_red = "`printf '\e[31m'`"
% set ansi_end = "`printf '\e[0m'`"
% set ansi_green = "`printf '\e[32m'`"
sh/ksh/bash/zsh:
$ ansi_red="$(printf '\e[31m')"
$ ansi_end="$(printf '\e[0m')"
$ ansi_green="$(printf '\e[32m')"
and then in all shells:
netwdiff -w $ansi_red -x $ansi_end -y $ansi_green -z $ansi_end f1 f2
-- this will highlight deleted words in red, and added words in green,
on standard ANSI terminals. This gets around bash's twee $'' idiom
for tputs sequences. Thanks to Christos Zoulas for setting me
straight on this, and thanks also to Alan Barrett for the nudge to
implement the region arguments.
Thanks to all of the people who pointed me to comm(1)'s arguments as
being the model for wdiff's inhibit. My apologies, I should have
thought of that. I'm still trying to work out the model for the
choice of -w/-x/-y/-z; all suggestions gratefully received.
To generate a diff of this commit:
cvs rdiff -u -r1.3 -r1.4 othersrc/external/bsd/netdiff/bin/Makefile
cvs rdiff -u -r1.5 -r1.6 othersrc/external/bsd/netdiff/dist/diff_subr.c
cvs rdiff -u -r1.6 -r1.7 othersrc/external/bsd/netdiff/dist/diffreg.c
cvs rdiff -u -r1.3 -r1.4 othersrc/external/bsd/netdiff/dist/netdiff.h
cvs rdiff -u -r1.2 -r1.3 othersrc/external/bsd/netdiff/dist/netwdiff.1
cvs rdiff -u -r1.1 -r1.2 othersrc/external/bsd/netdiff/dist/netwdiff.c
Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.
Modified files:
Index: othersrc/external/bsd/netdiff/bin/Makefile
diff -u othersrc/external/bsd/netdiff/bin/Makefile:1.3 othersrc/external/bsd/netdiff/bin/Makefile:1.4
--- othersrc/external/bsd/netdiff/bin/Makefile:1.3 Sun Jan 13 22:17:21 2013
+++ othersrc/external/bsd/netdiff/bin/Makefile Tue Jan 15 01:46:03 2013
@@ -1,7 +1,8 @@
-# $NetBSD: Makefile,v 1.3 2013/01/13 22:17:21 agc Exp $
+# $NetBSD: Makefile,v 1.4 2013/01/15 01:46:03 agc Exp $
SUBDIR= netdiff
-SUBDIR= wdiff
+SUBDIR+= wdiff
+SUBDIR+= cmp
.if !make(install)
SUBDIR+= memdiff
SUBDIR+= qdiff
@@ -14,3 +15,4 @@ t:
cd qdiff && ${MAKE} t
cd memdiff && ${MAKE} t
cd wdiff && ${MAKE} t
+ cd cmp && ${MAKE} t
Index: othersrc/external/bsd/netdiff/dist/diff_subr.c
diff -u othersrc/external/bsd/netdiff/dist/diff_subr.c:1.5 othersrc/external/bsd/netdiff/dist/diff_subr.c:1.6
--- othersrc/external/bsd/netdiff/dist/diff_subr.c:1.5 Sun Jan 13 22:17:22 2013
+++ othersrc/external/bsd/netdiff/dist/diff_subr.c Tue Jan 15 01:46:03 2013
@@ -350,7 +350,23 @@ diff_set_var(diff_t *diff, const char *k
return 1;
}
}
- return 1;
+ if (strcasecmp(key, "start-delete") == 0 && value != NULL) {
+ asprintf(&diff->deleteregion[0], "%s", value);
+ return 1;
+ }
+ if (strcasecmp(key, "end-delete") == 0 && value != NULL) {
+ asprintf(&diff->deleteregion[1], "%s", value);
+ return 1;
+ }
+ if (strcasecmp(key, "start-insert") == 0 && value != NULL) {
+ asprintf(&diff->insertregion[0], "%s", value);
+ return 1;
+ }
+ if (strcasecmp(key, "end-insert") == 0 && value != NULL) {
+ asprintf(&diff->insertregion[1], "%s", value);
+ return 1;
+ }
+ return 0;
}
/* finished with structure, clean up */
@@ -384,6 +400,14 @@ diff_fini(diff_t *diff)
}
free(diff->excludes);
}
+ for (i = 0 ; i < 2 ; i++) {
+ if (diff->insertregion[i]) {
+ free(diff->insertregion[i]);
+ }
+ if (diff->deleteregion[i]) {
+ free(diff->deleteregion[i]);
+ }
+ }
}
return 1;
}
Index: othersrc/external/bsd/netdiff/dist/diffreg.c
diff -u othersrc/external/bsd/netdiff/dist/diffreg.c:1.6 othersrc/external/bsd/netdiff/dist/diffreg.c:1.7
--- othersrc/external/bsd/netdiff/dist/diffreg.c:1.6 Mon Jan 14 05:20:40 2013
+++ othersrc/external/bsd/netdiff/dist/diffreg.c Tue Jan 15 01:46:03 2013
@@ -360,9 +360,9 @@ diff_fread(diff_t *diff, void *ptr, size
char *p;
if (f->mapped) {
- memcpy(ptr, &f->mapped[f->curpos], c * size);
- f->curpos += (c * size);
- cc = c;
+ cc = MIN(c * size, (size_t)(f->size - (size_t)f->curpos));
+ memcpy(ptr, &f->mapped[f->curpos], cc);
+ f->curpos += cc;
} else {
cc = fread(ptr, size, c, f->fp);
}
@@ -1492,19 +1492,6 @@ bdiff_encode_copy(diff_t *diff, int32_t
return 1;
}
-#if 0
-static int
-bdiff_encode_run(diff_t *diff, uint8_t ch, int32_t size)
-{
- char c = 'r';
-
- diff_write(diff, &c, 1);
- diff_write(diff, &ch, 1);
- diff_write(diff, &size, sizeof(size));
- return 1;
-}
-#endif
-
static int
bdiff_catchup(diff_t *diff, long *indices, file_t *f, int lineno)
{
@@ -1939,6 +1926,36 @@ closem:
return rval;
}
+/* byte by byte comparison a la cmp(1) */
+static int
+cmp(diff_t *diff, file_t *f, int flags)
+{
+ size_t diffc;
+ size_t line;
+ size_t i;
+ int ch[2];
+
+ f[0].size = diff->st[0].st_size;
+ f[1].size = diff->st[1].st_size;
+ for (diffc = 0, line = 1, i = 0 ; i < f[0].size ; i++) {
+ if ((ch[0] = diff_getc(diff, &f[0])) == '\n') {
+ line += 1;
+ }
+ ch[1] = diff_getc(diff, &f[1]);
+ if (ch[0] != ch[1]) {
+ diffc = 1;
+ if (DIFF_GET_FLAG(diff, 'l')) {
+ diff_printf(diff, "%6zu %3o %3o\n", i + 1, ch[0], ch[1]);
+ } else {
+ diff_printf(diff, "%s %s differ: char %zu, line %zu\n",
+ f[0].name, f[1].name, i + 1, line);
+ break;
+ }
+ }
+ }
+ return (int)diffc;
+}
+
/*********************** word diff/wdiff ************************/
/* struct which describes a file to diff for word diffs */
@@ -2038,7 +2055,7 @@ copy(FILE *fp, wordfile_t *f, int copysp
/* print words */
static int
-pwords(FILE *fp, wordfile_t *f, long words, const char *head, const char *tail)
+pwords(FILE *fp, wordfile_t *f, long words, char **region)
{
const int copyspace = 1;
const int copyword = 0;
@@ -2046,14 +2063,14 @@ pwords(FILE *fp, wordfile_t *f, long wor
for (i = 0 ; i < words ; i++) {
copy(fp, f, copyspace);
- if (i == 0 && head && fp) {
- fprintf(fp, "%s", head);
+ if (i == 0 && region && fp) {
+ fprintf(fp, "%s", region[0]);
}
copy(fp, f, copyword);
f->wordc += 1;
}
- if (tail && fp) {
- fprintf(fp, "%s", tail);
+ if (region && fp) {
+ fprintf(fp, "%s", region[1]);
}
return 1;
}
@@ -2085,27 +2102,27 @@ pdiffs(diff_t *diff, wordfile_t *f, char
in[2] = strtol(&d[match[5].rm_so], NULL, 0);
in[3] = (match[7].rm_so >= 0) ? strtol(&d[match[7].rm_so], NULL, 0) : in[2];
type = d[match[4].rm_so];
- pwords(common, &f[0], (long)(in[0] - f[0].wordc - 1), NULL, NULL);
+ pwords(common, &f[0], (long)(in[0] - f[0].wordc - 1), NULL);
if (diff->inhibit == 3) {
fprintf(stdout, "\n%s\n", WDIFF_COMMON_DELIM);
}
- pwords(NULL, &f[1], (long)(in[2] - f[1].wordc - 1), NULL, NULL);
+ pwords(NULL, &f[1], (long)(in[2] - f[1].wordc - 1), NULL);
switch(type) {
case 'a':
if (f->p != f->file) {
- pwords(common, &f[0], 1, NULL, NULL);
+ pwords(common, &f[0], 1, NULL);
}
- pwords(rhs, &f[1], in[3] - in[2] + 1, "{+", "+}");
+ pwords(rhs, &f[1], in[3] - in[2] + 1, diff->insertregion);
if (rhs && common && in[0] == 0) {
fprintf(rhs, "\n");
}
break;
case 'c':
- pwords(lhs, &f[0], in[1] - in[0] + 1, "[-", "-]");
- pwords(rhs, &f[1], in[3] - in[2] + 1, "{+", "+}");
+ pwords(lhs, &f[0], in[1] - in[0] + 1, diff->deleteregion);
+ pwords(rhs, &f[1], in[3] - in[2] + 1, diff->insertregion);
break;
case 'd':
- pwords(lhs, &f[0], in[1] - in[0] + 1, "[-", "-]");
+ pwords(lhs, &f[0], in[1] - in[0] + 1, diff->deleteregion);
break;
default:
break;
@@ -2116,7 +2133,7 @@ pdiffs(diff_t *diff, wordfile_t *f, char
if (diff->inhibit == 3) {
fprintf(stdout, "\n%s", WDIFF_COMMON_DELIM);
}
- pwords(common, &f[0], (long)(f[0].totwords - f[0].wordc), NULL, NULL);
+ pwords(common, &f[0], (long)(f[0].totwords - f[0].wordc), NULL);
/* copy trailing whitespace */
copy(stdout, &f[0], 1);
return 1;
@@ -2138,6 +2155,25 @@ cleanup(diff_t *diff, wordfile_t *f)
diff_fini(diff);
}
+/* check we have region patterns to display */
+static int
+check_region_patterns(diff_t *diff)
+{
+ if (diff->deleteregion[0] == NULL) {
+ asprintf(&diff->deleteregion[0], "[-");
+ }
+ if (diff->deleteregion[1] == NULL) {
+ asprintf(&diff->deleteregion[1], "-]");
+ }
+ if (diff->insertregion[0] == NULL) {
+ asprintf(&diff->insertregion[0], "{+");
+ }
+ if (diff->insertregion[1] == NULL) {
+ asprintf(&diff->insertregion[1], "+}");
+ }
+ return 1;
+}
+
/*******************************************************************/
/* compare two regular files */
@@ -2256,6 +2292,7 @@ wdiff_file(diff_t *diff, const char *f1,
if (!diff_get_diffs(&local, &diffs, &cc)) {
return 0;
}
+ check_region_patterns(diff);
pdiffs(diff, wdf, diffs);
cleanup(&local, wdf);
return 1;
@@ -2291,7 +2328,60 @@ wdiff_mem(diff_t *diff, const char *m1,
if (!diff_get_diffs(&local, &diffs, &cc)) {
return 0;
}
+ check_region_patterns(diff);
pdiffs(diff, wdf, diffs);
cleanup(&local, wdf);
return 1;
}
+
+/* compare two regular files byte by byte */
+int
+cmp_file(diff_t *diff, const char *ofile1, const char *ofile2, int flags)
+{
+ stone_t s;
+ file_t f[2];
+ mode_t d[2];
+
+ if (diff == NULL || ofile1 == NULL || ofile2 == NULL) {
+ return D_MISMATCH1;
+ }
+ if (diff->tabsize == 0) {
+ diff->tabsize = 8;
+ }
+ if (diff->fp == NULL) {
+ diff->fp = stdout;
+ }
+ if (diff->optfile == NULL) {
+ diff->optfile = "\0";
+ }
+ memset(&s, 0x0, sizeof(s));
+ memset(&f[0], 0x0, sizeof(f[0]));
+ memset(&f[1], 0x0, sizeof(f[1]));
+ f[0].name = ofile1;
+ f[1].name = ofile2;
+ s.changec = 0;
+ s.lastline = 0;
+ s.lastmatchline = 0;
+ s.max_context = 64;
+ s.context_vec_ptr = s.context_vec_start - 1;
+ d[0] = S_ISDIR(diff->st[0].st_mode);
+ d[1] = S_ISDIR(diff->st[1].st_mode);
+ if (d[0] != d[1]) {
+ return (S_ISDIR(d[0])) ? D_MISMATCH1 : D_MISMATCH2;
+ }
+ if (strcmp(f[0].name, "-") == 0 && strcmp(f[1].name, "-") == 0) {
+ diff->status |= 2;
+ return D_MISMATCH1;
+ }
+ if ((f[0].fp = openfile(diff, f[0].name, 0, flags)) == NULL) {
+ warn("%s", f[0].name);
+ diff->status |= 2;
+ return D_MISMATCH1;
+ }
+ if ((f[1].fp = openfile(diff, f[1].name, 1, flags)) == NULL) {
+ warn("%s", f[1].name);
+ diff->status |= 2;
+ return D_MISMATCH1;
+ }
+ return cmp(diff, f, flags);
+}
Index: othersrc/external/bsd/netdiff/dist/netdiff.h
diff -u othersrc/external/bsd/netdiff/dist/netdiff.h:1.3 othersrc/external/bsd/netdiff/dist/netdiff.h:1.4
--- othersrc/external/bsd/netdiff/dist/netdiff.h:1.3 Sun Jan 13 22:17:22 2013
+++ othersrc/external/bsd/netdiff/dist/netdiff.h Tue Jan 15 01:46:04 2013
@@ -57,6 +57,8 @@ typedef struct diff_t {
int Toflag;
const char *optfile;
int inhibit; /* for word diff */
+ char *deleteregion[2];
+ char *insertregion[2];
} diff_t;
diff_t *diff_init(void);
@@ -73,4 +75,6 @@ int difference(diff_t */*diff*/, char */
int wdiff_file(diff_t */*diff*/, const char */*f1*/, const char */*f2*/);
int wdiff_mem(diff_t */*diff*/, const char */*m1*/, size_t /*size1*/, const char */*m2*/, size_t /*size2*/);
+int cmp_file(diff_t */*diff*/, const char */*file1*/, const char */*file2*/, int /*flags*/);
+
#endif
Index: othersrc/external/bsd/netdiff/dist/netwdiff.1
diff -u othersrc/external/bsd/netdiff/dist/netwdiff.1:1.2 othersrc/external/bsd/netdiff/dist/netwdiff.1:1.3
--- othersrc/external/bsd/netdiff/dist/netwdiff.1:1.2 Mon Jan 14 01:54:23 2013
+++ othersrc/external/bsd/netdiff/dist/netwdiff.1 Tue Jan 15 01:46:04 2013
@@ -1,4 +1,4 @@
-.\" $NetBSD: netwdiff.1,v 1.2 2013/01/14 01:54:23 agc Exp $
+.\" $NetBSD: netwdiff.1,v 1.3 2013/01/15 01:46:04 agc Exp $
.\"
.\" Copyright (c) 2013 Alistair Crooks <[email protected]>
.\" All rights reserved.
@@ -23,7 +23,7 @@
.\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
.\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
.\"
-.Dd January 13, 2013
+.Dd January 14, 2013
.Dt NETWDIFF 1
.Os
.Sh NAME
@@ -32,22 +32,16 @@
.Sh SYNOPSIS
.Nm
.Op Fl 123i
+.Op Fl w Ar start-delete
+.Op Fl x Ar end-delete
+.Op Fl y Ar start-insert
+.Op Fl z Ar end-insert
.Ar file1 file2
.Sh DESCRIPTION
The
.Nm
command performs a word-based difference and comparison on the
two files given as input.
-For each difference, deleted text is prefixed with a
-.Da [-
-and ended with a
-.Dq -]
-pattern.
-Text which has been added is prefixed with a
-.Dq {+
-pattern, and ends with a
-.Dq +}
-pattern.
Changes are interleaved, making it easier to see changes made
within the line differences reported by
.Xr netdiff 1 .
@@ -59,7 +53,7 @@ utility uses the
library.
.Pp
The following options are available:
-.Bl -tag -width sector-size123
+.Bl -tag -width sector-size123456
.It Fl 1
Inhibit the display of text which has been deleted.
.It Fl 2
@@ -69,6 +63,22 @@ Inhibit the display of text common to bo
means that only the changes will be displayed.
.It Fl i
Perform comparisons in a case-insensitive manner.
+.It Fl w Ar start-delete
+Specify the character sequence to be used at the start of a region of deleted text.
+The default is
+.Dq [-
+.It Fl x Ar end-delete
+Specify the character sequence to be used at the end of a region of deleted text.
+The default is
+.Dq -]
+.It Fl y Ar start-insert
+Specify the character sequence to be used at the start of a region of inserted text.
+The default is
+.Dq {+
+.It Fl z Ar end-insert
+Specify the character sequence to be used at the end of a region of inserted text.
+The default is
+.Dq +}
.El
.Sh RETURN VALUES
The
@@ -114,8 +124,42 @@ static int
%
.Ed
+.Pp
+To use colors to highlight text which has been inserted and deleted,
+the
+.Fl w ,
+.Fl x ,
+.Fl y
+and
+.Fl z
+arguments can be used.
+In C shell, shell variables can be set in the following way:
+.Bd -literal
+% set ansi_red = "`printf '\\e[31m'`"
+% set ansi_end = "`printf '\\e[0m'`"
+% set ansi_green = "`printf '\\e[32m'`"
+.Ed
+.Pp
+whilst in
+.Xr sh 1 ,
+.Xr ksh 1 ,
+and all Bourne shell-derived programs, the variables
+will be set in the following way:
+.Bd -literal
+$ ansi_red="$(printf '\\e[31m')"
+$ ansi_end="$(printf '\\e[0m')"
+$ ansi_green="$(printf '\\e[32m')"
+.Ed
+.Pp
+Finally, the escape sequences can be used as follows:
+.Bd -literal
+% netwdiff -w $ansi_red -x $ansi_end -y $ansi_green -z $ansi_end f1 f2
+.Ed
.Sh SEE ALSO
+.Xr ksh 1 ,
.Xr netdiff 1 ,
+.Xr printf 1 ,
+.Xr sh 1 ,
.Xr libnetdiff 3
.Sh HISTORY
The
Index: othersrc/external/bsd/netdiff/dist/netwdiff.c
diff -u othersrc/external/bsd/netdiff/dist/netwdiff.c:1.1 othersrc/external/bsd/netdiff/dist/netwdiff.c:1.2
--- othersrc/external/bsd/netdiff/dist/netwdiff.c:1.1 Sun Jan 13 22:17:22 2013
+++ othersrc/external/bsd/netdiff/dist/netwdiff.c Tue Jan 15 01:46:04 2013
@@ -39,7 +39,7 @@ main(int argc, char **argv)
memset(&diff, 0x0, sizeof(diff));
diff_set_var(&diff, "format", "normal");
diff_set_var(&diff, "output", "[dynamic]");
- while ((i = getopt(argc, argv, "123i")) != -1) {
+ while ((i = getopt(argc, argv, "123iw:x:y:z:")) != -1) {
switch(i) {
case '1':
diff_set_var(&diff, "inhibit", "lhs");
@@ -53,6 +53,18 @@ main(int argc, char **argv)
case 'i':
diff_set_flag(&diff, i);
break;
+ case 'w':
+ diff_set_var(&diff, "start-delete", optarg);
+ break;
+ case 'x':
+ diff_set_var(&diff, "end-delete", optarg);
+ break;
+ case 'y':
+ diff_set_var(&diff, "start-insert", optarg);
+ break;
+ case 'z':
+ diff_set_var(&diff, "end-insert", optarg);
+ break;
default:
break;
}