02linux进程与调度管理
二、系统整理后的核心知识运维视角模块一内核体系分层总览课程先纠偏驱动不属于硬件层属于内核层硬件是物理设备本身驱动是内核里操控硬件的代码是内核的核心组成部分。没有独立的 “服务层”本质就是系统调用接口层是内核对外暴露的统一边界用户程序必须通过系统调用才能进入内核这是权限隔离的核心防线。未实现的系统调用返回标准错误码-ENOSYS不是简单的 “NO”上层应用根据错误码做对应处理。1. 四层分层架构从下到上四层核心设计思想是分层隔离、权限受控、接口统一这也是操作系统安全和可维护性的基础表格层级核心内容运维对应场景硬件层CPU、内存、磁盘、网卡、外设等物理设备硬件故障、存储设备、网络设备问题内核层进程调度、内存管理、文件系统、驱动、网络协议栈、IPC 通信内核本身所有系统能力的提供者直接操作硬件系统调用接口层内核对外暴露的统一 APIopen/read/write/fork 等所有命令、程序、库函数的底层入口用户层Shell、应用程序、服务、脚本日常操作的所有软件运行在最低权限级核心规则用户层绝对不能直接访问内核层必须通过系统调用走正规流程。内核会做权限检查、参数校验确保安全。2. 内核五大核心模块内核是模块化设计模块之间深度协作每个模块对应一大块运维领域进程调度模块分配 CPU 时间决定哪个进程什么时候跑、跑多久。对应ps/top、进程状态、优先级调优。内存管理模块管理物理内存分配虚拟地址空间内存隔离、页缓存、swap 交换。对应free、OOM、内存泄漏、缓存调优。文件系统模块通过 VFS 提供统一文件接口管理 ext4/xfs/nfs 等。对应磁盘挂载、空间管理、IO 性能。进程间通信IPC模块管道、消息队列、共享内存、信号。对应 Shell 管道、kill 信号、服务间通信。驱动管理模块对接硬件屏蔽差异提供统一接口。对应磁盘 / 网卡驱动、设备识别、硬件兼容性。3. 三类驱动与 VFS 思想Linux 把驱动分成三大类管理模式完全不同表格驱动类型核心特点典型设备运维对应字符设备按字节流顺序读写实时性强键盘、串口、终端/dev/tty*设备、控制台权限块设备按块读写支持随机访问追求吞吐量硬盘、U 盘、SD 卡磁盘 IO 性能、挂载、lsblk网络设备按数据包收发不走文件系统接口网卡、无线网卡网络流量、网卡驱动、协议栈调优VFS “一切皆文件”字符设备、块设备在用户层都呈现为文件上层用统一的open/read/write/close就能操作不同硬件不用管底层驱动怎么实现。4. 中断体系总览广义的中断是所有打断 CPU 正常执行流程的事件是内核响应内外事件的核心机制。分为两大类硬件中断外部设备异步触发比如磁盘、网卡、键盘中断。可屏蔽 / 不可屏蔽。软件中断CPU 执行指令时同步触发也叫异常。分为三类故障可恢复比如缺页异常陷阱主动触发比如系统调用中止严重错误无法恢复比如除以 0运维对应cat /proc/interrupts查看硬件中断次数strace跟踪系统调用软中断。模块二进程管理核心task_struct 与 fork 机制课程先纠偏0 号进程不是 fork 出来的它是系统唯一一个内核手工构造的进程没有父进程是所有进程的 “根”。TSS 不是用来做硬件任务切换的Linux 全程用软件做进程切换TSS 只干一件事 —— 保存每个进程的内核栈地址供中断 / 特权级切换时使用。不是分配 64MB 物理内存Linux 0.11 每个进程最大有 64MB虚拟地址空间不是直接分配物理内存物理内存是用到多少分配多少。1. 进程的 “身份证”task_structtask_struct 就是操作系统里的 “进程档案”PCB每个进程对应一个。运维最常用的核心字段1进程状态对应ps命令的STAT列共 5 种核心状态表格内核状态ps 状态核心含义运维常见场景运行 / 就绪态R正在占 CPU 跑或在就绪队列等调度跑计算、跑脚本的进程可中断睡眠S等资源 / 等 IO可以被信号唤醒大部分后台服务、等待输入的 shell不可中断睡眠D等硬件 IO不能被信号打断只能等 IO 完成等待磁盘读写、NFS IO 的进程停止态T被调试 / 暂停信号停下不调度也不运行CtrlZ 挂起的进程僵尸态Z进程已经退出但父进程没回收它的档案父进程异常退出、没调用 wait 回收2身份与权限pid进程唯一 ID全局不重复ppid父进程 ID用来梳理进程父子关系uid/euid用户 ID、有效用户 ID决定进程能访问哪些文件资源运维常识孤儿进程父进程先死会被 1 号进程init收养ppid 变成 1。3资源管理文件描述符表存进程打开的文件fork 时子进程会继承对应文件引用计数 1。对应运维场景文件句柄泄漏、父子进程共享文件偏移量。current_root/current_directory根目录、当前工作目录fork 时同样继承。内存边界代码段、数据段、栈、堆的地址范围。4调度相关counter剩余时间片单位是 10ms1 个 jiffy调度器靠这个选进程。priority进程优先级也是时间片的基准值数值越大优先级越高。5信号相关32 位信号位图每一位代表一个待处理的信号比如 kill 发的 9 号信号。每个信号对应的处理方式默认、忽略、自定义函数。2. fork创建进程的核心机制fork 是类 Unix 系统创建进程的唯一方式0 号进程除外最经典的特点一次调用两次返回—— 父进程返回子进程 PID子进程返回 0。1fork 完整流程第一步找空位、分配 PID 遍历进程表找一个空位置分配唯一 PID。槽位满了就报错这就是系统进程数上限的来源。第二步复制进程档案 给子进程分配新的 task_struct几乎完整拷贝父进程的档案然后修改关键信息子进程状态先设为不可中断睡眠防止创建到一半被调度修改 PID、PPID、创建时间时间片父子平分防止通过 fork 刷时间片清空待处理信号信号不继承第三步内存拷贝 拷贝父进程的地址空间映射为子进程建立独立的页表。早期内核完整拷贝物理内存父进程有多少数据就复制多少现代 Linux写时复制COW——fork 后父子先共享同一块物理内存只有其中一方修改内存时才真正复制一页。运维视角写时复制就是为什么 fork 一个大进程很快、而且初始内存占用不翻倍的原因。第四步资源继承文件描述符子进程继承父进程所有打开的文件对应文件引用计数 1。父子共享同一个文件读写偏移量。场景父进程打开日志文件写日志fork 出的子进程接着写会接着父进程的位置往后写。根目录、工作目录、权限掩码、信号处理函数全部继承。第五步设为就绪态 把 TSS、LDT 都配置好子进程状态改成就绪放进调度队列等待被调度执行。模块三进程调度与状态管理课程先纠偏不是冒泡排序选进程schedule 函数就是遍历一遍进程槽找出 counter 值最大的就绪进程本质是「一次遍历找最大值」不需要全排序。睡眠队列不是栈结构是链表实现的先进先出队列进程按等待顺序挂进去唤醒的时候按顺序唤醒。TSS 不负责保存全部寄存器进程切换时的通用寄存器是软件手动保存 / 加载的TSS 只存内核栈指针。Linux 全程用软件做上下文切换不用 x86 的硬件任务切换机制。1. 调度的驱动力时钟中断每 10ms 触发一次时钟中断内核做三件事全局计数器jiffies1系统时间往前走一格给当前进程记账在用户态就加用户时间utime在内核态就加系统时间stime这就是ps、top里 user%、sys% 的来源把当前进程的剩余时间片 counter-12. 调度触发的两个时机1主动调度进程自己调用sleep、wait等阻塞函数主动放弃 CPU进入睡眠然后主动调用调度器选下一个进程。场景进程读磁盘磁盘没准备好进程主动去睡觉让 CPU 跑别的进程。2被动调度时间片用完时钟中断里发现当前进程的 counter 减到 0 了并且当前处于用户态就打一个 “需要调度” 的标记。等中断处理完准备返回用户态的前夕检查到标记就执行调度。关键特性内核态不可抢占进程跑内核代码的时候哪怕时间片用完了也不能抢它的 CPU必须等它返回用户态或者主动放弃 CPU。运维场景为什么有时候一个进程调用了很慢的内核操作比如大量磁盘 IO整个系统都会卡就是因为它占着内核态不出来别的进程抢不到 CPU。3. 调度算法优先级时间片轮转核心逻辑两步找最大 counter → 全归零就重算。第一步遍历找最大剩余时间片 遍历所有进程跳过睡眠、停止、僵尸的只看就绪态的记录 counter 值最大的那个进程。第二步时间片全用完就重新分配 如果所有就绪进程的 counter 全是 0就用公式重新计算counter counter / 2 priority算法的精妙之处运维必懂优先级基准priority 是基准值优先级越高每次重新分配的时间片基数越大能拿到更多 CPU 时间。IO 密集型进程自动优先经常等 IO 的进程大部分时间在睡觉counter 用不完。重新计算时剩余的 counter 会折半累加counter 值比一直跑 CPU 的进程大下次优先被调度。效果IO 进程响应快不会因为频繁阻塞而 “饿死”这就是数据库平时 CPU 不高但查询响应还很快的底层原因。CPU 密集型进程公平轮转一直占 CPU 跑的进程时间片很快用完counter 变成 0。重新分配后就是 priority 的值大家同一起跑线轮流跑。不会永久霸占所有进程的 counter 都会动态衰减哪怕优先级再高也不会一直占着 CPU 不放低优先级进程也总能轮到。4. 进程切换上下文切换的开销选好新进程后靠switch_to做上下文切换核心做四件事保存旧进程现场把 CPU 的通用寄存器、栈指针保存到旧进程的内核栈里切换内核栈把栈指针换成新进程的内核栈地址切换地址空间加载新进程的 LDT更新页表基址恢复新进程现场从新进程的内核栈里弹出寄存器CPU 从新进程上次被切走的位置继续跑运维视角上下文切换是有开销的。每次切换都要做保存、加载、切换页表这些操作切换太频繁会浪费大量 CPU 在切换上。 用vmstat看到的cscontext switch列数值很高就是上下文切换频繁通常是线程太多、IO 太碎导致的。5. 睡眠与唤醒等待队列进程要等资源磁盘、锁的时候就会调用sleep_on把自己挂起来等资源可用了再被wake_up唤醒。sleep_on把自己改成睡眠状态挂到资源对应的等待队列链表主动调用调度器放弃 CPUwake_up资源可用时把队列里的进程改成就绪态从等待队列摘下来放进调度就绪队列运维场景对应大量 D 状态进程通常是磁盘 IO 瓶颈、NFS 挂载故障、存储设备响应慢进程都在等 IO。S 状态可以用 kill 唤醒D 状态不行只能等 IO 完成。模块四、进程生命周期退出、僵尸、信号与会话课程先纠偏没有 “rezie 函数”子进程自己退出走do_exit()不释放 task_struct只是置为僵尸态、发 SIGCHLD父进程收尸走sys_waitpid()才真正释放 task_struct。两步是分开的。kill pid-1不是发给所有进程是发给当前进程有权限发信号的所有进程除了自己和 init内核会做权限过滤。do_exit不释放 task_struct进程死了 task_struct 还留着目的是让父进程能拿到退出码。真正释放是父进程 wait 之后的事这就是僵尸进程的根源。会话头进程退出≠终止会话里所有进程是控制终端挂断时内核向前台进程组发 SIGHUP。会话头退出本身不直接杀全组而是它带走了控制终端终端关闭才触发 SIGHUP。1. 进程退出do_exit 完整流程进程退出有三种触发方式正常结束、异常结束致命信号、主动调用 exit。最终都汇到do_exit()按顺序做这些事第 1 步释放内存空间 释放代码段、数据段、页表进程占的物理内存全部还回去。运维视角这一步完成后进程虽然还占一个 task 槽但已经不占内存了。第 2 步关闭文件 把打开的文件描述符表全部关掉每个 file 结构体引用计数 - 1归零就真正释放。当前目录、根目录、inode 的引用计数也减一。运维视角这就是为什么文件句柄泄漏的进程死掉后句柄数会降下来。第 3 步处理子进程过继给 init 遍历自己的所有子进程把它们的父进程 PPID 改成 1 号进程init。这就是 “孤儿进程被 init 收养” 的实现。过继不等于杀子进程子进程继续跑只是换了个爹。以后这些子进程死了由 init 来收尸。第 4 步会话与控制终端处理 如果这个进程是会话领头进程它退出会导致控制终端被释放。终端一旦挂断内核会给前台进程组里的每个进程发 SIGHUP。这一条直接决定了你关 SSH 窗口时后台作业为什么会跟着死。第 5 步给父进程发 SIGCHLD 告诉父进程 “我死了来收尸”。第 6 步状态改成僵尸态TASK_ZOMBIE 注意到这里进程就结束了但 task_struct 还在内存里槽位还占着。然后调用调度器切走 CPU再也不会被调度回来。第 7 步父进程 wait 收尸 父进程要么阻塞在 wait () 里要么收到 SIGCHLD 后调用 waitpid ()。内核发现子进程是僵尸态就把子进程的退出码、运行时间累加到父进程释放 task_struct 内存清空 task 数组槽位到这里进程才算彻底消失。2. 僵尸进程与孤儿进程1僵尸进程Z 状态产生原因子进程死了父进程没有调用 wait/waitpid 来收尸。特点不占 CPU、不占内存只占一个 task 槽位ps里显示为 Z 状态命令名带defunct。为什么会产生父进程代码没写 wait、父进程对 SIGCHLD 设为忽略、父进程自己卡死了。运维怎么处理僵尸自己杀不死kill -9 没用正确做法杀掉它的父进程。父进程一死僵尸子进程会被 init 收养init 会自动 wait 收尸大量僵尸会占满进程槽位导致没法创建新进程2孤儿进程产生原因父进程先死了子进程还在跑。内核处理把这些子进程的 PPID 改成 1init子进程继续正常运行。运维视角孤儿进程本身不是问题是内核设计好的正常机制。nohup ./server 把父 shell 退掉server 就变成孤儿被 init 收养继续跑 —— 这正是我们想要的。两者对比表格孤儿进程僵尸进程本质父先死子还活着子先死父没收尸状态正常运行状态S/RZ 态已死占资源正常占 CPU / 内存只占 task 槽收尸者init 自动收养并 wait必须等亲爹 wait杀爹才能解是否有害正常现象大量积累有害3. 信号机制1信号怎么发出去内核发信号不是 “远程投递”就是在目标进程的 signal 位图上打一个标记位校验信号号是否合法、校验权限把目标进程的 signal 位图对应位置 1如果目标进程在可中断睡眠态就把它唤醒成就绪态注意不可中断睡眠D 状态的进程收不到信号这就是为什么 kill -9 对 D 状态进程无效。2kill 的 PID 规则运维必会表格pid 参数含义pid 0发给 PIDpid 的那个进程pid 0发给当前进程所在进程组的所有进程pid -1发给当前进程有权限发的所有进程除自己和 initpid -1发给进程组 PGID-pid 的所有进程常用对应kill 1234杀单个进程默认发 SIGTERMkill -9 -1234杀掉进程组 1234 整组常用于杀一条 fork 出来的进程树killall/pkill按名字找进程再杀本质还是调 kill3常用信号速查运维版表格信号值含义什么时候用SIGHUP1终端挂断 / 重载配置让 nginx/apache 重读配置kill -HUP pidSIGINT2CtrlC前台中断SIGKILL9强制杀不可捕获kill -9 兜底进程卡死时用SIGTERM15请求终止默认正常停服给进程清理资源的机会SIGCHLD17子进程退出父进程收尸用SIGSTOP19暂停不可捕获CtrlZ 等价SIGCONT18继续运行fg/bg 用核心原则先kill pid发 SIGTERM给进程清理资源的机会不行再kill -9。一上来就 - 9 容易让进程留下临时文件、没刷日志、没关连接。4. 会话、终端与 nohup 的底层原理这部分课程讲得散但对运维极其重要 —— 你天天用的、nohup、setsid、tmux底层全是这套机制。1三个概念进程一个运行实例有 PID进程组一组相关进程有 PGID。通常是一个 shell 启动的一条命令管道比如a | b | c里三个进程同组会话一组进程组有 SID。通常对应一个登录会话比如你 SSH 上去开的那个 shell2控制终端一个会话最多绑定一个控制终端就是你登录的那个 tty/pts。它的作用是终端输入产生的信号CtrlCSIGINT、CtrlZSIGTSTP发给前台进程组终端关闭 / SSH 断开时内核给前台进程组发 SIGHUP3SIGHUP 到底是什么HUPhang up挂起。语义是 “控制终端没了”。 你在终端跑./server 然后关掉终端窗口→内核发现终端挂断→给这个会话的前台 / 后台进程组发 SIGHUP→进程默认收到 SIGHUP 就退出→你的 server 没了。4后台保活手段的底层区别表格手段做了什么为什么能让进程活着cmd 放后台跑没用关终端照样死nohup cmd 把 cmd 对 SIGHUP 的处理设成忽略stdout/stderr 重定向到 nohup.out收到 SIGHUP 不退出继续跑disown把作业从 shell 的作业表里移除shell 退出时不再给它发 SIGHUPsetsid cmd让 cmd 开一个新会话脱离原控制终端原终端挂断时新会话根本没绑这个终端收不到 SIGHUPtmux/screen服务端开一个常驻会话你 attach 上去操作你断开的只是 attachtmux server 还在跑业务进程从没离开过它的会话运维一句话总结要让进程脱离 SSH 活着本质就是 “别让它收到 SIGHUP”。生产环境跑服务推荐用 systemd/supervisor比裸 nohup 更靠谱能自动重启、管日志。模块五、内核启动完整流程课程先纠偏没有 “SVC32 保护模式”SVC 是 ARM 架构的特权模式x86 架构对应的是 32 位保护模式 Ring0内核态课程混淆了不同 CPU 架构的术语。Bootsect 会先移动自身BIOS 把引导扇区加载到 0x7C00bootsect 第一件事是把自己搬到 0x90000腾出低地址空间给内核。Setup 会移动内核到 0 地址bootsect 把内核临时加载到 0x10000setup 阶段会把整个内核搬到内存最底端 0x00000为保护模式地址映射做准备。虚拟盘不是 “逻辑内存”ramdisk 是把一段物理内存模拟成块设备本质还是占用物理内存。init 不会调用 setupsetup 是引导阶段的汇编代码实模式下运行init 是 1 号用户态进程根本碰不到底层 setup 代码。1. x86 平台启动全流程从按下电源到出现 shell一共分 5 层每层只做自己的事层层交接控制权BIOS自检 → Bootsect第一阶段引导 → Setup第二阶段引导 → Head.s内核前置汇编 → main.c内核初始化 → 用户态init进程阶段 1BIOS 自检与引导硬件固件层按下电源后CPU 首先运行主板上的 BIOS 固件POST 上电自检检查内存、硬盘、键盘等硬件是否正常按启动顺序找引导设备读取硬盘第一个扇区MBR512 字节加载引导扇区到内存物理地址 0x7C00跳过去把控制权交给引导程序运维视角开机卡主板 logo、报硬件错误都是这一层的问题。现在的 UEFI 是 BIOS 的升级版本质还是硬件固件。引导扇区损坏、硬盘识别失败都会在这一步报错。阶段 2Bootsect第一阶段引导512 字节汇编硬盘第一个扇区的代码体积只有 512 字节核心目标把更大的引导程序和内核从硬盘搬进内存。 核心动作自身搬家从 0x7C00 移动到 0x90000腾出低地址空间加载 Setup读硬盘把紧跟在后面的 setup 模块加载到 0x90200加载内核读硬盘把整个内核镜像加载到 0x10000跳转交权跳转到 setup 的入口运维视角这就是传统 MBR 引导的原型。现在的 GRUB、SysLinux 就是功能更强的 bootsect能识别文件系统、读配置文件、支持多系统启动。修复 grub 本质就是重写这部分引导扇区和引导程序。阶段 3Setup第二阶段引导汇编负责做内核运行前的所有硬件准备核心目标收集硬件信息、配置保护模式、把内核放到正确位置。 核心动作收集硬件参数调用 BIOS 中断读取系统信息总内存大小、硬盘参数、显示模式等存在内存固定位置后面传给内核。运维对应现在dmesg里的硬件探测信息、内核启动参数最早就起源于这一步。重新配置中断控制器避免硬件中断和 CPU 自身异常冲突搭建保护模式基础环境设置临时 GDT 和 IDT满足进入保护模式的硬件要求移动内核到 0 地址把之前临时放在 0x10000 的整个内核搬到内存最底端 0x00000。方便后续分页和内存管理。开启保护模式设置 CPU 控制寄存器的保护模式位CPU 从 16 位实模式切换到 32 位保护模式。跳转交权跳转到内核的最入口 head.s正式进入内核本身。补充实模式 vs 保护模式运维必懂实模式CPU 刚上电的原始模式16 位寻址最多访问 1MB 内存没有权限隔离程序能直接读写所有硬件。DOS 就是实模式系统。保护模式32 位寻址支持 4GB 内存有 4 个特权级Ring0 最高Ring3 最低有段机制和分页机制能实现进程内存隔离、权限控制。现代操作系统都跑在保护模式下。运维场景为什么用户态程序不能直接操作硬件因为用户态跑在 Ring3内核跑在 Ring0越权就会触发段错误。为什么内核崩溃会 panic因为 Ring0 级别的错误系统无法自我修复只能停机。阶段 4Head.s内核最前端的汇编进入内核后的第一段汇编代码核心目标初始化保护模式核心机制为 C 语言内核运行搭好运行环境。 核心动作重新加载段寄存器设置内核专属的代码段、数据段重新设置完整的中断描述符表IDT开启分页机制设置页目录和页表把虚拟地址映射到物理地址正式开启虚拟内存。从此进程看到的都是虚拟地址由内核和 MMU 负责映射到物理内存进程之间天然隔离。初始化浮点协处理器跳转到main()函数正式进入 C 语言编写的内核主体。阶段 5main 函数内核 C 语言初始化入口内核的业务逻辑核心目标读取硬件参数初始化所有子系统最终拉起用户态。读取硬件参数从 setup 存在固定内存地址的地方取出内存大小、硬盘参数、根设备号这些信息。内存规划与初始化把物理内存从低到高分成三大块内核代码 数据区内核本身的代码、全局变量、内核栈高速缓冲区磁盘 IO 的缓存读盘先读缓存写盘先写缓存再刷盘用户主内存所有进程的内存都从这里分配运维视角为什么 Linux 总显示 “内存占用高”因为空闲内存会自动拿去做缓存这个设计从 0.11 版本就定了。虚拟盘ramdisk初始化可选从主内存里划出一段空间模拟成磁盘块设备。运维对应现在的 initramfs、tmpfs、ramfs都是这个思路的进化版。安装系统的镜像、Live CD、系统启动时的临时根文件系统本质都是 ramdisk。逐项初始化子系统陷阱、中断、时钟、块设备、字符设备、文件系统、进程调度…… 全部初始化一遍。拉起用户态手工创建 0 号进程切换到用户态fork 出 1 号 init 进程最终启动 shell。2. 0 号与 1 号进程的特殊地位10 号进程idle 进程系统唯一一个不是 fork 出来的进程完全由内核代码手动构造。没有独立的用户内存空间直接用内核地址空间。代码就是一个死循环没事干的时候执行 hlt 让 CPU 休眠等中断唤醒。运维视角0 号进程就是系统的 “兜底”。top里的%id空闲 CPU 占比本质就是 0 号进程运行的时间占比。系统没活儿干的时候CPU 就跑它。21 号进程init 进程0 号进程运行后做的第一件事就是调用 fork 创建 1 号进程。是所有用户态进程的 “祖宗”负责打开标准输入、输出、错误对应终端的 0、1、2 文件描述符执行 /etc/rc 开机脚本启动系统服务最后启动 shell给用户提供命令行界面核心职责回收孤儿进程、管理服务启动、提供交互环境。运维常识所有用户进程、服务进程最终父进程追溯上去都是 1 号。为什么 kill -9 杀不掉 init因为它是所有进程的根内核做了特殊保护。为什么 systemd 崩了系统就崩了因为所有进程都是它的子进程根没了整个进程树就崩溃了。3. ARM 平台 U-Boot 启动流程嵌入式 / ARM 平台没有 BIOS用 U-Boot 替代 BIOSbootloader 的全部功能核心逻辑和 x86 一脉相承。完整流程U-Boot初始化硬件 → 加载内核镜像DTB到内存 → 传入机器ID、DTB地址、启动参数 → 跳转到内核入口 → 内核汇编入口校验CPU → 架构层初始化匹配硬件 → 通用子系统初始化 → rest_init创建init内核线程 → init进程挂载根文件系统 → 启动服务1U-Boot 引导阶段U-Boot 本身就是个轻量系统能识别存储、读文件、配置硬件。启动内核用bootm命令把内核镜像从 flash/SD 卡读到内存指定位置准备三个关键参数机器 ID、启动参数地址、架构信息调用 do_bootm_linux直接跳转到内核入口地址运维视角路由器、机顶盒、安卓手机、嵌入式设备基本都是 U-Boot 引导内核。设备变砖、启动卡内核很多时候是 U-Boot 环境变量、内核镜像地址、设备树配置错了。2多平台适配machine_desc 与设备树同样一个内核镜像为什么能在不同型号板子上跑核心就是硬件描述符机制。machine_desc机器描述符可以理解成 “硬件板子的档案卡”。每一款支持的硬件板子都对应一个结构体里面记录板子的所有关键信息机器 ID、内存分布、中断号映射、外设配置、专属初始化函数。启动匹配流程U-Boot 传入机器 ID → 内核遍历编译进去的所有 machine_desc → 找到匹配的就用这个板子的参数和驱动来初始化。运维视角为什么跨型号刷固件容易变砖机器 ID 不匹配内核找不到对应的硬件描述要么启动失败要么外设全部用不了。内核裁剪很大一部分工作就是删掉不需要的 machine_desc 和驱动减小镜像体积。3ATAG vs 设备树DTB都是给内核传硬件参数的方式表格ATAG旧设备树 DTB新只能传少量核心参数内存、串口、cmdline能描述完整硬件拓扑有哪些外设、地址多少、中断号多少参数格式固定改硬件要改内核代码独立文件改硬件只需要换 dtb不用重新编译内核老版本内核、简单嵌入式设备现在 ARM Linux、安卓、路由器、机顶盒的主流方案运维场景嵌入式固件里的.dtb 文件就是设备树二进制文件。为什么内核升级经常要同步更新 dtb因为硬件描述改了不匹配就会识别不了外设、驱动加载失败。 你在 U-Boot 里改的bootargs比如consolettyS0,115200 root/dev/mmcblk0p1就是通过这个机制传给内核的。4. .init 段机制初始化代码为什么不占运行内存所有只在启动时执行一次的代码和数据都标记为.init 段。启动阶段正常执行内核启动完成后会把整个.init 段占用的内存一次性全部释放。运维视角这就是为什么内核运行时占用的内存比内核镜像文件大小要小的重要原因之一 —— 一次性的初始化代码用完就扔了。三、运维视角总总结排障有分层思路出问题从下往上逐层定位硬件→bootloader→内核→系统调用→应用层不会盲目瞎试。工具懂底层原理strace抓系统调用、ps看进程状态、top看用户 / 系统 / 空闲时间、vmstat看上下文切换这些工具的输出本质都是内核模块状态的体现。常见问题有根因僵尸进程找父进程、D 状态查磁盘 IO、关终端进程死是 SIGHUP、fork 快是因为写时复制这些日常问题本质都是进程管理机制决定的。启动故障分层查卡 BIOS/UEFI 查硬件卡 bootloader 查引导和硬盘卡内核查启动参数和驱动卡用户态查 init 和服务。

