VirtualBox

Changeset 28102 in vbox for trunk


Ignore:
Timestamp:
Apr 8, 2010 3:49:33 PM (15 years ago)
Author:
vboxsync
Message:

DevE1000: Check for MAX GSO frame size. Logging GSO decisions. Added more statistics relating to transfers.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Devices/Network/DevE1000.cpp

    r28089 r28102  
    2727 *
    2828 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa
    29  * Clara, CA 95054 USA or visit http://www.sun.com if you need
     29 * Clara, CA 95054 USA or visit http://www.sun.com if you need.
    3030 * additional information or have any questions.
    3131 */
     
    5757#include <VBox/pdmnetifs.h>
    5858#include <VBox/pdmnetinline.h>
     59#include <VBox/param.h>
    5960#include <VBox/tm.h>
    6061#include <VBox/vm.h>
     
    10721073    STAMPROFILE                         StatRxOverflow;
    10731074    STAMCOUNTER                         StatRxOverflowWakeup;
     1075    STAMCOUNTER                         StatTxDescCtxNormal;
     1076    STAMCOUNTER                         StatTxDescCtxTSE;
    10741077    STAMCOUNTER                         StatTxDescLegacy;
    10751078    STAMCOUNTER                         StatTxDescData;
    10761079    STAMCOUNTER                         StatTxDescTSEData;
     1080    STAMCOUNTER                         StatTxPathFallback;
     1081    STAMCOUNTER                         StatTxPathGSO;
     1082    STAMCOUNTER                         StatTxPathRegular;
    10771083    STAMCOUNTER                         StatPHYAccesses;
    10781084
     
    28232829    /* Check the header ordering and spacing: 1. Ethernet, 2. IP, 3. TCP/UDP. */
    28242830    if (RT_UNLIKELY( pCtx->ip.u8CSS < sizeof(RTNETETHERHDR) ))
     2831    {
     2832        E1kLog(("e1kSetupGsoCtx: IPCSS=%#x\n", pCtx->ip.u8CSS));
    28252833        return;
     2834    }
    28262835    if (RT_UNLIKELY( pCtx->tu.u8CSS     < (size_t)pCtx->ip.u8CSS + (pCtx->dw2.fIP  ? RTNETIPV4_MIN_LEN : RTNETIPV6_MIN_LEN) ))
     2836    {
     2837        E1kLog(("e1kSetupGsoCtx: TUCSS=%#x\n", pCtx->tu.u8CSS));
    28272838        return;
     2839    }
    28282840    if (RT_UNLIKELY(   pCtx->dw2.fTCP
    28292841                     ? pCtx->dw3.u8HDRLEN <  (size_t)pCtx->tu.u8CSS + RTNETTCP_MIN_LEN
    28302842                     : pCtx->dw3.u8HDRLEN != (size_t)pCtx->tu.u8CSS + RTNETUDP_MIN_LEN ))
     2843    {
     2844        E1kLog(("e1kSetupGsoCtx: HDRLEN=%#x TCP=%d\n", pCtx->dw3.u8HDRLEN, pCtx->dw2.fTCP));
    28312845        return;
     2846    }
    28322847
    28332848    /* The end of the TCP/UDP checksum should stop at the end of the packet or at least after the headers. */
    28342849    if (RT_UNLIKELY( pCtx->tu.u16CSE > 0 && pCtx->tu.u16CSE <= pCtx->dw3.u8HDRLEN ))
     2850    {
     2851        E1kLog(("e1kSetupGsoCtx: TUCSE=%#x HDRLEN=%#x\n", pCtx->tu.u16CSE, pCtx->dw3.u8HDRLEN));
    28352852        return;
     2853    }
    28362854
    28372855    /* IPv4 checksum offset. */
    28382856    if (RT_UNLIKELY( pCtx->dw2.fIP && pCtx->ip.u8CSO - pCtx->ip.u8CSS != RT_OFFSETOF(RTNETIPV4, ip_sum) ))
     2857    {
     2858        E1kLog(("e1kSetupGsoCtx: IPCSO=%#x IPCSS=%#x\n", pCtx->ip.u8CSO, pCtx->ip.u8CSS));
    28392859        return;
     2860    }
    28402861
    28412862    /* TCP/UDP checksum offsets. */
     
    28432864                                                         ? RT_OFFSETOF(RTNETTCP, th_sum)
    28442865                                                         : RT_OFFSETOF(RTNETUDP, uh_sum) ) ))
     2866    {
     2867        E1kLog(("e1kSetupGsoCtx: TUCSO=%#x TUCSS=%#x TCP=%d\n", pCtx->ip.u8CSO, pCtx->ip.u8CSS, pCtx->dw2.fTCP));
    28452868        return;
     2869    }
     2870
     2871    /*
     2872     * Because of internal networking using a 16-bit size field for GSO context
     2873     * pluss frame, we have to make sure we don't exceed this.
     2874     */
     2875    if (RT_UNLIKELY( pCtx->dw3.u8HDRLEN + pCtx->dw2.u20PAYLEN > VBOX_MAX_GSO_SIZE ))
     2876    {
     2877        E1kLog(("e1kSetupGsoCtx: HDRLEN(=%#x) + PAYLEN(=%#x) = %#x, max is %#x\n",
     2878                pCtx->dw3.u8HDRLEN, pCtx->dw2.u20PAYLEN, pCtx->dw3.u8HDRLEN + pCtx->dw2.u20PAYLEN, VBOX_MAX_GSO_SIZE));
     2879        return;
     2880    }
    28462881
    28472882    /*
     
    28702905    pGso->cbMaxSeg = pCtx->dw3.u16MSS;
    28712906    Assert(PDMNetGsoIsValid(pGso, sizeof(*pGso), pGso->cbMaxSeg * 5));
     2907    E1kLog2(("e1kSetupGsoCtx: mss=%#x hdr=%#x hdr1=%#x hdr2=%#x %s\n",
     2908             pGso->cbMaxSeg, pGso->cbHdrs, pGso->offHdr1, pGso->offHdr2, PDMNetGsoTypeName((PDMNETWORKGSOTYPE)pGso->u8Type) ));
    28722909}
    28732910
     
    28772914 * @param   pGso                The GSO context.
    28782915 * @param   pData               The first data descriptor of the frame.
    2879  */
    2880 DECLINLINE(bool) e1kCanDoGso(PCPDMNETWORKGSO pGso, E1KTXDAT const *pData)
     2916 * @param   pCtx                The TSO context descriptor.
     2917 */
     2918DECLINLINE(bool) e1kCanDoGso(PCPDMNETWORKGSO pGso, E1KTXDAT const *pData, E1KTXCTX const *pCtx)
    28812919{
    28822920    if (!pData->cmd.fTSE)
     2921    {
     2922        E1kLog2(("e1kCanDoGso: !TSE\n"));
    28832923        return false;
     2924    }
    28842925    if (pData->cmd.fVLE) /** @todo VLAN tagging. */
     2926    {
     2927        E1kLog(("e1kCanDoGso: VLE\n"));
    28852928        return false;
     2929    }
    28862930
    28872931    switch ((PDMNETWORKGSOTYPE)pGso->u8Type)
     
    28902934        case PDMNETWORKGSOTYPE_IPV4_UDP:
    28912935            if (!pData->dw3.fIXSM)
     2936            {
     2937                E1kLog(("e1kCanDoGso: !IXSM (IPv4)\n"));
    28922938                return false;
     2939            }
    28932940            if (!pData->dw3.fTXSM)
     2941            {
     2942                E1kLog(("e1kCanDoGso: !TXSM (IPv4)\n"));
    28942943                return false;
     2944            }
    28952945            /** @todo what more check should we perform here? Ethernet frame type? */
     2946            E1kLog2(("e1kCanDoGso: OK, IPv4\n"));
    28962947            return true;
    28972948
    28982949        case PDMNETWORKGSOTYPE_IPV6_TCP:
    28992950        case PDMNETWORKGSOTYPE_IPV6_UDP:
    2900             if (pData->dw3.fIXSM)
     2951            if (pData->dw3.fIXSM && pCtx->ip.u8CSO)
     2952            {
     2953                E1kLog(("e1kCanDoGso: IXSM (IPv6)\n"));
    29012954                return false;
     2955            }
    29022956            if (!pData->dw3.fTXSM)
     2957            {
     2958                E1kLog(("e1kCanDoGso: TXSM (IPv6)\n"));
    29032959                return false;
     2960            }
    29042961            /** @todo what more check should we perform here? Ethernet frame type? */
     2962            E1kLog2(("e1kCanDoGso: OK, IPv4\n"));
    29052963            return true;
    29062964
    29072965        default:
    29082966            Assert(pGso->u8Type == PDMNETWORKGSOTYPE_INVALID);
     2967            E1kLog2(("e1kCanDoGso: e1kSetupGsoCtx failed\n"));
    29092968            return false;
    29102969    }
     
    30053064DECLINLINE(bool) e1kXmitIsGsoBuf(PDMSCATTERGATHER const *pTxSg)
    30063065{
     3066#if 0
     3067    if (!pTxSg)
     3068        E1kLog(("e1kXmitIsGsoBuf: pTxSG is NULL\n"));
     3069    if (pTxSg && pTxSg->pvUser)
     3070        E1kLog(("e1kXmitIsGsoBuf: pvUser is NULL\n"));
     3071#endif
    30073072    return pTxSg && pTxSg->pvUser /* GSO indicator */;
    30083073}
     
    34883553                pState->u16HdrRemain = pDesc->context.dw3.u8HDRLEN;
    34893554                e1kSetupGsoCtx(&pState->GsoCtx, &pDesc->context);
     3555                STAM_COUNTER_INC(&pState->StatTxDescCtxTSE);
    34903556            }
    34913557            else
     3558            {
    34923559                pState->contextNormal = pDesc->context;
     3560                STAM_COUNTER_INC(&pState->StatTxDescCtxNormal);
     3561            }
    34933562            E1kLog2(("%s %s context updated: IP CSS=%02X, IP CSO=%02X, IP CSE=%04X"
    34943563                    ", TU CSS=%02X, TU CSO=%02X, TU CSE=%04X\n", INSTANCE(pState),
     
    35293598                         pState->fIPcsum ? " IP" : "",
    35303599                         pState->fTCPcsum ? " TCP/UDP" : ""));
    3531                 if (e1kCanDoGso(&pState->GsoCtx, &pDesc->data))
     3600                if (e1kCanDoGso(&pState->GsoCtx, &pDesc->data, &pState->contextTSE))
    35323601                    e1kXmitAllocBuf(pState, pState->contextTSE.dw2.u20PAYLEN + pState->contextTSE.dw3.u8HDRLEN,
    35333602                                    true /*fExactSize*/, true /*fGso*/);
     
    35453614            if (e1kXmitIsGsoBuf(pState->pTxSgR3))
    35463615            {
     3616                STAM_COUNTER_INC(&pState->StatTxPathGSO);
    35473617                bool fRc = e1kAddToFrame(pState, pDesc->data.u64BufAddr, pDesc->data.cmd.u20DTALEN);
    35483618                if (pDesc->data.cmd.fEOP)
     
    35693639            else if (!pDesc->data.cmd.fTSE)
    35703640            {
     3641                STAM_COUNTER_INC(&pState->StatTxPathRegular);
    35713642                bool fRc = e1kAddToFrame(pState, pDesc->data.u64BufAddr, pDesc->data.cmd.u20DTALEN);
    35723643                if (pDesc->data.cmd.fEOP)
     
    35933664            }
    35943665            else
     3666            {
     3667                STAM_COUNTER_INC(&pState->StatTxPathFallback);
    35953668                e1kFallbackAddToFrame(pState, pDesc, pDesc->data.cmd.u20DTALEN);
     3669            }
    35963670
    35973671            e1kDescReport(pState, pDesc, addr);
     
    57415815    PDMDevHlpSTAMRegisterF(pDevIns, &pState->StatTransmitSend,       STAMTYPE_PROFILE, STAMVISIBILITY_ALWAYS, STAMUNIT_TICKS_PER_CALL, "Profiling send transmit in HC",      "/Devices/E1k%d/Transmit/Send", iInstance);
    57425816
     5817    PDMDevHlpSTAMRegisterF(pDevIns, &pState->StatTxDescCtxNormal,    STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,     "Number of normal context descriptors","/Devices/E1k%d/TxDesc/ContexNormal", iInstance);
     5818    PDMDevHlpSTAMRegisterF(pDevIns, &pState->StatTxDescCtxTSE,       STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,     "Number of TSE context descriptors",  "/Devices/E1k%d/TxDesc/ContextTSE", iInstance);
     5819    PDMDevHlpSTAMRegisterF(pDevIns, &pState->StatTxDescData,         STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,     "Number of TX data descriptors",      "/Devices/E1k%d/TxDesc/Data", iInstance);
    57435820    PDMDevHlpSTAMRegisterF(pDevIns, &pState->StatTxDescLegacy,       STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,     "Number of TX legacy descriptors",    "/Devices/E1k%d/TxDesc/Legacy", iInstance);
    5744     PDMDevHlpSTAMRegisterF(pDevIns, &pState->StatTxDescData,         STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,     "Number of TX data descriptors",      "/Devices/E1k%d/TxDesc/Data", iInstance);
    57455821    PDMDevHlpSTAMRegisterF(pDevIns, &pState->StatTxDescTSEData,      STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,     "Number of TX TSE data descriptors",  "/Devices/E1k%d/TxDesc/TSEData", iInstance);
     5822    PDMDevHlpSTAMRegisterF(pDevIns, &pState->StatTxPathFallback,     STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,     "Fallback TSE descriptor path",       "/Devices/E1k%d/TxPath/Fallback", iInstance);
     5823    PDMDevHlpSTAMRegisterF(pDevIns, &pState->StatTxPathGSO,          STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,     "GSO TSE descriptor path",            "/Devices/E1k%d/TxPath/GSO", iInstance);
     5824    PDMDevHlpSTAMRegisterF(pDevIns, &pState->StatTxPathRegular,      STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,     "Regular descriptor path",            "/Devices/E1k%d/TxPath/Normal", iInstance);
    57465825    PDMDevHlpSTAMRegisterF(pDevIns, &pState->StatPHYAccesses,        STAMTYPE_COUNTER, STAMVISIBILITY_ALWAYS, STAMUNIT_OCCURENCES,     "Number of PHY accesses",             "/Devices/E1k%d/PHYAccesses", iInstance);
    57475826#endif /* VBOX_WITH_STATISTICS || E1K_REL_STATS */
Note: See TracChangeset for help on using the changeset viewer.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette