搜索
bottom↓
回复: 0
打印 上一主题 下一主题

《ESP32-S3使用指南—MicroPython版 V1.0》第六章 MicroPython固件编译

[复制链接]

出0入234汤圆

跳转到指定楼层
1
发表于 2024-8-16 09:40:11 | 只看该作者 |只看大图 回帖奖励 |倒序浏览 |阅读模式
本帖最后由 正点原子 于 2024-8-16 09:40 编辑


1)实验平台:正点原子ESP32S3开发板
2)购买链接:https://detail.tmall.com/item.htm?id=768499342659
3)全套实验源码+手册+视频下载地址:http://www.openedv.com/thread-347618-1-1.html
4)正点原子官方B站:https://space.bilibili.com/394620890
5)正点原子手把手教你学ESP32S3快速入门视频教程:https://www.bilibili.com/video/BV1sH4y1W7Tc
6)正点原子FPGA交流群:132780729



第六章 MicroPython固件编译


       本章将向读者介绍MicroPython ESP32固件编译的详细步骤和过程。我们将从准备工作开始,逐步指导开发者完成固件编译的各个环节。通过阅读本章,开发者将了解MicroPython固件编译的基本原理、所需工具和文件,以及编译过程中的注意事项和技巧。
       本章分为如下几个小节:
       6.1 搭建编译环境
       6.2 编译ESP32-S3固件
       6.3 总结

       6.1 搭建编译环境
       自编译MicroPython ESP32-S3固件需要搭建两个开发环境,一个是Linux环境,另一个是ESP-IDF环境。这两个环境是必需的,因为MicroPython ESP32固件依赖于它们进行编译。下面是对这两个环境的搭建流程的介绍。

       6.1.1 Linux环境搭建
       Linux环境的搭建有三种方式。第一种是使用VMware虚拟机并安装Ubuntu系统来搭建,第二种是安装多个操作系统,每次重启电脑时根据需要进行选择进入,第三种是在Windows系统下安装WSL Ubuntu子系统。前两种方式属于比较完整的安装方式,都可以有图形用户界面,适合对图形界面有需求的同学。而最后一种Linux子系统的方式,安装和运行最快,但是只有命令行,适合Linux老手或者对图形界面需求不大的用户。
       考虑到不需要安装VMware虚拟机且安装多个操作系统,本文介绍的是最后一种方式,如何在Windows上安装ubuntu linux子系统。本机是Windows10系统。

       一、下载ubuntu子系统
       进入Windows store 微软商城,输入关键词ubuntu,即可找到多个版本的ubuntu子系统,如下图所示。

图6.1.1.1 下载Ubuntu

       这里作者选的是Ubuntu22.04.2 LTS版本。点进去下载安装。接着我们打开linux子系统功能,如下步骤所示:
       打开电脑设置(快捷键为 WIN + i),如下图所示。

图6.1.1.2 Windown设置

       在上图中,点击“应用”选项,进入应用和功能界面,如下图所示。

图6.1.1.3 应用和功能界面

       在上图中,点击可选功能,进入可选功能界面,接着往下找到更多Windowns功能选项,并且点击进入,如下图所示。

图6.1.1.4 打开Windows功能

       在此界面下找到“适用Linux的windown子系统”选项,我们必须勾选这个选项,否则无法启动子系统,最后重启系统即可。
       重启完毕后,需要进行一下账户配置。我们还是从微软商城中进入,找到我们刚刚安装的Ubuntu22.04.2 LTS,点击“打开”。此时会提示正在安装,安装完毕后,会让您输入一个用户名,并配置密码,按照提示进行配置,最后进入Ubuntu22.04.2 LTS系统,如下图所示。

6.1.1.5 配置用户名称和密码

       二、WSL子系统搬迁
       Windows Store 微软商城安装的APP都默认被安装在C盘,然而C盘是我们电脑重要的磁盘,如果C盘空间满了,会影响电脑运行。因此,我们最好将子系统搬离C盘,也就是说,不使用C盘来存放文件。在这里,作者将子系统搬到D盘存储。
       WSL子系统搬迁流程,如下所示:
       1,查询WSL系统状态。使用管理员身份打开CMD命令行,并在命令行输入“wsl -l -v”查看wsl虚拟机的名称和状态,如下图所示。

图6.1.1.6 wsl虚拟机的名称与状态

       从上图可知,作者安装了两个WSL Ubuntu子系统,它们分别为Ubuntu和Ubuntu-22.04,目前它们的状态分别为停止状态和运行状态。下面,作者将以Ubuntu-22.04为例,说明如何将其搬迁到D盘。
       2,停止WSL子系统。输入wsl --shutdown使Ubuntu-22.04停止运行,再次使用wsl -l -v确保其处于stopped状态,如下图所示。

