Blog icon indicating copy to clipboard operation
Blog copied to clipboard

Chapter 2 Getting Started with the kernel

Open jason--liu opened this issue 5 years ago • 0 comments

内核开发准备

No libc or Standard Headers

为了保证内核运行速度和体积,kernel不会链接标准C库或其他任何库。但是libc常用的一些函数库内核已经实现了,例如字符串处理相关的都在#include <linux/string.h>。内核中不使用printf,而是使用printk函数。例如

printk(KERN_ERR" this is an error\n");

主要KERN_ERR后面没有引号。

GNUC

因为使用GNU C,所有内核中常使用GNU C中的一些扩展。

Inline Functions

static inline void wolf(unsigned long tail_size)

内联函数一般用于函数会被多次调用的场景,节约系统资源,但频繁使用内联函数会使代码边长,从而运行时会占用更多内存,内核函数一般放在头文件中。

Inline Assembly

内联汇编用于偏近底层或对执行时间严格要求的地方。如下

unsigned int low, high;
asm volatile("rdtsc" : "=a" (low), "=d" (high));

Branch Annotation

Linux内核提供了两个宏来优化if分支判断

//预测error发生可能性几乎为0
if(unlikely(error)){
    /*...*/
}
//预测success非常可能发生
if(likely(success)){
    /*...*/
}

No Memory Protection

因为内核是最低层的程序,所以如果内核访问的非法内存,那么整个系统都会挂掉!!所以内核开发的风险比用户程序开发的风险要大。而且,内核中的内存是不分页的,每用一个字节的内存,物理内存就少一个字节。所以内核中使用内存一定要谨慎。

No Use of Floating Float

除非在非常罕见的场景,否则不要在内核中使用浮点数。

Small, Fixed-size Stack

内核栈的大小有编译内核时决定的,对于不用的体系结构,内核栈的大小虽然不一样,但都是固定的。查看内核栈大小的方法:

ulimit -a | grep "stack size"

Synchronization and Concurrency

Linux是多用户的操作系统,所以必须处理好同步和并发操作,防止因竞争而出现死锁。

Importance of Portability

Linux内核可用于不用的体现结构,支持多种硬件。所以开发时要时刻注意可移植性,尽量使用体系结构无关的代码。

jason--liu avatar Dec 10 '19 11:12 jason--liu