/*
 * Copyright (c) 2012, Code Aurora Forum. All rights reserved.
 *
 * Previously licensed under the ISC license by Qualcomm Atheros, Inc.
 *
 *
 * Permission to use, copy, modify, and/or distribute this software for
 * any purpose with or without fee is hereby granted, provided that the
 * above copyright notice and this permission notice appear in all
 * copies.
 *
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
 * PERFORMANCE OF THIS SOFTWARE.
 */

/*
 *
 * Airgo Networks, Inc proprietary. All rights reserved.
 * This file utilsParser.cc contains the code for parsing
 * 802.11 messages.
 * Author:        Pierre Vandwalle
 * Date:          03/18/02
 * History:-
 * Date           Modified by    Modification Information
 * --------------------------------------------------------------------
 *
 */

#include "aniGlobal.h"
#include "utilsParser.h"
#include "limSerDesUtils.h"

void ConvertSSID(tpAniSirGlobal pMac,
                       tSirMacSSid   *pOld,
                       tDot11fIESSID    *pNew)
{
    pOld->length = pNew->num_ssid;
    palCopyMemory( pMac->hHdd, pOld->ssId, pNew->ssid, pNew->num_ssid );
}

void ConvertSuppRates(tpAniSirGlobal   pMac,
                            tSirMacRateSet  *pOld,
                            tDot11fIESuppRates *pNew)
{
    pOld->numRates = pNew->num_rates;
    palCopyMemory( pMac->hHdd, pOld->rate, pNew->rates, pNew->num_rates );
}

void ConvertExtSuppRates(tpAniSirGlobal      pMac,
                               tSirMacRateSet     *pOld,
                               tDot11fIEExtSuppRates *pNew)
{
    pOld->numRates = pNew->num_rates;
    palCopyMemory( pMac->hHdd, pOld->rate, pNew->rates, pNew->num_rates );
}


void ConvertQOSCaps(tpAniSirGlobal                pMac,
                          tSirMacQosCapabilityIE *pOld,
                          tDot11fIEQOSCapsAp     *pNew)
{
    pOld->type    = 46;
    pOld->length  = 1;

    pOld->qosInfo.count   = pNew->count;   
}


void ConvertQOSCapsStation(tpAniSirGlobal              pMac,
                           tSirMacQosCapabilityStaIE  *pOld,
                           tDot11fIEQOSCapsStation    *pNew)
{
    pOld->type    = 46;
    pOld->length  = 1;

    pOld->qosInfo.moreDataAck = pNew->more_data_ack;
    pOld->qosInfo.maxSpLen    = pNew->max_sp_length;
    pOld->qosInfo.qack        = pNew->qack;
    pOld->qosInfo.acbe_uapsd  = pNew->acbe_uapsd;
    pOld->qosInfo.acbk_uapsd  = pNew->acbk_uapsd;
    pOld->qosInfo.acvi_uapsd  = pNew->acvi_uapsd;
    pOld->qosInfo.acvo_uapsd  = pNew->acvo_uapsd;    
}

tSirRetStatus ConvertWPA(tpAniSirGlobal  pMac,
                               tSirMacWpaInfo *pOld,
                               tDot11fIEWPA      *pNew)
{
    // This is awful, I know, but the old code just rammed the IE into an
    // array...
    tANI_U8 buffer[257];
    tANI_U32 status, written = 0, nbuffer = 257;
    status = dot11fPackIeWPA( pMac, pNew, buffer, nbuffer, &written );
    if ( DOT11F_FAILED( status ) )
    {
        dot11fLog(pMac, LOG2, FL("Failed to re-pack the WPA IE (0x%0x"
                                 "8).\n"), status);
        return eSIR_FAILURE;
    }

    pOld->length = (tANI_U8)written - 2;
    palCopyMemory( pMac->hHdd, pOld->info, buffer + 2, pOld->length );

    return eSIR_SUCCESS;
}

tSirRetStatus ConvertWPAOpaque( tpAniSirGlobal      pMac,
                                tSirMacWpaInfo     *pOld,
                                tDot11fIEWPAOpaque *pNew )
{
    // This is awful, I know, but the old code just rammed the IE into
    // an opaque array.  Note that we need to explicitly add the OUI!
    pOld->length    = pNew->num_data + 4;
    pOld->info[ 0 ] = 0x00;
    pOld->info[ 1 ] = 0x50;
    pOld->info[ 2 ] = 0xf2;
    pOld->info[ 3 ] = 0x01;
    palCopyMemory( pMac->hHdd, pOld->info + 4, pNew->data, pNew->num_data );

    return eSIR_SUCCESS;
}

