| name | linux-kernel-style |
| description | Linux 内核编码风格 Skill。蒸馏自 Linux 内核源码、Documentation/process/coding-style.rst、
Linus Torvalds 的代码审查邮件(LKML)、Greg KH 的贡献者指南。
触发词:「Linux 内核风格」「像内核一样写 C」「kernel style」「写底层 C」。
适用:系统级 C 代码、驱动、嵌入式、底层库开发。
|
Linux Kernel · 编码 DNA
"God, I hate that style. I find it ugly as sin." — Linus,谈到他不喜欢的代码风格
角色定义
此 Skill 激活后,你写出的 C 代码应该让内核核心 maintainer 在 patch review 时点头,
而不是回复「Please follow the coding style guidelines.」
这意味着:代码不只是正确的,而是内核味道的。
命名 DNA
3 条直觉规则:
-
小写+下划线,永远 — 函数、变量、文件名全部 snake_case,没有例外
static int usb_device_init(struct usb_device *dev)
static int usbDeviceInit(UsbDevice *dev)
-
名字要能自解释,但不啰嗦 — 局部变量可以短(i、ret、tmp),
但全局符号和函数名必须说清楚 是什么 + 属于哪个子系统
int i, ret;
struct device *dev;
int pci_enable_device(struct pci_dev *dev)
int pei_dev(struct pci_dev *d)
-
宏全大写,但不滥用宏 — 宏用 ALL_CAPS,避免用宏做函数能做的事
#define MAX_RETRIES 3
#define min(a, b) ((a) < (b) ? (a) : (b))
结构偏好
函数粒度:
- 函数不超过 一屏(约 24 行),超了就是信号,需要拆
- 每个函数只做一件事,名字能说清楚那件事
- 函数参数不超过 5 个,否则考虑封结构体
缩进:
错误处理:
花括号:
注释哲学
核心原则:解释「为什么」,不解释「是什么」
spin_lock_irqsave(&dev->lock, flags);
i++;
注释格式:
- 块注释用
/* */,对齐成矩形
- 单行解释用
/* ... */(不用 //,内核 C89 时代遗留)
- 函数/结构体注释用
/** */(kernel-doc 格式)
struct urb *usb_alloc_urb(int iso_packets, gfp_t mem_flags)
反模式(绝不这样写)
-
typedef 结构体 — 内核不 typedef 结构体,永远用 struct foo *
typedef struct { ... } MyStruct;
struct my_struct { ... };
-
匈牙利命名法 — pDevice、iCount、bFlag 这种前缀污染
struct device *pDevice;
struct device *dev;
-
超长函数 — 500 行函数是 bug,不是设计
-
神奇数字 — 直接写 0x40,不如定义 #define CTRL_REG_READY 0x40
-
三目运算符嵌套 — a ? b ? c : d : e 是在考验 reviewer 的耐心
-
void * 到处传 — 能用具体类型就用具体类型
-
printk 乱用 — 调试完记得删,pr_debug 可以被编译掉
校验测试
写完代码,问自己:
- Tab 检查:
grep -P "^ " file.c 有输出吗?有就是用了空格缩进 → 不对
- 函数长度:每个函数
wc -l 超过 30 行吗?超了就是信号
- 错误路径检查:每个可能失败的调用都检查返回值了吗?
来源
- Linux 内核源码:
Documentation/process/coding-style.rst
- Linus Torvalds LKML 邮件列表评审记录
- Greg Kroah-Hartman 贡献者指南
- Linux Kernel Teaching 项目