nmxp_log.c 5.2 KB
Newer Older
1 2
/*! \file
 *
Matteo Quintiliani's avatar
Matteo Quintiliani committed
3
 * \brief Log for Nanometrics Protocol Library
4 5 6 7 8 9
 *
 * Author:
 * 	Matteo Quintiliani
 * 	Istituto Nazionale di Geofisica e Vulcanologia - Italy
 *	quintiliani@ingv.it
 *
10
 * $Id: nmxp_log.c,v 1.23 2009-08-31 12:16:41 mtheo Exp $
Matteo Quintiliani's avatar
Matteo Quintiliani committed
11
 *
12 13 14 15 16 17 18 19 20 21
 */

#include "nmxp_log.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdarg.h>

#include <time.h>

Matteo Quintiliani's avatar
Matteo Quintiliani committed
22 23
#include "config.h"

24
#define MAX_LOG_MESSAGE_LENGTH 8000
25

Matteo Quintiliani's avatar
Matteo Quintiliani committed
26 27
#define LIBRARY_NAME "libnmxp"
#define NMXP_LOG_PREFIX "nmxp"
28

29 30 31 32 33 34 35 36
static char nmxp_log_prefix[MAX_LOG_MESSAGE_LENGTH] = NMXP_LOG_PREFIX;

void nmxp_log_set_prefix(char *prefix) {
    if(prefix) {
	snprintf(nmxp_log_prefix, MAX_LOG_MESSAGE_LENGTH, "%s [%s]", NMXP_LOG_PREFIX, NMXP_LOG_STR(prefix));
    }
}

37 38
void nmxp_log_get_prefix(char *ret, int size ) {
    strncpy(ret, nmxp_log_prefix,size);
39 40
}

41

42 43
const char *nmxp_log_version() {
    static char ret_str[MAX_LOG_MESSAGE_LENGTH] = "";
44
    snprintf(ret_str, MAX_LOG_MESSAGE_LENGTH, "%s-%s", NMXP_LOG_STR(LIBRARY_NAME), NMXP_LOG_STR(PACKAGE_VERSION));
45 46 47
    return ret_str;
}

48 49 50 51 52 53 54 55 56 57 58 59 60 61 62

int nmxp_log_stdout(char *msg) {
    int ret = fprintf(stdout, msg);
    fflush(stdout);
    return ret;
}

int nmxp_log_stderr(char *msg) {
    int ret = fprintf(stderr, msg);
    fflush(stderr);
    return ret;
}

#define NMXP_MAX_FUNC_LOG 10

63 64 65 66 67
/* private variables */
static int n_func_log = 0;
static int n_func_log_err = 0;
static int (*p_func_log[NMXP_MAX_FUNC_LOG]) (char *);
static int (*p_func_log_err[NMXP_MAX_FUNC_LOG]) (char *);
68 69 70 71 72


void nmxp_log_init(int (*func_log)(char *), int (*func_log_err)(char *)) {
    n_func_log = 0;
    n_func_log_err = 0;
73 74 75 76 77
    nmxp_log_add(func_log, func_log_err);
}


void nmxp_log_add(int (*func_log)(char *), int (*func_log_err)(char *)) {
Matteo Quintiliani's avatar
Matteo Quintiliani committed
78
    if(func_log != NULL) {
79 80
	p_func_log[n_func_log++] = func_log;
    }
Matteo Quintiliani's avatar
Matteo Quintiliani committed
81
    if(func_log_err != NULL) {
82
	p_func_log_err[n_func_log_err++] = func_log_err;
83
    }
84 85 86

}

87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121
void nmxp_log_rem(int (*func_log)(char *), int (*func_log_err)(char *)) {
    int i = 0;
    int j = 0;
    if(func_log != NULL) {
	i = 0;
	while(i < n_func_log  &&  p_func_log[i] != func_log) {
	    i++;
	}
	if(i < n_func_log) {
	    for(j=i; j < n_func_log-1; j++) {
		 p_func_log[j] = p_func_log[j+1];
	    }
	    n_func_log--;
	} else {
	    /* TODO not found */
	}
    }

    if(func_log_err != NULL) {
	i = 0;
	while(i < n_func_log_err  &&  p_func_log_err[i] != func_log_err) {
	    i++;
	}
	if(i < n_func_log_err) {
	    for(j=i; j < n_func_log_err-1; j++) {
		 p_func_log_err[j] = p_func_log_err[j+1];
	    }
	    n_func_log_err--;
	} else {
	    /* TODO not found */
	}
    }

}