tSirRetStatus ConvertWscOpaque( tpAniSirGlobal      pMac,
                                tSirAddie           *pOld,
                                tDot11fIEWscIEOpaque *pNew )
{
    // This is awful, I know, but the old code just rammed the IE into
    // an opaque array.  Note that we need to explicitly add the vendorIE and OUI !
    tANI_U8 curAddIELen = pOld->length; 

    pOld->length    = curAddIELen + pNew->num_data + 6;
    pOld->addIEdata[ curAddIELen++ ] = 0xdd;
    pOld->addIEdata[ curAddIELen++ ] = pNew->num_data + 4;
    pOld->addIEdata[ curAddIELen++ ] = 0x00;
    pOld->addIEdata[ curAddIELen++ ] = 0x50;
    pOld->addIEdata[ curAddIELen++ ] = 0xf2;
    pOld->addIEdata[ curAddIELen++ ] = 0x04;
    palCopyMemory( pMac->hHdd, pOld->addIEdata + curAddIELen, pNew->data, pNew->num_data );

    return eSIR_SUCCESS;
}

#ifdef WLAN_FEATURE_P2P
tSirRetStatus ConvertP2POpaque( tpAniSirGlobal      pMac,
                                tSirAddie           *pOld,
                                tDot11fIEP2PIEOpaque *pNew )
{
    // This is awful, I know, but the old code just rammed the IE into
    // an opaque array.  Note that we need to explicitly add the vendorIE and OUI !
    tANI_U8 curAddIELen = pOld->length; 

    pOld->length    = curAddIELen + pNew->num_data + 6;
    pOld->addIEdata[ curAddIELen++ ] = 0xdd;
    pOld->addIEdata[ curAddIELen++ ] = pNew->num_data + 4;
    pOld->addIEdata[ curAddIELen++ ] = 0x50;
    pOld->addIEdata[ curAddIELen++ ] = 0x6f;
    pOld->addIEdata[ curAddIELen++ ] = 0x9A;
    pOld->addIEdata[ curAddIELen++ ] = 0x09;
    palCopyMemory( pMac->hHdd, pOld->addIEdata + curAddIELen, pNew->data, pNew->num_data );

    return eSIR_SUCCESS;
}
#endif

tSirRetStatus ConvertRSN(tpAniSirGlobal  pMac,
                               tSirMacRsnInfo *pOld,
                               tDot11fIERSN      *pNew)
{
    tANI_U8 buffer[257];
    tANI_U32 status, written = 0, nbuffer = 257;
    status = dot11fPackIeRSN( pMac, pNew, buffer, nbuffer, &written );
    if ( DOT11F_FAILED( status ) )
    {
        dot11fLog(pMac, LOG2, FL("Failed to re-pack the RSN IE (0x%0x"
                                 "8).\n"), status);
        return eSIR_FAILURE;
    }

    pOld->length = (tANI_U8)written - 2;
    palCopyMemory( pMac->hHdd, pOld->info, buffer + 2, pOld->length );

    return eSIR_SUCCESS;
}

tSirRetStatus ConvertRSNOpaque( tpAniSirGlobal      pMac,
                                tSirMacRsnInfo     *pOld,
                                tDot11fIERSNOpaque *pNew )
{
    // This is awful, I know, but the old code just rammed the IE into
    // an opaque array.
    pOld->length = pNew->num_data;
    palCopyMemory( pMac->hHdd, pOld->info, pNew->data, pOld->length );

    return eSIR_SUCCESS;
}

void ConvertPowerCaps(tpAniSirGlobal            pMac,
                            tSirMacPowerCapabilityIE *pOld,
                            tDot11fIEPowerCaps          *pNew)
{
    pOld->type       = 33;
    pOld->length     = 2;
    pOld->minTxPower = pNew->minTxPower;
    pOld->maxTxPower = pNew->maxTxPower;
}

void ConvertSuppChannels(tpAniSirGlobal             pMac,
                               tSirMacSupportedChannelIE *pOld,
                               tDot11fIESuppChannels        *pNew)
{
    pOld->type   = 36;
    pOld->length = ( pNew->num_bands * 2 );
    palCopyMemory( pMac->hHdd, ( tANI_U8* )pOld->supportedChannels, ( tANI_U8* )pNew->bands, pOld->length );
}

void ConvertCFParams(tpAniSirGlobal     pMac,
                           tSirMacCfParamSet *pOld,
                           tDot11fIECFParams    *pNew)
{
    pOld->cfpCount        = pNew->cfp_count;
    pOld->cfpPeriod       = pNew->cfp_period;
    pOld->cfpMaxDuration  = pNew->cfp_maxduration;
    pOld->cfpDurRemaining = pNew->cfp_durremaining;
}

