Enscript Output

extractedLnx/linux-2.6.38/drivers/staging/ath6kl/os/linux/ioctl.c_ar6000_ioctl.c

int ar6000_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
{
    AR_SOFTC_T *ar = (AR_SOFTC_T *)ar6k_priv(dev);
    HIF_DEVICE *hifDevice = ar->arHifDevice;
    int ret = 0, param;
    unsigned int address = 0;
    unsigned int length = 0;
    unsigned char *buffer;
    char *userdata;
    A_UINT32 connectCtrlFlags;


    WMI_SET_AKMP_PARAMS_CMD  akmpParams;
    WMI_SET_PMKID_LIST_CMD   pmkidInfo;

    WMI_SET_HT_CAP_CMD htCap;
    WMI_SET_HT_OP_CMD htOp;

    /*
     * ioctl operations may have to wait for the Target, so we cannot hold rtnl.
     * Prevent the device from disappearing under us and release the lock during
     * the ioctl operation.
     */
    dev_hold(dev);
    rtnl_unlock();

    if (cmd == AR6000_IOCTL_EXTENDED) {
        /*
         * This allows for many more wireless ioctls than would otherwise
         * be available.  Applications embed the actual ioctl command in
         * the first word of the parameter block, and use the command
         * AR6000_IOCTL_EXTENDED_CMD on the ioctl call.
         */
	if (get_user(cmd, (int *)rq->ifr_data)) {
	    ret = -EFAULT;
	    goto ioctl_done;
	}
        userdata = (char *)(((unsigned int *)rq->ifr_data)+1);
        if(is_xioctl_allowed(ar->arNextMode, cmd) != A_OK) {
            A_PRINTF("xioctl: cmd=%d not allowed in this mode\n",cmd);
            ret = -EOPNOTSUPP;
            goto ioctl_done;
    }
    } else {
        A_STATUS ret = is_iwioctl_allowed(ar->arNextMode, cmd);
        if(ret == A_ENOTSUP) {
            A_PRINTF("iwioctl: cmd=0x%x not allowed in this mode\n", cmd);
            ret = -EOPNOTSUPP;
            goto ioctl_done;
        } else if (ret == A_ERROR) {
            /* It is not our ioctl (out of range ioctl) */
            ret = -EOPNOTSUPP;
            goto ioctl_done;
        }
        userdata = (char *)rq->ifr_data;
    }

    if ((ar->arWlanState == WLAN_DISABLED) &&
        ((cmd != AR6000_XIOCTRL_WMI_SET_WLAN_STATE) &&
         (cmd != AR6000_XIOCTL_GET_WLAN_SLEEP_STATE) &&
         (cmd != AR6000_XIOCTL_DIAG_READ) &&
         (cmd != AR6000_XIOCTL_DIAG_WRITE) &&
         (cmd != AR6000_XIOCTL_SET_BT_HW_POWER_STATE) &&
         (cmd != AR6000_XIOCTL_GET_BT_HW_POWER_STATE) &&
         (cmd != AR6000_XIOCTL_ADD_AP_INTERFACE) &&
         (cmd != AR6000_XIOCTL_REMOVE_AP_INTERFACE) &&
         (cmd != AR6000_IOCTL_WMI_GETREV)))
    {
        ret = -EIO;
        goto ioctl_done;
    }

    ret = 0;
    switch(cmd)
    {
        case IEEE80211_IOCTL_SETPARAM:
        {
            int param, value;
            int *ptr = (int *)rq->ifr_ifru.ifru_newname;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else {
                param = *ptr++;
                value = *ptr;
                ret = ar6000_ioctl_setparam(ar,param,value);
            }
            break;
        }
        case IEEE80211_IOCTL_SETKEY:
        {
            struct ieee80211req_key keydata;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&keydata, userdata,
                            sizeof(struct ieee80211req_key))) {
                ret = -EFAULT;
            } else {
                ar6000_ioctl_setkey(ar, &keydata);
            }
            break;
        }
        case IEEE80211_IOCTL_DELKEY:
        case IEEE80211_IOCTL_SETOPTIE:
        {
            //ret = -EIO;
            break;
        }
        case IEEE80211_IOCTL_SETMLME:
        {
            struct ieee80211req_mlme mlme;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&mlme, userdata,
                            sizeof(struct ieee80211req_mlme))) {
                ret = -EFAULT;
            } else {
                switch (mlme.im_op) {
                    case IEEE80211_MLME_AUTHORIZE:
                        A_PRINTF("setmlme AUTHORIZE %02X:%02X\n",
                            mlme.im_macaddr[4], mlme.im_macaddr[5]);
                        break;
                    case IEEE80211_MLME_UNAUTHORIZE:
                        A_PRINTF("setmlme UNAUTHORIZE %02X:%02X\n",
                            mlme.im_macaddr[4], mlme.im_macaddr[5]);
                        break;
                    case IEEE80211_MLME_DEAUTH:
                        A_PRINTF("setmlme DEAUTH %02X:%02X\n",
                            mlme.im_macaddr[4], mlme.im_macaddr[5]);
                        //remove_sta(ar, mlme.im_macaddr);
                        break;
                    case IEEE80211_MLME_DISASSOC:
                        A_PRINTF("setmlme DISASSOC %02X:%02X\n",
                            mlme.im_macaddr[4], mlme.im_macaddr[5]);
                        //remove_sta(ar, mlme.im_macaddr);
                        break;
                    default:
                        ret = 0;
                        goto ioctl_done;
                }

                wmi_ap_set_mlme(ar->arWmi, mlme.im_op, mlme.im_macaddr,
                                mlme.im_reason);
            }
            break;
        }
        case IEEE80211_IOCTL_ADDPMKID:
        {
            struct ieee80211req_addpmkid  req;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&req, userdata, sizeof(struct ieee80211req_addpmkid))) {
                ret = -EFAULT;
            } else {
                A_STATUS status;

                AR_DEBUG_PRINTF(ATH_DEBUG_WLAN_CONNECT,("Add pmkid for %2.2x:%2.2x:%2.2x:%2.2x:%2.2x:%2.2x en=%d\n",
                    req.pi_bssid[0], req.pi_bssid[1], req.pi_bssid[2],
                    req.pi_bssid[3], req.pi_bssid[4], req.pi_bssid[5],
                    req.pi_enable));

                status = wmi_setPmkid_cmd(ar->arWmi, req.pi_bssid, req.pi_pmkid,
                              req.pi_enable);

                if (status != A_OK) {
                    ret = -EIO;
                    goto ioctl_done;
                }
            }
            break;
        }
#ifdef CONFIG_HOST_TCMD_SUPPORT
        case AR6000_XIOCTL_TCMD_CONT_TX:
            {
                TCMD_CONT_TX txCmd;

                if ((ar->tcmdPm == TCMD_PM_SLEEP) ||
                    (ar->tcmdPm == TCMD_PM_DEEPSLEEP))
                {
                    A_PRINTF("Can NOT send tx tcmd when target is asleep! \n");
                    ret = -EFAULT;
                    goto ioctl_done;
                }

                if(copy_from_user(&txCmd, userdata, sizeof(TCMD_CONT_TX))) {
                    ret = -EFAULT;
                    goto ioctl_done;
                } else {
                    wmi_test_cmd(ar->arWmi,(A_UINT8 *)&txCmd, sizeof(TCMD_CONT_TX));
                }
            }
            break;
        case AR6000_XIOCTL_TCMD_CONT_RX:
            {
                TCMD_CONT_RX rxCmd;

                if ((ar->tcmdPm == TCMD_PM_SLEEP) ||
                    (ar->tcmdPm == TCMD_PM_DEEPSLEEP))
                {
                    A_PRINTF("Can NOT send rx tcmd when target is asleep! \n");
                    ret = -EFAULT;
                    goto ioctl_done;
                }
                if(copy_from_user(&rxCmd, userdata, sizeof(TCMD_CONT_RX))) {
                    ret = -EFAULT;
                    goto ioctl_done;
                }

                switch(rxCmd.act)
                {
                    case TCMD_CONT_RX_PROMIS:
                    case TCMD_CONT_RX_FILTER:
                    case TCMD_CONT_RX_SETMAC:
                    case TCMD_CONT_RX_SET_ANT_SWITCH_TABLE:
                         wmi_test_cmd(ar->arWmi,(A_UINT8 *)&rxCmd,
                                                sizeof(TCMD_CONT_RX));
                         tcmdRxFreq = rxCmd.u.para.freq;
                         break;
                    case TCMD_CONT_RX_REPORT:
                         ar6000_ioctl_tcmd_get_rx_report(dev, rq,
                         (A_UINT8 *)&rxCmd, sizeof(TCMD_CONT_RX));
                         break;
                    default:
                         A_PRINTF("Unknown Cont Rx mode: %d\n",rxCmd.act);
                         ret = -EINVAL;
                         goto ioctl_done;
                }
            }
            break;
        case AR6000_XIOCTL_TCMD_PM:
            {
                TCMD_PM pmCmd;

                if(copy_from_user(&pmCmd, userdata, sizeof(TCMD_PM))) {
                    ret = -EFAULT;
                    goto ioctl_done;
                }
                ar->tcmdPm = pmCmd.mode;
                wmi_test_cmd(ar->arWmi, (A_UINT8*)&pmCmd, sizeof(TCMD_PM));
            }
            break;
#endif /* CONFIG_HOST_TCMD_SUPPORT */

        case AR6000_XIOCTL_BMI_DONE:
            if(bmienable)
            {
                rtnl_lock(); /* ar6000_init expects to be called holding rtnl lock */
                ret = ar6000_init(dev);
                rtnl_unlock();
            }
            else
            {
                ret = BMIDone(hifDevice);
            }
            break;

        case AR6000_XIOCTL_BMI_READ_MEMORY:
	     if (get_user(address, (unsigned int *)userdata) ||
		get_user(length, (unsigned int *)userdata + 1)) {
		ret = -EFAULT;
		break;
	    }

            AR_DEBUG_PRINTF(ATH_DEBUG_INFO,("Read Memory (address: 0x%x, length: %d)\n",
                             address, length));
            if ((buffer = (unsigned char *)A_MALLOC(length)) != NULL) {
                A_MEMZERO(buffer, length);
                ret = BMIReadMemory(hifDevice, address, buffer, length);
                if (copy_to_user(rq->ifr_data, buffer, length)) {
                    ret = -EFAULT;
                }
                A_FREE(buffer);
            } else {
                ret = -ENOMEM;
            }
            break;

        case AR6000_XIOCTL_BMI_WRITE_MEMORY:
	     if (get_user(address, (unsigned int *)userdata) ||
		get_user(length, (unsigned int *)userdata + 1)) {
		ret = -EFAULT;
		break;
	    }
            AR_DEBUG_PRINTF(ATH_DEBUG_INFO,("Write Memory (address: 0x%x, length: %d)\n",
                             address, length));
            if ((buffer = (unsigned char *)A_MALLOC(length)) != NULL) {
                A_MEMZERO(buffer, length);
                if (copy_from_user(buffer, &userdata[sizeof(address) +
                                   sizeof(length)], length))
                {
                    ret = -EFAULT;
                } else {
                    ret = BMIWriteMemory(hifDevice, address, buffer, length);
                }
                A_FREE(buffer);
            } else {
                ret = -ENOMEM;
            }
            break;

        case AR6000_XIOCTL_BMI_TEST:
           AR_DEBUG_PRINTF(ATH_DEBUG_ERR,("No longer supported\n"));
           ret = -EOPNOTSUPP;
           break;

        case AR6000_XIOCTL_BMI_EXECUTE:
	     if (get_user(address, (unsigned int *)userdata) ||
		get_user(param, (unsigned int *)userdata + 1)) {
		ret = -EFAULT;
		break;
	    }
            AR_DEBUG_PRINTF(ATH_DEBUG_INFO,("Execute (address: 0x%x, param: %d)\n",
                             address, param));
            ret = BMIExecute(hifDevice, address, (A_UINT32*)&param);
	    /* return value */
	    if (put_user(param, (unsigned int *)rq->ifr_data)) {
		ret = -EFAULT;
		break;
	    }
            break;

        case AR6000_XIOCTL_BMI_SET_APP_START:
	    if (get_user(address, (unsigned int *)userdata)) {
		ret = -EFAULT;
		break;
	    }
            AR_DEBUG_PRINTF(ATH_DEBUG_INFO,("Set App Start (address: 0x%x)\n", address));
            ret = BMISetAppStart(hifDevice, address);
            break;

        case AR6000_XIOCTL_BMI_READ_SOC_REGISTER:
	    if (get_user(address, (unsigned int *)userdata)) {
		ret = -EFAULT;
		break;
	    }
            ret = BMIReadSOCRegister(hifDevice, address, (A_UINT32*)&param);
	    /* return value */
	    if (put_user(param, (unsigned int *)rq->ifr_data)) {
		ret = -EFAULT;
		break;
	    }
            break;

        case AR6000_XIOCTL_BMI_WRITE_SOC_REGISTER:
	    if (get_user(address, (unsigned int *)userdata) ||
		get_user(param, (unsigned int *)userdata + 1)) {
		ret = -EFAULT;
		break;
	    }
            ret = BMIWriteSOCRegister(hifDevice, address, param);
            break;

