From nobody Sun May 5 01:00:23 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of redhat.com designates 209.132.183.28 as permitted sender) client-ip=209.132.183.28; envelope-from=libvir-list-bounces@redhat.com; helo=mx1.redhat.com; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of redhat.com designates 209.132.183.28 as permitted sender) smtp.mailfrom=libvir-list-bounces@redhat.com; dmarc=pass(p=none dis=none) header.from=redhat.com ARC-Seal: i=1; a=rsa-sha256; t=1560877090; cv=none; d=zoho.com; s=zohoarc; b=fv7Wm8BhKjAw60GNFdouS/lJaDGiUfGKnRHyEtKuZkXDkf+Z7mlL5ozU9qWa+OaWK/ubZSEnrF9rFmivMczywx6sN13dVEj9aQEyB86p1ew0Aq6kGTDHRnsaY9YVvIzb7jiIp6TZ3GIKMtCCm1KwMbdaDpCrm/ZKhUHcjxbgXxU= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zoho.com; s=zohoarc; t=1560877090; h=Content-Type:Content-Transfer-Encoding:Date:From:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:Sender:Subject:To:ARC-Authentication-Results; bh=8FTi9Q6VLs/DI0/eWYvyn56ofCG6VKjVrUliycqyPHg=; b=lIV57NaXovdqA54pUomm/9Fj+tSB3fqt3lAJfk2kGDdk0elX+2DQz+IAaP5aLaS/7xDc46I9xHEKxdnHGSeqBsLJp5pBTwqyvJzDlYq8tJXYrxzwjuec2llbbpv7VW5wpItnrQ2sh6UmV6vDgcXNRhdfzt9iILH5k/wcusF6u2w= ARC-Authentication-Results: i=1; mx.zoho.com; spf=pass (zoho.com: domain of redhat.com designates 209.132.183.28 as permitted sender) smtp.mailfrom=libvir-list-bounces@redhat.com; dmarc=pass header.from= (p=none dis=none) header.from= Return-Path: Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by mx.zohomail.com with SMTPS id 1560877090898638.3667099293226; Tue, 18 Jun 2019 09:58:10 -0700 (PDT) Received: from smtp.corp.redhat.com (int-mx08.intmail.prod.int.phx2.redhat.com [10.5.11.23]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 2BEB5356C4; Tue, 18 Jun 2019 16:57:54 +0000 (UTC) Received: from colo-mx.corp.redhat.com (colo-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.21]) by smtp.corp.redhat.com (Postfix) with ESMTPS id 799058090; Tue, 18 Jun 2019 16:57:48 +0000 (UTC) Received: from lists01.pubmisc.prod.ext.phx2.redhat.com (lists01.pubmisc.prod.ext.phx2.redhat.com [10.5.19.33]) by colo-mx.corp.redhat.com (Postfix) with ESMTP id 5BA70206D2; Tue, 18 Jun 2019 16:57:42 +0000 (UTC) Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.phx2.redhat.com [10.5.11.15]) by lists01.pubmisc.prod.ext.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id x5IGvdEY001424 for ; Tue, 18 Jun 2019 12:57:39 -0400 Received: by smtp.corp.redhat.com (Postfix) id DE6FB98B5; Tue, 18 Jun 2019 16:57:39 +0000 (UTC) Received: from localhost.localdomain.com (ovpn-112-51.ams2.redhat.com [10.36.112.51]) by smtp.corp.redhat.com (Postfix) with ESMTP id 03D7C39BE; Tue, 18 Jun 2019 16:57:36 +0000 (UTC) From: =?UTF-8?q?Daniel=20P=2E=20Berrang=C3=A9?= To: libvir-list@redhat.com Date: Tue, 18 Jun 2019 17:57:34 +0100 Message-Id: <20190618165734.6240-1-berrange@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.5.11.15 X-loop: libvir-list@redhat.com Subject: [libvirt] [go-xml PATCH] Add support for network port XML schema X-BeenThere: libvir-list@redhat.com X-Mailman-Version: 2.1.12 Precedence: junk List-Id: Development discussions about the libvirt library & tools List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Sender: libvir-list-bounces@redhat.com Errors-To: libvir-list-bounces@redhat.com X-Scanned-By: MIMEDefang 2.84 on 10.5.11.23 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.30]); Tue, 18 Jun 2019 16:58:07 +0000 (UTC) Signed-off-by: Daniel P. Berrang=C3=A9 --- domain.go | 1 + network.go | 1 + network_port.go | 200 ++++++++++++++++++++++++++++++++++++++++++++++++ xml_test.go | 3 + 4 files changed, 205 insertions(+) create mode 100644 network_port.go diff --git a/domain.go b/domain.go index 0757048..a7cbdcf 100644 --- a/domain.go +++ b/domain.go @@ -440,6 +440,7 @@ type DomainInterfaceSourceNetwork struct { Network string `xml:"network,attr,omitempty"` PortGroup string `xml:"portgroup,attr,omitempty"` Bridge string `xml:"bridge,attr,omitempty"` + PortID string `xml:"portid,attr,omitempty"` } =20 type DomainInterfaceSourceBridge struct { diff --git a/network.go b/network.go index d4faf46..61c1af0 100644 --- a/network.go +++ b/network.go @@ -282,6 +282,7 @@ type NetworkBandwidthParams struct { } =20 type NetworkBandwidth struct { + ClassID uint `xml:"classID,attr,omitempty"` Inbound *NetworkBandwidthParams `xml:"inbound"` Outbound *NetworkBandwidthParams `xml:"outbound"` } diff --git a/network_port.go b/network_port.go new file mode 100644 index 0000000..3cbc7fb --- /dev/null +++ b/network_port.go @@ -0,0 +1,200 @@ +/* + * This file is part of the libvirt-go-xml project + * + * Permission is hereby granted, free of charge, to any person obtaining a= copy + * of this software and associated documentation files (the "Software"), t= o deal + * in the Software without restriction, including without limitation the r= ights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or se= ll + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included= in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS= OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL= THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING= FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS = IN + * THE SOFTWARE. + * + * Copyright (C) 2019 Red Hat, Inc. + * + */ + +package libvirtxml + +import ( + "encoding/xml" + "fmt" +) + +type NetworkPort struct { + XMLName xml.Name `xml:"networkport"` + UUID string `xml:"uuid,omitempty"` + Owner *NetworkPortOwner `xml:"owner",` + MAC *NetworkPortMAC `xml:"mac"` + Group string `xml:"group,omitempty"` + Bandwidth *NetworkBandwidth `xml:"bandwidth"` + VirtualPort *NetworkVirtualPort `xml:"virtualport"` + RXFilters *NetworkPortRXFilters `xml:"rxfilters"` + Plug *NetworkPortPlug `xml:"plug"` +} + +type NetworkPortOwner struct { + UUID string `xml:"uuid,omitempty"` + Name string `xml:"name,omitempty"` +} + +type NetworkPortMAC struct { + Address string `xml:"address,attr"` +} + +type NetworkPortRXFilters struct { + TrustGuest string `xml:"trustGuest,attr"` +} + +type NetworkPortPlug struct { + Bridge *NetworkPortPlugBridge `xml:"-"` + Network *NetworkPortPlugNetwork `xml:"-"` + Direct *NetworkPortPlugDirect `xml:"-"` + HostDevPCI *NetworkPortPlugHostDevPCI `xml:"-"` +} + +type NetworkPortPlugBridge struct { + Bridge string `xml:"bridge,attr"` + MacTableManager string `xml:"macTableManager,attr,omitempty"` +} + +type NetworkPortPlugNetwork struct { + Bridge string `xml:"bridge,attr"` + MacTableManager string `xml:"macTableManager,attr,omitempty"` +} + +type NetworkPortPlugDirect struct { + Dev string `xml:"dev,attr"` + Mode string `xml:"mode,attr"` +} + +type NetworkPortPlugHostDevPCI struct { + Managed string `xml:"managed,attr,omitempty"` + Driver *NetworkPortPlugHostDevPCIDriver `xml:"driver"` + Address *NetworkPortPlugHostDevPCIAddress `xml:"address"` +} + +type NetworkPortPlugHostDevPCIDriver struct { + Name string `xml:"name,attr"` +} + +type NetworkPortPlugHostDevPCIAddress struct { + Domain *uint `xml:"domain,attr"` + Bus *uint `xml:"bus,attr"` + Slot *uint `xml:"slot,attr"` + Function *uint `xml:"function,attr"` +} + +func (a *NetworkPortPlugHostDevPCIAddress) MarshalXML(e *xml.Encoder, star= t xml.StartElement) error { + marshalUintAttr(&start, "domain", a.Domain, "0x%04x") + marshalUintAttr(&start, "bus", a.Bus, "0x%02x") + marshalUintAttr(&start, "slot", a.Slot, "0x%02x") + marshalUintAttr(&start, "function", a.Function, "0x%x") + e.EncodeToken(start) + e.EncodeToken(start.End()) + return nil +} + +func (a *NetworkPortPlugHostDevPCIAddress) UnmarshalXML(d *xml.Decoder, st= art xml.StartElement) error { + for _, attr :=3D range start.Attr { + if attr.Name.Local =3D=3D "domain" { + if err :=3D unmarshalUintAttr(attr.Value, &a.Domain, 0); err !=3D nil { + return err + } + } else if attr.Name.Local =3D=3D "bus" { + if err :=3D unmarshalUintAttr(attr.Value, &a.Bus, 0); err !=3D nil { + return err + } + } else if attr.Name.Local =3D=3D "slot" { + if err :=3D unmarshalUintAttr(attr.Value, &a.Slot, 0); err !=3D nil { + return err + } + } else if attr.Name.Local =3D=3D "function" { + if err :=3D unmarshalUintAttr(attr.Value, &a.Function, 0); err !=3D nil= { + return err + } + } + } + d.Skip() + return nil +} + +func (p *NetworkPortPlug) MarshalXML(e *xml.Encoder, start xml.StartElemen= t) error { + start.Name.Local =3D "plug" + if p.Bridge !=3D nil { + start.Attr =3D append(start.Attr, xml.Attr{ + xml.Name{Local: "type"}, "bridge", + }) + return e.EncodeElement(p.Bridge, start) + } else if p.Network !=3D nil { + start.Attr =3D append(start.Attr, xml.Attr{ + xml.Name{Local: "type"}, "network", + }) + return e.EncodeElement(p.Network, start) + } else if p.Direct !=3D nil { + start.Attr =3D append(start.Attr, xml.Attr{ + xml.Name{Local: "type"}, "direct", + }) + return e.EncodeElement(p.Direct, start) + } else if p.HostDevPCI !=3D nil { + start.Attr =3D append(start.Attr, xml.Attr{ + xml.Name{Local: "type"}, "hostdev-pci", + }) + return e.EncodeElement(p.HostDevPCI, start) + } + return nil +} + +func (p *NetworkPortPlug) UnmarshalXML(d *xml.Decoder, start xml.StartElem= ent) error { + typ, ok :=3D getAttr(start.Attr, "type") + if !ok { + return fmt.Errorf("Missing type attribute on plug") + } else if typ =3D=3D "bridge" { + var pb NetworkPortPlugBridge + if err :=3D d.DecodeElement(&pb, &start); err !=3D nil { + return err + } + p.Bridge =3D &pb + } else if typ =3D=3D "network" { + var pn NetworkPortPlugNetwork + if err :=3D d.DecodeElement(&pn, &start); err !=3D nil { + return err + } + p.Network =3D &pn + } else if typ =3D=3D "direct" { + var pd NetworkPortPlugDirect + if err :=3D d.DecodeElement(&pd, &start); err !=3D nil { + return err + } + p.Direct =3D &pd + } else if typ =3D=3D "hostdev-pci" { + var ph NetworkPortPlugHostDevPCI + if err :=3D d.DecodeElement(&ph, &start); err !=3D nil { + return err + } + p.HostDevPCI =3D &ph + } + d.Skip() + return nil +} + +func (s *NetworkPort) Unmarshal(doc string) error { + return xml.Unmarshal([]byte(doc), s) +} + +func (s *NetworkPort) Marshal() (string, error) { + doc, err :=3D xml.MarshalIndent(s, "", " ") + if err !=3D nil { + return "", err + } + return string(doc), nil +} diff --git a/xml_test.go b/xml_test.go index 320c248..7e3876a 100644 --- a/xml_test.go +++ b/xml_test.go @@ -83,6 +83,7 @@ var xmldirs =3D []string{ "testdata/libvirt/tests/storagevolxml2xmlin", "testdata/libvirt/tests/storagevolxml2xmlout", "testdata/libvirt/tests/vircaps2xmldata", + "testdata/libvirt/tests/virnetworkportxml2xmldata", "testdata/libvirt/tests/virstorageutildata", "testdata/libvirt/tests/vmx2xmldata", "testdata/libvirt/tests/xlconfigdata", @@ -306,6 +307,8 @@ func testRoundTrip(t *testing.T, xml string, filename s= tring) { doc =3D &Domain{} } else if strings.HasPrefix(xml, "