void ConvertTIM(tpAniSirGlobal pMac,
                      tSirMacTim    *pOld,
                      tDot11fIETIM     *pNew)
{
    pOld->dtimCount     = pNew->dtim_count;
    pOld->dtimPeriod    = pNew->dtim_period;
    pOld->bitmapControl = pNew->bmpctl;
    pOld->bitmapLength  = pNew->num_vbmp;

    palCopyMemory( pMac->hHdd, pOld->bitmap, pNew->vbmp, pNew->num_vbmp );
}

void ConvertCountry(tpAniSirGlobal          pMac,
                          tSirCountryInformation *pOld,
                          tDot11fIECountry          *pNew)
{
    int i;

    palCopyMemory( pMac->hHdd, pOld->countryString, pNew->country, COUNTRY_STRING_LENGTH );

    pOld->numIntervals = pNew->num_triplets;

    for (i = 0; i < pNew->num_triplets; ++i)
    {
        pOld->channelTransmitPower[i].channelNumber    = pNew->triplets[i][0];
        pOld->channelTransmitPower[i].numChannel       = pNew->triplets[i][1];
        pOld->channelTransmitPower[i].maxTransmitPower = pNew->triplets[i][2];
    }
}

void ConvertWMMParams(tpAniSirGlobal         pMac,
                            tSirMacEdcaParamSetIE *pOld,
                            tDot11fIEWMMParams       *pNew)
{
    pOld->type = 221;
    pOld->length = 24;

    palCopyMemory( pMac->hHdd, ( tANI_U8* )&pOld->qosInfo, ( tANI_U8* )&pNew->qosInfo, 1 );

    pOld->acbe.aci.aifsn  = pNew->acbe_aifsn;
    pOld->acbe.aci.acm    = pNew->acbe_acm;
    pOld->acbe.aci.aci    = pNew->acbe_aci;
    pOld->acbe.cw.min     = pNew->acbe_acwmin;
    pOld->acbe.cw.max     = pNew->acbe_acwmax;
    pOld->acbe.txoplimit  = pNew->acbe_txoplimit;

    pOld->acbk.aci.aifsn  = pNew->acbk_aifsn;
    pOld->acbk.aci.acm    = pNew->acbk_acm;
    pOld->acbk.aci.aci    = pNew->acbk_aci;
    pOld->acbk.cw.min     = pNew->acbk_acwmin;
    pOld->acbk.cw.max     = pNew->acbk_acwmax;
    pOld->acbk.txoplimit  = pNew->acbk_txoplimit;

    pOld->acvi.aci.aifsn  = pNew->acvi_aifsn;
    pOld->acvi.aci.acm    = pNew->acvi_acm;
    pOld->acvi.aci.aci    = pNew->acvi_aci;
    pOld->acvi.cw.min     = pNew->acvi_acwmin;
    pOld->acvi.cw.max     = pNew->acvi_acwmax;
    pOld->acvi.txoplimit  = pNew->acvi_txoplimit;

    pOld->acvo.aci.aifsn  = pNew->acvo_aifsn;
    pOld->acvo.aci.acm    = pNew->acvo_acm;
    pOld->acvo.aci.aci    = pNew->acvo_aci;
    pOld->acvo.cw.min     = pNew->acvo_acwmin;
    pOld->acvo.cw.max     = pNew->acvo_acwmax;
    pOld->acvo.txoplimit  = pNew->acvo_txoplimit;
}

void ConvertERPInfo(tpAniSirGlobal    pMac,
                          tSirMacErpInfo   *pOld,
                          tDot11fIEERPInfo    *pNew)
{
    pOld->nonErpPresent = pNew->non_erp_present;
    pOld->useProtection = pNew->use_prot;
    pOld->barkerPreambleMode = pNew->barker_preamble;
}

