/*-
 * $Id: rr-debug.c,v 1.8 2002/10/10 19:39:55 jonas Exp $
 *
 * See the file LICENSE for redistribution information. 
 * If you have not received a copy of the license, please contact CodeFactory
 * by email at info@codefactory.se, or on the web at http://www.codefactory.se/
 * You may also write to: CodeFactory AB, SE-903 47, Umeå, Sweden.
 *
 * Copyright (c) 2002 Jonas Borgström <jonas@codefactory.se>
 * Copyright (c) 2002 Daniel Lundin   <daniel@codefactory.se>
 * Copyright (c) 2002 CodeFactory AB.  All rights reserved.
 */

#include <librr/rr.h>

#include <stdio.h>
#include <string.h>
#include <stdarg.h>

static void rr_debug_log_handler (const gchar *log_domain, 
				  GLogLevelFlags log_level, 
				  const gchar *message,
				  gpointer user_data);

static RRLogLevelFlags debug_flags = 0;
static FILE *debug_file = NULL;
static FILE *debug_file_net = NULL;

static const GDebugKey debug_keys[] = {
	{"1",          RR_LOG_LEVEL_DEBUG1},
	{"2",          (RR_LOG_LEVEL_DEBUG1 | RR_LOG_LEVEL_DEBUG2)},
	{"3",          (RR_LOG_LEVEL_DEBUG1 | RR_LOG_LEVEL_DEBUG2 
	                | RR_LOG_LEVEL_DEBUG3)},
	{"4",          RR_LOG_LEVEL_DEBUG},
	{"NET",        RR_LOG_LEVEL_NET},
	{"ALL",        RR_LOG_LEVEL_NET | RR_LOG_LEVEL_DEBUG},
	{"TCP",        RR_LOG_LEVEL_NET},
	{"TCP_IN",     RR_LOG_LEVEL_NET_IN},
	{"NET_IN",     RR_LOG_LEVEL_NET_IN},
	{"TCP_OUT",    RR_LOG_LEVEL_NET_OUT},
	{"NET_OUT",    RR_LOG_LEVEL_NET_OUT}
};


#define NUM_DEBUG_KEYS (sizeof (debug_keys) / sizeof (GDebugKey))

static void
init_debug_output_files (const gchar *rr_debug)
{
	const gchar *str;
	
	if ((str = strstr (rr_debug, "FILE="))) {
		gchar *filename = g_strdup (str + 5);
		
		if (strchr (filename, ':'))
			*strchr (filename, ':') = 0;
		debug_file = fopen (filename, "w");
		g_free (filename);
	}
	if ((str = strstr (rr_debug, "FILE_NET="))) {
		gchar *filename = g_strdup (str + 9);
		
		if (strchr (filename, ':'))
			*strchr (filename, ':') = 0;
		debug_file_net = fopen (filename, "w");
		g_free (filename);
	}
	if (debug_file == NULL)
		debug_file = stderr;
	if (debug_file_net == NULL)
		debug_file_net = debug_file;
}

void
rr_debug_init (void)
{
	const gchar *env_rr_debug;

	env_rr_debug = g_getenv ("RR_DEBUG");

	if (env_rr_debug) {
		debug_flags = g_parse_debug_string (env_rr_debug, debug_keys,
						    NUM_DEBUG_KEYS);

		init_debug_output_files (env_rr_debug);
	}

	if (debug_flags)
		g_type_init_with_debug_flags (G_TYPE_DEBUG_OBJECTS);
	else
		g_type_init ();

	g_log_set_handler ("RR", RR_LOG_LEVEL_DEBUG, rr_debug_log_handler, 
			   NULL);
}


void
rr_debug_exit (void)
{
	if (debug_file && debug_file != stderr)
		fclose (debug_file);
	if (debug_file_net && debug_file_net != stderr)
		fclose (debug_file_net);
}


static void
rr_debug_log_handler (const gchar *log_domain, 
		      GLogLevelFlags log_level,                       
		      const gchar *message,                           
		      gpointer user_data)
{
	if (debug_flags & log_level) {
		fprintf (debug_file, message);
		fprintf (debug_file, "\n");
		fflush (debug_file);
	}
}


#ifdef RR_DEBUG_NET_ENABLE
void
rr_debug_net_log_transfer (const void *data, size_t size, gboolean is_read)
{
	if (debug_flags & (is_read ? RR_LOG_LEVEL_NET_IN 
			           : RR_LOG_LEVEL_NET_OUT)) {
		fprintf (debug_file_net, "RRNET-Debug %s %i:\n", 
			 (is_read?"Read":"Write"), size);
		fwrite (data, size, 1, debug_file_net);
		fprintf (debug_file_net, "\n");	
		fflush (debug_file_net);
	}
}
#endif


syntax highlighted by Code2HTML, v. 0.9.1