内核中高级语法和特殊数据结构

153 阅读2分钟

携手创作,共同成长!这是我参与「掘金日新计划 · 8 月更文挑战」的第2天,点击查看活动详情

内核中高级语法和特殊数据结构

attribute GNU C 的一大特色就是__attribute__ 机制。attribute 可以设置函数属性(Function Attribute )、变量属性(Variable Attribute )和类型属性(Type Attribute )。

#书写特征是:前后都有两个下划线,并切后面会紧跟一对原括弧,括弧里面是相应的__attribute__ 参数。

 __attribute__ 

#语法格式为:

 __attribute__ ((attribute-list))

示例代码:

Learning_set/Language/c++/c at master · EVAcacia/Learning_set · GitHub

static void __attribute__((constructor)) do_qemu_init_ ## function(void)    \
{                                                                           \
    register_module_init(function, type);                                   \
}

如果函数被设定为constructor属性,则该函数会在main()函数执行之前被自动的执行;

若函数被设定为destructor属性,则该函数会在main()函数执行之后或者exit()被调用后被自动的执行。

解析:

1.暂定

__read_mostly的使用 定义:

#define __read_mostly attribute((section(".data..read_mostly"))) 1 使用:

static unsigned int d_hash_shift __read_mostly;

1 也就是说被__read_mostly 形容的数据别放入到了段. data.read_mostly 中

那这个段的作用是什么呢?

定义到这个段的数据,再 linux 内核被加载时,数据会自动被存放到 cache 中,以提高整个系统的执行效率。另一方面,如果所在的平台没有 cache,或者有 cache,但是并没有提供存放数据的接口 (也就是不允许人工放置数据在 cache 中),这样定义为__ead_mostly 类型的数据将不能存放在 linux 内核中,甚至也不能被加载到系统内存去执行,将造成 linux 内核启动失败。

当不能存放数据时,解决方法:

1,修改 inclue/asm/cache.h 中的__read_mostly 定义为空的,如:__

__define __read_mostly 

2,修改 arch/mips/kernel/vmlinux.s,将. data.read_mostly 段的位置定义到实际内存空间中去。

c语言的可变参数

int func(int, ... ) 
{
   .
   .
   .
}

int main()
{
   func(2, 2, 3);
   func(3, 2, 3, 4);
}

使用 int 参数和 va_start 宏来初始化 va_list 变量为一个参数列表。

使用 va_arg 宏和 va_list 变量来访问参数列表中的每个项。

使用宏 va_end 来清理赋予 va_list 变量的内存。

#include <stdio.h>
#include <stdarg.h>

double average(int num,...)
{

    va_list valist;
    double sum = 0.0;
    int i;

    /* 为 num 个参数初始化 valist */
    va_start(valist, num);

    /* 访问所有赋给 valist 的参数 */
    for (i = 0; i < num; i++)
    {
       sum += va_arg(valist, int);
    }
    /* 清理为 valist 保留的内存 */
    va_end(valist);

    return sum/num;
}

int main()
{
   printf("Average of 2, 3, 4, 5 = %f\n", average(4, 2,3,4,5));
   printf("Average of 5, 10, 15 = %f\n", average(3, 5,10,15));
}