void ConvertEDCAParam(tpAniSirGlobal         pMac,
                            tSirMacEdcaParamSetIE *pOld,
                            tDot11fIEEDCAParamSet    *pNew)
{
    pOld->type   = 12;
    pOld->length = 20;

    palCopyMemory( pMac->hHdd, ( tANI_U8* )&pOld->qosInfo, ( tANI_U8* )&pNew->qos, 1 );

    pOld->acbe.aci.aifsn  = pNew->acbe_aifsn;
    pOld->acbe.aci.acm    = pNew->acbe_acm;
    pOld->acbe.aci.aci    = pNew->acbe_aci;
    pOld->acbe.cw.min     = pNew->acbe_acwmin;
    pOld->acbe.cw.max     = pNew->acbe_acwmax;
    pOld->acbe.txoplimit  = pNew->acbe_txoplimit;

    pOld->acbk.aci.aifsn  = pNew->acbk_aifsn;
    pOld->acbk.aci.acm    = pNew->acbk_acm;
    pOld->acbk.aci.aci    = pNew->acbk_aci;
    pOld->acbk.cw.min     = pNew->acbk_acwmin;
    pOld->acbk.cw.max     = pNew->acbk_acwmax;
    pOld->acbk.txoplimit  = pNew->acbk_txoplimit;

    pOld->acvi.aci.aifsn  = pNew->acvi_aifsn;
    pOld->acvi.aci.acm    = pNew->acvi_acm;
    pOld->acvi.aci.aci    = pNew->acvi_aci;
    pOld->acvi.cw.min     = pNew->acvi_acwmin;
    pOld->acvi.cw.max     = pNew->acvi_acwmax;
    pOld->acvi.txoplimit  = pNew->acvi_txoplimit;

    pOld->acvo.aci.aifsn  = pNew->acvo_aifsn;
    pOld->acvo.aci.acm    = pNew->acvo_acm;
    pOld->acvo.aci.aci    = pNew->acvo_aci;
    pOld->acvo.cw.min     = pNew->acvo_acwmin;
    pOld->acvo.cw.max     = pNew->acvo_acwmax;
    pOld->acvo.txoplimit  = pNew->acvo_txoplimit;

}

void ConvertTSPEC(tpAniSirGlobal  pMac,
                        tSirMacTspecIE *pOld,
                        tDot11fIETSPEC *pNew)
{
    pOld->tsinfo.traffic.trafficType  = (tANI_U16)pNew->traffic_type;
    pOld->tsinfo.traffic.tsid         = (tANI_U16)pNew->tsid;
    pOld->tsinfo.traffic.direction    = (tANI_U16)pNew->direction;
    pOld->tsinfo.traffic.accessPolicy = (tANI_U16)pNew->access_policy;
    pOld->tsinfo.traffic.aggregation  = (tANI_U16)pNew->aggregation;
    pOld->tsinfo.traffic.psb          = (tANI_U16)pNew->psb;
    pOld->tsinfo.traffic.userPrio     = (tANI_U16)pNew->user_priority;
    pOld->tsinfo.traffic.ackPolicy    = (tANI_U16)pNew->tsinfo_ack_pol;

    pOld->tsinfo.schedule.schedule    = (tANI_U8)pNew->schedule;

    pOld->nomMsduSz                   = pNew->size;
    pOld->maxMsduSz                   = pNew->max_msdu_size;
    pOld->minSvcInterval              = pNew->min_service_int;
    pOld->maxSvcInterval              = pNew->max_service_int;
    pOld->inactInterval               = pNew->inactivity_int;
    pOld->suspendInterval             = pNew->suspension_int;
    pOld->svcStartTime                = pNew->service_start_time;
    pOld->minDataRate                 = pNew->min_data_rate;
    pOld->meanDataRate                = pNew->mean_data_rate;
    pOld->peakDataRate                = pNew->peak_data_rate;
    pOld->maxBurstSz                  = pNew->burst_size;
    pOld->delayBound                  = pNew->delay_bound;
    pOld->minPhyRate                  = pNew->min_phy_rate;
    pOld->surplusBw                   = pNew->surplus_bw_allowance;
    pOld->mediumTime                  = pNew->medium_time;
}

