1
0
mirror of https://github.com/vcmi/vcmi.git synced 2024-12-24 22:14:36 +02:00

Merge pull request #3609 from IvanSavenko/single_process

Allow running server as part of client process
This commit is contained in:
Ivan Savenko 2024-02-14 12:06:22 +02:00 committed by GitHub
commit 9ebd194ab1
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
39 changed files with 1203 additions and 1282 deletions

View File

@ -24,12 +24,12 @@ set(battleAI_HEADERS
BattleExchangeVariant.h
)
if(NOT ENABLE_STATIC_AI_LIBS)
if(NOT ENABLE_STATIC_LIBS)
list(APPEND battleAI_SRCS main.cpp StdInc.cpp)
endif()
assign_source_group(${battleAI_SRCS} ${battleAI_HEADERS})
if(ENABLE_STATIC_AI_LIBS)
if(ENABLE_STATIC_LIBS)
add_library(BattleAI STATIC ${battleAI_SRCS} ${battleAI_HEADERS})
else()
add_library(BattleAI SHARED ${battleAI_SRCS} ${battleAI_HEADERS})
@ -37,7 +37,7 @@ else()
endif()
target_include_directories(BattleAI PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
target_link_libraries(BattleAI PRIVATE ${VCMI_LIB_TARGET} TBB::tbb)
target_link_libraries(BattleAI PRIVATE vcmi TBB::tbb)
vcmi_set_output_dir(BattleAI "AI")
enable_pch(BattleAI)

View File

@ -8,12 +8,12 @@ set(emptyAI_HEADERS
CEmptyAI.h
)
if(NOT ENABLE_STATIC_AI_LIBS)
if(NOT ENABLE_STATIC_LIBS)
list(APPEND emptyAI_SRCS main.cpp StdInc.cpp)
endif()
assign_source_group(${emptyAI_SRCS} ${emptyAI_HEADERS})
if(ENABLE_STATIC_AI_LIBS)
if(ENABLE_STATIC_LIBS)
add_library(EmptyAI STATIC ${emptyAI_SRCS} ${emptyAI_HEADERS})
else()
add_library(EmptyAI SHARED ${emptyAI_SRCS} ${emptyAI_HEADERS})
@ -21,7 +21,7 @@ else()
endif()
target_include_directories(EmptyAI PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
target_link_libraries(EmptyAI PRIVATE ${VCMI_LIB_TARGET})
target_link_libraries(EmptyAI PRIVATE vcmi)
vcmi_set_output_dir(EmptyAI "AI")
enable_pch(EmptyAI)

View File

@ -125,12 +125,12 @@ set(Nullkiller_HEADERS
AIGateway.h
)
if(NOT ENABLE_STATIC_AI_LIBS)
if(NOT ENABLE_STATIC_LIBS)
list(APPEND Nullkiller_SRCS main.cpp StdInc.cpp)
endif()
assign_source_group(${Nullkiller_SRCS} ${Nullkiller_HEADERS})
if(ENABLE_STATIC_AI_LIBS)
if(ENABLE_STATIC_LIBS)
add_library(Nullkiller STATIC ${Nullkiller_SRCS} ${Nullkiller_HEADERS})
else()
add_library(Nullkiller SHARED ${Nullkiller_SRCS} ${Nullkiller_HEADERS})
@ -138,7 +138,7 @@ else()
endif()
target_include_directories(Nullkiller PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
target_link_libraries(Nullkiller PUBLIC ${VCMI_LIB_TARGET} fuzzylite::fuzzylite TBB::tbb)
target_link_libraries(Nullkiller PUBLIC vcmi fuzzylite::fuzzylite TBB::tbb)
vcmi_set_output_dir(Nullkiller "AI")
enable_pch(Nullkiller)

View File

@ -8,19 +8,19 @@ set(stupidAI_HEADERS
StupidAI.h
)
if(NOT ENABLE_STATIC_AI_LIBS)
if(NOT ENABLE_STATIC_LIBS)
list(APPEND stupidAI_SRCS main.cpp StdInc.cpp)
endif()
assign_source_group(${stupidAI_SRCS} ${stupidAI_HEADERS})
if(ENABLE_STATIC_AI_LIBS)
if(ENABLE_STATIC_LIBS)
add_library(StupidAI STATIC ${stupidAI_SRCS} ${stupidAI_HEADERS})
else()
add_library(StupidAI SHARED ${stupidAI_SRCS} ${stupidAI_HEADERS})
install(TARGETS StupidAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR})
endif()
target_link_libraries(StupidAI PRIVATE ${VCMI_LIB_TARGET})
target_link_libraries(StupidAI PRIVATE vcmi)
target_include_directories(StupidAI PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
vcmi_set_output_dir(StupidAI "AI")

View File

@ -94,12 +94,12 @@ set(VCAI_HEADERS
VCAI.h
)
if(NOT ENABLE_STATIC_AI_LIBS)
if(NOT ENABLE_STATIC_LIBS)
list(APPEND VCAI_SRCS main.cpp StdInc.cpp)
endif()
assign_source_group(${VCAI_SRCS} ${VCAI_HEADERS})
if(ENABLE_STATIC_AI_LIBS)
if(ENABLE_STATIC_LIBS)
add_library(VCAI STATIC ${VCAI_SRCS} ${VCAI_HEADERS})
else()
add_library(VCAI SHARED ${VCAI_SRCS} ${VCAI_HEADERS})
@ -107,7 +107,7 @@ else()
endif()
target_include_directories(VCAI PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
target_link_libraries(VCAI PUBLIC ${VCMI_LIB_TARGET} fuzzylite::fuzzylite)
target_link_libraries(VCAI PUBLIC vcmi fuzzylite::fuzzylite)
vcmi_set_output_dir(VCAI "AI")
enable_pch(VCAI)

View File

@ -41,42 +41,69 @@ if(NOT CMAKE_BUILD_TYPE)
set_property(CACHE CMAKE_BUILD_TYPE PROPERTY STRINGS Debug Release RelWithDebInfo)
endif()
set(buildLobby OFF)
set(singleProcess OFF)
set(staticAI OFF)
if(ANDROID)
set(staticAI ON)
set(singleProcess ON)
endif()
# Platform-independent options
option(ENABLE_ERM "Enable compilation of ERM scripting module" OFF)
option(ENABLE_LUA "Enable compilation of LUA scripting module" OFF)
if(NOT ANDROID)
option(ENABLE_LAUNCHER "Enable compilation of launcher" ON)
option(ENABLE_EDITOR "Enable compilation of map editor" ON)
endif()
option(ENABLE_TRANSLATIONS "Enable generation of translations for launcher and editor" ON)
option(ENABLE_NULLKILLER_AI "Enable compilation of Nullkiller AI library" ON)
option(ENABLE_GITVERSION "Enable Version.cpp with Git commit hash" ON)
# Compilation options
option(ENABLE_PCH "Enable compilation using precompiled headers" ON)
option(ENABLE_DEBUG_CONSOLE "Enable debug console for Windows builds" ON)
option(ENABLE_STRICT_COMPILATION "Treat all compiler warnings as errors" OFF)
option(ENABLE_MULTI_PROCESS_BUILDS "Enable /MP flag for MSVS solution" ON)
option(ENABLE_COLORIZED_COMPILER_OUTPUT "Colorize compilation output (Clang/GNU)." ON)
option(ENABLE_CCACHE "Speed up recompilation by caching previous compilations" OFF)
# Platform-specific options
if(ANDROID)
set(ENABLE_STATIC_LIBS ON)
set(ENABLE_LAUNCHER OFF)
else()
option(ENABLE_STATIC_LIBS "Build library and all components such as AI statically" OFF)
option(ENABLE_LAUNCHER "Enable compilation of launcher" ON)
endif()
if(APPLE_IOS OR ANDROID)
set(ENABLE_MONOLITHIC_INSTALL OFF)
set(ENABLE_SINGLE_APP_BUILD ON)
set(ENABLE_EDITOR OFF)
set(ENABLE_TEST OFF)
set(ENABLE_LOBBY OFF)
set(ENABLE_SERVER OFF)
set(COPY_CONFIG_ON_BUILD OFF)
else()
option(ENABLE_MONOLITHIC_INSTALL "Install everything in single directory on Linux and Mac" OFF) # Used for Snap packages and also useful for debugging
option(COPY_CONFIG_ON_BUILD "Copies config folder into output directory at building phase" ON)
option(ENABLE_SERVER "Enable compilation of dedicated server" ON)
option(ENABLE_EDITOR "Enable compilation of map editor" ON)
option(ENABLE_SINGLE_APP_BUILD "Builds client and launcher as single executable" OFF)
option(ENABLE_TEST "Enable compilation of unit tests" OFF)
option(ENABLE_LOBBY "Enable compilation of lobby server" OFF)
endif()
# ERM depends on LUA implicitly
if(ENABLE_ERM AND NOT ENABLE_LUA)
set(ENABLE_LUA ON)
endif()
############################################
# Miscellaneous options #
############################################
if (ENABLE_STATIC_LIBS AND CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
set(CMAKE_POSITION_INDEPENDENT_CODE ON)
endif()
if(APPLE_IOS)
set(BUNDLE_IDENTIFIER_PREFIX "" CACHE STRING "Bundle identifier prefix")
set(APP_DISPLAY_NAME "VCMI" CACHE STRING "App name on the home screen")
set(ENABLE_SINGLE_APP_BUILD ON)
else()
option(ENABLE_TEST "Enable compilation of unit tests" OFF)
option(ENABLE_SINGLE_APP_BUILD "Builds client and server as single executable" ${singleProcess})
endif()
option(ENABLE_PCH "Enable compilation using precompiled headers" ON)
option(ENABLE_GITVERSION "Enable Version.cpp with Git commit hash" ON)
option(ENABLE_DEBUG_CONSOLE "Enable debug console for Windows builds" ON)
option(ENABLE_STRICT_COMPILATION "Treat all compiler warnings as errors" OFF)
option(ENABLE_MULTI_PROCESS_BUILDS "Enable /MP flag for MSVS solution" ON)
option(COPY_CONFIG_ON_BUILD "Copies config folder into output directory at building phase" ON)
option(ENABLE_STATIC_AI_LIBS "Add AI code into VCMI lib directly" ${staticAI})
option(ENABLE_COLORIZED_COMPILER_OUTPUT "Colorize compilation output (Clang/GNU)." ON)
if(ENABLE_COLORIZED_COMPILER_OUTPUT)
if(CMAKE_CXX_COMPILER_ID STREQUAL "Clang")
add_compile_options(-fcolor-diagnostics)
@ -85,20 +112,6 @@ if(ENABLE_COLORIZED_COMPILER_OUTPUT)
endif()
endif()
# Used for Snap packages and also useful for debugging
if(NOT APPLE_IOS AND NOT ANDROID)
option(ENABLE_MONOLITHIC_INSTALL "Install everything in single directory on Linux and Mac" OFF)
endif()
if(${CMAKE_SYSTEM_NAME} STREQUAL "Linux")
set(buildLobby ON)
endif()
if(NOT APPLE_IOS AND NOT ANDROID)
option(ENABLE_LOBBY "Enable compilation of lobby server" ${buildLobby})
endif()
option(ENABLE_CCACHE "Speed up recompilation by caching previous compilations" OFF)
if(ENABLE_CCACHE)
find_program(CCACHE ccache REQUIRED)
endif()
@ -128,20 +141,6 @@ endif()
set(PACKAGE_NAME_SUFFIX "" CACHE STRING "Suffix for CPack package name")
set(PACKAGE_FILE_NAME "" CACHE STRING "Override for CPack package filename")
# ERM depends on LUA implicitly
if(ENABLE_ERM AND NOT ENABLE_LUA)
set(ENABLE_LUA ON)
endif()
# We don't want to deploy assets into build directory for android/iOS build
if((APPLE_IOS OR ANDROID) AND COPY_CONFIG_ON_BUILD)
set(COPY_CONFIG_ON_BUILD OFF)
endif()
############################################
# Miscellaneous options #
############################################
set(CMAKE_MODULE_PATH ${CMAKE_HOME_DIRECTORY}/cmake_modules ${PROJECT_SOURCE_DIR}/CI)
# Contains custom functions and macros, but don't altering any options
@ -250,7 +249,7 @@ if(ENABLE_EDITOR)
endif()
if(ENABLE_SINGLE_APP_BUILD)
add_definitions(-DSINGLE_PROCESS_APP=1)
add_definitions(-DENABLE_SINGLE_APP_BUILD)
endif()
if(APPLE_IOS)
@ -609,21 +608,19 @@ if(APPLE_IOS)
add_subdirectory(ios)
endif()
set(VCMI_LIB_TARGET vcmi)
add_subdirectory_with_folder("AI" AI)
include(VCMI_lib)
add_subdirectory(lib)
if(ENABLE_SINGLE_APP_BUILD)
add_subdirectory(lib_server)
endif()
add_subdirectory(server)
if(ENABLE_ERM)
add_subdirectory(scripting/erm)
endif()
if(ENABLE_LUA)
add_subdirectory(scripting/lua)
endif()
if(NOT TARGET minizip::minizip)
add_subdirectory_with_folder("3rdparty" lib/minizip)
add_library(minizip::minizip ALIAS minizip)
@ -632,14 +629,21 @@ endif()
if(ENABLE_LAUNCHER)
add_subdirectory(launcher)
endif()
if(ENABLE_EDITOR)
add_subdirectory(mapeditor)
endif()
if(ENABLE_LOBBY)
add_subdirectory(lobby)
endif()
add_subdirectory(client)
add_subdirectory(server)
if(ENABLE_SERVER)
add_subdirectory(serverapp)
endif()
if(ENABLE_TEST)
enable_testing()
add_subdirectory(test)

View File

@ -51,7 +51,8 @@
"inherits": "linux-release",
"hidden": true,
"cacheVariables": {
"ENABLE_TEST": "ON",
"ENABLE_LOBBY": "ON",
"ENABLE_TEST": "ON",
"ENABLE_LUA": "ON"
}
},

View File

@ -36,12 +36,6 @@ public class NativeMethods
public static native void initClassloader();
public static native void createServer();
public static native void notifyServerReady();
public static native void notifyServerClosed();
public static native boolean tryToSaveTheGame();
public static void setupMsg(final Messenger msg)
@ -77,62 +71,6 @@ public class NativeMethods
return ctx.getApplicationInfo().nativeLibraryDir;
}
@SuppressWarnings(Const.JNI_METHOD_SUPPRESS)
public static void startServer()
{
Log.i("Got server create request");
final Context ctx = SDL.getContext();
if (!(ctx instanceof VcmiSDLActivity))
{
Log.e("Unexpected context... " + ctx);
return;
}
Intent intent = new Intent(ctx, SDLActivity.class);
intent.setAction(VcmiSDLActivity.NATIVE_ACTION_CREATE_SERVER);
// I probably do something incorrectly, but sending new intent to the activity "normally" breaks SDL events handling (probably detaches jnienv?)
// so instead let's call onNewIntent directly, as out context SHOULD be SDLActivity anyway
((VcmiSDLActivity) ctx).hackCallNewIntentDirectly(intent);
// ctx.startActivity(intent);
}
@SuppressWarnings(Const.JNI_METHOD_SUPPRESS)
public static void killServer()
{
Log.i("Got server close request");
final Context ctx = SDL.getContext();
ctx.stopService(new Intent(ctx, ServerService.class));
Messenger messenger = requireServerMessenger();
try
{
// we need to actually inform client about killing the server, beacuse it needs to unbind service connection before server gets destroyed
messenger.send(Message.obtain(null, VcmiSDLActivity.SERVER_MESSAGE_SERVER_KILLED));
}
catch (RemoteException e)
{
Log.w("Connection with client process broken?");
}
}
@SuppressWarnings(Const.JNI_METHOD_SUPPRESS)
public static void onServerReady()
{
Log.i("Got server ready msg");
Messenger messenger = requireServerMessenger();
try
{
messenger.send(Message.obtain(null, VcmiSDLActivity.SERVER_MESSAGE_SERVER_READY));
}
catch (RemoteException e)
{
Log.w("Connection with client process broken?");
}
}
@SuppressWarnings(Const.JNI_METHOD_SUPPRESS)
public static void showProgress()
{

View File

@ -58,15 +58,6 @@ public class ServerService extends Service
void onClientRegistered(Messenger client);
}
private static class ServerStartThread extends Thread
{
@Override
public void run()
{
NativeMethods.createServer();
}
}
private static class IncomingClientMessageHandler extends Handler
{
private WeakReference<IncomingClientMessageHandlerCallback> mCallbackRef;
@ -88,7 +79,6 @@ public class ServerService extends Service
callback.onClientRegistered(msg.replyTo);
}
NativeMethods.setupMsg(msg.replyTo);
new ServerStartThread().start();
break;
default:
super.handleMessage(msg);

View File

@ -20,9 +20,6 @@ import eu.vcmi.vcmi.util.Log;
public class VcmiSDLActivity extends SDLActivity
{
public static final int SERVER_MESSAGE_SERVER_READY = 1000;
public static final int SERVER_MESSAGE_SERVER_KILLED = 1001;
public static final String NATIVE_ACTION_CREATE_SERVER = "SDLActivity.Action.CreateServer";
protected static final int COMMAND_USER = 0x8000;
final Messenger mClientMessenger = new Messenger(
@ -96,10 +93,6 @@ public class VcmiSDLActivity extends SDLActivity
protected void onNewIntent(final Intent intent)
{
Log.i(this, "Got new intent with action " + intent.getAction());
if (NATIVE_ACTION_CREATE_SERVER.equals(intent.getAction()))
{
initService();
}
}
@Override
@ -188,26 +181,5 @@ public class VcmiSDLActivity extends SDLActivity
{
mCallback = callback;
}
@Override
public void handleMessage(Message msg)
{
Log.i(this, "Got server msg " + msg);
switch (msg.what)
{
case SERVER_MESSAGE_SERVER_READY:
NativeMethods.notifyServerReady();
break;
case SERVER_MESSAGE_SERVER_KILLED:
if (mCallback != null)
{
mCallback.unbindServer();
}
NativeMethods.notifyServerClosed();
break;
default:
super.handleMessage(msg);
}
}
}
}

View File

@ -190,6 +190,7 @@ int main(int argc, char * argv[])
console->start();
#endif
setThreadNameLoggingOnly("MainGUI");
const boost::filesystem::path logPath = VCMIDirs::get().userLogsPath() / "VCMI_Client_log.txt";
logConfig = new CBasicLogConfigurator(logPath, console);
logConfig->configureDefault();
@ -398,7 +399,10 @@ void playIntro()
static void mainLoop()
{
#ifndef VCMI_UNIX
// on Linux, name of main thread is also name of our process. Which we don't want to change
setThreadName("MainGUI");
#endif
while(1) //main SDL events loop
{

View File

@ -164,6 +164,7 @@ set(client_SRCS
HeroMovementController.cpp
NetPacksClient.cpp
NetPacksLobbyClient.cpp
ServerRunner.cpp
)
set(client_HEADERS
@ -346,6 +347,7 @@ set(client_HEADERS
ClientNetPackVisitors.h
HeroMovementController.h
LobbyClientNetPackVisitors.h
ServerRunner.h
resource.h
)
@ -373,8 +375,7 @@ else()
add_executable(vcmiclient ${client_SRCS} ${client_HEADERS})
endif()
add_dependencies(vcmiclient vcmiserver)
if(NOT ENABLE_STATIC_AI_LIBS)
if(NOT ENABLE_STATIC_LIBS)
add_dependencies(vcmiclient
BattleAI
EmptyAI
@ -451,14 +452,13 @@ elseif(APPLE_IOS)
set(CMAKE_EXE_LINKER_FLAGS "-Wl,-e,_client_main")
endif()
if(ENABLE_SINGLE_APP_BUILD)
target_link_libraries(vcmiclient PRIVATE vcmiserver)
if(ENABLE_LAUNCHER)
target_link_libraries(vcmiclient PRIVATE vcmilauncher)
endif()
target_link_libraries(vcmiclient PRIVATE vcmiservercommon)
if(ENABLE_SINGLE_APP_BUILD AND ENABLE_LAUNCHER)
target_link_libraries(vcmiclient PRIVATE vcmilauncher)
endif()
target_link_libraries(vcmiclient PRIVATE
${VCMI_LIB_TARGET} SDL2::SDL2 SDL2::Image SDL2::Mixer SDL2::TTF
vcmi SDL2::SDL2 SDL2::Image SDL2::Mixer SDL2::TTF
)
if(ffmpeg_LIBRARIES)

View File

@ -12,6 +12,7 @@
#include "CServerHandler.h"
#include "Client.h"
#include "CGameInfo.h"
#include "ServerRunner.h"
#include "CPlayerInterface.h"
#include "gui/CGuiHandler.h"
#include "gui/WindowHandler.h"
@ -25,17 +26,6 @@
#include "mainmenu/CPrologEpilogVideo.h"
#include "mainmenu/CHighScoreScreen.h"
#ifdef VCMI_ANDROID
#include "../lib/CAndroidVMHelper.h"
#elif defined(VCMI_IOS)
#include "ios/utils.h"
#include <dispatch/dispatch.h>
#endif
#ifdef SINGLE_PROCESS_APP
#include "../server/CVCMIServer.h"
#endif
#include "../lib/CConfigHandler.h"
#include "../lib/CGeneralTextHandler.h"
#include "../lib/CThreadHelper.h"
@ -61,16 +51,8 @@
#include <vcmi/events/EventBus.h>
#ifdef VCMI_WINDOWS
#include <windows.h>
#endif
template<typename T> class CApplyOnLobby;
#if defined(VCMI_ANDROID) && !defined(SINGLE_PROCESS_APP)
extern std::atomic_bool androidTestServerReadyFlag;
#endif
class CBaseForLobbyApply
{
public:
@ -126,9 +108,14 @@ public:
CServerHandler::~CServerHandler()
{
if (serverRunner)
serverRunner->shutdown();
networkHandler->stop();
try
{
if (serverRunner)
serverRunner->wait();
serverRunner.reset();
threadNetwork.join();
}
catch (const std::runtime_error & e)
@ -195,70 +182,22 @@ INetworkHandler & CServerHandler::getNetworkHandler()
void CServerHandler::startLocalServerAndConnect(bool connectToLobby)
{
if(threadRunLocalServer.joinable())
threadRunLocalServer.join();
th->update();
#if defined(SINGLE_PROCESS_APP)
boost::condition_variable cond;
std::vector<std::string> args{"--port=" + std::to_string(getLocalPort())};
if(connectToLobby)
args.push_back("--lobby");
threadRunLocalServer = boost::thread([&cond, args] {
setThreadName("CVCMIServer");
CVCMIServer::create(&cond, args);
});
#elif defined(VCMI_ANDROID)
{
CAndroidVMHelper envHelper;
envHelper.callStaticVoidMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "startServer", true);
}
logNetwork->trace("\tLocal server startup has been requested");
#ifdef VCMI_MOBILE
// mobile apps can't spawn separate processes - only thread mode is available
serverRunner.reset(new ServerThreadRunner());
#else
threadRunLocalServer = boost::thread(&CServerHandler::threadRunServer, this, connectToLobby); //runs server executable;
#endif
logNetwork->trace("Setting up thread calling server: %d ms", th->getDiff());
th->update();
#ifdef SINGLE_PROCESS_APP
{
#ifdef VCMI_IOS
dispatch_sync(dispatch_get_main_queue(), ^{
iOS_utils::showLoadingIndicator();
});
if (settings["server"]["useProcess"].Bool())
serverRunner.reset(new ServerProcessRunner());
else
serverRunner.reset(new ServerThreadRunner());
#endif
boost::mutex m;
boost::unique_lock<boost::mutex> lock{m};
logNetwork->info("waiting for server");
cond.wait(lock);
logNetwork->info("server is ready");
#ifdef VCMI_IOS
dispatch_sync(dispatch_get_main_queue(), ^{
iOS_utils::hideLoadingIndicator();
});
#endif
}
#elif defined(VCMI_ANDROID)
logNetwork->info("waiting for server");
while(!androidTestServerReadyFlag.load())
{
logNetwork->info("still waiting...");
boost::this_thread::sleep_for(boost::chrono::milliseconds(100));
}
logNetwork->info("waiting for server finished...");
androidTestServerReadyFlag = false;
#endif
logNetwork->trace("Waiting for server: %d ms", th->getDiff());
th->update(); //put breakpoint here to attach to server before it does something stupid
logNetwork->trace("\tStarting local server");
serverRunner->start(getLocalPort(), connectToLobby);
logNetwork->trace("\tConnecting to local server");
connectToServer(getLocalHostname(), getLocalPort());
logNetwork->trace("\tConnecting to the server: %d ms", th->getDiff());
logNetwork->trace("\tWaiting for connection");
}
void CServerHandler::connectToServer(const std::string & addr, const ui16 port)
@ -306,6 +245,10 @@ void CServerHandler::onTimer()
if(getState() == EClientState::CONNECTION_CANCELLED)
{
logNetwork->info("Connection aborted by player!");
serverRunner->wait();
serverRunner.reset();
if (GH.windows().topWindow<CSimpleJoinScreen>() != nullptr)
GH.windows().popWindows(1);
return;
}
@ -369,12 +312,15 @@ EClientState CServerHandler::getState() const
void CServerHandler::setState(EClientState newState)
{
if (newState == EClientState::CONNECTION_CANCELLED && serverRunner != nullptr)
serverRunner->shutdown();
state = newState;
}
bool CServerHandler::isServerLocal() const
{
return threadRunLocalServer.joinable();
return serverRunner != nullptr;
}
bool CServerHandler::isHost() const
@ -758,7 +704,6 @@ void CServerHandler::startCampaignScenario(HighScoreParameter param, std::shared
}
};
threadRunLocalServer.join();
if(epilogue.hasPrologEpilog)
{
GH.windows().createAndPushWindow<CPrologEpilogVideo>(epilogue, finisher);
@ -899,6 +844,8 @@ void CServerHandler::onPacketReceived(const std::shared_ptr<INetworkConnection>
void CServerHandler::onDisconnected(const std::shared_ptr<INetworkConnection> & connection, const std::string & errorMessage)
{
waitForServerShutdown();
if(getState() == EClientState::DISCONNECTING)
{
assert(networkConnection == nullptr);
@ -928,6 +875,34 @@ void CServerHandler::onDisconnected(const std::shared_ptr<INetworkConnection> &
networkConnection.reset();
}
void CServerHandler::waitForServerShutdown()
{
if (!serverRunner)
return; // may not exist for guest in MP
serverRunner->wait();
int exitCode = serverRunner->exitCode();
serverRunner.reset();
if (exitCode == 0)
{
logNetwork->info("Server closed correctly");
}
else
{
boost::mutex::scoped_lock interfaceLock(GH.interfaceMutex);
if (getState() == EClientState::CONNECTING)
{
showServerError(CGI->generaltexth->translate("vcmi.server.errors.existingProcess"));
setState(EClientState::CONNECTION_CANCELLED); // stop attempts to reconnect
}
logNetwork->error("Error: server failed to close correctly or crashed!");
logNetwork->error("Check log file for more info");
}
serverRunner.reset();
}
void CServerHandler::visitForLobby(CPackForLobby & lobbyPack)
{
if(applier->getApplier(CTypeList::getInstance().getTypeID(&lobbyPack))->applyOnLobbyHandler(this, lobbyPack))
@ -942,55 +917,6 @@ void CServerHandler::visitForClient(CPackForClient & clientPack)
client->handlePack(&clientPack);
}
void CServerHandler::threadRunServer(bool connectToLobby)
{
#if !defined(VCMI_MOBILE)
setThreadName("runServer");
const std::string logName = (VCMIDirs::get().userLogsPath() / "server_log.txt").string();
std::string comm = VCMIDirs::get().serverPath().string()
+ " --port=" + std::to_string(getLocalPort())
+ " --run-by-client";
if(connectToLobby)
comm += " --lobby";
comm += " > \"" + logName + '\"';
logGlobal->info("Server command line: %s", comm);
#ifdef VCMI_WINDOWS
int result = -1;
const auto bufSize = ::MultiByteToWideChar(CP_UTF8, 0, comm.c_str(), comm.size(), nullptr, 0);
if(bufSize > 0)
{
std::wstring wComm(bufSize, {});
const auto convertResult = ::MultiByteToWideChar(CP_UTF8, 0, comm.c_str(), comm.size(), &wComm[0], bufSize);
if(convertResult > 0)
result = ::_wsystem(wComm.c_str());
else
logNetwork->error("Error " + std::to_string(GetLastError()) + ": failed to convert server launch command to wide string: " + comm);
}
else
logNetwork->error("Error " + std::to_string(GetLastError()) + ": failed to obtain buffer length to convert server launch command to wide string : " + comm);
#else
int result = std::system(comm.c_str());
#endif
if (result == 0)
{
logNetwork->info("Server closed correctly");
}
else
{
boost::mutex::scoped_lock interfaceLock(GH.interfaceMutex);
if (getState() == EClientState::CONNECTING)
{
showServerError(CGI->generaltexth->translate("vcmi.server.errors.existingProcess"));
setState(EClientState::CONNECTION_CANCELLED); // stop attempts to reconnect
}
logNetwork->error("Error: server failed to close correctly or crashed!");
logNetwork->error("Check %s for more info", logName);
}
#endif
}
void CServerHandler::sendLobbyPack(const CPackForLobby & pack) const
{

View File

@ -36,6 +36,7 @@ VCMI_LIB_NAMESPACE_END
class CClient;
class CBaseForLobbyApply;
class GlobalLobbyClient;
class IServerRunner;
class HighScoreCalculation;
class HighScoreParameter;
@ -100,17 +101,17 @@ class CServerHandler final : public IServerAPI, public LobbyInfo, public INetwor
std::shared_ptr<INetworkConnection> networkConnection;
std::unique_ptr<GlobalLobbyClient> lobbyClient;
std::unique_ptr<CApplier<CBaseForLobbyApply>> applier;
std::unique_ptr<IServerRunner> serverRunner;
std::shared_ptr<CMapInfo> mapToStart;
std::vector<std::string> localPlayerNames;
std::shared_ptr<HighScoreCalculation> highScoreCalc;
boost::thread threadRunLocalServer;
boost::thread threadNetwork;
std::atomic<EClientState> state;
void threadRunNetwork();
void threadRunServer(bool connectToLobby);
void waitForServerShutdown();
void sendLobbyPack(const CPackForLobby & pack) const override;

View File

@ -46,10 +46,6 @@
#ifdef VCMI_ANDROID
#include "lib/CAndroidVMHelper.h"
#ifndef SINGLE_PROCESS_APP
std::atomic_bool androidTestServerReadyFlag;
#endif
#endif
ThreadSafeVector<int> CClient::waitingRequest;
@ -718,22 +714,6 @@ void CClient::removeGUI() const
}
#ifdef VCMI_ANDROID
#ifndef SINGLE_PROCESS_APP
extern "C" JNIEXPORT void JNICALL Java_eu_vcmi_vcmi_NativeMethods_notifyServerClosed(JNIEnv * env, jclass cls)
{
logNetwork->info("Received server closed signal");
if (CSH) {
CSH->campaignServerRestartLock.setn(false);
}
}
extern "C" JNIEXPORT void JNICALL Java_eu_vcmi_vcmi_NativeMethods_notifyServerReady(JNIEnv * env, jclass cls)
{
logNetwork->info("Received server ready signal");
androidTestServerReadyFlag.store(true);
}
#endif
extern "C" JNIEXPORT jboolean JNICALL Java_eu_vcmi_vcmi_NativeMethods_tryToSaveTheGame(JNIEnv * env, jclass cls)
{
logGlobal->info("Received emergency save game request");

88
client/ServerRunner.cpp Normal file
View File

@ -0,0 +1,88 @@
/*
* ServerRunner.cpp, part of VCMI engine
*
* Authors: listed in file AUTHORS in main folder
*
* License: GNU General Public License v2.0 or later
* Full text of license available in license.txt file, in main folder
*
*/
#include "StdInc.h"
#include "ServerRunner.h"
#include "../lib/VCMIDirs.h"
#include "../lib/CThreadHelper.h"
#include "../server/CVCMIServer.h"
#ifndef VCMI_MOBILE
#include <boost/process/child.hpp>
#include <boost/process/io.hpp>
#endif
ServerThreadRunner::ServerThreadRunner() = default;
ServerThreadRunner::~ServerThreadRunner() = default;
void ServerThreadRunner::start(uint16_t port, bool connectToLobby)
{
server = std::make_unique<CVCMIServer>(port, connectToLobby, true);
threadRunLocalServer = boost::thread([this]{
setThreadName("runServer");
server->run();
});
}
void ServerThreadRunner::shutdown()
{
server->setState(EServerState::SHUTDOWN);
}
void ServerThreadRunner::wait()
{
threadRunLocalServer.join();
}
int ServerThreadRunner::exitCode()
{
return 0;
}
#ifndef VCMI_MOBILE
ServerProcessRunner::ServerProcessRunner() = default;
ServerProcessRunner::~ServerProcessRunner() = default;
void ServerProcessRunner::shutdown()
{
child->terminate();
}
void ServerProcessRunner::wait()
{
child->wait();
}
int ServerProcessRunner::exitCode()
{
return child->exit_code();
}
void ServerProcessRunner::start(uint16_t port, bool connectToLobby)
{
boost::filesystem::path serverPath = VCMIDirs::get().serverPath();
boost::filesystem::path logPath = VCMIDirs::get().userLogsPath() / "server_log.txt";
std::vector<std::string> args;
args.push_back("--port=" + std::to_string(port));
args.push_back("--run-by-client");
if(connectToLobby)
args.push_back("--lobby");
std::error_code ec;
child = std::make_unique<boost::process::child>(serverPath, args, ec, boost::process::std_out > logPath);
if (ec)
throw std::runtime_error("Failed to start server! Reason: " + ec.message());
}
#endif

61
client/ServerRunner.h Normal file
View File

@ -0,0 +1,61 @@
/*
* ServerRunner.h, part of VCMI engine
*
* Authors: listed in file AUTHORS in main folder
*
* License: GNU General Public License v2.0 or later
* Full text of license available in license.txt file, in main folder
*
*/
#pragma once
class CVCMIServer;
class IServerRunner
{
public:
virtual void start(uint16_t port, bool connectToLobby) = 0;
virtual void shutdown() = 0;
virtual void wait() = 0;
virtual int exitCode() = 0;
virtual ~IServerRunner() = default;
};
/// Class that runs server instance as a thread of client process
class ServerThreadRunner : public IServerRunner, boost::noncopyable
{
std::unique_ptr<CVCMIServer> server;
boost::thread threadRunLocalServer;
public:
void start(uint16_t port, bool connectToLobby) override;
void shutdown() override;
void wait() override;
int exitCode() override;
ServerThreadRunner();
~ServerThreadRunner();
};
#ifndef VCMI_MOBILE
namespace boost::process {
class child;
}
/// Class that runs server instance as a child process
/// Available only on desktop systems where process management is allowed
class ServerProcessRunner : public IServerRunner, boost::noncopyable
{
std::unique_ptr<boost::process::child> child;
public:
void start(uint16_t port, bool connectToLobby) override;
void shutdown() override;
void wait() override;
int exitCode() override;
ServerProcessRunner();
~ServerProcessRunner();
};
#endif

View File

@ -60,11 +60,6 @@
#include "../../lib/CRandomGenerator.h"
#include "../../lib/CondSh.h"
#if defined(SINGLE_PROCESS_APP) && defined(VCMI_ANDROID)
#include "../../server/CVCMIServer.h"
#include <SDL.h>
#endif
std::shared_ptr<CMainMenu> CMM;
ISelectionScreenInfo * SEL;
@ -599,13 +594,6 @@ void CSimpleJoinScreen::onChange(const std::string & newText)
void CSimpleJoinScreen::startConnection(const std::string & addr, ui16 port)
{
#if defined(SINGLE_PROCESS_APP) && defined(VCMI_ANDROID)
// in single process build server must use same JNIEnv as client
// as server runs in a separate thread, it must not attempt to search for Java classes (and they're already cached anyway)
// https://github.com/libsdl-org/SDL/blob/main/docs/README-android.md#threads-and-the-java-vm
CVCMIServer::reuseClientJNIEnv(SDL_AndroidGetJNIEnv());
#endif
if(addr.empty())
CSH->startLocalServerAndConnect(false);
else

View File

@ -1,757 +0,0 @@
macro(add_main_lib TARGET_NAME LIBRARY_TYPE)
if(NOT DEFINED MAIN_LIB_DIR)
set(MAIN_LIB_DIR "${CMAKE_SOURCE_DIR}/lib")
endif()
set(lib_SRCS
${MAIN_LIB_DIR}/StdInc.cpp
${MAIN_LIB_DIR}/battle/AccessibilityInfo.cpp
${MAIN_LIB_DIR}/battle/BattleAction.cpp
${MAIN_LIB_DIR}/battle/BattleAttackInfo.cpp
${MAIN_LIB_DIR}/battle/BattleHex.cpp
${MAIN_LIB_DIR}/battle/BattleInfo.cpp
${MAIN_LIB_DIR}/battle/BattleProxy.cpp
${MAIN_LIB_DIR}/battle/BattleStateInfoForRetreat.cpp
${MAIN_LIB_DIR}/battle/CBattleInfoCallback.cpp
${MAIN_LIB_DIR}/battle/CBattleInfoEssentials.cpp
${MAIN_LIB_DIR}/battle/CObstacleInstance.cpp
${MAIN_LIB_DIR}/battle/CPlayerBattleCallback.cpp
${MAIN_LIB_DIR}/battle/CUnitState.cpp
${MAIN_LIB_DIR}/battle/DamageCalculator.cpp
${MAIN_LIB_DIR}/battle/Destination.cpp
${MAIN_LIB_DIR}/battle/IBattleState.cpp
${MAIN_LIB_DIR}/battle/ReachabilityInfo.cpp
${MAIN_LIB_DIR}/battle/SideInBattle.cpp
${MAIN_LIB_DIR}/battle/SiegeInfo.cpp
${MAIN_LIB_DIR}/battle/Unit.cpp
${MAIN_LIB_DIR}/bonuses/Bonus.cpp
${MAIN_LIB_DIR}/bonuses/BonusEnum.cpp
${MAIN_LIB_DIR}/bonuses/BonusList.cpp
${MAIN_LIB_DIR}/bonuses/BonusParams.cpp
${MAIN_LIB_DIR}/bonuses/BonusSelector.cpp
${MAIN_LIB_DIR}/bonuses/BonusCustomTypes.cpp
${MAIN_LIB_DIR}/bonuses/CBonusProxy.cpp
${MAIN_LIB_DIR}/bonuses/CBonusSystemNode.cpp
${MAIN_LIB_DIR}/bonuses/IBonusBearer.cpp
${MAIN_LIB_DIR}/bonuses/Limiters.cpp
${MAIN_LIB_DIR}/bonuses/Propagators.cpp
${MAIN_LIB_DIR}/bonuses/Updaters.cpp
${MAIN_LIB_DIR}/campaign/CampaignHandler.cpp
${MAIN_LIB_DIR}/campaign/CampaignState.cpp
${MAIN_LIB_DIR}/constants/EntityIdentifiers.cpp
${MAIN_LIB_DIR}/events/ApplyDamage.cpp
${MAIN_LIB_DIR}/events/GameResumed.cpp
${MAIN_LIB_DIR}/events/ObjectVisitEnded.cpp
${MAIN_LIB_DIR}/events/ObjectVisitStarted.cpp
${MAIN_LIB_DIR}/events/PlayerGotTurn.cpp
${MAIN_LIB_DIR}/events/TurnStarted.cpp
${MAIN_LIB_DIR}/filesystem/AdapterLoaders.cpp
${MAIN_LIB_DIR}/filesystem/CArchiveLoader.cpp
${MAIN_LIB_DIR}/filesystem/CBinaryReader.cpp
${MAIN_LIB_DIR}/filesystem/CCompressedStream.cpp
${MAIN_LIB_DIR}/filesystem/CFileInputStream.cpp
${MAIN_LIB_DIR}/filesystem/CFilesystemLoader.cpp
${MAIN_LIB_DIR}/filesystem/CMemoryBuffer.cpp
${MAIN_LIB_DIR}/filesystem/CMemoryStream.cpp
${MAIN_LIB_DIR}/filesystem/CZipLoader.cpp
${MAIN_LIB_DIR}/filesystem/CZipSaver.cpp
${MAIN_LIB_DIR}/filesystem/FileInfo.cpp
${MAIN_LIB_DIR}/filesystem/Filesystem.cpp
${MAIN_LIB_DIR}/filesystem/MinizipExtensions.cpp
${MAIN_LIB_DIR}/filesystem/ResourcePath.cpp
${MAIN_LIB_DIR}/gameState/CGameState.cpp
${MAIN_LIB_DIR}/gameState/CGameStateCampaign.cpp
${MAIN_LIB_DIR}/gameState/InfoAboutArmy.cpp
${MAIN_LIB_DIR}/gameState/TavernHeroesPool.cpp
${MAIN_LIB_DIR}/logging/CBasicLogConfigurator.cpp
${MAIN_LIB_DIR}/logging/CLogger.cpp
${MAIN_LIB_DIR}/mapObjectConstructors/AObjectTypeHandler.cpp
${MAIN_LIB_DIR}/mapObjectConstructors/CBankInstanceConstructor.cpp
${MAIN_LIB_DIR}/mapObjectConstructors/CObjectClassesHandler.cpp
${MAIN_LIB_DIR}/mapObjectConstructors/CommonConstructors.cpp
${MAIN_LIB_DIR}/mapObjectConstructors/CRewardableConstructor.cpp
${MAIN_LIB_DIR}/mapObjectConstructors/DwellingInstanceConstructor.cpp
${MAIN_LIB_DIR}/mapObjectConstructors/HillFortInstanceConstructor.cpp
${MAIN_LIB_DIR}/mapObjectConstructors/ShipyardInstanceConstructor.cpp
${MAIN_LIB_DIR}/mapObjects/CArmedInstance.cpp
${MAIN_LIB_DIR}/mapObjects/CBank.cpp
${MAIN_LIB_DIR}/mapObjects/CGCreature.cpp
${MAIN_LIB_DIR}/mapObjects/CGDwelling.cpp
${MAIN_LIB_DIR}/mapObjects/CGHeroInstance.cpp
${MAIN_LIB_DIR}/mapObjects/CGMarket.cpp
${MAIN_LIB_DIR}/mapObjects/CGObjectInstance.cpp
${MAIN_LIB_DIR}/mapObjects/CGPandoraBox.cpp
${MAIN_LIB_DIR}/mapObjects/CGTownBuilding.cpp
${MAIN_LIB_DIR}/mapObjects/CGTownInstance.cpp
${MAIN_LIB_DIR}/mapObjects/CObjectHandler.cpp
${MAIN_LIB_DIR}/mapObjects/CQuest.cpp
${MAIN_LIB_DIR}/mapObjects/CRewardableObject.cpp
${MAIN_LIB_DIR}/mapObjects/IMarket.cpp
${MAIN_LIB_DIR}/mapObjects/IObjectInterface.cpp
${MAIN_LIB_DIR}/mapObjects/MiscObjects.cpp
${MAIN_LIB_DIR}/mapObjects/ObjectTemplate.cpp
${MAIN_LIB_DIR}/mapping/CDrawRoadsOperation.cpp
${MAIN_LIB_DIR}/mapping/CMap.cpp
${MAIN_LIB_DIR}/mapping/CMapHeader.cpp
${MAIN_LIB_DIR}/mapping/CMapEditManager.cpp
${MAIN_LIB_DIR}/mapping/CMapInfo.cpp
${MAIN_LIB_DIR}/mapping/CMapOperation.cpp
${MAIN_LIB_DIR}/mapping/CMapService.cpp
${MAIN_LIB_DIR}/mapping/MapEditUtils.cpp
${MAIN_LIB_DIR}/mapping/MapIdentifiersH3M.cpp
${MAIN_LIB_DIR}/mapping/MapFeaturesH3M.cpp
${MAIN_LIB_DIR}/mapping/MapFormatH3M.cpp
${MAIN_LIB_DIR}/mapping/MapReaderH3M.cpp
${MAIN_LIB_DIR}/mapping/MapFormatJson.cpp
${MAIN_LIB_DIR}/mapping/ObstacleProxy.cpp
${MAIN_LIB_DIR}/modding/ActiveModsInSaveList.cpp
${MAIN_LIB_DIR}/modding/CModHandler.cpp
${MAIN_LIB_DIR}/modding/CModInfo.cpp
${MAIN_LIB_DIR}/modding/CModVersion.cpp
${MAIN_LIB_DIR}/modding/ContentTypeHandler.cpp
${MAIN_LIB_DIR}/modding/IdentifierStorage.cpp
${MAIN_LIB_DIR}/modding/ModUtility.cpp
${MAIN_LIB_DIR}/network/NetworkConnection.cpp
${MAIN_LIB_DIR}/network/NetworkHandler.cpp
${MAIN_LIB_DIR}/network/NetworkServer.cpp
${MAIN_LIB_DIR}/networkPacks/NetPacksLib.cpp
${MAIN_LIB_DIR}/pathfinder/CGPathNode.cpp
${MAIN_LIB_DIR}/pathfinder/CPathfinder.cpp
${MAIN_LIB_DIR}/pathfinder/NodeStorage.cpp
${MAIN_LIB_DIR}/pathfinder/PathfinderOptions.cpp
${MAIN_LIB_DIR}/pathfinder/PathfindingRules.cpp
${MAIN_LIB_DIR}/pathfinder/TurnInfo.cpp
${MAIN_LIB_DIR}/rewardable/Configuration.cpp
${MAIN_LIB_DIR}/rewardable/Info.cpp
${MAIN_LIB_DIR}/rewardable/Interface.cpp
${MAIN_LIB_DIR}/rewardable/Limiter.cpp
${MAIN_LIB_DIR}/rewardable/Reward.cpp
${MAIN_LIB_DIR}/rmg/RmgArea.cpp
${MAIN_LIB_DIR}/rmg/RmgObject.cpp
${MAIN_LIB_DIR}/rmg/RmgPath.cpp
${MAIN_LIB_DIR}/rmg/CMapGenerator.cpp
${MAIN_LIB_DIR}/rmg/CMapGenOptions.cpp
${MAIN_LIB_DIR}/rmg/CRmgTemplate.cpp
${MAIN_LIB_DIR}/rmg/CRmgTemplateStorage.cpp
${MAIN_LIB_DIR}/rmg/CZonePlacer.cpp
${MAIN_LIB_DIR}/rmg/TileInfo.cpp
${MAIN_LIB_DIR}/rmg/Zone.cpp
${MAIN_LIB_DIR}/rmg/Functions.cpp
${MAIN_LIB_DIR}/rmg/RmgMap.cpp
${MAIN_LIB_DIR}/rmg/PenroseTiling.cpp
${MAIN_LIB_DIR}/rmg/modificators/Modificator.cpp
${MAIN_LIB_DIR}/rmg/modificators/ObjectManager.cpp
${MAIN_LIB_DIR}/rmg/modificators/ObjectDistributor.cpp
${MAIN_LIB_DIR}/rmg/modificators/RoadPlacer.cpp
${MAIN_LIB_DIR}/rmg/modificators/TreasurePlacer.cpp
${MAIN_LIB_DIR}/rmg/modificators/PrisonHeroPlacer.cpp
${MAIN_LIB_DIR}/rmg/modificators/QuestArtifactPlacer.cpp
${MAIN_LIB_DIR}/rmg/modificators/ConnectionsPlacer.cpp
${MAIN_LIB_DIR}/rmg/modificators/WaterAdopter.cpp
${MAIN_LIB_DIR}/rmg/modificators/MinePlacer.cpp
${MAIN_LIB_DIR}/rmg/modificators/TownPlacer.cpp
${MAIN_LIB_DIR}/rmg/modificators/WaterProxy.cpp
${MAIN_LIB_DIR}/rmg/modificators/WaterRoutes.cpp
${MAIN_LIB_DIR}/rmg/modificators/RockPlacer.cpp
${MAIN_LIB_DIR}/rmg/modificators/RockFiller.cpp
${MAIN_LIB_DIR}/rmg/modificators/ObstaclePlacer.cpp
${MAIN_LIB_DIR}/rmg/modificators/RiverPlacer.cpp
${MAIN_LIB_DIR}/rmg/modificators/TerrainPainter.cpp
${MAIN_LIB_DIR}/rmg/threadpool/MapProxy.cpp
${MAIN_LIB_DIR}/serializer/BinaryDeserializer.cpp
${MAIN_LIB_DIR}/serializer/BinarySerializer.cpp
${MAIN_LIB_DIR}/serializer/CLoadFile.cpp
${MAIN_LIB_DIR}/serializer/CMemorySerializer.cpp
${MAIN_LIB_DIR}/serializer/Connection.cpp
${MAIN_LIB_DIR}/serializer/CSaveFile.cpp
${MAIN_LIB_DIR}/serializer/CSerializer.cpp
${MAIN_LIB_DIR}/serializer/CTypeList.cpp
${MAIN_LIB_DIR}/serializer/JsonDeserializer.cpp
${MAIN_LIB_DIR}/serializer/JsonSerializeFormat.cpp
${MAIN_LIB_DIR}/serializer/JsonSerializer.cpp
${MAIN_LIB_DIR}/serializer/JsonUpdater.cpp
${MAIN_LIB_DIR}/spells/AbilityCaster.cpp
${MAIN_LIB_DIR}/spells/AdventureSpellMechanics.cpp
${MAIN_LIB_DIR}/spells/BattleSpellMechanics.cpp
${MAIN_LIB_DIR}/spells/BonusCaster.cpp
${MAIN_LIB_DIR}/spells/CSpellHandler.cpp
${MAIN_LIB_DIR}/spells/ExternalCaster.cpp
${MAIN_LIB_DIR}/spells/ISpellMechanics.cpp
${MAIN_LIB_DIR}/spells/ObstacleCasterProxy.cpp
${MAIN_LIB_DIR}/spells/Problem.cpp
${MAIN_LIB_DIR}/spells/ProxyCaster.cpp
${MAIN_LIB_DIR}/spells/TargetCondition.cpp
${MAIN_LIB_DIR}/spells/ViewSpellInt.cpp
${MAIN_LIB_DIR}/spells/effects/Catapult.cpp
${MAIN_LIB_DIR}/spells/effects/Clone.cpp
${MAIN_LIB_DIR}/spells/effects/Damage.cpp
${MAIN_LIB_DIR}/spells/effects/DemonSummon.cpp
${MAIN_LIB_DIR}/spells/effects/Dispel.cpp
${MAIN_LIB_DIR}/spells/effects/Effect.cpp
${MAIN_LIB_DIR}/spells/effects/Effects.cpp
${MAIN_LIB_DIR}/spells/effects/Heal.cpp
${MAIN_LIB_DIR}/spells/effects/LocationEffect.cpp
${MAIN_LIB_DIR}/spells/effects/Moat.cpp
${MAIN_LIB_DIR}/spells/effects/Obstacle.cpp
${MAIN_LIB_DIR}/spells/effects/Registry.cpp
${MAIN_LIB_DIR}/spells/effects/UnitEffect.cpp
${MAIN_LIB_DIR}/spells/effects/Summon.cpp
${MAIN_LIB_DIR}/spells/effects/Teleport.cpp
${MAIN_LIB_DIR}/spells/effects/Timed.cpp
${MAIN_LIB_DIR}/spells/effects/RemoveObstacle.cpp
${MAIN_LIB_DIR}/spells/effects/Sacrifice.cpp
${MAIN_LIB_DIR}/vstd/DateUtils.cpp
${MAIN_LIB_DIR}/vstd/StringUtils.cpp
${MAIN_LIB_DIR}/ArtifactUtils.cpp
${MAIN_LIB_DIR}/BasicTypes.cpp
${MAIN_LIB_DIR}/BattleFieldHandler.cpp
${MAIN_LIB_DIR}/CAndroidVMHelper.cpp
${MAIN_LIB_DIR}/CArtHandler.cpp
${MAIN_LIB_DIR}/CArtifactInstance.cpp
${MAIN_LIB_DIR}/CBonusTypeHandler.cpp
${MAIN_LIB_DIR}/CBuildingHandler.cpp
${MAIN_LIB_DIR}/CConfigHandler.cpp
${MAIN_LIB_DIR}/CConsoleHandler.cpp
${MAIN_LIB_DIR}/CCreatureHandler.cpp
${MAIN_LIB_DIR}/CCreatureSet.cpp
${MAIN_LIB_DIR}/CGameInfoCallback.cpp
${MAIN_LIB_DIR}/CGameInterface.cpp
${MAIN_LIB_DIR}/CGeneralTextHandler.cpp
${MAIN_LIB_DIR}/CHeroHandler.cpp
${MAIN_LIB_DIR}/CPlayerState.cpp
${MAIN_LIB_DIR}/CRandomGenerator.cpp
${MAIN_LIB_DIR}/CScriptingModule.cpp
${MAIN_LIB_DIR}/CSkillHandler.cpp
${MAIN_LIB_DIR}/CStack.cpp
${MAIN_LIB_DIR}/CThreadHelper.cpp
${MAIN_LIB_DIR}/CTownHandler.cpp
${MAIN_LIB_DIR}/GameSettings.cpp
${MAIN_LIB_DIR}/IGameCallback.cpp
${MAIN_LIB_DIR}/IHandlerBase.cpp
${MAIN_LIB_DIR}/JsonDetail.cpp
${MAIN_LIB_DIR}/JsonNode.cpp
${MAIN_LIB_DIR}/JsonRandom.cpp
${MAIN_LIB_DIR}/LoadProgress.cpp
${MAIN_LIB_DIR}/LogicalExpression.cpp
${MAIN_LIB_DIR}/MetaString.cpp
${MAIN_LIB_DIR}/ObstacleHandler.cpp
${MAIN_LIB_DIR}/StartInfo.cpp
${MAIN_LIB_DIR}/ResourceSet.cpp
${MAIN_LIB_DIR}/RiverHandler.cpp
${MAIN_LIB_DIR}/RoadHandler.cpp
${MAIN_LIB_DIR}/ScriptHandler.cpp
${MAIN_LIB_DIR}/TerrainHandler.cpp
${MAIN_LIB_DIR}/TextOperations.cpp
${MAIN_LIB_DIR}/TurnTimerInfo.cpp
${MAIN_LIB_DIR}/VCMIDirs.cpp
${MAIN_LIB_DIR}/VCMI_Lib.cpp
)
# Version.cpp is a generated file
if(ENABLE_GITVERSION)
list(APPEND lib_SRCS ${CMAKE_BINARY_DIR}/Version.cpp)
set_source_files_properties(${CMAKE_BINARY_DIR}/Version.cpp
PROPERTIES GENERATED TRUE
)
endif()
set(lib_HEADERS
${MAIN_LIB_DIR}/../include/vstd/CLoggerBase.h
${MAIN_LIB_DIR}/../Global.h
${MAIN_LIB_DIR}/../AUTHORS.h
${MAIN_LIB_DIR}/StdInc.h
${MAIN_LIB_DIR}/../include/vstd/ContainerUtils.h
${MAIN_LIB_DIR}/../include/vstd/RNG.h
${MAIN_LIB_DIR}/../include/vstd/DateUtils.h
${MAIN_LIB_DIR}/../include/vstd/StringUtils.h
${MAIN_LIB_DIR}/../include/vcmi/events/AdventureEvents.h
${MAIN_LIB_DIR}/../include/vcmi/events/ApplyDamage.h
${MAIN_LIB_DIR}/../include/vcmi/events/BattleEvents.h
${MAIN_LIB_DIR}/../include/vcmi/events/Event.h
${MAIN_LIB_DIR}/../include/vcmi/events/EventBus.h
${MAIN_LIB_DIR}/../include/vcmi/events/GameResumed.h
${MAIN_LIB_DIR}/../include/vcmi/events/GenericEvents.h
${MAIN_LIB_DIR}/../include/vcmi/events/ObjectVisitEnded.h
${MAIN_LIB_DIR}/../include/vcmi/events/ObjectVisitStarted.h
${MAIN_LIB_DIR}/../include/vcmi/events/PlayerGotTurn.h
${MAIN_LIB_DIR}/../include/vcmi/events/SubscriptionRegistry.h
${MAIN_LIB_DIR}/../include/vcmi/events/TurnStarted.h
${MAIN_LIB_DIR}/../include/vcmi/scripting/Service.h
${MAIN_LIB_DIR}/../include/vcmi/spells/Caster.h
${MAIN_LIB_DIR}/../include/vcmi/spells/Magic.h
${MAIN_LIB_DIR}/../include/vcmi/spells/Service.h
${MAIN_LIB_DIR}/../include/vcmi/spells/Spell.h
${MAIN_LIB_DIR}/../include/vcmi/Artifact.h
${MAIN_LIB_DIR}/../include/vcmi/ArtifactService.h
${MAIN_LIB_DIR}/../include/vcmi/Creature.h
${MAIN_LIB_DIR}/../include/vcmi/CreatureService.h
${MAIN_LIB_DIR}/../include/vcmi/Entity.h
${MAIN_LIB_DIR}/../include/vcmi/Environment.h
${MAIN_LIB_DIR}/../include/vcmi/Faction.h
${MAIN_LIB_DIR}/../include/vcmi/FactionService.h
${MAIN_LIB_DIR}/../include/vcmi/HeroClass.h
${MAIN_LIB_DIR}/../include/vcmi/HeroClassService.h
${MAIN_LIB_DIR}/../include/vcmi/HeroType.h
${MAIN_LIB_DIR}/../include/vcmi/HeroTypeService.h
${MAIN_LIB_DIR}/../include/vcmi/Metatype.h
${MAIN_LIB_DIR}/../include/vcmi/Player.h
${MAIN_LIB_DIR}/../include/vcmi/ServerCallback.h
${MAIN_LIB_DIR}/../include/vcmi/Services.h
${MAIN_LIB_DIR}/../include/vcmi/Skill.h
${MAIN_LIB_DIR}/../include/vcmi/SkillService.h
${MAIN_LIB_DIR}/../include/vcmi/Team.h
${MAIN_LIB_DIR}/battle/AccessibilityInfo.h
${MAIN_LIB_DIR}/battle/AutocombatPreferences.h
${MAIN_LIB_DIR}/battle/BattleAction.h
${MAIN_LIB_DIR}/battle/BattleAttackInfo.h
${MAIN_LIB_DIR}/battle/BattleHex.h
${MAIN_LIB_DIR}/battle/BattleInfo.h
${MAIN_LIB_DIR}/battle/BattleStateInfoForRetreat.h
${MAIN_LIB_DIR}/battle/BattleProxy.h
${MAIN_LIB_DIR}/battle/CBattleInfoCallback.h
${MAIN_LIB_DIR}/battle/CBattleInfoEssentials.h
${MAIN_LIB_DIR}/battle/CObstacleInstance.h
${MAIN_LIB_DIR}/battle/CPlayerBattleCallback.h
${MAIN_LIB_DIR}/battle/CUnitState.h
${MAIN_LIB_DIR}/battle/DamageCalculator.h
${MAIN_LIB_DIR}/battle/Destination.h
${MAIN_LIB_DIR}/battle/IBattleInfoCallback.h
${MAIN_LIB_DIR}/battle/IBattleState.h
${MAIN_LIB_DIR}/battle/IUnitInfo.h
${MAIN_LIB_DIR}/battle/PossiblePlayerBattleAction.h
${MAIN_LIB_DIR}/battle/ReachabilityInfo.h
${MAIN_LIB_DIR}/battle/SideInBattle.h
${MAIN_LIB_DIR}/battle/SiegeInfo.h
${MAIN_LIB_DIR}/battle/Unit.h
${MAIN_LIB_DIR}/bonuses/Bonus.h
${MAIN_LIB_DIR}/bonuses/BonusEnum.h
${MAIN_LIB_DIR}/bonuses/BonusList.h
${MAIN_LIB_DIR}/bonuses/BonusParams.h
${MAIN_LIB_DIR}/bonuses/BonusSelector.h
${MAIN_LIB_DIR}/bonuses/BonusCustomTypes.h
${MAIN_LIB_DIR}/bonuses/CBonusProxy.h
${MAIN_LIB_DIR}/bonuses/CBonusSystemNode.h
${MAIN_LIB_DIR}/bonuses/IBonusBearer.h
${MAIN_LIB_DIR}/bonuses/Limiters.h
${MAIN_LIB_DIR}/bonuses/Propagators.h
${MAIN_LIB_DIR}/bonuses/Updaters.h
${MAIN_LIB_DIR}/campaign/CampaignConstants.h
${MAIN_LIB_DIR}/campaign/CampaignHandler.h
${MAIN_LIB_DIR}/campaign/CampaignScenarioPrologEpilog.h
${MAIN_LIB_DIR}/campaign/CampaignState.h
${MAIN_LIB_DIR}/constants/EntityIdentifiers.h
${MAIN_LIB_DIR}/constants/Enumerations.h
${MAIN_LIB_DIR}/constants/IdentifierBase.h
${MAIN_LIB_DIR}/constants/VariantIdentifier.h
${MAIN_LIB_DIR}/constants/NumericConstants.h
${MAIN_LIB_DIR}/constants/StringConstants.h
${MAIN_LIB_DIR}/events/ApplyDamage.h
${MAIN_LIB_DIR}/events/GameResumed.h
${MAIN_LIB_DIR}/events/ObjectVisitEnded.h
${MAIN_LIB_DIR}/events/ObjectVisitStarted.h
${MAIN_LIB_DIR}/events/PlayerGotTurn.h
${MAIN_LIB_DIR}/events/TurnStarted.h
${MAIN_LIB_DIR}/filesystem/AdapterLoaders.h
${MAIN_LIB_DIR}/filesystem/CArchiveLoader.h
${MAIN_LIB_DIR}/filesystem/CBinaryReader.h
${MAIN_LIB_DIR}/filesystem/CCompressedStream.h
${MAIN_LIB_DIR}/filesystem/CFileInputStream.h
${MAIN_LIB_DIR}/filesystem/CFilesystemLoader.h
${MAIN_LIB_DIR}/filesystem/CInputOutputStream.h
${MAIN_LIB_DIR}/filesystem/CInputStream.h
${MAIN_LIB_DIR}/filesystem/CMemoryBuffer.h
${MAIN_LIB_DIR}/filesystem/CMemoryStream.h
${MAIN_LIB_DIR}/filesystem/COutputStream.h
${MAIN_LIB_DIR}/filesystem/CStream.h
${MAIN_LIB_DIR}/filesystem/CZipLoader.h
${MAIN_LIB_DIR}/filesystem/CZipSaver.h
${MAIN_LIB_DIR}/filesystem/FileInfo.h
${MAIN_LIB_DIR}/filesystem/Filesystem.h
${MAIN_LIB_DIR}/filesystem/ISimpleResourceLoader.h
${MAIN_LIB_DIR}/filesystem/MinizipExtensions.h
${MAIN_LIB_DIR}/filesystem/ResourcePath.h
${MAIN_LIB_DIR}/gameState/CGameState.h
${MAIN_LIB_DIR}/gameState/CGameStateCampaign.h
${MAIN_LIB_DIR}/gameState/EVictoryLossCheckResult.h
${MAIN_LIB_DIR}/gameState/InfoAboutArmy.h
${MAIN_LIB_DIR}/gameState/SThievesGuildInfo.h
${MAIN_LIB_DIR}/gameState/TavernHeroesPool.h
${MAIN_LIB_DIR}/gameState/TavernSlot.h
${MAIN_LIB_DIR}/gameState/QuestInfo.h
${MAIN_LIB_DIR}/logging/CBasicLogConfigurator.h
${MAIN_LIB_DIR}/logging/CLogger.h
${MAIN_LIB_DIR}/mapObjectConstructors/AObjectTypeHandler.h
${MAIN_LIB_DIR}/mapObjectConstructors/CBankInstanceConstructor.h
${MAIN_LIB_DIR}/mapObjectConstructors/CDefaultObjectTypeHandler.h
${MAIN_LIB_DIR}/mapObjectConstructors/CObjectClassesHandler.h
${MAIN_LIB_DIR}/mapObjectConstructors/CommonConstructors.h
${MAIN_LIB_DIR}/mapObjectConstructors/CRewardableConstructor.h
${MAIN_LIB_DIR}/mapObjectConstructors/DwellingInstanceConstructor.h
${MAIN_LIB_DIR}/mapObjectConstructors/HillFortInstanceConstructor.h
${MAIN_LIB_DIR}/mapObjectConstructors/IObjectInfo.h
${MAIN_LIB_DIR}/mapObjectConstructors/RandomMapInfo.h
${MAIN_LIB_DIR}/mapObjectConstructors/ShipyardInstanceConstructor.h
${MAIN_LIB_DIR}/mapObjectConstructors/SObjectSounds.h
${MAIN_LIB_DIR}/mapObjects/CArmedInstance.h
${MAIN_LIB_DIR}/mapObjects/CBank.h
${MAIN_LIB_DIR}/mapObjects/CGCreature.h
${MAIN_LIB_DIR}/mapObjects/CGDwelling.h
${MAIN_LIB_DIR}/mapObjects/CGHeroInstance.h
${MAIN_LIB_DIR}/mapObjects/CGMarket.h
${MAIN_LIB_DIR}/mapObjects/CGObjectInstance.h
${MAIN_LIB_DIR}/mapObjects/CGPandoraBox.h
${MAIN_LIB_DIR}/mapObjects/CGTownBuilding.h
${MAIN_LIB_DIR}/mapObjects/CGTownInstance.h
${MAIN_LIB_DIR}/mapObjects/CObjectHandler.h
${MAIN_LIB_DIR}/mapObjects/CQuest.h
${MAIN_LIB_DIR}/mapObjects/CRewardableObject.h
${MAIN_LIB_DIR}/mapObjects/IMarket.h
${MAIN_LIB_DIR}/mapObjects/IObjectInterface.h
${MAIN_LIB_DIR}/mapObjects/MapObjects.h
${MAIN_LIB_DIR}/mapObjects/MiscObjects.h
${MAIN_LIB_DIR}/mapObjects/ObjectTemplate.h
${MAIN_LIB_DIR}/mapping/CDrawRoadsOperation.h
${MAIN_LIB_DIR}/mapping/CMapDefines.h
${MAIN_LIB_DIR}/mapping/CMapEditManager.h
${MAIN_LIB_DIR}/mapping/CMapHeader.h
${MAIN_LIB_DIR}/mapping/CMap.h
${MAIN_LIB_DIR}/mapping/CMapInfo.h
${MAIN_LIB_DIR}/mapping/CMapOperation.h
${MAIN_LIB_DIR}/mapping/CMapService.h
${MAIN_LIB_DIR}/mapping/MapEditUtils.h
${MAIN_LIB_DIR}/mapping/MapIdentifiersH3M.h
${MAIN_LIB_DIR}/mapping/MapFeaturesH3M.h
${MAIN_LIB_DIR}/mapping/MapFormatH3M.h
${MAIN_LIB_DIR}/mapping/MapFormat.h
${MAIN_LIB_DIR}/mapping/MapReaderH3M.h
${MAIN_LIB_DIR}/mapping/MapFormatJson.h
${MAIN_LIB_DIR}/mapping/ObstacleProxy.h
${MAIN_LIB_DIR}/modding/ActiveModsInSaveList.h
${MAIN_LIB_DIR}/modding/CModHandler.h
${MAIN_LIB_DIR}/modding/CModInfo.h
${MAIN_LIB_DIR}/modding/CModVersion.h
${MAIN_LIB_DIR}/modding/ContentTypeHandler.h
${MAIN_LIB_DIR}/modding/IdentifierStorage.h
${MAIN_LIB_DIR}/modding/ModIncompatibility.h
${MAIN_LIB_DIR}/modding/ModScope.h
${MAIN_LIB_DIR}/modding/ModUtility.h
${MAIN_LIB_DIR}/modding/ModVerificationInfo.h
${MAIN_LIB_DIR}/network/NetworkConnection.h
${MAIN_LIB_DIR}/network/NetworkDefines.h
${MAIN_LIB_DIR}/network/NetworkHandler.h
${MAIN_LIB_DIR}/network/NetworkInterface.h
${MAIN_LIB_DIR}/network/NetworkServer.h
${MAIN_LIB_DIR}/networkPacks/ArtifactLocation.h
${MAIN_LIB_DIR}/networkPacks/BattleChanges.h
${MAIN_LIB_DIR}/networkPacks/Component.h
${MAIN_LIB_DIR}/networkPacks/EInfoWindowMode.h
${MAIN_LIB_DIR}/networkPacks/EntityChanges.h
${MAIN_LIB_DIR}/networkPacks/EOpenWindowMode.h
${MAIN_LIB_DIR}/networkPacks/NetPacksBase.h
${MAIN_LIB_DIR}/networkPacks/NetPackVisitor.h
${MAIN_LIB_DIR}/networkPacks/ObjProperty.h
${MAIN_LIB_DIR}/networkPacks/PacksForClient.h
${MAIN_LIB_DIR}/networkPacks/PacksForClientBattle.h
${MAIN_LIB_DIR}/networkPacks/PacksForLobby.h
${MAIN_LIB_DIR}/networkPacks/PacksForServer.h
${MAIN_LIB_DIR}/networkPacks/SetStackEffect.h
${MAIN_LIB_DIR}/networkPacks/StackLocation.h
${MAIN_LIB_DIR}/networkPacks/TradeItem.h
${MAIN_LIB_DIR}/pathfinder/INodeStorage.h
${MAIN_LIB_DIR}/pathfinder/CGPathNode.h
${MAIN_LIB_DIR}/pathfinder/CPathfinder.h
${MAIN_LIB_DIR}/pathfinder/NodeStorage.h
${MAIN_LIB_DIR}/pathfinder/PathfinderOptions.h
${MAIN_LIB_DIR}/pathfinder/PathfinderUtil.h
${MAIN_LIB_DIR}/pathfinder/PathfindingRules.h
${MAIN_LIB_DIR}/pathfinder/TurnInfo.h
${MAIN_LIB_DIR}/registerTypes/RegisterTypes.h
${MAIN_LIB_DIR}/registerTypes/RegisterTypesClientPacks.h
${MAIN_LIB_DIR}/registerTypes/RegisterTypesLobbyPacks.h
${MAIN_LIB_DIR}/registerTypes/RegisterTypesMapObjects.h
${MAIN_LIB_DIR}/registerTypes/RegisterTypesServerPacks.h
${MAIN_LIB_DIR}/rewardable/Configuration.h
${MAIN_LIB_DIR}/rewardable/Info.h
${MAIN_LIB_DIR}/rewardable/Interface.h
${MAIN_LIB_DIR}/rewardable/Limiter.h
${MAIN_LIB_DIR}/rewardable/Reward.h
${MAIN_LIB_DIR}/rmg/RmgArea.h
${MAIN_LIB_DIR}/rmg/RmgObject.h
${MAIN_LIB_DIR}/rmg/RmgPath.h
${MAIN_LIB_DIR}/rmg/CMapGenerator.h
${MAIN_LIB_DIR}/rmg/CMapGenOptions.h
${MAIN_LIB_DIR}/rmg/CRmgTemplate.h
${MAIN_LIB_DIR}/rmg/CRmgTemplateStorage.h
${MAIN_LIB_DIR}/rmg/CZonePlacer.h
${MAIN_LIB_DIR}/rmg/TileInfo.h
${MAIN_LIB_DIR}/rmg/Zone.h
${MAIN_LIB_DIR}/rmg/RmgMap.h
${MAIN_LIB_DIR}/rmg/float3.h
${MAIN_LIB_DIR}/rmg/Functions.h
${MAIN_LIB_DIR}/rmg/PenroseTiling.h
${MAIN_LIB_DIR}/rmg/modificators/Modificator.h
${MAIN_LIB_DIR}/rmg/modificators/ObjectManager.h
${MAIN_LIB_DIR}/rmg/modificators/ObjectDistributor.h
${MAIN_LIB_DIR}/rmg/modificators/RoadPlacer.h
${MAIN_LIB_DIR}/rmg/modificators/TreasurePlacer.h
${MAIN_LIB_DIR}/rmg/modificators/PrisonHeroPlacer.h
${MAIN_LIB_DIR}/rmg/modificators/QuestArtifactPlacer.h
${MAIN_LIB_DIR}/rmg/modificators/ConnectionsPlacer.h
${MAIN_LIB_DIR}/rmg/modificators/WaterAdopter.h
${MAIN_LIB_DIR}/rmg/modificators/MinePlacer.h
${MAIN_LIB_DIR}/rmg/modificators/TownPlacer.h
${MAIN_LIB_DIR}/rmg/modificators/WaterProxy.h
${MAIN_LIB_DIR}/rmg/modificators/WaterRoutes.h
${MAIN_LIB_DIR}/rmg/modificators/RockPlacer.h
${MAIN_LIB_DIR}/rmg/modificators/RockFiller.h
${MAIN_LIB_DIR}/rmg/modificators/ObstaclePlacer.h
${MAIN_LIB_DIR}/rmg/modificators/RiverPlacer.h
${MAIN_LIB_DIR}/rmg/modificators/TerrainPainter.h
${MAIN_LIB_DIR}/rmg/threadpool/BlockingQueue.h
${MAIN_LIB_DIR}/rmg/threadpool/ThreadPool.h
${MAIN_LIB_DIR}/rmg/threadpool/MapProxy.h
${MAIN_LIB_DIR}/serializer/BinaryDeserializer.h
${MAIN_LIB_DIR}/serializer/BinarySerializer.h
${MAIN_LIB_DIR}/serializer/CLoadFile.h
${MAIN_LIB_DIR}/serializer/CMemorySerializer.h
${MAIN_LIB_DIR}/serializer/Connection.h
${MAIN_LIB_DIR}/serializer/CSaveFile.h
${MAIN_LIB_DIR}/serializer/CSerializer.h
${MAIN_LIB_DIR}/serializer/CTypeList.h
${MAIN_LIB_DIR}/serializer/JsonDeserializer.h
${MAIN_LIB_DIR}/serializer/JsonSerializeFormat.h
${MAIN_LIB_DIR}/serializer/JsonSerializer.h
${MAIN_LIB_DIR}/serializer/JsonUpdater.h
${MAIN_LIB_DIR}/serializer/Cast.h
${MAIN_LIB_DIR}/serializer/ESerializationVersion.h
${MAIN_LIB_DIR}/spells/AbilityCaster.h
${MAIN_LIB_DIR}/spells/AdventureSpellMechanics.h
${MAIN_LIB_DIR}/spells/BattleSpellMechanics.h
${MAIN_LIB_DIR}/spells/BonusCaster.h
${MAIN_LIB_DIR}/spells/CSpellHandler.h
${MAIN_LIB_DIR}/spells/ExternalCaster.h
${MAIN_LIB_DIR}/spells/ISpellMechanics.h
${MAIN_LIB_DIR}/spells/ObstacleCasterProxy.h
${MAIN_LIB_DIR}/spells/Problem.h
${MAIN_LIB_DIR}/spells/ProxyCaster.h
${MAIN_LIB_DIR}/spells/TargetCondition.h
${MAIN_LIB_DIR}/spells/ViewSpellInt.h
${MAIN_LIB_DIR}/spells/effects/Catapult.h
${MAIN_LIB_DIR}/spells/effects/Clone.h
${MAIN_LIB_DIR}/spells/effects/Damage.h
${MAIN_LIB_DIR}/spells/effects/DemonSummon.h
${MAIN_LIB_DIR}/spells/effects/Dispel.h
${MAIN_LIB_DIR}/spells/effects/Effect.h
${MAIN_LIB_DIR}/spells/effects/Effects.h
${MAIN_LIB_DIR}/spells/effects/EffectsFwd.h
${MAIN_LIB_DIR}/spells/effects/Heal.h
${MAIN_LIB_DIR}/spells/effects/LocationEffect.h
${MAIN_LIB_DIR}/spells/effects/Obstacle.h
${MAIN_LIB_DIR}/spells/effects/Registry.h
${MAIN_LIB_DIR}/spells/effects/UnitEffect.h
${MAIN_LIB_DIR}/spells/effects/Summon.h
${MAIN_LIB_DIR}/spells/effects/Teleport.h
${MAIN_LIB_DIR}/spells/effects/Timed.h
${MAIN_LIB_DIR}/spells/effects/RemoveObstacle.h
${MAIN_LIB_DIR}/spells/effects/Sacrifice.h
${MAIN_LIB_DIR}/AI_Base.h
${MAIN_LIB_DIR}/ArtifactUtils.h
${MAIN_LIB_DIR}/BattleFieldHandler.h
${MAIN_LIB_DIR}/CAndroidVMHelper.h
${MAIN_LIB_DIR}/CArtHandler.h
${MAIN_LIB_DIR}/CArtifactInstance.h
${MAIN_LIB_DIR}/CBonusTypeHandler.h
${MAIN_LIB_DIR}/CBuildingHandler.h
${MAIN_LIB_DIR}/CConfigHandler.h
${MAIN_LIB_DIR}/CConsoleHandler.h
${MAIN_LIB_DIR}/CCreatureHandler.h
${MAIN_LIB_DIR}/CCreatureSet.h
${MAIN_LIB_DIR}/CGameInfoCallback.h
${MAIN_LIB_DIR}/CGameInterface.h
${MAIN_LIB_DIR}/CGeneralTextHandler.h
${MAIN_LIB_DIR}/CHeroHandler.h
${MAIN_LIB_DIR}/CondSh.h
${MAIN_LIB_DIR}/ConstTransitivePtr.h
${MAIN_LIB_DIR}/Color.h
${MAIN_LIB_DIR}/CPlayerState.h
${MAIN_LIB_DIR}/CRandomGenerator.h
${MAIN_LIB_DIR}/CScriptingModule.h
${MAIN_LIB_DIR}/CSkillHandler.h
${MAIN_LIB_DIR}/CSoundBase.h
${MAIN_LIB_DIR}/CStack.h
${MAIN_LIB_DIR}/CStopWatch.h
${MAIN_LIB_DIR}/CThreadHelper.h
${MAIN_LIB_DIR}/CTownHandler.h
${MAIN_LIB_DIR}/ExtraOptionsInfo.h
${MAIN_LIB_DIR}/FunctionList.h
${MAIN_LIB_DIR}/GameCallbackHolder.h
${MAIN_LIB_DIR}/GameConstants.h
${MAIN_LIB_DIR}/GameSettings.h
${MAIN_LIB_DIR}/IBonusTypeHandler.h
${MAIN_LIB_DIR}/IGameCallback.h
${MAIN_LIB_DIR}/IGameEventsReceiver.h
${MAIN_LIB_DIR}/IHandlerBase.h
${MAIN_LIB_DIR}/int3.h
${MAIN_LIB_DIR}/JsonDetail.h
${MAIN_LIB_DIR}/JsonNode.h
${MAIN_LIB_DIR}/JsonRandom.h
${MAIN_LIB_DIR}/Languages.h
${MAIN_LIB_DIR}/LoadProgress.h
${MAIN_LIB_DIR}/LogicalExpression.h
${MAIN_LIB_DIR}/MetaString.h
${MAIN_LIB_DIR}/ObstacleHandler.h
${MAIN_LIB_DIR}/Point.h
${MAIN_LIB_DIR}/Rect.h
${MAIN_LIB_DIR}/Rect.cpp
${MAIN_LIB_DIR}/ResourceSet.h
${MAIN_LIB_DIR}/RiverHandler.h
${MAIN_LIB_DIR}/RoadHandler.h
${MAIN_LIB_DIR}/ScriptHandler.h
${MAIN_LIB_DIR}/ScopeGuard.h
${MAIN_LIB_DIR}/StartInfo.h
${MAIN_LIB_DIR}/TerrainHandler.h
${MAIN_LIB_DIR}/TextOperations.h
${MAIN_LIB_DIR}/TurnTimerInfo.h
${MAIN_LIB_DIR}/UnlockGuard.h
${MAIN_LIB_DIR}/VCMIDirs.h
${MAIN_LIB_DIR}/vcmi_endian.h
${MAIN_LIB_DIR}/VCMI_Lib.h
)
assign_source_group(${lib_SRCS} ${lib_HEADERS})
add_library(${TARGET_NAME} ${LIBRARY_TYPE} ${lib_SRCS} ${lib_HEADERS})
set_target_properties(${TARGET_NAME} PROPERTIES COMPILE_DEFINITIONS "VCMI_DLL=1")
target_link_libraries(${TARGET_NAME} PUBLIC
minizip::minizip ZLIB::ZLIB
${SYSTEM_LIBS} Boost::boost Boost::thread Boost::filesystem Boost::program_options Boost::locale Boost::date_time
)
if(APPLE_IOS)
target_link_libraries(${TARGET_NAME} PUBLIC iOS_utils)
endif()
target_include_directories(${TARGET_NAME}
PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}
PUBLIC ${MAIN_LIB_DIR}/..
PUBLIC ${MAIN_LIB_DIR}/../include
PUBLIC ${MAIN_LIB_DIR}
)
if(WIN32)
set_target_properties(${TARGET_NAME}
PROPERTIES
OUTPUT_NAME "VCMI_lib"
PROJECT_LABEL "VCMI_lib"
)
endif()
vcmi_set_output_dir(${TARGET_NAME} "")
enable_pch(${TARGET_NAME})
# We want to deploy assets into build directory for easier debugging without install
if(COPY_CONFIG_ON_BUILD)
add_custom_command(TARGET ${TARGET_NAME} POST_BUILD
COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/config
COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/Mods
COMMAND ${CMAKE_COMMAND} -P ${CMAKE_SOURCE_DIR}/cmake_modules/create_link.cmake ${MAIN_LIB_DIR}/../config ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/config
COMMAND ${CMAKE_COMMAND} -P ${CMAKE_SOURCE_DIR}/cmake_modules/create_link.cmake ${MAIN_LIB_DIR}/../Mods ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/Mods
)
endif()
# Update version before vcmi compiling
if(TARGET update_version)
add_dependencies(${TARGET_NAME} update_version)
endif()
if("${LIBRARY_TYPE}" STREQUAL SHARED)
install(TARGETS ${TARGET_NAME} RUNTIME DESTINATION ${LIB_DIR} LIBRARY DESTINATION ${LIB_DIR})
endif()
if(APPLE_IOS AND NOT USING_CONAN)
get_target_property(LINKED_LIBS ${TARGET_NAME} LINK_LIBRARIES)
foreach(LINKED_LIB IN LISTS LINKED_LIBS)
if(NOT TARGET ${LINKED_LIB})
if(LINKED_LIB MATCHES "\\${CMAKE_SHARED_LIBRARY_SUFFIX}$")
install(FILES ${LINKED_LIB} DESTINATION ${LIB_DIR})
endif()
continue()
endif()
get_target_property(LIB_TYPE ${LINKED_LIB} TYPE)
if(NOT LIB_TYPE STREQUAL "SHARED_LIBRARY")
continue()
endif()
get_target_property(_aliased ${LINKED_LIB} ALIASED_TARGET)
if(_aliased)
set(LINKED_LIB_REAL ${_aliased})
else()
set(LINKED_LIB_REAL ${LINKED_LIB})
endif()
get_target_property(_imported ${LINKED_LIB_REAL} IMPORTED)
if(_imported)
set(INSTALL_TYPE IMPORTED_RUNTIME_ARTIFACTS)
get_target_property(BOOST_DEPENDENCIES ${LINKED_LIB_REAL} INTERFACE_LINK_LIBRARIES)
foreach(BOOST_DEPENDENCY IN LISTS BOOST_DEPENDENCIES)
get_target_property(BOOST_DEPENDENCY_TYPE ${BOOST_DEPENDENCY} TYPE)
if(BOOST_DEPENDENCY_TYPE STREQUAL "SHARED_LIBRARY")
install(IMPORTED_RUNTIME_ARTIFACTS ${BOOST_DEPENDENCY} LIBRARY DESTINATION ${LIB_DIR})
endif()
endforeach()
else()
set(INSTALL_TYPE TARGETS)
endif()
install(${INSTALL_TYPE} ${LINKED_LIB_REAL} LIBRARY DESTINATION ${LIB_DIR})
endforeach()
endif()
endmacro()

View File

@ -463,7 +463,7 @@
"properties" : {
"format" : {
"type" : "string",
"default" : "[%c] %l %n - %m"
"default" : "[%c] %l [%t] %n - %m"
}
}
},

View File

@ -135,7 +135,7 @@ if (NOT APPLE_IOS AND NOT ANDROID)
target_link_libraries(vcmilauncher SDL2::SDL2)
endif()
target_link_libraries(vcmilauncher ${VCMI_LIB_TARGET} Qt${QT_VERSION_MAJOR}::Widgets Qt${QT_VERSION_MAJOR}::Network)
target_link_libraries(vcmilauncher vcmi Qt${QT_VERSION_MAJOR}::Widgets Qt${QT_VERSION_MAJOR}::Network)
target_include_directories(vcmilauncher
PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}
)

View File

@ -1,18 +1,775 @@
if(ENABLE_STATIC_AI_LIBS)
add_main_lib(${VCMI_LIB_TARGET} STATIC)
target_compile_definitions(${VCMI_LIB_TARGET} PRIVATE STATIC_AI)
target_link_libraries(${VCMI_LIB_TARGET} PRIVATE
set(lib_SRCS
StdInc.cpp
battle/AccessibilityInfo.cpp
battle/BattleAction.cpp
battle/BattleAttackInfo.cpp
battle/BattleHex.cpp
battle/BattleInfo.cpp
battle/BattleProxy.cpp
battle/BattleStateInfoForRetreat.cpp
battle/CBattleInfoCallback.cpp
battle/CBattleInfoEssentials.cpp
battle/CObstacleInstance.cpp
battle/CPlayerBattleCallback.cpp
battle/CUnitState.cpp
battle/DamageCalculator.cpp
battle/Destination.cpp
battle/IBattleState.cpp
battle/ReachabilityInfo.cpp
battle/SideInBattle.cpp
battle/SiegeInfo.cpp
battle/Unit.cpp
bonuses/Bonus.cpp
bonuses/BonusEnum.cpp
bonuses/BonusList.cpp
bonuses/BonusParams.cpp
bonuses/BonusSelector.cpp
bonuses/BonusCustomTypes.cpp
bonuses/CBonusProxy.cpp
bonuses/CBonusSystemNode.cpp
bonuses/IBonusBearer.cpp
bonuses/Limiters.cpp
bonuses/Propagators.cpp
bonuses/Updaters.cpp
campaign/CampaignHandler.cpp
campaign/CampaignState.cpp
constants/EntityIdentifiers.cpp
events/ApplyDamage.cpp
events/GameResumed.cpp
events/ObjectVisitEnded.cpp
events/ObjectVisitStarted.cpp
events/PlayerGotTurn.cpp
events/TurnStarted.cpp
filesystem/AdapterLoaders.cpp
filesystem/CArchiveLoader.cpp
filesystem/CBinaryReader.cpp
filesystem/CCompressedStream.cpp
filesystem/CFileInputStream.cpp
filesystem/CFilesystemLoader.cpp
filesystem/CMemoryBuffer.cpp
filesystem/CMemoryStream.cpp
filesystem/CZipLoader.cpp
filesystem/CZipSaver.cpp
filesystem/FileInfo.cpp
filesystem/Filesystem.cpp
filesystem/MinizipExtensions.cpp
filesystem/ResourcePath.cpp
gameState/CGameState.cpp
gameState/CGameStateCampaign.cpp
gameState/InfoAboutArmy.cpp
gameState/TavernHeroesPool.cpp
logging/CBasicLogConfigurator.cpp
logging/CLogger.cpp
mapObjectConstructors/AObjectTypeHandler.cpp
mapObjectConstructors/CBankInstanceConstructor.cpp
mapObjectConstructors/CObjectClassesHandler.cpp
mapObjectConstructors/CommonConstructors.cpp
mapObjectConstructors/CRewardableConstructor.cpp
mapObjectConstructors/DwellingInstanceConstructor.cpp
mapObjectConstructors/HillFortInstanceConstructor.cpp
mapObjectConstructors/ShipyardInstanceConstructor.cpp
mapObjects/CArmedInstance.cpp
mapObjects/CBank.cpp
mapObjects/CGCreature.cpp
mapObjects/CGDwelling.cpp
mapObjects/CGHeroInstance.cpp
mapObjects/CGMarket.cpp
mapObjects/CGObjectInstance.cpp
mapObjects/CGPandoraBox.cpp
mapObjects/CGTownBuilding.cpp
mapObjects/CGTownInstance.cpp
mapObjects/CObjectHandler.cpp
mapObjects/CQuest.cpp
mapObjects/CRewardableObject.cpp
mapObjects/IMarket.cpp
mapObjects/IObjectInterface.cpp
mapObjects/MiscObjects.cpp
mapObjects/ObjectTemplate.cpp
mapping/CDrawRoadsOperation.cpp
mapping/CMap.cpp
mapping/CMapHeader.cpp
mapping/CMapEditManager.cpp
mapping/CMapInfo.cpp
mapping/CMapOperation.cpp
mapping/CMapService.cpp
mapping/MapEditUtils.cpp
mapping/MapIdentifiersH3M.cpp
mapping/MapFeaturesH3M.cpp
mapping/MapFormatH3M.cpp
mapping/MapReaderH3M.cpp
mapping/MapFormatJson.cpp
mapping/ObstacleProxy.cpp
modding/ActiveModsInSaveList.cpp
modding/CModHandler.cpp
modding/CModInfo.cpp
modding/CModVersion.cpp
modding/ContentTypeHandler.cpp
modding/IdentifierStorage.cpp
modding/ModUtility.cpp
network/NetworkConnection.cpp
network/NetworkHandler.cpp
network/NetworkServer.cpp
networkPacks/NetPacksLib.cpp
pathfinder/CGPathNode.cpp
pathfinder/CPathfinder.cpp
pathfinder/NodeStorage.cpp
pathfinder/PathfinderOptions.cpp
pathfinder/PathfindingRules.cpp
pathfinder/TurnInfo.cpp
rewardable/Configuration.cpp
rewardable/Info.cpp
rewardable/Interface.cpp
rewardable/Limiter.cpp
rewardable/Reward.cpp
rmg/RmgArea.cpp
rmg/RmgObject.cpp
rmg/RmgPath.cpp
rmg/CMapGenerator.cpp
rmg/CMapGenOptions.cpp
rmg/CRmgTemplate.cpp
rmg/CRmgTemplateStorage.cpp
rmg/CZonePlacer.cpp
rmg/TileInfo.cpp
rmg/Zone.cpp
rmg/Functions.cpp
rmg/RmgMap.cpp
rmg/PenroseTiling.cpp
rmg/modificators/Modificator.cpp
rmg/modificators/ObjectManager.cpp
rmg/modificators/ObjectDistributor.cpp
rmg/modificators/RoadPlacer.cpp
rmg/modificators/TreasurePlacer.cpp
rmg/modificators/PrisonHeroPlacer.cpp
rmg/modificators/QuestArtifactPlacer.cpp
rmg/modificators/ConnectionsPlacer.cpp
rmg/modificators/WaterAdopter.cpp
rmg/modificators/MinePlacer.cpp
rmg/modificators/TownPlacer.cpp
rmg/modificators/WaterProxy.cpp
rmg/modificators/WaterRoutes.cpp
rmg/modificators/RockPlacer.cpp
rmg/modificators/RockFiller.cpp
rmg/modificators/ObstaclePlacer.cpp
rmg/modificators/RiverPlacer.cpp
rmg/modificators/TerrainPainter.cpp
rmg/threadpool/MapProxy.cpp
serializer/BinaryDeserializer.cpp
serializer/BinarySerializer.cpp
serializer/CLoadFile.cpp
serializer/CMemorySerializer.cpp
serializer/Connection.cpp
serializer/CSaveFile.cpp
serializer/CSerializer.cpp
serializer/CTypeList.cpp
serializer/JsonDeserializer.cpp
serializer/JsonSerializeFormat.cpp
serializer/JsonSerializer.cpp
serializer/JsonUpdater.cpp
spells/AbilityCaster.cpp
spells/AdventureSpellMechanics.cpp
spells/BattleSpellMechanics.cpp
spells/BonusCaster.cpp
spells/CSpellHandler.cpp
spells/ExternalCaster.cpp
spells/ISpellMechanics.cpp
spells/ObstacleCasterProxy.cpp
spells/Problem.cpp
spells/ProxyCaster.cpp
spells/TargetCondition.cpp
spells/ViewSpellInt.cpp
spells/effects/Catapult.cpp
spells/effects/Clone.cpp
spells/effects/Damage.cpp
spells/effects/DemonSummon.cpp
spells/effects/Dispel.cpp
spells/effects/Effect.cpp
spells/effects/Effects.cpp
spells/effects/Heal.cpp
spells/effects/LocationEffect.cpp
spells/effects/Moat.cpp
spells/effects/Obstacle.cpp
spells/effects/Registry.cpp
spells/effects/UnitEffect.cpp
spells/effects/Summon.cpp
spells/effects/Teleport.cpp
spells/effects/Timed.cpp
spells/effects/RemoveObstacle.cpp
spells/effects/Sacrifice.cpp
vstd/DateUtils.cpp
vstd/StringUtils.cpp
ArtifactUtils.cpp
BasicTypes.cpp
BattleFieldHandler.cpp
CAndroidVMHelper.cpp
CArtHandler.cpp
CArtifactInstance.cpp
CBonusTypeHandler.cpp
CBuildingHandler.cpp
CConfigHandler.cpp
CConsoleHandler.cpp
CCreatureHandler.cpp
CCreatureSet.cpp
CGameInfoCallback.cpp
CGameInterface.cpp
CGeneralTextHandler.cpp
CHeroHandler.cpp
CPlayerState.cpp
CRandomGenerator.cpp
CScriptingModule.cpp
CSkillHandler.cpp
CStack.cpp
CThreadHelper.cpp
CTownHandler.cpp
GameSettings.cpp
IGameCallback.cpp
IHandlerBase.cpp
JsonDetail.cpp
JsonNode.cpp
JsonRandom.cpp
LoadProgress.cpp
LogicalExpression.cpp
MetaString.cpp
ObstacleHandler.cpp
StartInfo.cpp
ResourceSet.cpp
RiverHandler.cpp
RoadHandler.cpp
ScriptHandler.cpp
TerrainHandler.cpp
TextOperations.cpp
TurnTimerInfo.cpp
VCMIDirs.cpp
VCMI_Lib.cpp
)
# Version.cpp is a generated file
if(ENABLE_GITVERSION)
list(APPEND lib_SRCS ${CMAKE_BINARY_DIR}/Version.cpp)
set_source_files_properties(${CMAKE_BINARY_DIR}/Version.cpp
PROPERTIES GENERATED TRUE
)
endif()
set(lib_HEADERS
../include/vstd/CLoggerBase.h
../Global.h
../AUTHORS.h
StdInc.h
../include/vstd/ContainerUtils.h
../include/vstd/RNG.h
../include/vstd/DateUtils.h
../include/vstd/StringUtils.h
../include/vcmi/events/AdventureEvents.h
../include/vcmi/events/ApplyDamage.h
../include/vcmi/events/BattleEvents.h
../include/vcmi/events/Event.h
../include/vcmi/events/EventBus.h
../include/vcmi/events/GameResumed.h
../include/vcmi/events/GenericEvents.h
../include/vcmi/events/ObjectVisitEnded.h
../include/vcmi/events/ObjectVisitStarted.h
../include/vcmi/events/PlayerGotTurn.h
../include/vcmi/events/SubscriptionRegistry.h
../include/vcmi/events/TurnStarted.h
../include/vcmi/scripting/Service.h
../include/vcmi/spells/Caster.h
../include/vcmi/spells/Magic.h
../include/vcmi/spells/Service.h
../include/vcmi/spells/Spell.h
../include/vcmi/Artifact.h
../include/vcmi/ArtifactService.h
../include/vcmi/Creature.h
../include/vcmi/CreatureService.h
../include/vcmi/Entity.h
../include/vcmi/Environment.h
../include/vcmi/Faction.h
../include/vcmi/FactionService.h
../include/vcmi/HeroClass.h
../include/vcmi/HeroClassService.h
../include/vcmi/HeroType.h
../include/vcmi/HeroTypeService.h
../include/vcmi/Metatype.h
../include/vcmi/Player.h
../include/vcmi/ServerCallback.h
../include/vcmi/Services.h
../include/vcmi/Skill.h
../include/vcmi/SkillService.h
../include/vcmi/Team.h
battle/AccessibilityInfo.h
battle/AutocombatPreferences.h
battle/BattleAction.h
battle/BattleAttackInfo.h
battle/BattleHex.h
battle/BattleInfo.h
battle/BattleStateInfoForRetreat.h
battle/BattleProxy.h
battle/CBattleInfoCallback.h
battle/CBattleInfoEssentials.h
battle/CObstacleInstance.h
battle/CPlayerBattleCallback.h
battle/CUnitState.h
battle/DamageCalculator.h
battle/Destination.h
battle/IBattleInfoCallback.h
battle/IBattleState.h
battle/IUnitInfo.h
battle/PossiblePlayerBattleAction.h
battle/ReachabilityInfo.h
battle/SideInBattle.h
battle/SiegeInfo.h
battle/Unit.h
bonuses/Bonus.h
bonuses/BonusEnum.h
bonuses/BonusList.h
bonuses/BonusParams.h
bonuses/BonusSelector.h
bonuses/BonusCustomTypes.h
bonuses/CBonusProxy.h
bonuses/CBonusSystemNode.h
bonuses/IBonusBearer.h
bonuses/Limiters.h
bonuses/Propagators.h
bonuses/Updaters.h
campaign/CampaignConstants.h
campaign/CampaignHandler.h
campaign/CampaignScenarioPrologEpilog.h
campaign/CampaignState.h
constants/EntityIdentifiers.h
constants/Enumerations.h
constants/IdentifierBase.h
constants/VariantIdentifier.h
constants/NumericConstants.h
constants/StringConstants.h
events/ApplyDamage.h
events/GameResumed.h
events/ObjectVisitEnded.h
events/ObjectVisitStarted.h
events/PlayerGotTurn.h
events/TurnStarted.h
filesystem/AdapterLoaders.h
filesystem/CArchiveLoader.h
filesystem/CBinaryReader.h
filesystem/CCompressedStream.h
filesystem/CFileInputStream.h
filesystem/CFilesystemLoader.h
filesystem/CInputOutputStream.h
filesystem/CInputStream.h
filesystem/CMemoryBuffer.h
filesystem/CMemoryStream.h
filesystem/COutputStream.h
filesystem/CStream.h
filesystem/CZipLoader.h
filesystem/CZipSaver.h
filesystem/FileInfo.h
filesystem/Filesystem.h
filesystem/ISimpleResourceLoader.h
filesystem/MinizipExtensions.h
filesystem/ResourcePath.h
gameState/CGameState.h
gameState/CGameStateCampaign.h
gameState/EVictoryLossCheckResult.h
gameState/InfoAboutArmy.h
gameState/SThievesGuildInfo.h
gameState/TavernHeroesPool.h
gameState/TavernSlot.h
gameState/QuestInfo.h
logging/CBasicLogConfigurator.h
logging/CLogger.h
mapObjectConstructors/AObjectTypeHandler.h
mapObjectConstructors/CBankInstanceConstructor.h
mapObjectConstructors/CDefaultObjectTypeHandler.h
mapObjectConstructors/CObjectClassesHandler.h
mapObjectConstructors/CommonConstructors.h
mapObjectConstructors/CRewardableConstructor.h
mapObjectConstructors/DwellingInstanceConstructor.h
mapObjectConstructors/HillFortInstanceConstructor.h
mapObjectConstructors/IObjectInfo.h
mapObjectConstructors/RandomMapInfo.h
mapObjectConstructors/ShipyardInstanceConstructor.h
mapObjectConstructors/SObjectSounds.h
mapObjects/CArmedInstance.h
mapObjects/CBank.h
mapObjects/CGCreature.h
mapObjects/CGDwelling.h
mapObjects/CGHeroInstance.h
mapObjects/CGMarket.h
mapObjects/CGObjectInstance.h
mapObjects/CGPandoraBox.h
mapObjects/CGTownBuilding.h
mapObjects/CGTownInstance.h
mapObjects/CObjectHandler.h
mapObjects/CQuest.h
mapObjects/CRewardableObject.h
mapObjects/IMarket.h
mapObjects/IObjectInterface.h
mapObjects/MapObjects.h
mapObjects/MiscObjects.h
mapObjects/ObjectTemplate.h
mapping/CDrawRoadsOperation.h
mapping/CMapDefines.h
mapping/CMapEditManager.h
mapping/CMapHeader.h
mapping/CMap.h
mapping/CMapInfo.h
mapping/CMapOperation.h
mapping/CMapService.h
mapping/MapEditUtils.h
mapping/MapIdentifiersH3M.h
mapping/MapFeaturesH3M.h
mapping/MapFormatH3M.h
mapping/MapFormat.h
mapping/MapReaderH3M.h
mapping/MapFormatJson.h
mapping/ObstacleProxy.h
modding/ActiveModsInSaveList.h
modding/CModHandler.h
modding/CModInfo.h
modding/CModVersion.h
modding/ContentTypeHandler.h
modding/IdentifierStorage.h
modding/ModIncompatibility.h
modding/ModScope.h
modding/ModUtility.h
modding/ModVerificationInfo.h
network/NetworkConnection.h
network/NetworkDefines.h
network/NetworkHandler.h
network/NetworkInterface.h
network/NetworkServer.h
networkPacks/ArtifactLocation.h
networkPacks/BattleChanges.h
networkPacks/Component.h
networkPacks/EInfoWindowMode.h
networkPacks/EntityChanges.h
networkPacks/EOpenWindowMode.h
networkPacks/NetPacksBase.h
networkPacks/NetPackVisitor.h
networkPacks/ObjProperty.h
networkPacks/PacksForClient.h
networkPacks/PacksForClientBattle.h
networkPacks/PacksForLobby.h
networkPacks/PacksForServer.h
networkPacks/SetStackEffect.h
networkPacks/StackLocation.h
networkPacks/TradeItem.h
pathfinder/INodeStorage.h
pathfinder/CGPathNode.h
pathfinder/CPathfinder.h
pathfinder/NodeStorage.h
pathfinder/PathfinderOptions.h
pathfinder/PathfinderUtil.h
pathfinder/PathfindingRules.h
pathfinder/TurnInfo.h
registerTypes/RegisterTypes.h
registerTypes/RegisterTypesClientPacks.h
registerTypes/RegisterTypesLobbyPacks.h
registerTypes/RegisterTypesMapObjects.h
registerTypes/RegisterTypesServerPacks.h
rewardable/Configuration.h
rewardable/Info.h
rewardable/Interface.h
rewardable/Limiter.h
rewardable/Reward.h
rmg/RmgArea.h
rmg/RmgObject.h
rmg/RmgPath.h
rmg/CMapGenerator.h
rmg/CMapGenOptions.h
rmg/CRmgTemplate.h
rmg/CRmgTemplateStorage.h
rmg/CZonePlacer.h
rmg/TileInfo.h
rmg/Zone.h
rmg/RmgMap.h
rmg/float3.h
rmg/Functions.h
rmg/PenroseTiling.h
rmg/modificators/Modificator.h
rmg/modificators/ObjectManager.h
rmg/modificators/ObjectDistributor.h
rmg/modificators/RoadPlacer.h
rmg/modificators/TreasurePlacer.h
rmg/modificators/PrisonHeroPlacer.h
rmg/modificators/QuestArtifactPlacer.h
rmg/modificators/ConnectionsPlacer.h
rmg/modificators/WaterAdopter.h
rmg/modificators/MinePlacer.h
rmg/modificators/TownPlacer.h
rmg/modificators/WaterProxy.h
rmg/modificators/WaterRoutes.h
rmg/modificators/RockPlacer.h
rmg/modificators/RockFiller.h
rmg/modificators/ObstaclePlacer.h
rmg/modificators/RiverPlacer.h
rmg/modificators/TerrainPainter.h
rmg/threadpool/BlockingQueue.h
rmg/threadpool/ThreadPool.h
rmg/threadpool/MapProxy.h
serializer/BinaryDeserializer.h
serializer/BinarySerializer.h
serializer/CLoadFile.h
serializer/CMemorySerializer.h
serializer/Connection.h
serializer/CSaveFile.h
serializer/CSerializer.h
serializer/CTypeList.h
serializer/JsonDeserializer.h
serializer/JsonSerializeFormat.h
serializer/JsonSerializer.h
serializer/JsonUpdater.h
serializer/Cast.h
serializer/ESerializationVersion.h
spells/AbilityCaster.h
spells/AdventureSpellMechanics.h
spells/BattleSpellMechanics.h
spells/BonusCaster.h
spells/CSpellHandler.h
spells/ExternalCaster.h
spells/ISpellMechanics.h
spells/ObstacleCasterProxy.h
spells/Problem.h
spells/ProxyCaster.h
spells/TargetCondition.h
spells/ViewSpellInt.h
spells/effects/Catapult.h
spells/effects/Clone.h
spells/effects/Damage.h
spells/effects/DemonSummon.h
spells/effects/Dispel.h
spells/effects/Effect.h
spells/effects/Effects.h
spells/effects/EffectsFwd.h
spells/effects/Heal.h
spells/effects/LocationEffect.h
spells/effects/Obstacle.h
spells/effects/Registry.h
spells/effects/UnitEffect.h
spells/effects/Summon.h
spells/effects/Teleport.h
spells/effects/Timed.h
spells/effects/RemoveObstacle.h
spells/effects/Sacrifice.h
AI_Base.h
ArtifactUtils.h
BattleFieldHandler.h
CAndroidVMHelper.h
CArtHandler.h
CArtifactInstance.h
CBonusTypeHandler.h
CBuildingHandler.h
CConfigHandler.h
CConsoleHandler.h
CCreatureHandler.h
CCreatureSet.h
CGameInfoCallback.h
CGameInterface.h
CGeneralTextHandler.h
CHeroHandler.h
CondSh.h
ConstTransitivePtr.h
Color.h
CPlayerState.h
CRandomGenerator.h
CScriptingModule.h
CSkillHandler.h
CSoundBase.h
CStack.h
CStopWatch.h
CThreadHelper.h
CTownHandler.h
ExtraOptionsInfo.h
FunctionList.h
GameCallbackHolder.h
GameConstants.h
GameSettings.h
IBonusTypeHandler.h
IGameCallback.h
IGameEventsReceiver.h
IHandlerBase.h
int3.h
JsonDetail.h
JsonNode.h
JsonRandom.h
Languages.h
LoadProgress.h
LogicalExpression.h
MetaString.h
ObstacleHandler.h
Point.h
Rect.h
Rect.cpp
ResourceSet.h
RiverHandler.h
RoadHandler.h
ScriptHandler.h
ScopeGuard.h
StartInfo.h
TerrainHandler.h
TextOperations.h
TurnTimerInfo.h
UnlockGuard.h
VCMIDirs.h
vcmi_endian.h
VCMI_Lib.h
)
assign_source_group(${lib_SRCS} ${lib_HEADERS})
if(ENABLE_STATIC_LIBS)
add_library(vcmi STATIC ${lib_SRCS} ${lib_HEADERS})
else()
add_library(vcmi SHARED ${lib_SRCS} ${lib_HEADERS})
endif()
set_target_properties(vcmi PROPERTIES COMPILE_DEFINITIONS "VCMI_DLL=1")
target_link_libraries(vcmi PUBLIC
minizip::minizip ZLIB::ZLIB
${SYSTEM_LIBS} Boost::boost Boost::thread Boost::filesystem Boost::program_options Boost::locale Boost::date_time
)
if(ENABLE_STATIC_LIBS)
target_compile_definitions(vcmi PRIVATE STATIC_AI)
target_link_libraries(vcmi PRIVATE
BattleAI
EmptyAI
StupidAI
VCAI
)
if(ENABLE_NULLKILLER_AI)
target_link_libraries(${VCMI_LIB_TARGET} PRIVATE Nullkiller)
target_link_libraries(vcmi PRIVATE Nullkiller)
endif()
else()
add_main_lib(${VCMI_LIB_TARGET} SHARED)
endif()
if(ENABLE_SINGLE_APP_BUILD)
target_compile_definitions(${VCMI_LIB_TARGET} PUBLIC VCMI_LIB_NAMESPACE=LIB_CLIENT)
# no longer necessary, but might be useful to keep in future
# unfortunately at the moment tests do not support namespaced build, so enable only on some systems
if(APPLE_IOS OR ANDROID)
target_compile_definitions(vcmi PUBLIC VCMI_LIB_NAMESPACE=VCMI)
endif()
if(APPLE_IOS)
target_link_libraries(vcmi PUBLIC iOS_utils)
endif()
target_include_directories(vcmi
PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}
PUBLIC ${CMAKE_SOURCE_DIR}
PUBLIC ${CMAKE_SOURCE_DIR}/include
)
if(WIN32)
set_target_properties(vcmi
PROPERTIES
OUTPUT_NAME "VCMI_lib"
PROJECT_LABEL "VCMI_lib"
)
endif()
vcmi_set_output_dir(vcmi "")
enable_pch(vcmi)
# We want to deploy assets into build directory for easier debugging without install
if(COPY_CONFIG_ON_BUILD)
add_custom_command(TARGET vcmi POST_BUILD
COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/config
COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/Mods
COMMAND ${CMAKE_COMMAND} -P ${CMAKE_SOURCE_DIR}/cmake_modules/create_link.cmake ${CMAKE_SOURCE_DIR}/config ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/config
COMMAND ${CMAKE_COMMAND} -P ${CMAKE_SOURCE_DIR}/cmake_modules/create_link.cmake ${CMAKE_SOURCE_DIR}/Mods ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/Mods
)
endif()
# Update version before vcmi compiling
if(TARGET update_version)
add_dependencies(vcmi update_version)
endif()
if(NOT ENABLE_STATIC_LIBS)
install(TARGETS vcmi RUNTIME DESTINATION ${LIB_DIR} LIBRARY DESTINATION ${LIB_DIR})
endif()
if(APPLE_IOS AND NOT USING_CONAN)
get_target_property(LINKED_LIBS vcmi LINK_LIBRARIES)
foreach(LINKED_LIB IN LISTS LINKED_LIBS)
if(NOT TARGET ${LINKED_LIB})
if(LINKED_LIB MATCHES "\\${CMAKE_SHARED_LIBRARY_SUFFIX}$")
install(FILES ${LINKED_LIB} DESTINATION ${LIB_DIR})
endif()
continue()
endif()
get_target_property(LIB_TYPE ${LINKED_LIB} TYPE)
if(NOT LIB_TYPE STREQUAL "SHARED_LIBRARY")
continue()
endif()
get_target_property(_aliased ${LINKED_LIB} ALIASED_TARGET)
if(_aliased)
set(LINKED_LIB_REAL ${_aliased})
else()
set(LINKED_LIB_REAL ${LINKED_LIB})
endif()
get_target_property(_imported ${LINKED_LIB_REAL} IMPORTED)
if(_imported)
set(INSTALL_TYPE IMPORTED_RUNTIME_ARTIFACTS)
get_target_property(BOOST_DEPENDENCIES ${LINKED_LIB_REAL} INTERFACE_LINK_LIBRARIES)
foreach(BOOST_DEPENDENCY IN LISTS BOOST_DEPENDENCIES)
get_target_property(BOOST_DEPENDENCY_TYPE ${BOOST_DEPENDENCY} TYPE)
if(BOOST_DEPENDENCY_TYPE STREQUAL "SHARED_LIBRARY")
install(IMPORTED_RUNTIME_ARTIFACTS ${BOOST_DEPENDENCY} LIBRARY DESTINATION ${LIB_DIR})
endif()
endforeach()
else()
set(INSTALL_TYPE TARGETS)
endif()
install(${INSTALL_TYPE} ${LINKED_LIB_REAL} LIBRARY DESTINATION ${LIB_DIR})
endforeach()
endif()

View File

@ -55,10 +55,25 @@ void CThreadHelper::processTasks()
}
}
// set name for this thread.
// NOTE: on *nix string will be trimmed to 16 symbols
static thread_local std::string threadNameForLogging;
std::string getThreadName()
{
if (!threadNameForLogging.empty())
return threadNameForLogging;
return boost::lexical_cast<std::string>(boost::this_thread::get_id());
}
void setThreadNameLoggingOnly(const std::string &name)
{
threadNameForLogging = name;
}
void setThreadName(const std::string &name)
{
threadNameForLogging = name;
#ifdef VCMI_WINDOWS
#ifndef __GNUC__
//follows http://msdn.microsoft.com/en-us/library/xcb2z8hs.aspx
@ -90,12 +105,12 @@ void setThreadName(const std::string &name)
//not supported
#endif
#elif defined(__linux__)
prctl(PR_SET_NAME, name.c_str(), 0, 0, 0);
#elif defined(VCMI_APPLE)
pthread_setname_np(name.c_str());
#elif defined(VCMI_HAIKU)
rename_thread(find_thread(NULL), name.c_str());
#elif defined(VCMI_UNIX)
prctl(PR_SET_NAME, name.c_str(), 0, 0, 0);
#endif
}

View File

@ -85,7 +85,14 @@ private:
}
};
/// Sets thread name that will be used for both logs and debugger (if supported)
/// WARNING: on Unix-like systems this method should not be used for main thread since it will also change name of the process
void DLL_LINKAGE setThreadName(const std::string &name);
/// Sets thread name for use in logging only
void DLL_LINKAGE setThreadNameLoggingOnly(const std::string &name);
/// Returns human-readable thread name that was set before, or string form of system-provided thread ID if no human-readable name was set
std::string DLL_LINKAGE getThreadName();
VCMI_LIB_NAMESPACE_END

View File

@ -368,11 +368,7 @@ bool IVCMIDirsUNIX::developmentMode() const
{
// We want to be able to run VCMI from single directory. E.g to run from build output directory
const bool result = bfs::exists("AI") && bfs::exists("config") && bfs::exists("Mods") && bfs::exists("vcmiclient");
#if SINGLE_PROCESS_APP
return result;
#else
return result && bfs::exists("vcmiserver");
#endif
}
bfs::path IVCMIDirsUNIX::clientPath() const { return binaryPath() / "vcmiclient"; }

View File

@ -9,6 +9,7 @@
*/
#include "StdInc.h"
#include "CLogger.h"
#include "../CThreadHelper.h"
#ifdef VCMI_ANDROID
#include <android/log.h>
@ -427,8 +428,7 @@ void CLogConsoleTarget::setColorMapping(const CColorMapping & colorMapping) { th
CLogFileTarget::CLogFileTarget(const boost::filesystem::path & filePath, bool append):
file(filePath.c_str(), append ? std::ios_base::app : std::ios_base::out)
{
// formatter.setPattern("%d %l %n [%t] - %m");
formatter.setPattern("%l %n [%t] - %m");
formatter.setPattern("[%c] %l %n [%t] - %m");
}
void CLogFileTarget::write(const LogRecord & record)
@ -446,4 +446,14 @@ CLogFileTarget::~CLogFileTarget()
file.close();
}
LogRecord::LogRecord(const CLoggerDomain & domain, ELogLevel::ELogLevel level, const std::string & message)
: domain(domain),
level(level),
message(message),
timeStamp(boost::posix_time::microsec_clock::local_time()),
threadId(getThreadName())
{
}
VCMI_LIB_NAMESPACE_END

View File

@ -107,12 +107,7 @@ private:
/// The struct LogRecord holds the log message and additional logging information.
struct DLL_LINKAGE LogRecord
{
LogRecord(const CLoggerDomain & domain, ELogLevel::ELogLevel level, const std::string & message)
: domain(domain),
level(level),
message(message),
timeStamp(boost::posix_time::microsec_clock::local_time()),
threadId(boost::lexical_cast<std::string>(boost::this_thread::get_id())) { }
LogRecord(const CLoggerDomain & domain, ELogLevel::ELogLevel level, const std::string & message);
CLoggerDomain domain;
ELogLevel::ELogLevel level;

View File

@ -1,3 +0,0 @@
add_main_lib(vcmi_lib_server STATIC)
target_compile_definitions(vcmi_lib_server PUBLIC VCMI_LIB_NAMESPACE=LIB_SERVER)
target_compile_definitions(vcmi_lib_server PUBLIC VCMI_DLL_STATIC=1)

View File

@ -178,7 +178,7 @@ if(APPLE)
set_property(GLOBAL PROPERTY AUTOGEN_TARGETS_FOLDER vcmieditor)
endif()
target_link_libraries(vcmieditor ${VCMI_LIB_TARGET} Qt${QT_VERSION_MAJOR}::Widgets Qt${QT_VERSION_MAJOR}::Network)
target_link_libraries(vcmieditor vcmi Qt${QT_VERSION_MAJOR}::Widgets Qt${QT_VERSION_MAJOR}::Network)
target_include_directories(vcmieditor
PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}
)

View File

@ -15,7 +15,7 @@ set(lib_HDRS
)
add_library(vcmiERM SHARED ${lib_SRCS} ${lib_HDRS})
target_link_libraries(vcmiERM Boost::boost ${VCMI_LIB_TARGET})
target_link_libraries(vcmiERM Boost::boost vcmi)
vcmi_set_output_dir(vcmiERM "scripting")
enable_pch(vcmiERM)

View File

@ -83,7 +83,7 @@ set(lib_HDRS
)
add_library(vcmiLua SHARED ${lib_SRCS} ${lib_HDRS})
target_link_libraries(vcmiLua Boost::boost luajit::luajit ${VCMI_LIB_TARGET})
target_link_libraries(vcmiLua Boost::boost luajit::luajit vcmi)
vcmi_set_output_dir(vcmiLua "scripting")
enable_pch(vcmiLua)

View File

@ -1,4 +1,4 @@
set(server_SRCS
set(vcmiservercommon_SRCS
StdInc.cpp
battles/BattleActionProcessor.cpp
@ -15,7 +15,6 @@ set(server_SRCS
processors/PlayerMessageProcessor.cpp
processors/TurnOrderProcessor.cpp
EntryPoint.cpp
CGameHandler.cpp
GlobalLobbyProcessor.cpp
ServerSpellCastEnvironment.cpp
@ -25,7 +24,7 @@ set(server_SRCS
TurnTimerHandler.cpp
)
set(server_HEADERS
set(vcmiservercommon_HEADERS
StdInc.h
battles/BattleActionProcessor.h
@ -51,45 +50,28 @@ set(server_HEADERS
TurnTimerHandler.h
)
assign_source_group(${server_SRCS} ${server_HEADERS})
assign_source_group(${vcmiservercommon_SRCS} ${vcmiservercommon_HEADERS})
if(ENABLE_SINGLE_APP_BUILD)
add_library(vcmiserver STATIC ${server_SRCS} ${server_HEADERS})
target_compile_definitions(vcmiserver PUBLIC VCMI_DLL_STATIC=1)
set(server_LIBS vcmi_lib_server)
else()
if(ANDROID)
add_library(vcmiserver SHARED ${server_SRCS} ${server_HEADERS})
else()
add_executable(vcmiserver ${server_SRCS} ${server_HEADERS})
endif()
set(server_LIBS vcmi)
endif()
add_library(vcmiservercommon STATIC ${vcmiservercommon_SRCS} ${vcmiservercommon_HEADERS})
set(vcmiservercommon_LIBS vcmi)
if(CMAKE_SYSTEM_NAME MATCHES FreeBSD OR HAIKU)
set(server_LIBS execinfo ${server_LIBS})
set(vcmiservercommon_LIBS execinfo ${vcmiservercommon_LIBS})
endif()
target_link_libraries(vcmiserver PRIVATE ${server_LIBS} minizip::minizip)
target_include_directories(vcmiserver
target_link_libraries(vcmiservercommon PRIVATE ${vcmiservercommon_LIBS} minizip::minizip)
target_include_directories(vcmiservercommon
PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}
)
if(WIN32)
set_target_properties(vcmiserver
set_target_properties(vcmiservercommon
PROPERTIES
OUTPUT_NAME "VCMI_server"
PROJECT_LABEL "VCMI_server"
OUTPUT_NAME "VCMI_vcmiservercommon"
PROJECT_LABEL "VCMI_vcmiservercommon"
)
endif()
vcmi_set_output_dir(vcmiserver "")
enable_pch(vcmiserver)
if(NOT ENABLE_SINGLE_APP_BUILD)
if(ANDROID)
install(TARGETS vcmiserver DESTINATION ${LIB_DIR})
else()
install(TARGETS vcmiserver DESTINATION ${BIN_DIR})
endif()
endif()
vcmi_set_output_dir(vcmiservercommon "")
enable_pch(vcmiservercommon)

View File

@ -116,10 +116,11 @@ public:
}
};
CVCMIServer::CVCMIServer(boost::program_options::variables_map & opts)
CVCMIServer::CVCMIServer(uint16_t port, bool connectToLobby, bool runByClient)
: currentClientId(1)
, currentPlayerId(1)
, cmdLineOptions(opts)
, port(port)
, runByClient(runByClient)
{
uuid = boost::uuids::to_string(boost::uuids::random_generator()());
logNetwork->trace("CVCMIServer created! UUID: %s", uuid);
@ -128,7 +129,7 @@ CVCMIServer::CVCMIServer(boost::program_options::variables_map & opts)
networkHandler = INetworkHandler::createHandler();
if(cmdLineOptions.count("lobby"))
if(connectToLobby)
lobbyProcessor = std::make_unique<GlobalLobbyProcessor>(*this);
else
startAcceptingIncomingConnections();
@ -138,10 +139,6 @@ CVCMIServer::~CVCMIServer() = default;
void CVCMIServer::startAcceptingIncomingConnections()
{
uint16_t port = 3030;
if(cmdLineOptions.count("port"))
port = cmdLineOptions["port"].as<uint16_t>();
logNetwork->info("Port %d will be used", port);
networkServer = networkHandler->createServerTCP(*this);
@ -197,15 +194,13 @@ std::shared_ptr<CConnection> CVCMIServer::findConnection(const std::shared_ptr<I
throw std::runtime_error("Unknown connection received in CVCMIServer::findConnection");
}
bool CVCMIServer::wasStartedByClient() const
{
return runByClient;
}
void CVCMIServer::run()
{
#if defined(VCMI_ANDROID) && !defined(SINGLE_PROCESS_APP)
if(!restartGameplay)
{
CAndroidVMHelper vmHelper;
vmHelper.callStaticVoidMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "onServerReady");
}
#endif
networkHandler->run();
}

View File

@ -12,12 +12,6 @@
#include "../lib/network/NetworkInterface.h"
#include "../lib/StartInfo.h"
#include <boost/program_options/variables_map.hpp>
#if defined(VCMI_ANDROID) && !defined(SINGLE_PROCESS_APP)
#define VCMI_ANDROID_DUAL_PROCESS 1
#endif
VCMI_LIB_NAMESPACE_BEGIN
class CMapInfo;
@ -64,6 +58,8 @@ class CVCMIServer : public LobbyInfo, public INetworkServerListener, public INet
int currentClientId;
ui8 currentPlayerId;
uint16_t port;
bool runByClient;
public:
/// List of all active connections
@ -76,13 +72,13 @@ public:
void onTimer() override;
std::shared_ptr<CGameHandler> gh;
boost::program_options::variables_map cmdLineOptions;
CVCMIServer(boost::program_options::variables_map & opts);
CVCMIServer(uint16_t port, bool connectToLobby, bool runByClient);
~CVCMIServer();
void run();
bool wasStartedByClient() const;
bool prepareToStartGame();
void prepareToRestart();
void startGameImmediately();
@ -131,13 +127,4 @@ public:
void setCampaignBonus(int bonusId);
ui8 getIdOfFirstUnallocatedPlayer() const;
#if VCMI_ANDROID_DUAL_PROCESS
static void create();
#elif defined(SINGLE_PROCESS_APP)
static void create(boost::condition_variable * cond, const std::vector<std::string> & args);
# ifdef VCMI_ANDROID
static void reuseClientJNIEnv(void * jniEnv);
# endif // VCMI_ANDROID
#endif // VCMI_ANDROID_DUAL_PROCESS
};

View File

@ -81,7 +81,7 @@ void ClientPermissionsCheckerNetPackVisitor::visitLobbyClientDisconnected(LobbyC
if(pack.shutdownServer)
{
if(!srv.cmdLineOptions.count("run-by-client"))
if(!srv.wasStartedByClient())
{
result = false;
return;

34
serverapp/CMakeLists.txt Normal file
View File

@ -0,0 +1,34 @@
set(serverapp_SRCS
StdInc.cpp
EntryPoint.cpp
)
set(serverapp_HEADERS
StdInc.h
)
assign_source_group(${serverapp_SRCS} ${serverapp_HEADERS})
add_executable(vcmiserver ${serverapp_SRCS} ${serverapp_HEADERS})
set(serverapp_LIBS vcmi)
if(CMAKE_SYSTEM_NAME MATCHES FreeBSD OR HAIKU)
set(serverapp_LIBS execinfo ${serverapp_LIBS})
endif()
target_link_libraries(vcmiserver PRIVATE ${serverapp_LIBS} minizip::minizip vcmiservercommon)
target_include_directories(vcmiserver
PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}
)
if(WIN32)
set_target_properties(vcmiserver
PROPERTIES
OUTPUT_NAME "VCMI_server"
PROJECT_LABEL "VCMI_server"
)
endif()
vcmi_set_output_dir(vcmiserver "")
enable_pch(vcmiserver)
install(TARGETS vcmiserver DESTINATION ${BIN_DIR})

View File

@ -9,40 +9,33 @@
*/
#include "StdInc.h"
#include "CVCMIServer.h"
#include "../server/CVCMIServer.h"
#include "../lib/CConsoleHandler.h"
#include "../lib/logging/CBasicLogConfigurator.h"
#include "../lib/VCMIDirs.h"
#include "../lib/VCMI_Lib.h"
#ifdef VCMI_ANDROID
#include <jni.h>
#include <android/log.h>
#include "lib/CAndroidVMHelper.h"
#endif
#include <boost/program_options.hpp>
const std::string SERVER_NAME_AFFIX = "server";
const std::string SERVER_NAME = GameConstants::VCMI_VERSION + std::string(" (") + SERVER_NAME_AFFIX + ')';
static const std::string SERVER_NAME_AFFIX = "server";
static const std::string SERVER_NAME = GameConstants::VCMI_VERSION + std::string(" (") + SERVER_NAME_AFFIX + ')';
static void handleCommandOptions(int argc, const char * argv[], boost::program_options::variables_map & options)
{
namespace po = boost::program_options;
po::options_description opts("Allowed options");
boost::program_options::options_description opts("Allowed options");
opts.add_options()
("help,h", "display help and exit")
("version,v", "display version information and exit")
("run-by-client", "indicate that server launched by client on same machine")
("port", po::value<ui16>(), "port at which server will listen to connections from client")
("port", boost::program_options::value<ui16>(), "port at which server will listen to connections from client")
("lobby", "start server in lobby mode in which server connects to a global lobby");
if(argc > 1)
{
try
{
po::store(po::parse_command_line(argc, argv, opts), options);
boost::program_options::store(boost::program_options::parse_command_line(argc, argv, opts), options);
}
catch(boost::program_options::error & e)
{
@ -50,13 +43,8 @@ static void handleCommandOptions(int argc, const char * argv[], boost::program_o
}
}
#ifdef SINGLE_PROCESS_APP
options.emplace("run-by-client", po::variable_value{true, true});
#endif
boost::program_options::notify(options);
po::notify(options);
#ifndef SINGLE_PROCESS_APP
if(options.count("help"))
{
auto time = std::time(nullptr);
@ -75,31 +63,14 @@ static void handleCommandOptions(int argc, const char * argv[], boost::program_o
std::cout << VCMIDirs::get().genHelpString();
exit(0);
}
#endif
}
#ifdef SINGLE_PROCESS_APP
#define main server_main
#endif
#if VCMI_ANDROID_DUAL_PROCESS
void CVCMIServer::create()
{
const int argc = 1;
const char * argv[argc] = { "android-server" };
#else
int main(int argc, const char * argv[])
{
#endif
#if !defined(VCMI_ANDROID) && !defined(SINGLE_PROCESS_APP)
// Correct working dir executable folder (not bundle folder) so we can use executable relative paths
boost::filesystem::current_path(boost::filesystem::system_complete(argv[0]).parent_path());
#endif
#ifndef VCMI_IOS
console = new CConsoleHandler();
#endif
CBasicLogConfigurator logConfig(VCMIDirs::get().userLogsPath() / "VCMI_Server_log.txt", console);
logConfig.configureDefault();
logGlobal->info(SERVER_NAME);
@ -113,58 +84,21 @@ int main(int argc, const char * argv[])
std::srand(static_cast<uint32_t>(time(nullptr)));
{
CVCMIServer server(opts);
bool connectToLobby = opts.count("lobby");
bool runByClient = opts.count("runByClient");
uint16_t port = 3030;
if(opts.count("port"))
port = opts["port"].as<uint16_t>();
#ifdef SINGLE_PROCESS_APP
boost::condition_variable * cond = reinterpret_cast<boost::condition_variable *>(const_cast<char *>(argv[0]));
cond->notify_one();
#endif
CVCMIServer server(port, connectToLobby, runByClient);
server.run();
// CVCMIServer destructor must be called here - before VLC cleanup
}
#if VCMI_ANDROID_DUAL_PROCESS
CAndroidVMHelper envHelper;
envHelper.callStaticVoidMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "killServer");
#endif
logConfig.deconfigure();
vstd::clear_pointer(VLC);
#if !VCMI_ANDROID_DUAL_PROCESS
return 0;
#endif
}
#if VCMI_ANDROID_DUAL_PROCESS
extern "C" JNIEXPORT void JNICALL Java_eu_vcmi_vcmi_NativeMethods_createServer(JNIEnv * env, jclass cls)
{
__android_log_write(ANDROID_LOG_INFO, "VCMI", "Got jni call to init server");
CAndroidVMHelper::cacheVM(env);
CVCMIServer::create();
}
extern "C" JNIEXPORT void JNICALL Java_eu_vcmi_vcmi_NativeMethods_initClassloader(JNIEnv * baseEnv, jclass cls)
{
CAndroidVMHelper::initClassloader(baseEnv);
}
#elif defined(SINGLE_PROCESS_APP)
void CVCMIServer::create(boost::condition_variable * cond, const std::vector<std::string> & args)
{
std::vector<const void *> argv = {cond};
for(auto & a : args)
argv.push_back(a.c_str());
main(argv.size(), reinterpret_cast<const char **>(&*argv.begin()));
}
#ifdef VCMI_ANDROID
void CVCMIServer::reuseClientJNIEnv(void * jniEnv)
{
CAndroidVMHelper::initClassloader(jniEnv);
CAndroidVMHelper::alwaysUseLoadedClass = true;
}
#endif // VCMI_ANDROID
#endif // VCMI_ANDROID_DUAL_PROCESS

2
serverapp/StdInc.cpp Normal file
View File

@ -0,0 +1,2 @@
// Creates the precompiled header
#include "StdInc.h"

14
serverapp/StdInc.h Normal file
View File

@ -0,0 +1,14 @@
/*
* StdInc.h, part of VCMI engine
*
* Authors: listed in file AUTHORS in main folder
*
* License: GNU General Public License v2.0 or later
* Full text of license available in license.txt file, in main folder
*
*/
#pragma once
#include "../Global.h"
VCMI_LIB_USING_NAMESPACE