我希望以 VFP Android 设备为目标 ARMv6。
我的Android.mk
文件中有以下行可以启用VFP
LOCAL_CFLAGS := -marm -mfloat-abi=softfp -mfpu=vfp -Wmultichar
我相信我的目标ARMv5
是VFP
.
我编辑android-ndk-r8b\toolchains\arm-linux-androideabi-4.6\setup.mk
删除-msoft-float
. 我也试过原版setup.mk
我的代码在 99.99% 的情况下都可以正常工作,但有时在 ARMv6 设备上会发疯。我有特殊的代码来检测它何时发疯。
代码
glm::vec3 D = P1 - P2;
float f1 = sqrtf(D.x*D.x + D.y*D.y + D.z*D.z);
if(!(f1 < 5)){
// f1 is bigger then 5 or NaN
mylog_fmt("Crazy %f %f %f %f", P1.x, P1.y, P1.z, f1);
mylog_fmt("%f %f %f", P2.x, P2.y, P2.z);
}
日志猫:
12-14 00:59:08.214: I/APP(17091): Crazy -20.000031 0.000000 0.000000 20.000000
12-14 00:59:08.214: I/APP(17091): -20.000000 0.000000 0.000000
它计算2点之间的距离。通常它是 0.000031 但是当crazy mode
它是 20.0
当我在 ARMv7 CPU 上运行它时,问题不存在。它仅存在于 ARMv6 CPU 上。
我相信它应该是一些与编译器设置或版本相关的常见已知错误。可能是代码缺少内存屏障。
我希望看到一些对类似错误的参考。解决它的方法。或关于错误的性质。
当 ARMv7 上的相同代码不给出 NaN 时,我也经常在 ARMv6 上得到 NaN 值。
我已经调试了 2 周的代码并在网上搜索。如果有人可以分享类似问题的链接,那将是一个很大的帮助!
PS。这是编译命令之一的示例。我已经尝试了许多不同的设置。
编译器设置
c:/soft/Android/android-ndk-r8b/toolchains/arm-linux-androideabi-4.6/prebuilt/windows/bin/arm-linux-androideabi-g++
-MMD -MP -MF ./obj/local/armeabi/objs/main/sys/base.o.d -fpic -ffunction-sections -funwind-tables -fstack-protector
-D__ARM_ARCH_5__ -D__ARM_ARCH_5T__ -D__ARM_ARCH_5E__
-D__ARM_ARCH_5TE__
-march=armv5te -mtune=arm6
-mfloat-abi=softfp -mfpu=vfp
-fno-exceptions -fno-rtti -mthumb -Os -fomit-frame-pointer -fno-strict-aliasing -finline-limit=64
-Ijni/main/ -Ijni/main/sys -Ijni/main/bullet/src -Ijni/main/bullet/src/LinearMath -Ijni/main/bullet/src/BulletCollision/BroadphaseCollision
-Ijni/main/bullet/src/BulletCollision/CollisionDispatch -Ijni/main/bullet/src/BulletCollision/CollisionShapes -Ijni/main/bullet/src/BulletCollision/NarrowPhaseCollision
-Ijni/main/bullet/src/BulletDynamics/ConstraintSolver -Ijni/main/bullet/src/BulletDynamics/Dynamics -Ijni/main/../libzip/ -Ic:/soft/Android/android-ndk-r8b/sources/cxx-stl/stlport/stlport
-Ic:/soft/Android/android-ndk-r8b/sources/cxx-stl//gabi++/include -Ijni/main
-DANDROID
-marm -march=armv6 -mfloat-abi=softfp -mfpu=vfp -Wmultichar
-Wa,--noexecstack -frtti -O2 -DNDEBUG -g -Ic:/soft/Android/android-ndk-r8b/platforms/android-5/arch-arm/usr/include -c jni/main/sys/base.cpp
-o ./obj/local/armeabi/objs/main/sys/base.o
更新 2
所有这些设备都有高通 MSM7227A 它有 ARM1136JF-S
到目前为止我了解到的是,该错误可能与de-norms
我在某处读到 ARMv7 与 ARMv6 的差异有关,该差异denorms
默认情况下已刷新为零,而 ARM1136SF-S 可以选择使用它。
http://infocenter.arm.com/help/topic/com.arm.doc.ddi0211k/DDI0211K_arm1136_r1p5_trm.pdf
尚不确定如何验证 ARM 上的 Flush-To-ZERO 标志。
更新 3
这个 CPU 的 VFP 被称为VFP11
I found --vfp11-denorm-fix
option。他们还--vfp-denorm-fix
纠正了VFP11
cpus 中的错误。看起来像我的目标问题。发现一些关于 VFP11 勘误的帖子。希望它能修复代码。