图6.1.1.7 Ubuntu-22.04停止运行

       3,导出/恢复备份。在D盘创建一个文件夹用来存放新的WSL,比如作者创建了一个 D:\Ubuntu_WSL文件夹。
       ①:导出它的备份(比如命名为Ubuntu.tar)。在CMD命令行下输入“wsl --export Ubuntu-22.04 D:\Ubuntu_WSL\Ubuntu.tar”。
       ②:确定在D:\Ubuntu_WSL下是否可看见备份Ubuntu.tar文件,如下图所示那样,之后注销原有的WSL。在CMD命令行输入“wsl --unregister Ubuntu-22.04”注销原本的WSL。

图6.1.1.8 在D:\Ubuntu_WSL目录下生成Ubuntu.tar文件

       ③:将备份文件恢复到D:\Ubuntu_WSL中去。在CMD命令行下输入“wsl --import Ubuntu-22.04 D:\Ubuntu_WSL D:\Ubuntu_WSL\Ubuntu.tar”恢复备份文件,如下图所示。

图6.1.1.9 恢复WSL备份

       这时候启动WSL,发现好像已经恢复正常了,但是用户变成了root,如下图所示。

图6.1.1.10 启动Ubuntu-22.04

       在使用git工具进行代码版本管理时,特别是在克隆开源市场中的Github仓库时,可能会遇到超时或失败的问题。这主要是因为国内网络连接国外服务器可能会显得冗余。为了解决这个问题,作者介绍了一种加速方法,可以帮助大家更好地搭建MicroPython环境。这种方法的具体操作步骤如下:

       ①:在Ubuntu子系统上输入以下命令来解析github.com的IP地址。
  1. nslookup github.com
复制代码
       解析完成之后,我们得到了Github仓库的IP地址,如下图所示。

图6.1.1.11 解析github仓库

       ②:修改hosts文件,该文件位于路径是:C:\Windows\System32\drivers\etc。添加内容如下。
  1. # GitHub520 Host Start
  2. 140.82.112.4                  alive.github.com
  3. 140.82.112.4                  live.github.com
  4. 18.207.134.67                 github.githubassets.com
  5. 140.82.112.4                  central.github.com
  6. 3.220.169.176                 desktop.githubusercontent.com
  7. 140.82.112.4                  assets-cdn.github.com
  8. 3.238.132.1                   camo.githubusercontent.com
  9. 151.101.1.6                   github.map.fastly.net
  10. 151.101.1.6                   github.global.ssl.fastly.net
  11. 140.82.112.4                  gist.github.com
  12. 185.199.108.153               github.io
  13. 20.205.243.166                github.com
  14. 192.0.66.2                    github.blog
  15. 140.82.112.4                  api.github.com
  16. 18.212.214.173                raw.githubusercontent.com
  17. 44.204.227.149                user-images.githubusercontent.com
  18. 18.208.143.190                favicons.githubusercontent.com
  19. 3.227.11.2                    avatars5.githubusercontent.com
  20. 44.192.25.139                 avatars4.githubusercontent.com
  21. 54.197.35.64                  avatars3.githubusercontent.com
  22. 44.211.83.233                 avatars2.githubusercontent.com
  23. 3.238.132.1                   avatars1.githubusercontent.com
  24. 3.238.199.124                 avatars0.githubusercontent.com
  25. 44.210.19.120                 avatars.githubusercontent.com
  26. 140.82.112.4                  codeload.github.com
  27. 72.21.206.80                  github-cloud.s3.amazonaws.com
  28. 72.21.206.80                  github-com.s3.amazonaws.com
  29. 72.21.206.80                  github-production-release-asset-2e65be.s3.amazonaws.com
  30. 72.21.206.80                  github-production-user-asset-6210df.s3.amazonaws.com
  31. 72.21.206.80                  github-production-repository-file-5c1aeb.s3.amazonaws.com
  32. 185.199.108.153               githubstatus.com
  33. 140.82.113.18                 github.community
  34. 52.224.38.193                 github.dev
  35. 140.82.112.4                  collector.github.com
  36. 3.238.235.79                  pipelines.actions.githubusercontent.com
  37. 18.207.249.155                media.githubusercontent.com
  38. 35.172.164.199                cloud.githubusercontent.com
  39. 54.198.215.57                 objects.githubusercontent.com
  40. 13.107.219.40                 vscode.dev
复制代码
       大部分情况下是直接生效,如未生效可尝试刷新 DNS,在 CMD 窗口输入“ipconfig /flushdns”命令。

       6.1.2 安装工具链
       到了这里,我们将开始在Ubuntu下工作。首先,我们需要安装Linux常用的工具链,例如gcc、cmake、python3、source、git等。为了安装这些工具链,我们首先需要打开Ubuntu-22.04子系统。然后,以命令的形式安装工具链,如下安装命令:
  1. 1,更新工具:sudo apt-get update
  2. 2,安装GCC:sudo apt-get install gcc
  3. 3,安装Cmake:sudo apt-get install cmake
  4. 4,安装python3.10:sudo apt-get install python3.10
  5. 5,安装python pip:sudo apt-get install python3-pip
  6. 6,安装子系统:sudo apt-get install source/ linux-source-5.7
  7. 7,安装virtualenv:sudo apt-get install virtualenv
  8. 8,安装git:sudo apt-get install git
