+static uint64_t
+get_kernel_ts(const char *ts_sec, const char *ts_nsec)
+{
+ uint64_t ts = strtoull(ts_sec, NULL, 10) * UDEBUG_TS_SEC +
+ strtoull(ts_nsec, NULL, 10) / 1000;
+ struct timespec wall, mono;
+
+ if (clock_gettime(CLOCK_REALTIME, &wall) ||
+ clock_gettime(CLOCK_MONOTONIC, &mono))
+ return 0;
+
+ ts += (wall.tv_sec - mono.tv_sec) * UDEBUG_TS_SEC;
+ ts += (wall.tv_nsec - mono.tv_nsec) / 1000;
+
+ return ts;
+}
+
+static void
+log_add_udebug(int priority, char *buf, int size, int source)
+{
+ regmatch_t matches[4];
+ struct udebug_buf *udb;
+ uint64_t ts = 0;
+
+ if (source == SOURCE_KLOG)
+ udb = &udb_kernel;
+ else if ((priority & LOG_FACMASK) == LOG_LOCAL7)
+ udb = &udb_debug;
+ else
+ udb = &udb_user;
+
+ if (!udebug_buf_valid(udb))
+ return;
+
+ if (source == SOURCE_KLOG &&
+ !regexec(&pat_tstamp, buf, 4, matches, 0)) {
+ ts = get_kernel_ts(&buf[matches[1].rm_so], &buf[matches[2].rm_so]);
+ buf += matches[3].rm_so;
+ size -= matches[3].rm_so;
+ }
+
+ if (!ts)
+ ts = udebug_timestamp();
+
+ udebug_entry_init_ts(udb, ts);
+ udebug_entry_printf(udb, "<%d>", priority);
+ udebug_entry_append(udb, buf, size - 1);
+ udebug_entry_add(udb);
+}
+
+