VirtualBox

儲存庫 vbox 的更動 12439


忽略:
時間撮記:
2008-9-12 下午05:37:42 (16 年 以前)
作者:
vboxsync
訊息:

installer code added to HostImpl, bugfixing in macket handing in the driver

位置:
trunk/src/VBox/Main
檔案:
修改 2 筆資料

圖例:

未更動
新增
刪除
  • trunk/src/VBox/Main/HostImpl.cpp

    r12400 r12439  
    8080# include <shlobj.h>
    8181# include <cfgmgr32.h>
     82
     83# ifdef VBOX_WITH_NETFLT
     84
     85# endif /* VBOX_WITH_NETFLT */
     86#include <Netcfgn.h>
    8287#endif /* RT_OS_WINDOWS */
    8388
     
    11501155    return rc;
    11511156}
     1157
     1158# ifdef VBOX_WITH_NETFLT
     1159
     1160#define VBOX_NETCFG_LOCK_TIME_OUT     5000
     1161
     1162/*TODO: should use some real VBox app name */
     1163#define VBOX_NETCFG_APP_NAME L"VirtualBox"
     1164
     1165/*
     1166 * Release reference
     1167 */
     1168static VOID vboxNetCfgWinReleaseRef (IN IUnknown* punk)
     1169{
     1170    if(punk)
     1171    {
     1172        punk->Release();
     1173    }
     1174
     1175    return;
     1176}
     1177
     1178/*
     1179 * Get a reference to INetCfg.
     1180 *
     1181 *    fGetWriteLock  [in]  If TRUE, Write lock.requested.
     1182 *    lpszAppName    [in]  Application name requesting the reference.
     1183 *    ppnc           [out] Reference to INetCfg.
     1184 *    lpszLockedBy   [in]  Optional. Application who holds the write lock.
     1185 *
     1186 * Returns:   S_OK on sucess, otherwise an error code.
     1187 */
     1188static HRESULT vboxNetCfgWinQueryINetCfg (IN BOOL fGetWriteLock,
     1189                      IN LPCWSTR lpszAppName,
     1190                      OUT INetCfg** ppnc,
     1191                      OUT LPWSTR *lpszLockedBy)
     1192{
     1193    INetCfg      *pnc = NULL;
     1194    INetCfgLock  *pncLock = NULL;
     1195    HRESULT      hr = S_OK;
     1196
     1197    /*
     1198     * Initialize the output parameters.
     1199     */
     1200    *ppnc = NULL;
     1201
     1202    if ( lpszLockedBy )
     1203    {
     1204        *lpszLockedBy = NULL;
     1205    }
     1206    /*
     1207     * Initialize COM
     1208     */
     1209    hr = CoInitialize( NULL );
     1210
     1211    if ( hr == S_OK )
     1212    {
     1213
     1214        /*
     1215         * Create the object implementing INetCfg.
     1216         */
     1217        hr = CoCreateInstance( CLSID_CNetCfg,
     1218                               NULL, CLSCTX_INPROC_SERVER,
     1219                               IID_INetCfg,
     1220                               (void**)&pnc );
     1221        if ( hr == S_OK )
     1222        {
     1223
     1224            if ( fGetWriteLock )
     1225            {
     1226
     1227                /*
     1228                 * Get the locking reference
     1229                 */
     1230                hr = pnc->QueryInterface( IID_INetCfgLock,
     1231                                          (LPVOID *)&pncLock );
     1232                if ( hr == S_OK )
     1233                {
     1234
     1235                    /*
     1236                     * Attempt to lock the INetCfg for read/write
     1237                     */
     1238                    hr = pncLock->AcquireWriteLock( VBOX_NETCFG_LOCK_TIME_OUT,
     1239                                                    lpszAppName,
     1240                                                    lpszLockedBy);
     1241                    if (hr == S_FALSE )
     1242                    {
     1243                        hr = NETCFG_E_NO_WRITE_LOCK;
     1244                    }
     1245                }
     1246            }
     1247
     1248            if ( hr == S_OK )
     1249            {
     1250
     1251                /*
     1252                 * Initialize the INetCfg object.
     1253                 */
     1254                hr = pnc->Initialize( NULL );
     1255
     1256                if ( hr == S_OK )
     1257                {
     1258                    *ppnc = pnc;
     1259                    pnc->AddRef();
     1260                }
     1261                else
     1262                {
     1263
     1264                    /*
     1265                     * Initialize failed, if obtained lock, release it
     1266                     */
     1267                    if ( pncLock )
     1268                    {
     1269                        pncLock->ReleaseWriteLock();
     1270                    }
     1271                }
     1272            }
     1273
     1274            vboxNetCfgWinReleaseRef( pncLock );
     1275            vboxNetCfgWinReleaseRef( pnc );
     1276        }
     1277
     1278        /*
     1279         * In case of error, uninitialize COM.
     1280         */
     1281        if ( hr != S_OK )
     1282        {
     1283            CoUninitialize();
     1284        }
     1285    }
     1286
     1287    return hr;
     1288}
     1289
     1290/*
     1291 * Get a reference to INetCfg.
     1292 *
     1293 *    pnc           [in] Reference to INetCfg to release.
     1294 *    fHasWriteLock [in] If TRUE, reference was held with write lock.
     1295 *
     1296 * Returns:   S_OK on sucess, otherwise an error code.
     1297 *
     1298 */
     1299static HRESULT vboxNetCfgWinReleaseINetCfg (IN INetCfg* pnc,
     1300                          IN BOOL fHasWriteLock)
     1301{
     1302    INetCfgLock    *pncLock = NULL;
     1303    HRESULT        hr = S_OK;
     1304
     1305    /*
     1306     * Uninitialize INetCfg
     1307     */
     1308    hr = pnc->Uninitialize();
     1309
     1310    /*
     1311     * If write lock is present, unlock it
     1312     */
     1313    if ( hr == S_OK && fHasWriteLock )
     1314    {
     1315
     1316        /*
     1317         * Get the locking reference
     1318         */
     1319        hr = pnc->QueryInterface( IID_INetCfgLock,
     1320                                  (LPVOID *)&pncLock);
     1321        if ( hr == S_OK )
     1322        {
     1323           hr = pncLock->ReleaseWriteLock();
     1324           vboxNetCfgWinReleaseRef( pncLock );
     1325        }
     1326    }
     1327
     1328    vboxNetCfgWinReleaseRef( pnc );
     1329
     1330    /*
     1331     * Uninitialize COM.
     1332     */
     1333    CoUninitialize();
     1334
     1335    return hr;
     1336}
     1337
     1338/*
     1339 * Get network component enumerator reference.
     1340 *
     1341 * Arguments:
     1342 *    pnc         [in]  Reference to INetCfg.
     1343 *    pguidClass  [in]  Class GUID of the network component.
     1344 *    ppencc      [out] Enumerator reference.
     1345 *
     1346 * Returns:   S_OK on sucess, otherwise an error code.
     1347 */
     1348static HRESULT vboxNetCfgWinGetComponentEnum (INetCfg* pnc,
     1349                            IN const GUID* pguidClass,
     1350                            OUT IEnumNetCfgComponent **ppencc)
     1351{
     1352    INetCfgClass  *pncclass;
     1353    HRESULT       hr;
     1354
     1355    *ppencc = NULL;
     1356
     1357    /*
     1358     * Get the class reference.
     1359     */
     1360    hr = pnc->QueryNetCfgClass( pguidClass,
     1361                                IID_INetCfgClass,
     1362                                (PVOID *)&pncclass );
     1363
     1364    if ( hr == S_OK )
     1365    {
     1366
     1367        /*
     1368         * Get the enumerator reference.
     1369         */
     1370        hr = pncclass->EnumComponents( ppencc );
     1371
     1372        /*
     1373         * We don't need the class reference any more.
     1374         */
     1375        vboxNetCfgWinReleaseRef( pncclass );
     1376    }
     1377
     1378    return hr;
     1379}
     1380
     1381/*
     1382 * Enumerates the first network component.
     1383 *
     1384 * Arguments:
     1385 *    pencc      [in]  Component enumerator reference.
     1386 *    ppncc      [out] Network component reference.
     1387 *
     1388 * Returns:   S_OK on sucess, otherwise an error code.
     1389 */
     1390static HRESULT vboxNetCfgWinGetFirstComponent (IN IEnumNetCfgComponent* pencc,
     1391                             OUT INetCfgComponent **ppncc)
     1392{
     1393    HRESULT  hr;
     1394    ULONG    ulCount;
     1395
     1396    *ppncc = NULL;
     1397
     1398    pencc->Reset();
     1399
     1400    hr = pencc->Next( 1,
     1401                      ppncc,
     1402                      &ulCount );
     1403    return hr;
     1404}
     1405
     1406/*
     1407 * Enumerate the next network component.
     1408 *
     1409 * The function behaves just like vboxNetCfgWinGetFirstComponent if
     1410 * it is called right after vboxNetCfgWinGetComponentEnum.
     1411 *
     1412 * Arguments:
     1413 *    pencc      [in]  Component enumerator reference.
     1414 *    ppncc      [out] Network component reference.
     1415 *
     1416 * Returns:   S_OK on sucess, otherwise an error code.
     1417 */
     1418static HRESULT vboxNetCfgWinGetNextComponent (IN IEnumNetCfgComponent* pencc,
     1419                            OUT INetCfgComponent **ppncc)
     1420{
     1421    HRESULT  hr;
     1422    ULONG    ulCount;
     1423
     1424    *ppncc = NULL;
     1425
     1426    hr = pencc->Next( 1,
     1427                      ppncc,
     1428                      &ulCount );
     1429    return hr;
     1430}
     1431
     1432/*
     1433 * Install a network component(protocols, clients and services)
     1434 *            given its INF file.
     1435 * Arguments:
     1436 *    pnc              [in] Reference to INetCfg.
     1437 *    lpszComponentId  [in] PnpID of the network component.
     1438 *    pguidClass       [in] Class GUID of the network component.
     1439 *
     1440 * Returns:   S_OK on sucess, otherwise an error code.
     1441 */
     1442static HRESULT vboxNetCfgWinInstallComponent(IN INetCfg* pnc,
     1443                           IN LPCWSTR szComponentId,
     1444                           IN const GUID* pguidClass)
     1445{
     1446    INetCfgClassSetup   *pncClassSetup = NULL;
     1447    INetCfgComponent    *pncc = NULL;
     1448    OBO_TOKEN           OboToken;
     1449    HRESULT             hr = S_OK;
     1450
     1451    /*
     1452     * OBO_TOKEN specifies on whose behalf this
     1453     * component is being installed.
     1454     * Set it to OBO_USER so that szComponentId will be installed
     1455     * on behalf of the user.
     1456     */
     1457
     1458    ZeroMemory( &OboToken,
     1459                sizeof(OboToken) );
     1460    OboToken.Type = OBO_USER;
     1461
     1462    /*
     1463     * Get component's setup class reference.
     1464     */
     1465    hr = pnc->QueryNetCfgClass ( pguidClass,
     1466                                 IID_INetCfgClassSetup,
     1467                                 (void**)&pncClassSetup );
     1468    if ( hr == S_OK ) {
     1469
     1470        hr = pncClassSetup->Install( szComponentId,
     1471                                     &OboToken,
     1472                                     0,
     1473                                     0,       /* Upgrade from build number. */
     1474                                     NULL,    /* Answerfile name */
     1475                                     NULL,    /* Answerfile section name */
     1476                                     &pncc ); /* Reference after the component */
     1477        if ( S_OK == hr ) {                   /* is installed. */
     1478
     1479            /*
     1480             * we don't need to use pncc (INetCfgComponent), release it
     1481             */
     1482            vboxNetCfgWinReleaseRef( pncc );
     1483        }
     1484
     1485        vboxNetCfgWinReleaseRef( pncClassSetup );
     1486    }
     1487
     1488    return hr;
     1489}
     1490
     1491/*
     1492 * Install a network component(protocols, clients and services)
     1493 *            given its INF file.
     1494 *
     1495 * Arguments:
     1496 *    pnc              [in] Reference to INetCfg.
     1497 *    lpszComponentId  [in] PnpID of the network component.
     1498 *    pguidClass       [in] Class GUID of the network component.
     1499 *    lpszInfFullPath  [in] INF file to install from.
     1500 *
     1501 * Returns:   S_OK on sucess, otherwise an error code.
     1502 */
     1503static HRESULT vboxNetCfgWinInstallNetComponent (IN INetCfg *pnc,
     1504                               IN LPCWSTR lpszComponentId,
     1505                               IN const GUID    *pguidClass,
     1506                               IN LPCWSTR lpszInfFullPath)
     1507{
     1508    DWORD     dwError;
     1509    HRESULT   hr = S_OK;
     1510    WCHAR     Drive[_MAX_DRIVE];
     1511    WCHAR     Dir[_MAX_DIR];
     1512    WCHAR     DirWithDrive[_MAX_DRIVE+_MAX_DIR];
     1513
     1514    /*
     1515     * If full path to INF has been specified, the INF
     1516     * needs to be copied using Setup API to ensure that any other files
     1517     * that the primary INF copies will be correctly found by Setup API
     1518     */
     1519
     1520    if ( lpszInfFullPath )
     1521    {
     1522
     1523        /*
     1524         * Get the path where the INF file is.
     1525         */
     1526        _wsplitpath( lpszInfFullPath, Drive, Dir, NULL, NULL );
     1527
     1528        wcscpy( DirWithDrive, Drive );
     1529        wcscat( DirWithDrive, Dir );
     1530
     1531        /*
     1532         * Copy the INF file and other files referenced in the INF file.
     1533         */
     1534        if ( !SetupCopyOEMInfW(lpszInfFullPath,
     1535                               DirWithDrive,  /* Other files are in the */
     1536                                              /* same dir. as primary INF */
     1537                               SPOST_PATH,    /* First param is path to INF */
     1538                               0,             /* Default copy style */
     1539                               NULL,          /* Name of the INF after */
     1540                                              /* it's copied to %windir%\inf */
     1541                               0,             /* Max buf. size for the above */
     1542                               NULL,          /* Required size if non-null */
     1543                               NULL) )        /* Optionally get the filename */
     1544                                              /* part of Inf name after it is copied. */
     1545        {
     1546            dwError = GetLastError();
     1547
     1548            hr = HRESULT_FROM_WIN32( dwError );
     1549        }
     1550    }
     1551
     1552    if ( S_OK == hr )
     1553    {
     1554
     1555        /*
     1556         * Install the network component.
     1557         */
     1558        hr = vboxNetCfgWinInstallComponent( pnc,
     1559                                 lpszComponentId,
     1560                                 pguidClass );
     1561        if ( hr == S_OK )
     1562        {
     1563
     1564            /*
     1565             * On success, apply the changes
     1566             */
     1567            hr = pnc->Apply();
     1568        }
     1569    }
     1570
     1571    return hr;
     1572}
     1573
     1574/*
     1575 * List installed network components of specific class.
     1576 *
     1577 * Arguments:
     1578 *    hwndTree      [in]  Tree handle in which to list.
     1579 *    pguidClass    [in]  Class GUID of the network compoent class.
     1580 *
     1581 * Returns:   None.
     1582 */
     1583static HRESULT vboxNetCfgWinQueryComponentInstalled(IN INetCfg *pnc, IN const GUID* pguidClass, IN LPWSTR pnpId, OUT bool * pResult)
     1584{
     1585    IEnumNetCfgComponent *pencc;
     1586    INetCfgComponent     *pncc;
     1587    HRESULT              hr;
     1588    LPWSTR           lpszId;
     1589
     1590
     1591    *pResult = false;
     1592
     1593
     1594        /*
     1595         * Get Component Enumerator Interface.
     1596         */
     1597        hr = vboxNetCfgWinGetComponentEnum( pnc,
     1598                pguidClass,
     1599                &pencc );
     1600        if ( hr == S_OK )
     1601        {
     1602
     1603            hr = vboxNetCfgWinGetFirstComponent( pencc, &pncc );
     1604
     1605            while( hr == S_OK )
     1606            {
     1607
     1608                hr = pncc->GetId( &lpszId );
     1609
     1610                if ( hr == S_OK )
     1611                {
     1612                    if(!wcscmp(lpszId, pnpId))
     1613                    {
     1614                        *pResult = true;
     1615                        vboxNetCfgWinReleaseRef( pncc );
     1616                        break;
     1617                    }
     1618                }
     1619
     1620                vboxNetCfgWinReleaseRef( pncc );
     1621
     1622                hr = vboxNetCfgWinGetNextComponent( pencc, &pncc );
     1623            }
     1624
     1625            vboxNetCfgWinReleaseRef( pencc );
     1626        }
     1627        else
     1628        {
     1629            Log(("Failed to get the network component enumerator."));
     1630        }
     1631
     1632
     1633    return hr;
     1634}
     1635
     1636/*
     1637 * Install a network component from an INF file.
     1638 *
     1639 * Arguments:
     1640 *    lpszInfFile [in]  INF file.
     1641 *    lpszPnpID   [in]  PnpID of the network component to install.
     1642 *    pguidClass  [in]  Class GUID of the network component.
     1643 *
     1644 * Returns:   None.
     1645 */
     1646static HRESULT vboxNetCfgWinInstallSpecifiedComponent (LPWSTR lpszInfFile,
     1647                                   LPWSTR lpszPnpID,
     1648                                   const GUID *pguidClass,
     1649                                   bool bForceInstall)
     1650{
     1651    INetCfg    *pnc;
     1652    LPWSTR     lpszApp;
     1653    HRESULT    hr;
     1654
     1655    hr = vboxNetCfgWinQueryINetCfg( TRUE,
     1656                       VBOX_NETCFG_APP_NAME,
     1657                       &pnc,
     1658                       &lpszApp );
     1659
     1660    if ( hr == S_OK )
     1661    {
     1662        bool bInstall = true;
     1663
     1664        if(!bForceInstall)
     1665        {
     1666            /* check if it is installed already */
     1667            bool bInstalled = false;
     1668            hr = vboxNetCfgWinQueryComponentInstalled(pnc, pguidClass, lpszPnpID, &bInstalled);
     1669            if(hr == S_OK && bInstalled)
     1670            {
     1671                /* no need to install */
     1672                bInstall = false;
     1673            }
     1674        }
     1675
     1676        if(bInstall)
     1677        {
     1678            /*
     1679             * Install the network component.
     1680             */
     1681            hr = vboxNetCfgWinInstallNetComponent( pnc,
     1682                                        lpszPnpID,
     1683                                        pguidClass,
     1684                                        lpszInfFile );
     1685            if ( (hr == S_OK) || (hr == NETCFG_S_REBOOT) )
     1686            {
     1687
     1688                hr = pnc->Apply();
     1689            }
     1690            else
     1691            {
     1692                if ( hr != HRESULT_FROM_WIN32(ERROR_CANCELLED) )
     1693                {
     1694                    Log(("Couldn't install the network component." ));
     1695                }
     1696            }
     1697
     1698        }
     1699        vboxNetCfgWinReleaseINetCfg( pnc,
     1700                          TRUE );
     1701    }
     1702    else
     1703    {
     1704        if ( (hr == NETCFG_E_NO_WRITE_LOCK) && lpszApp )
     1705        {
     1706            Log(("%s currently holds the lock, try later.", lpszApp));
     1707
     1708            CoTaskMemFree( lpszApp );
     1709        }
     1710        else
     1711        {
     1712            Log(("Couldn't the get notify object interface."));
     1713        }
     1714    }
     1715
     1716    return hr;
     1717}
     1718
     1719/**
     1720 * increments the reference to the netflt - to - aHostNetworkInterface binding reference count
     1721 * the exec flow:
     1722 * 1. if netflt is NOT installed currently - install it
     1723 * 2. if the NetFlt is not bound to the specified adapter - bind it
     1724 * 3. increase the binding reference count -
     1725 */
     1726STDMETHODIMP
     1727Host::NetFltAcquire (IHostNetworkInterface *aHostNetworkInterface,
     1728                                           IProgress **aProgress)
     1729{
     1730    HRESULT rc = S_OK;
     1731
     1732    /* TODO: encorporate with the VBoxSVC helper infastructure */
     1733
     1734    return rc;
     1735}
     1736
     1737/**
     1738 * decrements the reference to the netflt - to - aHostNetworkInterface binding reference count
     1739 */
     1740STDMETHODIMP
     1741Host::NetFltRelease (IHostNetworkInterface *aHostNetworkInterface,
     1742                                           IProgress **aProgress)
     1743{
     1744    HRESULT rc = S_OK;
     1745
     1746    /* TODO: encorporate with the VBoxSVC helper infastructure */
     1747
     1748    return rc;
     1749}
     1750# endif /*VBOX_WITH_NETFLT*/
    11521751
    11531752#endif /* RT_OS_WINDOWS */
  • trunk/src/VBox/Main/include/HostImpl.h

    r11258 r12439  
    9999                                           IHostNetworkInterface **aHostNetworkInterface,
    100100                                           IProgress **aProgress);
     101# ifdef VBOX_WITH_NETFLT
     102    /*
     103     * increments the reference to the netflt - to - aHostNetworkInterface binding reference count
     104     * the exec flow:
     105     * 1. if netflt is NOT installed currently - install it
     106     * 2. if the NetFlt is not bound to the specified adapter - bind it
     107     * 3. increase the binding reference count -
     108     */
     109    STDMETHOD(NetFltAcquire) (IHostNetworkInterface *aHostNetworkInterface,
     110                                           IProgress **aProgress);
     111
     112    /*
     113     * decrements the reference to the netflt - to - aHostNetworkInterface binding reference count
     114     */
     115    STDMETHOD(NetFltRelease) (IHostNetworkInterface *aHostNetworkInterface,
     116                                           IProgress **aProgress);
     117# endif /*VBOX_WITH_NETFLT*/
    101118#endif
    102119    STDMETHOD(CreateUSBDeviceFilter) (INPTR BSTR aName, IHostUSBDeviceFilter **aFilter);
注意: 瀏覽 TracChangeset 來幫助您使用更動檢視器

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