#ifdef HTC_RAW_INTERFACE
        case AR6000_XIOCTL_HTC_RAW_OPEN:
            ret = A_OK;
            if (!arRawIfEnabled(ar)) {
                /* make sure block size is set in case the target was reset since last
                  * BMI phase (i.e. flashup downloads) */
                ret = ar6000_set_htc_params(ar->arHifDevice,
                                            ar->arTargetType,
                                            0,  /* use default yield */
                                            0   /* use default number of HTC ctrl buffers */
                                            );
                if (A_FAILED(ret)) {
                    break;
                }
                /* Terminate the BMI phase */
                ret = BMIDone(hifDevice);
                if (ret == A_OK) {
                    ret = ar6000_htc_raw_open(ar);
                }
            }
            break;

        case AR6000_XIOCTL_HTC_RAW_CLOSE:
            if (arRawIfEnabled(ar)) {
                ret = ar6000_htc_raw_close(ar);
                arRawIfEnabled(ar) = FALSE;
            } else {
                ret = A_ERROR;
            }
            break;

        case AR6000_XIOCTL_HTC_RAW_READ:
            if (arRawIfEnabled(ar)) {
                unsigned int streamID;
		if (get_user(streamID, (unsigned int *)userdata) ||
		    get_user(length, (unsigned int *)userdata + 1)) {
		    ret = -EFAULT;
		    break;
		}
                buffer = (unsigned char*)rq->ifr_data + sizeof(length);
                ret = ar6000_htc_raw_read(ar, (HTC_RAW_STREAM_ID)streamID,
                                          (char*)buffer, length);
		if (put_user(ret, (unsigned int *)rq->ifr_data)) {
		    ret = -EFAULT;
		    break;
		}
            } else {
                ret = A_ERROR;
            }
            break;

        case AR6000_XIOCTL_HTC_RAW_WRITE:
            if (arRawIfEnabled(ar)) {
                unsigned int streamID;
		if (get_user(streamID, (unsigned int *)userdata) ||
		    get_user(length, (unsigned int *)userdata + 1)) {
		    ret = -EFAULT;
		    break;
		}
                buffer = (unsigned char*)userdata + sizeof(streamID) + sizeof(length);
                ret = ar6000_htc_raw_write(ar, (HTC_RAW_STREAM_ID)streamID,
                                           (char*)buffer, length);
		if (put_user(ret, (unsigned int *)rq->ifr_data)) {
		    ret = -EFAULT;
		    break;
		}
            } else {
                ret = A_ERROR;
            }
            break;
#endif /* HTC_RAW_INTERFACE */

        case AR6000_XIOCTL_BMI_LZ_STREAM_START:
	    if (get_user(address, (unsigned int *)userdata)) {
		ret = -EFAULT;
		break;
	    }
            AR_DEBUG_PRINTF(ATH_DEBUG_INFO,("Start Compressed Stream (address: 0x%x)\n", address));
            ret = BMILZStreamStart(hifDevice, address);
            break;

        case AR6000_XIOCTL_BMI_LZ_DATA:
	    if (get_user(length, (unsigned int *)userdata)) {
		ret = -EFAULT;
		break;
	    }
            AR_DEBUG_PRINTF(ATH_DEBUG_INFO,("Send Compressed Data (length: %d)\n", length));
            if ((buffer = (unsigned char *)A_MALLOC(length)) != NULL) {
                A_MEMZERO(buffer, length);
                if (copy_from_user(buffer, &userdata[sizeof(length)], length))
                {
                    ret = -EFAULT;
                } else {
                    ret = BMILZData(hifDevice, buffer, length);
                }
                A_FREE(buffer);
            } else {
                ret = -ENOMEM;
            }
            break;

#if defined(CONFIG_TARGET_PROFILE_SUPPORT)
        /*
         * Optional support for Target-side profiling.
         * Not needed in production.
         */

        /* Configure Target-side profiling */
        case AR6000_XIOCTL_PROF_CFG:
        {
            A_UINT32 period;
            A_UINT32 nbins;
	    if (get_user(period, (unsigned int *)userdata) ||
		get_user(nbins, (unsigned int *)userdata + 1)) {
		ret = -EFAULT;
		break;
	    }

            if (wmi_prof_cfg_cmd(ar->arWmi, period, nbins) != A_OK) {
                ret = -EIO;
            }

            break;
        }

        /* Start a profiling bucket/bin at the specified address */
        case AR6000_XIOCTL_PROF_ADDR_SET:
        {
            A_UINT32 addr;
	    if (get_user(addr, (unsigned int *)userdata)) {
		ret = -EFAULT;
		break;
	    }

            if (wmi_prof_addr_set_cmd(ar->arWmi, addr) != A_OK) {
                ret = -EIO;
            }

            break;
        }

        /* START Target-side profiling */
        case AR6000_XIOCTL_PROF_START:
            wmi_prof_start_cmd(ar->arWmi);
            break;

        /* STOP Target-side profiling */
        case AR6000_XIOCTL_PROF_STOP:
            wmi_prof_stop_cmd(ar->arWmi);
            break;
        case AR6000_XIOCTL_PROF_COUNT_GET:
        {
            if (ar->bIsDestroyProgress) {
                ret = -EBUSY;
                goto ioctl_done;
            }
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
                goto ioctl_done;
            }
            if (down_interruptible(&ar->arSem)) {
                ret = -ERESTARTSYS;
                goto ioctl_done;
            }
            if (ar->bIsDestroyProgress) {
                up(&ar->arSem);
                ret = -EBUSY;
                goto ioctl_done;
            }

            prof_count_available = FALSE;
            ret = prof_count_get(dev);
            if (ret != A_OK) {
                up(&ar->arSem);
                ret = -EIO;
                goto ioctl_done;
            }

            /* Wait for Target to respond. */
            wait_event_interruptible(arEvent, prof_count_available);
            if (signal_pending(current)) {
                ret = -EINTR;
            } else {
                if (copy_to_user(userdata, &prof_count_results,
                                 sizeof(prof_count_results)))
                {
                    ret = -EFAULT;
                }
            }
            up(&ar->arSem);
            break;
        }
