文章目录
- 基于树莓派的OpenEuler基础实验一
- 一、树莓派介绍
- 树莓派较普通电脑的优势
- 1、廉价便携可折腾
- 2、树莓派运行开源的Linux操作系统
- 3、编程好平台
- 4、开源大社区
- 5、引脚可编程
- 6、便携随身带
- 7、灵活可扩展
- 二、openEuler embedded介绍
- 三、树莓派开机指南
- 1. 硬件准备
- 2. 软件准备
- 3. openEuler embedded的构建
- 4. 第一次开机
- (1)格式化SD卡
- (2)烧录镜像
- (3)Wi-Fi网络配置
- 使能无线驱动
- 启用Wi-Fi网卡
- (4)远程登陆树莓派
- ★树莓派的关机
- 四、基于SDK的应用开发
- 1. 交叉编译
- 交叉编译是什么
- 为什么需要交叉编译?
- 2. SDK环境配置
- 3. 使用SDK交叉编译hello world样例
- 五、基于树莓派的OpenEuler内核模块基础实验
- 1. Linux内核模块
- 一些常用模块指令
- 2. 第一个内核模块helloworld
- (1)编写代码和生成hello内核模块
- (2)将编译好的hello.ko拷贝到openEuler Embedded系统中
- (3)原理
基于树莓派的OpenEuler基础实验一
一、树莓派介绍
树莓派由英国的树莓派基金会发行,旨在通过发行这个廉价开源的可随意破解的微型计算机,推动中小学编程教育,发行之后很快在全世界的开源创客圈中流行。截止到2018年10月,最新版本的树莓派主板是3B+,国内某宝上卖230元左右,还有更微型的树莓派主板Zero,国内某宝卖100元左右。树莓派是一种麻雀虽小五脏俱全的掌上电脑,它可以完成普通电脑的所有功能,有USB接口、HDMI显示屏接口、网线接口、耳机接口、蓝牙、Wifi、可编程引脚,可外接摄像头和显示屏。其CPU计算速度大概相当于iphone 4S,足以满足创客开发日常需求。而且,树莓派是最适合学习Linux和Python的工具,而且能通过它登堂入室,走进计算机科学的大千世界,搭上目前火热的人工智能、物联网、嵌入式开发、智能硬件的车。中国很多高校的毕业设计和课程设计要用到树莓派,特别是自动化专业。
树莓派较普通电脑的优势
1、廉价便携可折腾
在国内您花费千元左右就能够购买全套顶配的开发配件。在使用树莓派的时候,你可以大胆地尝试电路改线、CPU超频、破解、删库、病毒攻击、渗透测试、内存挤占等一系列实践,大不了就是重新安装操作系统(5分钟不到),闹翻天也不过买块新树莓派(五百元左右)。这样就不必冒着风险折腾自家宝贵的笔记本电脑和台式电脑。
史上最全的树莓派购买指南
2、树莓派运行开源的Linux操作系统
普通电脑上普遍运行Windows操作系统,但树莓派上运行的是Linux操作系统。你可以接触到真正的程序员和黑客每天面对的酷炫的Linux命令行和图形界面。Linux是开源的操作系统,由世界各地的开发者历经三十年的时间逐渐积累优化,衍生出许多发行版(比如智能手机上的安卓操作系统),Linux的诞生和发展催生了开源软件文化和开源软件社群,很多软件和代码库对Linux极其友好,但如果你用Windows安装配置就会发现十分困难。
十个使用Linux操作系统的理由
3、编程好平台
作为旨在为编程教学而生的计算机,树莓派内置了各种编程语言的开发环境,包括Python2、Python3、Java、Wolfram、科学计算内核,还有艺术图形可视化编程工具Processing、音乐可视化编程工具Sonic Pi、创客可视化编程工具Scratch、NodeJS、我的世界Mine Craft等。无需复杂的安装配置,直接上手敲代码运行即可。
4、开源大社区
树莓派的所有硬件、操作系统、软件、杂志、论坛全部是开源免费的,并且在全世界有规模庞大的玩家社群,他们贡献出自己的奇思妙想和源代码,你可以直接用别人写好的库和代码。一些知名开源项目,比如谷歌的人工智能框架TensorFlow、人脸识别项目face_recognition、开源机器视觉库SimpleCV、OpenCV、安卓操作系统等,都会专门开发树莓派可用的版本并撰写技术手册。
树莓派官方杂志MagPi的中文翻译版
开源人脸识别项目face_recognition
在树莓派上安装开源机器视觉库OpenCV
5、引脚可编程
树莓派主板上有GPIO引脚(通用输入输出接口),在3B+主板上是40个引脚,通过对这些引脚编程,可以控制各种各样的传感器、电子元器件、电路,进而进行机器人控制、数字电路实验,开发物联网应用。
6、便携随身带
树莓派非常便携,只有信用卡大小,可以随身携带,可以用普通安卓手机充电器或者移动电源供电,可以随身携带,非常方便。各种上天入地,翻山下海的任务都可以交给树莓派。树莓派除了传统的3B+之外还有微型的树莓派Zero,专门为便携嵌入式设计,可以放在手心里。
基于树莓派摄像头的冷水珊瑚礁科考
基于树莓派的FRILLER多地形机器人
7、灵活可扩展
你可以用树莓派进行各领域的开发,搭上当前火热的人工智能、大数据、物联网的车。搭配一个摄像头模块(40元),你可以做网络摄像头以及各种机器视觉和人工智能应用。搭配一个英特尔神经棒(500元),可以大大加快神经网络计算速度,可以达到毫秒级的物体检测。
二、openEuler embedded介绍
为从生态上解决国内嵌入式和实时操作系统遭受国外技术垄断的风险,华为公司推出了旨在具备实时性、安全可靠、互联互通、混合部署等特性的开源嵌入式操作系统OpenEuler Embedded。它基于openEuler社区的嵌入式系统软件平台,可同时部署Linux内核、自研微内核以及实时OS。OpenEuler Embedded针对嵌入式场景的需求,在内核特性、系统配置、软件包组合、镜像裁剪、安全加固、轻量化等方面进行创新,其OS镜像最小可达5M,并具有<5S的快速启动能力。OpenEuler Embedded总体架构如下图所示:
在硬件方面,OpenEuler Embedded目前重点支持ARM架构的处理器,如ARM32、ARM64,并通过QEMU和树莓派4B两个平台承载。未来OpenEuler Embedded还计划实现对RISC-V、X86、龙芯等架构的支持,全面面向多核异构嵌入式系统。在系统软件方面,OpenEuler Embedded采用了混合部署架构,加入linux内核以继承Linux的管理能力、丰富的生态,同时可加入RTOS内核以使系统能够支撑具有高实时、高可靠、高安全等需求的应用场景。在此基础上,OpenEuler Embedded摒弃了低效的资源静态部署方案,采用嵌入式虚拟化的办法,解决了混合关键性系统各子系统之间的兼容性、安全性等问题,实现了对各子系统内核的良好兼容,灵活开发和部署。OpenEuler Embedded还引入分布式软总线技术,打通了鸿蒙和欧拉两大生态。
在操作系统的开发方面,介于嵌入式系统资源有限,OpenEuler Embedded发布了专用的SDK (Software Development Kit)并集成了与OpenEuler Embedded配套的嵌入式系统仿真方案,未来计划集成图形化IDE (Integrated Development Environment), 组成一套完整的开发工具体系,实现对操作系统的开发、调试与优化。
综上所述,OpenEuler Embedded具有强大的开发平台,广阔的应用场景,着眼于生态建设,并且其结构的设计符合嵌入式和实时操作系统的未来发展趋势。因此,本课程的实践部分将基于OpenEuler开发,为中国嵌入式实时系统打破技术壁垒,走向世界,提供人才基础。
考虑到openeuler embedded更适用于产品化,在教学中对学生的门槛比较高,因此,为了方便教学,实验过程中,学生可自行构建openeuler embedded,或者选用已经构建好的openeuler树莓派镜像。
三、树莓派开机指南
1. 硬件准备
- SD卡、读卡器、树莓派实验套件、一台电脑
2. 软件准备
- 下载压缩包【树莓派开机工具】,解压,共有两个文件夹
- 基本工具包括:SD卡格式化工具SD Formatter、镜像烧录工具、局域网IP扫描器、远程ssh工具
- 开机常用文件:包括ssh空文件和wifi配置文件
3. openEuler embedded的构建
环境:Ubuntu20.04
1)运行环境准备
-
安装python3和pip
- apt-get install python3 python3-pip
-
安装oebuild
sudo su
pip install oebuild
- sudo apt install docker docker.io -y
- sudo groupadd docker
- sudo usermod -a -G docker $(whoami)
- sudo systemctl-reload && systemctl restart docker
- sudo chmod o+rw /var/run/docker.sock
2)构建
-
初始化oebuild
- cd ~
- oebuild init //该操作会初始化 oebuild 的目录,表示要初始化目录的名称
-
oebuild更新
-
cd
-
oebuild update
更新工作主要有两点:
- pull相关的运行容器镜像
- 从gitee上下载yocto-meta-openeuler仓代码,如果本地没有openeuler相关容器,则在这一步执行会比较漫长,请耐心等待。
-
-
编译环境建立
//进入oebuild工作目录,创建对应的编译配置文件
- cd
- oebuild generate -p raspberrypi4-64 //生成raspberrypi4-64配置文件
- oebuild bitbake //进入构建交互终端
- bitbake openeuler-image //构建镜像
- bitbake openeuler-image -c do_populate_sdk //构建sdk
-
二进制介绍
-
Image
: 树莓派内核镜像 -
openeuler-glibc-x86-64-openeuler-image-cortexa72-raspberrypi4-64-toolchain-*.sh
: SDK工具链 -
openeuler-image-raspberrypi4-64-*.rootfs.rpi-sdimg
: openEuler Embedded树莓派支持SD卡镜像 -
将得到的
openeuler-image-raspberrypi4-64-20230809013758.rootfs.rpi-sdimg
镜像通过共享文件夹传输给windows,windows后续再将其烧录到树莓派的SD卡中。
-
4. 第一次开机
(1)格式化SD卡
-
如果SD卡是旧卡,需要用SDFormatter格式化工具先格式化。如果用新的SD卡可以跳过此步。
格式化之后,可以看到SD卡对应的盘变成了空盘。
(2)烧录镜像
将第3步中获得的镜像文件
openeuler-image-raspberrypi4-64-20230809013758.rootfs.rpi-sdimg
烧录到SD卡中
-
打开烧录工具Win32DiskImager(或者另一个镜像烧录工具balena-etcher),选好镜像文件和要烧录的SD卡对应的盘。
选SD卡对应盘符号的时候一定要小心,不要选到其它盘或者硬件,不然镜像可能会覆盖写到其它盘里
-
然后点击write,开始烧录
-
烧录成功后,将空白的ssh文件放入SD卡的boot盘【旨在一开始就让树莓派允许SSH进行连接】
- 手动创建一个空白记事本.txt文件,命名为ssh,重命名,删除.txt扩展名,将这个文件放入SD卡的boot盘中。
- 在003文件夹中也有已创建好的ssh文件,可以直接复制到SD卡的boot盘中
(3)Wi-Fi网络配置
需要显示屏
配置wifi文件
-
新建一个空白文件wpa_supplicant.txt
-
编辑wpa_supplicant.txt文件,输入以下配置,其中可以使用多个network{}来配置多个wifi,【不建议使用校园网,需要认证】
country=GB ctrl_interface=DIR=/var/run/wpa_supplicant GROUP=netdev update_config=1 network={ ssid="第一个WiFi的名字,不删除引号,不能有中文" psk="WiFi密码,不删除引号" priority=数字,数字越大代表优先级越高 } network={ ssid="第二个WiFi的名字,不删除引号,不能有中文" psk="WiFi密码,不删除引号" priority=数字,数字越大代表优先级越高 }
priority表示几个wifi同时都搜得到的时候优先连接哪个。
-
将txt后缀改成conf
-
将wpa_supplicant.conf文件放入SD卡的boot盘中
开机
-
拔出SD卡,插到树莓派的SD卡槽里,插好HDMI线连接显示器、电源线、鼠标线以及键盘线(鼠键支持2.4G无线接收器类型),通电
- 树莓派上的红灯常亮,表示通电。绿灯间歇性亮,表示读写SD卡
-
开机后可以看到显示器上输出很多树莓派启动日志,待树莓派启动成功后,输入用户名(root),然后修改密码(比如说openeuler@123)**登录。
- 开机后通过命令
ifconfig
或者ip a
查看wlan0下是否有ip地址,或者通过手机热点查看是否连接上了设备,如果有则说明wifi连接成功,否则连接失败。
- 开机后通过命令
使能无线驱动
-
修改/etc/network/interfaces文件中无线网卡wlan0的配置
iface wlan0 inet dhcp wireless_mode managed wireless_essid any wpa-driver wext wpa-conf /etc/wpa_supplicant.conf 当前树莓派所使用的无线网卡驱动是 nl80211系列 因此将wpa-driver wext 改为 wpa-driver nl80211 才能正确启动wpa_supplicant iface wlan0 inet dhcp wireless_mode managed wireless_essid any wpa-driver nl80211 wpa-conf /etc/wpa_supplicant.conf
-
修改完成后重启networking service使配置生效
- service networking restart
启用Wi-Fi网卡
-
使用ifup启动Wi-Fi连接并自动获取IP地址
-
ifup wlan0
当修改/etc/wpa_supplicant.conf配置文件后, 例如新增Wi-Fi网络配置或修改Wi-Fi网络配置, 需要使用ifdown wlan0来关闭网卡, ifup wlan0开启网卡使wpa_supplicant配置重新加载生效
-
-
使用ifconfig命令查看wlan0网卡, 已经具有IP地址, 并可以正常通信
-
注意:如果不成功的话可以查看是否是wpa_supplicant.conf没有修改成功
- cat wpa_supplicant.conf
(4)远程登陆树莓派
知道树莓派的ip地址后,就可以用我们的笔记本电脑远程登录树莓派
-
以MobaXterm为例进行展示,课后可以自行尝试使用Putty
【注意:电脑需要与树莓派连接至同一个热点,确保二者在同一个网段,否则远程登陆不成功】
- 电脑端进入cmd终端窗口,输入ipconfig,查看二者是否在同一网段
与前面树莓派的ip地址192.168.1.110在同一网段(前三个数字相同)
-
输入前面获得的树莓派的ip地址和用户名,OK
-
输入密码
-
选No即可
-
输入密码,即可登录成功
-
输入uname -a 可以查看版本名
-
查看openeuler embedded系统信息
-
cat /etc/os-release
-
-
注意:服务器版本的openeuler树莓派镜像的网络配置过程可以参考 openeuler官方安装指导
★树莓派的关机
- 不能直接拔掉电源,会造成树莓派数据无法及时保存而丢失
- 可以按需选择相关的终端命令操作
- sudo poweroff 关闭电源
- sudo shutdown -h now 立刻关机
- sudo shutdown -r now 立刻重启
- sudo reboot 重启
- sudo shutdown -h +2 2分钟之后关机
四、基于SDK的应用开发
1. 交叉编译
交叉编译是什么
- 编译可以分为两类:
- 本地编译:编译器和目标程序都是相同架构的编译过程,如编译器运行在x86_64/ARM架构平台上,编译生成x86_64/ARM架构的可执行程序。
- 交叉编译:编译器和目标程序运行在不同架构的编译过程,如编译器运行在x86架构平台上,编译生成ARM架构的可执行程序。
- 通俗的来说,交叉编译就是在pc(x86架构)上的代码,通过相应的交叉编译工具链编译后,能在树莓派上运行(arm架构)。
为什么需要交叉编译?
这是因为通常编译工具链对编译环境有较高的要求,编译复杂的程序时,可能需要巨大的存储空间以及强大的 CPU 运算能力加快编译速度。嵌入式往往面临资源受限的问题,包括处理器性能、内存容量、存储空间等。因此,需要使用交叉编译器在构建主机上编译目标代码,以在嵌入式系统上运行。通常做法是在 PC 上使用交叉编译工具链生成能够在嵌入式设备运行的可执行程序,然后再将程序放到设备中去执行。
2. SDK环境配置
openEuler Embedded提供了SDK自解压安装包,包含了应用程序开发所依赖的交叉编译器、库、头文件,下面将介绍如何构建ARM64的SDK,以及如何使用SDK进行用户态程序、内核模块的开发。
安装SDK
在前面openEuler embedded的构建中,我们已经构建了SDK,得到了openeuler-glibc-x86-64-openeuler-image-cortexa72-raspberrypi4-64-toolchain-*.sh
文件,是SDK安装包。接下来进行安装
-
安装依赖软件包
- sudo apt-get install make gcc g++ flex bison libgmp3-dev libmpc-dev libssl-dev
-
执行SDK自解压安装脚本
- sh openeuler-glibc-x86_64-openeuler-image-cortexa72-raspberrypi4-64-toolchain-23.03.sh
- 根据提示输入工具链的安装路径,默认路径是
/opt/openeuler/<openeuler version>
-
设置SDK环境变量
前一步执行结束最后已打印source命令,运行即可
- . /opt/openeuler/oecore-x86_64/environment-setup-cortexa72-openeuler-linux
-
查看是否安装成功
-
运行如下命令,查看是否安装成功、环境设置成功
aarch64-openeuler-linux-gcc -v
-
3. 使用SDK交叉编译hello world样例
1)准备代码
以构建一个hello world程序为例,运行在openEuler Embedded根文件系统镜像中。
-
在Ubuntu上创建一个hello.c文件
#include <stdio.h> int main(void) { printf("hello openEuler\r\n"); }
-
在hello.c程序所在目录执行如下命令
-
交叉编译生成二进制
aarch64-linux-gnu-gcc hello.c -o hello
-
使用交叉编译器编译后,生成的 hello 已经变成了 ARM 平台的可执行文件
-
可以通过 readelf 工具来查看具体的程序信息,
readelf -a hello
-
-
将上一步生成的可执行文件拷贝到树莓派的openeuler embedded中,并执行
-
chmod +x hello
-
./hello
运行成功
-
五、基于树莓派的OpenEuler内核模块基础实验
1. Linux内核模块
内核模块就是实现了某个功能的一段内核代码,在内核运行过程中,可以加载这部分代码到内核中,从而动态地增加了内核的功能。Linux引入内核模块这一机制,当需要修改、增加内核某个功能时,不再需要重新编译一遍整个内核,只需要编译相关某一段功能代码即内核模块,再加载到内核中即可,避免内核变得臃肿,实现灵活增减。
一些常用模块指令
-
加载内核模块
lsmod xx.ko
-
卸载内核模块
rmmod xx.ko
-
列出当前内核中已经加载的内核模块
lsmod
查看全部内核模块lsmod | grep xx
查看指定内核模块 -
查看内核模块的相关信息
modinfo xx.ko
-
显示模块打印信息
dmesg
或者dmesg | tail -n 5
查看最后5行信息
2. 第一个内核模块helloworld
(1)编写代码和生成hello内核模块
-
创建文件hello.c
vi hello.c
- 按
i
进入编辑模式,输入或者复制以下内容
#include <linux/init.h> #include <linux/module.h> static int hello_init(void) { printk("Hello, openEuler Embedded!\r\n"); return 0; } static void hello_exit(void) { printk("Byebye!"); } module_init(hello_init); module_exit(hello_exit); MODULE_LICENSE("GPL");
- 按
Esc
进入命令行模式,按:wq
保存退出
-
编写Makefile,和hello.c文件放在同一个目录,方法同上
Makefile是用来执行一组操作的特殊文件,其中最重要的操作是程序的编译。
vi Makefile
KERNELDIR := ${KERNEL_SRC} CURRENT_PATH := $(shell pwd) target := hello obj-m := $(target).o build := kernel_modules kernel_modules: $(MAKE) -C $(KERNELDIR) M=$(CURRENT_PATH) modules clean: $(MAKE) -C $(KERNELDIR) M=$(CURRENT_PATH) clean
KERNEL_SRC
为SDK中内核源码树的目录,该变量在安装SDK后会被自动设置。
-
make指令用于执行Makefile,构建模块
make
(2)将编译好的hello.ko拷贝到openEuler Embedded系统中
-
加载模块
insmod hello.ko
-
查看加载的内容
dmesg | tail -n 2
-
模块的卸载及查看
rmmod hello
dmesg | tail -n 1
(3)原理
重新回顾hello.c,通过insmod加载helloworld.ko内核模块时,自动执行module_init()函数,该函数输出Hello, openEuler Embedded!
执行rmmod卸载内核模块helloworld.ko时,会自动执行hello_exit()函数,该函数输出Byebye!