嵌入式开发过程中结构体字节对齐问题pragma pack(1)
一、引言
曾经刚入门嵌入式在开发一个应用时,用到了自定义结构体,底层嵌入式单片机运行该结构体没问题,但是在Qt开发应用软件对接协议时,一直通不过,仔细分析才发现是QT这边的结构体字节并没有按照单字节对齐,后来在定义结构体时,增加了宏定义,强迫该结构体按照单字节对齐的方式进行编译,即可解决问题。
二、问题描述
假设有一个结构体,包含5字节头,一个字长度的负载,和一个字节的尾,例如:
typedef struct
{char head[5];unsigned short value;char endFlag;
}CMD_TypeDef;CMD_TypeDef TCMD;
很明显,这个结构体的字节大小为5+2+1=8字节,但是用sizeof对各个域进行测试,发现总共的字节数并不是8,测试代码如下:
qDebug()<<"size"<<QString::number(sizeof(TCMD.head));
qDebug()<<"size"<<QString::number(sizeof(TCMD.value));
qDebug()<<"size"<<QString::number(sizeof(TCMD.endFlag));
qDebug()<<"size"<<QString::number(sizeof(TCMD));
打印结果为:
size "5"
size "2"
size "1"
size "10"
进一步地,对这个结构体进行赋值,用并串口发出去该结构体的具体数据:
TCMD={{'A','T','+','D','='},10,0x0A};
port->write(( char*) &TCMD,sizeof(TCMD));
串口收到的数据为:41 54 2B 44 3D 1A 0A 00 0A 00
明显看到数据多了1A 和 00.
三、问题分析
从上面的串口收到结果来看,TCMD第一个成员head 变成了6字节【41 54 2B 44 3D 1A】,TCMD的成员endflag变成了2字节【0A 00】,结构体TCMD成员占用的内存分别是 6+2+2=10字节。
QT中定义的结构体在对成员进行内存分配时,往往按照“N”字节对齐的方式,即所有内容按照N字节的方式进行占用内存,如果剩余的内容占不满N字节,则N字节剩下的字节仍然给该结构成员,新的成员重新从下一个N字节进行对齐。
以上面的例子来说,显然N=2,即机构体按照2字节进行对齐,TCMD的头部head占5字节,需要占用3个N=6字节,负载value等于2字节,刚好占用一个N,而尾部endflag占用1字节,不足N,仍然需要占用一个N。
四、解决方法
既然QT编译系统对结构体按照N字节对齐,那么能否根据需要指定对齐的N数呢,其实C语言提供了这种操作,采用宏定义:
#pragram pack(N)
......//结构体定义内容
#pragram pack()
即可指定该定义的结构体内存对齐方式。
具体地,上述问题可以这样解决:
#pragram pack(1)
typedef struct
{char head[5];unsigned short value;char endFlag;
}CMD_TypeDef;
#pragram pack()CMD_TypeDef TCMD;
结构体定义的时候加上:#pragma pack(1)
定义结束部分结尾 #pragma pack()即可。
嵌入式开发过程中结构体字节对齐问题pragma pack(1)相关推荐
- 结构体字节对齐详解【含实例】
一.前言 结构体字节对齐属于老生常谈的问题,看似简单,却很容易忘记.而且因为结构体使用的普遍性,使得字节对齐也成为了一个不得不谈的话题. 二.什么是结构体字节对齐 假设现在有一个结构体如下,问你它的一 ...
- 指定结构体字节对齐方式
指定结构体字节对齐方式 #pragma pack(push,1) typedef struct { int b; char a; }struct_t1; #pragma pack(pop)
- 结构体字节对齐(转)
结构体字节对齐 在用sizeof运算符求算某结构体所占空间时,并不是简单地将结构体中所有元素各自占的空间相加,这里涉及到内存字节对齐的问题.从理论上讲,对于任何变量的访问都可以从任何地址开始访问,但是 ...
- 一文了解结构体字节对齐
结构体字节对齐详解 表述如有不正确的地方,欢迎批评指正. C++/C 常见的基本数据类型: bool short (short int) int long (long int) long long ( ...
- mysql字节对齐_结构体字节对齐(转)
结构体字节对齐 在用sizeof运算符求算某结构体所占空间时,并不是简单地将结构体中所有元素各自占的空间相加,这里涉及到内存字节对齐的问题.从理论上讲,对于任何变量的访问都可以从任何地址开始访问,但是 ...
- C语言结构体字节对齐
默认字节对齐 C语言结构体字节对齐是老生常谈的问题了,也是高频面试题,现在我们来深入研究这个问题,彻底弄懂到底是怎么回事,给你一个结构体定义和平台机器位数就能手动计算出结构体占用字节数,现在我们不 ...
- C语言结构体字节对齐规则
C语言结构体字节对齐规则 基本规则 规则1 :结构体(struct)的数据成员,第一个数据成员放在offset为0的地方,以后每个数据成员存放在offset为该数据成员大小的整数倍的地方(比如int在 ...
- c/c++下取消结构体字节对齐方法
c/c++下取消结构体字节对齐方法 在c/c++下编译器会默认地对结构体进行对齐,其对齐的方法跟平台具体的特性有关,本文主要介绍结构体不进行对齐的方法. 1.结构体字节不进行对齐的用途 (1).减小内 ...
- 整数边界对齐方式_c中结构体边界对齐(转)
c中结构体边界对齐(转) 2011-11-23 11:15:52| 分类: C&C++ | 标签: |字号大中小 C语言结构体对齐也是老生常谈的话题了.基本上是面试题的必考题.结构体到底怎 ...
最新文章
- CVPR2019:无人驾驶3D目标检测论文点评
- mysql rand()产生随机整数范围及方法
- 我们常用的撤销和恢复功能,你知道它们使用了什么设计模式吗?
- [转]计算机学习道路
- POJ1321(DFS)
- Redis之Pipeline(管道)
- csdn markdown 的使用
- 网传快手大幅度裁员30%
- 拓端tecdat|用R语言和python进行社交网络中的社区检测
- C#可空类型(Nullable)
- java即时聊天系统_基于Java技术的即时聊天系统实现(含源文件).doc
- 苏联W ndows视频,俄罗斯大神win10精简版32位
- 给想上MIT的牛学生说几句
- opencv python 巡线 最小二乘法
- VScode写Go代码引用的包报错飘红
- 2019年,大前端技术趋势程度解读
- 宏定义 指针 c语言,C语言宏定义讲解(C和指针 笔记)
- python简单笔试题_python编程简单笔试题
- python 黑白棋_python实现翻转棋游戏(othello)
- ISP算法介绍--------super Good
热门文章
- string和byte[]的相互转换
- 深度学习修炼(三)——自动求导机制
- 【51单片机快速入门指南】4.3.2: MPU6050:一阶互补滤波、二阶互补滤波和卡尔曼滤波获取欧拉角
- Linux 系统应用编程——网络编程(常用命令解析)
- PHP中全局变量的使用global和$GLOBALS[]
- 如何查看服务器当前的负载信息
- 为Ubuntu Server 安装图形桌面环境
- 为什么你应该使用OpenGL而不是DirectX?
- 对话框找不到WM_ERASEBKGND消息的解决方法与对话框背景图片的载入方法
- 安卓App报错:android.os.FileUriExposedException