Files
EmbeddedSoftwareLearn1/06-NetworkIot
2025-06-17 14:51:42 +08:00
..
2025-06-17 14:51:42 +08:00

🟣 第六层:网络通信与物联网协议(Network & IoT)

本模块聚焦于嵌入式系统中的通信机制和物联网协议栈,涵盖串口通信、无线模块、MQTT 等协议到云平台对接,适用于 IoT 产品开发全流程。


串口通信与Socket通信

串口通信

  • 串口基础:波特率、校验位、停止位、数据位
  • 应用:模块通信、调试信息输出
  • 中断方式与 DMA 模式接收
// 基本 UART 初始化
USART1->BRR = 0x1A1; // 设置波特率
USART1->CR1 |= USART_CR1_TE | USART_CR1_RE | USART_CR1_UE; // 使能收发

Socket网络通信

  • Socket 基础:TCP/UDP 区别、连接建立过程
  • 在 ESP32 等模块中使用 LWIP 实现 TCP 客户端/服务器
// TCP 客户端基础逻辑 (伪代码)
socket();
connect();
send();
recv();

无线通信协议

Wi-Fi

  • ESP32 支持 STA / AP 模式,常用于联网或热点传输
  • SmartConfig、ESP-NOW、HTTP Server 应用

BLE(蓝牙低功耗)

  • GATT 协议模型:服务、特征值、通知机制
  • 使用 nRF52、ESP32 等平台进行广播、连接和数据交互

LoRa / ZigBee

  • 长距离通信:适用于室外传感器
  • 使用 Semtech SX1278 / ZigBee 模块通信帧格式解析

物联网协议栈

MQTT

  • 轻量级发布-订阅协议,常用于设备与云平台交互
  • QoS 等级、主题结构、客户端连接
  • 常见平台支持:EMQX、OneNet、阿里云 IoT

HTTP / HTTPS

HTTP 请求方法(Methods)

  • GET:请求指定资源。常用于获取数据。
  • POST:提交数据到服务器,如表单、上传。
  • PUT:上传数据,通常是更新资源。
  • DELETE:删除指定资源。
  • HEAD:与 GET 类似,但不返回响应体。
  • OPTIONS:返回服务器支持的请求方法。
  • TRACE:诊断请求响应路径,回显请求报文。
  • CONNECT:用于建立隧道(如 HTTPS 代理)。

HTTP 状态码

分类 范围 含义
1xx 100~199 接收中,继续处理
2xx 200~299 请求成功
3xx 300~399 重定向或更多操作
4xx 400~499 客户端错误
5xx 500~599 服务器错误

部分状态码示例:

  • 200 OK
  • 201 Created
  • 204 No Content
  • 301 Moved Permanently
  • 302 Found
  • 304 Not Modified
  • 400 Bad Request
  • 401 Unauthorized
  • 403 Forbidden
  • 404 Not Found
  • 500 Internal Server Error
  • 502 Bad Gateway

HTTP 长连接与短连接

  • HTTP/1.0 默认使用短连接(每次请求后断开)
  • HTTP/1.1 默认使用长连接(Connection: keep-alive)

HTTP 请求报文格式

