SDK 环境部署(ubuntu22.04 X86_64平台)
Omni3576-SDK 主要在 Ubuntu 22.04 LTS 系统上进行开发和测试。为减少开发过程中可能出现的编译错误等问题,建议用户使用与我们相同或相近版本的操作系统,以确保开发环境的一致性和稳定性。注意:此 SDK 仅限于编译 Linux 系统使用。暂时还未公开 Android 14 的 SDK 源代码。SDK 运行环境应为 X86_64 架构的 Ubuntu 系统,其他架构可能会导致兼容性问题。
1. Luckfox-Omni3576-SDK 介绍
SDK(Software Development Kit) 是 软件开发工具包,它是一组工具、库、示例代码、文档、和相关支持文件,用于帮助开发者构建针对特定平台、操作系统、硬件、或者其他软件的应用程序。开发板上的操作系统,通常是基于 SDK 进行定制和开发的。SDK 提供了开发板所需的基础软件(内核、驱动、Bootloader 等),开发者在此基础上进行定制,生成最终可以在开发板上运行的系统固件。
1.1 SDK 目录说明
SDK 工程目录包含有 buildroot、debian、yocto、app、kernel、u-boot、device、docs、external、prebuilts 等目录。采用manifest来管理仓库,用repo工具来管理每个目录或其子目录会对应的 git 工程。
SDK目录结构。
├── build.sh -> device/rockchip/common/scripts/build.sh ---- SDK编译脚本
├── app ----------------------------- 存放上层应用 APP,主要是一些应用 Demo
├── buildroot ----------------------- 基于 Buildroot(2024)开发的根文件系统
├── debian -------------------------- 基于 Debian bookworm(12) 开发的根文件系统
├── device/rockchip ----------------- 存放芯片板级配置以及 SDK 编译和打包固件的脚本和文件
├── docs ---------------------------- 存放通用开发指导文档、芯片平台相关文档、Linux 系统开发相关文档、其他参考文档等
├── external ------------------------ 存放第三方相关仓库,包括显示、音视频、摄像头、网络、安全等
├── kernel -------------------------- 存放 Kernel 开发的代码
├── output -------------------------- 存放每次生成的固件信息、编译信息、XML、主机环境等
├── prebuilts ----------------------- 存放交叉编译工具链
├── rkbin --------------------------- 存放 Rockchip 相关二进制和工具
├── rockdev ------------------------- 存放编译输出固件,实际软链接到 output/firmware
├── tools --------------------------- 存放 Linux 和 Window 操作系统下常用工具
├── u-boot -------------------------- 存放基于 v2017.09 版本进行开发的 U-Boot 代码
└── yocto --------------------------- 存放基于 Yocto 5.0 开发的根文件系统镜像存放目录。
rockdev/
├── MiniLoaderAll.bin --------------- SPL 引导加载器,负责初始化最基本的硬件、后级固件加载
├── misc.img ------------------------- 兼容 Android 引导流程
├── parameter.txt -------------------- 分区表信息
├── uboot.img ------------------------ uboot 镜像
├── boot.img ------------------------ kernel 镜像
├── rootfs.img ----------------------- 根文件系统镜像文件
├── update.img ----------------------- 完整的镜像文件
└── recovery.img --------------------- 系统维护
1.2 SDK 配置文件说明
Omni3576 系列 SDK 配置文件存放在
device/rockchip/rk3576
目录下。-rw-rw-r-- 1 xt xt 1673 9月 11 09:37 boot4recovery.its
-rw-rw-r-- 1 xt xt 1430 9月 11 09:37 boot.its
-rwxrwxr-x 1 xt xt 293 9月 11 09:37 luckfox_omni3576_buildroot_defconfig
-rwxrwxr-x 1 xt xt 290 9月 11 09:37 luckfox_omni3576_debian_defconfig
-rw-rw-r-- 1 xt xt 477 9月 11 09:37 parameter-ab.txt
-rwxrwxr-x 1 xt xt 480 9月 11 09:37 parameter.txt
-rw-rw-r-- 1 xt xt 1429 9月 11 09:37 zboot.its不同系统对应的环境变量。
RK_ROOTFS_SYSTEM=buildroot #编译buildroot系统
RK_ROOTFS_SYSTEM=debian #编译debian系统
2. Ubuntu22.04 环境下编译镜像
1.1 搭建编译环境
安装依赖环境:
sudo apt update
sudo apt-get update && sudo apt-get install git ssh make gcc libssl-dev \
liblz4-tool expect expect-dev g++ patchelf chrpath gawk texinfo chrpath \
diffstat binfmt-support qemu-user-static live-build bison flex fakeroot \
cmake gcc-multilib g++-multilib unzip device-tree-compiler ncurses-dev \
libgucharmap-2-90-dev bzip2 expat gpgv2 cpp-aarch64-linux-gnu libgmp-dev \
libmpc-dev bc python-is-python3 python2设置 Python 环境设置。
#默认情况下链接的是python3
$ python --version
Python 3.10.12
which python2
sudo ln -sf /usr/bin/python2 /usr/bin/python从网盘链接下载最新的 SDK,并解压缩文件(请勿直接复制解压命令,因 SDK 名称可能会随着更新而变化)。
mkdir Omni3576-sdk && cd Omni3576-sdk
tar -xzvf luckfox-omni3576-241024.tar.gz将解压后的文件进行解包。
.repo/repo/repo sync -l
设置环境变量。
export RK_ROOTFS_SYSTEM=buildroot #编译buildroot系统
export RK_ROOTFS_SYSTEM=debian #编译debian系统编译镜像。
$ ./build.sh lunch
############### Rockchip Linux SDK ###############
Manifest: rk3576_linux6.1_release_v1.0.0_20240620.xml
Log colors: message notice warning error fatal
Parsing supported commands...
Log saved at /home/xt/new3576/output/sessions/2024-10-22_18-00-36
Pick a defconfig:
1. luckfox_omni3576_buildroot_defconfig
2. luckfox_omni3576_debian_defconfig
Which would you like? [1]: 1
Switching to defconfig: /home/xt/new3576/device/rockchip/.chip/luckfox_omni3576_buildroot_defconfig
mkdir -p /home/xt/new3576/output/kconf/lxdialog
make CC="gcc" HOSTCC="gcc" \
obj=/home/xt/new3576/output/kconf -C /home/xt/new3576/device/rockchip/common/kconfig -f Makefile.br conf
make[1]: Entering directory '/home/xt/new3576/device/rockchip/common/kconfig'
gcc -D_DEFAULT_SOURCE -D_XOPEN_SOURCE=600 -DCURSES_LOC="<ncurses.h>" -DNCURSES_WIDECHAR=1 -DLOCALE -I/home/xt/new3576/output/kconf -DCONFIG_=\"\" -MM *.c > /home/xt/new3576/output/kconf/.depend 2>/dev/null || :
gcc -D_DEFAULT_SOURCE -D_XOPEN_SOURCE=600 -DCURSES_LOC="<ncurses.h>" -DNCURSES_WIDECHAR=1 -DLOCALE -I/home/xt/new3576/output/kconf -DCONFIG_=\"\" -c conf.c -o /home/xt/new3576/output/kconf/conf.o
gcc -D_DEFAULT_SOURCE -D_XOPEN_SOURCE=600 -DCURSES_LOC="<ncurses.h>" -DNCURSES_WIDECHAR=1 -DLOCALE -I/home/xt/new3576/output/kconf -DCONFIG_=\"\" -I. -c /home/xt/new3576/output/kconf/zconf.tab.c -o /home/xt/new3576/output/kconf/zconf.tab.o
gcc -D_DEFAULT_SOURCE -D_XOPEN_SOURCE=600 -DCURSES_LOC="<ncurses.h>" -DNCURSES_WIDECHAR=1 -DLOCALE -I/home/xt/new3576/output/kconf -DCONFIG_=\"\" /home/xt/new3576/output/kconf/conf.o /home/xt/new3576/output/kconf/zconf.tab.o -o /home/xt/new3576/output/kconf/conf
rm /home/xt/new3576/output/kconf/zconf.tab.c
make[1]: Leaving directory '/home/xt/new3576/device/rockchip/common/kconfig'
#
# configuration written to /home/xt/new3576/output/.config
#
$ ./build.sh- 注意编译ubuntu时需要注意使用sudo,否则会导致文件系统错误
- 下文就不一一区分两者指令区别,请自行根据情况选择
1.2 部分编译
单独编译U-Boot
./build.sh uboot
- 生成镜像文件: rockdev/MiniLoaderAll.bin rockdev/uboot.img
单独编译kernel
./build.sh kernel
- 生成镜像文件: rockdev/boot.img
固件打包
./build.sh firmware
3. 文件共享
虚拟机和 Windows 电脑之间文件传输可以使用 Samba 服务来实现文件共享,在 Windows 的网络邻居中,可以轻松访问虚拟机的文件系统,非常便捷。
3.1 Ubuntu 环境配置
下载和安装 Samba 。
sudo apt-get update
sudo apt-get install samba -y配置Samba服务。
sudo vim /etc/samba/smb.conf
#在文件末尾填入以下内容
[share]
comment = share folder
browseable = yes
path = /home/luckfox
create mask = 0700
directory mask = 0700
valid users = luckfox
force user = luckfox
force group = luckfox
public = yes
available = yes
writable = yes- 其中luckfox为主机名,根据自己实际主机名填写。
设置分享账户密码。
sudo smbpasswd -a luckfox
查看虚拟机或主机的 IP 地址。
luckfox@luckfox:~/Luckfox-Pico/luckfox-pico$ ifconfig
enp0s3: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
inet 192.168.10.61 netmask 255.255.252.0 broadcast 192.168.11.255
inet6 fe80::814f:a51e:5f24:f0f7 prefixlen 64 scopeid 0x20<link>
ether 08:00:27:d2:60:b9 txqueuelen 1000 (Ethernet)
RX packets 699559 bytes 754875799 (754.8 MB)
RX errors 0 dropped 4 overruns 0 frame 0
TX packets 53024 bytes 3278048 (3.2 MB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
lo: flags=73<UP,LOOPBACK,RUNNING> mtu 65536
inet 127.0.0.1 netmask 255.0.0.0
inet6 ::1 prefixlen 128 scopeid 0x10<host>
loop txqueuelen 1000 (Local Loopback)
RX packets 190 bytes 24144 (24.1 KB)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 190 bytes 24144 (24.1 KB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
3.2 Windows 环境
在 Windows 地址栏输入(根据自己实际 IP 地址填写)。
输入虚拟机账户密码默认都是 luckfox 。
成功登录虚拟机或主机。
4. Linux下加载 ko 驱动模块
4.1 ko 文件简介
在Linux操作系统中,.ko文件是内核模块文件的扩展名。内核模块是一种可以在运行时加载和卸载的代码,用于扩展Linux内核的功能,无需重新编译整个内核。每个.ko文件包含模块的代码和元数据,允许用户在不重新启动系统的情况下添加或移除特定功能,如驱动程序或文件系统支持。
4.2 ko文件的优点
- 动态加载和卸载:内核模块可以在运行时动态加载到内核中,也可以随时卸载,无需重新启动系统。这使得系统管理员和开发人员能够在不中断系统运行的情况下添加、测试或修复功能。
- 节约资源:内核模块允许将不常用的功能作为模块加载,从而减少了系统内核的大小和内存占用。这有助于提高系统的资源利用率。
- 定制性: 内核模块允许用户根据需要添加或移除特定功能,从而实现定制化的系统。这对于嵌入式系统、特定硬件支持和特定应用场景非常有用。
- 减少编译时间: 重新编译整个内核可能会花费大量时间,而使用内核模块则可以避免这种情况。只需编译和加载所需的模块,节省了时间和资源。
- 快速调试和开发:内核模块可以在不重新启动系统的情况下加载和卸载,这使得驱动程序和其他内核代码的调试和开发变得更加高效。
- 易于维护: 内核模块的独立性使得它们可以独立于整个内核进行维护和升级。这有助于降低系统维护的复杂性。
- 增加兼容性:内核模块可以根据需要支持多个内核版本,从而增加了软件的兼容性和灵活性。
4.3 应用实例
下载工程文件戳我下载,整个工程只有两个文件,一个helloworld.c,一个用来控制编译的Makefile。
将工程文件复制到已经安装了编译通过的 Luckfox Omni3576 SDK 的 Ubuntu 主机或虚拟机上。
打开并修改 Makefile 文件,以便 make 命令能够进入指定的内核源代码目录,即 Luckfox Omni3576 SDK 中的 kernel-6.1 目录。建议直接下载 Makefile 文件,若使用复制粘贴,请自行调整 Tab 缩进问题。
obj-m += helloworld.o
KDIR:=/home/xt/zt-ssd/kernel-6.1
PWD?=$(shell pwd)
all:
make -C $(KDIR) M=$(PWD) modules
echo $(PWD)
clean:
rm -f *.ko *.o *.mod *.mod.o *.mod.c *.symvers *.order代码部分:
#include <linux/module.h>
#include <linux/init.h>
static int helloworld_init(void)
{
printk("helloworld!\n");
return 0;
}
static void helloworld_exit(void)
{
printk("helloworld bye\n");
}
module_init(helloworld_init);
module_exit(helloworld_exit);
MODULE_LICENSE("GPL");
MODULE_AUTHOR("Luckfox");
MODULE_VERSION("V1.0");- 模块加载函数:当通过insmod或modprobe命令加载内核模块时,模块的加载函数会自动被内核执行,完成本模块的相关初始化工作。 Linux内核模块加载函数一般以__init标识声明,模块加载函数以“module_init(函数名)”的形式被指定。它返回整型值,若初始化成功,应返回0。而在初始化失败时,应该返回错误编码。在Linux内核里,错误编码是一个接近于0的负值。
- 模块卸载函数:当通过rmmod命令卸载某模块时,模块的卸载函数会自动被内核执行,完成与模块卸载函数相反的功能。 Linux内核模块加载函数一般以__exit标识声明,模块卸载函数在模块卸载的时候执行,而不返回任何值,且必须以“module_exit(函数名)”的形式来指定。
- 模块许可证声明许可证(LICENSE):明描述内核模块的许可权限,如果不声明LICENSE,模块被加载时,将收到内核被污染(Kernel Tainted)的警告。在Linux内核模块领域,可接受的LICENSE包括“GPL”、“GPL v2”、“GPLand additional rights”、“Dual BSD/GPL”、“Dual MPL/GPL”和“Proprietary”(关于模块是否可以采用非GPL许可权,如“Proprietary”,这个在学术界和法律界都有争议)。大多数情况下,内核模块应遵循GPL兼容许可权。Linux内核模块最常见的是以MODULE_LICENSE(“GPL v2”)语句声明模块采用GPL v2。
- 模块作者等信息声明:MODULE_AUTHOR、MODULE_DESCRIPTION、MODULE_VERSION、MODULE_DEVICE_TABLE、MODULE_ALIAS分别声明模块的作者、描述、版本、设备表和别名
进入工程文件中,执行以下命令(其中CROSS_COMPILE的地址需要按SDK的实际路径填写):
export ARCH=arm64 CROSS_COMPILE=/home/xt/zt-ssd/prebuilts/gcc/linux-x86/aarch64/gcc-arm-10.3-2021.07-x86_64-aarch64-none-linux-gnu/bin/aarch64-none-linux-gnu-
make
#执行 make 后打印信息
$ make
make -C /home/xt/zt-ssd/kernel-6.1 M=/home/xt/ko-test modules
make[1]: Entering directory '/mnt/zitai-ssd/xt/kernel-6.1'
CC [M] /home/xt/ko-test/helloworld.o
MODPOST /home/xt/ko-test/Module.symvers
CC [M] /home/xt/ko-test/helloworld.mod.o
LD [M] /home/xt/ko-test/helloworld.ko
make[1]: Leaving directory '/mnt/zitai-ssd/xt/kernel-6.1'
echo /home/xt/ko-test
/home/xt/ko-test把 helloworld.ko上传到开发板上,可以使用 SCP,ADB等方式。
scp helloworld.ko root@192.168.10.188:/
执行以上命令可以进行验证。
root@rk3576-buildroot:/# insmod helloworld.ko
[13206.339477] helloworld!
root@rk3576-buildroot:/# rmmod helloworld.ko
[13181.378401] helloworld bye最后我们使用 dmesg 查看日志。
root@rk3576-buildroot:/# dmesg | grep hello
[13105.396731] helloworld!
[13181.378401] helloworld bye
5. 内核配置
menuconfig
是 Linux 内核的配置工具,提供终端图形化界面,便于直观地修改配置文件,同时自动处理配置项依赖关系。其他类似的配置界面还包括 nconfig
和 xconfig
,下面介绍 menuconfig
的基本功能和操作。
5.1 配置界面
执行如下指令,打开配置界面:
cd <SDK目录>/kernel-6.1
make ARCH=arm64 luckfox_linux_defconfig
make ARCH=arm64 menuconfig
make ARCH=arm64 savedefconfig
cp defconfig arch/arm64/configs/luckfox_linux_defconfig
5.2 基本操作
执行命令后显示的配置界面如下:
从界面上方我们可以看到 menuconfig 的基本操作和说明。
按键操作:
- ↑↓PgUpPgDn:浏览、选择内核功能
- ←→:选择Select、Exit等操作
- Enter:进入子菜单吃的
- Y:选中这项功能
- N:排除这项功能
- M:以模块的形式选择
- Esc:双击Esc返回上一级菜单
- ?:查看这项功能的帮助信息
- /:搜索
图例说明:
[*]
:已选中的项目[ ]
:未选中的项目<M>
:已选中的项目(以模块形式)< >
:未选中的项目(以模块形式)
中间区域是用户选择各项功能的地方,您可以使用上下方向键进行导航,同时也支持直接按下行首带颜色的字母,跳转到该行,如 Kernel Features 的首字母 K,当我们按下 K 键时就会直接跳转至该行。
底部区域包含了一些常用的操作选项,为用户提供了重要的交互功能。它们的作用如下:
<Select>
:进入当前高亮配置项的子菜单<Exit>
:退出当前菜单,返回上一层<Help>
:提供当前高亮配置项的帮助信息<Save>
:保存当前的配置更改,但不退出配置工具<Load>
:加载指定的配置文件
5.3 功能简述
内核配置界面的中间部分是一个多层级的菜单系统,您可以通过上下方向键进行导航,按 Enter 键进入子菜单,按 Esc 键返回上一级菜单,通过这个界面,用户可以根据系统需求灵活配置内核,选择需要的功能和驱动,以构建适合特定硬件和用途的定制内核,以下是 Linux 内核配置界面中的主要项目:
- General setup(常规设置):运行时的基本配置
- Kernel Features(内核特性):核心功能的配置,如模块化、块设备支持等
- CPU Power Management(CPU 功耗管理):配置 CPU 的功耗管理选项
- Enable loadable module support(启用可加载模块支持):是否支持内核模块
- IO Schedulers(I/O 调度器):配置磁盘 I/O 调度器
- Networking support(网络支持):配置网络支持,包括协议、设备等
- Device Drivers(设备驱动):配置各种设备驱动,如输入设备、USB 设备等
- File systems(文件系统):配置文件系统支持,选择支持的文件系统类型
- Security options(安全选项):配置内核安全相关选项
- Cryptographic API(加密 API):配置加密 API 支持
6. Buildroot 配置
Buildroot 是一个专为嵌入式系统设计的工具,其目标是简化嵌入式 Linux 系统的构建过程。通过配置 Buildroot,您可以定制嵌入式系统中包含的软件包和库,以满足特定的需求。
打开配置界面。
cd buildroot
make ARCH=arm64 luckfox_omni3576_defconfig
make ARCH=arm64 menuconfig保存配置。
make ARCH=arm64 savedefconfig
cd ..
./build.sh rootfs