复制代码
       一旦这些工具链成功安装,我们就可以开始搭建ESP-IDF环境并编译MicroPython固件。请注意,这些工具链的安装必须全部安装完成,否则在编译MicroPython时可能会出现问题。


       6.1.3 ESP-IDF环境搭建
       ESP-IDF(Espressif IoT Development Framework)是用于开发ESP系列芯片的官方开发环境,它支持Windows、Linux 和 macOS 操作系统,方便用户在不同系统下开发。在开发之前,我们先了解一下ESP-IDF和乐鑫芯片的版本关系,不同版本的IDF所支持的乐鑫芯片都不一样,下图总结了乐鑫芯片在 ESP-IDF 各版本中的支持状态,其中支持代表已支持,预览代表目前处于预览支持状态。预览支持状态通常有时间限制,而且仅适用于测试版芯片。请确保使用与芯片相匹配的 ESP-IDF 版本。

图6.1.3.1 不同版本的IDF支持乐鑫芯片关系表

       从上图可以看到,ESP32-S3芯片只能在IDF v4.4版本及以上运行,因此我们在使用MicroPython搭建IDF开发环境时,需要选择IDF v4.4版本及以上。在这里,作者选择的是V5.0.4版本,因为MicroPython目前仅支持IDF v5.0.4和V5.1.2版本(MicroPython IDF版本要求: MicroPython目前支持的IDF版本如下图所示)。然而,不排除以后可能会支持更高版本的可能性。

图6.1.3.2 MicroPython支持的IDF版本

       到了这里,我们已经了解了MicroPython目前支持的IDF版本,下面作者来讲解Micropython ESP-IDF环境搭建的基本步骤:

       1,克隆IDF库
       首先打开ubuntu 22.04.2 LTS子系统,然后在命令行下输出“git clone -b v5.0.4 --recursive https://github.com/espressif/esp-idf.git(目前官方建议使用5.0.4版本)”克隆Github仓库中的ESP-IDF源码库,如下图所示。

图6.1.3.3 克隆ESP32 IDF库

       当读者成功克隆IDF库后,我们会在子系统(D:\Ubuntu_WSL\rootfs\root)根目录下找到一个名为“esp-idf”的文件夹。这个文件夹包含了ESP-IDF开发环境的相关文件和工具(相关文件的描述,请用户观看IDF版的教程)。

       2,切换IDF 5.0.4版本
       在root@DESKTOP-QH7611H:~/根目录下输入“cd esp-idf”进入esp-idf文件夹,然后在root@DESKTOP-QH7611H:~/esp-idf#目录下输入“git checkout v5.0.4”命令,切换IDF版本为v5.0.4。如下图所示。


图6.1.3.4 切换IDF版本

       3,更新IDF版本子模块
       在root@DESKTOP-QH7611H:~/esp-idf#目录下输入“git submodule update --init --recursive”更新子模块,如下图所示。

图6.1.3.5 更新子模块

       一般来讲,在克隆IDF时会自动更新子模块,为了保险起见,最好重新更新子模块。
       4,运行安装脚本和设置环境变量
       root@DESKTOP-QH7611H:~/esp-idf#目录下输入两条命令“./install.sh”和“source export.sh”,它们分别是安装IDF环境和设置环境变量,设置成功之后系统提示“../export.sh”信息表示安装及设置环境变量成功如下图所示。

图6.1.3.6 IDF安装环境

       上图提示“../export.sh”信息表示安装成功,此时我们在子系统目录下发现了.espressif隐藏文件夹,这是IDF环境搭建时生成的文件。
       接着输入“source export.sh”设置环境变量,如下图所示。

图6.1.3.7 设置环境变量

       上图提示“idf.py build”信息表示设置环境变量成功。请注意,每次进入Ubuntu 22.04.2 LTS子系统时,用户必须在root@DESKTOP-QH7611H:~/esp-idf#目录下输入“source export.sh”来操作环境变量,否则在生成固件时可能会报错。
       为了解决上述的问题,作者在启动Ubuntu 22.04.2 LTS子系统时,在~/.bashrc直接执行export.sh文件,来设置ESP-IDF环境变量。
       ~/.bashrc 是一个在 Unix 和 Linux 系统中非常重要的 Shell 初始化文件。这个文件在 bash shell (Bourne Again SHell)启动时被读取(系统启动时),用户可以在这里定义别名、函数、环境变量、路径等,所有这些在以后启动的 bash shell 中都可用。
       这个文件通常位于系统的 home 目录下(~/.bashrc),用户可以使用文本编辑器(如 vim、nano 或 emacs)来编辑它。在此文件最后一行命令下添加以下命令,如下所示:
  1. source ./esp-idf/export.sh
