c1ab902ef1
把监听生命周期从 net_socket.c 整体抽出为真机专属模块 net_listener.c: 7 个函数 + 7 个状态数组 + 8 个常量 ≈470 行。 net_socket.c 4126 → 3656 行(-471)。 模块边界(详见 net_listener.h 头注释): - 搬入:relisten_locked / try / clear / done / retry_tick / pump / drain_chip_rx - 留在 net_socket.c:net_listen_locked(应用 API 路径)/ net_accept_locked (产出连接)/ net_lost_connect_probe(补 accept)/ net_listener_armed (双端公开 API)/ net_resync_listen / net_reconcile_tick / net_sock_t 字段 接口从「8 处散点直调 + 2 处直接写状态数组」收敛为 4 个窄接口: net_listener_settle(fd, level) / _try(fd) / _clear(fd) / _retry_tick() 新模块**不访问 s_net_socks**(改用 net_get_sock + ch395_sock)。 搬移中必要的两处可见性提升(非纯机械搬移,已注释留痕): - net_set_errno 由 static 提升为模块间可见(NET_ERR_RETURN_1 宏随迁头文件) - 新增 net_pending_active(fd),替代直接读 s_net_pending[i].active (L3 保险语义原样保留) 真机专属:net_listener.c 依赖 ch395f_* SPI 驱动,sim(Winsock)无对应 → 只注册 Keil 端,并在 check_registration.py 的 SIM_EXEMPT **显式点名** (不整目录一刀切,遵脚本既定原则)。 验证(纯搬移的可证判据): - 尺寸:**RW-data 980 与 ZI-data 143060 完全不变**(数据总量不变); Code 197236→197228(-8)、RO-data 17012→17000(-12)——接口改造的 极小开销,相对 471 行搬移可忽略 - 门禁全绿(cppcheck / C 规范 / 双端注册 / 主机侧单测 12 套 / mem-numbers) - @test PASS + 回读 No difference found - 全量回归::21 0ms×50 与 100ms×50 各 50/50;:8888 20/20;:7003 10/10; ftp_regression 11/11;Trap23 abort/graceful 各 5/5 - 设备侧:orphan listener **0**(保持 P2a 基线)、pump 留痕正常
Drivers/BSP/NET/ — 网络抽象层(BSD Socket API)
在 CH395F 硬件驱动之上提供 BSD Socket 风格 API,使上层(FTP 服务、时间同步、UI 推流) 以标准 socket 语义编程,无需关心芯片细节。核心是阻塞模型 + 事件驱动 + 周期对账自愈。
文件一览
| 文件 | 作用 |
|---|---|
net_socket.c/h |
BSD Socket API 实现:net_socket / net_connect / net_send / net_recv / net_close / net_listen / net_accept,含 L3 挂起(pending)与错误码 |
net_select.c/h |
select/poll 多路复用(基于芯片中断事件 + 周期轮询) |
net_types.h |
网络层公共类型定义 |
net_config.h |
网络层编译期配置(缓冲区大小、超时、对账周期等) |
lftpd/ |
轻量 FTP 服务器(第三方移植,见其子目录) |
核心机制
阻塞模型(L3 pending)
- 一期(RECV)已落地:
net_recv等支持带超时的阻塞(pending挂起 + tick 唤醒) - 二期(ACCEPT + SEND)待做 →
docs/待处理内容.mdN-4
周期对账自愈(Trap 22 修复)
net_reconcile_tick()(200ms)回读芯片状态修正三类失同步: 本层 ESTABLISHED 而芯片已断 → 断开;本层 LISTENING 而芯片已握手 → 补 accept; 本层 LISTENING 而芯片监听消失 → 重建- 去抖(连续 2 次)+ 冷却(1s)——单次状态读的重建动作必须去抖,
否则"刚 listen 未生效"瞬态会反复重建直至
relisten give up(三监听口全死)
异常复监听隔离(Trap 23 修复)
- 异常释放(TIMEOUT)的 socket 复监听前隔离:排空 RX 残渣 + 主动 close + 等 CLOSED
- 400ms 起、800ms 上限强制放行(上限须 < 重试放弃时限 2000ms)
- 仅异常路径生效,正常 FIN 路径零改动
错误码(E-03 修复)
- 按任务隔离:
s_net_errno_slots[8](每槽{任务句柄, err}),替代原全局s_net_errno net_get_errno()只读本任务槽位,对外语义不变(成功不清零)
依赖关系
上层(FTP / timeSync / UI 推流)
↓ BSD Socket API
net_socket.c ←→ net_select.c
↓ ch395f_* 接口
Drivers/BSP/CH395F/
⚠️ 改本模块前必读
- 就绪屏障位(
SYS_EVT_NET_READY等)等待必须osFlagsNoClear,不能用默认消费型 - 每次 CH395F SPI 事务须
ch395f_spi_begin()/end()包裹 - 改任何自愈/重建逻辑必须去抖,否则会引发重建风暴
- 相关陷阱:
docs/问题记录/CH395F_Trap_Records.mdTrap 21/22/23
相关文档
- 上层用法:
docs/网络/BSD_Socket_API_使用指南.md - 内部调用关系:
docs/网络/BSD_Socket_API_函数调用关系.md - 架构设计:
docs/网络/Net层阻塞模型架构设计.md(阻塞等待 / pending 请求模型) - 二期设计基线:
docs/待处理内容.md§5.1 - 测试:
docs/测试说明/CH395F_Test_Guide.md、docs/测试说明/FTP_Test_Guide.md