BL808 WiFi 屬于 SOC 單芯片型無線 MCU,片上集成 WiFi 功能,移植 RT-Thread 過程中,需要使用 RT-Thread wlan 框架。
RT-Thread wlan 框架是用于管理 Wi-Fi 驅動設備的框架,對下連接具體的 Wi-Fi 驅動,控制 Wi-Fi 的連接斷開、掃描等操作,對上為應用提供統一的 Wi-Fi 控制接口。
wlan 框架主要有 3 部分組成:
dev 驅動接口層:為 wlan 框架提供統一的接口調用。
manage 管理層:為用戶提供 Wi-Fi 掃描,鏈接,斷線重連等功能。
protocol 協議:負責處理 Wi-Fi 產生的數據流,如 lwip。
使用了 wlan 驅動框架之后,Wi-Fi 驅動只需要關注 Wi-Fi 的連接、斷開、掃描等動作,并通過 event 將相關動作告知 wlan 框架,由 wlan 框架根據收到的 event 管理 lwip。
1、使能 wlan 驅動
在 Linux 下 執行如下命令,并開啟 wlan 驅動。
$ scons --menuconfig
RT-Thread Components --->
Device Drivers --->
[*] Using Wi-Fi framework --->
開啟 wlan 驅動后,默認會選中 lwip。
如 WiFi SOC 類芯片,原廠 SDK 中已經有線程管理 WiFi 數據收發,可關閉 lwip 中的 Rx thread 和 Tx thread,以節省系統資源。
Network --->
- - LwIP: light weight TCP/IP stack --->
[ ] Not use Rx thread
[*] Not use Tx thread
2、wlan 驅動框架適配
初始化
通過 rt_wlan_dev_register() 注冊 STATION 和 AP 設備,并將 wlan 設備接口函數注冊進對應設備。
static const struct rt_wlan_dev_ops ops =
{
.wlan_init = drv_wlan_init,
.wlan_mode = drv_wlan_mode,
.wlan_scan = drv_wlan_scan,
.wlan_join = drv_wlan_join,
.wlan_softap = drv_wlan_softap,
.wlan_disconnect = drv_wlan_disconnect,
.wlan_ap_stop = drv_wlan_ap_stop,
.wlan_ap_deauth = drv_wlan_ap_deauth,
.wlan_scan_stop = drv_wlan_scan_stop,
.wlan_get_rssi = drv_wlan_get_rssi,
.wlan_set_powersave = drv_wlan_set_powersave,
.wlan_get_powersave = drv_wlan_get_powersave,
.wlan_cfg_promisc = drv_wlan_cfg_promisc,
.wlan_cfg_filter = drv_wlan_cfg_filter,
.wlan_cfg_mgnt_filter = drv_wlan_cfg_mgnt_filter,
.wlan_set_channel = drv_wlan_set_channel,
.wlan_get_channel = drv_wlan_get_channel,
.wlan_set_country = drv_wlan_set_country,
.wlan_get_country = drv_wlan_get_country,
.wlan_set_mac = drv_wlan_set_mac,
.wlan_get_mac = drv_wlan_get_mac,
.wlan_recv = drv_wlan_recv,
.wlan_send = drv_wlan_send,
};
int rt_hw_wifi_init(void)
{
rt_err_t ret = RT_EOK;
static struct rt_wlan_device wlan0;
static struct rt_wlan_device wlan1;
memset(&wifi_sta, 0, sizeof(wifi_sta));
ret = rt_wlan_dev_register(&wlan0, RT_WLAN_DEVICE_STA_NAME, &ops, 0, &wifi_sta);
wifi_sta.wlan = &wlan0;
memset(&wifi_ap, 0, sizeof(wifi_ap));
ret |= rt_wlan_dev_register(&wlan1, RT_WLAN_DEVICE_AP_NAME, &ops, 0, &wifi_ap);
wifi_ap.wlan = &wlan1;
return ret;
}
INIT_DEVICE_EXPORT(rt_hw_wifi_init);
啟動設備
在 main.c 中 加入 rt_wlan_set_mode 分別設置 STATION 和 AP 模式。
int main(void)
{
rt_kprintf("Hello, RISC-V!n");
/* set wifi work mode */
rt_wlan_set_mode(RT_WLAN_DEVICE_STA_NAME, RT_WLAN_STATION);
rt_wlan_set_mode(RT_WLAN_DEVICE_AP_NAME, RT_WLAN_AP);
return 0;
}
接口實現
在 STATION 模式下,至少需要實現連接路由器 drv_wlan_join() 和斷開路由器 drv_wlan_disconnect() 這 2 個函數。
在 AP 模式下,至少要實現 AP 開啟 drv_wlan_softap 和 AP 關閉 drv_wlan_ap_stop() 這 2個函數。
這 4 個函數可以按照芯片 SDK 上的接口對應實現即可。
event 管理
在實現以上接口用,需要在 Wi-Fi 觸發對應事件后,通過 event 通知 wlan 驅動框架。
在 STATION 模式下,當連接路由器成功后,通過 rt_wlan_dev_indicate_event_handle(wifi_sta.wlan, RT_WLAN_DEV_EVT_CONNECT, RT_NULL) 函數通知 wlan 框架 station 已經連接路由成功。當斷開路由器后,通過 rt_wlan_dev_indicate_event_handle(wifi_sta.wlan, RT_WLAN_DEV_EVT_DISCONNECT, RT_NULL) 函數通過 wlan 框架 station 已經斷開路由器。
wlan 框架在收到 RT_WLAN_DEV_EVT_CONNECT 時間后會通過 dhcp 服務獲取 IP。
在 AP 模式下,開啟軟 AP 成功后,通過 rt_wlan_dev_indicate_event_handle(wifi_ap.wlan, RT_WLAN_DEV_EVT_AP_START, RT_NULL) 函數通知 wlan 框架 AP 模式開啟成功。關閉軟 AP 成功后,通過 rt_wlan_dev_indicate_event_handle(wifi_ap.wlan, RT_WLAN_DEV_EVT_AP_STOP, RT_NULL) 函數通知 wlan 框架軟 AP 關閉。
wlan 框架在收到 RT_WLAN_DEV_EVT_AP_START 時間后會開啟 DHCP_SERVER 服務。
采用了 RT-Thread wlan 驅動框架后,芯片 SDK 只需要負責管理 WiFi 相關的連接服務,而不需要管理 lwip 協議棧,
數據收發
上面說到 wlan 框架在收到對應的 evnet 后,負責啟動 lwip 中的對應服務。
wlan 框架通過 drv_wlan_send() 函數將需要發送的網絡數據包發輸出去。針對WiFi 而言,需要通過判斷設備是 station 還是 ap 后,將對應的數據包發送給 WiFi 。
static int drv_wlan_send(struct rt_wlan_device *wlan, void *buff, int len)
{
if (wlan->user_data == &wifi_sta)
bl_wifi_tx(0, (struct pbuf *)buff);
else
bl_wifi_tx(1, (struct pbuf *)buff);
return RT_EOK;
}
WiFi 設備接收到數據后,通過 rt_wlan_dev_report_data() 函數,將數據傳遞給 wlan 框架,wlan 框架會進一步通過 lwip 做進一步處理。
int bl_wifi_rx(uint8_t idx, struct pbuf *p)
{
rt_err_t ret = RT_EOK;
if (idx == 0)
ret = rt_wlan_dev_report_data(wifi_sta.wlan, p, p->tot_len);
else
ret = rt_wlan_dev_report_data(wifi_ap.wlan, p, p->tot_len);
return ret;
}
其他必須實現的接口
mac相關
主要實現 mac 地址讀取和寫入。
static rt_err_t drv_wlan_set_mac(struct rt_wlan_device *wlan, rt_uint8_t mac[])
{
wifi_mgmr_sta_mac_set(mac);
return RT_EOK;
}
static rt_err_t drv_wlan_get_mac(struct rt_wlan_device *wlan, rt_uint8_t mac[])
{
wifi_mgmr_sta_mac_get(mac);
return RT_EOK;
}
Wi-Fi scan
static rt_err_t drv_wlan_scan(struct rt_wlan_device *wlan, struct rt_scan_info *scan_info)
{
int channel_input_num = 0;
uint8_t channel_input[MAX_FIXED_CHANNELS_LIMIT] = {0};
const char *ssid = NULL;
uint8_t bssid[6] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
uint8_t scan_mode = SCAN_ACTIVE;
uint32_t duration_scan_us = 0;
if (scan_info != NULL && scan_info->ssid.len > 0)
{
ssid = scan_info->ssid.val;
}
if (wifi_mgmr_scan_adv(wlan, wifi_scan_complete_callback, channel_input, channel_input_num, bssid, ssid, scan_mode, duration_scan_us) != 0)
return -RT_ERROR;
return RT_EOK;
-
WLAN
+關注
關注
2文章
658瀏覽量
73295 -
驅動器
+關注
關注
53文章
8288瀏覽量
147141 -
SoC芯片
+關注
關注
1文章
617瀏覽量
35059 -
LwIP協議
+關注
關注
0文章
11瀏覽量
8956 -
RT-Thread
+關注
關注
31文章
1306瀏覽量
40420
發布評論請先 登錄
相關推薦
BL808 RT-Thread Wi-Fi 驅動適配
![<b class='flag-5'>BL808</b> <b class='flag-5'>RT-Thread</b> <b class='flag-5'>Wi-Fi</b> <b class='flag-5'>驅動</b><b class='flag-5'>適配</b>](https://file1.elecfans.com/web2/M00/B2/4F/wKgaomVqnyuAZh1VAADmz_Dp0hY458.png)
RT-Thread NUC97x 移植 LVGL
DT-BL10 Wi-Fi和BLE共存模塊是什么
記錄BL808 BSP添加GPIO驅動時踩到的一些坑及解決方案
RT-Thread編程指南
RT-Thread Studio驅動SD卡
![<b class='flag-5'>RT-Thread</b> Studio<b class='flag-5'>驅動</b>SD卡](https://file.elecfans.com/web1/M00/D9/4E/pIYBAF_1ac2Ac0EEAABDkS1IP1s689.png)
【RT-Thread開源作品秀】基于RT-Thread的星務平臺研究
![【<b class='flag-5'>RT-Thread</b>開源作品秀】基于<b class='flag-5'>RT-Thread</b>的星務平臺研究](https://file.elecfans.com/web1/M00/D9/4E/pIYBAF_1ac2Ac0EEAABDkS1IP1s689.png)
RT-Thread學習筆記 RT-Thread的架構概述
![<b class='flag-5'>RT-Thread</b>學習筆記 <b class='flag-5'>RT-Thread</b>的架構概述](https://file.elecfans.com/web2/M00/52/31/pYYBAGLKk5WAA__jAADjdAdXhIs410.jpg)
RT-Thread文檔_RT-Thread 潘多拉 STM32L475 上手指南
![<b class='flag-5'>RT-Thread</b>文檔_<b class='flag-5'>RT-Thread</b> 潘多拉 STM32L475 上手指南](https://file.elecfans.com/web1/M00/D9/4E/pIYBAF_1ac2Ac0EEAABDkS1IP1s689.png)
記錄為BL808添加GPIO驅動
RT-Thread Wi-Fi Host Driver (WHD)
![<b class='flag-5'>RT-Thread</b> <b class='flag-5'>Wi-Fi</b> Host Driver (WHD)](https://file1.elecfans.com/web2/M00/C4/8A/wKgZomX0EhWACv8DAAAUet8ikhs451.png)
評論