GET /hello.htm HTTP/1.1
Host: www.example.com
User-Agent: Mozilla/5.0
Accept: */*
Connection: Keep-Alive
... 其他头部字段

HTTP 响应报文格式

HTTP/1.1 200 OK
Content-Type: text/html
Content-Length: 158
Server: Apache
Date: Sun, 14 Jun 2025 10:00:00 GMT

<html>...</html>

HTTPS 通信过程

HTTPS = HTTP + TLS/SSL 加密

通信过程:

  1. 客户端发起 HTTPS 请求(握手开始)
  2. 服务器返回证书(含公钥)
  3. 客户端验证证书合法性
  4. 客户端生成随机对称密钥(用公钥加密传给服务器)
  5. 双方使用对称密钥开始加密通信

对称加密(加解密使用同一密钥)

  • DES(56 位)
  • AES(128/192/256 位)

非对称加密(加密/解密使用公钥/私钥)

  • RSA:支持加密、签名
  • DSA:只支持签名(效率高,但不用于加解密)

哈希算法(不可逆)

  • MD5(128 位)
  • SHA-1(160 位)
  • SHA-256(256 位)

🔹 安全通信实践

  1. TLS 握手优化
  • 预共享密钥(PSK)模式:
    减少证书验证开销,适合资源受限设备。
// mbed TLS配置PSK
mbedtls_ssl_config_set_psk(&ssl_conf, 
                            psk,          // 预共享密钥
                            psk_length, 
                            identity,     // 身份标识
                            strlen(identity));
  1. 证书管理方案
  • 证书存储:
    • 根证书存储在安全 Flash 区域。
    • 设备证书通过安全通道动态更新。
  • 证书验证:
// 验证服务器证书链
int verify_cert(void *data, mbedtls_x509_crt *crt, int depth, uint32_t *flags) {
    // 检查证书有效期
    if (mbedtls_x509_crt_check_validity(crt, time(NULL)) != 0) {
        return MBEDTLS_ERR_X509_CERT_VERIFY_FAILED;
    }
    
    // 检查证书颁发者
    if (!mbedtls_x509_crt_verify(crt, trusted_certs, NULL, NULL, flags, NULL, NULL)) {
        return MBEDTLS_ERR_X509_CERT_VERIFY_FAILED;
    }
    
    return 0;
}

🔹 安全测试

  1. 固件逆向分析
  • 工具链:
    • Ghidra:反编译二进制文件,生成 C 语言伪代码。
    • IDA Pro:专业逆向工程工具,支持 ARM 架构。
  • 防御措施:
    • 固件加密:使用 AES-256 加密整个固件。
    • 反调试机制:检测调试接口是否被连接。
// 检测SWD/JTAG调试接口
bool IsDebuggerAttached(void) {
    // 读取DBGMCU_IDCODE寄存器
    uint32_t idcode = DBGMCU->IDCODE;
    // 检查调试使能位
    return ((DBGMCU->CR & (DBGMCU_CR_DBG_SLEEP | DBGMCU_CR_DBG_STOP | DBGMCU_CR_DBG_STANDBY)) != 0);
}
  1. 侧信道攻击防护
  • 电源分析攻击:
    通过测量设备功耗分析加密密钥。
  • 防护措施:
    常量时间实现:避免条件分支依赖密钥值。
// 常量时间比较(防止时序攻击)
bool ConstantTimeCompare(const uint8_t *a, const uint8_t *b, size_t len) {
    uint8_t result = 0;
    for (size_t i = 0; i < len; i++) {
        result |= a[i] ^ b[i];
    }
    return (result == 0);
}

CoAP / LwM2M

  • 适合低功耗终端的简化协议,UDP 传输,可压缩
  • 用于 NB-IoT、LwIP 等网络栈中

TCP/IP 协议栈基础与嵌入式实现

TCP/IP 协议栈分层结构(四层模型)

层级 协议/组件 功能说明
应用层 HTTP, MQTT, CoAP, DNS 面向用户的协议
传输层 TCP, UDP 数据传输可靠性与端口管理
网络层 IP, ICMP, ARP 地址与路由
链路层 Ethernet, Wi-Fi, BLE 硬件通信和数据帧传输

TCP 与 UDP 区别

特性 TCP UDP
是否连接 是(面向连接) 否(无连接)
是否可靠 是(有重传、确认) 否(可能丢包)
适用场景 Web、文件传输、SSH 视频流、语音、广播
开销 较大(握手、窗口等) 较小(直接发送)

嵌入式 TCP/IP 协议栈组件

  • LwIP(Lightweight IP)
    • 开源轻量级 TCP/IP 协议栈
    • 支持 TCP/UDP/IP/DNS/DHCP 等
    • 常用于 STM32、ESP32、RT-Thread 中
  • uIP(micro IP)
    • 更轻量,适合资源极小的 MCU
  • FreeRTOS+TCP
    • 与 FreeRTOS 配套的 TCP/IP 协议栈
  • Nut/Net、CycloneTCP:其他常用协议栈

嵌入式 TCP/IP 通信流程(以 LwIP 为例)

  1. 初始化网络接口:配置 IP、MAC、网关
  2. 创建 socket 套接字:TCP 或 UDP
  3. 建立连接 / 绑定端口
  4. 接收/发送数据:recv(), send()
  5. 关闭连接:close()

常用 API 示例(LwIP BSD socket)

// TCP 客户端示例
int sock = socket(AF_INET, SOCK_STREAM, 0);
struct sockaddr_in server;
server.sin_family = AF_INET;
server.sin_port = htons(12345);
server.sin_addr.s_addr = inet_addr("192.168.1.10");

connect(sock, (struct sockaddr*)&server, sizeof(server));
send(sock, "Hello", strlen("Hello"), 0);
recv(sock, buffer, sizeof(buffer), 0);
close(sock);

DHCP / DNS / ICMP 说明

  • DHCP:动态分配 IP(LwIP 可配置)
  • DNS:域名解析,调用 gethostbyname() 等
  • ICMP:如 ping 实现通信测试

推荐阅读资料


云平台接入 & OTA 实现

云平台对接

  • 主流平台:阿里云 IoT、腾讯连连、OneNet、ThingsBoard
  • 认证方式:三元组 / MQTT 密钥 / TLS 证书

OTA 升级机制

支持远程更新嵌入式系统的固件版本

  1. 双分区升级架构
Flash布局:
+-------------------+ 0x08000000
| Bootloader        |
+-------------------+ 0x08010000
| Application Slot A|
+-------------------+ 0x08040000
| Application Slot B|
+-------------------+ 0x08070000
| Configuration Area|
+-------------------+
  1. 升级状态机实现
typedef enum {
    OTA_IDLE,           // 空闲状态
    OTA_CHECKING,       // 检查更新
    OTA_DOWNLOADING,    // 下载中
    OTA_VERIFYING,      // 校验中
    OTA_READY,          // 准备重启
    OTA_UPGRADING,      // 升级中
    OTA_FAILED          // 升级失败
} OTA_State_t;

// OTA状态机处理函数
void OTA_Process(void) {
    switch (ota_state) {
        case OTA_IDLE:
            if (check_update_flag) {
                ota_state = OTA_CHECKING;
                vCheckForUpdate();
            }
            break;
        
        case OTA_DOWNLOADING:
            if (download_complete) {
                ota_state = OTA_VERIFYING;
                vVerifyFirmware();
            } else if (download_error) {
                ota_state = OTA_FAILED;
                vHandleError(DOWNLOAD_ERROR);
            }
            break;
        
        // 其他状态处理...
    }
}
  1. 失败回滚机制
// 启动时验证应用完整性
bool ValidateApplication(uint32_t start_address) {
    // 检查向量表签名
    uint32_t *vector_table = (uint32_t *)start_address;
    if (vector_table[0] == 0xFFFFFFFF) {  // 检查栈顶指针是否有效
        return false;
    }
    
    // 计算应用哈希并验证
    uint8_t calculated_hash[32];
    SHA256((uint8_t *)start_address, APPLICATION_SIZE, calculated_hash);
    
    // 从配置区获取预期哈希
    uint8_t *expected_hash = GetExpectedHash();
    return (memcmp(calculated_hash, expected_hash, 32) == 0);
}

// 主程序
int main(void) {
    // 初始化硬件
    HAL_Init();
    SystemClock_Config();
    
    // 检查主应用是否有效
    if (ValidateApplication(APPLICATION_SLOT_A_ADDRESS)) {
        // 跳转到主应用
        JumpToApplication(APPLICATION_SLOT_A_ADDRESS);
    } else if (ValidateApplication(APPLICATION_SLOT_B_ADDRESS)) {
        // 主应用无效,尝试从备份应用启动
        JumpToApplication(APPLICATION_SLOT_B_ADDRESS);
    } else {
        // 两个应用都无效,进入恢复模式
        EnterRecoveryMode();
    }
}

✅ OTA 流程核心步骤

  1. 检查版本更新(HTTP/MQTT 下载 manifest)
  2. 下载固件(二进制)
  3. 存储到备份区(Backup Slot)
  4. 校验 CRC/Hash / 签名
  5. 设置 Bootloader 标志位并重启
  6. Bootloader 引导进入新固件
  7. 若失败则回滚(Fail-safe 机制)

✅ 常用升级协议

  • HTTP / HTTPS
  • MQTT + Base64 二进制块传输
  • CoAP(轻量级)

✅ 推荐学习顺序

  1. 学习 UART 通信与基本网络 socket 原理
  2. 掌握 Wi-Fi / BLE 开发流程(推荐 ESP32/nRF52)
  3. 理解 MQTT 协议与平台接入逻辑
  4. 实践 OTA 升级流程,构建远程维护能力

📌 常见问题 FAQ

问题 解答
MQTT 断线如何重连? 设置心跳机制与 reconnect 回调逻辑
OTA 更新失败怎么办? 回退机制 + 双镜像分区设计
CoAP 和 MQTT 有何区别? CoAP 基于 UDP,适合低功耗设备;MQTT 基于 TCP,稳定性好