# Wi-Fi 驱动与设备选择

## 概述

CanMV 的 `network.WLAN` 建立在 RT-Smart WLAN 和 NetMgmt 之上。当前 SDK 包含
Realtek RTL8189FTV/RTL8733BS、CYW43xx/AP6212、RW007、AIC8800 系列以及
ESP-Hosted 驱动。Python API 不直接调用厂商驱动，而是按 USB、SDIO 或 SPI
传输类型选择已注册的物理射频。

是否能直接使用某个方案取决于目标板固件的 defconfig、接口接线、模组型号和
协处理器固件。标准固件未启用的驱动需要自定义构建。

```{warning}
当前发布的 K230D 标准固件不支持网络功能。本页的 K230D 相关使用场景属于自定义
板级和驱动适配范围，不能直接套用标准固件。
```

## 支持方案

| 方案 | 传输 | CanMV 能力 | 注册型号 |
| :-- | :-- | :-- | :-- |
| RTL8189FTV | SDIO | 2.4 GHz Wi-Fi 4，STA、SoftAP | `rtl8189ftv` |
| RTL8733BS | SDIO | 支持 5 GHz 的 Wi-Fi 4，STA、SoftAP | `rtl8733bs` |
| CYW43438/AP6212 | SDIO | 2.4 GHz Wi-Fi 4，STA、SoftAP | `cyw43438` |
| RW007 | SPI Mode 0 | STA、SoftAP | `rw007` |
| AIC8800/AIC8801、D80/D40/D80X2/DC/DW | USB；部分型号支持 SDIO | STA、SoftAP；USB 组合设备可选 BLE HCI | AIC 具体型号 |
| ESP-Hosted-FG | SPI Full-Duplex、SDIO | ESP 固件管理连接和 WPA | `esp-hosted-fg` |
| ESP-Hosted-NG | SPI Full-Duplex、SDIO | 主机认证路径，可提供 WLAN offload 控制设备 | `esp-hosted-ng` |
| ESP-Hosted-MCU | SPI Full-Duplex、Dual/Quad SPI Half-Duplex | RPC Wi-Fi，可选 BLE HCI | `esp-hosted-mcu` |

ESP-Hosted-FG、NG 和 MCU 的 wire protocol 不兼容。主机驱动必须与 ESP 端烧录
的 firmware personality 一致。ESP-Hosted-MCU 当前没有 RT-Smart SDIO backend。

CYW43xx 端口虽然来自支持 Bluetooth 的上游驱动，但当前 AP6212 集成将
`CYW43_ENABLE_BLUETOOTH` 设为 `0`，不能作为 CanMV NimBLE controller。BLE 的
配置和使用见 [NimBLE 低功耗蓝牙](bluetooth.md)。

## 默认板级配置

当前源码中：

- `k230_canmv_defconfig` 已启用 CYW43xx/AP6212 和 Realtek SDIO；
- 多数带板载 SDIO Wi-Fi 的 CanMV defconfig 已启用 Realtek，默认选择
  RTL8189FTV；使用 RTL8733BS 时需要更改 Realtek module 选项；
- `k230_canmv_rtt_evb_defconfig` 已启用 RW007；
- `k230_canmv_01studio_defconfig` 已启用 AIC8800 USB 和 SDIO；
- `k230_canmv_01studio_emmc_defconfig` 已启用 AIC8800 USB；
- `k230_canmv_lckfb_defconfig` 已启用 AIC8800 USB；
- ESP-Hosted 需要按实际接线在自定义固件中启用。

板级默认值只说明构建配置，不能替代硬件核对。同一 SDIO 插槽可以同时编译多个
厂商驱动，运行时按 SDIO manufacturer/product ID 匹配；但 Realtek 驱动内部一次
只能选择 RTL8189FTV 或 RTL8733BS 中的一种。

AIC 固件由 manifest 中的独立子仓库提供。执行 `repo sync` 后，应存在：

```text
src/rtsmart/rtsmart/kernel/bsp/maix3/drivers/extdrv/aic8800/firmware/
```

构建系统会把所需文件安装到镜像的 `/bin/firmware`。这些二进制具有独立的
vendor 许可条款。

## 自定义固件配置

