文章目录
- 1. 概述。
- 2. ko编译
- 3.环境构建
- 3.1 集成ch343驱动
- 3.2 修改内核配置
- 3.3 编译内核模块
- 3.4 部署安装
最近在RK3588的开发板上要接一个外部的小板,需要使用的ch343驱动,但是rk3588的板子上没有自带的ch343的驱动,就需要自己手动编译一个ch343.ko的驱动进行安装使用。
1. 概述。
在linux中所有的设备都需要驱动,才能被正确识别,一般的驱动会直接编译在内核中,也可以以单独的模块存在,然后加载到系统中。rk3588编译出来的boot镜像,里面就包含了很多的驱动。有时候,我们需要新加一些外设的时候,将驱动单独编译成 一个模块文件是很方便的事情。
这个驱动模块文件就是.ko文件。
linux提供了一种称为模块(Module)的机制,模块具有以下特点:
- 模块自身不被编译到内核映像中,从而不影响内核映像的大小
- 一旦模块被加载,模块和内核中的其他部分的功能完全一样。
2. ko编译
.ko文件能否像普通的可执行程序一样使用gcc直接编译.c文件那?
答案是不可以。
驱动程序中使用了大量的linux内核函数和数据,因此驱动程序的编译依赖linux内核源码。如下图:
#include <linux/errno.h>
#include <linux/idr.h>
#include <linux/init.h>
#include <linux/kernel.h>
#include <linux/list.h>
#include <linux/module.h>
#include <linux/mutex.h>
#include <linux/seq_file.h>
#include <linux/serial.h>
#include <linux/slab.h>
#include <linux/tty.h>
#include <linux/tty_driver.h>
#include <linux/tty_flip.h>
#include <linux/uaccess.h>
#include <linux/usb.h>
#include <linux/usb/cdc.h>
#include <linux/version.h>
#include <asm/byteorder.h>
#include <asm/unaligned.h>
一般的嵌入式环境是不包含内核源码的,使用的都是编译好的内核。所以要编译ko文件,需要一套内核的源码,对于嵌入式的板子还需要交叉编译环境。对于rk3588,集成的SDK里面已经包含了交叉编译环境和内核源码,所以可以直接使用。
然后就是编译方式,有两种
- 整编内核,就相当于编译boot.img.
- 单独编译ko文件。
本文只讲如何单独编译ko文件,如何整编内核,rk的文档介绍的很详细。
3.环境构建
首先下载 Rockchip 的 RK3588 Linux SDK.
下载ch343驱动源码。
3.1 集成ch343驱动
- 将下载好的ch343.c和ch343.h文件放到内核源码树的适当位置。在rk3588的sdk中,放在目录kernel/drivers/usb/serial/中即可。
- 修改内核的Makefile和Kconfig文件,以包含新的驱动。
在kernel/drivers/usb/serial/目录下有Makefile和Kconfig两个文件,需要修改这两个文件。
在Makefile文件中添加一行,用于编译CH343驱动,
obj-$(CONFIG_USB_SERIAL_CH343) += ch343.o
其中CONFIG_USB_SERIAL_CH343是驱动配置选项的名称(需要在Kconfig中定义这个选项)。
同样在目录kernel/drivers/usb/serial/中找到Kconfig文件进行修改。
添加一个新的配置选项来代表你的CH343驱动。这通常涉及到使用config、tristate(对于模块)、bool(对于内置选项)等关键字,以及depends on(依赖项)和help(帮助文本)等可选字段。
在文件中增加如下内容:
config USB_SERIAL_CH343
tristate "USB Winchiphead CH343 Single Port Serial Driver"
help
Say Y here if you want to use a Winchiphead CH343 single port
USB to serial adapter.
To compile this driver as a module, choose M here: the
module will be called ch343.
3.2 修改内核配置
进入到rk3588的SDK的kernel目录下。
defconfig文件是Linux内核构建过程中用于配置内核选项的文件,RK3588开发板默认配置文件为 rockchip_linux_defconfig,通过以下命令修改。
# 进入 SDK 下的 kernel 目录
cd kernel
# 在arm64架构下,通过交互式的方式打开内核配置选项。
sudo make ARCH=arm64 nconfig KCONFIG_CONFIG=arch/arm64/configs/rockchip_linux_defconfig
执行后会显示交互界面:
- 打开交互菜单后,依次选择[Device Drivers] -> [USB support] -> [USB Serial Converter support],
- 选定 USB Generic Serial Driver,
- 选择 USB Winchipherd CH343 Single Port Serial Driver, (注:此处按M键选中,M表示编译为模块)。
- 保存退出。
3.3 编译内核模块
从kernel目录退到上一级目录,通过build.sh进行编译,之所以使用build.sh是因为这个脚本已经配置好了交叉编译的环境,不需要自己再配置,执行起来比较方便。
crabe@crabe-ThinkPad:~/software/rk3588/rk3588_linux/linux$ ./build.sh modules
processing option: modules
============Start building kernel modules============
TARGET_KERNEL_ARCH =arm64
TARGET_KERNEL_CONFIG =rockchip_linux_defconfig
TARGET_KERNEL_CONFIG_FRAGMENT =rk3588_linux.config
==================================================
Using prebuilt GCC toolchain: /home/crabe/software/rk3588/rk3588_linux/linux/prebuilts/gcc/linux-x86/aarch64/gcc-arm-10.3-2021.07-x86_64-aarch64-none-linux-gnu/bin/aarch64-none-linux-gnu-
make: Entering directory '/home/crabe/software/rk3588/rk3588_linux/linux/kernel'
#
# configuration written to .config
#
Using .config as base
Merging ./arch/arm64/configs/rk3588_linux.config
Value of CONFIG_BCMDHD_PCIE is redefined by fragment ./arch/arm64/configs/rk3588_linux.config:
Previous value: # CONFIG_BCMDHD_PCIE is not set
New value: CONFIG_BCMDHD_PCIE=y
Value of CONFIG_MALI_CSF_SUPPORT is redefined by fragment ./arch/arm64/configs/rk3588_linux.config:
Previous value: # CONFIG_MALI_CSF_SUPPORT is not set
New value: CONFIG_MALI_CSF_SUPPORT=y
#
# merged configuration written to .config (needs make)
#
.config:7129:warning: override: BCMDHD_PCIE changes choice state
#
# configuration written to .config
#
make: Leaving directory '/home/crabe/software/rk3588/rk3588_linux/linux/kernel'
make: Entering directory '/home/crabe/software/rk3588/rk3588_linux/linux/kernel'
SYNC include/config/auto.conf.cmd
CALL scripts/atomic/check-atomics.sh
CALL scripts/checksyscalls.sh
CC [M] drivers/usb/serial/ch343.o
MODPOST modules-only.symvers
GEN Module.symvers
CC [M] drivers/usb/serial/ch343.mod.o
LD [M] drivers/usb/serial/ch343.ko
make: Leaving directory '/home/crabe/software/rk3588/rk3588_linux/linux/kernel'
Running build_modules succeeded.
编译出来的ko文件就在kernel/drivers/usb/serial/目录下。
crabe@crabe-ThinkPad:~/software/rk3588/rk3588_linux/linux/kernel/drivers/usb/serial$ ls | grep ch343
ch343.c
ch343.h
ch343.ko
ch343.mod
ch343.mod.c
ch343.mod.o
ch343.o
3.4 部署安装
将ch343.ko拷贝到开发板上进行安装即可。
#安装
insmod ch341.ko
确认是否安装成功了,使用命令lsmod
crabe@RK3588:~$ lsmod
Module Size Used by
ch343 32768 0
此时再插入外设,在/dev目录下就能正常看到设备了。