内核设备驱动API之__class_create

struct class *__class_create(struct module *owner, const char *name,
			     struct lock_class_key *key)
用于动态创建设备的逻辑类,并完成字段的初始化,并在/sys/class 下新建一个目录。
其使用的例程如下:
#define class_create(owner, name)		\
({						\
	static struct lock_class_key __key;	\
	__class_create(owner, name, &__key);	\
})
kernel中主要是通过class_create这个宏来调用__class_create
例如:
	cuse_class = class_create(THIS_MODULE, "cuse");
	if (IS_ERR(cuse_class))
		return PTR_ERR(cuse_class);
其源码分析如下:
struct class *__class_create(struct module *owner, const char *name,
			     struct lock_class_key *key)
{
	struct class *cls;
	int retval;
	#申请一个class 结构体,如果申请失败则退出
	cls = kzalloc(sizeof(*cls), GFP_KERNEL);
	if (!cls) {
		retval = -ENOMEM;
		goto error;
	}
	#针对class 结构体用形参来赋值
	cls->name = name;
	cls->owner = owner;
	cls->class_release = class_create_release;
	#将这个class 添加到kernel中,并在/sys/class 中新建一个目录
	retval = __class_register(cls, key);
	if (retval)
		goto error;

	return cls;

error:
	kfree(cls);
	
	return ERR_PTR(retval);
}
__class_register 的实现如下:
int __class_register(struct class *cls, struct lock_class_key *key)
{
	struct subsys_private *cp;
	int error;

	pr_debug("device class '%s': registering\n", cls->name);
	#class 一般作为subsys 注册给kernel,这里申请subsys 结构体并赋值
	cp = kzalloc(sizeof(*cp), GFP_KERNEL);
	if (!cp)
		return -ENOMEM;
	klist_init(&cp->klist_devices, klist_class_dev_get, klist_class_dev_put);
	INIT_LIST_HEAD(&cp->interfaces);
	kset_init(&cp->glue_dirs);
	__mutex_init(&cp->mutex, "subsys mutex", key);
	error = kobject_set_name(&cp->subsys.kobj, "%s", cls->name);
	if (error) {
		kfree(cp);
		return error;
	}

	/* set the default /sys/dev directory for devices of this class */
	if (!cls->dev_kobj)
		cls->dev_kobj = sysfs_dev_char_kobj;
#一般我们都会定义这个config_block
#if defined(CONFIG_BLOCK)
	/* let the block class directory show up in the root of sysfs */
	if (!sysfs_deprecated || cls != &block_class)
		cp->subsys.kobj.kset = class_kset;
#else
	cp->subsys.kobj.kset = class_kset;
#endif
	cp->subsys.kobj.ktype = &class_ktype;
	cp->class = cls;
	cls->p = cp;
	#注册给kernel 这个subsys
	error = kset_register(&cp->subsys);
	if (error) {
		kfree(cp);
		return error;
	}
	#添加这个class 给kernel
	error = class_add_groups(class_get(cls), cls->class_groups);
	class_put(cls);
	return error;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值