/* * Adds a timestamp before every line. * * Author: Peter Wu * Date: 2013-10-04 */ #include #include #include #include #include #include static void print_usage(const char *program_name) { fprintf(stderr, "Usage: %s [-d]\n", program_name); fputs("Options:\n" " -d Display time difference instead of a monotonic clock\n" " -z Start the monotonic clock at zero.\n", stderr); } struct timespec timediff(struct timespec begin, struct timespec end) { struct timespec diff; diff.tv_sec = end.tv_sec - begin.tv_sec; diff.tv_nsec = end.tv_nsec - begin.tv_nsec; if (end.tv_nsec < begin.tv_nsec) { /* alternative case: 3.2 -> 4.1, diff is 0.9 */ diff.tv_sec--; diff.tv_nsec += 1000000000; } return diff; } int main(int argc, char **argv) { const char *out_format; char buf[4096]; struct timespec tp[2] = { { 0, 0 } }; int tp_i = 0; int opt; bool diff = false; bool zero = false; while ((opt = getopt(argc, argv, "dz")) != -1) { switch (opt) { case 'd': diff = true; break; case 'z': zero = true; break; default: print_usage(argv[0]); return 1; } } if (diff) { out_format = "[%+6lld.%06lu] %s\n"; } else { out_format = "[%6llu.%06lu] %s\n"; } if (zero) { /* Use zero as reference. */ clock_gettime(CLOCK_MONOTONIC, &tp[1]); } while (fgets(buf, sizeof(buf), stdin) != NULL) { char *newline = strrchr(buf, '\n'); clock_gettime(CLOCK_MONOTONIC, &tp[tp_i]); if (newline) *newline = '\0'; if (diff) { /* new time is available in "tp_i". Old time (and print * target) is the inverse of tp_i (modulo 2). */ tp[tp_i ^ 1] = timediff(tp[tp_i ^ 1], tp[tp_i]); /* flip such that "tp_i" refers to difference time and * inverse "tp_i" points to the new time (in the next * iteration it becomes the old time) */ tp_i ^= 1; } else if (zero) { tp[tp_i] = timediff(tp[tp_i ^ 1], tp[tp_i]); } printf(out_format, (long long) tp[tp_i].tv_sec, tp[tp_i].tv_nsec / 1000, buf); } return 0; }