复制代码
       这样我们在子系统启动时,就无需进去ESP-IDF源码库设置环境变量,启动时直接运行export.sh文件设置ESP-IDF的环境变量了。
       到了这里,总共花费了作者一天的时间,因为Github是国外的服务器,国内的网路想要从Github下载资料,必须有更良好的网络才行,否则即使知道ESP-IDF搭建环境步骤,也未必能搭建成功。另外,作者还提供了第二种ESP-IDF环境搭建方法,请参考这个博客的文章,他是从国内的gitee仓库克隆下来的,这样我们下载时就比较快速了。但在子模块更新时可能会遇到“gitee Username for 'https://gitee.com':”这样的提示信息,需要大家自行解决。

       6.1.4 搭建MicroPython开发环境
       在root@DESKTOP-QH7611H:~/目录下输入“git clone https://github.com/micropython/micropython.git”克隆MicroPython库,如下图所示。

图6.1.4.1 克隆MicroPython库

       克隆成功之后,在此目录下输入“cd micropython”进入micropython库,然后输入“git submodule update --init --recursive”更新MicroPython子模块。
       子模块更新成功之后,在root@DESKTOP-QH7611H:~/micropython#目录下输入“make -C mpy-cross”构建MicroPython交叉编译器,以便将一些内置脚本预编译为字节码,如下图所示。

图6.1.4.2 构建MicroPython交叉编译

       构建MicroPython交叉编译器完成之后,就可以构建MicroPython ESP32固件了。首先在root@DESKTOP-QH7611H:~/micropython目录下输入“cd ports/esp32”进入MicroPython ESP32编译工程,在此目录下输入“make”构建ESP32 MicroPython固件,如下图所示。

图6.1.4.3 编译ESP32 MicroPython固件

       根据上图所示,系统在esp32\build-ESP32_GENERIC文件夹下生成了三个bin文件,它们分别为bootloader.bin、partition-table.bin和micropython.bin。然后,我们使用flash_download_tool_3.9.5.exe工具将这三个bin文件烧录到ESP32芯片中,设置方法如下所示:

图6.1.4.4 烧录bin文件的地址设置

       根据上图中的信息,我们可以得知烧录bin文件的地址是根据图5.1.4.4编译固件成功后的系统提示信息来进行的。根据提示信息,我们需要将生成的bin文件烧录到对应的地址中。另外,我们也可以使用esp32\build-ESP32_GENERIC文件夹下的firmware.bin文件,这个文件是bootloader.bin、partition-table.bin和micropython.bin三个文件的总bin文件:

图6.1.4.5 烧录总bin文件

       注意:此固件虽然能满足ESP32在MicroPython下的运作,但它是有缺陷的。它并没有适配芯片的资源,如,是否挂载PSRAM、Flash/PSRAM的大小、时钟是否调节到240MHz等等。如果我们不去配置的话,系统可能选择默认的配置,如时钟只能达到160MHz、Flash大小为2MB等。这种默认的配置无法体现该芯片的价值,所以作者在后续的教程中,会详细讲解如何配置一个与手上芯片相匹配的固件。

       6.1.5 MicroPython源文件结构分析
       在上小节中,我们在子系统的Ubuntu下克隆了MicroPython源码包,并且在这个源码包下编译出了ESP32 MicroPython固件。下面,作者重点介绍这个源码包文件架构及文件功能说明。
       MicroPython的基础源程序基本由C语言编写的,在编译过程中,使用了少量的Py脚本,用于在预编译过程中处理字符串。如下表中展示了MicroPython项目的源码文件结构。

表6.1.5.1 MicroPython项目的源文件结构

       docs目录: 可生成MicroPython文档,可以在GitHub仓库中找到MicroPython/docs目录,并安装相关的工具来生成HTML,如下图所示。

图6.1.5.1 命令生成MicroPython文档

       从上述可知,首先使用pip命令安装sphinx和sphinx_rtd_theme工具,然后在子系统上使用cd命令跳到micropython/docs目录下,最后在此目录下输入“make html”命令构建html文档。
       py目录:在MicroPython的开发过程中,为了确保与Python标准库的一致性,我们不会修改py目录中的任何源代码。这是因为py目录存放着Python内核的全部源代码,是实现Python功能的重要基础。
       lib目录和extmod目录:它们都包含了MicroPython扩展功能的组件,但它们的分工有所不同。lib目录中的内容是与MicroPython无关的,它们针对特定的微控制器平台,并可以独立地在这些平台上运行,以支持MicroPython功能的实现。它们位于MicroPython的下层,例如,包括各个微控制器平台的固件库、基本的文件系统协议栈和USB协议栈等。而extmod目录中实现的是扩展模块,这些模块都是基于MicroPython实现的,并在MicroPython内部实现扩展功能,例如,machine_spi模块就是在MicroPython的machine类中实现的SPI类模块。
       对于微控制器开发者最有用也是最直接操作的目录是ports,里面存在了MicroPython支持的所有微控制器的移植代码,如下图所示。

