当前位置:首页 > 开发 > 编程语言 > 编程 > 正文

结构体中最后一个元素是长度为0的数组

发表于: 2013-03-17   作者:dcj3sjt126com   来源:转载   浏览:
gcc c
摘要: 在Linux源代码中,有很多的结构体最后都定义了一个元素个数为0个的数组,如/usr/include/linux/if_pppox.h中有这样一个结构体: struct pppoe_tag {     __u16 tag_type;     __u16 tag_len;   &n

在Linux源代码中,有很多的结构体最后都定义了一个元素个数为0个的数组,如/usr/include/linux/if_pppox.h中有这样一个结构体: 
struct pppoe_tag { 
    __u16 tag_type; 
    __u16 tag_len; 
    char tag_data[0]; 
} __attribute ((packed));

又如在asterisk的源码中的Pbx.c: 
struct  ast_ignorepat  {  
    const  char  *registrar;  
    struct  ast_ignorepat  *next;  
    char  pattern[0];  
};   
  
结构体最后的长度为0的数组是GCC中广泛使用技巧,常用来构成可变长缓冲区。 
在创建时,malloc一段结构体大小加上可变长数据长度的空间给它:malloc(sizeof(struct  pppoe_tag)+  buff_len),可变长部分按数组访问方式访问;释放时,直接把整个结构体free掉就可以了。

例子如下: 
struct pppoe_tag *sample_tag; 
__u16 sample_tag_len = 10; 
sample_tag = (struct pppoe_tag *)malloc( sizeof(struct pppoe_tag) + sizeof(char) * sample_tag_len); 
sample_tag->tag_type = 0xffff; 
sample_tag->tag_len = sample_tag_len; 
sample_tag->tag_data[0]=…. 

释放时: 
free(sample_tag)

这样的好处有两个:  
一次分配解决问题,省了不少麻烦。为了防止内存泄漏,如果是分两次分配(结构体和缓冲区),那么要是第二次malloc失败了,必须回滚释放第一个分配的结构体。这样带来了编码麻烦。

其次,分配了第二个缓冲区以后,如果结构里面用的是指针,还要为这个指针赋值。同样,在free这个buffer的时候,用指针也要两次free。而且小内存的管理是非常困难的,如果用指针,这个buffer的struct部分就是小内存了,在系统内存在多了势必严重影响内存管理的性能。要是用空数组把struct和实际数据缓冲区一次分配大块问题,就没有这个问题。

所以,结构体最后使用0或1的长度数组的原因,主要是为了方便的管理内存缓冲区,如果你直接使用指针而不使用数组,那么,你在分配内存缓冲区时,就必须分配结构体一次,然后再分配结构体内的指针一次,(而此时分配的内存已经与结构体的内存不连续了,所以要分别管理即申请和释放)而如果使用数组,那么只需要一次就可以全部分配出来;反过来,释放时也是一样,使用数组,一次释放,使用指针,得先释放结构体内的指针,再释放结构体。还不能颠倒次序。

这个技巧其实就是分配一段连续的的内存,减少内存的碎片化。在Linux操作系统开发或者嵌入式开发,这种技巧尤其常见。

PS:某些编译器不支持长度为0的数组的定义,在这种情况下只要将它定义成char tag_data[1],使用方法相同。

结构体中最后一个元素是长度为0的数组

  • 0

    开心

    开心

  • 0

    板砖

    板砖

  • 0

    感动

    感动

  • 0

    有用

    有用

  • 0

    疑问

    疑问

  • 0

    难过

    难过

  • 0

    无聊

    无聊

  • 0

    震惊

    震惊

编辑推荐
前面在看Xen的源码时,遇到了一段代码,如下所示: 注意上面最后一行的代码,这里定义了一个长度为
前面在看Xen的源码时,遇到了一段代码,如下所示: 注意上面最后一行的代码,这里定义了一个长度为
前面在看Xen的源码时,遇到了一段代码,如下所示: 注意上面最后一行的代码,这里定义了一个长度为
题目 一个大小为n的数组,里面的数都属于范围[0, n-1],有不确定的重复元素,找到至少一个重复元素
./* *程序的版权和版本声明部分 * Copyright (c)2012, 烟台大学计算机学院学生 .* All rightsreserv
/* * 程序的版权和版本声明部分 * Copyright (c)2013, 烟台大学计算机学院学生 * All rightsreserve
/* * 程序的版权和版本声明部分 * Copyright (c)2013, 烟台大学计算机学院学生 * All rightsreserve
/* * 程序的版权和版本声明部分 * Copyright (c)2013, 烟台大学计算机学院学生 * All rightsreserve
/* * 程序的版权和版本声明部分: * Copyright (c) 2013, 烟台大学计算机学院 * All rights reserved
/* * 程序的版权和版本声明部分 * Copyright (c)2012, 烟台大学计算机学院学生 * All rightsreserve
版权所有 IT知识库 CopyRight © 2009-2015 IT知识库 IT610.com , All Rights Reserved. 京ICP备09083238号