mirror of
https://gitlab.freedesktop.org/NetworkManager/NetworkManager
synced 2024-09-16 06:40:41 +00:00
l3cfg: merge branch 'th/l3cfg-9'
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/626
This commit is contained in:
commit
86f2ea66f5
2
NEWS
2
NEWS
|
@ -15,6 +15,8 @@ USE AT YOUR OWN RISK. NOT RECOMMENDED FOR PRODUCTION USE!
|
|||
setting and runtime detection.
|
||||
"resolvconf" and "netconfig" are only considered iff NetworkManager
|
||||
was built with the respective options enabled.
|
||||
* The long deprecated D-Bus property "Ip4Address" on "org.freedesktop.NetworkManager.Device"
|
||||
interface is not defunct and always returns zero.
|
||||
|
||||
=============================================
|
||||
NetworkManager-1.26
|
||||
|
|
|
@ -100,7 +100,7 @@
|
|||
Ip4Address:
|
||||
|
||||
DEPRECATED; use the 'Addresses' property of the 'Ip4Config' object
|
||||
instead.
|
||||
instead. This property always returns 0.0.0.0 (numeric 0) as address.
|
||||
-->
|
||||
<property name="Ip4Address" type="u" access="read"/>
|
||||
|
||||
|
|
|
@ -4878,7 +4878,7 @@ nm_utils_is_uuid (const char *str)
|
|||
return FALSE;
|
||||
}
|
||||
|
||||
static char _nm_utils_inet_ntop_buffer[NM_UTILS_INET_ADDRSTRLEN];
|
||||
static _nm_thread_local char _nm_utils_inet_ntop_buffer[NM_UTILS_INET_ADDRSTRLEN];
|
||||
|
||||
/**
|
||||
* nm_utils_inet4_ntop: (skip)
|
||||
|
@ -4888,8 +4888,9 @@ static char _nm_utils_inet_ntop_buffer[NM_UTILS_INET_ADDRSTRLEN];
|
|||
* characters. If set to %NULL, it will return a pointer to an internal, static
|
||||
* buffer (shared with nm_utils_inet6_ntop()). Beware, that the internal
|
||||
* buffer will be overwritten with ever new call of nm_utils_inet4_ntop() or
|
||||
* nm_utils_inet6_ntop() that does not provide its own @dst buffer. Also,
|
||||
* using the internal buffer is not thread safe. When in doubt, pass your own
|
||||
* nm_utils_inet6_ntop() that does not provide its own @dst buffer. Since
|
||||
* 1.28, the internal buffer is thread local and thus thread safe. Before
|
||||
* it was not thread safe. When in doubt, pass your own
|
||||
* @dst buffer to avoid these issues.
|
||||
*
|
||||
* Wrapper for inet_ntop.
|
||||
|
@ -4916,8 +4917,9 @@ nm_utils_inet4_ntop (in_addr_t inaddr, char *dst)
|
|||
* characters. If set to %NULL, it will return a pointer to an internal, static
|
||||
* buffer (shared with nm_utils_inet4_ntop()). Beware, that the internal
|
||||
* buffer will be overwritten with ever new call of nm_utils_inet4_ntop() or
|
||||
* nm_utils_inet6_ntop() that does not provide its own @dst buffer. Also,
|
||||
* using the internal buffer is not thread safe. When in doubt, pass your own
|
||||
* nm_utils_inet6_ntop() that does not provide its own @dst buffer. Since
|
||||
* 1.28, the internal buffer is thread local and thus thread safe. Before
|
||||
* it was not thread safe. When in doubt, pass your own
|
||||
* @dst buffer to avoid these issues.
|
||||
*
|
||||
* Wrapper for inet_ntop.
|
||||
|
|
|
@ -405,6 +405,34 @@ nm_utils_gbytes_to_variant_ay (GBytes *bytes)
|
|||
|
||||
/*****************************************************************************/
|
||||
|
||||
#define _variant_singleton_get(create_variant) \
|
||||
({ \
|
||||
static GVariant *_singleton = NULL; \
|
||||
GVariant *_v; \
|
||||
\
|
||||
again: \
|
||||
_v = g_atomic_pointer_get (&_singleton); \
|
||||
if (G_UNLIKELY (!_v)) { \
|
||||
_v = (create_variant); \
|
||||
nm_assert (_v); \
|
||||
nm_assert (g_variant_is_floating (_v)); \
|
||||
g_variant_ref_sink (_v); \
|
||||
if (!g_atomic_pointer_compare_and_exchange (&_singleton, NULL, _v)) { \
|
||||
g_variant_unref (_v); \
|
||||
goto again; \
|
||||
} \
|
||||
} \
|
||||
_v; \
|
||||
})
|
||||
|
||||
GVariant *
|
||||
nm_g_variant_singleton_u_0 (void)
|
||||
{
|
||||
return _variant_singleton_get (g_variant_new_uint32 (0));
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
||||
/* Convert a hash table with "char *" keys and values to an "a{ss}" GVariant.
|
||||
* The keys will be sorted asciibetically.
|
||||
* Returns a floating reference.
|
||||
|
|
|
@ -1249,6 +1249,8 @@ char *nm_utils_str_utf8safe_unescape_cp (const char *str, NMUtilsStrUtf8SafeFlag
|
|||
|
||||
char *nm_utils_str_utf8safe_escape_take (char *str, NMUtilsStrUtf8SafeFlags flags);
|
||||
|
||||
GVariant *nm_g_variant_singleton_u_0 (void);
|
||||
|
||||
static inline void
|
||||
nm_g_variant_unref_floating (GVariant *var)
|
||||
{
|
||||
|
|
|
@ -377,8 +377,6 @@ typedef struct _NMDevicePrivate {
|
|||
|
||||
GCancellable *deactivating_cancellable;
|
||||
|
||||
guint32 ip4_address;
|
||||
|
||||
NMActRequest * queued_act_request;
|
||||
bool queued_act_request_is_waiting_for_carrier:1;
|
||||
NMDBusTrackObjPath act_request;
|
||||
|
@ -1179,7 +1177,7 @@ out_good:
|
|||
return duid_out;
|
||||
}
|
||||
|
||||
static gint32
|
||||
static guint32
|
||||
_prop_get_ipv6_ra_timeout (NMDevice *self)
|
||||
{
|
||||
NMConnection *connection;
|
||||
|
@ -1191,9 +1189,9 @@ _prop_get_ipv6_ra_timeout (NMDevice *self)
|
|||
connection = nm_device_get_applied_connection (self);
|
||||
|
||||
timeout = nm_setting_ip6_config_get_ra_timeout (NM_SETTING_IP6_CONFIG (nm_connection_get_setting_ip6_config (connection)));
|
||||
nm_assert (timeout >= 0);
|
||||
if (timeout)
|
||||
if (timeout > 0)
|
||||
return timeout;
|
||||
nm_assert (timeout == 0);
|
||||
|
||||
return nm_config_data_get_connection_default_int64 (NM_CONFIG_GET_DATA,
|
||||
NM_CON_DEFAULT ("ipv6.ra-timeout"),
|
||||
|
@ -10981,15 +10979,6 @@ addrconf6_start_with_link_ready (NMDevice *self)
|
|||
return;
|
||||
}
|
||||
|
||||
static NMNDiscNodeType
|
||||
ndisc_node_type (NMDevice *self)
|
||||
{
|
||||
if (nm_streq (nm_device_get_effective_ip_config_method (self, AF_INET6),
|
||||
NM_SETTING_IP4_CONFIG_METHOD_SHARED))
|
||||
return NM_NDISC_NODE_TYPE_ROUTER;
|
||||
return NM_NDISC_NODE_TYPE_HOST;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
addrconf6_start (NMDevice *self, NMSettingIP6ConfigPrivacy use_tempaddr)
|
||||
{
|
||||
|
@ -10999,6 +10988,12 @@ addrconf6_start (NMDevice *self, NMSettingIP6ConfigPrivacy use_tempaddr)
|
|||
GError *error = NULL;
|
||||
NMUtilsStableType stable_type;
|
||||
const char *stable_id;
|
||||
NMNDiscNodeType node_type;
|
||||
int max_addresses;
|
||||
int router_solicitations;
|
||||
int router_solicitation_interval;
|
||||
guint32 ra_timeout;
|
||||
guint32 default_ra_timeout;
|
||||
|
||||
connection = nm_device_get_applied_connection (self);
|
||||
g_assert (connection);
|
||||
|
@ -11012,6 +11007,27 @@ addrconf6_start (NMDevice *self, NMSettingIP6ConfigPrivacy use_tempaddr)
|
|||
s_ip6 = NM_SETTING_IP6_CONFIG (nm_connection_get_setting_ip6_config (connection));
|
||||
g_assert (s_ip6);
|
||||
|
||||
if (nm_streq (nm_device_get_effective_ip_config_method (self, AF_INET6),
|
||||
NM_SETTING_IP4_CONFIG_METHOD_SHARED))
|
||||
node_type = NM_NDISC_NODE_TYPE_ROUTER;
|
||||
else
|
||||
node_type = NM_NDISC_NODE_TYPE_HOST;
|
||||
|
||||
nm_lndp_ndisc_get_sysctl (nm_device_get_platform (self),
|
||||
nm_device_get_ip_iface (self),
|
||||
&max_addresses,
|
||||
&router_solicitations,
|
||||
&router_solicitation_interval,
|
||||
&default_ra_timeout);
|
||||
|
||||
if (node_type == NM_NDISC_NODE_TYPE_ROUTER)
|
||||
ra_timeout = 0u;
|
||||
else {
|
||||
ra_timeout = _prop_get_ipv6_ra_timeout (self);
|
||||
if (ra_timeout == 0u)
|
||||
ra_timeout = default_ra_timeout;
|
||||
}
|
||||
|
||||
stable_id = _prop_get_connection_stable_id (self, connection, &stable_type);
|
||||
priv->ndisc = nm_lndp_ndisc_new (nm_device_get_platform (self),
|
||||
nm_device_get_ip_ifindex (self),
|
||||
|
@ -11019,8 +11035,11 @@ addrconf6_start (NMDevice *self, NMSettingIP6ConfigPrivacy use_tempaddr)
|
|||
stable_type,
|
||||
stable_id,
|
||||
nm_setting_ip6_config_get_addr_gen_mode (s_ip6),
|
||||
ndisc_node_type (self),
|
||||
_prop_get_ipv6_ra_timeout (self),
|
||||
node_type,
|
||||
max_addresses,
|
||||
router_solicitations,
|
||||
router_solicitation_interval,
|
||||
ra_timeout,
|
||||
&error);
|
||||
if (!priv->ndisc) {
|
||||
_LOGE (LOGD_IP6, "addrconf6: failed to start neighbor discovery: %s", error->message);
|
||||
|
@ -11059,7 +11078,10 @@ addrconf6_cleanup (NMDevice *self)
|
|||
applied_config_clear (&priv->ac_ip6_config);
|
||||
nm_clear_pointer (&priv->rt6_temporary_not_available, g_hash_table_unref);
|
||||
nm_clear_g_source (&priv->rt6_temporary_not_available_id);
|
||||
if (priv->ndisc) {
|
||||
nm_ndisc_stop (priv->ndisc);
|
||||
g_clear_object (&priv->ndisc);
|
||||
}
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
@ -12276,24 +12298,6 @@ dnsmasq_cleanup (NMDevice *self)
|
|||
priv->dnsmasq_manager = NULL;
|
||||
}
|
||||
|
||||
static void
|
||||
_update_ip4_address (NMDevice *self)
|
||||
{
|
||||
NMDevicePrivate *priv = NM_DEVICE_GET_PRIVATE (self);
|
||||
const NMPlatformIP4Address *address;
|
||||
|
||||
g_return_if_fail (NM_IS_DEVICE (self));
|
||||
|
||||
if ( priv->ip_config_4
|
||||
&& ip_config_valid (priv->state)
|
||||
&& (address = nm_ip4_config_get_first_address (priv->ip_config_4))) {
|
||||
if (address->address != priv->ip4_address) {
|
||||
priv->ip4_address = address->address;
|
||||
_notify (self, PROP_IP4_ADDRESS);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_device_is_nm_owned (NMDevice *self)
|
||||
{
|
||||
|
@ -13725,9 +13729,6 @@ nm_device_set_ip_config (NMDevice *self,
|
|||
|
||||
if (has_changes) {
|
||||
|
||||
if (IS_IPv4)
|
||||
_update_ip4_address (self);
|
||||
|
||||
if (old_config != priv->ip_config_x[IS_IPv4])
|
||||
_notify (self, IS_IPv4 ? PROP_IP4_CONFIG : PROP_IP6_CONFIG);
|
||||
|
||||
|
@ -14252,8 +14253,6 @@ nm_device_bring_up (NMDevice *self, gboolean block, gboolean *no_firmware)
|
|||
/* Can only get HW address of some devices when they are up */
|
||||
nm_device_update_hw_address (self);
|
||||
|
||||
_update_ip4_address (self);
|
||||
|
||||
/* when the link comes up, we must restore IP configuration if necessary. */
|
||||
if (priv->ip_state_4 == NM_DEVICE_IP_STATE_DONE) {
|
||||
if (!ip_config_merge_and_apply (self, AF_INET, TRUE))
|
||||
|
@ -15975,12 +15974,6 @@ _cleanup_generic_post (NMDevice *self, CleanupType cleanup_type)
|
|||
act_request_set (self, NULL);
|
||||
}
|
||||
|
||||
/* Clear legacy IPv4 address property */
|
||||
if (priv->ip4_address) {
|
||||
priv->ip4_address = 0;
|
||||
_notify (self, PROP_IP4_ADDRESS);
|
||||
}
|
||||
|
||||
if (cleanup_type == CLEANUP_TYPE_DECONFIGURE) {
|
||||
/* Check if the device was deactivated, and if so, delete_link.
|
||||
* Don't call delete_link synchronously because we are currently
|
||||
|
@ -17794,7 +17787,7 @@ get_property (GObject *object, guint prop_id,
|
|||
g_value_set_uint (value, (priv->capabilities & ~NM_DEVICE_CAP_INTERNAL_MASK));
|
||||
break;
|
||||
case PROP_IP4_ADDRESS:
|
||||
g_value_set_uint (value, priv->ip4_address);
|
||||
g_value_set_variant (value, nm_g_variant_singleton_u_0 ());
|
||||
break;
|
||||
case PROP_CARRIER:
|
||||
g_value_set_boolean (value, priv->carrier);
|
||||
|
@ -18507,8 +18500,9 @@ nm_device_class_init (NMDeviceClass *klass)
|
|||
G_PARAM_READABLE |
|
||||
G_PARAM_STATIC_STRINGS);
|
||||
obj_properties[PROP_IP4_ADDRESS] =
|
||||
g_param_spec_uint (NM_DEVICE_IP4_ADDRESS, "", "",
|
||||
0, G_MAXUINT32, 0, /* FIXME */
|
||||
g_param_spec_variant (NM_DEVICE_IP4_ADDRESS, "", "",
|
||||
G_VARIANT_TYPE_UINT32,
|
||||
NULL,
|
||||
G_PARAM_READABLE |
|
||||
G_PARAM_STATIC_STRINGS);
|
||||
obj_properties[PROP_IP4_CONFIG] =
|
||||
|
|
|
@ -337,6 +337,14 @@ start (NMNDisc *ndisc)
|
|||
priv->receive_ra_id = g_timeout_add_seconds (ra->when, receive_ra, ndisc);
|
||||
}
|
||||
|
||||
static void
|
||||
stop (NMNDisc *ndisc)
|
||||
{
|
||||
NMFakeNDiscPrivate *priv = NM_FAKE_NDISC_GET_PRIVATE (ndisc);
|
||||
|
||||
nm_clear_g_source (&priv->receive_ra_id);
|
||||
}
|
||||
|
||||
void
|
||||
nm_fake_ndisc_emit_new_ras (NMFakeNDisc *self)
|
||||
{
|
||||
|
@ -360,6 +368,10 @@ nm_fake_ndisc_new (int ifindex, const char *ifname)
|
|||
NM_NDISC_NODE_TYPE, (int) NM_NDISC_NODE_TYPE_HOST,
|
||||
NM_NDISC_STABLE_TYPE, (int) NM_UTILS_STABLE_TYPE_UUID,
|
||||
NM_NDISC_NETWORK_ID, "fake",
|
||||
NM_NDISC_MAX_ADDRESSES, NM_NDISC_MAX_ADDRESSES_DEFAULT,
|
||||
NM_NDISC_ROUTER_SOLICITATIONS, NM_NDISC_ROUTER_SOLICITATIONS_DEFAULT,
|
||||
NM_NDISC_ROUTER_SOLICITATION_INTERVAL, NM_NDISC_ROUTER_SOLICITATION_INTERVAL_DEFAULT,
|
||||
NM_NDISC_RA_TIMEOUT, 30u,
|
||||
NULL);
|
||||
}
|
||||
|
||||
|
@ -385,6 +397,7 @@ nm_fake_ndisc_class_init (NMFakeNDiscClass *klass)
|
|||
object_class->dispose = dispose;
|
||||
|
||||
ndisc_class->start = start;
|
||||
ndisc_class->stop = stop;
|
||||
ndisc_class->send_rs = send_rs;
|
||||
|
||||
signals[RS_SENT] =
|
||||
|
|
|
@ -535,6 +535,36 @@ start (NMNDisc *ndisc)
|
|||
}
|
||||
}
|
||||
|
||||
static void
|
||||
_cleanup (NMNDisc *ndisc)
|
||||
{
|
||||
NMLndpNDiscPrivate *priv = NM_LNDP_NDISC_GET_PRIVATE (ndisc);
|
||||
|
||||
nm_clear_g_source_inst (&priv->event_source);
|
||||
|
||||
if (priv->ndp) {
|
||||
switch (nm_ndisc_get_node_type (ndisc)) {
|
||||
case NM_NDISC_NODE_TYPE_HOST:
|
||||
ndp_msgrcv_handler_unregister (priv->ndp, receive_ra, NDP_MSG_RA, nm_ndisc_get_ifindex (ndisc), ndisc);
|
||||
break;
|
||||
case NM_NDISC_NODE_TYPE_ROUTER:
|
||||
ndp_msgrcv_handler_unregister (priv->ndp, receive_rs, NDP_MSG_RS, nm_ndisc_get_ifindex (ndisc), ndisc);
|
||||
break;
|
||||
default:
|
||||
nm_assert_not_reached ();
|
||||
break;
|
||||
}
|
||||
ndp_close (priv->ndp);
|
||||
priv->ndp = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
stop (NMNDisc *ndisc)
|
||||
{
|
||||
_cleanup (ndisc);
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
||||
static int
|
||||
|
@ -550,6 +580,51 @@ ipv6_sysctl_get (NMPlatform *platform, const char *ifname, const char *property,
|
|||
defval);
|
||||
}
|
||||
|
||||
void
|
||||
nm_lndp_ndisc_get_sysctl (NMPlatform *platform,
|
||||
const char *ifname,
|
||||
int *out_max_addresses,
|
||||
int *out_router_solicitations,
|
||||
int *out_router_solicitation_interval,
|
||||
guint32 *out_default_ra_timeout)
|
||||
{
|
||||
int router_solicitation_interval = 0;
|
||||
int router_solicitations = 0;
|
||||
|
||||
if (out_max_addresses) {
|
||||
*out_max_addresses = ipv6_sysctl_get (platform,
|
||||
ifname,
|
||||
"max_addresses",
|
||||
0,
|
||||
G_MAXINT32,
|
||||
NM_NDISC_MAX_ADDRESSES_DEFAULT);
|
||||
}
|
||||
if (out_router_solicitations || out_default_ra_timeout) {
|
||||
router_solicitations = ipv6_sysctl_get (platform,
|
||||
ifname,
|
||||
"router_solicitations",
|
||||
1,
|
||||
G_MAXINT32,
|
||||
NM_NDISC_ROUTER_SOLICITATIONS_DEFAULT);
|
||||
NM_SET_OUT (out_router_solicitations, router_solicitations);
|
||||
}
|
||||
if (out_router_solicitation_interval || out_default_ra_timeout) {
|
||||
router_solicitation_interval = ipv6_sysctl_get (platform,
|
||||
ifname,
|
||||
"router_solicitation_interval",
|
||||
1,
|
||||
G_MAXINT32,
|
||||
NM_NDISC_ROUTER_SOLICITATION_INTERVAL_DEFAULT);
|
||||
NM_SET_OUT (out_router_solicitation_interval, router_solicitation_interval);
|
||||
}
|
||||
if (out_default_ra_timeout) {
|
||||
*out_default_ra_timeout = NM_MAX ((((gint64) router_solicitations) * router_solicitation_interval) + 1,
|
||||
30);
|
||||
}
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
||||
static void
|
||||
nm_lndp_ndisc_init (NMLndpNDisc *lndp_ndisc)
|
||||
{
|
||||
|
@ -563,7 +638,10 @@ nm_lndp_ndisc_new (NMPlatform *platform,
|
|||
const char *network_id,
|
||||
NMSettingIP6ConfigAddrGenMode addr_gen_mode,
|
||||
NMNDiscNodeType node_type,
|
||||
gint32 ra_timeout,
|
||||
int max_addresses,
|
||||
int router_solicitations,
|
||||
int router_solicitation_interval,
|
||||
guint32 ra_timeout,
|
||||
GError **error)
|
||||
{
|
||||
nm_auto_pop_netns NMPNetns *netns = NULL;
|
||||
|
@ -586,16 +664,10 @@ nm_lndp_ndisc_new (NMPlatform *platform,
|
|||
NM_NDISC_NETWORK_ID, network_id,
|
||||
NM_NDISC_ADDR_GEN_MODE, (int) addr_gen_mode,
|
||||
NM_NDISC_NODE_TYPE, (int) node_type,
|
||||
NM_NDISC_MAX_ADDRESSES, ipv6_sysctl_get (platform, ifname,
|
||||
"max_addresses",
|
||||
0, G_MAXINT32, NM_NDISC_MAX_ADDRESSES_DEFAULT),
|
||||
NM_NDISC_RA_TIMEOUT, (int) ra_timeout,
|
||||
NM_NDISC_ROUTER_SOLICITATIONS, ipv6_sysctl_get (platform, ifname,
|
||||
"router_solicitations",
|
||||
1, G_MAXINT32, NM_NDISC_ROUTER_SOLICITATIONS_DEFAULT),
|
||||
NM_NDISC_ROUTER_SOLICITATION_INTERVAL, ipv6_sysctl_get (platform, ifname,
|
||||
"router_solicitation_interval",
|
||||
1, G_MAXINT32, NM_NDISC_ROUTER_SOLICITATION_INTERVAL_DEFAULT),
|
||||
NM_NDISC_MAX_ADDRESSES, max_addresses,
|
||||
NM_NDISC_ROUTER_SOLICITATIONS, router_solicitations,
|
||||
NM_NDISC_ROUTER_SOLICITATION_INTERVAL, router_solicitation_interval,
|
||||
NM_NDISC_RA_TIMEOUT, (guint) ra_timeout,
|
||||
NULL);
|
||||
|
||||
priv = NM_LNDP_NDISC_GET_PRIVATE (ndisc);
|
||||
|
@ -617,24 +689,8 @@ static void
|
|||
dispose (GObject *object)
|
||||
{
|
||||
NMNDisc *ndisc = NM_NDISC (object);
|
||||
NMLndpNDiscPrivate *priv = NM_LNDP_NDISC_GET_PRIVATE (ndisc);
|
||||
|
||||
nm_clear_g_source_inst (&priv->event_source);
|
||||
|
||||
if (priv->ndp) {
|
||||
switch (nm_ndisc_get_node_type (ndisc)) {
|
||||
case NM_NDISC_NODE_TYPE_HOST:
|
||||
ndp_msgrcv_handler_unregister (priv->ndp, receive_ra, NDP_MSG_RA, nm_ndisc_get_ifindex (ndisc), ndisc);
|
||||
break;
|
||||
case NM_NDISC_NODE_TYPE_ROUTER:
|
||||
ndp_msgrcv_handler_unregister (priv->ndp, receive_rs, NDP_MSG_RS, nm_ndisc_get_ifindex (ndisc), ndisc);
|
||||
break;
|
||||
default:
|
||||
g_assert_not_reached ();
|
||||
}
|
||||
ndp_close (priv->ndp);
|
||||
priv->ndp = NULL;
|
||||
}
|
||||
_cleanup (ndisc);
|
||||
|
||||
G_OBJECT_CLASS (nm_lndp_ndisc_parent_class)->dispose (object);
|
||||
}
|
||||
|
@ -647,6 +703,7 @@ nm_lndp_ndisc_class_init (NMLndpNDiscClass *klass)
|
|||
|
||||
object_class->dispose = dispose;
|
||||
ndisc_class->start = start;
|
||||
ndisc_class->stop = stop;
|
||||
ndisc_class->send_rs = send_rs;
|
||||
ndisc_class->send_ra = send_ra;
|
||||
}
|
||||
|
|
|
@ -28,7 +28,17 @@ NMNDisc *nm_lndp_ndisc_new (NMPlatform *platform,
|
|||
const char *network_id,
|
||||
NMSettingIP6ConfigAddrGenMode addr_gen_mode,
|
||||
NMNDiscNodeType node_type,
|
||||
gint32 ra_timeout,
|
||||
int max_addresses,
|
||||
int router_solicitations,
|
||||
int router_solicitation_interval,
|
||||
guint32 ra_timeout,
|
||||
GError **error);
|
||||
|
||||
void nm_lndp_ndisc_get_sysctl (NMPlatform *platform,
|
||||
const char *ifname,
|
||||
int *out_max_addresses,
|
||||
int *out_router_solicitations,
|
||||
int *out_router_solicitation_interval,
|
||||
guint32 *out_default_ra_timeout);
|
||||
|
||||
#endif /* __NETWORKMANAGER_LNDP_NDISC_H__ */
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
#include "nm-utils.h"
|
||||
#include "platform/nm-platform.h"
|
||||
#include "platform/nmp-netns.h"
|
||||
#include "nm-l3-config-data.h"
|
||||
|
||||
#define _NMLOG_PREFIX_NAME "ndisc"
|
||||
|
||||
|
@ -25,6 +26,9 @@ struct _NMNDiscPrivate {
|
|||
/* this *must* be the first field. */
|
||||
NMNDiscDataInternal rdata;
|
||||
|
||||
char *last_error;
|
||||
GSource *ra_timeout_source;
|
||||
|
||||
union {
|
||||
gint32 solicitations_left;
|
||||
gint32 announcements_left;
|
||||
|
@ -37,9 +41,7 @@ struct _NMNDiscPrivate {
|
|||
gint32 last_rs;
|
||||
gint32 last_ra;
|
||||
};
|
||||
guint ra_timeout_id; /* first RA timeout */
|
||||
guint timeout_id; /* prefix/dns/etc lifetime timeout */
|
||||
char *last_error;
|
||||
NMUtilsIPv6IfaceId iid;
|
||||
|
||||
/* immutable values: */
|
||||
|
@ -48,7 +50,7 @@ struct _NMNDiscPrivate {
|
|||
char *network_id;
|
||||
NMSettingIP6ConfigAddrGenMode addr_gen_mode;
|
||||
NMUtilsStableType stable_type;
|
||||
gint32 ra_timeout;
|
||||
guint32 ra_timeout;
|
||||
gint32 max_addresses;
|
||||
gint32 router_solicitations;
|
||||
gint32 router_solicitation_interval;
|
||||
|
@ -92,6 +94,121 @@ static void _config_changed_log (NMNDisc *ndisc, NMNDiscConfigMap changed);
|
|||
|
||||
/*****************************************************************************/
|
||||
|
||||
NML3ConfigData *
|
||||
nm_ndisc_data_to_l3cd (NMDedupMultiIndex *multi_idx,
|
||||
int ifindex,
|
||||
const NMNDiscData *rdata,
|
||||
NMSettingIP6ConfigPrivacy ip6_privacy,
|
||||
guint32 route_table,
|
||||
guint32 route_metric,
|
||||
gboolean kernel_support_rta_pref,
|
||||
gboolean kernel_support_extended_ifa_flags)
|
||||
{
|
||||
nm_auto_unref_l3cd_init NML3ConfigData *l3cd = NULL;
|
||||
guint32 ifa_flags;
|
||||
guint8 plen;
|
||||
guint i;
|
||||
|
||||
l3cd = nm_l3_config_data_new (multi_idx,
|
||||
ifindex);
|
||||
|
||||
nm_l3_config_data_set_source (l3cd, NM_IP_CONFIG_SOURCE_NDISC);
|
||||
|
||||
nm_l3_config_data_set_ip6_privacy (l3cd, ip6_privacy);
|
||||
|
||||
/* Check, whether kernel is recent enough to help user space handling RA.
|
||||
* If it's not supported, we have no ipv6-privacy and must add autoconf
|
||||
* addresses as /128. The reason for the /128 is to prevent the kernel
|
||||
* from adding a prefix route for this address. */
|
||||
ifa_flags = 0;
|
||||
if (kernel_support_extended_ifa_flags) {
|
||||
ifa_flags |= IFA_F_NOPREFIXROUTE;
|
||||
if (NM_IN_SET (ip6_privacy, NM_SETTING_IP6_CONFIG_PRIVACY_PREFER_TEMP_ADDR,
|
||||
NM_SETTING_IP6_CONFIG_PRIVACY_PREFER_PUBLIC_ADDR))
|
||||
ifa_flags |= IFA_F_MANAGETEMPADDR;
|
||||
plen = 64;
|
||||
} else
|
||||
plen = 128;
|
||||
|
||||
for (i = 0; i < rdata->addresses_n; i++) {
|
||||
const NMNDiscAddress *ndisc_addr = &rdata->addresses[i];
|
||||
NMPlatformIP6Address a;
|
||||
|
||||
a = (NMPlatformIP6Address) {
|
||||
.ifindex = ifindex,
|
||||
.address = ndisc_addr->address,
|
||||
.plen = plen,
|
||||
.timestamp = ndisc_addr->timestamp,
|
||||
.lifetime = ndisc_addr->lifetime,
|
||||
.preferred = MIN (ndisc_addr->lifetime, ndisc_addr->preferred),
|
||||
.addr_source = NM_IP_CONFIG_SOURCE_NDISC,
|
||||
.n_ifa_flags = ifa_flags,
|
||||
};
|
||||
|
||||
nm_l3_config_data_add_address_6 (l3cd, &a);
|
||||
}
|
||||
|
||||
for (i = 0; i < rdata->routes_n; i++) {
|
||||
const NMNDiscRoute *ndisc_route = &rdata->routes[i];
|
||||
NMPlatformIP6Route r;
|
||||
|
||||
r = (NMPlatformIP6Route) {
|
||||
.ifindex = ifindex,
|
||||
.network = ndisc_route->network,
|
||||
.plen = ndisc_route->plen,
|
||||
.gateway = ndisc_route->gateway,
|
||||
.rt_source = NM_IP_CONFIG_SOURCE_NDISC,
|
||||
.table_coerced = nm_platform_route_table_coerce (route_table),
|
||||
.metric = route_metric,
|
||||
.rt_pref = ndisc_route->preference,
|
||||
};
|
||||
nm_assert ((NMIcmpv6RouterPref) r.rt_pref == ndisc_route->preference);
|
||||
|
||||
nm_l3_config_data_add_route_6 (l3cd, &r);
|
||||
}
|
||||
|
||||
if (rdata->gateways_n > 0) {
|
||||
const NMIcmpv6RouterPref first_pref = rdata->gateways[0].preference;
|
||||
NMPlatformIP6Route r = {
|
||||
.rt_source = NM_IP_CONFIG_SOURCE_NDISC,
|
||||
.ifindex = ifindex,
|
||||
.table_coerced = nm_platform_route_table_coerce (route_table),
|
||||
.metric = route_metric,
|
||||
};
|
||||
|
||||
for (i = 0; i < rdata->gateways_n; i++) {
|
||||
r.gateway = rdata->gateways[i].address;
|
||||
r.rt_pref = rdata->gateways[i].preference;
|
||||
nm_assert ((NMIcmpv6RouterPref) r.rt_pref == rdata->gateways[i].preference);
|
||||
nm_l3_config_data_add_route_6 (l3cd, &r);
|
||||
|
||||
if ( first_pref != rdata->gateways[i].preference
|
||||
&& !kernel_support_rta_pref) {
|
||||
/* We are unable to configure a router preference. Hence, we skip all gateways
|
||||
* with a different preference from the first gateway. Note, that the gateways
|
||||
* are sorted in order of highest to lowest preference. */
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < rdata->dns_servers_n; i++)
|
||||
nm_l3_config_data_add_nameserver (l3cd, AF_INET6, &rdata->dns_servers[i].address);
|
||||
|
||||
for (i = 0; i < rdata->dns_domains_n; i++)
|
||||
nm_l3_config_data_add_search (l3cd, AF_INET6, rdata->dns_domains[i].domain);
|
||||
|
||||
nm_l3_config_data_set_ndisc_hop_limit (l3cd, rdata->hop_limit);
|
||||
nm_l3_config_data_set_ndisc_reachable_time_msec (l3cd, rdata->reachable_time_ms);
|
||||
nm_l3_config_data_set_ndisc_retrans_timer_msec (l3cd, rdata->retrans_timer_ms);
|
||||
|
||||
nm_l3_config_data_set_ip6_mtu (l3cd, rdata->mtu);
|
||||
|
||||
return g_steal_pointer (&l3cd);
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
||||
static guint8
|
||||
_preference_to_priority (NMIcmpv6RouterPref pref)
|
||||
{
|
||||
|
@ -899,7 +1016,7 @@ ndisc_ra_timeout_cb (gpointer user_data)
|
|||
{
|
||||
NMNDisc *ndisc = NM_NDISC (user_data);
|
||||
|
||||
NM_NDISC_GET_PRIVATE (ndisc)->ra_timeout_id = 0;
|
||||
nm_clear_g_source_inst (&NM_NDISC_GET_PRIVATE (ndisc)->ra_timeout_source);
|
||||
g_signal_emit (ndisc, signals[RA_TIMEOUT_SIGNAL], 0);
|
||||
return G_SOURCE_REMOVE;
|
||||
}
|
||||
|
@ -915,7 +1032,7 @@ nm_ndisc_start (NMNDisc *ndisc)
|
|||
priv = NM_NDISC_GET_PRIVATE (ndisc);
|
||||
|
||||
nm_assert (NM_NDISC_GET_CLASS (ndisc)->start);
|
||||
nm_assert (!priv->ra_timeout_id);
|
||||
nm_assert (!priv->ra_timeout_source);
|
||||
|
||||
_LOGD ("starting neighbor discovery for ifindex %d%s",
|
||||
priv->ifindex,
|
||||
|
@ -929,27 +1046,83 @@ nm_ndisc_start (NMNDisc *ndisc)
|
|||
NM_NDISC_GET_CLASS (ndisc)->start (ndisc);
|
||||
|
||||
if (priv->node_type == NM_NDISC_NODE_TYPE_HOST) {
|
||||
gint32 ra_timeout = priv->ra_timeout;
|
||||
|
||||
G_STATIC_ASSERT_EXPR (NM_RA_TIMEOUT_DEFAULT == 0);
|
||||
G_STATIC_ASSERT_EXPR (NM_RA_TIMEOUT_INFINITY == G_MAXINT32);
|
||||
if (ra_timeout != NM_RA_TIMEOUT_INFINITY) {
|
||||
if (ra_timeout == NM_RA_TIMEOUT_DEFAULT) {
|
||||
ra_timeout = NM_MAX ((((gint64) priv->router_solicitations) * priv->router_solicitation_interval) + 1,
|
||||
30);
|
||||
}
|
||||
nm_assert (ra_timeout > 0 && ra_timeout < NM_RA_TIMEOUT_INFINITY);
|
||||
_LOGD ("scheduling RA timeout in %d seconds", ra_timeout);
|
||||
priv->ra_timeout_id = g_timeout_add_seconds (ra_timeout, ndisc_ra_timeout_cb, ndisc);
|
||||
nm_assert (priv->ra_timeout > 0u);
|
||||
nm_assert (priv->ra_timeout <= NM_RA_TIMEOUT_INFINITY);
|
||||
|
||||
if (priv->ra_timeout < NM_RA_TIMEOUT_INFINITY) {
|
||||
guint timeout_msec;
|
||||
|
||||
_LOGD ("scheduling RA timeout in %u seconds", priv->ra_timeout);
|
||||
if (priv->ra_timeout < G_MAXUINT / 1000u)
|
||||
timeout_msec = priv->ra_timeout * 1000u;
|
||||
else
|
||||
timeout_msec = G_MAXUINT;
|
||||
priv->ra_timeout_source = nm_g_timeout_source_new (timeout_msec,
|
||||
G_PRIORITY_DEFAULT,
|
||||
ndisc_ra_timeout_cb,
|
||||
ndisc,
|
||||
NULL);
|
||||
g_source_attach (priv->ra_timeout_source, NULL);
|
||||
}
|
||||
|
||||
solicit_routers (ndisc);
|
||||
return;
|
||||
}
|
||||
|
||||
nm_assert (priv->ra_timeout == 0u);
|
||||
nm_assert (priv->node_type == NM_NDISC_NODE_TYPE_ROUTER);
|
||||
announce_router_initial (ndisc);
|
||||
}
|
||||
|
||||
void
|
||||
nm_ndisc_stop (NMNDisc *ndisc)
|
||||
{
|
||||
nm_auto_pop_netns NMPNetns *netns = NULL;
|
||||
NMNDiscDataInternal *rdata;
|
||||
NMNDiscPrivate *priv;
|
||||
|
||||
g_return_if_fail (NM_IS_NDISC (ndisc));
|
||||
|
||||
priv = NM_NDISC_GET_PRIVATE (ndisc);
|
||||
|
||||
nm_assert (NM_NDISC_GET_CLASS (ndisc)->stop);
|
||||
|
||||
_LOGD ("stopping neighbor discovery for ifindex %d",
|
||||
priv->ifindex);
|
||||
|
||||
if (!nm_ndisc_netns_push (ndisc, &netns))
|
||||
return;
|
||||
|
||||
NM_NDISC_GET_CLASS (ndisc)->stop (ndisc);
|
||||
|
||||
rdata = &priv->rdata;
|
||||
|
||||
g_array_set_size (rdata->gateways, 0);
|
||||
g_array_set_size (rdata->addresses, 0);
|
||||
g_array_set_size (rdata->routes, 0);
|
||||
g_array_set_size (rdata->dns_servers, 0);
|
||||
g_array_set_size (rdata->dns_domains, 0);
|
||||
priv->rdata.public.hop_limit = 64;
|
||||
|
||||
/* Start at very low number so that last_rs - router_solicitation_interval
|
||||
* is much lower than nm_utils_get_monotonic_timestamp_sec() at startup.
|
||||
*/
|
||||
priv->last_rs = G_MININT32;
|
||||
nm_clear_g_source_inst (&priv->ra_timeout_source);
|
||||
nm_clear_g_source (&priv->send_rs_id);
|
||||
nm_clear_g_source (&priv->send_ra_id);
|
||||
nm_clear_g_free (&priv->last_error);
|
||||
nm_clear_g_source (&priv->timeout_id);
|
||||
|
||||
priv->solicitations_left = 0;
|
||||
priv->announcements_left = 0;
|
||||
|
||||
priv->last_rs = G_MININT32;
|
||||
priv->last_ra = G_MININT32;
|
||||
}
|
||||
|
||||
NMNDiscConfigMap
|
||||
nm_ndisc_dad_failed (NMNDisc *ndisc, const struct in6_addr *address, gboolean emit_changed_signal)
|
||||
{
|
||||
|
@ -1254,7 +1427,7 @@ nm_ndisc_ra_received (NMNDisc *ndisc, gint32 now, NMNDiscConfigMap changed)
|
|||
{
|
||||
NMNDiscPrivate *priv = NM_NDISC_GET_PRIVATE (ndisc);
|
||||
|
||||
nm_clear_g_source (&priv->ra_timeout_id);
|
||||
nm_clear_g_source_inst (&priv->ra_timeout_source);
|
||||
nm_clear_g_source (&priv->send_rs_id);
|
||||
nm_clear_g_free (&priv->last_error);
|
||||
check_timestamps (ndisc, now, changed);
|
||||
|
@ -1328,7 +1501,8 @@ set_property (GObject *object, guint prop_id,
|
|||
break;
|
||||
case PROP_RA_TIMEOUT:
|
||||
/* construct-only */
|
||||
priv->ra_timeout = g_value_get_int (value);
|
||||
priv->ra_timeout = g_value_get_uint (value);
|
||||
nm_assert (priv->ra_timeout <= NM_RA_TIMEOUT_INFINITY);
|
||||
break;
|
||||
case PROP_ROUTER_SOLICITATIONS:
|
||||
/* construct-only */
|
||||
|
@ -1381,7 +1555,7 @@ dispose (GObject *object)
|
|||
NMNDisc *ndisc = NM_NDISC (object);
|
||||
NMNDiscPrivate *priv = NM_NDISC_GET_PRIVATE (ndisc);
|
||||
|
||||
nm_clear_g_source (&priv->ra_timeout_id);
|
||||
nm_clear_g_source_inst (&priv->ra_timeout_source);
|
||||
nm_clear_g_source (&priv->send_rs_id);
|
||||
nm_clear_g_source (&priv->send_ra_id);
|
||||
nm_clear_g_free (&priv->last_error);
|
||||
|
@ -1468,7 +1642,7 @@ nm_ndisc_class_init (NMNDiscClass *klass)
|
|||
G_PARAM_STATIC_STRINGS);
|
||||
G_STATIC_ASSERT_EXPR (G_MAXINT32 == NM_RA_TIMEOUT_INFINITY);
|
||||
obj_properties[PROP_RA_TIMEOUT] =
|
||||
g_param_spec_int (NM_NDISC_RA_TIMEOUT, "", "",
|
||||
g_param_spec_uint (NM_NDISC_RA_TIMEOUT, "", "",
|
||||
0, G_MAXINT32, 0,
|
||||
G_PARAM_WRITABLE |
|
||||
G_PARAM_CONSTRUCT_ONLY |
|
||||
|
|
|
@ -16,8 +16,8 @@
|
|||
#include "platform/nm-platform.h"
|
||||
#include "platform/nmp-object.h"
|
||||
|
||||
#define NM_RA_TIMEOUT_DEFAULT ((gint32) 0)
|
||||
#define NM_RA_TIMEOUT_INFINITY G_MAXINT32
|
||||
#define NM_RA_TIMEOUT_DEFAULT ((guint32) 0)
|
||||
#define NM_RA_TIMEOUT_INFINITY ((guint32) G_MAXINT32)
|
||||
|
||||
#define NM_TYPE_NDISC (nm_ndisc_get_type ())
|
||||
#define NM_NDISC(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), NM_TYPE_NDISC, NMNDisc))
|
||||
|
@ -163,6 +163,7 @@ typedef struct {
|
|||
GObjectClass parent;
|
||||
|
||||
void (*start) (NMNDisc *ndisc);
|
||||
void (*stop) (NMNDisc *ndisc);
|
||||
gboolean (*send_rs) (NMNDisc *ndisc, GError **error);
|
||||
gboolean (*send_ra) (NMNDisc *ndisc, GError **error);
|
||||
} NMNDiscClass;
|
||||
|
@ -177,6 +178,7 @@ NMNDiscNodeType nm_ndisc_get_node_type (NMNDisc *self);
|
|||
|
||||
gboolean nm_ndisc_set_iid (NMNDisc *ndisc, const NMUtilsIPv6IfaceId iid);
|
||||
void nm_ndisc_start (NMNDisc *ndisc);
|
||||
void nm_ndisc_stop (NMNDisc *ndisc);
|
||||
NMNDiscConfigMap nm_ndisc_dad_failed (NMNDisc *ndisc,
|
||||
const struct in6_addr *address,
|
||||
gboolean emit_changed_signal);
|
||||
|
@ -217,4 +219,17 @@ nm_ndisc_dad_addr_is_fail_candidate (NMPlatform *platform,
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
||||
struct _NML3ConfigData;
|
||||
|
||||
struct _NML3ConfigData *nm_ndisc_data_to_l3cd (NMDedupMultiIndex *multi_idx,
|
||||
int ifindex,
|
||||
const NMNDiscData *rdata,
|
||||
NMSettingIP6ConfigPrivacy ip6_privacy,
|
||||
guint32 route_table,
|
||||
guint32 route_metric,
|
||||
gboolean kernel_support_rta_pref,
|
||||
gboolean kernel_support_extended_ifa_flags);
|
||||
|
||||
#endif /* __NETWORKMANAGER_NDISC_H__ */
|
||||
|
|
|
@ -25,6 +25,10 @@ main (int argc, char **argv)
|
|||
const char *ifname;
|
||||
NMUtilsIPv6IfaceId iid = { };
|
||||
GError *error = NULL;
|
||||
int max_addresses;
|
||||
int router_solicitations;
|
||||
int router_solicitation_interval;
|
||||
guint32 ra_timeout;
|
||||
|
||||
nmtst_init_with_logging (&argc, &argv, NULL, "DEFAULT");
|
||||
|
||||
|
@ -45,6 +49,13 @@ main (int argc, char **argv)
|
|||
return EXIT_FAILURE;
|
||||
}
|
||||
|
||||
nm_lndp_ndisc_get_sysctl (NM_PLATFORM_GET,
|
||||
ifname,
|
||||
&max_addresses,
|
||||
&router_solicitations,
|
||||
&router_solicitation_interval,
|
||||
&ra_timeout);
|
||||
|
||||
ndisc = nm_lndp_ndisc_new (NM_PLATFORM_GET,
|
||||
ifindex,
|
||||
ifname,
|
||||
|
@ -52,7 +63,10 @@ main (int argc, char **argv)
|
|||
"8ce666e8-d34d-4fb1-b858-f15a7al28086",
|
||||
NM_SETTING_IP6_CONFIG_ADDR_GEN_MODE_EUI64,
|
||||
NM_NDISC_NODE_TYPE_HOST,
|
||||
0,
|
||||
max_addresses,
|
||||
router_solicitations,
|
||||
router_solicitation_interval,
|
||||
ra_timeout,
|
||||
&error);
|
||||
if (!ndisc) {
|
||||
g_print ("Failed to create NMNDisc instance: %s\n", error->message);
|
||||
|
|
|
@ -72,21 +72,35 @@ nm_dbus_utils_get_property (GObject *obj,
|
|||
const char *signature,
|
||||
const char *property_name)
|
||||
{
|
||||
GParamSpec *pspec;
|
||||
nm_auto_unset_gvalue GValue value = G_VALUE_INIT;
|
||||
GParamSpec *pspec;
|
||||
GVariant *variant;
|
||||
|
||||
nm_assert (G_IS_OBJECT (obj));
|
||||
nm_assert (g_variant_type_string_is_valid (signature));
|
||||
nm_assert (property_name && property_name[0]);
|
||||
|
||||
pspec = g_object_class_find_property (G_OBJECT_GET_CLASS (obj), property_name);
|
||||
if (!pspec)
|
||||
g_return_val_if_reached (NULL);
|
||||
|
||||
nm_assert (pspec);
|
||||
|
||||
nm_assert ( pspec->value_type != G_TYPE_VARIANT
|
||||
|| nm_streq ((char *) (((GParamSpecVariant *) pspec)->type), signature));
|
||||
|
||||
g_value_init (&value, pspec->value_type);
|
||||
|
||||
g_object_get_property (obj, property_name, &value);
|
||||
|
||||
variant = g_dbus_gvalue_to_gvariant (&value, G_VARIANT_TYPE (signature));
|
||||
|
||||
nm_assert ( !variant
|
||||
|| g_variant_is_of_type (variant, G_VARIANT_TYPE (signature)));
|
||||
|
||||
/* returns never-floating variant */
|
||||
return g_dbus_gvalue_to_gvariant (&value, G_VARIANT_TYPE (signature));
|
||||
nm_assert ( !variant
|
||||
|| !g_variant_is_floating (variant));
|
||||
|
||||
return variant;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
|
|
@ -552,6 +552,10 @@ main (int argc, char *argv[])
|
|||
if (global_opt.slaac) {
|
||||
NMUtilsStableType stable_type = NM_UTILS_STABLE_TYPE_UUID;
|
||||
const char *stable_id = global_opt.uuid;
|
||||
int router_solicitation_interval;
|
||||
int router_solicitations;
|
||||
guint32 default_ra_timeout;
|
||||
int max_addresses;
|
||||
|
||||
nm_platform_link_set_user_ipv6ll_enabled (NM_PLATFORM_GET, gl.ifindex, TRUE);
|
||||
|
||||
|
@ -564,6 +568,14 @@ main (int argc, char *argv[])
|
|||
stable_type = (global_opt.stable_id[0] - '0');
|
||||
stable_id = &global_opt.stable_id[2];
|
||||
}
|
||||
|
||||
nm_lndp_ndisc_get_sysctl (NM_PLATFORM_GET,
|
||||
global_opt.ifname,
|
||||
&max_addresses,
|
||||
&router_solicitations,
|
||||
&router_solicitation_interval,
|
||||
&default_ra_timeout);
|
||||
|
||||
ndisc = nm_lndp_ndisc_new (NM_PLATFORM_GET,
|
||||
gl.ifindex,
|
||||
global_opt.ifname,
|
||||
|
@ -571,7 +583,10 @@ main (int argc, char *argv[])
|
|||
stable_id,
|
||||
global_opt.addr_gen_mode,
|
||||
NM_NDISC_NODE_TYPE_HOST,
|
||||
NM_RA_TIMEOUT_DEFAULT,
|
||||
max_addresses,
|
||||
router_solicitations,
|
||||
router_solicitation_interval,
|
||||
default_ra_timeout,
|
||||
NULL);
|
||||
g_assert (ndisc);
|
||||
|
||||
|
|
|
@ -119,16 +119,27 @@ struct _NML3ConfigData {
|
|||
|
||||
NMIPConfigSource source;
|
||||
|
||||
int ndisc_hop_limit_val;
|
||||
|
||||
guint32 mtu;
|
||||
guint32 ip6_mtu;
|
||||
guint32 ndisc_reachable_time_msec_val;
|
||||
guint32 ndisc_retrans_timer_msec_val;
|
||||
|
||||
NMTernary metered:3;
|
||||
|
||||
NMSettingIP6ConfigPrivacy ip6_privacy:4;
|
||||
|
||||
bool is_sealed:1;
|
||||
|
||||
bool has_routes_with_type_local_4_set:1;
|
||||
bool has_routes_with_type_local_6_set:1;
|
||||
bool has_routes_with_type_local_4_val:1;
|
||||
bool has_routes_with_type_local_6_val:1;
|
||||
|
||||
bool ndisc_hop_limit_set:1;
|
||||
bool ndisc_reachable_time_msec_set:1;
|
||||
bool ndisc_retrans_timer_msec_set:1;
|
||||
};
|
||||
|
||||
/*****************************************************************************/
|
||||
|
@ -406,6 +417,10 @@ nm_l3_config_data_new (NMDedupMultiIndex *multi_idx,
|
|||
.route_table_sync_4 = NM_IP_ROUTE_TABLE_SYNC_MODE_NONE,
|
||||
.route_table_sync_6 = NM_IP_ROUTE_TABLE_SYNC_MODE_NONE,
|
||||
.source = NM_IP_CONFIG_SOURCE_UNKNOWN,
|
||||
.ip6_privacy = NM_SETTING_IP6_CONFIG_PRIVACY_UNKNOWN,
|
||||
.ndisc_hop_limit_set = FALSE,
|
||||
.ndisc_reachable_time_msec_set = FALSE,
|
||||
.ndisc_retrans_timer_msec_set = FALSE,
|
||||
};
|
||||
|
||||
_idx_type_init (&self->idx_addresses_4, NMP_OBJECT_TYPE_IP4_ADDRESS);
|
||||
|
@ -1084,7 +1099,7 @@ nm_l3_config_data_add_nameserver (NML3ConfigData *self,
|
|||
}
|
||||
|
||||
gboolean
|
||||
nm_l3_config_data_clear_nameserver (NML3ConfigData *self,
|
||||
nm_l3_config_data_clear_nameservers (NML3ConfigData *self,
|
||||
int addr_family)
|
||||
{
|
||||
gs_unref_array GArray *old = NULL;
|
||||
|
@ -1182,6 +1197,19 @@ nm_l3_config_data_add_search (NML3ConfigData *self,
|
|||
return _check_and_add_domain (&self->searches_x[NM_IS_IPv4 (addr_family)], search);
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_l3_config_data_clear_searches (NML3ConfigData *self,
|
||||
int addr_family)
|
||||
{
|
||||
gs_unref_ptrarray GPtrArray *old = NULL;
|
||||
|
||||
nm_assert (_NM_IS_L3_CONFIG_DATA (self, FALSE));
|
||||
nm_assert_addr_family (addr_family);
|
||||
|
||||
old = g_steal_pointer (&self->searches_x[NM_IS_IPv4 (addr_family)]);
|
||||
return (nm_g_ptr_array_len (old) > 0);
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_l3_config_data_add_dns_option (NML3ConfigData *self,
|
||||
int addr_family,
|
||||
|
@ -1322,6 +1350,27 @@ nm_l3_config_data_set_mtu (NML3ConfigData *self,
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
guint32
|
||||
nm_l3_config_data_get_ip6_mtu (const NML3ConfigData *self)
|
||||
{
|
||||
nm_assert (_NM_IS_L3_CONFIG_DATA (self, TRUE));
|
||||
|
||||
return self->ip6_mtu;
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_l3_config_data_set_ip6_mtu (NML3ConfigData *self,
|
||||
guint32 ip6_mtu)
|
||||
{
|
||||
nm_assert (_NM_IS_L3_CONFIG_DATA (self, FALSE));
|
||||
|
||||
if (self->ip6_mtu == ip6_mtu)
|
||||
return FALSE;
|
||||
|
||||
self->ip6_mtu = ip6_mtu;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_l3_config_data_set_source (NML3ConfigData *self,
|
||||
NMIPConfigSource source)
|
||||
|
@ -1335,6 +1384,109 @@ nm_l3_config_data_set_source (NML3ConfigData *self,
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
NMSettingIP6ConfigPrivacy
|
||||
nm_l3_config_data_get_ip6_privacy (const NML3ConfigData *self)
|
||||
{
|
||||
nm_assert (_NM_IS_L3_CONFIG_DATA (self, FALSE));
|
||||
|
||||
return self->ip6_privacy;
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_l3_config_data_set_ip6_privacy (NML3ConfigData *self,
|
||||
NMSettingIP6ConfigPrivacy ip6_privacy)
|
||||
{
|
||||
nm_assert (_NM_IS_L3_CONFIG_DATA (self, FALSE));
|
||||
nm_assert (NM_IN_SET (ip6_privacy, NM_SETTING_IP6_CONFIG_PRIVACY_UNKNOWN,
|
||||
NM_SETTING_IP6_CONFIG_PRIVACY_DISABLED,
|
||||
NM_SETTING_IP6_CONFIG_PRIVACY_PREFER_PUBLIC_ADDR,
|
||||
NM_SETTING_IP6_CONFIG_PRIVACY_PREFER_TEMP_ADDR));
|
||||
|
||||
if (self->ip6_privacy == ip6_privacy)
|
||||
return FALSE;
|
||||
self->ip6_privacy = ip6_privacy;
|
||||
nm_assert (self->ip6_privacy == ip6_privacy);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_l3_config_data_get_ndisc_hop_limit (const NML3ConfigData *self,
|
||||
int *out_val)
|
||||
{
|
||||
nm_assert (_NM_IS_L3_CONFIG_DATA (self, FALSE));
|
||||
|
||||
if (!self->ndisc_hop_limit_set) {
|
||||
NM_SET_OUT (out_val, 0);
|
||||
return FALSE;
|
||||
}
|
||||
NM_SET_OUT (out_val, self->ndisc_hop_limit_val);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_l3_config_data_set_ndisc_hop_limit (NML3ConfigData *self,
|
||||
int val)
|
||||
{
|
||||
if ( self->ndisc_hop_limit_set
|
||||
&& self->ndisc_hop_limit_val == val)
|
||||
return FALSE;
|
||||
self->ndisc_hop_limit_set = TRUE;
|
||||
self->ndisc_hop_limit_val = val;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_l3_config_data_get_ndisc_reachable_time_msec (const NML3ConfigData *self,
|
||||
guint32 *out_val)
|
||||
{
|
||||
nm_assert (_NM_IS_L3_CONFIG_DATA (self, FALSE));
|
||||
|
||||
if (!self->ndisc_reachable_time_msec_set) {
|
||||
NM_SET_OUT (out_val, 0);
|
||||
return FALSE;
|
||||
}
|
||||
NM_SET_OUT (out_val, self->ndisc_reachable_time_msec_val);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_l3_config_data_set_ndisc_reachable_time_msec (NML3ConfigData *self,
|
||||
guint32 val)
|
||||
{
|
||||
if ( self->ndisc_reachable_time_msec_set
|
||||
&& self->ndisc_reachable_time_msec_val == val)
|
||||
return FALSE;
|
||||
self->ndisc_reachable_time_msec_set = TRUE;
|
||||
self->ndisc_reachable_time_msec_val = val;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_l3_config_data_get_ndisc_retrans_timer_msec (const NML3ConfigData *self,
|
||||
guint32 *out_val)
|
||||
{
|
||||
nm_assert (_NM_IS_L3_CONFIG_DATA (self, FALSE));
|
||||
|
||||
if (!self->ndisc_retrans_timer_msec_set) {
|
||||
NM_SET_OUT (out_val, 0);
|
||||
return FALSE;
|
||||
}
|
||||
NM_SET_OUT (out_val, self->ndisc_retrans_timer_msec_val);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_l3_config_data_set_ndisc_retrans_timer_msec (NML3ConfigData *self,
|
||||
guint32 val)
|
||||
{
|
||||
if ( self->ndisc_retrans_timer_msec_set
|
||||
&& self->ndisc_retrans_timer_msec_val == val)
|
||||
return FALSE;
|
||||
self->ndisc_retrans_timer_msec_set = TRUE;
|
||||
self->ndisc_retrans_timer_msec_val = val;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
||||
NMDhcpLease *
|
||||
|
@ -1479,7 +1631,21 @@ nm_l3_config_data_cmp (const NML3ConfigData *a, const NML3ConfigData *b)
|
|||
NM_CMP_DIRECT (a->mdns, b->mdns);
|
||||
NM_CMP_DIRECT (a->llmnr, b->llmnr);
|
||||
NM_CMP_DIRECT (a->mtu, b->mtu);
|
||||
NM_CMP_DIRECT (a->ip6_mtu, b->ip6_mtu);
|
||||
NM_CMP_DIRECT_UNSAFE (a->metered, b->metered);
|
||||
NM_CMP_DIRECT_UNSAFE (a->ip6_privacy, b->ip6_privacy);
|
||||
|
||||
NM_CMP_DIRECT_UNSAFE (a->ndisc_hop_limit_set, b->ndisc_hop_limit_set);
|
||||
if (a->ndisc_hop_limit_set)
|
||||
NM_CMP_DIRECT (a->ndisc_hop_limit_val, b->ndisc_hop_limit_val);
|
||||
|
||||
NM_CMP_DIRECT_UNSAFE (a->ndisc_reachable_time_msec_set, b->ndisc_reachable_time_msec_set);
|
||||
if (a->ndisc_reachable_time_msec_set)
|
||||
NM_CMP_DIRECT (a->ndisc_reachable_time_msec_val, b->ndisc_reachable_time_msec_val);
|
||||
|
||||
NM_CMP_DIRECT_UNSAFE (a->ndisc_retrans_timer_msec_set, b->ndisc_retrans_timer_msec_set);
|
||||
if (a->ndisc_retrans_timer_msec_set)
|
||||
NM_CMP_DIRECT (a->ndisc_retrans_timer_msec_val, b->ndisc_retrans_timer_msec_val);
|
||||
|
||||
NM_CMP_FIELD (a, b, source);
|
||||
|
||||
|
@ -2250,9 +2416,30 @@ nm_l3_config_data_merge (NML3ConfigData *self,
|
|||
if (self->metered == NM_TERNARY_DEFAULT)
|
||||
self->metered = src->metered;
|
||||
|
||||
if (self->mtu != 0u)
|
||||
if (self->ip6_privacy == NM_SETTING_IP6_CONFIG_PRIVACY_UNKNOWN)
|
||||
self->ip6_privacy = src->ip6_privacy;
|
||||
|
||||
if (!self->ndisc_hop_limit_set) {
|
||||
self->ndisc_hop_limit_set = TRUE;
|
||||
self->ndisc_hop_limit_val = src->ndisc_hop_limit_val;
|
||||
}
|
||||
|
||||
if (!self->ndisc_reachable_time_msec_set) {
|
||||
self->ndisc_reachable_time_msec_set = TRUE;
|
||||
self->ndisc_reachable_time_msec_val = src->ndisc_reachable_time_msec_val;
|
||||
}
|
||||
|
||||
if (!self->ndisc_retrans_timer_msec_set) {
|
||||
self->ndisc_retrans_timer_msec_set = TRUE;
|
||||
self->ndisc_retrans_timer_msec_val = src->ndisc_retrans_timer_msec_val;
|
||||
}
|
||||
|
||||
if (self->mtu == 0u)
|
||||
self->mtu = src->mtu;
|
||||
|
||||
if (self->ip6_mtu == 0u)
|
||||
self->ip6_mtu = src->ip6_mtu;
|
||||
|
||||
/* self->source does not get merged. */
|
||||
/* self->dhcp_lease_x does not get merged. */
|
||||
}
|
||||
|
|
|
@ -439,6 +439,11 @@ guint32 nm_l3_config_data_get_mtu (const NML3ConfigData *self);
|
|||
gboolean nm_l3_config_data_set_mtu (NML3ConfigData *self,
|
||||
guint32 mtu);
|
||||
|
||||
guint32 nm_l3_config_data_get_ip6_mtu (const NML3ConfigData *self);
|
||||
|
||||
gboolean nm_l3_config_data_set_ip6_mtu (NML3ConfigData *self,
|
||||
guint32 ip6_mtu);
|
||||
|
||||
const in_addr_t *nm_l3_config_data_get_wins (const NML3ConfigData *self,
|
||||
guint *out_len);
|
||||
|
||||
|
@ -453,7 +458,7 @@ gboolean nm_l3_config_data_add_nameserver (NML3ConfigData *self,
|
|||
int addr_family,
|
||||
gconstpointer /* (const NMIPAddr *) */ nameserver);
|
||||
|
||||
gboolean nm_l3_config_data_clear_nameserver (NML3ConfigData *self,
|
||||
gboolean nm_l3_config_data_clear_nameservers (NML3ConfigData *self,
|
||||
int addr_family);
|
||||
|
||||
gboolean nm_l3_config_data_add_nis_server (NML3ConfigData *self,
|
||||
|
@ -474,6 +479,9 @@ const char *const*nm_l3_config_data_get_searches (const NML3ConfigData *self,
|
|||
int addr_family,
|
||||
guint *out_len);
|
||||
|
||||
gboolean nm_l3_config_data_clear_searches (NML3ConfigData *self,
|
||||
int addr_family);
|
||||
|
||||
gboolean nm_l3_config_data_add_search (NML3ConfigData *self,
|
||||
int addr_family,
|
||||
const char *search);
|
||||
|
@ -486,6 +494,26 @@ gboolean nm_l3_config_data_set_dns_priority (NML3ConfigData *self,
|
|||
int addr_family,
|
||||
int dns_priority);
|
||||
|
||||
NMSettingIP6ConfigPrivacy nm_l3_config_data_get_ip6_privacy (const NML3ConfigData *self);
|
||||
|
||||
gboolean nm_l3_config_data_set_ip6_privacy (NML3ConfigData *self,
|
||||
NMSettingIP6ConfigPrivacy ip6_privacy);
|
||||
|
||||
gboolean nm_l3_config_data_get_ndisc_hop_limit (const NML3ConfigData *self,
|
||||
int *out_val);
|
||||
gboolean nm_l3_config_data_set_ndisc_hop_limit (NML3ConfigData *self,
|
||||
int val);
|
||||
|
||||
gboolean nm_l3_config_data_get_ndisc_reachable_time_msec (const NML3ConfigData *self,
|
||||
guint32 *out_val);
|
||||
gboolean nm_l3_config_data_set_ndisc_reachable_time_msec (NML3ConfigData *self,
|
||||
guint32 val);
|
||||
|
||||
gboolean nm_l3_config_data_get_ndisc_retrans_timer_msec (const NML3ConfigData *self,
|
||||
guint32 *out_val);
|
||||
gboolean nm_l3_config_data_set_ndisc_retrans_timer_msec (NML3ConfigData *self,
|
||||
guint32 val);
|
||||
|
||||
struct _NMDhcpLease *nm_l3_config_data_get_dhcp_lease (const NML3ConfigData *self,
|
||||
int addr_family);
|
||||
|
||||
|
|
|
@ -980,7 +980,7 @@ _l3_acd_nacd_event (int fd,
|
|||
n_acd_probe_get_userdata (event->_acd_event_payload.probe, (void **) &acd_data);
|
||||
_LOGT_acd (acd_data,
|
||||
"address %s %s from %s",
|
||||
(addr_str = nm_utils_inet4_ntop (acd_data->addr, sbuf_addr)),
|
||||
(addr_str = _nm_utils_inet4_ntop (acd_data->addr, sbuf_addr)),
|
||||
event->event == N_ACD_EVENT_DEFENDED
|
||||
? "defended"
|
||||
: "conflict detected",
|
||||
|
@ -993,7 +993,7 @@ _l3_acd_nacd_event (int fd,
|
|||
_LOGW ("IPv4 address collision detection sees conflict on interface %i%s%s%s for address %s from host %s",
|
||||
self->priv.ifindex,
|
||||
NM_PRINT_FMT_QUOTED (self->priv.pllink, " (", NMP_OBJECT_CAST_LINK (self->priv.pllink)->name, ")", ""),
|
||||
addr_str ?: nm_utils_inet4_ntop (acd_data->addr, sbuf_addr),
|
||||
addr_str ?: _nm_utils_inet4_ntop (acd_data->addr, sbuf_addr),
|
||||
sender_str
|
||||
?: (sender_str = nm_utils_bin2hexstr_full (event->_acd_event_payload.sender,
|
||||
event->_acd_event_payload.n_sender,
|
||||
|
@ -2848,6 +2848,11 @@ _platform_commit (NML3Cfg *self,
|
|||
}
|
||||
}
|
||||
|
||||
/* FIXME(l3cfg): need to honor and set nm_l3_config_data_get_ip6_privacy(). */
|
||||
/* FIXME(l3cfg): need to honor and set nm_l3_config_data_get_ndisc_*(). */
|
||||
/* FIXME(l3cfg): need to honor and set nm_l3_config_data_get_ip6_mtu(). */
|
||||
/* FIXME(l3cfg): need to honor and set nm_l3_config_data_get_mtu(). */
|
||||
|
||||
nm_platform_ip_address_sync (self->priv.platform,
|
||||
addr_family,
|
||||
self->priv.ifindex,
|
||||
|
|
|
@ -8172,7 +8172,7 @@ static const NMDBusInterfaceInfoExtended interface_info_manager = {
|
|||
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE_L ("ActivatingConnection", "o", NM_MANAGER_ACTIVATING_CONNECTION),
|
||||
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE_L ("Startup", "b", NM_MANAGER_STARTUP),
|
||||
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE_L ("Version", "s", NM_MANAGER_VERSION),
|
||||
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE_L ("Capabilities", "u", NM_MANAGER_CAPABILITIES),
|
||||
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE_L ("Capabilities", "au", NM_MANAGER_CAPABILITIES),
|
||||
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE_L ("State", "u", NM_MANAGER_STATE),
|
||||
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE_L ("Connectivity", "u", NM_MANAGER_CONNECTIVITY),
|
||||
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE_L ("ConnectivityCheckAvailable", "b", NM_MANAGER_CONNECTIVITY_CHECK_AVAILABLE),
|
||||
|
|
|
@ -6047,7 +6047,7 @@ nm_platform_ip4_address_to_string (const NMPlatformIP4Address *address, char *bu
|
|||
"",
|
||||
s_address, address->plen,
|
||||
broadcast_address ? " brd " : "",
|
||||
broadcast_address ? nm_utils_inet4_ntop (broadcast_address, str_broadcast) : "",
|
||||
broadcast_address ? _nm_utils_inet4_ntop (broadcast_address, str_broadcast) : "",
|
||||
str_lft_p,
|
||||
str_pref_p,
|
||||
str_time_p,
|
||||
|
|
Loading…
Reference in a new issue