图6.1.5.2 MicroPython已经支持的移植平台

       在具体微控制器平台的目录下,存放了各自对MicroPython的底层移植源文件以及移植工程的Makefile文件。因此,在6.1.4小节编译固件时,作者只输入“make”命令即可完成ESP32 MicroPython固件的编译和构建。

       6.2 编译ESP32-S3固件
       上小节中,我们直接make就可以构建ESP32固件了,make 这是Make的基本命令,用于生成目标文件。执行make命令时,Make会自动查找当前目录下的Makefile文件(如果真的要细说make命令和Makefile,可能需要客户了解linux相关知识了)。
       Makefile是用于自动编译和构建软件项目的工具。它使用简单的规则来告诉编译器如何构建软件。Makefile包含一组命令,这些命令用于编译、链接和构建源代码文件。
       在ESP32-S3的固件编译过程中,可以在ports/esp32目录中找到一个Makefile文件。这个Makefile文件包含了编译ESP32-S3固件的规则和指令。通过编辑Makefile文件,可以设置要编译的型号,例如GENERIC_S3,然后保存文件后在终端使用make命令开始编译适用于对应板型的固件。
       为了用户能够了解MicroPython固件编译,下面作者简单讲解一下ports/esp32目录Makefile文件到底有什么作用,该文件的部分内容如下所示:
  1. ifdef BOARD_DIR
  2. # (1)自定义板路径
  3. BOARD ?= $(notdir $(BOARD_DIR:/=))
  4. else
  5. # (2)如果命令行中未给出,则默认为ESP32_GENERIC.
  6. BOARD ?= ESP32_GENERIC
  7. # (3)得到对应芯片的编译路径
  8. BOARD_DIR ?= boards/$(BOARD)
  9. endif

  10. ifeq ($(wildcard $(BOARD_DIR)/.),)
  11. ifeq ($(findstring boards/GENERIC,$(BOARD_DIR)),boards/GENERIC)
  12. $(warning The GENERIC* boards have been renamed to ESP32_GENERIC*)
  13. endif
  14. $(error Invalid BOARD specified: $(BOARD_DIR))
  15. endif
  16. # (5)如果没有给出构建目录,使用默认文件名
  17. ifneq ($(BOARD_VARIANT),)
  18. BUILD ?= build-$(BOARD)-$(BOARD_VARIANT)
  19. else
  20. BUILD ?= build-$(BOARD)
  21. endif
  22. # (6)串口设备波特兰
  23. PORT ?= /dev/ttyUSB0
  24. BAUD ?= 460800
  25. # Python3
  26. PYTHON ?= python3

  27. .PHONY: all clean deploy erase submodules FORCE

  28. CMAKE_ARGS =
  29. # (5)使用C模块,把自己的C驱动编译成MicroPython调用的API
  30. ifdef USER_C_MODULES
  31.     CMAKE_ARGS += -DUSER_C_MODULES=${USER_C_MODULES}
  32. endif

  33. IDFPY_FLAGS += -D MICROPY_BOARD=$(BOARD) -D MICROPY_BOARD_DIR=$(abspath $(BOARD_DIR)) $(CMAKE_ARGS)

  34. ifdef FROZEN_MANIFEST
  35.        IDFPY_FLAGS += -D MICROPY_FROZEN_MANIFEST=$(FROZEN_MANIFEST)
  36. endif
  37. # (6)设置PSRAM SPI模式、D2WD等
  38. ifdef BOARD_VARIANT
  39.     IDFPY_FLAGS += -D MICROPY_BOARD_VARIANT=$(BOARD_VARIANT)
  40. endif

  41. HELP_BUILD_ERROR ?= "See \033[1;31m<a href="https://github.com/micropython/micropython/wiki/Build-Troubleshooting" target="_blank">https://github.com/micropython/micropython/wiki/Build-Troubleshooting</a>\033[0m"

  42. define RUN_IDF_PY
  43.     idf.py $(IDFPY_FLAGS) -B $(BUILD) -p $(PORT) -b $(BAUD) $(1)
  44. endef

  45. all:
  46.     idf.py $(IDFPY_FLAGS) -B $(BUILD) build || (echo -e $(HELP_BUILD_ERROR); false)
  47.     @$(PYTHON) makeimg.py \
  48.         $(BUILD)/sdkconfig \
  49.         $(BUILD)/bootloader/bootloader.bin \
  50.         $(BUILD)/partition_table/partition-table.bin \
  51.         $(BUILD)/micropython.bin \
  52.         $(BUILD)/firmware.bin \
  53.         $(BUILD)/micropython.uf2

  54. $(BUILD)/bootloader/bootloader.bin $(BUILD)/partition_table/partition-table.bin $(BUILD)/micropython.bin: FORCE

  55. clean:
  56.     $(call RUN_IDF_PY,fullclean)
  57. # 自动烧录
  58. deploy:
  59.     $(call RUN_IDF_PY,flash)
  60. # 擦除指令
  61. erase:
  62.     $(call RUN_IDF_PY,erase-flash)
  63. monitor:
  64.     $(call RUN_IDF_PY,monitor)
  65. size:
  66.     $(call RUN_IDF_PY,size)
  67. size-components:
  68.     $(call RUN_IDF_PY,size-components)
  69. size-files:
  70.     $(call RUN_IDF_PY,size-files)
  71. # 更新子模块
  72. submodules:
  73.     @GIT_SUBMODULES=$(idf.py $(IDFPY_FLAGS) -B $(BUILD)/submodules -D ECHO_SUBMODULES=1 build 2>&1 | \
  74.                       grep '^GIT_SUBMODULES=' | cut -d= -f2); \
  75.     $(MAKE) -f ../../py/mkrules.mk GIT_SUBMODULES="${GIT_SUBMODULES}" submodules
