| #include "headers.h" |
| |
| static INT bcm_notify_event(struct notifier_block *nb, ULONG event, PVOID dev) |
| { |
| struct net_device *ndev = (struct net_device*)dev; |
| PMINI_ADAPTER Adapter = GET_BCM_ADAPTER(gblpnetdev); |
| //PMINI_ADAPTER Adapter = (PMINI_ADAPTER)ndev->priv; |
| if(strncmp(ndev->name,gblpnetdev->name,5)==0) |
| { |
| switch(event) |
| { |
| case NETDEV_CHANGEADDR: |
| case NETDEV_GOING_DOWN: |
| /*ignore this */ |
| break; |
| case NETDEV_DOWN: |
| break; |
| |
| case NETDEV_UP: |
| break; |
| |
| case NETDEV_REGISTER: |
| /* Increment the Reference Count for "veth0" */ |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "Register RefCount: %x\n", |
| netdev_refcnt_read(ndev)); |
| dev_hold(ndev); |
| break; |
| |
| case NETDEV_UNREGISTER: |
| /* Decrement the Reference Count for "veth0" */ |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "Unregister RefCnt: %x\n", |
| netdev_refcnt_read(ndev)); |
| dev_put(ndev); |
| break; |
| }; |
| } |
| return NOTIFY_DONE; |
| } |
| |
| /* Notifier block to receive netdevice events */ |
| static struct notifier_block bcm_notifier_block = |
| { |
| .notifier_call = bcm_notify_event, |
| }; |
| |
| struct net_device *gblpnetdev; |
| /***************************************************************************************/ |
| /* proto-type of lower function */ |
| #ifdef BCM_SHM_INTERFACE |
| const char *bcmVirtDeviceName="bcmeth"; |
| #endif |
| |
| static INT bcm_open(struct net_device *dev) |
| { |
| PMINI_ADAPTER Adapter = NULL ; //(PMINI_ADAPTER)dev->priv; |
| Adapter = GET_BCM_ADAPTER(dev); |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "======>"); |
| if(Adapter->fw_download_done==FALSE) |
| return -EINVAL; |
| Adapter->if_up=1; |
| if(Adapter->LinkUpStatus == 1){ |
| if(netif_queue_stopped(Adapter->dev)){ |
| netif_carrier_on(Adapter->dev); |
| netif_start_queue(Adapter->dev); |
| } |
| } |
| |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "<======"); |
| return 0; |
| } |
| |
| static INT bcm_close(struct net_device *dev) |
| { |
| PMINI_ADAPTER Adapter = NULL ;//gpadapter ; |
| Adapter = GET_BCM_ADAPTER(dev); |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "=====>"); |
| Adapter->if_up=0; |
| if(!netif_queue_stopped(dev)) { |
| netif_carrier_off(dev); |
| netif_stop_queue(dev); |
| } |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL,"<====="); |
| return 0; |
| } |
| |
| static struct net_device_stats *bcm_get_stats(struct net_device *dev) |
| { |
| PLINUX_DEP_DATA pLinuxData=NULL; |
| PMINI_ADAPTER Adapter = NULL ;// gpadapter ; |
| Adapter = GET_BCM_ADAPTER(dev); |
| pLinuxData = (PLINUX_DEP_DATA)(Adapter->pvOsDepData); |
| |
| //BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "Dev = %p, pLinuxData = %p", dev, pLinuxData); |
| pLinuxData->netstats.rx_packets=atomic_read(&Adapter->RxRollOverCount)*64*1024+Adapter->PrevNumRecvDescs; |
| pLinuxData->netstats.rx_bytes=atomic_read(&Adapter->GoodRxByteCount)+atomic_read(&Adapter->BadRxByteCount); |
| pLinuxData->netstats.rx_dropped=atomic_read(&Adapter->RxPacketDroppedCount); |
| pLinuxData->netstats.rx_errors=atomic_read(&Adapter->RxPacketDroppedCount); |
| pLinuxData->netstats.rx_length_errors=0; |
| pLinuxData->netstats.rx_frame_errors=0; |
| pLinuxData->netstats.rx_crc_errors=0; |
| pLinuxData->netstats.tx_bytes=atomic_read(&Adapter->GoodTxByteCount); |
| pLinuxData->netstats.tx_packets=atomic_read(&Adapter->TxTotalPacketCount); |
| pLinuxData->netstats.tx_dropped=atomic_read(&Adapter->TxDroppedPacketCount); |
| |
| return &(pLinuxData->netstats); |
| } |
| /** |
| @ingroup init_functions |
| Register other driver entry points with the kernel |
| */ |
| #if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 29) |
| static struct net_device_ops bcmNetDevOps = { |
| .ndo_open = bcm_open, |
| .ndo_stop = bcm_close, |
| .ndo_get_stats = bcm_get_stats, |
| .ndo_start_xmit = bcm_transmit, |
| .ndo_change_mtu = eth_change_mtu, |
| .ndo_set_mac_address = eth_mac_addr, |
| .ndo_validate_addr = eth_validate_addr, |
| }; |
| #endif |
| |
| int register_networkdev(PMINI_ADAPTER Adapter) |
| { |
| int result=0; |
| #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,27) |
| void **temp = NULL; /* actually we're *allocating* the device in alloc_etherdev */ |
| #endif |
| Adapter->dev = alloc_etherdev(sizeof(PMINI_ADAPTER)); |
| if(!Adapter->dev) |
| { |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "ERR: No Dev"); |
| return -ENOMEM; |
| } |
| gblpnetdev = Adapter->dev; |
| #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,27) |
| Adapter->dev->priv = Adapter; |
| #else |
| temp = netdev_priv(Adapter->dev); |
| *temp = (void *)Adapter; |
| #endif |
| //BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "init adapterptr: %x %x\n", (UINT)Adapter, temp); |
| |
| #if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 29) |
| Adapter->dev->netdev_ops = &bcmNetDevOps; |
| #else |
| Adapter->dev->open = bcm_open; |
| Adapter->dev->stop = bcm_close; |
| Adapter->dev->get_stats = bcm_get_stats; |
| Adapter->dev->hard_start_xmit = bcm_transmit; |
| Adapter->dev->hard_header_len = ETH_HLEN + LEADER_SIZE; |
| #endif |
| |
| #ifndef BCM_SHM_INTERFACE |
| Adapter->dev->mtu = MTU_SIZE; /* 1400 Bytes */ |
| /* Read the MAC Address from EEPROM */ |
| ReadMacAddressFromNVM(Adapter); |
| |
| |
| /* Register the notifier block for getting netdevice events */ |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "Registering netdevice notifier\n"); |
| result = register_netdevice_notifier(&bcm_notifier_block); |
| if(result) |
| { |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "BCM Notifier Block did not get registered"); |
| Adapter->bNetdeviceNotifierRegistered = FALSE; |
| return result; |
| } |
| else |
| { |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "BCM Notifier got Registered"); |
| Adapter->bNetdeviceNotifierRegistered = TRUE; |
| } |
| |
| #else |
| |
| Adapter->dev->mtu = CPE_MTU_SIZE; |
| |
| #if 0 |
| //for CPE - harcode the virtual mac address |
| Adapter->dev->dev_addr[0] = MII_WIMAX_MACADDRESS[0]; |
| Adapter->dev->dev_addr[1] = MII_WIMAX_MACADDRESS[1]; |
| Adapter->dev->dev_addr[2] = MII_WIMAX_MACADDRESS[2]; |
| Adapter->dev->dev_addr[3] = MII_WIMAX_MACADDRESS[3]; |
| Adapter->dev->dev_addr[4] = MII_WIMAX_MACADDRESS[4]; |
| Adapter->dev->dev_addr[5] = MII_WIMAX_MACADDRESS[5]; |
| #else |
| ReadMacAddressFromNVM(Adapter); |
| #endif |
| strcpy(Adapter->dev->name, bcmVirtDeviceName); //Copy the device name |
| |
| #endif |
| |
| result = register_netdev(Adapter->dev); |
| if (!result) |
| { |
| Adapter->bNetworkInterfaceRegistered = TRUE ; |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "Beceem Network device name is %s!", Adapter->dev->name); |
| } |
| else |
| { |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "Network device can not be registered!"); |
| Adapter->bNetworkInterfaceRegistered = FALSE ; |
| return result; |
| } |
| |
| #if 0 |
| Adapter->stDebugState.debug_level = DBG_LVL_CURR; |
| Adapter->stDebugState.type =(UINT)0xffffffff; |
| Adapter->stDebugState.subtype[DBG_TYPE_OTHERS] = 0xffffffff; |
| Adapter->stDebugState.subtype[DBG_TYPE_RX] = 0xffffffff; |
| Adapter->stDebugState.subtype[DBG_TYPE_TX] = 0xffffffff; |
| Adapter->stDebugState.subtype[DBG_TYPE_INITEXIT] = 0xffffffff; |
| |
| printk("-------ps_adapter->stDebugState.type=%x\n",Adapter->stDebugState.type); |
| printk("-------ps_adapter->stDebugState.subtype[DBG_TYPE_OTHERS]=%x\n",Adapter->stDebugState.subtype[DBG_TYPE_OTHERS]); |
| printk("-------ps_adapter->stDebugState.subtype[DBG_TYPE_RX]=%x\n",Adapter->stDebugState.subtype[DBG_TYPE_RX]); |
| printk("-------ps_adapter->stDebugState.subtype[DBG_TYPE_TX]=%x\n",Adapter->stDebugState.subtype[DBG_TYPE_TX]); |
| #endif |
| |
| return 0; |
| } |
| |
| void bcm_unregister_networkdev(PMINI_ADAPTER Adapter) |
| { |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "Unregistering the Net Dev...\n"); |
| if(Adapter->dev && !IS_ERR(Adapter->dev) && Adapter->bNetworkInterfaceRegistered) |
| unregister_netdev(Adapter->dev); |
| /* Unregister the notifier block */ |
| if(Adapter->bNetdeviceNotifierRegistered == TRUE) |
| { |
| BCM_DEBUG_PRINT(Adapter,DBG_TYPE_INITEXIT, DRV_ENTRY, DBG_LVL_ALL, "Unregistering netdevice notifier\n"); |
| unregister_netdevice_notifier(&bcm_notifier_block); |
| } |
| } |
| |
| static int bcm_init(void) |
| { |
| int result; |
| result = InterfaceInitialize(); |
| if(result) |
| { |
| printk("Initialisation failed for usbbcm"); |
| } |
| else |
| { |
| printk("Initialised usbbcm"); |
| } |
| return result; |
| } |
| |
| |
| static void bcm_exit(void) |
| { |
| printk("%s %s Calling InterfaceExit\n",__FILE__, __FUNCTION__); |
| InterfaceExit(); |
| printk("%s %s InterfaceExit returned\n",__FILE__, __FUNCTION__); |
| } |
| |
| module_init(bcm_init); |
| module_exit(bcm_exit); |
| MODULE_LICENSE ("GPL"); |
| |
| |