linux下proc文件系统下创建文件

proc.c

/*************************
* 使用seq_file接口实现可读写的proc文件
* 适用于3.10以后的内核
*************************/
#include <linux/module.h>
#include <linux/sched.h>
#include <linux/fs.h>
#include <linux/proc_fs.h>
#include <linux/seq_file.h>
#include <linux/uaccess.h>
#include <linux/slab.h>
#include <linux/stat.h>
#include <linux/version.h>

#define PROC_NODE_ROOT_NAME	"proc_test"
#define PROC_NODE_NAME_1	"proc_test_1"
#define PROC_NODE_NAME_2	"proc_test_2"

static char *str = NULL;

static struct proc_dir_entry *proc_test_root;
static struct proc_dir_entry *proc_file1, *proc_file2;


/*********************
* seq_operations->show
* 详细学习seq_file用法
*********************/
static int my_proc_show(struct seq_file *m, void *v)
{
	/* 这里不能使用printfk之类的函数,要使用seq_file输出的一组特殊函数 */
	seq_printf(m, "current kernel time is %ld\n", jiffies);
	seq_printf(m, "str is %s\n", str);

	//必须返回0,否则什么也显示不出来
	return 0;
}

/***********************
* file_operations->open
***********************/
static int 
my_proc_open(struct inode *inode, struct file *file)
{
	return single_open(file, my_proc_show, NULL);
}

/************************
* file_operations->write
************************/
static ssize_t 
my_proc_write(struct file *file, const char __user *buffer, size_t count, loff_t *f_pos)
{
	char *tmp = kzalloc((count+1), GFP_KERNEL);
	if (!tmp)
		return -ENOMEM;

	if (copy_from_user(tmp,buffer,count)) {
		kfree(tmp);
		return -EFAULT;
	}

	kfree(str);
	str = tmp;

	return count;
}

static struct file_operations my_fops = {
	.owner	= THIS_MODULE,
	.open	= my_proc_open,
	.release = single_release,
	.read	= seq_read,
	.llseek	= seq_lseek,
	.write 	= my_proc_write,
};


#if LINUX_VERSION_CODE < KERNEL_VERSION(3,10,0)
/**
 * 3.10.0 之前的API调用
 * 更加详细的说明看/fs/proc/generic.c
 * proc_create_data 和 create_proc_entry有说明区别?
 * 前者需要自己定义文件操作函数,后者可以不需要但默认的
 * 功能单一,看源码可知。
 */
static int __init create_proc_file(void)
{
	/* 创建根文件夹 */
	proc_test_root = proc_mkdir(PROC_NODE_ROOT_NAME, NULL);
	/* 创建文件proc_file1 */
	proc_file1 = proc_create_data(PROC_NODE_NAME_1, 0666, proc_test_root, &my_fops, NULL);
	/* 创建文件proc_file2 */
	proc_file2 = create_proc_entry(PROC_NODE_NAME_2, 0666, proc_test_root);

	/* 同样自己也可以重新赋值 */
	if(proc_file2) {
		proc_file2->proc_fops = &my_fops;
	}
 
	printk(KERN_EMERG "create_sys_proc_init\n");
 
	return 0;
}
 
static void  __exit remove_proc_file(void)
{
	/* 删除文件 */
	remove_proc_entry(PROC_NODE_NAME_2, proc_test_root);
	remove_proc_entry(PROC_NODE_NAME_1, proc_test_root);
	/* 删除目录 */
	remove_proc_entry(PROC_NODE_ROOT_NAME, NULL);
 
	printk(KERN_EMERG "proc exit\n");
}

#else
/**
 * 3.10.0 之后的API调用
 */
static int __init create_proc_file(void)
{
	struct proc_dir_entry* file = NULL;

	file = proc_create(PROC_NODE_ROOT_NAME, 0666, NULL, &my_fops);
	if(!file)
	{
		printk(KERN_EMERG "create_proc_file Error !!!\n");
		return -ENOMEM;
	}	
	else
	{
		printk(KERN_EMERG "create_proc_file Finish.\n");
	}	

	return 0;
}


static void  __exit remove_proc_file(void)
{
	remove_proc_entry(PROC_NODE_ROOT_NAME, NULL);

	if(str)
	{
		kfree(str);
	}	

	printk(KERN_EMERG "remove_proc_file\n");
}
#endif

module_init(create_proc_file);
module_exit(remove_proc_file);

MODULE_AUTHOR("Yang");
MODULE_LICENSE("Dual BSD/GPL");


Makefile:

obj-m += proc.o

KERN_DIR := /lib/modules/$(shell uname -r)/build/

PWD := $(shell pwd)

all:
	sudo make -C $(KERN_DIR) M=$(PWD) modules

clean:
	sudo rm -rf *.o *.ko *.mod.c *.order *.symvers

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值