复制代码
       上述源码中的(1)表示要编译型号(如make BOARD=GENERIC_S3就是编译S3的MicroPython固件),如果在命令行中没有给出这个变量,则默认为ESP32_GENERIC(2),即编译ESP32这款芯片;(3)表示编译路径,也就是在这个路径下编译哪些文件,如果(1)中没有设置BOARD变量,则系统会编译boards/ESP32_GENERIC路径下的文件(如下图所示);(4)表示构建文件夹名称,这个文件夹包含系统编译产生的文件都会保存在这个文件夹中;(5)表示是否使用C模块,也就是说,使用C驱动编译成MicroPython可调用的API,这个方法我们到第六章时候讲解;(6)表示编译条件,如挂在PSRAM的SPI模式为SPIRAM_OCT。

图6.2.1 boards/ESP32_GENERIC路径下的文件

       上图中的mpconfigboard.cmake文件用于指定编译哪些sdkconfig文件。sdkconfig文件决定了系统应该编译和构建哪些功能(即加载项目的具体变量,通过具体变量让系统执行相应的代码),而mpconfigboard.h文件则用于定义全局宏定义,系统在运行时会根据这些宏定义的数值来执行相应的条件判断。
       打开mpconfigboard.cmake文件,如下:
  1. # 需执行的文件
  2. set(SDKCONFIG_DEFAULTS
  3.     boards/sdkconfig.base
  4.     boards/sdkconfig.ble
  5. )
  6. # 判断是否开启D2WD
  7. if(MICROPY_BOARD_VARIANT STREQUAL "D2WD")
  8.     set(SDKCONFIG_DEFAULTS
  9.         ${SDKCONFIG_DEFAULTS}
  10.         boards/ESP32_GENERIC/sdkconfig.d2wd
  11.     )

  12.     list(APPEND MICROPY_DEF_BOARD
  13.         MICROPY_HW_MCU_NAME="ESP32-D2WD"
  14.     )
  15. endif()
  16. # 省略以下代码
复制代码
       从上述内容可知,编译ESP32 MicroPython固件时,需要执行boards/路径下的sdkconfig.base和sdkconfig.ble文件以及条件判断下的sdkconfig.x文件。根据这些项目的具体变量,系统将有意识地编译哪些代码。下面,作者将以sdkconfig.spiram_sx为例来讲解这个文件的作用。
       打开ports/esp32/boards/sdkconfig.spiram_sx文件,如下:
  1. # PSRAM模式
  2. CONFIG_SPIRAM_MODE_QUAD=y
  3. ......
  4. # PSRAM 读取速率
  5. CONFIG_SPIRAM_SPEED_80M=y
  6. # 使能PSRAM
  7. CONFIG_SPIRAM=y
  8. ......
复制代码
       此文件用于配置ESP32芯片是否挂载PSRAM,以及设置SPI模式、速率等相关项目的具体变量。例如,正点原子ESP32-S3开发板的主控使用的是ESP32-S3-WROOM-1-N16R8模组,根据《esp32-s3-wroom-1_wroom-1u_datasheet_cn.pdf》模组数据手册第三页表1所示,该模组的PSRAM使用Octal SPI模式,因此在本章节编译ESP32-S3固件时,需要开启PSRAM,并将SPI模式设置为Octal SPI。
       ESP32-S3-WROOM-1-N16R8模组内置16MB Flash(Octal SPI)和8MB PSRAM(Octal SPI),可运行最高时钟频率为240MHz。这些信息来自《esp32-s3_datasheet_cn.pdf》和《esp32-s3-wroom-1_wroom-1u_datasheet_cn.pdf》这两份数据手册。
       根据上述的要求,作者划分几个步骤来讲解。

       1,修改sdkconfig.board文件
       打开ports/esp32/borads/ESP32_GENERIC_S3路径下打开sdkconfig.board文件,此文件的内容如下:
  1. CONFIG_ESPTOOLPY_FLASHMODE_QIO=y
  2. CONFIG_ESPTOOLPY_FLASHFREQ_80M=y
  3. CONFIG_ESPTOOLPY_AFTER_NORESET=y
  4. # Flash大小
  5. CONFIG_ESPTOOLPY_FLASHSIZE_4MB=
  6. CONFIG_ESPTOOLPY_FLASHSIZE_8MB=y
  7. CONFIG_ESPTOOLPY_FLASHSIZE_16MB=
  8. CONFIG_PARTITION_TABLE_CUSTOM=y
  9. # 分区表名称
  10. CONFIG_PARTITION_TABLE_CUSTOM_FILENAME="partitions-8MiB.csv"
