【雕爷学编程】MicroPython手册之 ESP32 特定端口库 esp32.ULP.set_wakeup_period()

在这里插入图片描述

MicroPython是为了在嵌入式系统中运行Python 3编程语言而设计的轻量级版本解释器。与常规Python相比,MicroPython解释器体积小(仅100KB左右),通过编译成二进制Executable文件运行,执行效率较高。它使用了轻量级的垃圾回收机制并移除了大部分Python标准库,以适应资源限制的微控制器。

MicroPython主要特点包括:
1、语法和功能与标准Python兼容,易学易用。支持Python大多数核心语法。
2、对硬件直接访问和控制,像Arduino一样控制GPIO、I2C、SPI等。
3、强大的模块系统,提供文件系统、网络、图形界面等功能。
4、支持交叉编译生成高效的原生代码,速度比解释器快10-100倍。
5、代码量少,内存占用小,适合运行在MCU和内存小的开发板上。
6、开源许可,免费使用。Shell交互环境为开发测试提供便利。
7、内置I/O驱动支持大量微控制器平台,如ESP8266、ESP32、STM32、micro:bit、掌控板和PyBoard等。有活跃的社区。

MicroPython的应用场景包括:
1、为嵌入式产品快速构建原型和用户交互。
2、制作一些小型的可 programmable 硬件项目。
3、作为教育工具,帮助初学者学习Python和物联网编程。
4、构建智能设备固件,实现高级控制和云连接。
5、各种微控制器应用如物联网、嵌入式智能、机器人等。

使用MicroPython需要注意:
1、内存和Flash空间有限。
2、解释执行效率不如C语言。
3、部分库函数与标准版有差异。
4、针对平台优化语法,订正与标准Python的差异。
5、合理使用内存资源,避免频繁分配大内存块。
6、利用原生代码提升速度关键部位的性能。
7、适当使用抽象来封装底层硬件操作。

总体来说,MicroPython让Python进入了微控制器领域,是一项重要的创新,既降低了编程门槛,又提供了良好的硬件控制能力。非常适合各类物联网和智能硬件的开发。
在这里插入图片描述

MicroPython的esp是指针对ESP8266和ESP32芯片的MicroPython固件和相关软件库。ESP8266和ESP32是一类广泛应用于物联网和嵌入式系统的低成本、低功耗的Wi-Fi和蓝牙模块。MicroPython的esp为这两种芯片提供了高级的脚本编程环境,使开发者能够使用Python语言进行快速原型设计和开发。

ESP8266:是一款低成本、低功耗的Wi-Fi模块/芯片,由Espressif Systems开发。它内置了TCP/IP协议栈,可以用于连接互联网,并具备较强的处理能力。MicroPython的esp提供了针对ESP8266的固件和相关软件库,使开发者可以使用MicroPython语言进行ESP8266应用的开发。

ESP32:是Espressif Systems推出的一款高度集成的Wi-Fi和蓝牙模块/芯片,与ESP8266相比,它具备更强大的处理能力、更多的外设接口和更多的内存。MicroPython的esp也提供了针对ESP32的固件和相关软件库,使开发者可以使用MicroPython语言进行ESP32应用的开发。

MicroPython的esp固件:是专门针对ESP8266和ESP32芯片的MicroPython固件版本。这些固件经过了针对性的优化,使得它们可以在ESP8266和ESP32上运行,并提供了与硬件交互、网络通信和外设控制等功能的API。

软件库:MicroPython的esp还提供了一系列与ESP8266和ESP32硬件相关的软件库,用于简化和加速开发过程。这些软件库提供了丰富的功能接口,涵盖了Wi-Fi、蓝牙、GPIO(通用输入输出)、I2C、SPI、PWM等常用的硬件和通信协议,使开发者可以方便地访问和控制硬件资源。
在这里插入图片描述

MicroPython的esp32.ULP.set_wakeup_period()是一个用于设置ULP(Ultra Low-Power)协处理器唤醒主CPU的周期的方法。它有以下主要特点、应用场景和注意事项:

主要特点:

esp32.ULP.set_wakeup_period()是一个esp32.ULP类的方法,它可以作用于任何一个ULP协处理器的对象。
esp32.ULP.set_wakeup_period()的功能是设置ULP协处理器在运行完一次程序后,等待多长时间再唤醒主CPU。
esp32.ULP.set_wakeup_period()的返回值是None,表示设置成功。
esp32.ULP.set_wakeup_period()的参数有两个,第一个是一个整数,表示唤醒周期的索引,范围为0-412。第二个是一个整数,表示唤醒周期的微秒数,范围为0-4294967295。
esp32.ULP.set_wakeup_period()的默认参数是0和0,表示不唤醒主CPU。

应用场景:

