其他分享
首页 > 其他分享> > C的字节对齐和位域操作

C的字节对齐和位域操作

作者:互联网

1、 字节对齐

首先分析字节对齐之前,需要了解概念

  1. 自身对齐:数据结构自身的大小
  2. 指定对齐:编译器或者用户指定的值,例如__attribute__ ((aligned (1))),设置为单字节对齐
  3. 有效对齐:取自身对齐和指定对齐中较小的

分析结构体占用内存大小要看以下两个条件

  1. 对于结构体或者类,要将其补齐为其有效对齐值的整数倍,结构体的有效对齐值是其最大数据成员的自身对齐值
  2. 存放成员的起始地址必须是该成员有效对齐值的整数倍

对于位域操作而言,我们需要关心如下:

a. 位域变量的长度不能大于其类型的长度sizeof(类型) ,例如bit_a中char a:10是不行的
b. 位域可以是无名位域,无名位域只能用作填充或调整位置,不能使用
c. 位域结构体的大小必须是其最长基本类型大小的整数倍sizeof(类型),参见foo4
d. 当一个字节不够放时,可以另起一个字节,也可以有意重新起一个字节,例如如bs
f. 当结构体中有非位域操作时,整个结构体不进行压缩,建test3

例子1:

struct bs     
{     
    unsigned a:4     
    unsigned :0 /*空域*/     
    unsigned b:4 /*从下一单元开始存放*/     
    unsigned c:4     
}

例子2:

struct foo4 {
    char    a : 2;
    char    b : 3;
    int c : 1;
};  //大小为4

2. 位对齐(__attribute__使用)

按照bit位,内存是连续的,配合__attribute__使用,GNU使用__attribute__选项来设置,例如下面例子中,Test1使用一位对齐

  1. attribute ((aligned (n))),按照n字节对齐
  2. attribute ((packed)),对于域是位对齐
#include <stdio.h>
#include <stdlib.h>
typedef struct Test3
{
    char a:1;
    int b:2;
    long c;
}test3;
typedef struct Test2
{
    char a:1;
    int b:2;
    int :1;
}test2;
struct bit{
int a:4; 
int b:4;
char c:4;
char d:4;
}bit1; //默认字节对齐
struct bit_a
{
	char a:5;
	char b:5;
	char c:5;
	char d:5;
	char e:5;
}__attribute__ ((packed)) bit_a1; //位对齐
struct bit_aa
{
	char a;
	int b;

}__attribute__ ((packed)) bit_aa; //位对齐
typedef struct Test1
{
    char a:1;
    short b:2;
}__attribute__ ((aligned (1))) test1; //单字节对齐
int main(int argc, char* argv[])
{

	fprintf(stderr,"%ld\n %ld\n %ld\n %ld\n %ld\n %ld\n",sizeof(test3),sizeof(test2),sizeof(bit1),sizeof(bit_a1),sizeof(bit_aa),sizeof(test1));
	exit(0);

}


~/Videos$ ./io_1
16
 4
 4
 4
 5
 2

标签:__,字节,int,attribute,char,对齐,位域,bit
来源: https://blog.csdn.net/weixin_44537992/article/details/106477059