- seen = 0;
- if (show_headers || (!hide_headers && nfiles > 1))
- printf("%s==> %s <==\n", i == 0 ? "" : "\n", argv[optind + i]);
- while ((nread = safe_read(fds[i], buf, sizeof(buf))) > 0) {
- if (from_top) {
-#ifdef BB_FEATURE_FANCY_TAIL
- if (units == BYTES) {
- if (count - 1 <= seen)
- nwrite = nread;
- else if (count - 1 <= seen + nread)
- nwrite = nread + seen - (count - 1);
- else
- nwrite = 0;
- seen += nread;
- } else {
-#else
- {
+
+ if (!G.from_top) {
+ off_t current = lseek(fd, 0, SEEK_END);
+ if (current > 0) {
+ unsigned off;
+ if (COUNT_BYTES) {
+ /* Optimizing count-bytes case if the file is seekable.
+ * Beware of backing up too far.
+ * Also we exclude files with size 0 (because of /proc/xxx) */
+ if (count == 0)
+ continue; /* showing zero bytes is easy :) */
+ current -= count;
+ if (current < 0)
+ current = 0;
+ xlseek(fd, current, SEEK_SET);
+ bb_copyfd_size(fd, STDOUT_FILENO, count);
+ continue;
+ }
+#if 1 /* This is technically incorrect for *LONG* strings, but very useful */
+ /* Optimizing count-lines case if the file is seekable.
+ * We assume the lines are <64k.
+ * (Users complain that tail takes too long
+ * on multi-gigabyte files) */
+ off = (count | 0xf); /* for small counts, be more paranoid */
+ if (off > (INT_MAX / (64*1024)))
+ off = (INT_MAX / (64*1024));
+ current -= off * (64*1024);
+ if (current < 0)
+ current = 0;
+ xlseek(fd, current, SEEK_SET);