复制代码
       此文件默认设置Flash大小为8MB,显然不符合ESP32-S3-WROOM-1-N16R8模组内置16MB Flash大小,因此,把CONFIG_ESPTOOLPY_FLASHSIZE_16MB配置为y,并且修改分区表名称为“partitions-16MiB.csv”,修改后如下:
  1. CONFIG_ESPTOOLPY_FLASHMODE_QIO=y
  2. CONFIG_ESPTOOLPY_FLASHFREQ_80M=y
  3. CONFIG_ESPTOOLPY_AFTER_NORESET=y
  4. # Flash大小为16MB
  5. CONFIG_ESPTOOLPY_FLASHSIZE_4MB=
  6. CONFIG_ESPTOOLPY_FLASHSIZE_8MB=
  7. CONFIG_ESPTOOLPY_FLASHSIZE_16MB=y
  8. CONFIG_PARTITION_TABLE_CUSTOM=y
  9. # 分区表名称
  10. CONFIG_PARTITION_TABLE_CUSTOM_FILENAME="partitions-16MiB.csv"
复制代码

       2,修改partitions-16MiB.csv分区表
       因为正点原子ESP32-S3 MicroPython固件使用了乐鑫AI库,因此这个AI库存储在Flash内需要大量的内存。因此,我们将分区表中的factory子分区(存储代码的区域)设置为6M。
       修改前的分区表:
  1. # Notes: the offset of the partition table itself is set in
  2. # $IDF_PATH/components/partition_table/Kconfig.projbuild.
  3. # Name,     Type,   SubType,    Offset,     Size,   Flags
  4. nvs,        data,   nvs,        0x9000,     0x6000  ,
  5. phy_init,   data,   phy,        0xf000,     0x1000  ,
  6. factory,    app,    factory,    0x10000,    0x1F0000,        # 1M内存
  7. vfs,        data,   fat,        0x200000,   0xE00000,         # 14M内存
复制代码
       修改后的分区表
  1. # Notes: the offset of the partition table itself is set in
  2. # $IDF_PATH/components/partition_table/Kconfig.projbuild.
  3. # Name,     Type,   SubType,    Offset,     Size,   Flags
  4. nvs,        data,   nvs,        0x9000,     0x6000  ,
  5. phy_init,   data,   phy,        0xf000,     0x1000  ,
  6. factory,    app,    factory,    0x10000,    0x600000,         # 6M内存
  7. vfs,        data,   fat,        0x700000,   0x900000,         # 9M内存
复制代码
       到了这里,我们成功让MicroPython源代码适配了ESP32-S3-WROOM-1-N16R8模组。有小伙伴会问,为什么CONFIG_ESPTOOLPY_FLASHMODE_QIO还是为y呢?其实,在编译固件时,通过在make命令后面加上“BOARD_VARIANT= SPIRAM_OCT”命令就可以覆盖这个项目具体变量。大家可以打开ports/esp32/boards/ESP32_GENERIC_S3路径下的mpconfigboard.cmake文件,如下所示:
  1. set(IDF_TARGET esp32s3)

  2. set(SDKCONFIG_DEFAULTS
  3.     boards/sdkconfig.base
  4.     boards/sdkconfig.usb
  5.     boards/sdkconfig.ble
  6.     boards/sdkconfig.spiram_sx
  7.     boards/ESP32_GENERIC_S3/sdkconfig.board
  8. )

  9. if(MICROPY_BOARD_VARIANT STREQUAL "SPIRAM_OCT")
  10.     set(SDKCONFIG_DEFAULTS
  11.         ${SDKCONFIG_DEFAULTS}
  12.         boards/sdkconfig.240mhz
  13.         boards/sdkconfig.spiram_oct
  14.     )

  15.     list(APPEND MICROPY_DEF_BOARD
  16.         MICROPY_HW_BOARD_NAME="Generic ESP32S3 module with Octal-SPIRAM"
  17.     )
  18. endif()
