Linux 驱动开发究竟在开发什么?

文章目录

  • [1 Linux 驱动开发架构图](#1 Linux 驱动开发架构图)

  • [2 更具体的例子:LED 驱动程序](#2 更具体的例子:LED 驱动程序)

    • [2.1 硬件层(Hardware Layer)](#2.1 硬件层(Hardware Layer))
    • [2.2 固件层(Firmware Layer)](#2.2 固件层(Firmware Layer))
    • [2.3 驱动程序层(Driver Layer)](#2.3 驱动程序层(Driver Layer))
    • [2.4 操作系统内核(Kernel Layer)](#2.4 操作系统内核(Kernel Layer))
    • [2.5 系统调用层(System Call Layer)](#2.5 系统调用层(System Call Layer))
    • [2.6 C 库(C Library)](#2.6 C 库(C Library))
    • [2.7 用户空间(User Space)](#2.7 用户空间(User Space))
  • [3 具体过程](#3 具体过程)

  • [4 从理解 `open()` 函数的层次到理解所有的架构层次](#4 从理解 open() 函数的层次到理解所有的架构层次)

    • [4.1 应用程序中的 `open()` 函数](#4.1 应用程序中的 open() 函数)
    • [4.2 C 库中的 `open()` 函数](#4.2 C 库中的 open() 函数)
    • [4.3 `open()` 系统调用](#4.3 open() 系统调用)
    • [4.4 驱动的 `open()` 函数](#4.4 驱动的 open() 函数)
  • [5 总结](#5 总结)

  • 参考链接

  • 封面

  • 本文将全面探讨 Linux 驱动开发在系统架构中的位置,包括应用程序、C 库、系统调用和内核之间的关系。

  • Linux 驱动开发着眼于硬件和操作系统内核之间的驱动程序层,当然,内核配置与编译、引导加载程序开发、根文件系统构建等内容也是必不可少的。

1 Linux 驱动开发架构图

在 Linux 系统中,驱动开发涉及多个层级的交互,以下是各层级的结构图示:
用户空间
应用程序和系统服务 C 库
标准库函数如 open, read, write 系统调用层
与内核交互的接口 操作系统内核
管理资源和硬件接口 驱动程序层
内核模块 .ko 文件 固件层
设备初始化和控制 硬件层
物理设备

2 更具体的例子:LED 驱动程序

以 LED 驱动程序为例,以下是各层级的具体作用:

2.1 硬件层(Hardware Layer)

  • 组成:物理 LED 灯。
  • 功能:发光和熄灭。
  • 例子:LED 硬件连接到计算机的 GPIO(通用输入输出)引脚。

2.2 固件层(Firmware Layer)

  • 组成:LED 控制芯片固件。
  • 功能:管理 LED 的基本操作。
  • 例子:初始化 LED 硬件并准备接收控制信号。

2.3 驱动程序层(Driver Layer)

  • 组成 :LED 驱动模块(如 led_driver.ko)。
  • 功能
    • 硬件抽象:将 LED 的物理信号转换为标准输入/输出操作。
    • 设备控制:处理 LED 的初始化和开/关控制。
    • 文件操作 :实现 openclosereadwrite 等函数。
  • 例子 :LED 驱动程序响应来自用户空间的 write 操作,控制 LED 的开关状态。

2.4 操作系统内核(Kernel Layer)

  • 组成:Linux 内核代码。
  • 功能:管理系统资源,提供对硬件的低级访问。
  • 例子:内核通过调用 LED 驱动程序中的函数来处理对 LED 的控制操作。

2.5 系统调用层(System Call Layer)

  • 组成 :如 open()read()write() 系统调用。
  • 功能:提供应用程序与内核交互的接口。
  • 例子 :当应用程序调用 write() 系统调用时,系统调用层将请求传递给内核。

2.6 C 库(C Library)

  • 组成:如 glibc 提供的标准库函数。
  • 功能:实现对系统调用的包装,使其易于使用。
  • 例子open()close()read()write() 函数在 C 库中实现,最终调用系统调用。

2.7 用户空间(User Space)

  • 组成:运行在操作系统上的应用程序,例如控制 LED 的程序。
  • 功能:通过文件操作与设备驱动交互。
  • 例子 :控制 LED 的应用程序通过 open("/dev/led") 打开设备文件,通过 write() 控制 LED 的开关状态。

3 具体过程

  1. LED 驱动开发 :编写 LED 驱动代码 led_driver.c,实现 LED 初始化、开/关控制和文件操作函数。
  2. 编译驱动模块 :将 led_driver.c 编译为内核模块 led_driver.ko
  3. 加载模块 :使用 insmod led_driver.ko 加载驱动模块到内核中。
  4. 创建设备文件 :在 /dev 目录下创建 led 设备文件。
  5. 用户程序交互 :应用程序使用 open("/dev/led") 打开设备文件,通过 write() 控制 LED 的开关状态。
  6. 库函数调用 :应用程序调用 C 库中的标准函数,如 openwrite,这些函数通过系统调用与内核交互。
  7. 系统调用:C 库函数调用相应的系统调用,系统调用层将请求传递给内核。
  8. 驱动响应:LED 驱动处理来自系统调用的请求,控制 LED 的硬件操作。

4 从理解 open() 函数的层次到理解所有的架构层次

4.1 应用程序中的 open() 函数

  • 功能:用于在应用程序中打开一个文件或者设备。
  • 示例代码
c 复制代码
int fd = open("/dev/led", O_WRONLY);

4.2 C 库中的 open() 函数

  • 功能:包装系统调用,提供一个易用的接口给用户空间程序。
  • 伪代码
c 复制代码
int open(const char *pathname, int flags) {
    return syscall(SYS_open, pathname, flags);
}

4.3 open() 系统调用

  • 功能:提供用户空间程序与内核交互的接口。
  • 伪代码
c 复制代码
int sys_open(const char *filename, int flags) {
    // 内核代码,处理打开文件的逻辑
    ...
    return file_descriptor;
}

4.4 驱动的 open() 函数

  • 功能:实现设备特定的打开操作逻辑。
  • 示例代码
c 复制代码
static int led_open(struct inode *inode, struct file *file) {
    // 设备特定的打开操作,如初始化硬件
    ...
    return 0; // 成功
}

5 总结

  • 通过本文的各个部分,可以清晰地看到 Linux 驱动开发在系统架构中的重要性。应用程序、C 库、系统调用和驱动程序之间的协作,使得用户能够方便地控制硬件设备,实现各种功能。
  • Linux 驱动开发着眼于硬件和操作系统内核之间的驱动程序层,当然,内核配置与编译、引导加载程序开发、根文件系统构建等内容也是必不可少的。

参考链接

封面

由 DALL-E-3 生成

相关推荐
知白守黑26715 分钟前
Linux磁盘阵列
linux·运维·服务器
维尔切1 小时前
Linux中基于Centos7使用lamp架构搭建个人论坛(wordpress)
linux·运维·架构
tan77º2 小时前
【项目】分布式Json-RPC框架 - 项目介绍与前置知识准备
linux·网络·分布式·网络协议·tcp/ip·rpc·json
sukalot5 小时前
window显示驱动开发—在混合系统中使用跨适配器资源
数据库·驱动开发·音视频
正在努力的小河5 小时前
Linux设备树简介
linux·运维·服务器
荣光波比5 小时前
Linux(十一)——LVM磁盘配额整理
linux·运维·云计算
LLLLYYYRRRRRTT5 小时前
WordPress (LNMP 架构) 一键部署 Playbook
linux·架构·ansible·mariadb
轻松Ai享生活6 小时前
crash 进程分析流程图
linux
大路谈数字化7 小时前
Centos中内存CPU硬盘的查询
linux·运维·centos
luoqice8 小时前
linux下查看 UDP Server 端口的启用情况
linux