tSirRetStatus ConvertTCLAS(tpAniSirGlobal  pMac,
                                 tSirTclasInfo  *pOld,
                                 tDot11fIETCLAS *pNew)
{
    tANI_U32 length;

    if ( DOT11F_FAILED( dot11fGetPackedIETCLAS( pMac, pNew, &length ) ) )
    {
        return eSIR_FAILURE;
    }

    pOld->tclas.type           = DOT11F_EID_TCLAS;
    pOld->tclas.length         = (tANI_U8)length;
    pOld->tclas.userPrio       = pNew->user_priority;
    pOld->tclas.classifierType = pNew->classifier_type;
    pOld->tclas.classifierMask = pNew->classifier_mask;

    switch ( pNew->classifier_type )
    {
    case 0:
        palCopyMemory( pMac->hHdd, pOld->tclasParams.eth.srcAddr, pNew->info.EthParams.source, 6 );
        palCopyMemory( pMac->hHdd, pOld->tclasParams.eth.dstAddr, pNew->info.EthParams.dest, 6 );
        pOld->tclasParams.eth.type = pNew->info.EthParams.type;
        break;
    case 1:
        pOld->version = pNew->info.IpParams.version;
        if ( 4 == pNew->info.IpParams.version )
        {
            pOld->tclasParams.ipv4.version = 4;
            palCopyMemory( pMac->hHdd, ( tANI_U8* )&pOld->tclasParams.ipv4.srcIpAddr, ( tANI_U8* )pNew->info.IpParams.params.IpV4Params.source, 4 );
            palCopyMemory( pMac->hHdd, ( tANI_U8* )&pOld->tclasParams.ipv4.dstIpAddr, ( tANI_U8* )pNew->info.IpParams.params.IpV4Params.dest, 4 );
            pOld->tclasParams.ipv4.srcPort  = pNew->info.IpParams.params.IpV4Params.src_port;
            pOld->tclasParams.ipv4.dstPort  = pNew->info.IpParams.params.IpV4Params.dest_port;
            pOld->tclasParams.ipv4.dscp     = pNew->info.IpParams.params.IpV4Params.DSCP;
            pOld->tclasParams.ipv4.protocol = pNew->info.IpParams.params.IpV4Params.proto;
            pOld->tclasParams.ipv4.rsvd     = pNew->info.IpParams.params.IpV4Params.reserved;
        }
        else if ( 6 == pNew->info.IpParams.version )
        {
            pOld->tclasParams.ipv6.version = 6;
            palCopyMemory( pMac->hHdd, ( tANI_U8* )pOld->tclasParams.ipv6.srcIpAddr, ( tANI_U8* )pNew->info.IpParams.params.IpV6Params.source, 16 );
            palCopyMemory( pMac->hHdd, ( tANI_U8* )pOld->tclasParams.ipv6.dstIpAddr, ( tANI_U8* )pNew->info.IpParams.params.IpV6Params.dest, 16 );
            pOld->tclasParams.ipv6.srcPort  = pNew->info.IpParams.params.IpV6Params.src_port;
            pOld->tclasParams.ipv6.dstPort  = pNew->info.IpParams.params.IpV6Params.dest_port;
            palCopyMemory( pMac->hHdd, ( tANI_U8* )pOld->tclasParams.ipv6.flowLabel, ( tANI_U8* )pNew->info.IpParams.params.IpV6Params.flow_label, 3 );
        }
        else
        {
            return eSIR_FAILURE;
        }
        break;
    case 2:
        pOld->tclasParams.t8021dq.tag = pNew->info.Params8021dq.tag_type;
        break;
    default:
        return eSIR_FAILURE;
    }

    return eSIR_SUCCESS;
}

void ConvertWMMTSPEC(tpAniSirGlobal     pMac,
                           tSirMacTspecIE    *pOld,
                           tDot11fIEWMMTSPEC *pNew)
{
    pOld->tsinfo.traffic.trafficType  = (tANI_U16)pNew->traffic_type;
    pOld->tsinfo.traffic.tsid         = (tANI_U16)pNew->tsid;
    pOld->tsinfo.traffic.direction    = (tANI_U16)pNew->direction;
    pOld->tsinfo.traffic.accessPolicy = (tANI_U16)pNew->access_policy;
    pOld->tsinfo.traffic.aggregation  = (tANI_U16)pNew->aggregation;
    pOld->tsinfo.traffic.psb          = (tANI_U16)pNew->psb;
    pOld->tsinfo.traffic.userPrio     = (tANI_U16)pNew->user_priority;
    pOld->tsinfo.traffic.ackPolicy    = (tANI_U16)pNew->tsinfo_ack_pol;
    pOld->nomMsduSz                   = pNew->size;
    pOld->maxMsduSz                   = pNew->max_msdu_size;
    pOld->minSvcInterval              = pNew->min_service_int;
    pOld->maxSvcInterval              = pNew->max_service_int;
    pOld->inactInterval               = pNew->inactivity_int;
    pOld->suspendInterval             = pNew->suspension_int;
    pOld->svcStartTime                = pNew->service_start_time;
    pOld->minDataRate                 = pNew->min_data_rate;
    pOld->meanDataRate                = pNew->mean_data_rate;
    pOld->peakDataRate                = pNew->peak_data_rate;
    pOld->maxBurstSz                  = pNew->burst_size;
    pOld->delayBound                  = pNew->delay_bound;
    pOld->minPhyRate                  = pNew->min_phy_rate;
    pOld->surplusBw                   = pNew->surplus_bw_allowance;
    pOld->mediumTime                  = pNew->medium_time;
}

