From 1d23dacdbd6b3a2b59b952f2fa3a578f9d15f60f Mon Sep 17 00:00:00 2001 From: Arif Hussain Date: Mon, 11 Nov 2013 22:59:34 -0800 Subject: wlan: wlan_hdd_wext Userspace data copy fix Use copy_to_user and copy_from_user for copying data to/from user space. Change-Id: I98fb6352b654af8f78160738e7ccd902c3c70031 CRs-Fixed: 561028 --- CORE/HDD/src/wlan_hdd_wext.c | 75 +++++++++++++++++++++++++------------------- 1 file changed, 42 insertions(+), 33 deletions(-) diff --git a/CORE/HDD/src/wlan_hdd_wext.c b/CORE/HDD/src/wlan_hdd_wext.c index 83107e1..1e9ba2e 100644 --- a/CORE/HDD/src/wlan_hdd_wext.c +++ b/CORE/HDD/src/wlan_hdd_wext.c @@ -1529,7 +1529,7 @@ static int iw_set_genie(struct net_device *dev, { hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev); hdd_wext_state_t *pWextState = WLAN_HDD_GET_WEXT_STATE_PTR(pAdapter); - u_int8_t *genie; + u_int8_t *genie = (u_int8_t *)extra; v_U16_t remLen; ENTER(); @@ -1544,7 +1544,6 @@ static int iw_set_genie(struct net_device *dev, return 0; } - genie = wrqu->data.pointer; remLen = wrqu->data.length; hddLog(LOG1,"iw_set_genie ioctl IE[0x%X], LEN[%d]\n", genie[0], genie[1]); @@ -1672,9 +1671,14 @@ static int iw_get_genie(struct net_device *dev, pAdapter->sessionId, &length, genIeBytes); - wrqu->data.length = VOS_MIN((u_int16_t) length, DOT11F_IE_RSN_MAX_LEN); - - vos_mem_copy( wrqu->data.pointer, (v_VOID_t*)genIeBytes, wrqu->data.length); + length = VOS_MIN((u_int16_t) length, DOT11F_IE_RSN_MAX_LEN); + if (wrqu->data.length < length) + { + hddLog(LOG1, "%s: failed to copy data to user buffer", __func__); + return -EFAULT; + } + vos_mem_copy( extra, (v_VOID_t*)genIeBytes, wrqu->data.length); + wrqu->data.length = length; hddLog(LOG1,"%s: RSN IE of %d bytes returned\n", __func__, wrqu->data.length ); @@ -2364,7 +2368,7 @@ static int iw_get_rssi(struct net_device *dev, union iwreq_data *wrqu, char *extra) { hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev); - char *cmd = (char*)wrqu->data.pointer; + char *cmd = extra; int len = wrqu->data.length; v_S7_t s7Rssi = 0; hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter); @@ -2621,7 +2625,7 @@ static int iw_set_priv(struct net_device *dev, union iwreq_data *wrqu, char *extra) { hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev); - char *cmd = (char*)wrqu->data.pointer; + char *cmd = extra; int cmd_len = wrqu->data.length; int ret = 0; int status = 0; @@ -2875,6 +2879,16 @@ done: /* there was an encoding error or overflow */ status = -EIO; } + else if (ret > 0) + { + if (copy_to_user(wrqu->data.pointer, cmd, ret)) + { + hddLog(VOS_TRACE_LEVEL_ERROR, + "%s: failed to copy data to user buffer", __func__); + return -EFAULT; + } + wrqu->data.length = ret; + } if (ioctl_debug) { @@ -2882,7 +2896,6 @@ done: __func__, cmd, wrqu->data.length, status); } return status; - } static int iw_set_nick(struct net_device *dev, @@ -3827,7 +3840,7 @@ static int iw_setchar_getnone(struct net_device *dev, struct iw_request_info *in #endif /* WLAN_FEATURE_VOWIFI */ VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO, "%s: Received length %d", __func__, wrqu->data.length); - VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO, "%s: Received data %s", __func__, (char*)wrqu->data.pointer); + VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO, "%s: Received data %s", __func__, extra); if ((WLAN_HDD_GET_CTX(pAdapter))->isLogpInProgress) { @@ -3840,11 +3853,11 @@ static int iw_setchar_getnone(struct net_device *dev, struct iw_request_info *in { case WE_WOWL_ADD_PTRN: VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO, "ADD_PTRN\n"); - hdd_add_wowl_ptrn(pAdapter, (char*)wrqu->data.pointer); + hdd_add_wowl_ptrn(pAdapter, extra); break; case WE_WOWL_DEL_PTRN: VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO, "DEL_PTRN\n"); - hdd_del_wowl_ptrn(pAdapter, (char*)wrqu->data.pointer); + hdd_del_wowl_ptrn(pAdapter, extra); break; #if defined WLAN_FEATURE_VOWIFI case WE_NEIGHBOR_REPORT_REQUEST: @@ -3859,7 +3872,7 @@ static int iw_setchar_getnone(struct net_device *dev, struct iw_request_info *in if( !neighborReq.no_ssid ) { neighborReq.ssid.length = (wrqu->data.length - 1) > 32 ? 32 : (wrqu->data.length - 1) ; - vos_mem_copy( neighborReq.ssid.ssId, wrqu->data.pointer, neighborReq.ssid.length ); + vos_mem_copy( neighborReq.ssid.ssId, extra, neighborReq.ssid.length ); } callbackInfo.neighborRspCallback = NULL; @@ -3877,10 +3890,10 @@ static int iw_setchar_getnone(struct net_device *dev, struct iw_request_info *in #endif case WE_SET_AP_WPS_IE: hddLog( LOGE, "Received WE_SET_AP_WPS_IE" ); - sme_updateP2pIe( WLAN_HDD_GET_HAL_CTX(pAdapter), wrqu->data.pointer, wrqu->data.length ); + sme_updateP2pIe( WLAN_HDD_GET_HAL_CTX(pAdapter), extra, wrqu->data.length ); break; case WE_SET_CONFIG: - vstatus = hdd_execute_config_command(pHddCtx, wrqu->data.pointer); + vstatus = hdd_execute_config_command(pHddCtx, extra); if (VOS_STATUS_SUCCESS != vstatus) { ret = -EINVAL; @@ -4400,7 +4413,7 @@ int iw_set_var_ints_getnone(struct net_device *dev, struct iw_request_info *info hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev); tHalHandle hHal = WLAN_HDD_GET_HAL_CTX(pAdapter); int sub_cmd = wrqu->data.flags; - int *value = (int*)wrqu->data.pointer; + int *value = (int*)extra; int apps_args[MAX_VAR_ARGS] = {0}; int num_args = wrqu->data.length; hdd_station_ctx_t *pStaCtx = NULL ; @@ -4751,10 +4764,10 @@ static int iw_qcom_set_wapi_mode(struct net_device *dev, struct iw_request_info hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter); tCsrRoamProfile *pRoamProfile = &pWextState->roamProfile; - WAPI_FUNCTION_MODE *pWapiMode = (WAPI_FUNCTION_MODE *)wrqu->data.pointer; + WAPI_FUNCTION_MODE *pWapiMode = (WAPI_FUNCTION_MODE *)extra; hddLog(LOG1, "The function iw_qcom_set_wapi_mode called"); - hddLog(LOG1, "%s: Received data %s", __func__, (char*)wrqu->data.pointer); + hddLog(LOG1, "%s: Received data %s", __func__, extra); hddLog(LOG1, "%s: Received length %d", __func__, wrqu->data.length); hddLog(LOG1, "%s: Input Data (wreq) WAPI Mode:%02d", __func__, pWapiMode->wapiMode); @@ -4817,7 +4830,6 @@ static int iw_qcom_set_wapi_assoc_info(struct net_device *dev, struct iw_request int i = 0, j = 0; hddLog(LOG1, "The function iw_qcom_set_wapi_assoc_info called"); hddLog(LOG1, "%s: Received length %d", __func__, wrqu->data.length); - hddLog(LOG1, "%s: Received data %s", __func__, (char*)wrqu->data.pointer); hddLog(LOG1, "%s: Received data %s", __func__, (char*)extra); if ((WLAN_HDD_GET_CTX(pAdapter))->isLogpInProgress) @@ -4883,7 +4895,6 @@ static int iw_qcom_set_wapi_key(struct net_device *dev, struct iw_request_info * hddLog(LOG1, "The function iw_qcom_set_wapi_key called "); hddLog(LOG1, "%s: Received length %d", __func__, wrqu->data.length); - hddLog(LOG1, "%s: Received data %s", __func__, (char*)wrqu->data.pointer); hddLog(LOG1, "%s: Received data %s", __func__, (char*)extra); hddLog(LOG1,":s: INPUT DATA:\nKey Type:0x%02x Key Direction:0x%02x KEY ID:0x%02x\n", __func__,pWapiKey->keyType,pWapiKey->keyDirection,pWapiKey->keyId); @@ -4984,12 +4995,11 @@ static int iw_qcom_set_wapi_bkid(struct net_device *dev, struct iw_request_info hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev); #ifdef WLAN_DEBUG int i = 0; - WLAN_BKID_LIST *pBkid = ( WLAN_BKID_LIST *) (wrqu->data.pointer); + WLAN_BKID_LIST *pBkid = ( WLAN_BKID_LIST *) extra; #endif hddLog(LOG1, "The function iw_qcom_set_wapi_bkid called"); hddLog(LOG1, "%s: Received length %d", __func__, wrqu->data.length); - hddLog(LOG1, "%s: Received data %s", __func__, (char*)wrqu->data.pointer); hddLog(LOG1, "%s: Received data %s", __func__, (char*)extra); hddLog(LOG1,"%s: INPUT DATA:\n BKID Length:0x%08lx\n", __func__,pBkid->length); @@ -5066,7 +5076,7 @@ static int iw_set_fties(struct net_device *dev, struct iw_request_info *info, #endif // Pass the received FT IEs to SME - sme_SetFTIEs( WLAN_HDD_GET_HAL_CTX(pAdapter), pAdapter->sessionId, wrqu->data.pointer, + sme_SetFTIEs( WLAN_HDD_GET_HAL_CTX(pAdapter), pAdapter->sessionId, extra, wrqu->data.length); return 0; @@ -5078,7 +5088,7 @@ static int iw_set_dynamic_mcbc_filter(struct net_device *dev, union iwreq_data *wrqu, char *extra) { hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev); - tpRcvFltMcAddrList pRequest = (tpRcvFltMcAddrList)wrqu->data.pointer; + tpRcvFltMcAddrList pRequest = (tpRcvFltMcAddrList)extra; hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter); tpSirWlanSetRxpFilters wlanRxpFilterParam; tHalHandle hHal = WLAN_HDD_GET_HAL_CTX(pAdapter); @@ -5227,7 +5237,7 @@ static int iw_set_host_offload(struct net_device *dev, struct iw_request_info *i union iwreq_data *wrqu, char *extra) { hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev); - tpHostOffloadRequest pRequest = (tpHostOffloadRequest)wrqu->data.pointer; + tpHostOffloadRequest pRequest = (tpHostOffloadRequest) extra; tSirHostOffloadReq offloadRequest; if ((WLAN_HDD_GET_CTX(pAdapter))->isLogpInProgress) @@ -5236,7 +5246,6 @@ static int iw_set_host_offload(struct net_device *dev, struct iw_request_info *i "%s:LOGP in Progress. Ignore!!!", __func__); return -EBUSY; } - /* Debug display of request components. */ switch (pRequest->offloadType) { @@ -5299,7 +5308,7 @@ static int iw_set_keepalive_params(struct net_device *dev, struct iw_request_inf union iwreq_data *wrqu, char *extra) { hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev); - tpKeepAliveRequest pRequest = (tpKeepAliveRequest)wrqu->data.pointer; + tpKeepAliveRequest pRequest = (tpKeepAliveRequest) extra; tSirKeepAliveReq keepaliveRequest; if ((WLAN_HDD_GET_CTX(pAdapter))->isLogpInProgress) @@ -5500,7 +5509,7 @@ static int iw_set_packet_filter_params(struct net_device *dev, struct iw_request union iwreq_data *wrqu, char *extra) { hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev); - tpPacketFilterCfg pRequest = (tpPacketFilterCfg)wrqu->data.pointer; + tpPacketFilterCfg pRequest = (tpPacketFilterCfg) extra; return wlan_hdd_set_filter(WLAN_HDD_GET_CTX(pAdapter), pRequest, pAdapter->sessionId); } @@ -5733,7 +5742,7 @@ VOS_STATUS iw_set_pno(struct net_device *dev, struct iw_request_info *info, VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO, "PNO data len %d data %s", wrqu->data.length, - wrqu->data.pointer); + extra); if (wrqu->data.length <= nOffset ) { @@ -5771,7 +5780,7 @@ VOS_STATUS iw_set_pno(struct net_device *dev, struct iw_request_info *info, scan every 5 seconds 2 times, scan every 300 seconds until stopped -----------------------------------------------------------------------*/ - ptr = (char*)(wrqu->data.pointer + nOffset); + ptr = extra + nOffset; sscanf(ptr,"%hhu%n", &(pnoRequest.enable), &nOffset); @@ -5982,7 +5991,7 @@ VOS_STATUS iw_set_rssi_filter(struct net_device *dev, struct iw_request_info *in v_U8_t rssiThreshold = 0; v_U8_t nRead; - nRead = sscanf(wrqu->data.pointer + nOffset,"%hhu", + nRead = sscanf(extra + nOffset,"%hhu", &rssiThreshold); if ( 1 != nRead ) @@ -6143,7 +6152,7 @@ static int iw_set_band_config(struct net_device *dev, union iwreq_data *wrqu, char *extra) { hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev); - tANI_U8 *ptr = (tANI_U8*)wrqu->data.pointer; + tANI_U8 *ptr = extra; int ret = 0; VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_ERROR,"%s: ", __func__); @@ -6190,7 +6199,7 @@ VOS_STATUS iw_set_power_params(struct net_device *dev, struct iw_request_info *i VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO, "Power Params data len %d data %s", wrqu->data.length, - wrqu->data.pointer); + extra); if ((WLAN_HDD_GET_CTX(pAdapter))->isLogpInProgress) { @@ -6232,7 +6241,7 @@ VOS_STATUS iw_set_power_params(struct net_device *dev, struct iw_request_info *i powerRequest.uEnableBET = SIR_NOCHANGE_POWER_VALUE; powerRequest.uBETInterval = SIR_NOCHANGE_POWER_VALUE; - ptr = (char*)(wrqu->data.pointer + nOffset); + ptr = extra + nOffset; while ( uTotalSize ) { -- cgit v1.1