复制代码
       根据上述文件内容,当MICROPY_BOARD_VARIANT变量等于SPIRAM_OCT时,将编译sdkconfig.240mhz和sdkconfig.spiram_oct文件。sdkconfig.240mhz文件用于将芯片的时钟频率配置为240MHz,而sdkconfig.spiram_oct文件则用于将外挂PSRAM的SPI模式配置为Otcal SPI。因此,在系统编译sdkconfig.spiram_oct时,将禁用CONFIG_SPIRAM_MODE_QUAD这个项目具体变量,并将CONFIG_SPIRAM_MODE_OCT这个项目具体变量设置为y。以下是sdkconfig.spiram_oct文件的内容:
  1. # MicroPython on ESP32-S2 and ESP32-PAD1_subscript_3, ESP IDF configuration with SPIRAM support in Octal mode
  2. CONFIG_SPIRAM_MODE_QUAD=
  3. CONFIG_SPIRAM_MODE_OCT=y
复制代码
       至此,MicroPython源代码适配ESP32-S3-WROOM-1-N16R8模组完成,接下来,在ports/esp32/路径下输入“make BOARD=ESP32_GENERIC_S3 BOARD_VARIANT=SPIRAM_OCT”命令构建ESP32-S3-WROOM-1-N16R8模组MicroPython固件,如下图所示。

图6.2.2 ESP32-S3-WROOM-1-N16R8模组MiroPython固件

       根据上图所示,系统会在build-ESP32_GENERIC_S3-SPIRAM_OCT文件夹下生成四个bin文件,它们分别是bootloader.bin、partition-table.bin、micropython.bin和firmware.bin(总bin)。接着,我们使用flash_download_tool.exe工具将这三个bin文件烧录到ESP32-S3-WROOM-1-N16R8模组中。设置flash_download_tool的方法请参考图5.1.4.5所示。需要注意的是,bootloader.bin、partition-table.bin和micropython.bin设置的下载地址分别为0x0000、0x8000和0x10000。如果烧录的是firmware.bin(总bin),则将烧录地址设置为0x0000。当然,我们也可以借助Thonny软件来烧录这个固件,如下图所示。

图6.2.3 烧录ESP32-S3 MicroPython固件

       烧录完成后,关闭烧录界面,切换Thonny软件的解释器。在Thonny软件的Shell下提示固件信息,如下图所示。

图6.2.4 固件提示信息

       在Shell交互环境下输入以下代码,查看固件资源信息,如下图所示。

图6.2.5 提示固件资源信息

       从上图中可知,这个固件的系统时钟被设置为240MHz,内部Flash大小为16MB,PSRAM经过申请和释放操作,最后打印剩余空间为7.930084MB约等于8MB。

       6.3 总结
       不妨读者思考一下MicroPython的ESP32-S3固件为什么能驱动ESP32-S3芯片,并且实现相关的应用。
       在编译MicroPython的ESP32-S3固件之前,需要先搭建ESP-IDF环境。这是因为ESP-IDF库为开发者提供了一套完善的API,使得开发者可以使用高级语言(如C/C++)来操作硬件,而不需要直接对硬件寄存器进行操作。这一设计大大降低了开发的难度,使得开发者可以更加专注于实现应用功能,而不必花费大量时间在底层的硬件操作上。
       MicroPython的ESP32-S3固件编译也是基于这一思想进行的。它在ESP-IDF库的基础上进行了Python的封装,使得用户可以使用Python的语法来实现对ESP32-S3芯片的控制。这种封装方式不仅使得使用MicroPython进行开发变得更加简单和方便,同时也提高了MicroPython的可读性和易用性。
       总的来说,MicroPython的ESP32-S3固件编译是基于ESP-IDF库进行的,它为开发者提供了一种更加高级、更加方便的方式来控制ESP32-S3芯片,使得开发者可以更加专注于实现应用功能。

阿莫论坛20周年了!感谢大家的支持与爱护!!

曾经有一段真挚的爱情摆在我的面前,我没有珍惜,现在想起来,还好我没有珍惜……
回帖提示: 反政府言论将被立即封锁ID 在按“提交”前,请自问一下:我这样表达会给举报吗,会给自己惹麻烦吗? 另外:尽量不要使用Mark、顶等没有意义的回复。不得大量使用大字体和彩色字。【本论坛不允许直接上传手机拍摄图片,浪费大家下载带宽和论坛服务器空间,请压缩后(图片小于1兆)才上传。压缩方法可以在微信里面发给自己(不要勾选“原图),然后下载,就能得到压缩后的图片。注意:要连续压缩2次才能满足要求!!】。另外,手机版只能上传图片,要上传附件需要切换到电脑版(不需要使用电脑,手机上切换到电脑版就行,页面底部)。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

手机版|Archiver|amobbs.com 阿莫电子技术论坛 ( 粤ICP备2022115958号, 版权所有:东莞阿莫电子贸易商行 创办于2004年 (公安交互式论坛备案:44190002001997 ) )

GMT+8, 2024-8-25 07:16

© Since 2004 www.amobbs.com, 原www.ourdev.cn, 原www.ouravr.com

快速回复 返回顶部 返回列表