#endif /* CONFIG_TARGET_PROFILE_SUPPORT */

        case AR6000_IOCTL_WMI_GETREV:
        {
            if (copy_to_user(rq->ifr_data, &ar->arVersion,
                             sizeof(ar->arVersion)))
            {
                ret = -EFAULT;
            }
            break;
        }
        case AR6000_IOCTL_WMI_SETPWR:
        {
            WMI_POWER_MODE_CMD pwrModeCmd;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&pwrModeCmd, userdata,
                                   sizeof(pwrModeCmd)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_powermode_cmd(ar->arWmi, pwrModeCmd.powerMode)
                       != A_OK)
                {
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_IOCTL_WMI_SET_IBSS_PM_CAPS:
        {
            WMI_IBSS_PM_CAPS_CMD ibssPmCaps;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&ibssPmCaps, userdata,
                                   sizeof(ibssPmCaps)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_ibsspmcaps_cmd(ar->arWmi, ibssPmCaps.power_saving, ibssPmCaps.ttl,
                    ibssPmCaps.atim_windows, ibssPmCaps.timeout_value) != A_OK)
                {
                    ret = -EIO;
                }
                AR6000_SPIN_LOCK(&ar->arLock, 0);
                ar->arIbssPsEnable = ibssPmCaps.power_saving;
                AR6000_SPIN_UNLOCK(&ar->arLock, 0);
            }
            break;
        }
        case AR6000_XIOCTL_WMI_SET_AP_PS:
        {
            WMI_AP_PS_CMD apPsCmd;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&apPsCmd, userdata,
                                   sizeof(apPsCmd)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_apps_cmd(ar->arWmi, apPsCmd.psType, apPsCmd.idle_time,
                    apPsCmd.ps_period, apPsCmd.sleep_period) != A_OK)
                {
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_IOCTL_WMI_SET_PMPARAMS:
        {
            WMI_POWER_PARAMS_CMD pmParams;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&pmParams, userdata,
                                      sizeof(pmParams)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_pmparams_cmd(ar->arWmi, pmParams.idle_period,
                                     pmParams.pspoll_number,
                                     pmParams.dtim_policy,
                                     pmParams.tx_wakeup_policy,
                                     pmParams.num_tx_to_wakeup,
#if WLAN_CONFIG_IGNORE_POWER_SAVE_FAIL_EVENT_DURING_SCAN
                                     IGNORE_POWER_SAVE_FAIL_EVENT_DURING_SCAN 
#else
                                     SEND_POWER_SAVE_FAIL_EVENT_ALWAYS
#endif
                                     ) != A_OK)
                {
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_IOCTL_WMI_SETSCAN:
        {
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&ar->scParams, userdata,
                                      sizeof(ar->scParams)))
            {
                ret = -EFAULT;
            } else {
                if (CAN_SCAN_IN_CONNECT(ar->scParams.scanCtrlFlags)) {
                    ar->arSkipScan = FALSE;
                } else {
                    ar->arSkipScan = TRUE;
                }

                if (wmi_scanparams_cmd(ar->arWmi, ar->scParams.fg_start_period,
                                       ar->scParams.fg_end_period,
                                       ar->scParams.bg_period,
                                       ar->scParams.minact_chdwell_time,
                                       ar->scParams.maxact_chdwell_time,
                                       ar->scParams.pas_chdwell_time,
                                       ar->scParams.shortScanRatio,
                                       ar->scParams.scanCtrlFlags,
                                       ar->scParams.max_dfsch_act_time,
                                       ar->scParams.maxact_scan_per_ssid) != A_OK)
                {
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_IOCTL_WMI_SETLISTENINT:
        {
            WMI_LISTEN_INT_CMD listenCmd;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&listenCmd, userdata,
                                      sizeof(listenCmd)))
            {
                ret = -EFAULT;
            } else {
                    if (wmi_listeninterval_cmd(ar->arWmi, listenCmd.listenInterval, listenCmd.numBeacons) != A_OK) {
                        ret = -EIO;
                    } else {
                        AR6000_SPIN_LOCK(&ar->arLock, 0);
                        ar->arListenIntervalT = listenCmd.listenInterval;
                        ar->arListenIntervalB = listenCmd.numBeacons;
                        AR6000_SPIN_UNLOCK(&ar->arLock, 0);
                    }

                }
            break;
        }
        case AR6000_IOCTL_WMI_SET_BMISS_TIME:
        {
            WMI_BMISS_TIME_CMD bmissCmd;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&bmissCmd, userdata,
                                      sizeof(bmissCmd)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_bmisstime_cmd(ar->arWmi, bmissCmd.bmissTime, bmissCmd.numBeacons) != A_OK) {
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_IOCTL_WMI_SETBSSFILTER:
        {
            WMI_BSS_FILTER_CMD filt;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&filt, userdata,
                                   sizeof(filt)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_bssfilter_cmd(ar->arWmi, filt.bssFilter, filt.ieMask)
                        != A_OK) {
                    ret = -EIO;
                } else {
                    ar->arUserBssFilter = param;
                }
            }
            break;
        }

        case AR6000_IOCTL_WMI_SET_SNRTHRESHOLD:
        {
            ret = ar6000_ioctl_set_snr_threshold(dev, rq);
            break;
        }
        case AR6000_XIOCTL_WMI_SET_RSSITHRESHOLD:
        {
            ret = ar6000_ioctl_set_rssi_threshold(dev, rq);
            break;
        }
        case AR6000_XIOCTL_WMI_CLR_RSSISNR:
        {
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            }
            ret = wmi_clr_rssi_snr(ar->arWmi);
            break;
        }
        case AR6000_XIOCTL_WMI_SET_LQTHRESHOLD:
        {
            ret = ar6000_ioctl_set_lq_threshold(dev, rq);
            break;
        }
        case AR6000_XIOCTL_WMI_SET_LPREAMBLE:
        {
            WMI_SET_LPREAMBLE_CMD setLpreambleCmd;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&setLpreambleCmd, userdata,
                                   sizeof(setLpreambleCmd)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_set_lpreamble_cmd(ar->arWmi, setLpreambleCmd.status,
#if WLAN_CONFIG_DONOT_IGNORE_BARKER_IN_ERP 
                           WMI_DONOT_IGNORE_BARKER_IN_ERP
#else
                           WMI_IGNORE_BARKER_IN_ERP
#endif
                ) != A_OK)
                {
                    ret = -EIO;
                }
            }

            break;
        }
        case AR6000_XIOCTL_WMI_SET_RTS:
        {
            WMI_SET_RTS_CMD rtsCmd;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&rtsCmd, userdata,
                                   sizeof(rtsCmd)))
            {
                ret = -EFAULT;
            } else {
                ar->arRTS = rtsCmd.threshold;
                if (wmi_set_rts_cmd(ar->arWmi, rtsCmd.threshold)
                       != A_OK)
                {
                    ret = -EIO;
                }
            }

            break;
        }
        case AR6000_XIOCTL_WMI_SET_WMM:
        {
            ret = ar6000_ioctl_set_wmm(dev, rq);
            break;
        }
       case AR6000_XIOCTL_WMI_SET_QOS_SUPP:
        {
            ret = ar6000_ioctl_set_qos_supp(dev, rq);
            break;
        }
        case AR6000_XIOCTL_WMI_SET_TXOP:
        {
            ret = ar6000_ioctl_set_txop(dev, rq);
            break;
        }
        case AR6000_XIOCTL_WMI_GET_RD:
        {
            ret = ar6000_ioctl_get_rd(dev, rq);
            break;
        }
        case AR6000_IOCTL_WMI_SET_CHANNELPARAMS:
        {
            ret = ar6000_ioctl_set_channelParams(dev, rq);
            break;
        }
        case AR6000_IOCTL_WMI_SET_PROBEDSSID:
        {
            ret = ar6000_ioctl_set_probedSsid(dev, rq);
            break;
        }
        case AR6000_IOCTL_WMI_SET_BADAP:
        {
            ret = ar6000_ioctl_set_badAp(dev, rq);
            break;
        }
        case AR6000_IOCTL_WMI_CREATE_QOS:
        {
            ret = ar6000_ioctl_create_qos(dev, rq);
            break;
        }
        case AR6000_IOCTL_WMI_DELETE_QOS:
        {
            ret = ar6000_ioctl_delete_qos(dev, rq);
            break;
        }
        case AR6000_IOCTL_WMI_GET_QOS_QUEUE:
        {
            ret = ar6000_ioctl_get_qos_queue(dev, rq);
            break;
        }
        case AR6000_IOCTL_WMI_GET_TARGET_STATS:
        {
            ret = ar6000_ioctl_get_target_stats(dev, rq);
            break;
        }
        case AR6000_IOCTL_WMI_SET_ERROR_REPORT_BITMASK:
        {
            ret = ar6000_ioctl_set_error_report_bitmask(dev, rq);
            break;
        }
        case AR6000_IOCTL_WMI_SET_ASSOC_INFO:
        {
            WMI_SET_ASSOC_INFO_CMD cmd;
            A_UINT8 assocInfo[WMI_MAX_ASSOC_INFO_LEN];

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
		break;
	    }

	    if (get_user(cmd.ieType, userdata)) {
		ret = -EFAULT;
		break;
	    }
	    if (cmd.ieType >= WMI_MAX_ASSOC_INFO_TYPE) {
		ret = -EIO;
		break;
	    }

	    if (get_user(cmd.bufferSize, userdata + 1) ||
		(cmd.bufferSize > WMI_MAX_ASSOC_INFO_LEN) ||
		copy_from_user(assocInfo, userdata + 2, cmd.bufferSize)) {
		ret = -EFAULT;
		break;
	    }
	    if (wmi_associnfo_cmd(ar->arWmi, cmd.ieType,
				  cmd.bufferSize, assocInfo) != A_OK) {
		ret = -EIO;
		break;
	    }
            break;
        }
        case AR6000_IOCTL_WMI_SET_ACCESS_PARAMS:
        {
            ret = ar6000_ioctl_set_access_params(dev, rq);
            break;
        }
        case AR6000_IOCTL_WMI_SET_DISC_TIMEOUT:
        {
            ret = ar6000_ioctl_set_disconnect_timeout(dev, rq);
            break;
        }
        case AR6000_XIOCTL_FORCE_TARGET_RESET:
        {
            if (ar->arHtcTarget)
            {
//                HTCForceReset(htcTarget);
            }
            else
            {
                AR_DEBUG_PRINTF(ATH_DEBUG_WARN,("ar6000_ioctl cannot attempt reset.\n"));
            }
            break;
        }
        case AR6000_XIOCTL_TARGET_INFO:
        case AR6000_XIOCTL_CHECK_TARGET_READY: /* backwards compatibility */
        {
            /* If we made it to here, then the Target exists and is ready. */

            if (cmd == AR6000_XIOCTL_TARGET_INFO) {
                if (copy_to_user((A_UINT32 *)rq->ifr_data, &ar->arVersion.target_ver,
                                 sizeof(ar->arVersion.target_ver)))
                {
                    ret = -EFAULT;
                }
                if (copy_to_user(((A_UINT32 *)rq->ifr_data)+1, &ar->arTargetType,
                                 sizeof(ar->arTargetType)))
                {
                    ret = -EFAULT;
                }
            }
            break;
        }
        case AR6000_XIOCTL_WMI_SET_HB_CHALLENGE_RESP_PARAMS:
        {
            WMI_SET_HB_CHALLENGE_RESP_PARAMS_CMD hbparam;

            if (copy_from_user(&hbparam, userdata, sizeof(hbparam)))
            {
                ret = -EFAULT;
            } else {
                AR6000_SPIN_LOCK(&ar->arLock, 0);
                /* Start a cyclic timer with the parameters provided. */
                if (hbparam.frequency) {
                    ar->arHBChallengeResp.frequency = hbparam.frequency;
                }
                if (hbparam.threshold) {
                    ar->arHBChallengeResp.missThres = hbparam.threshold;
                }

                /* Delete the pending timer and start a new one */
                if (timer_pending(&ar->arHBChallengeResp.timer)) {
                    A_UNTIMEOUT(&ar->arHBChallengeResp.timer);
                }
                A_TIMEOUT_MS(&ar->arHBChallengeResp.timer, ar->arHBChallengeResp.frequency * 1000, 0);
                AR6000_SPIN_UNLOCK(&ar->arLock, 0);
            }
            break;
        }
        case AR6000_XIOCTL_WMI_GET_HB_CHALLENGE_RESP:
        {
            A_UINT32 cookie;

            if (copy_from_user(&cookie, userdata, sizeof(cookie))) {
                ret = -EFAULT;
                goto ioctl_done;
            }

            /* Send the challenge on the control channel */
            if (wmi_get_challenge_resp_cmd(ar->arWmi, cookie, APP_HB_CHALLENGE) != A_OK) {
                ret = -EIO;
                goto ioctl_done;
            }
            break;
        }
#ifdef USER_KEYS
        case AR6000_XIOCTL_USER_SETKEYS:
        {

            ar->user_savedkeys_stat = USER_SAVEDKEYS_STAT_RUN;

            if (copy_from_user(&ar->user_key_ctrl, userdata,
                               sizeof(ar->user_key_ctrl)))
            {
                ret = -EFAULT;
                goto ioctl_done;
            }

            A_PRINTF("ar6000 USER set key %x\n", ar->user_key_ctrl);
            break;
        }
#endif /* USER_KEYS */

