Android Studio 3内嵌汇编编译报错求助:sub指令无大小后缀问题
解决Android NDK汇编中
sub指令缺少size后缀的错误 这个错误的核心原因是Clang在Thumb指令集模式下要求算术指令明确指定操作数宽度,而你的配置或指令写法没有满足这个要求。结合你使用的NDK 17和armeabi-v7a目标,这里有几个可行的解决方案:
方案1:强制函数使用ARM指令集编译
如果你不想修改汇编指令,可以给包含汇编的函数添加属性,强制编译器用ARM模式编译该函数,这样就不需要给sub加后缀了:
#include <android/log.h> #define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG, "ThreadTest", __VA_ARGS__) __attribute__((target("arm"))) void* thread_one(void* arg){ LOGD("Thread 1"); __asm__ __volatile__("sub r0, r0, r1"); return NULL; // 补充返回值,避免编译警告 }
方案2:正确配置CMake使用ARM模式(全局)
你之前添加的-DANDROID_ARM_MODE=arm需要确保配置正确,完整的externalNativeBuild.cmake配置应该是这样:
android { defaultConfig { ndk { abiFilters 'armeabi-v7a' // 只保留需要的ABI,x86不需要的话可以去掉 } externalNativeBuild { cmake { arguments '-DANDROID_TOOLCHAIN=clang', '-DANDROID_ABI=armeabi-v7a', '-DANDROID_ARM_MODE=arm' // 强制生成ARM 32位指令 } } } }
配置后重新同步项目并清理构建缓存,这样编译器会生成ARM指令集代码,sub r0, r0, r1就能正常编译。
方案3:适配Thumb指令集的正确写法
如果要保留Thumb模式,需要给sub指令添加宽度后缀。注意subw是针对64位的,32位Thumb-2应该用sub.w(小写w也可以):
void* thread_one(void* arg){ LOGD("Thread 1"); __asm__ __volatile__("sub.w r0, r0, r1"); return NULL; }
另外要确保你的目标ABI是armeabi-v7a(支持Thumb-2),x86的话汇编指令完全不同,需要单独处理。
额外注意点
- 你的函数没有返回值,C语言中
void*类型的函数必须返回指针,建议补充return NULL;避免编译警告。 - 清理构建缓存:Android Studio中点击
Build -> Clean Project,再Rebuild Project,确保旧的配置被清除。
内容的提问来源于stack exchange,提问作者Xudong Shao
相关产品推荐
相关产品推荐

