<div>Hi Rob,</div>
<div> </div>
<div>The attached KLOGD patch is an improved version of the one you have in hg.</div>
<div>This also has a fix for boundary condition crash.</div>
<div> </div>
<div>regards,</div>
<div>Ashwini</div>
<div><br><br> </div>
<div class="gmail_quote">On Mon, Jul 15, 2013 at 11:05 PM, Isaac <span dir="ltr"><<a href="mailto:idunham@lavabit.com" target="_blank">idunham@lavabit.com</a>></span> wrote:<br>
<blockquote style="BORDER-LEFT:#ccc 1px solid;MARGIN:0px 0px 0px 0.8ex;PADDING-LEFT:1ex" class="gmail_quote">
<div class="HOEnZb">
<div class="h5">On Mon, Jul 15, 2013 at 03:43:27PM +0530, Ashwini Sharma wrote:<br>> Hi Rob,<br>><br>> I have implemented klogd, Klogd has both the options as its source,<br>> 1. Reading from kernel ring buffer, thru KLOGCTL interface<br>
> 2. Reading from "/proc/kmsg". This is Configurable option.<br>><br>><br>> Attached is the patch for klogd.<br>><br>> Let me know for any comments you have.<br>><br>><br>> Thanks,<br>
> Ashwini<br><br></div></div>From what I've seen, you might want to change a couple things.<br><br>--- /dev/null 2013-07-15 12:17:51.251463096 +0900<br>+++ toys/other/klogd.c 2013-07-15 19:06:<a href="tel:19.188909098" value="+19188909098">19.188909098</a> +0900<br>
@@ -0,0 +1,146 @@<br>+/* klogd.c - Klogd, The kernel log Dameon.<br>+ *<br>+ * Copyright 2013 Sandeep Sharma <<a href="mailto:sandeep.jack2756@gmail.com">sandeep.jack2756@gmail.com</a>><br>+ *<br>+ * No standard<br>
+<br>+USE_KLOGD(NEWTOY(klogd, "c#<1>8n", TOYFLAG_SBIN))<br>+<br>+config KLOGD<br>+ bool "klogd"<br>+ default y<br>+ help<br>+ usage: klogd [-n] [-c N]<br>+<br>+ -c N Print to console messages more urgent than prio N (1-8)"<br>
+ -n Run in foreground.<br>+<br>+config KLOGD_SOURCE_RING_BUFFER<br>+ bool "enable kernel ring buffer as log source."<br>+ default n<br>+ depends on KLOGD<br>+*/<br>+<br>+#define FOR_klogd<br>+#include "toys.h"<br>
+#include <signal.h><br>+GLOBALS(<br>+ long level;<br>+ int fd;<br>+)<br>+<br>+#if CFG_KLOGD_SOURCE_RING_BUFFER<br>Most of these functions look like they should be inlined-they're only called<br>once.<br>The approach used throughout toybox is roughly equivalent to<br>
if (...RING_BUFFER) {<br> //use klogctl<br> } else {<br> //use /proc/kmesg<br> }<br><br>+#include <sys/klog.h><br>+static void open_klogd(void)<br>+{<br>+ syslog(LOG_NOTICE, "KLOGD: started with Kernel ring buffer as log source\n");<br>
+ klogctl(1, NULL, 0);<br>+}<br>+<br>+static int read_klogd(char *bufptr, int len)<br>+{<br>+ return klogctl(2, bufptr, len);<br>+}<br>+<br>+static void set_log_level(int level)<br>+{<br>+ klogctl(8, NULL, level);<br>+}<br>
+<br>+static void close_klogd(void)<br>+{<br>+ klogctl(7, NULL, 0);<br>+ klogctl(0, NULL, 0);<br>+}<br>+#else<br>+static void open_klogd(void)<br>+{<br>+ TT.fd = xopen("/proc/kmsg", O_RDONLY); //_PATH_KLOG in paths.h<br>
+ syslog(LOG_NOTICE, "KLOGD: started with /proc/kmsg as log source\n");<br>+}<br>+<br>+static int read_klogd(char *bufptr, int len)<br>+{<br>+ return xread(TT.fd, bufptr, len);<br>+}<br>+<br>+static void set_log_level(int level)<br>
+{<br>+ FILE *fptr = xfopen("/proc/sys/kernel/printk", "w");<br>+ fprintf(fptr, "%u\n", level);<br>+ fclose(fptr);<br>+ fptr = NULL;<br>+}<br>+<br>+static void close_klogd(void)<br>
+{<br>+ set_log_level(7);<br>+ xclose(TT.fd);<br>+}<br>+#endif<br>+<br>+static void handle_signal(int sig)<br>+{<br>+ close_klogd();<br>+ syslog(LOG_NOTICE,"KLOGD: Daemon exiting......");<br>+ exit(1);<br>+}<br>
+<br>+static int daemonize(void)<br>+{<br>+ pid_t pid;<br>+ int fd = open("/dev/null", O_RDWR);<br>+ if (fd < 0) fd = open("/", O_RDONLY, 0666);<br>+ if((pid = fork()) < 0) {<br>+ perror_msg("DAEMON: fail to fork");<br>
+ return -1;<br>Trivial, but I think perror_exit is for this purpose.<br><br>+ }<br>+ if (pid) exit(EXIT_SUCCESS);<br>+<br>+ setsid();<br>+ dup2(fd, 0);<br>+ dup2(fd, 1);<br>+ dup2(fd, 2);<br>+ if (fd > 2) close(fd);<br>
+ return 0;<br>+}<br><br>AFAIK, everything except handle_signal should be inlined.<br>And a less generic name should be given to that.<br>+<br>+/*<br>+ * Read kernel ring buffer in local buff and keep track of<br>+ * "used" amount to track next read to start.<br>
+ */<br>+void klogd_main(void)<br>+{<br>+ int prio, size, used = 0;<br>+ char *start, *line_start, msg_buffer[16348]; //LOG_LINE_LENGTH - Ring buffer size<br>+<br>+ sigatexit(handle_signal);<br>+ if (toys.optflags & FLAG_c) set_log_level(TT.level); //set log level<br>
+ if (!(toys.optflags & FLAG_n)) daemonize(); //Make it daemon<br>+ open_klogd();<br>+ openlog("Kernel", 0, LOG_KERN); //open connection to system logger..<br>+<br>+ while(1) {<br>+ start = msg_buffer + used; //start updated for re-read.<br>
+ size = read_klogd(start, sizeof(msg_buffer) - used - 1);<br>+ if (size < 0) perror_exit("error reading file:");<br>+ start[size] = '\0'; //Ensure last line to be NUL terminated.<br>+ if (used) start = msg_buffer;<br>
+ while(1) {<br>+ if ((line_start = strsep(&start, "\n")) != NULL && start != NULL) used = 0;<br>+ else { //Incomplete line, copy it to start of buff.<br>+ used = strlen(line_start);<br>
+ strcpy(msg_buffer, line_start);<br>+ if (used < (sizeof(msg_buffer) - 1)) break;<br>+ used = 0; //we have buffer full, log it as it is.<br>+ }<br>+ prio = LOG_INFO; //we dont know priority, mark it INFO<br>
+ if (*line_start == '<') { //we have new line to syslog<br>+ line_start++;<br>+ if (line_start) prio = (int)strtoul(line_start, &line_start, 10);<br>+ if (*line_start == '>') line_start++;<br>
+ }<br>+ if (*line_start) syslog(prio, "%s", line_start);<br>+ }<br>+ }<br>+}<br><br><br></blockquote></div><br>