Changeset 36075 in vbox for trunk/src/VBox/Devices
- Timestamp:
- Feb 24, 2011 4:36:48 PM (14 years ago)
- svn:sync-xref-src-repo-rev:
- 70197
- Location:
- trunk/src/VBox/Devices/Network
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Devices/Network/DrvIntNet.cpp
r35353 r36075 182 182 /** Pointer to instance data of the internal networking driver. */ 183 183 typedef DRVINTNET *PDRVINTNET; 184 185 /** 186 * Config value to flag translation structure. 187 */ 188 typedef struct DRVINTNETFLAG 189 { 190 /** The value. */ 191 const char *pszChoice; 192 /** The corresponding flag. */ 193 uint32_t fFlag; 194 } DRVINTNETFLAG; 195 /** Pointer to a const flag value translation. */ 196 typedef DRVINTNETFLAG const *PCDRVINTNETFLAG; 184 197 185 198 … … 1134 1147 AbortWaitReq.fNoMoreWaits = true; 1135 1148 int rc = PDMDrvHlpSUPCallVMMR0Ex(pDrvIns, VMMR0_DO_INTNET_IF_ABORT_WAIT, &AbortWaitReq, sizeof(AbortWaitReq)); 1136 Assert RC(rc);1149 AssertMsg(RT_SUCCESS(rc) || rc == VERR_SEM_DESTROYED, ("%Rrc\n", rc)); 1137 1150 } 1138 1151 … … 1218 1231 1219 1232 /** 1233 * Queries the 'fixed' policy config value and sets the corresponding flag. 1234 * 1235 * @returns VBox status code (error set on failure). 1236 * @param pDrvIns The driver instance. 1237 * @param pszName The value name. 1238 * @param fFixedFlag The open network flag. 1239 * @param pfFlags The flags variable to update. 1240 */ 1241 static int drvIntNetR3CfgFixedPolicy(PPDMDRVINS pDrvIns, const char *pszName, uint32_t fFixedFlag, uint32_t *pfFlags) 1242 { 1243 bool fFixed; 1244 int rc = CFGMR3QueryBoolDef(pDrvIns->pCfg, pszName, &fFixed, false /*fDef*/); 1245 if (RT_SUCCESS(rc)) 1246 { 1247 if (fFixed) 1248 *pfFlags |= fFixedFlag; 1249 } 1250 else 1251 rc = PDMDrvHlpVMSetError(pDrvIns, rc, RT_SRC_POS, 1252 N_("Configuration error: Failed to query the value of \"%s\""), pszName); 1253 return rc; 1254 } 1255 1256 1257 /** 1258 * Queries a policy config value and translates it into open network flag. 1259 * 1260 * @returns VBox status code (error set on failure). 1261 * @param pDrvIns The driver instance. 1262 * @param pszName The value name. 1263 * @param paFlags The open network flag descriptors. 1264 * @param cFlags The number of descriptors. 1265 * @param pfFlags The flags variable to update. 1266 */ 1267 static int drvIntNetR3CfgGetPolicy(PPDMDRVINS pDrvIns, const char *pszName, PCDRVINTNETFLAG paFlags, size_t cFlags, uint32_t *pfFlags) 1268 { 1269 char szValue[64]; 1270 int rc = CFGMR3QueryString(pDrvIns->pCfg, pszName, szValue, sizeof(szValue)); 1271 if (RT_SUCCESS(rc)) 1272 { 1273 size_t i = cFlags; 1274 while (i-- > 0) 1275 if (!strcmp(paFlags[i].pszChoice, szValue)) 1276 { 1277 *pfFlags |= paFlags[i].fFlag; 1278 return VINF_SUCCESS; 1279 } 1280 if (!strcmp(szValue, "none")) 1281 return VINF_SUCCESS; 1282 1283 rc = PDMDrvHlpVMSetError(pDrvIns, VERR_INVALID_PARAMETER, RT_SRC_POS, 1284 N_("Configuration error: The value of \"%s\" is unknown: \"%s\""), pszName, szValue); 1285 } 1286 else if (rc == VERR_CFGM_VALUE_NOT_FOUND) 1287 return VINF_SUCCESS; 1288 else 1289 rc = PDMDrvHlpVMSetError(pDrvIns, rc, RT_SRC_POS, 1290 N_("Configuration error: Failed to query value of \"%s\""), pszName); 1291 return rc; 1292 } 1293 1294 1295 /** 1220 1296 * Construct a TAP network transport driver instance. 1221 1297 * … … 1226 1302 PDRVINTNET pThis = PDMINS_2_DATA(pDrvIns, PDRVINTNET); 1227 1303 bool f; 1228 bool fIgnoreConnectFailure;1229 1304 PDMDRV_CHECK_VERSIONS_RETURN(pDrvIns); 1230 1305 … … 1261 1336 * Validate the config. 1262 1337 */ 1263 if (!CFGMR3AreValuesValid(pCfg, 1264 "Network\0" 1265 "Trunk\0" 1266 "TrunkType\0" 1267 "ReceiveBufferSize\0" 1268 "SendBufferSize\0" 1269 "RestrictAccess\0" 1270 "SharedMacOnWire\0" 1271 "IgnoreAllPromisc\0" 1272 "QuietlyIgnoreAllPromisc\0" 1273 "IgnoreClientPromisc\0" 1274 "QuietlyIgnoreClientPromisc\0" 1275 "IgnoreTrunkWirePromisc\0" 1276 "QuietlyIgnoreTrunkWirePromisc\0" 1277 "IgnoreTrunkHostPromisc\0" 1278 "IgnoreConnectFailure\0" 1279 "QuietlyIgnoreTrunkHostPromisc\0" 1280 "IsService\0")) 1281 return VERR_PDM_DRVINS_UNKNOWN_CFG_VALUES; 1338 PDMDRV_VALIDATE_CONFIG_RETURN(pDrvIns, 1339 "Network" 1340 "|Trunk" 1341 "|TrunkType" 1342 "|ReceiveBufferSize" 1343 "|SendBufferSize" 1344 "|SharedMacOnWire" 1345 "|RestrictAccess" 1346 "|RequireExactPolicyMatch" 1347 "|RequireAsRestrictivePolicy" 1348 "|AccessPolicy" 1349 "|AccessPolicyFixed" 1350 "|PromiscPolicyClients" 1351 "|PromiscPolicyHost" 1352 "|PromiscPolicyWire" 1353 "|PromiscPolicyFixed" 1354 "|IfPolicyPromisc" 1355 "|IfPolicyFixed" 1356 "|TrunkPolicyHost" 1357 "|TrunkPolicyWire" 1358 "|TrunkPolicyFixed" 1359 "|IsService" 1360 "|IgnoreConnectFailure", 1361 ""); 1282 1362 1283 1363 /* … … 1303 1383 */ 1304 1384 INTNETOPENREQ OpenReq; 1305 memset(&OpenReq, 0, sizeof(OpenReq));1385 RT_ZERO(OpenReq); 1306 1386 OpenReq.Hdr.cbReq = sizeof(OpenReq); 1307 1387 OpenReq.Hdr.u32Magic = SUPVMMR0REQHDR_MAGIC; … … 1339 1419 N_("Configuration error: Failed to get the \"Trunk\" value")); 1340 1420 1341 /** @cfgm{RestrictAccess, boolean, true} 1342 * Whether to restrict the access to the network or if it should be public. Everyone on 1343 * the computer can connect to a public network. Don't change this. 1344 */ 1345 bool fRestrictAccess; 1346 rc = CFGMR3QueryBool(pCfg, "RestrictAccess", &fRestrictAccess); 1347 if (rc == VERR_CFGM_VALUE_NOT_FOUND) 1348 fRestrictAccess = true; 1349 else if (RT_FAILURE(rc)) 1350 return PDMDRV_SET_ERROR(pDrvIns, rc, 1351 N_("Configuration error: Failed to get the \"RestrictAccess\" value")); 1352 OpenReq.fFlags = fRestrictAccess ? 0 : INTNET_OPEN_FLAGS_PUBLIC; 1353 1354 /** @cfgm{IgnoreAllPromisc, boolean, false} 1355 * When set all request for operating any interface or trunk in promiscuous 1356 * mode will be ignored. */ 1357 rc = CFGMR3QueryBoolDef(pCfg, "IgnoreAllPromisc", &f, false); 1358 if (RT_FAILURE(rc)) 1359 return PDMDRV_SET_ERROR(pDrvIns, rc, 1360 N_("Configuration error: Failed to get the \"IgnoreAllPromisc\" value")); 1361 if (f) 1362 OpenReq.fFlags |= INTNET_OPEN_FLAGS_IGNORE_PROMISC; 1363 1364 /** @cfgm{QuietlyIgnoreAllPromisc, boolean, false} 1365 * When set all request for operating any interface or trunk in promiscuous 1366 * mode will be ignored. This differs from IgnoreAllPromisc in that clients 1367 * won't get VERR_INTNET_INCOMPATIBLE_FLAGS. */ 1368 rc = CFGMR3QueryBoolDef(pCfg, "QuietlyIgnoreAllPromisc", &f, false); 1369 if (RT_FAILURE(rc)) 1370 return PDMDRV_SET_ERROR(pDrvIns, rc, 1371 N_("Configuration error: Failed to get the \"QuietlyIgnoreAllPromisc\" value")); 1372 if (f) 1373 OpenReq.fFlags |= INTNET_OPEN_FLAGS_QUIETLY_IGNORE_PROMISC; 1374 1375 /** @cfgm{IgnoreClientPromisc, boolean, false} 1376 * When set all request for operating any non-trunk interface in promiscuous 1377 * mode will be ignored. */ 1378 rc = CFGMR3QueryBoolDef(pCfg, "IgnoreClientPromisc", &f, false); 1379 if (RT_FAILURE(rc)) 1380 return PDMDRV_SET_ERROR(pDrvIns, rc, 1381 N_("Configuration error: Failed to get the \"IgnoreClientPromisc\" value")); 1382 if (f) 1383 OpenReq.fFlags |= INTNET_OPEN_FLAGS_IGNORE_PROMISC; /** @todo add special flag for this. */ 1384 1385 /** @cfgm{QuietlyIgnoreClientPromisc, boolean, false} 1386 * When set all request for operating any non-trunk interface promiscuous mode 1387 * will be ignored. This differs from IgnoreClientPromisc in that clients won't 1388 * get VERR_INTNET_INCOMPATIBLE_FLAGS. */ 1389 rc = CFGMR3QueryBoolDef(pCfg, "QuietlyIgnoreClientPromisc", &f, false); 1390 if (RT_FAILURE(rc)) 1391 return PDMDRV_SET_ERROR(pDrvIns, rc, 1392 N_("Configuration error: Failed to get the \"QuietlyIgnoreClientPromisc\" value")); 1393 if (f) 1394 OpenReq.fFlags |= INTNET_OPEN_FLAGS_QUIETLY_IGNORE_PROMISC; /** @todo add special flag for this. */ 1395 1396 /** @cfgm{IgnoreTrunkWirePromisc, boolean, false} 1397 * When set all request for operating the trunk-wire connection in promiscuous 1398 * mode will be ignored. */ 1399 rc = CFGMR3QueryBoolDef(pCfg, "IgnoreTrunkWirePromisc", &f, false); 1400 if (RT_FAILURE(rc)) 1401 return PDMDRV_SET_ERROR(pDrvIns, rc, 1402 N_("Configuration error: Failed to get the \"IgnoreTrunkWirePromisc\" value")); 1403 if (f) 1404 OpenReq.fFlags |= INTNET_OPEN_FLAGS_IGNORE_PROMISC_TRUNK_WIRE; 1405 1406 /** @cfgm{QuietlyIgnoreTrunkWirePromisc, boolean, false} 1407 * When set all request for operating any trunk-wire connection promiscuous mode 1408 * will be ignored. This differs from IgnoreTrunkWirePromisc in that clients 1409 * won't get VERR_INTNET_INCOMPATIBLE_FLAGS. */ 1410 rc = CFGMR3QueryBoolDef(pCfg, "QuietlyIgnoreTrunkWirePromisc", &f, false); 1411 if (RT_FAILURE(rc)) 1412 return PDMDRV_SET_ERROR(pDrvIns, rc, 1413 N_("Configuration error: Failed to get the \"QuietlyIgnoreTrunkWirePromisc\" value")); 1414 if (f) 1415 OpenReq.fFlags |= INTNET_OPEN_FLAGS_QUIETLY_IGNORE_PROMISC_TRUNK_WIRE; 1416 1417 /** @cfgm{IgnoreTrunkHostPromisc, boolean, false} 1418 * When set all request for operating the trunk-host connection in promiscuous 1419 * mode will be ignored. */ 1420 rc = CFGMR3QueryBoolDef(pCfg, "IgnoreTrunkHostPromisc", &f, false); 1421 if (RT_FAILURE(rc)) 1422 return PDMDRV_SET_ERROR(pDrvIns, rc, 1423 N_("Configuration error: Failed to get the \"IgnoreTrunkHostPromisc\" value")); 1424 if (f) 1425 OpenReq.fFlags |= INTNET_OPEN_FLAGS_IGNORE_PROMISC_TRUNK_HOST; 1426 1427 /** @cfgm{QuietlyIgnoreTrunkHostPromisc, boolean, false} 1428 * When set all request for operating any trunk-host connection promiscuous mode 1429 * will be ignored. This differs from IgnoreTrunkHostPromisc in that clients 1430 * won't get VERR_INTNET_INCOMPATIBLE_FLAGS. */ 1431 rc = CFGMR3QueryBoolDef(pCfg, "QuietlyIgnoreTrunkHostPromisc", &f, false); 1432 if (RT_FAILURE(rc)) 1433 return PDMDRV_SET_ERROR(pDrvIns, rc, 1434 N_("Configuration error: Failed to get the \"QuietlyIgnoreTrunkHostPromisc\" value")); 1435 if (f) 1436 OpenReq.fFlags |= INTNET_OPEN_FLAGS_QUIETLY_IGNORE_PROMISC_TRUNK_HOST; 1437 1438 /** @todo flags for not sending to the host and for setting the trunk-wire 1439 * connection in promiscuous mode. */ 1440 1441 1442 /** @cfgm{IgnoreConnectFailure, boolean, false} 1443 * When set only raise a runtime error if we cannot connect to the internal 1444 * network. */ 1445 rc = CFGMR3QueryBoolDef(pCfg, "IgnoreConnectFailure", &fIgnoreConnectFailure, false); 1446 if (RT_FAILURE(rc)) 1447 return PDMDRV_SET_ERROR(pDrvIns, rc, 1448 N_("Configuration error: Failed to get the \"IgnoreConnectFailure\" value")); 1449 if (f) 1450 OpenReq.fFlags |= INTNET_OPEN_FLAGS_IGNORE_PROMISC; 1451 1421 OpenReq.fFlags = 0; 1452 1422 1453 1423 /** @cfgm{SharedMacOnWire, boolean, false} … … 1462 1432 if (fSharedMacOnWire) 1463 1433 OpenReq.fFlags |= INTNET_OPEN_FLAGS_SHARED_MAC_ON_WIRE; 1434 1435 /** @cfgm{RestrictAccess, boolean, true} 1436 * Whether to restrict the access to the network or if it should be public. 1437 * Everyone on the computer can connect to a public network. 1438 * @deprecated Use AccessPolicy instead. 1439 */ 1440 rc = CFGMR3QueryBool(pCfg, "RestrictAccess", &f); 1441 if (RT_SUCCESS(rc)) 1442 { 1443 if (f) 1444 OpenReq.fFlags |= INTNET_OPEN_FLAGS_ACCESS_RESTRICTED; 1445 else 1446 OpenReq.fFlags |= INTNET_OPEN_FLAGS_ACCESS_PUBLIC; 1447 } 1448 else if (rc != VERR_CFGM_VALUE_NOT_FOUND) 1449 return PDMDRV_SET_ERROR(pDrvIns, rc, 1450 N_("Configuration error: Failed to get the \"RestrictAccess\" value")); 1451 1452 1453 /** @cfgm{AccessPolicy, string, "none"} 1454 * The access policy of the network: public, restricted or none. A 1455 * "public" network is accessible to everyone on the same host, while a 1456 * "restricted" one is only accessible to VMs & services started by the 1457 * same user. The "none" policy, which is the default, means no policy 1458 * change or choice is made and that the current (existing network) or 1459 * default (new) policy should be used. */ 1460 static const DRVINTNETFLAG s_aAccessPolicyFlags[] = 1461 { 1462 { "public", INTNET_OPEN_FLAGS_ACCESS_PUBLIC }, 1463 { "restricted", INTNET_OPEN_FLAGS_ACCESS_RESTRICTED } 1464 }; 1465 rc = drvIntNetR3CfgGetPolicy(pDrvIns, "AccessPolicy", &s_aAccessPolicyFlags[0], RT_ELEMENTS(s_aAccessPolicyFlags), 1466 &OpenReq.fFlags); 1467 AssertRCReturn(rc, rc); 1468 /** @cfgm{AccessPolicyFixed, boolean, false} 1469 * Whether the access policy is to be locked against further changes. */ 1470 rc = drvIntNetR3CfgFixedPolicy(pDrvIns, "AccessPolicyFixed", INTNET_OPEN_FLAGS_ACCESS_FIXED, &OpenReq.fFlags); 1471 AssertRCReturn(rc, rc); 1472 1473 /** @cfgm{PromiscPolicyClients, string, "none"} 1474 * The network wide promiscuous mode policy for client (non-trunk) 1475 * interfaces: allow, deny, none. */ 1476 static const DRVINTNETFLAG s_aPromiscPolicyClient[] = 1477 { 1478 { "allow", INTNET_OPEN_FLAGS_PROMISC_ALLOW_CLIENTS }, 1479 { "deny", INTNET_OPEN_FLAGS_PROMISC_DENY_CLIENTS } 1480 }; 1481 rc = drvIntNetR3CfgGetPolicy(pDrvIns, "PromiscPolicyClients", &s_aPromiscPolicyClient[0], RT_ELEMENTS(s_aPromiscPolicyClient), 1482 &OpenReq.fFlags); 1483 AssertRCReturn(rc, rc); 1484 /** @cfgm{PromiscPolicyHost, string, "none"} 1485 * The promiscuous mode policy for the trunk-host 1486 * connection: allow, deny, none. */ 1487 static const DRVINTNETFLAG s_aPromiscPolicyHost[] = 1488 { 1489 { "allow", INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_HOST }, 1490 { "deny", INTNET_OPEN_FLAGS_PROMISC_DENY_TRUNK_HOST } 1491 }; 1492 rc = drvIntNetR3CfgGetPolicy(pDrvIns, "PromiscPolicyHost", &s_aPromiscPolicyHost[0], RT_ELEMENTS(s_aPromiscPolicyHost), 1493 &OpenReq.fFlags); 1494 AssertRCReturn(rc, rc); 1495 /** @cfgm{PromiscPolicyWire, string, "none"} 1496 * The promiscuous mode policy for the trunk-host 1497 * connection: allow, deny, none. */ 1498 static const DRVINTNETFLAG s_aPromiscPolicyWire[] = 1499 { 1500 { "allow", INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_WIRE }, 1501 { "deny", INTNET_OPEN_FLAGS_PROMISC_DENY_TRUNK_WIRE } 1502 }; 1503 rc = drvIntNetR3CfgGetPolicy(pDrvIns, "PromiscPolicyWire", &s_aPromiscPolicyWire[0], RT_ELEMENTS(s_aPromiscPolicyWire), 1504 &OpenReq.fFlags); 1505 AssertRCReturn(rc, rc); 1506 /** @cfgm{PromiscPolicyFixed, boolean, false} 1507 * Whether the promiscuous mode policies are to be locked against further 1508 * changes. */ 1509 rc = drvIntNetR3CfgFixedPolicy(pDrvIns, "PromiscPolicyFixed", INTNET_OPEN_FLAGS_PROMISC_FIXED, &OpenReq.fFlags); 1510 AssertRCReturn(rc, rc); 1511 1512 1513 /** @cfgm{IfPolicyPromisc, string, "none"} 1514 * The promiscuous mode policy for this 1515 * interface: allow, deny, none. */ 1516 static const DRVINTNETFLAG s_aIfPolicyPromisc[] = 1517 { 1518 { "allow", INTNET_OPEN_FLAGS_IF_PROMISC_ALLOW }, 1519 { "deny", INTNET_OPEN_FLAGS_IF_PROMISC_DENY } 1520 }; 1521 rc = drvIntNetR3CfgGetPolicy(pDrvIns, "IfPolicyPromisc", &s_aIfPolicyPromisc[0], RT_ELEMENTS(s_aIfPolicyPromisc), 1522 &OpenReq.fFlags); 1523 AssertRCReturn(rc, rc); 1524 1525 /** @cfgm{IfPolicyPromiscTrunk, string, "none"} 1526 * The promiscuous mode policy for this interface with regard to unrelated 1527 * trunk traffic: see-trunk, no-trunk, none. */ 1528 static const DRVINTNETFLAG s_aIfPolicyPromiscTrunk[] = 1529 { 1530 { "see-trunk", INTNET_OPEN_FLAGS_IF_PROMISC_SEE_TRUNK }, 1531 { "no-trunk", INTNET_OPEN_FLAGS_IF_PROMISC_NO_TRUNK } 1532 }; 1533 rc = drvIntNetR3CfgGetPolicy(pDrvIns, "IfPolicyPromiscTrunk", &s_aIfPolicyPromiscTrunk[0], RT_ELEMENTS(s_aIfPolicyPromiscTrunk), 1534 &OpenReq.fFlags); 1535 AssertRCReturn(rc, rc); 1536 1537 /** @cfgm{IfPolicyFixed, boolean, false} 1538 * Whether the interface policies are to be locked against further 1539 * changes. */ 1540 rc = drvIntNetR3CfgFixedPolicy(pDrvIns, "IfPolicyFixed", INTNET_OPEN_FLAGS_IF_FIXED, &OpenReq.fFlags); 1541 AssertRCReturn(rc, rc); 1542 1543 1544 /** @cfgm{TrunkPolicyHost, string, "none"} 1545 * The trunk-host policy: enabled, disabled, non 1546 * This can be used to prevent packages to be routed to the host. */ 1547 static const DRVINTNETFLAG s_aTrunkPolicyHost[] = 1548 { 1549 { "enabled", INTNET_OPEN_FLAGS_TRUNK_HOST_ENABLED }, 1550 { "disabled", INTNET_OPEN_FLAGS_TRUNK_HOST_DISABLED } 1551 }; 1552 rc = drvIntNetR3CfgGetPolicy(pDrvIns, "TrunkPolicyHost", &s_aTrunkPolicyHost[0], RT_ELEMENTS(s_aTrunkPolicyHost), 1553 &OpenReq.fFlags); 1554 AssertRCReturn(rc, rc); 1555 /** @cfgm{TrunkPolicyWire, string, "none"} 1556 * The trunk-host policy: enabled, disabled, non 1557 * This can be used to prevent packages to be routed to the host. */ 1558 static const DRVINTNETFLAG s_aTrunkPolicyWire[] = 1559 { 1560 { "enabled", INTNET_OPEN_FLAGS_TRUNK_WIRE_ENABLED }, 1561 { "disabled", INTNET_OPEN_FLAGS_TRUNK_WIRE_DISABLED } 1562 }; 1563 rc = drvIntNetR3CfgGetPolicy(pDrvIns, "TrunkPolicyWire", &s_aTrunkPolicyWire[0], RT_ELEMENTS(s_aTrunkPolicyWire), 1564 &OpenReq.fFlags); 1565 AssertRCReturn(rc, rc); 1566 /** @cfgm{TrunkPolicyFixed, boolean, false} 1567 * Whether the trunk policies are to be locked against further changes. */ 1568 rc = drvIntNetR3CfgFixedPolicy(pDrvIns, "TrunkPolicyFixed", INTNET_OPEN_FLAGS_TRUNK_FIXED, &OpenReq.fFlags); 1569 AssertRCReturn(rc, rc); 1570 1464 1571 1465 1572 /** @cfgm{ReceiveBufferSize, uint32_t, 318 KB} … … 1504 1611 N_("Configuration error: Failed to get the \"IsService\" value")); 1505 1612 1506 LogRel(("IntNet#%u: szNetwork={%s} enmTrunkType=%d szTrunk={%s} fFlags=%#x cbRecv=%u cbSend=%u\n", 1613 1614 /** @cfgm{IgnoreConnectFailure, boolean, false} 1615 * When set only raise a runtime error if we cannot connect to the internal 1616 * network. */ 1617 bool fIgnoreConnectFailure; 1618 rc = CFGMR3QueryBoolDef(pCfg, "IgnoreConnectFailure", &fIgnoreConnectFailure, false); 1619 if (RT_FAILURE(rc)) 1620 return PDMDRV_SET_ERROR(pDrvIns, rc, 1621 N_("Configuration error: Failed to get the \"IgnoreConnectFailure\" value")); 1622 1623 LogRel(("IntNet#%u: szNetwork={%s} enmTrunkType=%d szTrunk={%s} fFlags=%#x cbRecv=%u cbSend=%u fIgnoreConnectFailure=%RTbool\n", 1507 1624 pDrvIns->iInstance, OpenReq.szNetwork, OpenReq.enmTrunkType, OpenReq.szTrunk, OpenReq.fFlags, 1508 OpenReq.cbRecv, OpenReq.cbSend ));1625 OpenReq.cbRecv, OpenReq.cbSend, fIgnoreConnectFailure)); 1509 1626 1510 1627 #ifdef RT_OS_DARWIN … … 1559 1676 * Therefore don't abort but just raise a runtime warning. 1560 1677 */ 1561 PDMDrvHlpVMSetRuntimeError 1562 1563 1564 1565 1678 PDMDrvHlpVMSetRuntimeError(pDrvIns, 0 /*fFlags*/, "HostIfNotConnecting", 1679 N_ ("Cannot connect to the network interface '%s'. The virtual " 1680 "network card will appear to work but the guest will not " 1681 "be able to connect. Please choose a different network in the " 1682 "network settings"), OpenReq.szTrunk); 1566 1683 1567 1684 return VERR_PDM_NO_ATTACHED_DRIVER; 1568 1685 } 1569 else 1570 { 1571 return PDMDrvHlpVMSetError(pDrvIns, rc, RT_SRC_POS, 1572 N_("Failed to open/create the internal network '%s'"), pThis->szNetwork); 1573 } 1686 return PDMDrvHlpVMSetError(pDrvIns, rc, RT_SRC_POS, 1687 N_("Failed to open/create the internal network '%s'"), pThis->szNetwork); 1574 1688 } 1575 1689 -
trunk/src/VBox/Devices/Network/SrvIntNetR0.cpp
r35346 r36075 5 5 6 6 /* 7 * Copyright (C) 2006-201 0Oracle Corporation7 * Copyright (C) 2006-2011 Oracle Corporation 8 8 * 9 9 * This file is part of VirtualBox Open Source Edition (OSE), as … … 72 72 /** The MAC address of this entry. */ 73 73 RTMAC MacAddr; 74 /** Is it promiscuous. */ 75 bool fPromiscuous; 74 /** Is it promiscuous. 75 * Shadows INTNETIF::fPromiscuousEff. */ 76 bool fPromiscuousEff; 77 /** Is it promiscuous and should it see unrelated trunk traffic. */ 78 bool fPromiscuousSeeTrunk; 76 79 /** Is it active. 77 80 * We ignore the entry if this is clear and may end up sending packets addressed … … 102 105 /** The host MAC address (reported). */ 103 106 RTMAC HostMac; 104 /** The host promiscuous setting (reported). */ 105 bool fHostPromiscuous; 107 /** The effective host promiscuous setting (reported). */ 108 bool fHostPromiscuousEff; 109 /** The real host promiscuous setting (reported). */ 110 bool fHostPromiscuousReal; 106 111 /** Whether the host is active. */ 107 112 bool fHostActive; 108 113 109 114 /** Whether the wire is promiscuous (config). */ 110 bool fWirePromiscuous; 115 bool fWirePromiscuousEff; 116 /** Whether the wire is promiscuous (config). 117 * (Shadows INTNET_OPEN_FLAGS_TRUNK_WIRE_PROMISC_MODE in 118 * INTNETNETWORK::fFlags.) */ 119 bool fWirePromiscuousReal; 111 120 /** Whether the wire is active. */ 112 121 bool fWireActive; … … 217 226 /** Set if the interface is in promiscuous mode. 218 227 * This is shadowed by INTNETMACTABENTRY::fPromiscuous. */ 219 bool fPromiscuous; 228 bool fPromiscuousEff; 229 /** Tracks the desired promiscuous setting of the interface. */ 230 bool fPromiscuousReal; 220 231 /** Whether the interface is active or not. 221 232 * This is shadowed by INTNETMACTABENTRY::fActive. */ … … 224 235 * the end is nigh by means of IntNetR0IfAbortWait. */ 225 236 bool volatile fDestroying; 237 /** The flags specified when opening this interface. */ 238 uint32_t fOpenFlags; 226 239 /** Number of yields done to try make the interface read pending data. 227 240 * We will stop yielding when this reaches a threshold assuming that the VM is … … 357 370 /** Network creation flags (INTNET_OPEN_FLAGS_*). */ 358 371 uint32_t fFlags; 372 /** Any restrictive policies required as a minimum by some interface. 373 * (INTNET_OPEN_FLAGS_REQUIRE_AS_RESTRICTIVE_POLICIES) */ 374 uint32_t fMinFlags; 359 375 /** The number of active interfaces (excluding the trunk). */ 360 376 uint32_t cActiveIFs; … … 370 386 /** Pointer to an internal network. */ 371 387 typedef INTNETNETWORK *PINTNETNETWORK; 388 /** Pointer to a const internal network. */ 389 typedef const INTNETNETWORK *PCINTNETNETWORK; 372 390 373 391 /** The size of the buffer INTNETNETWORK::pbTmp points at. */ … … 403 421 static PINTNET volatile g_pIntNet = NULL; 404 422 423 static const struct INTNETOPENNETWORKFLAGS 424 { 425 uint32_t fRestrictive; /**< The restrictive flag (deny/disabled). */ 426 uint32_t fRelaxed; /**< The relaxed flag (allow/enabled). */ 427 uint32_t fFixed; /**< The config-fixed flag. */ 428 uint32_t fPair; /**< The pair of restrictive and relaxed flags. */ 429 } 430 /** Open network policy flags relating to the network. */ 431 g_afIntNetOpenNetworkNetFlags[] = 432 { 433 { INTNET_OPEN_FLAGS_ACCESS_RESTRICTED, INTNET_OPEN_FLAGS_ACCESS_PUBLIC, INTNET_OPEN_FLAGS_ACCESS_FIXED, INTNET_OPEN_FLAGS_ACCESS_RESTRICTED | INTNET_OPEN_FLAGS_ACCESS_PUBLIC }, 434 { INTNET_OPEN_FLAGS_PROMISC_DENY_CLIENTS, INTNET_OPEN_FLAGS_PROMISC_ALLOW_CLIENTS, INTNET_OPEN_FLAGS_PROMISC_FIXED, INTNET_OPEN_FLAGS_PROMISC_DENY_CLIENTS | INTNET_OPEN_FLAGS_PROMISC_ALLOW_CLIENTS }, 435 { INTNET_OPEN_FLAGS_PROMISC_DENY_TRUNK_HOST, INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_HOST, INTNET_OPEN_FLAGS_PROMISC_FIXED, INTNET_OPEN_FLAGS_PROMISC_DENY_TRUNK_HOST | INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_HOST }, 436 { INTNET_OPEN_FLAGS_PROMISC_DENY_TRUNK_WIRE, INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_WIRE, INTNET_OPEN_FLAGS_PROMISC_FIXED, INTNET_OPEN_FLAGS_PROMISC_DENY_TRUNK_WIRE | INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_WIRE }, 437 { INTNET_OPEN_FLAGS_TRUNK_HOST_DISABLED, INTNET_OPEN_FLAGS_TRUNK_HOST_ENABLED, INTNET_OPEN_FLAGS_TRUNK_FIXED, INTNET_OPEN_FLAGS_TRUNK_HOST_DISABLED | INTNET_OPEN_FLAGS_TRUNK_HOST_ENABLED }, 438 { INTNET_OPEN_FLAGS_TRUNK_HOST_CHASTE_MODE, INTNET_OPEN_FLAGS_TRUNK_HOST_PROMISC_MODE, INTNET_OPEN_FLAGS_TRUNK_FIXED, INTNET_OPEN_FLAGS_TRUNK_HOST_CHASTE_MODE | INTNET_OPEN_FLAGS_TRUNK_HOST_PROMISC_MODE }, 439 { INTNET_OPEN_FLAGS_TRUNK_WIRE_DISABLED, INTNET_OPEN_FLAGS_TRUNK_WIRE_ENABLED, INTNET_OPEN_FLAGS_TRUNK_FIXED, INTNET_OPEN_FLAGS_TRUNK_WIRE_DISABLED | INTNET_OPEN_FLAGS_TRUNK_WIRE_ENABLED }, 440 { INTNET_OPEN_FLAGS_TRUNK_WIRE_CHASTE_MODE, INTNET_OPEN_FLAGS_TRUNK_WIRE_PROMISC_MODE, INTNET_OPEN_FLAGS_TRUNK_FIXED, INTNET_OPEN_FLAGS_TRUNK_WIRE_CHASTE_MODE | INTNET_OPEN_FLAGS_TRUNK_WIRE_PROMISC_MODE }, 441 }, 442 /** Open network policy flags relating to the new interface. */ 443 g_afIntNetOpenNetworkIfFlags[] = 444 { 445 { INTNET_OPEN_FLAGS_IF_PROMISC_DENY, INTNET_OPEN_FLAGS_IF_PROMISC_ALLOW, INTNET_OPEN_FLAGS_IF_FIXED, INTNET_OPEN_FLAGS_IF_PROMISC_DENY | INTNET_OPEN_FLAGS_IF_PROMISC_ALLOW }, 446 { INTNET_OPEN_FLAGS_IF_PROMISC_NO_TRUNK, INTNET_OPEN_FLAGS_IF_PROMISC_SEE_TRUNK, INTNET_OPEN_FLAGS_IF_FIXED, INTNET_OPEN_FLAGS_IF_PROMISC_NO_TRUNK | INTNET_OPEN_FLAGS_IF_PROMISC_SEE_TRUNK }, 447 }; 448 405 449 406 450 /******************************************************************************* … … 1419 1463 PINTNETIF pIf = pTab->paEntries[iIfMac].pIf; AssertPtr(pIf); Assert(pIf->pNetwork == pNetwork); 1420 1464 bool fExact = intnetR0IfAddrCacheLookup(&pIf->aAddrCache[enmL3AddrType], pL3Addr, cbL3Addr) >= 0; 1421 if (fExact || pTab->paEntries[iIfMac].fPromiscuous )1465 if (fExact || pTab->paEntries[iIfMac].fPromiscuousSeeTrunk) 1422 1466 { 1423 1467 cExactHits += fExact; … … 1437 1481 if ( fExact 1438 1482 || intnetR0IsMacAddrDummy(&pTab->HostMac) 1439 || pTab->fHostPromiscuous )1483 || pTab->fHostPromiscuousEff) 1440 1484 { 1441 1485 cExactHits += fExact; … … 1445 1489 1446 1490 /* Hit the wire if there are no exact matches or if it's in promiscuous mode. */ 1447 if (pTab->fWireActive && (!cExactHits || pTab->fWirePromiscuous ))1491 if (pTab->fWireActive && (!cExactHits || pTab->fWirePromiscuousEff)) 1448 1492 pDstTab->fTrunkDst |= INTNETTRUNKDIR_WIRE; 1449 1493 pDstTab->fTrunkDst &= ~fSrc; … … 1476 1520 { 1477 1521 Assert(!intnetR0IsMacAddrMulticast(pDstAddr)); 1522 Assert(fSrc); 1478 1523 1479 1524 /* … … 1497 1542 break; 1498 1543 1544 /* Promiscuous mode? */ 1545 if (pTab->paEntries[iIfMac].fPromiscuousSeeTrunk) 1546 break; 1547 1499 1548 /* Paranoia - this shouldn't happen, right? */ 1500 1549 if ( pSrcAddr … … 1505 1554 if (intnetR0AreMacAddrsEqual(&pTab->paEntries[iIfMac].MacAddr, pDstAddr)) 1506 1555 { 1507 enmSwDecision = pTab->fHostPromiscuous && fSrc == INTNETTRUNKDIR_WIRE1556 enmSwDecision = pTab->fHostPromiscuousEff && fSrc == INTNETTRUNKDIR_WIRE 1508 1557 ? INTNETSWDECISION_BROADCAST 1509 1558 : INTNETSWDECISION_INTNET; … … 1557 1606 if ( fExact 1558 1607 || intnetR0IsMacAddrDummy(&pTab->paEntries[iIfMac].MacAddr) 1559 || pTab->paEntries[iIfMac].fPromiscuous) 1608 || ( pTab->paEntries[iIfMac].fPromiscuousSeeTrunk 1609 || (!fSrc && pTab->paEntries[iIfMac].fPromiscuousEff) ) 1610 ) 1560 1611 { 1561 1612 cExactHits += fExact; … … 1580 1631 if ( fExact 1581 1632 || intnetR0IsMacAddrDummy(&pTab->HostMac) 1582 || pTab->fHostPromiscuous )1633 || pTab->fHostPromiscuousEff) 1583 1634 { 1584 1635 cExactHits += fExact; … … 1590 1641 if ( fSrc != INTNETTRUNKDIR_WIRE 1591 1642 && pTab->fWireActive 1592 && (!cExactHits || pTab->fWirePromiscuous )1643 && (!cExactHits || pTab->fWirePromiscuousEff) 1593 1644 ) 1594 1645 pDstTab->fTrunkDst |= INTNETTRUNKDIR_WIRE; … … 1702 1753 { 1703 1754 if ( pTab->paEntries[iIfMac].fActive 1704 && pTab->paEntries[iIfMac].fPromiscuous) 1755 && ( pTab->paEntries[iIfMac].fPromiscuousSeeTrunk 1756 || (!fSrc && pTab->paEntries[iIfMac].fPromiscuousEff) ) 1757 ) 1705 1758 { 1706 1759 PINTNETIF pIf = pTab->paEntries[iIfMac].pIf; AssertPtr(pIf); Assert(pIf->pNetwork == pNetwork); … … 3602 3655 RTSpinlockAcquireNoInts(pNetwork->hAddrSpinlock, &Tmp); 3603 3656 3604 if (pIf->fPromiscuous != fPromiscuous)3657 if (pIf->fPromiscuousReal != fPromiscuous) 3605 3658 { 3606 Log(("IntNetR0IfSetPromiscuousMode: hIf=%RX32: Changed from %d -> %d\n", 3607 hIf, !fPromiscuous, !!fPromiscuous)); 3608 ASMAtomicUoWriteBool(&pIf->fPromiscuous, fPromiscuous); 3659 const bool fPromiscuousEff = fPromiscuous 3660 && (pIf->fOpenFlags & INTNET_OPEN_FLAGS_IF_PROMISC_ALLOW) 3661 && (pNetwork->fFlags & INTNET_OPEN_FLAGS_PROMISC_ALLOW_CLIENTS); 3662 Log(("IntNetR0IfSetPromiscuousMode: hIf=%RX32: Changed from %d (%d) -> %d (%d)\n", 3663 hIf, !fPromiscuous, pIf->fPromiscuousEff, !!fPromiscuous, fPromiscuousEff)); 3664 3665 pIf->fPromiscuousReal = fPromiscuous; 3666 pIf->fPromiscuousEff = fPromiscuousEff; 3609 3667 3610 3668 PINTNETMACTABENTRY pEntry = intnetR0NetworkFindMacAddrEntry(pNetwork, pIf); Assert(pEntry); 3611 3669 if (RT_LIKELY(pEntry)) 3612 pEntry->fPromiscuous = fPromiscuous; 3613 pIf->fPromiscuous = fPromiscuous; 3670 { 3671 pEntry->fPromiscuousEff = fPromiscuousEff; 3672 pEntry->fPromiscuousSeeTrunk = fPromiscuousEff 3673 && (pIf->fOpenFlags & INTNET_OPEN_FLAGS_IF_PROMISC_SEE_TRUNK); 3674 } 3614 3675 } 3615 3676 … … 3781 3842 if (pTrunk) 3782 3843 { 3783 pNetwork->MacTab.fHostActive = true;3784 pNetwork->MacTab.fWireActive = true;3844 pNetwork->MacTab.fHostActive = RT_BOOL(pNetwork->fFlags & INTNET_OPEN_FLAGS_TRUNK_HOST_ENABLED); 3845 pNetwork->MacTab.fWireActive = RT_BOOL(pNetwork->fFlags & INTNET_OPEN_FLAGS_TRUNK_WIRE_ENABLED); 3785 3846 } 3786 3847 } … … 4179 4240 } 4180 4241 4242 /* recalc the min flags. */ 4243 if (pIf->fOpenFlags & INTNET_OPEN_FLAGS_REQUIRE_AS_RESTRICTIVE_POLICIES) 4244 { 4245 uint32_t fMinFlags = 0; 4246 iIf = pNetwork->MacTab.cEntries; 4247 while (iIf-- > 0) 4248 { 4249 PINTNETIF pIf2 = pNetwork->MacTab.paEntries[iIf].pIf; 4250 if ( pIf2 /* paranoia */ 4251 && (pIf2->fOpenFlags & INTNET_OPEN_FLAGS_REQUIRE_AS_RESTRICTIVE_POLICIES)) 4252 fMinFlags |= pIf2->fOpenFlags & INTNET_OPEN_FLAGS_STRICT_MASK; 4253 } 4254 pNetwork->fMinFlags = fMinFlags; 4255 } 4181 4256 PINTNETTRUNKIF pTrunk = pNetwork->MacTab.pTrunk; 4182 4257 … … 4281 4356 * @param cbSend The size of the send buffer. 4282 4357 * @param cbRecv The size of the receive buffer. 4358 * @param fFlags The open network flags. 4283 4359 * @param phIf Where to store the interface handle. 4284 4360 */ 4285 static int intnetR0NetworkCreateIf(PINTNETNETWORK pNetwork, PSUPDRVSESSION pSession, unsigned cbSend, unsigned cbRecv, 4361 static int intnetR0NetworkCreateIf(PINTNETNETWORK pNetwork, PSUPDRVSESSION pSession, 4362 unsigned cbSend, unsigned cbRecv, uint32_t fFlags, 4286 4363 PINTNETIFHANDLE phIf) 4287 4364 { 4288 LogFlow(("intnetR0NetworkCreateIf: pNetwork=%p pSession=%p cbSend=%u cbRecv=%u phIf=%p\n",4289 pNetwork, pSession, cbSend, cbRecv, phIf));4365 LogFlow(("intnetR0NetworkCreateIf: pNetwork=%p pSession=%p cbSend=%u cbRecv=%u fFlags=%#x phIf=%p\n", 4366 pNetwork, pSession, cbSend, cbRecv, fFlags, phIf)); 4290 4367 4291 4368 /* … … 4294 4371 AssertPtr(pNetwork); 4295 4372 AssertPtr(phIf); 4373 4374 /* 4375 * Adjust the flags with defaults for the interface policies. 4376 * Note: Main restricts promiscuous mode per interface. 4377 */ 4378 uint32_t const fDefFlags = INTNET_OPEN_FLAGS_IF_PROMISC_ALLOW 4379 | INTNET_OPEN_FLAGS_IF_PROMISC_SEE_TRUNK; 4380 for (uint32_t i = 0; i < RT_ELEMENTS(g_afIntNetOpenNetworkIfFlags); i++) 4381 if (!(fFlags & g_afIntNetOpenNetworkIfFlags[i].fPair)) 4382 fFlags |= g_afIntNetOpenNetworkIfFlags[i].fPair & fDefFlags; 4296 4383 4297 4384 /* … … 4311 4398 memset(&pIf->MacAddr, 0xff, sizeof(pIf->MacAddr)); /* broadcast */ 4312 4399 //pIf->fMacSet = false; 4313 //pIf->fPromiscuous = false; 4400 //pIf->fPromiscuousEff = false; 4401 //pIf->fPromiscuousReal = false; 4314 4402 //pIf->fActive = false; 4315 4403 //pIf->fDestroying = false; 4404 pIf->fOpenFlags = fFlags; 4316 4405 //pIf->cYields = 0; 4317 4406 //pIf->pIntBuf = 0; … … 4378 4467 Assert(iIf + 1 <= pNetwork->MacTab.cEntriesAllocated); 4379 4468 4380 pNetwork->MacTab.paEntries[iIf].MacAddr = pIf->MacAddr; 4381 pNetwork->MacTab.paEntries[iIf].fActive = false; 4382 pNetwork->MacTab.paEntries[iIf].fPromiscuous = false; 4383 pNetwork->MacTab.paEntries[iIf].pIf = pIf; 4469 pNetwork->MacTab.paEntries[iIf].MacAddr = pIf->MacAddr; 4470 pNetwork->MacTab.paEntries[iIf].fActive = false; 4471 pNetwork->MacTab.paEntries[iIf].fPromiscuousEff = false; 4472 pNetwork->MacTab.paEntries[iIf].fPromiscuousSeeTrunk = false; 4473 pNetwork->MacTab.paEntries[iIf].pIf = pIf; 4384 4474 4385 4475 pNetwork->MacTab.cEntries = iIf + 1; … … 4492 4582 RTSpinlockAcquireNoInts(pNetwork->hAddrSpinlock, &Tmp); 4493 4583 4494 pNetwork->MacTab.fHostPromiscuous = fPromiscuous; 4584 pNetwork->MacTab.fHostPromiscuousReal = fPromiscuous 4585 || (pNetwork->fFlags & INTNET_OPEN_FLAGS_TRUNK_HOST_PROMISC_MODE); 4586 pNetwork->MacTab.fHostPromiscuousEff = pNetwork->MacTab.fHostPromiscuousReal 4587 && (pNetwork->fFlags & INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_HOST); 4495 4588 4496 4589 RTSpinlockReleaseNoInts(pNetwork->hAddrSpinlock, &Tmp); … … 4945 5038 * Note! We don't need to lock the MacTab here - creation time. 4946 5039 */ 4947 pNetwork->MacTab.pTrunk = pTrunk; 4948 pNetwork->MacTab.HostMac = pTrunk->MacAddr; 4949 pNetwork->MacTab.fHostPromiscuous = false; 4950 pNetwork->MacTab.fHostActive = false; 4951 pNetwork->MacTab.fWirePromiscuous = false; /** @todo !!(fFlags & INTNET_OPEN_FLAGS_PROMISC_TRUNK_WIRE); */ 4952 pNetwork->MacTab.fWireActive = false; 5040 pNetwork->MacTab.pTrunk = pTrunk; 5041 pNetwork->MacTab.HostMac = pTrunk->MacAddr; 5042 pNetwork->MacTab.fHostPromiscuousReal = false; 5043 pNetwork->MacTab.fHostPromiscuousEff = (pNetwork->fFlags & INTNET_OPEN_FLAGS_TRUNK_HOST_PROMISC_MODE) 5044 && (pNetwork->fFlags & INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_HOST); 5045 pNetwork->MacTab.fHostActive = false; 5046 pNetwork->MacTab.fWirePromiscuousReal = pNetwork->fFlags & INTNET_OPEN_FLAGS_TRUNK_WIRE_PROMISC_MODE; 5047 pNetwork->MacTab.fWirePromiscuousEff = pNetwork->MacTab.fWirePromiscuousReal 5048 && (pNetwork->fFlags & INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_WIRE); 5049 pNetwork->MacTab.fWireActive = false; 4953 5050 4954 5051 #ifdef IN_RING0 /* (testcase is ring-3) */ … … 5125 5222 5126 5223 /** 5224 * Checks if the open network flags are compatible. 5225 * 5226 * @returns VBox status code. 5227 * @param pNetwork The network. 5228 * @param fFlags The open network flags. 5229 */ 5230 static int intnetR0CheckOpenNetworkFlags(PINTNETNETWORK pNetwork, uint32_t fFlags) 5231 { 5232 uint32_t const fNetFlags = pNetwork->fFlags; 5233 5234 if ( (fFlags & INTNET_OPEN_FLAGS_SHARED_MAC_ON_WIRE) 5235 ^ (fNetFlags & INTNET_OPEN_FLAGS_SHARED_MAC_ON_WIRE)) 5236 return VERR_INTNET_INCOMPATIBLE_FLAGS; 5237 5238 if (fFlags & INTNET_OPEN_FLAGS_REQUIRE_EXACT) 5239 { 5240 for (uint32_t i = 0; i < RT_ELEMENTS(g_afIntNetOpenNetworkNetFlags); i++) 5241 if ( (fFlags & g_afIntNetOpenNetworkNetFlags[i].fPair) 5242 && (fFlags & g_afIntNetOpenNetworkNetFlags[i].fPair) 5243 != (fNetFlags & g_afIntNetOpenNetworkNetFlags[i].fPair) ) 5244 return VERR_INTNET_INCOMPATIBLE_FLAGS; 5245 } 5246 5247 if (fFlags & INTNET_OPEN_FLAGS_REQUIRE_AS_RESTRICTIVE_POLICIES) 5248 { 5249 for (uint32_t i = 0; i < RT_ELEMENTS(g_afIntNetOpenNetworkNetFlags); i++) 5250 if ( (fFlags & g_afIntNetOpenNetworkNetFlags[i].fRestrictive) 5251 && !(fNetFlags & g_afIntNetOpenNetworkNetFlags[i].fRestrictive) 5252 && (fNetFlags & g_afIntNetOpenNetworkNetFlags[i].fFixed) ) 5253 return VERR_INTNET_INCOMPATIBLE_FLAGS; 5254 } 5255 5256 return VINF_SUCCESS; 5257 } 5258 5259 5260 /** 5261 * Adapts flag changes on network opening. 5262 * 5263 * @returns VBox status code. 5264 * @param pNetwork The network. 5265 * @param fFlags The open network flags. 5266 */ 5267 static int intnetR0AdaptOpenNetworkFlags(PINTNETNETWORK pNetwork, uint32_t fFlags) 5268 { 5269 /* 5270 * Upgrade the minimum policy flags. 5271 */ 5272 uint32_t fNetMinFlags = pNetwork->fMinFlags; 5273 Assert(!(fNetMinFlags & INTNET_OPEN_FLAGS_RELAXED_MASK)); 5274 if (fFlags & INTNET_OPEN_FLAGS_REQUIRE_AS_RESTRICTIVE_POLICIES) 5275 { 5276 fNetMinFlags |= fFlags & INTNET_OPEN_FLAGS_STRICT_MASK; 5277 if (fNetMinFlags != pNetwork->fMinFlags) 5278 { 5279 LogRel(("INTNET: %s - min flags changed %#x -> %#x\n", pNetwork->szName, pNetwork->fMinFlags, fNetMinFlags)); 5280 pNetwork->fMinFlags = fNetMinFlags; 5281 } 5282 } 5283 5284 /* 5285 * Calculate the new network flags. 5286 * (Depends on fNetMinFlags being recalculated first.) 5287 */ 5288 uint32_t fNetFlags = pNetwork->fFlags; 5289 5290 for (uint32_t i = 0; i < RT_ELEMENTS(g_afIntNetOpenNetworkNetFlags); i++) 5291 { 5292 Assert(fNetFlags & g_afIntNetOpenNetworkNetFlags[i].fPair); 5293 Assert(!(fNetMinFlags & g_afIntNetOpenNetworkNetFlags[i].fRelaxed)); 5294 5295 if (!(fFlags & g_afIntNetOpenNetworkNetFlags[i].fPair)) 5296 continue; 5297 if (fNetFlags & g_afIntNetOpenNetworkNetFlags[i].fFixed) 5298 continue; 5299 5300 if ( (fNetMinFlags & g_afIntNetOpenNetworkNetFlags[i].fRestrictive) 5301 || (fFlags & g_afIntNetOpenNetworkNetFlags[i].fRestrictive) ) 5302 { 5303 fNetFlags &= ~g_afIntNetOpenNetworkNetFlags[i].fPair; 5304 fNetFlags |= g_afIntNetOpenNetworkNetFlags[i].fRestrictive; 5305 } 5306 else if (!(fFlags & INTNET_OPEN_FLAGS_REQUIRE_AS_RESTRICTIVE_POLICIES)) 5307 { 5308 fNetFlags &= ~g_afIntNetOpenNetworkNetFlags[i].fPair; 5309 fNetFlags |= g_afIntNetOpenNetworkNetFlags[i].fRelaxed; 5310 } 5311 } 5312 5313 for (uint32_t i = 0; i < RT_ELEMENTS(g_afIntNetOpenNetworkNetFlags); i++) 5314 { 5315 Assert(fNetFlags & g_afIntNetOpenNetworkNetFlags[i].fPair); 5316 fNetFlags |= fFlags & g_afIntNetOpenNetworkNetFlags[i].fFixed; 5317 } 5318 5319 /* 5320 * Apply the flags if they changed. 5321 */ 5322 uint32_t const fOldNetFlags = pNetwork->fFlags; 5323 if (fOldNetFlags != fNetFlags) 5324 { 5325 LogRel(("INTNET: %s - flags changed %#x -> %#x\n", pNetwork->szName, fOldNetFlags, fNetFlags)); 5326 5327 RTSPINLOCKTMP Tmp = RTSPINLOCKTMP_INITIALIZER; 5328 RTSpinlockAcquireNoInts(pNetwork->hAddrSpinlock, &Tmp); 5329 5330 pNetwork->fFlags = fNetFlags; 5331 5332 /* Recalculate some derived switcher variables. */ 5333 bool fActiveTrunk = pNetwork->MacTab.pTrunk 5334 && pNetwork->cActiveIFs > 0; 5335 pNetwork->MacTab.fHostActive = fActiveTrunk 5336 && (fNetFlags & INTNET_OPEN_FLAGS_TRUNK_HOST_ENABLED); 5337 pNetwork->MacTab.fHostPromiscuousEff = ( pNetwork->MacTab.fHostPromiscuousReal 5338 || (fNetFlags & INTNET_OPEN_FLAGS_TRUNK_HOST_PROMISC_MODE)) 5339 && (fNetFlags & INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_HOST); 5340 5341 pNetwork->MacTab.fWireActive = fActiveTrunk 5342 && (fNetFlags & INTNET_OPEN_FLAGS_TRUNK_HOST_ENABLED); 5343 pNetwork->MacTab.fWirePromiscuousReal= (fNetFlags & INTNET_OPEN_FLAGS_TRUNK_WIRE_PROMISC_MODE); 5344 pNetwork->MacTab.fWirePromiscuousEff = pNetwork->MacTab.fWirePromiscuousReal 5345 && (fNetFlags & INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_WIRE); 5346 5347 if ((fOldNetFlags ^ fNetFlags) & INTNET_OPEN_FLAGS_PROMISC_ALLOW_CLIENTS) 5348 { 5349 uint32_t iIf = pNetwork->MacTab.cEntries; 5350 while (iIf-- > 0) 5351 { 5352 PINTNETMACTABENTRY pEntry = &pNetwork->MacTab.paEntries[iIf]; 5353 PINTNETIF pIf2 = pEntry->pIf; 5354 if ( pIf2 /* paranoia */ 5355 && pIf2->fPromiscuousReal) 5356 { 5357 bool fPromiscuousEff = (fNetFlags & INTNET_OPEN_FLAGS_PROMISC_ALLOW_CLIENTS) 5358 && (pIf2->fOpenFlags & INTNET_OPEN_FLAGS_IF_PROMISC_ALLOW); 5359 pIf2->fPromiscuousEff = fPromiscuousEff; 5360 pEntry->fPromiscuousEff = fPromiscuousEff; 5361 pEntry->fPromiscuousSeeTrunk = fPromiscuousEff 5362 && (pIf2->fOpenFlags & INTNET_OPEN_FLAGS_IF_PROMISC_SEE_TRUNK); 5363 } 5364 } 5365 } 5366 5367 RTSpinlockReleaseNoInts(pNetwork->hAddrSpinlock, &Tmp); 5368 } 5369 5370 return VINF_SUCCESS; 5371 } 5372 5373 5374 /** 5127 5375 * Opens an existing network. 5128 5376 * … … 5150 5398 Assert(enmTrunkType > kIntNetTrunkType_Invalid && enmTrunkType < kIntNetTrunkType_End); 5151 5399 AssertPtr(pszTrunk); 5152 Assert(!(fFlags & ~ (INTNET_OPEN_FLAGS_MASK)));5400 Assert(!(fFlags & ~INTNET_OPEN_FLAGS_MASK)); 5153 5401 AssertPtr(ppNetwork); 5154 5402 *ppNetwork = NULL; … … 5176 5424 && !strcmp(pCur->szTrunk, pszTrunk))) 5177 5425 { 5178 if (!((pCur->fFlags ^ fFlags) & INTNET_OPEN_FLAGS_COMPATIBILITY_XOR_MASK)) 5426 rc = intnetR0CheckOpenNetworkFlags(pCur, fFlags); 5427 if (RT_SUCCESS(rc)) 5179 5428 { 5180 5429 /* … … 5185 5434 if (RT_SUCCESS(rc)) 5186 5435 { 5187 if ( !(pCur->fFlags & INTNET_OPEN_FLAGS_PUBLIC))5436 if (pCur->fFlags & INTNET_OPEN_FLAGS_ACCESS_RESTRICTED) 5188 5437 rc = SUPR0ObjVerifyAccess(pCur->pvObj, pSession, pCur->szName); 5189 5438 if (RT_SUCCESS(rc)) 5190 {5191 pCur->fFlags |= fFlags & INTNET_OPEN_FLAGS_SECURITY_OR_MASK;5192 5193 5439 *ppNetwork = pCur; 5194 }5195 5440 else 5196 5441 SUPR0ObjRelease(pCur->pvObj, pSession); … … 5199 5444 rc = VERR_NOT_FOUND; /* destruction race, pretend the other isn't there. */ 5200 5445 } 5201 else5202 rc = VERR_INTNET_INCOMPATIBLE_FLAGS;5203 5446 } 5204 5447 else … … 5253 5496 Assert(!(fFlags & ~INTNET_OPEN_FLAGS_MASK)); 5254 5497 AssertPtr(ppNetwork); 5498 5255 5499 *ppNetwork = NULL; 5500 5501 /* 5502 * Adjust the flags with defaults for the network policies. 5503 * Note: Main restricts promiscuous mode on the per interface level. 5504 */ 5505 fFlags &= ~( INTNET_OPEN_FLAGS_IF_FIXED 5506 | INTNET_OPEN_FLAGS_IF_PROMISC_ALLOW 5507 | INTNET_OPEN_FLAGS_IF_PROMISC_DENY 5508 | INTNET_OPEN_FLAGS_IF_PROMISC_SEE_TRUNK 5509 | INTNET_OPEN_FLAGS_IF_PROMISC_NO_TRUNK 5510 | INTNET_OPEN_FLAGS_REQUIRE_AS_RESTRICTIVE_POLICIES 5511 | INTNET_OPEN_FLAGS_REQUIRE_EXACT); 5512 uint32_t const fDefFlags = INTNET_OPEN_FLAGS_ACCESS_RESTRICTED 5513 | INTNET_OPEN_FLAGS_PROMISC_ALLOW_CLIENTS 5514 | INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_HOST 5515 | INTNET_OPEN_FLAGS_PROMISC_ALLOW_TRUNK_WIRE 5516 | INTNET_OPEN_FLAGS_TRUNK_HOST_ENABLED 5517 | INTNET_OPEN_FLAGS_TRUNK_HOST_CHASTE_MODE 5518 | INTNET_OPEN_FLAGS_TRUNK_WIRE_ENABLED 5519 | INTNET_OPEN_FLAGS_TRUNK_WIRE_CHASTE_MODE 5520 ; 5521 for (uint32_t i = 0; i < RT_ELEMENTS(g_afIntNetOpenNetworkNetFlags); i++) 5522 if (!(fFlags & g_afIntNetOpenNetworkNetFlags[i].fPair)) 5523 fFlags |= g_afIntNetOpenNetworkNetFlags[i].fPair & fDefFlags; 5256 5524 5257 5525 /* … … 5264 5532 if (!pNetwork) 5265 5533 return VERR_NO_MEMORY; 5266 //pNetwork->pNext = NULL; 5267 //pNetwork->pIfs = NULL; 5268 pNetwork->hAddrSpinlock = NIL_RTSPINLOCK; 5269 pNetwork->MacTab.cEntries = 0; 5270 pNetwork->MacTab.cEntriesAllocated = INTNET_GROW_DSTTAB_SIZE; 5271 pNetwork->MacTab.paEntries = NULL; 5272 pNetwork->MacTab.fHostPromiscuous = false; 5273 pNetwork->MacTab.fHostActive = false; 5274 pNetwork->MacTab.fWirePromiscuous = false; 5275 pNetwork->MacTab.fWireActive = false; 5276 pNetwork->MacTab.pTrunk = NULL; 5277 pNetwork->hEvtBusyIf = NIL_RTSEMEVENT; 5278 pNetwork->pIntNet = pIntNet; 5279 //pNetwork->pvObj = NULL; 5534 //pNetwork->pNext = NULL; 5535 //pNetwork->pIfs = NULL; 5536 pNetwork->hAddrSpinlock = NIL_RTSPINLOCK; 5537 pNetwork->MacTab.cEntries = 0; 5538 pNetwork->MacTab.cEntriesAllocated = INTNET_GROW_DSTTAB_SIZE; 5539 pNetwork->MacTab.paEntries = NULL; 5540 pNetwork->MacTab.fHostPromiscuousReal = false; 5541 pNetwork->MacTab.fHostPromiscuousEff = false; 5542 pNetwork->MacTab.fHostActive = false; 5543 pNetwork->MacTab.fWirePromiscuousReal = false; 5544 pNetwork->MacTab.fWirePromiscuousEff = false; 5545 pNetwork->MacTab.fWireActive = false; 5546 pNetwork->MacTab.pTrunk = NULL; 5547 pNetwork->hEvtBusyIf = NIL_RTSEMEVENT; 5548 pNetwork->pIntNet = pIntNet; 5549 //pNetwork->pvObj = NULL; 5280 5550 if (fFlags & INTNET_OPEN_FLAGS_SHARED_MAC_ON_WIRE) 5281 pNetwork->pbTmp = RT_ALIGN_PT(pNetwork + 1, 64, uint8_t *);5551 pNetwork->pbTmp = RT_ALIGN_PT(pNetwork + 1, 64, uint8_t *); 5282 5552 //else 5283 // pNetwork->pbTmp = NULL; 5284 pNetwork->fFlags = fFlags; 5285 //pNetwork->cActiveIFs = 0; 5286 size_t cchName = strlen(pszNetwork); 5287 pNetwork->cchName = (uint8_t)cchName; 5553 // pNetwork->pbTmp = NULL; 5554 pNetwork->fFlags = fFlags; 5555 //pNetwork->fMinFlags = 0; 5556 //pNetwork->cActiveIFs = 0; 5557 size_t cchName = strlen(pszNetwork); 5558 pNetwork->cchName = (uint8_t)cchName; 5288 5559 Assert(cchName && cchName < sizeof(pNetwork->szName)); /* caller's responsibility. */ 5289 5560 memcpy(pNetwork->szName, pszNetwork, cchName); /* '\0' at courtesy of alloc. */ 5290 pNetwork->enmTrunkType = enmTrunkType;5561 pNetwork->enmTrunkType = enmTrunkType; 5291 5562 Assert(strlen(pszTrunk) < sizeof(pNetwork->szTrunk)); /* caller's responsibility. */ 5292 5563 strcpy(pNetwork->szTrunk, pszTrunk); … … 5422 5693 5423 5694 AssertMsgReturn(!(fFlags & ~INTNET_OPEN_FLAGS_MASK), ("%#x\n", fFlags), VERR_INVALID_PARAMETER); 5695 for (uint32_t i = 0; i < RT_ELEMENTS(g_afIntNetOpenNetworkNetFlags); i++) 5696 AssertMsgReturn((fFlags & g_afIntNetOpenNetworkNetFlags[i].fPair) != g_afIntNetOpenNetworkNetFlags[i].fPair, 5697 ("%#x (%#x)\n", fFlags, g_afIntNetOpenNetworkNetFlags[i].fPair), VERR_INVALID_PARAMETER); 5698 for (uint32_t i = 0; i < RT_ELEMENTS(g_afIntNetOpenNetworkIfFlags); i++) 5699 AssertMsgReturn((fFlags & g_afIntNetOpenNetworkIfFlags[i].fPair) != g_afIntNetOpenNetworkIfFlags[i].fPair, 5700 ("%#x (%#x)\n", fFlags, g_afIntNetOpenNetworkIfFlags[i].fPair), VERR_INVALID_PARAMETER); 5424 5701 AssertPtrReturn(phIf, VERR_INVALID_PARAMETER); 5425 5702 … … 5439 5716 if (RT_SUCCESS(rc)) 5440 5717 { 5441 rc = intnetR0NetworkCreateIf(pNetwork, pSession, cbSend, cbRecv, phIf);5718 rc = intnetR0NetworkCreateIf(pNetwork, pSession, cbSend, cbRecv, fFlags, phIf); 5442 5719 if (RT_SUCCESS(rc)) 5720 { 5721 intnetR0AdaptOpenNetworkFlags(pNetwork, fFlags); 5443 5722 rc = VINF_ALREADY_INITIALIZED; 5723 } 5444 5724 else 5445 5725 SUPR0ObjRelease(pNetwork->pvObj, pSession); … … 5450 5730 if (RT_SUCCESS(rc)) 5451 5731 { 5452 rc = intnetR0NetworkCreateIf(pNetwork, pSession, cbSend, cbRecv, phIf);5732 rc = intnetR0NetworkCreateIf(pNetwork, pSession, cbSend, cbRecv, fFlags, phIf); 5453 5733 if (RT_FAILURE(rc)) 5454 5734 SUPR0ObjRelease(pNetwork->pvObj, pSession);
Note:
See TracChangeset
for help on using the changeset viewer.