122

123 124 125 126 127 128 129 130 131 132 133 134
/* Private function */
void nmxp_log_print_all(char *message, int (*a_func_log[NMXP_MAX_FUNC_LOG]) (char *), int a_n_func_log) {
    int i;
    if(a_n_func_log > 0) {
	for(i=0; i < a_n_func_log; i++) {
	    a_func_log[i](message);
	}
    } else {
	nmxp_log_stdout(message);
    }
}

135
#define MAX_SIZE_TIMESTR 100
136 137 138 139
int nmxp_log(int level, int verb, ... )
{
  static int staticverb = 0;
  int retvalue = 0;
140 141
  char message[MAX_LOG_MESSAGE_LENGTH];
  char message_final[MAX_LOG_MESSAGE_LENGTH];
142
  char prefix[MAX_LOG_MESSAGE_LENGTH];  
143
  char timestr[MAX_SIZE_TIMESTR];
144
  char *format;
145

146 147 148 149
  va_list listptr;
  time_t loc_time;

  if ( level == NMXP_LOG_SET ) {
150 151
    staticverb = verb;
    retvalue = staticverb;
152
  } else if ( (verb & staticverb)  ||  level == NMXP_LOG_ERR  ||  verb == NMXP_LOG_D_ANY ) {
153 154 155 156 157 158

    va_start(listptr, verb);
    format = va_arg(listptr, char *);

    /* Build local time string and cut off the newline */
    time(&loc_time);
159 160
    /*use reentrant ctime_r -D_POSIX_PTHREAD_SEMANTICS*/
    ctime_r(&loc_time,timestr);
161

162 163
    timestr[strlen(timestr) - 1] = '\0';
 
164
    retvalue = vsnprintf(message, MAX_LOG_MESSAGE_LENGTH, format, listptr);
165
    nmxp_log_get_prefix(prefix,MAX_LOG_MESSAGE_LENGTH);
166
    switch(level) {
Matteo Quintiliani's avatar
Matteo Quintiliani committed
167
	case NMXP_LOG_ERR:
168 169
	    //snprintf(message_final, MAX_LOG_MESSAGE_LENGTH, "%s - %s error: %s", timestr, nmxp_log_get_prefix(), message);
	    snprintf(message_final, MAX_LOG_MESSAGE_LENGTH, "%s - %s error: %s", timestr, prefix, message);            
170
	    nmxp_log_print_all(message_final, p_func_log_err, n_func_log_err);
171
	    break;
Matteo Quintiliani's avatar
Matteo Quintiliani committed
172
	case NMXP_LOG_WARN:
173 174
	    //snprintf(message_final, MAX_LOG_MESSAGE_LENGTH, "%s - %s warning: %s", timestr, nmxp_log_get_prefix(), message);
	    snprintf(message_final, MAX_LOG_MESSAGE_LENGTH, "%s - %s warning: %s", timestr, prefix, message);            
175
	    nmxp_log_print_all(message_final, p_func_log, n_func_log);
176
	    break;
Matteo Quintiliani's avatar
Matteo Quintiliani committed
177
	case NMXP_LOG_NORM_NO:
178
	    snprintf(message_final, MAX_LOG_MESSAGE_LENGTH, "%s", message);
179
	    nmxp_log_print_all(message_final, p_func_log, n_func_log);
180
	    break;
Matteo Quintiliani's avatar
Matteo Quintiliani committed
181
	case NMXP_LOG_NORM_PKG:
182 183
	    //snprintf(message_final, MAX_LOG_MESSAGE_LENGTH, "%s: %s", nmxp_log_get_prefix(), message);
	    snprintf(message_final, MAX_LOG_MESSAGE_LENGTH, "%s: %s", prefix, message);            
184
	    nmxp_log_print_all(message_final, p_func_log, n_func_log);
185 186
	    break;
	default:
187 188
	    //snprintf(message_final, MAX_LOG_MESSAGE_LENGTH, "%s - %s: %s", timestr, nmxp_log_get_prefix(), message);
	    snprintf(message_final, MAX_LOG_MESSAGE_LENGTH, "%s - %s: %s", timestr, prefix, message);            
189
	    nmxp_log_print_all(message_final, p_func_log, n_func_log);
190
	    break;
191 192 193 194 195 196 197 198
    }

    va_end(listptr);
  }

  return retvalue;
} /* End of nmxp_log() */