/*
 * QrfeTraceModule.cpp
 *
 *  Created on: 31.01.2011
 *      Author: stefan.detter
 */

#include "../inc/QrfeTraceModule.h"

#include <QrfeTrace>

#define TIME_INFO   "[" + QTime::currentTime().toString("hh:mm:ss.zzz") + "] "
#define THREAD_INFO "|" + QString("0x%1").arg((ulong)QThread::currentThreadId(), 4, 16, QChar('0')) + "| - "

#define CHECK_TRACE()		if(!QrfeTrace::m_theInstance.m_trcOn)return;

QrfeTraceFunction::QrfeTraceFunction ( const QrfeTraceModule* module, const QString& name, QStringList args )
	: m_module(module)
	, m_name(name)
{
	m_module->trc(m_module->functionTraceLevel, ">>>>[ " + m_name + " ( " + args.join(", ") + " ) ]");
}

QrfeTraceFunction::~QrfeTraceFunction ( )
{
	m_module->trc(m_module->functionTraceLevel, "<<<<[ " + m_name + " ]");
}


QrfeTraceModule::QrfeTraceModule(QString name)
{
	traceModuleName = prepareModuleName(name);
	minimumTraceLevel = 0;
	functionTraceLevel = 0;
}

QrfeTraceModule::QrfeTraceModule(QString name, uint minimumTraceLevel)
{
	traceModuleName = prepareModuleName(name);
	this->minimumTraceLevel = minimumTraceLevel;
	this->functionTraceLevel = 0;
}

QrfeTraceModule::QrfeTraceModule(QString name, uint minimumTraceLevel, uint functionTraceLevel)
{
	traceModuleName = prepareModuleName(name);
	this->minimumTraceLevel = minimumTraceLevel;
	this->functionTraceLevel = functionTraceLevel;
}

QrfeTraceModule::~QrfeTraceModule()
{
}


QString QrfeTraceModule::prepareModuleName(const QString& moduleName)
{
	QString traceModuleName = moduleName;
	if ((uint) traceModuleName.size() < QRFE_TRACE_MAX_MODULE_NAME_SIZE)
		traceModuleName += QString(QRFE_TRACE_MAX_MODULE_NAME_SIZE - traceModuleName.size(), QChar(' '));

	return traceModuleName;
}

void QrfeTraceModule::setMinimumTraceLevel ( uint minimumTraceLevel )
{
	this->minimumTraceLevel = minimumTraceLevel;
}

void QrfeTraceModule::setFunctionTraceLevel ( uint functionTraceLevel )
{
	this->functionTraceLevel = functionTraceLevel;
}



#ifndef QRFE_TRACE_ON

void QrfeTraceModule::warning(const QString& /*msg*/) const{}
void QrfeTraceModule::error(const QString& /*msg*/) const{}
void QrfeTraceModule::fatal(const QString& /*msg*/) const{}
void QrfeTraceModule::trc(const int /*trcLevel*/, const QString& /*msg*/) const{}
void QrfeTraceModule::trcBytes(const int /*trcLevel*/, const QString& /*msg*/,
		const QByteArray& /*bytes*/, const QString& /*pattern*/) const{}


void QrfeTraceModule::swarning(const QString& /*msg*/){}
void QrfeTraceModule::serror(const QString& /*msg*/){}
void QrfeTraceModule::sfatal(const QString& /*msg*/){}
void QrfeTraceModule::strc(const int /*trcLevel*/, const QString& /*msg*/){}
void QrfeTraceModule::strcBytes(const int /*trcLevel*/, const QString& /*msg*/,
		const QByteArray& /*bytes*/, const QString& /*pattern*/){}

void QrfeTraceModule::swarning(const QString& /*moduleName*/, const QString& /*msg*/) {}
void QrfeTraceModule::serror(const QString& /*moduleName*/, const QString& /*msg*/){}
void QrfeTraceModule::sfatal(const QString& /*moduleName*/, const QString& /*msg*/){}
void QrfeTraceModule::strc(const QString& /*moduleName*/, const int /*trcLevel*/,
		const QString& /*msg*/){}
void QrfeTraceModule::strcBytes(const QString& /*moduleName*/, const int /*trcLevel*/,
		const QString& /*msg*/, const QByteArray& /*bytes*/, const QString& /*pattern*/){}

#else


/*************************************************************************************************************************/
/*******************************   Protected functions */


