当内核出现比较严重的错误时,如内核空指针,内存访问出错,堆栈溢出等会触发panic,无论是什么原因触发的kernel panic,最后都会调用panic(const char *fmt, ...)函数。在调用该函数之前,系统仍然处于运行状态,所以如果想要在机器发生kernel panic时及时保存一些重要的资源,如存放在内存中的一些日志文件,可以有两种方案,一是得知存放日志的物理地址,直接在执行panic流程之中,将整个内存块dump下来,可以模拟kmsg日志操作方法。另一种方法是通过panic函数与用户层进程进行通信,通知用户进程将日志保存到磁盘的某个位置。此时panic流程不能继续,需要等用户进程完成相关操作之后才能继续。这涉及到用户进程和内核线程之间双向的通信,通信方式有很多种,双向通信一般包括,proc文件系统,debugfs文件系统,以及netlink。本文所采用的策略是创建debugfs节点进行通信。
首先创建debugfs节点:
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/slab.h>
#include <linux/debugfs.h>
#include <asm/uaccess.h>
static struct dentry *my_debugfs_root;
static u32 my_sign = 0;
void set_my_sign(int value){
my_sign = value;
}
unsigned int get_my_sign(void){
return my_sign;
}
static int __init my_debugfs_init(void)
{
struct dentry *r_my_sign;
printk(KERN