summaryrefslogtreecommitdiff
path: root/appl/cmd/comm.b
diff options
context:
space:
mode:
Diffstat (limited to 'appl/cmd/comm.b')
-rwxr-xr-xappl/cmd/comm.b124
1 files changed, 124 insertions, 0 deletions
diff --git a/appl/cmd/comm.b b/appl/cmd/comm.b
new file mode 100755
index 00000000..1e56310e
--- /dev/null
+++ b/appl/cmd/comm.b
@@ -0,0 +1,124 @@
+implement Comm;
+
+# Copyright © 2002 Lucent Technologies Inc.
+# Subject to the Lucent Public Licence 1.02
+# Limbo translation by Vita Nuova 2004; bug fixed.
+
+include "sys.m";
+ sys: Sys;
+
+include "draw.m";
+
+include "bufio.m";
+ bufio: Bufio;
+ Iobuf: import bufio;
+
+include "arg.m";
+
+Comm: module
+{
+ init: fn(nil: ref Draw->Context, args: list of string);
+};
+
+One, Two, Three: con 1<<iota;
+cols := One|Two|Three;
+ldr := array[3] of {"", "\t", "\t\t"};
+
+init(nil: ref Draw->Context, args: list of string)
+{
+ sys = load Sys Sys->PATH;
+ bufio = load Bufio Bufio->PATH;
+
+ arg := load Arg Arg->PATH;
+ arg->init(args);
+ arg->setusage("comm [-123] file1 file2");
+ while((c := arg->opt()) != 0){
+ case c {
+ '1' to '3' =>
+ cols &= ~(1 << (c-'1'));
+ * =>
+ arg->usage();
+ }
+ }
+ args = arg->argv();
+ if(len args != 2)
+ arg->usage();
+ arg = nil;
+
+ if((cols & One) == 0){
+ ldr[1] = "";
+ ldr[2] = ldr[2][1:];
+ }
+ if((cols & Two) == 0)
+ ldr[2] = ldr[2][1:];
+
+ ib1 := openfil(hd args);
+ ib2 := openfil(hd tl args);
+ if((lb1 := ib1.gets('\n')) == nil){
+ if((lb2 := ib2.gets('\n')) == nil)
+ exit;
+ copy(ib2, lb2, 2);
+ }
+ if((lb2 := ib2.gets('\n')) == nil)
+ copy(ib1, lb1, 1);
+ for(;;)
+ case compare(lb1, lb2) {
+ 0 =>
+ wr(lb1, 3);
+ if((lb1 = ib1.gets('\n')) == nil){
+ if((lb2 = ib2.gets('\n')) == nil)
+ exit;
+ copy(ib2, lb2, 2);
+ }
+ if((lb2 = ib2.gets('\n')) == nil)
+ copy(ib1, lb1, 1);
+ 1 =>
+ wr(lb1, 1);
+ if((lb1 = ib1.gets('\n')) == nil)
+ copy(ib2, lb2, 2);
+ 2 =>
+ wr(lb2, 2);
+ if((lb2 = ib2.gets('\n')) == nil)
+ copy(ib1, lb1, 1);
+ }
+}
+
+wr(str: string, n: int)
+{
+ if(cols & (1<<(n-1)))
+ sys->print("%s%s", ldr[n-1], str);
+}
+
+copy(ibuf: ref Iobuf, lbuf: string, n: int)
+{
+ do
+ wr(lbuf, n);
+ while((lbuf = ibuf.gets('\n')) != nil);
+ exit;
+}
+
+compare(a: string, b: string): int
+{
+ for(i := 0; i < len a; i++){
+ if(i >= len b || a[i] < b[i])
+ return 1;
+ if(a[i] != b[i])
+ return 2;
+ }
+ if(i == len b)
+ return 0;
+ return 2;
+}
+
+openfil(s: string): ref Iobuf
+{
+ if(s == "-")
+ b := bufio->fopen(sys->fildes(0), Bufio->OREAD);
+ else
+ b = bufio->open(s, Bufio->OREAD);
+ if(b != nil)
+ return b;
+ sys->fprint(sys->fildes(2), "comm: cannot open %s: %r\n", s);
+ raise "fail:open";
+}
+