mirror of
https://gitlab.freedesktop.org/NetworkManager/NetworkManager.git
synced 2026-01-11 04:00:20 +01:00
wwan: merge branch 'th/modem-ip-iface'
https://github.com/NetworkManager/NetworkManager/pull/55
This commit is contained in:
commit
0b25e30238
11 changed files with 394 additions and 293 deletions
|
|
@ -540,11 +540,16 @@ modem_ip4_config_result (NMModem *modem,
|
|||
}
|
||||
|
||||
static void
|
||||
data_port_changed_cb (NMModem *modem, GParamSpec *pspec, gpointer user_data)
|
||||
ip_ifindex_changed_cb (NMModem *modem, GParamSpec *pspec, gpointer user_data)
|
||||
{
|
||||
NMDevice *self = NM_DEVICE (user_data);
|
||||
NMDevice *device = NM_DEVICE (user_data);
|
||||
|
||||
nm_device_set_ip_iface (self, nm_modem_get_data_port (modem));
|
||||
if (!nm_device_set_ip_ifindex (device,
|
||||
nm_modem_get_ip_ifindex (modem))) {
|
||||
nm_device_state_changed (device,
|
||||
NM_DEVICE_STATE_FAILED,
|
||||
NM_DEVICE_STATE_REASON_IP_CONFIG_UNAVAILABLE);
|
||||
}
|
||||
}
|
||||
|
||||
static gboolean
|
||||
|
|
@ -640,29 +645,24 @@ component_added (NMDevice *device, GObject *component)
|
|||
NMDeviceBt *self = NM_DEVICE_BT (device);
|
||||
NMDeviceBtPrivate *priv = NM_DEVICE_BT_GET_PRIVATE (self);
|
||||
NMModem *modem;
|
||||
const gchar *modem_data_port;
|
||||
const gchar *modem_control_port;
|
||||
char *base;
|
||||
NMDeviceState state;
|
||||
NMDeviceStateReason failure_reason = NM_DEVICE_STATE_REASON_NONE;
|
||||
|
||||
if (!component || !NM_IS_MODEM (component))
|
||||
if ( !component
|
||||
|| !NM_IS_MODEM (component))
|
||||
return FALSE;
|
||||
|
||||
modem = NM_MODEM (component);
|
||||
|
||||
modem_data_port = nm_modem_get_data_port (modem);
|
||||
modem_control_port = nm_modem_get_control_port (modem);
|
||||
g_return_val_if_fail (modem_data_port != NULL || modem_control_port != NULL, FALSE);
|
||||
|
||||
if (!priv->rfcomm_iface)
|
||||
return FALSE;
|
||||
|
||||
base = g_path_get_basename (priv->rfcomm_iface);
|
||||
if (g_strcmp0 (base, modem_data_port) && g_strcmp0 (base, modem_control_port)) {
|
||||
g_free (base);
|
||||
return FALSE;
|
||||
{
|
||||
gs_free char *base = NULL;
|
||||
|
||||
base = g_path_get_basename (priv->rfcomm_iface);
|
||||
if (!nm_streq (base, nm_modem_get_control_port (modem)))
|
||||
return FALSE;
|
||||
}
|
||||
g_free (base);
|
||||
|
||||
/* Got the modem */
|
||||
nm_clear_g_source (&priv->timeout_id);
|
||||
|
|
@ -696,7 +696,7 @@ component_added (NMDevice *device, GObject *component)
|
|||
g_signal_connect (modem, NM_MODEM_STATE_CHANGED, G_CALLBACK (modem_state_cb), self);
|
||||
g_signal_connect (modem, NM_MODEM_REMOVED, G_CALLBACK (modem_removed_cb), self);
|
||||
|
||||
g_signal_connect (modem, "notify::" NM_MODEM_DATA_PORT, G_CALLBACK (data_port_changed_cb), self);
|
||||
g_signal_connect (modem, "notify::" NM_MODEM_IP_IFINDEX, G_CALLBACK (ip_ifindex_changed_cb), self);
|
||||
|
||||
/* Kick off the modem connection */
|
||||
if (!modem_stage1 (self, modem, &failure_reason))
|
||||
|
|
@ -753,7 +753,7 @@ bluez_connect_cb (GObject *object,
|
|||
GAsyncResult *res,
|
||||
void *user_data)
|
||||
{
|
||||
NMDeviceBt *self = NM_DEVICE_BT (user_data);
|
||||
gs_unref_object NMDeviceBt *self = NM_DEVICE_BT (user_data);
|
||||
NMDeviceBtPrivate *priv = NM_DEVICE_BT_GET_PRIVATE (self);
|
||||
GError *error = NULL;
|
||||
const char *device;
|
||||
|
|
@ -761,6 +761,9 @@ bluez_connect_cb (GObject *object,
|
|||
device = nm_bluez_device_connect_finish (NM_BLUEZ_DEVICE (object),
|
||||
res, &error);
|
||||
|
||||
if (!nm_device_is_activating (NM_DEVICE (self)))
|
||||
return;
|
||||
|
||||
if (!device) {
|
||||
_LOGW (LOGD_BT, "Error connecting with bluez: %s", error->message);
|
||||
g_clear_error (&error);
|
||||
|
|
@ -768,7 +771,6 @@ bluez_connect_cb (GObject *object,
|
|||
nm_device_state_changed (NM_DEVICE (self),
|
||||
NM_DEVICE_STATE_FAILED,
|
||||
NM_DEVICE_STATE_REASON_BT_FAILED);
|
||||
g_object_unref (self);
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
@ -776,7 +778,13 @@ bluez_connect_cb (GObject *object,
|
|||
g_free (priv->rfcomm_iface);
|
||||
priv->rfcomm_iface = g_strdup (device);
|
||||
} else if (priv->bt_type == NM_BT_CAPABILITY_NAP) {
|
||||
nm_device_set_ip_iface (NM_DEVICE (self), device);
|
||||
if (!nm_device_set_ip_iface (NM_DEVICE (self), device)) {
|
||||
_LOGW (LOGD_BT, "Error connecting with bluez: cannot find device %s", device);
|
||||
nm_device_state_changed (NM_DEVICE (self),
|
||||
NM_DEVICE_STATE_FAILED,
|
||||
NM_DEVICE_STATE_REASON_BT_FAILED);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
_LOGD (LOGD_BT, "connect request successful");
|
||||
|
|
@ -784,7 +792,6 @@ bluez_connect_cb (GObject *object,
|
|||
/* Stage 3 gets scheduled when Bluez says we're connected */
|
||||
priv->have_iface = TRUE;
|
||||
check_connect_continue (self);
|
||||
g_object_unref (self);
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
|
|||
|
|
@ -1282,126 +1282,102 @@ nm_device_get_ip_ifindex (const NMDevice *self)
|
|||
return priv->ip_iface ? priv->ip_ifindex : priv->ifindex;
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_device_set_ip_ifindex (NMDevice *self, int ifindex)
|
||||
static void
|
||||
_set_ip_ifindex (NMDevice *self,
|
||||
int ifindex,
|
||||
const char *ifname)
|
||||
{
|
||||
NMDevicePrivate *priv;
|
||||
NMDevicePrivate *priv = NM_DEVICE_GET_PRIVATE (self);
|
||||
NMPlatform *platform;
|
||||
const char *name = NULL;
|
||||
gboolean eq_name;
|
||||
|
||||
g_return_val_if_fail (NM_IS_DEVICE (self), FALSE);
|
||||
/* normalize arguments */
|
||||
if (ifindex <= 0) {
|
||||
ifindex = 0;
|
||||
ifname = NULL;
|
||||
}
|
||||
|
||||
priv = NM_DEVICE_GET_PRIVATE (self);
|
||||
platform = nm_device_get_platform (self);
|
||||
eq_name = nm_streq0 (priv->ip_iface, ifname);
|
||||
|
||||
if (ifindex > 0) {
|
||||
const NMPlatformLink *plink;
|
||||
if ( eq_name
|
||||
&& priv->ip_ifindex == ifindex)
|
||||
return;
|
||||
|
||||
plink = nm_platform_link_get (platform, ifindex);
|
||||
if (!plink) {
|
||||
nm_platform_process_events (platform);
|
||||
plink = nm_platform_link_get (NM_PLATFORM_GET, ifindex);
|
||||
}
|
||||
if (!plink) {
|
||||
_LOGW (LOGD_DEVICE, "ip-ifindex: ifindex %d not found", ifindex);
|
||||
return FALSE;
|
||||
}
|
||||
name = plink->name;
|
||||
} else
|
||||
g_return_val_if_fail (ifindex == 0, FALSE);
|
||||
_LOGD (LOGD_DEVICE, "ip-ifindex: update ip-interface to %s%s%s, ifindex %d",
|
||||
NM_PRINT_FMT_QUOTE_STRING (ifname),
|
||||
ifindex);
|
||||
|
||||
if (priv->ip_ifindex == ifindex)
|
||||
return TRUE;
|
||||
|
||||
_LOGD (LOGD_DEVICE, "ip-ifindex: update ifindex to %d", ifindex);
|
||||
priv->ip_ifindex = ifindex;
|
||||
if (!nm_streq0 (priv->ip_iface, name)) {
|
||||
_LOGD (LOGD_DEVICE, "ip-ifindex: update ip-iface to %s%s%s",
|
||||
NM_PRINT_FMT_QUOTED (name, "\"", name, "\"", "NULL"));
|
||||
priv->ip_iface = g_strdup (name);
|
||||
if (!eq_name) {
|
||||
g_free (priv->ip_iface);
|
||||
priv->ip_iface = g_strdup (ifname);
|
||||
_notify (self, PROP_IP_IFACE);
|
||||
}
|
||||
|
||||
if (priv->ip_ifindex > 0) {
|
||||
if (nm_platform_check_kernel_support (nm_device_get_platform (self),
|
||||
NM_PLATFORM_KERNEL_SUPPORT_USER_IPV6LL))
|
||||
nm_platform_link_set_user_ipv6ll_enabled (nm_device_get_platform (self), priv->ip_ifindex, TRUE);
|
||||
platform = nm_device_get_platform (self);
|
||||
|
||||
if (!nm_platform_link_is_up (nm_device_get_platform (self), priv->ip_ifindex))
|
||||
nm_platform_link_set_up (nm_device_get_platform (self), priv->ip_ifindex, NULL);
|
||||
nm_platform_process_events_ensure_link (platform,
|
||||
priv->ip_ifindex,
|
||||
priv->ip_iface);
|
||||
|
||||
if (nm_platform_check_kernel_support (platform,
|
||||
NM_PLATFORM_KERNEL_SUPPORT_USER_IPV6LL))
|
||||
nm_platform_link_set_user_ipv6ll_enabled (platform, priv->ip_ifindex, TRUE);
|
||||
|
||||
if (!nm_platform_link_is_up (platform, priv->ip_ifindex))
|
||||
nm_platform_link_set_up (platform, priv->ip_ifindex, NULL);
|
||||
}
|
||||
|
||||
/* We don't care about any saved values from the old iface */
|
||||
g_hash_table_remove_all (priv->ip6_saved_properties);
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
gboolean
|
||||
nm_device_set_ip_ifindex (NMDevice *self, int ifindex)
|
||||
{
|
||||
char ifname_buf[IFNAMSIZ];
|
||||
const char *ifname = NULL;
|
||||
|
||||
g_return_val_if_fail (NM_IS_DEVICE (self), FALSE);
|
||||
g_return_val_if_fail (nm_device_is_activating (self), FALSE);
|
||||
|
||||
if (ifindex > 0) {
|
||||
ifname = nm_platform_if_indextoname (nm_device_get_platform (self), ifindex, ifname_buf);
|
||||
if (!ifname)
|
||||
_LOGW (LOGD_DEVICE, "ip-ifindex: ifindex %d not found", ifindex);
|
||||
}
|
||||
|
||||
_set_ip_ifindex (self, ifindex, ifname);
|
||||
return ifindex > 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* nm_device_set_ip_iface:
|
||||
* @self: the #NMDevice
|
||||
* @iface: the new IP interface name
|
||||
* @ifname: the new IP interface name
|
||||
*
|
||||
* Updates the IP interface name and possibly the ifindex.
|
||||
*
|
||||
* Returns: %TRUE if the anything (name or ifindex) changed, %FALSE if nothing
|
||||
* changed.
|
||||
* Returns: %TRUE if an interface with name @ifname exists,
|
||||
* and %FALSE, if @ifname is %NULL or no such interface exists.
|
||||
*/
|
||||
gboolean
|
||||
nm_device_set_ip_iface (NMDevice *self, const char *iface)
|
||||
nm_device_set_ip_iface (NMDevice *self, const char *ifname)
|
||||
{
|
||||
NMDevicePrivate *priv;
|
||||
int ifindex;
|
||||
int ifindex = 0;
|
||||
|
||||
g_return_val_if_fail (NM_IS_DEVICE (self), FALSE);
|
||||
g_return_val_if_fail (nm_device_is_activating (self), FALSE);
|
||||
|
||||
priv = NM_DEVICE_GET_PRIVATE (self);
|
||||
if (nm_streq0 (iface, priv->ip_iface)) {
|
||||
if (!iface)
|
||||
return FALSE;
|
||||
ifindex = nm_platform_if_nametoindex (nm_device_get_platform (self), iface);
|
||||
if ( ifindex <= 0
|
||||
|| priv->ip_ifindex == ifindex)
|
||||
return FALSE;
|
||||
|
||||
priv->ip_ifindex = ifindex;
|
||||
_LOGD (LOGD_DEVICE, "ip-ifname: update ifindex for ifname '%s': %d", iface, priv->ip_ifindex);
|
||||
} else {
|
||||
g_free (priv->ip_iface);
|
||||
priv->ip_iface = g_strdup (iface);
|
||||
|
||||
if (iface) {
|
||||
/* The @iface name is not in sync with the platform cache.
|
||||
* So, there is no point asking the platform cache to resolve
|
||||
* the ifindex. Instead, we can only hope that the interface
|
||||
* with this name still exists and we resolve the ifindex
|
||||
* anew.
|
||||
*/
|
||||
priv->ip_ifindex = nm_platform_if_nametoindex (nm_device_get_platform (self), iface);
|
||||
if (priv->ip_ifindex > 0)
|
||||
_LOGD (LOGD_DEVICE, "ip-ifname: set ifname '%s', ifindex %d", iface, priv->ip_ifindex);
|
||||
else
|
||||
_LOGW (LOGD_DEVICE, "ip-ifname: set ifname '%s', unknown ifindex", iface);
|
||||
} else {
|
||||
priv->ip_ifindex = 0;
|
||||
_LOGD (LOGD_DEVICE, "ip-ifname: clear ifname");
|
||||
}
|
||||
if (ifname) {
|
||||
ifindex = nm_platform_if_nametoindex (nm_device_get_platform (self), ifname);
|
||||
if (ifindex <= 0)
|
||||
_LOGW (LOGD_DEVICE, "ip-ifindex: ifname %s not found", ifname);
|
||||
}
|
||||
|
||||
if (priv->ip_ifindex > 0) {
|
||||
if (nm_platform_check_kernel_support (nm_device_get_platform (self),
|
||||
NM_PLATFORM_KERNEL_SUPPORT_USER_IPV6LL))
|
||||
nm_platform_link_set_user_ipv6ll_enabled (nm_device_get_platform (self), priv->ip_ifindex, TRUE);
|
||||
|
||||
if (!nm_platform_link_is_up (nm_device_get_platform (self), priv->ip_ifindex))
|
||||
nm_platform_link_set_up (nm_device_get_platform (self), priv->ip_ifindex, NULL);
|
||||
}
|
||||
|
||||
/* We don't care about any saved values from the old iface */
|
||||
g_hash_table_remove_all (priv->ip6_saved_properties);
|
||||
|
||||
_notify (self, PROP_IP_IFACE);
|
||||
return TRUE;
|
||||
_set_ip_ifindex (self, ifindex, ifname);
|
||||
return ifindex > 0;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
|
|
@ -12941,7 +12917,7 @@ _cleanup_generic_post (NMDevice *self, CleanupType cleanup_type)
|
|||
* those are identified by ip_iface, not by iface (which might be a tty
|
||||
* or ATM device).
|
||||
*/
|
||||
nm_device_set_ip_iface (self, NULL);
|
||||
_set_ip_ifindex (self, 0, NULL);
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
|
|||
|
|
@ -11,10 +11,10 @@ global:
|
|||
nm_modem_get_capabilities;
|
||||
nm_modem_get_configured_mtu;
|
||||
nm_modem_get_control_port;
|
||||
nm_modem_get_data_port;
|
||||
nm_modem_get_driver;
|
||||
nm_modem_get_iid;
|
||||
nm_modem_get_path;
|
||||
nm_modem_get_ip_ifindex;
|
||||
nm_modem_get_secrets;
|
||||
nm_modem_get_state;
|
||||
nm_modem_get_type;
|
||||
|
|
|
|||
|
|
@ -260,21 +260,26 @@ modem_ip6_config_result (NMModem *modem,
|
|||
}
|
||||
|
||||
static void
|
||||
data_port_changed_cb (NMModem *modem, GParamSpec *pspec, gpointer user_data)
|
||||
ip_ifindex_changed_cb (NMModem *modem, GParamSpec *pspec, gpointer user_data)
|
||||
{
|
||||
NMDevice *self = NM_DEVICE (user_data);
|
||||
gboolean changed;
|
||||
NMDevice *device = NM_DEVICE (user_data);
|
||||
|
||||
/* We set the IP iface in the device as soon as we know it, so that we
|
||||
* properly ifup it if needed */
|
||||
changed = nm_device_set_ip_iface (self, nm_modem_get_data_port (modem));
|
||||
if (!nm_device_is_activating (device))
|
||||
return;
|
||||
|
||||
if (!nm_device_set_ip_ifindex (device,
|
||||
nm_modem_get_ip_ifindex (modem))) {
|
||||
nm_device_state_changed (device,
|
||||
NM_DEVICE_STATE_FAILED,
|
||||
NM_DEVICE_STATE_REASON_IP_CONFIG_UNAVAILABLE);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Disable IPv6 immediately on the interface since NM handles IPv6
|
||||
* internally, and leaving it enabled could allow the kernel's IPv6
|
||||
* RA handling code to run before NM is ready.
|
||||
*/
|
||||
if (changed)
|
||||
nm_device_ipv6_sysctl_set (self, "disable_ipv6", "1");
|
||||
nm_device_ipv6_sysctl_set (device, "disable_ipv6", "1");
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -629,11 +634,7 @@ set_modem (NMDeviceModem *self, NMModem *modem)
|
|||
g_signal_connect (modem, NM_MODEM_STATE_CHANGED, G_CALLBACK (modem_state_cb), self);
|
||||
g_signal_connect (modem, NM_MODEM_REMOVED, G_CALLBACK (modem_removed_cb), self);
|
||||
|
||||
/* In the old ModemManager the data port is known from the very beginning;
|
||||
* while in the new ModemManager the data port is set afterwards when the bearer gets
|
||||
* created */
|
||||
g_signal_connect (modem, "notify::" NM_MODEM_DATA_PORT, G_CALLBACK (data_port_changed_cb), self);
|
||||
|
||||
g_signal_connect (modem, "notify::" NM_MODEM_IP_IFINDEX, G_CALLBACK (ip_ifindex_changed_cb), self);
|
||||
g_signal_connect (modem, "notify::" NM_MODEM_DEVICE_ID, G_CALLBACK (ids_changed_cb), self);
|
||||
g_signal_connect (modem, "notify::" NM_MODEM_SIM_ID, G_CALLBACK (ids_changed_cb), self);
|
||||
g_signal_connect (modem, "notify::" NM_MODEM_SIM_OPERATOR_ID, G_CALLBACK (ids_changed_cb), self);
|
||||
|
|
@ -708,34 +709,23 @@ nm_device_modem_new (NMModem *modem)
|
|||
{
|
||||
NMDeviceModemCapabilities caps = NM_DEVICE_MODEM_CAPABILITY_NONE;
|
||||
NMDeviceModemCapabilities current_caps = NM_DEVICE_MODEM_CAPABILITY_NONE;
|
||||
NMDevice *device;
|
||||
const char *data_port;
|
||||
|
||||
g_return_val_if_fail (NM_IS_MODEM (modem), NULL);
|
||||
|
||||
/* Load capabilities */
|
||||
nm_modem_get_capabilities (modem, &caps, ¤t_caps);
|
||||
|
||||
device = (NMDevice *) g_object_new (NM_TYPE_DEVICE_MODEM,
|
||||
NM_DEVICE_UDI, nm_modem_get_path (modem),
|
||||
NM_DEVICE_IFACE, nm_modem_get_uid (modem),
|
||||
NM_DEVICE_DRIVER, nm_modem_get_driver (modem),
|
||||
NM_DEVICE_TYPE_DESC, "Broadband",
|
||||
NM_DEVICE_DEVICE_TYPE, NM_DEVICE_TYPE_MODEM,
|
||||
NM_DEVICE_RFKILL_TYPE, RFKILL_TYPE_WWAN,
|
||||
NM_DEVICE_MODEM_MODEM, modem,
|
||||
NM_DEVICE_MODEM_CAPABILITIES, caps,
|
||||
NM_DEVICE_MODEM_CURRENT_CAPABILITIES, current_caps,
|
||||
NULL);
|
||||
|
||||
/* If the data port is known, set it as the IP interface immediately */
|
||||
data_port = nm_modem_get_data_port (modem);
|
||||
if (data_port) {
|
||||
nm_device_set_ip_iface (device, data_port);
|
||||
nm_device_ipv6_sysctl_set (device, "disable_ipv6", "1");
|
||||
}
|
||||
|
||||
return device;
|
||||
return g_object_new (NM_TYPE_DEVICE_MODEM,
|
||||
NM_DEVICE_UDI, nm_modem_get_path (modem),
|
||||
NM_DEVICE_IFACE, nm_modem_get_uid (modem),
|
||||
NM_DEVICE_DRIVER, nm_modem_get_driver (modem),
|
||||
NM_DEVICE_TYPE_DESC, "Broadband",
|
||||
NM_DEVICE_DEVICE_TYPE, NM_DEVICE_TYPE_MODEM,
|
||||
NM_DEVICE_RFKILL_TYPE, RFKILL_TYPE_WWAN,
|
||||
NM_DEVICE_MODEM_MODEM, modem,
|
||||
NM_DEVICE_MODEM_CAPABILITIES, caps,
|
||||
NM_DEVICE_MODEM_CURRENT_CAPABILITIES, current_caps,
|
||||
NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -743,9 +733,10 @@ dispose (GObject *object)
|
|||
{
|
||||
NMDeviceModemPrivate *priv = NM_DEVICE_MODEM_GET_PRIVATE ((NMDeviceModem *) object);
|
||||
|
||||
if (priv->modem)
|
||||
if (priv->modem) {
|
||||
g_signal_handlers_disconnect_by_data (priv->modem, NM_DEVICE_MODEM (object));
|
||||
g_clear_object (&priv->modem);
|
||||
g_clear_object (&priv->modem);
|
||||
}
|
||||
|
||||
G_OBJECT_CLASS (nm_device_modem_parent_class)->dispose (object);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -385,9 +385,10 @@ connect_ready (MMModemSimple *simple_iface,
|
|||
g_dbus_error_strip_remote_error (error);
|
||||
ctx->first_error = error;
|
||||
} else
|
||||
g_error_free (error);
|
||||
g_clear_error (&error);
|
||||
|
||||
if (ctx->ip_type_tries == 0 && g_error_matches (error, MM_CORE_ERROR, MM_CORE_ERROR_RETRY)) {
|
||||
if ( ctx->ip_type_tries == 0
|
||||
&& g_error_matches (error, MM_CORE_ERROR, MM_CORE_ERROR_RETRY)) {
|
||||
/* Try one more time */
|
||||
ctx->ip_type_tries++;
|
||||
} else {
|
||||
|
|
@ -410,21 +411,20 @@ connect_ready (MMModemSimple *simple_iface,
|
|||
if (self->_priv.ipv6_config)
|
||||
ip6_method = get_bearer_ip_method (self->_priv.ipv6_config);
|
||||
|
||||
if (ip4_method == NM_MODEM_IP_METHOD_UNKNOWN &&
|
||||
ip6_method == NM_MODEM_IP_METHOD_UNKNOWN) {
|
||||
_LOGW ("failed to connect modem: invalid bearer IP configuration");
|
||||
if (!nm_modem_set_data_port (NM_MODEM (self),
|
||||
NM_PLATFORM_GET,
|
||||
mm_bearer_get_interface (self->_priv.bearer),
|
||||
ip4_method,
|
||||
ip6_method,
|
||||
mm_bearer_get_ip_timeout (self->_priv.bearer),
|
||||
&error)) {
|
||||
_LOGW ("failed to connect modem: %s", error->message);
|
||||
g_error_free (error);
|
||||
nm_modem_emit_prepare_result (NM_MODEM (self), FALSE, NM_DEVICE_STATE_REASON_CONFIG_FAILED);
|
||||
connect_context_clear (self);
|
||||
return;
|
||||
}
|
||||
|
||||
g_object_set (self,
|
||||
NM_MODEM_DATA_PORT, mm_bearer_get_interface (self->_priv.bearer),
|
||||
NM_MODEM_IP4_METHOD, ip4_method,
|
||||
NM_MODEM_IP6_METHOD, ip6_method,
|
||||
NM_MODEM_IP_TIMEOUT, mm_bearer_get_ip_timeout (self->_priv.bearer),
|
||||
NULL);
|
||||
|
||||
ctx->step++;
|
||||
connect_context_step (self);
|
||||
}
|
||||
|
|
@ -1409,35 +1409,34 @@ nm_modem_broadband_init (NMModemBroadband *self)
|
|||
NMModem *
|
||||
nm_modem_broadband_new (GObject *object, GError **error)
|
||||
{
|
||||
NMModem *modem;
|
||||
MMObject *modem_object;
|
||||
MMModem *modem_iface;
|
||||
gchar *drivers;
|
||||
const char *const*drivers;
|
||||
gs_free char *driver = NULL;
|
||||
|
||||
g_return_val_if_fail (MM_IS_OBJECT (object), NULL);
|
||||
modem_object = MM_OBJECT (object);
|
||||
|
||||
/* Ensure we have the 'Modem' interface and the primary port at least */
|
||||
modem_iface = mm_object_peek_modem (modem_object);
|
||||
g_return_val_if_fail (!!modem_iface, NULL);
|
||||
g_return_val_if_fail (!!mm_modem_get_primary_port (modem_iface), NULL);
|
||||
g_return_val_if_fail (modem_iface, NULL);
|
||||
g_return_val_if_fail (mm_modem_get_primary_port (modem_iface), NULL);
|
||||
|
||||
/* Build a single string with all drivers listed */
|
||||
drivers = g_strjoinv (", ", (gchar **)mm_modem_get_drivers (modem_iface));
|
||||
drivers = mm_modem_get_drivers (modem_iface);
|
||||
if (drivers)
|
||||
driver = g_strjoinv (", ", (char **) drivers);
|
||||
|
||||
modem = g_object_new (NM_TYPE_MODEM_BROADBAND,
|
||||
NM_MODEM_PATH, mm_object_get_path (modem_object),
|
||||
NM_MODEM_UID, mm_modem_get_primary_port (modem_iface),
|
||||
NM_MODEM_CONTROL_PORT, mm_modem_get_primary_port (modem_iface),
|
||||
NM_MODEM_DATA_PORT, NULL, /* We don't know it until bearer created */
|
||||
NM_MODEM_IP_TYPES, mm_ip_family_to_nm (mm_modem_get_supported_ip_families (modem_iface)),
|
||||
NM_MODEM_STATE, (int) mm_state_to_nm (mm_modem_get_state (modem_iface)),
|
||||
NM_MODEM_DEVICE_ID, mm_modem_get_device_identifier (modem_iface),
|
||||
NM_MODEM_BROADBAND_MODEM, modem_object,
|
||||
NM_MODEM_DRIVER, drivers,
|
||||
NULL);
|
||||
g_free (drivers);
|
||||
return modem;
|
||||
return g_object_new (NM_TYPE_MODEM_BROADBAND,
|
||||
NM_MODEM_PATH, mm_object_get_path (modem_object),
|
||||
NM_MODEM_UID, mm_modem_get_primary_port (modem_iface),
|
||||
NM_MODEM_CONTROL_PORT, mm_modem_get_primary_port (modem_iface),
|
||||
NM_MODEM_IP_TYPES, mm_ip_family_to_nm (mm_modem_get_supported_ip_families (modem_iface)),
|
||||
NM_MODEM_STATE, (int) mm_state_to_nm (mm_modem_get_state (modem_iface)),
|
||||
NM_MODEM_DEVICE_ID, mm_modem_get_device_identifier (modem_iface),
|
||||
NM_MODEM_BROADBAND_MODEM, modem_object,
|
||||
NM_MODEM_DRIVER, driver,
|
||||
NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
|
|||
|
|
@ -836,6 +836,7 @@ context_property_changed (GDBusProxy *proxy,
|
|||
guint32 address_network, gateway_network;
|
||||
guint32 ip4_route_table, ip4_route_metric;
|
||||
int ifindex;
|
||||
GError *error = NULL;
|
||||
|
||||
_LOGD ("PropertyChanged: %s", property);
|
||||
|
||||
|
|
@ -860,27 +861,26 @@ context_property_changed (GDBusProxy *proxy,
|
|||
_LOGW ("Settings 'Interface' missing");
|
||||
goto out;
|
||||
}
|
||||
if (!interface || !interface[0]) {
|
||||
_LOGW ("Settings 'Interface'; empty");
|
||||
goto out;
|
||||
}
|
||||
|
||||
ifindex = nm_platform_link_get_ifindex (NM_PLATFORM_GET, interface);
|
||||
if (ifindex <= 0) {
|
||||
_LOGW ("Interface \"%s\" not found", interface);
|
||||
goto out;
|
||||
}
|
||||
|
||||
_LOGD ("Interface: %s", interface);
|
||||
g_object_set (self,
|
||||
NM_MODEM_DATA_PORT, interface,
|
||||
NM_MODEM_IP4_METHOD, NM_MODEM_IP_METHOD_STATIC,
|
||||
NULL);
|
||||
if (!nm_modem_set_data_port (NM_MODEM (self),
|
||||
NM_PLATFORM_GET,
|
||||
interface,
|
||||
NM_MODEM_IP_METHOD_STATIC,
|
||||
NM_MODEM_IP_METHOD_UNKNOWN,
|
||||
0,
|
||||
&error)) {
|
||||
_LOGW ("failed to connect to modem: %s", error->message);
|
||||
g_clear_error (&error);
|
||||
goto out;
|
||||
}
|
||||
|
||||
ifindex = nm_modem_get_ip_ifindex (NM_MODEM (self));
|
||||
nm_assert (ifindex > 0);
|
||||
|
||||
/* TODO: verify handling of ip4_config; check other places it's used... */
|
||||
g_clear_object (&priv->ip4_config);
|
||||
|
||||
|
||||
priv->ip4_config = nm_ip4_config_new (nm_platform_get_multi_idx (NM_PLATFORM_GET),
|
||||
ifindex);
|
||||
|
||||
|
|
|
|||
|
|
@ -44,13 +44,10 @@
|
|||
|
||||
NM_GOBJECT_PROPERTIES_DEFINE (NMModem,
|
||||
PROP_CONTROL_PORT,
|
||||
PROP_DATA_PORT,
|
||||
PROP_IP_IFINDEX,
|
||||
PROP_PATH,
|
||||
PROP_UID,
|
||||
PROP_DRIVER,
|
||||
PROP_IP4_METHOD,
|
||||
PROP_IP6_METHOD,
|
||||
PROP_IP_TIMEOUT,
|
||||
PROP_STATE,
|
||||
PROP_DEVICE_ID,
|
||||
PROP_SIM_ID,
|
||||
|
|
@ -79,7 +76,12 @@ typedef struct _NMModemPrivate {
|
|||
char *driver;
|
||||
char *control_port;
|
||||
char *data_port;
|
||||
char *ppp_iface;
|
||||
|
||||
/* TODO: ip_iface is solely used for nm_modem_owns_port().
|
||||
* We should rework the code that it's not necessary */
|
||||
char *ip_iface;
|
||||
|
||||
int ip_ifindex;
|
||||
NMModemIPMethod ip4_method;
|
||||
NMModemIPMethod ip6_method;
|
||||
NMUtilsIPv6IfaceId iid;
|
||||
|
|
@ -96,7 +98,7 @@ typedef struct _NMModemPrivate {
|
|||
guint32 secrets_tries;
|
||||
NMActRequestGetSecretsCallId *secrets_id;
|
||||
|
||||
guint32 mm_ip_timeout;
|
||||
guint mm_ip_timeout;
|
||||
|
||||
guint32 ip4_route_table;
|
||||
guint32 ip4_route_metric;
|
||||
|
|
@ -152,6 +154,10 @@ _nmlog_prefix (char *prefix, NMModem *self)
|
|||
_NM_UTILS_MACRO_REST (__VA_ARGS__)); \
|
||||
} G_STMT_END
|
||||
|
||||
/*****************************************************************************/
|
||||
|
||||
static void _set_ip_ifindex (NMModem *self, int ifindex, const char *ifname);
|
||||
|
||||
/*****************************************************************************/
|
||||
/* State/enabled/connected */
|
||||
|
||||
|
|
@ -456,16 +462,18 @@ ppp_ifindex_set (NMPPPManager *ppp_manager,
|
|||
gpointer user_data)
|
||||
{
|
||||
NMModem *self = NM_MODEM (user_data);
|
||||
NMModemPrivate *priv = NM_MODEM_GET_PRIVATE (self);
|
||||
|
||||
/* Notify about the new data port to use.
|
||||
*
|
||||
* @iface might be %NULL. */
|
||||
if (g_strcmp0 (priv->data_port, iface) != 0) {
|
||||
g_free (priv->data_port);
|
||||
priv->data_port = g_strdup (iface);
|
||||
_notify (self, PROP_DATA_PORT);
|
||||
nm_assert (ifindex >= 0);
|
||||
nm_assert (NM_MODEM_GET_PRIVATE (self)->ppp_manager == ppp_manager);
|
||||
|
||||
if (ifindex <= 0 && iface) {
|
||||
/* this might happen, if the ifname was already deleted
|
||||
* and we failed to resolve ifindex.
|
||||
*
|
||||
* Forget about the name. */
|
||||
iface = NULL;
|
||||
}
|
||||
_set_ip_ifindex (self, ifindex, iface);
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -556,6 +564,18 @@ port_speed_is_zero (const char *port)
|
|||
{
|
||||
struct termios options;
|
||||
nm_auto_close int fd = -1;
|
||||
gs_free char *path = NULL;
|
||||
|
||||
nm_assert (port);
|
||||
|
||||
if (port[0] != '/') {
|
||||
if ( !port[0]
|
||||
|| strchr (port, '/')
|
||||
|| NM_IN_STRSET (port, ".", ".."))
|
||||
return FALSE;
|
||||
path = g_build_path ("/sys/class/tty", port, NULL);
|
||||
port = path;
|
||||
}
|
||||
|
||||
fd = open (port, O_RDWR | O_NONBLOCK | O_NOCTTY | O_CLOEXEC);
|
||||
if (fd < 0)
|
||||
|
|
@ -597,6 +617,12 @@ ppp_stage3_ip_config_start (NMModem *self,
|
|||
return NM_ACT_STAGE_RETURN_FAILURE;
|
||||
}
|
||||
|
||||
if (!priv->data_port) {
|
||||
_LOGE ("error starting PPP (no data port)");
|
||||
NM_SET_OUT (out_failure_reason, NM_DEVICE_STATE_REASON_PPP_START_FAILED);
|
||||
return NM_ACT_STAGE_RETURN_FAILURE;
|
||||
}
|
||||
|
||||
/* Check if ModemManager requested a specific IP timeout to be used. If 0 reported,
|
||||
* use the default one (30s) */
|
||||
if (priv->mm_ip_timeout > 0) {
|
||||
|
|
@ -628,9 +654,7 @@ ppp_stage3_ip_config_start (NMModem *self,
|
|||
ip_timeout, baud_override, &error)) {
|
||||
_LOGE ("error starting PPP: %s", error->message);
|
||||
g_error_free (error);
|
||||
|
||||
g_clear_object (&priv->ppp_manager);
|
||||
|
||||
NM_SET_OUT (out_failure_reason, NM_DEVICE_STATE_REASON_PPP_START_FAILED);
|
||||
return NM_ACT_STAGE_RETURN_FAILURE;
|
||||
}
|
||||
|
|
@ -1097,7 +1121,10 @@ deactivate_cleanup (NMModem *self, NMDevice *device)
|
|||
|
||||
priv->in_bytes = priv->out_bytes = 0;
|
||||
|
||||
g_clear_object (&priv->ppp_manager);
|
||||
if (priv->ppp_manager) {
|
||||
g_signal_handlers_disconnect_by_data (priv->ppp_manager, self);
|
||||
g_clear_object (&priv->ppp_manager);
|
||||
}
|
||||
|
||||
if (device) {
|
||||
g_return_if_fail (NM_IS_DEVICE (device));
|
||||
|
|
@ -1116,11 +1143,12 @@ deactivate_cleanup (NMModem *self, NMDevice *device)
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
nm_clear_g_free (&priv->data_port);
|
||||
priv->mm_ip_timeout = 0;
|
||||
priv->ip4_method = NM_MODEM_IP_METHOD_UNKNOWN;
|
||||
priv->ip6_method = NM_MODEM_IP_METHOD_UNKNOWN;
|
||||
|
||||
g_free (priv->ppp_iface);
|
||||
priv->ppp_iface = NULL;
|
||||
_set_ip_ifindex (self, -1, NULL);
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
|
@ -1371,17 +1399,117 @@ nm_modem_get_control_port (NMModem *self)
|
|||
return NM_MODEM_GET_PRIVATE (self)->control_port;
|
||||
}
|
||||
|
||||
const char *
|
||||
nm_modem_get_data_port (NMModem *self)
|
||||
int
|
||||
nm_modem_get_ip_ifindex (NMModem *self)
|
||||
{
|
||||
g_return_val_if_fail (NM_IS_MODEM (self), NULL);
|
||||
NMModemPrivate *priv;
|
||||
|
||||
/* The ppp_iface takes precedence over the data interface when PPP is used,
|
||||
* since data_iface is the TTY over which PPP is run, and that TTY can't
|
||||
* do IP. The caller really wants the thing that's doing IP.
|
||||
*/
|
||||
return NM_MODEM_GET_PRIVATE (self)->ppp_iface ?
|
||||
NM_MODEM_GET_PRIVATE (self)->ppp_iface : NM_MODEM_GET_PRIVATE (self)->data_port;
|
||||
g_return_val_if_fail (NM_IS_MODEM (self), 0);
|
||||
|
||||
priv = NM_MODEM_GET_PRIVATE (self);
|
||||
|
||||
/* internally we track an unset ip_ifindex as -1.
|
||||
* For the caller of nm_modem_get_ip_ifindex(), this
|
||||
* shall be zero too. */
|
||||
return priv->ip_ifindex != -1 ? priv->ip_ifindex : 0;
|
||||
}
|
||||
|
||||
static void
|
||||
_set_ip_ifindex (NMModem *self, int ifindex, const char *ifname)
|
||||
{
|
||||
NMModemPrivate *priv = NM_MODEM_GET_PRIVATE (self);
|
||||
|
||||
nm_assert (ifindex >= -1);
|
||||
nm_assert ((ifindex > 0) == !!ifname);
|
||||
|
||||
if (!nm_streq0 (priv->ip_iface, ifname)) {
|
||||
g_free (priv->ip_iface);
|
||||
priv->ip_iface = g_strdup (ifname);
|
||||
}
|
||||
|
||||
if (priv->ip_ifindex != ifindex) {
|
||||
priv->ip_ifindex = ifindex;
|
||||
_notify (self, PROP_IP_IFINDEX);
|
||||
}
|
||||
}
|
||||
|
||||
gboolean
|
||||
nm_modem_set_data_port (NMModem *self,
|
||||
NMPlatform *platform,
|
||||
const char *data_port,
|
||||
NMModemIPMethod ip4_method,
|
||||
NMModemIPMethod ip6_method,
|
||||
guint timeout,
|
||||
GError **error)
|
||||
{
|
||||
NMModemPrivate *priv;
|
||||
gboolean is_ppp;
|
||||
int ifindex = -1;
|
||||
|
||||
g_return_val_if_fail (NM_IS_MODEM (self), FALSE);
|
||||
g_return_val_if_fail (NM_IS_PLATFORM (platform), FALSE);
|
||||
g_return_val_if_fail (!error || !*error, FALSE);
|
||||
|
||||
priv = NM_MODEM_GET_PRIVATE (self);
|
||||
|
||||
if ( priv->ppp_manager
|
||||
|| priv->data_port
|
||||
|| priv->ip_ifindex != -1) {
|
||||
g_set_error_literal (error, NM_UTILS_ERROR, NM_UTILS_ERROR_UNKNOWN,
|
||||
"cannot set data port in activated state");
|
||||
/* this really shouldn't happen. Assert. */
|
||||
g_return_val_if_reached (FALSE);
|
||||
}
|
||||
|
||||
if (!data_port) {
|
||||
g_set_error_literal (error, NM_UTILS_ERROR, NM_UTILS_ERROR_UNKNOWN,
|
||||
"missing data port");
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
is_ppp = (ip4_method == NM_MODEM_IP_METHOD_PPP)
|
||||
|| (ip6_method == NM_MODEM_IP_METHOD_PPP);
|
||||
if (is_ppp) {
|
||||
if ( !NM_IN_SET (ip4_method, NM_MODEM_IP_METHOD_UNKNOWN, NM_MODEM_IP_METHOD_PPP)
|
||||
|| !NM_IN_SET (ip6_method, NM_MODEM_IP_METHOD_UNKNOWN, NM_MODEM_IP_METHOD_PPP)) {
|
||||
g_set_error_literal (error, NM_UTILS_ERROR, NM_UTILS_ERROR_UNKNOWN,
|
||||
"conflicting ip methods");
|
||||
return FALSE;
|
||||
}
|
||||
} else if ( !NM_IN_SET (ip4_method, NM_MODEM_IP_METHOD_UNKNOWN, NM_MODEM_IP_METHOD_STATIC, NM_MODEM_IP_METHOD_AUTO)
|
||||
|| !NM_IN_SET (ip6_method, NM_MODEM_IP_METHOD_UNKNOWN, NM_MODEM_IP_METHOD_STATIC, NM_MODEM_IP_METHOD_AUTO)
|
||||
|| ( ip4_method == NM_MODEM_IP_METHOD_UNKNOWN
|
||||
&& ip6_method == NM_MODEM_IP_METHOD_UNKNOWN)) {
|
||||
g_set_error_literal (error, NM_UTILS_ERROR, NM_UTILS_ERROR_UNKNOWN,
|
||||
"invalid ip methods");
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (!is_ppp) {
|
||||
ifindex = nm_platform_if_nametoindex (platform, data_port);
|
||||
if (ifindex <= 0) {
|
||||
g_set_error (error, NM_UTILS_ERROR, NM_UTILS_ERROR_UNKNOWN,
|
||||
"cannot find network interface %s", data_port);
|
||||
return FALSE;
|
||||
}
|
||||
if (!nm_platform_process_events_ensure_link (platform, ifindex, data_port)) {
|
||||
g_set_error (error, NM_UTILS_ERROR, NM_UTILS_ERROR_UNKNOWN,
|
||||
"cannot find network interface %s in platform cache", data_port);
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
priv->mm_ip_timeout = timeout;
|
||||
priv->ip4_method = ip4_method;
|
||||
priv->ip6_method = ip6_method;
|
||||
if (is_ppp) {
|
||||
priv->data_port = g_strdup (data_port);
|
||||
_set_ip_ifindex (self, -1, NULL);
|
||||
} else {
|
||||
priv->data_port = NULL;
|
||||
_set_ip_ifindex (self, ifindex, data_port);
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
gboolean
|
||||
|
|
@ -1394,15 +1522,10 @@ nm_modem_owns_port (NMModem *self, const char *iface)
|
|||
if (NM_MODEM_GET_CLASS (self)->owns_port)
|
||||
return NM_MODEM_GET_CLASS (self)->owns_port (self, iface);
|
||||
|
||||
/* Fall back to data/control ports */
|
||||
if (priv->ppp_iface && (strcmp (priv->ppp_iface, iface) == 0))
|
||||
return TRUE;
|
||||
if (priv->data_port && (strcmp (priv->data_port, iface) == 0))
|
||||
return TRUE;
|
||||
if (priv->control_port && (strcmp (priv->control_port, iface) == 0))
|
||||
return TRUE;
|
||||
|
||||
return FALSE;
|
||||
return NM_IN_STRSET (iface,
|
||||
priv->ip_iface,
|
||||
priv->data_port,
|
||||
priv->control_port);
|
||||
}
|
||||
|
||||
gboolean
|
||||
|
|
@ -1502,7 +1625,8 @@ static void
|
|||
get_property (GObject *object, guint prop_id,
|
||||
GValue *value, GParamSpec *pspec)
|
||||
{
|
||||
NMModemPrivate *priv = NM_MODEM_GET_PRIVATE ((NMModem *) object);
|
||||
NMModem *self = NM_MODEM (object);
|
||||
NMModemPrivate *priv = NM_MODEM_GET_PRIVATE (self);
|
||||
|
||||
switch (prop_id) {
|
||||
case PROP_PATH:
|
||||
|
|
@ -1514,21 +1638,12 @@ get_property (GObject *object, guint prop_id,
|
|||
case PROP_CONTROL_PORT:
|
||||
g_value_set_string (value, priv->control_port);
|
||||
break;
|
||||
case PROP_DATA_PORT:
|
||||
g_value_set_string (value, nm_modem_get_data_port (NM_MODEM (object)));
|
||||
case PROP_IP_IFINDEX:
|
||||
g_value_set_int (value, nm_modem_get_ip_ifindex (self));
|
||||
break;
|
||||
case PROP_UID:
|
||||
g_value_set_string (value, priv->uid);
|
||||
break;
|
||||
case PROP_IP4_METHOD:
|
||||
g_value_set_uint (value, priv->ip4_method);
|
||||
break;
|
||||
case PROP_IP6_METHOD:
|
||||
g_value_set_uint (value, priv->ip6_method);
|
||||
break;
|
||||
case PROP_IP_TIMEOUT:
|
||||
g_value_set_uint (value, priv->mm_ip_timeout);
|
||||
break;
|
||||
case PROP_STATE:
|
||||
g_value_set_int (value, priv->state);
|
||||
break;
|
||||
|
|
@ -1571,23 +1686,10 @@ set_property (GObject *object, guint prop_id,
|
|||
/* construct-only */
|
||||
priv->control_port = g_value_dup_string (value);
|
||||
break;
|
||||
case PROP_DATA_PORT:
|
||||
g_free (priv->data_port);
|
||||
priv->data_port = g_value_dup_string (value);
|
||||
break;
|
||||
case PROP_UID:
|
||||
/* construct-only */
|
||||
priv->uid = g_value_dup_string (value);
|
||||
break;
|
||||
case PROP_IP4_METHOD:
|
||||
priv->ip4_method = g_value_get_uint (value);
|
||||
break;
|
||||
case PROP_IP6_METHOD:
|
||||
priv->ip6_method = g_value_get_uint (value);
|
||||
break;
|
||||
case PROP_IP_TIMEOUT:
|
||||
priv->mm_ip_timeout = g_value_get_uint (value);
|
||||
break;
|
||||
case PROP_STATE:
|
||||
/* construct-only */
|
||||
priv->state = g_value_get_int (value);
|
||||
|
|
@ -1625,6 +1727,7 @@ nm_modem_init (NMModem *self)
|
|||
self->_priv = G_TYPE_INSTANCE_GET_PRIVATE (self, NM_TYPE_MODEM, NMModemPrivate);
|
||||
priv = self->_priv;
|
||||
|
||||
priv->ip_ifindex = -1;
|
||||
priv->ip4_route_table = RT_TABLE_MAIN;
|
||||
priv->ip4_route_metric = 700;
|
||||
priv->ip6_route_table = RT_TABLE_MAIN;
|
||||
|
|
@ -1640,7 +1743,7 @@ constructed (GObject *object)
|
|||
|
||||
priv = NM_MODEM_GET_PRIVATE (NM_MODEM (object));
|
||||
|
||||
g_return_if_fail (priv->data_port || priv->control_port);
|
||||
g_return_if_fail (priv->control_port);
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
|
@ -1665,6 +1768,7 @@ finalize (GObject *object)
|
|||
g_free (priv->driver);
|
||||
g_free (priv->control_port);
|
||||
g_free (priv->data_port);
|
||||
g_free (priv->ip_iface);
|
||||
g_free (priv->device_id);
|
||||
g_free (priv->sim_id);
|
||||
g_free (priv->sim_operator_id);
|
||||
|
|
@ -1713,33 +1817,11 @@ nm_modem_class_init (NMModemClass *klass)
|
|||
G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY |
|
||||
G_PARAM_STATIC_STRINGS);
|
||||
|
||||
obj_properties[PROP_DATA_PORT] =
|
||||
g_param_spec_string (NM_MODEM_DATA_PORT, "", "",
|
||||
NULL,
|
||||
G_PARAM_READWRITE | G_PARAM_CONSTRUCT |
|
||||
G_PARAM_STATIC_STRINGS);
|
||||
|
||||
obj_properties[PROP_IP4_METHOD] =
|
||||
g_param_spec_uint (NM_MODEM_IP4_METHOD, "", "",
|
||||
NM_MODEM_IP_METHOD_UNKNOWN,
|
||||
NM_MODEM_IP_METHOD_AUTO,
|
||||
NM_MODEM_IP_METHOD_UNKNOWN,
|
||||
G_PARAM_READWRITE | G_PARAM_CONSTRUCT |
|
||||
G_PARAM_STATIC_STRINGS);
|
||||
|
||||
obj_properties[PROP_IP6_METHOD] =
|
||||
g_param_spec_uint (NM_MODEM_IP6_METHOD, "", "",
|
||||
NM_MODEM_IP_METHOD_UNKNOWN,
|
||||
NM_MODEM_IP_METHOD_AUTO,
|
||||
NM_MODEM_IP_METHOD_UNKNOWN,
|
||||
G_PARAM_READWRITE | G_PARAM_CONSTRUCT |
|
||||
G_PARAM_STATIC_STRINGS);
|
||||
|
||||
obj_properties[PROP_IP_TIMEOUT] =
|
||||
g_param_spec_uint (NM_MODEM_IP_TIMEOUT, "", "",
|
||||
0, 360, 20,
|
||||
G_PARAM_READWRITE |
|
||||
G_PARAM_STATIC_STRINGS);
|
||||
obj_properties[PROP_IP_IFINDEX] =
|
||||
g_param_spec_int (NM_MODEM_IP_IFINDEX, "", "",
|
||||
0, G_MAXINT, 0,
|
||||
G_PARAM_READABLE |
|
||||
G_PARAM_STATIC_STRINGS);
|
||||
|
||||
obj_properties[PROP_STATE] =
|
||||
g_param_spec_int (NM_MODEM_STATE, "", "",
|
||||
|
|
|
|||
|
|
@ -37,10 +37,7 @@
|
|||
#define NM_MODEM_PATH "path"
|
||||
#define NM_MODEM_DRIVER "driver"
|
||||
#define NM_MODEM_CONTROL_PORT "control-port"
|
||||
#define NM_MODEM_DATA_PORT "data-port"
|
||||
#define NM_MODEM_IP4_METHOD "ip4-method"
|
||||
#define NM_MODEM_IP6_METHOD "ip6-method"
|
||||
#define NM_MODEM_IP_TIMEOUT "ip-timeout"
|
||||
#define NM_MODEM_IP_IFINDEX "ip-ifindex"
|
||||
#define NM_MODEM_STATE "state"
|
||||
#define NM_MODEM_DEVICE_ID "device-id"
|
||||
#define NM_MODEM_SIM_ID "sim-id"
|
||||
|
|
@ -167,13 +164,21 @@ GType nm_modem_get_type (void);
|
|||
const char *nm_modem_get_path (NMModem *modem);
|
||||
const char *nm_modem_get_uid (NMModem *modem);
|
||||
const char *nm_modem_get_control_port (NMModem *modem);
|
||||
const char *nm_modem_get_data_port (NMModem *modem);
|
||||
int nm_modem_get_ip_ifindex (NMModem *modem);
|
||||
const char *nm_modem_get_driver (NMModem *modem);
|
||||
const char *nm_modem_get_device_id (NMModem *modem);
|
||||
const char *nm_modem_get_sim_id (NMModem *modem);
|
||||
const char *nm_modem_get_sim_operator_id (NMModem *modem);
|
||||
gboolean nm_modem_get_iid (NMModem *modem, NMUtilsIPv6IfaceId *out_iid);
|
||||
|
||||
gboolean nm_modem_set_data_port (NMModem *self,
|
||||
NMPlatform *platform,
|
||||
const char *data_port,
|
||||
NMModemIPMethod ip4_method,
|
||||
NMModemIPMethod ip6_method,
|
||||
guint timeout,
|
||||
GError **error);
|
||||
|
||||
gboolean nm_modem_owns_port (NMModem *modem, const char *iface);
|
||||
|
||||
void nm_modem_get_capabilities (NMModem *self,
|
||||
|
|
|
|||
|
|
@ -80,7 +80,7 @@ modem_added_cb (NMModemManager *manager,
|
|||
{
|
||||
NMWwanFactory *self = NM_WWAN_FACTORY (user_data);
|
||||
NMDevice *device;
|
||||
const char *driver, *port;
|
||||
const char *driver;
|
||||
|
||||
/* Do nothing if the modem was consumed by some other plugin */
|
||||
if (nm_device_factory_emit_component_added (NM_DEVICE_FACTORY (self), G_OBJECT (modem)))
|
||||
|
|
@ -93,10 +93,8 @@ modem_added_cb (NMModemManager *manager,
|
|||
* by the Bluetooth code during the connection process.
|
||||
*/
|
||||
if (driver && strstr (driver, "bluetooth")) {
|
||||
port = nm_modem_get_data_port (modem);
|
||||
if (!port)
|
||||
port = nm_modem_get_control_port (modem);
|
||||
nm_log_info (LOGD_MB, "ignoring modem '%s' (no associated Bluetooth device)", port);
|
||||
nm_log_info (LOGD_MB, "ignoring modem '%s' (no associated Bluetooth device)",
|
||||
nm_modem_get_control_port (modem));
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -353,6 +353,45 @@ nm_platform_process_events (NMPlatform *self)
|
|||
klass->process_events (self);
|
||||
}
|
||||
|
||||
const NMPlatformLink *
|
||||
nm_platform_process_events_ensure_link (NMPlatform *self,
|
||||
int ifindex,
|
||||
const char *ifname)
|
||||
{
|
||||
const NMPObject *obj;
|
||||
gboolean refreshed = FALSE;
|
||||
|
||||
g_return_val_if_fail (NM_IS_PLATFORM (self), NULL);
|
||||
|
||||
if (ifindex <= 0 && !ifname)
|
||||
return NULL;
|
||||
|
||||
/* we look into the cache, whether a link for given ifindex/ifname
|
||||
* exits. If not, we poll the netlink socket, maybe the event
|
||||
* with the link is waiting.
|
||||
*
|
||||
* Then we try again to find the object.
|
||||
*
|
||||
* If the link is already cached the first time, we avoid polling
|
||||
* the netlink socket. */
|
||||
again:
|
||||
obj = nmp_cache_lookup_link_full (nm_platform_get_cache (self),
|
||||
ifindex,
|
||||
ifname,
|
||||
FALSE, /* also invisible. We don't care here whether udev is ready */
|
||||
NM_LINK_TYPE_NONE,
|
||||
NULL, NULL);
|
||||
if (obj)
|
||||
return NMP_OBJECT_CAST_LINK (obj);
|
||||
if (!refreshed) {
|
||||
refreshed = TRUE;
|
||||
nm_platform_process_events (self);
|
||||
goto again;
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -1106,6 +1106,10 @@ const char *nm_platform_link_get_type_name (NMPlatform *self, int ifindex);
|
|||
gboolean nm_platform_link_refresh (NMPlatform *self, int ifindex);
|
||||
void nm_platform_process_events (NMPlatform *self);
|
||||
|
||||
const NMPlatformLink *nm_platform_process_events_ensure_link (NMPlatform *self,
|
||||
int ifindex,
|
||||
const char *ifname);
|
||||
|
||||
gboolean nm_platform_link_set_up (NMPlatform *self, int ifindex, gboolean *out_no_firmware);
|
||||
gboolean nm_platform_link_set_down (NMPlatform *self, int ifindex);
|
||||
gboolean nm_platform_link_set_arp (NMPlatform *self, int ifindex);
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue