[libvirt] [PATCH 0/1] Add VLAN capability to openvswitch virtualport types

With this change, it is now possible to support VLANs (both access and trunks) for openvswitch ports in libvirt. This also takes into account the profileid parameter, as the vlantag parameter is also optional. Examples of this configuration are below. Setup the port as an access port: <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2' vlantag='70'/> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface> Setup the port as an trunk port: <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2' vlantag='70,71,72'/> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface> src/conf/netdev_vport_profile_conf.c | 34 ++++++++++++++++++++++++++++++---- src/util/virnetdevopenvswitch.c | 23 +++++++++++++++++++++-- src/util/virnetdevvportprofile.h | 2 ++ 3 files changed, 53 insertions(+), 6 deletions(-) -- 1.7.11.2

Add the ability to specify a "vlantag" parameter for bridge networks with a virtualport type of openvswitch. This allows for specifying the port is on a single VLAN, and should receive untagged traffic (e.g. vlantag=10), or that a port should receive tagged traffic and is a trunk port (e.g. vlantag=10,11). Signed-off-by: Kyle Mestery <kmestery@cisco.com> --- src/conf/netdev_vport_profile_conf.c | 34 ++++++++++++++++++++++++++++++---- src/util/virnetdevopenvswitch.c | 23 +++++++++++++++++++++-- src/util/virnetdevvportprofile.h | 2 ++ 3 files changed, 53 insertions(+), 6 deletions(-) diff --git a/src/conf/netdev_vport_profile_conf.c b/src/conf/netdev_vport_profile_conf.c index d008042..5a4e894 100644 --- a/src/conf/netdev_vport_profile_conf.c +++ b/src/conf/netdev_vport_profile_conf.c @@ -46,6 +46,7 @@ virNetDevVPortProfileParse(xmlNodePtr node) char *virtPortInstanceID = NULL; char *virtPortProfileID = NULL; char *virtPortInterfaceID = NULL; + char *virtPortVlanTag = NULL; virNetDevVPortProfilePtr virtPort = NULL; xmlNodePtr cur = node->children; @@ -76,6 +77,7 @@ virNetDevVPortProfileParse(xmlNodePtr node) virtPortInstanceID = virXMLPropString(cur, "instanceid"); virtPortProfileID = virXMLPropString(cur, "profileid"); virtPortInterfaceID = virXMLPropString(cur, "interfaceid"); + virtPortVlanTag = virXMLPropString(cur, "vlantag"); break; } @@ -196,6 +198,18 @@ virNetDevVPortProfileParse(xmlNodePtr node) } else { virtPort->u.openvswitch.profileID[0] = '\0'; } + /* vlantag is not mandatory for Open vSwitch */ + if (virtPortVlanTag != NULL) { + + if (virStrcpyStatic(virtPort->u.openvswitch.vlantag, + virtPortVlanTag) == NULL) { + virReportError(VIR_ERR_XML_ERROR, "%s", + _("vlantag parameter too long")); + goto error; + } + } else { + virtPort->u.openvswitch.vlantag[0] = '\0'; + } break; default: @@ -254,13 +268,25 @@ virNetDevVPortProfileFormat(virNetDevVPortProfilePtr virtPort, case VIR_NETDEV_VPORT_PROFILE_OPENVSWITCH: virUUIDFormat(virtPort->u.openvswitch.interfaceID, uuidstr); - if (virtPort->u.openvswitch.profileID[0] == '\0') { + if (virtPort->u.openvswitch.profileID[0] == '\0' && + virtPort->u.openvswitch.vlantag[0] == '\0') { virBufferAsprintf(buf, " <parameters interfaceid='%s'/>\n", uuidstr); } else { - virBufferAsprintf(buf, " <parameters interfaceid='%s' " - "profileid='%s'/>\n", uuidstr, - virtPort->u.openvswitch.profileID); + if (virtPort->u.openvswitch.vlantag[0] == '\0') { + virBufferAsprintf(buf, " <parameters interfaceid='%s' " + "profileid='%s'/>\n", uuidstr, + virtPort->u.openvswitch.profileID); + } else if (virtPort->u.openvswitch.profileID[0] == '\0') { + virBufferAsprintf(buf, " <parameters interfaceid='%s' " + "vlantag='%s'/>\n", uuidstr, + virtPort->u.openvswitch.vlantag); + } else { + virBufferAsprintf(buf, " <parameters interfaceid='%s' " + "profileid='%s' vlantag='%s'/>\n", uuidstr, + virtPort->u.openvswitch.profileID, + virtPort->u.openvswitch.vlantag); + } } break; diff --git a/src/util/virnetdevopenvswitch.c b/src/util/virnetdevopenvswitch.c index 7e0beef..ea71dd1 100644 --- a/src/util/virnetdevopenvswitch.c +++ b/src/util/virnetdevopenvswitch.c @@ -57,6 +57,7 @@ int virNetDevOpenvswitchAddPort(const char *brname, const char *ifname, char *ifaceid_ex_id = NULL; char *profile_ex_id = NULL; char *vmid_ex_id = NULL; + char *vlantag = NULL; virMacAddrFormat(macaddr, macaddrstr); virUUIDFormat(ovsport->u.openvswitch.interfaceID, ifuuidstr); @@ -76,11 +77,29 @@ int virNetDevOpenvswitchAddPort(const char *brname, const char *ifname, ovsport->u.openvswitch.profileID) < 0) goto out_of_memory; } + if (ovsport->u.openvswitch.vlantag[0] != '\0') { + int i = 0; + const char *ovsvlan = "tag"; + + /* Parse this. It's either a single entry, or multiple */ + while (ovsport->u.openvswitch.vlantag[i] != '\0') { + if (ovsport->u.openvswitch.vlantag[i] == ',') { + ovsvlan = "trunks"; + break; + } + + i++; + } + + if (virAsprintf(&vlantag, "%s=%s", ovsvlan, + ovsport->u.openvswitch.vlantag) < 0) + goto out_of_memory; + } cmd = virCommandNew(OVSVSCTL); if (ovsport->u.openvswitch.profileID[0] == '\0') { virCommandAddArgList(cmd, "--", "--may-exist", "add-port", - brname, ifname, + brname, ifname, vlantag, "--", "set", "Interface", ifname, attachedmac_ex_id, "--", "set", "Interface", ifname, ifaceid_ex_id, "--", "set", "Interface", ifname, vmid_ex_id, @@ -89,7 +108,7 @@ int virNetDevOpenvswitchAddPort(const char *brname, const char *ifname, NULL); } else { virCommandAddArgList(cmd, "--", "--may-exist", "add-port", - brname, ifname, + brname, ifname, vlantag, "--", "set", "Interface", ifname, attachedmac_ex_id, "--", "set", "Interface", ifname, ifaceid_ex_id, "--", "set", "Interface", ifname, vmid_ex_id, diff --git a/src/util/virnetdevvportprofile.h b/src/util/virnetdevvportprofile.h index 6cce1bb..7cacd4f 100644 --- a/src/util/virnetdevvportprofile.h +++ b/src/util/virnetdevvportprofile.h @@ -31,6 +31,7 @@ # include "virmacaddr.h" # define LIBVIRT_IFLA_VF_PORT_PROFILE_MAX 40 +# define LIBVIRT_VLANTAG_MAX 128 enum virNetDevVPortProfile { VIR_NETDEV_VPORT_PROFILE_NONE, @@ -74,6 +75,7 @@ struct _virNetDevVPortProfile { struct { unsigned char interfaceID[VIR_UUID_BUFLEN]; char profileID[LIBVIRT_IFLA_VF_PORT_PROFILE_MAX]; + char vlantag[LIBVIRT_VLANTAG_MAX]; } openvswitch; } u; }; -- 1.7.11.2

On 08/08/2012 03:47 PM, Kyle Mestery wrote:
Add the ability to specify a "vlantag" parameter for bridge networks with a virtualport type of openvswitch. This allows for specifying the port is on a single VLAN, and should receive untagged traffic (e.g. vlantag=10), or that a port should receive tagged traffic and is a trunk port (e.g. vlantag=10,11).
Ha! We must have a telepathic link! I'm just about to add vlan support for SR-IOV VFs in PCI passthrough (aka "hostdev") and macvtap passthrough modes (the only thing that's kept me from action is indecision about where to put the vlan tag in the xml), and since at least one of those modes doesn't use <virtualport> at all, I was planning to add a <vlan tag='x'/> element at the toplevel of interface. There would also be a similar element at the toplevel of <network>, and another within <portgroup>. Something like this: <interface type='hostdev'> <mac address='52:54:00:11:22:33'/> <vlan tag='42'/> ... </interface> In this case, there is no <network> involved. Here's a case that uses a network: <interface type='network'> <mac address='52:54:00:11:22:33'/> <source network='net42'/> ... </interface> <network> <name>net42</name> <vlan tag='42'/> <forward mode='passthrough'> <interface dev='eth5'/> <interface dev='eth6'/> <interface dev='eth7'/> </forward> </network> In this second case, when the interface was brought up, it would allocate a physical device from the pool, and inherit the vlan tag, which would be set in the SR-IOV card's hardware as it's assigned to the guest. Note that hostdev passthrough would behave similarly (except forward mode would be 'hostdev') Finally, there may be a network with multiple vlans. portgroups could be used for that: <interface type='network'> <mac address='52:54:00:11:22:33'/> <source network='physnet' portgroup='production'/> ... </interface> <network> <name>net42</name> <forward mode='passthrough'> <interface dev='eth5'/> <interface dev='eth6'/> <interface dev='eth7'/> </forward> <portgroup name='production' default='yes'> <vlan tag='42'/> <bandwidth> .. </bandwidth> </portgroup> <portgroup name='test'> <vlan tag='666'/> <bandwidth> .. </bandwidth> </portgroup> </network> Selecting a different portgroup would put you on a difference vlan of the same switch. We would need to make a decision about which would take precedence if the vlan tag was given in multiple places - should the domain's request be honored, in order to allow it to made individual modifications to the general config in the <network>? Or should the network, as an entity of higher authority, be allowed to override what the domain asks for? I've never used vlan trunk groups, but I'm guessing whatever information you needed could be added as attributes to the <vlan> element. BTW, in general we don't like to have multiple pieces of data in a single element. We would prefer that they be in separate elements. So maybe if you wanted a single vlan tag, you could do it as above, but when you wanted a trunk group, you could do something like: <vlan trunk='yes'> <tag id='23'/> <tag id='24'/> <tag id='25'/> </vlan> (you might allow omitting the "trunk='yes'") Or possibly put them all at the top level: <vlan tag='23'/> <vlan tag='24'/> <vlan tag='25'/> and if you wanted a vlan trunk with only a single vlan in it: <vlan tag='23' trunk='yes'/> (actually, having multiple toplevel elements could get messy if we started talking about merging the elements from network/portgroup/interface together, so maybe that's not such a good idea). *Still another* possibility would be to put the vlan element as described above inside <virtualport>, then allow <virtualport> with no type to contain a <vlan> element. This would require a change to my recent <virtualport> merging patches, but they haven't been pushed yet. I'm not convinced I like that option, though. I think this needs a day or so to stew...

On Aug 9, 2012, at 3:14 PM, Laine Stump wrote:
On 08/08/2012 03:47 PM, Kyle Mestery wrote:
Add the ability to specify a "vlantag" parameter for bridge networks with a virtualport type of openvswitch. This allows for specifying the port is on a single VLAN, and should receive untagged traffic (e.g. vlantag=10), or that a port should receive tagged traffic and is a trunk port (e.g. vlantag=10,11).
Ha! We must have a telepathic link!
Well, we're at least thinking in the same general direction. :)
I'm just about to add vlan support for SR-IOV VFs in PCI passthrough (aka "hostdev") and macvtap passthrough modes (the only thing that's kept me from action is indecision about where to put the vlan tag in the xml), and since at least one of those modes doesn't use <virtualport> at all, I was planning to add a <vlan tag='x'/> element at the toplevel of interface. There would also be a similar element at the toplevel of <network>, and another within <portgroup>.
Something like this:
<interface type='hostdev'> <mac address='52:54:00:11:22:33'/> <vlan tag='42'/> ... </interface>
In this case, there is no <network> involved. Here's a case that uses a network:
<interface type='network'> <mac address='52:54:00:11:22:33'/> <source network='net42'/> ... </interface>
<network> <name>net42</name> <vlan tag='42'/> <forward mode='passthrough'> <interface dev='eth5'/> <interface dev='eth6'/> <interface dev='eth7'/> </forward> </network>
In this second case, when the interface was brought up, it would allocate a physical device from the pool, and inherit the vlan tag, which would be set in the SR-IOV card's hardware as it's assigned to the guest. Note that hostdev passthrough would behave similarly (except forward mode would be 'hosted')
Those cases both look good. I think the formatting works just fine for virtualport type=openvswitch as well, something like this: Single VLAN (no trunk): <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <vlan tag='70'/> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2'> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface> Single VLAN (trunk): <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <vlan tag='70'/ trunk=yes> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2'> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface> Multiple VLANs (trunk): <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <vlan trunk='yes'> <tag id='70'> <tag id='71'> </vlan> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2'> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
Finally, there may be a network with multiple vlans. portgroups could be used for that:
<interface type='network'> <mac address='52:54:00:11:22:33'/> <source network='physnet' portgroup='production'/> ... </interface>
<network> <name>net42</name> <forward mode='passthrough'> <interface dev='eth5'/> <interface dev='eth6'/> <interface dev='eth7'/> </forward> <portgroup name='production' default='yes'> <vlan tag='42'/> <bandwidth> .. </bandwidth> </portgroup> <portgroup name='test'> <vlan tag='666'/> <bandwidth> .. </bandwidth> </portgroup> </network>
Selecting a different portgroup would put you on a difference vlan of the same switch. We would need to make a decision about which would take precedence if the vlan tag was given in multiple places - should the domain's request be honored, in order to allow it to made individual modifications to the general config in the <network>? Or should the network, as an entity of higher authority, be allowed to override what the domain asks for?
I think this is the most elegant solution, and dovetails nicely with the fact that virtualport type='openvswitch' ports already support port-profiles. I think in general, my feeling here is the domain XML should override the network element. This is similar to an interface override of a port-profile on a Cisco switch, for example, where you define configuration in a port-profile, but allow configuration directly on the interface itself to override the port-profile configuration.
I've never used vlan trunk groups, but I'm guessing whatever information you needed could be added as attributes to the <vlan> element. BTW, in general we don't like to have multiple pieces of data in a single element. We would prefer that they be in separate elements. So maybe if you wanted a single vlan tag, you could do it as above, but when you wanted a trunk group, you could do something like:
<vlan trunk='yes'> <tag id='23'/> <tag id='24'/> <tag id='25'/> </vlan>
(you might allow omitting the "trunk='yes'") Or possibly put them all at the top level:
<vlan tag='23'/> <vlan tag='24'/> <vlan tag='25'/>
and if you wanted a vlan trunk with only a single vlan in it:
<vlan tag='23' trunk='yes'/>
(actually, having multiple toplevel elements could get messy if we started talking about merging the elements from network/portgroup/interface together, so maybe that's not such a good idea).
*Still another* possibility would be to put the vlan element as described above inside <virtualport>, then allow <virtualport> with no type to contain a <vlan> element. This would require a change to my recent <virtualport> merging patches, but they haven't been pushed yet. I'm not convinced I like that option, though.
I think this needs a day or so to stew...
So I guess the question is, are you going to role this up into your patches? If so, you can likely make use of some pieces of the patches I posted. Let me know, and I can also work with you on this as well. Thanks, Kyle

On 08/10/2012 11:21 AM, Kyle Mestery (kmestery) wrote:
On Aug 9, 2012, at 3:14 PM, Laine Stump wrote:
On 08/08/2012 03:47 PM, Kyle Mestery wrote:
Add the ability to specify a "vlantag" parameter for bridge networks with a virtualport type of openvswitch. This allows for specifying the port is on a single VLAN, and should receive untagged traffic (e.g. vlantag=10), or that a port should receive tagged traffic and is a trunk port (e.g. vlantag=10,11). Ha! We must have a telepathic link!
Well, we're at least thinking in the same general direction. :)
I'm just about to add vlan support for SR-IOV VFs in PCI passthrough (aka "hostdev") and macvtap passthrough modes (the only thing that's kept me from action is indecision about where to put the vlan tag in the xml), and since at least one of those modes doesn't use <virtualport> at all, I was planning to add a <vlan tag='x'/> element at the toplevel of interface. There would also be a similar element at the toplevel of <network>, and another within <portgroup>.
Something like this:
<interface type='hostdev'> <mac address='52:54:00:11:22:33'/> <vlan tag='42'/> ... </interface>
In this case, there is no <network> involved. Here's a case that uses a network:
<interface type='network'> <mac address='52:54:00:11:22:33'/> <source network='net42'/> ... </interface>
<network> <name>net42</name> <vlan tag='42'/> <forward mode='passthrough'> <interface dev='eth5'/> <interface dev='eth6'/> <interface dev='eth7'/> </forward> </network>
In this second case, when the interface was brought up, it would allocate a physical device from the pool, and inherit the vlan tag, which would be set in the SR-IOV card's hardware as it's assigned to the guest. Note that hostdev passthrough would behave similarly (except forward mode would be 'hosted')
Those cases both look good. I think the formatting works just fine for virtualport type=openvswitch as well, something like this:
Single VLAN (no trunk): <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <vlan tag='70'/> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2'> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
Single VLAN (trunk): <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <vlan tag='70'/ trunk=yes> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2'> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
Multiple VLANs (trunk): <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <vlan trunk='yes'> <tag id='70'> <tag id='71'> </vlan> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2'> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
Finally, there may be a network with multiple vlans. portgroups could be used for that:
<interface type='network'> <mac address='52:54:00:11:22:33'/> <source network='physnet' portgroup='production'/> ... </interface>
<network> <name>net42</name> <forward mode='passthrough'> <interface dev='eth5'/> <interface dev='eth6'/> <interface dev='eth7'/> </forward> <portgroup name='production' default='yes'> <vlan tag='42'/> <bandwidth> .. </bandwidth> </portgroup> <portgroup name='test'> <vlan tag='666'/> <bandwidth> .. </bandwidth> </portgroup> </network>
Selecting a different portgroup would put you on a difference vlan of the same switch. We would need to make a decision about which would take precedence if the vlan tag was given in multiple places - should the domain's request be honored, in order to allow it to made individual modifications to the general config in the <network>? Or should the network, as an entity of higher authority, be allowed to override what the domain asks for?
I think this is the most elegant solution, and dovetails nicely with the fact that virtualport type='openvswitch' ports already support port-profiles. I think in general, my feeling here is the domain XML should override the network element. This is similar to an interface override of a port-profile on a Cisco switch, for example, where you define configuration in a port-profile, but allow configuration directly on the interface itself to override the port-profile configuration.
Okay. Thanks - it's good to know how the rest of the world works. Best to mirror that as much as possible.
I've never used vlan trunk groups, but I'm guessing whatever information you needed could be added as attributes to the <vlan> element. BTW, in general we don't like to have multiple pieces of data in a single element. We would prefer that they be in separate elements. So maybe if you wanted a single vlan tag, you could do it as above, but when you wanted a trunk group, you could do something like:
<vlan trunk='yes'> <tag id='23'/> <tag id='24'/> <tag id='25'/> </vlan>
(you might allow omitting the "trunk='yes'") Or possibly put them all at the top level:
<vlan tag='23'/> <vlan tag='24'/> <vlan tag='25'/>
and if you wanted a vlan trunk with only a single vlan in it:
<vlan tag='23' trunk='yes'/>
(actually, having multiple toplevel elements could get messy if we started talking about merging the elements from network/portgroup/interface together, so maybe that's not such a good idea).
*Still another* possibility would be to put the vlan element as described above inside <virtualport>, then allow <virtualport> with no type to contain a <vlan> element. This would require a change to my recent <virtualport> merging patches, but they haven't been pushed yet. I'm not convinced I like that option, though.
I think this needs a day or so to stew... So I guess the question is, are you going to role this up into your patches? If so, you can likely make use of some pieces of the patches I posted. Let me know, and I can also work with you on this as well.
How about this - I'll try to produce patches today that 1) get the <vlan> element into <interface>, <network>, and <portgroup> as a virNetDevVlan object, and 2) merge all of those properly so that you end up with an optional virNetDevVlanPtr vlan in the actual netdef, accessible via the new function virDomainNetGetActualVlan(net). I'm thinking virNetDevVlan will just be something like this: struct _virNetDevVlan { bool trunk; /* true if this is a trunk */ unsigned int *tag; /* pointer to array of tags */ } I guess this will need to be defined in src/util, since it needs to be passed into virnetdevopenvswitch.c and virnetdevvportprofile.c I'll submit those patches by themselves, and leave the patches that actually use the vlan info until that's done. That way you'll have what you need to rework your patches as soon as possible.

On Fri, Aug 10, 2012 at 10:21 AM, Kyle Mestery (kmestery) <kmestery@cisco.com> wrote:
Those cases both look good. I think the formatting works just fine for virtualport type=openvswitch as well, something like this:
Single VLAN (no trunk): <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <vlan tag='70'/> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2'> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
Single VLAN (trunk): <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <vlan tag='70'/ trunk=yes> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2'> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
Multiple VLANs (trunk): <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <vlan trunk='yes'> <tag id='70'> <tag id='71'> </vlan> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2'> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
I think that making "tag id=" an XML attribute in one case and an element in another is problematic. May I suggest just using: <vlan [trunk='yes|no']> <!-- if unspecified, trunk defaults to 'no' --> <tag id='nn'/> [<tag id='nn'/> ...] </vlan>

On 08/10/2012 03:59 PM, Dennis Jenkins wrote:
On Fri, Aug 10, 2012 at 10:21 AM, Kyle Mestery (kmestery) <kmestery@cisco.com> wrote:
Those cases both look good. I think the formatting works just fine for virtualport type=openvswitch as well, something like this:
Single VLAN (no trunk): <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <vlan tag='70'/> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2'> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
Single VLAN (trunk): <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <vlan tag='70'/ trunk=yes> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2'> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
Multiple VLANs (trunk): <interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <vlan trunk='yes'> <tag id='70'> <tag id='71'> </vlan> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2'> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
I think that making "tag id=" an XML attribute in one case and an element in another is problematic. May I suggest just using:
<vlan [trunk='yes|no']> <!-- if unspecified, trunk defaults to 'no' --> <tag id='nn'/> [<tag id='nn'/> ...] </vlan>
Yeah, I think you're right. It's sad though that it makes the config longer even for the 99% of uses where people just want a single vlan tag (that's what blinded me). One last try before I give up: How about allowing multiple <vlan tag='n' [trunk='yes|no']/> at the toplevel? Then you could have: <vlan tag='42'/> in the simplest case, or: <vlan tag='42' trunk='yes'/> if you wanted a trunk with a single tag, or: <vlan tag='42'/> <vlan tag='43'/> <vlan tag='44'/> if you want a trunk with multiple tags (trunk='yes' would be implicit). For either of these cases, the data definition can remain the same (as long as we don't require that superfluous "trunk='yes|no'" attributes be preserved across an iteration of parse/format.) I got stuck with other stuff during the day, so I'll get back to this later tonight.

On 08/10/2012 05:44 PM, Laine Stump wrote:
How about allowing multiple <vlan tag='n' [trunk='yes|no']/> at the toplevel? Then you could have:
<vlan tag='42'/>
in the simplest case, or:
<vlan tag='42' trunk='yes'/>
if you wanted a trunk with a single tag, or:
<vlan tag='42'/> <vlan tag='43'/> <vlan tag='44'/>
if you want a trunk with multiple tags (trunk='yes' would be implicit).
For either of these cases, the data definition can remain the same (as long as we don't require that superfluous "trunk='yes|no'" attributes be preserved across an iteration of parse/format.)
I've implemented the data structure, parser, and formatter for the above proposal, and tied it into the domain and network config, as well as modifying the network driver to grab the most appropriate vlan object from the interface / portgroup / network configuration and make it available via a single function call: https://www.redhat.com/archives/libvir-list/2012-August/msg00790.html I haven't yet implemented actually *setting* the vlan for PCI passthrough with <interface type='hostdev'/>, but all of the xml2xml tests run properly, so hopefully it's all functional enough to hook into the openvswitch backend.

On Aug 13, 2012, at 12:04 AM, Laine Stump wrote:
On 08/10/2012 05:44 PM, Laine Stump wrote:
How about allowing multiple <vlan tag='n' [trunk='yes|no']/> at the toplevel? Then you could have:
<vlan tag='42'/>
in the simplest case, or:
<vlan tag='42' trunk='yes'/>
if you wanted a trunk with a single tag, or:
<vlan tag='42'/> <vlan tag='43'/> <vlan tag='44'/>
if you want a trunk with multiple tags (trunk='yes' would be implicit).
For either of these cases, the data definition can remain the same (as long as we don't require that superfluous "trunk='yes|no'" attributes be preserved across an iteration of parse/format.)
I've implemented the data structure, parser, and formatter for the above proposal, and tied it into the domain and network config, as well as modifying the network driver to grab the most appropriate vlan object from the interface / portgroup / network configuration and make it available via a single function call:
https://www.redhat.com/archives/libvir-list/2012-August/msg00790.html
I haven't yet implemented actually *setting* the vlan for PCI passthrough with <interface type='hostdev'/>, but all of the xml2xml tests run properly, so hopefully it's all functional enough to hook into the openvswitch backend.
Thanks Laine, I see your patches, I'll review them now and see if I can test out hooking up Open vSwitch support. If it all works, I'll send out a new patch to allow setting this for Open vSwitch networks. Thanks! Kyle

How would one specify VLAN trunk mode with only one vlan tag present? On Wed, Aug 8, 2012 at 2:47 PM, Kyle Mestery <kmestery@cisco.com> wrote:
With this change, it is now possible to support VLANs (both access and trunks) for openvswitch ports in libvirt. This also takes into account the profileid parameter, as the vlantag parameter is also optional.
Examples of this configuration are below.
Setup the port as an access port:
<interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2' vlantag='70'/> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
Setup the port as an trunk port:
<interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2' vlantag='70,71,72'/> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
src/conf/netdev_vport_profile_conf.c | 34 ++++++++++++++++++++++++++++++---- src/util/virnetdevopenvswitch.c | 23 +++++++++++++++++++++-- src/util/virnetdevvportprofile.h | 2 ++ 3 files changed, 53 insertions(+), 6 deletions(-)
-- 1.7.11.2
-- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list

On Aug 8, 2012, at 3:53 PM, dennis jenkins wrote:
How would one specify VLAN trunk mode with only one vlan tag present?
Actually, this is a deficiency with the model below, it isn't possible. I had thought of using "vlantag=<tag>" for access ports, and "vlantrunk=<tags>" for trunks, but was hoping to simplify things. Would the 2 different parameter approach be better? What do others think? Thanks, Kyle
On Wed, Aug 8, 2012 at 2:47 PM, Kyle Mestery <kmestery@cisco.com> wrote:
With this change, it is now possible to support VLANs (both access and trunks) for openvswitch ports in libvirt. This also takes into account the profileid parameter, as the vlantag parameter is also optional.
Examples of this configuration are below.
Setup the port as an access port:
<interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2' vlantag='70'/> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
Setup the port as an trunk port:
<interface type='bridge'> <mac address='52:54:00:30:23:a6'/> <source bridge='data-br'/> <virtualport type='openvswitch'> <parameters interfaceid='cdbbbc31-b7fe-16ca-a715-cc7cc76e18b2' vlantag='70,71,72'/> </virtualport> <model type='virtio'/> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface>
src/conf/netdev_vport_profile_conf.c | 34 ++++++++++++++++++++++++++++++---- src/util/virnetdevopenvswitch.c | 23 +++++++++++++++++++++-- src/util/virnetdevvportprofile.h | 2 ++ 3 files changed, 53 insertions(+), 6 deletions(-)
-- 1.7.11.2
-- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
-- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
participants (5)
-
Dennis Jenkins
-
dennis jenkins
-
Kyle Mestery
-
Kyle Mestery (kmestery)
-
Laine Stump