1/* 2 debug.c: log (or not) messages 3 Copyright (C) 2003-2011 Ludovic Rousseau 4 5 This library is free software; you can redistribute it and/or 6 modify it under the terms of the GNU Lesser General Public 7 License as published by the Free Software Foundation; either 8 version 2.1 of the License, or (at your option) any later version. 9 10 This library is distributed in the hope that it will be useful, 11 but WITHOUT ANY WARRANTY; without even the implied warranty of 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 Lesser General Public License for more details. 14 15 You should have received a copy of the GNU Lesser General Public License 16 along with this library; if not, write to the Free Software Foundation, 17 Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. 18*/ 19 20/* 21 * $Id: debug.c 6760 2013-10-01 12:57:50Z rousseau $ 22 */ 23 24 25#include "config.h" 26#include "misc.h" 27#include "debug.h" 28 29#include <stdarg.h> 30#include <stdio.h> 31#include <string.h> 32#include <sys/time.h> 33#include <stdlib.h> 34 35#include "strlcpycat.h" 36 37#undef LOG_TO_STDERR 38 39#ifdef LOG_TO_STDERR 40#define LOG_STREAM stderr 41#else 42#define LOG_STREAM stdout 43#endif 44 45void log_msg(const int priority, const char *fmt, ...) 46{ 47 char debug_buffer[160]; /* up to 2 lines of 80 characters */ 48 va_list argptr; 49 static struct timeval last_time = { 0, 0 }; 50 struct timeval new_time = { 0, 0 }; 51 struct timeval tmp; 52 int delta; 53 const char *color_pfx = "", *color_sfx = ""; 54 const char *time_pfx = "", *time_sfx = ""; 55 static int initialized = 0; 56 static int LogDoColor = 0; 57 58 if (!initialized) 59 { 60 char *term; 61 62 initialized = 1; 63 term = getenv("TERM"); 64 if (term) 65 { 66 const char *terms[] = { "linux", "xterm", "xterm-color", "Eterm", "rxvt", "rxvt-unicode", "xterm-256color" }; 67 unsigned int i; 68 69 /* for each known color terminal */ 70 for (i = 0; i < COUNT_OF(terms); i++) 71 { 72 /* we found a supported term? */ 73 if (0 == strcmp(terms[i], term)) 74 { 75 LogDoColor = 1; 76 break; 77 } 78 } 79 } 80 } 81 82 if (LogDoColor) 83 { 84 color_sfx = "\33[0m"; 85 time_sfx = color_sfx; 86 time_pfx = "\33[36m"; /* Cyan */ 87 88 switch (priority) 89 { 90 case PCSC_LOG_CRITICAL: 91 color_pfx = "\33[01;31m"; /* bright + Red */ 92 break; 93 94 case PCSC_LOG_ERROR: 95 color_pfx = "\33[35m"; /* Magenta */ 96 break; 97 98 case PCSC_LOG_INFO: 99 color_pfx = "\33[34m"; /* Blue */ 100 break; 101 102 case PCSC_LOG_DEBUG: 103 color_pfx = ""; /* normal (black) */ 104 color_sfx = ""; 105 break; 106 } 107 } 108 109 gettimeofday(&new_time, NULL); 110 if (0 == last_time.tv_sec) 111 last_time = new_time; 112 113 tmp.tv_sec = new_time.tv_sec - last_time.tv_sec; 114 tmp.tv_usec = new_time.tv_usec - last_time.tv_usec; 115 if (tmp.tv_usec < 0) 116 { 117 tmp.tv_sec--; 118 tmp.tv_usec += 1000000; 119 } 120 if (tmp.tv_sec < 100) 121 delta = tmp.tv_sec * 1000000 + tmp.tv_usec; 122 else 123 delta = 99999999; 124 125 last_time = new_time; 126 127 va_start(argptr, fmt); 128 (void)vsnprintf(debug_buffer, sizeof debug_buffer, fmt, argptr); 129 va_end(argptr); 130 131 (void)fprintf(LOG_STREAM, "%s%.8d%s %s%s%s\n", time_pfx, delta, time_sfx, 132 color_pfx, debug_buffer, color_sfx); 133 fflush(LOG_STREAM); 134} /* log_msg */ 135 136void log_xxd(const int priority, const char *msg, const unsigned char *buffer, 137 const int len) 138{ 139 int i; 140 char *c, debug_buffer[len*3 + strlen(msg) +1]; 141 size_t l; 142 143 (void)priority; 144 145 l = strlcpy(debug_buffer, msg, sizeof debug_buffer); 146 c = debug_buffer + l; 147 148 for (i = 0; i < len; ++i) 149 { 150 /* 2 hex characters, 1 space, 1 NUL : total 4 characters */ 151 (void)snprintf(c, 4, "%02X ", buffer[i]); 152 c += 3; 153 } 154 155 (void)fprintf(LOG_STREAM, "%s\n", debug_buffer); 156 fflush(LOG_STREAM); 157} /* log_xxd */ 158