相关新闻

系统辨识教案:从黑匣子到可交付讲义的落地路径

系统辨识教案:从黑匣子到可交付讲义的落地路径

简介:这份系统辨识教案面向自动化专业学生与相关工程技术人员,围绕从输入输出数据中建立系统模型这一核心问题展开,帮助读者掌握辨识理论、实验设计与编程计算能力。内容涵盖实体与模型的分类、Zadeh 辨识定义的三要素、辨识目的与模型类选择…

2026/10/10 2:42:03 阅读更多 →
蓝牙芯片驱动开发-第3章第5题-SDIO协议中cmd和data线的主要区别是什么

蓝牙芯片驱动开发-第3章第5题-SDIO协议中cmd和data线的主要区别是什么

蓝牙面试题解析:SDIO 协议中 cmd 和 data 线的主要区别是什么? 难度:⭐⭐⭐⭐ 较难 | 场景:社招二面/三面、蓝牙 SDIO 驱动 | 高频:🔥🔥🔥🔥 标准答案 SDIO 协议中 CMD 线(命令线) 和 DATA 线(数据线) 职责明确分离——CMD 传控制指令,DATA 传批量数据: ①…

2026/10/10 2:41:02 阅读更多 →
MAS激活脚本教程:免费一行命令激活Windows和Office,不用密钥

MAS激活脚本教程:免费一行命令激活Windows和Office,不用密钥

MAS激活脚本教程:免费一行命令激活Windows和Office,不用密钥 【免费下载链接】Microsoft-Activation-Scripts Open-source Windows and Office activator featuring HWID, Ohook, TSforge, and Online KMS activation methods, along with advanced trou…

2026/10/10 2:41:02 阅读更多 →

最新新闻

Obsidian离线插件实战指南:断网不崩、本地全控的生产力底座

Obsidian离线插件实战指南:断网不崩、本地全控的生产力底座

简介:本资源是面向Obsidian深度用户与离线环境工作者的「离线插件大全」,专为无法稳定访问官方插件社区的场景设计,解决第三方插件安装受阻、网络受限时的功能扩展难题。压缩包共967个文件,涵盖686个可直接部署的插件ZIP包&#x…

2026/10/10 4:13:39 阅读更多 →
知识蒸馏到Agent蒸馏:OPD在线策略蒸馏的原理与工程实践

知识蒸馏到Agent蒸馏:OPD在线策略蒸馏的原理与工程实践

知识蒸馏这几年在模型压缩和训练加速上都快被讲烂了,但一旦把问题从“教一个网络模仿另一个网络”换成“教一个 Agent 模仿另一个 Agent”,事情立刻就不一样了。标题里那串词——知识蒸馏、OPD、策略梯度、Agent——看着像四个独立概念,实际是…

2026/10/10 4:13:39 阅读更多 →
新电脑硬盘分区实战指南:从原理到三种落地方法

新电脑硬盘分区实战指南:从原理到三种落地方法

1. 为什么新电脑硬盘分区这件事,比你想象中更重要?“新电脑到手第一件事该干啥?”——很多人会说装软件、调壁纸、连WiFi。但真正决定这台机器未来三年用得顺不顺、卡不卡、重装系统麻不麻烦的,其实是开机后那几分钟里&#xff0c…

2026/10/10 4:13:39 阅读更多 →
医院超声影像系统落地:DICOM接入、存储调阅与DICOMweb实践

医院超声影像系统落地:DICOM接入、存储调阅与DICOMweb实践

简介:医院超声影像系统是一套面向医疗机构的信息化解决方案,围绕护士端与医生端协同工作,覆盖患者登记、排队叫号、超声影像查看与诊断分析等环节,适合医疗软件开发人员、医院信息科人员及医学信息化方向的学习者参考。资源包共23…

2026/10/10 4:13:39 阅读更多 →
PCA9422与STM32L073RZ低功耗电源管理方案设计与I2C配置实战

PCA9422与STM32L073RZ低功耗电源管理方案设计与I2C配置实战

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/10 4:13:39 阅读更多 →
多Agent集群24小时稳定运行实战:架构设计、调度机制与运维踩坑记录