#ifdef CONFIG_HOST_GPIO_SUPPORT
        case AR6000_XIOCTL_GPIO_OUTPUT_SET:
        {
            struct ar6000_gpio_output_set_cmd_s gpio_output_set_cmd;

            if (ar->bIsDestroyProgress) {
                ret = -EBUSY;
                goto ioctl_done;
            }
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
                goto ioctl_done;
            }
            if (down_interruptible(&ar->arSem)) {
                ret = -ERESTARTSYS;
                goto ioctl_done;
            }
            if (ar->bIsDestroyProgress) {
                up(&ar->arSem);
                ret = -EBUSY;
                goto ioctl_done;
            }

            if (copy_from_user(&gpio_output_set_cmd, userdata,
                                sizeof(gpio_output_set_cmd)))
            {
                ret = -EFAULT;
            } else {
                ret = ar6000_gpio_output_set(dev,
                                             gpio_output_set_cmd.set_mask,
                                             gpio_output_set_cmd.clear_mask,
                                             gpio_output_set_cmd.enable_mask,
                                             gpio_output_set_cmd.disable_mask);
                if (ret != A_OK) {
                    ret = EIO;
                }
            }
            up(&ar->arSem);
            break;
        }
        case AR6000_XIOCTL_GPIO_INPUT_GET:
        {
            if (ar->bIsDestroyProgress) {
                ret = -EBUSY;
                goto ioctl_done;
            }
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
                goto ioctl_done;
            }
            if (down_interruptible(&ar->arSem)) {
                ret = -ERESTARTSYS;
                goto ioctl_done;
            }
            if (ar->bIsDestroyProgress) {
                up(&ar->arSem);
                ret = -EBUSY;
                goto ioctl_done;
            }

            ret = ar6000_gpio_input_get(dev);
            if (ret != A_OK) {
                up(&ar->arSem);
                ret = -EIO;
                goto ioctl_done;
            }

            /* Wait for Target to respond. */
            wait_event_interruptible(arEvent, gpio_data_available);
            if (signal_pending(current)) {
                ret = -EINTR;
            } else {
                A_ASSERT(gpio_reg_results.gpioreg_id == GPIO_ID_NONE);

                if (copy_to_user(userdata, &gpio_reg_results.value,
                                 sizeof(gpio_reg_results.value)))
                {
                    ret = -EFAULT;
                }
            }
            up(&ar->arSem);
            break;
        }
        case AR6000_XIOCTL_GPIO_REGISTER_SET:
        {
            struct ar6000_gpio_register_cmd_s gpio_register_cmd;

            if (ar->bIsDestroyProgress) {
                ret = -EBUSY;
                goto ioctl_done;
            }
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
                goto ioctl_done;
            }
            if (down_interruptible(&ar->arSem)) {
                ret = -ERESTARTSYS;
                goto ioctl_done;
            }
            if (ar->bIsDestroyProgress) {
                up(&ar->arSem);
                ret = -EBUSY;
                goto ioctl_done;
            }

            if (copy_from_user(&gpio_register_cmd, userdata,
                                sizeof(gpio_register_cmd)))
            {
                ret = -EFAULT;
            } else {
                ret = ar6000_gpio_register_set(dev,
                                               gpio_register_cmd.gpioreg_id,
                                               gpio_register_cmd.value);
                if (ret != A_OK) {
                    ret = EIO;
                }

                /* Wait for acknowledgement from Target */
                wait_event_interruptible(arEvent, gpio_ack_received);
                if (signal_pending(current)) {
                    ret = -EINTR;
                }
            }
            up(&ar->arSem);
            break;
        }
        case AR6000_XIOCTL_GPIO_REGISTER_GET:
        {
            struct ar6000_gpio_register_cmd_s gpio_register_cmd;

            if (ar->bIsDestroyProgress) {
                ret = -EBUSY;
                goto ioctl_done;
            }
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
                goto ioctl_done;
            }
            if (down_interruptible(&ar->arSem)) {
                ret = -ERESTARTSYS;
                goto ioctl_done;
            }
            if (ar->bIsDestroyProgress) {
                up(&ar->arSem);
                ret = -EBUSY;
                goto ioctl_done;
            }

            if (copy_from_user(&gpio_register_cmd, userdata,
                                sizeof(gpio_register_cmd)))
            {
                ret = -EFAULT;
            } else {
                ret = ar6000_gpio_register_get(dev, gpio_register_cmd.gpioreg_id);
                if (ret != A_OK) {
                    up(&ar->arSem);
                    ret = -EIO;
                    goto ioctl_done;
                }

                /* Wait for Target to respond. */
                wait_event_interruptible(arEvent, gpio_data_available);
                if (signal_pending(current)) {
                    ret = -EINTR;
                } else {
                    A_ASSERT(gpio_register_cmd.gpioreg_id == gpio_reg_results.gpioreg_id);
                    if (copy_to_user(userdata, &gpio_reg_results,
                                     sizeof(gpio_reg_results)))
                    {
                        ret = -EFAULT;
                    }
                }
            }
            up(&ar->arSem);
            break;
        }
        case AR6000_XIOCTL_GPIO_INTR_ACK:
        {
            struct ar6000_gpio_intr_ack_cmd_s gpio_intr_ack_cmd;

            if (ar->bIsDestroyProgress) {
                ret = -EBUSY;
                goto ioctl_done;
            }
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
                goto ioctl_done;
            }
            if (down_interruptible(&ar->arSem)) {
                ret = -ERESTARTSYS;
                goto ioctl_done;
            }
            if (ar->bIsDestroyProgress) {
                up(&ar->arSem);
                ret = -EBUSY;
                goto ioctl_done;
            }

            if (copy_from_user(&gpio_intr_ack_cmd, userdata,
                                sizeof(gpio_intr_ack_cmd)))
            {
                ret = -EFAULT;
            } else {
                ret = ar6000_gpio_intr_ack(dev, gpio_intr_ack_cmd.ack_mask);
                if (ret != A_OK) {
                    ret = EIO;
                }
            }
            up(&ar->arSem);
            break;
        }
        case AR6000_XIOCTL_GPIO_INTR_WAIT:
        {
            /* Wait for Target to report an interrupt. */
            wait_event_interruptible(arEvent, gpio_intr_available);

            if (signal_pending(current)) {
                ret = -EINTR;
            } else {
                if (copy_to_user(userdata, &gpio_intr_results,
                                 sizeof(gpio_intr_results)))
                {
                    ret = -EFAULT;
                }
            }
            break;
        }
