aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--plugins/mm-plugin-cinterion.c4
-rw-r--r--plugins/mm-plugin-generic.c6
-rw-r--r--plugins/mm-plugin-gobi.c6
-rw-r--r--plugins/mm-plugin-nokia.c10
-rw-r--r--src/mm-base-modem.c361
-rw-r--r--src/mm-base-modem.h13
-rw-r--r--src/mm-broadband-modem.c54
-rw-r--r--src/mm-manager.c19
-rw-r--r--src/mm-port-probe.c19
-rw-r--r--src/mm-port-probe.h11
-rw-r--r--src/mm-port.h1
11 files changed, 336 insertions, 168 deletions
diff --git a/plugins/mm-plugin-cinterion.c b/plugins/mm-plugin-cinterion.c
index c5f02616..28de08f1 100644
--- a/plugins/mm-plugin-cinterion.c
+++ b/plugins/mm-plugin-cinterion.c
@@ -73,7 +73,9 @@ grab_port (MMPluginBase *base,
if (!mm_base_modem_grab_port (existing ? existing : modem,
subsys,
name,
- MM_PORT_TYPE_UNKNOWN)) {
+ MM_PORT_TYPE_AT, /* we only allow AT ports here */
+ MM_AT_PORT_FLAG_NONE,
+ error)) {
if (modem)
g_object_unref (modem);
return NULL;
diff --git a/plugins/mm-plugin-generic.c b/plugins/mm-plugin-generic.c
index 5c45322e..d167ec06 100644
--- a/plugins/mm-plugin-generic.c
+++ b/plugins/mm-plugin-generic.c
@@ -100,9 +100,9 @@ grab_port (MMPluginBase *base,
if (!mm_base_modem_grab_port (existing ? existing : modem,
subsys,
name,
- (mm_port_probe_is_qcdm (probe) ?
- MM_PORT_TYPE_QCDM :
- MM_PORT_TYPE_UNKNOWN))) {
+ mm_port_probe_get_port_type (probe),
+ MM_AT_PORT_FLAG_NONE,
+ error)) {
if (modem)
g_object_unref (modem);
return NULL;
diff --git a/plugins/mm-plugin-gobi.c b/plugins/mm-plugin-gobi.c
index 89bc9243..eef27e9c 100644
--- a/plugins/mm-plugin-gobi.c
+++ b/plugins/mm-plugin-gobi.c
@@ -71,9 +71,9 @@ grab_port (MMPluginBase *base,
if (!mm_base_modem_grab_port (existing ? existing : modem,
subsys,
name,
- (mm_port_probe_is_qcdm (probe) ?
- MM_PORT_TYPE_QCDM :
- MM_PORT_TYPE_UNKNOWN))) {
+ mm_port_probe_get_port_type (probe),
+ MM_AT_PORT_FLAG_NONE,
+ error)) {
if (modem)
g_object_unref (modem);
return NULL;
diff --git a/plugins/mm-plugin-nokia.c b/plugins/mm-plugin-nokia.c
index 5bde6444..343921a3 100644
--- a/plugins/mm-plugin-nokia.c
+++ b/plugins/mm-plugin-nokia.c
@@ -87,7 +87,7 @@ grab_port (MMPluginBase *base,
GUdevDevice *port;
const gchar *name, *subsys, *driver;
guint16 vendor = 0, product = 0;
- MMPortType ptype = MM_PORT_TYPE_UNKNOWN;
+ MMAtPortFlag pflags = MM_AT_PORT_FLAG_NONE;
/* The Nokia plugin cannot do anything with non-AT ports */
if (!mm_port_probe_is_at (probe)) {
@@ -113,9 +113,9 @@ grab_port (MMPluginBase *base,
/* Look for port type hints */
if (g_udev_device_get_property_as_boolean (port, "ID_MM_NOKIA_PORT_TYPE_MODEM"))
- ptype = MM_PORT_TYPE_PRIMARY;
+ pflags = MM_AT_PORT_FLAG_PRIMARY;
else if (g_udev_device_get_property_as_boolean (port, "ID_MM_NOKIA_PORT_TYPE_AUX"))
- ptype = MM_PORT_TYPE_SECONDARY;
+ pflags = MM_AT_PORT_FLAG_SECONDARY;
/* If this is the first port being grabbed, create a new modem object */
if (!existing)
@@ -128,7 +128,9 @@ grab_port (MMPluginBase *base,
if (!mm_base_modem_grab_port (existing ? existing : modem,
subsys,
name,
- ptype)) {
+ MM_PORT_TYPE_AT, /* we only allow AT ports here */
+ pflags,
+ error)) {
if (modem)
g_object_unref (modem);
return NULL;
diff --git a/src/mm-base-modem.c b/src/mm-base-modem.c
index 762d76bc..a9e0f78c 100644
--- a/src/mm-base-modem.c
+++ b/src/mm-base-modem.c
@@ -145,38 +145,13 @@ serial_port_timed_out_cb (MMSerialPort *port,
}
}
-static void
-initialize_ready (MMBaseModem *self,
- GAsyncResult *res)
-{
- GError *error = NULL;
-
- if (!MM_BASE_MODEM_GET_CLASS (self)->initialize_finish (self, res, &error)) {
- /* Wrong state is returned when modem is found locked */
- if (g_error_matches (error,
- MM_CORE_ERROR,
- MM_CORE_ERROR_WRONG_STATE)) {
- mm_dbg ("Couldn't finish initialization in the current state: '%s'",
- error->message);
- mm_base_modem_set_valid (self, TRUE);
- } else {
- mm_warn ("couldn't initialize the modem: '%s'", error->message);
- mm_base_modem_set_valid (self, FALSE);
- }
-
- g_error_free (error);
- return;
- }
-
- mm_dbg ("modem properly initialized");
- mm_base_modem_set_valid (self, TRUE);
-}
-
gboolean
mm_base_modem_grab_port (MMBaseModem *self,
const gchar *subsys,
const gchar *name,
- MMPortType suggested_type)
+ MMPortType ptype,
+ MMAtPortFlag at_pflags,
+ GError **error)
{
MMPort *port;
gchar *key;
@@ -188,16 +163,12 @@ mm_base_modem_grab_port (MMBaseModem *self,
/* Only allow 'tty' and 'net' ports */
if (!g_str_equal (subsys, "net") &&
!g_str_equal (subsys, "tty")) {
- mm_warn ("(%s/%s): cannot add port, unhandled subsystem",
- subsys, name);
- return FALSE;
- }
-
- /* Don't allow more than one Primary port to be set */
- if (self->priv->primary &&
- suggested_type == MM_PORT_TYPE_PRIMARY) {
- mm_warn ("(%s/%s): cannot add port, primary port already exists",
- subsys, name);
+ g_set_error (error,
+ MM_CORE_ERROR,
+ MM_CORE_ERROR_UNSUPPORTED,
+ "Cannot add port '%s/%s', unhandled subsystem",
+ subsys,
+ name);
return FALSE;
}
@@ -205,38 +176,22 @@ mm_base_modem_grab_port (MMBaseModem *self,
key = get_hash_key (subsys, name);
port = g_hash_table_lookup (self->priv->ports, key);
if (port) {
- mm_warn ("(%s/%s): cannot add port, already exists",
- subsys, name);
+ g_set_error (error,
+ MM_CORE_ERROR,
+ MM_CORE_ERROR_UNSUPPORTED,
+ "Cannot add port '%s/%s', already exists",
+ subsys,
+ name);
g_free (key);
return FALSE;
}
- /* If we have a tty, decide whether it will be primary, secondary, or none */
+ /* Serial ports... */
if (g_str_equal (subsys, "tty")) {
- MMPortType ptype;
-
- /* Decide port type */
- if (suggested_type != MM_PORT_TYPE_UNKNOWN)
- ptype = suggested_type;
- else {
- if (!self->priv->primary)
- ptype = MM_PORT_TYPE_PRIMARY;
- else if (!self->priv->secondary)
- ptype = MM_PORT_TYPE_SECONDARY;
- else
- ptype = MM_PORT_TYPE_IGNORED;
- }
-
- if (ptype == MM_PORT_TYPE_QCDM) {
+ if (ptype == MM_PORT_TYPE_QCDM)
/* QCDM port */
port = MM_PORT (mm_qcdm_serial_port_new (name));
- if (!self->priv->qcdm)
- self->priv->qcdm = g_object_ref (port);
- } else {
- GRegex *regex;
- GPtrArray *array;
- int i;
-
+ else if (ptype == MM_PORT_TYPE_AT) {
/* AT port */
port = MM_PORT (mm_at_serial_port_new (name));
@@ -245,100 +200,49 @@ mm_base_modem_grab_port (MMBaseModem *self,
mm_serial_parser_v1_parse,
mm_serial_parser_v1_new (),
mm_serial_parser_v1_destroy);
-
- /* Set up CREG unsolicited message handlers, with NULL callbacks */
- array = mm_3gpp_creg_regex_get (FALSE);
- for (i = 0; i < array->len; i++) {
- mm_at_serial_port_add_unsolicited_msg_handler (MM_AT_SERIAL_PORT (port),
- (GRegex *)g_ptr_array_index (array, i),
- NULL,
- NULL,
- NULL);
- }
- mm_3gpp_creg_regex_destroy (array);
-
- /* Set up CIEV unsolicited message handler, with NULL callback */
- regex = mm_3gpp_ciev_regex_get ();
- mm_at_serial_port_add_unsolicited_msg_handler (MM_AT_SERIAL_PORT (port),
- regex,
- NULL,
- NULL,
- NULL);
- g_regex_unref (regex);
-
- /* Set up CMTI unsolicited message handler, with NULL callback */
- regex = mm_3gpp_cmti_regex_get ();
- mm_at_serial_port_add_unsolicited_msg_handler (MM_AT_SERIAL_PORT (port),
- regex,
- NULL,
- NULL,
- NULL);
- g_regex_unref (regex);
-
- /* Set up CUSD unsolicited message handler, with NULL callback */
- regex = mm_3gpp_cusd_regex_get ();
- mm_at_serial_port_add_unsolicited_msg_handler (MM_AT_SERIAL_PORT (port),
- regex,
- NULL,
- NULL,
- NULL);
- g_regex_unref (regex);
-
- if (ptype == MM_PORT_TYPE_PRIMARY) {
- self->priv->primary = g_object_ref (port);
-
- /* Primary port, which will also be data port */
- if (!self->priv->data)
- self->priv->data = g_object_ref (port);
-
- /* As soon as we get the primary AT port, we initialize the
- * modem */
- MM_BASE_MODEM_GET_CLASS (self)->initialize (self,
- MM_AT_SERIAL_PORT (port),
- NULL, /* TODO: cancellable */
- (GAsyncReadyCallback)initialize_ready,
- NULL);
-
- } else if (ptype == MM_PORT_TYPE_SECONDARY)
- self->priv->secondary = g_object_ref (port);
+ /* Store flags already */
+ mm_at_serial_port_set_flags (MM_AT_SERIAL_PORT (port), at_pflags);
+ } else {
+ g_set_error (error,
+ MM_CORE_ERROR,
+ MM_CORE_ERROR_UNSUPPORTED,
+ "Cannot add port '%s/%s', unhandled serial type",
+ subsys,
+ name);
+ g_free (key);
+ return FALSE;
}
/* For serial ports, enable port timeout checks */
- if (port)
- g_signal_connect (port,
- "timed-out",
- G_CALLBACK (serial_port_timed_out_cb),
- self);
-
- mm_dbg ("(%s/%s) port (%s) grabbed by %s",
- subsys,
- name,
- mm_port_type_get_string (ptype),
- mm_port_get_device (port));
- } else {
- /* Net */
+ g_signal_connect (port,
+ "timed-out",
+ G_CALLBACK (serial_port_timed_out_cb),
+ self);
+ }
+ /* Net ports... */
+ else if (g_str_equal (subsys, "net")) {
port = MM_PORT (g_object_new (MM_TYPE_PORT,
MM_PORT_DEVICE, name,
MM_PORT_SUBSYS, MM_PORT_SUBSYS_NET,
- MM_PORT_TYPE, MM_PORT_TYPE_IGNORED,
+ /* MM_PORT_TYPE, MM_PORT_TYPE_IGNORED, */
NULL));
+ } else
+ /* We already filter out before all non-tty, non-net ports */
+ g_assert_not_reached();
- /* Net device (if any) is the preferred data port */
- if (!self->priv->data || MM_IS_AT_SERIAL_PORT (self->priv->data)) {
- g_clear_object (&self->priv->data);
- self->priv->data = g_object_ref (port);
- }
-
- mm_dbg ("(%s/%s) port grabbed by %s",
- subsys,
- name,
- mm_port_get_device (port));
- }
+ mm_dbg ("(%s) type '%s' claimed by %s",
+ name,
+ mm_port_type_get_string (ptype),
+ mm_base_modem_get_device (self));
/* Add it to the tracking HT.
* Note: 'key' and 'port' now owned by the HT. */
g_hash_table_insert (self->priv->ports, key, port);
+ /* Let subclasses know we've grabbed it */
+ if (MM_BASE_MODEM_GET_CLASS (self)->port_grabbed)
+ MM_BASE_MODEM_GET_CLASS (self)->port_grabbed (self, port);
+
return TRUE;
}
@@ -389,9 +293,6 @@ mm_base_modem_release_port (MMBaseModem *self,
mm_port_get_device (port));
g_hash_table_remove (self->priv->ports, key);
g_free (key);
-
- /* TODO */
- /* check_valid (MM_GENERIC_GSM (modem)); */
}
void
@@ -480,6 +381,172 @@ mm_base_modem_get_best_at_port (MMBaseModem *self,
return port;
}
+static void
+initialize_ready (MMBaseModem *self,
+ GAsyncResult *res)
+{
+ GError *error = NULL;
+
+ if (!MM_BASE_MODEM_GET_CLASS (self)->initialize_finish (self, res, &error)) {
+ /* Wrong state is returned when modem is found locked */
+ if (g_error_matches (error,
+ MM_CORE_ERROR,
+ MM_CORE_ERROR_WRONG_STATE)) {
+ mm_dbg ("Couldn't finish initialization in the current state: '%s'",
+ error->message);
+ mm_base_modem_set_valid (self, TRUE);
+ } else {
+ mm_warn ("couldn't initialize the modem: '%s'", error->message);
+ mm_base_modem_set_valid (self, FALSE);
+ }
+
+ g_error_free (error);
+ return;
+ }
+
+ mm_dbg ("modem properly initialized");
+ mm_base_modem_set_valid (self, TRUE);
+}
+
+static inline void
+log_port (MMBaseModem *self, MMPort *port, const char *desc)
+{
+ if (port) {
+ mm_dbg ("(%s) %s/%s %s",
+ self->priv->device,
+ mm_port_subsys_get_string (mm_port_get_subsys (port)),
+ mm_port_get_device (port),
+ desc);
+ }
+}
+
+gboolean
+mm_base_modem_organize_ports (MMBaseModem *self,
+ GError **error)
+{
+ GHashTableIter iter;
+ MMPort *candidate;
+ MMAtPortFlag flags;
+ MMAtSerialPort *backup_primary = NULL;
+ MMAtSerialPort *primary = NULL;
+ MMAtSerialPort *secondary = NULL;
+ MMAtSerialPort *backup_secondary = NULL;
+ MMQcdmSerialPort *qcdm = NULL;
+ MMPort *data = NULL;
+
+ g_return_val_if_fail (MM_IS_BASE_MODEM (self), FALSE);
+
+ /* If ports have already been organized, just return success */
+ if (self->priv->primary)
+ return TRUE;
+
+ g_hash_table_iter_init (&iter, self->priv->ports);
+ while (g_hash_table_iter_next (&iter, NULL, (gpointer *) &candidate)) {
+ MMPortSubsys subsys = mm_port_get_subsys (candidate);
+
+ if (MM_IS_AT_SERIAL_PORT (candidate)) {
+ flags = mm_at_serial_port_get_flags (MM_AT_SERIAL_PORT (candidate));
+
+ if (flags & MM_AT_PORT_FLAG_PRIMARY) {
+ if (!primary)
+ primary = MM_AT_SERIAL_PORT (candidate);
+ else if (!backup_primary) {
+ /* Just in case the plugin gave us more than one primary
+ * and no secondaries, treat additional primary ports as
+ * secondary.
+ */
+ backup_primary = MM_AT_SERIAL_PORT (candidate);
+ }
+ }
+
+ if (!data && (flags & MM_AT_PORT_FLAG_PPP))
+ data = candidate;
+
+ /* Explicitly flagged secondary ports trump NONE ports for secondary */
+ if (flags & MM_AT_PORT_FLAG_SECONDARY) {
+ if (!secondary || !(mm_at_serial_port_get_flags (secondary) & MM_AT_PORT_FLAG_SECONDARY))
+ secondary = MM_AT_SERIAL_PORT (candidate);
+ }
+
+ /* Fallback secondary */
+ if (flags == MM_AT_PORT_FLAG_NONE) {
+ if (!secondary)
+ secondary = MM_AT_SERIAL_PORT (candidate);
+ else if (!backup_secondary)
+ backup_secondary = MM_AT_SERIAL_PORT (candidate);
+ }
+ } else if (MM_IS_QCDM_SERIAL_PORT (candidate)) {
+ if (!qcdm)
+ qcdm = MM_QCDM_SERIAL_PORT (candidate);
+ } else if (subsys == MM_PORT_SUBSYS_NET) {
+ /* Net device (if any) is the preferred data port */
+ if (!data || MM_IS_AT_SERIAL_PORT (data))
+ data = candidate;
+ }
+ }
+
+ /* Fall back to a secondary port if we didn't find a primary port */
+ if (!primary) {
+ if (!secondary) {
+ g_set_error_literal (error,
+ MM_CORE_ERROR,
+ MM_CORE_ERROR_FAILED,
+ "Failed to find primary port");
+ return FALSE;
+ }
+ primary = secondary;
+ secondary = NULL;
+ }
+ g_assert (primary);
+
+ /* If the plugin didn't give us any secondary ports, use any additional
+ * primary ports or backup secondary ports as secondary.
+ */
+ if (!secondary)
+ secondary = backup_primary ? backup_primary : backup_secondary;
+
+ /* Data port defaults to primary AT port */
+ if (!data)
+ data = MM_PORT (primary);
+ g_assert (data);
+
+ /* Reset flags on all ports; clear data port first since it might also
+ * be the primary or secondary port.
+ */
+ if (MM_IS_AT_SERIAL_PORT (data))
+ mm_at_serial_port_set_flags (MM_AT_SERIAL_PORT (data), MM_AT_PORT_FLAG_NONE);
+
+ mm_at_serial_port_set_flags (primary, MM_AT_PORT_FLAG_PRIMARY);
+ if (secondary)
+ mm_at_serial_port_set_flags (secondary, MM_AT_PORT_FLAG_SECONDARY);
+
+ if (MM_IS_AT_SERIAL_PORT (data)) {
+ flags = mm_at_serial_port_get_flags (MM_AT_SERIAL_PORT (data));
+ mm_at_serial_port_set_flags (MM_AT_SERIAL_PORT (data), flags | MM_AT_PORT_FLAG_PPP);
+ }
+
+ log_port (self, MM_PORT (primary), "primary");
+ log_port (self, MM_PORT (secondary), "secondary");
+ log_port (self, MM_PORT (data), "data");
+ log_port (self, MM_PORT (qcdm), "qcdm");
+
+ /* We keep new refs to the objects here */
+ self->priv->primary = g_object_ref (primary);
+ self->priv->secondary = (secondary ? g_object_ref (secondary) : NULL);
+ self->priv->data = g_object_ref (data);
+ self->priv->qcdm = (qcdm ? g_object_ref (qcdm) : NULL);
+
+ /* As soon as we get the ports organized, we initialize the modem */
+ MM_BASE_MODEM_GET_CLASS (self)->initialize (self,
+ /* FIXME: don't bother passing the port */
+ MM_AT_SERIAL_PORT (self->priv->primary),
+ NULL, /* TODO: cancellable */
+ (GAsyncReadyCallback)initialize_ready,
+ NULL);
+
+ return TRUE;
+}
+
gboolean
mm_base_modem_auth_request (MMBaseModem *self,
const gchar *authorization,
diff --git a/src/mm-base-modem.h b/src/mm-base-modem.h
index ef83d715..10211547 100644
--- a/src/mm-base-modem.h
+++ b/src/mm-base-modem.h
@@ -56,6 +56,12 @@ struct _MMBaseModem {
struct _MMBaseModemClass {
MmGdbusObjectSkeletonClass parent;
+ /* Called after the base class grabs a port so that subclasses can
+ * set port flags and other properties on the new port.
+ */
+ void (*port_grabbed) (MMBaseModem *self,
+ MMPort *port);
+
/* Modem initialization.
* Whenever the primary AT port is grabbed, this method gets called */
void (* initialize) (MMBaseModem *self,
@@ -93,7 +99,9 @@ GType mm_base_modem_get_type (void);
gboolean mm_base_modem_grab_port (MMBaseModem *self,
const gchar *subsys,
const gchar *name,
- MMPortType suggested_type);
+ MMPortType ptype,
+ MMAtPortFlag at_pflags,
+ GError **error);
void mm_base_modem_release_port (MMBaseModem *self,
const gchar *subsys,
const gchar *name);
@@ -104,6 +112,9 @@ gboolean mm_base_modem_owns_port (MMBaseModem *self,
const gchar *subsys,
const gchar *name);
+gboolean mm_base_modem_organize_ports (MMBaseModem *self,
+ GError **error);
+
MMAtSerialPort *mm_base_modem_get_port_primary (MMBaseModem *self);
MMAtSerialPort *mm_base_modem_get_port_secondary (MMBaseModem *self);
MMQcdmSerialPort *mm_base_modem_get_port_qcdm (MMBaseModem *self);
diff --git a/src/mm-broadband-modem.c b/src/mm-broadband-modem.c
index 2a710426..0c87b06b 100644
--- a/src/mm-broadband-modem.c
+++ b/src/mm-broadband-modem.c
@@ -5511,6 +5511,59 @@ modem_location_load_capabilities (MMIfaceModemLocation *self,
/*****************************************************************************/
+static void
+port_grabbed (MMBaseModem *self,
+ MMPort *port)
+{
+ GRegex *regex;
+ GPtrArray *array;
+ int i;
+
+ /* Nothing special to be done on non-AT ports */
+ if (!MM_IS_AT_SERIAL_PORT (port))
+ return;
+
+ /* Set up CREG unsolicited message handlers, with NULL callbacks */
+ array = mm_3gpp_creg_regex_get (FALSE);
+ for (i = 0; i < array->len; i++) {
+ mm_at_serial_port_add_unsolicited_msg_handler (MM_AT_SERIAL_PORT (port),
+ (GRegex *)g_ptr_array_index (array, i),
+ NULL,
+ NULL,
+ NULL);
+ }
+ mm_3gpp_creg_regex_destroy (array);
+
+ /* Set up CIEV unsolicited message handler, with NULL callback */
+ regex = mm_3gpp_ciev_regex_get ();
+ mm_at_serial_port_add_unsolicited_msg_handler (MM_AT_SERIAL_PORT (port),
+ regex,
+ NULL,
+ NULL,
+ NULL);
+ g_regex_unref (regex);
+
+ /* Set up CMTI unsolicited message handler, with NULL callback */
+ regex = mm_3gpp_cmti_regex_get ();
+ mm_at_serial_port_add_unsolicited_msg_handler (MM_AT_SERIAL_PORT (port),
+ regex,
+ NULL,
+ NULL,
+ NULL);
+ g_regex_unref (regex);
+
+ /* Set up CUSD unsolicited message handler, with NULL callback */
+ regex = mm_3gpp_cusd_regex_get ();
+ mm_at_serial_port_add_unsolicited_msg_handler (MM_AT_SERIAL_PORT (port),
+ regex,
+ NULL,
+ NULL,
+ NULL);
+ g_regex_unref (regex);
+}
+
+/*****************************************************************************/
+
typedef enum {
DISABLING_STEP_FIRST,
DISABLING_STEP_DISCONNECT_BEARERS,
@@ -6741,6 +6794,7 @@ mm_broadband_modem_class_init (MMBroadbandModemClass *klass)
object_class->dispose = dispose;
object_class->finalize = finalize;
+ base_modem_class->port_grabbed = port_grabbed;
base_modem_class->initialize = initialize;
base_modem_class->initialize_finish = initialize_finish;
base_modem_class->enable = enable;
diff --git a/src/mm-manager.c b/src/mm-manager.c
index e3a793b6..6b8ceba9 100644
--- a/src/mm-manager.c
+++ b/src/mm-manager.c
@@ -115,6 +115,8 @@ remove_modem (MMManager *manager,
mm_dbg ("Unexported modem '%s' from path '%s'", device, path);
g_free (path);
+ } else {
+ mm_dbg ("Removing modem '%s', which wasn't exported yet", device);
}
/* Run dispose before unref-ing, in order to cleanup the SIM object,
@@ -161,6 +163,7 @@ static void
check_export_modem (MMManager *self,
MMBaseModem *modem)
{
+ GError *error = NULL;
static guint32 id = 0;
const gchar *modem_physdev;
const gchar *name;
@@ -194,12 +197,22 @@ check_export_modem (MMManager *self,
return;
}
- /* If modem not yet valid, don't export it */
- if (!mm_base_modem_get_valid (modem)) {
- mm_dbg ("Not exporting invalid modem '%s'", modem_physdev);
+ /* Plugin manager is not trying to find more ports supported by this device,
+ * so we can organize the ports now (if not done already). */
+ if (!mm_base_modem_organize_ports (modem, &error)) {
+ /* If the ports were not properly organized, the modem will be marked as
+ * invalid and therefore removed */
+ mm_err ("Failed to organize modem ports: '%s'",
+ error->message);
+ g_error_free (error);
+ remove_modem (self, modem);
return;
}
+ /* If modem not yet valid (not fully initialized), don't export it */
+ if (!mm_base_modem_get_valid (modem))
+ return;
+
/* Don't export already exported modems */
g_object_get (modem,
"g-object-path", &path,
diff --git a/src/mm-port-probe.c b/src/mm-port-probe.c
index 268e9380..744889d0 100644
--- a/src/mm-port-probe.c
+++ b/src/mm-port-probe.c
@@ -797,6 +797,25 @@ mm_port_probe_is_qcdm (MMPortProbe *self)
return self->priv->is_qcdm;
}
+MMPortType
+mm_port_probe_get_port_type (MMPortProbe *self)
+{
+ g_return_val_if_fail (MM_IS_PORT_PROBE (self), FALSE);
+
+ if (g_str_equal (self->priv->subsys, "net"))
+ return MM_PORT_TYPE_UNKNOWN;
+
+ if (self->priv->flags & MM_PORT_PROBE_QCDM &&
+ self->priv->is_qcdm)
+ return MM_PORT_TYPE_QCDM;
+
+ if (self->priv->flags & MM_PORT_PROBE_AT &&
+ self->priv->is_at)
+ return MM_PORT_TYPE_AT;
+
+ return MM_PORT_TYPE_UNKNOWN;
+}
+
GUdevDevice *
mm_port_probe_get_port (MMPortProbe *self)
{
diff --git a/src/mm-port-probe.h b/src/mm-port-probe.h
index 996b10a1..8986a829 100644
--- a/src/mm-port-probe.h
+++ b/src/mm-port-probe.h
@@ -24,6 +24,7 @@
#include <gudev/gudev.h>
#include "mm-port-probe-at-command.h"
+#include "mm-at-serial-port.h"
#define MM_TYPE_PORT_PROBE (mm_port_probe_get_type ())
#define MM_PORT_PROBE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), MM_TYPE_PORT_PROBE, MMPortProbe))
@@ -76,10 +77,10 @@ gboolean mm_port_probe_run_finish (MMPortProbe *self,
gboolean mm_port_probe_run_cancel (MMPortProbe *self);
/* Probing result getters */
-gboolean mm_port_probe_is_at (MMPortProbe *self);
-gboolean mm_port_probe_is_qcdm (MMPortProbe *self);
-const gchar *mm_port_probe_get_vendor (MMPortProbe *self);
-const gchar *mm_port_probe_get_product (MMPortProbe *self);
+MMPortType mm_port_probe_get_port_type (MMPortProbe *self);
+gboolean mm_port_probe_is_at (MMPortProbe *self);
+gboolean mm_port_probe_is_qcdm (MMPortProbe *self);
+const gchar *mm_port_probe_get_vendor (MMPortProbe *self);
+const gchar *mm_port_probe_get_product (MMPortProbe *self);
#endif /* MM_PORT_PROBE_H */
-
diff --git a/src/mm-port.h b/src/mm-port.h
index d84212ed..084dceab 100644
--- a/src/mm-port.h
+++ b/src/mm-port.h
@@ -29,7 +29,6 @@ typedef enum { /*< underscore_name=mm_port_subsys >*/
typedef enum { /*< underscore_name=mm_port_type >*/
MM_PORT_TYPE_UNKNOWN = 0x0,
- MM_PORT_TYPE_AT,
MM_PORT_TYPE_IGNORED,
MM_PORT_TYPE_AT,
MM_PORT_TYPE_QCDM,