安卓binder驱动内核日志调试打印开放及原理(第二节)

背景:

针对上一篇文章已经讲解了如何通过命令写入debug_mask值来开放binder驱动中的相关debug日志,在本节将剖析为啥通过echo写入值到debug_mask就可以实现开放相关日志。

源码分析:

入手点可以先从我们直接打印日志的binder_debug方法开始:
正常如要打印日志只需要调用

	static void binder_vma_open(struct vm_area_struct *vma)
{
	struct binder_proc *proc = vma->vm_private_data;
//这里会调用binder_debug来进行打印
	binder_debug(BINDER_DEBUG_OPEN_CLOSE,
		     "%d open vm area %lx-%lx (%ld K) vma %lx pagep %lx\n",
		     proc->pid, vma->vm_start, vma->vm_end,
		     (vma->vm_end - vma->vm_start) / SZ_1K, vma->vm_flags,
		     (unsigned long)pgprot_val(vma->vm_page_prot));
}

这里看看binder_debug方法:
kernel/nubia/msm8998/drivers/android/binder.c

#define binder_debug(mask, x...) \
	do { \
		if (binder_debug_mask & mask) \
			pr_info(x); \
	} while (0)

这里可以看到binder_debug第一个参数就是mask,第二个是x其实就是正常日志打印参数,这个mask其实就是前面一节说道的开放哪些binder日志打印的枚举,这里上面看到我们传递值是BINDER_DEBUG_OPEN_CLOSE。
binder_debug_mask 是全局的一个变量,其实可以简单认为系统会把binder_debug_mask变量和我们/sys/module/binder/parameters/debug_mask值一样。
那么上面(binder_debug_mask & mask)就是检测debug_mask文件中的值是否包含了mask这个项,如果包含则会调用下面的pr_info(x)方法来进行打印
看看pr_info方法
kernel/nubia/msm8998/include/linux/printk.h

#define pr_info(fmt, ...) \
	printk(KERN_INFO pr_fmt(fmt), ##__VA_ARGS__)

其实就是调用printk打印。
那么上面就已经讲解清楚了,binder_debug在各个binder的相关操作方法中都有进行调用,但是binder_debug具体是否可以调用到printk进行输入,其实最后还是要看binder_debug_mask这个值,那么这个值具体又是怎么来的呢?
kernel/nubia/msm8998/drivers/android/binder.c

static uint32_t binder_debug_mask = BINDER_DEBUG_USER_ERROR |
	BINDER_DEBUG_FAILED_TRANSACTION | BINDER_DEBUG_DEAD_TRANSACTION;
module_param_named(debug_mask, binder_debug_mask, uint, 0644);

这里看到binder_debug_mask赋值一共两个地方,有一个初始值,有一个传递到module_param_named方法中的,其实binder_debug_mask的改变就是靠这个module_param_named方法,下面我们来重点讨论一下module_param_named方法。

module_param_named解析

module_param_named 是 Linux 内核中用于模块参数的一个宏定义,它允许模块开发者定义模块参数,这些参数可以在模块加载时通过命令行或配置文件等方式设置。module_param_named 宏定义在 <linux/moduleparam.h> 头文件中,通常用在模块的源代码中。

上面解释可能比较抽象,无法时刻理解,下面以debug_mask为案例先进行直观剖析

module_param_named(debug_mask, binder_debug_mask, uint, S_IWUSR | S_IRUGO);

module_param_named的第一个参数为debug_mask,首先会生成/sys/module/binder/parameters/目录下生成debug_mask文件节点,而且如果读取debug_mask文件就是binder_debug_mask变量的值。
当通过echo xxx > debug_mask命令,会触发动态修改module_param_named的第二个参数binder_debug_mask值进行改变,一旦binder_debug_mask改变就会。

上面总结就是:第一个参数debug_mask会有一个文件在/sys/module/binder/parameters/,读取和写入这个文件的值都会同步到binder_debug_mask这个变量上。

那么具体是怎么实现的debug_mask就可以同步到binder_debug_mask变量呢?这块就需要内核驱动相关的一些知识,比较复杂,这块就不给大家分析具体源码了,这里给大家一个参考blog:
https://blog.youkuaiyun.com/tugouxp/article/details/122759735

更多framework实战干货,请关注“千里马学框架”

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

千里马学框架

帮助你了,就请我喝杯咖啡

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值