void QrfeTraceModule::warning(const QString& msg) const
{
	CHECK_TRACE();
	QString trc = TIME_INFO + traceModuleName + THREAD_INFO;
	trc += "WARNING: " + msg;
	QrfeTrace::trc(0, trc);
}

void QrfeTraceModule::error(const QString& msg) const
{
	CHECK_TRACE();
	QString trc = TIME_INFO + traceModuleName + THREAD_INFO;
	trc += "ERROR: " + msg;
	QrfeTrace::trc(0, trc);
	QrfeTrace::trcError(trc);
}

void QrfeTraceModule::fatal(const QString& msg) const
{
	CHECK_TRACE();
	QString trc = TIME_INFO + traceModuleName + THREAD_INFO;
	trc += "FATAL: " + msg;
	QrfeTrace::trc(0, trc);
	QrfeTrace::trcError(trc);
    qFatal("%s\n", trc.toLatin1().data());
}

void QrfeTraceModule::trc(const int trcLevel, const QString& msg) const
{
	CHECK_TRACE();
	QString trc = TIME_INFO + traceModuleName + THREAD_INFO;
	trc += msg;
	QrfeTrace::trc(trcLevel + minimumTraceLevel, trc);
}

void QrfeTraceModule::trcBytes(const int trcLevel, const QString& msg,
		const QByteArray& bytes, const QString& pattern) const
{
	CHECK_TRACE();
	QString data;
	for (int i = 0; i < bytes.size(); i++)
		data += QString(pattern).arg((unsigned char) bytes[i], 2, 16,
				QChar('0'));
	trc(trcLevel, msg + " " + QString::number(bytes.size()) + " Bytes: " + data);
}


/*************************************************************************************************************************/
/*******************************   Static functions */

void QrfeTraceModule::swarning(const QString& msg)
{
	CHECK_TRACE();
	swarning("STATIC", msg);
}

void QrfeTraceModule::serror(const QString& msg)
{
	CHECK_TRACE();
	serror("STATIC", msg);
}

void QrfeTraceModule::sfatal(const QString& msg)
{
	CHECK_TRACE();
	sfatal("STATIC", msg);
}

void QrfeTraceModule::strc(const int trcLevel, const QString& msg)
{
	CHECK_TRACE();
	strc("STATIC", trcLevel, msg);
}

void QrfeTraceModule::strcBytes(const int trcLevel, const QString& msg,
		const QByteArray& bytes, const QString& pattern)
{
	CHECK_TRACE();
	strcBytes("STATIC", trcLevel, msg, bytes, pattern);
}



/*************************************************************************************************************************/
/*******************************   Static functions with module info */

void QrfeTraceModule::swarning(const QString& moduleName, const QString& msg)
{
	CHECK_TRACE();
	QString trc = TIME_INFO + prepareModuleName(moduleName) + THREAD_INFO;
	trc += "WARNING: " + msg;
	QrfeTrace::trc(0, trc);
}

void QrfeTraceModule::serror(const QString& moduleName, const QString& msg)
{
	CHECK_TRACE();
	QString trc = TIME_INFO + prepareModuleName(moduleName) + THREAD_INFO;
	trc += "ERROR: " + msg;
	QrfeTrace::trc(0, trc);
	QrfeTrace::trcError(trc);
}

void QrfeTraceModule::sfatal(const QString& moduleName, const QString& msg)
{
	CHECK_TRACE();
	QString trc = TIME_INFO + prepareModuleName(moduleName) + THREAD_INFO;
	trc += "FATAL: " + msg;
	QrfeTrace::trc(0, trc);
	QrfeTrace::trcError(trc);
}

void QrfeTraceModule::strc(const QString& moduleName, const int trcLevel,
		const QString& msg)
{
	CHECK_TRACE();
	QString trc = TIME_INFO + prepareModuleName(moduleName) + THREAD_INFO;
	trc += msg;
	QrfeTrace::trc(trcLevel, trc);
}

void QrfeTraceModule::strcBytes(const QString& moduleName, const int trcLevel,
		const QString& msg, const QByteArray& bytes, const QString& pattern)
{
	CHECK_TRACE();
	QString data;
	for (int i = 0; i < bytes.size(); i++)
		data += QString(pattern).arg((unsigned char) bytes[i], 2, 16,
				QChar('0'));
	strc(moduleName, trcLevel, msg + " " + QString::number(bytes.size())
			+ " Bytes: " + data);
}

#endif

