4.4.8.2. OTA API
本系统提供底层刷写库 libupdate.so,并实现了一套跨平台的 API,用于烧写 OTA 升级包。
源码路径:hbre/otaupdate/src/ota_apis/hobot_ota_hl.c
头文件: hobot_ota_hl.h
针对 OTA HighLevel API开发了ota_tool 工具,使用该工具可以帮助客户在设计 OTA Service 时更便捷地参考和实现相关功能。
源码路径:hbre/otaupdate/src/ota_tool
头文件: hobot_ota_hl.h
链接库: libupdate.so
动态库接口返回的错误类型
动态库错误值定义如下:
enum ota_err_e {
OTA_SUCCESS = 0,
OTAERR_IO,
OTAERR_PLAT_UNSUPPORT,
OTAERR_REPEAT,
OTAERR_MUTEX_INIT_LOCK_ERR,
OTAERR_NOTINIT,
OTAERR_NULLPOINTER,
OTAERR_SHORTBUF,
OTAERR_THREAD_CREATE,
OTAERR_RANGE,
OTAERR_STAGE,
OTAERR_IMAGE_WRITE,
OTAERR_BOOT_FAILED,
OTAERR_VEEPROM,
OTAERR_FILE_TYPE,
OTAERR_UNZIP,
OTAERR_NO_EXISTS,
OTAERR_MALLOC,
OTAERR_VERIFY,
OTAERR_IMG_SIZE,
OTAERR_UPDATE_STATUS,
}
接口列表
| 接口原型 | 描述 |
|---|---|
| int32_t otaInitLib(void); | 动态库初始化 |
| int32_t otaDeinitLib(void); | 动态库反初始化 |
| int32_t otaGetLibVersion(char *version, int32_t len); | 获取动态库版本 |
| int32_t otaRequestStart(const char *image_name, enum ota_update_owner owner); | 启动升级线程 |
| int32_t otaGetResult(void); | 获取升级状态和结果 |
| int32_t otaGetProgress(void); | 获取升级进度 |
| int32_t otaGetUpdatingImageName(char *image_name , int32_t len); | 获取正在升级的包 |
| int32_t otaGetSysVersion(char *version, int32_t len); | 获取当前系统版本 |
| int32_t otaGetPartition(uint8_t *partition); | 获取当前启动的 AB 分区 |
| int32_t otaSetPartition(uint8_t partition); | 设置下次启动的 AB 分区 |
| int32_t otaGetOwnerFlag(enum ota_update_owner *owner); | 获取 OTA owner(重启后) |
| int32_t otaMarkOTASuccessful(void); | 标记 OTA 升级成功(重启后) |
| int32_t otaCheckUpdate(void); | 检查是否升级成功(重启后) |
| int32_t otaPartitionSync(void); | AB 分区、bak 分区同步 |
| void otaClearFlags(void); | 结束升级,清除 ota 标志 |
otaInitLib
【函数声明】
int32_t otaInitLib(void);
【参数描述】
[OUT] N/A
[IN] N/A
【返回值】
OTA_SUCCESS: 成功
-OTAERR_REPEAT: 重复初始化
【功能描述】
板端刷写接口动态库初始化,主要进行全局结构体g_upgrade_info的初始化。
【示例代码】
#include <stdio.h>
#include <hobot_ota_hl.h>
int main(void) {
int32_t ret;
ret = otaInitLib();
if (ret != 0) {
printf("otaInitLib return: %d\n", ret);
return ret;
}
ret = otaDeinitLib();
if (ret != 0) {
printf("otaDeinitLib return: %d\n", ret);
return ret;
}
return 0;
}
otaDeinitLib
【函数声明】
int32_t otaDeinitLib(void);
【参数描述】
[OUT] N/A
[IN] N/A
【返回值】
OTA_SUCCESS: 成功
-OTAERR_NOTINIT: 当前未初始化,不能调用反初始化
【功能描述】
反初始化
【示例代码】
参考 otaInitLib
otaGetLibVersion
【函数声明】
int32_t otaGetLibVersion(char *version, int32_t len);
【参数描述】
[OUT] version: 用于存储 version 信息。version以三段式字符串形式返回(如:1.0.0)
[IN] len: 传入的 buffer 长度
【返回值】
OTA_SUCCESS: 成功
-OTAERR_NULLPOINTER: version 空指针
-OTAERR_SHORTBUF: 传入的 buffer 过小
-OTAERR_PLAT_UNSUPPORT: 不支持获取版本号
【功能描述】
获取本动态库版本
【示例代码】
#include <stdio.h>
#include <hobot_ota_hl.h>
int main(void) {
int32_t ret;
char version[128];
if (ret = otaGetLibVersion(version, sizeof(version))) {
return ret;
}
printf("version: %s\n", version);
}
otaRequestStart
【函数声明】
int32_t otaRequestStart(const char *image_name, enum ota_update_owner owner);
【参数描述】
[OUT] N/A
[IN] image_name: 升级包绝对路径。支持多种不同类型的包同时传入,用分号隔开。
[IN] owner: 发起本次升级的进程, owner 由 enum ota_update_owner 定义
【返回值】
OTA_SUCCESS: 成功
-OTAERR_NULLPOINTER: image_name 空指针
-OTAERR_RANGE: owner设置错误,超出当前定义范围
-OTAERR_NOTINIT: 未初始化本动态库
-OTAERR_REPEAT: 当前有其他进程正在升级
-OTAERR_IO: IO失败
-OTAERR_THREAD_CREATE: 线程创建失败
【功能描述】
启动升级线程,对传入的image_name进行升级,并设置当前升级所有者
【示例代码】
#include <stdio.h>
#include <hobot_ota_hl.h>
int main(void) {
int32_t ret;
int32_t result;
int32_t progress;
char imgname[256];
ret = otaInitLib();
if (ret != 0) {
printf("otaInitLib return: %d\n", ret);
return ret;
}
if (ret = otaRequestStart("/userdata/all_in_one.zip", OTA_TOOL)) {
printf("otaRequestStart return: %d\n", ret);
return ret;
}
do {
result = otaGetResult();
if (ret = otaGetUpdatingImageName(imgname, sizeof(imgname))) {
printf("otaGetUpdatingImageName return: %d\n", imgname);
}
progress = otaGetProgress();
printf("current image: %s, progress: %d\n", imgname, progress);
sleep(1);
} while(result != 0 && result != 3);
ret = otaGetPartition(&cur_part);
if (ret != 0) {
printf("otaGetPartition returned with %d\n", ret);
}
ret = otaSetPartition(1 - cur_part);
if (ret != 0) {
printf("otaSetPartition returned with %d\n", ret);
}
/* Then reboot system */
return 0;
}
otaGetResult
【函数声明】
int32_t otaGetResult(void);
【参数描述】
[OUT] N/A
[IN] N/A
【返回值】
OTA_UPGRADE_NOT_START: 升级未开始
OTA_UPGRADE_IN_PROGRESS: 升级中
OTA_UPGRADE_SUCCESS: 升级结束,成功
OTA_UPGRADE_FAILED: 升级结束,失败
-OTAERR_NOTINIT: 未初始化本动态库
【功能描述】
获取升级结果
【示例代码】
otaGetProgress
【函数声明】
int32_t otaGetProgress(void);
【参数描述】
[OUT] N/A
[IN] N/A
【返回值】
0 ~ 100: 当前升级进度(%)
-OTAERR_NOTINIT: 未初始化本动态库
【功能描述】
获取当前升级进度
【示例代码】
otaGetUpdatingImageName
【函数声明】
int32_t otaGetUpdatingImageName(char *image_name , int32_t len);
【参数描述】
[OUT] image_name: 用于存放结果的 buffer。 image_name 可能出现的内容: “idle_state”–升级未开始 “all_img_finish”–升级完成 “”–未开始烧写镜像就失败 其他以”.img”结尾的包名
[IN] len: buffer 长度
【返回值】
OTA_SUCCESS: 成功
-OTAERR_NULLPOINTER: image_name 空指针
-OTAERR_NOTINIT: 本动态库未初始化
-OTAERR_SHORTBUF: buffer长度太短
【功能描述】
获取当前正在升级的镜像
【示例代码】
otaGetSysVersion
【函数声明】
int32_t otaGetSysVersion(char *version, int32_t len);
【参数描述】
[OUT] version: 用于存储 version 信息。version 中保存系统软件版本,以日期开头(yyyymmdd)
[IN] len: 传入的 buffer 长度
【返回值】
OTA_SUCCESS: 成功
-OTAERR_NULLPOINTER: version 空指针
-OTAERR_SHORTBUF: 传入的 buffer 过小
-OTAERR_IO: io 错误,请重试
【功能描述】
获取当前系统软件版本
【示例代码】
#include <stdio.h>
#include <hobot_ota_hl.h>
int main(void) {
int32_t ret;
char version[128];
if (ret = otaGetSysVersion(version, sizeof(version))) {
printf("otaGetSysVersion return: %d\n", ret);
return -1;
}
printf("current system version: %s\n", version);
return 0;
}
otaGetPartition
【函数声明】
int32_t otaGetPartition(uint8_t *partition);
【参数描述】
[OUT] partition: 用于接收当前分区的变量地址。 *partition=0:当前为 A 分区,*partition=1:当前为 B 分区
[IN] N/A
【返回值】
OTA_SUCCESS: 成功
-OTAERR_NULLPOINTER: partition 为空指针
-OTAERR_IO: io 错误,请重试
【功能描述】
获取当前启动 AB 分区
【示例代码】
otaSetPartition
【函数声明】
int32_t otaSetPartition(uint8_t partition);
【参数描述】
[OUT] N/A
[IN] partition: 下次启动分区。0:A 分区,1:B 分区
【返回值】
OTA_SUCCESS: 成功
-OTAERR_NOTINIT: 本动态库未初始化
-OTAERR_RANGE: partition 范围错误,partition 范围为0和1
-OTAERR_IO: io 错误,请重试
-OTAERR_STAGE: 当前升级阶段不支持。升级过程中或升级失败不支持
【功能描述】
设置下次启动的 AB 分区
【示例代码】
otaGetOwnerFlag
【函数声明】
int32_t otaGetOwnerFlag(enum ota_update_owner *owner);
【参数描述】
[OUT] owner: 用于接收当前升级 owner 的变量。请参考 enum ota_update_owner
[IN] N/A
【返回值】
OTA_SUCCESS: 成功
-OTAERR_NOTINIT: 未初始化
-OTAERR_NULLPOINTER: partition 为空指针
-OTAERR_IO: io 错误,请重试
【功能描述】
获取当前升级 owner
【示例代码】
static int check_and_mark(void) {
enum ota_update_owner owner;
int32_t ret;
ret = otaGetOwnerFlag(&owner);
if (ret != 0) {
printf("otaGetOwnerFlag returned with %d\n", ret);
return -1;
}
if (owner != OTA_TOOL) {
printf("The OTA update is not launched by ota_tool, owner: %d\n", owner);
return -1;
}
ret = otaCheckUpdate();
if (ret == -OTAERR_IMAGE_WRITE) {
printf("ota_tool: OTA image write failed, is there a reboot during update?\n");
goto clearFlags;
}
if (ret == -OTAERR_BOOT_FAILED) {
printf("ota_tool: The new package boot failed. Please check the packages\n");
goto clearFlags;
}
if (ret != 0) {
printf("otaCheckUpdate returned with %d\n", ret);
goto clearFlags;
}
ret = otaMarkOTASuccessful();
if (ret != 0) {
printf("otaMarkOTASuccessful returned with %d\n", ret);
goto clearFlags;
}
ret = otaPartitionSync();
if (ret != 0) {
printf("otaPartitionSync returned with %d\n", ret);
goto clearFlags;
}
clearFlags:
otaClearFlags();
return ret;
}
otaMarkOTASuccessful
【函数声明】
int32_t otaMarkOTASuccessful(void);
【参数描述】
[OUT] N/A
[IN] N/A
【返回值】
OTA_SUCCESS: 成功
-OTAERR_NOTINIT: 未初始化
-OTAERR_IO: io 错误,请重试
【功能描述】
标记本次升级成功
【示例代码】
otaCheckUpdate
【函数声明】
int32_t otaCheckUpdate(void);
【参数描述】
[OUT] N/A
[IN] N/A
【返回值】
OTA_SUCCESS: 成功
-OTAERR_IO: io 错误,请重试
-OTAERR_STAGE: 未进行升级
-OTAERR_IMAGE_WRITE: 镜像写入失败
-OTAERR_BOOT_FAILED: 新镜像启动失败或未切换分区
【功能描述】
检查本次升级是否成功
【示例代码】
otaClearFlags
【函数声明】
void otaClearFlags(void);
【参数描述】
[OUT] N/A
[IN] N/A
【返回值】
N/A
【功能描述】
清除 OTA flags
【示例代码】
otaPartitionSync
【函数声明】
int32_t otaPartitionSync(void);
【参数描述】
[OUT] N/A
[IN] N/A
【返回值】
-OTAERR_NOTINIT: 未初始化
-OTAERR_IO: io 错误
-OTAERR_REPEAT: 与其他升级进程冲突
OTA_SUCCESS: 成功
【功能描述】
AB分区、bak分区同步