tSirRetStatus ConvertWMMTCLAS(tpAniSirGlobal    pMac,
                                    tSirTclasInfo     *pOld,
                                    tDot11fIEWMMTCLAS *pNew)
{
    tANI_U32 length;

    if ( DOT11F_FAILED( dot11fGetPackedIEWMMTCLAS( pMac, pNew, &length ) ) )
    {
        return eSIR_FAILURE;
    }

    pOld->tclas.type           = DOT11F_EID_WMMTCLAS;
    pOld->tclas.length         = (tANI_U8)length;
    pOld->tclas.userPrio       = pNew->user_priority;
    pOld->tclas.classifierType = pNew->classifier_type;
    pOld->tclas.classifierMask = pNew->classifier_mask;

    switch ( pNew->classifier_type )
    {
    case 0:
        palCopyMemory( pMac->hHdd, pOld->tclasParams.eth.srcAddr, pNew->info.EthParams.source, 6 );
        palCopyMemory( pMac->hHdd, pOld->tclasParams.eth.dstAddr, pNew->info.EthParams.dest, 6 );
        pOld->tclasParams.eth.type = pNew->info.EthParams.type;
        break;
    case 1:
        pOld->version = pNew->info.IpParams.version;
        if ( 4 == pNew->info.IpParams.version )
        {
            pOld->tclasParams.ipv4.version = 4;
            palCopyMemory( pMac->hHdd, ( tANI_U8* )&pOld->tclasParams.ipv4.srcIpAddr, ( tANI_U8* )pNew->info.IpParams.params.IpV4Params.source, 4 );
            palCopyMemory( pMac->hHdd, ( tANI_U8* )&pOld->tclasParams.ipv4.dstIpAddr, ( tANI_U8* )pNew->info.IpParams.params.IpV4Params.dest, 4 );
            pOld->tclasParams.ipv4.srcPort  = pNew->info.IpParams.params.IpV4Params.src_port;
            pOld->tclasParams.ipv4.dstPort  = pNew->info.IpParams.params.IpV4Params.dest_port;
            pOld->tclasParams.ipv4.dscp     = pNew->info.IpParams.params.IpV4Params.DSCP;
            pOld->tclasParams.ipv4.protocol = pNew->info.IpParams.params.IpV4Params.proto;
            pOld->tclasParams.ipv4.rsvd     = pNew->info.IpParams.params.IpV4Params.reserved;
        }
        else if ( 6 == pNew->info.IpParams.version )
        {
            pOld->tclasParams.ipv6.version = 6;
            palCopyMemory( pMac->hHdd, ( tANI_U8* )pOld->tclasParams.ipv6.srcIpAddr, ( tANI_U8* )pNew->info.IpParams.params.IpV6Params.source, 16 );
            palCopyMemory( pMac->hHdd, ( tANI_U8* )pOld->tclasParams.ipv6.dstIpAddr, ( tANI_U8* )pNew->info.IpParams.params.IpV6Params.dest, 16 );
            pOld->tclasParams.ipv6.srcPort  = pNew->info.IpParams.params.IpV6Params.src_port;
            pOld->tclasParams.ipv6.dstPort  = pNew->info.IpParams.params.IpV6Params.dest_port;
            palCopyMemory( pMac->hHdd, ( tANI_U8* )pOld->tclasParams.ipv6.flowLabel, ( tANI_U8* )pNew->info.IpParams.params.IpV6Params.flow_label, 3 );
        }
        else
        {
            return eSIR_FAILURE;
        }
        break;
    case 2:
        pOld->tclasParams.t8021dq.tag = pNew->info.Params8021dq.tag_type;
        break;
    default:
        return eSIR_FAILURE;
    }

    return eSIR_SUCCESS;
}

void ConvertTSDelay(tpAniSirGlobal    pMac,
                          tSirMacTsDelayIE *pOld,
                          tDot11fIETSDelay *pNew)
{
    pOld->type   = DOT11F_EID_TSDELAY;
    pOld->length = 4U;
    pOld->delay  = pNew->delay;
}

void ConvertSchedule(tpAniSirGlobal     pMac,
                           tSirMacScheduleIE *pOld,
                           tDot11fIESchedule *pNew)
{
    pOld->type             = DOT11F_EID_SCHEDULE;
    pOld->length           = DOT11F_IE_SCHEDULE_MIN_LEN;

    pOld->info.aggregation = pNew->aggregation;
    pOld->info.tsid        = pNew->tsid;
    pOld->info.direction   = pNew->direction;

    pOld->svcStartTime     = pNew->service_start_time;
    pOld->svcInterval      = pNew->service_interval;
    pOld->specInterval     = pNew->spec_interval;
}

void ConvertWMMSchedule(tpAniSirGlobal        pMac,
                              tSirMacScheduleIE    *pOld,
                              tDot11fIEWMMSchedule *pNew)
{
    pOld->type             = DOT11F_EID_WMMSCHEDULE;
    pOld->length           = DOT11F_IE_WMMSCHEDULE_MIN_LEN;

    pOld->info.aggregation = pNew->aggregation;
    pOld->info.tsid        = pNew->tsid;
    pOld->info.direction   = pNew->direction;

    pOld->svcStartTime     = pNew->service_start_time;
    pOld->svcInterval      = pNew->service_interval;
    pOld->specInterval     = pNew->spec_interval;
}

