Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- // RAServerController.cpp : main Windows Service project file.
- #include "stdafx.h"
- #include "RAServerController.h"
- #include "Global.h"
- #include "GameServerDescriptor.h"
- #include "MonitorDescriptor.h"
- #include "smallobj/SmallObj.h"
- #undef GetCurrentDirectory
- // ************************************************************************************************************************************************************
- #define MAIN_THREAD_SLEEP_TIME_GAP 200
- #define PERFORMANCE_MEASURE_TIME_GAP 500 // 500 ms
- #define COUNTER_SERVER_TIME_GAP 600000 // 10 min
- // ************************************************************************************************************************************************************
- using namespace Runewaker;
- // ************************************************************************************************************************************************************
- //To install/uninstall the service, type: "RAServerController.exe -Install [-u]"
- int _tmain(int argc, _TCHAR* argv[])
- {
- #ifndef _DEBUG
- if (argc >= 2)
- {
- if (argv[1][0] == _T('/'))
- {
- argv[1][0] = _T('-');
- }
- if (_tcsicmp(argv[1], _T("-Install")) == 0)
- {
- array<String^>^ myargs = System::Environment::GetCommandLineArgs();
- array<String^>^ args = gcnew array<String^>(myargs->Length - 1);
- // Set args[0] with the full path to the assembly,
- Assembly^ assem = Assembly::GetExecutingAssembly();
- args[0] = assem->Location;
- Array::Copy(myargs, 2, args, 1, args->Length - 1);
- AppDomain^ dom = AppDomain::CreateDomain(L"execDom");
- Type^ type = System::Object::typeid;
- String^ path = type->Assembly->Location;
- StringBuilder^ sb = gcnew StringBuilder(path->Substring(0, path->LastIndexOf(L"\\")));
- sb->Append(L"\\InstallUtil.exe");
- Evidence^ evidence = gcnew Evidence();
- dom->ExecuteAssembly(sb->ToString(), evidence, args);
- }
- }
- else
- {
- //----------------------------------------------------------------------
- // Change Current Working Directory
- System::Diagnostics::Process^ p = System::Diagnostics::Process::GetCurrentProcess();
- String^ moduleFileName = p->MainModule->FileName;
- String^ workingDirectory = moduleFileName->Remove(moduleFileName->LastIndexOf("\\"));
- Directory::SetCurrentDirectory(workingDirectory);
- //----------------------------------------------------------------------
- ServiceBase::Run(gcnew RAServerController());
- }
- #else
- System::Diagnostics::Process^ p = System::Diagnostics::Process::GetCurrentProcess();
- String^ moduleFileName = p->MainModule->FileName;
- String^ workingDirectory = moduleFileName->Remove(moduleFileName->LastIndexOf("\\"));
- Directory::SetCurrentDirectory(workingDirectory);
- RAServerController^ myService = gcnew RAServerController();
- myService->onDebug();
- System::Threading::Thread::Sleep(System::Threading::Timeout::Infinite);
- #endif
- }
- // ************************************************************************************************************************************************************
- namespace Runewaker
- {
- void RAServerController::onDebug()
- {
- OnStart(nullptr);
- }
- //---------------------------------------------------------------------------------------------------------------------
- //
- //---------------------------------------------------------------------------------------------------------------------
- void RAServerController::OnStart(array<String^>^ args)
- {
- #ifndef _DEBUG
- //----------------------------------------------------------------------
- // Initialize event log
- System::String^ eventSource = "RA Server Controller";
- System::String^ logName = "RA Server Controller Log";
- // Verify that the event source exists
- if(!Diagnostics::EventLog::SourceExists(eventSource))
- {
- // Create event source if it does not exist
- Diagnostics::EventLog::CreateEventSource(eventSource, logName);
- }
- m_log = gcnew Diagnostics::EventLog(logName);
- m_log->Source = eventSource;
- // Modify overflow policy
- m_log->ModifyOverflowPolicy(Diagnostics::OverflowAction::OverwriteAsNeeded, 7);
- //----------------------------------------------------------------------
- //----------------------------------------------------------------------
- // Acquire registry key
- m_configuratonFilePath = "";
- RegistryKey ^softwareRegKey = Registry::LocalMachine->OpenSubKey("Software");
- RegistryKey ^runewakerRegKey = softwareRegKey->OpenSubKey("Runewaker");
- if(runewakerRegKey)
- {
- RegistryKey ^raSrvCtrlRegKey = runewakerRegKey->OpenSubKey("RA Server Controller");
- if(raSrvCtrlRegKey)
- {
- // Load program settings from registry
- m_configuratonFilePath = safe_cast<System::String ^>(raSrvCtrlRegKey->GetValue("Configuration File Path", ""));
- }
- }
- //----------------------------------------------------------------------
- RAServerController::LogEvent("Registry keys read, log object generated.", Diagnostics::EventLogEntryType::Information);
- #else
- System::Diagnostics::Process^ p = System::Diagnostics::Process::GetCurrentProcess();
- String^ moduleFileName = p->MainModule->FileName;
- String^ workingDirectory = moduleFileName->Remove(moduleFileName->LastIndexOf("\\"));
- m_configuratonFilePath = System::String::Format("{0}\\RAServerController.ini", workingDirectory);
- RAServerController::LogEvent("Configuration loaded.", Diagnostics::EventLogEntryType::Information);
- #endif
- m_PerformanceCounter = gcnew PerformanceCounter("Processor", "% Processor Time", "_Total");
- //Global Init
- Global::Init();
- LoadServerDescriptions();
- // Initialize service thread
- Threading::ThreadStart ^threadStart = gcnew Threading::ThreadStart(this, &RAServerController::ServiceLoop);
- m_serviceThread = gcnew Threading::Thread(threadStart);
- m_serviceThread->Start();
- RAServerController::LogEvent("Main service thread started.", Diagnostics::EventLogEntryType::Information);
- }
- //---------------------------------------------------------------------------------------------------------------------
- //
- //---------------------------------------------------------------------------------------------------------------------
- void RAServerController::OnStop()
- {
- //CNetService::OnStop();
- RAServerController::m_stopping = true;
- // Terminate servers
- PG_CtoM_ClearServerInfo Packet;
- MonitorDescriptorManager::SendToAllMonitor(sizeof(Packet), &Packet);
- Global::Release();
- }
- //---------------------------------------------------------------------------------------------------------------------
- //
- //---------------------------------------------------------------------------------------------------------------------
- bool RAServerController::LogEvent(System::String ^eventString, Diagnostics::EventLogEntryType entryType)
- {
- #ifndef _DEBUG
- try
- {
- m_log->WriteEntry(eventString, entryType);
- }
- catch (...)
- {
- return false;
- }
- #else
- System::String ^eventMessage = System::String::Format("[{0}] {1}\n", entryType, eventString);
- printf(StringToChar(eventMessage));
- #endif
- return true;
- }
- //---------------------------------------------------------------------------------------------------------------------
- //
- //---------------------------------------------------------------------------------------------------------------------
- void RAServerController::ServiceLoop()
- {
- m_stopping = false;
- while(!m_stopping)
- {
- //check Schedular Event
- SchedularEvent();
- //
- Global::Process();
- // Sleep for some period of time
- Threading::Thread::Sleep(MAIN_THREAD_SLEEP_TIME_GAP);
- }
- }
- //---------------------------------------------------------------------------------------------------------------------
- //
- //---------------------------------------------------------------------------------------------------------------------
- void RAServerController::SchedularEvent()
- {
- unsigned long dwNowTick = Global::GetNowTick();
- unsigned long dwGap = 0;
- //-----------------------------------------------------------
- if (GameServerDescriptorManager::LoadConfigRequest)
- {
- LoadServerDescriptions();
- }
- //-----------------------------------------------------------
- //-----------------------------------------------------------
- if (GameServerDescriptorManager::SaveConfigRequest)
- {
- SaveServerDescriptions();
- }
- //-----------------------------------------------------------
- //-----------------------------------------------------------
- // update Performance Counter
- dwGap = dwNowTick - m_LastUpdatePerformanceCounterTick;
- if (dwGap >= PERFORMANCE_MEASURE_TIME_GAP)
- {
- Global::UpdateGlobalPerformanceData((int)m_PerformanceCounter->NextValue());
- m_LastUpdatePerformanceCounterTick = dwNowTick;
- }
- //-----------------------------------------------------------
- //-----------------------------------------------------------
- // Log registered server count
- dwGap = dwNowTick - m_LastCountServerTick;
- if (dwGap >= COUNTER_SERVER_TIME_GAP)
- {
- System::String ^eventMessage = System::String::Format("Registered server count is {0}.", GameServerDescriptorManager::GetServerCount());
- LogEvent(eventMessage, Diagnostics::EventLogEntryType::Information);
- m_LastCountServerTick = dwNowTick;
- }
- //-----------------------------------------------------------
- }
- //---------------------------------------------------------------------------------------------------------------------
- //
- //---------------------------------------------------------------------------------------------------------------------
- const char* RAServerController::StringToChar(String^ strValue)
- {
- static std::string Result = "";
- Encoding^ ec = Encoding::UTF8;
- array<unsigned char>^ charArray = ec->GetBytes(strValue);
- pin_ptr<char> pinnedChar = interior_ptr<char>(&charArray[0]);
- Result = pinnedChar;
- return Result.c_str();
- }
- //---------------------------------------------------------------------------------------------------------------------
- //
- //---------------------------------------------------------------------------------------------------------------------
- void RAServerController::LoadServerDescriptions()
- {
- std::vector<std::vector<std::string>>& vecDescs = GameServerDescriptorManager::vecLoadData;
- vecDescs.clear();
- String ^line = nullptr;
- String^ strSplitor = "\t\"";
- // Open configuration file
- if(File::Exists(m_configuratonFilePath))
- {
- StreamReader ^reader = File::OpenText(m_configuratonFilePath);
- // Read all lines in configuration file
- while ((line = reader->ReadLine()) != nullptr)
- {
- array<String^>^ arrayParas = line->Split(strSplitor->ToCharArray(), StringSplitOptions::RemoveEmptyEntries);
- if (arrayParas->Length >= 5)
- {
- std::vector<std::string> vecTmp;
- vecTmp.clear();
- vecDescs.push_back(vecTmp);
- std::vector<std::string>& vecParas = vecDescs[vecDescs.size() - 1];
- System::Collections::IEnumerator^ enumParameters = arrayParas->GetEnumerator();
- while ( (enumParameters->MoveNext()) && (enumParameters->Current != nullptr) )
- {
- std::string strTmp = StringToChar(dynamic_cast<System::String ^>(enumParameters->Current));
- vecParas.push_back(strTmp.c_str());
- }
- }
- }
- reader->Close();
- }
- GameServerDescriptorManager::LoadConfigRequest = false;
- GameServerDescriptorManager::LoadServerDescription();
- unsigned long dwPacketSize = 0;
- void* pData = GameServerDescriptorManager::GatherAllGameServerInfo(&dwPacketSize);
- MonitorDescriptorManager::SendToAllMonitor(dwPacketSize, pData);
- }
- //---------------------------------------------------------------------------------------------------------------------
- //
- //---------------------------------------------------------------------------------------------------------------------
- void RAServerController::SaveServerDescriptions()
- {
- std::vector<std::string>& vecDescs = GameServerDescriptorManager::vecSaveData;
- StringBuilder^ sb = gcnew StringBuilder(2048);
- for(int i = 0; i < (int)vecDescs.size(); ++i)
- {
- sb->Append(gcnew String(Utf8ToWchar(vecDescs[i].c_str()).c_str()));
- sb->Append("\r\n");
- }
- File::WriteAllText(m_configuratonFilePath, sb->ToString(), Encoding::Unicode);
- GameServerDescriptorManager::SaveConfigRequest = false;
- }
- }
- // ************************************************************************************************************************************************************
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement