From ed8724c8bb1a26eb9bf8a9696726fb9f3043ce5c Mon Sep 17 00:00:00 2001 From: pelya Date: Wed, 23 May 2012 16:40:27 +0300 Subject: [PATCH] Another unsuccessful try to get unaligned memory access error in Ballfield --- .../jni/application/ballfield/ballfield.cpp | 83 +++++++++++++------ project/jni/application/ballfield/unaligned.c | 22 ----- project/jni/application/src | 2 +- 3 files changed, 58 insertions(+), 49 deletions(-) delete mode 100644 project/jni/application/ballfield/unaligned.c diff --git a/project/jni/application/ballfield/ballfield.cpp b/project/jni/application/ballfield/ballfield.cpp index a6f9e3877..52b0e41df 100644 --- a/project/jni/application/ballfield/ballfield.cpp +++ b/project/jni/application/ballfield/ballfield.cpp @@ -405,7 +405,48 @@ void tiled_back(SDL_Surface *back, SDL_Surface *screen, int xo, int yo) SDL_BlitSurface(back, NULL, screen, &r); } +#pragma GCC push_options +#pragma GCC optimize ("O0") +extern "C" unsigned misaligned_mem_access(unsigned value, unsigned shift); +unsigned misaligned_mem_access(unsigned value, unsigned shift) +{ + volatile unsigned *iptr = NULL; + volatile char *cptr = NULL; + volatile unsigned ret = 0; + +#if defined(__GNUC__) +# if defined(__i386__) + /* Enable Alignment Checking on x86 */ + __asm__("pushf\norl $0x40000,(%esp)\npopf"); +# elif defined(__x86_64__) + /* Enable Alignment Checking on x86_64 */ + __asm__("pushf\norl $0x40000,(%rsp)\npopf"); +# endif +#endif + + /* malloc() always provides aligned memory */ + cptr = (volatile char *)malloc(sizeof(unsigned) + 10); + + /* Increment the pointer by one, making it misaligned */ + iptr = (volatile unsigned *) (cptr + shift); + + /* Dereference it as an int pointer, causing an unaligned access */ + /* GCC usually tries to optimize this, thus our test succeeds when it should fail, if we remove "volatile" specifiers */ + *iptr = value; + //memcpy( &ret, iptr, sizeof(unsigned) ); + ret = *iptr; + /* + *((volatile char *)(&ret) + 0) = cptr[shift+0]; + *((volatile char *)(&ret) + 1) = cptr[shift+1]; + *((volatile char *)(&ret) + 2) = cptr[shift+2]; + *((volatile char *)(&ret) + 3) = cptr[shift+3]; + */ + free((void *)cptr); + + return ret; +} +#pragma GCC pop_options /*---------------------------------------------------------- main() @@ -414,8 +455,8 @@ void tiled_back(SDL_Surface *back, SDL_Surface *screen, int xo, int yo) extern "C" void unaligned_test(unsigned * data, unsigned * target); extern "C" unsigned val0, val1, val2, val3, val4; -unsigned char data[8] = { 1, 2, 3, 4, 5, 6, 7, 8 }; -//unsigned val0 = 0x12345678, val1 = 0x23456789, val2 = 0x34567890, val3 = 0x45678901, val4 = 0x56789012; +unsigned val0 = 0x01234567, val1, val2, val3; + int main(int argc, char* argv[]) { @@ -558,39 +599,29 @@ int main(int argc, char* argv[]) SDL_BlitSurface(logo, NULL, screen, &r); /* FPS counter */ - if(tick > fps_start + 500) + if(tick > fps_start + 1000) { fps = (float)fps_count * 1000.0 / (tick - fps_start); fps_count = 0; fps_start = tick; - - // This wonderful unaligned memory access scenario still fails on my HTC Evo and ADP1 devices, and even on the Beagleboard. - // I mean - the test fails, unaligned access works - - // UNALIGNED MEMORY ACCESS HERE! However all the devices that I have won't report it and won't send a signal or write to the /proc/kmsg, - // despite the /proc/cpu/alignment flag set. -/* - unsigned * ptr = (unsigned *)(data); - unaligned_test(ptr, &val0); - * ((unsigned *)&ptr) += 1; - unaligned_test(ptr, &val1); - * ((unsigned *)&ptr) += 1; - unaligned_test(ptr, &val2); - * ((unsigned *)&ptr) += 1; - unaligned_test(ptr, &val3); - * ((unsigned *)&ptr) += 1; - unaligned_test(ptr, &val4); -*/ + + *((unsigned char *)(&val0) + 0) += 1; + *((unsigned char *)(&val0) + 1) += 1; + *((unsigned char *)(&val0) + 2) += 1; + *((unsigned char *)(&val0) + 3) += 1; } - print_num(screen, font, screen->w-37, screen->h-12, fps); -/* + // MISALIGNED MEMORY ACCESS HERE! However all the devices that I have won't report it and won't send a signal or write to the /proc/kmsg, + // despite the /proc/cpu/alignment flag set. + val1 = misaligned_mem_access(val0, 1); + val2 = misaligned_mem_access(val0, 2); + val3 = misaligned_mem_access(val0, 3); print_num_hex(screen, font_hex, 0, 40, val0); print_num_hex(screen, font_hex, 0, 60, val1); print_num_hex(screen, font_hex, 0, 80, val2); print_num_hex(screen, font_hex, 0, 100, val3); - print_num_hex(screen, font_hex, 0, 120, val4); - print_num_hex(screen, font_hex, 0, 180, 0x12345678); -*/ + + + print_num(screen, font, screen->w-37, screen->h-12, fps); ++fps_count; for(i=0; i - -extern void unaligned_test2(int x1, int x2, int x3, int x4, int x5, int x6, int x7, unsigned * data, unsigned * target); -extern void unaligned_test(unsigned * data, unsigned * target); -extern unsigned val0, val1, val2, val3, val4; - -unsigned val0 = 1, val1 = 2, val2 = 3, val3 = 4, val4 = 5; - -void unaligned_test2(int x1, int x2, int x3, int x4, int x5, int x6, int x7, unsigned * data, unsigned * target) -{ - int xx = x1 + x2 - x3 + x4 - x5 + x6 - x7; - *target = xx + data[3]; -} - -void unaligned_test(unsigned * data, unsigned * target) -{ - //__android_log_print(ANDROID_LOG_INFO, "Ballfield", "data %p target %p", data, target); - int x1 = *data, x2 = *target, x3 = *data + *target, x4 = *data - *target, x5 = *data - *target * 2, x6 = *data + *target * 2, x7 = *target * 3 + *data; - unaligned_test2(x1, x2, x3, x4, x5, x6, x7, data-3, target); -}; - diff --git a/project/jni/application/src b/project/jni/application/src index 550b7b622..104f796a6 120000 --- a/project/jni/application/src +++ b/project/jni/application/src @@ -1 +1 @@ -openttd \ No newline at end of file +ballfield \ No newline at end of file