]>
Commit | Line | Data |
---|---|---|
f5eabba0 | 1 | package PVE::Network::SDN::Zones::VxlanPlugin; |
7e720d4d AD |
2 | |
3 | use strict; | |
4 | use warnings; | |
f5eabba0 | 5 | use PVE::Network::SDN::Zones::Plugin; |
c692cbfa | 6 | use PVE::Tools qw($IPV4RE); |
e3dca233 | 7 | use PVE::INotify; |
ba7ac021 | 8 | use PVE::Network::SDN::Controllers::EvpnPlugin; |
1d44ce70 | 9 | use PVE::Exception qw(raise raise_param_exc); |
7e720d4d | 10 | |
f5eabba0 | 11 | use base('PVE::Network::SDN::Zones::Plugin'); |
7e720d4d | 12 | |
6bffe819 AD |
13 | PVE::JSONSchema::register_format('pve-sdn-vxlanrange', \&pve_verify_sdn_vxlanrange); |
14 | sub pve_verify_sdn_vxlanrange { | |
7e720d4d AD |
15 | my ($vxlanstr) = @_; |
16 | ||
f5eabba0 | 17 | PVE::Network::SDN::Zones::Plugin::parse_tag_number_or_range($vxlanstr, '16777216'); |
7e720d4d AD |
18 | |
19 | return $vxlanstr; | |
20 | } | |
21 | ||
22 | sub type { | |
3ee45e4c | 23 | return 'vxlan'; |
7e720d4d AD |
24 | } |
25 | ||
26 | sub properties { | |
27 | return { | |
ba7ac021 AD |
28 | 'peers' => { |
29 | description => "peers address list.", | |
30 | type => 'string', format => 'ip-list' | |
7e720d4d | 31 | }, |
7e720d4d AD |
32 | }; |
33 | } | |
34 | ||
35 | sub options { | |
7e720d4d | 36 | return { |
65cb893e TL |
37 | nodes => { optional => 1}, |
38 | peers => { optional => 0 }, | |
823f2e2a | 39 | mtu => { optional => 1 }, |
4ad78442 AD |
40 | dns => { optional => 1 }, |
41 | reversedns => { optional => 1 }, | |
42 | dnszone => { optional => 1 }, | |
57a335c4 | 43 | ipam => { optional => 1 }, |
7e720d4d AD |
44 | }; |
45 | } | |
46 | ||
47 | # Plugin implementation | |
6bffe819 | 48 | sub generate_sdn_config { |
efffa0ff | 49 | my ($class, $plugin_config, $zoneid, $vnetid, $vnet, $controller, $controller_cfg, $subnet_cfg, $interfaces_config, $config) = @_; |
7e720d4d AD |
50 | |
51 | my $tag = $vnet->{tag}; | |
dc7e431e | 52 | my $alias = $vnet->{alias}; |
7e720d4d | 53 | my $multicastaddress = $plugin_config->{'multicast-address'}; |
3caa7687 FG |
54 | my @peers; |
55 | @peers = PVE::Tools::split_list($plugin_config->{'peers'}) if $plugin_config->{'peers'}; | |
ff3088cb | 56 | my $vxlan_iface = "vxlan_$vnetid"; |
7e720d4d AD |
57 | |
58 | die "missing vxlan tag" if !$tag; | |
3ee45e4c | 59 | |
1f543c5f | 60 | my ($ifaceip, $iface) = PVE::Network::SDN::Zones::Plugin::find_local_ip_interface_peers(\@peers); |
c1ae8486 AD |
61 | |
62 | my $mtu = 1450; | |
ba7ac021 | 63 | $mtu = $interfaces_config->{$iface}->{mtu} - 50 if $interfaces_config->{$iface}->{mtu}; |
0251ed2f | 64 | $mtu = $plugin_config->{mtu} if $plugin_config->{mtu}; |
7e720d4d | 65 | |
93dea3aa AD |
66 | #vxlan interface |
67 | my @iface_config = (); | |
68 | push @iface_config, "vxlan-id $tag"; | |
3ee45e4c | 69 | |
65cb893e | 70 | for my $address (@peers) { |
ba7ac021 AD |
71 | next if $address eq $ifaceip; |
72 | push @iface_config, "vxlan_remoteip $address"; | |
3ee45e4c AD |
73 | } |
74 | ||
ff3088cb | 75 | |
93dea3aa | 76 | push @iface_config, "mtu $mtu" if $mtu; |
ff3088cb | 77 | push(@{$config->{$vxlan_iface}}, @iface_config) if !$config->{$vxlan_iface}; |
93dea3aa AD |
78 | |
79 | #vnet bridge | |
80 | @iface_config = (); | |
ff3088cb | 81 | push @iface_config, "bridge_ports $vxlan_iface"; |
93dea3aa AD |
82 | push @iface_config, "bridge_stp off"; |
83 | push @iface_config, "bridge_fd 0"; | |
65cb893e TL |
84 | if ($vnet->{vlanaware}) { |
85 | push @iface_config, "bridge-vlan-aware yes"; | |
86 | push @iface_config, "bridge-vids 2-4094"; | |
912fb443 | 87 | } |
93dea3aa AD |
88 | push @iface_config, "mtu $mtu" if $mtu; |
89 | push @iface_config, "alias $alias" if $alias; | |
87d8b623 | 90 | push(@{$config->{$vnetid}}, @iface_config) if !$config->{$vnetid}; |
126fc68c | 91 | |
7e720d4d AD |
92 | return $config; |
93 | } | |
94 | ||
5ca07ed9 | 95 | sub vnet_update_hook { |
88d9562b | 96 | my ($class, $vnet_cfg, $vnetid, $zone_cfg) = @_; |
1d44ce70 | 97 | |
88d9562b AD |
98 | my $vnet = $vnet_cfg->{ids}->{$vnetid}; |
99 | my $tag = $vnet->{tag}; | |
100 | ||
101 | raise_param_exc({ tag => "missing vxlan tag"}) if !defined($tag); | |
102 | raise_param_exc({ tag => "vxlan tag max value is 16777216"}) if $tag > 16777216; | |
103 | ||
104 | # verify that tag is not already defined globally (vxlan-id are unique) | |
65cb893e | 105 | for my $id (sort keys %{$vnet_cfg->{ids}}) { |
88d9562b AD |
106 | next if $id eq $vnetid; |
107 | my $othervnet = $vnet_cfg->{ids}->{$id}; | |
108 | my $other_tag = $othervnet->{tag}; | |
109 | my $other_zoneid = $othervnet->{zone}; | |
110 | my $other_zone = $zone_cfg->{ids}->{$other_zoneid}; | |
111 | next if $other_zone->{type} ne 'vxlan' && $other_zone->{type} ne 'evpn'; | |
112 | raise_param_exc({ tag => "vxlan tag $tag already exist in vnet $id in zone $other_zoneid "}) if $other_tag && $tag eq $other_tag; | |
113 | } | |
1d44ce70 AD |
114 | } |
115 | ||
7e720d4d AD |
116 | 1; |
117 | ||
118 |