aboutsummaryrefslogtreecommitdiff
path: root/src/server/shared
diff options
context:
space:
mode:
authorSubv <s.v.h21@hotmail.com>2012-08-07 13:44:22 -0500
committerSubv <s.v.h21@hotmail.com>2012-08-07 13:44:22 -0500
commitd82266bc0ef31df82dc67c1023d6208df6ac247b (patch)
treea0c5970a82e568ca54a25809555b7abad52e1bc1 /src/server/shared
parent224cf663e2af8b355b4bdca4069080636321b0ba (diff)
parentf8cd39b2ed1056f409c2690ac8bb661fbcb68e18 (diff)
Merge branch 'master' of github.com:TrinityCore/TrinityCore into 4.3.4
Conflicts: src/server/authserver/Server/AuthSocket.cpp src/server/game/Achievements/AchievementMgr.cpp src/server/game/Chat/Chat.h src/server/game/Chat/Commands/Level1.cpp src/server/game/Chat/Commands/Level2.cpp src/server/game/Chat/Commands/Level3.cpp src/server/game/DataStores/DBCStores.cpp src/server/game/DataStores/DBCStructure.h src/server/game/Entities/Object/Object.cpp src/server/game/Entities/Object/Updates/UpdateData.cpp src/server/game/Entities/Player/Player.cpp src/server/game/Globals/ObjectMgr.cpp src/server/game/Guilds/Guild.cpp src/server/game/Guilds/GuildMgr.cpp src/server/game/Handlers/AuctionHouseHandler.cpp src/server/game/Handlers/CharacterHandler.cpp src/server/game/Handlers/ChatHandler.cpp src/server/game/Handlers/GroupHandler.cpp src/server/game/Handlers/ItemHandler.cpp src/server/game/Handlers/MailHandler.cpp src/server/game/Handlers/MiscHandler.cpp src/server/game/Handlers/MovementHandler.cpp src/server/game/Handlers/PetHandler.cpp src/server/game/Handlers/QuestHandler.cpp src/server/game/Handlers/VehicleHandler.cpp src/server/game/Server/WorldSession.cpp src/server/game/Server/WorldSocket.cpp src/server/game/Spells/Auras/SpellAuraEffects.cpp src/server/game/Spells/SpellEffects.cpp src/server/game/Spells/SpellMgr.cpp src/server/game/World/World.cpp src/server/scripts/Commands/cs_debug.cpp src/server/scripts/Commands/cs_modify.cpp src/server/scripts/Commands/cs_reload.cpp src/server/scripts/Kalimdor/azuremyst_isle.cpp src/server/shared/Logging/Log.cpp src/server/shared/Logging/Log.h src/server/worldserver/worldserver.conf.dist
Diffstat (limited to 'src/server/shared')
-rwxr-xr-xsrc/server/shared/Configuration/Config.cpp8
-rwxr-xr-xsrc/server/shared/Configuration/Config.h1
-rwxr-xr-xsrc/server/shared/Cryptography/Authentication/AuthCrypt.h1
-rwxr-xr-xsrc/server/shared/DataStores/DBCStore.h10
-rwxr-xr-xsrc/server/shared/Database/DatabaseWorkerPool.h16
-rwxr-xr-xsrc/server/shared/Database/Field.h24
-rwxr-xr-xsrc/server/shared/Database/Implementation/LoginDatabase.cpp2
-rwxr-xr-xsrc/server/shared/Database/Implementation/WorldDatabase.cpp3
-rwxr-xr-xsrc/server/shared/Database/Implementation/WorldDatabase.h3
-rwxr-xr-xsrc/server/shared/Database/MySQLConnection.cpp114
-rwxr-xr-xsrc/server/shared/Database/MySQLThreading.h4
-rwxr-xr-xsrc/server/shared/Database/PreparedStatement.cpp6
-rwxr-xr-xsrc/server/shared/Database/QueryHolder.cpp8
-rwxr-xr-xsrc/server/shared/Database/QueryResult.cpp4
-rwxr-xr-xsrc/server/shared/Debugging/Errors.h8
-rw-r--r--src/server/shared/Logging/Appender.cpp218
-rw-r--r--src/server/shared/Logging/Appender.h154
-rw-r--r--src/server/shared/Logging/AppenderConsole.cpp193
-rw-r--r--src/server/shared/Logging/AppenderConsole.h59
-rw-r--r--src/server/shared/Logging/AppenderDB.cpp55
-rw-r--r--src/server/shared/Logging/AppenderDB.h36
-rw-r--r--src/server/shared/Logging/AppenderFile.cpp71
-rw-r--r--src/server/shared/Logging/AppenderFile.h40
-rw-r--r--[-rwxr-xr-x]src/server/shared/Logging/Log.cpp1188
-rw-r--r--[-rwxr-xr-x]src/server/shared/Logging/Log.h213
-rw-r--r--src/server/shared/Logging/LogOperation.cpp31
-rw-r--r--src/server/shared/Logging/LogOperation.h41
-rw-r--r--src/server/shared/Logging/LogWorker.cpp50
-rw-r--r--src/server/shared/Logging/LogWorker.h47
-rw-r--r--src/server/shared/Logging/Logger.cpp84
-rw-r--r--src/server/shared/Logging/Logger.h46
-rwxr-xr-xsrc/server/shared/Packets/ByteBuffer.h84
-rwxr-xr-xsrc/server/shared/Utilities/ServiceWin32.cpp2
33 files changed, 1612 insertions, 1212 deletions
diff --git a/src/server/shared/Configuration/Config.cpp b/src/server/shared/Configuration/Config.cpp
index b82d86cc5d0..e0df22b88ae 100755
--- a/src/server/shared/Configuration/Config.cpp
+++ b/src/server/shared/Configuration/Config.cpp
@@ -80,7 +80,7 @@ std::string GetStringDefault(const char* name, const std::string &def)
{
ACE_TString val;
return GetValueHelper(name, val) ? val.c_str() : def;
-};
+}
bool GetBoolDefault(const char* name, bool def)
{
@@ -91,19 +91,19 @@ bool GetBoolDefault(const char* name, bool def)
return (val == "true" || val == "TRUE" || val == "yes" || val == "YES" ||
val == "1");
-};
+}
int GetIntDefault(const char* name, int def)
{
ACE_TString val;
return GetValueHelper(name, val) ? atoi(val.c_str()) : def;
-};
+}
float GetFloatDefault(const char* name, float def)
{
ACE_TString val;
return GetValueHelper(name, val) ? (float)atof(val.c_str()) : def;
-};
+}
const std::string & GetFilename()
{
diff --git a/src/server/shared/Configuration/Config.h b/src/server/shared/Configuration/Config.h
index a870379881b..82e4d9bcce0 100755
--- a/src/server/shared/Configuration/Config.h
+++ b/src/server/shared/Configuration/Config.h
@@ -34,4 +34,3 @@ namespace ConfigMgr
}
#endif
-
diff --git a/src/server/shared/Cryptography/Authentication/AuthCrypt.h b/src/server/shared/Cryptography/Authentication/AuthCrypt.h
index 7081b4973d4..b40ce8ac40c 100755
--- a/src/server/shared/Cryptography/Authentication/AuthCrypt.h
+++ b/src/server/shared/Cryptography/Authentication/AuthCrypt.h
@@ -41,4 +41,3 @@ class AuthCrypt
bool _initialized;
};
#endif
-
diff --git a/src/server/shared/DataStores/DBCStore.h b/src/server/shared/DataStores/DBCStore.h
index f8a983d22f3..0c502d3fd77 100755
--- a/src/server/shared/DataStores/DBCStore.h
+++ b/src/server/shared/DataStores/DBCStore.h
@@ -117,7 +117,7 @@ class DBCStorage
// Check if sql index pos is valid
if (int32(result->GetFieldCount()-1) < sql->sqlIndexPos)
{
- sLog->outError("Invalid index pos for dbc:'%s'", sql->sqlTableName.c_str());
+ sLog->outError(LOG_FILTER_GENERAL, "Invalid index pos for dbc:'%s'", sql->sqlTableName.c_str());
return false;
}
}
@@ -148,7 +148,7 @@ class DBCStorage
uint32 id = fields[sql->sqlIndexPos].GetUInt32();
if (indexTable.asT[id])
{
- sLog->outError("Index %d already exists in dbc:'%s'", id, sql->sqlTableName.c_str());
+ sLog->outError(LOG_FILTER_GENERAL, "Index %d already exists in dbc:'%s'", id, sql->sqlTableName.c_str());
return false;
}
indexTable.asT[id]=(T*)&sqlDataTable[offset];
@@ -203,7 +203,7 @@ class DBCStorage
offset+=1;
break;
case FT_STRING:
- sLog->outError("Unsupported data type in table '%s' at char %d", sql->sqlTableName.c_str(), columnNumber);
+ sLog->outError(LOG_FILTER_GENERAL, "Unsupported data type in table '%s' at char %d", sql->sqlTableName.c_str(), columnNumber);
return false;
case FT_SORT:
break;
@@ -215,13 +215,13 @@ class DBCStorage
}
else
{
- sLog->outError("Incorrect sql format string '%s' at char %d", sql->sqlTableName.c_str(), columnNumber);
+ sLog->outError(LOG_FILTER_GENERAL, "Incorrect sql format string '%s' at char %d", sql->sqlTableName.c_str(), columnNumber);
return false;
}
}
if (sqlColumnNumber != (result->GetFieldCount()-1))
{
- sLog->outError("SQL and DBC format strings are not matching for table: '%s'", sql->sqlTableName.c_str());
+ sLog->outError(LOG_FILTER_GENERAL, "SQL and DBC format strings are not matching for table: '%s'", sql->sqlTableName.c_str());
return false;
}
diff --git a/src/server/shared/Database/DatabaseWorkerPool.h b/src/server/shared/Database/DatabaseWorkerPool.h
index 314d196cc06..9d6fabb9dfa 100755
--- a/src/server/shared/Database/DatabaseWorkerPool.h
+++ b/src/server/shared/Database/DatabaseWorkerPool.h
@@ -64,7 +64,7 @@ class DatabaseWorkerPool
bool res = true;
_connectionInfo = MySQLConnectionInfo(infoString);
- sLog->outSQLDriver("Opening DatabasePool '%s'. Asynchronous connections: %u, synchronous connections: %u.",
+ sLog->outInfo(LOG_FILTER_SQL_DRIVER, "Opening DatabasePool '%s'. Asynchronous connections: %u, synchronous connections: %u.",
GetDatabaseName(), async_threads, synch_threads);
//! Open asynchronous connections (delayed operations)
@@ -88,17 +88,17 @@ class DatabaseWorkerPool
}
if (res)
- sLog->outSQLDriver("DatabasePool '%s' opened successfully. %u total connections running.", GetDatabaseName(),
+ sLog->outInfo(LOG_FILTER_SQL_DRIVER, "DatabasePool '%s' opened successfully. %u total connections running.", GetDatabaseName(),
(_connectionCount[IDX_SYNCH] + _connectionCount[IDX_ASYNC]));
else
- sLog->outError("DatabasePool %s NOT opened. There were errors opening the MySQL connections. Check your SQLDriverLogFile "
+ sLog->outError(LOG_FILTER_SQL_DRIVER, "DatabasePool %s NOT opened. There were errors opening the MySQL connections. Check your SQLDriverLogFile "
"for specific errors.", GetDatabaseName());
return res;
}
void Close()
{
- sLog->outSQLDriver("Closing down DatabasePool '%s'.", GetDatabaseName());
+ sLog->outInfo(LOG_FILTER_SQL_DRIVER, "Closing down DatabasePool '%s'.", GetDatabaseName());
//! Shuts down delaythreads for this connection pool by underlying deactivate().
//! The next dequeue attempt in the worker thread tasks will result in an error,
@@ -114,7 +114,7 @@ class DatabaseWorkerPool
t->Close(); //! Closes the actualy MySQL connection.
}
- sLog->outSQLDriver("Asynchronous connections on DatabasePool '%s' terminated. Proceeding with synchronous connections.",
+ sLog->outInfo(LOG_FILTER_SQL_DRIVER, "Asynchronous connections on DatabasePool '%s' terminated. Proceeding with synchronous connections.",
GetDatabaseName());
//! Shut down the synchronous connections
@@ -127,7 +127,7 @@ class DatabaseWorkerPool
//! Deletes the ACE_Activation_Queue object and its underlying ACE_Message_Queue
delete _queue;
- sLog->outSQLDriver("All connections on DatabasePool '%s' closed.", GetDatabaseName());
+ sLog->outInfo(LOG_FILTER_SQL_DRIVER, "All connections on DatabasePool '%s' closed.", GetDatabaseName());
}
/**
@@ -351,10 +351,10 @@ class DatabaseWorkerPool
switch (transaction->GetSize())
{
case 0:
- sLog->outSQLDriver("Transaction contains 0 queries. Not executing.");
+ sLog->outDebug(LOG_FILTER_SQL_DRIVER, "Transaction contains 0 queries. Not executing.");
return;
case 1:
- sLog->outSQLDriver("Warning: Transaction only holds 1 query, consider removing Transaction context in code.");
+ sLog->outDebug(LOG_FILTER_SQL_DRIVER, "Warning: Transaction only holds 1 query, consider removing Transaction context in code.");
break;
default:
break;
diff --git a/src/server/shared/Database/Field.h b/src/server/shared/Database/Field.h
index bfa42dbe574..61e8fb7ccef 100755
--- a/src/server/shared/Database/Field.h
+++ b/src/server/shared/Database/Field.h
@@ -43,7 +43,7 @@ class Field
#ifdef TRINITY_DEBUG
if (!IsType(MYSQL_TYPE_TINY))
{
- sLog->outSQLDriver("Warning: GetUInt8() on non-tinyint field. Using type: %s.", FieldTypeToString(data.type));
+ sLog->outWarn(LOG_FILTER_SQL, "Warning: GetUInt8() on non-tinyint field. Using type: %s.", FieldTypeToString(data.type));
return 0;
}
#endif
@@ -61,7 +61,7 @@ class Field
#ifdef TRINITY_DEBUG
if (!IsType(MYSQL_TYPE_TINY))
{
- sLog->outSQLDriver("Warning: GetInt8() on non-tinyint field. Using type: %s.", FieldTypeToString(data.type));
+ sLog->outWarn(LOG_FILTER_SQL, "Warning: GetInt8() on non-tinyint field. Using type: %s.", FieldTypeToString(data.type));
return 0;
}
#endif
@@ -79,7 +79,7 @@ class Field
#ifdef TRINITY_DEBUG
if (!IsType(MYSQL_TYPE_SHORT) && !IsType(MYSQL_TYPE_YEAR))
{
- sLog->outSQLDriver("Warning: GetUInt16() on non-smallint field. Using type: %s.", FieldTypeToString(data.type));
+ sLog->outWarn(LOG_FILTER_SQL, "Warning: GetUInt16() on non-smallint field. Using type: %s.", FieldTypeToString(data.type));
return 0;
}
#endif
@@ -97,7 +97,7 @@ class Field
#ifdef TRINITY_DEBUG
if (!IsType(MYSQL_TYPE_SHORT) && !IsType(MYSQL_TYPE_YEAR))
{
- sLog->outSQLDriver("Warning: GetInt16() on non-smallint field. Using type: %s.", FieldTypeToString(data.type));
+ sLog->outWarn(LOG_FILTER_SQL, "Warning: GetInt16() on non-smallint field. Using type: %s.", FieldTypeToString(data.type));
return 0;
}
#endif
@@ -115,7 +115,7 @@ class Field
#ifdef TRINITY_DEBUG
if (!IsType(MYSQL_TYPE_INT24) && !IsType(MYSQL_TYPE_LONG))
{
- sLog->outSQLDriver("Warning: GetUInt32() on non-(medium)int field. Using type: %s.", FieldTypeToString(data.type));
+ sLog->outWarn(LOG_FILTER_SQL, "Warning: GetUInt32() on non-(medium)int field. Using type: %s.", FieldTypeToString(data.type));
return 0;
}
#endif
@@ -133,7 +133,7 @@ class Field
#ifdef TRINITY_DEBUG
if (!IsType(MYSQL_TYPE_INT24) && !IsType(MYSQL_TYPE_LONG))
{
- sLog->outSQLDriver("Warning: GetInt32() on non-(medium)int field. Using type: %s.", FieldTypeToString(data.type));
+ sLog->outWarn(LOG_FILTER_SQL, "Warning: GetInt32() on non-(medium)int field. Using type: %s.", FieldTypeToString(data.type));
return 0;
}
#endif
@@ -151,7 +151,7 @@ class Field
#ifdef TRINITY_DEBUG
if (!IsType(MYSQL_TYPE_LONGLONG) && !IsType(MYSQL_TYPE_BIT))
{
- sLog->outSQLDriver("Warning: GetUInt64() on non-bigint field. Using type: %s.", FieldTypeToString(data.type));
+ sLog->outWarn(LOG_FILTER_SQL, "Warning: GetUInt64() on non-bigint field. Using type: %s.", FieldTypeToString(data.type));
return 0;
}
#endif
@@ -169,7 +169,7 @@ class Field
#ifdef TRINITY_DEBUG
if (!IsType(MYSQL_TYPE_LONGLONG) && !IsType(MYSQL_TYPE_BIT))
{
- sLog->outSQLDriver("Warning: GetInt64() on non-bigint field. Using type: %s.", FieldTypeToString(data.type));
+ sLog->outWarn(LOG_FILTER_SQL, "Warning: GetInt64() on non-bigint field. Using type: %s.", FieldTypeToString(data.type));
return 0;
}
#endif
@@ -187,7 +187,7 @@ class Field
#ifdef TRINITY_DEBUG
if (!IsType(MYSQL_TYPE_FLOAT))
{
- sLog->outSQLDriver("Warning: GetFloat() on non-float field. Using type: %s.", FieldTypeToString(data.type));
+ sLog->outWarn(LOG_FILTER_SQL, "Warning: GetFloat() on non-float field. Using type: %s.", FieldTypeToString(data.type));
return 0.0f;
}
#endif
@@ -205,7 +205,7 @@ class Field
#ifdef TRINITY_DEBUG
if (!IsType(MYSQL_TYPE_DOUBLE))
{
- sLog->outSQLDriver("Warning: GetDouble() on non-double field. Using type: %s.", FieldTypeToString(data.type));
+ sLog->outWarn(LOG_FILTER_SQL, "Warning: GetDouble() on non-double field. Using type: %s.", FieldTypeToString(data.type));
return 0.0f;
}
#endif
@@ -223,7 +223,7 @@ class Field
#ifdef TRINITY_DEBUG
if (IsNumeric())
{
- sLog->outSQLDriver("Error: GetCString() on numeric field. Using type: %s.", FieldTypeToString(data.type));
+ sLog->outWarn(LOG_FILTER_SQL, "Error: GetCString() on numeric field. Using type: %s.", FieldTypeToString(data.type));
return NULL;
}
#endif
@@ -322,7 +322,7 @@ class Field
MYSQL_TYPE_SET:
*/
default:
- sLog->outSQLDriver("SQL::SizeForType(): invalid field type %u", uint32(field->type));
+ sLog->outWarn(LOG_FILTER_SQL, "SQL::SizeForType(): invalid field type %u", uint32(field->type));
return 0;
}
}
diff --git a/src/server/shared/Database/Implementation/LoginDatabase.cpp b/src/server/shared/Database/Implementation/LoginDatabase.cpp
index 028d927a720..31d9f5ec1f6 100755
--- a/src/server/shared/Database/Implementation/LoginDatabase.cpp
+++ b/src/server/shared/Database/Implementation/LoginDatabase.cpp
@@ -59,7 +59,7 @@ void LoginDatabaseConnection::DoPrepareStatements()
PREPARE_STATEMENT(LOGIN_INS_REALM_CHARACTERS_INIT, "INSERT INTO realmcharacters (realmid, acctid, numchars) SELECT realmlist.id, account.id, 0 FROM realmlist, account LEFT JOIN realmcharacters ON acctid=account.id WHERE acctid IS NULL", CONNECTION_ASYNC);
PREPARE_STATEMENT(LOGIN_UPD_EXPANSION, "UPDATE account SET expansion = ? WHERE id = ?", CONNECTION_ASYNC);
PREPARE_STATEMENT(LOGIN_UPD_ACCOUNT_LOCK, "UPDATE account SET locked = ? WHERE id = ?", CONNECTION_ASYNC);
- PREPARE_STATEMENT(LOGIN_INS_LOG, "INSERT INTO logs (time, realm, type, string) VALUES (UNIX_TIMESTAMP(), ? , ?, ?)", CONNECTION_ASYNC);
+ PREPARE_STATEMENT(LOGIN_INS_LOG, "INSERT INTO logs (time, realm, type, level, string) VALUES (?, ?, ?, ?, ?)", CONNECTION_ASYNC);
PREPARE_STATEMENT(LOGIN_UPD_USERNAME, "UPDATE account SET v = 0, s = 0, username = ?, sha_pass_hash = ? WHERE id = ?", CONNECTION_ASYNC);
PREPARE_STATEMENT(LOGIN_UPD_PASSWORD, "UPDATE account SET v = 0, s = 0, sha_pass_hash = ? WHERE id = ?", CONNECTION_ASYNC);
PREPARE_STATEMENT(LOGIN_UPD_MUTE_TIME, "UPDATE account SET mutetime = ? WHERE id = ?", CONNECTION_ASYNC);
diff --git a/src/server/shared/Database/Implementation/WorldDatabase.cpp b/src/server/shared/Database/Implementation/WorldDatabase.cpp
index e3455891909..872d9ec415c 100755
--- a/src/server/shared/Database/Implementation/WorldDatabase.cpp
+++ b/src/server/shared/Database/Implementation/WorldDatabase.cpp
@@ -88,4 +88,7 @@ void WorldDatabaseConnection::DoPrepareStatements()
PREPARE_STATEMENT(WORLD_DEL_GAME_EVENT_CREATURE, "DELETE FROM game_event_creature WHERE guid = ?", CONNECTION_ASYNC);
PREPARE_STATEMENT(WORLD_DEL_GAME_EVENT_MODEL_EQUIP, "DELETE FROM game_event_model_equip WHERE guid = ?", CONNECTION_ASYNC);
PREPARE_STATEMENT(WORLD_INS_GAMEOBJECT, "INSERT INTO gameobject (guid, id, map, spawnMask, phaseMask, position_x, position_y, position_z, orientation, rotation0, rotation1, rotation2, rotation3, spawntimesecs, animprogress, state) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", CONNECTION_ASYNC);
+ PREPARE_STATEMENT(WORLD_INS_DISABLES, "INSERT INTO disables (entry, sourceType, flags, comment) VALUES (?, ?, ?, ?)", CONNECTION_ASYNC);
+ PREPARE_STATEMENT(WORLD_SEL_DISABLES, "SELECT entry FROM disables WHERE entry = ? AND sourceType = ?", CONNECTION_SYNCH);
+ PREPARE_STATEMENT(WORLD_DEL_DISABLES, "DELETE FROM disables WHERE entry = ? AND sourceType = ?", CONNECTION_ASYNC);
}
diff --git a/src/server/shared/Database/Implementation/WorldDatabase.h b/src/server/shared/Database/Implementation/WorldDatabase.h
index 0580cecec7e..6d7df87cc80 100755
--- a/src/server/shared/Database/Implementation/WorldDatabase.h
+++ b/src/server/shared/Database/Implementation/WorldDatabase.h
@@ -109,6 +109,9 @@ enum WorldDatabaseStatements
WORLD_DEL_GAME_EVENT_CREATURE,
WORLD_DEL_GAME_EVENT_MODEL_EQUIP,
WORLD_INS_GAMEOBJECT,
+ WORLD_SEL_DISABLES,
+ WORLD_INS_DISABLES,
+ WORLD_DEL_DISABLES,
MAX_WORLDDATABASE_STATEMENTS,
};
diff --git a/src/server/shared/Database/MySQLConnection.cpp b/src/server/shared/Database/MySQLConnection.cpp
index 7fb4a4f7025..c6d2a165ca2 100755
--- a/src/server/shared/Database/MySQLConnection.cpp
+++ b/src/server/shared/Database/MySQLConnection.cpp
@@ -22,6 +22,8 @@
#include <winsock2.h>
#endif
#include <mysql.h>
+#include <mysqld_error.h>
+#include <errmsg.h>
#include "MySQLConnection.h"
#include "MySQLThreading.h"
@@ -79,7 +81,7 @@ bool MySQLConnection::Open()
mysqlInit = mysql_init(NULL);
if (!mysqlInit)
{
- sLog->outError("Could not initialize Mysql connection to database `%s`", m_connectionInfo.database.c_str());
+ sLog->outError(LOG_FILTER_SQL, "Could not initialize Mysql connection to database `%s`", m_connectionInfo.database.c_str());
return false;
}
@@ -123,13 +125,13 @@ bool MySQLConnection::Open()
{
if (!m_reconnecting)
{
- sLog->outSQLDriver("MySQL client library: %s", mysql_get_client_info());
- sLog->outSQLDriver("MySQL server ver: %s ", mysql_get_server_info(m_Mysql));
+ sLog->outInfo(LOG_FILTER_SQL, "MySQL client library: %s", mysql_get_client_info());
+ sLog->outInfo(LOG_FILTER_SQL, "MySQL server ver: %s ", mysql_get_server_info(m_Mysql));
if (mysql_get_server_version(m_Mysql) != mysql_get_client_version())
- sLog->outSQLDriver("[WARNING] MySQL client/server version mismatch; may conflict with behaviour of prepared statements.");
+ sLog->outInfo(LOG_FILTER_SQL, "[WARNING] MySQL client/server version mismatch; may conflict with behaviour of prepared statements.");
}
- sLog->outDetail("Connected to MySQL database at %s", m_connectionInfo.host.c_str());
+ sLog->outInfo(LOG_FILTER_SQL, "Connected to MySQL database at %s", m_connectionInfo.host.c_str());
mysql_autocommit(m_Mysql, 1);
// set connection properties to UTF8 to properly handle locales for different
@@ -139,7 +141,7 @@ bool MySQLConnection::Open()
}
else
{
- sLog->outError("Could not connect to MySQL database at %s: %s\n", m_connectionInfo.host.c_str(), mysql_error(mysqlInit));
+ sLog->outError(LOG_FILTER_SQL, "Could not connect to MySQL database at %s: %s\n", m_connectionInfo.host.c_str(), mysql_error(mysqlInit));
mysql_close(mysqlInit);
return false;
}
@@ -159,26 +161,22 @@ bool MySQLConnection::Execute(const char* sql)
return false;
{
- uint32 _s = 0;
- if (sLog->GetSQLDriverQueryLogging())
- _s = getMSTime();
+ uint32 _s = getMSTime();
if (mysql_query(m_Mysql, sql))
{
uint32 lErrno = mysql_errno(m_Mysql);
- sLog->outSQLDriver("SQL: %s", sql);
- sLog->outSQLDriver("ERROR: [%u] %s", lErrno, mysql_error(m_Mysql));
+ sLog->outInfo(LOG_FILTER_SQL, "SQL: %s", sql);
+ sLog->outError(LOG_FILTER_SQL, "[%u] %s", lErrno, mysql_error(m_Mysql));
if (_HandleMySQLErrno(lErrno)) // If it returns true, an error was handled successfully (i.e. reconnection)
return Execute(sql); // Try again
return false;
}
- else if (sLog->GetSQLDriverQueryLogging())
- {
- sLog->outSQLDriver("[%u ms] SQL: %s", getMSTimeDiff(_s, getMSTime()), sql);
- }
+ else
+ sLog->outDebug(LOG_FILTER_SQL, "[%u ms] SQL: %s", getMSTimeDiff(_s, getMSTime()), sql);
}
return true;
@@ -201,14 +199,12 @@ bool MySQLConnection::Execute(PreparedStatement* stmt)
MYSQL_STMT* msql_STMT = m_mStmt->GetSTMT();
MYSQL_BIND* msql_BIND = m_mStmt->GetBind();
- uint32 _s = 0;
- if (sLog->GetSQLDriverQueryLogging())
- _s = getMSTime();
+ uint32 _s = getMSTime();
if (mysql_stmt_bind_param(msql_STMT, msql_BIND))
{
uint32 lErrno = mysql_errno(m_Mysql);
- sLog->outSQLDriver("SQL(p): %s\n [ERROR]: [%u] %s", m_mStmt->getQueryString(m_queries[index].first).c_str(), lErrno, mysql_stmt_error(msql_STMT));
+ sLog->outError(LOG_FILTER_SQL, "SQL(p): %s\n [ERROR]: [%u] %s", m_mStmt->getQueryString(m_queries[index].first).c_str(), lErrno, mysql_stmt_error(msql_STMT));
if (_HandleMySQLErrno(lErrno)) // If it returns true, an error was handled successfully (i.e. reconnection)
return Execute(stmt); // Try again
@@ -220,7 +216,7 @@ bool MySQLConnection::Execute(PreparedStatement* stmt)
if (mysql_stmt_execute(msql_STMT))
{
uint32 lErrno = mysql_errno(m_Mysql);
- sLog->outSQLDriver("SQL(p): %s\n [ERROR]: [%u] %s", m_mStmt->getQueryString(m_queries[index].first).c_str(), lErrno, mysql_stmt_error(msql_STMT));
+ sLog->outError(LOG_FILTER_SQL, "SQL(p): %s\n [ERROR]: [%u] %s", m_mStmt->getQueryString(m_queries[index].first).c_str(), lErrno, mysql_stmt_error(msql_STMT));
if (_HandleMySQLErrno(lErrno)) // If it returns true, an error was handled successfully (i.e. reconnection)
return Execute(stmt); // Try again
@@ -229,8 +225,7 @@ bool MySQLConnection::Execute(PreparedStatement* stmt)
return false;
}
- if (sLog->GetSQLDriverQueryLogging())
- sLog->outSQLDriver("[%u ms] SQL(p): %s", getMSTimeDiff(_s, getMSTime()), m_mStmt->getQueryString(m_queries[index].first).c_str());
+ sLog->outDebug(LOG_FILTER_SQL, "[%u ms] SQL(p): %s", getMSTimeDiff(_s, getMSTime()), m_mStmt->getQueryString(m_queries[index].first).c_str());
m_mStmt->ClearParameters();
return true;
@@ -254,14 +249,12 @@ bool MySQLConnection::_Query(PreparedStatement* stmt, MYSQL_RES **pResult, uint6
MYSQL_STMT* msql_STMT = m_mStmt->GetSTMT();
MYSQL_BIND* msql_BIND = m_mStmt->GetBind();
- uint32 _s = 0;
- if (sLog->GetSQLDriverQueryLogging())
- _s = getMSTime();
+ uint32 _s = getMSTime();
if (mysql_stmt_bind_param(msql_STMT, msql_BIND))
{
uint32 lErrno = mysql_errno(m_Mysql);
- sLog->outSQLDriver("SQL(p): %s\n [ERROR]: [%u] %s", m_mStmt->getQueryString(m_queries[index].first).c_str(), lErrno, mysql_stmt_error(msql_STMT));
+ sLog->outError(LOG_FILTER_SQL, "SQL(p): %s\n [ERROR]: [%u] %s", m_mStmt->getQueryString(m_queries[index].first).c_str(), lErrno, mysql_stmt_error(msql_STMT));
if (_HandleMySQLErrno(lErrno)) // If it returns true, an error was handled successfully (i.e. reconnection)
return _Query(stmt, pResult, pRowCount, pFieldCount); // Try again
@@ -273,7 +266,7 @@ bool MySQLConnection::_Query(PreparedStatement* stmt, MYSQL_RES **pResult, uint6
if (mysql_stmt_execute(msql_STMT))
{
uint32 lErrno = mysql_errno(m_Mysql);
- sLog->outSQLDriver("SQL(p): %s\n [ERROR]: [%u] %s",
+ sLog->outError(LOG_FILTER_SQL, "SQL(p): %s\n [ERROR]: [%u] %s",
m_mStmt->getQueryString(m_queries[index].first).c_str(), lErrno, mysql_stmt_error(msql_STMT));
if (_HandleMySQLErrno(lErrno)) // If it returns true, an error was handled successfully (i.e. reconnection)
@@ -283,8 +276,7 @@ bool MySQLConnection::_Query(PreparedStatement* stmt, MYSQL_RES **pResult, uint6
return false;
}
- if (sLog->GetSQLDriverQueryLogging())
- sLog->outSQLDriver("[%u ms] SQL(p): %s", getMSTimeDiff(_s, getMSTime()), m_mStmt->getQueryString(m_queries[index].first).c_str());
+ sLog->outDebug(LOG_FILTER_SQL, "[%u ms] SQL(p): %s", getMSTimeDiff(_s, getMSTime()), m_mStmt->getQueryString(m_queries[index].first).c_str());
m_mStmt->ClearParameters();
@@ -319,25 +311,21 @@ bool MySQLConnection::_Query(const char *sql, MYSQL_RES **pResult, MYSQL_FIELD *
return false;
{
- uint32 _s = 0;
- if (sLog->GetSQLDriverQueryLogging())
- _s = getMSTime();
+ uint32 _s = getMSTime();
if (mysql_query(m_Mysql, sql))
{
uint32 lErrno = mysql_errno(m_Mysql);
- sLog->outSQLDriver("SQL: %s", sql);
- sLog->outSQLDriver("ERROR: [%u] %s", lErrno, mysql_error(m_Mysql));
+ sLog->outInfo(LOG_FILTER_SQL, "SQL: %s", sql);
+ sLog->outError(LOG_FILTER_SQL, "[%u] %s", lErrno, mysql_error(m_Mysql));
if (_HandleMySQLErrno(lErrno)) // If it returns true, an error was handled successfully (i.e. reconnection)
return _Query(sql, pResult, pFields, pRowCount, pFieldCount); // We try again
return false;
}
- else if (sLog->GetSQLDriverQueryLogging())
- {
- sLog->outSQLDriver("[%u ms] SQL: %s", getMSTimeDiff(_s, getMSTime()), sql);
- }
+ else
+ sLog->outDebug(LOG_FILTER_SQL, "[%u ms] SQL: %s", getMSTimeDiff(_s, getMSTime()), sql);
*pResult = mysql_store_result(m_Mysql);
*pRowCount = mysql_affected_rows(m_Mysql);
@@ -393,7 +381,7 @@ bool MySQLConnection::ExecuteTransaction(SQLTransaction& transaction)
ASSERT(stmt);
if (!Execute(stmt))
{
- sLog->outSQLDriver("[Warning] Transaction aborted. %u queries not executed.", (uint32)queries.size());
+ sLog->outWarn(LOG_FILTER_SQL, "Transaction aborted. %u queries not executed.", (uint32)queries.size());
RollbackTransaction();
return false;
}
@@ -405,7 +393,7 @@ bool MySQLConnection::ExecuteTransaction(SQLTransaction& transaction)
ASSERT(sql);
if (!Execute(sql))
{
- sLog->outSQLDriver("[Warning] Transaction aborted. %u queries not executed.", (uint32)queries.size());
+ sLog->outWarn(LOG_FILTER_SQL, "Transaction aborted. %u queries not executed.", (uint32)queries.size());
RollbackTransaction();
return false;
}
@@ -428,7 +416,7 @@ MySQLPreparedStatement* MySQLConnection::GetPreparedStatement(uint32 index)
ASSERT(index < m_stmts.size());
MySQLPreparedStatement* ret = m_stmts[index];
if (!ret)
- sLog->outSQLDriver("ERROR: Could not fetch prepared statement %u on database `%s`, connection type: %s.",
+ sLog->outError(LOG_FILTER_SQL, "Could not fetch prepared statement %u on database `%s`, connection type: %s.",
index, m_connectionInfo.database.c_str(), (m_connectionFlags & CONNECTION_ASYNC) ? "asynchronous" : "synchronous");
return ret;
@@ -449,19 +437,19 @@ void MySQLConnection::PrepareStatement(uint32 index, const char* sql, Connection
return;
}
- MYSQL_STMT * stmt = mysql_stmt_init(m_Mysql);
+ MYSQL_STMT* stmt = mysql_stmt_init(m_Mysql);
if (!stmt)
{
- sLog->outSQLDriver("[ERROR]: In mysql_stmt_init() id: %u, sql: \"%s\"", index, sql);
- sLog->outSQLDriver("[ERROR]: %s", mysql_error(m_Mysql));
+ sLog->outError(LOG_FILTER_SQL, "In mysql_stmt_init() id: %u, sql: \"%s\"", index, sql);
+ sLog->outError(LOG_FILTER_SQL, "%s", mysql_error(m_Mysql));
m_prepareError = true;
}
else
{
if (mysql_stmt_prepare(stmt, sql, static_cast<unsigned long>(strlen(sql))))
{
- sLog->outSQLDriver("[ERROR]: In mysql_stmt_prepare() id: %u, sql: \"%s\"", index, sql);
- sLog->outSQLDriver("[ERROR]: %s", mysql_stmt_error(stmt));
+ sLog->outError(LOG_FILTER_SQL, "In mysql_stmt_prepare() id: %u, sql: \"%s\"", index, sql);
+ sLog->outError(LOG_FILTER_SQL, "%s", mysql_stmt_error(stmt));
mysql_stmt_close(stmt);
m_prepareError = true;
}
@@ -493,19 +481,19 @@ bool MySQLConnection::_HandleMySQLErrno(uint32 errNo)
{
switch (errNo)
{
- case 2006: // "MySQL server has gone away"
- case 2013: // "Lost connection to MySQL server during query"
- case 2048: // "Invalid connection handle"
- case 2055: // "Lost connection to MySQL server at '%s', system error: %d"
+ case CR_SERVER_GONE_ERROR:
+ case CR_SERVER_LOST:
+ case CR_INVALID_CONN_HANDLE:
+ case CR_SERVER_LOST_EXTENDED:
{
m_reconnecting = true;
uint64 oldThreadId = mysql_thread_id(GetHandle());
mysql_close(GetHandle());
if (this->Open()) // Don't remove 'this' pointer unless you want to skip loading all prepared statements....
{
- sLog->outSQLDriver("Connection to the MySQL server is active.");
+ sLog->outInfo(LOG_FILTER_SQL, "Connection to the MySQL server is active.");
if (oldThreadId != mysql_thread_id(GetHandle()))
- sLog->outSQLDriver("Successfully reconnected to %s @%s:%s (%s).",
+ sLog->outInfo(LOG_FILTER_SQL, "Successfully reconnected to %s @%s:%s (%s).",
m_connectionInfo.database.c_str(), m_connectionInfo.host.c_str(), m_connectionInfo.port_or_socket.c_str(),
(m_connectionFlags & CONNECTION_ASYNC) ? "asynchronous" : "synchronous");
@@ -518,21 +506,27 @@ bool MySQLConnection::_HandleMySQLErrno(uint32 errNo)
return _HandleMySQLErrno(lErrno); // Call self (recursive)
}
- case 1213: // "Deadlock found when trying to get lock; try restarting transaction"
+ case ER_LOCK_DEADLOCK:
return false; // Implemented in TransactionTask::Execute and DatabaseWorkerPool<T>::DirectCommitTransaction
// Query related errors - skip query
- case 1058: // "Column count doesn't match value count"
- case 1062: // "Duplicate entry '%s' for key '%d'"
+ case ER_WRONG_VALUE_COUNT:
+ case ER_DUP_ENTRY:
return false;
// Outdated table or database structure - terminate core
- case 1054: // "Unknown column '%s' in '%s'"
- case 1146: // "Table '%s' doesn't exist"
- WPFatal(!errNo, "Your database structure is not up to date. Please make sure you've executed all queries in the sql/updates folders.");
+ case ER_BAD_FIELD_ERROR:
+ case ER_NO_SUCH_TABLE:
+ sLog->outError(LOG_FILTER_SQL, "Your database structure is not up to date. Please make sure you've executed all queries in the sql/updates folders.");
+ ACE_OS::sleep(10);
+ std::abort();
+ return false;
+ case ER_PARSE_ERROR:
+ sLog->outError(LOG_FILTER_SQL, "Error while parsing SQL. Core fix required.");
+ ACE_OS::sleep(10);
+ std::abort();
return false;
-
default:
- sLog->outSQLDriver("Unhandled MySQL errno %u. Unexpected behaviour possible.", errNo);
+ sLog->outError(LOG_FILTER_SQL, "Unhandled MySQL errno %u. Unexpected behaviour possible.", errNo);
return false;
}
}
diff --git a/src/server/shared/Database/MySQLThreading.h b/src/server/shared/Database/MySQLThreading.h
index 2004ee9826c..038ec4ee794 100755
--- a/src/server/shared/Database/MySQLThreading.h
+++ b/src/server/shared/Database/MySQLThreading.h
@@ -33,7 +33,7 @@ class MySQL
static void Thread_Init()
{
mysql_thread_init();
- sLog->outSQLDriver("Core thread with ID ["UI64FMTD"] initializing MySQL thread.",
+ sLog->outWarn(LOG_FILTER_SQL, "Core thread with ID ["UI64FMTD"] initializing MySQL thread.",
(uint64)ACE_Based::Thread::currentId());
}
@@ -44,7 +44,7 @@ class MySQL
static void Thread_End()
{
mysql_thread_end();
- sLog->outSQLDriver("Core thread with ID ["UI64FMTD"] shutting down MySQL thread.",
+ sLog->outWarn(LOG_FILTER_SQL, "Core thread with ID ["UI64FMTD"] shutting down MySQL thread.",
(uint64)ACE_Based::Thread::currentId());
}
diff --git a/src/server/shared/Database/PreparedStatement.cpp b/src/server/shared/Database/PreparedStatement.cpp
index ae69fc5f913..08b554ff696 100755
--- a/src/server/shared/Database/PreparedStatement.cpp
+++ b/src/server/shared/Database/PreparedStatement.cpp
@@ -78,7 +78,7 @@ void PreparedStatement::BindParameters()
}
#ifdef _DEBUG
if (i < m_stmt->m_paramCount)
- sLog->outSQLDriver("[WARNING]: BindParameters() for statement %u did not bind all allocated parameters", m_index);
+ sLog->outWarn(LOG_FILTER_SQL, "[WARNING]: BindParameters() for statement %u did not bind all allocated parameters", m_index);
#endif
}
@@ -232,7 +232,7 @@ void MySQLPreparedStatement::ClearParameters()
static bool ParementerIndexAssertFail(uint32 stmtIndex, uint8 index, uint32 paramCount)
{
- sLog->outError("Attempted to bind parameter %u%s on a PreparedStatement %u (statement has only %u parameters)", uint32(index) + 1, (index == 1 ? "st" : (index == 2 ? "nd" : (index == 3 ? "rd" : "nd"))), stmtIndex, paramCount);
+ sLog->outError(LOG_FILTER_SQL_DRIVER, "Attempted to bind parameter %u%s on a PreparedStatement %u (statement has only %u parameters)", uint32(index) + 1, (index == 1 ? "st" : (index == 2 ? "nd" : (index == 3 ? "rd" : "nd"))), stmtIndex, paramCount);
return false;
}
@@ -242,7 +242,7 @@ bool MySQLPreparedStatement::CheckValidIndex(uint8 index)
ASSERT(index < m_paramCount || ParementerIndexAssertFail(m_stmt->m_index, index, m_paramCount));
if (m_paramsSet[index])
- sLog->outSQLDriver("[WARNING] Prepared Statement (id: %u) trying to bind value on already bound index (%u).", m_stmt->m_index, index);
+ sLog->outWarn(LOG_FILTER_SQL, "[WARNING] Prepared Statement (id: %u) trying to bind value on already bound index (%u).", m_stmt->m_index, index);
return true;
}
diff --git a/src/server/shared/Database/QueryHolder.cpp b/src/server/shared/Database/QueryHolder.cpp
index a3602531205..99772c7e323 100755
--- a/src/server/shared/Database/QueryHolder.cpp
+++ b/src/server/shared/Database/QueryHolder.cpp
@@ -24,7 +24,7 @@ bool SQLQueryHolder::SetQuery(size_t index, const char *sql)
{
if (m_queries.size() <= index)
{
- sLog->outError("Query index (%zu) out of range (size: %u) for query: %s", index, (uint32)m_queries.size(), sql);
+ sLog->outError(LOG_FILTER_SQL, "Query index (%zu) out of range (size: %u) for query: %s", index, (uint32)m_queries.size(), sql);
return false;
}
@@ -44,7 +44,7 @@ bool SQLQueryHolder::SetPQuery(size_t index, const char *format, ...)
{
if (!format)
{
- sLog->outError("Query (index: %zu) is empty.", index);
+ sLog->outError(LOG_FILTER_SQL, "Query (index: %zu) is empty.", index);
return false;
}
@@ -56,7 +56,7 @@ bool SQLQueryHolder::SetPQuery(size_t index, const char *format, ...)
if (res == -1)
{
- sLog->outError("SQL Query truncated (and not execute) for format: %s", format);
+ sLog->outError(LOG_FILTER_SQL, "SQL Query truncated (and not execute) for format: %s", format);
return false;
}
@@ -67,7 +67,7 @@ bool SQLQueryHolder::SetPreparedQuery(size_t index, PreparedStatement* stmt)
{
if (m_queries.size() <= index)
{
- sLog->outError("Query index (%zu) out of range (size: %u) for prepared statement", index, (uint32)m_queries.size());
+ sLog->outError(LOG_FILTER_SQL, "Query index (%zu) out of range (size: %u) for prepared statement", index, (uint32)m_queries.size());
return false;
}
diff --git a/src/server/shared/Database/QueryResult.cpp b/src/server/shared/Database/QueryResult.cpp
index 95034387089..cb21c088d00 100755
--- a/src/server/shared/Database/QueryResult.cpp
+++ b/src/server/shared/Database/QueryResult.cpp
@@ -59,7 +59,7 @@ m_length(NULL)
//- This is where we store the (entire) resultset
if (mysql_stmt_store_result(m_stmt))
{
- sLog->outSQLDriver("%s:mysql_stmt_store_result, cannot bind result from MySQL server. Error: %s", __FUNCTION__, mysql_stmt_error(m_stmt));
+ sLog->outWarn(LOG_FILTER_SQL, "%s:mysql_stmt_store_result, cannot bind result from MySQL server. Error: %s", __FUNCTION__, mysql_stmt_error(m_stmt));
return;
}
@@ -86,7 +86,7 @@ m_length(NULL)
//- This is where we bind the bind the buffer to the statement
if (mysql_stmt_bind_result(m_stmt, m_rBind))
{
- sLog->outSQLDriver("%s:mysql_stmt_bind_result, cannot bind result from MySQL server. Error: %s", __FUNCTION__, mysql_stmt_error(m_stmt));
+ sLog->outWarn(LOG_FILTER_SQL, "%s:mysql_stmt_bind_result, cannot bind result from MySQL server. Error: %s", __FUNCTION__, mysql_stmt_error(m_stmt));
delete[] m_rBind;
delete[] m_isNull;
delete[] m_length;
diff --git a/src/server/shared/Debugging/Errors.h b/src/server/shared/Debugging/Errors.h
index 48a8bda32ed..6ce3d926f4c 100755
--- a/src/server/shared/Debugging/Errors.h
+++ b/src/server/shared/Debugging/Errors.h
@@ -24,10 +24,10 @@
#include <ace/Stack_Trace.h>
#include <ace/OS_NS_unistd.h>
-#define WPAssert(assertion) { if (!(assertion)) { ACE_Stack_Trace st; sLog->outError("\n%s:%i in %s ASSERTION FAILED:\n %s\n%s\n", __FILE__, __LINE__, __FUNCTION__, #assertion, st.c_str()); *((volatile int*)NULL) = 0; } }
-#define WPError(assertion, errmsg) { if (!(assertion)) { sLog->outError("%\n%s:%i in %s ERROR:\n %s\n", __FILE__, __LINE__, __FUNCTION__, (char *)errmsg); *((volatile int*)NULL) = 0; } }
-#define WPWarning(assertion, errmsg) { if (!(assertion)) { sLog->outError("\n%s:%i in %s WARNING:\n %s\n", __FILE__, __LINE__, __FUNCTION__, (char *)errmsg); } }
-#define WPFatal(assertion, errmsg) { if (!(assertion)) { sLog->outError("\n%s:%i in %s FATAL ERROR:\n %s\n", __FILE__, __LINE__, __FUNCTION__, (char *)errmsg); ACE_OS::sleep(10); *((volatile int*)NULL) = 0; } }
+#define WPAssert(assertion) { if (!(assertion)) { ACE_Stack_Trace st; sLog->outError(LOG_FILTER_GENERAL, "\n%s:%i in %s ASSERTION FAILED:\n %s\n%s\n", __FILE__, __LINE__, __FUNCTION__, #assertion, st.c_str()); *((volatile int*)NULL) = 0; } }
+#define WPError(assertion, errmsg) { if (!(assertion)) { sLog->outError(LOG_FILTER_GENERAL, "%\n%s:%i in %s ERROR:\n %s\n", __FILE__, __LINE__, __FUNCTION__, (char *)errmsg); *((volatile int*)NULL) = 0; } }
+#define WPWarning(assertion, errmsg) { if (!(assertion)) { sLog->outError(LOG_FILTER_GENERAL, "\n%s:%i in %s WARNING:\n %s\n", __FILE__, __LINE__, __FUNCTION__, (char *)errmsg); } }
+#define WPFatal(assertion, errmsg) { if (!(assertion)) { sLog->outError(LOG_FILTER_GENERAL, "\n%s:%i in %s FATAL ERROR:\n %s\n", __FILE__, __LINE__, __FUNCTION__, (char *)errmsg); ACE_OS::sleep(10); *((volatile int*)NULL) = 0; } }
#define ASSERT WPAssert
#endif
diff --git a/src/server/shared/Logging/Appender.cpp b/src/server/shared/Logging/Appender.cpp
new file mode 100644
index 00000000000..7950e045201
--- /dev/null
+++ b/src/server/shared/Logging/Appender.cpp
@@ -0,0 +1,218 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "Appender.h"
+#include "Common.h"
+
+std::string LogMessage::getTimeStr(time_t time)
+{
+ tm* aTm = localtime(&time);
+ char buf[20];
+ snprintf(buf, 20, "%04d-%02d-%02d_%02d:%02d:%02d", aTm->tm_year+1900, aTm->tm_mon+1, aTm->tm_mday, aTm->tm_hour, aTm->tm_min, aTm->tm_sec);
+ return std::string(buf);
+}
+
+std::string LogMessage::getTimeStr()
+{
+ return getTimeStr(mtime);
+}
+
+Appender::Appender(uint8 _id, std::string const& _name, AppenderType _type /* = APPENDER_NONE*/, LogLevel _level /* = LOG_LEVEL_DISABLED */, AppenderFlags _flags /* = APPENDER_FLAGS_NONE */):
+id(_id), name(_name), type(_type), level(_level), flags(_flags)
+{
+}
+
+Appender::~Appender()
+{
+}
+
+uint8 Appender::getId() const
+{
+ return id;
+}
+
+std::string const& Appender::getName() const
+{
+ return name;
+}
+
+AppenderType Appender::getType() const
+{
+ return type;
+}
+
+LogLevel Appender::getLogLevel() const
+{
+ return level;
+}
+
+AppenderFlags Appender::getFlags() const
+{
+ return flags;
+}
+
+void Appender::setLogLevel(LogLevel _level)
+{
+ level = _level;
+}
+
+void Appender::write(LogMessage& message)
+{
+ if (!level || level > message.level)
+ {
+ //fprintf(stderr, "Appender::write: Appender %s, Level %s. Msg %s Level %s Type %s WRONG LEVEL MASK\n", getName().c_str(), getLogLevelString(level), message.text.c_str(), getLogLevelString(message.level), getLogFilterTypeString(message.type)); // DEBUG - RemoveMe
+ return;
+ }
+
+ message.prefix.clear();
+ if (flags & APPENDER_FLAGS_PREFIX_TIMESTAMP)
+ message.prefix.append(message.getTimeStr().c_str());
+
+ if (flags & APPENDER_FLAGS_PREFIX_LOGLEVEL)
+ {
+ if (!message.prefix.empty())
+ message.prefix.push_back(' ');
+
+ char text[MAX_QUERY_LEN];
+ snprintf(text, MAX_QUERY_LEN, "%-5s", Appender::getLogLevelString(message.level));
+ message.prefix.append(text);
+ }
+
+ if (flags & APPENDER_FLAGS_PREFIX_LOGFILTERTYPE)
+ {
+ if (!message.prefix.empty())
+ message.prefix.push_back(' ');
+
+ char text[MAX_QUERY_LEN];
+ snprintf(text, MAX_QUERY_LEN, "[%-15s]", Appender::getLogFilterTypeString(message.type));
+ message.prefix.append(text);
+ }
+
+ if (!message.prefix.empty())
+ message.prefix.push_back(' ');
+
+ _write(message);
+}
+
+const char* Appender::getLogLevelString(LogLevel level)
+{
+ switch (level)
+ {
+ case LOG_LEVEL_FATAL:
+ return "FATAL";
+ case LOG_LEVEL_ERROR:
+ return "ERROR";
+ case LOG_LEVEL_WARN:
+ return "WARN";
+ case LOG_LEVEL_INFO:
+ return "INFO";
+ case LOG_LEVEL_DEBUG:
+ return "DEBUG";
+ case LOG_LEVEL_TRACE:
+ return "TRACE";
+ default:
+ return "DISABLED";
+ }
+}
+
+char const* Appender::getLogFilterTypeString(LogFilterType type)
+{
+ switch (type)
+ {
+ case LOG_FILTER_GENERAL:
+ return "GENERAL";
+ case LOG_FILTER_UNITS:
+ return "UNITS";
+ case LOG_FILTER_PETS:
+ return "PETS";
+ case LOG_FILTER_VEHICLES:
+ return "VEHICLES";
+ case LOG_FILTER_TSCR:
+ return "TSCR";
+ case LOG_FILTER_DATABASE_AI:
+ return "DATABASE_AI";
+ case LOG_FILTER_MAPSCRIPTS:
+ return "MAPSCRIPTS";
+ case LOG_FILTER_NETWORKIO:
+ return "NETWORKIO";
+ case LOG_FILTER_SPELLS_AURAS:
+ return "SPELLS_AURAS";
+ case LOG_FILTER_ACHIEVEMENTSYS:
+ return "ACHIEVEMENTSYS";
+ case LOG_FILTER_CONDITIONSYS:
+ return "CONDITIONSYS";
+ case LOG_FILTER_POOLSYS:
+ return "POOLSYS";
+ case LOG_FILTER_AUCTIONHOUSE:
+ return "AUCTIONHOUSE";
+ case LOG_FILTER_BATTLEGROUND:
+ return "BATTLEGROUND";
+ case LOG_FILTER_OUTDOORPVP:
+ return "OUTDOORPVP";
+ case LOG_FILTER_CHATSYS:
+ return "CHATSYS";
+ case LOG_FILTER_LFG:
+ return "LFG";
+ case LOG_FILTER_MAPS:
+ return "MAPS";
+ case LOG_FILTER_PLAYER:
+ return "PLAYER";
+ case LOG_FILTER_PLAYER_LOADING:
+ return "PLAYER_LOADING";
+ case LOG_FILTER_PLAYER_ITEMS:
+ return "PLAYER_ITEMS";
+ case LOG_FILTER_PLAYER_SKILLS:
+ return "PLAYER_SKILLS";
+ case LOG_FILTER_PLAYER_CHATLOG:
+ return "PLAYER_CHATLOG";
+ case LOG_FILTER_LOOT:
+ return "LOOT";
+ case LOG_FILTER_GUILD:
+ return "GUILD";
+ case LOG_FILTER_TRANSPORTS:
+ return "TRANSPORTS";
+ case LOG_FILTER_SQL:
+ return "SQL";
+ case LOG_FILTER_GMCOMMAND:
+ return "GMCOMMAND";
+ case LOG_FILTER_REMOTECOMMAND:
+ return "REMOTECOMMAND";
+ case LOG_FILTER_WARDEN:
+ return "WARDEN";
+ case LOG_FILTER_AUTHSERVER:
+ return "AUTHSERVER";
+ case LOG_FILTER_WORLDSERVER:
+ return "WORLDSERVER";
+ case LOG_FILTER_GAMEEVENTS:
+ return "GAMEEVENTS";
+ case LOG_FILTER_CALENDAR:
+ return "CALENDAR";
+ case LOG_FILTER_CHARACTER:
+ return "CHARACTER";
+ case LOG_FILTER_ARENAS:
+ return "ARENAS";
+ case LOG_FILTER_SQL_DRIVER:
+ return "SQL DRIVER";
+ case LOG_FILTER_SQL_DEV:
+ return "SQL DEV";
+ case LOG_FILTER_OPCODES:
+ return "OPCODES";
+ default:
+ break;
+ }
+ return "???";
+}
diff --git a/src/server/shared/Logging/Appender.h b/src/server/shared/Logging/Appender.h
new file mode 100644
index 00000000000..956776c500b
--- /dev/null
+++ b/src/server/shared/Logging/Appender.h
@@ -0,0 +1,154 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef APPENDER_H
+#define APPENDER_H
+
+#include "Define.h"
+#include <time.h>
+#include <string>
+#include <map>
+
+enum LogFilterType
+{
+ LOG_FILTER_GENERAL, // This one should only be used inside Log.cpp
+ LOG_FILTER_UNITS, // Anything related to units that doesn't fit in other categories. ie. creature formations
+ LOG_FILTER_PETS,
+ LOG_FILTER_VEHICLES,
+ LOG_FILTER_TSCR, // C++ AI, instance scripts, etc.
+ LOG_FILTER_DATABASE_AI, // SmartAI, EventAI, Creature* * AI
+ LOG_FILTER_MAPSCRIPTS,
+ LOG_FILTER_NETWORKIO,
+ LOG_FILTER_SPELLS_AURAS,
+ LOG_FILTER_ACHIEVEMENTSYS,
+ LOG_FILTER_CONDITIONSYS,
+ LOG_FILTER_POOLSYS,
+ LOG_FILTER_AUCTIONHOUSE,
+ LOG_FILTER_BATTLEGROUND,
+ LOG_FILTER_OUTDOORPVP,
+ LOG_FILTER_CHATSYS,
+ LOG_FILTER_LFG,
+ LOG_FILTER_MAPS,
+ LOG_FILTER_PLAYER, // Any player log that does not fit in other player filters
+ LOG_FILTER_PLAYER_LOADING, // Debug output from Player::_Load functions
+ LOG_FILTER_PLAYER_ITEMS,
+ LOG_FILTER_PLAYER_SKILLS,
+ LOG_FILTER_PLAYER_CHATLOG,
+ LOG_FILTER_LOOT,
+ LOG_FILTER_GUILD,
+ LOG_FILTER_TRANSPORTS,
+ LOG_FILTER_SQL,
+ LOG_FILTER_GMCOMMAND,
+ LOG_FILTER_REMOTECOMMAND,
+ LOG_FILTER_WARDEN,
+ LOG_FILTER_AUTHSERVER,
+ LOG_FILTER_WORLDSERVER,
+ LOG_FILTER_GAMEEVENTS,
+ LOG_FILTER_CALENDAR,
+ LOG_FILTER_CHARACTER,
+ LOG_FILTER_ARENAS,
+ LOG_FILTER_SQL_DRIVER,
+ LOG_FILTER_SQL_DEV,
+ LOG_FILTER_OPCODES
+};
+
+const uint8 MaxLogFilter = uint8(LOG_FILTER_SQL_DEV) + 1;
+
+// Values assigned have their equivalent in enum ACE_Log_Priority
+enum LogLevel
+{
+ LOG_LEVEL_DISABLED = 0,
+ LOG_LEVEL_TRACE = 1,
+ LOG_LEVEL_DEBUG = 2,
+ LOG_LEVEL_INFO = 3,
+ LOG_LEVEL_WARN = 4,
+ LOG_LEVEL_ERROR = 5,
+ LOG_LEVEL_FATAL = 6,
+};
+
+const uint8 MaxLogLevels = 6;
+
+enum AppenderType
+{
+ APPENDER_NONE,
+ APPENDER_CONSOLE,
+ APPENDER_FILE,
+ APPENDER_DB,
+};
+
+enum AppenderFlags
+{
+ APPENDER_FLAGS_NONE = 0x00,
+ APPENDER_FLAGS_PREFIX_TIMESTAMP = 0x01,
+ APPENDER_FLAGS_PREFIX_LOGLEVEL = 0x02,
+ APPENDER_FLAGS_PREFIX_LOGFILTERTYPE = 0x04,
+ APPENDER_FLAGS_USE_TIMESTAMP = 0x08, // only used by FileAppender
+ APPENDER_FLAGS_MAKE_FILE_BACKUP = 0x10 // only used by FileAppender
+};
+
+struct LogMessage
+{
+ LogMessage(LogLevel _level, LogFilterType _type, std::string _text)
+ : level(_level)
+ , type(_type)
+ , text(_text)
+ , param1(0)
+ {
+ mtime = time(NULL);
+ }
+
+ static std::string getTimeStr(time_t time);
+ std::string getTimeStr();
+
+ LogLevel level;
+ LogFilterType type;
+ std::string text;
+ std::string prefix;
+ uint32 param1;
+ time_t mtime;
+};
+
+class Appender
+{
+ public:
+ Appender(uint8 _id, std::string const& name, AppenderType type = APPENDER_NONE, LogLevel level = LOG_LEVEL_DISABLED, AppenderFlags flags = APPENDER_FLAGS_NONE);
+ virtual ~Appender();
+
+ uint8 getId() const;
+ std::string const& getName() const;
+ AppenderType getType() const;
+ LogLevel getLogLevel() const;
+ AppenderFlags getFlags() const;
+
+ void setLogLevel(LogLevel);
+ void write(LogMessage& message);
+ static const char* getLogLevelString(LogLevel level);
+ static const char* getLogFilterTypeString(LogFilterType type);
+
+ private:
+ virtual void _write(LogMessage& /*message*/) {};
+
+ uint8 id;
+ std::string name;
+ AppenderType type;
+ LogLevel level;
+ AppenderFlags flags;
+};
+
+typedef std::map<uint8, Appender*> AppenderMap;
+
+#endif
diff --git a/src/server/shared/Logging/AppenderConsole.cpp b/src/server/shared/Logging/AppenderConsole.cpp
new file mode 100644
index 00000000000..839f8512ad7
--- /dev/null
+++ b/src/server/shared/Logging/AppenderConsole.cpp
@@ -0,0 +1,193 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "AppenderConsole.h"
+#include "Config.h"
+#include "Util.h"
+
+#include <sstream>
+
+AppenderConsole::AppenderConsole(uint8 id, std::string const& name, LogLevel level, AppenderFlags flags):
+Appender(id, name, APPENDER_CONSOLE, level, flags), _colored(false)
+{
+ for (uint8 i = 0; i < MaxLogLevels; ++i)
+ _colors[i] = ColorTypes(MaxColors);
+}
+
+void AppenderConsole::InitColors(std::string const& str)
+{
+ if (str.empty())
+ {
+ _colored = false;
+ return;
+ }
+
+ int color[MaxLogLevels];
+
+ std::istringstream ss(str);
+
+ for (uint8 i = 0; i < MaxLogLevels; ++i)
+ {
+ ss >> color[i];
+
+ if (!ss)
+ return;
+
+ if (color[i] < 0 || color[i] >= MaxColors)
+ return;
+ }
+
+ for (uint8 i = 0; i < MaxLogLevels; ++i)
+ _colors[i] = ColorTypes(color[i]);
+
+ _colored = true;
+}
+
+void AppenderConsole::SetColor(bool stdout_stream, ColorTypes color)
+{
+ #if PLATFORM == PLATFORWINDOWS
+ static WORD WinColorFG[MaxColors] =
+ {
+ 0, // BLACK
+ FOREGROUND_RED, // RED
+ FOREGROUND_GREEN, // GREEN
+ FOREGROUND_RED | FOREGROUND_GREEN, // BROWN
+ FOREGROUND_BLUE, // BLUE
+ FOREGROUND_RED | FOREGROUND_BLUE, // MAGENTA
+ FOREGROUND_GREEN | FOREGROUND_BLUE, // CYAN
+ FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_BLUE, // WHITE
+ // YELLOW
+ FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_INTENSITY,
+ // RED_BOLD
+ FOREGROUND_RED | FOREGROUND_INTENSITY,
+ // GREEN_BOLD
+ FOREGROUND_GREEN | FOREGROUND_INTENSITY,
+ FOREGROUND_BLUE | FOREGROUND_INTENSITY, // BLUE_BOLD
+ // MAGENTA_BOLD
+ FOREGROUND_RED | FOREGROUND_BLUE | FOREGROUND_INTENSITY,
+ // CYAN_BOLD
+ FOREGROUND_GREEN | FOREGROUND_BLUE | FOREGROUND_INTENSITY,
+ // WHITE_BOLD
+ FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_BLUE | FOREGROUND_INTENSITY
+ };
+
+ HANDLE hConsole = GetStdHandle(stdout_stream ? STD_OUTPUT_HANDLE : STD_ERROR_HANDLE);
+ SetConsoleTextAttribute(hConsole, WinColorFG[color]);
+ #else
+ enum ANSITextAttr
+ {
+ TA_NORMAL = 0,
+ TA_BOLD = 1,
+ TA_BLINK = 5,
+ TA_REVERSE = 7
+ };
+
+ enum ANSIFgTextAttr
+ {
+ FG_BLACK = 30,
+ FG_RED,
+ FG_GREEN,
+ FG_BROWN,
+ FG_BLUE,
+ FG_MAGENTA,
+ FG_CYAN,
+ FG_WHITE,
+ FG_YELLOW
+ };
+
+ enum ANSIBgTextAttr
+ {
+ BG_BLACK = 40,
+ BG_RED,
+ BG_GREEN,
+ BG_BROWN,
+ BG_BLUE,
+ BG_MAGENTA,
+ BG_CYAN,
+ BG_WHITE
+ };
+
+ static uint8 UnixColorFG[MaxColors] =
+ {
+ FG_BLACK, // BLACK
+ FG_RED, // RED
+ FG_GREEN, // GREEN
+ FG_BROWN, // BROWN
+ FG_BLUE, // BLUE
+ FG_MAGENTA, // MAGENTA
+ FG_CYAN, // CYAN
+ FG_WHITE, // WHITE
+ FG_YELLOW, // YELLOW
+ FG_RED, // LRED
+ FG_GREEN, // LGREEN
+ FG_BLUE, // LBLUE
+ FG_MAGENTA, // LMAGENTA
+ FG_CYAN, // LCYAN
+ FG_WHITE // LWHITE
+ };
+
+ fprintf((stdout_stream? stdout : stderr), "\x1b[%d%sm", UnixColorFG[color], (color >= YELLOW && color < MaxColors ? ";1" : ""));
+ #endif
+}
+
+void AppenderConsole::ResetColor(bool stdout_stream)
+{
+ #if PLATFORM == PLATFORWINDOWS
+ HANDLE hConsole = GetStdHandle(stdout_stream ? STD_OUTPUT_HANDLE : STD_ERROR_HANDLE);
+ SetConsoleTextAttribute(hConsole, FOREGROUND_BLUE | FOREGROUND_GREEN | FOREGROUND_RED);
+ #else
+ fprintf((stdout_stream ? stdout : stderr), "\x1b[0m");
+ #endif
+}
+
+void AppenderConsole::_write(LogMessage& message)
+{
+ bool stdout_stream = message.level == LOG_LEVEL_ERROR || message.level == LOG_LEVEL_FATAL;
+
+ if (_colored)
+ {
+ uint8 index;
+ switch (message.level)
+ {
+ case LOG_LEVEL_TRACE:
+ index = 5;
+ break;
+ case LOG_LEVEL_DEBUG:
+ index = 4;
+ break;
+ case LOG_LEVEL_INFO:
+ index = 3;
+ break;
+ case LOG_LEVEL_WARN:
+ index = 2;
+ break;
+ case LOG_LEVEL_FATAL:
+ index = 0;
+ break;
+ case LOG_LEVEL_ERROR: // No break on purpose
+ default:
+ index = 1;
+ break;
+ }
+
+ SetColor(stdout_stream, _colors[index]);
+ utf8printf(stdout_stream ? stdout : stderr, "%s%s", message.prefix.c_str(), message.text.c_str());
+ ResetColor(stdout_stream);
+ }
+ else
+ utf8printf(stdout_stream ? stdout : stderr, "%s%s", message.prefix.c_str(), message.text.c_str());
+}
diff --git a/src/server/shared/Logging/AppenderConsole.h b/src/server/shared/Logging/AppenderConsole.h
new file mode 100644
index 00000000000..ad7d9543cdb
--- /dev/null
+++ b/src/server/shared/Logging/AppenderConsole.h
@@ -0,0 +1,59 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef APPENDERCONSOLE_H
+#define APPENDERCONSOLE_H
+
+#include "Appender.h"
+#include <string>
+
+enum ColorTypes
+{
+ BLACK,
+ RED,
+ GREEN,
+ BROWN,
+ BLUE,
+ MAGENTA,
+ CYAN,
+ GREY,
+ YELLOW,
+ LRED,
+ LGREEN,
+ LBLUE,
+ LMAGENTA,
+ LCYAN,
+ WHITE
+};
+
+const uint8 MaxColors = uint8(WHITE) + 1;
+
+class AppenderConsole: public Appender
+{
+ public:
+ AppenderConsole(uint8 _id, std::string const& name, LogLevel level, AppenderFlags flags);
+ void InitColors(const std::string& init_str);
+
+ private:
+ void SetColor(bool stdout_stream, ColorTypes color);
+ void ResetColor(bool stdout_stream);
+ void _write(LogMessage& message);
+ bool _colored;
+ ColorTypes _colors[MaxLogLevels];
+};
+
+#endif
diff --git a/src/server/shared/Logging/AppenderDB.cpp b/src/server/shared/Logging/AppenderDB.cpp
new file mode 100644
index 00000000000..76abfca2d85
--- /dev/null
+++ b/src/server/shared/Logging/AppenderDB.cpp
@@ -0,0 +1,55 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "AppenderDB.h"
+#include "Database/DatabaseEnv.h"
+
+AppenderDB::AppenderDB(uint8 id, std::string const& name, LogLevel level, uint8 realmId):
+Appender(id, name, APPENDER_DB, level), realm(realmId), enable(false)
+{
+}
+
+AppenderDB::~AppenderDB()
+{
+}
+
+void AppenderDB::_write(LogMessage& message)
+{
+ if (!enable)
+ return;
+ switch (message.type)
+ {
+ case LOG_FILTER_SQL:
+ case LOG_FILTER_SQL_DRIVER:
+ case LOG_FILTER_SQL_DEV:
+ break; // Avoid infinite loop, PExecute triggers Logging with LOG_FILTER_SQL type
+ default:
+ PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_INS_LOG);
+ stmt->setUInt64(0, message.mtime);
+ stmt->setUInt32(1, realm);
+ stmt->setUInt8(2, message.type);
+ stmt->setUInt8(3, message.level);
+ stmt->setString(4, message.text);
+ LoginDatabase.Execute(stmt);
+ break;
+ }
+}
+
+void AppenderDB::setEnable(bool _enable)
+{
+ enable = _enable;
+}
diff --git a/src/server/shared/Logging/AppenderDB.h b/src/server/shared/Logging/AppenderDB.h
new file mode 100644
index 00000000000..4399195b181
--- /dev/null
+++ b/src/server/shared/Logging/AppenderDB.h
@@ -0,0 +1,36 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef APPENDERDB_H
+#define APPENDERDB_H
+
+#include "Appender.h"
+
+class AppenderDB: public Appender
+{
+ public:
+ AppenderDB(uint8 _id, std::string const& _name, LogLevel level, uint8 realmId);
+ ~AppenderDB();
+ void setEnable(bool enable);
+
+ private:
+ uint8 realm;
+ bool enable;
+ void _write(LogMessage& message);
+};
+
+#endif
diff --git a/src/server/shared/Logging/AppenderFile.cpp b/src/server/shared/Logging/AppenderFile.cpp
new file mode 100644
index 00000000000..d66771b9055
--- /dev/null
+++ b/src/server/shared/Logging/AppenderFile.cpp
@@ -0,0 +1,71 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "AppenderFile.h"
+#include "Common.h"
+
+AppenderFile::AppenderFile(uint8 id, std::string const& name, LogLevel level, const char* _filename, const char* _logDir, const char* _mode, AppenderFlags _flags)
+ : Appender(id, name, APPENDER_FILE, level, _flags)
+ , filename(_filename)
+ , logDir(_logDir)
+ , mode(_mode)
+{
+ dynamicName = std::string::npos != filename.find("%u");
+ backup = _flags & APPENDER_FLAGS_MAKE_FILE_BACKUP;
+ if (!dynamicName)
+ logfile = OpenFile(_filename, _mode, backup);
+}
+
+AppenderFile::~AppenderFile()
+{
+ if (logfile)
+ {
+ fclose(logfile);
+ logfile = NULL;
+ }
+}
+
+void AppenderFile::_write(LogMessage& message)
+{
+ if (dynamicName)
+ {
+ char namebuf[TRINITY_PATH_MAX];
+ snprintf(namebuf, TRINITY_PATH_MAX, filename.c_str(), message.param1);
+ logfile = OpenFile(namebuf, mode, backup);
+ }
+
+ if (logfile)
+ {
+ fprintf(logfile, "%s%s", message.prefix.c_str(), message.text.c_str());
+ fflush(logfile);
+
+ if (dynamicName)
+ fclose(logfile);
+ }
+}
+
+FILE* AppenderFile::OpenFile(std::string const &filename, std::string const &mode, bool backup)
+{
+ if (mode == "w" && backup)
+ {
+ std::string newName(filename);
+ newName.push_back('.');
+ newName.append(LogMessage::getTimeStr(time(NULL)));
+ rename(filename.c_str(), newName.c_str()); // no error handling... if we couldn't make a backup, just ignore
+ }
+ return fopen((logDir + filename).c_str(), mode.c_str());
+}
diff --git a/src/server/shared/Logging/AppenderFile.h b/src/server/shared/Logging/AppenderFile.h
new file mode 100644
index 00000000000..e9cb858f625
--- /dev/null
+++ b/src/server/shared/Logging/AppenderFile.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef APPENDERFILE_H
+#define APPENDERFILE_H
+
+#include "Appender.h"
+
+class AppenderFile: public Appender
+{
+ public:
+ AppenderFile(uint8 _id, std::string const& _name, LogLevel level, const char* filename, const char* logDir, const char* mode, AppenderFlags flags);
+ ~AppenderFile();
+ FILE* OpenFile(std::string const& _name, std::string const& _mode, bool _backup);
+
+ private:
+ void _write(LogMessage& message);
+ FILE* logfile;
+ std::string filename;
+ std::string logDir;
+ std::string mode;
+ bool dynamicName;
+ bool backup;
+};
+
+#endif
diff --git a/src/server/shared/Logging/Log.cpp b/src/server/shared/Logging/Log.cpp
index 493e30d36c0..14234dfb155 100755..100644
--- a/src/server/shared/Logging/Log.cpp
+++ b/src/server/shared/Logging/Log.cpp
@@ -1,6 +1,6 @@
/*
* Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
- * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/>
+ * Copyright (C) 2005-2008 MaNGOS <http://getmangos.com/>
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
@@ -16,1071 +16,485 @@
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-#include "Common.h"
#include "Log.h"
-#include "Configuration/Config.h"
+#include "Common.h"
+#include "Config.h"
#include "Util.h"
+#include "AppenderConsole.h"
+#include "AppenderFile.h"
+#include "AppenderDB.h"
+#include "LogOperation.h"
-#include "Implementation/LoginDatabase.h" // For logging
-extern LoginDatabaseWorkerPool LoginDatabase;
-
-#include <stdarg.h>
-#include <stdio.h>
+#include <cstdarg>
+#include <cstdio>
+#include <sstream>
-Log::Log() :
- raLogfile(NULL), logfile(NULL), gmLogfile(NULL), charLogfile(NULL),
- dberLogfile(NULL), chatLogfile(NULL), arenaLogFile(NULL), sqlLogFile(NULL), sqlDevLogFile(NULL), wardenLogFile(NULL),
- m_gmlog_per_account(false), m_enableLogDBLater(false),
- m_enableLogDB(false), m_colored(false)
+Log::Log() : worker(NULL)
{
- Initialize();
+ SetRealmID(0);
+ m_logsTimestamp = "_" + GetTimestampStr();
+ LoadFromConfig();
}
Log::~Log()
{
- if (logfile != NULL)
- fclose(logfile);
- logfile = NULL;
-
- if (gmLogfile != NULL)
- fclose(gmLogfile);
- gmLogfile = NULL;
-
- if (charLogfile != NULL)
- fclose(charLogfile);
- charLogfile = NULL;
-
- if (dberLogfile != NULL)
- fclose(dberLogfile);
- dberLogfile = NULL;
-
- if (raLogfile != NULL)
- fclose(raLogfile);
- raLogfile = NULL;
-
- if (chatLogfile != NULL)
- fclose(chatLogfile);
- chatLogfile = NULL;
-
- if (arenaLogFile != NULL)
- fclose(arenaLogFile);
- arenaLogFile = NULL;
-
- if (sqlLogFile != NULL)
- fclose(sqlLogFile);
- sqlLogFile = NULL;
-
- if (sqlDevLogFile != NULL)
- fclose(sqlDevLogFile);
- sqlDevLogFile = NULL;
-
- if (wardenLogFile != NULL)
- fclose(wardenLogFile);
- wardenLogFile = NULL;
+ Close();
}
-void Log::SetLogLevel(char *Level)
+uint8 Log::NextAppenderId()
{
- int32 NewLevel = atoi((char*)Level);
- if (NewLevel < 0)
- NewLevel = 0;
- m_logLevel = NewLevel;
-
- outString("LogLevel is %u", m_logLevel);
+ return AppenderId++;
}
-void Log::SetLogFileLevel(char *Level)
+int32 GetConfigIntDefault(std::string base, const char* name, int32 value)
{
- int32 NewLevel = atoi((char*)Level);
- if (NewLevel < 0)
- NewLevel = 0;
- m_logFileLevel = NewLevel;
-
- outString("LogFileLevel is %u", m_logFileLevel);
+ base.append(name);
+ return ConfigMgr::GetIntDefault(base.c_str(), value);
}
-void Log::SetDBLogLevel(char *Level)
+std::string GetConfigStringDefault(std::string base, const char* name, const char* value)
{
- int32 NewLevel = atoi((char*)Level);
- if (NewLevel < 0)
- NewLevel = 0;
- m_dbLogLevel = NewLevel;
-
- outString("DBLogLevel is %u", m_dbLogLevel);
+ base.append(name);
+ return ConfigMgr::GetStringDefault(base.c_str(), value);
}
-void Log::Initialize()
+// Returns default logger if the requested logger is not found
+Logger* Log::GetLoggerByType(LogFilterType filter)
{
- /// Check whether we'll log GM commands/RA events/character outputs/chat stuffs
- m_dbChar = ConfigMgr::GetBoolDefault("LogDB.Char", false);
- m_dbRA = ConfigMgr::GetBoolDefault("LogDB.RA", false);
- m_dbGM = ConfigMgr::GetBoolDefault("LogDB.GM", false);
- m_dbChat = ConfigMgr::GetBoolDefault("LogDB.Chat", false);
-
- /// Realm must be 0 by default
- SetRealmID(0);
-
- /// Common log files data
- m_logsDir = ConfigMgr::GetStringDefault("LogsDir", "");
- if (!m_logsDir.empty())
- if ((m_logsDir.at(m_logsDir.length() - 1) != '/') && (m_logsDir.at(m_logsDir.length() - 1) != '\\'))
- m_logsDir.push_back('/');
-
- m_logsTimestamp = "_" + GetTimestampStr();
-
- /// Open specific log files
- logfile = openLogFile("LogFile", "LogTimestamp", "w");
- InitColors(ConfigMgr::GetStringDefault("LogColors", ""));
-
- m_gmlog_per_account = ConfigMgr::GetBoolDefault("GmLogPerAccount", false);
- if (!m_gmlog_per_account)
- gmLogfile = openLogFile("GMLogFile", "GmLogTimestamp", "a");
- else
- {
- // GM log settings for per account case
- m_gmlog_filename_format = ConfigMgr::GetStringDefault("GMLogFile", "");
- if (!m_gmlog_filename_format.empty())
- {
- bool m_gmlog_timestamp = ConfigMgr::GetBoolDefault("GmLogTimestamp", false);
-
- size_t dot_pos = m_gmlog_filename_format.find_last_of('.');
- if (dot_pos!=m_gmlog_filename_format.npos)
- {
- if (m_gmlog_timestamp)
- m_gmlog_filename_format.insert(dot_pos, m_logsTimestamp);
-
- m_gmlog_filename_format.insert(dot_pos, "_#%u");
- }
- else
- {
- m_gmlog_filename_format += "_#%u";
-
- if (m_gmlog_timestamp)
- m_gmlog_filename_format += m_logsTimestamp;
- }
+ LoggerMap::iterator it = loggers.begin();
+ while (it != loggers.end() && it->second.getType() != filter)
+ ++it;
- m_gmlog_filename_format = m_logsDir + m_gmlog_filename_format;
- }
- }
-
- charLogfile = openLogFile("CharLogFile", "CharLogTimestamp", "a");
- dberLogfile = openLogFile("DBErrorLogFile", NULL, "a");
- raLogfile = openLogFile("RaLogFile", NULL, "a");
- chatLogfile = openLogFile("ChatLogFile", "ChatLogTimestamp", "a");
- arenaLogFile = openLogFile("ArenaLogFile", NULL, "a");
- sqlLogFile = openLogFile("SQLDriverLogFile", NULL, "a");
- sqlDevLogFile = openLogFile("SQLDeveloperLogFile", NULL, "a");
- wardenLogFile = openLogFile("Warden.LogFile",NULL,"a");
-
- // Main log file settings
- m_logLevel = ConfigMgr::GetIntDefault("LogLevel", LOGL_NORMAL);
- m_logFileLevel = ConfigMgr::GetIntDefault("LogFileLevel", LOGL_NORMAL);
- m_dbLogLevel = ConfigMgr::GetIntDefault("DBLogLevel", LOGL_NORMAL);
- m_sqlDriverQueryLogging = ConfigMgr::GetBoolDefault("SQLDriverQueryLogging", false);
-
- m_DebugLogMask = DebugLogFilters(ConfigMgr::GetIntDefault("DebugLogMask", LOG_FILTER_NONE));
-
- // Char log settings
- m_charLog_Dump = ConfigMgr::GetBoolDefault("CharLogDump", false);
- m_charLog_Dump_Separate = ConfigMgr::GetBoolDefault("CharLogDump.Separate", false);
- if (m_charLog_Dump_Separate)
- {
- m_dumpsDir = ConfigMgr::GetStringDefault("CharLogDump.SeparateDir", "");
- if (!m_dumpsDir.empty())
- if ((m_dumpsDir.at(m_dumpsDir.length() - 1) != '/') && (m_dumpsDir.at(m_dumpsDir.length() - 1) != '\\'))
- m_dumpsDir.push_back('/');
- }
-}
-
-void Log::ReloadConfig()
-{
- m_logLevel = ConfigMgr::GetIntDefault("LogLevel", LOGL_NORMAL);
- m_logFileLevel = ConfigMgr::GetIntDefault("LogFileLevel", LOGL_NORMAL);
- m_dbLogLevel = ConfigMgr::GetIntDefault("DBLogLevel", LOGL_NORMAL);
-
- m_DebugLogMask = DebugLogFilters(ConfigMgr::GetIntDefault("DebugLogMask", LOG_FILTER_NONE));
+ return it == loggers.end() ? &(loggers[0]) : &(it->second);
}
-FILE* Log::openLogFile(char const* configFileName, char const* configTimeStampFlag, char const* mode)
+Appender* Log::GetAppenderByName(std::string const& name)
{
- std::string logfn=ConfigMgr::GetStringDefault(configFileName, "");
- if (logfn.empty())
- return NULL;
-
- if (configTimeStampFlag && ConfigMgr::GetBoolDefault(configTimeStampFlag, false))
- {
- size_t dot_pos = logfn.find_last_of(".");
- if (dot_pos!=logfn.npos)
- logfn.insert(dot_pos, m_logsTimestamp);
- else
- logfn += m_logsTimestamp;
- }
+ AppenderMap::iterator it = appenders.begin();
+ while (it != appenders.end() && it->second && it->second->getName() != name)
+ ++it;
- return fopen((m_logsDir+logfn).c_str(), mode);
+ return it == appenders.end() ? NULL : it->second;
}
-FILE* Log::openGmlogPerAccount(uint32 account)
+void Log::CreateAppenderFromConfig(const char* name)
{
- if (m_gmlog_filename_format.empty())
- return NULL;
+ if (!name || *name == '\0')
+ return;
- char namebuf[TRINITY_PATH_MAX];
- snprintf(namebuf, TRINITY_PATH_MAX, m_gmlog_filename_format.c_str(), account);
- return fopen(namebuf, "a");
-}
+ // Format=type,level,flags,optional1,optional2
+ // if type = File. optional1 = file and option2 = mode
+ // if type = Console. optional1 = Color
+ std::string options = "Appender.";
+ options.append(name);
+ options = ConfigMgr::GetStringDefault(options.c_str(), "");
+ Tokens tokens(options, ',');
+ Tokens::iterator iter = tokens.begin();
-void Log::outTimestamp(FILE* file)
-{
- time_t t = time(NULL);
- tm* aTm = localtime(&t);
- // YYYY year
- // MM month (2 digits 01-12)
- // DD day (2 digits 01-31)
- // HH hour (2 digits 00-23)
- // MM minutes (2 digits 00-59)
- // SS seconds (2 digits 00-59)
- fprintf(file, "%-4d-%02d-%02d %02d:%02d:%02d ", aTm->tm_year+1900, aTm->tm_mon+1, aTm->tm_mday, aTm->tm_hour, aTm->tm_min, aTm->tm_sec);
-}
-
-void Log::InitColors(const std::string& str)
-{
- if (str.empty())
+ if (tokens.size() < 2)
{
- m_colored = false;
+ fprintf(stderr, "Log::CreateAppenderFromConfig: Wrong configuration for appender %s. Config line: %s\n", name, options.c_str());
return;
}
- int color[4];
-
- std::istringstream ss(str);
-
- for (uint8 i = 0; i < LogLevels; ++i)
+ AppenderFlags flags = APPENDER_FLAGS_NONE;
+ AppenderType type = AppenderType(atoi(*iter));
+ ++iter;
+ LogLevel level = LogLevel(atoi(*iter));
+ if (level > LOG_LEVEL_FATAL)
{
- ss >> color[i];
-
- if (!ss)
- return;
-
- if (color[i] < 0 || color[i] >= Colors)
- return;
+ fprintf(stderr, "Log::CreateAppenderFromConfig: Wrong Log Level %u for appender %s\n", level, name);
+ return;
}
- for (uint8 i = 0; i < LogLevels; ++i)
- m_colors[i] = ColorTypes(color[i]);
-
- m_colored = true;
-}
-
-void Log::SetColor(bool stdout_stream, ColorTypes color)
-{
- #if PLATFORM == PLATFORM_WINDOWS
- static WORD WinColorFG[Colors] =
- {
- 0, // BLACK
- FOREGROUND_RED, // RED
- FOREGROUND_GREEN, // GREEN
- FOREGROUND_RED | FOREGROUND_GREEN, // BROWN
- FOREGROUND_BLUE, // BLUE
- FOREGROUND_RED | FOREGROUND_BLUE, // MAGENTA
- FOREGROUND_GREEN | FOREGROUND_BLUE, // CYAN
- FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_BLUE, // WHITE
- // YELLOW
- FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_INTENSITY,
- // RED_BOLD
- FOREGROUND_RED | FOREGROUND_INTENSITY,
- // GREEN_BOLD
- FOREGROUND_GREEN | FOREGROUND_INTENSITY,
- FOREGROUND_BLUE | FOREGROUND_INTENSITY, // BLUE_BOLD
- // MAGENTA_BOLD
- FOREGROUND_RED | FOREGROUND_BLUE | FOREGROUND_INTENSITY,
- // CYAN_BOLD
- FOREGROUND_GREEN | FOREGROUND_BLUE | FOREGROUND_INTENSITY,
- // WHITE_BOLD
- FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_BLUE | FOREGROUND_INTENSITY
- };
-
- HANDLE hConsole = GetStdHandle(stdout_stream ? STD_OUTPUT_HANDLE : STD_ERROR_HANDLE );
- SetConsoleTextAttribute(hConsole, WinColorFG[color]);
- #else
- enum ANSITextAttr
- {
- TA_NORMAL=0,
- TA_BOLD=1,
- TA_BLINK=5,
- TA_REVERSE=7
- };
-
- enum ANSIFgTextAttr
- {
- FG_BLACK=30, FG_RED, FG_GREEN, FG_BROWN, FG_BLUE,
- FG_MAGENTA, FG_CYAN, FG_WHITE, FG_YELLOW
- };
-
- enum ANSIBgTextAttr
+ if (++iter != tokens.end())
+ flags = AppenderFlags(atoi(*iter));
+
+ switch (type)
{
- BG_BLACK=40, BG_RED, BG_GREEN, BG_BROWN, BG_BLUE,
- BG_MAGENTA, BG_CYAN, BG_WHITE
- };
-
- static uint8 UnixColorFG[Colors] =
- {
- FG_BLACK, // BLACK
- FG_RED, // RED
- FG_GREEN, // GREEN
- FG_BROWN, // BROWN
- FG_BLUE, // BLUE
- FG_MAGENTA, // MAGENTA
- FG_CYAN, // CYAN
- FG_WHITE, // WHITE
- FG_YELLOW, // YELLOW
- FG_RED, // LRED
- FG_GREEN, // LGREEN
- FG_BLUE, // LBLUE
- FG_MAGENTA, // LMAGENTA
- FG_CYAN, // LCYAN
- FG_WHITE // LWHITE
- };
-
- fprintf((stdout_stream? stdout : stderr), "\x1b[%d%sm", UnixColorFG[color], (color >= YELLOW && color < Colors ? ";1" : ""));
- #endif
-}
-
-void Log::ResetColor(bool stdout_stream)
-{
- #if PLATFORM == PLATFORM_WINDOWS
- HANDLE hConsole = GetStdHandle(stdout_stream ? STD_OUTPUT_HANDLE : STD_ERROR_HANDLE );
- SetConsoleTextAttribute(hConsole, FOREGROUND_BLUE | FOREGROUND_GREEN | FOREGROUND_RED );
- #else
- fprintf(( stdout_stream ? stdout : stderr ), "\x1b[0m");
- #endif
-}
+ case APPENDER_CONSOLE:
+ {
+ if (flags == APPENDER_FLAGS_NONE)
+ flags = AppenderFlags(APPENDER_FLAGS_PREFIX_LOGLEVEL | APPENDER_FLAGS_PREFIX_LOGFILTERTYPE);
+
+ AppenderConsole* appender = new AppenderConsole(NextAppenderId(), name, level, flags);
+ appenders[appender->getId()] = appender;
+ if (++iter != tokens.end())
+ appender->InitColors(*iter);
+ //fprintf(stdout, "Log::CreateAppenderFromConfig: Created Appender %s (%u), Type CONSOLE, Mask %u\n", appender->getName().c_str(), appender->getId(), appender->getLogLevel()); // DEBUG - RemoveMe
+ break;
+ }
+ case APPENDER_FILE:
+ {
+ std::string filename;
+ std::string mode = "a";
-std::string Log::GetTimestampStr()
-{
- time_t t = time(NULL);
- tm* aTm = localtime(&t);
- // YYYY year
- // MM month (2 digits 01-12)
- // DD day (2 digits 01-31)
- // HH hour (2 digits 00-23)
- // MM minutes (2 digits 00-59)
- // SS seconds (2 digits 00-59)
- char buf[20];
- snprintf(buf, 20, "%04d-%02d-%02d_%02d-%02d-%02d", aTm->tm_year+1900, aTm->tm_mon+1, aTm->tm_mday, aTm->tm_hour, aTm->tm_min, aTm->tm_sec);
- return std::string(buf);
-}
+ if (++iter == tokens.end())
+ {
+ fprintf(stderr, "Log::CreateAppenderFromConfig: Missing file name for appender %s\n", name);
+ return;
+ }
-void Log::outDB(LogTypes type, const char * str)
-{
- if (!str || type >= MAX_LOG_TYPES)
- return;
+ if (flags == APPENDER_FLAGS_NONE)
+ flags = AppenderFlags(APPENDER_FLAGS_PREFIX_LOGLEVEL | APPENDER_FLAGS_PREFIX_LOGFILTERTYPE | APPENDER_FLAGS_PREFIX_TIMESTAMP);
- std::string logStr(str);
- if (logStr.empty())
- return;
+ filename = *iter;
- PreparedStatement* stmt = LoginDatabase.GetPreparedStatement(LOGIN_INS_LOG);
+ if (++iter != tokens.end())
+ mode = *iter;
- stmt->setInt32(0, realm);
- stmt->setUInt8(1, uint8(type));
- stmt->setString(2, logStr);
+ if (flags & APPENDER_FLAGS_USE_TIMESTAMP)
+ {
+ size_t dot_pos = filename.find_last_of(".");
+ if (dot_pos != filename.npos)
+ filename.insert(dot_pos, m_logsTimestamp);
+ else
+ filename += m_logsTimestamp;
+ }
- LoginDatabase.Execute(stmt);
+ uint8 id = NextAppenderId();
+ appenders[id] = new AppenderFile(id, name, level, filename.c_str(), m_logsDir.c_str(), mode.c_str(), flags);
+ //fprintf(stdout, "Log::CreateAppenderFromConfig: Created Appender %s (%u), Type FILE, Mask %u, File %s, Mode %s\n", name, id, level, filename.c_str(), mode.c_str()); // DEBUG - RemoveMe
+ break;
+ }
+ case APPENDER_DB:
+ {
+ uint8 id = NextAppenderId();
+ appenders[id] = new AppenderDB(id, name, level, realm);
+ break;
+ }
+ default:
+ fprintf(stderr, "Log::CreateAppenderFromConfig: Unknown type %u for appender %s\n", type, name);
+ break;
+ }
}
-void Log::outString(const char * str, ...)
+void Log::CreateLoggerFromConfig(const char* name)
{
- if (!str)
+ if (!name || *name == '\0')
return;
- if (m_enableLogDB)
- {
- // we don't want empty strings in the DB
- std::string s(str);
- if (s.empty() || s == " ")
- return;
-
- va_list ap2;
- va_start(ap2, str);
- char nnew_str[MAX_QUERY_LEN];
- vsnprintf(nnew_str, MAX_QUERY_LEN, str, ap2);
- outDB(LOG_TYPE_STRING, nnew_str);
- va_end(ap2);
- }
-
- if (m_colored)
- SetColor(true, m_colors[LOGL_NORMAL]);
-
- va_list ap;
+ LogLevel level = LOG_LEVEL_DISABLED;
+ int32 type = -1;
- va_start(ap, str);
- vutf8printf(stdout, str, &ap);
- va_end(ap);
+ std::string options = "Logger.";
+ options.append(name);
+ options = ConfigMgr::GetStringDefault(options.c_str(), "");
- if (m_colored)
- ResetColor(true);
+ Tokens tokens(options, ',');
+ Tokens::iterator iter = tokens.begin();
- printf("\n");
- if (logfile)
+ if (tokens.size() != 3)
{
- outTimestamp(logfile);
- va_start(ap, str);
- vfprintf(logfile, str, ap);
- fprintf(logfile, "\n");
- va_end(ap);
-
- fflush(logfile);
+ fprintf(stderr, "Log::CreateLoggerFromConfig: Wrong configuration for logger %s. Config line: %s\n", name, options.c_str());
+ return;
}
- fflush(stdout);
-}
-void Log::outString()
-{
- printf("\n");
- if (logfile)
+ type = atoi(*iter);
+ if (type > MaxLogFilter)
{
- outTimestamp(logfile);
- fprintf(logfile, "\n");
- fflush(logfile);
+ fprintf(stderr, "Log::CreateLoggerFromConfig: Wrong type %u for logger %s\n", type, name);
+ return;
}
- fflush(stdout);
-}
-void Log::outCrash(const char * err, ...)
-{
- if (!err)
+ Logger& logger = loggers[type];
+ if (!logger.getName().empty())
+ {
+ fprintf(stderr, "Error while configuring Logger %s. Already defined\n", name);
return;
+ }
- if (m_enableLogDB)
+ ++iter;
+ level = LogLevel(atoi(*iter));
+ if (level > LOG_LEVEL_FATAL)
{
- va_list ap2;
- va_start(ap2, err);
- char nnew_str[MAX_QUERY_LEN];
- vsnprintf(nnew_str, MAX_QUERY_LEN, err, ap2);
- outDB(LOG_TYPE_CRASH, nnew_str);
- va_end(ap2);
+ fprintf(stderr, "Log::CreateLoggerFromConfig: Wrong Log Level %u for logger %s\n", type, name);
+ return;
}
- if (m_colored)
- SetColor(false, LRED);
+ logger.Create(name, LogFilterType(type), level);
+ //fprintf(stdout, "Log::CreateLoggerFromConfig: Created Logger %s, Type %u, mask %u\n", name, LogFilterType(type), level); // DEBUG - RemoveMe
- va_list ap;
-
- va_start(ap, err);
- vutf8printf(stderr, err, &ap);
- va_end(ap);
+ ++iter;
+ std::istringstream ss(*iter);
+ std::string str;
- if (m_colored)
- ResetColor(false);
-
- fprintf(stderr, "\n");
- if (logfile)
+ ss >> str;
+ while (ss)
{
- outTimestamp(logfile);
- fprintf(logfile, "CRASH ALERT: ");
-
- va_start(ap, err);
- vfprintf(logfile, err, ap);
- va_end(ap);
-
- fprintf(logfile, "\n");
- fflush(logfile);
+ if (Appender* appender = GetAppenderByName(str))
+ {
+ logger.addAppender(appender->getId(), appender);
+ //fprintf(stdout, "Log::CreateLoggerFromConfig: Added Appender %s to Logger %s\n", appender->getName().c_str(), name); // DEBUG - RemoveMe
+ }
+ else
+ fprintf(stderr, "Error while configuring Appender %s in Logger %s. Appender does not exist", str.c_str(), name);
+ ss >> str;
}
- fflush(stderr);
}
-void Log::outError(const char * err, ...)
+void Log::ReadAppendersFromConfig()
{
- if (!err)
- return;
+ std::istringstream ss(ConfigMgr::GetStringDefault("Appenders", ""));
+ std::string name;
- if (m_enableLogDB)
+ do
{
- va_list ap2;
- va_start(ap2, err);
- char nnew_str[MAX_QUERY_LEN];
- vsnprintf(nnew_str, MAX_QUERY_LEN, err, ap2);
- outDB(LOG_TYPE_ERROR, nnew_str);
- va_end(ap2);
+ ss >> name;
+ CreateAppenderFromConfig(name.c_str());
+ name = "";
}
+ while (ss);
+}
- if (m_colored)
- SetColor(false, LRED);
-
- va_list ap;
-
- va_start(ap, err);
- vutf8printf(stderr, err, &ap);
- va_end(ap);
-
- if (m_colored)
- ResetColor(false);
+void Log::ReadLoggersFromConfig()
+{
+ std::istringstream ss(ConfigMgr::GetStringDefault("Loggers", ""));
+ std::string name;
- fprintf( stderr, "\n");
- if (logfile)
+ do
{
- outTimestamp(logfile);
- fprintf(logfile, "ERROR: ");
+ ss >> name;
+ CreateLoggerFromConfig(name.c_str());
+ name = "";
+ }
+ while (ss);
- va_start(ap, err);
- vfprintf(logfile, err, ap);
- va_end(ap);
+ LoggerMap::const_iterator it = loggers.begin();
- fprintf(logfile, "\n");
- fflush(logfile);
- }
- fflush(stderr);
+ while (it != loggers.end() && it->first)
+ ++it;
+
+ // root logger must exist. Marking as disabled as its not configured
+ if (it == loggers.end())
+ loggers[0].Create("root", LOG_FILTER_GENERAL, LOG_LEVEL_DISABLED);
}
-void Log::outArena(const char * str, ...)
+void Log::EnableDBAppenders()
{
- if (!str)
- return;
-
- if (arenaLogFile)
- {
- va_list ap;
- outTimestamp(arenaLogFile);
- va_start(ap, str);
- vfprintf(arenaLogFile, str, ap);
- fprintf(arenaLogFile, "\n");
- va_end(ap);
- fflush(arenaLogFile);
- }
+ for (AppenderMap::iterator it = appenders.begin(); it != appenders.end(); ++it)
+ if (it->second && it->second->getType() == APPENDER_DB)
+ ((AppenderDB *)it->second)->setEnable(true);
}
-void Log::outSQLDriver(const char* str, ...)
+void Log::log(LogFilterType filter, LogLevel level, char const* str, ...)
{
- if (!str)
+ if (!str || !ShouldLog(filter, level))
return;
va_list ap;
va_start(ap, str);
- vutf8printf(stdout, str, &ap);
- va_end(ap);
-
- printf("\n");
-
- if (sqlLogFile)
- {
- outTimestamp(sqlLogFile);
-
- va_list apSQL;
- va_start(apSQL, str);
- vfprintf(sqlLogFile, str, apSQL);
- va_end(apSQL);
- fprintf(sqlLogFile, "\n");
- fflush(sqlLogFile);
- }
+ vlog(filter, level, str, ap);
- fflush(stdout);
+ va_end(ap);
}
-void Log::outErrorDb(const char * err, ...)
+void Log::vlog(LogFilterType filter, LogLevel level, char const* str, va_list argptr)
{
- if (!err)
- return;
-
- if (m_colored)
- SetColor(false, LRED);
-
- va_list ap;
+ char text[MAX_QUERY_LEN];
+ vsnprintf(text, MAX_QUERY_LEN, str, argptr);
+ write(new LogMessage(level, filter, text));
+}
- va_start(ap, err);
- vutf8printf(stderr, err, &ap);
- va_end(ap);
+void Log::write(LogMessage* msg)
+{
+ msg->text.append("\n");
+ Logger* logger = GetLoggerByType(msg->type);
+ worker->enqueue(new LogOperation(logger, msg));
+}
- if (m_colored)
- ResetColor(false);
+std::string Log::GetTimestampStr()
+{
+ time_t t = time(NULL);
+ tm* aTm = localtime(&t);
+ // YYYY year
+ // MM month (2 digits 01-12)
+ // DD day (2 digits 01-31)
+ // HH hour (2 digits 00-23)
+ // MM minutes (2 digits 00-59)
+ // SS seconds (2 digits 00-59)
+ char buf[20];
+ snprintf(buf, 20, "%04d-%02d-%02d_%02d-%02d-%02d", aTm->tm_year+1900, aTm->tm_mon+1, aTm->tm_mday, aTm->tm_hour, aTm->tm_min, aTm->tm_sec);
+ return std::string(buf);
+}
- fprintf( stderr, "\n" );
+bool Log::SetLogLevel(std::string const& name, const char* newLevelc, bool isLogger /* = true */)
+{
+ LogLevel newLevel = LogLevel(atoi(newLevelc));
+ if (newLevel < 0)
+ return false;
- if (logfile)
+ if (isLogger)
{
- outTimestamp(logfile);
- fprintf(logfile, "ERROR: " );
+ LoggerMap::iterator it = loggers.begin();
+ while (it != loggers.end() && it->second.getName() != name)
+ ++it;
- va_start(ap, err);
- vfprintf(logfile, err, ap);
- va_end(ap);
+ if (it == loggers.end())
+ return false;
- fprintf(logfile, "\n" );
- fflush(logfile);
+ it->second.setLogLevel(newLevel);
}
-
- if (dberLogfile)
+ else
{
- outTimestamp(dberLogfile);
- va_start(ap, err);
- vfprintf(dberLogfile, err, ap);
- va_end(ap);
+ Appender* appender = GetAppenderByName(name);
+ if (!appender)
+ return false;
- fprintf(dberLogfile, "\n" );
- fflush(dberLogfile);
+ appender->setLogLevel(newLevel);
}
- fflush(stderr);
+ return true;
}
-void Log::outBasic(const char * str, ...)
+bool Log::ShouldLog(LogFilterType type, LogLevel level) const
{
- if (!str)
- return;
+ LoggerMap::const_iterator it = loggers.begin();
+ while (it != loggers.end() && it->second.getType() != type)
+ ++it;
- if (m_enableLogDB && m_dbLogLevel > LOGL_NORMAL)
+ if (it != loggers.end())
{
- va_list ap2;
- va_start(ap2, str);
- char nnew_str[MAX_QUERY_LEN];
- vsnprintf(nnew_str, MAX_QUERY_LEN, str, ap2);
- outDB(LOG_TYPE_BASIC, nnew_str);
- va_end(ap2);
+ LogLevel loggerLevel = it->second.getLogLevel();
+ return loggerLevel && loggerLevel <= level;
}
- if (m_logLevel > LOGL_NORMAL)
- {
- if (m_colored)
- SetColor(true, m_colors[LOGL_BASIC]);
-
- va_list ap;
- va_start(ap, str);
- vutf8printf(stdout, str, &ap);
- va_end(ap);
+ if (type != LOG_FILTER_GENERAL)
+ return ShouldLog(LOG_FILTER_GENERAL, level);
- if (m_colored)
- ResetColor(true);
-
- printf("\n");
-
- if (logfile)
- {
- outTimestamp(logfile);
- va_list ap2;
- va_start(ap2, str);
- vfprintf(logfile, str, ap2);
- fprintf(logfile, "\n" );
- va_end(ap2);
- fflush(logfile);
- }
- }
- fflush(stdout);
+ return false;
}
-void Log::outDetail(const char * str, ...)
+void Log::outTrace(LogFilterType filter, const char * str, ...)
{
- if (!str)
+ if (!str || !ShouldLog(filter, LOG_LEVEL_TRACE))
return;
- if (m_enableLogDB && m_dbLogLevel > LOGL_BASIC)
- {
- va_list ap2;
- va_start(ap2, str);
- char nnew_str[MAX_QUERY_LEN];
- vsnprintf(nnew_str, MAX_QUERY_LEN, str, ap2);
- outDB(LOG_TYPE_DETAIL, nnew_str);
- va_end(ap2);
- }
-
- if (m_logLevel > LOGL_BASIC)
- {
- if (m_colored)
- SetColor(true, m_colors[LOGL_DETAIL]);
-
- va_list ap;
- va_start(ap, str);
- vutf8printf(stdout, str, &ap);
- va_end(ap);
-
- if (m_colored)
- ResetColor(true);
-
- printf("\n");
+ va_list ap;
+ va_start(ap, str);
- if (logfile)
- {
- outTimestamp(logfile);
- va_list ap2;
- va_start(ap2, str);
- vfprintf(logfile, str, ap2);
- va_end(ap2);
-
- fprintf(logfile, "\n");
- fflush(logfile);
- }
- }
+ vlog(filter, LOG_LEVEL_TRACE, str, ap);
- fflush(stdout);
+ va_end(ap);
}
-void Log::outDebugInLine(const char * str, ...)
+void Log::outDebug(LogFilterType filter, const char * str, ...)
{
- if (!str)
+ if (!str || !ShouldLog(filter, LOG_LEVEL_DEBUG))
return;
- if (m_logLevel > LOGL_DETAIL)
- {
- va_list ap;
- va_start(ap, str);
- vutf8printf(stdout, str, &ap);
- va_end(ap);
+ va_list ap;
+ va_start(ap, str);
- //if (m_colored)
- // ResetColor(true);
+ vlog(filter, LOG_LEVEL_DEBUG, str, ap);
- if (logfile)
- {
- va_list ap2;
- va_start(ap2, str);
- vfprintf(logfile, str, ap2);
- va_end(ap2);
- }
- }
+ va_end(ap);
}
-void Log::outSQLDev(const char* str, ...)
+void Log::outInfo(LogFilterType filter, const char * str, ...)
{
- if (!str)
+ if (!str || !ShouldLog(filter, LOG_LEVEL_INFO))
return;
va_list ap;
va_start(ap, str);
- vutf8printf(stdout, str, &ap);
- va_end(ap);
-
- printf("\n");
- if (sqlDevLogFile)
- {
- va_list ap2;
- va_start(ap2, str);
- vfprintf(sqlDevLogFile, str, ap2);
- va_end(ap2);
-
- fprintf(sqlDevLogFile, "\n");
- fflush(sqlDevLogFile);
- }
+ vlog(filter, LOG_LEVEL_INFO, str, ap);
- fflush(stdout);
+ va_end(ap);
}
-void Log::outDebug(DebugLogFilters f, const char * str, ...)
+void Log::outWarn(LogFilterType filter, const char * str, ...)
{
- if (!(m_DebugLogMask & f))
- return;
-
- if (!str)
+ if (!str || !ShouldLog(filter, LOG_LEVEL_WARN))
return;
- if (m_enableLogDB && m_dbLogLevel > LOGL_DETAIL)
- {
- va_list ap2;
- va_start(ap2, str);
- char nnew_str[MAX_QUERY_LEN];
- vsnprintf(nnew_str, MAX_QUERY_LEN, str, ap2);
- outDB(LOG_TYPE_DEBUG, nnew_str);
- va_end(ap2);
- }
-
- if ( m_logLevel > LOGL_DETAIL )
- {
- if (m_colored)
- SetColor(true, m_colors[LOGL_DEBUG]);
-
- va_list ap;
- va_start(ap, str);
- vutf8printf(stdout, str, &ap);
- va_end(ap);
-
- if (m_colored)
- ResetColor(true);
+ va_list ap;
+ va_start(ap, str);
- printf( "\n" );
+ vlog(filter, LOG_LEVEL_WARN, str, ap);
- if (logfile)
- {
- outTimestamp(logfile);
- va_list ap2;
- va_start(ap2, str);
- vfprintf(logfile, str, ap2);
- va_end(ap2);
-
- fprintf(logfile, "\n" );
- fflush(logfile);
- }
- }
- fflush(stdout);
+ va_end(ap);
}
-void Log::outStaticDebug(const char * str, ...)
+void Log::outError(LogFilterType filter, const char * str, ...)
{
- if (!str)
+ if (!str || !ShouldLog(filter, LOG_LEVEL_ERROR))
return;
- if (m_enableLogDB && m_dbLogLevel > LOGL_DETAIL)
- {
- va_list ap2;
- va_start(ap2, str);
- char nnew_str[MAX_QUERY_LEN];
- vsnprintf(nnew_str, MAX_QUERY_LEN, str, ap2);
- outDB(LOG_TYPE_DEBUG, nnew_str);
- va_end(ap2);
- }
-
- if ( m_logLevel > LOGL_DETAIL )
- {
- if (m_colored)
- SetColor(true, m_colors[LOGL_DEBUG]);
-
- va_list ap;
- va_start(ap, str);
- vutf8printf(stdout, str, &ap);
- va_end(ap);
-
- if (m_colored)
- ResetColor(true);
+ va_list ap;
+ va_start(ap, str);
- printf( "\n" );
+ vlog(filter, LOG_LEVEL_ERROR, str, ap);
- if (logfile)
- {
- outTimestamp(logfile);
- va_list ap2;
- va_start(ap2, str);
- vfprintf(logfile, str, ap2);
- va_end(ap2);
-
- fprintf(logfile, "\n" );
- fflush(logfile);
- }
- }
- fflush(stdout);
+ va_end(ap);
}
-void Log::outStringInLine(const char * str, ...)
+void Log::outFatal(LogFilterType filter, const char * str, ...)
{
- if (!str)
+ if (!str || !ShouldLog(filter, LOG_LEVEL_FATAL))
return;
va_list ap;
-
va_start(ap, str);
- vutf8printf(stdout, str, &ap);
- va_end(ap);
-
- if (logfile)
- {
- va_start(ap, str);
- vfprintf(logfile, str, ap);
- va_end(ap);
- }
-}
-
-void Log::outCommand(uint32 account, const char * str, ...)
-{
- if (!str)
- return;
-
- // TODO: support accountid
- if (m_enableLogDB && m_dbGM)
- {
- va_list ap2;
- va_start(ap2, str);
- char nnew_str[MAX_QUERY_LEN];
- vsnprintf(nnew_str, MAX_QUERY_LEN, str, ap2);
- outDB(LOG_TYPE_GM, nnew_str);
- va_end(ap2);
- }
-
- if (m_logLevel > LOGL_NORMAL)
- {
- if (m_colored)
- SetColor(true, m_colors[LOGL_BASIC]);
-
- va_list ap;
- va_start(ap, str);
- vutf8printf(stdout, str, &ap);
- va_end(ap);
-
- if (m_colored)
- ResetColor(true);
-
- printf("\n");
-
- if (logfile)
- {
- outTimestamp(logfile);
- va_list ap2;
- va_start(ap2, str);
- vfprintf(logfile, str, ap2);
- fprintf(logfile, "\n" );
- va_end(ap2);
- fflush(logfile);
- }
- }
- if (m_gmlog_per_account)
- {
- if (FILE* per_file = openGmlogPerAccount (account))
- {
- outTimestamp(per_file);
- va_list ap;
- va_start(ap, str);
- vfprintf(per_file, str, ap);
- fprintf(per_file, "\n" );
- va_end(ap);
- fclose(per_file);
- }
- }
- else if (gmLogfile)
- {
- outTimestamp(gmLogfile);
- va_list ap;
- va_start(ap, str);
- vfprintf(gmLogfile, str, ap);
- fprintf(gmLogfile, "\n" );
- va_end(ap);
- fflush(gmLogfile);
- }
+ vlog(filter, LOG_LEVEL_FATAL, str, ap);
- fflush(stdout);
+ va_end(ap);
}
-void Log::outChar(const char * str, ...)
+void Log::outCommand(uint32 account, const char * str, ...)
{
- if (!str)
+ if (!str || !ShouldLog(LOG_FILTER_GMCOMMAND, LOG_LEVEL_INFO))
return;
- if (m_enableLogDB && m_dbChar)
- {
- va_list ap2;
- va_start(ap2, str);
- char nnew_str[MAX_QUERY_LEN];
- vsnprintf(nnew_str, MAX_QUERY_LEN, str, ap2);
- outDB(LOG_TYPE_CHAR, nnew_str);
- va_end(ap2);
- }
+ va_list ap;
+ va_start(ap, str);
+ char text[MAX_QUERY_LEN];
+ vsnprintf(text, MAX_QUERY_LEN, str, ap);
+ va_end(ap);
- if (charLogfile)
- {
- outTimestamp(charLogfile);
- va_list ap;
- va_start(ap, str);
- vfprintf(charLogfile, str, ap);
- fprintf(charLogfile, "\n" );
- va_end(ap);
- fflush(charLogfile);
- }
-}
+ LogMessage* msg = new LogMessage(LOG_LEVEL_INFO, LOG_FILTER_GMCOMMAND, text);
+ msg->param1 = account;
-void Log::outCharDump(const char * str, uint32 account_id, uint32 guid, const char * name)
-{
- FILE* file = NULL;
- if (m_charLog_Dump_Separate)
- {
- char fileName[29]; // Max length: name(12) + guid(11) + _.log (5) + \0
- snprintf(fileName, 29, "%d_%s.log", guid, name);
- std::string sFileName(m_dumpsDir);
- sFileName.append(fileName);
- file = fopen((m_logsDir + sFileName).c_str(), "w");
- }
- else
- file = charLogfile;
- if (file)
- {
- fprintf(file, "== START DUMP == (account: %u guid: %u name: %s )\n%s\n== END DUMP ==\n",
- account_id, guid, name, str);
- fflush(file);
- if (m_charLog_Dump_Separate)
- fclose(file);
- }
+ write(msg);
}
-void Log::outOpCode(uint32 op, const char * name, bool smsg)
+void Log::outOpCode(uint32 op, const char* name, bool smsg)
{
- if (!(m_DebugLogMask & LOG_FILTER_OPCODES))
+ if (!ShouldLog(LOG_FILTER_OPCODES, LOG_LEVEL_DEBUG))
return;
- outString("%s: %s 0x%.4X (%u)", smsg ? "S->C" : "C->S", name, op, op);
+
+ outInfo(LOG_FILTER_OPCODES, "%s: %s 0x%.4X (%u)", smsg ? "S->C" : "C->S", name, op, op);
}
-void Log::outRemote(const char * str, ...)
+void Log::SetRealmID(uint32 id)
{
- if (!str)
- return;
-
- if (m_enableLogDB && m_dbRA)
- {
- va_list ap2;
- va_start(ap2, str);
- char nnew_str[MAX_QUERY_LEN];
- vsnprintf(nnew_str, MAX_QUERY_LEN, str, ap2);
- outDB(LOG_TYPE_RA, nnew_str);
- va_end(ap2);
- }
-
- if (raLogfile)
- {
- outTimestamp(raLogfile);
- va_list ap;
- va_start(ap, str);
- vfprintf(raLogfile, str, ap);
- fprintf(raLogfile, "\n" );
- va_end(ap);
- fflush(raLogfile);
- }
+ realm = id;
}
-void Log::outChat(const char * str, ...)
+void Log::Close()
{
- if (!str)
- return;
-
- if (m_enableLogDB && m_dbChat)
+ for (AppenderMap::iterator it = appenders.begin(); it != appenders.end(); ++it)
{
- va_list ap2;
- va_start(ap2, str);
- char nnew_str[MAX_QUERY_LEN];
- vsnprintf(nnew_str, MAX_QUERY_LEN, str, ap2);
- outDB(LOG_TYPE_CHAT, nnew_str);
- va_end(ap2);
- }
-
- if (chatLogfile)
- {
- outTimestamp(chatLogfile);
- va_list ap;
- va_start(ap, str);
- vfprintf(chatLogfile, str, ap);
- fprintf(chatLogfile, "\n" );
- fflush(chatLogfile);
- va_end(ap);
+ delete it->second;
+ it->second = NULL;
}
+ appenders.clear();
+ loggers.clear();
+ delete worker;
+ worker = NULL;
}
-void Log::outErrorST(const char * str, ...)
+void Log::LoadFromConfig()
{
- va_list ap;
- va_start(ap, str);
- char nnew_str[MAX_QUERY_LEN];
- vsnprintf(nnew_str, MAX_QUERY_LEN, str, ap);
- va_end(ap);
-
- ACE_Stack_Trace st;
- outError("%s [Stacktrace: %s]", nnew_str, st.c_str());
-}
-
-void Log::outWarden(const char * str, ...)
-{
- if (!str)
- return;
-
- if (wardenLogFile)
- {
- outTimestamp(wardenLogFile);
- va_list ap;
- va_start(ap, str);
- vfprintf(wardenLogFile, str, ap);
- fprintf(wardenLogFile, "\n" );
- fflush(wardenLogFile);
- va_end(ap);
- }
+ Close();
+ AppenderId = 0;
+ m_logsDir = ConfigMgr::GetStringDefault("LogsDir", "");
+ if (!m_logsDir.empty())
+ if ((m_logsDir.at(m_logsDir.length() - 1) != '/') && (m_logsDir.at(m_logsDir.length() - 1) != '\\'))
+ m_logsDir.push_back('/');
+ ReadAppendersFromConfig();
+ ReadLoggersFromConfig();
+ worker = new LogWorker();
}
diff --git a/src/server/shared/Logging/Log.h b/src/server/shared/Logging/Log.h
index e32ea7765a9..898db43a883 100755..100644
--- a/src/server/shared/Logging/Log.h
+++ b/src/server/shared/Logging/Log.h
@@ -19,198 +19,71 @@
#ifndef TRINITYCORE_LOG_H
#define TRINITYCORE_LOG_H
-#include "Common.h"
-#include <ace/Singleton.h>
-
-class Config;
-
-enum DebugLogFilters
-{
- LOG_FILTER_NONE = 0x00000000,
- LOG_FILTER_UNITS = 0x00000001, // Anything related to units that doesn't fit in other categories. ie. creature formations
- LOG_FILTER_PETS = 0x00000002,
- LOG_FILTER_VEHICLES = 0x00000004,
- LOG_FILTER_TSCR = 0x00000008, // C++ AI, instance scripts, etc.
- LOG_FILTER_DATABASE_AI = 0x00000010, // SmartAI, EventAI, CreatureAI
- LOG_FILTER_MAPSCRIPTS = 0x00000020,
- LOG_FILTER_NETWORKIO = 0x00000040, // Anything packet/netcode related
- LOG_FILTER_SPELLS_AURAS = 0x00000080,
- LOG_FILTER_ACHIEVEMENTSYS = 0x00000100,
- LOG_FILTER_CONDITIONSYS = 0x00000200,
- LOG_FILTER_POOLSYS = 0x00000400,
- LOG_FILTER_AUCTIONHOUSE = 0x00000800,
- LOG_FILTER_BATTLEGROUND = 0x00001000, // Anything related to arena's and battlegrounds
- LOG_FILTER_OUTDOORPVP = 0x00002000,
- LOG_FILTER_CHATSYS = 0x00004000,
- LOG_FILTER_LFG = 0x00008000,
- LOG_FILTER_MAPS = 0x00010000, // Maps, instances, grids, cells, visibility
- LOG_FILTER_PLAYER_LOADING = 0x00020000, // Debug output from Player::_Load functions
- LOG_FILTER_PLAYER_ITEMS = 0x00040000, // Anything item related
- LOG_FILTER_PLAYER_SKILLS = 0x00080000, // Skills related
- LOG_FILTER_LOOT = 0x00100000, // Loot related
- LOG_FILTER_GUILD = 0x00200000, // Guild related
- LOG_FILTER_TRANSPORTS = 0x00400000, // Transport related
- LOG_FILTER_WARDEN = 0x00800000, // Warden related
- LOG_FILTER_OPCODES = 0x01000000, // OpCodes
-};
-
-enum LogTypes
-{
- LOG_TYPE_STRING = 0,
- LOG_TYPE_ERROR = 1,
- LOG_TYPE_BASIC = 2,
- LOG_TYPE_DETAIL = 3,
- LOG_TYPE_DEBUG = 4,
- LOG_TYPE_CHAR = 5,
- LOG_TYPE_WORLD = 6,
- LOG_TYPE_RA = 7,
- LOG_TYPE_GM = 8,
- LOG_TYPE_CRASH = 9,
- LOG_TYPE_CHAT = 10,
- MAX_LOG_TYPES
-};
-
-enum LogLevel
-{
- LOGL_NORMAL = 0,
- LOGL_BASIC,
- LOGL_DETAIL,
- LOGL_DEBUG
-};
-
-const int LogLevels = int(LOGL_DEBUG)+1;
+#include "Define.h"
+#include "Appender.h"
+#include "LogWorker.h"
+#include "Logger.h"
-enum ColorTypes
-{
- BLACK,
- RED,
- GREEN,
- BROWN,
- BLUE,
- MAGENTA,
- CYAN,
- GREY,
- YELLOW,
- LRED,
- LGREEN,
- LBLUE,
- LMAGENTA,
- LCYAN,
- WHITE
-};
+#include <ace/Singleton.h>
-const int Colors = int(WHITE)+1;
+#include <string>
+#include <set>
class Log
{
friend class ACE_Singleton<Log, ACE_Thread_Mutex>;
+ typedef std::map<uint8, Logger> LoggerMap;
+
private:
Log();
~Log();
public:
- void Initialize();
-
- void ReloadConfig();
-
- void InitColors(const std::string& init_str);
- void SetColor(bool stdout_stream, ColorTypes color);
- void ResetColor(bool stdout_stream);
-
- void outErrorST(const char * err, ...) ATTR_PRINTF(2, 3);
- void outDB(LogTypes type, const char * str);
- void outString(const char * str, ...) ATTR_PRINTF(2, 3);
- void outString();
- void outStringInLine(const char * str, ...) ATTR_PRINTF(2, 3);
- void outError(const char * err, ...) ATTR_PRINTF(2, 3);
- void outCrash(const char * err, ...) ATTR_PRINTF(2, 3);
- void outBasic(const char * str, ...) ATTR_PRINTF(2, 3);
- void outDetail(const char * str, ...) ATTR_PRINTF(2, 3);
- void outSQLDev(const char * str, ...) ATTR_PRINTF(2, 3);
- void outDebug(DebugLogFilters f, const char* str, ...) ATTR_PRINTF(3, 4);
- void outStaticDebug(const char * str, ...) ATTR_PRINTF(2, 3);
- void outDebugInLine(const char * str, ...) ATTR_PRINTF(2, 3);
- void outErrorDb(const char * str, ...) ATTR_PRINTF(2, 3);
- void outChar(const char * str, ...) ATTR_PRINTF(2, 3);
- void outCommand(uint32 account, const char * str, ...) ATTR_PRINTF(3, 4);
- void outRemote(const char * str, ...) ATTR_PRINTF(2, 3);
- void outChat(const char * str, ...) ATTR_PRINTF(2, 3);
- void outArena(const char * str, ...) ATTR_PRINTF(2, 3);
- void outSQLDriver(const char* str, ...) ATTR_PRINTF(2, 3);
- void outWarden(const char * str, ...) ATTR_PRINTF(2, 3);
- void outCharDump(const char * str, uint32 account_id, uint32 guid, const char * name);
- void outOpCode(uint32 op, const char * name, bool smsg = true);
-
- static void outTimestamp(FILE* file);
+ void LoadFromConfig();
+ void Close();
+ bool ShouldLog(LogFilterType type, LogLevel level) const;
+ bool SetLogLevel(std::string const& name, char const* level, bool isLogger = true);
+
+ void log(LogFilterType f, LogLevel level, char const* str, ...) ATTR_PRINTF(4,5);
+
+ void outTrace(LogFilterType f, char const* str, ...) ATTR_PRINTF(3,4);
+ void outDebug(LogFilterType f, char const* str, ...) ATTR_PRINTF(3,4);
+ void outInfo(LogFilterType f, char const* str, ...) ATTR_PRINTF(3,4);
+ void outWarn(LogFilterType f, char const* str, ...) ATTR_PRINTF(3,4);
+ void outError(LogFilterType f, char const* str, ...) ATTR_PRINTF(3,4);
+ void outFatal(LogFilterType f, char const* str, ...) ATTR_PRINTF(3,4);
+ void outOpCode(uint32 op, const char* name, bool smsg);
+
+ void EnableDBAppenders();
+ void outCommand(uint32 account, const char * str, ...) ATTR_PRINTF(3, 4);
static std::string GetTimestampStr();
- void SetLogLevel(char * Level);
- void SetLogFileLevel(char * Level);
- void SetDBLogLevel(char * Level);
- void SetSQLDriverQueryLogging(bool newStatus) { m_sqlDriverQueryLogging = newStatus; }
- void SetRealmID(uint32 id) { realm = id; }
-
- bool IsOutDebug() const { return m_logLevel > 2 || (m_logFileLevel > 2 && logfile); }
- bool IsOutCharDump() const { return m_charLog_Dump; }
+ void SetRealmID(uint32 id);
- bool GetLogDB() const { return m_enableLogDB; }
- bool GetLogDBLater() const { return m_enableLogDBLater; }
- void SetLogDB(bool enable) { m_enableLogDB = enable; }
- void SetLogDBLater(bool value) { m_enableLogDBLater = value; }
- bool GetSQLDriverQueryLogging() const { return m_sqlDriverQueryLogging; }
private:
- FILE* openLogFile(char const* configFileName, char const* configTimeStampFlag, char const* mode);
- FILE* openGmlogPerAccount(uint32 account);
-
- FILE* raLogfile;
- FILE* logfile;
- FILE* gmLogfile;
- FILE* charLogfile;
- FILE* dberLogfile;
- FILE* chatLogfile;
- FILE* arenaLogFile;
- FILE* sqlLogFile;
- FILE* sqlDevLogFile;
- FILE* wardenLogFile;
-
- // cache values for after initilization use (like gm log per account case)
+ void vlog(LogFilterType f, LogLevel level, char const* str, va_list argptr);
+ void write(LogMessage* msg);
+
+ Logger* GetLoggerByType(LogFilterType filter);
+ Appender* GetAppenderByName(std::string const& name);
+ uint8 NextAppenderId();
+ void CreateAppenderFromConfig(const char* name);
+ void CreateLoggerFromConfig(const char* name);
+ void ReadAppendersFromConfig();
+ void ReadLoggersFromConfig();
+
+ AppenderMap appenders;
+ LoggerMap loggers;
+ uint8 AppenderId;
+
std::string m_logsDir;
std::string m_logsTimestamp;
- // gm log control
- bool m_gmlog_per_account;
- std::string m_gmlog_filename_format;
-
- bool m_enableLogDBLater;
- bool m_enableLogDB;
uint32 realm;
-
- // log coloring
- bool m_colored;
- ColorTypes m_colors[4];
-
- // log levels:
- // false: errors only, true: full query logging
- bool m_sqlDriverQueryLogging;
-
- // log levels:
- // 0 minimum/string, 1 basic/error, 2 detail, 3 full/debug
- uint8 m_dbLogLevel;
- uint8 m_logLevel;
- uint8 m_logFileLevel;
- bool m_dbChar;
- bool m_dbRA;
- bool m_dbGM;
- bool m_dbChat;
- bool m_charLog_Dump;
- bool m_charLog_Dump_Separate;
- std::string m_dumpsDir;
-
- DebugLogFilters m_DebugLogMask;
+ LogWorker* worker;
};
#define sLog ACE_Singleton<Log, ACE_Thread_Mutex>::instance()
#endif
-
diff --git a/src/server/shared/Logging/LogOperation.cpp b/src/server/shared/Logging/LogOperation.cpp
new file mode 100644
index 00000000000..b36dd3a8b1e
--- /dev/null
+++ b/src/server/shared/Logging/LogOperation.cpp
@@ -0,0 +1,31 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "LogOperation.h"
+#include "Logger.h"
+
+LogOperation::~LogOperation()
+{
+ delete msg;
+}
+
+int LogOperation::call()
+{
+ if (logger && msg)
+ logger->write(*msg);
+ return 0;
+}
diff --git a/src/server/shared/Logging/LogOperation.h b/src/server/shared/Logging/LogOperation.h
new file mode 100644
index 00000000000..d872670d756
--- /dev/null
+++ b/src/server/shared/Logging/LogOperation.h
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef LOGOPERATION_H
+#define LOGOPERATION_H
+
+class Logger;
+struct LogMessage;
+
+class LogOperation
+{
+ public:
+ LogOperation(Logger* _logger, LogMessage* _msg)
+ : logger(_logger)
+ , msg(_msg)
+ { }
+
+ ~LogOperation();
+
+ int call();
+
+ protected:
+ Logger *logger;
+ LogMessage *msg;
+};
+
+#endif
diff --git a/src/server/shared/Logging/LogWorker.cpp b/src/server/shared/Logging/LogWorker.cpp
new file mode 100644
index 00000000000..a12faaf224c
--- /dev/null
+++ b/src/server/shared/Logging/LogWorker.cpp
@@ -0,0 +1,50 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "LogWorker.h"
+
+LogWorker::LogWorker()
+ : m_queue(HIGH_WATERMARK, LOW_WATERMARK)
+{
+ ACE_Task_Base::activate(THR_NEW_LWP | THR_JOINABLE | THR_INHERIT_SCHED, 1);
+}
+
+LogWorker::~LogWorker()
+{
+ m_queue.deactivate();
+ wait();
+}
+
+int LogWorker::enqueue(LogOperation* op)
+{
+ return m_queue.enqueue(op);
+}
+
+int LogWorker::svc()
+{
+ while (1)
+ {
+ LogOperation* request;
+ if (m_queue.dequeue(request) == -1)
+ break;
+
+ request->call();
+ delete request;
+ }
+
+ return 0;
+}
diff --git a/src/server/shared/Logging/LogWorker.h b/src/server/shared/Logging/LogWorker.h
new file mode 100644
index 00000000000..ea1744f9790
--- /dev/null
+++ b/src/server/shared/Logging/LogWorker.h
@@ -0,0 +1,47 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef LOGWORKER_H
+#define LOGWORKER_H
+
+#include "LogOperation.h"
+
+#include <ace/Task.h>
+#include <ace/Activation_Queue.h>
+
+class LogWorker: protected ACE_Task_Base
+{
+ public:
+ LogWorker();
+ ~LogWorker();
+
+ typedef ACE_Message_Queue_Ex<LogOperation, ACE_MT_SYNCH> LogMessageQueueType;
+
+ enum
+ {
+ HIGH_WATERMARK = 8 * 1024 * 1024,
+ LOW_WATERMARK = 8 * 1024 * 1024
+ };
+
+ int enqueue(LogOperation *op);
+
+ private:
+ virtual int svc();
+ LogMessageQueueType m_queue;
+};
+
+#endif
diff --git a/src/server/shared/Logging/Logger.cpp b/src/server/shared/Logging/Logger.cpp
new file mode 100644
index 00000000000..10276eb3acb
--- /dev/null
+++ b/src/server/shared/Logging/Logger.cpp
@@ -0,0 +1,84 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "Logger.h"
+
+Logger::Logger(): name(""), type(LOG_FILTER_GENERAL), level(LOG_LEVEL_DISABLED)
+{
+}
+
+void Logger::Create(std::string const& _name, LogFilterType _type, LogLevel _level)
+{
+ name = _name;
+ type = _type;
+ level = _level;
+}
+
+Logger::~Logger()
+{
+ for (AppenderMap::iterator it = appenders.begin(); it != appenders.end(); ++it)
+ it->second = NULL;
+ appenders.clear();
+}
+
+std::string const& Logger::getName() const
+{
+ return name;
+}
+
+LogFilterType Logger::getType() const
+{
+ return type;
+}
+
+LogLevel Logger::getLogLevel() const
+{
+ return level;
+}
+
+void Logger::addAppender(uint8 id, Appender* appender)
+{
+ appenders[id] = appender;
+}
+
+void Logger::delAppender(uint8 id)
+{
+ AppenderMap::iterator it = appenders.find(id);
+ if (it != appenders.end())
+ {
+ it->second = NULL;
+ appenders.erase(it);
+ }
+}
+
+void Logger::setLogLevel(LogLevel _level)
+{
+ level = _level;
+}
+
+void Logger::write(LogMessage& message)
+{
+ if (!level || level > message.level || message.text.empty())
+ {
+ //fprintf(stderr, "Logger::write: Logger %s, Level %u. Msg %s Level %u WRONG LEVEL MASK OR EMPTY MSG\n", getName().c_str(), messge.level, message.text.c_str(), .message.level); // DEBUG - RemoveMe
+ return;
+ }
+
+ for (AppenderMap::iterator it = appenders.begin(); it != appenders.end(); ++it)
+ if (it->second)
+ it->second->write(message);
+}
diff --git a/src/server/shared/Logging/Logger.h b/src/server/shared/Logging/Logger.h
new file mode 100644
index 00000000000..9d13f08620f
--- /dev/null
+++ b/src/server/shared/Logging/Logger.h
@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2008-2012 TrinityCore <http://www.trinitycore.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef LOGGER_H
+#define LOGGER_H
+
+#include "Appender.h"
+
+class Logger
+{
+ public:
+ Logger();
+ ~Logger();
+
+ void Create(std::string const& name, LogFilterType type, LogLevel level);
+ void addAppender(uint8 type, Appender *);
+ void delAppender(uint8 type);
+
+ std::string const& getName() const;
+ LogFilterType getType() const;
+ LogLevel getLogLevel() const;
+ void setLogLevel(LogLevel level);
+ void write(LogMessage& message);
+
+ private:
+ std::string name;
+ LogFilterType type;
+ LogLevel level;
+ AppenderMap appenders;
+};
+
+#endif
diff --git a/src/server/shared/Packets/ByteBuffer.h b/src/server/shared/Packets/ByteBuffer.h
index a86a3524cbc..51c253057d2 100755
--- a/src/server/shared/Packets/ByteBuffer.h
+++ b/src/server/shared/Packets/ByteBuffer.h
@@ -52,8 +52,10 @@ class ByteBufferPositionException : public ByteBufferException
protected:
void PrintError() const
{
- sLog->outError("Attempted to %s value with size: "SIZEFMTD" in ByteBuffer (pos: " SIZEFMTD " size: "SIZEFMTD") " ,
- (_add ? "put" : "get"), ValueSize, Pos, Size);
+ ACE_Stack_Trace trace;
+
+ sLog->outError(LOG_FILTER_GENERAL, "Attempted to %s value with size: "SIZEFMTD" in ByteBuffer (pos: " SIZEFMTD " size: "SIZEFMTD")\n[Stacktrace: %s]" ,
+ (_add ? "put" : "get"), ValueSize, Pos, Size, trace.c_str());
}
private:
@@ -72,8 +74,10 @@ class ByteBufferSourceException : public ByteBufferException
protected:
void PrintError() const
{
- sLog->outError("Attempted to put a %s in ByteBuffer (pos: "SIZEFMTD" size: "SIZEFMTD")",
- (ValueSize > 0 ? "NULL-pointer" : "zero-sized value"), Pos, Size);
+ ACE_Stack_Trace trace;
+
+ sLog->outError(LOG_FILTER_GENERAL, "Attempted to put a %s in ByteBuffer (pos: "SIZEFMTD" size: "SIZEFMTD")\n[Stacktrace: %s]",
+ (ValueSize > 0 ? "NULL-pointer" : "zero-sized value"), Pos, Size, trace.c_str());
}
};
@@ -540,79 +544,65 @@ class ByteBuffer
void print_storage() const
{
- if (!sLog->IsOutDebug()) // optimize disabled debug output
+ if (!sLog->ShouldLog(LOG_FILTER_NETWORKIO, LOG_LEVEL_TRACE)) // optimize disabled debug output
return;
- sLog->outDebug(LOG_FILTER_NETWORKIO, "STORAGE_SIZE: %lu", (unsigned long)size() );
+ std::ostringstream o;
+ o << "STORAGE_SIZE: " << size();
for (uint32 i = 0; i < size(); ++i)
- sLog->outDebugInLine("%u - ", read<uint8>(i) );
- sLog->outDebug(LOG_FILTER_NETWORKIO, " ");
+ o << read<uint8>(i) << " - ";
+ o << " ";
+
+ sLog->outTrace(LOG_FILTER_NETWORKIO, "%s", o.str().c_str());
}
void textlike() const
{
- if (!sLog->IsOutDebug()) // optimize disabled debug output
+ if (!sLog->ShouldLog(LOG_FILTER_NETWORKIO, LOG_LEVEL_TRACE)) // optimize disabled debug output
return;
- sLog->outDebug(LOG_FILTER_NETWORKIO, "STORAGE_SIZE: %lu", (unsigned long)size() );
+ std::ostringstream o;
+ o << "STORAGE_SIZE: " << size();
for (uint32 i = 0; i < size(); ++i)
- sLog->outDebugInLine("%c", read<uint8>(i) );
- sLog->outDebug(LOG_FILTER_NETWORKIO, " ");
+ {
+ char buf[1];
+ snprintf(buf, 1, "%c", read<uint8>(i));
+ o << buf;
+ }
+ o << " ";
+ sLog->outTrace(LOG_FILTER_NETWORKIO, "%s", o.str().c_str());
}
void hexlike() const
{
- if (!sLog->IsOutDebug()) // optimize disabled debug output
+ if (!sLog->ShouldLog(LOG_FILTER_NETWORKIO, LOG_LEVEL_TRACE)) // optimize disabled debug output
return;
uint32 j = 1, k = 1;
- sLog->outDebug(LOG_FILTER_NETWORKIO, "STORAGE_SIZE: %lu", (unsigned long)size() );
+
+ std::ostringstream o;
+ o << "STORAGE_SIZE: " << size();
for (uint32 i = 0; i < size(); ++i)
{
+ char buf[3];
+ snprintf(buf, 1, "%2X ", read<uint8>(i));
if ((i == (j * 8)) && ((i != (k * 16))))
{
- if (read<uint8>(i) < 0x10)
- {
- sLog->outDebugInLine("| 0%X ", read<uint8>(i) );
- }
- else
- {
- sLog->outDebugInLine("| %X ", read<uint8>(i) );
- }
+ o << "| ";
++j;
}
else if (i == (k * 16))
{
- if (read<uint8>(i) < 0x10)
- {
- sLog->outDebugInLine("\n");
-
- sLog->outDebugInLine("0%X ", read<uint8>(i) );
- }
- else
- {
- sLog->outDebugInLine("\n");
-
- sLog->outDebugInLine("%X ", read<uint8>(i) );
- }
-
+ o << "\n";
++k;
++j;
}
- else
- {
- if (read<uint8>(i) < 0x10)
- {
- sLog->outDebugInLine("0%X ", read<uint8>(i) );
- }
- else
- {
- sLog->outDebugInLine("%X ", read<uint8>(i) );
- }
- }
+
+ o << buf;
}
- sLog->outDebugInLine("\n");
+ o << " ";
+ sLog->outTrace(LOG_FILTER_NETWORKIO, "%s", o.str().c_str());
}
protected:
diff --git a/src/server/shared/Utilities/ServiceWin32.cpp b/src/server/shared/Utilities/ServiceWin32.cpp
index f2887a4d1bd..c6e9d385be3 100755
--- a/src/server/shared/Utilities/ServiceWin32.cpp
+++ b/src/server/shared/Utilities/ServiceWin32.cpp
@@ -257,7 +257,7 @@ bool WinServiceRun()
if (!StartServiceCtrlDispatcher(serviceTable))
{
- sLog->outError("StartService Failed. Error [%u]", ::GetLastError());
+ sLog->outError(LOG_FILTER_GENERAL, "StartService Failed. Error [%u]", ::GetLastError());
return false;
}
return true;