【深入内核】ARM64下的内核栈 2月前查看 评论
【深入内核】ARM64下的内核栈

本文深入探讨了Linux内核栈的运作机制。内核栈是进程生命周期中不可或缺的部分,用于保存用户态和内核态之间的上下文信息。文章解释了内核栈如何通过`task_struct`结构体与进程关联,以及`pt_regs`和`cpu_context`在任务切换和异常处理中的关键作用。此外,文章还详细说明了ARM64架构中`sp_el0`寄存器如何直接存储当前任务的`task_struct`指针,从而优化了栈指针的使用。文章最后讨论了内核栈的配置和栈回溯技术,为内核稳定性问题的分析提供了宝贵的见解。

【深入内核】内核printk原理介绍 2月前查看 评论
【深入内核】内核printk原理介绍

printk 是 Linux 内核用于输出调试信息的接口,通过 log buffer 存储日志信息,并在系统出现问题后记录错误信息。文章详细介绍了 printk 内核框架,包括 printk 接口的作用、log buffer 的设计和初始化、log buffer 的数据结构,以及 printk 函数的流程。文章还分析了 printk ring buffer 的写入过程,包括 prb_reserve、printk_sprint 和 prb_commit 等函数的核心作用。最后,文章通过 trace32 读取 printk_ringbuffer 在内存中的数据,并解释了 printk_ringbuffer 在内存中的增长方向,使读者对环形缓冲区的整体印象更加清晰。

[Linux进程调度] 第001篇 一篇文章全面了解Linux进程调度 3月前查看 评论
[Linux进程调度] 第001篇 一篇文章全面了解Linux进程调度

进程调度是操作系统确保进程高效运行的核心机制,决定哪个处于运行状态的进程能够投入运行以及运行时间。Linux 2.6内核引入了内核抢占特性,允许多个执行流交叉执行。进程和线程的生命周期包括创建、就绪、执行、阻塞和终止状态。多任务操作系统分为非抢占式和抢占式,后者如Unix系统允许调度程序强制挂起进程,分配执行机会给其他进程。Linux进程调度围绕`task_struct`数据结构,包含进程状态、优先级、时间片、调度策略等信息。调度器类负责管理不同类型的进程,如完全公平调度(CFS)、实时调度等。CFS使用红黑树组织进程队列,根据虚拟运行时间调度,保证公平性。实时调度类包括循环进程和先进先出进程,分别采用时间片轮转和先进先出机制。内核抢占允许在特定条件下中断当前进程,执行更高优先级的任务。SMP调度支持负载均衡、CPU亲和性设置、进程迁移等功能。

任务调度器:从入门到放弃(二) 3月前查看 评论
任务调度器:从入门到放弃(二)

这篇文章主要讨论了Linux内核中的线程调度策略,特别是针对多核异构架构(如Big.Little)的任务分配问题。作者分析了CFS(完全公平调度器)的工作原理,包括如何根据线程的优先级和虚拟运行时来分配CPU资源。文章指出,调度器是基于事件驱动的,而不是实时监控所有线程的状态,这导致了调度策略的实际效果与理论模型之间存在差异。 此外,文章还介绍了两种负载跟踪模型:PELT和WALT。PELT考虑了所有过去运行时间的负载,而WALT则将时间划分为窗口,通过统计线程在每个窗口的运行时间来计算负载。两种模型各有优缺点,PELT可能对非周期性负载不够敏感,而WALT可能会因为窗口划分而低估某些负载。 最后,作者提出了一个关于任务分配的问题:在Big.Little架构下,是否应该严格遵循“大任务跑大核,小任务跑小核”的原则。文章指出,这取决于任务的负载和CPU的能效曲线,并非所有情况下都适用。

任务调度器:从入门到放弃(一) 4月前查看 评论
任务调度器:从入门到放弃(一)

本文探讨了Linux调度器的运作机制,特别是完全公平调度器(CFS)和实时调度类(RT)的区别,以及控制组(cgroup)如何通过限制资源配额来影响调度结果。文章指出,CFS的优先级代表权重,而非传统意义上的优先级顺序,而cgroup则通过cpu.shares参数来控制资源占比。实验表明,当进程在同一个分组时,其资源占比受到priority权重的影响;当进程在不同分组时,其资源配额受到组的cpu.shares的控制。文章还讨论了cgroup可能带来的问题,如默认资源配额不合理和跨资源group组调用的问题。

