mirror of
https://gitlab.freedesktop.org/NetworkManager/NetworkManager
synced 2024-10-03 06:45:26 +00:00
platform: promise that the link lnk is an immutable NMPObject and expose it
Expose internal lnk object and promise in the API that the object will not be modified (which allows the user to ref it).
This commit is contained in:
parent
f8fa4a0970
commit
4b1e1f8aab
|
@ -79,6 +79,8 @@ typedef struct _NMPlatformIP6Address NMPlatformIP6Address;
|
|||
typedef struct _NMPlatformIP6Route NMPlatformIP6Route;
|
||||
typedef struct _NMPlatformLink NMPlatformLink;
|
||||
|
||||
typedef struct _NMPObject NMPObject;
|
||||
|
||||
typedef enum {
|
||||
/* Please don't interpret type numbers outside nm-platform and use functions
|
||||
* like nm_platform_link_is_software() and nm_platform_supports_slaves().
|
||||
|
|
|
@ -27,6 +27,7 @@
|
|||
#include <linux/rtnetlink.h>
|
||||
|
||||
#include "nm-utils.h"
|
||||
#include "nmp-object.h"
|
||||
#include "NetworkManagerUtils.h"
|
||||
#include "nm-fake-platform.h"
|
||||
#include "nm-default.h"
|
||||
|
@ -74,8 +75,7 @@ typedef struct {
|
|||
NMPlatformLink link;
|
||||
|
||||
char *udi;
|
||||
NMPlatformLnkVlan lnk_vlan;
|
||||
NMPlatformLnkInfiniband lnk_infiniband;
|
||||
NMPObject *lnk;
|
||||
struct in6_addr ip6_lladdr;
|
||||
} NMFakePlatformLink;
|
||||
|
||||
|
@ -260,7 +260,7 @@ _nm_platform_link_get_by_address (NMPlatform *platform,
|
|||
return NULL;
|
||||
}
|
||||
|
||||
static gconstpointer
|
||||
static const NMPObject *
|
||||
link_get_lnk (NMPlatform *platform,
|
||||
int ifindex,
|
||||
NMLinkType link_type,
|
||||
|
@ -273,17 +273,17 @@ link_get_lnk (NMPlatform *platform,
|
|||
|
||||
NM_SET_OUT (out_link, &device->link);
|
||||
|
||||
if (link_type != device->link.type)
|
||||
if (!device->lnk)
|
||||
return NULL;
|
||||
|
||||
switch (link_type) {
|
||||
case NM_LINK_TYPE_VLAN:
|
||||
return &device->lnk_vlan;
|
||||
case NM_LINK_TYPE_INFINIBAND:
|
||||
return &device->lnk_infiniband;
|
||||
default:
|
||||
if (link_type == NM_LINK_TYPE_NONE)
|
||||
return device->lnk;
|
||||
|
||||
if ( link_type != device->link.type
|
||||
|| link_type != NMP_OBJECT_GET_CLASS (device->lnk)->lnk_link_type)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return device->lnk;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
|
@ -331,6 +331,8 @@ link_delete (NMPlatform *platform, int ifindex)
|
|||
|
||||
memcpy (&deleted_device, &device->link, sizeof (deleted_device));
|
||||
memset (&device->link, 0, sizeof (device->link));
|
||||
g_clear_pointer (&device->lnk, nmp_object_unref);
|
||||
g_clear_pointer (&device->udi, g_free);
|
||||
|
||||
/* Remove addresses and routes which belong to the deleted interface */
|
||||
for (i = 0; i < priv->ip4_addresses->len; i++) {
|
||||
|
@ -671,8 +673,10 @@ vlan_add (NMPlatform *platform, const char *name, int parent, int vlan_id, guint
|
|||
device = link_get (platform, nm_platform_link_get_ifindex (platform, name));
|
||||
|
||||
g_return_val_if_fail (device, FALSE);
|
||||
g_return_val_if_fail (!device->lnk, FALSE);
|
||||
|
||||
device->lnk_vlan.id = vlan_id;
|
||||
device->lnk = nmp_object_new (NMP_OBJECT_TYPE_LNK_VLAN, NULL);
|
||||
device->lnk->lnk_vlan.id = vlan_id;
|
||||
device->link.parent = parent;
|
||||
|
||||
if (out_link)
|
||||
|
@ -707,9 +711,11 @@ infiniband_partition_add (NMPlatform *platform, int parent, int p_key, NMPlatfor
|
|||
|
||||
device = link_get (platform, nm_platform_link_get_ifindex (platform, name));
|
||||
g_return_val_if_fail (device, FALSE);
|
||||
g_return_val_if_fail (!device->lnk, FALSE);
|
||||
|
||||
device->lnk_infiniband.p_key = p_key;
|
||||
device->lnk_infiniband.mode = "datagram";
|
||||
device->lnk = nmp_object_new (NMP_OBJECT_TYPE_LNK_VLAN, NULL);
|
||||
device->lnk->lnk_infiniband.p_key = p_key;
|
||||
device->lnk->lnk_infiniband.mode = "datagram";
|
||||
device->link.parent = parent;
|
||||
|
||||
return TRUE;
|
||||
|
@ -1381,6 +1387,7 @@ nm_fake_platform_finalize (GObject *object)
|
|||
NMFakePlatformLink *device = &g_array_index (priv->links, NMFakePlatformLink, i);
|
||||
|
||||
g_free (device->udi);
|
||||
g_clear_pointer (&device->lnk, nmp_object_unref);
|
||||
}
|
||||
g_array_unref (priv->links);
|
||||
g_array_unref (priv->ip4_addresses);
|
||||
|
|
|
@ -3252,7 +3252,7 @@ _nm_platform_link_get_by_address (NMPlatform *platform,
|
|||
|
||||
/*****************************************************************************/
|
||||
|
||||
static gconstpointer
|
||||
static const NMPObject *
|
||||
link_get_lnk (NMPlatform *platform, int ifindex, NMLinkType link_type, const NMPlatformLink **out_link)
|
||||
{
|
||||
const NMPObject *obj = cache_lookup_link (platform, ifindex);
|
||||
|
@ -3262,34 +3262,14 @@ link_get_lnk (NMPlatform *platform, int ifindex, NMLinkType link_type, const NMP
|
|||
|
||||
NM_SET_OUT (out_link, &obj->link);
|
||||
|
||||
if (link_type != obj->link.type)
|
||||
if (!obj->_link.netlink.lnk)
|
||||
return NULL;
|
||||
if ( link_type != NM_LINK_TYPE_NONE
|
||||
&& ( link_type != obj->link.type
|
||||
|| link_type != NMP_OBJECT_GET_CLASS (obj->_link.netlink.lnk)->lnk_link_type))
|
||||
return NULL;
|
||||
|
||||
switch (link_type) {
|
||||
case NM_LINK_TYPE_GRE:
|
||||
if (NMP_OBJECT_GET_TYPE (obj->_link.netlink.lnk) == NMP_OBJECT_TYPE_LNK_GRE)
|
||||
return &obj->_link.netlink.lnk->lnk_gre;
|
||||
break;
|
||||
case NM_LINK_TYPE_INFINIBAND:
|
||||
if (NMP_OBJECT_GET_TYPE (obj->_link.netlink.lnk) == NMP_OBJECT_TYPE_LNK_INFINIBAND)
|
||||
return &obj->_link.netlink.lnk->lnk_infiniband;
|
||||
break;
|
||||
case NM_LINK_TYPE_MACVLAN:
|
||||
if (NMP_OBJECT_GET_TYPE (obj->_link.netlink.lnk) == NMP_OBJECT_TYPE_LNK_MACVLAN)
|
||||
return &obj->_link.netlink.lnk->lnk_macvlan;
|
||||
break;
|
||||
case NM_LINK_TYPE_VLAN:
|
||||
if (NMP_OBJECT_GET_TYPE (obj->_link.netlink.lnk) == NMP_OBJECT_TYPE_LNK_VLAN)
|
||||
return &obj->_link.netlink.lnk->lnk_vlan;
|
||||
break;
|
||||
case NM_LINK_TYPE_VXLAN:
|
||||
if (NMP_OBJECT_GET_TYPE (obj->_link.netlink.lnk) == NMP_OBJECT_TYPE_LNK_VXLAN)
|
||||
return &obj->_link.netlink.lnk->lnk_vxlan;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
return NULL;
|
||||
return obj->_link.netlink.lnk;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
|
|
@ -36,6 +36,7 @@
|
|||
#include "nm-utils.h"
|
||||
#include "nm-platform.h"
|
||||
#include "nm-platform-utils.h"
|
||||
#include "nmp-object.h"
|
||||
#include "NetworkManagerUtils.h"
|
||||
#include "nm-default.h"
|
||||
#include "nm-enum-types.h"
|
||||
|
@ -1369,7 +1370,29 @@ nm_platform_link_get_master (NMPlatform *self, int slave)
|
|||
|
||||
/*****************************************************************************/
|
||||
|
||||
gconstpointer
|
||||
/**
|
||||
* nm_platform_link_get_lnk:
|
||||
* @self: the platform instance
|
||||
* @ifindex: the link ifindex to lookup
|
||||
* @link_type: filter by link-type.
|
||||
* @out_link: (allow-none): returns the platform link instance
|
||||
*
|
||||
* If the function returns %NULL, that could mean that no such ifindex
|
||||
* exists, of that the link has no lnk data. You can find that out
|
||||
* by checking @out_link. @out_link will always be set if a link
|
||||
* with @ifindex exists.
|
||||
*
|
||||
* If @link_type is %NM_LINK_TYPE_NONE, the function returns the lnk
|
||||
* object if it is present. If you set link-type, you can be sure
|
||||
* that only a link type of the matching type is returned (or %NULL).
|
||||
*
|
||||
* Returns: the internal link lnk object. The returned object
|
||||
* is owned by the platform cache and must not be modified. Note
|
||||
* however, that the object is guaranteed to be immutable, so
|
||||
* you can savely take a reference and keep it for yourself
|
||||
* (but don't modify it).
|
||||
*/
|
||||
const NMPObject *
|
||||
nm_platform_link_get_lnk (NMPlatform *self, int ifindex, NMLinkType link_type, const NMPlatformLink **out_link)
|
||||
{
|
||||
_CHECK_SELF (self, klass, FALSE);
|
||||
|
@ -1381,34 +1404,43 @@ nm_platform_link_get_lnk (NMPlatform *self, int ifindex, NMLinkType link_type, c
|
|||
return klass->link_get_lnk (self, ifindex, link_type, out_link);
|
||||
}
|
||||
|
||||
static gconstpointer
|
||||
_link_get_lnk (NMPlatform *self, int ifindex, NMLinkType link_type, const NMPlatformLink **out_link)
|
||||
{
|
||||
const NMPObject *lnk;
|
||||
|
||||
lnk = nm_platform_link_get_lnk (self, ifindex, link_type, out_link);
|
||||
return lnk ? &lnk->object : NULL;
|
||||
}
|
||||
|
||||
const NMPlatformLnkGre *
|
||||
nm_platform_link_get_lnk_gre (NMPlatform *self, int ifindex, const NMPlatformLink **out_link)
|
||||
{
|
||||
return nm_platform_link_get_lnk (self, ifindex, NM_LINK_TYPE_GRE, out_link);
|
||||
return _link_get_lnk (self, ifindex, NM_LINK_TYPE_GRE, out_link);
|
||||
}
|
||||
|
||||
const NMPlatformLnkInfiniband *
|
||||
nm_platform_link_get_lnk_infiniband (NMPlatform *self, int ifindex, const NMPlatformLink **out_link)
|
||||
{
|
||||
return nm_platform_link_get_lnk (self, ifindex, NM_LINK_TYPE_INFINIBAND, out_link);
|
||||
return _link_get_lnk (self, ifindex, NM_LINK_TYPE_INFINIBAND, out_link);
|
||||
}
|
||||
|
||||
const NMPlatformLnkMacvlan *
|
||||
nm_platform_link_get_lnk_macvlan (NMPlatform *self, int ifindex, const NMPlatformLink **out_link)
|
||||
{
|
||||
return nm_platform_link_get_lnk (self, ifindex, NM_LINK_TYPE_MACVLAN, out_link);
|
||||
return _link_get_lnk (self, ifindex, NM_LINK_TYPE_MACVLAN, out_link);
|
||||
}
|
||||
|
||||
const NMPlatformLnkVlan *
|
||||
nm_platform_link_get_lnk_vlan (NMPlatform *self, int ifindex, const NMPlatformLink **out_link)
|
||||
{
|
||||
return nm_platform_link_get_lnk (self, ifindex, NM_LINK_TYPE_VLAN, out_link);
|
||||
return _link_get_lnk (self, ifindex, NM_LINK_TYPE_VLAN, out_link);
|
||||
}
|
||||
|
||||
const NMPlatformLnkVxlan *
|
||||
nm_platform_link_get_lnk_vxlan (NMPlatform *self, int ifindex, const NMPlatformLink **out_link)
|
||||
{
|
||||
return nm_platform_link_get_lnk (self, ifindex, NM_LINK_TYPE_VXLAN, out_link);
|
||||
return _link_get_lnk (self, ifindex, NM_LINK_TYPE_VXLAN, out_link);
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
|
|
@ -457,7 +457,7 @@ typedef struct {
|
|||
const NMPlatformLink *(*link_get_by_ifname) (NMPlatform *platform, const char *ifname);
|
||||
const NMPlatformLink *(*link_get_by_address) (NMPlatform *platform, gconstpointer address, size_t length);
|
||||
|
||||
gconstpointer (*link_get_lnk) (NMPlatform *platform, int ifindex, NMLinkType link_type, const NMPlatformLink **out_link);
|
||||
const NMPObject *(*link_get_lnk) (NMPlatform *platform, int ifindex, NMLinkType link_type, const NMPlatformLink **out_link);
|
||||
|
||||
GArray *(*link_get_all) (NMPlatform *);
|
||||
gboolean (*link_add) (NMPlatform *,
|
||||
|
@ -696,7 +696,7 @@ char *nm_platform_master_get_option (NMPlatform *self, int ifindex, const char *
|
|||
gboolean nm_platform_slave_set_option (NMPlatform *self, int ifindex, const char *option, const char *value);
|
||||
char *nm_platform_slave_get_option (NMPlatform *self, int ifindex, const char *option);
|
||||
|
||||
gconstpointer nm_platform_link_get_lnk (NMPlatform *self, int ifindex, NMLinkType link_type, const NMPlatformLink **out_link);
|
||||
const NMPObject *nm_platform_link_get_lnk (NMPlatform *self, int ifindex, NMLinkType link_type, const NMPlatformLink **out_link);
|
||||
const NMPlatformLnkGre *nm_platform_link_get_lnk_gre (NMPlatform *self, int ifindex, const NMPlatformLink **out_link);
|
||||
const NMPlatformLnkInfiniband *nm_platform_link_get_lnk_infiniband (NMPlatform *self, int ifindex, const NMPlatformLink **out_link);
|
||||
const NMPlatformLnkMacvlan *nm_platform_link_get_lnk_macvlan (NMPlatform *self, int ifindex, const NMPlatformLink **out_link);
|
||||
|
|
|
@ -1891,6 +1891,7 @@ const NMPClass _nmp_classes[NMP_OBJECT_TYPE_MAX] = {
|
|||
.sizeof_data = sizeof (NMPObjectLnkGre),
|
||||
.sizeof_public = sizeof (NMPlatformLnkGre),
|
||||
.obj_type_name = "gre",
|
||||
.lnk_link_type = NM_LINK_TYPE_GRE,
|
||||
.cmd_plobj_to_string = (const char *(*) (const NMPlatformObject *obj, char *buf, gsize len)) nm_platform_lnk_gre_to_string,
|
||||
.cmd_plobj_cmp = (int (*) (const NMPlatformObject *obj1, const NMPlatformObject *obj2)) nm_platform_lnk_gre_cmp,
|
||||
},
|
||||
|
@ -1899,6 +1900,7 @@ const NMPClass _nmp_classes[NMP_OBJECT_TYPE_MAX] = {
|
|||
.sizeof_data = sizeof (NMPObjectLnkInfiniband),
|
||||
.sizeof_public = sizeof (NMPlatformLnkInfiniband),
|
||||
.obj_type_name = "infiniband",
|
||||
.lnk_link_type = NM_LINK_TYPE_INFINIBAND,
|
||||
.cmd_plobj_to_string = (const char *(*) (const NMPlatformObject *obj, char *buf, gsize len)) nm_platform_lnk_infiniband_to_string,
|
||||
.cmd_plobj_cmp = (int (*) (const NMPlatformObject *obj1, const NMPlatformObject *obj2)) nm_platform_lnk_infiniband_cmp,
|
||||
},
|
||||
|
@ -1907,6 +1909,7 @@ const NMPClass _nmp_classes[NMP_OBJECT_TYPE_MAX] = {
|
|||
.sizeof_data = sizeof (NMPObjectLnkMacvlan),
|
||||
.sizeof_public = sizeof (NMPlatformLnkMacvlan),
|
||||
.obj_type_name = "macvlan",
|
||||
.lnk_link_type = NM_LINK_TYPE_MACVLAN,
|
||||
.cmd_plobj_to_string = (const char *(*) (const NMPlatformObject *obj, char *buf, gsize len)) nm_platform_lnk_macvlan_to_string,
|
||||
.cmd_plobj_cmp = (int (*) (const NMPlatformObject *obj1, const NMPlatformObject *obj2)) nm_platform_lnk_macvlan_cmp,
|
||||
},
|
||||
|
@ -1915,6 +1918,7 @@ const NMPClass _nmp_classes[NMP_OBJECT_TYPE_MAX] = {
|
|||
.sizeof_data = sizeof (NMPObjectLnkVlan),
|
||||
.sizeof_public = sizeof (NMPlatformLnkVlan),
|
||||
.obj_type_name = "vlan",
|
||||
.lnk_link_type = NM_LINK_TYPE_VLAN,
|
||||
.cmd_plobj_to_string = (const char *(*) (const NMPlatformObject *obj, char *buf, gsize len)) nm_platform_lnk_vlan_to_string,
|
||||
.cmd_plobj_cmp = (int (*) (const NMPlatformObject *obj1, const NMPlatformObject *obj2)) nm_platform_lnk_vlan_cmp,
|
||||
},
|
||||
|
@ -1923,6 +1927,7 @@ const NMPClass _nmp_classes[NMP_OBJECT_TYPE_MAX] = {
|
|||
.sizeof_data = sizeof (NMPObjectLnkVxlan),
|
||||
.sizeof_public = sizeof (NMPlatformLnkVxlan),
|
||||
.obj_type_name = "vxlan",
|
||||
.lnk_link_type = NM_LINK_TYPE_VXLAN,
|
||||
.cmd_plobj_to_string = (const char *(*) (const NMPlatformObject *obj, char *buf, gsize len)) nm_platform_lnk_vxlan_to_string,
|
||||
.cmd_plobj_cmp = (int (*) (const NMPlatformObject *obj1, const NMPlatformObject *obj2)) nm_platform_lnk_vxlan_cmp,
|
||||
},
|
||||
|
|
|
@ -119,6 +119,9 @@ typedef struct {
|
|||
const char *obj_type_name;
|
||||
const char *signal_type;
|
||||
|
||||
/* Only for NMPObjectLnk* types. */
|
||||
NMLinkType lnk_link_type;
|
||||
|
||||
/* returns %FALSE, if the obj type would never have an entry for index type @id_type. If @obj has an index,
|
||||
* initialize @id and set @out_id to it. Otherwise, @out_id is NULL. */
|
||||
gboolean (*cmd_obj_init_cache_id) (const NMPObject *obj, NMPCacheIdType id_type, NMPCacheId *id, const NMPCacheId **out_id);
|
||||
|
|
|
@ -1,5 +1,7 @@
|
|||
#include "config.h"
|
||||
|
||||
#include "nmp-object.h"
|
||||
|
||||
#include "test-common.h"
|
||||
#include "nm-test-utils.h"
|
||||
|
||||
|
@ -640,7 +642,7 @@ test_software_detect (gconstpointer user_data)
|
|||
const TestAddSoftwareDetectData *test_data = user_data;
|
||||
int ifindex, ifindex_parent;
|
||||
const NMPlatformLink *plink;
|
||||
gconstpointer plnk_void;
|
||||
const NMPObject *lnk;
|
||||
guint i_step;
|
||||
int exit_code;
|
||||
|
||||
|
@ -708,15 +710,16 @@ test_software_detect (gconstpointer user_data)
|
|||
nmtstp_link_set_updown (-1, ifindex, set_up);
|
||||
}
|
||||
|
||||
plnk_void = nm_platform_link_get_lnk (NM_PLATFORM_GET, ifindex, test_data->link_type, &plink);
|
||||
lnk = nm_platform_link_get_lnk (NM_PLATFORM_GET, ifindex, test_data->link_type, &plink);
|
||||
g_assert (plink);
|
||||
g_assert_cmpint (plink->ifindex, ==, ifindex);
|
||||
g_assert (plnk_void);
|
||||
g_assert (lnk);
|
||||
|
||||
switch (test_data->link_type) {
|
||||
case NM_LINK_TYPE_GRE: {
|
||||
const NMPlatformLnkGre *plnk = plnk_void;
|
||||
const NMPlatformLnkGre *plnk = &lnk->lnk_gre;
|
||||
|
||||
g_assert (plnk == nm_platform_link_get_lnk_gre (NM_PLATFORM_GET, ifindex, NULL));
|
||||
g_assert_cmpint (plnk->parent_ifindex, ==, 0);
|
||||
g_assert_cmpint (plnk->input_flags, ==, 0);
|
||||
g_assert_cmpint (plnk->output_flags, ==, 0);
|
||||
|
@ -730,21 +733,24 @@ test_software_detect (gconstpointer user_data)
|
|||
break;
|
||||
}
|
||||
case NM_LINK_TYPE_MACVLAN: {
|
||||
const NMPlatformLnkMacvlan *plnk = plnk_void;
|
||||
const NMPlatformLnkMacvlan *plnk = &lnk->lnk_macvlan;
|
||||
|
||||
g_assert (plnk == nm_platform_link_get_lnk_macvlan (NM_PLATFORM_GET, ifindex, NULL));
|
||||
g_assert_cmpint (plnk->no_promisc, ==, FALSE);
|
||||
g_assert_cmpstr (plnk->mode, ==, "vepa");
|
||||
break;
|
||||
}
|
||||
case NM_LINK_TYPE_VLAN: {
|
||||
const NMPlatformLnkVlan *plnk = plnk_void;
|
||||
const NMPlatformLnkVlan *plnk = &lnk->lnk_vlan;
|
||||
|
||||
g_assert (plnk == nm_platform_link_get_lnk_vlan (NM_PLATFORM_GET, ifindex, NULL));
|
||||
g_assert_cmpint (plnk->id, ==, 1242);
|
||||
break;
|
||||
}
|
||||
case NM_LINK_TYPE_VXLAN: {
|
||||
const NMPlatformLnkVxlan *plnk = plnk_void;
|
||||
const NMPlatformLnkVxlan *plnk = &lnk->lnk_vxlan;
|
||||
|
||||
g_assert (plnk == nm_platform_link_get_lnk_vxlan (NM_PLATFORM_GET, ifindex, NULL));
|
||||
g_assert_cmpint (plnk->parent_ifindex, !=, 0);
|
||||
g_assert_cmpint (plnk->tos, ==, 0);
|
||||
g_assert_cmpint (plnk->ttl, ==, 0);
|
||||
|
|
Loading…
Reference in a new issue