1a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/* 2a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * WlanDrvIf.c 3a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 4a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved. 5a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * All rights reserved. 6a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 7a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Redistribution and use in source and binary forms, with or without 8a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * modification, are permitted provided that the following conditions 9a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * are met: 10a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 11a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * * Redistributions of source code must retain the above copyright 12a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * notice, this list of conditions and the following disclaimer. 13a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * * Redistributions in binary form must reproduce the above copyright 14a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * notice, this list of conditions and the following disclaimer in 15a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * the documentation and/or other materials provided with the 16a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * distribution. 17a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * * Neither the name Texas Instruments nor the names of its 18a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * contributors may be used to endorse or promote products derived 19a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * from this software without specific prior written permission. 20a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 21a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 22a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 23a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 24a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 25a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 26a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 27a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 28a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 29a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 30a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 31a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 32a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 33a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 34a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 35a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/* 36a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * src/esta_drv.c 37a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 38a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Kernel level portion of eSTA DK Linux module driver 39a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 40a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 41a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 42a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 43a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** \file WlanDrvIf.c 44a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief The OS-Dependent interfaces of the WLAN driver with external applications: 45a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * - Configuration utilities (including download, configuration and activation) 46a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * - Network Stack (Tx and Rx) 47a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * - Interrupts 48a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * - Events to external applications 49a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 50a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \see WlanDrvIf.h, Wext.c 51a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 52a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 53a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 54a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include <net/sock.h> 55a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include <linux/etherdevice.h> 56a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include <linux/delay.h> 57a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include <linux/netlink.h> 58a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 59a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "WlanDrvIf.h" 60a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "osApi.h" 61a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "host_platform.h" 62a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "context.h" 63a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "CmdHndlr.h" 64a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "WlanDrvWext.h" 65a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "DrvMain.h" 66a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "txDataQueue_Api.h" 67a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "txMgmtQueue_Api.h" 68a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "TWDriver.h" 69a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "Ethernet.h" 70a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#ifdef TI_DBG 71a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "tracebuf_api.h" 72a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 73a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/* PM hooks */ 74ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifdef TI_CONFIG_PM_HOOKS 75a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "SdioDrv.h" 76a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic int wlanDrvIf_pm_resume(void); 77a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic int wlanDrvIf_pm_suspend(void); 78a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 79a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#include "bmtrace_api.h" 80ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifdef STACK_PROFILE 81ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#include "stack_profile.h" 82ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 83a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 84a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/* save driver handle just for module cleanup */ 85a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic TWlanDrvIfObj *pDrvStaticHandle; 86a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 87a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#define OS_SPECIFIC_RAM_ALLOC_LIMIT (0xFFFFFFFF) /* assume OS never reach that limit */ 88a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 89a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 90a615fb1650af6e111053506f1b764b28a5b4631dDmitry ShmidtMODULE_DESCRIPTION("TI WLAN Embedded Station Driver"); 91a615fb1650af6e111053506f1b764b28a5b4631dDmitry ShmidtMODULE_LICENSE("GPL"); 92a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 93a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 94ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#if (LINUX_VERSION_CODE > KERNEL_VERSION(2, 6, 31)) 95ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtstatic int wlanDrvIf_Xmit(struct sk_buff *skb, struct net_device *dev); 96ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtstatic int wlanDrvIf_XmitDummy(struct sk_buff *skb, struct net_device *dev); 97ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtstatic struct net_device_stats *wlanDrvIf_NetGetStat(struct net_device *dev); 98ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtint wlanDrvIf_Open(struct net_device *dev); 99ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtint wlanDrvIf_Release(struct net_device *dev); 100ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt 101ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtstatic struct net_device_ops tiwlan_ops_pri = { 102ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt .ndo_open = wlanDrvIf_Open, 103ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt .ndo_stop = wlanDrvIf_Release, 104ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt .ndo_get_stats = wlanDrvIf_NetGetStat, 105ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt .ndo_do_ioctl = NULL, 106ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt .ndo_start_xmit = wlanDrvIf_Xmit, 107ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt}; 108ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt 109ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtstatic struct net_device_ops tiwlan_ops_dummy = { 110ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt .ndo_open = wlanDrvIf_Open, 111ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt .ndo_stop = wlanDrvIf_Release, 112ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt .ndo_get_stats = wlanDrvIf_NetGetStat, 113ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt .ndo_do_ioctl = NULL, 114ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt .ndo_start_xmit = wlanDrvIf_XmitDummy, 115ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt}; 116ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 117a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 118a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 119a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_Xmit 120a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Packets transmission 121a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 122a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * The network stack calls this function in order to transmit a packet 123a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * through the WLAN interface. 124a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * The packet is inserted to the drver Tx queues and its handling is continued 125a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * after switching to the driver context. 126a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 127a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 128a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param skb - The Linux packet buffer structure 129a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param dev - The driver network-interface handle 130a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return 0 (= OK) 131a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa 132a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 133a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic int wlanDrvIf_Xmit (struct sk_buff *skb, struct net_device *dev) 134a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 135ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)NETDEV_GET_PRIVATE(dev); 136ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TTxCtrlBlk * pPktCtrlBlk; 137ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt int status; 138a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 139ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt CL_TRACE_START_L1(); 140a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 141ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_profile (drv, 0, 0); 142ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->stats.tx_packets++; 143ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->stats.tx_bytes += skb->len; 144a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 145ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Allocate a TxCtrlBlk for the Tx packet and save timestamp, length and packet handle */ 146ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt pPktCtrlBlk = TWD_txCtrlBlk_Alloc (drv->tCommon.hTWD); 147a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 148ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt pPktCtrlBlk->tTxDescriptor.startTime = os_timeStampMs(drv); /* remove use of skb->tstamp.off_usec */ 149ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt pPktCtrlBlk->tTxDescriptor.length = skb->len; 150ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt pPktCtrlBlk->tTxPktParams.pInputPkt = skb; 151a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 152ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Point the first BDL buffer to the Ethernet header, and the second buffer to the rest of the packet */ 153ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt pPktCtrlBlk->tTxnStruct.aBuf[0] = skb->data; 154ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt pPktCtrlBlk->tTxnStruct.aLen[0] = ETHERNET_HDR_LEN; 155ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt pPktCtrlBlk->tTxnStruct.aBuf[1] = skb->data + ETHERNET_HDR_LEN; 156ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt pPktCtrlBlk->tTxnStruct.aLen[1] = (TI_UINT16)skb->len - ETHERNET_HDR_LEN; 157ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt pPktCtrlBlk->tTxnStruct.aLen[2] = 0; 158a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 159ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Send the packet to the driver for transmission. */ 160ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt status = txDataQ_InsertPacket (drv->tCommon.hTxDataQ, pPktCtrlBlk,(TI_UINT8)skb->priority); 161a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 162ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* If failed (queue full or driver not running), drop the packet. */ 163a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if (status != TI_OK) 164a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 165a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->stats.tx_errors++; 166a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 167ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_profile (drv, 1, 0); 168a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 169ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt CL_TRACE_END_L1("tiwlan_drv.ko", "OS", "TX", ""); 170a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 171ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return 0; 172a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 173a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/*--------------------------------------------------------------------------------------*/ 174a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 175a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_FreeTxPacket 176a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Free the OS Tx packet 177a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 178a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Free the OS Tx packet after driver processing is finished. 179a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 180a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 181a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param hOs - The OAL object handle 182a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param pPktCtrlBlk - The packet CtrlBlk 183a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param eStatus - The packet transmission status (OK/NOK) 184a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return void 185a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa 186a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 187a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/*--------------------------------------------------------------------------------------*/ 188a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 189a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtvoid wlanDrvIf_FreeTxPacket (TI_HANDLE hOs, TTxCtrlBlk *pPktCtrlBlk, TI_STATUS eStatus) 190a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 191a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt dev_kfree_skb((struct sk_buff *)pPktCtrlBlk->tTxPktParams.pInputPkt); 192a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 193a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 194a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 195a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_XmitDummy 196a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Dummy transmission handler 197a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 198a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * This function is registered at the network stack interface as the packets-transmission 199a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * handler (replacing wlanDrvIf_Xmit) when the driver is not operational. 200a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Using this dummy handler is more efficient then checking the driver state for every 201a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * packet transmission. 202a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 203a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 204a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param skb - The Linux packet buffer structure 205a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param dev - The driver network-interface handle 206a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return error 207a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa wlanDrvIf_Xmit 208a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 209a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic int wlanDrvIf_XmitDummy (struct sk_buff *skb, struct net_device *dev) 210a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 211ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Just return error. The driver is not running (network stack frees the packet) */ 212ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return -ENODEV; 213a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 214a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 215a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 216a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 217a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_NetGetStat 218a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Provides driver statistics 219a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 220a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Provides driver Tx and Rx statistics to network stack. 221a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 222a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 223a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param dev - The driver network-interface handle 224a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return The statistics pointer 225a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa 226a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 227a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic struct net_device_stats *wlanDrvIf_NetGetStat (struct net_device *dev) 228a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 229ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)NETDEV_GET_PRIVATE(dev); 230ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_OTHER, "wlanDrvIf_NetGetStat()\n"); 231ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt 232ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return &drv->stats; 233a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 234a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 235a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 236a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 237a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_UpdateDriverState 238a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Update the driver state 239a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 240a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * The DrvMain uses this function to update the OAL with the driver steady state 241a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * that is relevant for the driver users. 242a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 243a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 244a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param hOs - The driver object handle 245a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param eDriverState - The new driver state 246a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return void 247a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa 248a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 249a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtvoid wlanDrvIf_UpdateDriverState (TI_HANDLE hOs, EDriverSteadyState eDriverState) 250a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 251ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)hOs; 252a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 253ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf(TIWLAN_LOG_OTHER, "wlanDrvIf_UpdateDriverState(): State = %d\n", eDriverState); 254a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 255ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Save the new state */ 256ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->tCommon.eDriverState = eDriverState; 257a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 258ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* If the new state is not RUNNING, replace the Tx handler to a dummy one. */ 259ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (eDriverState != DRV_STATE_RUNNING) { 260ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#if (LINUX_VERSION_CODE <= KERNEL_VERSION(2, 6, 31)) 261ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->netdev->hard_start_xmit = wlanDrvIf_XmitDummy; 262ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#else 263ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->netdev->netdev_ops = &tiwlan_ops_dummy; 264ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 265ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 266a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 267a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 268a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 269a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 270a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_HandleInterrupt 271a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief The WLAN interrupt handler 272a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 273a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * The WLAN driver interrupt handler called in the interrupt context. 274a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * The actual handling is done in the driver's context after switching to the workqueue. 275a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 276a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 277a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param irq - The interrupt type 278a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param hDrv - The driver object handle 279a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param cpu_regs - The CPU registers 280a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return IRQ_HANDLED 281a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa 282a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 283a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtirqreturn_t wlanDrvIf_HandleInterrupt (int irq, void *hDrv, struct pt_regs *cpu_regs) 284a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 285ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)hDrv; 286a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 287ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWD_InterruptRequest (drv->tCommon.hTWD); 288a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 289ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return IRQ_HANDLED; 290a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 291a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 292a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 293a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 294a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn PollIrqHandler 295a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief WLAN IRQ polling handler - for debug! 296a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 297a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * A debug option to catch the WLAN events in polling instead of interrupts. 298a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * A timer calls this function periodically to check the interrupt status register. 299a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 300a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 301a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param parm - The driver object handle 302a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return void 303a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa 304a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 305a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#ifdef PRIODIC_INTERRUPT 306a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic void wlanDrvIf_PollIrqHandler (TI_HANDLE parm) 307a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 308ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)parm; 309a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 310ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt wlanDrvIf_HandleInterrupt (0, drv, NULL); 311ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_periodicIntrTimerStart (drv); 312a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 313a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 314a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 315a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 316a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 317a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_DriverTask 318a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief The driver task 319a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 320a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * This is the driver's task, where most of its job is done. 321a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * External contexts just save required information and schedule the driver's 322a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * task to continue the handling. 323a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * See more information in the context engine module (context.c). 324a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 325a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 326a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param hDrv - The driver object handle 327a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return void 328a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa 329ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt */ 330a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,23) 331a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic void wlanDrvIf_DriverTask (void *hDrv) 332a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 333ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)hDrv; 334a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#else 335a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic void wlanDrvIf_DriverTask(struct work_struct *work) 336a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 337ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifdef STACK_PROFILE 338ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt register unsigned long sp asm ("sp"); 339ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt unsigned long local_sp = sp; 340ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 341ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWlanDrvIfObj *drv = container_of(work, TWlanDrvIfObj, tWork); 342a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 343a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 344a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#ifdef STACK_PROFILE 345ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt unsigned long curr1, base1; 346ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt unsigned long curr2, base2; 347ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt static unsigned long maximum_stack = 0; 348a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 349ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_profile (drv, 0, 0); 350a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 351a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#ifdef STACK_PROFILE 352ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt curr1 = check_stack_start(&base1, local_sp + 4, 0); 353a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 354a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 355ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Call the driver main task */ 356ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt context_DriverTask (drv->tCommon.hContext); 357a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 358ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_profile (drv, 1, 0); 359ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_wake_lock_timeout(drv); 360ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_wake_unlock(drv); 361a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#ifdef STACK_PROFILE 362ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt curr2 = check_stack_stop(&base2, 0); 363ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (base2 == base1) { 364ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* if the current measurement is bigger then the maximum store it and print*/ 365ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if ((curr1 - curr2) > maximum_stack) { 366ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt printk("STACK PROFILER GOT THE LOCAL MAXIMMUM!!!! \n"); 367ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt printk("current operation stack use=%lu \n",(curr1 - curr2)); 368ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt printk("total stack use=%lu \n",8192 - curr2 + base2); 369ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt printk("total stack usage=%lu percent \n",100 * (8192 - curr2 + base2) / 8192); 370a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt maximum_stack = curr1 - curr2; 371ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 372ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 373a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 374a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 375a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 376a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 377a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 378a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_LoadFiles 379a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Load init files from loader 380a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 381a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * This function is called from the loader context right after the driver 382a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * is created (in IDLE state). 383a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * It copies the following files to the driver's memory: 384a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * - Ini-File - The driver's default parameters values 385a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * - NVS-File - The NVS data for FW usage 386a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * - FW-Image - The FW program image 387a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 388a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 389a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param drv - The driver object handle 390a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return void 391a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa wlanDrvIf_GetFile 392a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 393a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtint wlanDrvIf_LoadFiles (TWlanDrvIfObj *drv, TLoaderFilesData *pInitFiles) 394a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 395a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if (!pInitFiles) 396a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 397a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "No Init Files!\n"); 398a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return -EINVAL; 399a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 400a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 401a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if (drv->tCommon.eDriverState != DRV_STATE_IDLE) 402a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 403a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "Trying to load files not in IDLE state!\n"); 404a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return -EINVAL; 405a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 406a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 407a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if (pInitFiles->uIniFileLength) 408a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 409a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->tCommon.tIniFile.uSize = pInitFiles->uIniFileLength; 410a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->tCommon.tIniFile.pImage = kmalloc (pInitFiles->uIniFileLength, GFP_KERNEL); 411a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt #ifdef TI_MEM_ALLOC_TRACE 412a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt os_printf ("MTT:%s:%d ::kmalloc(%lu, %x) : %lu\n", __FUNCTION__, __LINE__, pInitFiles->uIniFileLength, GFP_KERNEL, pInitFiles->uIniFileLength); 413a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt #endif 414a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if (!drv->tCommon.tIniFile.pImage) 415a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 416a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "Cannot allocate buffer for Ini-File!\n"); 417a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return -ENOMEM; 418a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 419a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt memcpy (drv->tCommon.tIniFile.pImage, 420a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt &pInitFiles->data[pInitFiles->uNvsFileLength + pInitFiles->uFwFileLength], 421a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->tCommon.tIniFile.uSize); 422a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 423a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 424a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if (pInitFiles->uNvsFileLength) 425a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 426a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->tCommon.tNvsImage.uSize = pInitFiles->uNvsFileLength; 427a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->tCommon.tNvsImage.pImage = kmalloc (drv->tCommon.tNvsImage.uSize, GFP_KERNEL); 428a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt #ifdef TI_MEM_ALLOC_TRACE 429ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_printf ("MTT:%s:%d ::kmalloc(%lu, %x) : %lu\n", 430a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt __FUNCTION__, __LINE__, drv->tCommon.tNvsImage.uSize, GFP_KERNEL, drv->tCommon.tNvsImage.uSize); 431a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt #endif 432a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if (!drv->tCommon.tNvsImage.pImage) 433a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 434a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "Cannot allocate buffer for NVS image\n"); 435a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return -ENOMEM; 436a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 437a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt memcpy (drv->tCommon.tNvsImage.pImage, &pInitFiles->data[0], drv->tCommon.tNvsImage.uSize ); 438a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 439a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 440a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->tCommon.tFwImage.uSize = pInitFiles->uFwFileLength; 441a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if (!drv->tCommon.tFwImage.uSize) 442a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 443a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "No firmware image\n"); 444a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return -EINVAL; 445a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 446a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->tCommon.tFwImage.pImage = os_memoryAlloc (drv, drv->tCommon.tFwImage.uSize); 447a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt #ifdef TI_MEM_ALLOC_TRACE 448ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_printf ("MTT:%s:%d ::kmalloc(%lu, %x) : %lu\n", 449a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt __FUNCTION__, __LINE__, drv->tCommon.tFwImage.uSize, GFP_KERNEL, drv->tCommon.tFwImage.uSize); 450a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt #endif 451a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if (!drv->tCommon.tFwImage.pImage) 452a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 453a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt ti_dprintf(TIWLAN_LOG_ERROR, "Cannot allocate buffer for firmware image\n"); 454a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return -ENOMEM; 455a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 456a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt memcpy (drv->tCommon.tFwImage.pImage, 457a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt &pInitFiles->data[pInitFiles->uNvsFileLength], 458a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->tCommon.tFwImage.uSize); 459a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 460a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt ti_dprintf(TIWLAN_LOG_OTHER, "--------- Eeeprom=%p(%lu), Firmware=%p(%lu), IniFile=%p(%lu)\n", 461a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->tCommon.tNvsImage.pImage, drv->tCommon.tNvsImage.uSize, 462a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->tCommon.tFwImage.pImage, drv->tCommon.tFwImage.uSize, 463a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->tCommon.tIniFile.pImage, drv->tCommon.tIniFile.uSize); 464a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 465a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return 0; 466a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 467a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 468a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 469a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 470a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_GetFile 471a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Provides access to a requested init file 472a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 473a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Provide the requested file information and call the requester callback. 474a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Note that in Linux the files were previously loaded to driver memory 475a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * by the loader (see wlanDrvIf_LoadFiles). 476a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 477a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 478a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param hOs - The driver object handle 479a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param pFileInfo - The requested file's properties 480a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return TI_OK 481a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa wlanDrvIf_LoadFiles 482a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 483a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtint wlanDrvIf_GetFile (TI_HANDLE hOs, TFileInfo *pFileInfo) 484a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 4855d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)hOs; 486a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 487a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if (drv == NULL || pFileInfo == NULL) { 488a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt ti_dprintf(TIWLAN_LOG_ERROR, "wlanDrv_GetFile: ERROR: Null File Handler, Exiting"); 489a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return TI_NOK; 490a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 491a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 4925d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt /* Future option for getting the FW image part by part */ 4935d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt pFileInfo->hOsFileDesc = NULL; 4945d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt 4955d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt /* Fill the file's location and size in the file's info structure */ 4965d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt switch (pFileInfo->eFileType) 4975d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt { 4985d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt case FILE_TYPE_INI: 4995d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt pFileInfo->pBuffer = (TI_UINT8 *)drv->tCommon.tIniFile.pImage; 5005d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt pFileInfo->uLength = drv->tCommon.tIniFile.uSize; 5015d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt break; 5025d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt case FILE_TYPE_NVS: 5035d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt pFileInfo->pBuffer = (TI_UINT8 *)drv->tCommon.tNvsImage.pImage; 5045d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt pFileInfo->uLength = drv->tCommon.tNvsImage.uSize; 5055d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt break; 506a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt case FILE_TYPE_FW: 5075d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt if (drv->tCommon.tFwImage.pImage == NULL) 5085d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt { 5095d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt ti_dprintf(TIWLAN_LOG_ERROR, "wlanDrv_GetFile: ERROR: no Firmware image, exiting\n"); 5105d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt return TI_NOK; 5115d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt } 5125d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt 513a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->pBuffer = (TI_UINT8 *)drv->tCommon.tFwImage.pImage; 514a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->bLast = TI_FALSE; 515a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->uLength = 0; 516a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->uOffset = 0; 517a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->uChunkBytesLeft = 0; 518a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->uChunksLeft = BYTE_SWAP_LONG( *((TI_UINT32*)(pFileInfo->pBuffer)) ); 519a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* check uChunksLeft's Validity */ 520a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if (( pFileInfo->uChunksLeft == 0 ) || ( pFileInfo->uChunksLeft > MAX_CHUNKS_IN_FILE )) 521a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 522a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "wlanDrvIf_GetFile() Read Invalid Chunks Left: %d!\n",pFileInfo->uChunksLeft); 523a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return TI_NOK; 524a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 525a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->pBuffer += DRV_ADDRESS_SIZE; 526a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* FALL THROUGH */ 527a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt case FILE_TYPE_FW_NEXT: 528a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* check dec. validity */ 529a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if ( pFileInfo->uChunkBytesLeft >= pFileInfo->uLength ) 530a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 531a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->uChunkBytesLeft -= pFileInfo->uLength; 532a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 533a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* invalid Dec. */ 534a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt else 535a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 536a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "wlanDrvIf_GetFile() No. of Bytes Left < File Length\n"); 537a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return TI_NOK; 538a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 539a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->pBuffer += pFileInfo->uLength; 540a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 541a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* Finished reading all Previous Chunk */ 542a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if ( pFileInfo->uChunkBytesLeft == 0 ) 543a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 544a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* check dec. validity */ 545a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if ( pFileInfo->uChunksLeft > 0 ) 546a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 547a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->uChunksLeft--; 548a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 549a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* invalid Dec. */ 550a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt else 551a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 552a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "No. of Bytes Left = 0 and Chunks Left <= 0\n"); 553a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return TI_NOK; 554a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 555a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* read Chunk's address */ 556a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->uAddress = BYTE_SWAP_LONG( *((TI_UINT32*)(pFileInfo->pBuffer)) ); 557a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->pBuffer += DRV_ADDRESS_SIZE; 558a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* read Portion's length */ 559a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->uChunkBytesLeft = BYTE_SWAP_LONG( *((TI_UINT32*)(pFileInfo->pBuffer)) ); 560a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->pBuffer += DRV_ADDRESS_SIZE; 561a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 562a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* Reading Chunk is NOT complete */ 563a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt else 564a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 565a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->uAddress += pFileInfo->uLength; 566a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 567a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 568a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if ( pFileInfo->uChunkBytesLeft < OS_SPECIFIC_RAM_ALLOC_LIMIT ) 569a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 570a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->uLength = pFileInfo->uChunkBytesLeft; 571a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 572a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt else 573a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 574a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->uLength = OS_SPECIFIC_RAM_ALLOC_LIMIT; 575a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 576a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 577a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* If last chunk to download */ 578a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt if (( pFileInfo->uChunksLeft == 0 ) && 579a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt ( pFileInfo->uLength == pFileInfo->uChunkBytesLeft )) 580a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt { 581a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt pFileInfo->bLast = TI_TRUE; 582a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt } 583a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 5845d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt break; 5855d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt } 586a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 5875d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt /* Call the requester callback */ 5885d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt if (pFileInfo->fCbFunc) 5895d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt { 5905d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt pFileInfo->fCbFunc (pFileInfo->hCbHndl); 5915d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt } 592a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 5935d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt return TI_OK; 594a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 595a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 596a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 597a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 598a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_SetMacAddress 599a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Set STA MAC address 600a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 601a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Called by DrvMain from init process. 602a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Copies STA MAC address to the network interface structure. 603a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 604a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 605a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param hOs - The driver object handle 606a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param pMacAddr - The STA MAC address 607a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return TI_OK 608a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa wlanDrvIf_LoadFiles 609a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 610a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtvoid wlanDrvIf_SetMacAddress (TI_HANDLE hOs, TI_UINT8 *pMacAddr) 611a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 612ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)hOs; 613a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 614ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Copy STA MAC address to the network interface structure */ 615ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt MAC_COPY (drv->netdev->dev_addr, pMacAddr); 616a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 617a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 618a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 619a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 620a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_Start 621a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Start driver 622a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 623a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Called by network stack upon opening network interface (ifconfig up). 624a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Can also be called from user application or CLI for flight mode. 625a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Start the driver initialization process up to OPERATIONAL state. 626a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 627a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 628a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param dev - The driver network-interface handle 629a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return 0 if succeeded, error if driver not available 630a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa wlanDrvIf_Stop 631a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 632a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtint wlanDrvIf_Start (struct net_device *dev) 633a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 634ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)NETDEV_GET_PRIVATE(dev); 6355d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt int status; 636a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 637ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_OTHER, "wlanDrvIf_Start()\n"); 638ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt printk("%s\n", __func__); 639005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt if (!drv->tCommon.hDrvMain) 640005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt { 641ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "wlanDrvIf_Start() Driver not created!\n"); 642ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return -ENODEV; 643ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 644a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 6455d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt if (DRV_STATE_FAILED == drv->tCommon.eDriverState) 6465d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt { 6475d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "wlanDrvIf_Start() Driver failed!\n"); 6485d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt return -ENODEV; 6495d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt } 6505d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt 651ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* 652ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt * Insert Start command in DrvMain action queue, request driver scheduling 653ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt * and wait for action completion (all init process). 654ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt */ 655ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_wake_lock_timeout_enable(drv); 6565d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt status = drvMain_InsertAction (drv->tCommon.hDrvMain, ACTION_TYPE_START); 6575d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt return (status) ? -1 : 0; 658a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 659a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 660a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtint wlanDrvIf_Open (struct net_device *dev) 661a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 662ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)NETDEV_GET_PRIVATE(dev); 6635d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt int status = 0; 664a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 665ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_OTHER, "wlanDrvIf_Open()\n"); 666ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt printk("%s\n", __func__); 667ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (!drv->tCommon.hDrvMain) { 668ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "wlanDrvIf_Open() Driver not created!\n"); 669ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return -ENODEV; 670ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 671a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 6725d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt if (drv->tCommon.eDriverState == DRV_STATE_STOPPED || 6735d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt drv->tCommon.eDriverState == DRV_STATE_IDLE) { 6745d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt status = wlanDrvIf_Start(dev); 6755d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt } 676a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 677ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* 678ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt * Finalize network interface setup 679ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt */ 680ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#if (LINUX_VERSION_CODE <= KERNEL_VERSION(2, 6, 31)) 681ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->netdev->hard_start_xmit = wlanDrvIf_Xmit; 682ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#else 683ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->netdev->netdev_ops = &tiwlan_ops_pri; 684a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 685ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->netdev->addr_len = MAC_ADDR_LEN; 686ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt netif_start_queue (dev); 687a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 688ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* register 3430 PM hooks in our SDIO driver */ 689ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifdef TI_CONFIG_PM_HOOKS 690ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifndef CONFIG_MMC_EMBEDDED_SDIO 691ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt sdioDrv_register_pm(wlanDrvIf_pm_resume, wlanDrvIf_pm_suspend); 692ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 693ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 6945d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt return status; 695a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 696a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 697a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 698a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_Stop 699a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Stop driver 700a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 701a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Called by network stack upon closing network interface (ifconfig down). 702a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Can also be called from user application or CLI for flight mode. 703a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Stop the driver and turn off the device. 704a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 705a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 706a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param dev - The driver network-interface handle 707a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return 0 (OK) 708a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa wlanDrvIf_Start 709a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 710a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtint wlanDrvIf_Stop (struct net_device *dev) 711a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 712ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)NETDEV_GET_PRIVATE(dev); 713ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt 714ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_OTHER, "wlanDrvIf_Stop()\n"); 715ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt printk("%s\n", __func__); 7165d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt 7175d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt if (DRV_STATE_FAILED == drv->tCommon.eDriverState) 7185d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt { 7195d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt return -ENODEV; 7205d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt } 7215d969c3c4738de33d100a514cc06079c1fdaa0e7Dmitry Shmidt 722ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* 723ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt * Insert Stop command in DrvMain action queue, request driver scheduling 724ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt * and wait for Stop process completion. 725ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt */ 726ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_wake_lock_timeout_enable(drv); 727ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drvMain_InsertAction (drv->tCommon.hDrvMain, ACTION_TYPE_STOP); 728ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return 0; 729a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 730a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 731a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtint wlanDrvIf_Release (struct net_device *dev) 732a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 733ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* TWlanDrvIfObj *drv = (TWlanDrvIfObj *)NETDEV_GET_PRIVATE(dev); */ 734a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 735ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_OTHER, "wlanDrvIf_Release()\n"); 736ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt printk("%s\n", __func__); 737ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Disable network interface queue */ 738ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt netif_stop_queue (dev); 739ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return 0; 740a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 741a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 742a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/* 3430 PM hooks */ 743ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifdef TI_CONFIG_PM_HOOKS 744a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic int wlanDrvIf_pm_resume(void) 745a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 746a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return(wlanDrvIf_Open(pDrvStaticHandle->netdev)); 747a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 748a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 749a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic int wlanDrvIf_pm_suspend(void) 750a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 751a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt wlanDrvIf_Release(pDrvStaticHandle->netdev); 752a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt return(wlanDrvIf_Stop(pDrvStaticHandle->netdev)); 753a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 754a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 755a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 756a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 757a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_SetupNetif 758a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Setup driver network interface 759a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 760a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Called in driver creation process. 761a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Setup driver network interface. 762a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 763a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 764a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param drv - The driver object handle 765a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return 0 - OK, else - failure 766a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa 767a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 768a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic int wlanDrvIf_SetupNetif (TWlanDrvIfObj *drv) 769a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 770ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt struct net_device *dev; 771ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt int res; 772ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt 773ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Allocate network interface structure for the driver */ 774ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt dev = alloc_etherdev (0); 775005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt if (dev == NULL) 776005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt { 777ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "alloc_etherdev() failed\n"); 778ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return -ENOMEM; 779ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 780a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 781ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Setup the network interface */ 782ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ether_setup (dev); 783a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 784ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt NETDEV_SET_PRIVATE(dev,drv); 785ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->netdev = dev; 786ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt strcpy (dev->name, TIWLAN_DRV_IF_NAME); 787ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt netif_carrier_off (dev); 788ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#if (LINUX_VERSION_CODE <= KERNEL_VERSION(2, 6, 31)) 789a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/* the following is required on at least BSP 23.8 and higher. 790a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt Without it, the Open function of the driver will not be called 791a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt when trying to 'ifconfig up' the interface */ 792a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,23) 793ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt dev->validate_addr = NULL; 794ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 795ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt dev->open = wlanDrvIf_Open; 796ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt dev->stop = wlanDrvIf_Release; 797ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt dev->hard_start_xmit = wlanDrvIf_XmitDummy; 798ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt dev->get_stats = wlanDrvIf_NetGetStat; 799ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt dev->do_ioctl = NULL; 800ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#else 801ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt dev->netdev_ops = &tiwlan_ops_dummy; 802a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 803ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt dev->tx_queue_len = 100; 804a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 805ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Initialize Wireless Extensions interface (WEXT) */ 806ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt wlanDrvWext_Init (dev); 807a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 808ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt res = register_netdev (dev); 809005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt if (res != 0) 810005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt { 811ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "register_netdev() failed : %d\n", res); 812ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt kfree (dev); 813ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return res; 814ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 815a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/* 816a615fb1650af6e111053506f1b764b28a5b4631dDmitry ShmidtOn the latest Kernel there is no more support for the below macro. 817a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt*/ 818a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,24) 819ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt SET_MODULE_OWNER (dev); 820a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 821ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return 0; 822a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 823a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 824a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 825a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_CommandDone 826a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Free current command semaphore. 827a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 828a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * This routine is called whenever a command has finished executing and Free current command semaphore. 829a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 830a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 831a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param hOs - The driver object handle 832a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param pSignalObject - handle to complete mechanism per OS 833a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param CmdResp_p - respond structure (TCmdRespUnion) for OSE OS only 834a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return 0 - OK, else - failure 835a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa wlanDrvIf_Destroy 836a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 837a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtvoid wlanDrvIf_CommandDone (TI_HANDLE hOs, void *pSignalObject, TI_UINT8 *CmdResp_p) 838a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 839ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Free semaphore */ 840ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_SignalObjectSet (hOs, pSignalObject); 841a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 842a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 843a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 844a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 845a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_Create 846a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Create the driver instance 847a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 848a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Allocate driver object. 849a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Initialize driver OS resources (IRQ, workqueue, events socket) 850a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Setup driver network interface. 851a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Create and link all driver modules. 852a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 853a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 854a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param void 855a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return 0 - OK, else - failure 856a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa wlanDrvIf_Destroy 857a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 858a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic int wlanDrvIf_Create (void) 859a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 860ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt TWlanDrvIfObj *drv; /* Dm: Failure is not cleaned properly !!! */ 861ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt int rc; 862a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 863ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Allocate driver's structure */ 864ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv = kmalloc (sizeof(TWlanDrvIfObj), GFP_KERNEL); 865005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt if (!drv) 866005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt { 867ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return -ENOMEM; 868ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 869a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#ifdef TI_DBG 870a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt tb_init(TB_OPTION_NONE); 871a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 872ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt pDrvStaticHandle = drv; /* save for module destroy */ 873ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifdef TI_MEM_ALLOC_TRACE 874ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_printf ("MTT:%s:%d ::kmalloc(%lu, %x) : %lu\n", __FUNCTION__, __LINE__, sizeof(TWlanDrvIfObj), GFP_KERNEL, sizeof(TWlanDrvIfObj)); 875ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 876ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt memset (drv, 0, sizeof(TWlanDrvIfObj)); 877a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 878ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Dm: drv->irq = TNETW_IRQ; */ 879ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->tCommon.eDriverState = DRV_STATE_IDLE; 880a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 881ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->tiwlan_wq = create_freezeable_workqueue(DRIVERWQ_NAME); 882ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (!drv->tiwlan_wq) { 883ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "wlanDrvIf_Create(): Failed to create workQ!\n"); 884ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt rc = -EINVAL; 885ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt goto drv_create_end_1; 886ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 887ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->wl_packet = 0; 888ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->wl_count = 0; 889a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#ifdef CONFIG_HAS_WAKELOCK 890ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt wake_lock_init(&drv->wl_wifi, WAKE_LOCK_SUSPEND, "wifi_wake"); 891ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt wake_lock_init(&drv->wl_rxwake, WAKE_LOCK_SUSPEND, "wifi_rx_wake"); 892a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 893a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,23) 894ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt INIT_WORK(&drv->tWork, wlanDrvIf_DriverTask, (void *)drv); 895a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#else 896ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt INIT_WORK(&drv->tWork, wlanDrvIf_DriverTask); 897a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 898ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt spin_lock_init (&drv->lock); 899a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 900ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Setup driver network interface. */ 901ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt rc = wlanDrvIf_SetupNetif (drv); 902ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (rc) { 903ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt goto drv_create_end_2; 904ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 905a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 906ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Create the events socket interface */ 907a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,23) 908a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt drv->wl_sock = netlink_kernel_create( NETLINK_USERSOCK, 0, NULL, THIS_MODULE ); 909a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#else 910ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->wl_sock = netlink_kernel_create(&init_net, NETLINK_USERSOCK, 0, NULL, NULL, THIS_MODULE ); 911a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 912ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (drv->wl_sock == NULL) { 913ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "netlink_kernel_create() failed !\n"); 914ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt rc = -EINVAL; 915ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt goto drv_create_end_3; 916ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 917a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 918ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Create all driver modules and link their handles */ 919ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt rc = drvMain_Create (drv, 920ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt &drv->tCommon.hDrvMain, 921ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt &drv->tCommon.hCmdHndlr, 922ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt &drv->tCommon.hContext, 923ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt &drv->tCommon.hTxDataQ, 924ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt &drv->tCommon.hTxMgmtQ, 925ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt &drv->tCommon.hTxCtrl, 926ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt &drv->tCommon.hTWD, 927a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt &drv->tCommon.hEvHandler, 928a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt &drv->tCommon.hCmdDispatch, 929ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt &drv->tCommon.hReport); 930ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (rc != TI_OK) { 931ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "%s: Failed to dvrMain_Create!\n", __func__); 932ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt rc = -EINVAL; 933ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt goto drv_create_end_4; 934ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 935ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* 936ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt * Initialize interrupts (or polling mode for debug): 937ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt */ 938a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#ifdef PRIODIC_INTERRUPT 939ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Debug mode: Polling (the timer is started by HwInit process) */ 940ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drv->hPollTimer = os_timerCreate ((TI_HANDLE)drv, wlanDrvIf_PollIrqHandler, (TI_HANDLE)drv); 941a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#else 942ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Normal mode: Interrupts (the default mode) */ 943ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt rc = hPlatform_initInterrupt (drv, (void*)wlanDrvIf_HandleInterrupt); 944ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (rc) { 945ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt ti_dprintf (TIWLAN_LOG_ERROR, "wlanDrvIf_Create(): Failed to register interrupt handler!\n"); 946ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt goto drv_create_end_5; 947ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 948a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif /* PRIODIC_INTERRUPT */ 949ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return 0; 950ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtdrv_create_end_5: 951ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Destroy all driver modules */ 952ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (drv->tCommon.hDrvMain) { 953ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drvMain_Destroy (drv->tCommon.hDrvMain); 954ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 955ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtdrv_create_end_4: 956ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (drv->wl_sock) { 957ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt sock_release (drv->wl_sock->sk_socket); 958ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 959ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt 960ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtdrv_create_end_3: 961ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Release the driver network interface */ 962ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (drv->netdev) { 963ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt unregister_netdev (drv->netdev); 964ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt free_netdev (drv->netdev); 965ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 966ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt 967ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtdrv_create_end_2: 968ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifdef CONFIG_HAS_WAKELOCK 969ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt wake_lock_destroy(&drv->wl_wifi); 970ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt wake_lock_destroy(&drv->wl_rxwake); 971ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 972ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (drv->tiwlan_wq) 973ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt destroy_workqueue(drv->tiwlan_wq); 974a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 975ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtdrv_create_end_1: 976ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt kfree(drv); 977ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt printk("%s: Fail\n", __func__); 978ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return rc; 979a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 980a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 981a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 982a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 983a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_Destroy 984a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Destroy the driver instance 985a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 986a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Destroy all driver modules. 987a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Release driver OS resources (IRQ, workqueue, events socket) 988a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Release driver network interface. 989a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Free init files memory. 990a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * Free driver object. 991a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 992a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 993a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param drv - The driver object handle 994a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return void 995a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa wlanDrvIf_Create 996a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 997a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic void wlanDrvIf_Destroy (TWlanDrvIfObj *drv) 998a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 999ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (!drv) 1000ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return; 1001a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1002ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (drv->tiwlan_wq) { 1003ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt cancel_work_sync(&drv->tWork); 1004ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt flush_workqueue(drv->tiwlan_wq); 1005ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 1006a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1007ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Release the driver network interface */ 1008ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (drv->netdev) { 1009ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt netif_stop_queue (drv->netdev); 1010ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt wlanDrvIf_Stop (drv->netdev); 1011ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt unregister_netdev (drv->netdev); 1012ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt free_netdev (drv->netdev); 1013ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 1014a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1015a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* Destroy all driver modules */ 1016ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (drv->tCommon.hDrvMain) { 1017ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt drvMain_Destroy (drv->tCommon.hDrvMain); 1018ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 1019a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1020ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* close the ipc_kernel socket*/ 1021005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt if (drv && drv->wl_sock) 1022005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt { 1023ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt sock_release (drv->wl_sock->sk_socket); 1024ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 1025ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* Release the driver interrupt (or polling timer) */ 1026a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#ifdef PRIODIC_INTERRUPT 1027ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt os_timerDestroy (drv, drv->hPollTimer); 1028a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#else 1029005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt if (drv->irq) 1030005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt { 1031ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt hPlatform_freeInterrupt(drv); 1032ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt } 1033a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 1034ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt if (drv->tiwlan_wq) 1035ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt destroy_workqueue(drv->tiwlan_wq); 1036a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1037a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#ifdef CONFIG_HAS_WAKELOCK 1038ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt wake_lock_destroy(&drv->wl_wifi); 1039ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt wake_lock_destroy(&drv->wl_rxwake); 1040a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#endif 1041ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt /* 1042ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt * Free init files memory 1043ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt */ 1044005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt if (drv->tCommon.tFwImage.pImage) 1045005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt { 1046005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt os_memoryFree (drv, drv->tCommon.tFwImage.pImage, drv->tCommon.tFwImage.uSize); 1047005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt #ifdef TI_MEM_ALLOC_TRACE 1048005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt os_printf ("MTT:%s:%d ::kfree(0x%p) : %d\n", 1049005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt __FUNCTION__, __LINE__, drv->tCommon.tFwImage.uSize, -drv->tCommon.tFwImage.uSize); 1050005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt #endif 1051005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt } 1052005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt if (drv->tCommon.tNvsImage.pImage) 1053005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt { 1054005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt kfree (drv->tCommon.tNvsImage.pImage); 1055005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt #ifdef TI_MEM_ALLOC_TRACE 1056005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt os_printf ("MTT:%s:%d ::kfree(0x%p) : %d\n", 1057005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt __FUNCTION__, __LINE__, drv->tCommon.tNvsImage.uSize, -drv->tCommon.tNvsImage.uSize); 1058005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt #endif 1059005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt } 1060005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt if (drv->tCommon.tIniFile.pImage) 1061005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt { 1062005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt kfree (drv->tCommon.tIniFile.pImage); 1063005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt #ifdef TI_MEM_ALLOC_TRACE 1064005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt os_printf ("MTT:%s:%d ::kfree(0x%p) : %d\n", 1065005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt __FUNCTION__, __LINE__, drv->tCommon.tIniFile.uSize, -drv->tCommon.tIniFile.uSize); 1066005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt #endif 1067005bbf20350954d05c8a111d3f487d6fddb049bbDmitry Shmidt } 1068a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1069a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt /* Free the driver object */ 1070a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt#ifdef TI_DBG 1071a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt tb_destroy(); 1072ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 1073ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt kfree (drv); 1074a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 1075a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1076a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1077a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 1078a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_ModuleInit & wlanDrvIf_ModuleExit 1079a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Linux Init/Exit functions 1080a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 1081a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * The driver Linux Init/Exit functions (insmod/rmmod) 1082a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 1083a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 1084a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param void 1085a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return Init: 0 - OK, else - failure. Exit: void 1086a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa wlanDrvIf_Create, wlanDrvIf_Destroy 1087a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 1088ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifndef TI_SDIO_STANDALONE 1089ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtstatic int sdc_ctrl = 2; 1090ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtmodule_param(sdc_ctrl, int, S_IRUGO | S_IWUSR | S_IWGRP); 1091ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt 1092ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtextern int sdioDrv_init(int sdcnum); 1093ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidtextern void sdioDrv_exit(void); 1094ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 1095ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt 1096a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic int __init wlanDrvIf_ModuleInit (void) 1097a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 1098ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt printk(KERN_INFO "TIWLAN: driver init\n"); 1099ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifndef TI_SDIO_STANDALONE 1100ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifndef CONFIG_MMC_EMBEDDED_SDIO 1101ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt sdioDrv_init(sdc_ctrl); 1102ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 1103ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 1104ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt return wlanDrvIf_Create (); 1105a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 1106a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1107a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtstatic void __exit wlanDrvIf_ModuleExit (void) 1108a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 1109ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt wlanDrvIf_Destroy (pDrvStaticHandle); 1110ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifndef TI_SDIO_STANDALONE 1111ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#ifndef CONFIG_MMC_EMBEDDED_SDIO 1112ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt sdioDrv_exit(); 1113ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 1114ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt#endif 1115ddac9c138c5b4b16b99fb8bc5f0f10418efa1029Dmitry Shmidt printk (KERN_INFO "TI WLAN: driver unloaded\n"); 1116a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 1117a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1118a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1119a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 1120a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_StopTx 1121a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief block Tx thread until wlanDrvIf_ResumeTx called . 1122a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 1123a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * This routine is called whenever we need to stop the network stack to send us pakets since one of our Q's is full. 1124a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 1125a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 1126a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param hOs - The driver object handle 1127a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt* \return 1128a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa wlanDrvIf_StopTx 1129a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 1130a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtvoid wlanDrvIf_StopTx (TI_HANDLE hOs) 1131a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 1132a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)hOs; 1133a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1134a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt netif_stop_queue (drv->netdev); 1135a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 1136a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1137a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt/** 1138a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \fn wlanDrvIf_ResumeTx 1139a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \brief Resume Tx thread . 1140a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 1141a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * This routine is called whenever we need to resume the network stack to send us pakets since our Q's are empty. 1142a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * 1143a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \note 1144a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \param hOs - The driver object handle 1145a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \return 1146a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt * \sa wlanDrvIf_ResumeTx 1147a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt */ 1148a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtvoid wlanDrvIf_ResumeTx (TI_HANDLE hOs) 1149a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt{ 1150a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt TWlanDrvIfObj *drv = (TWlanDrvIfObj *)hOs; 1151a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1152a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt netif_wake_queue (drv->netdev); 1153a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt} 1154a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidt 1155a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtmodule_init (wlanDrvIf_ModuleInit); 1156a615fb1650af6e111053506f1b764b28a5b4631dDmitry Shmidtmodule_exit (wlanDrvIf_ModuleExit); 1157