【深入内核】linux ftrace详解 4月前查看 1 条
【深入内核】linux ftrace详解

本文主要介绍了Ftrace(Function Tracer)的概念、实现原理和使用方法。Ftrace是Linux内核自带的轻量级跟踪框架,用于记录内核内部发生的事件与函数调用,帮助开发者洞察系统最深处的执行路径、时序瓶颈与异常行为。文章详细阐述了Ftrace的实现原理,包括静态插桩和动态插桩两种方式,并介绍了Ftrace的开启方法,包括设置tracer类型、设置tracer参数、使能tracer、进行测试和提取trace结果等步骤。此外,文章还介绍了常见的trace event详解和特别注意点,如能够使用adb和开机过程中死机的情况。

linux-dead-lock-detect-lockdep 4月前查看 评论
linux-dead-lock-detect-lockdep

**死锁概念**:死锁是指多个进程(线程)因等待已被其他进程占有的资源而陷入阻塞的状态。死锁一旦发生,程序本身无法解决,只能依靠外部力量使程序恢复运行。Linux 提供了检测死锁的机制,主要分为 D 状态死锁和 R 状态死锁。 **死锁类型**: * **D 状态死锁**:进程等待 I/O 资源无法得到满足,长时间处于 TASK_UNINTERRUPTIBLE 睡眠状态。触发成因复杂多样,可能因为 synchronized_irq、mutex lock、内存不足等。 * **R 状态死锁**:进程长时间处于 TASK_RUNNING 状态垄断 CPU 而不发生切换,导致多 CPU 间互锁,整个系统无法正常调度。 **常见错误**: * AA: 重复上锁 * ABBA: 曾经使用 AB 顺序上锁,又使用 BA 上锁 * ABBCCA: 这种类型是 ABBA 的扩展。AB 顺序 , AB 顺序,CA 顺序。 * 多次 unlock **AB-BA 死锁的形成**:假设有两处代码都要获取两个锁(lockA 和 lockB),如果进程 P 持有 lockA 后再去获取 lockB,而此时恰好由进程 Q 持有 lockB 且它也正在尝试获取 lockA,那么此时就是处于死锁的状态。 **lockdep 死锁检测模块**:lockdep 是 Linux 内核中的一种死锁检测机制,通过跟踪锁类的使用历史状态和依赖关系,以确保锁类状态和锁类之间的依赖总是正确的。lockdep 会检测并报告死锁风险,并提供相应的出错处理机制。 **检查规则**: * 单锁状态规则:一个软中断不安全的锁类也是硬中断不安全的锁类。 * 多锁依赖规则:同一个锁类不能被获取两次,不能以不同的顺序获取两个锁类,同一个锁实例在任何两个锁类之间,嵌套获取锁的状态前后需要保持一致。 **使用实例**:Lockdep 检测到死锁风险时,会打印相应的风险提示,并建议开发者修复代码,避免死锁。

MTK平台模块加载顺序控制 5月前查看 评论
MTK平台模块加载顺序控制

本文主要探讨了Android设备中模块加载顺序控制的相关知识点。首先,介绍了模块在文件系统中的位置要求,包括不同启动模式下模块的存放位置和加载顺序。接着,阐述了Android构建系统如何通过定义变量来支持模块加载,并举例说明了供应商内核模块的配置方式。然后,针对MTK平台,详细分析了模块加载控制机制,包括`ko_order_table.csv`文件的作用、编译逻辑以及树外驱动编译控制。最后,总结了设置模块加载顺序的原则,即通过调整`ko_order_table.csv`中的顺序来控制模块加载顺序,遵循先加载ramdisk模块,后加载vendor模块,且同一类型模块中,顺序靠前的先加载。

【深入内核】Linux 内核栈初步了解 6月前查看 评论
【深入内核】Linux 内核栈初步了解

这篇文章详细介绍了Linux内核栈的概念、重要性以及与之相关的常见问题和调试方法。内核栈是Linux为每个线程在运行内核代码时专用的一块栈空间,用于保存函数调用链、局部变量、寄存器上下文等信息。文章强调了内核栈的大小固定(在ARM64架构下默认为16KB),不可扩展,并指出了在栈上分配大数组、返回栈上变量地址等常见“死亡操作”。此外,还提供了如何调试内核栈使用的方法,包括编译选项、工具和查看系统文件。最后,总结了避免内核栈溢出的建议,以确保系统稳定运行。