mtk7621驱动
无线驱动在完成驱动注册的同时,需要进行 cfg80211接口注册(提供命令支持)。
1.驱动
mtk wifi驱动基于pci进行扩展,第一个文件:/os/linux/pci_main_dev.c
文件用于创建和注册基于pci接口的网络设备,PCI设备上有三种地址空间:PCI的I/O空间、PCI的存储空间和PCI的配置空间。CPU可以访问PCI设备上的所有地址空间,其中I/O空间和存储空间提供给设备驱动程序使用,而配置空间则由Linux内核中的PCI初始化代码使用。内核在启动时负责对所有PCI设备进行初始化,配置好所有的PCI设备,包括中断号以及I/O基址,并在文件/proc/pci中列出所有找到的PCI设备,以及这些设备的参数和属性。
Linux驱动程序通常使用结构(struct)来表示一种设备,而结构体中的变量则代表某一具体设备,该变量存放了与该设备相关的所有信息。好的驱动程序都应该能驱动多个同种设备,每个设备之间用次设备号进行区分,如果采用结构数据来代表所有能由该驱动程序驱动的设备,那么就可以简单地使用数组下标来表示次设备号。
1.1数据结构
1 static struct pci_device_id rt_pci_tbl[]
DEVINITDATA =
{
{PCI_DEVICE(NIC_PCI_VENDOR_ID,
NIC3091_PCIe_DEVICE_ID)},
#ifdef RT8592
{PCI_DEVICE(NIC_PCI_VENDOR_ID,
NIC8592_PCIe_DEVICE_ID)},
#endif /* RT8592 */
#ifdef MT76x2
{PCI_DEVICE(0x1400, NIC7650_PCIe_DEVICE_ID)},
{PCI_DEVICE(0x1400,
NIC7662_PCIe_DEVICE_ID)},
{PCI_DEVICE(MTK_PCI_VENDOR_ID,
NIC7662_PCIe_DEVICE_ID)},
{PCI_DEVICE(MTK_PCI_VENDOR_ID,
NIC7632_PCIe_DEVICE_ID)},
{PCI_DEVICE(MTK_PCI_VENDOR_ID,
NIC7612_PCIe_DEVICE_ID)},
{PCI_DEVICE(MTK_PCI_VENDOR_ID,
NIC7602_PCIe_DEVICE_ID)},
#endif /* MT76x2 */
{} /* terminate list */
};
struct pci_device_id {
__u32
vendor,device;
//厂商和设备ID
__u32
subvendor,subdevice; //子系统和设备ID
__u32 class,class_mask;
//类、子类、prog-if三元组
kernel_ulong_t
driver_data; //驱动私有数据
pci_device_id 用MODULE_DEVICE_TABLE映射到用户空间。
2 struct pci_driver {
struct list_head node;
const char *name;
const struct pci_device_id *id_table; /* must
be non-NULL for probe to be called */
int (*probe) (struct pci_dev *dev, const
struct pci_device_id *id); /* New device inserted */
void (*remove) (struct pci_dev *dev); /*
Device removed (NULL if not a hot-plug capable driver) */
int (*suspend) (struct pci_dev *dev,
pm_message_t state); /* Device suspended */
int (*suspend_late) (struct pci_dev *dev,
pm_message_t state);
int (*resume_early) (struct pci_dev *dev);
int (*resume) (struct pci_dev *dev); /*
Device woken up */
void (*shutdown) (struct pci_dev *dev);
int (*sriov_configure) (struct pci_dev
*dev, int num_vfs); /* PF pdev */
const struct pci_error_handlers
*err_handler;
struct device_driver driver;
struct pci_dynids dynids;
};
3 struct pci_dev {
struct list_head bus_list;
/* 总线设备链表元素bus_list:每一个pci_dev结构除了链接到全局设备链表中外,还会通过这个成员连接到其所属PCI总线的设备链表中。每一条PCI总线都维护一条它自己的设备链表视图,以便描述所有连接在该PCI总线上的设备,其表头由PCI总线的pci_bus结构中的 devices成员所描述t*/
struct pci_bus *bus;
/* 总线指针bus:指向这个PCI设备所在的PCI总线的pci_bus结构。因此,对于桥设备而言,bus指针将指向桥设备的主总线(primary bus),也即指向桥设备所在的PCI总线*/
struct pci_bus *subordinate;
/* 指针subordinate:指向这个PCI设备所桥接的下级总线。这个指针成员仅对桥设备才有意义,而对于一般的非桥PCI设备而言,该指针成员总是为NULL*/
void *sysdata;
/* 无类型指针sysdata:指向一片特定于系统的扩展数据*/
struct proc_dir_entry *procent;
/* 指针procent:指向该PCI设备在/proc文件系统中对应的目录项*/
uns