aboutsummaryrefslogtreecommitdiff
path: root/src/mangosd
diff options
context:
space:
mode:
Diffstat (limited to 'src/mangosd')
-rw-r--r--src/mangosd/CMakeLists.txt53
-rw-r--r--src/mangosd/CliRunnable.cpp366
-rw-r--r--src/mangosd/CliRunnable.h35
-rw-r--r--src/mangosd/Main.cpp165
-rw-r--r--src/mangosd/Makefile.am62
-rw-r--r--src/mangosd/Master.cpp517
-rw-r--r--src/mangosd/Master.h52
-rw-r--r--src/mangosd/RASocket.cpp259
-rw-r--r--src/mangosd/RASocket.h67
-rw-r--r--src/mangosd/TrinityCore.icobin0 -> 136606 bytes
-rw-r--r--src/mangosd/WorldRunnable.cpp86
-rw-r--r--src/mangosd/WorldRunnable.h35
-rw-r--r--src/mangosd/mangosd.conf.dist.in1352
-rw-r--r--src/mangosd/mangosd.rc85
-rw-r--r--src/mangosd/monitor-mangosd18
-rw-r--r--src/mangosd/resource.h15
-rw-r--r--src/mangosd/run-mangosd14
17 files changed, 3181 insertions, 0 deletions
diff --git a/src/mangosd/CMakeLists.txt b/src/mangosd/CMakeLists.txt
new file mode 100644
index 00000000000..dc5941ef4e2
--- /dev/null
+++ b/src/mangosd/CMakeLists.txt
@@ -0,0 +1,53 @@
+
+########### next target ###############
+
+SET(trinity-core_SRCS
+CliRunnable.cpp
+CliRunnable.h
+Main.cpp
+Master.cpp
+Master.h
+RASocket.cpp
+RASocket.h
+WorldRunnable.cpp
+WorldRunnable.h
+)
+
+add_executable(trinity-core ${trinity-core_SRCS})
+add_definitions(
+-D_TRINITY_CORE_CONFIG='"${CONF_DIR}/trinitycore.conf"'
+)
+IF (DO_MYSQL)
+ SET_TARGET_PROPERTIES(trinity-core PROPERTIES LINK_FLAGS "-pthread")
+ENDIF(DO_MYSQL)
+
+
+
+target_link_libraries(
+trinity-core
+game
+shared
+zlib
+trinityframework
+trinitysockets
+trinitydatabase
+trinityauth
+trinityconfig
+vmaps
+ZThread
+g3dlite
+${SCRIPT_LIB}
+${MYSQL_LIBRARIES}
+${POSTGRE_LIBS}
+${SSLLIB}
+${ACE_LIBRARY}
+${ZLIB}
+)
+
+install(TARGETS trinity-core DESTINATION bin)
+
+
+########### install files ###############
+
+install(FILES mangosd.conf.dist.in DESTINATION etc)
+
diff --git a/src/mangosd/CliRunnable.cpp b/src/mangosd/CliRunnable.cpp
new file mode 100644
index 00000000000..7193fa705a0
--- /dev/null
+++ b/src/mangosd/CliRunnable.cpp
@@ -0,0 +1,366 @@
+/*
+ * Copyright (C) 2005-2008 MaNGOS <http://www.mangosproject.org/>
+ *
+ * Copyright (C) 2008 Trinity <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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/// \addtogroup Trinityd
+/// @{
+/// \file
+
+#include "Common.h"
+#include "Language.h"
+#include "Log.h"
+#include "World.h"
+#include "ScriptCalls.h"
+#include "ObjectMgr.h"
+#include "WorldSession.h"
+#include "Config/ConfigEnv.h"
+#include "Util.h"
+#include "AccountMgr.h"
+#include "CliRunnable.h"
+#include "MapManager.h"
+#include "Player.h"
+#include "Chat.h"
+
+void utf8print(const char* str)
+{
+#if PLATFORM == PLATFORM_WINDOWS
+ wchar_t wtemp_buf[6000];
+ size_t wtemp_len = 6000-1;
+ if(!Utf8toWStr(str,strlen(str),wtemp_buf,wtemp_len))
+ return;
+
+ char temp_buf[6000];
+ CharToOemBuffW(&wtemp_buf[0],&temp_buf[0],wtemp_len+1);
+ printf(temp_buf);
+#else
+ printf(str);
+#endif
+}
+
+/// Delete a user account and all associated characters in this realm
+/// \todo This function has to be enhanced to respect the login/realm split (delete char, delete account chars in realm, delete account chars in realm then delete account
+bool ChatHandler::HandleAccountDeleteCommand(const char* args)
+{
+ if(!*args)
+ return false;
+
+ ///- Get the account name from the command line
+ char *account_name_str=strtok ((char*)args," ");
+ if (!account_name_str)
+ return false;
+
+ std::string account_name = account_name_str;
+ if(!AccountMgr::normilizeString(account_name))
+ {
+ PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
+ SetSentErrorMessage(true);
+ return false;
+ }
+
+ uint32 account_id = accmgr.GetId(account_name);
+ if(!account_id)
+ {
+ PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
+ SetSentErrorMessage(true);
+ return false;
+ }
+
+ /// Commands not recommended call from chat, but support anyway
+ /// can delete only for account with less security
+ /// This is also reject self apply in fact
+ if(HasLowerSecurityAccount (NULL,account_id,true))
+ return false;
+
+ AccountOpResult result = accmgr.DeleteAccount(account_id);
+ switch(result)
+ {
+ case AOR_OK:
+ PSendSysMessage(LANG_ACCOUNT_DELETED,account_name.c_str());
+ break;
+ case AOR_NAME_NOT_EXIST:
+ PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
+ SetSentErrorMessage(true);
+ return false;
+ case AOR_DB_INTERNAL_ERROR:
+ PSendSysMessage(LANG_ACCOUNT_NOT_DELETED_SQL_ERROR,account_name.c_str());
+ SetSentErrorMessage(true);
+ return false;
+ default:
+ PSendSysMessage(LANG_ACCOUNT_NOT_DELETED,account_name.c_str());
+ SetSentErrorMessage(true);
+ return false;
+ }
+
+ return true;
+}
+
+bool ChatHandler::HandleCharacterDeleteCommand(const char* args)
+{
+ if(!*args)
+ return false;
+
+ char *character_name_str = strtok((char*)args," ");
+ if(!character_name_str)
+ return false;
+
+ std::string character_name = character_name_str;
+ if(!normalizePlayerName(character_name))
+ return false;
+
+ uint64 character_guid;
+ uint32 account_id;
+
+ Player *player = objmgr.GetPlayer(character_name.c_str());
+ if(player)
+ {
+ character_guid = player->GetGUID();
+ account_id = player->GetSession()->GetAccountId();
+ player->GetSession()->KickPlayer();
+ }
+ else
+ {
+ character_guid = objmgr.GetPlayerGUIDByName(character_name);
+ if(!character_guid)
+ {
+ PSendSysMessage(LANG_NO_PLAYER,character_name.c_str());
+ SetSentErrorMessage(true);
+ return false;
+ }
+
+ account_id = objmgr.GetPlayerAccountIdByGUID(character_guid);
+ }
+
+ std::string account_name;
+ accmgr.GetName (account_id,account_name);
+
+ Player::DeleteFromDB(character_guid, account_id, true);
+ PSendSysMessage(LANG_CHARACTER_DELETED,character_name.c_str(),GUID_LOPART(character_guid),account_name.c_str(), account_id);
+ return true;
+}
+
+/// Exit the realm
+bool ChatHandler::HandleServerExitCommand(const char* args)
+{
+ SendSysMessage(LANG_COMMAND_EXIT);
+ World::StopNow(SHUTDOWN_EXIT_CODE);
+ return true;
+}
+
+/// Display info on users currently in the realm
+bool ChatHandler::HandleAccountOnlineListCommand(const char* args)
+{
+ ///- Get the list of accounts ID logged to the realm
+ QueryResult *resultDB = CharacterDatabase.Query("SELECT name,account FROM characters WHERE online > 0");
+ if (!resultDB)
+ return true;
+
+ ///- Display the list of account/characters online
+ SendSysMessage("=====================================================================");
+ SendSysMessage(LANG_ACCOUNT_LIST_HEADER);
+ SendSysMessage("=====================================================================");
+
+ ///- Circle through accounts
+ do
+ {
+ Field *fieldsDB = resultDB->Fetch();
+ std::string name = fieldsDB[0].GetCppString();
+ uint32 account = fieldsDB[1].GetUInt32();
+
+ ///- Get the username, last IP and GM level of each account
+ // No SQL injection. account is uint32.
+ // 0 1 2 3
+ QueryResult *resultLogin = LoginDatabase.PQuery("SELECT username, last_ip, gmlevel, expansion FROM account WHERE id = '%u'",account);
+
+ if(resultLogin)
+ {
+ Field *fieldsLogin = resultLogin->Fetch();
+ PSendSysMessage("|%15s| %20s | %15s |%4d|%5d|",
+ fieldsLogin[0].GetString(),name.c_str(),fieldsLogin[1].GetString(),fieldsLogin[2].GetUInt32(),fieldsLogin[3].GetUInt32());
+
+ delete resultLogin;
+ }
+ else
+ PSendSysMessage(LANG_ACCOUNT_LIST_ERROR,name.c_str());
+
+ }while(resultDB->NextRow());
+
+ delete resultDB;
+
+ SendSysMessage("=====================================================================");
+ return true;
+}
+
+/// Create an account
+bool ChatHandler::HandleAccountCreateCommand(const char* args)
+{
+ if(!*args)
+ return false;
+
+ ///- %Parse the command line arguments
+ char *szAcc = strtok((char*)args, " ");
+ char *szPassword = strtok(NULL, " ");
+ if(!szAcc || !szPassword)
+ return false;
+
+ // normilized in accmgr.CreateAccount
+ std::string account_name = szAcc;
+ std::string password = szPassword;
+
+ AccountOpResult result = accmgr.CreateAccount(account_name, password);
+ switch(result)
+ {
+ case AOR_OK:
+ PSendSysMessage(LANG_ACCOUNT_CREATED,account_name.c_str());
+ break;
+ case AOR_NAME_TOO_LONG:
+ SendSysMessage(LANG_ACCOUNT_TOO_LONG);
+ SetSentErrorMessage(true);
+ return false;
+ case AOR_NAME_ALREDY_EXIST:
+ SendSysMessage(LANG_ACCOUNT_ALREADY_EXIST);
+ SetSentErrorMessage(true);
+ return false;
+ case AOR_DB_INTERNAL_ERROR:
+ PSendSysMessage(LANG_ACCOUNT_NOT_CREATED_SQL_ERROR,account_name.c_str());
+ SetSentErrorMessage(true);
+ return false;
+ default:
+ PSendSysMessage(LANG_ACCOUNT_NOT_CREATED,account_name.c_str());
+ SetSentErrorMessage(true);
+ return false;
+ }
+
+ return true;
+}
+
+/// Set the level of logging
+bool ChatHandler::HandleServerSetLogLevelCommand(const char *args)
+{
+ if(!*args)
+ return false;
+
+ char *NewLevel = strtok((char*)args, " ");
+ if (!NewLevel)
+ return false;
+
+ sLog.SetLogLevel(NewLevel);
+ return true;
+}
+
+/// set diff time record interval
+bool ChatHandler::HandleServerSetDiffTimeCommand(const char *args)
+{
+ if(!*args)
+ return false;
+
+ char *NewTimeStr = strtok((char*)args, " ");
+ if(!NewTimeStr)
+ return false;
+
+ int32 NewTime =atoi(NewTimeStr);
+ if(NewTime < 0)
+ return false;
+
+ sWorld.SetRecordDiffInterval(NewTime);
+ printf( "Record diff every %u ms\n", NewTime);
+ return true;
+}
+
+
+/// @}
+
+#ifdef linux
+// Non-blocking keypress detector, when return pressed, return 1, else always return 0
+int kb_hit_return()
+{
+ struct timeval tv;
+ fd_set fds;
+ tv.tv_sec = 0;
+ tv.tv_usec = 0;
+ FD_ZERO(&fds);
+ FD_SET(STDIN_FILENO, &fds);
+ select(STDIN_FILENO+1, &fds, NULL, NULL, &tv);
+ return FD_ISSET(STDIN_FILENO, &fds);
+}
+#endif
+
+/// %Thread start
+void CliRunnable::run()
+{
+ ///- Init new SQL thread for the world database (one connection call enough)
+ WorldDatabase.ThreadStart(); // let thread do safe mySQL requests
+
+ char commandbuf[256];
+
+ ///- Display the list of available CLI functions then beep
+ sLog.outString();
+
+ if(sConfig.GetBoolDefault("BeepAtStart", true))
+ printf("\a"); // \a = Alert
+
+ // print this here the first time
+ // later it will be printed after command queue updates
+ printf("TC>");
+
+ ///- As long as the World is running (no World::m_stopEvent), get the command line and handle it
+ while (!World::IsStopped())
+ {
+ fflush(stdout);
+ #ifdef linux
+ while (!kb_hit_return() && !World::IsStopped())
+ // With this, we limit CLI to 10commands/second
+ usleep(100);
+ if (World::IsStopped())
+ break;
+ #endif
+ char *command_str = fgets(commandbuf,sizeof(commandbuf),stdin);
+ if (command_str != NULL)
+ {
+ for(int x=0;command_str[x];x++)
+ if(command_str[x]=='\r'||command_str[x]=='\n')
+ {
+ command_str[x]=0;
+ break;
+ }
+
+
+ if(!*command_str)
+ {
+ printf("TC>");
+ continue;
+ }
+
+ std::string command;
+ if(!consoleToUtf8(command_str,command)) // convert from console encoding to utf8
+ {
+ printf("TC>");
+ continue;
+ }
+
+ sWorld.QueueCliCommand(&utf8print,command.c_str());
+ }
+ else if (feof(stdin))
+ {
+ World::StopNow(SHUTDOWN_EXIT_CODE);
+ }
+ }
+
+ ///- End the database thread
+ WorldDatabase.ThreadEnd(); // free mySQL thread resources
+}
diff --git a/src/mangosd/CliRunnable.h b/src/mangosd/CliRunnable.h
new file mode 100644
index 00000000000..c3c1792b6e8
--- /dev/null
+++ b/src/mangosd/CliRunnable.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2005-2008 MaNGOS <http://www.mangosproject.org/>
+ *
+ * Copyright (C) 2008 Trinity <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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/// \addtogroup Trinityd
+/// @{
+/// \file
+
+#ifndef __CLIRUNNABLE_H
+#define __CLIRUNNABLE_H
+
+/// Command Line Interface handling thread
+class CliRunnable : public ZThread::Runnable
+{
+ public:
+ void run();
+};
+#endif
+/// @}
diff --git a/src/mangosd/Main.cpp b/src/mangosd/Main.cpp
new file mode 100644
index 00000000000..9e3c3cbd2d3
--- /dev/null
+++ b/src/mangosd/Main.cpp
@@ -0,0 +1,165 @@
+/*
+ * Copyright (C) 2005-2008 MaNGOS <http://www.mangosproject.org/>
+ *
+ * Copyright (C) 2008 Trinity <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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/// \addtogroup Trinityd Trinity Daemon
+/// @{
+/// \file
+
+#include "Common.h"
+#include "Database/DatabaseEnv.h"
+#include "Config/ConfigEnv.h"
+#include "Log.h"
+#include "Master.h"
+
+#ifndef _TRINITY_CORE_CONFIG
+# define _TRINITY_CORE_CONFIG "TrinityCore.conf"
+#endif //_TRINITY_CORE_CONFIG
+
+// Format is YYYYMMDDRR where RR is the change in the conf file
+// for that day.
+#ifndef _TRINITY_CORE_CONFVER
+# define _TRINITY_CORE_CONFVER 2008022901
+#endif //_TRINITY_CORE_CONFVER
+
+#ifdef WIN32
+#include "ServiceWin32.h"
+char serviceName[] = "TrinityCore";
+char serviceLongName[] = "Trinity core service";
+char serviceDescription[] = "Massive Network Game Object Server";
+/*
+ * -1 - not in service mode
+ * 0 - stopped
+ * 1 - running
+ * 2 - paused
+ */
+int m_ServiceStatus = -1;
+#endif
+
+DatabaseType WorldDatabase; ///< Accessor to the world database
+DatabaseType CharacterDatabase; ///< Accessor to the character database
+DatabaseType LoginDatabase; ///< Accessor to the realm/login database
+
+uint32 realmID; ///< Id of the realm
+
+/// Print out the usage string for this program on the console.
+void usage(const char *prog)
+{
+ sLog.outString("Usage: \n %s [<options>]\n"
+ " -c config_file use config_file as configuration file\n\r"
+ #ifdef WIN32
+ " Running as service functions:\n\r"
+ " --service run as service\n\r"
+ " -s install install service\n\r"
+ " -s uninstall uninstall service\n\r"
+ #endif
+ ,prog);
+}
+
+/// Launch the Trinity server
+extern int main(int argc, char **argv)
+{
+ ///- Command line parsing to get the configuration file name
+ char const* cfg_file = _TRINITY_CORE_CONFIG;
+ int c=1;
+ while( c < argc )
+ {
+ if( strcmp(argv[c],"-c") == 0)
+ {
+ if( ++c >= argc )
+ {
+ sLog.outError("Runtime-Error: -c option requires an input argument");
+ usage(argv[0]);
+ return 1;
+ }
+ else
+ cfg_file = argv[c];
+ }
+
+ #ifdef WIN32
+ ////////////
+ //Services//
+ ////////////
+ if( strcmp(argv[c],"-s") == 0)
+ {
+ if( ++c >= argc )
+ {
+ sLog.outError("Runtime-Error: -s option requires an input argument");
+ usage(argv[0]);
+ return 1;
+ }
+ if( strcmp(argv[c],"install") == 0)
+ {
+ if (WinServiceInstall())
+ sLog.outString("Installing service");
+ return 1;
+ }
+ else if( strcmp(argv[c],"uninstall") == 0)
+ {
+ if(WinServiceUninstall())
+ sLog.outString("Uninstalling service");
+ return 1;
+ }
+ else
+ {
+ sLog.outError("Runtime-Error: unsupported option %s",argv[c]);
+ usage(argv[0]);
+ return 1;
+ }
+ }
+ if( strcmp(argv[c],"--service") == 0)
+ {
+ WinServiceRun();
+ }
+ ////
+ #endif
+ ++c;
+ }
+
+ if (!sConfig.SetSource(cfg_file))
+ {
+ sLog.outError("Could not find configuration file %s.", cfg_file);
+ return 1;
+ }
+ sLog.outString("Using configuration file %s.", cfg_file);
+
+ uint32 confVersion = sConfig.GetIntDefault("ConfVersion", 0);
+ if (confVersion < _TRINITY_CORE_CONFVER)
+ {
+ sLog.outError("*****************************************************************************");
+ sLog.outError(" WARNING: Your trinitycore.conf version indicates your conf file is out of date!");
+ sLog.outError(" Please check for updates, as your current default values may cause");
+ sLog.outError(" strange behavior.");
+ sLog.outError("*****************************************************************************");
+ clock_t pause = 3000 + clock();
+
+ while (pause > clock()) {}
+ }
+
+ ///- and run the 'Master'
+ /// \todo Why do we need this 'Master'? Can't all of this be in the Main as for Realmd?
+ return sMaster.Run();
+
+ // at sMaster return function exist with codes
+ // 0 - normal shutdown
+ // 1 - shutdown at error
+ // 2 - restart command used, this code can be used by restarter for restart Trinityd
+}
+
+/// @}
diff --git a/src/mangosd/Makefile.am b/src/mangosd/Makefile.am
new file mode 100644
index 00000000000..e930feeb252
--- /dev/null
+++ b/src/mangosd/Makefile.am
@@ -0,0 +1,62 @@
+# Copyright (C) 2005-2008 MaNGOS <http://www.mangosproject.org/>
+#
+# Copyright (C) 2008 Trinity <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, write to the Free Software
+# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+
+## Process this file with automake to produce Makefile.in
+
+## CPP flags for includes, defines, etc.
+AM_CPPFLAGS = $(TRINI_INCLUDES) -I$(top_builddir)/src/shared -I$(srcdir)/../../dep/include -I$(srcdir)/../framework -I$(srcdir)/../shared -I$(srcdir)/../game -I$(srcdir) -DSYSCONFDIR=\"$(sysconfdir)/\"
+
+## Build world list daemon as standalone program
+bin_PROGRAMS = trinity-worldd
+trinity_worldd_SOURCES = \
+ CliRunnable.cpp \
+ CliRunnable.h \
+ Main.cpp \
+ Master.cpp \
+ Master.h \
+ RASocket.cpp \
+ RASocket.h \
+ WorldRunnable.cpp \
+ WorldRunnable.h
+
+## Link world daemon against the shared library
+trinity_worldd_LDADD = ../bindings/scripts/libtrinityscript.la ../game/libmangosgame.a ../shared/Database/libmangosdatabase.a ../shared/Config/libmangosconfig.a ../shared/Auth/libmangosauth.a ../shared/libmangosshared.a ../shared/vmap/libmangosvmaps.a ../framework/libmangosframework.a ../../dep/src/sockets/libmangossockets.a ../../dep/src/zthread/libZThread.la ../../dep/src/g3dlite/libg3dlite.a
+trinity_worldd_LDFLAGS = -L../../dep/src/sockets -L../../dep/src/zthread -L../../dep/src/g3dlite -L../bindings/scripts/ -L$(libdir) $(TRINI_LIBS) -export-dynamic
+
+## Additional files to include when running 'make dist'
+# Include world daemon configuration
+EXTRA_DIST = \
+ mangosd.conf.dist
+
+## Additional files to install
+sysconf_DATA = \
+ mangosd.conf.dist
+
+install-data-hook:
+ @list='$(sysconf_DATA)'; for p in $$list; do \
+ dest=`echo $$p | sed -e s/.dist//`; \
+ if test -f $(DESTDIR)$(sysconfdir)/$$dest; then \
+ echo "$@ will not overwrite existing $(DESTDIR)$(sysconfdir)/$$dest"; \
+ else \
+ echo " $(INSTALL_DATA) $$p $(DESTDIR)$(sysconfdir)/$$dest"; \
+ $(INSTALL_DATA) $$p $(DESTDIR)$(sysconfdir)/$$dest; \
+ fi; \
+ done
+
+clean-local:
+ rm -f $(sysconf_DATA)
diff --git a/src/mangosd/Master.cpp b/src/mangosd/Master.cpp
new file mode 100644
index 00000000000..c1484fede8e
--- /dev/null
+++ b/src/mangosd/Master.cpp
@@ -0,0 +1,517 @@
+/*
+ * Copyright (C) 2005-2008 MaNGOS <http://www.mangosproject.org/>
+ *
+ * Copyright (C) 2008 Trinity <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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/** \file
+ \ingroup Trinityd
+*/
+
+#include <ace/OS_NS_signal.h>
+
+#include "WorldSocketMgr.h"
+#include "Common.h"
+#include "Master.h"
+#include "WorldSocket.h"
+#include "WorldRunnable.h"
+#include "World.h"
+#include "Log.h"
+#include "Timer.h"
+#include "Policies/SingletonImp.h"
+#include "SystemConfig.h"
+#include "Config/ConfigEnv.h"
+#include "Database/DatabaseEnv.h"
+#include "CliRunnable.h"
+#include "RASocket.h"
+#include "ScriptCalls.h"
+#include "Util.h"
+
+#include "sockets/TcpSocket.h"
+#include "sockets/Utility.h"
+#include "sockets/Parse.h"
+#include "sockets/Socket.h"
+#include "sockets/SocketHandler.h"
+#include "sockets/ListenSocket.h"
+
+#ifdef WIN32
+#include "ServiceWin32.h"
+extern int m_ServiceStatus;
+#endif
+
+/// \todo Warning disabling not useful under VC++2005. Can somebody say on which compiler it is useful?
+#pragma warning(disable:4305)
+
+INSTANTIATE_SINGLETON_1( Master );
+
+volatile uint32 Master::m_masterLoopCounter = 0;
+
+class FreezeDetectorRunnable : public ZThread::Runnable
+{
+public:
+ FreezeDetectorRunnable() { _delaytime = 0; }
+ uint32 m_loops, m_lastchange;
+ uint32 w_loops, w_lastchange;
+ uint32 _delaytime;
+ void SetDelayTime(uint32 t) { _delaytime = t; }
+ void run(void)
+ {
+ if(!_delaytime)
+ return;
+ sLog.outString("Starting up anti-freeze thread (%u seconds max stuck time)...",_delaytime/1000);
+ m_loops = 0;
+ w_loops = 0;
+ m_lastchange = 0;
+ w_lastchange = 0;
+ while(!World::IsStopped())
+ {
+ ZThread::Thread::sleep(1000);
+ uint32 curtime = getMSTime();
+ //DEBUG_LOG("anti-freeze: time=%u, counters=[%u; %u]",curtime,Master::m_masterLoopCounter,World::m_worldLoopCounter);
+
+ // There is no Master anymore
+ // TODO: clear the rest of the code
+// // normal work
+// if(m_loops != Master::m_masterLoopCounter)
+// {
+// m_lastchange = curtime;
+// m_loops = Master::m_masterLoopCounter;
+// }
+// // possible freeze
+// else if(getMSTimeDiff(m_lastchange,curtime) > _delaytime)
+// {
+// sLog.outError("Main/Sockets Thread hangs, kicking out server!");
+// *((uint32 volatile*)NULL) = 0; // bang crash
+// }
+
+ // normal work
+ if(w_loops != World::m_worldLoopCounter)
+ {
+ w_lastchange = curtime;
+ w_loops = World::m_worldLoopCounter;
+ }
+ // possible freeze
+ else if(getMSTimeDiff(w_lastchange,curtime) > _delaytime)
+ {
+ sLog.outError("World Thread hangs, kicking out server!");
+ *((uint32 volatile*)NULL) = 0; // bang crash
+ }
+ }
+ sLog.outString("Anti-freeze thread exiting without problems.");
+ }
+};
+
+class RARunnable : public ZThread::Runnable
+{
+public:
+ uint32 numLoops, loopCounter;
+
+ RARunnable ()
+ {
+ uint32 socketSelecttime = sWorld.getConfig (CONFIG_SOCKET_SELECTTIME);
+ numLoops = (sConfig.GetIntDefault ("MaxPingTime", 30) * (MINUTE * 1000000 / socketSelecttime));
+ loopCounter = 0;
+ }
+
+ void
+ checkping ()
+ {
+ // ping if need
+ if ((++loopCounter) == numLoops)
+ {
+ loopCounter = 0;
+ sLog.outDetail ("Ping MySQL to keep connection alive");
+ delete WorldDatabase.Query ("SELECT 1 FROM command LIMIT 1");
+ delete LoginDatabase.Query ("SELECT 1 FROM realmlist LIMIT 1");
+ delete CharacterDatabase.Query ("SELECT 1 FROM bugreport LIMIT 1");
+ }
+ }
+
+ void
+ run (void)
+ {
+ SocketHandler h;
+
+ // Launch the RA listener socket
+ ListenSocket<RASocket> RAListenSocket (h);
+ bool usera = sConfig.GetBoolDefault ("Ra.Enable", false);
+
+ if (usera)
+ {
+ port_t raport = sConfig.GetIntDefault ("Ra.Port", 3443);
+ std::string stringip = sConfig.GetStringDefault ("Ra.IP", "0.0.0.0");
+ ipaddr_t raip;
+ if (!Utility::u2ip (stringip, raip))
+ sLog.outError ("Trinity RA can not bind to ip %s", stringip.c_str ());
+ else if (RAListenSocket.Bind (raip, raport))
+ sLog.outError ("Trinity RA can not bind to port %d on %s", raport, stringip.c_str ());
+ else
+ {
+ h.Add (&RAListenSocket);
+
+ sLog.outString ("Starting Remote access listner on port %d on %s", raport, stringip.c_str ());
+ }
+ }
+
+ // Socket Selet time is in microseconds , not miliseconds!!
+ uint32 socketSelecttime = sWorld.getConfig (CONFIG_SOCKET_SELECTTIME);
+
+ // if use ra spend time waiting for io, if not use ra ,just sleep
+ if (usera)
+ while (!World::IsStopped())
+ {
+ h.Select (0, socketSelecttime);
+ checkping ();
+ }
+ else
+ while (!World::IsStopped())
+ {
+ ZThread::Thread::sleep (static_cast<unsigned long> (socketSelecttime / 1000));
+ checkping ();
+ }
+ }
+};
+
+Master::Master()
+{
+}
+
+Master::~Master()
+{
+}
+
+/// Main function
+int Master::Run()
+{
+ sLog.outString( "%s (core-daemon)", _FULLVERSION );
+ sLog.outString( "<Ctrl-C> to stop.\n" );
+
+ sLog.outTitle( " ______ __");
+ sLog.outTitle( "/\\__ _\\ __ __/\\ \\__");
+ sLog.outTitle( "\\/_/\\ \\/ _ __ /\\_\\ ___ /\\_\\ \\ ,_\\ __ __");
+ sLog.outTitle( " \\ \\ \\/\\`'__\\/\\ \\ /' _ `\\/\\ \\ \\ \\/ /\\ \\/\\ \\");
+ sLog.outTitle( " \\ \\ \\ \\ \\/ \\ \\ \\/\\ \\/\\ \\ \\ \\ \\ \\_\\ \\ \\_\\ \\");
+ sLog.outTitle( " \\ \\_\\ \\_\\ \\ \\_\\ \\_\\ \\_\\ \\_\\ \\__\\\\/`____ \\");
+ sLog.outTitle( " \\/_/\\/_/ \\/_/\\/_/\\/_/\\/_/\\/__/ `/___/> \\");
+ sLog.outTitle( " C O R E /\\___/");
+ sLog.outTitle( "http://TrinityCore.org \\/__/\n");
+
+ /// worldd PID file creation
+ std::string pidfile = sConfig.GetStringDefault("PidFile", "");
+ if(!pidfile.empty())
+ {
+ uint32 pid = CreatePIDFile(pidfile);
+ if( !pid )
+ {
+ sLog.outError( "Cannot create PID file %s.\n", pidfile.c_str() );
+ return 1;
+ }
+
+ sLog.outString( "Daemon PID: %u\n", pid );
+ }
+
+ ///- Start the databases
+ if (!_StartDB())
+ return 1;
+
+ ///- Initialize the World
+ sWorld.SetInitialWorldSettings();
+
+ ///- Catch termination signals
+ _HookSignals();
+
+ ///- Launch WorldRunnable thread
+ ZThread::Thread t(new WorldRunnable);
+ t.setPriority ((ZThread::Priority )2);
+
+ // set server online
+ LoginDatabase.PExecute("UPDATE realmlist SET color = 0, population = 0 WHERE id = '%d'",realmID);
+
+#ifdef WIN32
+ if (sConfig.GetBoolDefault("Console.Enable", true) && (m_ServiceStatus == -1)/* need disable console in service mode*/)
+#else
+ if (sConfig.GetBoolDefault("Console.Enable", true))
+#endif
+ {
+ ///- Launch CliRunnable thread
+ ZThread::Thread td1(new CliRunnable);
+ }
+
+ ZThread::Thread td2(new RARunnable);
+
+ ///- Handle affinity for multiple processors and process priority on Windows
+ #ifdef WIN32
+ {
+ HANDLE hProcess = GetCurrentProcess();
+
+ uint32 Aff = sConfig.GetIntDefault("UseProcessors", 0);
+ if(Aff > 0)
+ {
+ ULONG_PTR appAff;
+ ULONG_PTR sysAff;
+
+ if(GetProcessAffinityMask(hProcess,&appAff,&sysAff))
+ {
+ ULONG_PTR curAff = Aff & appAff; // remove non accessible processors
+
+ if(!curAff )
+ {
+ sLog.outError("Processors marked in UseProcessors bitmask (hex) %x not accessible for Trinityd. Accessible processors bitmask (hex): %x",Aff,appAff);
+ }
+ else
+ {
+ if(SetProcessAffinityMask(hProcess,curAff))
+ sLog.outString("Using processors (bitmask, hex): %x", curAff);
+ else
+ sLog.outError("Can't set used processors (hex): %x",curAff);
+ }
+ }
+ sLog.outString();
+ }
+
+ bool Prio = sConfig.GetBoolDefault("ProcessPriority", false);
+
+// if(Prio && (m_ServiceStatus == -1)/* need set to default process priority class in service mode*/)
+ if(Prio)
+ {
+ if(SetPriorityClass(hProcess,HIGH_PRIORITY_CLASS))
+ sLog.outString("TrinityCore process priority class set to HIGH");
+ else
+ sLog.outError("ERROR: Can't set Trinityd process priority class.");
+ sLog.outString();
+ }
+ }
+ #endif
+
+ uint32 realCurrTime, realPrevTime;
+ realCurrTime = realPrevTime = getMSTime();
+
+ uint32 socketSelecttime = sWorld.getConfig(CONFIG_SOCKET_SELECTTIME);
+
+ // maximum counter for next ping
+ uint32 numLoops = (sConfig.GetIntDefault( "MaxPingTime", 30 ) * (MINUTE * 1000000 / socketSelecttime));
+ uint32 loopCounter = 0;
+
+ ///- Start up freeze catcher thread
+ uint32 freeze_delay = sConfig.GetIntDefault("MaxCoreStuckTime", 0);
+ if(freeze_delay)
+ {
+ FreezeDetectorRunnable *fdr = new FreezeDetectorRunnable();
+ fdr->SetDelayTime(freeze_delay*1000);
+ ZThread::Thread t(fdr);
+ t.setPriority(ZThread::High);
+ }
+
+ ///- Launch the world listener socket
+ port_t wsport = sWorld.getConfig (CONFIG_PORT_WORLD);
+ std::string bind_ip = sConfig.GetStringDefault ("BindIP", "0.0.0.0");
+
+ if (sWorldSocketMgr->StartNetwork (wsport, bind_ip.c_str ()) == -1)
+ {
+ sLog.outError ("Failed to start network");
+ World::StopNow(ERROR_EXIT_CODE);
+ // go down and shutdown the server
+ }
+
+ sWorldSocketMgr->Wait ();
+
+ // set server offline
+ LoginDatabase.PExecute("UPDATE realmlist SET color = 2 WHERE id = '%d'",realmID);
+
+ ///- Remove signal handling before leaving
+ _UnhookSignals();
+
+ // when the main thread closes the singletons get unloaded
+ // since worldrunnable uses them, it will crash if unloaded after master
+ t.wait();
+ td2.wait ();
+
+ ///- Clean database before leaving
+ clearOnlineAccounts();
+
+ ///- Wait for delay threads to end
+ CharacterDatabase.HaltDelayThread();
+ WorldDatabase.HaltDelayThread();
+ LoginDatabase.HaltDelayThread();
+
+ sLog.outString( "Halting process..." );
+
+ #ifdef WIN32
+ if (sConfig.GetBoolDefault("Console.Enable", true))
+ {
+ // this only way to terminate CLI thread exist at Win32 (alt. way exist only in Windows Vista API)
+ //_exit(1);
+ // send keyboard input to safely unblock the CLI thread
+ INPUT_RECORD b[5];
+ HANDLE hStdIn = GetStdHandle(STD_INPUT_HANDLE);
+ b[0].EventType = KEY_EVENT;
+ b[0].Event.KeyEvent.bKeyDown = TRUE;
+ b[0].Event.KeyEvent.uChar.AsciiChar = 'X';
+ b[0].Event.KeyEvent.wVirtualKeyCode = 'X';
+ b[0].Event.KeyEvent.wRepeatCount = 1;
+
+ b[1].EventType = KEY_EVENT;
+ b[1].Event.KeyEvent.bKeyDown = FALSE;
+ b[1].Event.KeyEvent.uChar.AsciiChar = 'X';
+ b[1].Event.KeyEvent.wVirtualKeyCode = 'X';
+ b[1].Event.KeyEvent.wRepeatCount = 1;
+
+ b[2].EventType = KEY_EVENT;
+ b[2].Event.KeyEvent.bKeyDown = TRUE;
+ b[2].Event.KeyEvent.dwControlKeyState = 0;
+ b[2].Event.KeyEvent.uChar.AsciiChar = '\r';
+ b[2].Event.KeyEvent.wVirtualKeyCode = VK_RETURN;
+ b[2].Event.KeyEvent.wRepeatCount = 1;
+ b[2].Event.KeyEvent.wVirtualScanCode = 0x1c;
+
+ b[3].EventType = KEY_EVENT;
+ b[3].Event.KeyEvent.bKeyDown = FALSE;
+ b[3].Event.KeyEvent.dwControlKeyState = 0;
+ b[3].Event.KeyEvent.uChar.AsciiChar = '\r';
+ b[3].Event.KeyEvent.wVirtualKeyCode = VK_RETURN;
+ b[3].Event.KeyEvent.wVirtualScanCode = 0x1c;
+ b[3].Event.KeyEvent.wRepeatCount = 1;
+ DWORD numb;
+ BOOL ret = WriteConsoleInput(hStdIn, b, 4, &numb);
+ }
+ #endif
+
+ // for some unknown reason, unloading scripts here and not in worldrunnable
+ // fixes a memory leak related to detaching threads from the module
+ UnloadScriptingModule();
+
+ // Exit the process with specified return value
+ return World::GetExitCode();
+}
+
+/// Initialize connection to the databases
+bool Master::_StartDB()
+{
+ ///- Get world database info from configuration file
+ std::string dbstring;
+ if(!sConfig.GetString("WorldDatabaseInfo", &dbstring))
+ {
+ sLog.outError("Database not specified in configuration file");
+ return false;
+ }
+ sLog.outString("World Database: %s", dbstring.c_str());
+
+ ///- Initialise the world database
+ if(!WorldDatabase.Initialize(dbstring.c_str()))
+ {
+ sLog.outError("Cannot connect to world database %s",dbstring.c_str());
+ return false;
+ }
+
+ if(!sConfig.GetString("CharacterDatabaseInfo", &dbstring))
+ {
+ sLog.outError("Character Database not specified in configuration file");
+ return false;
+ }
+ sLog.outString("Character Database: %s", dbstring.c_str());
+
+ ///- Initialise the Character database
+ if(!CharacterDatabase.Initialize(dbstring.c_str()))
+ {
+ sLog.outError("Cannot connect to Character database %s",dbstring.c_str());
+ return false;
+ }
+
+ ///- Get login database info from configuration file
+ if(!sConfig.GetString("LoginDatabaseInfo", &dbstring))
+ {
+ sLog.outError("Login database not specified in configuration file");
+ return false;
+ }
+
+ ///- Initialise the login database
+ sLog.outString("Login Database: %s", dbstring.c_str() );
+ if(!LoginDatabase.Initialize(dbstring.c_str()))
+ {
+ sLog.outError("Cannot connect to login database %s",dbstring.c_str());
+ return false;
+ }
+
+ ///- Get the realm Id from the configuration file
+ realmID = sConfig.GetIntDefault("RealmID", 0);
+ if(!realmID)
+ {
+ sLog.outError("Realm ID not defined in configuration file");
+ return false;
+ }
+ sLog.outString("Realm running as realm ID %d", realmID);
+
+ ///- Clean the database before starting
+ clearOnlineAccounts();
+
+ sWorld.LoadDBVersion();
+
+ sLog.outString("Using %s", sWorld.GetDBVersion());
+ return true;
+}
+
+/// Clear 'online' status for all accounts with characters in this realm
+void Master::clearOnlineAccounts()
+{
+ // Cleanup online status for characters hosted at current realm
+ /// \todo Only accounts with characters logged on *this* realm should have online status reset. Move the online column from 'account' to 'realmcharacters'?
+ LoginDatabase.PExecute(
+ "UPDATE account SET online = 0 WHERE online > 0 "
+ "AND id IN (SELECT acctid FROM realmcharacters WHERE realmid = '%d')",realmID);
+
+
+ CharacterDatabase.Execute("UPDATE characters SET online = 0 WHERE online<>0");
+}
+
+/// Handle termination signals
+void Master::_OnSignal(int s)
+{
+ switch (s)
+ {
+ case SIGINT:
+ World::StopNow(RESTART_EXIT_CODE);
+ break;
+ case SIGTERM:
+ #ifdef _WIN32
+ case SIGBREAK:
+ #endif
+ World::StopNow(SHUTDOWN_EXIT_CODE);
+ break;
+ }
+
+ signal(s, _OnSignal);
+}
+
+/// Define hook '_OnSignal' for all termination signals
+void Master::_HookSignals()
+{
+ signal(SIGINT, _OnSignal);
+ signal(SIGTERM, _OnSignal);
+ #ifdef _WIN32
+ signal(SIGBREAK, _OnSignal);
+ #endif
+}
+
+/// Unhook the signals before leaving
+void Master::_UnhookSignals()
+{
+ signal(SIGINT, 0);
+ signal(SIGTERM, 0);
+ #ifdef _WIN32
+ signal(SIGBREAK, 0);
+ #endif
+}
diff --git a/src/mangosd/Master.h b/src/mangosd/Master.h
new file mode 100644
index 00000000000..2485dd456b1
--- /dev/null
+++ b/src/mangosd/Master.h
@@ -0,0 +1,52 @@
+/*
+ * Copyright (C) 2005-2008 MaNGOS <http://www.mangosproject.org/>
+ *
+ * Copyright (C) 2008 Trinity <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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/// \addtogroup Trinityd
+/// @{
+/// \file
+
+#ifndef _MASTER_H
+#define _MASTER_H
+
+#include "Common.h"
+#include "Policies/Singleton.h"
+
+/// Start the server
+class Master
+{
+ public:
+ Master();
+ ~Master();
+ int Run();
+ static volatile uint32 m_masterLoopCounter;
+
+ private:
+ bool _StartDB();
+
+ void _HookSignals();
+ void _UnhookSignals();
+ static void _OnSignal(int s);
+
+ void clearOnlineAccounts();
+};
+
+#define sMaster Trinity::Singleton<Master>::Instance()
+#endif
+/// @}
diff --git a/src/mangosd/RASocket.cpp b/src/mangosd/RASocket.cpp
new file mode 100644
index 00000000000..cfc50d95f89
--- /dev/null
+++ b/src/mangosd/RASocket.cpp
@@ -0,0 +1,259 @@
+/*
+ * Copyright (C) 2005-2008 MaNGOS <http://www.mangosproject.org/>
+ *
+ * Copyright (C) 2008 Trinity <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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/** \file
+ \ingroup Trinityd
+*/
+
+#include "Common.h"
+#include "Database/DatabaseEnv.h"
+#include "Log.h"
+#include "RASocket.h"
+#include "World.h"
+#include "Config/ConfigEnv.h"
+#include "Util.h"
+#include "AccountMgr.h"
+
+/// \todo Make this thread safe if in the future 2 admins should be able to log at the same time.
+SOCKET r;
+
+#define dropclient {Sendf("I'm busy right now, come back later."); \
+ SetCloseAndDelete(); \
+ return; \
+ }
+
+uint32 iSession=0; ///< Session number (incremented each time a new connection is made)
+unsigned int iUsers=0; ///< Number of active administrators
+
+typedef int(* pPrintf)(const char*,...);
+
+void ParseCommand(CliCommandHolder::Print*, char*command);
+
+/// RASocket constructor
+RASocket::RASocket(ISocketHandler &h): TcpSocket(h)
+{
+
+ ///- Increment the session number
+ iSess =iSession++ ;
+
+ ///- Get the config parameters
+ bSecure = sConfig.GetBoolDefault( "RA.Secure", true );
+ iMinLevel = sConfig.GetIntDefault( "RA.MinLevel", 3 );
+
+ ///- Initialize buffer and data
+ iInputLength=0;
+ buff=new char[RA_BUFF_SIZE];
+ stage=NONE;
+}
+
+/// RASocket destructor
+RASocket::~RASocket()
+{
+ ///- Delete buffer and decrease active admins count
+ delete [] buff;
+
+ sLog.outRALog("Connection was closed.\n");
+
+ if(stage==OK)
+ iUsers--;
+}
+
+/// Accept an incoming connection
+void RASocket::OnAccept()
+{
+ std::string ss=GetRemoteAddress();
+ sLog.outRALog("Incoming connection from %s.\n",ss.c_str());
+ ///- If there is already an active admin, drop the connection
+ if(iUsers)
+ dropclient
+
+ ///- Else print Motd
+ Sendf("%s\r\n",sWorld.GetMotd());
+}
+
+/// Read data from the network
+void RASocket::OnRead()
+{
+ ///- Read data and check input length
+ TcpSocket::OnRead();
+
+ unsigned int sz=ibuf.GetLength();
+ if(iInputLength+sz>=RA_BUFF_SIZE)
+ {
+ sLog.outRALog("Input buffer overflow, possible DOS attack.\n");
+ SetCloseAndDelete();
+ return;
+ }
+
+ ///- If there is already an active admin (other than you), drop the connection
+ if(stage!=OK && iUsers)
+ dropclient
+
+ char *inp = new char [sz+1];
+ ibuf.Read(inp,sz);
+
+ /// \todo Can somebody explain this 'Linux bugfix'?
+ if(stage==NONE)
+ if(sz>4) //linux remote telnet
+ if(memcmp(inp ,"USER ",5))
+ {
+ delete [] inp;return;
+ printf("lin bugfix");
+ } //linux bugfix
+
+ ///- Discard data after line break or line feed
+ bool gotenter=false;
+ unsigned int y=0;
+ for(;y<sz;y++)
+ if(inp[y]=='\r'||inp[y]=='\n')
+ {
+ gotenter=true;
+ break;
+ }
+
+ //No buffer overflow (checked above)
+ memcpy(&buff[iInputLength],inp,y);
+ iInputLength+=y;
+ delete [] inp;
+ if(gotenter)
+ {
+
+ buff[iInputLength]=0;
+ iInputLength=0;
+ switch(stage)
+ {
+ /// <ul> <li> If the input is 'USER <username>'
+ case NONE:
+ if(!memcmp(buff,"USER ",5)) //got "USER" cmd
+ {
+ szLogin=&buff[5];
+
+ ///- Get the gmlevel and password from the account table
+ std::string login = szLogin;
+
+ ///- Convert Account name to Upper Format
+ AccountMgr::normilizeString(login);
+
+ ///- Escape the Login to allow quotes in names
+ LoginDatabase.escape_string(login);
+
+ QueryResult* result = LoginDatabase.PQuery("SELECT gmlevel FROM account WHERE username = '%s'",login.c_str());
+
+ ///- If the user is not found, deny access
+ if(!result)
+ {
+ Sendf("-No such user.\r\n");
+ sLog.outRALog("User %s does not exist.\n",szLogin.c_str());
+ if(bSecure)SetCloseAndDelete();
+ }
+ else
+ {
+ Field *fields = result->Fetch();
+
+ //szPass=fields[0].GetString();
+
+ ///- if gmlevel is too low, deny access
+ if(fields[0].GetUInt32()<iMinLevel)
+ {
+ Sendf("-Not enough privileges.\r\n");
+ sLog.outRALog("User %s has no privilege.\n",szLogin.c_str());
+ if(bSecure)SetCloseAndDelete();
+ } else
+ {
+ stage=LG;
+ }
+ delete result;
+ }
+ }
+ break;
+ ///<li> If the input is 'PASS <password>' (and the user already gave his username)
+ case LG:
+ if(!memcmp(buff,"PASS ",5)) //got "PASS" cmd
+ { //login+pass ok
+ ///- If password is correct, increment the number of active administrators
+ std::string login = szLogin;
+ std::string pw = &buff[5];
+
+ AccountMgr::normilizeString(login);
+ AccountMgr::normilizeString(pw);
+ LoginDatabase.escape_string(login);
+ LoginDatabase.escape_string(pw);
+
+ QueryResult *check = LoginDatabase.PQuery(
+ "SELECT 1 FROM account WHERE username = '%s' AND sha_pass_hash=SHA1(CONCAT(username,':','%s'))",
+ login.c_str(), pw.c_str());
+
+ if(check)
+ {
+ delete check;
+ r=GetSocket();
+ stage=OK;
+ ++iUsers;
+
+ Sendf("+Logged in.\r\n");
+ sLog.outRALog("User %s has logged in.\n",szLogin.c_str());
+ Sendf("TC>");
+ }
+ else
+ {
+ ///- Else deny access
+ Sendf("-Wrong pass.\r\n");
+ sLog.outRALog("User %s has failed to log in.\n",szLogin.c_str());
+ if(bSecure)SetCloseAndDelete();
+ }
+ }
+ break;
+ ///<li> If user is logged, parse and execute the command
+ case OK:
+ if(strlen(buff))
+ {
+ sLog.outRALog("Got '%s' cmd.\n",buff);
+ sWorld.QueueCliCommand(&RASocket::zprint , buff);
+ }
+ else
+ Sendf("TC>");
+ break;
+ ///</ul>
+ };
+
+ }
+}
+
+/// Output function
+void RASocket::zprint( const char * szText )
+{
+ if( !szText )
+ return;
+
+ #ifdef RA_CRYPT
+
+ char *megabuffer=strdup(szText);
+ unsigned int sz=strlen(megabuffer);
+ Encrypt(megabuffer,sz);
+ send(r,megabuffer,sz,0);
+ delete [] megabuffer;
+
+ #else
+
+ unsigned int sz=strlen(szText);
+ send(r,szText,sz,0);
+
+ #endif
+}
diff --git a/src/mangosd/RASocket.h b/src/mangosd/RASocket.h
new file mode 100644
index 00000000000..a164c9d3aa2
--- /dev/null
+++ b/src/mangosd/RASocket.h
@@ -0,0 +1,67 @@
+/*
+ * Copyright (C) 2005-2008 MaNGOS <http://www.mangosproject.org/>
+ *
+ * Copyright (C) 2008 Trinity <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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/// \addtogroup Trinityd
+/// @{
+/// \file
+
+#ifndef _RASOCKET_H
+#define _RASOCKET_H
+
+#include "Common.h"
+#include "sockets/TcpSocket.h"
+
+#define RA_BUFF_SIZE 1024
+
+class ISocketHandler;
+
+/// Remote Administration socket
+class RASocket: public TcpSocket
+{
+ public:
+
+ RASocket(ISocketHandler& h);
+ ~RASocket();
+
+ void OnAccept();
+ void OnRead();
+
+ private:
+
+ char * buff;
+ std::string szLogin;
+ uint32 iSess;
+ unsigned int iInputLength;
+ bool bLog;
+ bool bSecure; //kick on wrong pass, non exist. user, user with no priv
+ //will protect from DOS, bruteforce attacks
+ //some 'smart' protection must be added for more security
+ uint8 iMinLevel;
+ enum
+ {
+ NONE, //initial value
+ LG, //only login was entered
+ OK, //both login and pass were given, and they are correct and user have enough priv.
+ }stage;
+
+ static void zprint( const char * szText );
+};
+#endif
+/// @}
diff --git a/src/mangosd/TrinityCore.ico b/src/mangosd/TrinityCore.ico
new file mode 100644
index 00000000000..6f0a5721957
--- /dev/null
+++ b/src/mangosd/TrinityCore.ico
Binary files differ
diff --git a/src/mangosd/WorldRunnable.cpp b/src/mangosd/WorldRunnable.cpp
new file mode 100644
index 00000000000..b57dbc6bce2
--- /dev/null
+++ b/src/mangosd/WorldRunnable.cpp
@@ -0,0 +1,86 @@
+/*
+ * Copyright (C) 2005-2008 MaNGOS <http://www.mangosproject.org/>
+ *
+ * Copyright (C) 2008 Trinity <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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/** \file
+ \ingroup Trinityd
+*/
+
+#include "WorldSocketMgr.h"
+#include "Common.h"
+#include "World.h"
+#include "WorldRunnable.h"
+#include "Timer.h"
+#include "ObjectAccessor.h"
+#include "MapManager.h"
+
+#include "Database/DatabaseEnv.h"
+
+#ifdef WIN32
+#define WORLD_SLEEP_CONST 50
+#else
+#define WORLD_SLEEP_CONST 100 //Is this still needed?? [On linux some time ago not working 50ms]
+#endif
+
+/// Heartbeat for the World
+void WorldRunnable::run()
+{
+ ///- Init new SQL thread for the world database
+ WorldDatabase.ThreadStart(); // let thread do safe mySQL requests (one connection call enough)
+ sWorld.InitResultQueue();
+
+ uint32 realCurrTime = 0;
+ uint32 realPrevTime = getMSTime();
+
+ uint32 prevSleepTime = 0; // used for balanced full tick time length near WORLD_SLEEP_CONST
+
+ ///- While we have not World::m_stopEvent, update the world
+ while (!World::IsStopped())
+ {
+ ++World::m_worldLoopCounter;
+ realCurrTime = getMSTime();
+
+ uint32 diff = getMSTimeDiff(realPrevTime,realCurrTime);
+
+ sWorld.Update( diff );
+ realPrevTime = realCurrTime;
+
+ // diff (D0) include time of previous sleep (d0) + tick time (t0)
+ // we want that next d1 + t1 == WORLD_SLEEP_CONST
+ // we can't know next t1 and then can use (t0 + d1) == WORLD_SLEEP_CONST requirement
+ // d1 = WORLD_SLEEP_CONST - t0 = WORLD_SLEEP_CONST - (D0 - d0) = WORLD_SLEEP_CONST + d0 - D0
+ if (diff <= WORLD_SLEEP_CONST+prevSleepTime)
+ {
+ prevSleepTime = WORLD_SLEEP_CONST+prevSleepTime-diff;
+ ZThread::Thread::sleep(prevSleepTime);
+ }
+ else
+ prevSleepTime = 0;
+ }
+
+ sWorld.KickAll(); // save and kick all players
+ sWorld.UpdateSessions( 1 ); // real players unload required UpdateSessions call
+
+ sWorldSocketMgr->StopNetwork();
+
+ MapManager::Instance().UnloadAll(); // unload all grids (including locked in memory)
+
+ ///- End the database thread
+ WorldDatabase.ThreadEnd(); // free mySQL thread resources
+}
diff --git a/src/mangosd/WorldRunnable.h b/src/mangosd/WorldRunnable.h
new file mode 100644
index 00000000000..8891186dec4
--- /dev/null
+++ b/src/mangosd/WorldRunnable.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2005-2008 MaNGOS <http://www.mangosproject.org/>
+ *
+ * Copyright (C) 2008 Trinity <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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+/// \addtogroup Trinityd
+/// @{
+/// \file
+
+#ifndef __WORLDRUNNABLE_H
+#define __WORLDRUNNABLE_H
+
+/// Heartbeat thread for the World
+class WorldRunnable : public ZThread::Runnable
+{
+ public:
+ void run();
+};
+#endif
+/// @}
diff --git a/src/mangosd/mangosd.conf.dist.in b/src/mangosd/mangosd.conf.dist.in
new file mode 100644
index 00000000000..c0ec604a7aa
--- /dev/null
+++ b/src/mangosd/mangosd.conf.dist.in
@@ -0,0 +1,1352 @@
+##########################################
+# Trinity Core worldd configuration file #
+##########################################
+ConfVersion=2008080101
+
+###################################################################################################################
+# CONNECTIONS AND DIRECTORIES
+#
+# RealmID
+# RealmID must match the realmlist inside the realmd database
+#
+# DataDir
+# Data directory setting.
+# Important: DataDir needs to be quoted, as it is a string which may contain space characters.
+# Example: "@prefix@/share/trinitycore"
+#
+# LogsDir
+# Logs directory setting.
+# Important: Logs dir must exists, or all logs need to be disabled
+# Default: "" - no log directory prefix, if used log names isn't absolute path
+# then logs will be stored in current directory for run program.
+#
+#
+# LoginDatabaseInfo
+# WorldDatabaseInfo
+# CharacterDatabaseInfo
+# Database connection settings for the world server.
+# Default: hostname;port;username;password;database
+# .;somenumber;username;password;database - use named pipes at Windows
+# Named pipes: mySQL required adding "enable-named-pipe" to [mysqld] section my.ini
+# .;/path/to/unix_socket;username;password;database - use Unix sockets at Unix/Linux
+# Unix sockets: experimental, not tested
+#
+# MaxPingTime
+# Settings for maximum database-ping interval (minutes between pings)
+#
+# WorldServerPort
+# Default WorldServerPort
+#
+# BindIP
+# Bind World Server to IP/hostname
+#
+###################################################################################################################
+
+RealmID = 1
+DataDir = "."
+LogsDir = ""
+LoginDatabaseInfo = "127.0.0.1;3306;trinity;trinity;realmd"
+WorldDatabaseInfo = "127.0.0.1;3306;trinity;trinity;world"
+CharacterDatabaseInfo = "127.0.0.1;3306;trinity;trinity;characters"
+MaxPingTime = 30
+WorldServerPort = 8085
+BindIP = "0.0.0.0"
+
+###################################################################################################################
+# SCRIPTING SETTINGS
+#
+# Locale
+# Setting for current (DBC) locale to use
+#
+# EventAI Error reporting
+# 0 - Only startup (Default)
+# 1 - Startup errors and Runtime event errors
+# 2 - Startup errors, Runtime event errors, and Creation errors
+###################################################################################################################
+
+Locale = 0
+EAIErrorLevel = 2
+
+###################################################################################################################
+# PERFORMANCE SETINGS
+#
+# UseProcessors
+# Used processors mask for multi-processors system (Used only at Windows)
+# Default: 0 (selected by OS)
+# number (bitmask value of selected processors)
+#
+# ProcessPriority
+# Process priority setting (Used only at Windows)
+# Default: 1 (HIGH)
+# 0 (Normal)
+#
+# Compression
+# Compression level for update packages sent to client (1..9)
+# Default: 1 (speed)
+# 9 (best compression)
+#
+# PlayerLimit
+# Maximum number of players in the world. Excluding Mods, GM's and Admins
+# Default: 100
+# 0 (for infinite players)
+# -1 (for Mods, GM's and Admins only)
+# -2 (for GM's and Admins only)
+# -3 (for Admins only)
+#
+# SaveRespawnTimeImmediately
+# Save respawn time for creatures at death and for gameobjects at use/open
+# Default: 1 (save creature/gameobject respawn time without waiting grid unload)
+# 0 (save creature/gameobject respawn time at grid unload)
+#
+# MaxOverspeedPings
+# Maximum overspeed ping count before player kick (minimum is 2, 0 used for disable check)
+# Default: 2
+#
+# GridUnload
+# Unload grids (if you have lot memory you can disable it to speed up player move to new grids second time)
+# Default: 1 (unload grids)
+# 0 (do not unload grids)
+#
+# SocketSelectTime
+# Socket select time (in milliseconds)
+# Default: 10000
+#
+# GridCleanUpDelay
+# Grid clean up delay (in milliseconds)
+# Default: 300000 (5 min)
+#
+# MapUpdateInterval
+# Map update interval (in milliseconds)
+# Default: 100
+#
+# ChangeWeatherInterval
+# Weather update interval (in milliseconds)
+# Default: 600000 (10 min)
+#
+# PlayerSaveInterval
+# Player save interval (in milliseconds)
+# Default: 900000 (15 min)
+#
+# vmap.enableLOS
+# vmap.enableHeight
+# Enable/Disable VMmap support for line of sight and height calculation
+# Default: 1 (true)
+# 0 (false)
+#
+# vmap.ignoreMapIds
+# Map id that will be ignored by VMaps
+# List of ids with delimiter ','
+# If more then one id is defined and spaces are included, the string has to be enclosed by "
+# Example: "369,0,1,530"
+#
+# vmap.ignoreSpellIds
+# These spells are ignored for LoS calculation
+# List of ids with delimiter ','
+#
+# DetectPosCollision
+# Check final move position, summon position, etc for visible collision with other objects or
+# wall (wall only if vmaps are enabled)
+# Default: 1 (enable, required more CPU power usage)
+# 0 (disable, less nice position selection but will less CPU power usage)
+#
+# TargetPosRecalculateRange
+# Max distance from movement target point (+moving unit size) and targeted object (+size)
+# after that new target movmeent point calculated. Max: melee attack range (5), min: contact range (0.5)
+# More distance let have better performence, less distance let have more sensitive reaction at target move.
+# Default: 1.5
+#
+# UpdateUptimeInterval
+# Update realm uptime period in minutes (for save data in 'uptime' table). Must be > 0
+# Default: 10 (minutes)
+#
+# MaxCoreStuckTime
+# Periodically check if the process got freezed, if this is the case force crash after the specified
+# amount of seconds. Must be > 0. Recommended > 10 secs if you use this.
+# Default: 0 (Disabled)
+#
+# AddonChannel
+# Permit/disable the use of the addon channel through the server
+# (some client side addons can stop work correctly with disabled addon channel)
+# Default: 1 (permit addon channel)
+# 0 (do not permit addon channel)
+#
+###################################################################################################################
+
+UseProcessors = 0
+ProcessPriority = 1
+Compression = 1
+PlayerLimit = 100
+SaveRespawnTimeImmediately = 1
+MaxOverspeedPings = 2
+GridUnload = 1
+SocketSelectTime = 10000
+GridCleanUpDelay = 300000
+MapUpdateInterval = 100
+ChangeWeatherInterval = 600000
+PlayerSaveInterval = 900000
+vmap.enableLOS = 0
+vmap.enableHeight = 0
+vmap.ignoreMapIds = "369"
+vmap.ignoreSpellIds = "7720"
+DetectPosCollision = 1
+TargetPosRecalculateRange = 1.5
+UpdateUptimeInterval = 10
+MaxCoreStuckTime = 0
+AddonChannel = 1
+
+###################################################################################################################
+# SERVER LOGGING
+#
+# LogSQL
+# Enable logging of GM commands - all SQL code will be written to a log file
+# All commands are written to a file: YYYY-MM-DD_logSQL.sql
+# If a new day starts (00:00:00) then a new file is created - the old file will not be deleted.
+# Default: 1 - Write SQL code to logfile
+# 0 - Do not log
+#
+# PidFile
+# World daemon PID file
+# Default: "" - do not create PID file
+# "./worldd.pid" - create PID file (recommended name)
+#
+# LogLevel
+# Server console level of logging
+# 0 = Minimum; 1 = Basic&Error; 2 = Detail; 3 = Full/Debug
+# Default: 3
+#
+# LogTime
+# Include time in server console output [hh:mm:ss]
+# Default: 0 (no time)
+# 1 (print time)
+#
+# LogFile
+# Logfile name
+# Default: "Server.log"
+# "" - Empty name disable creating log file
+#
+# LogTimestamp
+# Logfile with timestamp of server start in name
+# Default: 0 - no timestamp in name
+# 1 - add timestamp in name in form Logname_YYYY-MM-DD_HH-MM-SS.Ext for Logname.Ext
+#
+# LogFileLevel
+# Server file level of logging
+# 0 = Minimum; 1 = Error; 2 = Detail; 3 = Full/Debug
+# Default: 0
+#
+# LogFilter_TransportMoves
+# LogFilter_CreatureMoves
+# LogFilter_VisibilityChanges
+# Log filters
+# Default: 1 - not include with any log level
+# 0 - include in log if log level permit
+#
+# WorldLogFile
+# Packet logging file for the worldserver
+# Default: "world.log"
+#
+# DBErrorLogFile
+# Log file of DB errors detected at server run
+# Default: "DBErrors.log"
+#
+# CharLogFile
+# Character operations logfile name
+# Default: "Char.log"
+# "" - Empty name disable creating log file
+#
+# CharLogTimestamp
+# Logfile with timestamp of server start in name
+# Default: 0 - no timestamp in name
+# 1 - add timestamp in name in form Logname_YYYY-MM-DD_HH-MM-SS.Ext for Logname.Ext
+#
+# CharLogDump
+# Write character dump before deleting in Char.log
+# For restoration, cut character data from log starting from
+# line == START DUMP == to line == END DUMP == (without its) in file and load it using loadpdump command
+# Default: 0 - don't include dumping chars to log
+# 1 - include dumping chars to log
+#
+# GmLogFile
+# Log file of gm commands
+# Default: "gm_commands.log"
+# "" - Empty name for disable
+#
+# GmLogTimestamp
+# GM Logfile with timestamp of server start in name
+# Default: 0 - no timestamp in name
+# 1 - add timestamp in name in form Logname_YYYY-MM-DD_HH-MM-SS.Ext for Logname.Ext
+#
+# GmLogPerAccount
+# GM Logfiles with GM account id (Note: logs not created if GmLogFile not set)
+# Default: 0 - add gm log data to single log file
+# 1 - add gm log data to account specific log files with name
+# in form Logname_#ID_YYYY-MM-DD_HH-MM-SS.Ext
+# or form Logname_#ID.Ext
+#
+# RaLogFile
+# Log file of RA commands
+# Default: "Ra.log"
+# "" - Empty name for disable
+#
+# LogColors
+# Color for messages (format "normal_color details_color debug_color error_color")
+# Colors: 0 - BLACK, 1 - RED, 2 - GREEN, 3 - BROWN, 4 - BLUE, 5 - MAGENTA, 6 - CYAN, 7 - GREY,
+# 8 - YELLOW, 9 - LRED, 10 - LGREEN, 11 - LBLUE, 12 - LMAGENTA, 13 - LCYAN, 14 - WHITE
+# Default: "" - none colors
+# Example: "13 7 11 9"
+#
+###################################################################################################################
+
+LogSQL = 1
+PidFile = ""
+LogLevel = 1
+LogTime = 0
+LogFile = "Server.log"
+LogTimestamp = 0
+LogFileLevel = 0
+LogFilter_TransportMoves = 1
+LogFilter_CreatureMoves = 1
+LogFilter_VisibilityChanges = 1
+WorldLogFile = ""
+DBErrorLogFile = "db_errors.log"
+CharLogFile = "characters.log"
+CharLogTimestamp = 0
+CharLogDump = 0
+GmLogFile = "gm_commands.log"
+GmLogTimestamp = 0
+GmLogPerAccount = 0
+RaLogFile = "ra_commands.log"
+LogColors = ""
+
+###################################################################################################################
+# SERVER SETTINGS
+#
+# GameType
+# Server realm style
+# 0 = NORMAL;1 = PVP; 4 = NORMAL; 6 = RP; 8 = RPPVP
+# also custom type: 16 FFA_PVP (free for all pvp mode like arena PvP in all zones except rest
+# activated places and sanctuaries)
+#
+# RealmZone
+# Server realm zone (set allowed alphabet in character names/etc). See also Strict*Names options.
+#
+# 1 Development - any language (Default)
+# 2 United States - extended-Latin
+# 3 Oceanic - extended-Latin
+# 4 Latin America - extended-Latin
+# 5 Tournament - basic-Latin at create, any at login
+# 6 Korea - East-Asian
+# 7 Tournament - basic-Latin at create, any at login
+# 8 English - extended-Latin
+# 9 German - extended-Latin
+# 10 French - extended-Latin
+# 11 Spanish - extended-Latin
+# 12 Russian - Cyrillic
+# 13 Tournament - basic-Latin at create, any at login
+# 14 Taiwan - East-Asian
+# 15 Tournament - basic-Latin at create, any at login
+# 16 China - East-Asian
+# 17 CN1 - basic-Latin at create, any at login
+# 18 CN2 - basic-Latin at create, any at login
+# 19 CN3 - basic-Latin at create, any at login
+# 20 CN4 - basic-Latin at create, any at login
+# 21 CN5 - basic-Latin at create, any at login
+# 22 CN6 - basic-Latin at create, any at login
+# 23 CN7 - basic-Latin at create, any at login
+# 24 CN8 - basic-Latin at create, any at login
+# 25 Tournament - basic-Latin at create, any at login
+# 26 Test Server - any language
+# 27 Tournament - basic-Latin at create, any at login
+# 28 QA Server - any language
+# 29 CN9 - basic-Latin at create, any at login
+#
+# Expansion
+# Allow server use content from expansion
+# Default: 2 - check expansion 2 maps existence, and if client support expansion 2 and account have
+# expansion 2 setting then allow visit expansion 2 maps, allow create new class character)
+# 1 - check expansion 1 maps existence, and if client support expansion 1 and account have
+# expansion 1 setting then allow visit expansion 1 maps, allow create new races character)
+# 0 - not check expansion maps existence, not allow wisit its, not allow create new race or new class
+# characters, ignore account expansion setting)
+#
+# DBC.Locale
+# DBC Language Settings
+# 0 = English; 1 = Korean; 2 = French; 3 = German; 4 = Chinese; 5 = Taiwanese; 6 = Spanish; 7 = Spanish Mexico
+# 8 = Russian; 255 = Auto Detect (Default)
+#
+# DeclinedNames
+# Allow russian clients to set and use declined names
+# Default: 0 - do not use declined names, except when the Russian RealmZone is set
+# 1 - use declined names
+#
+# StrictPlayerNames
+# Limit player name to language specific symbols set, not allow create characters, and set rename request and disconnect at not allowed symbols name
+# Default: 0 disable (but limited server timezone dependent client check)
+# 1 basic latin characters (strict)
+# 2 realm zone specific (strict). See RealmZone setting.
+# Note: In any case if you want correctly see character name at client this client must have apporopriate fonts
+# (included in client by default, with active official localization or custom localization fonts in clientdir/Fonts).
+# 3 basic latin characters + server timezone specific
+#
+# StrictCharterNames
+# Limit guild/arena team charter names to language specific symbols set, not allow create charters with allowed symbols in name
+# Default: 0 disable
+# 1 basic latin characters (strict)
+# 2 realm zone specific (strict). See RealmZone setting.
+# Note: In any case if you want correctly see character name at client this client must have apporopriate fonts
+# (included in client by default, with active official localization or custom localization fonts in clientdir/Fonts).
+# 3 basic latin characters + server timezone specific
+#
+# StrictPetNames
+# Limit pet names to language specific symbols set
+# Default: 0 disable
+# 1 basic latin characters (strict)
+# 2 realm zone specific (strict). See RealmZone setting.
+# Note: In any case if you want correctly see character name at client this client must have apporopriate fonts
+# (included in client by default, with active official localization or custom localization fonts in clientdir/Fonts).
+# 3 basic latin characters + server timezone specific
+#
+# CharactersCreatingDisabled
+# Disable characters creating for specific team or any (non-player accounts not affected)
+# Default: 0 - enabled
+# 1 - disabled only for Alliance
+# 2 - disabled only for Horde
+# 3 - disabled for both teams
+#
+# MaxWhoListReturns
+# Set the maximum number of players returned in the /who list and interface.
+# Default: 49 (stable)
+#
+# CharactersPerAccount
+# Limit numbers of characters per account (at all realms).
+# Note: this setting limit character creating at _current_ realm base at characters amount at all realms
+# Default: 50
+# The number must be >= CharactersPerRealm
+#
+# CharactersPerRealm
+# Limit numbers of characters for account at realm
+# Default: 10 (client limitation)
+# The number must be between 1 and 10
+#
+# HeroicCharactersPerRealm
+# Limit numbers of heroic class characters for account at realm
+# Default: 1
+# The number must be between 0 (not allowed) and 10
+#
+# MinLevelForHeroicCharacterCreating
+# Limit creating heroic characters only for account with another character of specific level (ignored for GM accounts)
+# 0 - not require any existed chaarcter
+# 1 - require at least any character existed
+# Default: 55 - default requirement
+#
+#
+# SkipCinematics
+# Disable in-game script movie at first character's login(allows to prevent buggy intro in case of custom start location coordinates)
+# Default: 0 - show intro for each new characrer
+# 1 - show intro only for first character of selected race
+# 2 - disable intro show in all cases
+#
+# MaxPlayerLevel
+# Max level that can be reached by player for experience (in range from 1 to 100).
+# Change not recommended
+# Default: 80
+#
+# StartPlayerLevel
+# Staring level that have character at creating (in range 1 to MaxPlayerLevel)
+# Default: 1
+#
+# StartHeroicPlayerLevel
+# Staring level that have character of heroic class at creating (in range 1 to MaxPlayerLevel)
+# Default: 55
+#
+# StartPlayerMoney
+# Amount of money that new players will start with.
+# If you want to start with silver, use for example 100 (100 copper = 1 silver)
+# Default: 0
+#
+# MaxHonorPoints
+# Max honor points that player can have.
+# Default: 75000
+#
+# StartHonorPoints
+# Amount of honor that new players will start with
+# Default: 0
+#
+# MaxArenaPoints
+# Max arena points that player can have.
+# Default: 5000
+#
+# StartArenaPoints
+# Amount of arena points that new players will start with
+# Default: 0
+#
+# InstantLogout
+# Enable or disable instant logout for security level (0..4) or high (NOT in combat/while dueling/while falling)
+# Default: 1 (Mods/GMs/Admins)
+#
+# DisableWaterBreath
+# Disable/enable waterbreathing for security level (0..4) or high
+# Default: 4 (None)
+#
+# AllFlightPaths
+# Players will start with all flight paths (Note: ALL flight paths, not only player's team)
+# Default: 0 (true)
+# 1 (false)
+#
+# AlwaysMaxSkillForLevel
+# Players will automatically gain max level dependent (weapon/defense) skill when logging in, leveling up etc.
+# Default: 0 (false)
+# 1 (true)
+#
+# ActivateWeather
+# Activate weather system
+# Default: 1 (true)
+# 0 (false)
+#
+# Battleground.CastDeserter
+# Cast or not Deserter spell at player who leave battleground in progress
+# Default: 1 (true)
+# 0 (false)
+#
+# Battleground.QueueAnnouncer.Enable
+# Enable queue announcer posting to chat
+# Default: 0 (false)
+# 1 (true)
+#
+# Battleground.QueueAnnouncer.PlayerOnly
+# Enable queue announcer posting to chat
+# Default: 0 (false)
+# 1 (true)
+#
+# Arena.QueueAnnouncer.Enable: Enable queue announcer posting to chat
+# Default: 0 (false)
+# 1 (true)
+#
+# CastUnstuck
+# Allow cast or not Unstuck spell at .start or client Help option use
+# Default: 1 (true)
+# 0 (false)
+#
+# Instance.IgnoreLevel
+# Ignore level requirement to enter instance
+# Default: 0 (false)
+# 1 (true)
+#
+# Instance.IgnoreRaid
+# Ignore raid requirement to enter instance
+# Default: 0 (false)
+# 1 (true)
+#
+# Instance.ResetTimeHour
+# The hour of the day (0-23) when the global instance resets occur.
+# Default: 4
+#
+# Instance.UnloadDelay
+# Unload the instance map from memory after some time if no players are inside.
+# Default: 1800000 (miliseconds, i.e 30 minutes)
+# 0 (instance maps are kept in memory until they are reset)
+#
+# Quests.LowLevelHideDiff
+# Quest level difference to hide for player low level quests:
+# if player_level > quest_level + LowLevelQuestsHideDiff then quest "!" mark not show for quest giver
+# Default: 4
+# -1 (show all available quests marks)
+#
+# Quests.HighLevelHideDiff
+# Quest level difference to hide for player high level quests:
+# if player_level < quest_min_level - HighLevelQuestsHideDiff then quest "!" mark not show for quest giver
+# Default: 7
+# -1 (show all available quests marks)
+#
+# MaxPrimaryTradeSkill
+# Max count that player can learn the primary trade skill.
+# Default: 2
+# Max : 10
+#
+# MinPetitionSigns
+# Min signatures count to creating guild (0..9).
+# Default: 9
+#
+# MaxGroupXPDistance
+# Max distance to creature for group memeber to get XP at creature death.
+# Default: 74
+#
+# MailDeliveryDelay
+# Mail delivery delay time for item sending
+# Default: 3600 sec (1 hour)
+#
+# SkillChance.Prospecting
+# For prospecting skillup impossible by default, but can be allowed as custom setting
+# Default: 0 - no skilups
+# 1 - skilups possible
+#
+# SkillChance.Milling
+# For milling skillup impossible by default, but can be allowed as custom setting
+# Default: 0 - no skilups
+# 1 - skilups possible
+#
+# Event.Announce
+# Default: 0 (false)
+# 1 (true)
+#
+# BeepAtStart
+# Beep at core start finished (mostly work only at Unix/Linux systems)
+# Default: 1 (true)
+# 0 (false)
+#
+# Motd
+# Message of the Day. Displayed at worldlogin for every user ('@' for a newline).
+#
+###################################################################################################################
+
+GameType = 1
+RealmZone = 1
+Expansion = 2
+DBC.Locale = 255
+DeclinedNames = 0
+StrictPlayerNames = 0
+StrictCharterNames = 0
+StrictPetNames = 0
+MaxWhoListReturns = 49
+CharactersCreatingDisabled = 0
+CharactersPerAccount = 50
+CharactersPerRealm = 10
+HeroicCharactersPerRealm = 1
+MinLevelForHeroicCharacterCreating = 55
+SkipCinematics = 0
+MaxPlayerLevel = 80
+StartPlayerLevel = 1
+StartHeroicPlayerLevel = 55
+StartPlayerMoney = 0
+MaxHonorPoints = 75000
+StartHonorPoints = 0
+MaxArenaPoints = 5000
+StartArenaPoints = 0
+InstantLogout = 1
+DisableWaterBreath = 4
+AllFlightPaths = 0
+AlwaysMaxSkillForLevel = 0
+ActivateWeather = 1
+Battleground.CastDeserter = 1
+Battleground.QueueAnnouncer.Enable = 0
+Battleground.QueueAnnouncer.PlayerOnly = 0
+Arena.QueueAnnouncer.Enable = 0
+CastUnstuck = 1
+Instance.IgnoreLevel = 0
+Instance.IgnoreRaid = 0
+Instance.ResetTimeHour = 4
+Instance.UnloadDelay = 1800000
+Quests.LowLevelHideDiff = 4
+Quests.HighLevelHideDiff = 7
+MaxPrimaryTradeSkill = 2
+MinPetitionSigns = 9
+MaxGroupXPDistance = 74
+MailDeliveryDelay = 3600
+SkillChance.Prospecting = 0
+SkillChance.Milling = 0
+Event.Announce = 0
+BeepAtStart = 1
+Motd = "Welcome to a Trinity Core server."
+
+###################################################################################################################
+# PLAYER INTERACTION
+#
+# AllowTwoSide.Accounts
+# Allow or not accounts to create characters in the 2 teams in any game type.
+# Default: 0 (Not allowed)
+# 1 (Allowed)
+#
+# AllowTwoSide.Interaction.Chat
+# AllowTwoSide.Interaction.Channel
+# AllowTwoSide.Interaction.Group
+# AllowTwoSide.Interaction.Guild
+# AllowTwoSide.Interaction.Auction
+# AllowTwoSide.Interaction.Mail
+# Allow or not common :chat(say,yell);channel(chat)group(join)guild(join);merge all auction houses for players from
+# different teams, send mail to different team.
+# Default: 0 (Not allowed)
+# 1 (Allowed)
+#
+# AllowTwoSide.WhoList
+# Allow or not show player from both team in who list.
+# Default: 0 (Not allowed)
+# 1 (Allowed)
+#
+# AllowTwoSide.AddFriend
+# Allow or not adding friends from other team in friend list.
+# Default: 0 (Not allowed)
+# 1 (Allowed)
+#
+# TalentsInspecting
+# Allow other players see character talents in inspect dialog (Characters in Gamemaster mode can
+# inspect talents always)
+# Default: 1 (allow)
+# 0 (not allow)
+#
+###################################################################################################################
+
+AllowTwoSide.Accounts = 0
+AllowTwoSide.Interaction.Chat = 0
+AllowTwoSide.Interaction.Channel = 0
+AllowTwoSide.Interaction.Group = 0
+AllowTwoSide.Interaction.Guild = 0
+AllowTwoSide.Interaction.Auction = 0
+AllowTwoSide.Interaction.Mail = 0
+AllowTwoSide.WhoList = 0
+AllowTwoSide.AddFriend = 0
+TalentsInspecting = 1
+
+###################################################################################################################
+# CREATURE SETTINGS
+#
+# ThreatRadius
+# Radius for creature to evade after being pulled away from combat start point
+# If ThreatRadius is less than creature aggro radius then aggro radius will be used
+# Default: 100 yards
+#
+# Rate.Creature.Aggro
+# Aggro radius percent or off.
+# Default: 1 - 100%
+# 1.5 - 150%
+# 0 - off (0%)
+#
+# CreatureFamilyAssistanceRadius
+# Creature family assistance radius
+# Default: 10
+# 0 - off
+#
+# CreatureFamilyAssistanceDelay
+# Reaction time for creature assistance call
+# Default: 1500 (1.5s)
+#
+# WorldBossLevelDiff
+# Difference for boss dynamic level with target
+# Default: 3
+#
+# Corpse.Decay.NORMAL
+# Corpse.Decay.RARE
+# Corpse.Decay.ELITE
+# Corpse.Decay.RAREELITE
+# Corpse.Decay.WORLDBOSS
+# Seconds until creature corpse will decay without being looted or skinned.
+# Default: 60, 300, 300, 300, 3600
+#
+# Rate.Corpse.Decay.Looted
+# Controls how long the creature corpse stays after it had been looted, as a multiplier of its Corpse.Decay.* config.
+# Default: 0.1
+#
+# Rate.Creature.Normal.Damage
+# Rate.Creature.Elite.Elite.Damage
+# Rate.Creature.Elite.RAREELITE.Damage
+# Rate.Creature.Elite.WORLDBOSS.Damage
+# Rate.Creature.Elite.RARE.Damage
+# Creature Damage Rates.
+# Examples: 2 - creatures will damage 2x, 1.7 - 1.7x.
+#
+# Rate.Creature.Normal.SpellDamage
+# Rate.Creature.Elite.Elite.SpellDamage
+# Rate.Creature.Elite.RAREELITE.SpellDamage
+# Rate.Creature.Elite.WORLDBOSS.SpellDamag
+# Rate.Creature.Elite.RARE.SpellDamage
+# Creature Spell Damage Rates.
+# Examples: 2 - creatures will damage with spells 2x, 1.7 - 1.7x.
+#
+# Rate.Creature.Normal.HP
+# Rate.Creature.Elite.Elite.HP
+# Rate.Creature.Elite.RAREELITE.HP
+# Rate.Creature.Elite.WORLDBOSS.HP
+# Rate.Creature.Elite.RARE.HP
+# Creature Health Ammount Modifier.
+# Examples: 2 - creatures have 2x health, 1.7 - 1.7x.
+#
+# ListenRange.Say
+# Distance from player to listen text that creature (or other world object) say
+# Default: 25
+#
+# ListenRange.TextEmote
+# Distance from player to listen textemote that creature (or other world object) say
+# Default: 25
+#
+# ListenRange.Yell
+# Distance from player to listen text that creature (or other world object) yell
+# Default: 300
+#
+###################################################################################################################
+
+ThreatRadius = 100
+Rate.Creature.Aggro = 1
+CreatureFamilyAssistanceRadius = 10
+CreatureFamilyAssistanceDelay = 1500
+WorldBossLevelDiff = 3
+Corpse.Decay.NORMAL = 60
+Corpse.Decay.RARE = 300
+Corpse.Decay.ELITE = 300
+Corpse.Decay.RAREELITE = 300
+Corpse.Decay.WORLDBOSS = 3600
+Rate.Corpse.Decay.Looted = 0.1
+Rate.Creature.Normal.Damage = 1
+Rate.Creature.Elite.Elite.Damage = 1
+Rate.Creature.Elite.RAREELITE.Damage = 1
+Rate.Creature.Elite.WORLDBOSS.Damage = 1
+Rate.Creature.Elite.RARE.Damage = 1
+Rate.Creature.Normal.SpellDamage = 1
+Rate.Creature.Elite.Elite.SpellDamage = 1
+Rate.Creature.Elite.RAREELITE.SpellDamage = 1
+Rate.Creature.Elite.WORLDBOSS.SpellDamage = 1
+Rate.Creature.Elite.RARE.SpellDamage = 1
+Rate.Creature.Normal.HP = 1
+Rate.Creature.Elite.Elite.HP = 1
+Rate.Creature.Elite.RAREELITE.HP = 1
+Rate.Creature.Elite.WORLDBOSS.HP = 1
+Rate.Creature.Elite.RARE.HP = 1
+ListenRange.Say = 40
+ListenRange.TextEmote = 40
+ListenRange.Yell = 300
+
+###################################################################################################################
+# CHAT SETTINGS
+#
+# ChatFakeMessagePreventing
+# Chat protection from creating fake messages using a lot spaces (other invisible symbols),
+# not applied to addon language messages, but can prevent working old addons
+# that use normal languages for sending data to another clients.
+# Default: 0 (disible fake messages preventing)
+# 1 (enabled fake messages preventing)
+#
+# ChatFlood.MessageCount
+# Chat anti-flood protection, haste message count to activate protection
+# Default: 10
+# 0 (disible anti-flood protection)
+#
+# ChatFlood.MessageDelay
+# Chat anti-flood protection, minimum message delay to count message
+# Default: 1 (in secs)
+#
+# ChatFlood.MuteTime
+# Chat anti-flood protection, mute time at activation flood protection (not saved)
+# Default: 10 (in secs)
+#
+# Channel.RestrictedLfg
+# Restrict use LookupForGroup channel only registered in LFG tool players
+# Default: 1 (allow join to channel only if active in LFG)
+# 0 (allow join to channel in any time)
+#
+# Channel.SilentlyGMJoin
+# Silently join GM characters (security level > 1) to channels
+# Default: 0 (join announcement in normal way)
+# 1 (GM join without announcement)
+#
+###################################################################################################################
+
+ChatFakeMessagePreventing = 0
+ChatFlood.MessageCount = 10
+ChatFlood.MessageDelay = 1
+ChatFlood.MuteTime = 10
+Channel.RestrictedLfg = 1
+Channel.SilentlyGMJoin = 0
+
+###################################################################################################################
+# GAME MASTER SETTINGS
+#
+# GM.LoginState
+# GM mode at login
+# Default: 2 (last save state)
+# 0 (disable)
+# 1 (enable)
+#
+# GM.Visible
+# GM visibility at login
+# Default: 2 (last save state)
+# 0 (invisible)
+# 1 (visible)
+#
+# GM.AcceptTickets
+# Is GM accepting tickets from player by default or not.
+# Default: 2 (last save state)
+# 0 (disable)
+# 1 (enable)
+#
+# GM.Chat
+# GM chat mode at login
+# Default: 2 (last save state)
+# 0 (disable)
+# 1 (enable)
+#
+# GM.WhisperingTo
+# Is GM accepting whispers from player by default or not.
+# Default: 2 (last save state)
+# 0 (disable)
+# 1 (enable)
+#
+# GM.InGMList
+# Is GM showed in GM list (if visible) in non-GM state (.gmoff)
+# Default: 0 (false)
+# 1 (true)
+#
+# GM.InWhoList
+# Is GM showed in who list (if visible).
+# Default: 0 (false)
+# 1 (true)
+#
+# GM.LogTrade
+# Include GM trade and trade slot enchanting operations in GM log if it enable
+# Default: 1 (include)
+# 0 (not include)
+#
+# GM.StartLevel
+# GM starting level (1-100)
+# Default: 1
+#
+# GM.LowerSecurity
+# Disallow a lower security member to interact with a higher one using commands
+# Default: 0 (disable)
+# 1 (enable)
+#
+# GM.AllowAchievementGain
+# If enabled it allows gaining achievements for GM characters
+# Default: 0 (disable)
+# 1 (enable) (default)
+#
+###################################################################################################################
+
+GM.LoginState = 2
+GM.Visible = 2
+GM.AcceptTickets = 2
+GM.Chat = 2
+GM.WhisperingTo = 2
+GM.InGMList = 0
+GM.InWhoList = 0
+GM.LogTrade = 1
+GM.StartLevel = 80
+GM.LowerSecurity = 0
+GM.AllowAchievementGain = 1
+
+###################################################################################################################
+# VISIBILITY AND RADIUSES
+#
+# Visibility.GroupMode
+# Group visibility modes
+# Default: 0 (standard setting: only members from same group can 100% auto detect invisible player)
+# 1 (raid members 100% auto detect invisible player from same raid)
+# 2 (players from same team can 100% auto detect invisible player)
+#
+# Visibility.Distance.Creature
+# Visibility.Distance.Player
+# Visibility distance for different in game object
+# Max limited by active player zone: ~ 166
+# Min limit dependent from objects
+# Default: 66 (cell size)
+# Min limit is max aggro radius (45) * Rate.Creature.Aggro
+#
+# Visibility.Distance.Object
+# Visible distance for gameobject, dynobject, bodies, corpses, bones
+# Min limit is iteraction distance (5)
+#
+# Visibility.Distance.InFlight
+# Visible distance for player in flight
+# Min limit is 0 (not show any objects)
+#
+# Visibility.Distance.Grey.Unit
+# Visibility grey distance for creatures/players (fast changing objects)
+# addition to appropriate object type Visibility.Distance.* use in case visibility removing to
+# object (except corpse around distences) If � is distance and G is grey distance then object
+# make visible if distance to it <= D but make non visible if distance > D+G
+# Default: 1 (yard)
+#
+# Visibility.Distance.Grey.Object
+# Visibility grey distance for dynobjects/gameobjects/corpses/creature bodies
+# Default: 10 (yards)
+#
+#
+###################################################################################################################
+
+Visibility.GroupMode = 0
+Visibility.Distance.Creature = 66
+Visibility.Distance.Player = 66
+Visibility.Distance.Object = 66
+Visibility.Distance.InFlight = 66
+Visibility.Distance.Grey.Unit = 1
+Visibility.Distance.Grey.Object = 10
+
+###################################################################################################################
+# SERVER RATES
+#
+# Rate.Health
+# Rate.Mana
+# Rate.Rage.Income
+# Rate.Rage.Loss
+# Rate.RunicPower.Income
+# Rate.RunicPower.Loss
+# Rate.Focus
+# Health and power regeneration and rage income from damage.
+# Default: 1
+#
+# Rate.Skill.Discovery
+# Skill Discovery Rates
+# Default: 1
+#
+# Rate.Drop.Item.Poor
+# Rate.Drop.Item.Normal
+# Rate.Drop.Item.Uncommon
+# Rate.Drop.Item.Rare
+# Rate.Drop.Item.Epic
+# Rate.Drop.Item.Legendary
+# Rate.Drop.Item.Artifact
+# Rate.Drop.Item.Referenced
+# Rate.Drop.Money
+# Drop rates (items by quality and money)
+# Default: 1
+#
+# Rate.Drop.Money
+# Drop rates
+# Default: 1
+#
+# Rate.XP.Kill
+# Rate.XP.Quest
+# Rate.XP.Explore
+# XP rates
+# Default: 1
+#
+# Rate.Rest.InGame
+# Rate.Rest.Offline.InTavernOrCity
+# Rate.Rest.Offline.InWilderness
+# Resting points grow rates (1 - normal, 2 - double rate, 0.5 - half rate, etc) from standard values
+#
+# Rate.Damage.Fall
+# Damage after fall rate. (1 - standard, 2 - double damage, 0.5 - half damage, etc)
+#
+# Rate.Auction.Time
+# Rate.Auction.Deposit
+# Rate.Auction.Cut
+# Auction rates (auction time, deposit get at auction start, auction cut from price at auction end)
+#
+# Rate.Honor
+# Honor gain rate
+#
+# Rate.Mining.Amount
+# Rate.Mining.Next
+# Mining Rates (Mining.Amount changes minimum/maximum usetimes of a deposit,
+# Mining.Next changes chance to have next use of a deposit)
+#
+# Rate.Talent
+# Talent Point rates
+# Default: 1
+#
+# Rate.Reputation.Gain
+# Reputation Gain rate
+# Default: 1
+#
+# Rate.InstanceResetTime
+# Multiplier for the number of days in between global raid/heroic instance resets.
+# Default: 1
+#
+# SkillGain.Crafting
+# SkillGain.Defense
+# SkillGain.Gathering
+# SkillGain.Weapon
+# crafting/defense/gathering/weapon skills gain at skill grow (1,2,...)
+# Default: 1
+#
+# SkillChance.Orange
+# SkillChance.Yellow
+# SkillChance.Green
+# SkillChance.Grey
+# Skill chance values (0..100)
+# Default: 100-75-25-0
+#
+# SkillChance.MiningSteps
+# SkillChance.SkinningSteps
+# For skinning and Mining chance decrease with skill level.
+# Default: 0 - no decrease
+# 75 - in 2 times each 75 skill points
+#
+# DurabilityLossChance.Damage
+# Chance lost one from equiped items durability point at damage apply or receive.
+# Default: 0.5 (100/0.5 = 200) Each 200 damage apply one from 19 possible equipped items
+#
+# DurabilityLossChance.Absorb
+# Chance lost one from armor items durability point at damage absorb.
+# Default: 0.5 (100/0.5 = 200) Each 200 absorbs apply one from 15 possible armor equipped items
+#
+# DurabilityLossChance.Parry
+# Chance lost weapon durability point at parry.
+# Default: 0.05 (100/0.05 = 2000) Each 2000 parry attacks main weapon lost point
+#
+# DurabilityLossChance.Block
+# Chance lost sheild durability point at damage block.
+# Default: 0.05 (100/0.05 = 2000) Each 2000 partly or full blocked attacks shield lost point
+#
+# Death.SicknessLevel
+# Starting Character start gain sickness at spirit resurrection (1 min)
+# Default: 11
+# -10 - character will have full time (10min) sickness at 1 level
+# maxplayerlevel+1 - chaarcter will not have sickess at any level
+#
+# Death.CorpseReclaimDelay.PvP
+# Death.CorpseReclaimDelay.PvE
+# Enabled/disabled increase corpse reclaim delay at often PvP/PvE deaths
+# Default: 1 (enabled)
+# 0 (disabled)
+#
+# Death.Bones.World
+# Death.Bones.BattlegroundOrArena
+# Enabled/disabled creating bones instead corpse at resurrection (in normal zones/instacnes, or battleground/arenas)
+# Default: 1 (enabled)
+# 0 (disabled)
+#
+###################################################################################################################
+
+Rate.Health = 1
+Rate.Mana = 1
+Rate.Rage.Income = 1
+Rate.Rage.Loss = 1
+Rate.RunicPower.Income = 1
+Rate.RunicPower.Loss = 1
+Rate.Focus = 1
+Rate.Skill.Discovery = 1
+Rate.Drop.Item.Poor = 1
+Rate.Drop.Item.Normal = 1
+Rate.Drop.Item.Uncommon = 1
+Rate.Drop.Item.Rare = 1
+Rate.Drop.Item.Epic = 1
+Rate.Drop.Item.Legendary = 1
+Rate.Drop.Item.Artifact = 1
+Rate.Drop.Item.Referenced = 1
+Rate.Drop.Money = 1
+Rate.XP.Kill = 1
+Rate.XP.Quest = 1
+Rate.XP.Explore = 1
+Rate.Rest.InGame = 1
+Rate.Rest.Offline.InTavernOrCity = 1
+Rate.Rest.Offline.InWilderness = 1
+Rate.Damage.Fall = 1
+Rate.Auction.Time = 1
+Rate.Auction.Deposit = 1
+Rate.Auction.Cut = 1
+Rate.Honor = 1
+Rate.Mining.Amount = 1
+Rate.Mining.Next = 1
+Rate.Talent = 1
+Rate.Reputation.Gain = 1
+Rate.InstanceResetTime = 1
+SkillGain.Crafting = 1
+SkillGain.Defense = 1
+SkillGain.Gathering = 1
+SkillGain.Weapon = 1
+SkillChance.Orange = 100
+SkillChance.Yellow = 75
+SkillChance.Green = 25
+SkillChance.Grey = 0
+SkillChance.MiningSteps = 0
+SkillChance.SkinningSteps = 0
+DurabilityLossChance.Damage = 0.5
+DurabilityLossChance.Absorb = 0.5
+DurabilityLossChance.Parry = 0.05
+DurabilityLossChance.Block = 0.05
+Death.SicknessLevel = 11
+Death.CorpseReclaimDelay.PvP = 1
+Death.CorpseReclaimDelay.PvE = 1
+Death.Bones.World = 1
+Death.Bones.BattlegroundOrArena = 1
+
+###################################################################################################################
+#
+# Rated arena matches config
+#
+# MaxRatingDifference: the maximum rating difference between two groups in rated matches
+# Default: 0 (disable, rating difference is discarded)
+#
+# RatingDiscardTimer: after the specified milliseconds has passed,
+# rating information will be discarded when selecting teams for matches
+# also initiates an update by this timer
+# Default: 60000
+#
+# AutoDistributePoints: set if arena points should be distributed automatically, or by GM command
+# Default: 0 (disable) (recommended): use gm command or sql query to distribute the points
+# 1 (enable): arena points are distributed automatically
+#
+# AutoDistributeInterval: how often should the distribution take place
+# if automatic distribution is enabled
+# in days
+# Default: 7 (weekly)
+#
+# ArenaSeason.ID: current area season id show in client
+# Default: 1
+#
+# ArenaSeason.InProgress: current area season state
+# Default: 1 (active)
+# 0 (finished)
+#
+###################################################################################################################
+
+Arena.MaxRatingDifference = 0
+Arena.RatingDiscardTimer = 60000
+Arena.AutoDistributePoints = 0
+Arena.AutoDistributeInterval = 7
+Arena.ArenaSeason.ID = 1
+Arena.ArenaSeason.InProgress = 1
+
+###################################################################################################################
+#
+# Battleground config
+#
+# PrematureFinishTimer: the time to end the bg if there are less than minplayersperteam on one side
+# in milliseconds
+# Default: 300000
+# 0 - disable
+#
+###################################################################################################################
+
+BattleGround.PrematureFinishTimer = 300000
+
+
+###################################################################################################################
+#
+# NETWORK CONFIG
+#
+# Network.Threads
+# Number of threads for network, recommend 1 thread per 1000 connections.
+# Default: 1
+#
+# Network.OutKBuff
+# The size of the output kernel buffer used ( SO_SNDBUF socket option, tcp manual ).
+# Default: -1 (Use system default setting)
+#
+# Network.OutUBuff
+# Userspace buffer for output. This is amount of memory reserved per each connection.
+# Default: 65536
+#
+# Network.TcpNoDelay:
+# TCP Nagle algorithm setting
+# Default: 0 (enable Nagle algorithm, less traffic, more latency)
+# 1 (TCP_NO_DELAY, disable Nagle algorithm, more traffic but less latency)
+#
+###################################################################################################################
+
+Network.Threads = 1
+Network.OutKBuff = -1
+Network.OutUBuff = 65536
+Network.TcpNodelay = 1
+
+###################################################################################################################
+# CONSOLE AND REMOTE ACCESS
+#
+# Console.Enable
+# Enable console
+# Default: 1 - on
+# 0 - off
+#
+# Ra.Enable
+# Enable remote console
+# Default: 0 - off
+# 1 - on
+#
+# Ra.IP
+# Default remote console ip address, use 0.0.0.0 for every address
+#
+# Ra.Port
+# Default remote console port
+#
+# Ra.MinLevel
+# Minimum level that's required to login,3 by default
+#
+# Ra.Secure
+# Kick client on wrong pass
+#
+###################################################################################################################
+
+Console.Enable = 1
+Ra.Enable = 0
+Ra.IP = 0.0.0.0
+Ra.Port = 3443
+Ra.MinLevel = 3
+Ra.Secure = 1
+
+###################################################################################################################
+# CUSTOM SERVER OPTIONS
+#
+# PlayerStart.AllReputation
+# Players will start with most of the high level reputations that are needed for items, mounts etc.
+# If there are any reputation faction you want to be added, just tell me.
+#
+# PlayerStart.AllSpells
+# If enabled, players will start with all their class spells (not talents). Useful for instant 70 servers.
+# You must import playercreateinfo_spell_custom.sql, it's included in the SQL folder.
+# Default: 0 - off
+# 1 - on
+#
+# PlayerStart.MapsExplored
+# Players will start with all maps explored if enabled
+#
+# MusicInBattleground
+# If enabled, "L70ETC - Power of the horde" will be played when BG starts ;)
+#
+# HonorPointsAfterDuel
+# The amount of honor points the duel winner will get after a duel.
+# Default: 0 - disable
+#
+# AlwaysMaxWeaponSkill
+# Players will automatically gain max weapon/defense skill when logging in, leveling up etc.
+#
+# PvPToken.Enable
+# Enable/disable PvP Token System. Players will get a token after slaying another player that gives honor.
+#
+# PvPToken.MapAllowType
+# Where players can receive the pvp token
+# 4 - In all maps
+# 3 - In battlegrounds only
+# 2 - In FFA areas only (gurubashi arena etc)
+# 1 - In battlegrounds AND FFA areas only
+#
+# PvPToken.ItemID
+# The item players will get after killing someone if PvP Token system is enabled.
+# Default: 29434 - Badge of justice
+#
+# PvPToken.ItemCount
+# Modify the item ID count - Default: 1
+#
+# NoResetTalentsCost
+# Enable or disable no cost when reseting talents
+#
+# ForbiddenMaps
+# map ids that users below SEC_GAMEMASTER cannot enter, with delimiter ','
+# Default: ""
+# example: "538,90"
+# Note that it's HIGHLY DISCOURAGED to forbid starting maps (0, 1, 530)!
+#
+# ShowKickInWorld
+# determines wether a message is broadcasted to the entire server when a player gets kicked
+# Default: 0
+# 1 = Enable
+# 0 = Disable
+#
+# RecordUpdateTimeDiffInterval
+# record update time diff to the log file
+# update diff can be used as a criterion of performance
+# diff < 300: good performance
+# diff > 600: bad performance, may be caused by high cpu usage
+# Default: 60000 (diff is written into log every 60000 ms or 1 minute.
+# >0 = Interval
+# 0 = Disable
+#
+# PlayerStart.String
+# If set to anything else than "", this string will be displayed to players when they login
+# to a newly created character.
+# Default: "" - send no text
+#
+###################################################################################################################
+
+PlayerStart.AllReputation = 0
+PlayerStart.AllSpells = 0
+PlayerStart.MapsExplored = 0
+MusicInBattleground = 0
+HonorPointsAfterDuel = 0
+AlwaysMaxWeaponSkill = 0
+PvPToken.Enable = 0
+PvPToken.MapAllowType = 4
+PvPToken.ItemID = 29434
+PvPToken.ItemCount = 1
+NoResetTalentsCost = 0
+ShowKickInWorld = 0
+RecordUpdateTimeDiffInterval = 60000
+PlayerStart.String = ""
diff --git a/src/mangosd/mangosd.rc b/src/mangosd/mangosd.rc
new file mode 100644
index 00000000000..4e6510c0407
--- /dev/null
+++ b/src/mangosd/mangosd.rc
@@ -0,0 +1,85 @@
+/*
+ * Copyright (C) 2005-2008 MaNGOS <http://www.mangosproject.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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#include "resource.h"
+
+#define APSTUDIO_READONLY_SYMBOLS
+/////////////////////////////////////////////////////////////////////////////
+//
+// Generated from the TEXTINCLUDE 2 resource.
+//
+#include "windows.h"
+
+/////////////////////////////////////////////////////////////////////////////
+#undef APSTUDIO_READONLY_SYMBOLS
+
+/////////////////////////////////////////////////////////////////////////////
+//
+// Icon
+//
+
+// Icon with lowest ID value placed first to ensure application icon
+// remains consistent on all systems.
+IDI_APPICON ICON "TrinityCore.ico"
+
+/////////////////////////////////////////////////////////////////////////////
+// Neutre (Par défaut système) resources
+
+#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_NEUSD)
+#ifdef _WIN32
+LANGUAGE LANG_NEUTRAL, SUBLANG_SYS_DEFAULT
+#pragma code_page(1252)
+#endif //_WIN32
+
+/////////////////////////////////////////////////////////////////////////////
+//
+// Version
+//
+
+VS_VERSION_INFO VERSIONINFO
+ FILEVERSION 0,4,6743,685
+ PRODUCTVERSION 0,4,6743,685
+ FILEFLAGSMASK 0x17L
+#ifdef _DEBUG
+ FILEFLAGS 0x1L
+#else
+ FILEFLAGS 0x0L
+#endif
+ FILEOS 0x0L
+ FILETYPE 0x0L
+ FILESUBTYPE 0x0L
+BEGIN
+ BLOCK "StringFileInfo"
+ BEGIN
+ BLOCK "080004b0"
+ BEGIN
+ VALUE "FileDescription", "TrinityCore"
+ VALUE "FileVersion", "0, 4, 6743, 685"
+ VALUE "InternalName", "TrinityCore"
+ VALUE "LegalCopyright", "Copyright (C) 2008"
+ VALUE "OriginalFilename", "TrinityCore.exe"
+ VALUE "ProductName", "TrinityCore"
+ VALUE "ProductVersion", "0, 4, 6743, 685"
+ END
+ END
+ BLOCK "VarFileInfo"
+ BEGIN
+ VALUE "Translation", 0x800, 1200
+ END
+END
+#endif
diff --git a/src/mangosd/monitor-mangosd b/src/mangosd/monitor-mangosd
new file mode 100644
index 00000000000..a740ae5e8fa
--- /dev/null
+++ b/src/mangosd/monitor-mangosd
@@ -0,0 +1,18 @@
+#!/bin/bash
+# Massive Network Game Object Server
+# Monitoring Script
+
+pid=`ps ax | awk '($5 ~ /mangos-worldd/) { print $1 }'`
+cpu=`top -b -n 1 -p $pid | awk '($12 ~ /mangos-worldd/) { print $9 }'`
+#echo $pid
+#echo $cpu
+intcpu=${cpu%.*}
+#echo $intcpu
+if [ "$intcpu" -gt "95" ]
+then
+ kill -9 $pid
+ echo "Killed MaNGOS for exceeding it's cpu limit."
+ echo `date` ", Killed MaNGOS for $intcpu% CPU Usage." >> serverlog
+else
+ echo "MaNGOS Passes the cpu test."
+fi
diff --git a/src/mangosd/resource.h b/src/mangosd/resource.h
new file mode 100644
index 00000000000..7e7d8e4b76f
--- /dev/null
+++ b/src/mangosd/resource.h
@@ -0,0 +1,15 @@
+//{{NO_DEPENDENCIES}}
+// Microsoft Visual C++ generated include file.
+// Used by TrinityCore.rc
+//
+
+// Next default values for new objects
+//
+#ifdef APSTUDIO_INVOKED
+#ifndef APSTUDIO_READONLY_SYMBOLS
+#define _APS_NEXT_RESOURCE_VALUE 101
+#define _APS_NEXT_COMMAND_VALUE 40001
+#define _APS_NEXT_CONTROL_VALUE 1000
+#define _APS_NEXT_SYMED_VALUE 101
+#endif
+#endif
diff --git a/src/mangosd/run-mangosd b/src/mangosd/run-mangosd
new file mode 100644
index 00000000000..f307bd9e1ad
--- /dev/null
+++ b/src/mangosd/run-mangosd
@@ -0,0 +1,14 @@
+#!/bin/bash
+# Trinity Server
+# autorestart Script
+
+while :
+do
+ echo "TrinityCore daemon restarted"
+ echo `date` >> crash.log &
+ ./mangosd | tail -n 20 >> crash.log
+ echo " " >> crash.log &
+ pid=`ps ax | awk '($5 ~ /trinitycore/) { print $1 }'`
+ wait $pid
+ echo `date` ", TrinityCore daemon crashed and restarted." >> serverlog
+done