diff options
Diffstat (limited to 'src/devices/wwan')
| -rw-r--r-- | src/devices/wwan/Makefile.am | 24 | ||||
| -rw-r--r-- | src/devices/wwan/Makefile.in | 55 | ||||
| -rw-r--r-- | src/devices/wwan/nm-device-modem-glue.h | 73 | ||||
| -rw-r--r-- | src/devices/wwan/nm-device-modem.c | 33 | ||||
| -rw-r--r-- | src/devices/wwan/nm-device-modem.h | 3 | ||||
| -rw-r--r-- | src/devices/wwan/nm-modem-broadband.c | 368 | ||||
| -rw-r--r-- | src/devices/wwan/nm-modem-broadband.h | 1 | ||||
| -rw-r--r-- | src/devices/wwan/nm-modem-enum-types.c | 2 | ||||
| -rw-r--r-- | src/devices/wwan/nm-modem-manager.c | 15 | ||||
| -rw-r--r-- | src/devices/wwan/nm-modem-manager.h | 1 | ||||
| -rw-r--r-- | src/devices/wwan/nm-modem.c | 171 | ||||
| -rw-r--r-- | src/devices/wwan/nm-modem.h | 50 | ||||
| -rw-r--r-- | src/devices/wwan/nm-wwan-factory.c | 17 | ||||
| -rw-r--r-- | src/devices/wwan/nm-wwan-factory.h | 2 |
14 files changed, 483 insertions, 332 deletions
diff --git a/src/devices/wwan/Makefile.am b/src/devices/wwan/Makefile.am index 055b07b9..107f630b 100644 --- a/src/devices/wwan/Makefile.am +++ b/src/devices/wwan/Makefile.am @@ -8,14 +8,14 @@ AM_CPPFLAGS = \ -I${top_srcdir}/src/devices \ -I${top_srcdir}/src/settings \ -I${top_srcdir}/src/platform \ - -I${top_srcdir}/include \ - -I$(top_builddir)/include \ + -I${top_builddir}/introspection \ + -I${top_srcdir}/shared \ + -I$(top_builddir)/shared \ -I${top_srcdir}/libnm-core \ -I${top_builddir}/libnm-core \ -DG_LOG_DOMAIN=\""NetworkManager-wwan"\" \ - -DNETWORKMANAGER_COMPILATION \ + -DNETWORKMANAGER_COMPILATION=NM_NETWORKMANAGER_COMPILATION_INSIDE_DAEMON \ -DNM_VERSION_MAX_ALLOWED=NM_VERSION_NEXT_STABLE \ - $(DBUS_CFLAGS) \ $(GLIB_CFLAGS) \ $(MM_GLIB_CFLAGS) @@ -47,31 +47,29 @@ WWAN_SYMBOL_VIS_FILE=$(srcdir)/wwan-exports.ver libnm_wwan_la_LDFLAGS = \ -avoid-version \ -Wl,--version-script=$(WWAN_SYMBOL_VIS_FILE) -libnm_wwan_la_LIBADD = $(DBUS_LIBS) $(MM_GLIB_LIBS) +libnm_wwan_la_LIBADD = \ + $(top_builddir)/introspection/libnmdbus.la \ + $(GLIB_LIBS) \ + $(MM_GLIB_LIBS) ########################################################### -nm-device-modem-glue.h: $(top_srcdir)/introspection/nm-device-modem.xml - dbus-binding-tool --prefix=nm_device_modem --mode=glib-server --output=$@ $< - -BUILT_SOURCES += nm-device-modem-glue.h - SYMBOL_VIS_FILE=$(srcdir)/exports.ver libnm_device_plugin_wwan_la_SOURCES = \ nm-wwan-factory.c \ nm-wwan-factory.h \ nm-device-modem.c \ - nm-device-modem.h \ - nm-device-modem-glue.h + nm-device-modem.h libnm_device_plugin_wwan_la_LDFLAGS = \ -module -avoid-version \ -Wl,--version-script=$(SYMBOL_VIS_FILE) libnm_device_plugin_wwan_la_LIBADD = \ + $(top_builddir)/introspection/libnmdbus.la \ libnm-wwan.la \ - $(DBUS_LIBS) + $(GLIB_LIBS) ########################################################### diff --git a/src/devices/wwan/Makefile.in b/src/devices/wwan/Makefile.in index 571b1b7d..ac13135e 100644 --- a/src/devices/wwan/Makefile.in +++ b/src/devices/wwan/Makefile.in @@ -140,7 +140,8 @@ am__uninstall_files_from_dir = { \ am__installdirs = "$(DESTDIR)$(pkglibdir)" LTLIBRARIES = $(pkglib_LTLIBRARIES) am__DEPENDENCIES_1 = -libnm_device_plugin_wwan_la_DEPENDENCIES = libnm-wwan.la \ +libnm_device_plugin_wwan_la_DEPENDENCIES = \ + $(top_builddir)/introspection/libnmdbus.la libnm-wwan.la \ $(am__DEPENDENCIES_1) am_libnm_device_plugin_wwan_la_OBJECTS = nm-wwan-factory.lo \ nm-device-modem.lo @@ -154,8 +155,9 @@ libnm_device_plugin_wwan_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libnm_device_plugin_wwan_la_LDFLAGS) \ $(LDFLAGS) -o $@ -libnm_wwan_la_DEPENDENCIES = $(am__DEPENDENCIES_1) \ - $(am__DEPENDENCIES_1) +libnm_wwan_la_DEPENDENCIES = \ + $(top_builddir)/introspection/libnmdbus.la \ + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am__objects_1 = nm-modem-enum-types.lo am_libnm_wwan_la_OBJECTS = nm-modem-broadband.lo nm-modem-manager.lo \ nm-modem.lo $(am__objects_1) @@ -243,7 +245,6 @@ BLUEZ5_LIBS = @BLUEZ5_LIBS@ CC = @CC@ CCDEPMODE = @CCDEPMODE@ CFLAGS = @CFLAGS@ -CKDB_PATH = @CKDB_PATH@ CODE_COVERAGE_CFLAGS = @CODE_COVERAGE_CFLAGS@ CODE_COVERAGE_ENABLED = @CODE_COVERAGE_ENABLED@ CODE_COVERAGE_LDFLAGS = @CODE_COVERAGE_LDFLAGS@ @@ -255,8 +256,6 @@ CXXDEPMODE = @CXXDEPMODE@ CXXFLAGS = @CXXFLAGS@ CYGPATH_W = @CYGPATH_W@ DBUS_CFLAGS = @DBUS_CFLAGS@ -DBUS_GLIB_100_CFLAGS = @DBUS_GLIB_100_CFLAGS@ -DBUS_GLIB_100_LIBS = @DBUS_GLIB_100_LIBS@ DBUS_LIBS = @DBUS_LIBS@ DBUS_SYS_DIR = @DBUS_SYS_DIR@ DEFS = @DEFS@ @@ -266,6 +265,7 @@ DHCPCD_PATH = @DHCPCD_PATH@ DISTRO_NETWORK_SERVICE = @DISTRO_NETWORK_SERVICE@ DLLTOOL = @DLLTOOL@ DNSMASQ_PATH = @DNSMASQ_PATH@ +DNSSEC_TRIGGER_SCRIPT = @DNSSEC_TRIGGER_SCRIPT@ DSYMUTIL = @DSYMUTIL@ DUMPBIN = @DUMPBIN@ ECHO_C = @ECHO_C@ @@ -320,16 +320,13 @@ INTROSPECTION_MAKEFILE = @INTROSPECTION_MAKEFILE@ INTROSPECTION_SCANNER = @INTROSPECTION_SCANNER@ INTROSPECTION_TYPELIBDIR = @INTROSPECTION_TYPELIBDIR@ IPTABLES_PATH = @IPTABLES_PATH@ -IWMX_SDK_CFLAGS = @IWMX_SDK_CFLAGS@ -IWMX_SDK_LIBS = @IWMX_SDK_LIBS@ KERNEL_FIRMWARE_DIR = @KERNEL_FIRMWARE_DIR@ LCOV = @LCOV@ LD = @LD@ LDFLAGS = @LDFLAGS@ +LIBAUDIT_CFLAGS = @LIBAUDIT_CFLAGS@ +LIBAUDIT_LIBS = @LIBAUDIT_LIBS@ LIBDL = @LIBDL@ -LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ -LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ -LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBM = @LIBM@ @@ -366,6 +363,8 @@ NEWT_LIBS = @NEWT_LIBS@ NM = @NM@ NMEDIT = @NMEDIT@ NM_CONFIG_DEFAULT_AUTH_POLKIT_TEXT = @NM_CONFIG_DEFAULT_AUTH_POLKIT_TEXT@ +NM_CONFIG_DEFAULT_LOGGING_AUDIT_TEXT = @NM_CONFIG_DEFAULT_LOGGING_AUDIT_TEXT@ +NM_CONFIG_LOGGING_BACKEND_DEFAULT_TEXT = @NM_CONFIG_LOGGING_BACKEND_DEFAULT_TEXT@ NM_MAJOR_VERSION = @NM_MAJOR_VERSION@ NM_MICRO_VERSION = @NM_MICRO_VERSION@ NM_MINOR_VERSION = @NM_MINOR_VERSION@ @@ -394,7 +393,6 @@ POLKIT_LIBS = @POLKIT_LIBS@ POSUB = @POSUB@ PPPD_PATH = @PPPD_PATH@ PPPD_PLUGIN_DIR = @PPPD_PLUGIN_DIR@ -PPPOE_PATH = @PPPOE_PATH@ QT_CFLAGS = @QT_CFLAGS@ QT_LIBS = @QT_LIBS@ RANLIB = @RANLIB@ @@ -409,6 +407,8 @@ SYSTEMD_200_CFLAGS = @SYSTEMD_200_CFLAGS@ SYSTEMD_200_LIBS = @SYSTEMD_200_LIBS@ SYSTEMD_INHIBIT_CFLAGS = @SYSTEMD_INHIBIT_CFLAGS@ SYSTEMD_INHIBIT_LIBS = @SYSTEMD_INHIBIT_LIBS@ +SYSTEMD_JOURNAL_CFLAGS = @SYSTEMD_JOURNAL_CFLAGS@ +SYSTEMD_JOURNAL_LIBS = @SYSTEMD_JOURNAL_LIBS@ SYSTEMD_LOGIN_CFLAGS = @SYSTEMD_LOGIN_CFLAGS@ SYSTEMD_LOGIN_LIBS = @SYSTEMD_LOGIN_LIBS@ SYSTEM_CA_PATH = @SYSTEM_CA_PATH@ @@ -469,6 +469,7 @@ mkdir_p = @mkdir_p@ nmbinary = @nmbinary@ nmconfdir = @nmconfdir@ nmdatadir = @nmdatadir@ +nmlibdir = @nmlibdir@ nmrundir = @nmrundir@ nmstatedir = @nmstatedir@ oldincludedir = @oldincludedir@ @@ -476,6 +477,7 @@ pdfdir = @pdfdir@ prefix = @prefix@ program_transform_name = @program_transform_name@ psdir = @psdir@ +runstatedir = @runstatedir@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ @@ -497,18 +499,18 @@ AM_CPPFLAGS = \ -I${top_srcdir}/src/devices \ -I${top_srcdir}/src/settings \ -I${top_srcdir}/src/platform \ - -I${top_srcdir}/include \ - -I$(top_builddir)/include \ + -I${top_builddir}/introspection \ + -I${top_srcdir}/shared \ + -I$(top_builddir)/shared \ -I${top_srcdir}/libnm-core \ -I${top_builddir}/libnm-core \ -DG_LOG_DOMAIN=\""NetworkManager-wwan"\" \ - -DNETWORKMANAGER_COMPILATION \ + -DNETWORKMANAGER_COMPILATION=NM_NETWORKMANAGER_COMPILATION_INSIDE_DAEMON \ -DNM_VERSION_MAX_ALLOWED=NM_VERSION_NEXT_STABLE \ - $(DBUS_CFLAGS) \ $(GLIB_CFLAGS) \ $(MM_GLIB_CFLAGS) -BUILT_SOURCES = $(null) $(GLIB_GENERATED) nm-device-modem-glue.h +BUILT_SOURCES = $(null) $(GLIB_GENERATED) pkglib_LTLIBRARIES = libnm-wwan.la libnm-device-plugin-wwan.la ########################################################### @@ -531,22 +533,28 @@ libnm_wwan_la_LDFLAGS = \ -avoid-version \ -Wl,--version-script=$(WWAN_SYMBOL_VIS_FILE) -libnm_wwan_la_LIBADD = $(DBUS_LIBS) $(MM_GLIB_LIBS) +libnm_wwan_la_LIBADD = \ + $(top_builddir)/introspection/libnmdbus.la \ + $(GLIB_LIBS) \ + $(MM_GLIB_LIBS) + + +########################################################### SYMBOL_VIS_FILE = $(srcdir)/exports.ver libnm_device_plugin_wwan_la_SOURCES = \ nm-wwan-factory.c \ nm-wwan-factory.h \ nm-device-modem.c \ - nm-device-modem.h \ - nm-device-modem-glue.h + nm-device-modem.h libnm_device_plugin_wwan_la_LDFLAGS = \ -module -avoid-version \ -Wl,--version-script=$(SYMBOL_VIS_FILE) libnm_device_plugin_wwan_la_LIBADD = \ + $(top_builddir)/introspection/libnmdbus.la \ libnm-wwan.la \ - $(DBUS_LIBS) + $(GLIB_LIBS) ########################################################### @@ -887,11 +895,6 @@ include $(GLIB_MAKEFILE) @GNOME_CODE_COVERAGE_RULES@ -########################################################### - -nm-device-modem-glue.h: $(top_srcdir)/introspection/nm-device-modem.xml - dbus-binding-tool --prefix=nm_device_modem --mode=glib-server --output=$@ $< - @ENABLE_TESTS_TRUE@check-local: @ENABLE_TESTS_TRUE@ $(top_srcdir)/tools/check-exports.sh $(builddir)/.libs/libnm-device-plugin-wwan.so $(SYMBOL_VIS_FILE) @ENABLE_TESTS_TRUE@ $(top_srcdir)/tools/check-exports.sh $(builddir)/.libs/libnm-wwan.so $(WWAN_SYMBOL_VIS_FILE) diff --git a/src/devices/wwan/nm-device-modem-glue.h b/src/devices/wwan/nm-device-modem-glue.h deleted file mode 100644 index 21271491..00000000 --- a/src/devices/wwan/nm-device-modem-glue.h +++ /dev/null @@ -1,73 +0,0 @@ -/* Generated by dbus-binding-tool; do not edit! */ - - -#ifndef __dbus_glib_marshal_nm_device_modem_MARSHAL_H__ -#define __dbus_glib_marshal_nm_device_modem_MARSHAL_H__ - -#include <glib-object.h> - -G_BEGIN_DECLS - -#ifdef G_ENABLE_DEBUG -#define g_marshal_value_peek_boolean(v) g_value_get_boolean (v) -#define g_marshal_value_peek_char(v) g_value_get_schar (v) -#define g_marshal_value_peek_uchar(v) g_value_get_uchar (v) -#define g_marshal_value_peek_int(v) g_value_get_int (v) -#define g_marshal_value_peek_uint(v) g_value_get_uint (v) -#define g_marshal_value_peek_long(v) g_value_get_long (v) -#define g_marshal_value_peek_ulong(v) g_value_get_ulong (v) -#define g_marshal_value_peek_int64(v) g_value_get_int64 (v) -#define g_marshal_value_peek_uint64(v) g_value_get_uint64 (v) -#define g_marshal_value_peek_enum(v) g_value_get_enum (v) -#define g_marshal_value_peek_flags(v) g_value_get_flags (v) -#define g_marshal_value_peek_float(v) g_value_get_float (v) -#define g_marshal_value_peek_double(v) g_value_get_double (v) -#define g_marshal_value_peek_string(v) (char*) g_value_get_string (v) -#define g_marshal_value_peek_param(v) g_value_get_param (v) -#define g_marshal_value_peek_boxed(v) g_value_get_boxed (v) -#define g_marshal_value_peek_pointer(v) g_value_get_pointer (v) -#define g_marshal_value_peek_object(v) g_value_get_object (v) -#define g_marshal_value_peek_variant(v) g_value_get_variant (v) -#else /* !G_ENABLE_DEBUG */ -/* WARNING: This code accesses GValues directly, which is UNSUPPORTED API. - * Do not access GValues directly in your code. Instead, use the - * g_value_get_*() functions - */ -#define g_marshal_value_peek_boolean(v) (v)->data[0].v_int -#define g_marshal_value_peek_char(v) (v)->data[0].v_int -#define g_marshal_value_peek_uchar(v) (v)->data[0].v_uint -#define g_marshal_value_peek_int(v) (v)->data[0].v_int -#define g_marshal_value_peek_uint(v) (v)->data[0].v_uint -#define g_marshal_value_peek_long(v) (v)->data[0].v_long -#define g_marshal_value_peek_ulong(v) (v)->data[0].v_ulong -#define g_marshal_value_peek_int64(v) (v)->data[0].v_int64 -#define g_marshal_value_peek_uint64(v) (v)->data[0].v_uint64 -#define g_marshal_value_peek_enum(v) (v)->data[0].v_long -#define g_marshal_value_peek_flags(v) (v)->data[0].v_ulong -#define g_marshal_value_peek_float(v) (v)->data[0].v_float -#define g_marshal_value_peek_double(v) (v)->data[0].v_double -#define g_marshal_value_peek_string(v) (v)->data[0].v_pointer -#define g_marshal_value_peek_param(v) (v)->data[0].v_pointer -#define g_marshal_value_peek_boxed(v) (v)->data[0].v_pointer -#define g_marshal_value_peek_pointer(v) (v)->data[0].v_pointer -#define g_marshal_value_peek_object(v) (v)->data[0].v_pointer -#define g_marshal_value_peek_variant(v) (v)->data[0].v_pointer -#endif /* !G_ENABLE_DEBUG */ - - -G_END_DECLS - -#endif /* __dbus_glib_marshal_nm_device_modem_MARSHAL_H__ */ - -#include <dbus/dbus-glib.h> -static const DBusGMethodInfo dbus_glib_nm_device_modem_methods[] = { -}; - -const DBusGObjectInfo dbus_glib_nm_device_modem_object_info = { 1, - dbus_glib_nm_device_modem_methods, - 0, -"\0", -"org.freedesktop.NetworkManager.Device.Modem\0PropertiesChanged\0\0", -"org.freedesktop.NetworkManager.Device.Modem\0ModemCapabilities\0modem_capabilities\0read\0org.freedesktop.NetworkManager.Device.Modem\0CurrentCapabilities\0current_capabilities\0read\0\0" -}; - diff --git a/src/devices/wwan/nm-device-modem.c b/src/devices/wwan/nm-device-modem.c index ca724c04..edecd24d 100644 --- a/src/devices/wwan/nm-device-modem.c +++ b/src/devices/wwan/nm-device-modem.c @@ -21,14 +21,12 @@ #include "config.h" #include <string.h> -#include <glib.h> +#include "nm-default.h" #include "nm-device-modem.h" #include "nm-modem.h" #include "nm-device-private.h" #include "nm-rfkill-manager.h" -#include "nm-logging.h" -#include "nm-dbus-manager.h" #include "nm-settings-connection.h" #include "nm-modem-broadband.h" #include "NetworkManagerUtils.h" @@ -37,12 +35,12 @@ #include "nm-device-logging.h" _LOG_DECLARE_SELF(NMDeviceModem); +#include "nmdbus-device-modem.h" + G_DEFINE_TYPE (NMDeviceModem, nm_device_modem, NM_TYPE_DEVICE) #define NM_DEVICE_MODEM_GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE ((o), NM_TYPE_DEVICE_MODEM, NMDeviceModemPrivate)) -#include "nm-device-modem-glue.h" - typedef struct { NMModem *modem; NMDeviceModemCapabilities caps; @@ -108,7 +106,7 @@ modem_prepare_result (NMModem *modem, * the device to be auto-activated anymore, which would risk locking * the SIM if the incorrect PIN continues to be used. */ - g_object_set (G_OBJECT (device), NM_DEVICE_AUTOCONNECT, FALSE, NULL); + nm_device_set_autoconnect (device, FALSE); _LOGI (LOGD_MB, "disabling autoconnect due to failed SIM PIN"); } @@ -256,6 +254,12 @@ data_port_changed_cb (NMModem *modem, GParamSpec *pspec, gpointer user_data) } static void +ids_changed_cb (NMModem *modem, GParamSpec *pspec, gpointer user_data) +{ + nm_device_recheck_available_connections (NM_DEVICE (user_data)); +} + +static void modem_state_cb (NMModem *modem, NMModemState new_state, NMModemState old_state, @@ -332,7 +336,7 @@ device_state_changed (NMDevice *device, { NMDeviceModem *self = NM_DEVICE_MODEM (device); NMDeviceModemPrivate *priv = NM_DEVICE_MODEM_GET_PRIVATE (device); - NMConnection *connection = nm_device_get_connection (device); + NMConnection *connection = nm_device_get_applied_connection (device); g_assert (priv->modem); @@ -411,10 +415,7 @@ check_connection_available (NMDevice *device, return FALSE; if (state == NM_MODEM_STATE_LOCKED) { - NMSettingGsm *s_gsm = nm_connection_get_setting_gsm (connection); - - /* Can't use a connection without a PIN if the modem is locked */ - if (!s_gsm || !nm_setting_gsm_get_pin (s_gsm)) + if (!nm_connection_get_setting_gsm (connection)) return FALSE; } @@ -679,6 +680,10 @@ set_modem (NMDeviceModem *self, NMModem *modem) * 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_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); } static void @@ -795,7 +800,7 @@ nm_device_modem_class_init (NMDeviceModemClass *mclass) G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY | G_PARAM_STATIC_STRINGS)); - nm_dbus_manager_register_exported_type (nm_dbus_manager_get (), - G_TYPE_FROM_CLASS (mclass), - &dbus_glib_nm_device_modem_object_info); + nm_exported_object_class_add_interface (NM_EXPORTED_OBJECT_CLASS (mclass), + NMDBUS_TYPE_DEVICE_MODEM_SKELETON, + NULL); } diff --git a/src/devices/wwan/nm-device-modem.h b/src/devices/wwan/nm-device-modem.h index 996195c4..1cf399e1 100644 --- a/src/devices/wwan/nm-device-modem.h +++ b/src/devices/wwan/nm-device-modem.h @@ -21,9 +21,6 @@ #ifndef __NETWORKMANAGER_DEVICE_MODEM_H__ #define __NETWORKMANAGER_DEVICE_MODEM_H__ -#include <glib.h> -#include <glib-object.h> - #include "nm-device.h" #include "nm-modem.h" diff --git a/src/devices/wwan/nm-modem-broadband.c b/src/devices/wwan/nm-modem-broadband.c index ec4f4a2f..427f3ed6 100644 --- a/src/devices/wwan/nm-modem-broadband.c +++ b/src/devices/wwan/nm-modem-broadband.c @@ -20,28 +20,51 @@ #include "config.h" -#include <glib/gi18n.h> #include <string.h> #include <arpa/inet.h> #include <libmm-glib.h> #include "nm-modem-broadband.h" #include "nm-core-internal.h" -#include "nm-logging.h" +#include "nm-default.h" #include "NetworkManagerUtils.h" #include "nm-device-private.h" #include "nm-platform.h" G_DEFINE_TYPE (NMModemBroadband, nm_modem_broadband, NM_TYPE_MODEM) +typedef enum { + CONNECT_STEP_FIRST, + CONNECT_STEP_WAIT_FOR_SIM, + CONNECT_STEP_UNLOCK, + CONNECT_STEP_WAIT_FOR_READY, + CONNECT_STEP_CONNECT, + CONNECT_STEP_LAST +} ConnectStep; + +typedef struct { + NMModemBroadband *self; + ConnectStep step; + + MMModemCapability caps; + NMConnection *connection; + GCancellable *cancellable; + MMSimpleConnectProperties *connect_properties; + GArray *ip_types; + guint ip_types_i; + GError *first_error; +} ConnectContext; + struct _NMModemBroadbandPrivate { /* The modem object from dbus */ MMObject *modem_object; /* Per-interface objects */ MMModem *modem_iface; MMModemSimple *simple_iface; + MMSim *sim_iface; /* Connection setup */ + ConnectContext *ctx; MMBearer *bearer; MMBearerIpConfig *ipv4_config; @@ -257,45 +280,45 @@ create_gsm_connect_properties (NMConnection *connection) return properties; } -typedef struct { - NMModemBroadband *self; - MMModemCapability caps; - MMSimpleConnectProperties *connect_properties; - GArray *ip_types; - guint ip_types_i; - GError *first_error; -} ActStageContext; - static void -act_stage_context_free (ActStageContext *ctx) +connect_context_clear (NMModemBroadband *self) { - g_clear_error (&ctx->first_error); - g_clear_pointer (&ctx->ip_types, (GDestroyNotify) g_array_unref); - g_clear_object (&ctx->connect_properties); - g_object_unref (ctx->self); - g_slice_free (ActStageContext, ctx); + if (self->priv->ctx) { + ConnectContext *ctx = self->priv->ctx; + + g_clear_error (&ctx->first_error); + g_clear_pointer (&ctx->ip_types, (GDestroyNotify) g_array_unref); + g_clear_object (&ctx->cancellable); + g_clear_object (&ctx->connection); + g_clear_object (&ctx->connect_properties); + g_clear_object (&ctx->self); + g_slice_free (ConnectContext, ctx); + self->priv->ctx = NULL; + } } -static void act_stage_context_step (ActStageContext *ctx); +static void connect_context_step (NMModemBroadband *self); static void connect_ready (MMModemSimple *simple_iface, GAsyncResult *res, - ActStageContext *ctx) + NMModemBroadband *self) { + ConnectContext *ctx = self->priv->ctx; GError *error = NULL; NMModemIPMethod ip4_method = NM_MODEM_IP_METHOD_UNKNOWN; NMModemIPMethod ip6_method = NM_MODEM_IP_METHOD_UNKNOWN; - ctx->self->priv->bearer = mm_modem_simple_connect_finish (simple_iface, res, &error); - if (!ctx->self->priv->bearer) { + self->priv->bearer = mm_modem_simple_connect_finish (simple_iface, res, &error); + if (!self->priv->bearer) { if (g_error_matches (error, MM_MOBILE_EQUIPMENT_ERROR, MM_MOBILE_EQUIPMENT_ERROR_SIM_PIN) || (g_error_matches (error, MM_CORE_ERROR, MM_CORE_ERROR_UNAUTHORIZED) && - mm_modem_get_unlock_required (ctx->self->priv->modem_iface) == MM_MODEM_LOCK_SIM_PIN)) { - /* Request PIN */ - ask_for_pin (ctx->self); + mm_modem_get_unlock_required (self->priv->modem_iface) == MM_MODEM_LOCK_SIM_PIN)) { g_error_free (error); - act_stage_context_free (ctx); + + /* Request PIN */ + ask_for_pin (self); + connect_context_clear (self); return; } @@ -312,79 +335,190 @@ connect_ready (MMModemSimple *simple_iface, * retry with the next one, if any. */ ctx->ip_types_i++; - act_stage_context_step (ctx); + connect_context_clear (self); return; } /* Grab IP configurations */ - ctx->self->priv->ipv4_config = mm_bearer_get_ipv4_config (ctx->self->priv->bearer); - if (ctx->self->priv->ipv4_config) - ip4_method = get_bearer_ip_method (ctx->self->priv->ipv4_config); + self->priv->ipv4_config = mm_bearer_get_ipv4_config (self->priv->bearer); + if (self->priv->ipv4_config) + ip4_method = get_bearer_ip_method (self->priv->ipv4_config); - ctx->self->priv->ipv6_config = mm_bearer_get_ipv6_config (ctx->self->priv->bearer); - if (ctx->self->priv->ipv6_config) - ip6_method = get_bearer_ip_method (ctx->self->priv->ipv6_config); + self->priv->ipv6_config = mm_bearer_get_ipv6_config (self->priv->bearer); + 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) { nm_log_warn (LOGD_MB, "(%s): failed to connect modem: invalid bearer IP configuration", - nm_modem_get_uid (NM_MODEM (ctx->self))); - g_signal_emit_by_name (ctx->self, NM_MODEM_PREPARE_RESULT, FALSE, NM_DEVICE_STATE_REASON_CONFIG_FAILED); - act_stage_context_free (ctx); + nm_modem_get_uid (NM_MODEM (self))); + g_signal_emit_by_name (self, NM_MODEM_PREPARE_RESULT, FALSE, NM_DEVICE_STATE_REASON_CONFIG_FAILED); + connect_context_clear (self); return; } - g_object_set (ctx->self, - NM_MODEM_DATA_PORT, mm_bearer_get_interface (ctx->self->priv->bearer), + 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 (ctx->self->priv->bearer), + NM_MODEM_IP_TIMEOUT, mm_bearer_get_ip_timeout (self->priv->bearer), NULL); - g_signal_emit_by_name (ctx->self, NM_MODEM_PREPARE_RESULT, TRUE, NM_DEVICE_STATE_REASON_NONE); - act_stage_context_free (ctx); + ctx->step++; + connect_context_step (self); } static void -act_stage_context_step (ActStageContext *ctx) +send_pin_ready (MMSim *sim, GAsyncResult *result, NMModemBroadband *self) { - if (ctx->ip_types_i < ctx->ip_types->len) { - NMModemIPType current; - - current = g_array_index (ctx->ip_types, NMModemIPType, ctx->ip_types_i); - - if (current == NM_MODEM_IP_TYPE_IPV4) - mm_simple_connect_properties_set_ip_type (ctx->connect_properties, MM_BEARER_IP_FAMILY_IPV4); - else if (current == NM_MODEM_IP_TYPE_IPV6) - mm_simple_connect_properties_set_ip_type (ctx->connect_properties, MM_BEARER_IP_FAMILY_IPV6); - else if (current == NM_MODEM_IP_TYPE_IPV4V6) - mm_simple_connect_properties_set_ip_type (ctx->connect_properties, MM_BEARER_IP_FAMILY_IPV4V6); - else - g_assert_not_reached (); - - nm_log_dbg (LOGD_MB, "(%s): launching connection with ip type '%s'", - nm_modem_get_uid (NM_MODEM (ctx->self)), - nm_modem_ip_type_to_string (current)); - - mm_modem_simple_connect (ctx->self->priv->simple_iface, - ctx->connect_properties, - NULL, - (GAsyncReadyCallback)connect_ready, - ctx); + GError *error = NULL; + + if (!mm_sim_send_pin_finish (sim, result, &error)) { + if (g_error_matches (error, MM_MOBILE_EQUIPMENT_ERROR, MM_MOBILE_EQUIPMENT_ERROR_SIM_PIN) || + (g_error_matches (error, MM_CORE_ERROR, MM_CORE_ERROR_UNAUTHORIZED) && + mm_modem_get_unlock_required (self->priv->modem_iface) == MM_MODEM_LOCK_SIM_PIN)) { + ask_for_pin (self); + } else { + g_signal_emit_by_name (self, NM_MODEM_PREPARE_RESULT, FALSE, translate_mm_error (error)); + } + g_error_free (error); return; + } + + self->priv->ctx->step++; + connect_context_step (self); +} + +static void +connect_context_step (NMModemBroadband *self) +{ + ConnectContext *ctx = self->priv->ctx; + + switch (ctx->step) { + case CONNECT_STEP_FIRST: + ctx->step++; + /* fall through */ + + case CONNECT_STEP_WAIT_FOR_SIM: + if (MODEM_CAPS_3GPP (ctx->caps) && !self->priv->sim_iface) { + /* Have to wait for the SIM to show up */ + break; + } + ctx->step++; + /* fall through */ + + case CONNECT_STEP_UNLOCK: + if ( MODEM_CAPS_3GPP (ctx->caps) + && mm_modem_get_unlock_required (self->priv->modem_iface) == MM_MODEM_LOCK_SIM_PIN) { + NMSettingGsm *s_gsm = nm_connection_get_setting_gsm (ctx->connection); + const char *pin = nm_setting_gsm_get_pin (s_gsm); + + /* If we have a PIN already, send it. If we don't, get it. */ + if (pin) { + mm_sim_send_pin (self->priv->sim_iface, + pin, + ctx->cancellable, + (GAsyncReadyCallback) send_pin_ready, + self); + } else { + ask_for_pin (self); + } + break; + } + ctx->step++; + /* fall through */ + + case CONNECT_STEP_WAIT_FOR_READY: { + GError *error = NULL; + + if (mm_modem_get_state (self->priv->modem_iface) <= MM_MODEM_STATE_LOCKED) + break; + + /* Create core connect properties based on the modem capabilities */ + g_assert (!ctx->connect_properties); + + if (MODEM_CAPS_3GPP (ctx->caps)) + ctx->connect_properties = create_gsm_connect_properties (ctx->connection); + else if (MODEM_CAPS_3GPP2 (ctx->caps)) + ctx->connect_properties = create_cdma_connect_properties (ctx->connection); + else { + nm_log_warn (LOGD_MB, "(%s): Failed to connect '%s': not a mobile broadband modem", + nm_modem_get_uid (NM_MODEM (self)), + nm_connection_get_id (ctx->connection)); + + g_signal_emit_by_name (self, NM_MODEM_PREPARE_RESULT, FALSE, NM_DEVICE_STATE_REASON_MODEM_INIT_FAILED); + connect_context_clear (self); + break; + } + g_assert (ctx->connect_properties); + + /* Build up list of IP types that we need to use in the retries */ + ctx->ip_types = nm_modem_get_connection_ip_type (NM_MODEM (self), ctx->connection, &error); + if (!ctx->ip_types) { + nm_log_warn (LOGD_MB, "(%s): Failed to connect '%s': %s", + nm_modem_get_uid (NM_MODEM (self)), + nm_connection_get_id (ctx->connection), + error ? error->message : "unknown error"); + g_clear_error (&error); + + g_signal_emit_by_name (self, NM_MODEM_PREPARE_RESULT, FALSE, NM_DEVICE_STATE_REASON_MODEM_INIT_FAILED); + connect_context_clear (self); + break; + } + + ctx->step++; + /* fall through */ } - /* If we have a saved error from a previous attempt, use it */ - if (!ctx->first_error) - ctx->first_error = g_error_new_literal (NM_DEVICE_ERROR, - NM_DEVICE_ERROR_INVALID_CONNECTION, - "invalid bearer IP configuration"); - - nm_log_warn (LOGD_MB, "(%s): failed to connect modem: %s", - nm_modem_get_uid (NM_MODEM (ctx->self)), - ctx->first_error->message); - g_signal_emit_by_name (ctx->self, NM_MODEM_PREPARE_RESULT, FALSE, translate_mm_error (ctx->first_error)); - act_stage_context_free (ctx); + case CONNECT_STEP_CONNECT: + if (ctx->ip_types_i < ctx->ip_types->len) { + NMModemIPType current; + + current = g_array_index (ctx->ip_types, NMModemIPType, ctx->ip_types_i); + + if (current == NM_MODEM_IP_TYPE_IPV4) + mm_simple_connect_properties_set_ip_type (ctx->connect_properties, MM_BEARER_IP_FAMILY_IPV4); + else if (current == NM_MODEM_IP_TYPE_IPV6) + mm_simple_connect_properties_set_ip_type (ctx->connect_properties, MM_BEARER_IP_FAMILY_IPV6); + else if (current == NM_MODEM_IP_TYPE_IPV4V6) + mm_simple_connect_properties_set_ip_type (ctx->connect_properties, MM_BEARER_IP_FAMILY_IPV4V6); + else + g_assert_not_reached (); + + nm_log_dbg (LOGD_MB, "(%s): launching connection with ip type '%s'", + nm_modem_get_uid (NM_MODEM (self)), + nm_modem_ip_type_to_string (current)); + + mm_modem_simple_connect (self->priv->simple_iface, + ctx->connect_properties, + NULL, + (GAsyncReadyCallback) connect_ready, + self); + break; + } + + ctx->step++; + /* fall through */ + + case CONNECT_STEP_LAST: + if (self->priv->ipv4_config || self->priv->ipv6_config) { + g_signal_emit_by_name (self, NM_MODEM_PREPARE_RESULT, TRUE, NM_DEVICE_STATE_REASON_NONE); + } else { + /* If we have a saved error from a previous attempt, use it */ + if (!ctx->first_error) + ctx->first_error = g_error_new_literal (NM_DEVICE_ERROR, + NM_DEVICE_ERROR_INVALID_CONNECTION, + "invalid bearer IP configuration"); + + nm_log_warn (LOGD_MB, "(%s): failed to connect modem: %s", + nm_modem_get_uid (NM_MODEM (self)), + ctx->first_error->message); + g_signal_emit_by_name (self, NM_MODEM_PREPARE_RESULT, FALSE, translate_mm_error (ctx->first_error)); + } + + connect_context_clear (self); + break; + } } static NMActStageReturn @@ -393,8 +527,6 @@ act_stage1_prepare (NMModem *_self, NMDeviceStateReason *reason) { NMModemBroadband *self = NM_MODEM_BROADBAND (_self); - ActStageContext *ctx; - GError *error = NULL; /* Make sure we can get the Simple interface from the modem */ if (!self->priv->simple_iface) { @@ -407,41 +539,16 @@ act_stage1_prepare (NMModem *_self, } } - /* Allocate new context for this activation stage attempt */ - ctx = g_slice_new0 (ActStageContext); - ctx->self = NM_MODEM_BROADBAND (g_object_ref (self)); - ctx->caps = mm_modem_get_current_capabilities (self->priv->modem_iface); + connect_context_clear (self); - /* Create core connect properties based on the modem capabilities */ - if (MODEM_CAPS_3GPP (ctx->caps)) - ctx->connect_properties = create_gsm_connect_properties (connection); - else if (MODEM_CAPS_3GPP2 (ctx->caps)) - ctx->connect_properties = create_cdma_connect_properties (connection); - else { - nm_log_warn (LOGD_MB, "(%s): Failed to connect '%s': not a mobile broadband modem", - nm_modem_get_uid (NM_MODEM (self)), - nm_connection_get_id (connection)); - act_stage_context_free (ctx); - *reason = NM_DEVICE_STATE_REASON_MODEM_INIT_FAILED; - return NM_ACT_STAGE_RETURN_FAILURE; - } - g_assert (ctx->connect_properties); - - /* Checkout list of IP types that we need to use in the retries */ - ctx->ip_types = nm_modem_get_connection_ip_type (NM_MODEM (self), connection, &error); - if (!ctx->ip_types) { - nm_log_warn (LOGD_MB, "(%s): Failed to connect '%s': %s", - nm_modem_get_uid (NM_MODEM (self)), - nm_connection_get_id (connection), - error ? error->message : "unknown error"); - g_clear_error (&error); - act_stage_context_free (ctx); - *reason = NM_DEVICE_STATE_REASON_MODEM_INIT_FAILED; - return NM_ACT_STAGE_RETURN_FAILURE; - } + /* Allocate new context for this connect stage attempt */ + self->priv->ctx = g_slice_new0 (ConnectContext); + self->priv->ctx->caps = mm_modem_get_current_capabilities (self->priv->modem_iface); + self->priv->ctx->cancellable = g_cancellable_new (); + self->priv->ctx->connection = g_object_ref (connection); g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (self->priv->simple_iface), MODEM_CONNECT_TIMEOUT_SECS * 1000); - act_stage_context_step (ctx); + connect_context_step (self); return NM_ACT_STAGE_RETURN_POSTPONE; } @@ -715,6 +822,7 @@ static_stage3_ip4_done (NMModemBroadband *self) { GError *error = NULL; NMIP4Config *config = NULL; + const char *data_port; const gchar *address_string; const gchar *gw_string; guint32 address_network; @@ -724,6 +832,7 @@ static_stage3_ip4_done (NMModemBroadband *self) guint i; g_assert (self->priv->ipv4_config); + g_assert (self->priv->bearer); nm_log_info (LOGD_MB, "(%s): IPv4 static configuration:", nm_modem_get_uid (NM_MODEM (self))); @@ -743,10 +852,13 @@ static_stage3_ip4_done (NMModemBroadband *self) gw_string = mm_bearer_ip_config_get_gateway (self->priv->ipv4_config); ip4_string_to_num (gw_string, &gw); - config = nm_ip4_config_new (); + data_port = mm_bearer_get_interface (self->priv->bearer); + g_assert (data_port); + config = nm_ip4_config_new (nm_platform_link_get_ifindex (NM_PLATFORM_GET, data_port)); memset (&address, 0, sizeof (address)); address.address = address_network; + address.peer_address = address_network; address.plen = mm_bearer_ip_config_get_prefix (self->priv->ipv4_config); address.source = NM_IP_CONFIG_SOURCE_WWAN; nm_ip4_config_add_address (config, &address); @@ -796,6 +908,7 @@ stage3_ip6_done (NMModemBroadband *self) { GError *error = NULL; NMIP6Config *config = NULL; + const char *data_port; const gchar *address_string; NMPlatformIP6Address address; NMModemIPMethod ip_method; @@ -833,7 +946,9 @@ stage3_ip6_done (NMModemBroadband *self) nm_log_info (LOGD_MB, "(%s): IPv6 base configuration:", nm_modem_get_uid (NM_MODEM (self))); - config = nm_ip6_config_new (); + data_port = mm_bearer_get_interface (self->priv->bearer); + g_assert (data_port); + config = nm_ip6_config_new (nm_platform_link_get_ifindex (NM_PLATFORM_GET, data_port)); address.plen = mm_bearer_ip_config_get_prefix (self->priv->ipv6_config); nm_ip6_config_add_address (config, &address); @@ -941,10 +1056,11 @@ simple_disconnect_ready (MMModemSimple *modem_iface, GError *error = NULL; if (!mm_modem_simple_disconnect_finish (modem_iface, res, &error)) { - if (ctx->warn) + if (ctx->warn && !g_error_matches (error, G_DBUS_ERROR, G_DBUS_ERROR_SERVICE_UNKNOWN)) { nm_log_warn (LOGD_MB, "(%s) failed to disconnect modem: %s", nm_modem_get_uid (NM_MODEM (ctx->self)), error->message); + } g_simple_async_result_take_error (ctx->result, error); } @@ -1042,7 +1158,6 @@ modem_state_changed (MMModem *modem, MMModemStateChangeReason reason, NMModemBroadband *self) { - /* After the SIM is unlocked MM1 will move the device to INITIALIZING which * is an unavailable state. That makes state handling confusing here, so * suppress this state change and let the modem move from LOCKED to DISABLED. @@ -1053,6 +1168,9 @@ modem_state_changed (MMModem *modem, nm_modem_set_state (NM_MODEM (self), mm_state_to_nm (new_state), mm_modem_state_change_reason_get_string (reason)); + + if (self->priv->ctx && self->priv->ctx->step == CONNECT_STEP_WAIT_FOR_READY) + connect_context_step (self); } /*****************************************************************************/ @@ -1114,12 +1232,23 @@ get_sim_ready (MMModem *modem, GError *error = NULL; MMSim *new_sim; + new_sim = mm_modem_get_sim_finish (modem, res, &error); - if (new_sim) { + if (new_sim != self->priv->sim_iface) { + g_clear_object (&self->priv->sim_iface); + self->priv->sim_iface = new_sim; + } else + g_clear_object (&new_sim); + + if (self->priv->sim_iface) { g_object_set (G_OBJECT (self), - NM_MODEM_SIM_ID, mm_sim_get_identifier (new_sim), + NM_MODEM_SIM_ID, mm_sim_get_identifier (self->priv->sim_iface), + NM_MODEM_SIM_OPERATOR_ID, mm_sim_get_operator_identifier (self->priv->sim_iface), NULL); - g_object_unref (new_sim); + + /* If we're waiting for the SIM during a connect, proceed with the connect */ + if (self->priv->ctx && self->priv->ctx->step == CONNECT_STEP_WAIT_FOR_SIM) + connect_context_step (self); } else { nm_log_warn (LOGD_MB, "(%s): failed to retrieve SIM object: %s", nm_modem_get_uid (NM_MODEM (self)), @@ -1142,7 +1271,10 @@ sim_changed (MMModem *modem, GParamSpec *pspec, gpointer user_data) (GAsyncReadyCallback) get_sim_ready, g_object_ref (self)); } else - g_object_set (G_OBJECT (self), NM_MODEM_SIM_ID, NULL, NULL); + g_object_set (G_OBJECT (self), + NM_MODEM_SIM_ID, NULL, + NM_MODEM_SIM_OPERATOR_ID, NULL, + NULL); } static void @@ -1226,11 +1358,13 @@ dispose (GObject *object) { NMModemBroadband *self = NM_MODEM_BROADBAND (object); + connect_context_clear (self); g_clear_object (&self->priv->ipv4_config); g_clear_object (&self->priv->ipv6_config); g_clear_object (&self->priv->bearer); g_clear_object (&self->priv->modem_iface); g_clear_object (&self->priv->simple_iface); + g_clear_object (&self->priv->sim_iface); g_clear_object (&self->priv->modem_object); G_OBJECT_CLASS (nm_modem_broadband_parent_class)->dispose (object); diff --git a/src/devices/wwan/nm-modem-broadband.h b/src/devices/wwan/nm-modem-broadband.h index 2268bac4..a54e63a6 100644 --- a/src/devices/wwan/nm-modem-broadband.h +++ b/src/devices/wwan/nm-modem-broadband.h @@ -21,7 +21,6 @@ #ifndef __NETWORKMANAGER_MODEM_BROADBAND_H__ #define __NETWORKMANAGER_MODEM_BROADBAND_H__ -#include <glib-object.h> #include "nm-modem.h" G_BEGIN_DECLS diff --git a/src/devices/wwan/nm-modem-enum-types.c b/src/devices/wwan/nm-modem-enum-types.c index 6fbb3b6d..2d02ede9 100644 --- a/src/devices/wwan/nm-modem-enum-types.c +++ b/src/devices/wwan/nm-modem-enum-types.c @@ -3,6 +3,8 @@ /* Generated by glib-mkenums. Do not edit */ +#include "config.h" + #include "nm-modem-enum-types.h" #include "nm-modem.h" diff --git a/src/devices/wwan/nm-modem-manager.c b/src/devices/wwan/nm-modem-manager.c index f0e56926..c28d86ad 100644 --- a/src/devices/wwan/nm-modem-manager.c +++ b/src/devices/wwan/nm-modem-manager.c @@ -27,7 +27,8 @@ #include <libmm-glib.h> #include "nm-modem-manager.h" -#include "nm-logging.h" +#include "nm-default.h" +#include "nm-dbus-compat.h" #include "nm-modem.h" #include "nm-modem-broadband.h" @@ -193,10 +194,7 @@ modem_manager_name_owner_changed (MMManager *modem_manager, gchar *name_owner; /* Quit poking, if any */ - if (self->priv->mm_launch_id) { - g_source_remove (self->priv->mm_launch_id); - self->priv->mm_launch_id = 0; - } + nm_clear_g_source (&self->priv->mm_launch_id); name_owner = g_dbus_object_manager_client_get_name_owner (G_DBUS_OBJECT_MANAGER_CLIENT (modem_manager)); if (!name_owner) { @@ -265,7 +263,7 @@ modem_manager_poke (NMModemManager *self) g_dbus_connection_call (self->priv->dbus_connection, "org.freedesktop.ModemManager1", "/org/freedesktop/ModemManager1", - "org.freedesktop.DBus.Peer", + DBUS_INTERFACE_PEER, "Ping", NULL, /* inputs */ NULL, /* outputs */ @@ -434,10 +432,7 @@ dispose (GObject *object) { NMModemManager *self = NM_MODEM_MANAGER (object); - if (self->priv->mm_launch_id) { - g_source_remove (self->priv->mm_launch_id); - self->priv->mm_launch_id = 0; - } + nm_clear_g_source (&self->priv->mm_launch_id); modem_manager_clear_signals (self); g_clear_object (&self->priv->modem_manager); diff --git a/src/devices/wwan/nm-modem-manager.h b/src/devices/wwan/nm-modem-manager.h index 9e0db41e..b0014c6a 100644 --- a/src/devices/wwan/nm-modem-manager.h +++ b/src/devices/wwan/nm-modem-manager.h @@ -23,7 +23,6 @@ #ifndef __NETWORKMANAGER_MODEM_MANAGER_H__ #define __NETWORKMANAGER_MODEM_MANAGER_H__ -#include <glib-object.h> #include "nm-modem.h" #define NM_TYPE_MODEM_MANAGER (nm_modem_manager_get_type ()) diff --git a/src/devices/wwan/nm-modem.c b/src/devices/wwan/nm-modem.c index 3385a6fd..15104307 100644 --- a/src/devices/wwan/nm-modem.c +++ b/src/devices/wwan/nm-modem.c @@ -22,17 +22,17 @@ #include "config.h" #include <string.h> + #include "nm-modem.h" +#include "nm-core-internal.h" #include "nm-platform.h" -#include "nm-dbus-manager.h" #include "nm-setting-connection.h" -#include "nm-properties-changed-signal.h" -#include "nm-logging.h" +#include "nm-default.h" #include "NetworkManagerUtils.h" #include "nm-device-private.h" -#include "nm-dbus-glib-types.h" #include "nm-modem-enum-types.h" #include "nm-route-manager.h" +#include "gsystem-local-alloc.h" G_DEFINE_TYPE (NMModem, nm_modem, G_TYPE_OBJECT) @@ -52,6 +52,7 @@ enum { PROP_DEVICE_ID, PROP_SIM_ID, PROP_IP_TYPES, + PROP_SIM_OPERATOR_ID, LAST_PROP }; @@ -71,12 +72,13 @@ typedef struct { char *device_id; char *sim_id; NMModemIPType ip_types; + char *sim_operator_id; NMPPPManager *ppp_manager; NMActRequest *act_request; guint32 secrets_tries; - guint32 secrets_id; + NMActRequestGetSecretsCallId secrets_id; guint32 mm_ip_timeout; @@ -287,7 +289,7 @@ nm_modem_get_connection_ip_type (NMModem *self, NM_DEVICE_ERROR, NM_DEVICE_ERROR_INCOMPATIBLE_CONNECTION, "Connection requested IPv4 but IPv4 is " - "unsuported by the modem."); + "unsupported by the modem."); return NULL; } return build_single_ip_type_array (NM_MODEM_IP_TYPE_IPV4); @@ -299,7 +301,7 @@ nm_modem_get_connection_ip_type (NMModem *self, NM_DEVICE_ERROR, NM_DEVICE_ERROR_INCOMPATIBLE_CONNECTION, "Connection requested IPv6 but IPv6 is " - "unsuported by the modem."); + "unsupported by the modem."); return NULL; } return build_single_ip_type_array (NM_MODEM_IP_TYPE_IPV6); @@ -350,6 +352,24 @@ nm_modem_get_connection_ip_type (NMModem *self, return NULL; } +const char * +nm_modem_get_device_id (NMModem *self) +{ + return NM_MODEM_GET_PRIVATE (self)->device_id; +} + +const char * +nm_modem_get_sim_id (NMModem *self) +{ + return NM_MODEM_GET_PRIVATE (self)->sim_id; +} + +const char * +nm_modem_get_sim_operator_id (NMModem *self) +{ + return NM_MODEM_GET_PRIVATE (self)->sim_operator_id; +} + /*****************************************************************************/ /* IP method PPP */ @@ -493,7 +513,7 @@ ppp_stage3_ip_config_start (NMModem *self, return NM_ACT_STAGE_RETURN_POSTPONE; if (NM_MODEM_GET_CLASS (self)->get_user_pass) { - NMConnection *connection = nm_act_request_get_connection (req); + NMConnection *connection = nm_act_request_get_applied_connection (req); g_assert (connection); if (!NM_MODEM_GET_CLASS (self)->get_user_pass (self, connection, &ppp_name, NULL)) @@ -511,7 +531,7 @@ ppp_stage3_ip_config_start (NMModem *self, priv->ppp_manager = nm_ppp_manager_new (priv->data_port); if (nm_ppp_manager_start (priv->ppp_manager, req, ppp_name, ip_timeout, &error)) { - g_signal_connect (priv->ppp_manager, "state-changed", + g_signal_connect (priv->ppp_manager, NM_PPP_MANAGER_STATE_CHANGED, G_CALLBACK (ppp_state_changed), self); g_signal_connect (priv->ppp_manager, "ip4-config", @@ -532,8 +552,7 @@ ppp_stage3_ip_config_start (NMModem *self, error && error->message ? error->message : "(unknown)"); g_error_free (error); - g_object_unref (priv->ppp_manager); - priv->ppp_manager = NULL; + nm_exported_object_clear_and_unexport (&priv->ppp_manager); *reason = NM_DEVICE_STATE_REASON_PPP_START_FAILED; ret = NM_ACT_STAGE_RETURN_FAILURE; @@ -563,7 +582,7 @@ nm_modem_stage3_ip4_config_start (NMModem *self, req = nm_device_get_act_request (device); g_assert (req); - connection = nm_act_request_get_connection (req); + connection = nm_act_request_get_applied_connection (req); g_assert (connection); method = nm_utils_get_ip_config_method (connection, NM_TYPE_SETTING_IP4_CONFIG); @@ -680,7 +699,7 @@ nm_modem_stage3_ip6_config_start (NMModem *self, g_return_val_if_fail (NM_IS_ACT_REQUEST (req), NM_ACT_STAGE_RETURN_FAILURE); g_return_val_if_fail (reason != NULL, NM_ACT_STAGE_RETURN_FAILURE); - connection = nm_act_request_get_connection (req); + connection = nm_act_request_get_applied_connection (req); g_assert (connection); method = nm_utils_get_ip_config_method (connection, NM_TYPE_SETTING_IP6_CONFIG); @@ -725,16 +744,13 @@ cancel_get_secrets (NMModem *self) { NMModemPrivate *priv = NM_MODEM_GET_PRIVATE (self); - if (priv->secrets_id) { - nm_act_request_cancel_secrets (priv->act_request, priv->secrets_id); - priv->secrets_id = 0; - } + nm_act_request_cancel_secrets (priv->act_request, priv->secrets_id); } static void modem_secrets_cb (NMActRequest *req, - guint32 call_id, - NMConnection *connection, + NMActRequestGetSecretsCallId call_id, + NMSettingsConnection *connection, GError *error, gpointer user_data) { @@ -743,7 +759,10 @@ modem_secrets_cb (NMActRequest *req, g_return_if_fail (call_id == priv->secrets_id); - priv->secrets_id = 0; + priv->secrets_id = NULL; + + if (g_error_matches (error, G_IO_ERROR, G_IO_ERROR_CANCELLED)) + return; if (error) nm_log_warn (LOGD_MB, "(%s): %s", nm_modem_get_uid (self), error->message); @@ -751,7 +770,7 @@ modem_secrets_cb (NMActRequest *req, g_signal_emit (self, signals[AUTH_RESULT], 0, error); } -gboolean +void nm_modem_get_secrets (NMModem *self, const char *setting_name, gboolean request_new, @@ -770,10 +789,8 @@ nm_modem_get_secrets (NMModem *self, hint, modem_secrets_cb, self); - if (priv->secrets_id) - g_signal_emit (self, signals[AUTH_REQUESTED], 0); - - return !!(priv->secrets_id); + g_return_if_fail (priv->secrets_id); + g_signal_emit (self, signals[AUTH_REQUESTED], 0); } /*****************************************************************************/ @@ -793,8 +810,7 @@ nm_modem_act_stage1_prepare (NMModem *self, NMDeviceStateReason *reason) { NMModemPrivate *priv = NM_MODEM_GET_PRIVATE (self); - NMActStageReturn ret; - GPtrArray *hints = NULL; + gs_unref_ptrarray GPtrArray *hints = NULL; const char *setting_name = NULL; NMSecretAgentGetSecretsFlags flags = NM_SECRET_AGENT_GET_SECRETS_FLAG_ALLOW_INTERACTION; NMConnection *connection; @@ -803,7 +819,7 @@ nm_modem_act_stage1_prepare (NMModem *self, g_object_unref (priv->act_request); priv->act_request = g_object_ref (req); - connection = nm_act_request_get_connection (req); + connection = nm_act_request_get_applied_connection (req); g_assert (connection); setting_name = nm_connection_need_secrets (connection, &hints); @@ -823,18 +839,9 @@ nm_modem_act_stage1_prepare (NMModem *self, hints ? g_ptr_array_index (hints, 0) : NULL, modem_secrets_cb, self); - if (priv->secrets_id) { - g_signal_emit (self, signals[AUTH_REQUESTED], 0); - ret = NM_ACT_STAGE_RETURN_POSTPONE; - } else { - *reason = NM_DEVICE_STATE_REASON_NO_SECRETS; - ret = NM_ACT_STAGE_RETURN_FAILURE; - } - - if (hints) - g_ptr_array_free (hints, TRUE); - - return ret; + g_return_val_if_fail (priv->secrets_id, NM_ACT_STAGE_RETURN_FAILURE); + g_signal_emit (self, signals[AUTH_REQUESTED], 0); + return NM_ACT_STAGE_RETURN_POSTPONE; } /*****************************************************************************/ @@ -859,6 +866,67 @@ nm_modem_act_stage2_config (NMModem *self, gboolean nm_modem_check_connection_compatible (NMModem *self, NMConnection *connection) { + NMModemPrivate *priv = NM_MODEM_GET_PRIVATE (self); + NMSettingConnection *s_con; + + s_con = nm_connection_get_setting_connection (connection); + g_assert (s_con); + + if (g_str_equal (nm_setting_connection_get_connection_type (s_con), + NM_SETTING_GSM_SETTING_NAME)) { + NMSettingGsm *s_gsm; + const char *str; + + s_gsm = nm_connection_get_setting_gsm (connection); + if (!s_gsm) + return FALSE; + + str = nm_setting_gsm_get_device_id (s_gsm); + if (str) { + if (!priv->device_id) { + nm_log_dbg (LOGD_MB, "(%s): %s/%s has device-id, device does not", + priv->uid, + nm_connection_get_uuid (connection), + nm_connection_get_id (connection)); + return FALSE; + } + if (strcmp (str, priv->device_id)) { + nm_log_dbg (LOGD_MB, "(%s): %s/%s device-id mismatch", + priv->uid, + nm_connection_get_uuid (connection), + nm_connection_get_id (connection)); + return FALSE; + } + } + + /* SIM properties may not be available before the SIM is unlocked, so + * to ensure that autoconnect works, the connection's SIM properties + * are only compared if present on the device. + */ + + str = nm_setting_gsm_get_sim_id (s_gsm); + if (str && priv->sim_id) { + if (strcmp (str, priv->sim_id)) { + nm_log_dbg (LOGD_MB, "(%s): %s/%s sim-id mismatch", + priv->uid, + nm_connection_get_uuid (connection), + nm_connection_get_id (connection)); + return FALSE; + } + } + + str = nm_setting_gsm_get_sim_operator_id (s_gsm); + if (str && priv->sim_operator_id) { + if (strcmp (str, priv->sim_operator_id)) { + nm_log_dbg (LOGD_MB, "(%s): %s/%s sim-operator-id mismatch", + priv->uid, + nm_connection_get_uuid (connection), + nm_connection_get_id (connection)); + return FALSE; + } + } + } + if (NM_MODEM_GET_CLASS (self)->check_connection_compatible) return NM_MODEM_GET_CLASS (self)->check_connection_compatible (self, connection); return FALSE; @@ -899,10 +967,7 @@ deactivate_cleanup (NMModem *self, NMDevice *device) priv->in_bytes = priv->out_bytes = 0; - if (priv->ppp_manager) { - g_object_unref (priv->ppp_manager); - priv->ppp_manager = NULL; - } + nm_exported_object_clear_and_unexport (&priv->ppp_manager); if (device) { g_return_if_fail (NM_IS_DEVICE (device)); @@ -1315,6 +1380,9 @@ get_property (GObject *object, guint prop_id, case PROP_IP_TYPES: g_value_set_uint (value, priv->ip_types); break; + case PROP_SIM_OPERATOR_ID: + g_value_set_string (value, priv->sim_operator_id); + break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); break; @@ -1326,6 +1394,7 @@ set_property (GObject *object, guint prop_id, const GValue *value, GParamSpec *pspec) { NMModemPrivate *priv = NM_MODEM_GET_PRIVATE (object); + const char *s; switch (prop_id) { case PROP_PATH: @@ -1369,6 +1438,12 @@ set_property (GObject *object, guint prop_id, case PROP_IP_TYPES: priv->ip_types = g_value_get_uint (value); break; + case PROP_SIM_OPERATOR_ID: + g_clear_pointer (&priv->sim_operator_id, g_free); + s = g_value_get_string (value); + if (s && s[0]) + priv->sim_operator_id = g_strdup (s); + break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); break; @@ -1400,6 +1475,7 @@ finalize (GObject *object) g_free (priv->data_port); g_free (priv->device_id); g_free (priv->sim_id); + g_free (priv->sim_operator_id); G_OBJECT_CLASS (nm_modem_parent_class)->finalize (object); } @@ -1514,6 +1590,13 @@ nm_modem_class_init (NMModemClass *klass) 0, G_MAXUINT32, NM_MODEM_IP_TYPE_IPV4, G_PARAM_READWRITE | G_PARAM_CONSTRUCT)); + g_object_class_install_property + (object_class, PROP_SIM_OPERATOR_ID, + g_param_spec_string (NM_MODEM_SIM_OPERATOR_ID, "", "", + NULL, + G_PARAM_READWRITE | G_PARAM_CONSTRUCT | + G_PARAM_STATIC_STRINGS)); + /* Signals */ signals[PPP_STATS] = diff --git a/src/devices/wwan/nm-modem.h b/src/devices/wwan/nm-modem.h index 2cace890..60e5589b 100644 --- a/src/devices/wwan/nm-modem.h +++ b/src/devices/wwan/nm-modem.h @@ -22,7 +22,7 @@ #ifndef __NETWORKMANAGER_MODEM_H__ #define __NETWORKMANAGER_MODEM_H__ -#include <glib-object.h> +#include "nm-default.h" #include "ppp-manager/nm-ppp-manager.h" #include "nm-device.h" @@ -36,18 +36,19 @@ G_BEGIN_DECLS #define NM_MODEM_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), NM_TYPE_MODEM, NMModemClass)) /* Properties */ -#define NM_MODEM_UID "uid" -#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_STATE "state" -#define NM_MODEM_DEVICE_ID "device-id" -#define NM_MODEM_SIM_ID "sim-id" -#define NM_MODEM_IP_TYPES "ip-types" /* Supported IP types */ +#define NM_MODEM_UID "uid" +#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_STATE "state" +#define NM_MODEM_DEVICE_ID "device-id" +#define NM_MODEM_SIM_ID "sim-id" +#define NM_MODEM_IP_TYPES "ip-types" /* Supported IP types */ +#define NM_MODEM_SIM_OPERATOR_ID "sim-operator-id" /* Signals */ #define NM_MODEM_PPP_STATS "ppp-stats" @@ -179,12 +180,15 @@ typedef struct { 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); -const char *nm_modem_get_driver (NMModem *modem); -gboolean nm_modem_get_iid (NMModem *modem, NMUtilsIPv6IfaceId *out_iid); +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); +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_owns_port (NMModem *modem, const char *iface); @@ -218,10 +222,10 @@ NMActStageReturn nm_modem_stage3_ip6_config_start (NMModem *modem, void nm_modem_ip4_pre_commit (NMModem *modem, NMDevice *device, NMIP4Config *config); -gboolean nm_modem_get_secrets (NMModem *modem, - const char *setting_name, - gboolean request_new, - const char *hint); +void nm_modem_get_secrets (NMModem *modem, + const char *setting_name, + gboolean request_new, + const char *hint); void nm_modem_deactivate (NMModem *modem, NMDevice *device); diff --git a/src/devices/wwan/nm-wwan-factory.c b/src/devices/wwan/nm-wwan-factory.c index 49b0b0af..2fd9e0bd 100644 --- a/src/devices/wwan/nm-wwan-factory.c +++ b/src/devices/wwan/nm-wwan-factory.c @@ -29,12 +29,12 @@ #include "nm-setting-cdma.h" #include "nm-modem-manager.h" #include "nm-device-modem.h" -#include "nm-logging.h" +#include "nm-default.h" #include "nm-platform.h" static GType nm_wwan_factory_get_type (void); -static void device_factory_interface_init (NMDeviceFactory *factory_iface); +static void device_factory_interface_init (NMDeviceFactoryInterface *factory_iface); G_DEFINE_TYPE_EXTENDED (NMWwanFactory, nm_wwan_factory, G_TYPE_OBJECT, 0, G_IMPLEMENT_INTERFACE (NM_TYPE_DEVICE_FACTORY, device_factory_interface_init)) @@ -96,9 +96,14 @@ NM_DEVICE_FACTORY_DECLARE_TYPES ( ) static NMDevice * -new_link (NMDeviceFactory *factory, NMPlatformLink *plink, gboolean *out_ignore, GError **error) +create_device (NMDeviceFactory *factory, + const char *iface, + const NMPlatformLink *plink, + NMConnection *connection, + gboolean *out_ignore) { - g_warn_if_fail (plink->type == NM_LINK_TYPE_WWAN_ETHERNET); + g_return_val_if_fail (plink, NULL); + g_return_val_if_fail (plink->type == NM_LINK_TYPE_WWAN_ETHERNET, NULL); *out_ignore = TRUE; return NULL; } @@ -123,10 +128,10 @@ nm_wwan_factory_init (NMWwanFactory *self) } static void -device_factory_interface_init (NMDeviceFactory *factory_iface) +device_factory_interface_init (NMDeviceFactoryInterface *factory_iface) { factory_iface->get_supported_types = get_supported_types; - factory_iface->new_link = new_link; + factory_iface->create_device = create_device; factory_iface->start = start; } diff --git a/src/devices/wwan/nm-wwan-factory.h b/src/devices/wwan/nm-wwan-factory.h index c6c03f1f..78031e60 100644 --- a/src/devices/wwan/nm-wwan-factory.h +++ b/src/devices/wwan/nm-wwan-factory.h @@ -21,7 +21,7 @@ #ifndef __NETWORKMANAGER_WWAN_FACTORY_H__ #define __NETWORKMANAGER_WWAN_FACTORY_H__ -#include <glib-object.h> +#include "nm-default.h" #define NM_TYPE_WWAN_FACTORY (nm_wwan_factory_get_type ()) #define NM_WWAN_FACTORY(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), NM_TYPE_WWAN_FACTORY, NMWwanFactory)) |