Android内核驱动Linux设备驱动工程 - 第1节

1. Linux内核与Android系统概述

Linux内核是一个宏内核(Monolithic Kernel),但吸收了微内核的设计思想,通过模块机制实现动态扩展。其核心架构分为以下几个层次:

关键认知: Linux内核并非纯粹的宏内核,而是“宏内核 + 模块化”的混合体。驱动开发者主要工作在内核空间,与硬件直接交互。
Linux 内核架构分层图 用户空间 (User Space) 应用程序 · C库 (glibc) · 系统调用接口 系统调用层 (System Call Interface) 内核核心 (Kernel Core) 进程管理 调度 · IPC 内存管理 MMU · 页分配 文件系统 VFS · 具体FS 网络协议栈 TCP/IP · Socket 设备驱动 字符/块/网络 安全模块 SELinux · Cap 硬件抽象层 (HAL / 固件接口) 硬件 (CPU · 内存 · 外设)

1.1.1 内核空间与用户空间

Linux 通过 CPU 特权级(x86 的 Ring 0 ~ Ring 3,ARM 的 EL0 ~ EL3)隔离内核与用户程序:

  • 内核空间:运行在最高特权级,可访问所有硬件资源。驱动、调度、内存管理均在此运行。
  • 用户空间:运行在最低特权级,通过系统调用陷入内核。应用程序、C库、守护进程在此运行。
驱动开发者视角: 设备驱动运行在内核空间,一个指针错误就可能导致系统崩溃(Oops)。调试手段主要是 printk、ftrace、kgdb。

1.1.2 内核子系统概览

子系统核心职责驱动开发者关注点
进程管理创建/调度/销毁进程,管理CPU时间片驱动中的并发控制(spinlock/mutex)
内存管理虚拟地址映射、页分配、slab缓存DMA缓冲区分配、kmalloc/vmalloc选择
文件系统VFS抽象层,支持ext4/btrfs等驱动通过file_operations暴露设备节点
网络协议栈TCP/UDP/IP协议实现,Socket接口网络设备驱动(NAPI、sk_buff)
设备驱动字符/块/网络设备框架,中断处理核心工作区:probe、open、ioctl、中断
安全模块SELinux、Capabilities、密钥管理驱动需考虑权限检查(capable())

1.2 Android系统层次结构

Android 基于 Linux 内核,但在其之上构建了完整的应用框架层和运行时环境。整体层次从下到上分为:

Android 系统层次结构 应用层 (Applications) 系统应用 · 第三方应用 · Launcher 应用框架层 (Application Framework) Activity Manager · Window Manager · Content Providers · View System 系统运行时层 (Android Runtime & Native Libs) ART / Dalvik 虚拟机 Native C/C++ 库 (libc, libutils, libbinder) 硬件抽象层 (HAL) Camera HAL · Audio HAL · Sensors HAL · GPS HAL Linux 内核层 (Linux Kernel) 进程调度 · 内存管理 · 设备驱动 · 网络栈 · 电源管理 硬件 (SoC · 外设 · 传感器)

1.2.1 各层职责详解

  • 应用层:用户直接交互的界面,使用 Java/Kotlin 开发,运行在 ART 之上。
  • 应用框架层:提供四大组件(Activity、Service、ContentProvider、BroadcastReceiver)和系统服务(WindowManager、PackageManager 等)。
  • 系统运行时层:ART 负责执行 Dex 字节码;Native 库提供底层能力(Binder IPC、SurfaceFlinger、Media 编解码)。
  • 硬件抽象层 (HAL):驱动开发者最常接触的接口层。HAL 封装内核驱动,向上提供稳定 API,使框架层不依赖具体内核实现。
  • Linux 内核层:标准 Linux 内核 + Android 特有增强(wakelock、ashmem、binder 驱动等)。
重要区别: 标准 Linux 的驱动直接暴露 /dev 节点给用户空间;Android 则强制通过 HAL 封装,框架层不直接访问内核节点。这意味着 Android 驱动开发者既要写内核驱动,也要写对应的 HAL 模块。

1.3 Android与标准Linux的区别

Android 虽然使用 Linux 内核,但在用户空间架构、驱动模型、电源管理、IPC 机制等方面与标准 Linux 发行版有显著差异。下表总结了核心区别:

对比维度标准 LinuxAndroid
用户空间GNU C库 + X11/Wayland + 桌面环境Bionic libc + SurfaceFlinger + ART
IPC 机制D-Bus、Socket、管道Binder(内核驱动实现的高性能 IPC)
设备驱动访问用户空间直接 open /dev 节点通过 HAL 封装,框架层不直接访问
电源管理标准 Linux PM(suspend/resume)Android wakelock + 早期 suspend 机制
进程管理标准 fork/execZygote 预孵化 + 按需 fork
存储分区传统分区表(/boot, /root, /home)system、vendor、product、data 动态分区
显示系统DRM/KMS + Wayland/X11SurfaceFlinger + HWC (Hardware Composer)
安全模型DAC(传统 Unix 权限)DAC + MAC(SELinux 强制访问控制)
内核特有驱动标准主线内核Binder、ashmem、ion、wakelock(部分已合入主线)

1.3.1 驱动开发者需要关注的 Android 特有机制

  • Binder 驱动:Android 的核心 IPC,驱动位于 drivers/android/binder.c。所有跨进程通信(ServiceManager、AMS、WMS)都依赖它。
  • Ion 内存分配器:用于连续/非连续物理内存分配,是 Camera、GPU、Display 驱动的基础。
  • Ashmem:匿名共享内存,用于进程间大数据传递(已逐渐被 ION 替代)。
  • Wakelock:防止系统进入深度睡眠,驱动中需要正确管理 wakelock 以避免功耗问题。
  • HAL 接口:每个硬件模块(Camera、Audio、Sensors)都有对应的 HAL 接口定义(.hal 文件),驱动需要实现这些接口。
实战要点: 在 Android 上开发驱动,不能只写内核模块。你需要同时完成:
1) 内核驱动(字符设备、platform driver、中断处理)
2) HAL 实现(hardware/libhardware 或 HIDL/AIDL 服务)
3) SELinux 策略(允许 HAL 进程访问内核节点)
4) 权限配置(AndroidManifest 或权限 XML)

1.3.2 Android 内核版本演进

Android 使用长期稳定版(LTS)内核,并在此基础上增加 Android 特有补丁。常见对应关系:

Android 版本内核基线主要驱动变化
Android 9 (Pie)Linux 4.4 / 4.9 / 4.14Treble 架构强制 HAL 独立
Android 10Linux 4.9 / 4.14 / 4.19Ion 驱动重构,dma-buf 标准化
Android 11Linux 4.14 / 4.19 / 5.4Binder 增加冻结功能,SELinux 策略收紧
Android 12+Linux 5.4 / 5.10 / 5.15通用内核映像 (GKI) 启动,驱动与内核解耦
GKI(通用内核映像):从 Android 12 开始,Google 要求设备使用预编译的通用内核,厂商驱动以模块形式加载。这改变了传统的内核 + 驱动一体化编译方式,驱动开发者需要适配模块化接口。

1.4 本章小结

  • Linux 内核是宏内核 + 模块化架构,驱动运行在内核空间,需注意安全与稳定性。
  • Android 在 Linux 内核之上构建了应用框架、运行时、HAL 三层,驱动通过 HAL 向上提供服务。
  • Android 与标准 Linux 在 IPC、电源管理、显示系统、安全模型等方面存在本质差异。
  • 驱动开发者需要掌握内核驱动 + HAL + SELinux + 权限配置 的全栈技能。