diff --git a/build.sh b/build.sh index 1dd45d6a9..5e5b4787d 100755 --- a/build.sh +++ b/build.sh @@ -25,7 +25,7 @@ fi cd project && env PATH=$NDKBUILDPATH nice -n19 ndk-build -j4 V=1 && \ { grep "CustomBuildScript=y" ../AndroidAppSettings.cfg > /dev/null && \ - [ -`which ndk-build | grep '/android-ndk-r5b/\|/android-ndk-r5-crystax/'` != - ] && \ + [ -`which ndk-build | grep '/android-ndk-r5'` != - ] && \ echo Stripping libapplication.so by hand \ rm obj/local/armeabi/libapplication.so && \ cp jni/application/src/libapplication.so obj/local/armeabi && \ @@ -34,6 +34,4 @@ cd project && env PATH=$NDKBUILDPATH nice -n19 ndk-build -j4 V=1 && \ || true ; } && \ ant debug && \ test -z "$1" && cd bin && adb uninstall `grep AppFullName ../../AndroidAppSettings.cfg | sed 's/.*=//'` && \ - adb push DemoActivity-debug.apk /data/local && \ - adb shell pm install -f /data/local/DemoActivity-debug.apk && \ - adb shell rm /data/local/DemoActivity-debug.apk + adb install -r DemoActivity-debug.apk diff --git a/project/java/DataDownloader.java b/project/java/DataDownloader.java index d08b711f9..5b89b6d06 100644 --- a/project/java/DataDownloader.java +++ b/project/java/DataDownloader.java @@ -230,7 +230,9 @@ class DataDownloader extends Thread // Create output directory (not necessary for phone storage) System.out.println("Downloading data to: '" + outFilesDir + "'"); try { - (new File( outFilesDir )).mkdirs(); + File outDir = new File( outFilesDir ); + if( !(outDir.exists() && outDir.isDirectory()) ) + outDir.mkdirs(); OutputStream out = new FileOutputStream( getOutFilePath(".nomedia") ); out.flush(); out.close(); @@ -340,7 +342,9 @@ class DataDownloader extends Thread OutputStream out = null; try { try { - (new File( path.substring(0, path.lastIndexOf("/") ))).mkdirs(); + File outDir = new File( path.substring(0, path.lastIndexOf("/") )); + if( !(outDir.exists() && outDir.isDirectory()) ) + outDir.mkdirs(); } catch( SecurityException e ) { }; out = new FileOutputStream( path ); @@ -405,7 +409,9 @@ class DataDownloader extends Thread { System.out.println("Creating dir '" + getOutFilePath(entry.getName()) + "'"); try { - (new File( getOutFilePath(entry.getName()) )).mkdirs(); + File outDir = new File( getOutFilePath(entry.getName()) ); + if( !(outDir.exists() && outDir.isDirectory()) ) + outDir.mkdirs(); } catch( SecurityException e ) { }; continue; } @@ -416,7 +422,9 @@ class DataDownloader extends Thread System.out.println("Saving file '" + path + "'"); try { - (new File( path.substring(0, path.lastIndexOf("/") ))).mkdirs(); + File outDir = new File( path.substring(0, path.lastIndexOf("/") )); + if( !(outDir.exists() && outDir.isDirectory()) ) + outDir.mkdirs(); } catch( SecurityException e ) { }; try { @@ -431,9 +439,7 @@ class DataDownloader extends Thread } System.out.println("File '" + path + "' exists and passed CRC check - not overwriting it"); continue; - } catch( Exception e ) - { - } + } catch( Exception e ) { } try { out = new FileOutputStream( path ); diff --git a/project/java/Globals.java b/project/java/Globals.java index 562412ab5..33db03623 100644 --- a/project/java/Globals.java +++ b/project/java/Globals.java @@ -67,7 +67,7 @@ class Globals { public static int MoveMouseWithJoystickSpeed = 0; public static int MoveMouseWithJoystickAccel = 0; public static boolean ClickMouseWithDpad = false; - public static boolean RelativeMouseMovement = AppNeedsTwoButtonMouse; // Laptop touchpad mode + public static boolean RelativeMouseMovement = false; // Laptop touchpad mode public static int RelativeMouseMovementSpeed = 2; public static int RelativeMouseMovementAccel = 0; public static boolean ShowScreenUnderFinger = false; diff --git a/project/java/MainActivity.java b/project/java/MainActivity.java index c7877c1a9..cb4850ec0 100644 --- a/project/java/MainActivity.java +++ b/project/java/MainActivity.java @@ -43,6 +43,8 @@ import java.io.InputStream; import java.io.OutputStream; import java.io.FileOutputStream; import java.io.File; +import java.io.FileInputStream; +import java.util.zip.*; import java.util.zip.ZipEntry; import java.util.zip.ZipInputStream; import android.text.SpannedString; @@ -584,6 +586,20 @@ public class MainActivity extends Activity { OutputStream out = null; String path = cacheDir.getAbsolutePath() + "/" + entry.getName(); + try { + CheckedInputStream check = new CheckedInputStream( new FileInputStream(path), new CRC32() ); + while( check.read(buf, 0, buf.length) > 0 ) {}; + check.close(); + if( check.getChecksum().getValue() != entry.getCrc() ) + { + File ff = new File(path); + ff.delete(); + throw new Exception(); + } + System.out.println("File '" + path + "' exists and passed CRC check - not overwriting it"); + continue; + } catch( Exception e ) { } + System.out.println("Saving to file '" + path + "'"); out = new FileOutputStream( path ); @@ -597,7 +613,12 @@ public class MainActivity extends Activity { out.flush(); out.close(); - (new ProcessBuilder().command("/system/bin/chmod", "0755", path).start()).waitFor(); + try { + (new ProcessBuilder().command("/system/bin/chmod", "0755", path).start()).waitFor(); + } catch ( Exception eeee ) {} + try { + (new ProcessBuilder().command("/system/xbin/chmod", "0755", path).start()).waitFor(); + } catch ( Exception eeeee ) {} } } catch ( Exception eee ) diff --git a/project/java/Video.java b/project/java/Video.java index c9666451d..7597809d5 100644 --- a/project/java/Video.java +++ b/project/java/Video.java @@ -265,18 +265,6 @@ class DemoRenderer extends GLSurfaceView_SDL.Renderer mGlContextLost = false; - // ----- VCMI hack ----- - try - { - File libpath = new File(context.getFilesDir(), "libvcmi.so"); - System.load(libpath.getPath()); - } - catch ( UnsatisfiedLinkError eee ) - { - //System.out.println("libSDL: error loading lib: " + eee.toString()); - } - // ----- VCMI hack ----- - String libs[] = { "application", "sdl_main" }; try { diff --git a/project/jni/application/setEnvironment-r5b.sh b/project/jni/application/setEnvironment-r5b.sh index a41543a7e..f45560369 100755 --- a/project/jni/application/setEnvironment-r5b.sh +++ b/project/jni/application/setEnvironment-r5b.sh @@ -25,11 +25,6 @@ LOCAL_PATH=`dirname $0` LOCAL_PATH=`cd $LOCAL_PATH && pwd` echo LOCAL_PATH $LOCAL_PATH -if [ -z "`echo $NDK | grep 'android-ndk-r5b'``echo $NDK | grep 'android-ndk-r5-crystax'`" ] ; then - echo "The only supported NDK versions are android-ndk-r5b or android-ndk-r5-crystax" - exit 1 -fi - APP_MODULES=`grep 'APP_MODULES [:][=]' $LOCAL_PATH/../Settings.mk | sed 's@.*[=]\(.*\)@\1@'` APP_AVAILABLE_STATIC_LIBS=`grep 'APP_AVAILABLE_STATIC_LIBS [:][=]' $LOCAL_PATH/../Settings.mk | sed 's@.*[=]\(.*\)@\1@'` APP_SHARED_LIBS=$( @@ -72,7 +67,6 @@ if [ -n "$NO_SHARED_LIBS" ]; then fi -#-shared flag creates problems with damn libtool, so we're using -Wl,-shared instead LDFLAGS="\ -fexceptions -frtti $SHARED \ --sysroot=$NDK/platforms/$PLATFORMVER/arch-arm \ diff --git a/project/jni/application/setEnvironment.sh b/project/jni/application/setEnvironment.sh index 091e6d1e8..c340132f3 100755 --- a/project/jni/application/setEnvironment.sh +++ b/project/jni/application/setEnvironment.sh @@ -14,7 +14,7 @@ LOCAL_PATH=`cd $LOCAL_PATH && pwd` SCRIPT=setEnvironment-r4b.sh CRYSTAX_WCHAR= -if [ -n "`echo $NDK | grep 'android-ndk-r5b\|android-ndk-r5-crystax-1.beta3'`" ]; then +if [ -n "`echo $NDK | grep 'android-ndk-r5'`" ]; then SCRIPT=setEnvironment-r5b.sh if [ -n "`echo $NDK | grep 'android-ndk-r5-crystax-1.beta3'`" ]; then CRYSTAX_WCHAR=1 diff --git a/project/jni/application/src b/project/jni/application/src index 59d41f41e..8193e5e18 120000 --- a/project/jni/application/src +++ b/project/jni/application/src @@ -1 +1 @@ -fheroes2 \ No newline at end of file +vcmi \ No newline at end of file diff --git a/project/jni/application/vcmi/Android.mk b/project/jni/application/vcmi/Android.mk new file mode 100644 index 000000000..541bc8d9d --- /dev/null +++ b/project/jni/application/vcmi/Android.mk @@ -0,0 +1,19 @@ +LOCAL_PATH := $(call my-dir) + +include $(CLEAR_VARS) + +LOCAL_MODULE := vcmi + +ifneq ($(NDK_R5_TOOLCHAIN),) +LOCAL_SRC_FILES := libvcmi.so +include $(PREBUILT_SHARED_LIBRARY) +else +LOCAL_SRC_FILES := dummy.c +include $(BUILD_SHARED_LIBRARY) +$(abspath $(LOCAL_PATH)/../../obj/local/armeabi/libvcmi.so): $(LOCAL_PATH)/libvcmi.so OVERRIDE_CUSTOM_LIB + cp -f $< $@ +$(abspath $(LOCAL_PATH)/../../obj/local/armeabi-v7a/libvcmi.so): $(LOCAL_PATH)/libvcmi.so OVERRIDE_CUSTOM_LIB + cp -f $< $@ +.PHONY: OVERRIDE_CUSTOM_LIB +OVERRIDE_CUSTOM_LIB: +endif diff --git a/project/jni/application/vcmi/AndroidAppSettings.cfg b/project/jni/application/vcmi/AndroidAppSettings.cfg index 2cdd9900c..a09a029ae 100644 --- a/project/jni/application/vcmi/AndroidAppSettings.cfg +++ b/project/jni/application/vcmi/AndroidAppSettings.cfg @@ -25,12 +25,12 @@ RedefinedKeysScreenKb="LALT RETURN KP_PLUS KP_MINUS SPACE DELETE KP_PLUS KP_MINU StartupMenuButtonTimeout=3000 HiddenMenuOptions='KeyboardConfigMainMenu AudioConfig OptionalDownloadConfig' MultiABI=n -AppVersionCode=08501 -AppVersionName="0.85.01" -CompiledLibraries="sdl_mixer sdl_image sdl_ttf avutil avcore avcodec avformat swscale boost_program_options boost_filesystem boost_iostreams boost_system boost_thread" +AppVersionCode=08502 +AppVersionName="0.85.02" +CompiledLibraries="sdl_mixer sdl_image sdl_ttf avutil avcore avcodec avformat swscale boost_program_options boost_filesystem boost_iostreams boost_system boost_thread vcmi" CustomBuildScript=n AppCflags='-DDATA_DIR=\\\"/sdcard/app-data/eu.vcmi\\\" -DBIN_DIR=\\\"/data/data/eu.vcmi/files\\\" -DLIB_DIR=\\\"/data/data/eu.vcmi/files\\\" -DWITH_AVCODEC_DECODE_VIDEO2=1' AppLdflags='-lz -Ljni/application/vcmi -lvcmi' -AppSubdirsBuild='vcmi vcmi/client' +AppSubdirsBuild='vcmi/client vcmi/CGameInterface.cpp vcmi/CCallback.cpp' AppCmdline='' ReadmeText='^You may press "Home" now - the data will be downloaded in background' diff --git a/project/jni/application/vcmi/AndroidData/vcmiserver0 b/project/jni/application/vcmi/AndroidData/vcmiserver0 index 888a0bdea..d3e9b6925 100644 Binary files a/project/jni/application/vcmi/AndroidData/vcmiserver0 and b/project/jni/application/vcmi/AndroidData/vcmiserver0 differ diff --git a/project/jni/application/vcmi/AndroidData/vcmiserver1 b/project/jni/application/vcmi/AndroidData/vcmiserver1 index 9a5a8fcd8..f76ed6d35 100644 Binary files a/project/jni/application/vcmi/AndroidData/vcmiserver1 and b/project/jni/application/vcmi/AndroidData/vcmiserver1 differ diff --git a/project/jni/application/vcmi/AndroidData/vcmiserver2 b/project/jni/application/vcmi/AndroidData/vcmiserver2 deleted file mode 100644 index 4ae217d03..000000000 Binary files a/project/jni/application/vcmi/AndroidData/vcmiserver2 and /dev/null differ diff --git a/project/jni/application/vcmi/Makefile b/project/jni/application/vcmi/Makefile index 9b368f2d1..9736bec62 100644 --- a/project/jni/application/vcmi/Makefile +++ b/project/jni/application/vcmi/Makefile @@ -28,7 +28,7 @@ AndroidData/vcmiserver0: vcmiserver.zip split -b 1048576 -d -a 1 $< AndroidData/vcmiserver cp -f AndroidData/vcmiserver* ../../../assets -vcmiserver.zip: vcmiserver libvcmi.so GeniusAI.so StupidAI.so +vcmiserver.zip: vcmiserver GeniusAI.so StupidAI.so rm -f $@ zip $@ $^ @@ -41,6 +41,7 @@ $(OBJS_SERVER) $(OBJS_LIB) $(OBJS_GENIUSAI) $(OBJS_STUPIDAI) $(OBJS_CLIENT): out -DLIB_DIR=\\\"/data/data/eu.vcmi/files\\\" \ -DWITH_AVCODEC_DECODE_VIDEO2=1 \ $< -o $@" +# -Werror=strict-aliasing -Werror=cast-align -Werror=pointer-arith -Werror=address vcmiserver: $(OBJS_SERVER) $(OBJS_LIB) env BUILD_EXECUTABLE=1 NO_SHARED_LIBS=1 ../setEnvironment.sh sh -c \ diff --git a/project/jni/application/vcmi/vcmi-android.diff b/project/jni/application/vcmi/vcmi-android.diff index 76f857732..173c28fa6 100644 --- a/project/jni/application/vcmi/vcmi-android.diff +++ b/project/jni/application/vcmi/vcmi-android.diff @@ -1,6 +1,6 @@ Index: server/stdafx.h =================================================================== ---- server/stdafx.h (revision 2178) +--- server/stdafx.h (revision 2183) +++ server/stdafx.h (working copy) @@ -15,8 +15,8 @@ #include "../global.h" @@ -15,7 +15,7 @@ Index: server/stdafx.h #include Index: server/CVCMIServer.cpp =================================================================== ---- server/CVCMIServer.cpp (revision 2178) +--- server/CVCMIServer.cpp (revision 2183) +++ server/CVCMIServer.cpp (working copy) @@ -29,7 +29,7 @@ using namespace boost; @@ -52,58 +52,84 @@ Index: server/CVCMIServer.cpp acc.join(); if (error) -Index: server/CGameHandler.cpp +Index: lib/CLodHandler.cpp =================================================================== ---- server/CGameHandler.cpp (revision 2178) -+++ server/CGameHandler.cpp (working copy) -@@ -739,6 +739,7 @@ - //gs = NULL; - IObjectInterface::cb = this; - applier = new CApplier; -+ tlog1 << "registerTypes3: " << __FILE__ << ":" << __LINE__ << std::endl; - registerTypes3(*applier); - visitObjectAfterVictory = false; - battleEndCallback = NULL; -@@ -1786,7 +1787,7 @@ - iw.player = h1->tempOwner; - iw.components.push_back(Component(Component::SEC_SKILL, 18, ScholarLevel, 0)); +--- lib/CLodHandler.cpp (revision 2183) ++++ lib/CLodHandler.cpp (working copy) +@@ -60,6 +60,9 @@ + return ret; + } -- iw.text.addTxt(MetaString::GENERAL_TXT, 139);//"%s, who has studied magic extensively, -+ iw.text.addTxt(MetaString::GENERAL_TXT, 139);//%s, who has studied magic extensively, - iw.text.addReplacement(h1->name); - - if (cs2.spells.size())//if found new spell - apply -Index: lib/CGameState.cpp -=================================================================== ---- lib/CGameState.cpp (revision 2178) -+++ lib/CGameState.cpp (working copy) -@@ -54,6 +54,7 @@ - void foofoofoo() ++int CLodHandler::dbgLastFileSize = 0; ++std::string CLodHandler::dbgLastFileName; ++ + unsigned char * CLodHandler::giveFile(const std::string defName, LodFileType type, int * length) { - //never called function to force instantation of templates -+ tlog1 << "registerTypes: " << __FILE__ << ":" << __LINE__ << std::endl; - int *ccc = NULL; - registerTypes((CISer&)*ccc); - registerTypes((COSer&)*ccc); -@@ -124,6 +125,7 @@ + std::string fname = defName; +@@ -78,13 +81,15 @@ + Entry ourEntry = *en_it; - CObjectCallersHandler() + if(length) *length = ourEntry.realSize; ++ enum { SAFETY_MARGIN = 4096 }; // VCMI functions tend to read past the array end, crashing at random + mutex->lock(); + + unsigned char * outp; + if (ourEntry.offset<0) //file is in the sprites/ folder; no compression { -+ tlog1 << "registerTypes1: " << __FILE__ << ":" << __LINE__ << std::endl; - registerTypes1(*this); + int result; +- outp = new unsigned char[ourEntry.realSize]; ++ outp = new unsigned char[ourEntry.realSize+SAFETY_MARGIN]; ++ memset(outp+ourEntry.realSize, 0, SAFETY_MARGIN); + FILE * f = fopen((myDir + "/" + ourEntry.realName).c_str(), "rb"); + if (f) + { +@@ -100,16 +105,25 @@ + delete[] outp; + return NULL; + } +- else ++ else ++ { ++ dbgLastFileSize = ourEntry.realSize; ++ dbgLastFileName = defName; ++ //tlog0 << "Loaded file: " << fname << " size " << ourEntry.realSize << " ptr " << (void *)outp << " safety " << (int)SAFETY_MARGIN << std::endl; + return outp; ++ } } + else if (ourEntry.size==0) //file is not compressed + { +- outp = new unsigned char[ourEntry.realSize]; ++ outp = new unsigned char[ourEntry.realSize+SAFETY_MARGIN]; ++ memset(outp+ourEntry.realSize, 0, SAFETY_MARGIN); -@@ -797,6 +799,7 @@ - gs = this; - mx = new boost::shared_mutex(); - applierGs = new CApplier; -+ tlog1 << "registerTypes2: " << __FILE__ << ":" << __LINE__ << std::endl; - registerTypes2(*applierGs); - objCaller = new CObjectCallersHandler; - globalEffects.description = "Global effects"; + LOD.seekg(ourEntry.offset, std::ios::beg); + LOD.read((char*)outp, ourEntry.realSize); + mutex->unlock(); ++ dbgLastFileSize = ourEntry.realSize; ++ dbgLastFileName = defName; ++ //tlog0 << "Loaded file: " << fname << " size " << ourEntry.realSize << " ptr " << (void *)outp << " safety " << (int)SAFETY_MARGIN << std::endl; + return outp; + } + else //we will decompress file +@@ -122,7 +136,14 @@ + infs2(outp, ourEntry.size, ourEntry.realSize, decomp); + mutex->unlock(); + delete[] outp; +- return decomp; ++ outp = new unsigned char[ourEntry.realSize+SAFETY_MARGIN]; ++ memset(outp+ourEntry.realSize, 0, SAFETY_MARGIN); ++ memcpy(outp, decomp, ourEntry.realSize); ++ delete [] decomp; ++ dbgLastFileSize = ourEntry.realSize; ++ dbgLastFileName = defName; ++ //tlog0 << "Loaded file: " << fname << " size " << ourEntry.realSize << " ptr " << (void *)outp << " safety " << (int)SAFETY_MARGIN << std::endl; ++ return outp; + } + return NULL; + } Index: lib/Interprocess.h =================================================================== ---- lib/Interprocess.h (revision 2178) +--- lib/Interprocess.h (revision 2183) +++ lib/Interprocess.h (working copy) @@ -1,3 +1,4 @@ +/* @@ -175,7 +201,7 @@ Index: lib/Interprocess.h +} Index: lib/Connection.h =================================================================== ---- lib/Connection.h (revision 2178) +--- lib/Connection.h (revision 2183) +++ lib/Connection.h (working copy) @@ -82,7 +82,9 @@ { @@ -188,75 +214,22 @@ Index: lib/Connection.h } }; -Index: lib/ERMInterpreter.cpp +Index: lib/CLodHandler.h =================================================================== ---- lib/ERMInterpreter.cpp (revision 2178) -+++ lib/ERMInterpreter.cpp (working copy) -@@ -2546,7 +2546,8 @@ - else if(symToFunc.find(opt.text) != symToFunc.end()) - { - VFunc f(symToFunc[opt.text]); -- return f(erm->evalEach(exp.children.cdr())); -+ VOptionList ls = erm->evalEach(exp.children.cdr()); -+ return f(VermTreeIterator(ls)); - } +--- lib/CLodHandler.h (revision 2183) ++++ lib/CLodHandler.h (working copy) +@@ -116,6 +116,8 @@ + void extractFile(const std::string FName, const std::string name); //extracts a specific file + + static unsigned char * getUnpackedFile(const std::string & path, int * sizeOut); //loads given file, decompresses and returns ++ static int dbgLastFileSize; ++ static std::string dbgLastFileName; + }; -Index: lib/VCMIDirs.h -=================================================================== ---- lib/VCMIDirs.h (revision 2178) -+++ lib/VCMIDirs.h (working copy) -@@ -1,3 +1,6 @@ -+#ifndef __VCMI__DIRS_H__ -+#define __VCMI__DIRS_H__ -+ - /* - * UserHome.h, part of VCMI engine - * -@@ -13,7 +16,6 @@ - using namespace boost::filesystem; - #endif - -- - /// Where to find the various VCMI files. This is mostly usefull for linux. - class VCMIDirs { - public: -@@ -24,14 +26,25 @@ - #ifdef _WIN32 - UserPath = DATA_DIR; - #else -- // Find vcmi user directory and create it if necessary -- std::string home_dir = getenv("HOME"); -- UserPath = path(home_dir + "/.vcmi").string(); -- -- create_directory(UserPath); -- create_directory(UserPath + "/config"); -- create_directory(UserPath + "/Games"); -+ try { -+ // Find vcmi user directory and create it if necessary -+ std::string home_dir = "."; -+ if( getenv("HOME") != NULL ) -+ home_dir = getenv("HOME"); -+ UserPath = path(home_dir + "/.vcmi").string(); -+#ifdef ANDROID -+ UserPath = DATA_DIR; - #endif -+ create_directory(UserPath); -+ create_directory(UserPath + "/config"); -+ create_directory(UserPath + "/Games"); -+ } -+ catch(const std::exception & e) -+ { -+ } -+#endif - } - }; - extern VCMIDirs GVCMIDirs; -+ -+#endif Index: CConsoleHandler.cpp =================================================================== ---- CConsoleHandler.cpp (revision 2178) +--- CConsoleHandler.cpp (revision 2183) +++ CConsoleHandler.cpp (working copy) @@ -143,6 +143,7 @@ @@ -276,95 +249,264 @@ Index: CConsoleHandler.cpp int CConsoleHandler::run() Index: global.h =================================================================== ---- global.h (revision 2178) +--- global.h (revision 2183) +++ global.h (working copy) -@@ -10,6 +10,10 @@ - using boost::logic::tribool; - #include - #include -+#ifdef ANDROID -+#include -+#include -+#endif - //filesystem version 3 causes problems (and it's default as of boost 1.46) - #define BOOST_FILESYSTEM_VERSION 2 - typedef boost::uint64_t ui64; //unsigned int 64 bits (8 bytes) -@@ -618,20 +622,45 @@ - class CLogger //logger, prints log info to console and saves in file +@@ -4,6 +4,7 @@ + #include + #include + #include //std::find ++#include //memcpy + #include //std::find + #include + #include +@@ -727,29 +728,21 @@ + } + + +-#if defined(linux) && defined(sparc) +-/* SPARC does not support unaligned memory access. Let gcc know when +- * to emit the right code. */ +-struct unaligned_Uint16 { ui16 val __attribute__(( packed )); }; +-struct unaligned_Uint32 { ui32 val __attribute__(( packed )); }; + + static inline ui16 read_unaligned_u16(const void *p) { - const int lvl; -+#ifdef ANDROID -+ std::ostringstream buf; -+ int androidloglevel; -+ void outputAndroid() -+ { -+ int pos = buf.str().find("\n"); -+ while( pos >= 0 ) -+ { -+ __android_log_print(androidloglevel, "VCMI", "%s", buf.str().substr(0, pos).c_str() ); -+ buf.str( buf.str().substr(pos+1) ); -+ pos = buf.str().find("\n"); -+ } -+ } -+#endif +- const struct unaligned_Uint16 *v = (const struct unaligned_Uint16 *)p; +- return v->val; ++ ui16 out; ++ memcpy(&out, p, sizeof(out)); ++ return out; + } - public: - CLogger& operator<<(std::ostream& (*fun)(std::ostream&)) - { + static inline ui32 read_unaligned_u32(const void *p) + { +- const struct unaligned_Uint32 *v = (const struct unaligned_Uint32 *)p; +- return v->val; ++ ui32 out; ++ memcpy(&out, p, sizeof(out)); ++ return out; + } + +-#else +-#define read_unaligned_u16(p) (* reinterpret_cast(p)) +-#define read_unaligned_u32(p) (* reinterpret_cast(p)) +-#endif +- + //for explicit overrides + #ifdef _MSC_VER + #define OVERRIDE override +Index: CThreadHelper.cpp +=================================================================== +--- CThreadHelper.cpp (revision 2183) ++++ CThreadHelper.cpp (working copy) +@@ -24,10 +24,16 @@ + } + void CThreadHelper::run() + { +#ifdef ANDROID -+ buf << fun; -+ outputAndroid(); ++ // For debug make it single-threaded ++ for(int i=0;isize();i++) ++ (*tasks)[i](); +#else - if(lvl < CONSOLE_LOGGING_LEVEL) -+ { - std::cout << fun; -+ } - if((lvl < FILE_LOGGING_LEVEL) && logfile) - *logfile << fun; + boost::thread_group grupa; + for(int i=0;i - CLogger & operator<<(const T & data) + CThreadHelper th(&tasks,std::max((unsigned int)1,boost::thread::hardware_concurrency())); + th.run(); ++ ++ tlog0<<__FUNCTION__ << " at " << __FILE__ << ":" << __LINE__ << " heroMoveArrows " << heroMoveArrows <ourImages.size(); ++y) { -+#ifdef ANDROID -+ buf << data; -+ outputAndroid(); -+#else - if(lvl < CONSOLE_LOGGING_LEVEL) ++ tlog0<<__FUNCTION__ << " at " << __FILE__ << ":" << __LINE__ << " heroMoveArrows " << y << "/" << heroMoveArrows->ourImages.size() <ourImages[y].bitmap); + } ++ tlog0<<__FUNCTION__ << " at " << __FILE__ << ":" << __LINE__ <notFreeImgs = true; +@@ -354,9 +361,11 @@ + bigImgs[i-2] = smi2->ourImages[i].bitmap; + } + delete smi2; ++ tlog0<<__FUNCTION__ << " at " << __FILE__ << ":" << __LINE__ <>numberOfPortraits; +@@ -384,6 +393,7 @@ + + void Graphics::loadWallPositions() + { ++ tlog0<<__FUNCTION__ << " at " << __FILE__ << ":" << __LINE__ < > rotations; //first - group number to be rotated1, second - group number after rotation1 + rotations += std::make_pair(6,10), std::make_pair(7,11), std::make_pair(8,12), std::make_pair(1,13), + std::make_pair(2,14), std::make_pair(3,15); ++ tlog0<<__FUNCTION__ << " at " << __FILE__ << ":" << __LINE__ < > &rotations, std::vector Graphics::*dst ) + { ++ tlog0<<__FUNCTION__ << " at " << __FILE__ << ":" << __LINE__ << " load " << name <*dst).push_back(anim); + int pom = 0; //how many groups has been rotated +@@ -472,12 +490,15 @@ + + void Graphics::loadHeroFlags(std::pair Graphics::*, std::vector > &pr, bool mode) + { ++ tlog0<<__FUNCTION__ << " at " << __FILE__ << ":" << __LINE__ <*pr.first).push_back(CDefHandler::giveDefEss(pr.second[i])); ++ tlog0<<__FUNCTION__ << " at " << __FILE__ << ":" << __LINE__ < > rotations; //first - group number to be rotated1, second - group number after rotation1 + rotations += std::make_pair(6,10), std::make_pair(7,11), std::make_pair(8,12); + for(int q=0; q<8; ++q) + { ++ tlog0<<__FUNCTION__ << " at " << __FILE__ << ":" << __LINE__ < &curImgs = (this->*pr.first)[q]->ourImages; + for(size_t o=0; o Graphics::*, std::vector > pr[4]; ++ tlog0<<__FUNCTION__ << " at " << __FILE__ << ":" << __LINE__ <=0; --g) + { + grupa.create_thread(boost::bind(&Graphics::loadHeroFlags,this,boost::ref(pr[g]),true)); + } + grupa.join_all(); +#endif -+ } - }; + tlog0 << "Loading and transforming heroes' flags: "<giveFile(name, FILE_FONT, &len); + if(!hlp || !len) +@@ -725,6 +762,7 @@ + + void Graphics::loadFonts() + { ++ tlog0<<__FUNCTION__ << " at " << __FILE__ << ":" << __LINE__ <; -+ tlog1 << "registerTypes2: " << __FILE__ << ":" << __LINE__ << std::endl; - registerTypes2(*applier); -+ tlog1 << "-----Start applier: registerTypes2" << std::endl; -+ for( std::map :: const_iterator it = applier->apps.begin(); -+ it != applier->apps.end(); it++ ) -+ { -+ tlog1 << "applier ID " << it->first << " ptr " << typeid(*it->second).name() << std::endl; -+ } -+ tlog1 << "-----End applier: registerTypes2" << std::endl; -+ - IObjectInterface::cb = this; - serv = NULL; - gs = NULL; -@@ -498,9 +507,9 @@ +@@ -498,9 +498,9 @@ void CClient::handlePack( CPack * pack ) { @@ -404,16 +529,7 @@ Index: client/Client.cpp apply->applyOnClBefore(this,pack); tlog5 << "\tMade first apply on cl\n"; gs->apply(pack); -@@ -510,7 +519,7 @@ - } - else - { -- tlog1 << "Message cannot be applied, cannot find applier!\n"; -+ tlog1 << "Message cannot be applied, cannot find applier! TypeID " << typeList.getTypeID(pack) << std::endl; - } - delete pack; - } -@@ -628,18 +637,22 @@ +@@ -628,18 +628,22 @@ startServer(); th.update(); @@ -437,7 +553,7 @@ Index: client/Client.cpp waitForServer(); th.update(); -@@ -654,27 +667,31 @@ +@@ -654,27 +658,31 @@ CServerHandler::CServerHandler(bool runServer /*= false*/) { serverThread = NULL; @@ -473,7 +589,7 @@ Index: client/Client.cpp } Index: client/GUIBase.cpp =================================================================== ---- client/GUIBase.cpp (revision 2178) +--- client/GUIBase.cpp (revision 2183) +++ client/GUIBase.cpp (working copy) @@ -11,6 +11,7 @@ #include "../CThreadHelper.h" @@ -510,9 +626,21 @@ Index: client/GUIBase.cpp CGuiHandler::CGuiHandler() :lastClick(-500, -500) +Index: client/CDefHandler.h +=================================================================== +--- client/CDefHandler.h (revision 2183) ++++ client/CDefHandler.h (working copy) +@@ -30,7 +30,6 @@ + ui32 totalInBlock; + ui32 unknown2; + ui32 unknown3; +- unsigned char data[0]; + }; + + // Def entry in file. Integer fields are all little endian and will Index: client/Client.h =================================================================== ---- client/Client.h (revision 2178) +--- client/Client.h (revision 2183) +++ client/Client.h (working copy) @@ -43,7 +43,7 @@ public: @@ -523,21 +651,9 @@ Index: client/Client.h bool verbose; //whether to print log msgs std::string port; //port number in text form -Index: client/CPreGame.cpp -=================================================================== ---- client/CPreGame.cpp (revision 2178) -+++ client/CPreGame.cpp (working copy) -@@ -525,6 +525,7 @@ - } - - applier = new CApplier; -+ tlog1 << "registerTypes4: " << __FILE__ << ":" << __LINE__ << std::endl; - registerTypes4(*applier); - serverHandlingThread = new boost::thread(&CSelectionScreen::handleConnection, this); - } Index: client/CMT.cpp =================================================================== ---- client/CMT.cpp (revision 2178) +--- client/CMT.cpp (revision 2183) +++ client/CMT.cpp (working copy) @@ -92,8 +92,10 @@ void dispose(); @@ -571,7 +687,17 @@ Index: client/CMT.cpp initDLL(::console,logfile); const_cast(CGI)->setFromLib(); -@@ -186,11 +191,15 @@ +@@ -154,7 +159,9 @@ + CCS->curh->show(); + tlog0<<"Screen handler: "<loadHeroAnims(); + tlog0<<"\tMain graphics: "<start(); atexit(dispose); tlog0 <<"Creating console and logfile: "<playerInfos[1].color = 1; startGame(si); } @@ -633,7 +759,7 @@ Index: client/CMT.cpp return 0; } -@@ -559,10 +582,12 @@ +@@ -559,10 +584,12 @@ tlog2 << "Warning: SDL says that " << bpp << "bpp is wrong and suggests " << suggestedBpp << std::endl; } @@ -646,7 +772,7 @@ Index: client/CMT.cpp if((screen = SDL_SetVideoMode(w, h, suggestedBpp, SDL_SWSURFACE|(fullscreen?SDL_FULLSCREEN:0))) == NULL) { -@@ -607,14 +632,27 @@ +@@ -607,14 +634,27 @@ setResolution = true; } @@ -677,7 +803,7 @@ Index: client/CMT.cpp //tlog0 << "got " << (int)ev->type; if (ret == 0 || (ev->type==SDL_QUIT) || (ev->type == SDL_KEYDOWN && ev->key.keysym.sym==SDLK_F4 && (ev->key.keysym.mod & KMOD_ALT))) -@@ -633,7 +671,7 @@ +@@ -633,7 +673,7 @@ SDL_Delay(750); SDL_Quit(); tlog0 << "Ending...\n"; @@ -686,7 +812,7 @@ Index: client/CMT.cpp } else if(LOCPLINT && ev->type == SDL_KEYDOWN && ev->key.keysym.sym==SDLK_F4) { -@@ -642,7 +680,7 @@ +@@ -642,7 +682,7 @@ setScreenRes(conf.cc.screenx, conf.cc.screeny, conf.cc.bpp, full); GH.totalRedraw(); delete ev; @@ -695,7 +821,7 @@ Index: client/CMT.cpp } else if(ev->type == SDL_USEREVENT) { -@@ -672,7 +710,7 @@ +@@ -672,7 +712,7 @@ } delete ev; @@ -704,7 +830,7 @@ Index: client/CMT.cpp } //tlog0 << " pushing "; -@@ -680,7 +718,7 @@ +@@ -680,7 +720,7 @@ events.push(ev); eventsM.unlock(); //tlog0 << " done\n"; @@ -713,14 +839,317 @@ Index: client/CMT.cpp } void startGame(StartInfo * options, CConnection *serv/* = NULL*/) -@@ -741,3 +779,4 @@ +@@ -741,3 +781,4 @@ ev.user.code = 1; SDL_PushEvent(&ev); } + +Index: client/CDefHandler.cpp +=================================================================== +--- client/CDefHandler.cpp (revision 2183) ++++ client/CDefHandler.cpp (working copy) +@@ -50,10 +50,19 @@ + SDL_FreeSurface(ourImages[i].bitmap); + } + ++#define CHECK_LOD_MEM_BLOCK_SIZE1(S, FF, F, L) { \ ++ if( CLodHandler::dbgLastFileSize < (S) ) \ ++ tlog1<<"ERROR in " << FF << " " << F << ":" << L << ": reading past the end of LOD mem block at " << \ ++ (S) << " memblock " << CLodHandler::dbgLastFileSize << " fname " << CLodHandler::dbgLastFileName << std::endl; } ++#define CHECK_LOD_MEM_BLOCK_SIZE(S) CHECK_LOD_MEM_BLOCK_SIZE1(S, __FUNCTION__, __FILE__, __LINE__) ++ + void CDefHandler::openFromMemory(unsigned char *table, const std::string & name) + { ++ //tlog0<<"openFromMemory ptr " << (void *)table <(table); ++ SDefEntry de; ++ memcpy(&de, table, sizeof(de)); + unsigned char *p; + + defName = name; +@@ -61,6 +70,8 @@ + width = SDL_SwapLE32(de.width); + height = SDL_SwapLE32(de.height); + unsigned int totalBlocks = SDL_SwapLE32(de.totalBlocks); ++ ++ //tlog0<<"openFromMemory w " << width << " h " << height << " totalBlocks " << totalBlocks <(&de); ++ p = table; + p += sizeof(de); +- ++ + int totalEntries=0; + for (unsigned int z=0; z(p); ++ //tlog0<<"Megadebug 443 - read size " << p - table <(FDef + BaseOffset); ++ SSpriteDef sd; ++ CHECK_LOD_MEM_BLOCK_SIZE(BaseOffset + sizeof(sd)); ++ ++ memcpy(&sd, FDef + BaseOffset, sizeof(sd)); + + prSize = SDL_SwapLE32(sd.prSize); //TODO use me + defType2 = SDL_SwapLE32(sd.defType2); +@@ -170,12 +206,14 @@ + if (add==4) + add=0; + ++ //tlog0<<"getSprite: 11: SDL_CreateRGBSurface " << FullWidth << ":" << FullHeight << std::endl; + ret = SDL_CreateRGBSurface(SDL_SWSURFACE, FullWidth, FullHeight, 8, 0, 0, 0, 0); + //int tempee2 = readNormalNr(0,4,((unsigned char *)tempee.c_str())); + + BaseOffset += sizeof(SSpriteDef); + int BaseOffsetor = BaseOffset; + ++ //tlog0<<"getSprite: 12: set palette" << std::endl; + for(int i=0; i<256; ++i) + { + SDL_Color pr; +@@ -188,6 +226,7 @@ + + int ftcp=0; + ++ //tlog0<<"getSprite: 13" << std::endl; + // If there's a margin anywhere, just blank out the whole surface. + if (TopMargin > 0 || BottomMargin > 0 || LeftMargin > 0 || RightMargin > 0) { + memset( reinterpret_cast(ret->pixels), 0, FullHeight*FullWidth); +@@ -197,6 +236,7 @@ + if (TopMargin > 0) + ftcp += TopMargin*(FullWidth+add); + ++ //tlog0<<"getSprite: 14: defType2 " << defType2 << std::endl; + switch(defType2) + { + case 0: +@@ -206,6 +246,8 @@ + if (LeftMargin>0) + ftcp += LeftMargin; + ++ CHECK_LOD_MEM_BLOCK_SIZE(BaseOffset + SpriteWidth); ++ CHECK_OUTBUF_MEM_BLOCK_SIZE(ftcp + SpriteWidth); + memcpy(reinterpret_cast(ret->pixels)+ftcp, &FDef[BaseOffset], SpriteWidth); + ftcp += SpriteWidth; + BaseOffset += SpriteWidth; +@@ -218,11 +260,12 @@ + + case 1: + { +- const unsigned int * RWEntriesLoc = reinterpret_cast(FDef+BaseOffset); ++ unsigned int RWEntriesLoc = BaseOffset; + BaseOffset += sizeof(int) * SpriteHeight; + for (unsigned int i=0;i0) + ftcp += LeftMargin; + +@@ -230,17 +273,22 @@ + do + { + unsigned int SegmentLength; ++ ++ CHECK_LOD_MEM_BLOCK_SIZE(BaseOffset + 4); + + SegmentType=FDef[BaseOffset++]; + SegmentLength=FDef[BaseOffset++] + 1; +- ++ + if (SegmentType==0xFF) + { ++ CHECK_LOD_MEM_BLOCK_SIZE(BaseOffset + SegmentLength); ++ CHECK_OUTBUF_MEM_BLOCK_SIZE(ftcp + SegmentLength); + memcpy(reinterpret_cast(ret->pixels)+ftcp, FDef + BaseOffset, SegmentLength); + BaseOffset+=SegmentLength; + } + else + { ++ CHECK_OUTBUF_MEM_BLOCK_SIZE(ftcp + SegmentLength); + memset(reinterpret_cast(ret->pixels)+ftcp, SegmentType, SegmentLength); + } + ftcp += SegmentLength; +@@ -260,6 +308,7 @@ + + case 2: + { ++ CHECK_LOD_MEM_BLOCK_SIZE(BaseOffsetor+2); + BaseOffset = BaseOffsetor + SDL_SwapLE16(read_unaligned_u16(FDef + BaseOffsetor)); + + for (unsigned int i=0;i(ret->pixels)+ftcp, &FDef[BaseOffset], value); + ftcp += value; + BaseOffset += value; + } + else + { ++ CHECK_OUTBUF_MEM_BLOCK_SIZE(ftcp + value); + memset(reinterpret_cast(ret->pixels)+ftcp, code, value); + ftcp += value; + } +@@ -304,6 +357,7 @@ + { + for (unsigned int i=0;i0) + ftcp += LeftMargin; +@@ -312,6 +366,7 @@ + + do + { ++ CHECK_LOD_MEM_BLOCK_SIZE(BaseOffset+1); + SegmentType=FDef[BaseOffset++]; + unsigned char code = SegmentType / 32; + unsigned char value = (SegmentType & 31) + 1; +@@ -321,12 +376,15 @@ + + if(code==7) + { ++ CHECK_LOD_MEM_BLOCK_SIZE(BaseOffset + len); ++ CHECK_OUTBUF_MEM_BLOCK_SIZE(ftcp + len); + memcpy((ui8*)ret->pixels + ftcp, FDef + BaseOffset, len); + ftcp += len; + BaseOffset += len; + } + else + { ++ CHECK_OUTBUF_MEM_BLOCK_SIZE(ftcp + len); + memset((ui8*)ret->pixels + ftcp, code, len); + ftcp += len; + } +@@ -345,6 +403,7 @@ + break; + + default: ++ tlog1<<"getSprite: Unknown sprite format."<< std::endl; + throw std::string("Unknown sprite format."); + break; + } +@@ -365,9 +424,12 @@ + + CDefHandler * CDefHandler::giveDef(const std::string & defName) + { ++ tlog0<<"giveDef " << defName <giveFile(defName, FILE_ANIMATION); +- if(!data) +- throw "bad def name!"; ++ if(!data) { ++ tlog0<<"Bad def name: " << defName <openFromMemory(data, defName); + delete [] data; Index: client/GUIBase.h =================================================================== ---- client/GUIBase.h (revision 2178) +--- client/GUIBase.h (revision 2183) +++ client/GUIBase.h (working copy) @@ -546,6 +546,8 @@ CGuiHandler(); diff --git a/project/jni/boost/include/boost/config/user.hpp b/project/jni/boost/include/boost/config/user.hpp index 5b7f5a410..370b28cbd 100644 --- a/project/jni/boost/include/boost/config/user.hpp +++ b/project/jni/boost/include/boost/config/user.hpp @@ -14,13 +14,13 @@ // // Android defines -#define BOOST_THREAD_LINUX 1 -#define BOOST_HAS_PTHREADS 1 +// #define BOOST_THREAD_LINUX 1 // defined in thread/detail/platform.hpp +// #define BOOST_HAS_PTHREADS 1 // defined in config/posix_features.hpp #define __arm__ 1 #define _REENTRANT 1 #define _GLIBCXX__PTHREADS 1 -#define BOOST_HAS_GETTIMEOFDAY 1 -#define BOOST_HAS_UNISTD_H 1 +// #define BOOST_HAS_GETTIMEOFDAY 1 // defined in config/posix_features.hpp +// #define BOOST_HAS_UNISTD_H 1 // defined in config/platform/linux.hpp #define BOOST_INTERPROCESS_POSIX_PROCESS_SHARED 1 // define this to locate a compiler config file: diff --git a/project/jni/vcmi b/project/jni/vcmi new file mode 120000 index 000000000..f9de72653 --- /dev/null +++ b/project/jni/vcmi @@ -0,0 +1 @@ +application/vcmi \ No newline at end of file