VirtualBox

Changeset 43507 in vbox for trunk/src/VBox


Ignore:
Timestamp:
Oct 2, 2012 1:22:31 PM (12 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
81089
Message:

Main/Metrics: Alternative way to get link speed for old kernels (#6345)

Location:
trunk/src/VBox/Main
Files:
9 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Main/include/HostNetworkInterfaceImpl.h

    r43445 r43507  
    110110        HostNetworkInterfaceMediumType_T mediumType;
    111111        HostNetworkInterfaceStatus_T status;
     112        ULONG speedMbytes;
    112113    } m;
    113114
  • trunk/src/VBox/Main/include/Performance.h

    r43456 r43507  
    361361        /** Returns CPU usage counters in platform-specific units. */
    362362        virtual int getRawHostCpuLoad(uint64_t *user, uint64_t *kernel, uint64_t *idle);
    363         /** Returns received and transmitted bytes as well as link speed. */
    364         virtual int getRawHostNetworkLoad(const char *name, uint64_t *rx, uint64_t *tx, uint64_t *speed);
     363        /** Returns received and transmitted bytes. */
     364        virtual int getRawHostNetworkLoad(const char *name, uint64_t *rx, uint64_t *tx);
    365365        /** Returns process' CPU usage counter in platform-specific units. */
    366366        virtual int getRawProcessCpuLoad(RTPROCESS process, uint64_t *user, uint64_t *kernel, uint64_t *total);
     
    496496    {
    497497    public:
    498         HostNetworkLoadRaw(CollectorHAL *hal, ComPtr<IUnknown> object, com::Utf8Str name, com::Utf8Str ifname, SubMetric *rx, SubMetric *tx)
    499             : BaseMetric(hal, name, object), mInterfaceName(ifname), mRx(rx), mTx(tx), mRxPrev(0), mTxPrev(0), mRc(VINF_SUCCESS) {};
     498        HostNetworkLoadRaw(CollectorHAL *hal, ComPtr<IUnknown> object, com::Utf8Str name, com::Utf8Str ifname, uint32_t speed, SubMetric *rx, SubMetric *tx)
     499            : BaseMetric(hal, name, object), mInterfaceName(ifname), mRx(rx), mTx(tx), mRxPrev(0), mTxPrev(0), mRc(VINF_SUCCESS) { mSpeed = (uint64_t)speed * (1000000/8); /* Convert to bytes/sec */ };
    500500        ~HostNetworkLoadRaw() { delete mRx; delete mTx; };
    501501
     
    515515        uint64_t      mRxPrev;
    516516        uint64_t      mTxPrev;
     517        uint64_t      mSpeed;
    517518        int           mRc;
    518519    };
  • trunk/src/VBox/Main/include/netif.h

    r36057 r43507  
    7272    NETIFTYPE      enmMediumType;
    7373    NETIFSTATUS    enmStatus;
     74    uint32_t       uSpeedMbytes;
    7475    RTUUID         Uuid;
    7576    char           szShortName[VBOXNET_MAX_SHORT_NAME];
     
    9293int NetIfGetConfigByName(PNETIFINFO pInfo);
    9394int NetIfDhcpRediscover(VirtualBox *pVbox, HostNetworkInterface * pIf);
     95int NetIfAdpCtlOut(const char * pcszName, const char * pcszCmd, char *pszBuffer, size_t cBufSize);
    9496
    9597DECLINLINE(Bstr) composeIPv6Address(PRTNETADDRIPV6 aAddrPtr)
  • trunk/src/VBox/Main/src-server/HostNetworkInterfaceImpl.cpp

    r43453 r43507  
    100100
    101101    /* Create and register base metrics */
    102     pm::BaseMetric *networkLoad = new pm::HostNetworkLoadRaw(hal, objptr, strName, Utf8Str(mInterfaceName), networkLoadRx, networkLoadTx);
     102    pm::BaseMetric *networkLoad = new pm::HostNetworkLoadRaw(hal, objptr, strName, Utf8Str(mInterfaceName), m.speedMbytes, networkLoadRx, networkLoadTx);
    103103    aCollector->registerBaseMetric(networkLoad);
    104104
     
    149149        m.mediumType = info.enmMediumType;
    150150        m.status = info.enmStatus;
    151 
    152151#endif /* !RT_OS_WINDOWS */
     152        m.speedMbytes = info.uSpeedMbytes;
    153153        return S_OK;
    154154    }
     
    201201    m.status = pIf->enmStatus;
    202202#endif /* !RT_OS_WINDOWS */
     203    m.speedMbytes = pIf->uSpeedMbytes;
    203204
    204205    /* Confirm a successful initialization */
  • trunk/src/VBox/Main/src-server/Performance.cpp

    r43456 r43507  
    5959}
    6060
    61 int CollectorHAL::getRawHostNetworkLoad(const char * /* name */, uint64_t * /* rx */, uint64_t * /* tx */, uint64_t */* speed */)
     61int CollectorHAL::getRawHostNetworkLoad(const char * /* name */, uint64_t * /* rx */, uint64_t * /* tx */)
    6262{
    6363    return E_NOTIMPL;
     
    656656    mRx->init(mLength);
    657657    mTx->init(mLength);
    658     uint64_t speed;
    659     int rc = mHAL->getRawHostNetworkLoad(mInterfaceName.c_str(), &mRxPrev, &mTxPrev, &speed);
     658    int rc = mHAL->getRawHostNetworkLoad(mInterfaceName.c_str(), &mRxPrev, &mTxPrev);
    660659    AssertRC(rc);
    661660}
     
    670669        if (SUCCEEDED(hrc))
    671670        {
    672             LogRel(("Failed to collect network metrics for %s: %Rrc (%d).", mInterfaceName.c_str(), mRc, mRc));
     671            LogRel(("Failed to collect network metrics for %s: %Rrc (%d).\n", mInterfaceName.c_str(), mRc, mRc));
    673672            mRc = VINF_SUCCESS;
    674673        }
     
    678677void HostNetworkLoadRaw::collect()
    679678{
    680     uint64_t rx, tx, speed;
    681 
    682     mRc = mHAL->getRawHostNetworkLoad(mInterfaceName.c_str(), &rx, &tx, &speed);
     679    uint64_t rx, tx;
     680
     681    mRc = mHAL->getRawHostNetworkLoad(mInterfaceName.c_str(), &rx, &tx);
    683682    if (RT_SUCCESS(mRc))
    684683    {
     
    686685        uint64_t txDiff = tx - mTxPrev;
    687686
    688         if (RT_UNLIKELY(speed * getPeriod() == 0))
    689         {
    690             Assert(speed * getPeriod());
    691             LogFlowThisFunc(("Impossible! speed=%llu period=%d.\n", speed, getPeriod()));
     687        if (RT_UNLIKELY(mSpeed * getPeriod() == 0))
     688        {
     689            Assert(mSpeed * getPeriod());
     690            LogFlowThisFunc(("Impossible! speed=%llu period=%d.\n", mSpeed, getPeriod()));
    692691            mRx->put(0);
    693692            mTx->put(0);
     
    695694        else
    696695        {
    697             mRx->put((ULONG)(PM_NETWORK_LOAD_MULTIPLIER * rxDiff / (speed * getPeriod())));
    698             mTx->put((ULONG)(PM_NETWORK_LOAD_MULTIPLIER * txDiff / (speed * getPeriod())));
     696            mRx->put((ULONG)(PM_NETWORK_LOAD_MULTIPLIER * rxDiff / (mSpeed * getPeriod())));
     697            mTx->put((ULONG)(PM_NETWORK_LOAD_MULTIPLIER * txDiff / (mSpeed * getPeriod())));
    699698        }
    700699
  • trunk/src/VBox/Main/src-server/generic/NetIf-generic.cpp

    r42994 r43507  
    7777    Utf8Str strName(interfaceName);
    7878    return NetIfAdpCtl(strName.c_str(), pszAddr, pszOption, pszMask);
     79}
     80
     81int NetIfAdpCtlOut(const char * pcszName, const char * pcszCmd, char *pszBuffer, size_t cBufSize)
     82{
     83    char szAdpCtl[RTPATH_MAX];
     84    int rc = RTPathExecDir(szAdpCtl, sizeof(szAdpCtl) - sizeof("/" VBOXNETADPCTL_NAME " ") - strlen(pcszCmd));
     85    if (RT_FAILURE(rc))
     86    {
     87        LogRel(("NetIfAdpCtlStream: Failed to get program path, rc=%Rrc\n", rc));
     88        return VERR_INVALID_PARAMETER;
     89    }
     90    strcat(szAdpCtl, "/" VBOXNETADPCTL_NAME " ");
     91    if (pcszName && strlen(pcszName) <= RTPATH_MAX - strlen(szAdpCtl) - 1 - strlen(pcszCmd))
     92    {
     93        strcat(szAdpCtl, pcszName);
     94        strcat(szAdpCtl, " ");
     95        strcat(szAdpCtl, pcszCmd);
     96    }
     97    else
     98    {
     99        LogRel(("NetIfAdpCtlStream: Command line is too long: %s%s %s\n", szAdpCtl, pcszName, pcszCmd));
     100        return VERR_INVALID_PARAMETER;
     101    }
     102    if (strlen(szAdpCtl) < RTPATH_MAX - sizeof(" 2>&1"))
     103        strcat(szAdpCtl, " 2>&1");
     104    FILE *fp = popen(szAdpCtl, "r");
     105    if (fp)
     106    {
     107        if (fgets(pszBuffer, cBufSize, fp))
     108        {
     109            if (!strncmp(VBOXNETADPCTL_NAME ":", pszBuffer, sizeof(VBOXNETADPCTL_NAME)))
     110            {
     111                LogRel(("NetIfAdpCtlStream: %s", pszBuffer));
     112                rc = VERR_INTERNAL_ERROR;
     113            }
     114        }
     115        else
     116        {
     117            LogRel(("NetIfAdpCtlStream: No output from " VBOXNETADPCTL_NAME));
     118            rc = VERR_INTERNAL_ERROR;
     119        }
     120        pclose(fp);
     121    }
     122    return rc;
    79123}
    80124
  • trunk/src/VBox/Main/src-server/linux/NetIf-linux.cpp

    r33540 r43507  
    149149            fclose(fp);
    150150        }
     151        /*
     152         * I wish I could do simple ioctl here, but older kernels require root
     153         * privileges for any ethtool commands.
     154         */
     155        char szBuf[256];
     156        /* First, we try to retrieve the speed via sysfs. */
     157        RTStrPrintf(szBuf, sizeof(szBuf), "/sys/class/net/%s/speed", pszName);
     158        fp = fopen(szBuf, "r");
     159        if (fp && fscanf(fp, "%u", &pInfo->uSpeedMbytes) == 1)
     160            fclose(fp);
     161        else
     162        {
     163            /* Failed to get speed via sysfs, go to plan B. */
     164            int rc = NetIfAdpCtlOut(pszName, "info", szBuf, sizeof(szBuf));
     165            if (RT_SUCCESS(rc))
     166            {
     167                pInfo->uSpeedMbytes = RTStrToUInt32(szBuf);
     168            }
     169            else
     170                return rc;
     171        }
    151172    }
    152173    return VINF_SUCCESS;
  • trunk/src/VBox/Main/src-server/linux/PerformanceLinux.cpp

    r43445 r43507  
    4040
    4141    virtual int getRawHostCpuLoad(uint64_t *user, uint64_t *kernel, uint64_t *idle);
    42     virtual int getRawHostNetworkLoad(const char *name, uint64_t *rx, uint64_t *tx, uint64_t *speed);
     42    virtual int getRawHostNetworkLoad(const char *name, uint64_t *rx, uint64_t *tx);
    4343    virtual int getRawProcessCpuLoad(RTPROCESS process, uint64_t *user, uint64_t *kernel, uint64_t *total);
    4444private:
     
    218218}
    219219
    220 int CollectorLinux::getRawHostNetworkLoad(const char *name, uint64_t *rx, uint64_t *tx, uint64_t *speed)
     220int CollectorLinux::getRawHostNetworkLoad(const char *name, uint64_t *rx, uint64_t *tx)
    221221{
    222222    int rc = VINF_SUCCESS;
     
    242242                rc = VERR_FILE_IO_ERROR;
    243243            fclose(f);
    244             RTStrPrintf(szIfName, sizeof(szIfName), "/sys/class/net/%s/speed", name);
    245             f = fopen(szIfName, "r");
    246             if (f)
    247             {
    248                 if (fscanf(f, "%llu", &u64Speed) == 1)
    249                     *speed = u64Speed * (1000000/8); /* Convert to bytes/sec */
    250                 else
    251                     rc = VERR_FILE_IO_ERROR;
    252                 fclose(f);
    253             }
    254             else
    255                 rc = VERR_ACCESS_DENIED;
    256244        }
    257245        else
  • trunk/src/VBox/Main/testcase/tstCollector.cpp

    r43445 r43507  
    145145{
    146146    pm::CollectorHints hints;
    147     uint64_t hostRxStart, hostTxStart, speedStart;
    148     uint64_t hostRxStop, hostTxStop, speedStop;
     147    uint64_t hostRxStart, hostTxStart;
     148    uint64_t hostRxStop, hostTxStop, speed = 125000000; /* Assume 1Gbit/s */
    149149
    150150    RTPrintf("\ntstCollector: TESTING - Network load, sleeping for 5 sec...\n");
     
    156156        return 1;
    157157    }
    158     rc = collector->getRawHostNetworkLoad("eth0", &hostRxStart, &hostTxStart, &speedStart);
     158    rc = collector->getRawHostNetworkLoad("eth0", &hostRxStart, &hostTxStart);
    159159    if (RT_FAILURE(rc))
    160160    {
     
    171171        return 1;
    172172    }
    173     rc = collector->getRawHostNetworkLoad("eth0", &hostRxStop, &hostTxStop, &speedStop);
     173    rc = collector->getRawHostNetworkLoad("eth0", &hostRxStop, &hostTxStop);
    174174    if (RT_FAILURE(rc))
    175175    {
     
    177177        return 1;
    178178    }
    179     if (speedStart != speedStop)
    180         RTPrintf("tstCollector: getRawHostNetworkLoad() returned different bandwidth (%llu != %llu)\n", speedStart, speedStop);
    181179    RTPrintf("tstCollector: host network speed = %llu bytes/sec (%llu mbit/sec)\n",
    182              speedStop, speedStop/(1000000/8));
     180             speed, speed/(1000000/8));
    183181    RTPrintf("tstCollector: host network rx    = %llu bytes/sec (%llu mbit/sec, %d %%*100)\n",
    184182             (hostRxStop - hostRxStart)/5, (hostRxStop - hostRxStart)/(5000000/8),
    185              (hostRxStop - hostRxStart) * 10000 / (speedStop * 5));
     183             (hostRxStop - hostRxStart) * 10000 / (speed * 5));
    186184    RTPrintf("tstCollector: host network tx    = %llu bytes/sec (%llu mbit/sec, %d %%*100)\n",
    187185             (hostTxStop - hostTxStart)/5, (hostTxStop - hostTxStart)/(5000000/8),
    188              (hostTxStop - hostTxStart) * 10000 / (speedStop * 5));
     186             (hostTxStop - hostTxStart) * 10000 / (speed * 5));
    189187
    190188    return 0;
Note: See TracChangeset for help on using the changeset viewer.

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