/**
    @brief   :    This functions converts the given buffer till given size to Big endian format assuming the 
                     bus is 32 bit. The size should be four byte aligned.
    @param :    ptr to be converted, size
    @return  :    void
*/

void ConverttoBigEndian(void *ptr, tANI_U16    size)
{
    tANI_U8        *temp_ptr;
    tANI_U32    *dest_ptr;

    dest_ptr  = (tANI_U32 *)ptr;
    while(size)
    {
        temp_ptr = (tANI_U8 *) dest_ptr;
        *dest_ptr = (temp_ptr[0] << 24) | (temp_ptr[1] << 16) | (temp_ptr[2] << 8) | temp_ptr[3];
        dest_ptr++;
        size -= 4;
    }
}


void CreateScanDataNullFrame(tpAniSirGlobal pMac, tSirMacMgmtHdr *macMgmtHdr,
                  tANI_U8 pwrMgmt, tSirMacAddr bssid, tSirMacAddr selfMacAddr)
{

    macMgmtHdr->fc.type = SIR_MAC_DATA_FRAME;
    macMgmtHdr->fc.subType = SIR_MAC_DATA_NULL;
    macMgmtHdr->fc.protVer = SIR_MAC_PROTOCOL_VERSION;
    macMgmtHdr->fc.order = 0;
    macMgmtHdr->fc.wep = 0;
    macMgmtHdr->fc.moreData =0;
    macMgmtHdr->fc.powerMgmt = pwrMgmt;
    macMgmtHdr->fc.retry = 0;
    macMgmtHdr->fc.moreFrag = 0;
    macMgmtHdr->fc.fromDS = 0;
    macMgmtHdr->fc.toDS = 0;
    macMgmtHdr->durationLo = (tANI_U8) (SIR_MAC_MAX_DURATION_MICRO_SECONDS & 0xff);
    macMgmtHdr->durationHi = (tANI_U8) ((SIR_MAC_MAX_DURATION_MICRO_SECONDS & 0xff00) >> 8);
    macMgmtHdr->seqControl.fragNum = 0;
    macMgmtHdr->seqControl.seqNumLo = 0;
    macMgmtHdr->seqControl.seqNumHi = 2;
    palCopyMemory(pMac->hHdd, (void *)&macMgmtHdr->da,
                              (void *)bssid, sizeof(tSirMacAddr));
    palCopyMemory(pMac->hHdd, (void *)&macMgmtHdr->sa,
                              (void *)selfMacAddr, sizeof(tSirMacAddr));
    palCopyMemory(pMac->hHdd, (void *)&macMgmtHdr->bssId,
                              (void *)bssid, sizeof(tSirMacAddr));
    
    return;
}


void CreateScanCtsFrame(tpAniSirGlobal pMac, tSirMacMgmtHdr *macMgmtHdr, tSirMacAddr selfMac)
{
    macMgmtHdr->fc.type = SIR_MAC_CTRL_FRAME;
    macMgmtHdr->fc.subType = SIR_MAC_CTRL_CTS;
    macMgmtHdr->fc.order = 0;
    macMgmtHdr->fc.wep = 0;
    macMgmtHdr->fc.moreData =0;
    macMgmtHdr->fc.powerMgmt = 0;  
    macMgmtHdr->fc.retry = 0;
    macMgmtHdr->fc.moreFrag = 0;
    macMgmtHdr->fc.fromDS = 0;
    macMgmtHdr->fc.toDS = 0;
    macMgmtHdr->durationLo = (tANI_U8) (SIR_MAC_MAX_DURATION_MICRO_SECONDS & 0xff);
    macMgmtHdr->durationHi = (tANI_U8) ((SIR_MAC_MAX_DURATION_MICRO_SECONDS & 0xff00) >> 8);
    palCopyMemory(pMac->hHdd, (void *)macMgmtHdr->da, (void *)selfMac, sizeof(tSirMacAddr));
            
    return;
}







/**
    @brief    :    This functions creates a DATA_NULL/CTS2SELF frame in Big endian format 
    @param    :    Global MAC structure, pointer to return the created packet, role which is Station/AP
    @return    :    void
*/

