]> git.ipfire.org Git - thirdparty/freeradius-server.git/commitdiff
Alternate where we write errors in fr_strerror_printf to allow error messages to...
authorArran Cudbard-Bell <a.cudbardb@freeradius.org>
Wed, 15 Jul 2015 03:36:16 +0000 (23:36 -0400)
committerArran Cudbard-Bell <a.cudbardb@freeradius.org>
Wed, 15 Jul 2015 03:36:16 +0000 (23:36 -0400)
src/lib/log.c

index b0a978e5461abb54675795578c6f417a2acc847f..227b3a42d4d0660059fca8b9405eb3f57ca13172 100644 (file)
@@ -65,7 +65,7 @@ void fr_strerror_printf(char const *fmt, ...)
                /*
                 *      malloc is thread safe, talloc is not
                 */
-               buffer = malloc(sizeof(char) * (FR_STRERROR_BUFSIZE + 1));      /* One byte extra for status */
+               buffer = calloc((FR_STRERROR_BUFSIZE * 2) + 1, sizeof(char));   /* One byte extra for status */
                if (!buffer) {
                        fr_perror("Failed allocating memory for libradius error buffer");
                        return;
@@ -83,13 +83,26 @@ void fr_strerror_printf(char const *fmt, ...)
         *      NULL has a special meaning, setting the new byte to false.
         */
        if (!fmt) {
-               buffer[FR_STRERROR_BUFSIZE] = '\0';
+               buffer[FR_STRERROR_BUFSIZE * 2] = '\0';
                return;
        }
 
        va_start(ap, fmt);
-       vsnprintf(buffer, FR_STRERROR_BUFSIZE, fmt, ap);
-       buffer[FR_STRERROR_BUFSIZE] = '\1';                     /* Flip the 'new' byte to true */
+       /*
+        *      Alternate where we write the message, so we can do:
+        *      fr_strerror_printf("Additional error: %s", fr_strerror());
+        */
+       switch (buffer[FR_STRERROR_BUFSIZE * 2]) {
+       default:
+               vsnprintf(buffer + FR_STRERROR_BUFSIZE, FR_STRERROR_BUFSIZE, fmt, ap);
+               buffer[FR_STRERROR_BUFSIZE * 2] = '\2';                 /* Flip the 'new' byte to true */
+               break;
+
+       case '\2':
+               vsnprintf(buffer, FR_STRERROR_BUFSIZE, fmt, ap);
+               buffer[FR_STRERROR_BUFSIZE * 2] = '\1';                 /* Flip the 'new' byte to true */
+               break;
+       }
        va_end(ap);
 }
 
@@ -104,12 +117,20 @@ char const *fr_strerror(void)
        char *buffer;
 
        buffer = fr_thread_local_get(fr_strerror_buffer);
-       if (buffer && (buffer[FR_STRERROR_BUFSIZE] != '\0')) {
-               buffer[FR_STRERROR_BUFSIZE] = '\0';             /* Flip the 'new' byte to false */
+       if (!buffer) return "";
+
+       switch (buffer[FR_STRERROR_BUFSIZE * 2]) {
+       default:
+               return "";
+
+       case '\1':
+               buffer[FR_STRERROR_BUFSIZE * 2] = '\0';         /* Flip the 'new' byte to false */
                return buffer;
-       }
 
-       return "";
+       case '\2':
+               buffer[FR_STRERROR_BUFSIZE * 2] = '\0';         /* Flip the 'new' byte to false */
+               return buffer + FR_STRERROR_BUFSIZE;
+       }
 }
 
 /** Guaranteed to be thread-safe version of strerror