#endif /* CONFIG_HOST_GPIO_SUPPORT */

        case AR6000_XIOCTL_DBGLOG_CFG_MODULE:
        {
            struct ar6000_dbglog_module_config_s config;

            if (copy_from_user(&config, userdata, sizeof(config))) {
                ret = -EFAULT;
                goto ioctl_done;
            }

            /* Send the challenge on the control channel */
            if (wmi_config_debug_module_cmd(ar->arWmi, config.mmask,
                                            config.tsr, config.rep,
                                            config.size, config.valid) != A_OK)
            {
                ret = -EIO;
                goto ioctl_done;
            }
            break;
        }

        case AR6000_XIOCTL_DBGLOG_GET_DEBUG_LOGS:
        {
            /* Send the challenge on the control channel */
            if (ar6000_dbglog_get_debug_logs(ar) != A_OK)
            {
                ret = -EIO;
                goto ioctl_done;
            }
            break;
        }

        case AR6000_XIOCTL_SET_ADHOC_BSSID:
        {
            WMI_SET_ADHOC_BSSID_CMD adhocBssid;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&adhocBssid, userdata,
                                      sizeof(adhocBssid)))
            {
                ret = -EFAULT;
            } else if (A_MEMCMP(adhocBssid.bssid, bcast_mac,
                                AR6000_ETH_ADDR_LEN) == 0)
            {
                ret = -EFAULT;
            } else {

                A_MEMCPY(ar->arReqBssid, adhocBssid.bssid, sizeof(ar->arReqBssid));
        }
            break;
        }

        case AR6000_XIOCTL_SET_OPT_MODE:
        {
        WMI_SET_OPT_MODE_CMD optModeCmd;
            AR_SOFTC_T *ar = (AR_SOFTC_T *)ar6k_priv(dev);

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&optModeCmd, userdata,
                                      sizeof(optModeCmd)))
            {
                ret = -EFAULT;
            } else if (ar->arConnected && optModeCmd.optMode == SPECIAL_ON) {
                ret = -EFAULT;

            } else if (wmi_set_opt_mode_cmd(ar->arWmi, optModeCmd.optMode)
                       != A_OK)
            {
                ret = -EIO;
            }
            break;
        }

        case AR6000_XIOCTL_OPT_SEND_FRAME:
        {
        WMI_OPT_TX_FRAME_CMD optTxFrmCmd;
            A_UINT8 data[MAX_OPT_DATA_LEN];

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&optTxFrmCmd, userdata,
                                      sizeof(optTxFrmCmd)))
            {
                ret = -EFAULT;
            } else if (copy_from_user(data,
                                      userdata+sizeof(WMI_OPT_TX_FRAME_CMD)-1,
                                      optTxFrmCmd.optIEDataLen))
            {
                ret = -EFAULT;
            } else {
                ret = wmi_opt_tx_frame_cmd(ar->arWmi,
                                           optTxFrmCmd.frmType,
                                           optTxFrmCmd.dstAddr,
                                           optTxFrmCmd.bssid,
                                           optTxFrmCmd.optIEDataLen,
                                           data);
            }

            break;
        }
        case AR6000_XIOCTL_WMI_SETRETRYLIMITS:
        {
            WMI_SET_RETRY_LIMITS_CMD setRetryParams;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&setRetryParams, userdata,
                                      sizeof(setRetryParams)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_set_retry_limits_cmd(ar->arWmi, setRetryParams.frameType,
                                          setRetryParams.trafficClass,
                                          setRetryParams.maxRetries,
                                          setRetryParams.enableNotify) != A_OK)
                {
                    ret = -EIO;
                }
                AR6000_SPIN_LOCK(&ar->arLock, 0);
                ar->arMaxRetries = setRetryParams.maxRetries;
                AR6000_SPIN_UNLOCK(&ar->arLock, 0);
            }
            break;
        }

        case AR6000_XIOCTL_SET_BEACON_INTVAL:
        {
            WMI_BEACON_INT_CMD bIntvlCmd;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&bIntvlCmd, userdata,
                       sizeof(bIntvlCmd)))
            {
                ret = -EFAULT;
            } else if (wmi_set_adhoc_bconIntvl_cmd(ar->arWmi, bIntvlCmd.beaconInterval)
                        != A_OK)
            {
                ret = -EIO;
            }
            if(ret == 0) {
                ar->ap_beacon_interval = bIntvlCmd.beaconInterval;
                ar->ap_profile_flag = 1; /* There is a change in profile */
            }
            break;
        }
        case IEEE80211_IOCTL_SETAUTHALG:
        {
            AR_SOFTC_T *ar = (AR_SOFTC_T *)ar6k_priv(dev);
            struct ieee80211req_authalg req;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&req, userdata,
                       sizeof(struct ieee80211req_authalg)))
            {
                ret = -EFAULT;
            } else {
                if (req.auth_alg & AUTH_ALG_OPEN_SYSTEM) {
                    ar->arDot11AuthMode  |= OPEN_AUTH;
                    ar->arPairwiseCrypto  = NONE_CRYPT;
                    ar->arGroupCrypto     = NONE_CRYPT;
                }
                if (req.auth_alg & AUTH_ALG_SHARED_KEY) {
                    ar->arDot11AuthMode  |= SHARED_AUTH;
                    ar->arPairwiseCrypto  = WEP_CRYPT;
                    ar->arGroupCrypto     = WEP_CRYPT;
                    ar->arAuthMode        = NONE_AUTH;
                }
                if (req.auth_alg == AUTH_ALG_LEAP) {
                    ar->arDot11AuthMode   = LEAP_AUTH;
                }
            }
            break;
        }

        case AR6000_XIOCTL_SET_VOICE_PKT_SIZE:
            ret = ar6000_xioctl_set_voice_pkt_size(dev, userdata);
            break;

        case AR6000_XIOCTL_SET_MAX_SP:
            ret = ar6000_xioctl_set_max_sp_len(dev, userdata);
            break;

        case AR6000_XIOCTL_WMI_GET_ROAM_TBL:
            ret = ar6000_ioctl_get_roam_tbl(dev, rq);
            break;
        case AR6000_XIOCTL_WMI_SET_ROAM_CTRL:
            ret = ar6000_ioctl_set_roam_ctrl(dev, userdata);
            break;
        case AR6000_XIOCTRL_WMI_SET_POWERSAVE_TIMERS:
            ret = ar6000_ioctl_set_powersave_timers(dev, userdata);
            break;
        case AR6000_XIOCTRL_WMI_GET_POWER_MODE:
            ret = ar6000_ioctl_get_power_mode(dev, rq);
            break;
        case AR6000_XIOCTRL_WMI_SET_WLAN_STATE:
        {
            AR6000_WLAN_STATE state;
	    if (get_user(state, (unsigned int *)userdata))
		ret = -EFAULT;
	    else if (ar6000_set_wlan_state(ar, state) != A_OK)
                ret = -EIO;
            break;
        }
        case AR6000_XIOCTL_WMI_GET_ROAM_DATA:
            ret = ar6000_ioctl_get_roam_data(dev, rq);
            break;

        case AR6000_XIOCTL_WMI_SET_BT_STATUS:
            ret = ar6000_xioctl_set_bt_status_cmd(dev, userdata);
            break;

        case AR6000_XIOCTL_WMI_SET_BT_PARAMS:
            ret = ar6000_xioctl_set_bt_params_cmd(dev, userdata);
            break;

		case AR6000_XIOCTL_WMI_SET_BTCOEX_FE_ANT:
			ret = ar6000_xioctl_set_btcoex_fe_ant_cmd(dev, userdata);
			break;

		case AR6000_XIOCTL_WMI_SET_BTCOEX_COLOCATED_BT_DEV:
			ret = ar6000_xioctl_set_btcoex_colocated_bt_dev_cmd(dev, userdata);
			break;

		case AR6000_XIOCTL_WMI_SET_BTCOEX_BTINQUIRY_PAGE_CONFIG:
			ret = ar6000_xioctl_set_btcoex_btinquiry_page_config_cmd(dev, userdata);
			break;

		case AR6000_XIOCTL_WMI_SET_BTCOEX_SCO_CONFIG:
			ret = ar6000_xioctl_set_btcoex_sco_config_cmd( dev, userdata);
			break;

		case AR6000_XIOCTL_WMI_SET_BTCOEX_A2DP_CONFIG:
			ret = ar6000_xioctl_set_btcoex_a2dp_config_cmd(dev, userdata);
			break;

		case AR6000_XIOCTL_WMI_SET_BTCOEX_ACLCOEX_CONFIG:
			ret = ar6000_xioctl_set_btcoex_aclcoex_config_cmd(dev, userdata);
			break;

		case AR6000_XIOCTL_WMI_SET_BTCOEX_DEBUG:
			ret = ar60000_xioctl_set_btcoex_debug_cmd(dev, userdata);
			break;

		case AR6000_XIOCTL_WMI_SET_BT_OPERATING_STATUS:
			ret = ar6000_xioctl_set_btcoex_bt_operating_status_cmd(dev, userdata);
			break;

		case AR6000_XIOCTL_WMI_GET_BTCOEX_CONFIG:
			ret = ar6000_xioctl_get_btcoex_config_cmd(dev, userdata, rq);
			break;

		case AR6000_XIOCTL_WMI_GET_BTCOEX_STATS:
			ret = ar6000_xioctl_get_btcoex_stats_cmd(dev, userdata, rq);
			break;

        case AR6000_XIOCTL_WMI_STARTSCAN:
        {
            WMI_START_SCAN_CMD setStartScanCmd, *cmdp;

            if (ar->arWmiReady == FALSE) {
                    ret = -EIO;
                } else if (copy_from_user(&setStartScanCmd, userdata,
                                          sizeof(setStartScanCmd)))
                {
                    ret = -EFAULT;
                } else {
                    if (setStartScanCmd.numChannels > 1) {
                        cmdp = A_MALLOC(130);
                        if (copy_from_user(cmdp, userdata,
                                           sizeof (*cmdp) +
                                           ((setStartScanCmd.numChannels - 1) *
                                           sizeof(A_UINT16))))
                        {
                            kfree(cmdp);
                            ret = -EFAULT;
                            goto ioctl_done;
                        }
                    } else {
                        cmdp = &setStartScanCmd;
                    }

                    if (wmi_startscan_cmd(ar->arWmi, cmdp->scanType,
                                          cmdp->forceFgScan,
                                          cmdp->isLegacy,
                                          cmdp->homeDwellTime,
                                          cmdp->forceScanInterval,
                                          cmdp->numChannels,
                                          cmdp->channelList) != A_OK)
                    {
                        ret = -EIO;
                    }
                }
            break;
        }
        case AR6000_XIOCTL_WMI_SETFIXRATES:
        {
            WMI_FIX_RATES_CMD setFixRatesCmd;
            A_STATUS returnStatus;

            if (ar->arWmiReady == FALSE) {
                    ret = -EIO;
                } else if (copy_from_user(&setFixRatesCmd, userdata,
                                          sizeof(setFixRatesCmd)))
                {
                    ret = -EFAULT;
                } else {
                    returnStatus = wmi_set_fixrates_cmd(ar->arWmi, setFixRatesCmd.fixRateMask);
                    if (returnStatus == A_EINVAL) {
                        ret = -EINVAL;
                    } else if(returnStatus != A_OK) {
                        ret = -EIO;
                    } else {
                        ar->ap_profile_flag = 1; /* There is a change in profile */
                    }
                }
            break;
        }

        case AR6000_XIOCTL_WMI_GETFIXRATES:
        {
            WMI_FIX_RATES_CMD getFixRatesCmd;
            AR_SOFTC_T *ar = (AR_SOFTC_T *)ar6k_priv(dev);
            int ret = 0;

            if (ar->bIsDestroyProgress) {
                ret = -EBUSY;
                goto ioctl_done;
            }
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
                goto ioctl_done;
            }

            if (down_interruptible(&ar->arSem)) {
                ret = -ERESTARTSYS;
                goto ioctl_done;
            }
            if (ar->bIsDestroyProgress) {
                up(&ar->arSem);
                ret = -EBUSY;
                goto ioctl_done;
            }
            /* Used copy_from_user/copy_to_user to access user space data */
            if (copy_from_user(&getFixRatesCmd, userdata, sizeof(getFixRatesCmd))) {
                ret = -EFAULT;
            } else {
                ar->arRateMask = 0xFFFFFFFF;

                if (wmi_get_ratemask_cmd(ar->arWmi) != A_OK) {
                    up(&ar->arSem);
                    ret = -EIO;
                    goto ioctl_done;
                }

                wait_event_interruptible_timeout(arEvent, ar->arRateMask != 0xFFFFFFFF, wmitimeout * HZ);

                if (signal_pending(current)) {
                    ret = -EINTR;
                }

                if (!ret) {
                    getFixRatesCmd.fixRateMask = ar->arRateMask;
                }

                if(copy_to_user(userdata, &getFixRatesCmd, sizeof(getFixRatesCmd))) {
                   ret = -EFAULT;
                }

                up(&ar->arSem);
            }
            break;
        }
        case AR6000_XIOCTL_WMI_SET_AUTHMODE:
        {
            WMI_SET_AUTH_MODE_CMD setAuthMode;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&setAuthMode, userdata,
                                      sizeof(setAuthMode)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_set_authmode_cmd(ar->arWmi, setAuthMode.mode) != A_OK)
                {
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_XIOCTL_WMI_SET_REASSOCMODE:
        {
            WMI_SET_REASSOC_MODE_CMD setReassocMode;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&setReassocMode, userdata,
                                      sizeof(setReassocMode)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_set_reassocmode_cmd(ar->arWmi, setReassocMode.mode) != A_OK)
                {
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_XIOCTL_DIAG_READ:
        {
            A_UINT32 addr, data;
	    if (get_user(addr, (unsigned int *)userdata)) {
		ret = -EFAULT;
		break;
	    }
            addr = TARG_VTOP(ar->arTargetType, addr);
            if (ar6000_ReadRegDiag(ar->arHifDevice, &addr, &data) != A_OK) {
                ret = -EIO;
            }
	    if (put_user(data, (unsigned int *)userdata + 1)) {
		ret = -EFAULT;
		break;
	    }
            break;
        }
        case AR6000_XIOCTL_DIAG_WRITE:
        {
            A_UINT32 addr, data;
	    if (get_user(addr, (unsigned int *)userdata) ||
		get_user(data, (unsigned int *)userdata + 1)) {
		ret = -EFAULT;
		break;
	    }
            addr = TARG_VTOP(ar->arTargetType, addr);
            if (ar6000_WriteRegDiag(ar->arHifDevice, &addr, &data) != A_OK) {
                ret = -EIO;
            }
            break;
        }
        case AR6000_XIOCTL_WMI_SET_KEEPALIVE:
        {
             WMI_SET_KEEPALIVE_CMD setKeepAlive;
             if (ar->arWmiReady == FALSE) {
                 ret = -EIO;
                 goto ioctl_done;
             } else if (copy_from_user(&setKeepAlive, userdata,
                        sizeof(setKeepAlive))){
                 ret = -EFAULT;
             } else {
                 if (wmi_set_keepalive_cmd(ar->arWmi, setKeepAlive.keepaliveInterval) != A_OK) {
                     ret = -EIO;
               }
             }
             break;
        }
        case AR6000_XIOCTL_WMI_SET_PARAMS:
        {
             WMI_SET_PARAMS_CMD cmd;
             if (ar->arWmiReady == FALSE) {
                 ret = -EIO;
                 goto ioctl_done;
             } else if (copy_from_user(&cmd, userdata,
                        sizeof(cmd))){
                 ret = -EFAULT;
             } else if (copy_from_user(&cmd, userdata,
                        sizeof(cmd) + cmd.length))
            {
                ret = -EFAULT;
            } else {
                 if (wmi_set_params_cmd(ar->arWmi, cmd.opcode, cmd.length, cmd.buffer) != A_OK) {
                     ret = -EIO;
               }
             }
             break;
        }
        case AR6000_XIOCTL_WMI_SET_MCAST_FILTER:
        {
             WMI_SET_MCAST_FILTER_CMD cmd;
             if (ar->arWmiReady == FALSE) {
                 ret = -EIO;
                 goto ioctl_done;
             } else if (copy_from_user(&cmd, userdata,
                        sizeof(cmd))){
                 ret = -EFAULT;
             } else {
                 if (wmi_set_mcast_filter_cmd(ar->arWmi, cmd.multicast_mac[0],
                                                                                     cmd.multicast_mac[1],
                                                                                     cmd.multicast_mac[2],
                                                                                     cmd.multicast_mac[3]) != A_OK) {
                     ret = -EIO;
               }
             }
             break;
        }
        case AR6000_XIOCTL_WMI_DEL_MCAST_FILTER:
        {
             WMI_SET_MCAST_FILTER_CMD cmd;
             if (ar->arWmiReady == FALSE) {
                 ret = -EIO;
                 goto ioctl_done;
             } else if (copy_from_user(&cmd, userdata,
                        sizeof(cmd))){
                 ret = -EFAULT;
             } else {
                 if (wmi_del_mcast_filter_cmd(ar->arWmi, cmd.multicast_mac[0],
                                                                                     cmd.multicast_mac[1],
                                                                                     cmd.multicast_mac[2],
                                                                                     cmd.multicast_mac[3]) != A_OK) {
                     ret = -EIO;
               }
             }
             break;
        }
        case AR6000_XIOCTL_WMI_MCAST_FILTER:
        {
             WMI_MCAST_FILTER_CMD cmd;
             if (ar->arWmiReady == FALSE) {
                 ret = -EIO;
                 goto ioctl_done;
             } else if (copy_from_user(&cmd, userdata,
                        sizeof(cmd))){
                 ret = -EFAULT;
             } else {
                 if (wmi_mcast_filter_cmd(ar->arWmi, cmd.enable)  != A_OK) {
                     ret = -EIO;
               }
             }
             break;
        }
        case AR6000_XIOCTL_WMI_GET_KEEPALIVE:
        {
            AR_SOFTC_T *ar = (AR_SOFTC_T *)ar6k_priv(dev);
            WMI_GET_KEEPALIVE_CMD getKeepAlive;
            int ret = 0;
            if (ar->bIsDestroyProgress) {
                ret =-EBUSY;
                goto ioctl_done;
            }
            if (ar->arWmiReady == FALSE) {
               ret = -EIO;
               goto ioctl_done;
            }
            if (down_interruptible(&ar->arSem)) {
                ret = -ERESTARTSYS;
                goto ioctl_done;
            }
            if (ar->bIsDestroyProgress) {
                up(&ar->arSem);
                ret = -EBUSY;
                goto ioctl_done;
            }
            if (copy_from_user(&getKeepAlive, userdata,sizeof(getKeepAlive))) {
               ret = -EFAULT;
            } else {
            getKeepAlive.keepaliveInterval = wmi_get_keepalive_cmd(ar->arWmi);
            ar->arKeepaliveConfigured = 0xFF;
            if (wmi_get_keepalive_configured(ar->arWmi) != A_OK){
                up(&ar->arSem);
                ret = -EIO;
                goto ioctl_done;
            }
            wait_event_interruptible_timeout(arEvent, ar->arKeepaliveConfigured != 0xFF, wmitimeout * HZ);
            if (signal_pending(current)) {
                ret = -EINTR;
            }

            if (!ret) {
                getKeepAlive.configured = ar->arKeepaliveConfigured;
            }
            if (copy_to_user(userdata, &getKeepAlive, sizeof(getKeepAlive))) {
               ret = -EFAULT;
            }
            up(&ar->arSem);
            }
            break;
        }
        case AR6000_XIOCTL_WMI_SET_APPIE:
        {
            WMI_SET_APPIE_CMD appIEcmd;
            A_UINT8           appIeInfo[IEEE80211_APPIE_FRAME_MAX_LEN];
            A_UINT32            fType,ieLen;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
                goto ioctl_done;
            }
	    if (get_user(fType, (A_UINT32 *)userdata)) {
		ret = -EFAULT;
		break;
	    }
            appIEcmd.mgmtFrmType = fType;
            if (appIEcmd.mgmtFrmType >= IEEE80211_APPIE_NUM_OF_FRAME) {
                ret = -EIO;
            } else {
		if (get_user(ieLen, (A_UINT32 *)(userdata + 4))) {
		    ret = -EFAULT;
		    break;
		}
                appIEcmd.ieLen = ieLen;
                A_PRINTF("WPSIE: Type-%d, Len-%d\n",appIEcmd.mgmtFrmType, appIEcmd.ieLen);
                if (appIEcmd.ieLen > IEEE80211_APPIE_FRAME_MAX_LEN) {
                    ret = -EIO;
                    break;
                }
                if (copy_from_user(appIeInfo, userdata + 8, appIEcmd.ieLen)) {
                    ret = -EFAULT;
                } else {
                    if (wmi_set_appie_cmd(ar->arWmi, appIEcmd.mgmtFrmType,
                                          appIEcmd.ieLen,  appIeInfo) != A_OK)
                    {
                        ret = -EIO;
                    }
                }
            }
            break;
        }
        case AR6000_XIOCTL_WMI_SET_MGMT_FRM_RX_FILTER:
        {
            WMI_BSS_FILTER_CMD cmd;
            A_UINT32    filterType;

            if (copy_from_user(&filterType, userdata, sizeof(A_UINT32)))
            {
                ret = -EFAULT;
                goto ioctl_done;
            }
            if (filterType & (IEEE80211_FILTER_TYPE_BEACON |
                                    IEEE80211_FILTER_TYPE_PROBE_RESP))
            {
                cmd.bssFilter = ALL_BSS_FILTER;
            } else {
                cmd.bssFilter = NONE_BSS_FILTER;
            }
            if (wmi_bssfilter_cmd(ar->arWmi, cmd.bssFilter, 0) != A_OK) {
                ret = -EIO;
            } else {
                ar->arUserBssFilter = cmd.bssFilter;
            }

            AR6000_SPIN_LOCK(&ar->arLock, 0);
            ar->arMgmtFilter = filterType;
            AR6000_SPIN_UNLOCK(&ar->arLock, 0);
            break;
        }
        case AR6000_XIOCTL_WMI_SET_WSC_STATUS:
        {
            A_UINT32    wsc_status;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
                goto ioctl_done;
            } else if (copy_from_user(&wsc_status, userdata, sizeof(A_UINT32)))
            {
                ret = -EFAULT;
                goto ioctl_done;
            }
            if (wmi_set_wsc_status_cmd(ar->arWmi, wsc_status) != A_OK) {
                ret = -EIO;
            }
            break;
        }
        case AR6000_XIOCTL_BMI_ROMPATCH_INSTALL:
        {
            A_UINT32 ROM_addr;
            A_UINT32 RAM_addr;
            A_UINT32 nbytes;
            A_UINT32 do_activate;
            A_UINT32 rompatch_id;

	    if (get_user(ROM_addr, (A_UINT32 *)userdata) ||
		get_user(RAM_addr, (A_UINT32 *)userdata + 1) ||
		get_user(nbytes, (A_UINT32 *)userdata + 2) ||
		get_user(do_activate, (A_UINT32 *)userdata + 3)) {
		ret = -EFAULT;
		break;
	    }
            AR_DEBUG_PRINTF(ATH_DEBUG_INFO,("Install rompatch from ROM: 0x%x to RAM: 0x%x  length: %d\n",
                             ROM_addr, RAM_addr, nbytes));
            ret = BMIrompatchInstall(hifDevice, ROM_addr, RAM_addr,
                                        nbytes, do_activate, &rompatch_id);
            if (ret == A_OK) {
		/* return value */
		if (put_user(rompatch_id, (unsigned int *)rq->ifr_data)) {
		    ret = -EFAULT;
		    break;
		}
            }
            break;
        }

        case AR6000_XIOCTL_BMI_ROMPATCH_UNINSTALL:
        {
            A_UINT32 rompatch_id;

	    if (get_user(rompatch_id, (A_UINT32 *)userdata)) {
		ret = -EFAULT;
		break;
	    }
            AR_DEBUG_PRINTF(ATH_DEBUG_INFO,("UNinstall rompatch_id %d\n", rompatch_id));
            ret = BMIrompatchUninstall(hifDevice, rompatch_id);
            break;
        }

        case AR6000_XIOCTL_BMI_ROMPATCH_ACTIVATE:
        case AR6000_XIOCTL_BMI_ROMPATCH_DEACTIVATE:
        {
            A_UINT32 rompatch_count;

	    if (get_user(rompatch_count, (A_UINT32 *)userdata)) {
		ret = -EFAULT;
		break;
	    }
            AR_DEBUG_PRINTF(ATH_DEBUG_INFO,("Change rompatch activation count=%d\n", rompatch_count));
            length = sizeof(A_UINT32) * rompatch_count;
            if ((buffer = (unsigned char *)A_MALLOC(length)) != NULL) {
                A_MEMZERO(buffer, length);
                if (copy_from_user(buffer, &userdata[sizeof(rompatch_count)], length))
                {
                    ret = -EFAULT;
                } else {
                    if (cmd == AR6000_XIOCTL_BMI_ROMPATCH_ACTIVATE) {
                        ret = BMIrompatchActivate(hifDevice, rompatch_count, (A_UINT32 *)buffer);
                    } else {
                        ret = BMIrompatchDeactivate(hifDevice, rompatch_count, (A_UINT32 *)buffer);
                    }
                }
                A_FREE(buffer);
            } else {
                ret = -ENOMEM;
            }

            break;
        }
        case AR6000_XIOCTL_SET_IP:
        {
            WMI_SET_IP_CMD setIP;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&setIP, userdata,
                                      sizeof(setIP)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_set_ip_cmd(ar->arWmi,
                                &setIP) != A_OK)
                {
                    ret = -EIO;
                }
            }
            break;
        }

        case AR6000_XIOCTL_WMI_SET_HOST_SLEEP_MODE:
        {
            WMI_SET_HOST_SLEEP_MODE_CMD setHostSleepMode;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&setHostSleepMode, userdata,
                                      sizeof(setHostSleepMode)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_set_host_sleep_mode_cmd(ar->arWmi,
                                &setHostSleepMode) != A_OK)
                {
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_XIOCTL_WMI_SET_WOW_MODE:
        {
            WMI_SET_WOW_MODE_CMD setWowMode;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&setWowMode, userdata,
                                      sizeof(setWowMode)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_set_wow_mode_cmd(ar->arWmi,
                                &setWowMode) != A_OK)
                {
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_XIOCTL_WMI_GET_WOW_LIST:
        {
            WMI_GET_WOW_LIST_CMD getWowList;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&getWowList, userdata,
                                      sizeof(getWowList)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_get_wow_list_cmd(ar->arWmi,
                                &getWowList) != A_OK)
                {
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_XIOCTL_WMI_ADD_WOW_PATTERN:
        {
#define WOW_PATTERN_SIZE 64
#define WOW_MASK_SIZE 64

            WMI_ADD_WOW_PATTERN_CMD cmd;
            A_UINT8 mask_data[WOW_PATTERN_SIZE]={0};
            A_UINT8 pattern_data[WOW_PATTERN_SIZE]={0};

            do {
                if (ar->arWmiReady == FALSE) {
                    ret = -EIO;
                    break;        
                } 
                if(copy_from_user(&cmd, userdata,
                            sizeof(WMI_ADD_WOW_PATTERN_CMD))) 
                {
                    ret = -EFAULT;
                    break;        
                }
                if (copy_from_user(pattern_data,
                                      userdata + 3,
                                      cmd.filter_size)) 
                {
                    ret = -EFAULT;
                    break;        
                }
                if (copy_from_user(mask_data,
                                  (userdata + 3 + cmd.filter_size),
                                  cmd.filter_size))
                {
                    ret = -EFAULT;
                    break;
                }
                if (wmi_add_wow_pattern_cmd(ar->arWmi,
                            &cmd, pattern_data, mask_data, cmd.filter_size) != A_OK)
                {
                    ret = -EIO;
                }
            } while(FALSE);
#undef WOW_PATTERN_SIZE
#undef WOW_MASK_SIZE
            break;
        }
        case AR6000_XIOCTL_WMI_DEL_WOW_PATTERN:
        {
            WMI_DEL_WOW_PATTERN_CMD delWowPattern;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&delWowPattern, userdata,
                                      sizeof(delWowPattern)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_del_wow_pattern_cmd(ar->arWmi,
                                &delWowPattern) != A_OK)
                {
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_XIOCTL_DUMP_HTC_CREDIT_STATE:
            if (ar->arHtcTarget != NULL) {
#ifdef ATH_DEBUG_MODULE
                HTCDumpCreditStates(ar->arHtcTarget);
#endif /* ATH_DEBUG_MODULE */
#ifdef HTC_EP_STAT_PROFILING
                {
                    HTC_ENDPOINT_STATS stats;
                    int i;

                    for (i = 0; i < 5; i++) {
                        if (HTCGetEndpointStatistics(ar->arHtcTarget,
                                                     i,
                                                     HTC_EP_STAT_SAMPLE_AND_CLEAR,
                                                     &stats)) {
                            A_PRINTF(KERN_ALERT"------- Profiling Endpoint : %d \n", i);
                            A_PRINTF(KERN_ALERT"TxCreditLowIndications : %d \n", stats.TxCreditLowIndications);
                            A_PRINTF(KERN_ALERT"TxIssued : %d \n", stats.TxIssued);
                            A_PRINTF(KERN_ALERT"TxDropped: %d \n", stats.TxDropped);
                            A_PRINTF(KERN_ALERT"TxPacketsBundled : %d \n", stats.TxPacketsBundled);
                            A_PRINTF(KERN_ALERT"TxBundles : %d \n", stats.TxBundles);
                            A_PRINTF(KERN_ALERT"TxCreditRpts : %d \n", stats.TxCreditRpts);
                            A_PRINTF(KERN_ALERT"TxCreditsRptsFromRx : %d \n", stats.TxCreditRptsFromRx);
                            A_PRINTF(KERN_ALERT"TxCreditsRptsFromOther : %d \n", stats.TxCreditRptsFromOther);
                            A_PRINTF(KERN_ALERT"TxCreditsRptsFromEp0 : %d \n", stats.TxCreditRptsFromEp0);
                            A_PRINTF(KERN_ALERT"TxCreditsFromRx : %d \n", stats.TxCreditsFromRx);
                            A_PRINTF(KERN_ALERT"TxCreditsFromOther : %d \n", stats.TxCreditsFromOther);
                            A_PRINTF(KERN_ALERT"TxCreditsFromEp0 : %d \n", stats.TxCreditsFromEp0);
                            A_PRINTF(KERN_ALERT"TxCreditsConsummed : %d \n", stats.TxCreditsConsummed);
                            A_PRINTF(KERN_ALERT"TxCreditsReturned : %d \n", stats.TxCreditsReturned);
                            A_PRINTF(KERN_ALERT"RxReceived : %d \n", stats.RxReceived);
                            A_PRINTF(KERN_ALERT"RxPacketsBundled : %d \n", stats.RxPacketsBundled);
                            A_PRINTF(KERN_ALERT"RxLookAheads : %d \n", stats.RxLookAheads);
                            A_PRINTF(KERN_ALERT"RxBundleLookAheads : %d \n", stats.RxBundleLookAheads);
                            A_PRINTF(KERN_ALERT"RxBundleIndFromHdr : %d \n", stats.RxBundleIndFromHdr);
                            A_PRINTF(KERN_ALERT"RxAllocThreshHit : %d \n", stats.RxAllocThreshHit);
                            A_PRINTF(KERN_ALERT"RxAllocThreshBytes : %d \n", stats.RxAllocThreshBytes);
                            A_PRINTF(KERN_ALERT"---- \n");

                        }
            }
                }
#endif
            }
            break;
        case AR6000_XIOCTL_TRAFFIC_ACTIVITY_CHANGE:
            if (ar->arHtcTarget != NULL) {
                struct ar6000_traffic_activity_change data;

                if (copy_from_user(&data, userdata, sizeof(data)))
                {
                    ret = -EFAULT;
                    goto ioctl_done;
                }
                    /* note, this is used for testing (mbox ping testing), indicate activity
                     * change using the stream ID as the traffic class */
                ar6000_indicate_tx_activity(ar,
                                            (A_UINT8)data.StreamID,
                                            data.Active ? TRUE : FALSE);
            }
            break;
        case AR6000_XIOCTL_WMI_SET_CONNECT_CTRL_FLAGS:
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&connectCtrlFlags, userdata,
                                      sizeof(connectCtrlFlags)))
            {
                ret = -EFAULT;
            } else {
                ar->arConnectCtrlFlags = connectCtrlFlags;
            }
            break;
        case AR6000_XIOCTL_WMI_SET_AKMP_PARAMS:
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&akmpParams, userdata,
                                      sizeof(WMI_SET_AKMP_PARAMS_CMD)))
            {
                ret = -EFAULT;
            } else {
                if (wmi_set_akmp_params_cmd(ar->arWmi, &akmpParams) != A_OK) {
                    ret = -EIO;
                }
            }
            break;
        case AR6000_XIOCTL_WMI_SET_PMKID_LIST:
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else {
                if (copy_from_user(&pmkidInfo.numPMKID, userdata,
                                      sizeof(pmkidInfo.numPMKID)))
                {
                    ret = -EFAULT;
                    break;
                }
                if (copy_from_user(&pmkidInfo.pmkidList,
                                   userdata + sizeof(pmkidInfo.numPMKID),
                                   pmkidInfo.numPMKID * sizeof(WMI_PMKID)))
                {
                    ret = -EFAULT;
                    break;
                }
                if (wmi_set_pmkid_list_cmd(ar->arWmi, &pmkidInfo) != A_OK) {
                    ret = -EIO;
                }
            }
            break;
        case AR6000_XIOCTL_WMI_GET_PMKID_LIST:
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else  {
                if (wmi_get_pmkid_list_cmd(ar->arWmi) != A_OK) {
                    ret = -EIO;
                }
            }
            break;
        case AR6000_XIOCTL_WMI_ABORT_SCAN:
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            }
            ret = wmi_abort_scan_cmd(ar->arWmi);
            break;
        case AR6000_XIOCTL_AP_HIDDEN_SSID:
        {
            A_UINT8    hidden_ssid;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&hidden_ssid, userdata, sizeof(hidden_ssid))) {
                ret = -EFAULT;
            } else {
                wmi_ap_set_hidden_ssid(ar->arWmi, hidden_ssid);
                ar->ap_hidden_ssid = hidden_ssid;
                ar->ap_profile_flag = 1; /* There is a change in profile */
            }
            break;
        }
        case AR6000_XIOCTL_AP_GET_STA_LIST:
        {
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else {
                A_UINT8 i;
                ap_get_sta_t temp;
                A_MEMZERO(&temp, sizeof(temp));
                for(i=0;i<AP_MAX_NUM_STA;i++) {
                    A_MEMCPY(temp.sta[i].mac, ar->sta_list[i].mac, ATH_MAC_LEN);
                    temp.sta[i].aid = ar->sta_list[i].aid;
                    temp.sta[i].keymgmt = ar->sta_list[i].keymgmt;
                    temp.sta[i].ucipher = ar->sta_list[i].ucipher;
                    temp.sta[i].auth = ar->sta_list[i].auth;
                }
                if(copy_to_user((ap_get_sta_t *)rq->ifr_data, &temp,
                                 sizeof(ar->sta_list))) {
                    ret = -EFAULT;
                }
            }
            break;
        }
        case AR6000_XIOCTL_AP_SET_NUM_STA:
        {
            A_UINT8    num_sta;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&num_sta, userdata, sizeof(num_sta))) {
                ret = -EFAULT;
            } else if(num_sta > AP_MAX_NUM_STA) {
                /* value out of range */
                ret = -EINVAL;
            } else {
                wmi_ap_set_num_sta(ar->arWmi, num_sta);
            }
            break;
        }
        case AR6000_XIOCTL_AP_SET_ACL_POLICY:
        {
            A_UINT8    policy;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&policy, userdata, sizeof(policy))) {
                ret = -EFAULT;
            } else if(policy == ar->g_acl.policy) {
                /* No change in policy */
            } else {
                if(!(policy & AP_ACL_RETAIN_LIST_MASK)) {
                    /* clear ACL list */
                    memset(&ar->g_acl,0,sizeof(WMI_AP_ACL));
                }
                ar->g_acl.policy = policy;
                wmi_ap_set_acl_policy(ar->arWmi, policy);
            }
            break;
        }
        case AR6000_XIOCTL_AP_SET_ACL_MAC:
        {
            WMI_AP_ACL_MAC_CMD    acl;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&acl, userdata, sizeof(acl))) {
                ret = -EFAULT;
            } else {
                if(acl_add_del_mac(&ar->g_acl, &acl)) {
                    wmi_ap_acl_mac_list(ar->arWmi, &acl);
                } else {
                    A_PRINTF("ACL list error\n");
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_XIOCTL_AP_GET_ACL_LIST:
        {
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if(copy_to_user((WMI_AP_ACL *)rq->ifr_data, &ar->g_acl,
                                 sizeof(WMI_AP_ACL))) {
                    ret = -EFAULT;
            }
            break;
        }
        case AR6000_XIOCTL_AP_COMMIT_CONFIG:
        {
            ret = ar6000_ap_mode_profile_commit(ar);
            break;
        }
        case IEEE80211_IOCTL_GETWPAIE:
        {
            struct ieee80211req_wpaie wpaie;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&wpaie, userdata, sizeof(wpaie))) {
                ret = -EFAULT;
            } else if (ar6000_ap_mode_get_wpa_ie(ar, &wpaie)) {
                ret = -EFAULT;
            } else if(copy_to_user(userdata, &wpaie, sizeof(wpaie))) {
                ret = -EFAULT;
            }
            break;
        }
        case AR6000_XIOCTL_AP_CONN_INACT_TIME:
        {
            A_UINT32    period;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&period, userdata, sizeof(period))) {
                ret = -EFAULT;
            } else {
                wmi_ap_conn_inact_time(ar->arWmi, period);
            }
            break;
        }
        case AR6000_XIOCTL_AP_PROT_SCAN_TIME:
        {
            WMI_AP_PROT_SCAN_TIME_CMD  bgscan;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&bgscan, userdata, sizeof(bgscan))) {
                ret = -EFAULT;
            } else {
                wmi_ap_bgscan_time(ar->arWmi, bgscan.period_min, bgscan.dwell_ms);
            }
            break;
        }
        case AR6000_XIOCTL_AP_SET_COUNTRY:
        {
            ret = ar6000_ioctl_set_country(dev, rq);
            break;
        }
        case AR6000_XIOCTL_AP_SET_DTIM:
        {
            WMI_AP_SET_DTIM_CMD  d;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&d, userdata, sizeof(d))) {
                ret = -EFAULT;
            } else {
                if(d.dtim > 0 && d.dtim < 11) {
                    ar->ap_dtim_period = d.dtim;
                    wmi_ap_set_dtim(ar->arWmi, d.dtim);
                    ar->ap_profile_flag = 1; /* There is a change in profile */
                } else {
                    A_PRINTF("DTIM out of range. Valid range is [1-10]\n");
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_XIOCTL_WMI_TARGET_EVENT_REPORT:
        {
            WMI_SET_TARGET_EVENT_REPORT_CMD evtCfgCmd;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            }
            if (copy_from_user(&evtCfgCmd, userdata,
                               sizeof(evtCfgCmd))) {
                ret = -EFAULT;
                break;
            }
            ret = wmi_set_target_event_report_cmd(ar->arWmi, &evtCfgCmd);
            break;
        }
        case AR6000_XIOCTL_AP_INTRA_BSS_COMM:
        {
            A_UINT8    intra=0;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&intra, userdata, sizeof(intra))) {
                ret = -EFAULT;
            } else {
                ar->intra_bss = (intra?1:0);
            }
            break;
        }
        case AR6000_XIOCTL_DUMP_MODULE_DEBUG_INFO:
        {
            struct drv_debug_module_s moduleinfo;

            if (copy_from_user(&moduleinfo, userdata, sizeof(moduleinfo))) {
                ret = -EFAULT;
                break;
            }

            a_dump_module_debug_info_by_name(moduleinfo.modulename);
            ret = 0;
            break;
        }
        case AR6000_XIOCTL_MODULE_DEBUG_SET_MASK:
        {
            struct drv_debug_module_s moduleinfo;

            if (copy_from_user(&moduleinfo, userdata, sizeof(moduleinfo))) {
                ret = -EFAULT;
                break;
            }

            if (A_FAILED(a_set_module_mask(moduleinfo.modulename, moduleinfo.mask))) {
                ret = -EFAULT;
            }

            break;
        }
        case AR6000_XIOCTL_MODULE_DEBUG_GET_MASK:
        {
            struct drv_debug_module_s moduleinfo;

            if (copy_from_user(&moduleinfo, userdata, sizeof(moduleinfo))) {
                ret = -EFAULT;
                break;
            }

            if (A_FAILED(a_get_module_mask(moduleinfo.modulename, &moduleinfo.mask))) {
                ret = -EFAULT;
                break;
            }

            if (copy_to_user(userdata, &moduleinfo, sizeof(moduleinfo))) {
                ret = -EFAULT;
                break;
            }

            break;
        }