esp32.ULP.set_wakeup_period()的功能可以用于在ESP32的低功耗模式下,定时唤醒主CPU,执行一些需要定时或周期性执行的任务,例如监测传感器、控制外设、更新数据等。
esp32.ULP.set_wakeup_period()的功能可以用于在ESP32的正常工作模式下,让主CPU在一定时间后被ULP协处理器唤醒,执行一些需要延迟或定时执行的任务,例如发送网络请求、显示结果、保存数据等。
esp32.ULP.set_wakeup_period()的功能还可以用于在ESP32的深度睡眠模式下,让主CPU在一定时间后被ULP协处理器唤醒,执行一些需要低频率或低功耗执行的任务,例如检查电池电量、同步时间、更新固件等。

注意事项:

esp32.ULP.set_wakeup_period()的功能需要注意与其他占用ULP协处理器或引脚的功能的冲突,例如SPI、I2C、UART等。
esp32.ULP.set_wakeup_period()的功能需要注意与其他占用共享内存或中断信号的功能的影响,例如网络通信、文件系统、垃圾回收等。
esp32.ULP.set_wakeup_period()的功能需要注意与其他需要中断服务或定时器服务的功能的协调,例如机器定时器、机器中断等。

以下是几个使用MicroPython的esp32.ULP.set_wakeup_period()方法的实际运用程序案例:

案例一:使用esp32.ULP.set_wakeup_period()来设置ULP协处理器每隔10秒唤醒主CPU一次,并打印出当前时间。

# 导入必要的模块
import esp32
import machine
import time

# 定义一个空程序的源代码,使用esp32_ulp提供的汇编语法
empty_src = """
entry: halt # 停止执行
"""

# 使用esp32_ulp.assemble()函数来编译源代码,并返回一个字节对象
empty_bin = esp32_ulp.assemble(empty_src)

# 使用esp32.ULP.set_wakeup_period()函数来设置ULP协处理器唤醒周期为10秒
esp32.ULP.set_wakeup_period(0, 10000000)

# 使用esp32.ULP.load_binary()函数来加载二进制文件到ULP协处理器内存中,起始地址为0
esp32.ULP.load_binary(0, empty_bin)

# 使用esp32.ULP.run()函数来运行二进制文件,起始地址为0
esp32.ULP.run(0)

# 定义一个循环,每次被唤醒后打印出当前时间,并让主CPU重新进入睡眠模式
while True:
    # 使用time.localtime()函数来获取当前时间,返回一个元组
    t = time.localtime()
    # 使用print()函数来打印出当前时间,格式为年-月-日 时:分:秒
    print('%d-%02d-%02d %02d:%02d:%02d' % t[:6])
    # 使用machine.lightsleep()函数来让主CPU进入轻度睡眠模式,等待下一次唤醒
    machine.lightsleep()

案例二:使用esp32.ULP.set_wakeup_period()来设置ULP协处理器在运行完一次程序后,延迟5秒再唤醒主CPU,并控制一个LED灯的闪烁。

# 导入必要的模块
import esp32
import machine

# 定义一个控制LED灯的程序的源代码,使用py-esp32-ulp提供的汇编语法
led_src = """
data: .long 0
entry: move r3, data # 将数据地址存入r3寄存器
       load r0, r3, 0 # 将数据值加载到r0寄存器
       move r1, 18 # 将引脚号18存入r1寄存器
       i2c_rd r2, r1, 28, 1 # 读取GPIO_OUT寄存器的值,存入r2寄存器
       xor r2, r2, r0 # 将r2和r0做异或运算,得到反转后的值,存入r2寄存器
       i2c_wr r2, r1, 28, 1 # 将r2的值写入GPIO_OUT寄存器,控制LED灯的状态
       store r2, r3, 0 # 将r2的值存回数据地址,更新数据值
       halt # 停止执行
"""

# 使用py_esp32_ulp.assemble()函数来编译源代码,并返回一个字节对象
led_bin = py_esp32_ulp.assemble(led_src)

# 使用esp32.ULP.set_wakeup_period()函数来设置ULP协处理器唤醒周期为5秒
esp32.ULP.set_wakeup_period(0, 5000000)

# 使用esp32.ULP.load_binary()函数来加载二进制文件到ULP协处理器内存中,起始地址为0
esp32.ULP.load_binary(0, led_bin)

# 使用esp32.ULP.run()函数来运行二进制文件,起始地址为0
esp32.ULP.run(0)

# 创建一个Pin对象,绑定到第18号引脚,设置为输出模式,并初始化为低电平(关闭LED灯)
led = machine.Pin(18, machine.Pin.OUT)
led.value(0)

# 此时,ESP32的第18号引脚会每隔5秒反转一次电平,从而控制LED灯的闪烁

案例三:使用esp32.ULP.set_wakeup_period()来设置ULP协处理器在运行完一次程序后,等待一个外部中断再唤醒主CPU,并读取一个按钮的状态。

