7.3.2 OneTLS 加密组件
7.3.2 OneTLS 加密组件
📚 本节导读
学习时长:约 30 分钟
难度级别:⭐⭐⭐⭐☆
前置知识:第 7.3.1 节 MBED TLS、TLS 1.3 协议原理
🎯 学习目标
- 理解 OneTLS 与 MBED TLS 的关系和定位差异
- 掌握 OneTLS 的分层架构(crypto + tls)
- 掌握
onetls_*核心 API 的使用 - 掌握 OneTLS 的 Kconfig 配置方法
- 知道何时选择 OneTLS vs MBED TLS
一、OneTLS 概述
OneTLS 是 OneOS 自研的轻量级 SSL/TLS 安全通信库,位于 components/security/onetls/。它支持最新的 TLS 1.3 与 DTLS 1.3(draft 38) 标准,向用户提供简单易用的 onetls_* 操作接口,为物联网通信安全提供保障。
一句话核心:onetls_ctx(会话上下文)→ onetls_new_ctx 创建 → onetls_set_socket 绑定 Socket → onetls_connect 握手(TLS 1.3 一次往返完成)→ onetls_send/onetls_recv 加解密收发应用数据 → onetls_del_ctx 释放。
典型场景:
- 资源受限 MCU 上的 TLS 1.3 安全通信(PSK/证书模式);
- 低时延场景(TLS 1.3 握手更快、支持 0-RTT 与会话恢复);
- 需要国密 SM4/SM2 合规的场景(
TLS_SM4_GCM_SM3/TLS_SM4_CCM_SM3套件、curve_SM2)。
1.1 与 MBED TLS 的对比
| 特性 | OneTLS | MBED TLS |
|---|---|---|
| 来源 | OneOS 自研 | ARM 开源(mbedTLS) |
| 协议版本 | TLS 1.3 / DTLS 1.3(draft 38) | TLS 1.0/1.1/1.2、DTLS 1.0/1.2 |
| 握手效率 | TLS 1.3 更快,支持 0-RTT | TLS 1.2 需多次往返 |
| 会话恢复 | 支持(ONETLS_SUPPORT_RESUMPTION,Session Ticket) | 支持 |
| 国密 | 支持 SM4/SM2 | 需额外配置 |
| 体积 | 更精简 | 功能完整 |
| 适用场景 | 资源受限、需 TLS 1.3/国密 | 需要完整 TLS 功能、证书管理 |
关键理解(重要):OneTLS 支持 DTLS(
ONETLS_RUN_DTLS默认 y),并支持 0-RTT、会话恢复、密钥更新、MTU 设置。因此"需要 DTLS 就得选 MBED TLS"是错误认知——OneTLS 同样提供 DTLS 能力。
1.2 目录结构
components/security/onetls/
├── crypto/ # 密码学模块(AES/SM4/SHA/椭圆曲线等)
│ ├── include/ # 密码学接口头文件
│ └── source/ # 密码学实现
├── tls/ # TLS/DTLS 协议实现
│ ├── include/ # TLS 接口头文件
│ ├── source/ # TLS 协议实现
│ └── weave.yaml
├── tests/ # 测试示例(tls 和 dtls 测试)
├── Kconfig # 配置选项
├── readme.md
└── weave.yaml二、分层架构
┌─────────────────────────────────┐
│ 应用层 │
│ (MQTT over TLS, HTTPS 等) │
├─────────────────────────────────┤
│ OneTLS TLS 协议层 (tls/) │
│ ┌───────────┬───────────────┐ │
│ │ TLS 1.3 │ DTLS 1.3 │ │
│ │ 握手/记录 │ 握手/记录 │ │
│ │ 0-RTT/恢复│ MTU 分片 │ │
│ └───────────┴───────────────┘ │
├─────────────────────────────────┤
│ OneTLS 密码学层 (crypto/) │
│ ┌──────┬──────┬──────┬──────┐ │
│ │ AES │ SM4 │ ECC │ SHA │ │
│ │ GCM │ GCM │ SM2 │ HMAC│ │
│ └──────┴──────┴──────┴──────┘ │
├─────────────────────────────────┤
│ 硬件平台 │
└─────────────────────────────────┘关键理解(crypto + tls 分层):
- crypto/ 密码学层:提供底层算法(AES-GCM/CCM、SM4-GCM/CCM、SHA-256、HMAC、椭圆曲线 curve25519/secp256r1/SM2 等),与算法实现解耦;
- tls/ 协议层:基于 crypto 层实现 TLS 1.3 / DTLS 1.3 的握手、密钥调度、记录层加解密、会话恢复与 0-RTT;
- 通过 Kconfig 按需裁剪密码套件与椭圆曲线组,控制 ROM 占用。
三、核心 API(onetls_*)
OneTLS 的核心操作接口全部以 onetls_ 前缀命名,采用"上下文 + 句柄"模型。完整源码(头文件声明):
uint32_t onetls_init(void);
const char *onetls_version(onetls_version_vrcb *vrcb);
onetls_ctx *onetls_new_ctx(uint8_t mode);
void onetls_del_ctx(onetls_ctx *ctx);
void onetls_set_socket(onetls_ctx *ctx, int recv_fd, int send_fd);
uint32_t onetls_set_outband_psk_hint(onetls_ctx *ctx, uint8_t *hint, uint32_t hint_len);
void onetls_set_nst_callback(onetls_ctx *ctx, onetls_nst_callback cb);
uint32_t onetls_set_ticket(onetls_ctx *ctx, void *data, uint32_t data_len);
uint32_t onetls_set_mtu(onetls_ctx *ctx, void *data, uint16_t mtu);
uint32_t onetls_connect(onetls_ctx *ctx);
uint32_t onetls_shutdown(onetls_ctx *ctx);
uint32_t onetls_update_key(onetls_ctx *ctx, void *data, uint8_t way);
uint32_t onetls_send(onetls_ctx *ctx, uint8_t *out, uint32_t out_len, uint32_t *send_len);
uint32_t onetls_recv(onetls_ctx *ctx, uint8_t *in, uint32_t in_len, uint32_t *recv_len);
uint32_t onetls_send_early_data(onetls_ctx *ctx, uint8_t *out, uint32_t out_len);
uint32_t onetls_flush(onetls_ctx *ctx);
uint32_t onetls_pending(onetls_ctx *ctx);关键 API 详解:
| API | 作用 | 说明 |
|---|---|---|
onetls_init | 初始化协议栈 | 返回 0 成功,非 0 失败;使用前先调用 |
onetls_new_ctx(mode) / onetls_del_ctx(ctx) | 创建/释放会话上下文 | mode 指定协议模式(TLS/DTLS 等);返回 onetls_ctx* |
onetls_set_socket(ctx, recv_fd, send_fd) | 绑定 Socket | 绑定底层收发句柄(可同 fd) |
onetls_connect(ctx) | 发起 TLS 1.3 握手 | 返回 0 成功;TLS 1.3 握手一次往返即可完成 |
onetls_shutdown(ctx) | 断开连接 | 发送 close_notify 并释放会话 |
onetls_send/recv(ctx, buf, len, &out_len) | 加密发送/解密接收应用数据 | send_len/recv_len 输出实际收发长度 |
onetls_send_early_data(ctx, out, out_len) | 发送 0-RTT 早期数据 | 需先恢复会话(持有效 Ticket) |
onetls_update_key(ctx, data, way) | 密钥更新 | TLS 1.3 支持后续密钥更新 |
onetls_set_mtu(ctx, data, mtu) | 设置 DTLS MTU | 用于 DTLS 分片 |
onetls_set_ticket / onetls_set_nst_callback | 会话恢复 | 设置/接收 Session Ticket 实现恢复 |
onetls_pending / onetls_flush | 缓冲检测/刷新 | 判断是否可读、清空缓冲 |
数值演算(TLS 1.3 握手往返):TLS 1.2 完整握手需 2 次往返(2-RTT);TLS 1.3 完整握手只需 1 次往返(1-RTT);配合 0-RTT(onetls_send_early_data)可在第 1 个往返的同时就携带应用数据(0-RTT),显著降低首次建连时延——这是 OneTLS 相比 TLS 1.2 的核心优势。
四、Kconfig 配置
OneTLS 的配置定义在 components/security/onetls/Kconfig。完整源码:
menu "OneTLS"
config SECURITY_USING_ONETLS
bool "Enable onetls"
select NET_USING_BSD
default n
help
OneTLS is a lightweight SSL/TLS library, supporting the newest TLS 1.3 industry standards
if SECURITY_USING_ONETLS
menu "Select Cipher"
config ONETLS_CIPHER_AES_128_GCM_SHA256
bool "AES_128_GCM_SHA256"
default y
config ONETLS_CIPHER_CHACHA20_POLY1305_SHA256
bool "CHACHA20_POLY1305_SHA256"
config ONETLS_CIPHER_AES_128_CCM_SHA256
bool "AES_128_CCM_SHA256"
config ONETLS_CIPHER_AES_128_CCM_8_SHA256
bool "AES_128_CCM_8_SHA256"
config ONETLS_CIPHER_TLS_SM4_GCM_SM3
bool "TLS_SM4_GCM_SM3"
config ONETLS_CIPHER_TLS_SM4_CCM_SM3
bool "TLS_SM4_CCM_SM3"
endmenu
menu "Select Elliptic Curve Groups"
config ONETLS_ECP_DP_CURVE25519_ENABLED
bool "curve25519"
default y
config ONETLS_ECP_DP_SECP256R1_ENABLED
bool "secp256r1"
config ONETLS_ECP_DP_SECP384R1_ENABLED
bool "secp384r1"
config ONETLS_ECP_DP_SECP521R1_ENABLED
bool "secp521r1"
config ONETLS_ECP_DP_CURVE_SM2_ENABLED
bool "curve_SM2"
endmenu
config ONETLS_DEBUG
bool "Enable onetls debug"
default n
config ONETLS_RUN_DTLS
bool "Enable onetls dtls"
default y
config ONETLS_MAX_RECORD_PACKET_LEN
int "The max record packet length"
range 512 16384
default 1024
config ONETLS_SUPPORT_RESUMPTION
bool "Support resumption"
default y
config ONETLS_SUPPORT_0RTT
bool "Support 0-RTT"
default y
config ONETLS_TESTS
bool "Enable (d)tls tests demo"
default n
endif
endmenu配置宏详解:
| 配置项 | 类型 | 默认值 | 说明 |
|---|---|---|---|
SECURITY_USING_ONETLS | bool | n | 启用 OneTLS(自动 select NET_USING_BSD),使能后配置其他项 |
ONETLS_CIPHER_AES_128_GCM_SHA256 | bool | y | 密码套件:AES-128-GCM-SHA256(TLS 1.3 默认) |
ONETLS_CIPHER_CHACHA20_POLY1305_SHA256 | bool | n | 密码套件:CHACHA20-POLY1305-SHA256 |
ONETLS_CIPHER_AES_128_CCM_SHA256 | bool | n | 密码套件:AES-128-CCM-SHA256 |
ONETLS_CIPHER_AES_128_CCM_8_SHA256 | bool | n | 密码套件:AES-128-CCM-8-SHA256 |
ONETLS_CIPHER_TLS_SM4_GCM_SM3 | bool | n | 国密套件:SM4-GCM-SM3 |
ONETLS_CIPHER_TLS_SM4_CCM_SM3 | bool | n | 国密套件:SM4-CCM-SM3 |
ONETLS_ECP_DP_CURVE25519_ENABLED | bool | y | 椭圆曲线组:curve25519 |
ONETLS_ECP_DP_SECP256R1_ENABLED | bool | n | 椭圆曲线组:secp256r1 |
ONETLS_ECP_DP_SECP384R1_ENABLED | bool | n | 椭圆曲线组:secp384r1 |
ONETLS_ECP_DP_SECP521R1_ENABLED | bool | n | 椭圆曲线组:secp521r1 |
ONETLS_ECP_DP_CURVE_SM2_ENABLED | bool | n | 国密椭圆曲线组:curve_SM2 |
ONETLS_DEBUG | bool | n | 启用调试输出 |
ONETLS_RUN_DTLS | bool | y | 启用 DTLS(OneTLS 支持 DTLS 1.3) |
ONETLS_MAX_RECORD_PACKET_LEN | int | 1024 | 最大记录包长度(range 512~16384) |
ONETLS_SUPPORT_RESUMPTION | bool | y | 支持会话恢复(Session Ticket) |
ONETLS_SUPPORT_0RTT | bool | y | 支持 0-RTT 早期数据 |
ONETLS_TESTS | bool | n | 编译 TLS/DTLS 测试 demo |
关键理解(配置注意):
- 启用 OneTLS 后,按需在 Select Cipher 选择密码套件(
AES_128_GCM_SHA256默认开,国密TLS_SM4_GCM_SM3/TLS_SM4_CCM_SM3需手动开); - 按需在 Select Elliptic Curve Groups 选椭圆曲线(
curve25519默认开,国密curve_SM2需手动开); ONETLS_MAX_RECORD_PACKET_LEN决定单条记录最大长度,越大越耗内存(range 512~16384);- 不需要 DTLS 时建议关闭
ONETLS_RUN_DTLS以省 ROM;ONETLS_SUPPORT_RESUMPTION/ONETLS_SUPPORT_0RTT决定是否支持会话恢复与 0-RTT。
五、使用建议
5.1 何时选择 OneTLS
- 资源严重受限的 MCU(Flash < 128KB);
- 需要 TLS 1.3 / DTLS 1.3 与 0-RTT 低时延;
- 需要国密 SM4/SM2 合规;
- 需要与 OneOS 深度集成和定制,只需基本客户端功能。
5.2 何时选择 MBED TLS
- 需要 TLS 1.0/1.1/1.2 旧版本兼容;
- 需要完整的 X.509 证书解析与管理;
- 需要丰富的密码学算法库(RSA/各类 hash 等);
- 需要与标准 mbedTLS 生态兼容、第三方库依赖。
关键理解:OneTLS 与 MBED TLS 都支持 DTLS(OneTLS 是 DTLS 1.3、MBED TLS 是 DTLS 1.0/1.2),选型不因"是否需要 DTLS"而分歧,核心看协议版本(TLS 1.3 vs 1.2)、国密需求、证书管理需求。
5.3 共存使用
OneTLS 和 MBED TLS 可以在同一个 OneOS 工程中共存,通过 Kconfig 分别控制启用。两者使用不同的 API 命名空间(onetls_* vs mbedtls_*),不会冲突。
📝 本节小结
核心要点回顾
- 协议版本:OneTLS 支持 TLS 1.3 与 DTLS 1.3(draft 38),不是 TLS 1.2;这是与 MBED TLS 最重要的差异。
- 轻量 + 低时延:TLS 1.3 握手 1-RTT,配合
onetls_send_early_data0-RTT、ONETLS_SUPPORT_RESUMPTION会话恢复,显著降低建连时延。 - 分层架构:crypto/(算法:AES-GCM/CCM、SM4、SHA、椭圆曲线)+ tls/(协议:握手、记录、密钥调度)。
- 核心 API:
onetls_init→onetls_new_ctx(mode)→onetls_set_socket(ctx, recv_fd, send_fd)→onetls_connect→onetls_send/onetls_recv(send_len/recv_len输出实际长度)→onetls_shutdown/onetls_del_ctx。 - 会话/密钥管理:
onetls_set_ticket/onetls_set_nst_callback(恢复)、onetls_update_key(更新密钥)、onetls_set_mtu(DTLS 分片)。 - Kconfig:
SECURITY_USING_ONETLS(select NET_USING_BSD)→ Select Cipher(ONETLS_CIPHER_*,含国密TLS_SM4_GCM_SM3)+ Select Elliptic Curve Groups(ONETLS_ECP_DP_*,含国密CURVE_SM2)+ONETLS_RUN_DTLS/ONETLS_MAX_RECORD_PACKET_LEN/ONETLS_SUPPORT_RESUMPTION/ONETLS_SUPPORT_0RTT/ONETLS_TESTS。 - 国密合规:支持 SM4(GCM/CCM)与 SM2 曲线,满足国密应用需求。
关键易错点速查
| 易错点 | 正确做法 |
|---|---|
| 以为 OneTLS 只支持 TLS 1.2 | 真实支持 TLS 1.3 / DTLS 1.3(draft 38)→ 按 TLS 1.3 流程使用 |
| 以为 OneTLS 不支持 DTLS | 支持 DTLS(ONETLS_RUN_DTLS 默认 y)→ 需要 DTLS 时直接启用即可 |
用 ONETLS_USING_TLS/DTLS/CRYPTO/AES/... 配置 | 不存在 → 用真实的 SECURITY_USING_ONETLS + ONETLS_CIPHER_*/ONETLS_ECP_DP_* |
把 send_len/recv_len 当返回值 | onetls_send/recv 返回 0 表示成功,实际收发长度在 *send_len/*recv_len → 用指针取 |
建连后直接 onetls_send 不判返回值 | 握手失败时 send 无效 → 判 onetls_connect 返回 0 再收发 |
| 用 TLS 1.3 却想用旧 RSA 证书交换 | TLS 1.3 移除 RSA 密钥交换,只保留证书签名 → 用 ECDHE/PSK |
| 开了 0-RTT 不管理 Ticket | 0-RTT 依赖会话恢复的 Ticket → 用 onetls_set_ticket/onetls_set_nst_callback 维护 |
ONETLS_MAX_RECORD_PACKET_LEN 设很大 | 每连接占用大内存 → 按实际报文设(range 512~16384,默认 1024) |
| 不需要国密却开 SM4/SM2 | 白白增加 ROM → 只需非国密时不开 TLS_SM4_*/CURVE_SM2 |
下一步
- 7.3.3 libSSH 组件:OneTLS 已掌握 TLS 1.3 安全通信,下一节学习 libSSH 组件,掌握 OneOS 的 SSH 服务端能力,实现设备远程登录与 Shell 交互。