为什么同样的C代码在arm64-v8a可以跑,在armeabi-v7a会奔溃?
文章目录
- 背景
- 过程
- 第一个坑
- 第二个坑
- arm64-v8a 和 armeabi-v7a的区别
- 实例
- 64位,Android设备CPU:arm64-v8a
- 32位,Android设备CPU:armeabi-v7a
- 基本数据类型在32位和64位的区别
- 指针长度在32位和64位的区别
- 其他可能性
- chatgpt回答参考
背景
使用NDK开发项目的一个安全库的时候,踩了一个坑。在这里做一个记录和总结,避免以后重复踩坑。
需求:开发安全库,用作密钥加密解密,体系位非对称密钥体系。
经历:使用的是合作公司提供的C源码,通过JNI接入C代码,提供给Java层调用。
过程
第一个坑
运行的时候Android stduio显示列链接错误,怀疑是CMake的问题。新建一个test.c和test.h可以正常运行。发现是C源码里面没有加上:
#ifdef __cplusplus
extern "C"
{
#endif
//c代码声明
#ifdef __cplusplus
};
#endif
导致C++链接时候和C的符号对不上,链接失败,坑的地方在于编译器没有提示这个问题。只能这样试出来。
第二个坑
前面几个接口可以正常运行,中间某个接口不能打印,程序不崩溃,只是不能打印。
同样的代码在Linux设备可以正常运行。
debug进去C源码里面进行代码review和数据观察分析,发现里面定义了long 、long long之类的变量。每次在某些循环操作里面断开debug。没能找出原因。
在代码里面加上数据打印,在怀疑的代码段加上大量的打印日志,观察数据是否越界。数据太多,也发现也没有越界导致crash。
调试和思路了半天,没有思路了。那另外一台机器来跑一下,bingo!
居然可以正常打印结果值了。
首先第一件想到的是,可能是cpu架构不同导致的。
第一台机器是arm64-v8a,第二台测试正常的cpu是armeabi-v7a。
好吧,他们的区别是一台是64位,一台是32位。
怀疑就是不同位数cpu里面数据长度不同导致的。
arm64-v8a 和 armeabi-v7a的区别
在Android开发中,arm64-v8a
和 armeabi-v7a
是两种不同的CPU架构。arm64-v8a
适用于64位ARM处理器,而 armeabi-v7a
适用于32位ARM处理器。
先来跑一个实例看看。
实例
void print64And32(){//写一个代码32位机器上运行时,输出sizeof(指针)的结果是多少,64位机器上运行时,输出sizeof(指针)的结果是多少?LOGD("sizeof(int) = %d\n", sizeof(int));LOGD("sizeof(long) = %d\n", sizeof(long));LOGD("sizeof(long long) = %d\n", sizeof(long long));LOGD("sizeof(char) = %d\n", sizeof(char));LOGD("sizeof(float) = %d\n", sizeof(float));LOGD("sizeof(double) = %d\n", sizeof(double));LOGD("sizeof(void *) = %d\n", sizeof(void *));LOGD("sizeof(char *) = %d\n", sizeof(char *));LOGD("sizeof(int *) = %d\n", sizeof(int *));LOGD("sizeof(long *) = %d\n", sizeof(long *));LOGD("sizeof(long long *) = %d\n", sizeof(long long *));LOGD("sizeof(float *) = %d\n", sizeof(float *));LOGD("sizeof(double *) = %d\n", sizeof(double *));}
64位,Android设备CPU:arm64-v8a
sizeof(int) = 4
sizeof(long) = 8
sizeof(long long) = 8
sizeof(char) = 1
sizeof(float) = 4
sizeof(double) = 8
sizeof(void *) = 8
sizeof(char *) = 8
sizeof(int *) = 8
sizeof(long *) = 8
sizeof(long long *) = 8
sizeof(float *) = 8
sizeof(double *) = 8
32位,Android设备CPU:armeabi-v7a
sizeof(int) = 4
sizeof(long) = 4
sizeof(long long) = 8
sizeof(char) = 1
sizeof(float) = 4
sizeof(double) = 8
sizeof(void *) = 4
sizeof(char *) = 4
sizeof(int *) = 4
sizeof(long *) = 4
sizeof(long long *) = 4
sizeof(float *) = 4
sizeof(double *) = 4
基本数据类型在32位和64位的区别
从上述实测可以知道,在32位机器上,基本数据类型的大小如下:
int
:4字节long
:4字节long long
:8字节char
:1字节float
:4字节double
:8字节
在64位机器上,基本数据类型的大小如下:
int
:4字节long
:8字节long long
:8字节char
:1字节float
:4字节double
:8字节
需要注意的是,指针的大小在32位和64位机器上都是相同的,都是8字节。
指针长度在32位和64位的区别
32位机器上运行时,输出sizeof(指针)的结果是4。
64位机器上运行时,输出sizeof(指针)的结果是8。
其他可能性
-
架构相关的问题: 你的应用程序可能包含了特定于
arm64-v8a
架构的代码,而这段代码在armeabi-v7a
上无法正确运行。确保你的应用程序中没有架构相关的问题,并且所有的本地代码都是通用的。 -
依赖库问题: 如果你的应用程序使用了本地库(例如C/C++库),这些库可能是特定于
arm64-v8a
的。确保你的应用程序包含适用于armeabi-v7a
的版本的这些库。 -
指令集兼容性:
arm64-v8a
使用ARMv8-A指令集,而armeabi-v7a
使用ARMv7-A指令集。确保你的应用程序中的本地代码对目标指令集是兼容的。 -
ABI Filters: 在你的
build.gradle
文件中,可能设置了 ABI Filters,导致只有arm64-v8a
被打包到 APK 中。检查你的构建配置,确保包含了armeabi-v7a
的支持。
chatgpt回答参考
当你的 C 代码在 32 位处理器上能够正常运行,但在 64 位处理器上出现问题时,可能有一些常见的原因:
-
指针大小和类型问题: 64 位处理器上的指针大小为 8 字节,而在 32 位处理器上为 4 字节。如果你的代码中存在对指针大小的假设或者类型转换问题,可能导致在 64 位系统上出现问题。请确保你的代码对指针操作和类型大小有正确的处理。
-
整数溢出: 如果你的代码依赖于特定的整数大小,可能会在 64 位系统上溢出。在 64 位系统上,
int
类型仍然是 32 位,但long
类型变为 64 位。确保你的代码中没有整数溢出的问题。 -
对齐问题: 在 64 位系统上,对齐要求可能更加严格。如果你的代码依赖于特定的数据结构对齐方式,确保你的结构体或变量的对齐方式是正确的。
-
未初始化变量: 64 位系统上的内存布局可能与 32 位系统不同。确保你的代码中所有的变量都被正确初始化,以防止使用未初始化的内存。
-
依赖的库或第三方代码: 如果你的代码依赖于特定的库或第三方代码,确保这些库在 64 位系统上是兼容的。有时,问题可能并不是在你的代码中,而是在你依赖的库中。
-
汇编语言代码: 如果你的代码包含了汇编语言部分,确保这些汇编语言代码是对 64 位系统的正确支持。
总体而言,要确保 C 代码能够在 64 位处理器上正确运行,需要注意 32 位和 64 位系统之间的差异,并确保代码中没有与平台相关的假设。最好的做法是使用编译器提供的宏来处理不同平台的区别,以确保代码的可移植性。
相关文章:
为什么同样的C代码在arm64-v8a可以跑,在armeabi-v7a会奔溃?
文章目录 背景过程第一个坑第二个坑 arm64-v8a 和 armeabi-v7a的区别实例64位,Android设备CPU:arm64-v8a32位,Android设备CPU:armeabi-v7a 基本数据类型在32位和64位的区别指针长度在32位和64位的区别 其他可能性chatgpt回答参考 背景 使用NDK开发项目的…...
C++初学者线路图 23年12月
高精度计算 1. 高精度加减法 高精度加减法课程(12月1日~12月4日)高精度加减法配套程序(12月5日~12月6日) 2. 高精度乘法 高精度乘法课程(12月7日~12月10日)高精度乘法…...
Day37| Leetcode 738. 单调递增的数字
今天就一个题目,做完吃完饭抓紧做六级试题。 Leetcode 738. 单调递增的数字 题目链接 738 单调递增的数字 本题目思路还是比较巧妙的,对于98,一旦出现strNum[i - 1] > strNum[i]的情况(非单调递增),首…...

【工具分享】| 阅读论文神器 使用技巧 AI润色 AI翻译
文章目录 1 使用技巧1.1 功能一 即时翻译1.2 功能二 文献跳转1.3 功能三 多设备阅读1.4 功能四 小组讨论笔记共享1.5 功能五 个人文献管理 2 其他功能 超级喜欢Readpaper这一款论文阅读软件,吹爆他哈哈 为什么? 当然是他可以解决我们传统阅读论文的种种…...
String.prototype.match进行==判断
今天发现一个String.prototype.match的奇葩用法 export const isWeChat (() > {let ua window.navigator.userAgent.toLowerCase();return ua.match(/MicroMessenger/i) "micromessenger"; })();这是我在网站上找到的一个判断是否是微信浏览器的方法ÿ…...
less 笔记
<link rel"stylesheet/less" type"text/css" href"styles.less" /> <script src"https://cdn.jsdelivr.net/npm/less4" ></script>变量(Variables) 原生已支持 --前缀定义属性 var() 函数获取…...

Java中的异常你了解多少?
目录 一.认识异常二.异常分类三.异常的分类1.编译时异常2.运行时异常 四.异常的处理1.LYBL:事前防御型2.EAFP:事后认错型 五.异常的抛出Throw注意事项 六.异常的捕获1.异常的捕获2.异常声明throws3.try-catch捕获并处理 七.自定义异常 一.认识异常 在Jav…...

查找算法及哈希表
1 二分查找 1.1 重要概念 拟解决的问题:判断某个区间是否包含某个元素,无法确定区间中包含重复元素的具体位置;使用条件:查找的区间必须符合单调性;本质:采用分治思想,将某个单调区间一分为二…...

ELK分布式日志管理平台部署
目录 一、ELK概述 1、ELK概念: 2、其他数据收集工具: 3、ELK工作流程图: 4、ELK 的工作原理: 5、日志系统的特征: 二、实验部署: 1、ELK Elasticsearch 集群部署 2、安装 Elasticsearch-head 插件 …...

四、虚拟机网络配置
目录 1、VMware网卡配置模式 1.1 桥接模式 1.2 NAT模式 1.3 仅主机模式 2、编辑虚拟机的网络编辑器 3、编辑Window的虚拟网卡 4、修改IP地址为静态 4.1 查看网卡名字 4.2 编辑修改网卡IP地址的配置文件 4.3 重启网络: 4.…...

四、Lua循环
文章目录 一、while(循环条件)二、for(一)数值for(二)泛型for(三)repeat util 既然同为编程语言,那么控制逻辑里的循环就不能缺少,它可以帮助我们实现有规律的重复操作,而…...

生成对抗网络(GAN)手写数字生成
文章目录 一、前言二、前期工作1. 设置GPU(如果使用的是CPU可以忽略这步) 二、什么是生成对抗网络1. 简单介绍2. 应用领域 三、网络结构四、构建生成器五、构建鉴别器六、训练模型1. 保存样例图片2. 训练模型 七、生成动图 一、前言 我的环境࿱…...

LeetCode Hot100 31.下一个排列
题目: 整数数组的一个 排列 就是将其所有成员以序列或线性顺序排列。 例如,arr [1,2,3] ,以下这些都可以视作 arr 的排列:[1,2,3]、[1,3,2]、[3,1,2]、[2,3,1] 。 整数数组的 下一个排列 是指其整数的下一个字典序更大的排列…...

Redis主从与哨兵架构详解
目录 主从架构 主从环境搭建 主从复制流程 1. 全量复制 2. 部分复制 主从风暴 哨兵架构 概念 哨兵环境搭建 主从架构 主从环境搭建 1. 复制一份redis.conf文件, 修改下面几行配置 port 6380 pidfile /var/run/redis_6380.pid logfile "6380.log" dir /usr/…...

Linux:docker的数据管理(6)
数据管理操作*方便查看容器内产生的数据 *多容器间实现数据共享 两种管理方式数据卷 数据卷容器 1.数据卷 数据卷是一个供容器使用的特殊目录,位于容器中,可将宿主机的目录挂载到数据卷上,对数据卷的修改操作立刻可见,并且更新数…...

深入理解Zookeeper系列-1.初识Zoookeeper
👏作者简介:大家好,我是爱吃芝士的土豆倪,24届校招生Java选手,很高兴认识大家📕系列专栏:Spring源码、JUC源码、Kafka原理、分布式技术原理🔥如果感觉博主的文章还不错的话ÿ…...

芯片技术探索:了解构芯片的设计与制造之旅
芯片技术探索:了解构芯片的设计与制造之旅 一、引言 随着现代科技的飞速发展,芯片作为信息技术的核心,已经渗透到我们生活的方方面面。从智能手机、电视、汽车到医疗设备和工业控制系统,芯片在各个领域都发挥着至关重要的作用。然而,对于大多数人来说,芯片仍然是一个神秘…...

STM32 超声波模块(HC-SR04)
HC-SR04介绍 典型工作电压:5v (如果你的超声波模块没有工作,可以看一下是不是电压不够)超小静态工作电流:<2mA 感应角度:<15 (超声波模块,是一个范围式的探…...

ELK+Filebeat
Filebeat概述 1.Filebeat简介 Filebeat是一款轻量级的日志收集工具,可以在非JAVA环境下运行。 因此,Filebeat常被用在非JAVAf的服务器上用于替代Logstash,收集日志信息。实际上,Filebeat几乎可以起到与Logstash相同的作用&…...
MySql之锁表、锁行解决方案
查询正在使用的表,没有跑业务,一般情况下是锁表了 show open tables where in_use > 0 ;查看进程,可以看到Command类型(Sleep为阻塞线程) show processlist;kill事务,kill 进程Id kill 8193583;其他 …...

wordpress后台更新后 前端没变化的解决方法
使用siteground主机的wordpress网站,会出现更新了网站内容和修改了php模板文件、js文件、css文件、图片文件后,网站没有变化的情况。 不熟悉siteground主机的新手,遇到这个问题,就很抓狂,明明是哪都没操作错误&#x…...

Opencv中的addweighted函数
一.addweighted函数作用 addweighted()是OpenCV库中用于图像处理的函数,主要功能是将两个输入图像(尺寸和类型相同)按照指定的权重进行加权叠加(图像融合),并添加一个标量值&#x…...
1688商品列表API与其他数据源的对接思路
将1688商品列表API与其他数据源对接时,需结合业务场景设计数据流转链路,重点关注数据格式兼容性、接口调用频率控制及数据一致性维护。以下是具体对接思路及关键技术点: 一、核心对接场景与目标 商品数据同步 场景:将1688商品信息…...
土地利用/土地覆盖遥感解译与基于CLUE模型未来变化情景预测;从基础到高级,涵盖ArcGIS数据处理、ENVI遥感解译与CLUE模型情景模拟等
🔍 土地利用/土地覆盖数据是生态、环境和气象等诸多领域模型的关键输入参数。通过遥感影像解译技术,可以精准获取历史或当前任何一个区域的土地利用/土地覆盖情况。这些数据不仅能够用于评估区域生态环境的变化趋势,还能有效评价重大生态工程…...

mysql已经安装,但是通过rpm -q 没有找mysql相关的已安装包
文章目录 现象:mysql已经安装,但是通过rpm -q 没有找mysql相关的已安装包遇到 rpm 命令找不到已经安装的 MySQL 包时,可能是因为以下几个原因:1.MySQL 不是通过 RPM 包安装的2.RPM 数据库损坏3.使用了不同的包名或路径4.使用其他包…...

推荐 github 项目:GeminiImageApp(图片生成方向,可以做一定的素材)
推荐 github 项目:GeminiImageApp(图片生成方向,可以做一定的素材) 这个项目能干嘛? 使用 gemini 2.0 的 api 和 google 其他的 api 来做衍生处理 简化和优化了文生图和图生图的行为(我的最主要) 并且有一些目标检测和切割(我用不到) 视频和 imagefx 因为没 a…...

无人机侦测与反制技术的进展与应用
国家电网无人机侦测与反制技术的进展与应用 引言 随着无人机(无人驾驶飞行器,UAV)技术的快速发展,其在商业、娱乐和军事领域的广泛应用带来了新的安全挑战。特别是对于关键基础设施如电力系统,无人机的“黑飞”&…...

【网络安全】开源系统getshell漏洞挖掘
审计过程: 在入口文件admin/index.php中: 用户可以通过m,c,a等参数控制加载的文件和方法,在app/system/entrance.php中存在重点代码: 当M_TYPE system并且M_MODULE include时,会设置常量PATH_OWN_FILE为PATH_APP.M_T…...
LOOI机器人的技术实现解析:从手势识别到边缘检测
LOOI机器人作为一款创新的AI硬件产品,通过将智能手机转变为具有情感交互能力的桌面机器人,展示了前沿AI技术与传统硬件设计的完美结合。作为AI与玩具领域的专家,我将全面解析LOOI的技术实现架构,特别是其手势识别、物体识别和环境…...
深度学习之模型压缩三驾马车:模型剪枝、模型量化、知识蒸馏
一、引言 在深度学习中,我们训练出的神经网络往往非常庞大(比如像 ResNet、YOLOv8、Vision Transformer),虽然精度很高,但“太重”了,运行起来很慢,占用内存大,不适合部署到手机、摄…...