多Agent集群24小时稳定运行实战:架构设计、调度机制与运维踩坑记录

这段时间我折腾出来一套 24 小时不停工作的多 Agent 集群,不是那种跑几分钟就结束的 demo,而是真的把一堆 AI Agent 挂在后台,日复一日地处理任务。这个项目从构思到稳定运行,前前后后踩了不少坑,也把很多藏在文档背后…

2026/10/10 4:12:39 阅读更多 →

日新闻

卫星轨道分类全解析:从LEO到GEO的选型逻辑与工程实践

卫星轨道分类全解析:从LEO到GEO的选型逻辑与工程实践

1. 从“卫星轨道分类”这个标题说起:为什么值得花时间搞懂第一次接触“卫星轨道分类”这个概念,很多人会觉得它离自己很远——不就是天上的星星怎么转吗?但如果你正在做航天任务规划、遥感数据接收、星座设计,甚至只是准备一场航天…

2026/10/10 0:00:39 阅读更多 →
Spring AOP 核心原理与实战:从概念到日志切面落地

Spring AOP 核心原理与实战:从概念到日志切面落地

1. 从一个真实痛点说起:为什么你的代码里到处都是重复逻辑刚入行那会儿,我写过一个用户管理模块,注册、登录、改密码、注销四个接口。每个接口里都塞了几乎一样的日志打印、参数校验、事务开启和提交。当时觉得没什么,能跑就行。直…

