On Tue, Dec 11, 2012 at 02:59:43PM +0400, Dmitry Guryanov wrote:
> Allow changing network interfaces in domain configuration.
>
> ifname is used as iterface identifier: if there is interface
> with some ifname in old config and there are no interfaces with
> such name in the new config - issue prlctl command to delete
> the network interface. And vice versa - if interface with
> some ifname exists only in new config - issue prlctl command
> to create it.
>
> Signed-off-by: Dmitry Guryanov <[email protected]>
> ---
> src/parallels/parallels_driver.c | 169
> +++++++++++++++++++++++++++++++++++++-
> 1 files changed, 168 insertions(+), 1 deletions(-)
>
> diff --git a/src/parallels/parallels_driver.c
> b/src/parallels/parallels_driver.c
> index 755816e..f29b6ca 100644
> --- a/src/parallels/parallels_driver.c
> +++ b/src/parallels/parallels_driver.c
> @@ -1776,6 +1776,170 @@ parallelsApplyDisksParams(virConnectPtr conn,
> parallelsDomObjPtr pdom,
> return 0;
> }
>
> +static int parallelsApplyIfaceParams(parallelsDomObjPtr pdom,
> + virDomainNetDefPtr oldnet,
> + virDomainNetDefPtr newnet)
> +{
> + bool create = false;
> + bool is_changed = false;
> + virCommandPtr cmd;
> + char strmac[VIR_MAC_STRING_BUFLEN];
> + int i;
> +
> + if (!oldnet) {
> + create = true;
> + if (VIR_ALLOC(oldnet) < 0) {
> + virReportOOMError();
> + return -1;
> + }
> + }
> +
> + if (!create && oldnet->type != newnet->type) {
> + virReportError(VIR_ERR_ARGUMENT_UNSUPPORTED, "%s",
> + _("Changing network type is not supported"));
> + return -1;
> + }
> +
> + if (!STREQ_NULLABLE(oldnet->model, newnet->model)) {
> + virReportError(VIR_ERR_ARGUMENT_UNSUPPORTED, "%s",
> + _("Changing network device model is not supported"));
> + return -1;
> + }
> +
> + if (!STREQ_NULLABLE(oldnet->data.network.portgroup,
> + newnet->data.network.portgroup)) {
> + virReportError(VIR_ERR_ARGUMENT_UNSUPPORTED, "%s",
> + _("Changing network portgroup is not supported"));
> + return -1;
> + }
> +
> + if (!virNetDevVPortProfileEqual(oldnet->virtPortProfile,
> + newnet->virtPortProfile)) {
> + virReportError(VIR_ERR_ARGUMENT_UNSUPPORTED, "%s",
> + _("Changing virtual port profile is not supported"));
> + return -1;
> + }
> +
> + if (newnet->tune.sndbuf_specified) {
> + virReportError(VIR_ERR_ARGUMENT_UNSUPPORTED, "%s",
> + _("Setting send buffer size is not supported"));
> + return -1;
> + }
> +
> + if (!STREQ_NULLABLE(oldnet->script, newnet->script)) {
> + virReportError(VIR_ERR_ARGUMENT_UNSUPPORTED, "%s",
> + _("Setting startup script is not supported"));
> + return -1;
> + }
> +
> + if (!STREQ_NULLABLE(oldnet->filter, newnet->filter)) {
> + virReportError(VIR_ERR_ARGUMENT_UNSUPPORTED, "%s",
> + _("Changing filter params is not supported"));
> + return -1;
> + }
> +
> + if (newnet->bandwidth != NULL) {
> + virReportError(VIR_ERR_ARGUMENT_UNSUPPORTED, "%s",
> + _("Setting bandwidth params is not supported"));
> + return -1;
> + }
> +
> + for (i = 0; i < sizeof(newnet->vlan); i++) {
> + if (((char *)&newnet->vlan)[i] != 0) {
> + virReportError(VIR_ERR_ARGUMENT_UNSUPPORTED, "%s",
> + _("Setting vlan params is not supported"));
> + return -1;
> + }
> + }
> +
> + /* Here we know, that there are no differences, that are forbidden.
> + * Check is something changed, if no - do nothing */
> +
> + if (create) {
> + cmd = virCommandNewArgList(PRLCTL, "set", pdom->uuid,
> + "--device-add", "net", NULL);
> + } else {
> + cmd = virCommandNewArgList(PRLCTL, "set", pdom->uuid,
> + "--device-set", newnet->ifname, NULL);
> + }
> +
> + if (virMacAddrCmp(&oldnet->mac, &newnet->mac)) {
> + virMacAddrFormat(&newnet->mac, strmac);
> + virCommandAddArgFormat(cmd, "--mac=%s", strmac);
> + is_changed = true;
> + }
> +
> + if (!STREQ_NULLABLE(oldnet->data.network.name,
> newnet->data.network.name)) {
> + virCommandAddArgFormat(cmd, "--network=%s",
> newnet->data.network.name);
> + is_changed = true;
> + }
> +
> + if (oldnet->linkstate != newnet->linkstate) {
> + if (newnet->linkstate == VIR_DOMAIN_NET_INTERFACE_LINK_STATE_UP) {
> + virCommandAddArgFormat(cmd, "--connect");
> + } else if (newnet->linkstate ==
> VIR_DOMAIN_NET_INTERFACE_LINK_STATE_DOWN) {
> + virCommandAddArgFormat(cmd, "--disconnect");
> + }
> + is_changed = true;
> + }
> +
> + if (!create && !is_changed) {
> + /* nothing changed - no need to run prlctl */
> + return 0;
> + }
> +
> + if (virCommandRun(cmd, NULL))
> + return -1;
> +
> + return 0;
> +}
> +
> +static int
> +parallelsApplyIfacesParams(parallelsDomObjPtr pdom,
> + virDomainNetDefPtr *oldnets, int nold,
> + virDomainNetDefPtr *newnets, int nnew)
> +{
> + int i, j;
> +
> + for (i = 0; i < nold; i++) {
> + virDomainNetDefPtr newnet = NULL;
> + virDomainNetDefPtr oldnet = oldnets[i];
let's move those declarations out of the loop
> + for (j = 0; j < nnew; j++) {
> + if (STREQ_NULLABLE(newnets[j]->ifname, oldnet->ifname)) {
> + newnet = newnets[j];
> + break;
> + }
> + }
> +
> + if (!newnet) {
> + if (parallelsCmdRun(PRLCTL, "set", pdom->uuid,
> + "--device-del", oldnet->ifname, NULL) < 0)
> + return -1;
> +
> + continue;
> + }
> +
> + if (parallelsApplyIfaceParams(pdom, oldnet, newnet) < 0)
> + return -1;
> + }
> +
> + for (i = 0; i < nnew; i++) {
> + virDomainNetDefPtr newnet = newnets[i];
> + bool found = false;
> +
same
> + for (j = 0; j < nold; j++)
> + if (STREQ_NULLABLE(oldnets[j]->ifname, newnet->ifname))
> + found = true;
> + if (found)
> + continue;
> +
> + if (parallelsApplyIfaceParams(pdom, NULL, newnet))
> + return -1;
> + }
> +
> + return 0;
> +}
> +
> static int
> parallelsApplyChanges(virConnectPtr conn, virDomainObjPtr dom,
> virDomainDefPtr new)
> {
> @@ -1975,7 +2139,7 @@ parallelsApplyChanges(virConnectPtr conn,
> virDomainObjPtr dom, virDomainDefPtr n
> new->graphics, new->ngraphics) < 0)
> return -1;
>
> - if (new->nfss != 0 || new->nnets != 0 ||
> + if (new->nfss != 0 ||
> new->nsounds != 0 || new->nhostdevs != 0 ||
> new->nredirdevs != 0 || new->nsmartcards != 0 ||
> new->nparallels || new->nchannels != 0 ||
> @@ -2013,6 +2177,9 @@ parallelsApplyChanges(virConnectPtr conn,
> virDomainObjPtr dom, virDomainDefPtr n
> if (parallelsApplyDisksParams(conn, pdom, old->disks, old->ndisks,
> new->disks, new->ndisks) < 0)
> return -1;
> + if (parallelsApplyIfacesParams(pdom, old->nets, old->nnets,
> + new->nets, new->nnets) < 0)
> + return -1;
>
> return 0;
> }
ACK with associated fixup:
diff --git a/src/parallels/parallels_driver.c b/src/parallels/parallels_driver.c
index f16777a..60507e7 100644
--- a/src/parallels/parallels_driver.c
+++ b/src/parallels/parallels_driver.c
@@ -1924,10 +1924,13 @@ parallelsApplyIfacesParams(parallelsDomObjPtr pdom,
virDomainNetDefPtr *newnets, int nnew)
{
int i, j;
+ virDomainNetDefPtr newnet;
+ virDomainNetDefPtr oldnet;
+ bool found;
for (i = 0; i < nold; i++) {
- virDomainNetDefPtr newnet = NULL;
- virDomainNetDefPtr oldnet = oldnets[i];
+ newnet = NULL;
+ oldnet = oldnets[i];
for (j = 0; j < nnew; j++) {
if (STREQ_NULLABLE(newnets[j]->ifname, oldnet->ifname)) {
newnet = newnets[j];
@@ -1948,8 +1951,8 @@ parallelsApplyIfacesParams(parallelsDomObjPtr pdom,
}
for (i = 0; i < nnew; i++) {
- virDomainNetDefPtr newnet = newnets[i];
- bool found = false;
+ newnet = newnets[i];
+ found = false;
for (j = 0; j < nold; j++)
if (STREQ_NULLABLE(oldnets[j]->ifname, newnet->ifname))
Daniel
--
Daniel Veillard | Open Source and Standards, Red Hat
[email protected] | libxml Gnome XML XSLT toolkit http://xmlsoft.org/
http://veillard.com/ | virtualization library http://libvirt.org/
--
libvir-list mailing list
[email protected]
https://www.redhat.com/mailman/listinfo/libvir-list