先按 [自定义固件](how_to_build.md) 选择板级配置，再运行 `make rtsmart-menuconfig`
或对应的容器命令。

### SDIO 公共板级配置

Realtek、CYW43xx、AIC8800 SDIO 和 ESP-Hosted SDIO 共用以下板级设置：

```text
BSP_WIFI_SDIO_HOST_0=y              # 或 BSP_WIFI_SDIO_HOST_1
BSP_WIFI_SDIO_REG_ON_PIN=<gpio>     # -1 表示使用板级固定接线
BSP_WIFI_SDIO_RESET_ACTIVE_LOW=y
BSP_WIFI_SDIO_RESET_PULSE_MS=200
BSP_WIFI_SDIO_POWER_UP_DELAY_MS=50
```

选择的 host 必须已启用对应的 `RT_USING_SDIO0` 或 `RT_USING_SDIO1`。REG_ON、复位
有效电平和上电延时必须按原理图及模组手册设置。

### Realtek RTL8189FTV/RTL8733BS

启用 `RT_USING_REALTEK`，并且在 Realtek module 选项中二选一：

```text
REALTEK_SDIO_RTL8189FTV=y
# REALTEK_SDIO_RTL8733BS=y
```

RTL8189FTV 的 SDIO ID 为 `024c:f179`，RTL8733BS 为 `024c:b733`。驱动按 ID
绑定设备；选错模块时即使 SDIO 总线发现了卡也不会注册 WLAN。调试命令和驱动
日志可分别通过 `REALTEK_INTERACTIVE_CMD` 和 `REALTEK_ENABLE_DEBUG` 启用。

### CYW43xx/AP6212

启用：

```text
RT_USING_CYW43XX=y
```

当前端口按 `02d0:a9a6` 匹配 CYW43438/AP6212，并在驱动中内置 Wi-Fi firmware
和 NVRAM。`CYW43XX_THREAD_PRIORITY` 与 `CYW43XX_THREAD_STACK_SIZE` 可用于调整
工作线程。此端口当前只启用 Wi-Fi，不启用 CYW43xx Bluetooth。

### RW007

启用 `RT_USING_RW007`，并按板级接线配置：

```text
RW007_SPI_BUS_NAME="spi0"
RW007_SPI_MAX_HZ=25000000
RW007_RST_PIN=20
RW007_CS_PIN=63
RW007_INT_BUSY_PIN=62
```

驱动使用 SPI Mode 0、8-bit、单数据线，并把从设备挂载为 `wspi`。上面的 GPIO
只是 Kconfig 默认值，移植到其他板卡时必须核对 Reset、CS 和 INT/BUSY 引脚。

### AIC8800

启用：

```text
RT_USING_AIC8800_WIFI=y
AIC8800_WIFI_TRANSPORT_USB=y        # USB 网卡
AIC8800_WIFI_TRANSPORT_SDIO=y       # SDIO 模组，可与 USB 同时启用
```

2.4 GHz-only 模组应关闭 `AIC8800_WIFI_5GHZ`。AIC8800D40L 与 D80 可能使用相同
USB ID，D40L 必须启用 `AIC8800_WIFI_USB_LIMIT_40MHZ`。USB BLE 需要
`AIC8800_WIFI_BLE`，同时 CanMV 顶层还需启用 `ENABLE_BLUETOOTH`。

### ESP-Hosted-FG/NG

启用 `RT_USING_ESP_HOSTED_WIFI`，选择 FG 或 NG，再选择 SPI Full-Duplex 或
SDIO。SPI mode、频率、checksum、Handshake/Data Ready 电平及引脚必须与 ESP
固件一致。SDIO 还需填写从机实际发布的 manufacturer/product ID。当前 FG/NG
端口不向 CanMV 注册 BLE HCI controller。

### ESP-Hosted-MCU

启用 `RT_USING_ESP_HOSTED_MCU`，选择 SPI Full-Duplex 或 SPI Half-Duplex。
Half-Duplex 使用 2/4 条双向数据线，不支持 1-line 模式。启用
`ESP_HOSTED_BLE` 后，再启用 CanMV `ENABLE_BLUETOOTH`，MicroPython NimBLE 才能
使用动态注册的 `/dev/hciN` controller。

