开发笔记:如何为"小智"服务器启用并调试 License 功能
在嵌入式开发中,集成第三方服务(如"小智"语音助手)时,License 授权验证是绕不开的一环。最近在处理 某芯片AI语音智能体项目时,我整理了一下的 License 功能开启、调试及恢复流程。
这篇博客将详细记录从修改 CMake 配置、编写代码逻辑,到通过串口工具获取和写入密钥的全过程,希望能帮助遇到同样问题的开发者。
1. 项目配置:指定服务器与开启宏定义
首先,我们需要在编译配置中明确指定服务器实现为"小智",并打开 License 相关的功能开关。
第一步:修改 CMakeLists.txt
打开项目根目录下的 CMakeLists.txt 文件,找到服务器实现的配置部分。我们需要将 SERVER_IMPL 设置为 xiaozhi。
1# 选择服务器实现
2set(SERVER_IMPL xiaozhi)
注意:确保注释掉其他服务器(如 qiniu)的配置,以免冲突。

第二步:开启 License 宏
在 project/ln_model_public/app/common.h 文件中,我们需要定义 License 相关的宏。将 CONFIG_LICENSE_ENABLE 的值设为 1。
1// common.h
2#define CONFIG_LICENSE_ENABLE (1)
3#define CONFIG_LICENSE_ERASE (0)
4#define CONFIG_OTA_ENABLE (0)
2. 代码逻辑:植入检查与条件编译
配置修改完成后,我们需要在应用代码中植入检查逻辑,并确保"小智"特有的接口被正确调用。
在 usr_app.c 中启动检查
在用户应用任务创建函数 creat_usr_app_task 中,加入 License 检查代码。如果检查失败,程序应直接返回,阻止后续运行。
1// usr_app.c
2void creat_usr_app_task(void)
3{
4 // ... 其他初始化代码 ...
5
6 #if defined(CONFIG_LICENSE_ENABLE) && CONFIG_LICENSE_ENABLE
7 // 启动 License 检查,如果返回 false 则终止
8 if (!cli_license_check()) return;
9 #endif
10
11 // ... 后续业务逻辑 ...
12}

在 server_interface.h 中适配接口
为了让编译器识别 cli_license_check 函数,我们需要在 server_interface.h 中添加条件编译。只有当定义了 CONFIG_SERVER_IMPL_XIAOZHI 时,才声明该函数,否则提供一个空的 inline 实现以避免编译错误。

3. 调试阶段:绕过验证进入写入模式
这是最关键的一步。为了能够向设备写入新的序列号(Serial Num)和密钥(License Key),我们需要暂时"欺骗"系统,让它认为当前的 License 是无效的,从而进入激活/写入模式。
修改 cli_license.c
打开 project/ln_model_public/app/servers/xiaozhi/cli_license.c。找到 cli_license_check 函数,注释掉 is_license_key_valid() 的判断逻辑。
将这句license_key判断注释掉,否则无法进入小智的串码写入模式

4. 硬件调试:读取 MAC 与 写入密钥
代码编译下载后,我们需要通过串口调试助手(如 SSCOM)与设备交互。
步骤 A:确认进入激活模式
使用 921600 波特率打开串口。如果看到如下日志,说明我们成功绕过了验证,进入了激活等待状态:
[cli_license_check:441] license key is invalid, start to activate
[ate_cli_thr_entry:373] start

步骤 B:获取设备信息
将波特率切换为 1000000(下载口波特率),发送查询指令:
- 查询 MAC 地址 :发送
AT+MAC=?- 返回示例:
+MAC:00:50:19:81:c9:bb
- 返回示例:
- 查询当前密钥状态 :发送
AT+SER_KEY=?- 此时会返回设备当前的
SER_NUM和LIC_KEY(如果是新设备可能是默认值或空)。
- 此时会返回设备当前的

步骤 C:生成并写入新的 License
如果你还没有对接官方的商务流程,可以使用官方提供的测试链接生成临时密钥:
-
测试生成地址 :
https://xiaozhi.me/api/developers/generate-license...(需替换 token) -
写入指令格式:
AT+SER_KEY="设备序列号","授权密钥" -
实际示例:
举例:00:50:3b:66:d4:aA:
AT+SER_KEY="LN882H_AI_BOX_1_03522700A30980BF","7PMBsN2WugX6QdHfUhWKWaykEoQgUQ3W"
发送指令后,若返回 OK,则说明写入成功。
5. 最终发布:恢复代码保护
调试完成后,千万不要直接发布 当前的代码!必须回到 cli_license.c,将第 3 步中注释掉的 is_license_key_valid() 判断恢复。
1// 恢复后的代码
2if (is_license_key_valid()) return -1;

这样,设备在下次启动时就会严格执行 License 校验,确保产品的安全性。