#ifdef ATH_AR6K_11N_SUPPORT
        case AR6000_XIOCTL_DUMP_RCV_AGGR_STATS:
        {
            PACKET_LOG *copy_of_pkt_log;

            aggr_dump_stats(ar->aggr_cntxt, &copy_of_pkt_log);
            if (copy_to_user(rq->ifr_data, copy_of_pkt_log, sizeof(PACKET_LOG))) {
                ret = -EFAULT;
            }
            break;
        }
        case AR6000_XIOCTL_SETUP_AGGR:
        {
            WMI_ADDBA_REQ_CMD cmd;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&cmd, userdata, sizeof(cmd))) {
                ret = -EFAULT;
            } else {
                wmi_setup_aggr_cmd(ar->arWmi, cmd.tid);
            }
        }
        break;

        case AR6000_XIOCTL_DELE_AGGR:
        {
            WMI_DELBA_REQ_CMD cmd;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&cmd, userdata, sizeof(cmd))) {
                ret = -EFAULT;
            } else {
                wmi_delete_aggr_cmd(ar->arWmi, cmd.tid, cmd.is_sender_initiator);
            }
        }
        break;

        case AR6000_XIOCTL_ALLOW_AGGR:
        {
            WMI_ALLOW_AGGR_CMD cmd;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&cmd, userdata, sizeof(cmd))) {
                ret = -EFAULT;
            } else {
                wmi_allow_aggr_cmd(ar->arWmi, cmd.tx_allow_aggr, cmd.rx_allow_aggr);
            }
        }
        break;

        case AR6000_XIOCTL_SET_HT_CAP:
        {
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&htCap, userdata,
                                      sizeof(htCap)))
            {
                ret = -EFAULT;
            } else {

                if (wmi_set_ht_cap_cmd(ar->arWmi, &htCap) != A_OK)
                {
                    ret = -EIO;
                }
            }
            break;
        }
        case AR6000_XIOCTL_SET_HT_OP:
        {
             if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&htOp, userdata,
                                      sizeof(htOp)))
            {
                 ret = -EFAULT;
             } else {

                if (wmi_set_ht_op_cmd(ar->arWmi, htOp.sta_chan_width) != A_OK)
                {
                     ret = -EIO;
               }
             }
             break;
        }
