summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBeniamino Galvani <bgalvani@redhat.com>2015-09-30 17:50:45 +0200
committerBeniamino Galvani <bgalvani@redhat.com>2015-10-02 15:02:30 +0200
commite65849cd776fa7eed6b989312fc43ae07722b367 (patch)
treebc26461dc65a204d63b88ad949b05dc076255a26
parenteb1b67615eb34543054a3448f2c804946a221c88 (diff)
downloadNetworkManager-e65849cd776fa7eed6b989312fc43ae07722b367.tar.gz
platform: add support for creating new MAC-VLAN links
Add platform functions for creating new MAC-VLAN links and add some checks in configure.ac to detect when libnl supports it.
-rw-r--r--configure.ac6
-rw-r--r--src/platform/nm-linux-platform.c25
-rw-r--r--src/platform/nm-platform.c32
-rw-r--r--src/platform/nm-platform.h4
4 files changed, 67 insertions, 0 deletions
diff --git a/configure.ac b/configure.ac
index 16ffa4f876..59cdd84412 100644
--- a/configure.ac
+++ b/configure.ac
@@ -530,6 +530,12 @@ AC_CHECK_LIB([nl-route-3], [rtnl_link_inet6_get_addr_gen_mode],
AC_DEFINE_UNQUOTED(HAVE_LIBNL_INET6_ADDR_GEN_MODE,
$ac_have_addr_gen_mode, [Define if libnl has rtnl_link_inet6_get_addr_gen_mode()])
+AC_CHECK_LIB([nl-route-3], [rtnl_link_macvlan_alloc],
+ ac_have_libnl_macvlan="1",
+ ac_have_libnl_macvlan="0")
+AC_DEFINE_UNQUOTED(HAVE_LIBNL_MACVLAN,
+ $ac_have_libnl_macvlan, [Define if libnl has macvlan support])
+
AC_MSG_CHECKING([Linux kernel IN6_ADDR_GEN_MODE enum])
AC_COMPILE_IFELSE(
[AC_LANG_PROGRAM(
diff --git a/src/platform/nm-linux-platform.c b/src/platform/nm-linux-platform.c
index bc3c67442c..7f6cb3761c 100644
--- a/src/platform/nm-linux-platform.c
+++ b/src/platform/nm-linux-platform.c
@@ -50,6 +50,10 @@
#endif
#endif
+#if HAVE_LIBNL_MACVLAN
+#include <netlink/route/link/macvlan.h>
+#endif
+
#include "nm-core-internal.h"
#include "NetworkManagerUtils.h"
#include "nm-linux-platform.h"
@@ -3266,6 +3270,25 @@ vlan_set_egress_map (NMPlatform *platform, int ifindex, int from, int to)
return do_change_link (platform, change, TRUE) == NM_PLATFORM_ERROR_SUCCESS;
}
+static int
+macvlan_add (NMPlatform *platform, const char *name, int parent, int mode, NMPlatformLink *out_link)
+{
+#if HAVE_LIBNL_MACVLAN
+ auto_nl_object struct rtnl_link *rtnllink;
+
+ rtnllink = (struct rtnl_link *) build_rtnl_link (0, name, NM_LINK_TYPE_MACVLAN);
+ rtnl_link_macvlan_set_mode (rtnllink, mode);
+ rtnl_link_set_link (rtnllink, parent);
+
+ _LOGD ("link: add macvlan '%s', parent %d, mode %d", name, parent, mode);
+
+ return do_add_link_with_lookup (platform, name, rtnllink, NM_LINK_TYPE_MACVLAN, out_link);
+#else
+ _LOGW ("link: add macvlan '%s', parent %d, mode %d: MAC-VLAN support disabled", name, parent, mode);
+ return FALSE;
+#endif
+}
+
static gboolean
link_enslave (NMPlatform *platform, int master, int slave)
{
@@ -5083,6 +5106,8 @@ nm_linux_platform_class_init (NMLinuxPlatformClass *klass)
platform_class->vlan_set_ingress_map = vlan_set_ingress_map;
platform_class->vlan_set_egress_map = vlan_set_egress_map;
+ platform_class->macvlan_add = macvlan_add;
+
platform_class->infiniband_partition_add = infiniband_partition_add;
platform_class->infiniband_get_info = infiniband_get_info;
diff --git a/src/platform/nm-platform.c b/src/platform/nm-platform.c
index 1549321db4..c16910a134 100644
--- a/src/platform/nm-platform.c
+++ b/src/platform/nm-platform.c
@@ -1435,6 +1435,7 @@ nm_platform_team_add (NMPlatform *self, const char *name, NMPlatformLink *out_li
* nm_platform_vlan_add:
* @self: platform instance
* @name: New interface name
+ * @parent: the parent interface
* @vlanid: VLAN identifier
* @vlanflags: VLAN flags from libnm
* @out_link: on success, the link object
@@ -1469,6 +1470,37 @@ nm_platform_vlan_add (NMPlatform *self,
return NM_PLATFORM_ERROR_SUCCESS;
}
+/**
+ * nm_platform_macvlan_add:
+ * @self: platform instance
+ * @name: new interface name
+ * @parent: the parent interface
+ * @mode: a MAC-VLAN mode as MACVLAN_MODE_VEPA, MACVLAN_MODE_BRIDGE, etc.
+ * @out_link: on success, the link object
+ *
+ * Create a MAC-VLAN interface.
+ */
+NMPlatformError
+nm_platform_macvlan_add (NMPlatform *self, const char *name, int parent, int mode,
+ NMPlatformLink *out_link)
+{
+ NMPlatformError plerr;
+
+ _CHECK_SELF (self, klass, NM_PLATFORM_ERROR_BUG);
+
+ g_return_val_if_fail (name, NM_PLATFORM_ERROR_BUG);
+ g_return_val_if_fail (klass->macvlan_add, NM_PLATFORM_ERROR_BUG);
+
+ plerr = _link_add_check_existing (self, name, NM_LINK_TYPE_MACVLAN, out_link);
+ if (plerr != NM_PLATFORM_ERROR_SUCCESS)
+ return plerr;
+
+ _LOGD ("link: adding macvlan '%s', parent %d mode %d", name, parent, mode);
+ if (!klass->macvlan_add (self, name, parent, mode, out_link))
+ return NM_PLATFORM_ERROR_UNSPECIFIED;
+ return NM_PLATFORM_ERROR_SUCCESS;
+}
+
gboolean
nm_platform_master_set_option (NMPlatform *self, int ifindex, const char *option, const char *value)
{
diff --git a/src/platform/nm-platform.h b/src/platform/nm-platform.h
index 3c657b7055..71dd24fe3d 100644
--- a/src/platform/nm-platform.h
+++ b/src/platform/nm-platform.h
@@ -490,6 +490,8 @@ typedef struct {
int *p_key,
const char **mode);
+ gboolean (*macvlan_add) (NMPlatform *platform, const char *name, int parent, int mode, NMPlatformLink *out_link);
+
gboolean (*veth_get_properties) (NMPlatform *, int ifindex, NMPlatformVethProperties *properties);
gboolean (*tun_get_properties) (NMPlatform *, int ifindex, NMPlatformTunProperties *properties);
gboolean (*macvlan_get_properties) (NMPlatform *, int ifindex, NMPlatformMacvlanProperties *props);
@@ -673,6 +675,8 @@ gboolean nm_platform_vlan_get_info (NMPlatform *self, int ifindex, int *parent,
gboolean nm_platform_vlan_set_ingress_map (NMPlatform *self, int ifindex, int from, int to);
gboolean nm_platform_vlan_set_egress_map (NMPlatform *self, int ifindex, int from, int to);
+NMPlatformError nm_platform_macvlan_add (NMPlatform *self, const char *name, int parent, int mode, NMPlatformLink *out_link);
+
NMPlatformError nm_platform_infiniband_partition_add (NMPlatform *self, int parent, int p_key, NMPlatformLink *out_link);
gboolean nm_platform_infiniband_get_info (NMPlatform *self, int ifindex, int *parent, int *p_key, const char **mode);