]> Pileus Git - ~andy/fetchmail/commitdiff
Add rawlog.patch.
authorMatthias Andree <matthias.andree@gmx.de>
Sun, 21 Aug 2011 09:55:05 +0000 (11:55 +0200)
committerMatthias Andree <matthias.andree@gmx.de>
Sun, 21 Aug 2011 09:58:02 +0000 (11:58 +0200)
contrib/rawlog.patch [new file with mode: 0644]

diff --git a/contrib/rawlog.patch b/contrib/rawlog.patch
new file mode 100644 (file)
index 0000000..a341d4e
--- /dev/null
@@ -0,0 +1,114 @@
+This patch logs raw socket data, to assist debugging when discriminating
+between server and fetchmail bugs.
+
+Apply it to fetchmail 6.3.20 and set the environment variable
+FETCHMAIL_RAW_LOGFILE to a log file writable by fetchmail. If it's not
+there, it gets created with mode 0600 (which requires directory write
+permission).
+
+The file gets appended to, so you can log into named pipes, character
+(stream) devices and to the console if you're so inclined.
+
+Note 1: any logging failures cause fetchmail to abort() forcefully.
+
+Note 2: non-printable characters are hex-escaped, so it is safe to use
+FETCHMAIL_RAW_LOGFILE=/dev/stderr or similar.
+
+-- Matthias Andree, August 2011
+
+diff --git a/sink.c b/sink.c
+index 5d92556..ff6208d 100644
+--- a/sink.c
++++ b/sink.c
+@@ -649,6 +649,10 @@ int stuffline(struct query *ctl, char *buf)
+     while ((last += strlen(last)) && (last[-1] != '\n'))
+         last++;
++    if (outlevel >= O_DEBUG && (size_t)(last - buf) != strlen(buf))
++      report(stdout, GT_("DEBUG: stuffline shipping line with NULs, length=%lu, strlen=%lu\n"), last - buf, strlen(buf));
++
++
+     /* fix message lines that have only \n termination (for qmail) */
+     if (ctl->forcecr)
+     {
+diff --git a/socket.c b/socket.c
+index e338207..dcaf19d 100644
+--- a/socket.c
++++ b/socket.c
+@@ -381,6 +381,49 @@ static    SSL *_ssl_context[FD_SETSIZE];
+ static SSL    *SSLGetContext( int );
+ #endif /* SSL_ENABLE */
++#include <fcntl.h>
++
++static const char *rawlogfile;
++static FILE *rlogstream;
++
++static int SockLog(void) {
++    static int haveinit;
++    static int wantlog;
++    static int logfd = -1;
++
++    if (!haveinit) {
++      haveinit = 1;
++      if ((rawlogfile = getenv("FETCHMAIL_RAW_LOGFILE"))) {
++          if ((logfd = open(rawlogfile, O_WRONLY|O_APPEND|O_CREAT, 0600)) == -1) {
++              report(stderr, GT_("FETCHMAIL_RAW_LOGFILE is set, but opening \"%s\" for appending write failed: %s\n"), rawlogfile, strerror(errno));
++              abort();
++          }
++          if (!(rlogstream = fdopen(logfd, "a"))) {
++              report(stderr, GT_("FETCHMAIL_RAW_LOGFILE is set, but fdopen(%d) failed: %s\n"), logfd, strerror(errno));
++              abort();
++          }
++          setvbuf(rlogstream, NULL, _IOLBF, 0);
++          wantlog = 1;
++      }
++    }
++    return wantlog;
++}
++
++static void LogPrintf(const char *fmt, ...) {
++    va_list va;
++    const char *locsav;
++    va_start(va, fmt);
++    if (!SockLog()) return;
++    locsav = setlocale(LC_ALL, NULL);
++    (void)setlocale(LC_ALL, "C");
++    if (EOF == vfprintf(rlogstream, fmt, va) || EOF == fflush(rlogstream)) {
++      report(stderr, GT_("FETCHMAIL_RAW_LOGFILE is set, but logging failed: %s\n"), strerror(errno));
++      abort();
++    }
++    (void)setlocale(LC_ALL, locsav);
++    va_end(va);
++}
++
+ int SockWrite(int sock, const char *buf, int len)
+ {
+     int n, wrlen = 0;
+@@ -388,6 +431,12 @@ int SockWrite(int sock, const char *buf, int len)
+     SSL *ssl;
+ #endif
++    if (SockLog()) {
++      char *tmps = sdump(buf, len);
++      LogPrintf("[>%d-%s count=%04d] %s\n", sock, SSLGetContext(sock) ? "crypt" : "plain", len, tmps);
++      free(tmps);
++    }
++
+     while (len)
+     {
+ #ifdef SSL_ENABLE
+@@ -504,6 +553,13 @@ int SockRead(int sock, char *buf, int len)
+           (!newline && len);
+     *bp = '\0';
++    if (SockLog())
++    {
++      char *tmps = sdump(buf, bp - buf);
++      LogPrintf("[<%d-%s count=%04d] %s\n", sock, SSLGetContext(sock) ? "crypt" : "plain", bp - buf, tmps);
++      free(tmps);
++    }
++
+     return bp - buf;
+ }