From 8c6d0b51c719e1817e308375d129b17ede3b82fc Mon Sep 17 00:00:00 2001 From: Tiger Wang Date: Mon, 7 Nov 2016 22:15:07 +0000 Subject: Use CMake's Android generators to crosscompile --- src/Bindings/CMakeLists.txt | 2 +- src/ByteBuffer.cpp | 37 ------------------------ src/CMakeLists.txt | 24 +++++++-------- src/ClientHandle.h | 2 +- src/FurnaceRecipe.cpp | 6 +++- src/LoggerListeners.cpp | 53 ++++------------------------------ src/OSSupport/CMakeLists.txt | 8 ----- src/OSSupport/Errors.cpp | 2 +- src/OSSupport/File.cpp | 6 +++- src/OSSupport/NetworkInterfaceEnum.cpp | 14 ++++----- src/OSSupport/NetworkSingleton.cpp | 15 ++++++++++ src/OSSupport/StackTrace.cpp | 4 +-- src/Root.cpp | 22 +++++++------- src/StringUtils.cpp | 4 --- src/World.cpp | 6 ++-- src/main.cpp | 18 +++++++++--- 16 files changed, 79 insertions(+), 144 deletions(-) (limited to 'src') diff --git a/src/Bindings/CMakeLists.txt b/src/Bindings/CMakeLists.txt index 640fd60fa..c4fae1148 100644 --- a/src/Bindings/CMakeLists.txt +++ b/src/Bindings/CMakeLists.txt @@ -159,7 +159,7 @@ set_source_files_properties(${BINDING_OUTPUTS} PROPERTIES GENERATED TRUE) set_source_files_properties(${CMAKE_SOURCE_DIR}/src/Bindings/Bindings.cpp PROPERTIES COMPILE_FLAGS -Wno-error) if("${CMAKE_CXX_COMPILER_ID}" STREQUAL "Clang") - set_source_files_properties(${CMAKE_SOURCE_DIR}/src/Bindings/Bindings.cpp PROPERTIES COMPILE_FLAGS ${COMPILE_FLAGS} "-Wno-old-style-cast -Wno-missing-prototypes") + set_source_files_properties(Bindings.cpp PROPERTIES COMPILE_FLAGS ${COMPILE_FLAGS} "-Wno-old-style-cast -Wno-missing-prototypes") set_source_files_properties(LuaWindow.cpp PROPERTIES COMPILE_FLAGS "-Wno-error=switch-enum") endif() diff --git a/src/ByteBuffer.cpp b/src/ByteBuffer.cpp index 6cfb66f9a..1a4dc8bb8 100644 --- a/src/ByteBuffer.cpp +++ b/src/ByteBuffer.cpp @@ -22,27 +22,6 @@ Unfortunately it is very slow, so it is disabled even for regular DEBUG builds. -// Try to determine endianness: -#if ( \ - defined(__i386__) || defined(__alpha__) || \ - defined(__ia64) || defined(__ia64__) || \ - defined(_M_IX86) || defined(_M_IA64) || \ - defined(_M_ALPHA) || defined(__amd64) || \ - defined(__amd64__) || defined(_M_AMD64) || \ - defined(__x86_64) || defined(__x86_64__) || \ - defined(_M_X64) || defined(__bfin__) || \ - defined(__ARMEL__) || defined(__AARCH64EL__) || \ - (defined(_WIN32) && defined(__ARM__) && defined(_MSC_VER)) \ -) - #define IS_LITTLE_ENDIAN -#elif ( \ - defined (__ARMEB__) || defined(__sparc) || defined(__powerpc__) || defined(__POWERPC__) \ -) - #define IS_BIG_ENDIAN -#else - #error Cannot determine endianness of this platform -#endif - // If a string sent over the protocol is larger than this, a warning is emitted to the console #define MAX_STRING_SIZE (512 KiB) @@ -754,22 +733,6 @@ bool cByteBuffer::WriteVarUTF8String(const AString & a_Value) -bool cByteBuffer::WriteLEInt32(Int32 a_Value) -{ - CHECK_THREAD - CheckValid(); - #ifdef IS_LITTLE_ENDIAN - return WriteBuf(reinterpret_cast(&a_Value), 4); - #else - int Value = ((a_Value >> 24) & 0xff) | ((a_Value >> 16) & 0xff00) | ((a_Value >> 8) & 0xff0000) | (a_Value & 0xff000000); - return WriteBuf(reinterpret_cast(&Value), 4); - #endif -} - - - - - bool cByteBuffer::WritePosition64(Int32 a_BlockX, Int32 a_BlockY, Int32 a_BlockZ) { CHECK_THREAD diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index ac1c8138b..0bb1e442a 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -290,9 +290,6 @@ foreach(arg ${ALLFILES}) endforeach() FILE(WRITE "AllFiles.lst" "${ALLFILESLINES}") - -set(EXECUTABLE Cuberite) - if (MSVC) get_directory_property(BINDING_OUTPUTS DIRECTORY "Bindings" DEFINITION BINDING_OUTPUTS) get_directory_property(BINDING_DEPENDENCIES DIRECTORY "Bindings" DEFINITION BINDING_DEPENDENCIES) @@ -324,46 +321,45 @@ if (MSVC) endif() endif() -add_executable(${EXECUTABLE} ${SOURCE}) +add_executable(${CMAKE_PROJECT_NAME} ${SOURCE}) # Output the executable into the $/Server folder, so that it has access to external resources: -set(EXECUTABLE_OUTPUT_PATH ${CMAKE_SOURCE_DIR}/Server) -SET_TARGET_PROPERTIES(${EXECUTABLE} PROPERTIES +SET_TARGET_PROPERTIES(${CMAKE_PROJECT_NAME} PROPERTIES RUNTIME_OUTPUT_DIRECTORY_DEBUG ${CMAKE_SOURCE_DIR}/Server RUNTIME_OUTPUT_DIRECTORY_RELEASE ${CMAKE_SOURCE_DIR}/Server RUNTIME_OUTPUT_DIRECTORY_DEBUGPROFILE ${CMAKE_SOURCE_DIR}/Server RUNTIME_OUTPUT_DIRECTORY_RELEASEPROFILE ${CMAKE_SOURCE_DIR}/Server ) - # Make the debug executable have a "_debug" suffix -SET_TARGET_PROPERTIES(${EXECUTABLE} PROPERTIES DEBUG_POSTFIX "_debug") +SET_TARGET_PROPERTIES(${CMAKE_PROJECT_NAME} PROPERTIES DEBUG_POSTFIX "_debug") # Make the profiled executables have a "_profile" postfix -SET_TARGET_PROPERTIES(${EXECUTABLE} PROPERTIES DEBUGPROFILE_POSTFIX "_debug_profile") -SET_TARGET_PROPERTIES(${EXECUTABLE} PROPERTIES RELEASEPROFILE_POSTFIX "_profile") +SET_TARGET_PROPERTIES(${CMAKE_PROJECT_NAME} PROPERTIES DEBUGPROFILE_POSTFIX "_debug_profile") +SET_TARGET_PROPERTIES(${CMAKE_PROJECT_NAME} PROPERTIES RELEASEPROFILE_POSTFIX "_profile") # Precompiled headers (2nd part) if (MSVC) SET_TARGET_PROPERTIES( - ${EXECUTABLE} PROPERTIES COMPILE_FLAGS "/Yu\"Globals.h\"" + ${CMAKE_PROJECT_NAME} PROPERTIES COMPILE_FLAGS "/Yu\"Globals.h\"" OBJECT_DEPENDS "$(IntDir)/$(TargetName.pch)" ) endif () if (NOT MSVC) - target_link_libraries(${EXECUTABLE} + target_link_libraries(${CMAKE_PROJECT_NAME} OSSupport HTTPServer Bindings Items Blocks Noise Protocol Generating WorldStorage Mobs Entities Simulator IncrementalRedstoneSimulator BlockEntities UI PolarSSL++ ) endif () + if (WIN32) - target_link_libraries(${EXECUTABLE} expat tolualib ws2_32.lib Psapi.lib) + target_link_libraries(${CMAKE_PROJECT_NAME} expat tolualib ws2_32.lib Psapi.lib) endif() if (${CMAKE_SYSTEM_NAME} STREQUAL "FreeBSD") @@ -371,7 +367,7 @@ if (${CMAKE_SYSTEM_NAME} STREQUAL "FreeBSD") add_flags_lnk(-L/usr/ports/devel) endif() -target_link_libraries(${EXECUTABLE} luaexpat jsoncpp_lib_static mbedtls zlib sqlite lua SQLiteCpp event_core event_extra) +target_link_libraries(${CMAKE_PROJECT_NAME} luaexpat jsoncpp_lib_static mbedtls zlib sqlite lua SQLiteCpp event_core event_extra) # Create a folder for Bindings' documentation: FILE(MAKE_DIRECTORY "Bindings/docs") diff --git a/src/ClientHandle.h b/src/ClientHandle.h index e6982d546..8b6a78127 100644 --- a/src/ClientHandle.h +++ b/src/ClientHandle.h @@ -55,7 +55,7 @@ class cClientHandle // tolua_export { // tolua_export public: // tolua_export - #if defined(ANDROID_NDK) + #if defined(ANDROID) static const int DEFAULT_VIEW_DISTANCE = 4; // The default ViewDistance (used when no value is set in Settings.ini) #else static const int DEFAULT_VIEW_DISTANCE = 10; diff --git a/src/FurnaceRecipe.cpp b/src/FurnaceRecipe.cpp index 2c20eec0f..d1082b63f 100644 --- a/src/FurnaceRecipe.cpp +++ b/src/FurnaceRecipe.cpp @@ -6,7 +6,7 @@ #include -#define FURNACE_RECIPE_FILE "furnace.txt" +#define FURNACE_RECIPE_FILE FILE_IO_PREFIX "furnace.txt" @@ -70,6 +70,10 @@ void cFurnaceRecipe::ReloadRecipes(void) LineNum++; if (ParsingLine.empty()) { + // There is a problem here on Android. Text files transferred from another OS may have a newline representation Android's implementation of getline doesn't expect + // Thus, part of a newline may be left in ParsingLine. ::empty() thus thinks the string isn't empty, and the below code outputs interesting errors since it was passed a nearly empty string + // Ref: http://stackoverflow.com/questions/6089231/getting-std-ifstream-to-handle-lf-cr-and-crlf + // TODO: There is a solution in the above reference, but it isn't very pretty. Fix it somehow. continue; } diff --git a/src/LoggerListeners.cpp b/src/LoggerListeners.cpp index 1d6d9c6ce..91f166bda 100644 --- a/src/LoggerListeners.cpp +++ b/src/LoggerListeners.cpp @@ -8,14 +8,12 @@ #if defined(_WIN32) #include // Needed for _isatty(), not available on Linux #include -#elif defined(__linux) && !defined(ANDROID_NDK) +#elif defined(__linux) #include // Needed for isatty() on Linux -#elif defined(ANDROID_NDK) - #include #endif -#if defined(_WIN32) || (defined (__linux) && !defined(ANDROID_NDK)) +#if defined(_WIN32) || defined (__linux) class cColouredConsoleListener : public cLogger::cListener { @@ -107,7 +105,7 @@ -#elif defined (__linux) && !defined(ANDROID_NDK) +#elif defined (__linux) @@ -154,46 +152,6 @@ } }; - - -#elif defined(ANDROID_NDK) - - - - class cAndroidConsoleListener - : public cLogger::cListener - { - public: - virtual void Log(AString a_Message, cLogger::eLogLevel a_LogLevel) override - { - android_LogPriority AndroidLogLevel; - switch (a_LogLevel) - { - case cLogger::llRegular: - { - AndroidLogLevel = ANDROID_LOG_VERBOSE; - break; - } - case cLogger::llInfo: - { - AndroidLogLevel = ANDROID_LOG_INFO; - break; - } - case cLogger::llWarning: - { - AndroidLogLevel = ANDROID_LOG_WARNING; - break; - } - case cLogger::llError: - { - AndroidLogLevel = ANDROID_LOG_ERROR; - break; - } - } - __android_log_print(AndroidLogLevel, "Cuberite", "%s", a_Message.c_str()); - } - }; - #endif @@ -273,8 +231,7 @@ std::unique_ptr MakeConsoleListener(bool a_IsService) { return cpp14::make_unique(); } - - #elif defined (__linux) && !defined(ANDROID_NDK) + #elif defined (__linux) && !defined(ANDROID) // TODO: lookup terminal in terminfo if (isatty(fileno(stdout))) { @@ -306,7 +263,7 @@ public: bool Open() { // Assume creation succeeds, as the API does not provide a way to tell if the folder exists. - cFile::CreateFolder(FILE_IO_PREFIX + AString("logs")); + cFile::CreateFolder(FILE_IO_PREFIX "logs"); bool success = m_File.Open( FILE_IO_PREFIX + Printf( "logs/LOG_%d.txt", diff --git a/src/OSSupport/CMakeLists.txt b/src/OSSupport/CMakeLists.txt index 876b4f789..22699f7cd 100644 --- a/src/OSSupport/CMakeLists.txt +++ b/src/OSSupport/CMakeLists.txt @@ -43,12 +43,4 @@ endif() if(NOT MSVC) add_library(OSSupport ${SRCS} ${HDRS}) - - if(UNIX) - if(NOT APPLE) - target_link_libraries(OSSupport rt) - endif() - - target_link_libraries(OSSupport pthread event_core event_extra) - endif() endif() diff --git a/src/OSSupport/Errors.cpp b/src/OSSupport/Errors.cpp index a05650111..004cbaccc 100644 --- a/src/OSSupport/Errors.cpp +++ b/src/OSSupport/Errors.cpp @@ -22,7 +22,7 @@ AString GetOSErrorString( int a_ErrNo) // According to http://linux.die.net/man/3/strerror_r there are two versions of strerror_r(): - #if defined(__GLIBC__) && defined( _GNU_SOURCE) && !defined(ANDROID_NDK) // GNU version of strerror_r() + #if defined(__GLIBC__) && defined( _GNU_SOURCE) && !defined(ANDROID) // GNU version of strerror_r() char * res = strerror_r( errno, buffer, ARRAYCOUNT(buffer)); if (res != nullptr) diff --git a/src/OSSupport/File.cpp b/src/OSSupport/File.cpp index a59f599ae..062161144 100644 --- a/src/OSSupport/File.cpp +++ b/src/OSSupport/File.cpp @@ -653,9 +653,13 @@ unsigned cFile::GetLastModificationTime(const AString & a_FileName) { return 0; } - #ifdef _WIN32 + #if defined(_WIN32) // Windows returns times in local time already return static_cast(st.st_mtime); + #elif defined(ANDROID) + // Identical to Linux below, but st_mtime is an unsigned long, so cast is needed: + auto Time = static_cast(st.st_mtime); + return static_cast(mktime(localtime(&Time))); #else // Linux returns UTC time, convert to local timezone: return static_cast(mktime(localtime(&st.st_mtime))); diff --git a/src/OSSupport/NetworkInterfaceEnum.cpp b/src/OSSupport/NetworkInterfaceEnum.cpp index d3a254c23..439710c38 100644 --- a/src/OSSupport/NetworkInterfaceEnum.cpp +++ b/src/OSSupport/NetworkInterfaceEnum.cpp @@ -7,10 +7,10 @@ #include "Network.h" #include "event2/util.h" -#ifdef _WIN32 +#if defined(_WIN32) #include #pragma comment(lib, "IPHLPAPI.lib") -#else // _WIN32 +#elif !defined(ANDROID) // _WIN32 #include #include #include @@ -21,7 +21,7 @@ -#ifdef _WIN32 +#if defined(_WIN32) /** Converts the SOCKET_ADDRESS structure received from the OS into an IP address string. */ static AString PrintAddress(SOCKET_ADDRESS & a_Addr) @@ -50,7 +50,7 @@ static AString PrintAddress(SOCKET_ADDRESS & a_Addr) return IP; } -#else // _WIN32 +#elif !defined(ANDROID) // _WIN32 static AString PrintAddress(ifaddrs * InterfaceAddress) { @@ -82,7 +82,7 @@ static AString PrintAddress(ifaddrs * InterfaceAddress) } } -#endif // else _WIN32 +#endif // else !ANDROID @@ -92,7 +92,7 @@ AStringVector cNetwork::EnumLocalIPAddresses(void) { AStringVector res; - #ifdef _WIN32 + #if defined(_WIN32) // Query the OS for all adapters' addresses: char buffer[64 KiB]; // A buffer backing the address list @@ -129,7 +129,7 @@ AStringVector cNetwork::EnumLocalIPAddresses(void) } // for pUnicast } // for pCurrAddresses - #else // _WIN32 + #elif !defined(ANDROID) // _WIN32 struct ifaddrs * ifAddrStruct = nullptr; getifaddrs(&ifAddrStruct); diff --git a/src/OSSupport/NetworkSingleton.cpp b/src/OSSupport/NetworkSingleton.cpp index dcf17bccb..3a8dbbdc7 100644 --- a/src/OSSupport/NetworkSingleton.cpp +++ b/src/OSSupport/NetworkSingleton.cpp @@ -13,6 +13,11 @@ #include "IPLookup.h" #include "HostnameLookup.h" +#ifdef ANDROID + // For DNS server retrieval + #include +#endif + @@ -89,6 +94,16 @@ void cNetworkSingleton::Initialise(void) abort(); } + #ifdef ANDROID + char PropertyBuffer[PROP_VALUE_MAX]; + + __system_property_get("net.dns1", PropertyBuffer); + evdns_base_nameserver_ip_add(m_DNSBase, PropertyBuffer); + + __system_property_get("net.dns2", PropertyBuffer); + evdns_base_nameserver_ip_add(m_DNSBase, PropertyBuffer); + #endif + // Create the event loop thread: m_HasTerminated = false; m_EventLoopThread = std::thread(RunEventLoop, this); diff --git a/src/OSSupport/StackTrace.cpp b/src/OSSupport/StackTrace.cpp index 030566065..c84e2cbca 100644 --- a/src/OSSupport/StackTrace.cpp +++ b/src/OSSupport/StackTrace.cpp @@ -7,7 +7,7 @@ #include "StackTrace.h" #ifdef _WIN32 #include "../StackWalker.h" -#else +#elif !defined(ANDROID) // The Android NDK has no execinfo header #ifdef __GLIBC__ #include #endif @@ -32,7 +32,7 @@ void PrintStackTrace(void) } } sw; sw.ShowCallstack(); - #else + #elif !defined(ANDROID) #ifdef __GLIBC__ // Use the backtrace() function to get and output the stackTrace: // Code adapted from https://stackoverflow.com/questions/77005/how-to-generate-a-stacktrace-when-my-gcc-c-app-crashes diff --git a/src/Root.cpp b/src/Root.cpp index 55e149511..206bddfbc 100644 --- a/src/Root.cpp +++ b/src/Root.cpp @@ -207,18 +207,16 @@ void cRoot::Start(std::unique_ptr a_OverridesRepo) { m_WebAdmin->Start(); - #if !defined(ANDROID_NDK) - LOGD("Starting InputThread..."); - try - { - m_InputThreadRunFlag.test_and_set(); - m_InputThread = std::thread(InputThread, std::ref(*this)); - } - catch (std::system_error & a_Exception) - { - LOGERROR("cRoot::Start (std::thread) error %i: could not construct input thread; %s", a_Exception.code().value(), a_Exception.what()); - } - #endif + LOGD("Starting InputThread..."); + try + { + m_InputThreadRunFlag.test_and_set(); + m_InputThread = std::thread(InputThread, std::ref(*this)); + } + catch (std::system_error & a_Exception) + { + LOGERROR("cRoot::Start (std::thread) error %i: could not construct input thread; %s", a_Exception.code().value(), a_Exception.what()); + } LOG("Startup complete, took %ldms!", static_cast(std::chrono::duration_cast(std::chrono::steady_clock::now() - BeginTime).count())); diff --git a/src/StringUtils.cpp b/src/StringUtils.cpp index 521aa79f4..81999a35d 100644 --- a/src/StringUtils.cpp +++ b/src/StringUtils.cpp @@ -5,10 +5,6 @@ #include "Globals.h" -#if defined(ANDROID_NDK) -#include -#endif - #ifdef _MSC_VER // Under MSVC, link to WinSock2 (needed by RawBEToUTF8's byteswapping) #pragma comment(lib, "ws2_32.lib") diff --git a/src/World.cpp b/src/World.cpp index eafd44ce0..e02ca7964 100644 --- a/src/World.cpp +++ b/src/World.cpp @@ -354,10 +354,10 @@ bool cWorld::SetSpawn(double a_X, double a_Y, double a_Z) void cWorld::InitializeSpawn(void) { // For the debugging builds, don't make the server build too much world upon start: - #if defined(_DEBUG) || defined(ANDROID_NDK) - const int DefaultViewDist = 9; + #if defined(_DEBUG) || defined(ANDROID) + const int DefaultViewDist = 9; #else - const int DefaultViewDist = 20; // Always prepare an area 20 chunks across, no matter what the actual cClientHandle::VIEWDISTANCE is + const int DefaultViewDist = 20; // Always prepare an area 20 chunks across, no matter what the actual cClientHandle::VIEWDISTANCE is #endif // _DEBUG if (!m_IsSpawnExplicitlySet) diff --git a/src/main.cpp b/src/main.cpp index 6061602d7..83056bf61 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -8,6 +8,20 @@ #include #include +#ifdef ANDROID + // Workaround for Android NDK builds that do not support std::to_string + namespace std + { + template + std::string to_string(T Value) + { + std::ostringstream TempStream; + TempStream << Value; + return TempStream.str(); + } + } +#endif + #ifdef _MSC_VER #include #endif // _MSC_VER @@ -223,14 +237,11 @@ static void UniversalMain(std::unique_ptr a_Overri // Initialize LibEvent: cNetworkSingleton::Get().Initialise(); - #if !defined(ANDROID_NDK) try - #endif { cRoot Root; Root.Start(std::move(a_OverridesRepo)); } - #if !defined(ANDROID_NDK) catch (std::exception & e) { LOGERROR("Standard exception: %s", e.what()); @@ -239,7 +250,6 @@ static void UniversalMain(std::unique_ptr a_Overri { LOGERROR("Unknown exception!"); } - #endif // Shutdown all of LibEvent: cNetworkSingleton::Get().Terminate(); -- cgit v1.2.3