跳转至

fota - 底层固件升级

孟伟

一、概述

fota库是LuatOS系统中的底层固件升级模块,用于实现设备固件的远程更新功能。该模块支持多种升级方式,包括:

  • 逐段接收并写入升级包数据

  • 直接从文件系统读取升级包文件进行升级

fota模块支持灵活的存储位置配置,可以使用内部存储或外部SPI Flash进行固件升级,同时提供了完整的升级流程控制和状态查询功能。

1.1 主要功能

  • 初始化升级流程,配置存储位置和大小

  • 逐段接收并写入升级包数据或直接从文件读取升级包

  • 检查升级状态和进度

  • 完成升级流程并重启系统

二、核心示例

1、核心示例是指:使用本库文件提供的核心API,开发的基础业务逻辑的演示代码;

2、核心示例的作用是:帮助开发者快速理解如何使用本库,所以核心示例的逻辑都比较简单;

3、对于升级,不建议使用原始接口,可以使用更简单的libfota2扩展库,demo请参考 LuatOS仓库 中各个产品目录下的demo/fota2

-- 如果是从http获取升级包, 那么看demo/fota就可以了
-- 以下是从其他途径获取更新包后, 调用本fota库的基本逻辑

-- 逐段传入
sys.taskInit(function()
    fota.init()
    while 1 do
        local buf = xxx -- 这里是从其他途径获取的升级包片段
        -- buf 可以是zbuff 也可以是string
        -- 每次写入的数据长度最大不应超过4k
        local result, isDone, cache = fota.run(buf)
        if not result then
            log.info("fota", "出错了")
            break
        end
        if isDone then
            while true do
                local succ,fotaDone  = fota.isDone()
                if not succ then
                    log.info("fota", "出错了")
                    break
                end
                if fotaDone then
                    log.info("fota", "已完成")
                    break
                end
                sys.wait(100)
            end
            break
        end
        sys.wait(100)
    end
end)

-- 使用文件一次性传入
sys.taskInit(function()
    fota.init()
    fota.file("/xxx") -- 传入具体的路径
end)

三、常量详解

核心库常量,顾名思义是由合宙LuatOS内核固件中定义的、不可重新赋值或修改的固定值,在脚本代码中不需要声明,可直接调用;

fota核心库没有常量。

四、函数详解

4.1 fota.init(storge_location, len, param1, param2)

功能

初始化fota流程,配置升级包的存储位置和最大空间。

参数

storge_location

参数含义:fota数据存储的起始位置
         如果是int,则由芯片平台具体判断
         如果是string,则存储在文件系统中
         如果为nil,则由底层决定存储位置
数据类型:int或string或nil
取值范围:int类型时:根据芯片平台不同,支持不同的地址范围
         string类型时:有效的文件系统路径
是否必选:可选
参数示例:nil

len

参数含义:数据存储的最大空间
数据类型:int
取值范围:根据实际硬件平台和可用存储空间确定
是否必选:可选

param1

参数含义:当数据存储在spiflash时,为spi_device
数据类型:userdata
取值范围:有效的SPI设备句柄
是否必选:仅当使用外部SPI Flash时必选

param2

参数含义:目前只用于外部flash更新时spiflash电源控制脚
数据类型:int
取值范围:有效的GPIO引脚编号
是否必选:仅当需要控制SPI Flash电源时必选

返回值

local result = fota.init()

result

参数含义:初始化是否成功;成功返回true,失败返回false
数据类型:boolean
取值范围:true/false

例子

local result = fota.init()    --Air780EXXX系列使用固定内部地址,所以不需要参数了
local result = fota.init(0xe0000000, 0, spi_device, 27)    --EC7XX系列允许使用外部flash更新,但是地址必须加上0xe0000000的偏移

4.2 fota.wait()

功能

等待底层fota流程准备好

参数

返回值

local isDone = fota.wait()

isDone

参数含义:是否准备好;准备好返回true,否则返回false
数据类型:boolean
取值范围:true/false

例子

local isDone = fota.wait()

4.3 fota.run(buff, offset, len)

功能

写入fota数据,支持逐段写入升级包。

注意事项:如果传入的是zbuff,写入成功后,请自行清空zbuff内的数据

参数

buff

参数含义:fota数据,尽量用zbuff以提高性能
数据类型:zbuff或string
取值范围:有效的二进制数据
是否必选:是

offset

参数含义:起始偏移量,仅在传入zbuff时有效
数据类型:int
取值范围:非负整数,不超过zbuff大小
是否必选:可选,默认是0

len

参数含义:写入长度,仅在传入zbuff时有效
数据类型:int
取值范围:非负整数,不超过zbuff剩余空间
是否必选:可选,默认是zbuff:used()

返回值

local result, isDone, cache = fota.run(buff, offset, len)

result

参数含义:写入是否成功;成功返回true,失败返回false
数据类型:boolean
取值范围:true/false

isDone

参数含义:是否写入到最后一块;写入到最后一块返回true,否则返回false
数据类型:boolean
取值范围:true/false

cache

参数含义:还未写入的数据量,超过64K必须做等待
数据类型:int
取值范围:非负整数,超过64K必须做等待

例子

local result, isDone, cache = fota.run(buff, offset, len) -- 写入fota流程

-- 提示:如果传入的是zbuff,写入成功后,请自行清空zbuff内的数据

fota.run(buff, 0, 1024)

4.4 fota.file(path)

功能

从指定文件读取fota数据

参数

path

参数含义:升级文件的文件路径
数据类型:string
取值范围:有效的文件系统路径
是否必选:是

返回值

local result, isDone, cache = fota.file("/xxx.bin")

result

参数含义:写入是否成功;有异常返回false,无异常返回true
数据类型:boolean
取值范围:true/false

isDone

参数含义:接收到最后一块返回true,否则返回false
数据类型:boolean
取值范围:true/false

cache

参数含义:还未写入的数据量,超过64K必须做等待
数据类型:int
取值范围:非负整数,超过64K必须做等待

例子

local result, isDone, cache = fota.file("/xxx.bin") -- 写入fota流程

4.5 fota.isDone()

功能

等待底层fota流程完成

参数

返回值

local result, isDone = fota.isDone()

result

参数含义:有异常返回false,无异常返回true
数据类型:boolean
取值范围:true/false

isDone

参数含义:写入到最后一块返回true,否则返回false
数据类型:boolean
取值范围:true/false

例子

local result, isDone = fota.isDone()

4.6 fota.finish(is_ok)

功能

结束fota流程

参数

is_ok

参数含义:是否完整走完流程,true表示正确走完流程了
数据类型:boolean
取值范围:true或false
是否必选:是

返回值

local result = fota.finish(is_ok)

result

参数含义:成功返回true, 失败返回false
数据类型:boolean
取值范围:true或false

例子

local result = fota.finish(true)

五、产品支持说明

支持LuatOS开发的所有产品都支持fota核心库