《Linux4.0设备驱动开发详解》笔记--第三章:Linux下的C编程特点

来源:互联网 发布:知的笔顺怎么写呀 编辑:程序博客网 时间:2024/05/17 22:26

3.1 Linux编码风格

  • 参考文章:Documentation/CodingStyle
  • 缩进用TAB
  • {}使用:
    • 对于结构体、if、for、while以及switch语句,“{”不另起一行
    • 如果if、for循环后只有1行,不要加“{”和“}”
    • if和else混合用的时候,else语句不另起一行
    • 对于函数,“{”另起一行
  • switch和case对齐

3.2 GNU C与ANSI C

  • 零长度和变量长度数组
struct var_data {    int len;    char data[0]};int main(int argc, char *argv[]){    int i, n = argc;    double x[n];    for(i=0; i<n; i++)        x[i] = i;    return 0;}
  • case范围:支持case x … y这样的语法,区间[x,y]中的数都会满足这个case条件
  • 语句表达式:包含在括号里的语句看成一个表达式,它可以出现在任何允许表达式的地方。
  • typeof关键字:其可以获得x的类型,因此可以借助typedef来定义min这个宏
#define min(x,y) ({    const typeof(x) _x = (x);  \    const typeof(y) _y = (y);  \    (void) (&_x == &_y);       \    _x < _y ? _x : _y;         \})
  • 可变参数宏,标准C就支持可变参数函数,意味着函数的参数是不固定的,如printf()函数,GNU C 中宏也可以接受可变参数目的参数,如
#define pr_debug(fmt,arg...)  \            printf(fmt,##arg)

这里的arg表示其余的参数,可以是零个或多个,##是为了处理arg不代表任何参数的情况,这时候前面的逗号就显得多余了,使用##之后,CNU C 就会预处理会丢掉前面的逗号,这样

pr_debug("success!\n");扩展为:printk("success!\n");
  • 标号元素:允许数组和结构体的元素初始化的顺序任意顺序出现。
    数组初始化方式为在初始化值前添加”[INDEX]=”,或者用”[FIRST … LAST]=”的形式指定一个范围。
unsigned char data[MAX] = {[0 ... MAX] = 0};

结构体初始化方式

struct file_operations ext2_file_operation = {    .llseek = generic_file_llseek,    .read = generic_file_read,    ...};
  • 当前函数名:FUNCTION或者func保存当前函数的名字
  • 特殊属性声明:GUN C允许申明函数、变量和类型的特殊属性,以便手动优化和定制代码检查的方法,申明方法:在申明后加上attribute((ATTRIBUTE)). ATTRIBUTE为属性说明,若存在多个则逗号隔开。
  • 内建函数:不属于标准库的内建函数通常以__builtin开始
  • do{} while语句:其主要用于宏定义中,为了保证宏定义的使用者不会出现编译错误,他不对其他使用则做任何假设。
  • goto语句:一般只限于错误处理中
0 0