On Mon, Oct 02, 2017 at 01:34:26AM +0700, Robert Elz wrote: > Date: Sun, 1 Oct 2017 11:53:05 -0400 > From: Thor Lancelot Simon <t...@panix.com> > Message-ID: <20171001155305.ga27...@panix.com> > > | It's low risk (unlike, say, modifying the parser in the shell ;-)), > > Nah - that's easy, no risk at all! > > | And, frankly, I like the name ("tac") > > So do I, I used to have a tac command, and I miss it. > > coypu - your latest diff still had optind used incorrectly, thoe two optind > lines should be inside the "if we are tail" { statement-list } after the > getopt while loop. The tac case isn't using getopt, and so shouldn't be > using optind either. > > And I'd code it as "if we are [not]? tac" rather that "if we are tail" (ie: > strcmp(..., "tac") rather than tail, just in case someone has tail > linked to some other name ("lastlines" ??) we don't want to break that > by turning that into tac rather than tail.
I've done this, and added a man page.
Index: Makefile =================================================================== RCS file: /cvsroot/src/usr.bin/tail/Makefile,v retrieving revision 1.3 diff -u -r1.3 Makefile --- Makefile 23 Nov 1994 07:41:55 -0000 1.3 +++ Makefile 1 Oct 2017 19:22:32 -0000 @@ -1,7 +1,10 @@ # $NetBSD: Makefile,v 1.3 1994/11/23 07:41:55 jtc Exp $ # @(#)Makefile 8.1 (Berkeley) 6/6/93 - PROG= tail SRCS= forward.c misc.c read.c reverse.c tail.c +LINKS= ${BINDIR}/tail ${BINDIR}/tac + +MAN= tail.1 tac.1 + .include <bsd.prog.mk> Index: tac.1 =================================================================== RCS file: tac.1 diff -N tac.1 --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ tac.1 1 Oct 2017 19:22:32 -0000 @@ -0,0 +1,54 @@ +.\" $NetBSD$ +.\" +.\" Copyright (c) 2017 The NetBSD Foundation, Inc. +.\" All rights reserved. +.\" +.\" This code is derived from software contributed to The NetBSD Foundation +.\" by Maya Rashish. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in +.\" the documentation and/or other materials provided with the +.\" distribution. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +.\" ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +.\" LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS +.\" FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE +.\" COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, +.\" INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING, +.\" BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +.\" LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED +.\" AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +.\" OR TORT (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 October 1, 2017 +.Dt TAC 1 +.Os +.Sh NAME +.Nm tac +.Nd display file in reverse +.Sh SYNOPSIS +.Nm +.Op Ar file ... +.Sh DESCRIPTION +This displays the contents of each of each of the specified files, +or of the standard input if no files are specified its standard input, +in reverse order. +.Sh EXIT STATUS +.Ex -std tac +.Sh COMPATIBILITY +The +.Nm +utility doesn't support any of the options of GNU tac. +.Sh SEE ALSO +.Xr cat 1 , +.Xr tail 1 Index: tail.1 =================================================================== RCS file: /cvsroot/src/usr.bin/tail/tail.1,v retrieving revision 1.17 diff -u -r1.17 tail.1 --- tail.1 4 Jul 2017 07:04:50 -0000 1.17 +++ tail.1 1 Oct 2017 19:22:33 -0000 @@ -32,7 +32,7 @@ .\" .\" @(#)tail.1 8.1 (Berkeley) 6/6/93 .\" -.Dd June 15, 2014 +.Dd October 1, 2017 .Dt TAIL 1 .Os .Sh NAME @@ -43,7 +43,7 @@ .Oo .Fl f | .Fl F | -.Fl r +.Fl rqv .Oc .Oo .Fl b Ar number | @@ -133,12 +133,17 @@ option is to display all of the input. .El .Pp -If more than a single file is specified, each file is preceded by a +If more than a single file is specified, or the +.Fl v +option is used, each file is preceded by a header consisting of the string .Dq ==> XXX \*[Le]= where .Dq XXX is the name of the file. +The +.Fl q +flag disables the printing of the header in all cases. .Sh EXIT STATUS .Ex -std tail .Sh SEE ALSO Index: tail.c =================================================================== RCS file: /cvsroot/src/usr.bin/tail/tail.c,v retrieving revision 1.17 diff -u -r1.17 tail.c --- tail.c 31 Jan 2013 23:09:06 -0000 1.17 +++ tail.c 1 Oct 2017 19:22:33 -0000 @@ -67,6 +67,8 @@ enum STYLE style; int ch, first; char *p; + int qflag = 0; + int vflag = 0; setprogname(argv[0]); off = 0; @@ -105,32 +107,48 @@ obsolete(argv); style = NOTSET; - while ((ch = getopt(argc, argv, "Fb:c:fn:r")) != -1) - switch(ch) { - case 'F': - fflag = 2; - break; - case 'b': - ARG(512, FBYTES, RBYTES); - break; - case 'c': - ARG(1, FBYTES, RBYTES); - break; - case 'f': - fflag = 1; - break; - case 'n': - ARG(1, FLINES, RLINES); - break; - case 'r': - rflag = 1; - break; - case '?': - default: - usage(); - } - argc -= optind; - argv += optind; + if (strcmp(getprogname(), "tac") == 0) { + qflag = 1; + vflag = 0; + rflag = 1; + argc -= 1; + argv += 1; + } else { /* tail */ + while ((ch = getopt(argc, argv, "Fb:c:fn:rqv")) != -1) + switch(ch) { + case 'F': + fflag = 2; + break; + case 'b': + ARG(512, FBYTES, RBYTES); + break; + case 'c': + ARG(1, FBYTES, RBYTES); + break; + case 'f': + fflag = 1; + break; + case 'n': + ARG(1, FLINES, RLINES); + break; + case 'r': + rflag = 1; + break; + case 'q': + qflag = 1; + vflag = 0; + break; + case 'v': + qflag = 0; + vflag = 1; + break; + case '?': + default: + usage(); + } + argc -= optind; + argv += optind; + } if (fflag && argc > 1) xerrx(1, @@ -169,7 +187,7 @@ ierr(); continue; } - if (argc > 1) { + if (vflag || (qflag == 0 && argc > 1)) { (void)printf("%s==> %s <==\n", first ? "" : "\n", fname); first = 0; @@ -299,7 +317,7 @@ usage(void) { (void)fprintf(stderr, - "Usage: %s [-f | -F | -r] [-b # | -c # | -n #] [file ...]\n", + "Usage: %s [-f | -F | -rqv] [-b # | -c # | -n #] [file ...]\n", getprogname()); exit(1); }