Add mandoc-manpage for comm(1) and clean up code

and mark it as finished in README.
This commit is contained in:
FRIGN 2015-01-18 00:07:29 +01:00 committed by sin
parent 572cea058c
commit f9a1e11661
3 changed files with 80 additions and 74 deletions

2
README
View File

@ -18,7 +18,7 @@ The following tools are implemented (* == finished):
* cksum yes none
* cmp yes none
* cols non-posix none
comm yes none
* comm yes none
cp no -H, -i, -L
* cron non-posix none
cut yes none

74
comm.1
View File

@ -1,33 +1,43 @@
.TH COMM 1 sbase\-VERSION
.SH NAME
comm \- select or reject lines common to two files
.SH SYNOPSIS
.B comm
.RB [ \-123 ]
.IR file1
.IR file2
.SH DESCRIPTION
The comm utility reads
.IR file1
.Dd January 18, 2015
.Dt COMM 1 sbase\-VERSION
.Sh NAME
.Nm comm
.Nd select or reject lines common to two files
.Sh SYNOPSIS
.Nm comm
.Op Fl 123
.Ar file1
.Ar file2
.Sh DESCRIPTION
.Nm
reads
.Ar file1
and
.IR file2,
which should be sorted lexically,
and produces three text columns as output: lines only in
.IR file1;
lines only in
.IR file2;
and lines in both files.
.SH OPTIONS
.TP
.BI \-1
Suppress printing of column 1
.TP
.BI \-2
Suppress printing of column 2
.TP
.BI \-3
Suppress printing of column 3
.SH SEE ALSO
.IR cmp (1),
.IR sort (1),
.IR uniq (1)
.Ar file2,
which should both be sorted lexically, and writes three text columns
to stdout:
.Bl -tag -width Ds
.It 1
Lines only in
.Ar file1 .
.It 2
Lines only in
.Ar file2 .
.It 3
Common lines.
.El
.Sh OPTIONS
.Bl -tag -width Ds
.It Fl 1 | Fl 2 | Fl 3
Suppress column 1 | 2 | 3
.El
.Sh SEE ALSO
.Xr cmp 1 ,
.Xr sort 1 ,
.Xr uniq 1
.Sh STANDARDS
The
.Nm
utility is compliant with the
.St -p1003.1-2008
specification.

78
comm.c
View File

@ -8,12 +8,44 @@
#define CLAMP(x, l, h) MIN(h, MAX(l, x))
static void printline(int, char *);
static char *nextline(char *, int, FILE *, char *);
static void finish(int, FILE *, char *);
static int show = 0x07;
static void
printline(int pos, char *line)
{
int i;
if (!(show & (0x1 << pos)))
return;
for (i = 0; i < pos; i++) {
if (show & (0x1 << i))
putchar('\t');
}
printf("%s", line);
}
static char *
nextline(char *buf, int n, FILE *f, char *name)
{
buf = fgets(buf, n, f);
if (!buf && !feof(f))
eprintf("%s: read error:", name);
if (buf && !strchr(buf, '\n'))
eprintf("%s: line too long\n", name);
return buf;
}
static void
finish(int pos, FILE *f, char *name)
{
char buf[LINE_MAX + 1];
while (nextline(buf, sizeof(buf), f, name))
printline(pos, buf);
exit(1);
}
static void
usage(void)
{
@ -25,7 +57,7 @@ main(int argc, char *argv[])
{
int i, diff = 0;
FILE *fp[2];
char lines[2][LINE_MAX+1];
char lines[2][LINE_MAX + 1];
ARGBEGIN {
case '1':
@ -73,39 +105,3 @@ main(int argc, char *argv[])
return 0;
}
static void
printline(int pos, char *line)
{
int i;
if (!(show & (0x1 << pos)))
return;
for (i = 0; i < pos; i++) {
if (show & (0x1 << i))
putchar('\t');
}
printf("%s", line);
}
static char *
nextline(char *buf, int n, FILE *f, char *name)
{
buf = fgets(buf, n, f);
if (!buf && !feof(f))
eprintf("%s: read error:", name);
if (buf && !strchr(buf, '\n'))
eprintf("%s: line too long\n", name);
return buf;
}
static void
finish(int pos, FILE *f, char *name)
{
char buf[LINE_MAX+1];
while (nextline(buf, sizeof(buf), f, name))
printline(pos, buf);
exit(1);
}