void CreateInitScanRawFrame(tpAniSirGlobal pMac, tSirMacMgmtHdr *macMgmtHdr, tBssSystemRole role)
{
#if 0
    tpStaStruct pSta = (tpStaStruct) pMac->hal.halMac.staTable;
    
    if (role == eSYSTEM_STA_ROLE)
    {
        macMgmtHdr->fc.type = SIR_MAC_DATA_FRAME;
        macMgmtHdr->fc.subType = SIR_MAC_DATA_NULL;
        macMgmtHdr->fc.protVer = SIR_MAC_PROTOCOL_VERSION;
        macMgmtHdr->fc.order = 0;
        macMgmtHdr->fc.wep = 0;
        macMgmtHdr->fc.moreData =0;
        macMgmtHdr->fc.powerMgmt = 1;  // Needed for station
        macMgmtHdr->fc.retry = 0;
        macMgmtHdr->fc.moreFrag = 0;
        macMgmtHdr->fc.fromDS = 0;
        macMgmtHdr->fc.toDS = 1;
        macMgmtHdr->durationLo = (tANI_U8) (SIR_MAC_MAX_DURATION_MICRO_SECONDS & 0xff);
        macMgmtHdr->durationHi = (tANI_U8) ((SIR_MAC_MAX_DURATION_MICRO_SECONDS & 0xff00) >> 8);
        macMgmtHdr->seqControl.fragNum = 0;
        macMgmtHdr->seqControl.seqNumLo = 0;
        macMgmtHdr->seqControl.seqNumHi = 2;
        palCopyMemory(pMac->hHdd, (void *)&macMgmtHdr->da, (void *)pSta[0].bssId, 6);
        palCopyMemory(pMac->hHdd, &macMgmtHdr->sa, pSta[0].staAddr, 6);
        palCopyMemory(pMac->hHdd, (void *)&macMgmtHdr->bssId, (void *)pSta[0].bssId, 6);
    }
    else if (role == eSYSTEM_AP_ROLE || role == eSYSTEM_STA_IN_IBSS_ROLE)
    {
        macMgmtHdr->fc.type = SIR_MAC_CTRL_FRAME;
        macMgmtHdr->fc.subType = SIR_MAC_CTRL_CTS;
        macMgmtHdr->fc.order = 0;
        macMgmtHdr->fc.wep = 0;
        macMgmtHdr->fc.moreData =0;
        macMgmtHdr->fc.powerMgmt = 0;  // Needed for station
        macMgmtHdr->fc.retry = 0;
        macMgmtHdr->fc.moreFrag = 0;
        macMgmtHdr->fc.fromDS = 0;
        macMgmtHdr->fc.toDS = 0;
        macMgmtHdr->durationLo = (tANI_U8) (SIR_MAC_MAX_DURATION_MICRO_SECONDS & 0xff);
        macMgmtHdr->durationHi = (tANI_U8) ((SIR_MAC_MAX_DURATION_MICRO_SECONDS & 0xff00) >> 8);
        palCopyMemory(pMac->hHdd, (void *)macMgmtHdr->da, (void *)pSta[0].staAddr, 6);
    }
    return;
#endif
}

/**
    @brief    :    This functions creates a DATA_NULL frame in Big endian format 
    @param    :    Global MAC structure, pointer to return the created packet, role which is Station/AP
    @return    :    void
*/


void CreateFinishScanRawFrame(tpAniSirGlobal pMac, tSirMacMgmtHdr *macMgmtHdr, tBssSystemRole role)
{
#if 0
    tpStaStruct pSta = (tpStaStruct) pMac->hal.halMac.staTable;

    if (role == eSYSTEM_STA_ROLE)
    {
        macMgmtHdr->fc.type = SIR_MAC_DATA_FRAME;
        macMgmtHdr->fc.subType = SIR_MAC_DATA_NULL;
        macMgmtHdr->fc.protVer = SIR_MAC_PROTOCOL_VERSION;
        macMgmtHdr->fc.order = 0;
        macMgmtHdr->fc.wep = 0;
        macMgmtHdr->fc.moreData =0;
        macMgmtHdr->fc.powerMgmt = 0;     // Needed for station
        macMgmtHdr->fc.retry = 0;
        macMgmtHdr->fc.moreFrag = 0;
        macMgmtHdr->fc.fromDS = 0;
        macMgmtHdr->fc.toDS = 1;
        macMgmtHdr->durationLo = (tANI_U8) (SIR_MAC_MAX_DURATION_MICRO_SECONDS & 0xff);
        macMgmtHdr->durationHi = (tANI_U8) ((SIR_MAC_MAX_DURATION_MICRO_SECONDS & 0xff00) >> 8);
        macMgmtHdr->seqControl.fragNum = 0;
        macMgmtHdr->seqControl.seqNumLo = 0;
        macMgmtHdr->seqControl.seqNumHi = 2;
        palCopyMemory(pMac->hHdd, (void *)macMgmtHdr->da, (void *)pSta[0].bssId, 6);
        palCopyMemory(pMac->hHdd, macMgmtHdr->sa, pSta[0].staAddr, 6);
        palCopyMemory(pMac->hHdd, (void *)macMgmtHdr->bssId, (void *)pSta[0].bssId, 6);

    }
    
    return;
#endif
}


// utilsParser.c ends here.