所有 ESP-Hosted 方案都应优先连接可控 Reset。Reset 未连接时，只重启 K230 或
ESP 一端可能使 transport session 不同步。

## Python 设备选择

构造 `network.WLAN` 时第二个参数选择传输：

```python
import network

auto_sta = network.WLAN(network.STA_IF, network.WLAN_AUTO)
usb_sta = network.WLAN(network.STA_IF, network.WLAN_USB)
sdio_sta = network.WLAN(network.STA_IF, network.WLAN_SDIO)
spi_ap = network.WLAN(network.AP_IF, network.WLAN_SPI)
```

对应常量：

| 常量 | 传输和适用驱动 |
| :-- | :-- |
| `network.WLAN_AUTO` | 保持当前可用射频，否则按 SDIO、SPI、USB 选择 |
| `network.WLAN_USB` | AIC8800 USB |
| `network.WLAN_SDIO` | RTL8189FTV、RTL8733BS、CYW43438/AP6212、AIC8800、ESP-Hosted-FG/NG |
| `network.WLAN_SPI` | RW007、ESP-Hosted-FG/NG/MCU |

该参数选择传输类型，不选择 vendor model。通常使用 `WLAN_AUTO`；只有多块 Wi-Fi
同时存在且应用确实依赖某条总线时才固定类型。当前 Python API 不能区分同一传输
上同时存在的两个不同型号。

连接并查询动态 netdev：

```python
import network
import time

sta = network.WLAN(network.STA_IF, network.WLAN_AUTO)
if not sta.active(True):
    raise RuntimeError("Wi-Fi device unavailable")

sta.connect("TEST", "12345678")
deadline = time.time() + 20
while not sta.isconnected() and time.time() < deadline:
    time.sleep_ms(200)

print(network.get_dev_list())
print(sta.netdev_name())
print(sta.ifconfig())
```

网卡名通常是 `wlanN`/`wlanNap`，但 `N` 由探测顺序决定。不要在脚本中写死
`wlan0`。

## 安全模式限制

- Realtek、CYW43xx 和 RW007 的安全模式取决于厂商驱动及模组 firmware；切换
  模组时应重新验证扫描、STA 加密连接和 SoftAP。
- AIC8800 STA 的普通 WPA/WPA2 Personal 可由内置认证路径完成；受限 WPA3-SAE
  使用 group 19，不支持 SAE H2E 和 Enterprise/802.1X。
- AIC8800 SoftAP 支持开放网络和 WPA2-PSK/CCMP，不支持 WPA3、Enterprise、WPS、
  DFS/CAC 或动态 VLAN。
- ESP-Hosted-FG 的实际安全能力由 ESP firmware 提供。
- ESP-Hosted-NG 可使用内置普通 WPA/WPA2 STA 和开放/WPA2 SoftAP 路径；其他
  安全模式需要完整用户态 supplicant。
- ESP-Hosted-MCU 的实际能力取决于 ESP 芯片、ESP-IDF 和从机编译配置。

## 验证与排错

1. `network.get_dev_list()` 没有 WLAN：检查固件是否启用对应驱动、接口供电、
   SDIO host/REG_ON、RW007 SPI 引脚、AIC firmware 文件或 ESP transport ready 日志。
1. Realtek 未注册：核对 SDIO ID，并确认选择的是 RTL8189FTV 还是 RTL8733BS。
1. RW007 未注册：核对 SPI bus、Mode 0、最大频率、CS、Reset 和 INT/BUSY。
1. `active(True)` 返回 `False`：指定传输当前没有可用设备，先改为
   `network.WLAN_AUTO`。
1. AIC D40 连接速率异常：检查 `AIC8800_WIFI_USB_LIMIT_40MHZ`。
1. ESP 无法初始化：优先核对 firmware personality、SPI mode、checksum、引脚和
   HS/DR 有效电平。
1. 已关联但不能访问网络：先检查 `ifconfig()` 是否取得非零 IP 和网关，再测试
   局域网网关，最后排查 DNS 和公网。

Python 接口和完整示例分别见 [network 模块 API](../api/extmod/k230_canmv_network_api_manual.md)
和 [无线网例程](../example/network/wlan.md)。
