个人总结,不一定对。
1. 申请内存:
struct ieee80211_hw *hw;
const struct wl12xx_platform_data *wlan_data;
struct wl1271 *wl;
int ret;
/* We are only able to handle the wlan function */
if (func->num != 0x02)
return -ENODEV;
hw = wl1271_alloc_hw();
if (IS_ERR(hw))
return PTR_ERR(hw);
2. 初始化内容
wl = hw->priv;
wl->if_priv = func;
wl->if_ops = &sdio_ops;
/* Grab access to FN0 for ELP reg. */
func->card->quirks |= MMC_QUIRK_LENIENT_FN0;
wlan_data = wl12xx_get_platform_data();
if (IS_ERR(wlan_data)) {
ret = PTR_ERR(wlan_data);
wl1271_error("missing wlan platform data: %d", ret);
goto out_free;
}
wl->irq = wlan_data->irq;
wl->ref_clock = wlan_data->board_ref_clock;
ret = request_irq(wl->irq, wl1271_irq, 0, DRIVER_NAME, wl);
if (ret < 0) {
wl1271_error("request_irq() failed: %d", ret);
goto out_free;
}
set_irq_type(wl->irq, IRQ_TYPE_EDGE_RISING);
disable_irq(wl->irq);
ret = wl1271_init_ieee80211(wl); //初始化
if (ret)
goto out_irq;
3. 注册
ret = wl1271_register_hw(wl);
if (ret)
goto out_irq;
4. 赋值指针:
sdio_set_drvdata(func, wl);
具体讨论:
1. wl1271_alloc_hw():
struct ieee80211_hw *wl1271_alloc_hw(void)
{
struct ieee80211_hw *hw;
struct platform_device *plat_dev = NULL;
struct wl1271 *wl;
int i, ret;
unsigned int order;
hw = ieee80211_alloc_hw(sizeof(*wl), &wl1271_ops); //申请ieee 802.11 phy hw 内存
if (!hw) {
wl1271_error("could not alloc ieee80211_hw");
ret = -ENOMEM;
goto err_hw_alloc;
}
plat_dev = kmemdup(&wl1271_device, sizeof(wl1271_device), GFP_KERNEL); //复制内存
if (!plat_dev) {
wl1271_error("could not allocate platform_device");
ret = -ENOMEM;
goto err_plat_alloc;
}
wl = hw->priv;
memset(wl, 0, sizeof(*wl)); //wl初始化为0
INIT_LIST_HEAD(&wl->list); //初始化list
wl->hw = hw;
wl->plat_dev = plat_dev;
skb_queue_head_init(&wl->tx_queue);
INIT_DELAYED_WORK(&wl->elp_work, wl1271_elp_work);
INIT_DELAYED_WORK(&wl->pspoll_work, wl1271_pspoll_work);
INIT_WORK(&wl->irq_work, wl1271_irq_work);
INIT_WORK(&wl->tx_work, wl1271_tx_work);
INIT_WORK(&wl->recovery_work, wl1271_recovery_work);
INIT_DELAYED_WORK(&wl->scan_complete_work, wl1271_scan_complete_work);
wl->channel = WL1271_DEFAULT_CHANNEL;
wl->beacon_int = WL1271_DEFAULT_BEACON_INT;
wl->default_key = 0;
wl->rx_counter = 0;
wl->rx_config = WL1271_DEFAULT_RX_CONFIG;
wl->rx_filter = WL1271_DEFAULT_RX_FILTER;
wl->psm_entry_retry = 0;