#endif
        case AR6000_XIOCTL_ACL_DATA:
        {
            void *osbuf = NULL;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (ar6000_create_acl_data_osbuf(dev, (A_UINT8*)userdata, &osbuf) != A_OK) {
                     ret = -EIO;
            } else {
                if (wmi_data_hdr_add(ar->arWmi, osbuf, DATA_MSGTYPE, 0, WMI_DATA_HDR_DATA_TYPE_ACL,0,NULL) != A_OK) {
                    AR_DEBUG_PRINTF(ATH_DEBUG_ERR,("XIOCTL_ACL_DATA - wmi_data_hdr_add failed\n"));
                } else {
                    /* Send data buffer over HTC */
                    ar6000_acl_data_tx(osbuf, ar->arNetDev);
                }
            }
            break;
        }
        case AR6000_XIOCTL_HCI_CMD:
        {
            char tmp_buf[512];
            A_INT8 i;
            WMI_HCI_CMD *cmd = (WMI_HCI_CMD *)tmp_buf;
            A_UINT8 size;

            size = sizeof(cmd->cmd_buf_sz);
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(cmd, userdata, size)) {
                 ret = -EFAULT;
            } else if(copy_from_user(cmd->buf, userdata + size, cmd->cmd_buf_sz)) {
                    ret = -EFAULT;
            } else {
                if (wmi_send_hci_cmd(ar->arWmi, cmd->buf, cmd->cmd_buf_sz) != A_OK) {
                     ret = -EIO;
                }else if(loghci) {
                    A_PRINTF_LOG("HCI Command To PAL --> \n");
                    for(i = 0; i < cmd->cmd_buf_sz; i++) {
                        A_PRINTF_LOG("0x%02x ",cmd->buf[i]);
                        if((i % 10) == 0) {
                            A_PRINTF_LOG("\n");
                        }
                    }
                    A_PRINTF_LOG("\n");
                    A_PRINTF_LOG("==================================\n");
                }
            }
            break;
        }
        case AR6000_XIOCTL_WLAN_CONN_PRECEDENCE:
        {
            WMI_SET_BT_WLAN_CONN_PRECEDENCE cmd;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&cmd, userdata, sizeof(cmd))) {
                ret = -EFAULT;
            } else {
                if (cmd.precedence == BT_WLAN_CONN_PRECDENCE_WLAN ||
                            cmd.precedence == BT_WLAN_CONN_PRECDENCE_PAL) {
                    if ( wmi_set_wlan_conn_precedence_cmd(ar->arWmi, cmd.precedence) != A_OK) {
                        ret = -EIO;
                    }
                } else {
                    ret = -EINVAL;
                }
            }
            break;
        }
        case AR6000_XIOCTL_AP_GET_STAT:
        {
            ret = ar6000_ioctl_get_ap_stats(dev, rq);
            break;
        }
        case AR6000_XIOCTL_SET_TX_SELECT_RATES:
        {
            WMI_SET_TX_SELECT_RATES_CMD masks;

             if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&masks, userdata,
                                      sizeof(masks)))
            {
                 ret = -EFAULT;
             } else {

                if (wmi_set_tx_select_rates_cmd(ar->arWmi, masks.rateMasks) != A_OK)
                {
                     ret = -EIO;
               }
             }
             break;
        }
        case AR6000_XIOCTL_AP_GET_HIDDEN_SSID:
        {
            WMI_AP_HIDDEN_SSID_CMD ssid;
            ssid.hidden_ssid = ar->ap_hidden_ssid;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if(copy_to_user((WMI_AP_HIDDEN_SSID_CMD *)rq->ifr_data,
                                    &ssid, sizeof(WMI_AP_HIDDEN_SSID_CMD))) {
                    ret = -EFAULT;
            }
            break;
        }
        case AR6000_XIOCTL_AP_GET_COUNTRY:
        {
            WMI_AP_SET_COUNTRY_CMD cty;
            A_MEMCPY(cty.countryCode, ar->ap_country_code, 3);

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if(copy_to_user((WMI_AP_SET_COUNTRY_CMD *)rq->ifr_data,
                                    &cty, sizeof(WMI_AP_SET_COUNTRY_CMD))) {
                    ret = -EFAULT;
            }
            break;
        }
        case AR6000_XIOCTL_AP_GET_WMODE:
        {
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if(copy_to_user((A_UINT8 *)rq->ifr_data,
                                    &ar->ap_wmode, sizeof(A_UINT8))) {
                    ret = -EFAULT;
            }
            break;
        }
        case AR6000_XIOCTL_AP_GET_DTIM:
        {
            WMI_AP_SET_DTIM_CMD dtim;
            dtim.dtim = ar->ap_dtim_period;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if(copy_to_user((WMI_AP_SET_DTIM_CMD *)rq->ifr_data,
                                    &dtim, sizeof(WMI_AP_SET_DTIM_CMD))) {
                    ret = -EFAULT;
            }
            break;
        }
        case AR6000_XIOCTL_AP_GET_BINTVL:
        {
            WMI_BEACON_INT_CMD bi;
            bi.beaconInterval = ar->ap_beacon_interval;

            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if(copy_to_user((WMI_BEACON_INT_CMD *)rq->ifr_data,
                                    &bi, sizeof(WMI_BEACON_INT_CMD))) {
                    ret = -EFAULT;
            }
            break;
        }
        case AR6000_XIOCTL_AP_GET_RTS:
        {
            WMI_SET_RTS_CMD rts;
            rts.threshold = ar->arRTS;
	     
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if(copy_to_user((WMI_SET_RTS_CMD *)rq->ifr_data,
                                    &rts, sizeof(WMI_SET_RTS_CMD))) {
                    ret = -EFAULT;
            }
            break;
        }
        case AR6000_XIOCTL_FETCH_TARGET_REGS:
        {
            A_UINT32 targregs[AR6003_FETCH_TARG_REGS_COUNT];

            if (ar->arTargetType == TARGET_TYPE_AR6003) {
                ar6k_FetchTargetRegs(hifDevice, targregs);
                if (copy_to_user((A_UINT32 *)rq->ifr_data, &targregs, sizeof(targregs)))
                {
                    ret = -EFAULT;
                }
            } else {
                ret = -EOPNOTSUPP;
            }
            break;
        }
        case AR6000_XIOCTL_AP_SET_11BG_RATESET:
        {
            WMI_AP_SET_11BG_RATESET_CMD  rate;
            if (ar->arWmiReady == FALSE) {
                ret = -EIO;
            } else if (copy_from_user(&rate, userdata, sizeof(rate))) {
                ret = -EFAULT;
            } else {
                wmi_ap_set_rateset(ar->arWmi, rate.rateset);
            }
            break;
        }
        case AR6000_XIOCTL_GET_WLAN_SLEEP_STATE:
        {
            WMI_REPORT_SLEEP_STATE_EVENT  wmiSleepEvent ;

            if (ar->arWlanState == WLAN_ENABLED) {
                wmiSleepEvent.sleepState = WMI_REPORT_SLEEP_STATUS_IS_AWAKE;
            } else {
                wmiSleepEvent.sleepState = WMI_REPORT_SLEEP_STATUS_IS_DEEP_SLEEP;
            }
            rq->ifr_ifru.ifru_ivalue = ar->arWlanState; /* return value */

            ar6000_send_event_to_app(ar, WMI_REPORT_SLEEP_STATE_EVENTID, (A_UINT8*)&wmiSleepEvent,
                                     sizeof(WMI_REPORT_SLEEP_STATE_EVENTID));
            break;
        }
