生活随笔
收集整理的這篇文章主要介紹了
Linux Wireless架构总结
小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.
1、無線網(wǎng)絡(luò)驅(qū)動(dòng)(ath9k_htc)
ath9k_htc是一個(gè)基于USB接口的SoftMAC無線網(wǎng)絡(luò)適配器。為了其驅(qū)動(dòng)能正常工作,首先必須調(diào)用usb_register來注冊驅(qū)動(dòng)定義的usb_driver,以借助USB Core的力量來處理與USB協(xié)議相關(guān)的事件。其代碼如下:
[cpp]?view plaincopy
static?struct?usb_driver?ath9k_hif_usb_driver?=?{???? ????.name?=?KBUILD_MODNAME,???? ????.probe?=?ath9k_hif_usb_probe,???? ????.disconnect?=?ath9k_hif_usb_disconnect,???? #ifdef?CONFIG_PM???? ????.suspend?=?ath9k_hif_usb_suspend,???? ????.resume?=?ath9k_hif_usb_resume,???? ????.reset_resume?=?ath9k_hif_usb_resume,???? #endif???? ????.id_table?=?ath9k_hif_usb_ids,???? ????.soft_unbind?=?1,???? };????
2. 關(guān)鍵數(shù)據(jù)結(jié)構(gòu)
1) struct ieee80211_hw: 它包含802.11 PHY的配置和硬件信息
2.1 各層間關(guān)鍵數(shù)據(jù)接口
3、USB無線適配器枚舉過程?
? ? ?當(dāng)此基于USB接口的無線網(wǎng)絡(luò)適配器被枚舉時(shí),ath9k_hif_usb_probe將被調(diào)用。其調(diào)用流程如下圖所示:
3.1 struct ieee80211_ops 實(shí)例 ath9k_htc_ops(驅(qū)動(dòng)實(shí)現(xiàn))
? ? ? ?ath9k_htc_ops: mac80211通過這些回調(diào)函數(shù)回調(diào)driver的處理函數(shù)。ath9k_htc為了接受mac80211的管理,它必須首先向mac80211注冊,以申明自己的存在,從而可以接受mac80211的調(diào)用。
[cpp]?view plaincopy
struct?ieee80211_ops?ath9k_htc_ops?=?{???? ????.tx?????????????????=?ath9k_htc_tx,???? ????.start??????????????=?ath9k_htc_start,??? ????.stop???????????????=?ath9k_htc_stop,???? ????.add_interface??????=?ath9k_htc_add_interface,??? ????.remove_interface???=?ath9k_htc_remove_interface,??? ????.config?????????????=?ath9k_htc_config,????????????? ????.configure_filter???=?ath9k_htc_configure_filter,??? ????.sta_add????????????=?ath9k_htc_sta_add,???? ????.sta_remove?????????=?ath9k_htc_sta_remove,???? ????.conf_tx????????????=?ath9k_htc_conf_tx,???? ????.bss_info_changed???=?ath9k_htc_bss_info_changed,???? ????.set_key????????????=?ath9k_htc_set_key,???? ????.get_tsf????????????=?ath9k_htc_get_tsf,???? ????.set_tsf????????????=?ath9k_htc_set_tsf,???? ????.reset_tsf??????????=?ath9k_htc_reset_tsf,???? ????.ampdu_action???????=?ath9k_htc_ampdu_action,???? ????.sw_scan_start??????=?ath9k_htc_sw_scan_start,???? ????.sw_scan_complete???=?ath9k_htc_sw_scan_complete,???? ????.set_rts_threshold??=?ath9k_htc_set_rts_threshold,???? ????.rfkill_poll????????=?ath9k_htc_rfkill_poll_state,???? ????.set_coverage_class?=?ath9k_htc_set_coverage_class,???? ????.set_bitrate_mask???=?ath9k_htc_set_bitrate_mask,???? };????
3.2 struct cfg80211_ops 實(shí)例 mac80211_config_ops(mac80211實(shí)現(xiàn)) ?
? ?cfg80211_ops定義了無線配置的操作,在它的增加虛擬接口(ieee80211_add_iface)中,它將創(chuàng)建并注冊net_device。在mac80211中,其定義如下所示:
[cpp]?view plaincopy
struct?cfg80211_ops?mac80211_config_ops?=?{???? ????.add_virtual_intf?=?ieee80211_add_iface,??? ????.del_virtual_intf?=?ieee80211_del_iface,??? ????.change_virtual_intf?=?ieee80211_change_iface,???? ????.add_key?=?ieee80211_add_key,???? ????.del_key?=?ieee80211_del_key,???? ????.get_key?=?ieee80211_get_key,???? ????.set_default_key?=?ieee80211_config_default_key,???? ????.set_default_mgmt_key?=?ieee80211_config_default_mgmt_key,???? ????.add_beacon?=?ieee80211_add_beacon,???? ????.set_beacon?=?ieee80211_set_beacon,???? ????.del_beacon?=?ieee80211_del_beacon,???? ????.add_station?=?ieee80211_add_station,???? ????.del_station?=?ieee80211_del_station,???? ????.change_station?=?ieee80211_change_station,???? ????.get_station?=?ieee80211_get_station,???? ????.dump_station?=?ieee80211_dump_station,???? ????.dump_survey?=?ieee80211_dump_survey,???? #ifdef?CONFIG_MAC80211_MESH???? ????.add_mpath?=?ieee80211_add_mpath,???? ????.del_mpath?=?ieee80211_del_mpath,???? ????.change_mpath?=?ieee80211_change_mpath,???? ????.get_mpath?=?ieee80211_get_mpath,???? ????.dump_mpath?=?ieee80211_dump_mpath,???? ????.update_mesh_config?=?ieee80211_update_mesh_config,???? ????.get_mesh_config?=?ieee80211_get_mesh_config,???? ????.join_mesh?=?ieee80211_join_mesh,???? ????.leave_mesh?=?ieee80211_leave_mesh,???? #endif???? ????.change_bss?=?ieee80211_change_bss,???? ????.set_txq_params?=?ieee80211_set_txq_params,???? ????.set_channel?=?ieee80211_set_channel,???? ????.suspend?=?ieee80211_suspend,???? ????.resume?=?ieee80211_resume,???? ????.scan?=?ieee80211_scan,???? ????.sched_scan_start?=?ieee80211_sched_scan_start,???? ????.sched_scan_stop?=?ieee80211_sched_scan_stop,???? ????.auth?=?ieee80211_auth,???? ????.assoc?=?ieee80211_assoc,???? ????.deauth?=?ieee80211_deauth,???? ????.disassoc?=?ieee80211_disassoc,???? ????.join_ibss?=?ieee80211_join_ibss,???? ????.leave_ibss?=?ieee80211_leave_ibss,???? ????.set_wiphy_params?=?ieee80211_set_wiphy_params,???? ????.set_tx_power?=?ieee80211_set_tx_power,???? ????.get_tx_power?=?ieee80211_get_tx_power,???? ????.set_wds_peer?=?ieee80211_set_wds_peer,???? ????.rfkill_poll?=?ieee80211_rfkill_poll,???? ????CFG80211_TESTMODE_CMD(ieee80211_testmode_cmd)???? ????.set_power_mgmt?=?ieee80211_set_power_mgmt,???? ????.set_bitrate_mask?=?ieee80211_set_bitrate_mask,???? ????.remain_on_channel?=?ieee80211_remain_on_channel,???? ????.cancel_remain_on_channel?=?ieee80211_cancel_remain_on_channel,???? ????.mgmt_tx?=?ieee80211_mgmt_tx,???? ????.mgmt_tx_cancel_wait?=?ieee80211_mgmt_tx_cancel_wait,???? ????.set_cqm_rssi_config?=?ieee80211_set_cqm_rssi_config,???? ????.mgmt_frame_register?=?ieee80211_mgmt_frame_register,???? ????.set_antenna?=?ieee80211_set_antenna,???? ????.get_antenna?=?ieee80211_get_antenna,???? ????.set_ringparam?=?ieee80211_set_ringparam,???? ????.get_ringparam?=?ieee80211_get_ringparam,???? }????
3.3 struct iw_handler_def ?實(shí)例 cfg80211_wext_handler(wireless實(shí)現(xiàn))
? ? ? cfg80211_wext_handler實(shí)現(xiàn)了wext要求的ioctl操作,將通過net_device->wireless_handlers->standard[ioctl cmd- SIOCIWFIRST]來進(jìn)行調(diào)用。在net/wireless/wext-compat.c中的定義如下所示:
[cpp]?view plaincopy
tatic?const?iw_handler?cfg80211_handlers[]?=?{???? ????[IW_IOCTL_IDX(SIOCGIWNAME)]?=?(iw_handler)?cfg80211_wext_giwname,???? ????[IW_IOCTL_IDX(SIOCSIWFREQ)]?=?(iw_handler)?cfg80211_wext_siwfreq,???? ????[IW_IOCTL_IDX(SIOCGIWFREQ)]?=?(iw_handler)?cfg80211_wext_giwfreq,???? ????[IW_IOCTL_IDX(SIOCSIWMODE)]?=?(iw_handler)?cfg80211_wext_siwmode,???? ????[IW_IOCTL_IDX(SIOCGIWMODE)]?=?(iw_handler)?cfg80211_wext_giwmode,???? ????[IW_IOCTL_IDX(SIOCGIWRANGE)]????=?(iw_handler)?cfg80211_wext_giwrange,???? ????[IW_IOCTL_IDX(SIOCSIWAP)]???=?(iw_handler)?cfg80211_wext_siwap,???? ????[IW_IOCTL_IDX(SIOCGIWAP)]???=?(iw_handler)?cfg80211_wext_giwap,???? ????[IW_IOCTL_IDX(SIOCSIWMLME)]?=?(iw_handler)?cfg80211_wext_siwmlme,???? ????[IW_IOCTL_IDX(SIOCSIWSCAN)]?=?(iw_handler)?cfg80211_wext_siwscan,???? ????[IW_IOCTL_IDX(SIOCGIWSCAN)]?=?(iw_handler)?cfg80211_wext_giwscan,???? ????[IW_IOCTL_IDX(SIOCSIWESSID)]????=?(iw_handler)?cfg80211_wext_siwessid,???? ????[IW_IOCTL_IDX(SIOCGIWESSID)]????=?(iw_handler)?cfg80211_wext_giwessid,???? ????[IW_IOCTL_IDX(SIOCSIWRATE)]?=?(iw_handler)?cfg80211_wext_siwrate,???? ????[IW_IOCTL_IDX(SIOCGIWRATE)]?=?(iw_handler)?cfg80211_wext_giwrate,???? ????[IW_IOCTL_IDX(SIOCSIWRTS)]??=?(iw_handler)?cfg80211_wext_siwrts,???? ????[IW_IOCTL_IDX(SIOCGIWRTS)]??=?(iw_handler)?cfg80211_wext_giwrts,???? ????[IW_IOCTL_IDX(SIOCSIWFRAG)]?=?(iw_handler)?cfg80211_wext_siwfrag,???? ????[IW_IOCTL_IDX(SIOCGIWFRAG)]?=?(iw_handler)?cfg80211_wext_giwfrag,???? ????[IW_IOCTL_IDX(SIOCSIWTXPOW)]????=?(iw_handler)?cfg80211_wext_siwtxpower,???? ????[IW_IOCTL_IDX(SIOCGIWTXPOW)]????=?(iw_handler)?cfg80211_wext_giwtxpower,???? ????[IW_IOCTL_IDX(SIOCSIWRETRY)]????=?(iw_handler)?cfg80211_wext_siwretry,???? ????[IW_IOCTL_IDX(SIOCGIWRETRY)]????=?(iw_handler)?cfg80211_wext_giwretry,???? ????[IW_IOCTL_IDX(SIOCSIWENCODE)]???=?(iw_handler)?cfg80211_wext_siwencode,???? ????[IW_IOCTL_IDX(SIOCGIWENCODE)]???=?(iw_handler)?cfg80211_wext_giwencode,???? ????[IW_IOCTL_IDX(SIOCSIWPOWER)]????=?(iw_handler)?cfg80211_wext_siwpower,???? ????[IW_IOCTL_IDX(SIOCGIWPOWER)]????=?(iw_handler)?cfg80211_wext_giwpower,???? ????[IW_IOCTL_IDX(SIOCSIWGENIE)]????=?(iw_handler)?cfg80211_wext_siwgenie,???? ????[IW_IOCTL_IDX(SIOCSIWAUTH)]?=?(iw_handler)?cfg80211_wext_siwauth,???? ????[IW_IOCTL_IDX(SIOCGIWAUTH)]?=?(iw_handler)?cfg80211_wext_giwauth,???? ????[IW_IOCTL_IDX(SIOCSIWENCODEEXT)]=?(iw_handler)?cfg80211_wext_siwencodeext,???? ????[IW_IOCTL_IDX(SIOCSIWPMKSA)]????=?(iw_handler)?cfg80211_wext_siwpmksa,???? ??[IW_IOCTL_IDX(SIOCSIWPRIV)]?=?(iw_handler)cfg80211_wext_setpriv???? };???? ???? const?struct?iw_handler_def?cfg80211_wext_handler?=?{???? ????.num_standard???????=?ARRAY_SIZE(cfg80211_handlers),???? ????.standard???????=?cfg80211_handlers,???? ????.get_wireless_stats?=?cfg80211_wireless_stats,????
4、創(chuàng)建并注冊net_device
? ? ? ? ? ? ?當(dāng)執(zhí)行mac80211_config_ops-> ieee80211_add_iface時(shí),它將創(chuàng)建net_device和對(duì)應(yīng)的ieee80211_sub_if_data, 然后主要做了以下幾件事:
1) 把net_device對(duì)應(yīng)的名字增加到/sys/class/net/目錄下 ??
2) 把新創(chuàng)建的net_device插入到init_net->dev_base_head中
3) 通知上層協(xié)議,有一個(gè)新的net_device出現(xiàn)了,大家可以使用它了
4) 把新創(chuàng)建的ieee80211_sub_if_data增加到ieee80211_local的interfaces列表中 ? ? ? ?
其流程如下圖所示:
??
mac80211中定義的net_device_ops ieee80211_dataif_ops,以下這些方法,都有一個(gè)struct net_device參數(shù)。其具體定義如下: ??
[cpp]?view plaincopy
static?const?struct?net_device_ops?ieee80211_dataif_ops?=?{???? ????.ndo_open???????=?ieee80211_open,???????????????? ????.ndo_stop???????=?ieee80211_stop,???????????????? ????.ndo_uninit?????=?ieee80211_teardown_sdata,?????? ????.ndo_start_xmit?????=?ieee80211_subif_start_xmit,???? ????.ndo_set_multicast_list?=?ieee80211_set_multicast_list,?? ????.ndo_change_mtu?????=?ieee80211_change_mtu,?????????? ????.ndo_set_mac_address????=?ieee80211_change_mac,?????????? ????.ndo_select_queue???=?ieee80211_netdev_select_queue,??? };????
mac80211中初始化net_device->netdev_ops:
[cpp]?view plaincopy
static?void?ieee80211_if_setup(struct?net_device?*dev)???? {???? ????ether_setup(dev);???? ????dev->priv_flags?&=?~IFF_TX_SKB_SHARING;???? ????dev->netdev_ops?=?&ieee80211_dataif_ops;???? ????dev->destructor?=?free_netdev;???? }????
5. 數(shù)據(jù)接收(Data RX)流程
? ?數(shù)據(jù)接收流程如下圖所示:
IP層與TCP/UDP層接口定義如下:
[cpp]?view plaincopy
static?const?struct?net_protocol?tcp_protocol?=?{???? ????.handler?=??tcp_v4_rcv,???? ????.err_handler?=??tcp_v4_err,???? ????.gso_send_check?=?tcp_v4_gso_send_check,???? ????.gso_segment?=??tcp_tso_segment,???? ????.gro_receive?=??tcp4_gro_receive,???? ????.gro_complete?=?tcp4_gro_complete,???? ????.no_policy?=????1,???? ????.netns_ok?=?1,???? };???? ???? static?const?struct?net_protocol?udp_protocol?=?{???? ????.handler?=??udp_rcv,???? ????.err_handler?=??udp_err,???? ????.gso_send_check?=?udp4_ufo_send_check,???? ????.gso_segment?=?udp4_ufo_fragment,???? ????.no_policy?=????1,???? ????.netns_ok?=?1,???? };???? ???? static?const?struct?net_protocol?icmp_protocol?=?{???? ????.handler?=??icmp_rcv,???? ????.err_handler?=??ping_err,???? ????.no_policy?=????1,???? ????.netns_ok?=?1,???? };????
IP層與net/core層接口定義如下
[cpp]?view plaincopy
static?struct?packet_type?ip_packet_type?__read_mostly?=?{???? ????.type?=?cpu_to_be16(ETH_P_IP),???? ????.func?=?ip_rcv,???? ????.gso_send_check?=?inet_gso_send_check,???? ????.gso_segment?=?inet_gso_segment,???? ????.gro_receive?=?inet_gro_receive,???? ????.gro_complete?=?inet_gro_complete,???? };????
6、數(shù)據(jù)發(fā)送(Data TX)流珵
? ?數(shù)據(jù)發(fā)送流程如下圖所示:
上半部分涉及到的相關(guān)代碼如下所示(以上流程主要通過dump_stack獲取):
? ? ?net/socket.c
? ? ?net/ipv4/af_net.c
? ? ?net/ipv4/tcp.c
? ? ?net/ipv4/tcp_output.c
? ? ?net/ipv4/ip_output.c
? ? ?net/core/neighbour.c
? ? ?net/core/dev.c
7、INET初始化
? ? INET為Linux OS實(shí)現(xiàn)了TCP/IP協(xié)議集,它使用BSD Socket接口作為與User通訊的方式。其初始化代碼如下所示:
代碼位于:net/ipv4/af_inet.c
[cpp]?view plaincopy
static?int?__init?inet_init(void)???? {???? ????struct?sk_buff?*dummy_skb;???? ????struct?inet_protosw?*q;???? ????struct?list_head?*r;???? ????int?rc?=?-EINVAL;???? ???? ????BUILD_BUG_ON(sizeof(struct?inet_skb_parm)?>?sizeof(dummy_skb->cb));???? ???? ????sysctl_local_reserved_ports?=?kzalloc(65536?/?8,?GFP_KERNEL);???? ????if?(!sysctl_local_reserved_ports)???? ????????goto?out;???? ???? ????rc?=?proto_register(&tcp_prot,?1);???? ????if?(rc)???? ????????goto?out_free_reserved_ports;???? ???? ????rc?=?proto_register(&udp_prot,?1);???? ????if?(rc)???? ????????goto?out_unregister_tcp_proto;???? ???? ????rc?=?proto_register(&raw_prot,?1);???? ????if?(rc)???? ????????goto?out_unregister_udp_proto;???? ???? ????rc?=?proto_register(&ping_prot,?1);???? ????if?(rc)???? ????????goto?out_unregister_raw_proto;???? ???? ????? ? ???? ???? ????(void)sock_register(&inet_family_ops);???? ???? #ifdef?CONFIG_SYSCTL???? ????ip_static_sysctl_init();???? #endif???? ???? ????? ? ???? ???? ????if?(inet_add_protocol(&icmp_protocol,?IPPROTO_ICMP)?<?0)???? ????????printk(KERN_CRIT?"inet_init:?Cannot?add?ICMP?protocol\n");???? ????if?(inet_add_protocol(&udp_protocol,?IPPROTO_UDP)?<?0)???? ????????printk(KERN_CRIT?"inet_init:?Cannot?add?UDP?protocol\n");???? ????if?(inet_add_protocol(&tcp_protocol,?IPPROTO_TCP)?<?0)???? ????????printk(KERN_CRIT?"inet_init:?Cannot?add?TCP?protocol\n");???? #ifdef?CONFIG_IP_MULTICAST???? ????if?(inet_add_protocol(&igmp_protocol,?IPPROTO_IGMP)?<?0)???? ????????printk(KERN_CRIT?"inet_init:?Cannot?add?IGMP?protocol\n");???? #endif???? ???? ???????? ????for?(r?=?&inetsw[0];?r?<?&inetsw[SOCK_MAX];?++r)???? ????????INIT_LIST_HEAD(r);???? ???? ????for?(q?=?inetsw_array;?q?<?&inetsw_array[INETSW_ARRAY_LEN];?++q)???? ????????inet_register_protosw(q);???? ???? ????? ? ???? ???? ????arp_init();???? ???? ????? ? ???? ???? ????ip_init();???? ???? ????tcp_v4_init();???? ???? ???????? ????tcp_init();???? ???? ???????? ????udp_init();???? ???? ???????? ????udplite4_register();???? ???? ????ping_init();???? ???? ????? ? ???? ???? ????if?(icmp_init()?<?0)???? ????????panic("Failed?to?create?the?ICMP?control?socket.\n");???? ???? ????? ? ???? #if?defined(CONFIG_IP_MROUTE)???? ????if?(ip_mr_init())???? ????????printk(KERN_CRIT?"inet_init:?Cannot?init?ipv4?mroute\n");???? #endif???? ????? ? ???? ???? ????if?(init_ipv4_mibs())???? ????????printk(KERN_CRIT?"inet_init:?Cannot?init?ipv4?mibs\n");???? ???? ????ipv4_proc_init();???? ???? ????ipfrag_init();???? ???? ????dev_add_pack(&ip_packet_type);???? ???? ????rc?=?0;???? out:???? ????return?rc;???? out_unregister_raw_proto:???? ????proto_unregister(&raw_prot);???? out_unregister_udp_proto:???? ????proto_unregister(&udp_prot);???? out_unregister_tcp_proto:???? ????proto_unregister(&tcp_prot);???? out_free_reserved_ports:???? ????kfree(sysctl_local_reserved_ports);???? ????goto?out;???? } ? ?
總結(jié)
以上是生活随笔為你收集整理的Linux Wireless架构总结的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。