# 导入必要的模块
import esp32
import machine

# 定义一个读取按钮的程序的源代码,使用binutils-esp32ulp编译生成,保存在ESP32的文件系统中,文件名为button.bin

# 使用open()函数来打开二进制文件,并读取其内容,返回一个字节对象
with open('button.bin', 'rb') as f:
    button_bin = f.read()

# 使用esp32.ULP.set_wakeup_period()函数来设置ULP协处理器唤醒周期为-1,表示等待一个外部中断再唤醒主CPU
esp32.ULP.set_wakeup_period(-1)

# 使用esp32.ULP.load_binary()函数来加载二进制文件到ULP协处理器内存中,起始地址为0
esp32.ULP.load_binary(0, button_bin)

# 使用esp32.ULP.run()函数来运行二进制文件,起始地址为0
esp32.ULP.run(0)

# 创建一个Pin对象,绑定到第19号引脚,设置为输入模式,并启用内部上拉电阻
button = machine.Pin(19, machine.Pin.IN, machine.Pin.PULL_UP)

# 定义一个中断处理函数,用于唤醒ULP协处理器
def wake_ulp(pin):
    # 使用esp32.ULP.set_wakeup_period()函数来设置ULP协处理器唤醒周期为0,表示立即唤醒
    esp32.ULP.set_wakeup_period(0)

# 使用Pin对象的irq()方法来设置中断触发模式为下降沿,并绑定中断处理函数
button.irq(trigger=machine.Pin.IRQ_FALLING, handler=wake_ulp)

# 定义一个循环,每次被唤醒后读取共享内存中的数据,并打印出按钮的状态
while True:
    # 使用esp32.ULP.mem_read()函数来读取共享内存中的数据,地址为0,返回一个整数
    button_state = esp32.ULP.mem_read(0)
    # 判断按钮的状态是按下还是松开,并打印出结果
    if button_state == 0:
        print('Button is pressed')
    else:
        print('Button is released')
    # 使用machine.lightsleep()函数来让主CPU进入轻度睡眠模式,等待下一次唤醒
    machine.lightsleep()

案例四:设置低功耗唤醒周期:

import esp32
esp32.ULP.set_wakeup_period(5000) # every 5 seconds

案例五:设置不同周期重复唤醒:

import esp32, math
for i in range(5):
esp32.ULP.set_wakeup_period(int(2000*math.sin(i)+3000))

案例六:清除唤醒周期设置:

import esp32
esp32.ULP.set_wakeup_period(0)

第一个例子设置固定5秒的唤醒周期。第二个例子设置不同的随机周期循环唤醒。第三个例子清除之前的唤醒周期设置。这个函数用于设置ULP协处理器的定期唤醒周期,起到低功耗管理的作用。通过 steward, frequency等参数可以灵活配置唤醒策略。

案例七:设置 ULP 协处理器的唤醒周期为 1 秒:

import esp32

# 定义 ULP 程序
ulp_program = esp32.ULP()

# 设置 ULP 协处理器的唤醒周期为 1 秒
ulp_program.set_wakeup_period(1)

这个示例程序展示了如何使用 set_wakeup_period() 方法将 ULP 协处理器的唤醒周期设置为 1 秒。

案例八:设置 ULP 协处理器的唤醒周期为 500 毫秒:

import esp32

# 定义 ULP 程序
ulp_program = esp32.ULP()

# 设置 ULP 协处理器的唤醒周期为 500 毫秒
ulp_program.set_wakeup_period(0.5)

这个示例程序展示了如何使用 set_wakeup_period() 方法将 ULP 协处理器的唤醒周期设置为 500 毫秒。

案例九:动态设置 ULP 协处理器的唤醒周期:

import esp32
import time

# 定义 ULP 程序
ulp_program = esp32.ULP()

# 设置 ULP 协处理器的初始唤醒周期为 1 秒
ulp_program.set_wakeup_period(1)

# 等待一段时间
time.sleep(5)

# 动态调整 ULP 协处理器的唤醒周期为 500 毫秒
ulp_program.set_wakeup_period(0.5)

这个示例程序展示了如何在运行过程中动态地调整 ULP 协处理器的唤醒周期。开始时,将唤醒周期设置为 1 秒,然后等待 5 秒后将其调整为 500 毫秒。

这些示例程序展示了如何使用 esp32.ULP.set_wakeup_period() 方法设置 ESP32 的 ULP 协处理器的唤醒周期。通过调整唤醒周期,您可以控制 ULP 协处理器的运行时间和功耗,以满足特定的需求和应用场景。请注意,唤醒周期的单位是秒,可以使用小数表示毫秒。

在这里插入图片描述

猜你喜欢

转载自blog.csdn.net/weixin_41659040/article/details/132943293
今日推荐