Fill bridge name and mac for bridged network and DHCP server parameter for host-only network.
Signed-off-by: Dmitry Guryanov <dgurya...@parallels.com> --- src/parallels/parallels_network.c | 172 +++++++++++++++++++++++++++++++++++++ 1 files changed, 172 insertions(+), 0 deletions(-) diff --git a/src/parallels/parallels_network.c b/src/parallels/parallels_network.c index d30c94d..64e5351 100644 --- a/src/parallels/parallels_network.c +++ b/src/parallels/parallels_network.c @@ -35,6 +35,158 @@ virReportErrorHelper(VIR_FROM_TEST, VIR_ERR_OPERATION_FAILED, __FILE__, \ __FUNCTION__, __LINE__, _("Can't parse prlctl output")) +#define SYSFS_NET_DIR "/sys/class/net" + +static int parallelsGetBridgedNetInfo(virNetworkDefPtr def, virJSONValuePtr jobj) +{ + const char *ifname; + char *bridgeLink = NULL; + char *bridgePath = NULL; + char *bridgeAddressPath = NULL; + char *bridgeAddress = NULL; + int len = 0; + int ret = -1; + + if (!(ifname = virJSONValueObjectGetString(jobj, "Bound To"))) { + parallelsParseError(); + goto cleanup; + } + + if (virAsprintf(&bridgeLink, "%s/%s/brport/bridge", + SYSFS_NET_DIR, ifname) < 0) { + virReportOOMError(); + goto cleanup; + } + + if (virFileResolveLink(bridgeLink, &bridgePath) < 0) { + virReportSystemError(errno, _("cannot read link '%s'"), bridgeLink); + goto cleanup; + } + + if (!(def->bridge = strdup(basename(bridgePath)))) { + virReportOOMError(); + goto cleanup; + } + + if (virAsprintf(&bridgeAddressPath, "%s/%s/brport/bridge/address", + SYSFS_NET_DIR, ifname) < 0) { + virReportOOMError(); + goto cleanup; + } + + if ((len = virFileReadAll(bridgeAddressPath, 18, &bridgeAddress)) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, + _("Error reading file '%s'"), bridgeAddressPath); + + goto cleanup; + } + + if (len < VIR_MAC_STRING_BUFLEN) { + virReportError(VIR_ERR_INTERNAL_ERROR, + _("Error reading MAC from '%s'"), bridgeAddressPath); + } + + bridgeAddress[VIR_MAC_STRING_BUFLEN - 1] = '\0'; + if (virMacAddrParse(bridgeAddress, &def->mac) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, + _("Can't parse MAC '%s'"), bridgeAddress); + goto cleanup; + } + def->mac_specified = 1; + + ret = 0; + +cleanup: + VIR_FREE(bridgeLink); + VIR_FREE(bridgePath); + VIR_FREE(bridgeAddress); + VIR_FREE(bridgeAddressPath); + return ret; +} + +static int parallelsGetHostOnlyNetInfo(virNetworkDefPtr def, const char *name) +{ + const char *tmp; + virJSONValuePtr jobj, jobj2; + int ret = -1; + + if (VIR_EXPAND_N(def->ips, def->nips, 1) < 0) { + virReportOOMError(); + goto cleanup; + } + + jobj = parallelsParseOutput("prlsrvctl", "net", "info", "-j", name, NULL); + + if (!jobj) { + parallelsParseError(); + goto cleanup; + } + + if (!(jobj2 = virJSONValueObjectGet(jobj, "Parallels adapter"))) { + parallelsParseError(); + goto cleanup; + } + + if (!(def->ips[0].family = strdup("ipv4"))) { + virReportOOMError(); + goto cleanup; + }; + if (!(tmp = virJSONValueObjectGetString(jobj2, "IP address"))) { + parallelsParseError(); + goto cleanup; + } + + if (virSocketAddrParseIPv4(&def->ips[0].address, tmp) < 0) { + parallelsParseError(); + goto cleanup; + } + + if (!(tmp = virJSONValueObjectGetString(jobj2, "Subnet mask"))) { + parallelsParseError(); + goto cleanup; + } + + if (virSocketAddrParseIPv4(&def->ips[0].netmask, tmp) < 0) { + parallelsParseError(); + goto cleanup; + } + + if (!(jobj2 = virJSONValueObjectGet(jobj, "DHCPv4 server"))) { + parallelsParseError(); + goto cleanup; + } + + if (VIR_EXPAND_N(def->ips[0].ranges, def->ips[0].nranges, 1) < 0) { + virReportOOMError(); + goto cleanup; + } + + if (!(tmp = virJSONValueObjectGetString(jobj2, "IP scope start address"))) { + parallelsParseError(); + goto cleanup; + } + + if (virSocketAddrParseIPv4(&def->ips[0].ranges[0].start, tmp) < 0) { + parallelsParseError(); + goto cleanup; + } + + if (!(tmp = virJSONValueObjectGetString(jobj2, "IP scope end address"))) { + parallelsParseError(); + goto cleanup; + } + + if (virSocketAddrParseIPv4(&def->ips[0].ranges[0].end, tmp) < 0) { + parallelsParseError(); + goto cleanup; + } + + ret = 0; +cleanup: + virJSONValueFree(jobj); + return ret; +} + static virNetworkObjPtr parallelsLoadNetwork(parallelsConnPtr privconn, virJSONValuePtr jobj) { @@ -61,6 +213,26 @@ parallelsLoadNetwork(parallelsConnPtr privconn, virJSONValuePtr jobj) memcpy(def->uuid, md5, VIR_UUID_BUFLEN); def->uuid_specified = 1; + if (!(tmp = virJSONValueObjectGetString(jobj, "Type"))) { + parallelsParseError(); + goto cleanup; + } + + if (STREQ(tmp, "bridged")) { + def->forwardType = VIR_NETWORK_FORWARD_BRIDGE; + + if (parallelsGetBridgedNetInfo(def, jobj) < 0) + goto cleanup; + } else if (STREQ(tmp, "host-only")) { + def->forwardType = VIR_NETWORK_FORWARD_NONE; + + if (parallelsGetHostOnlyNetInfo(def, def->name) < 0) + goto cleanup; + } else { + parallelsParseError(); + goto cleanup; + } + if (!(net = virNetworkAssignDef(&privconn->networks, def, false))) { virNetworkDefFree(def); goto cleanup; -- 1.7.7.6 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list