2026/10/10 0:00:40 阅读更多 →
Python招聘数据采集与分析可视化:从采集清洗到薪资技能城市可视化全链路

Python招聘数据采集与分析可视化:从采集清洗到薪资技能城市可视化全链路

简介:这是一套面向计算机相关专业学生与项目实战学习者的Python数据采集与分析可视化完整项目,以Boss直聘岗位数据为对象,适合用作毕业设计、课程设计或期末大作业。资源包共38个文件,约246KB,以13个py源码文件为核心&…

2026/10/10 0:00:40 阅读更多 →

周新闻

KT148A语音芯片外挂8002D功放的工程实践指南

KT148A语音芯片外挂8002D功放的工程实践指南

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/8 15:26:32 阅读更多 →
LLC谐振变换器增益公式推导:从FHA等效到完整归一化表达式

LLC谐振变换器增益公式推导:从FHA等效到完整归一化表达式

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/10 1:36:08 阅读更多 →
ARM架构深度解析:从RISC设计理念到交叉编译实战

ARM架构深度解析:从RISC设计理念到交叉编译实战

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/9 10:11:06 阅读更多 →

月新闻

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/8 21:13:17 阅读更多 →
Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/9 21:32:20 阅读更多 →
黑夜航拍船只数据集训练YOLOV5模型全流程解析

黑夜航拍船只数据集训练YOLOV5模型全流程解析

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/9 6:17:20 阅读更多 →