#ifdef CONFIG_PM
        case AR6000_XIOCTL_SET_BT_HW_POWER_STATE:
        {
            unsigned int state;
	    if (get_user(state, (unsigned int *)userdata)) {
		ret = -EFAULT;
		break;
	    }
            if (ar6000_set_bt_hw_state(ar, state)!=A_OK) {
                ret = -EIO;
            }       
        }
            break;
        case AR6000_XIOCTL_GET_BT_HW_POWER_STATE:
            rq->ifr_ifru.ifru_ivalue = !ar->arBTOff; /* return value */
            break;
#endif

        case AR6000_XIOCTL_WMI_SET_TX_SGI_PARAM:
        {
             WMI_SET_TX_SGI_PARAM_CMD SGICmd;

             if (ar->arWmiReady == FALSE) {
                 ret = -EIO;
             } else if (copy_from_user(&SGICmd, userdata,
                                       sizeof(SGICmd))){
                 ret = -EFAULT;
             } else{
                     if (wmi_SGI_cmd(ar->arWmi, SGICmd.sgiMask, SGICmd.sgiPERThreshold) != A_OK) {
                         ret = -EIO;
                     }

             }
             break;
        }

        case AR6000_XIOCTL_ADD_AP_INTERFACE:
#ifdef CONFIG_AP_VIRTUAL_ADAPTER_SUPPORT
        {
            char ap_ifname[IFNAMSIZ] = {0,};
            if (copy_from_user(ap_ifname, userdata, IFNAMSIZ)) {
                ret = -EFAULT;
            } else {
                if (ar6000_add_ap_interface(ar, ap_ifname) != A_OK) {
                    ret = -EIO;
                } 
            }
        }
#else
            ret = -EOPNOTSUPP;
#endif
            break;
        case AR6000_XIOCTL_REMOVE_AP_INTERFACE:
#ifdef CONFIG_AP_VIRTUAL_ADAPTER_SUPPORT
            if (ar6000_remove_ap_interface(ar) != A_OK) {
                ret = -EIO;
            } 
#else
            ret = -EOPNOTSUPP;
#endif
            break;

        default:
            ret = -EOPNOTSUPP;
    }

ioctl_done:
    rtnl_lock(); /* restore rtnl state */
    dev_put(dev);

    return ret;
}

Generated by GNU enscript 1.6.4.