mirror of
https://gitlab.freedesktop.org/NetworkManager/NetworkManager.git
synced 2026-02-28 23:50:35 +01:00
device: prevent IP state from reaching ready while DNS update pending
The goal would be to ensure that a device cannot move to activated, while a DNS update is still pending. This does not really work for most cases. That is, because NMDevice does not directly push DNS updates to NMDnsManager, instead, NMPolicy is watching all device changes, and doing it. But when NMPolicy decides to to that, may not be the right moment. We really should let NMDevice (or better, NML3Cfg) directly talk to NMDnsManager. Why not? They have all the information when new DNS configuration is available. The only thing that NMPolicy does on top of that, is determining which device has the best default route. NMPolicy could continue to do that (or maybe NMDnsManager could), but the update needs to be directly triggered by NMDevice/NML3Cfg.
This commit is contained in:
parent
6c27e58d8d
commit
80c9e2d9ec
1 changed files with 34 additions and 1 deletions
|
|
@ -604,6 +604,7 @@ typedef struct _NMDevicePrivate {
|
|||
const NMDeviceIPState state;
|
||||
NMDeviceIPState state_;
|
||||
};
|
||||
gulong dnsmgr_update_pending_signal_id;
|
||||
} ip_data;
|
||||
|
||||
union {
|
||||
|
|
@ -2929,6 +2930,13 @@ _add_capabilities(NMDevice *self, NMDeviceCapabilities capabilities)
|
|||
|
||||
/*****************************************************************************/
|
||||
|
||||
static void
|
||||
_dev_ip_state_dnsmgr_update_pending_changed(NMDnsManager *dnsmgr, GParamSpec *pspec, NMDevice *self)
|
||||
{
|
||||
_dev_ip_state_check(self, AF_INET);
|
||||
_dev_ip_state_check(self, AF_INET6);
|
||||
}
|
||||
|
||||
static void
|
||||
_dev_ip_state_req_timeout_cancel(NMDevice *self, int addr_family)
|
||||
{
|
||||
|
|
@ -3321,6 +3329,27 @@ got_ip_state:
|
|||
combinedip_state = priv->ip_data.state;
|
||||
}
|
||||
|
||||
if (combinedip_state == NM_DEVICE_IP_STATE_READY
|
||||
&& priv->ip_data.state <= NM_DEVICE_IP_STATE_PENDING
|
||||
&& nm_dns_manager_get_update_pending(nm_manager_get_dns_manager(priv->manager))) {
|
||||
/* We would be ready, but a DNS update is pending. That prevents us from getting fully ready. */
|
||||
if (priv->ip_data.dnsmgr_update_pending_signal_id == 0) {
|
||||
priv->ip_data.dnsmgr_update_pending_signal_id =
|
||||
g_signal_connect(nm_manager_get_dns_manager(priv->manager),
|
||||
"notify::" NM_DNS_MANAGER_UPDATE_PENDING,
|
||||
G_CALLBACK(_dev_ip_state_dnsmgr_update_pending_changed),
|
||||
self);
|
||||
_LOGT_ip(AF_UNSPEC,
|
||||
"check-state: (combined) state: wait for DNS before becoming ready");
|
||||
}
|
||||
combinedip_state = NM_DEVICE_IP_STATE_PENDING;
|
||||
}
|
||||
if (combinedip_state != NM_DEVICE_IP_STATE_PENDING
|
||||
&& priv->ip_data.dnsmgr_update_pending_signal_id != 0) {
|
||||
nm_clear_g_signal_handler(nm_manager_get_dns_manager(priv->manager),
|
||||
&priv->ip_data.dnsmgr_update_pending_signal_id);
|
||||
}
|
||||
|
||||
_LOGT_ip(AF_UNSPEC,
|
||||
"check-state: (combined) state %s => %s",
|
||||
nm_device_ip_state_to_string(priv->ip_data.state),
|
||||
|
|
@ -12329,7 +12358,8 @@ delete_on_deactivate_check_and_schedule(NMDevice *self)
|
|||
static void
|
||||
_cleanup_ip_pre(NMDevice *self, int addr_family, CleanupType cleanup_type, gboolean from_reapply)
|
||||
{
|
||||
const int IS_IPv4 = NM_IS_IPv4(addr_family);
|
||||
const int IS_IPv4 = NM_IS_IPv4(addr_family);
|
||||
NMDevicePrivate *priv = NM_DEVICE_GET_PRIVATE(self);
|
||||
|
||||
_dev_ipsharedx_cleanup(self, addr_family);
|
||||
|
||||
|
|
@ -12345,6 +12375,9 @@ _cleanup_ip_pre(NMDevice *self, int addr_family, CleanupType cleanup_type, gbool
|
|||
|
||||
_dev_ipmanual_cleanup(self);
|
||||
|
||||
nm_clear_g_signal_handler(nm_manager_get_dns_manager(priv->manager),
|
||||
&priv->ip_data.dnsmgr_update_pending_signal_id);
|
||||
|
||||
_dev_ip_state_cleanup(self, AF_UNSPEC, from_reapply);
|
||||
_dev_ip_state_cleanup(self, addr_family, from_reapply);
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue