summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorlandry <landry@openbsd.org>2008-11-13 18:33:03 +0000
committerlandry <landry@openbsd.org>2008-11-13 18:33:03 +0000
commit06fe599792e6549b00e524aa16a47ab66eb9d6d3 (patch)
treebabdf63274875ada9250d143c944a765139c279f
parentadd support for ST's chip since documentation is now available at (diff)
downloadwireguard-openbsd-06fe599792e6549b00e524aa16a47ab66eb9d6d3.tar.xz
wireguard-openbsd-06fe599792e6549b00e524aa16a47ab66eb9d6d3.zip
Backout previous commit, there are still some issues with it.
ok sthen@
-rw-r--r--usr.bin/tail/extern.h3
-rw-r--r--usr.bin/tail/forward.c219
-rw-r--r--usr.bin/tail/tail.c50
3 files changed, 83 insertions, 189 deletions
diff --git a/usr.bin/tail/extern.h b/usr.bin/tail/extern.h
index 1cda5b85cfd..948f4e49bb0 100644
--- a/usr.bin/tail/extern.h
+++ b/usr.bin/tail/extern.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: extern.h,v 1.10 2008/10/17 11:38:20 landry Exp $ */
+/* $OpenBSD: extern.h,v 1.11 2008/11/13 18:33:03 landry Exp $ */
/* $NetBSD: extern.h,v 1.3 1994/11/23 07:42:00 jtc Exp $ */
/*-
@@ -40,7 +40,6 @@ enum STYLE { NOTSET = 0, FBYTES, FLINES, RBYTES, RLINES, REVERSE };
void forward(FILE *, enum STYLE, off_t, struct stat *);
void reverse(FILE *, enum STYLE, off_t, struct stat *);
-void follow(char **, int, enum STYLE, off_t);
int bytes(FILE *, off_t);
int lines(FILE *, off_t);
diff --git a/usr.bin/tail/forward.c b/usr.bin/tail/forward.c
index e36498d9285..47cba10d3a3 100644
--- a/usr.bin/tail/forward.c
+++ b/usr.bin/tail/forward.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: forward.c,v 1.24 2008/10/17 11:38:20 landry Exp $ */
+/* $OpenBSD: forward.c,v 1.25 2008/11/13 18:33:03 landry Exp $ */
/* $NetBSD: forward.c,v 1.7 1996/02/13 16:49:10 ghudson Exp $ */
/*-
@@ -37,7 +37,7 @@
#if 0
static char sccsid[] = "@(#)forward.c 8.1 (Berkeley) 6/6/93";
#endif
-static char rcsid[] = "$OpenBSD: forward.c,v 1.24 2008/10/17 11:38:20 landry Exp $";
+static char rcsid[] = "$OpenBSD: forward.c,v 1.25 2008/11/13 18:33:03 landry Exp $";
#endif /* not lint */
#include <sys/types.h>
@@ -48,7 +48,6 @@ static char rcsid[] = "$OpenBSD: forward.c,v 1.24 2008/10/17 11:38:20 landry Exp
#include <stdio.h>
#include <string.h>
#include <unistd.h>
-#include <stdlib.h>
#include "extern.h"
@@ -80,6 +79,9 @@ void
forward(FILE *fp, enum STYLE style, off_t off, struct stat *sbp)
{
int ch;
+ struct stat nsb;
+ int kq, queue;
+ struct kevent ke;
switch(style) {
case FBYTES:
@@ -158,188 +160,83 @@ forward(FILE *fp, enum STYLE style, off_t off, struct stat *sbp)
break;
}
- while (!feof(fp) && (ch = getc(fp)) != EOF)
- if (putchar(ch) == EOF)
- oerr();
- if (ferror(fp)) {
- ierr();
- return;
- }
- (void)fflush(stdout);
-}
-
-struct file_info {
- FILE *fp;
- char *fname;
- struct stat fst;
-};
-
-/*
- * follow one or multiple files, i.e don't stop when end-of-file is reached,
- * but rather wait for additional data to be appended to the input.
- * this implements -f switch.
- */
-void
-follow(char **fnames, int nbfiles, enum STYLE style, off_t off)
-{
- int ch, first, i;
- int kq;
- struct kevent ke;
- struct stat cst;
- FILE *fp;
- struct file_info *files;
-
kq = -1;
- if ((kq = kqueue()) < 0)
- err(2, "kqueue() failed");
-
- if ((files = calloc(nbfiles, sizeof(struct file_info))) == NULL)
- err(1, "calloc() failed");
-
- for (first = 1, i = 0; (files[i].fname = *fnames++); i++) {
- if ((fp = fopen(files[i].fname, "r")) == NULL ||
- fstat(fileno(fp), &(files[i].fst))) {
- warn("%s",files[i].fname);
- nbfiles--;
- i--;
- continue;
- }
- if (S_ISDIR(files[i].fst.st_mode)) {
- warnx("%s is a directory, skipping.",files[i].fname);
- nbfiles--;
- i--;
- continue;
- }
- files[i].fp = fp;
- if (nbfiles > 1) {
- (void)printf("%s==> %s <==\n",
- first ? "" : "\n", files[i].fname);
- first = 0;
- }
-
- /* print from the given offset to the end */
- if (off != 0) {
- if (style == RBYTES) {
- if (S_ISREG(files[i].fst.st_mode)) {
- if (files[i].fst.st_size >= off &&
- fseeko(fp, -off, SEEK_END) == -1) {
- ierr();
- goto cleanup;
- }
- }
- if (bytes(fp, off))
- goto cleanup;
- } else if (rlines(fp, off, &(files[i].fst)) != 0)
- lines(fp, off);
- }
- (void)fflush(stdout);
-
- /* one event to see if there is data to read */
- ke.ident = fileno(fp);
+kq_retry:
+ if (fflag && ((kq = kqueue()) >= 0)) {
EV_SET(&ke, fileno(fp), EVFILT_READ,
EV_ENABLE | EV_ADD | EV_CLEAR,
- NULL, 0, NULL);
- if (kevent(kq, &ke, 1, NULL, 0, NULL) < 0)
- goto cleanup;
- else if (S_ISREG(files[i].fst.st_mode)) {
- /* one event to detect if inode changed */
+ 0,
+ 0, NULL);
+ if (kevent(kq, &ke, 1, NULL, 0, NULL) < 0) {
+ close(kq);
+ kq = -1;
+ } else if (S_ISREG(sbp->st_mode)) {
EV_SET(&ke, fileno(fp), EVFILT_VNODE,
EV_ENABLE | EV_ADD | EV_CLEAR,
NOTE_DELETE | NOTE_RENAME | NOTE_TRUNCATE,
0, NULL);
- if (kevent(kq, &ke, 1, NULL, 0, NULL) < 0)
- goto cleanup;
+ if (kevent(kq, &ke, 1, NULL, 0, NULL) < 0) {
+ close(kq);
+ kq = -1;
+ }
}
}
- /* no files to read */
- if (nbfiles == 0)
- goto cleanup;
-
- if (fp == NULL)
- fp = files[nbfiles - 1].fp;
-
for (;;) {
while (!feof(fp) && (ch = getc(fp)) != EOF)
if (putchar(ch) == EOF)
oerr();
- if (ferror(fp))
- goto cleanup;
-
+ if (ferror(fp)) {
+ ierr();
+ if (kq != -1)
+ close(kq);
+ return;
+ }
(void)fflush(stdout);
+ if (!fflag)
+ break;
clearerr(fp);
- /* give it a chance to fail.. */
- if (kevent(kq, NULL, 0, &ke, 1, NULL) <= 0) {
+ queue = 1;
+ if (kq < 0 || kevent(kq, NULL, 0, &ke, 1, NULL) <= 0) {
+ queue = 0;
sleep(1);
+ } else if (ke.filter == EVFILT_READ) {
continue;
- } else {
- /* an event occured on file #i */
- for (i = 0 ; i < nbfiles ; i++)
- if (fileno(files[i].fp) == ke.ident)
- break;
+ } else if ((ke.fflags & NOTE_TRUNCATE) == 0) {
+ /*
+ * File was renamed or deleted.
+ *
+ * Continue to look at it until a new file reappears
+ * with the same name.
+ * Fall back to the old algorithm for that.
+ */
+ close(kq);
+ kq = -1;
+ }
- /* EVFILT_READ event, check that it's on the current fp */
- if (ke.filter == EVFILT_READ) {
- if (fp != files[i].fp) {
- (void)printf("\n==> %s <==\n",files[i].fname);
- fp = files[i].fp;
- clearerr(fp);
- }
- /* EVFILT_VNODE event and File was renamed or deleted */
- } else if (ke.fflags & (NOTE_DELETE | NOTE_RENAME)) {
- /* file didn't reappear */
- if (stat(files[i].fname, &cst) != 0) {
- warnx("%s has been renamed or deleted.", files[i].fname);
- if (--nbfiles == 0)
- goto cleanup;
- /* overwrite with the latest file_info */
- fp = files[nbfiles].fp;
- (void)memcpy(&files[i], &files[nbfiles], sizeof(struct file_info));
- } else {
- /* Reopen file if the inode changed */
- if (cst.st_ino != files[i].fst.st_ino) {
- warnx("%s has been replaced, reopening.", files[i].fname);
- if ((fp = freopen(files[i].fname, "r", files[i].fp)) == NULL) {
- ierr();
- goto cleanup;
- }
- /*
- * on freopen(), events corresponding to the fp
- * were deleted from kqueue, we readd them
- */
- ke.ident = fileno(fp);
- EV_SET(&ke, fileno(fp), EVFILT_READ,
- EV_ENABLE | EV_ADD | EV_CLEAR,
- NULL, 0, NULL);
- if (kevent(kq, &ke, 1, NULL, 0, NULL) < 0)
- goto cleanup;
- else if (S_ISREG(files[i].fst.st_mode)) {
- EV_SET(&ke, fileno(fp), EVFILT_VNODE,
- EV_ENABLE | EV_ADD | EV_CLEAR,
- NOTE_DELETE | NOTE_RENAME | NOTE_TRUNCATE,
- 0, NULL);
- if (kevent(kq, &ke, 1, NULL, 0, NULL) < 0)
- goto cleanup;
- }
- files[i].fp = fp;
- }
- (void)memcpy(&(files[i].fst), &cst, sizeof(cst));
- }
- } else if (ke.fflags & NOTE_TRUNCATE) {
- /* reset file if it was truncated */
- warnx("%s has been truncated, resetting.", files[i].fname);
- fpurge(files[i].fp);
- rewind(files[i].fp);
- continue;
+ if (is_stdin || stat(fname, &nsb) != 0)
+ continue;
+ /* Reopen file if the inode changes or file was truncated */
+ if (nsb.st_ino != sbp->st_ino) {
+ warnx("%s has been replaced, reopening.", fname);
+ if ((fp = freopen(fname, "r", fp)) == NULL) {
+ ierr();
+ if (kq >= 0)
+ close(kq);
+ return;
}
+ (void)memcpy(sbp, &nsb, sizeof(nsb));
+ goto kq_retry;
+ } else if ((queue && (ke.fflags & NOTE_TRUNCATE)) ||
+ (!queue && nsb.st_size < sbp->st_size)) {
+ warnx("%s has been truncated, resetting.", fname);
+ fpurge(fp);
+ rewind(fp);
}
+ (void)memcpy(sbp, &nsb, sizeof(nsb));
}
-
-cleanup:
if (kq >= 0)
close(kq);
- free(files);
- return;
}
/*
diff --git a/usr.bin/tail/tail.c b/usr.bin/tail/tail.c
index 10d164290cd..c0aa35c725b 100644
--- a/usr.bin/tail/tail.c
+++ b/usr.bin/tail/tail.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: tail.c,v 1.15 2008/10/17 11:38:20 landry Exp $ */
+/* $OpenBSD: tail.c,v 1.16 2008/11/13 18:33:03 landry Exp $ */
/*-
* Copyright (c) 1991, 1993
@@ -42,7 +42,7 @@ static char copyright[] =
#if 0
static char sccsid[] = "@(#)tail.c 8.1 (Berkeley) 6/6/93";
#endif
-static char rcsid[] = "$OpenBSD: tail.c,v 1.15 2008/10/17 11:38:20 landry Exp $";
+static char rcsid[] = "$OpenBSD: tail.c,v 1.16 2008/11/13 18:33:03 landry Exp $";
#endif /* not lint */
#include <sys/types.h>
@@ -132,6 +132,10 @@ main(int argc, char *argv[])
}
argc -= optind;
argv += optind;
+
+ if (fflag && argc > 1)
+ errx(1, "-f option only appropriate for a single file");
+
/*
* If displaying in reverse, don't permit follow option, and convert
* style values.
@@ -158,33 +162,27 @@ main(int argc, char *argv[])
style = RLINES;
}
}
-
- if (*argv) {
- if (fflag) {
- follow(argv, argc, style, off);
- }
- else {
- for (first = 1; (fname = *argv++);) {
- if ((fp = fopen(fname, "r")) == NULL ||
- fstat(fileno(fp), &sb)) {
- ierr();
- continue;
- }
- if (argc > 1) {
- (void)printf("%s==> %s <==\n",
- first ? "" : "\n", fname);
- first = 0;
- (void)fflush(stdout);
- }
- if (rflag)
- reverse(fp, style, off, &sb);
- else
- forward(fp, style, off, &sb);
- (void)fclose(fp);
+ if (*argv)
+ for (first = 1; (fname = *argv++);) {
+ if ((fp = fopen(fname, "r")) == NULL ||
+ fstat(fileno(fp), &sb)) {
+ ierr();
+ continue;
}
+ if (argc > 1) {
+ (void)printf("%s==> %s <==\n",
+ first ? "" : "\n", fname);
+ first = 0;
+ (void)fflush(stdout);
+ }
+
+ if (rflag)
+ reverse(fp, style, off, &sb);
+ else
+ forward(fp, style, off, &sb);
+ (void)fclose(fp);
}
- }
else {
fname = "stdin";
is_stdin = 1;