static MMBaseModem * create_modem (MMPlugin *self, const gchar *sysfs_path, const gchar **drivers, guint16 vendor, guint16 product, GList *probes, GError **error) { #if defined WITH_QMI if (mm_port_probe_list_has_qmi_port (probes)) { mm_dbg ("QMI-powered Sierra modem found..."); return MM_BASE_MODEM (mm_broadband_modem_qmi_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); } #endif if (sierra_port_probe_list_is_icera (probes)) return MM_BASE_MODEM (mm_broadband_modem_sierra_icera_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); return MM_BASE_MODEM (mm_broadband_modem_sierra_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); }
static MMBaseModem * create_modem (MMPlugin *self, const gchar *sysfs_path, const gchar **drivers, guint16 vendor, guint16 product, GList *probes, GError **error) { propagate_port_mode_results (probes); #if defined WITH_QMI if (mm_port_probe_list_has_qmi_port (probes)) { mm_dbg ("QMI-powered Huawei modem found..."); return MM_BASE_MODEM (mm_broadband_modem_qmi_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); } #endif return MM_BASE_MODEM (mm_broadband_modem_huawei_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); }
MM_PLUGIN_DEFINE_MAJOR_VERSION MM_PLUGIN_DEFINE_MINOR_VERSION /*****************************************************************************/ static MMBaseModem * create_modem (MMPlugin *self, const gchar *sysfs_path, const gchar **drivers, guint16 vendor, guint16 product, GList *probes, GError **error) { #if defined WITH_QMI if (mm_port_probe_list_has_qmi_port (probes)) { mm_dbg ("QMI-powered SimTech modem found..."); return MM_BASE_MODEM (mm_broadband_modem_qmi_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); } #endif return MM_BASE_MODEM (mm_broadband_modem_simtech_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); }
static MMModem * grab_port (MMPluginBase *base, MMModem *existing, MMPluginBaseSupportsTask *task, GError **error) { GUdevDevice *port = NULL; MMModem *modem = NULL; const char *name, *subsys, *devfile, *sysfs_path; guint32 caps; MMPortType ptype = MM_PORT_TYPE_UNKNOWN; port = mm_plugin_base_supports_task_get_port (task); g_assert (port); devfile = g_udev_device_get_device_file (port); if (!devfile) { g_set_error (error, 0, 0, "Could not get port's sysfs file."); return NULL; } subsys = g_udev_device_get_subsystem (port); name = g_udev_device_get_name (port); /* Is it a GSM secondary port? */ if (g_object_get_data (G_OBJECT (task), TAG_SIERRA_SECONDARY_PORT)) ptype = MM_PORT_TYPE_SECONDARY; caps = mm_plugin_base_supports_task_get_probed_capabilities (task); sysfs_path = mm_plugin_base_supports_task_get_physdev_path (task); if (!existing) { if ((caps & MM_PLUGIN_BASE_PORT_CAP_GSM) || (ptype != MM_PORT_TYPE_UNKNOWN)) { modem = mm_modem_sierra_gsm_new (sysfs_path, mm_plugin_base_supports_task_get_driver (task), mm_plugin_get_name (MM_PLUGIN (base))); } else if (caps & CAP_CDMA) { modem = mm_modem_sierra_cdma_new (sysfs_path, mm_plugin_base_supports_task_get_driver (task), mm_plugin_get_name (MM_PLUGIN (base)), !!(caps & MM_PLUGIN_BASE_PORT_CAP_IS856), !!(caps & MM_PLUGIN_BASE_PORT_CAP_IS856_A)); } if (modem) { if (!mm_modem_grab_port (modem, subsys, name, ptype, NULL, error)) { g_object_unref (modem); return NULL; } } } else if (get_level_for_capabilities (caps) || (ptype != MM_PORT_TYPE_UNKNOWN)) { modem = existing; if (!mm_modem_grab_port (modem, subsys, name, ptype, NULL, error)) return NULL; } return modem; }
static void grab_port (MMManager *manager, MMPlugin *plugin, GUdevDevice *device, GUdevDevice *physical_device) { GError *error = NULL; MMBaseModem *modem; MMBaseModem *existing; existing = g_hash_table_lookup (manager->priv->modems, g_udev_device_get_sysfs_path (physical_device)); /* While grabbing the first port, modem will get created */ modem = mm_plugin_grab_port (plugin, g_udev_device_get_subsystem (device), g_udev_device_get_name (device), existing, &error); if (!modem) { mm_warn ("plugin '%s' claimed to support %s/%s but couldn't: (%d) %s", mm_plugin_get_name (plugin), g_udev_device_get_subsystem (device), g_udev_device_get_name (device), error ? error->code : -1, (error && error->message) ? error->message : "(unknown)"); g_clear_error (&error); if (existing) check_export_modem (manager, existing); return; } mm_info ("(%s): modem %s claimed port %s", mm_plugin_get_name (plugin), mm_base_modem_get_device (modem), g_udev_device_get_name (device)); if (existing) { g_assert (existing == modem); check_export_modem (manager, modem); } else { /* If the modem was just created, store it */ add_modem (manager, modem, plugin); } }
static void suggest_supports_info_result (MMPluginManager *self, const gchar *physdev_path, MMPlugin *suggested_plugin) { SupportsInfoList *list; GSList *l; list = g_hash_table_lookup (self->priv->supports, physdev_path); if (!list) return; /* Look for support infos on the same physical path */ for (l = list->info_list; l; l = g_slist_next (l)) { SupportsInfo *info = l->data; if (!info->best_plugin && !info->suggested_plugin) { /* TODO: Cancel probing in the port if the plugin being * checked right now is not the one being suggested. */ mm_dbg ("(%s): (%s) suggested plugin for port", mm_plugin_get_name (suggested_plugin), info->name); info->suggested_plugin = suggested_plugin; /* If we got a task deferred until a suggestion comes, * complete it */ if (info->defer_until_suggested) { mm_dbg ("(%s): (%s) deferred task completed, got suggested plugin", mm_plugin_get_name (suggested_plugin), info->name); /* Schedule checking support, which will end the operation */ info->best_plugin = info->suggested_plugin; info->current = NULL; info->source_id = g_idle_add ((GSourceFunc)find_port_support_idle, info); } } } }
static MMBaseModem * grab_port (MMPluginBase *base, MMBaseModem *existing, MMPortProbe *probe, GError **error) { MMBaseModem *modem = NULL; const gchar *name, *subsys; guint16 vendor = 0, product = 0; /* The Motorola plugin cannot do anything with non-AT ports */ if (!mm_port_probe_is_at (probe)) { g_set_error_literal (error, MM_CORE_ERROR, MM_CORE_ERROR_UNSUPPORTED, "Ignoring non-AT port"); return NULL; } subsys = mm_port_probe_get_port_subsys (probe); name = mm_port_probe_get_port_name (probe); if (!mm_plugin_base_get_device_ids (base, subsys, name, &vendor, &product)) { g_set_error_literal (error, MM_CORE_ERROR, MM_CORE_ERROR_FAILED, "Could not get modem product ID"); return NULL; } /* If this is the first port being grabbed, create a new modem object */ if (!existing) modem = MM_BASE_MODEM (mm_broadband_modem_motorola_new ( mm_port_probe_get_port_physdev (probe), mm_port_probe_get_port_driver (probe), mm_plugin_get_name (MM_PLUGIN (base)), vendor, product)); if (!mm_base_modem_grab_port (existing ? existing : modem, subsys, name, MM_PORT_TYPE_AT, /* we only allow AT ports here */ MM_AT_PORT_FLAG_NONE, error)) { if (modem) g_object_unref (modem); return NULL; } return existing ? existing : modem; }
static MMBaseModem * grab_port (MMPluginBase *base, MMBaseModem *existing, MMPortProbe *probe, GError **error) { MMBaseModem *modem = NULL; const gchar *name, *subsys, *driver; guint16 vendor = 0, product = 0; /* The Gobi plugin only handles AT and QCDM ports (for now) */ if (!mm_port_probe_is_at (probe) && !mm_port_probe_is_qcdm (probe)) { g_set_error_literal (error, MM_CORE_ERROR, MM_CORE_ERROR_UNSUPPORTED, "Ignoring non-AT/non-QCDM port"); return NULL; } subsys = mm_port_probe_get_port_subsys (probe); name = mm_port_probe_get_port_name (probe); driver = mm_port_probe_get_port_driver (probe); if (!mm_plugin_base_get_device_ids (base, subsys, name, &vendor, &product)) { g_set_error_literal (error, MM_CORE_ERROR, MM_CORE_ERROR_FAILED, "Could not get modem product ID"); return NULL; } /* If this is the first port being grabbed, create a new modem object */ if (!existing) modem = MM_BASE_MODEM (mm_broadband_modem_gobi_new (mm_port_probe_get_port_physdev (probe), driver, mm_plugin_get_name (MM_PLUGIN (base)), vendor, product)); if (!mm_base_modem_grab_port (existing ? existing : modem, subsys, name, mm_port_probe_get_port_type (probe), MM_AT_PORT_FLAG_NONE, error)) { if (modem) g_object_unref (modem); return NULL; } return existing ? existing : modem; }
static MMModem * grab_port (MMPluginBase *base, MMModem *existing, MMPluginBaseSupportsTask *task, GError **error) { GUdevDevice *port = NULL; MMModem *modem = NULL; const char *name, *subsys, *sysfs_path; guint32 caps; guint16 vendor = 0, product = 0; MMPortType ptype; port = mm_plugin_base_supports_task_get_port (task); g_assert (port); subsys = g_udev_device_get_subsystem (port); name = g_udev_device_get_name (port); if (!mm_plugin_base_get_device_ids (base, subsys, name, &vendor, &product)) { g_set_error (error, 0, 0, "Could not get modem product ID."); return NULL; } caps = mm_plugin_base_supports_task_get_probed_capabilities (task); ptype = mm_plugin_base_probed_capabilities_to_port_type (caps); sysfs_path = mm_plugin_base_supports_task_get_physdev_path (task); if (!existing) { if (caps & MM_PLUGIN_BASE_PORT_CAP_GSM) { modem = mm_modem_wavecom_gsm_new (sysfs_path, mm_plugin_base_supports_task_get_driver (task), mm_plugin_get_name (MM_PLUGIN (base)), vendor, product); } if (modem) { if (!mm_modem_grab_port (modem, subsys, name, ptype, MM_AT_PORT_FLAG_NONE, NULL, error)) { g_object_unref (modem); return NULL; } } } else if (get_level_for_capabilities (caps)) { modem = existing; if (!mm_modem_grab_port (modem, subsys, name, ptype, MM_AT_PORT_FLAG_NONE, NULL, error)) return NULL; } return modem; }
static MMBaseModem * grab_port (MMPluginBase *base, MMBaseModem *existing, MMPortProbe *probe, GError **error) { MMBaseModem *modem = NULL; const gchar *name, *subsys, *driver; guint16 vendor = 0, product = 0; /* The Iridium plugin cannot do anything with non-AT ports */ if (!mm_port_probe_is_at (probe)) { g_set_error_literal (error, MM_CORE_ERROR, MM_CORE_ERROR_UNSUPPORTED, "Ignoring non-AT port"); return NULL; } subsys = mm_port_probe_get_port_subsys (probe); name = mm_port_probe_get_port_name (probe); driver = mm_port_probe_get_port_driver (probe); /* Try to get Product IDs from udev. Note that it is not an error * if we can't get them in our case, as we also support serial * modems. */ mm_plugin_base_get_device_ids (base, subsys, name, &vendor, &product); /* If this is the first port being grabbed, create a new modem object */ if (!existing) modem = MM_BASE_MODEM (mm_broadband_modem_iridium_new ( mm_port_probe_get_port_physdev (probe), driver, mm_plugin_get_name (MM_PLUGIN (base)), vendor, product)); if (!mm_base_modem_grab_port (existing ? existing : modem, subsys, name, MM_PORT_TYPE_AT, /* we only allow AT ports here */ MM_AT_PORT_FLAG_NONE, error)) { if (modem) g_object_unref (modem); return NULL; } return existing ? existing : modem; }
static MMBaseModem * create_modem (MMPlugin *self, const gchar *sysfs_path, const gchar **drivers, guint16 vendor, guint16 product, GList *probes, GError **error) { return MM_BASE_MODEM (mm_broadband_modem_thuraya_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); }
static void find_port_support_ready_cb (MMPluginManager *plugin_manager, GAsyncResult *result, FindPortSupportContext *ctx) { GError *error = NULL; MMPlugin *best_plugin; best_plugin = mm_plugin_manager_find_port_support_finish (plugin_manager, result, &error); if (!best_plugin) { MMBaseModem *existing; if (error) { mm_dbg ("(%s/%s): error checking support: '%s'", g_udev_device_get_subsystem (ctx->device), g_udev_device_get_name (ctx->device), error->message); g_error_free (error); } else { mm_dbg ("(%s/%s): not supported by any plugin", g_udev_device_get_subsystem (ctx->device), g_udev_device_get_name (ctx->device)); } /* So we couldn't get a plugin for this port, we should anyway check if * there is already an existing modem for the physical device, and if * so, check if it can already be exported. */ existing = find_modem_for_device ( ctx->manager, g_udev_device_get_sysfs_path (ctx->physical_device)); if (existing) check_export_modem (ctx->manager, existing); } else { mm_dbg ("(%s/%s): found plugin '%s' giving best support", g_udev_device_get_subsystem (ctx->device), g_udev_device_get_name (ctx->device), mm_plugin_get_name ((MMPlugin *)best_plugin)); grab_port (ctx->manager, best_plugin, ctx->device, ctx->physical_device); } find_port_support_context_free (ctx); }
static gboolean try_open (gpointer user_data) { MMPluginBaseSupportsTask *task = MM_PLUGIN_BASE_SUPPORTS_TASK (user_data); MMPluginBaseSupportsTaskPrivate *task_priv = MM_PLUGIN_BASE_SUPPORTS_TASK_GET_PRIVATE (task); GError *error = NULL; task_priv->open_id = 0; if (!mm_serial_port_open (MM_SERIAL_PORT (task_priv->probe_port), &error)) { if (++task_priv->open_tries > 4) { /* took too long to open the port; give up */ g_warning ("(%s): failed to open after 4 tries.", mm_port_get_device (MM_PORT (task_priv->probe_port))); probe_complete (task); } else if (g_error_matches (error, MM_SERIAL_ERROR, MM_SERIAL_ERROR_OPEN_FAILED_NO_DEVICE)) { /* this is nozomi being dumb; try again */ task_priv->open_id = g_timeout_add_seconds (1, try_open, task); } else { /* some other hard error */ probe_complete (task); } g_clear_error (&error); } else { /* success, start probing */ GUdevDevice *port; port = mm_plugin_base_supports_task_get_port (task); g_assert (port); task_priv->full_id = g_signal_connect (task_priv->probe_port, "buffer-full", G_CALLBACK (port_buffer_full), task); g_debug ("(%s): probe requested by plugin '%s'", g_udev_device_get_name (port), mm_plugin_get_name (MM_PLUGIN (task_priv->plugin))); mm_serial_port_flash (MM_SERIAL_PORT (task_priv->probe_port), 100, TRUE, flash_done, task); } return FALSE; }
static gboolean load_plugins (MMPluginManager *self, GError **error) { GDir *dir = NULL; const gchar *fname; MMPlugin *generic_plugin = NULL; gchar *plugindir_display = NULL; if (!g_module_supported ()) { g_set_error (error, MM_CORE_ERROR, MM_CORE_ERROR_UNSUPPORTED, "GModules are not supported on your platform!"); goto out; } /* Get printable UTF-8 string of the path */ plugindir_display = g_filename_display_name (PLUGINDIR); mm_dbg ("Looking for plugins in '%s'", plugindir_display); dir = g_dir_open (PLUGINDIR, 0, NULL); if (!dir) { g_set_error (error, MM_CORE_ERROR, MM_CORE_ERROR_NO_PLUGINS, "Plugin directory '%s' not found", plugindir_display); goto out; } while ((fname = g_dir_read_name (dir)) != NULL) { gchar *path; MMPlugin *plugin; if (!g_str_has_suffix (fname, G_MODULE_SUFFIX)) continue; path = g_module_build_path (PLUGINDIR, fname); plugin = load_plugin (path); g_free (path); if (plugin) { if (g_str_equal (mm_plugin_get_name (plugin), MM_PLUGIN_GENERIC_NAME)) generic_plugin = plugin; else self->priv->plugins = g_slist_append (self->priv->plugins, plugin); } } /* Sort last plugins that request it */ self->priv->plugins = g_slist_sort (self->priv->plugins, (GCompareFunc)compare_plugins); /* Make sure the generic plugin is last */ if (generic_plugin) self->priv->plugins = g_slist_append (self->priv->plugins, generic_plugin); /* Treat as error if we don't find any plugin */ if (!self->priv->plugins) { g_set_error (error, MM_CORE_ERROR, MM_CORE_ERROR_NO_PLUGINS, "No plugins found in plugin directory '%s'", plugindir_display); goto out; } /* Now report about all the found plugins, in the same order they will be * used while checking support */ g_slist_foreach (self->priv->plugins, (GFunc)found_plugin, NULL); mm_info ("Successfully loaded %u plugins", g_slist_length (self->priv->plugins)); out: if (dir) g_dir_close (dir); g_free (plugindir_display); return !!self->priv->plugins; }
static void found_plugin (MMPlugin *plugin) { mm_info ("Loaded plugin '%s'", mm_plugin_get_name (plugin)); }
static void supports_port_ready_cb (MMPlugin *plugin, GAsyncResult *result, SupportsInfo *info) { MMPluginSupportsResult support_result; GError *error = NULL; /* Get supports check results */ support_result = mm_plugin_supports_port_finish (plugin, result, &error); if (error) { mm_warn ("(%s): (%s) error when checking support: '%s'", mm_plugin_get_name (plugin), info->name, error->message); g_error_free (error); } switch (support_result) { case MM_PLUGIN_SUPPORTS_PORT_SUPPORTED: /* Found a best plugin */ info->best_plugin = plugin; if (info->suggested_plugin && info->suggested_plugin != plugin) { /* The last plugin we tried said it supported this port, but it * doesn't correspond with the one we're being suggested. */ g_warn_if_reached (); } mm_dbg ("(%s): (%s) found best plugin for port", mm_plugin_get_name (info->best_plugin), info->name); info->current = NULL; /* Schedule checking support, which will end the operation */ info->source_id = g_idle_add ((GSourceFunc)find_port_support_idle, info); break; case MM_PLUGIN_SUPPORTS_PORT_UNSUPPORTED: if (info->suggested_plugin) { if (info->suggested_plugin == plugin) { /* If the plugin that just completed the support check claims * not to support this port, but this plugin is clearly the * right plugin since it claimed this port's physical modem, * just drop the port. */ mm_dbg ("(%s/%s): ignoring port unsupported by physical modem's plugin", info->subsys, info->name); info->best_plugin = NULL; info->current = NULL; } else { /* The last plugin we tried is NOT the one we got suggested, so * directly check support with the suggested plugin. If we * already checked its support, it won't be checked again. */ info->current = g_slist_find (info->current, info->suggested_plugin); } } else { /* If the plugin knows it doesn't support the modem, just keep on * checking the next plugin. */ info->current = g_slist_next (info->current); } info->source_id = g_idle_add ((GSourceFunc)find_port_support_idle, info); break; case MM_PLUGIN_SUPPORTS_PORT_DEFER: /* Try with the suggested one after being deferred */ if (info->suggested_plugin) { mm_dbg ("(%s): (%s) deferring support check, suggested: %s", mm_plugin_get_name (MM_PLUGIN (info->current->data)), info->name, mm_plugin_get_name (MM_PLUGIN (info->suggested_plugin))); info->current = g_slist_find (info->current, info->suggested_plugin); } else { mm_dbg ("(%s): (%s) deferring support check", mm_plugin_get_name (MM_PLUGIN (info->current->data)), info->name); } /* Schedule checking support */ info->source_id = g_timeout_add_seconds (SUPPORTS_DEFER_TIMEOUT_SECS, (GSourceFunc)find_port_support_idle, info); break; case MM_PLUGIN_SUPPORTS_PORT_DEFER_UNTIL_SUGGESTED: /* If we arrived here and we already have a plugin suggested, use it */ if (info->suggested_plugin) { mm_dbg ("(%s): (%s) task completed, got suggested plugin", mm_plugin_get_name (info->suggested_plugin), info->name); /* Schedule checking support, which will end the operation */ info->best_plugin = info->suggested_plugin; info->current = NULL; info->source_id = g_idle_add ((GSourceFunc)find_port_support_idle, info); } else { /* We are deferred until a suggested plugin is given. If last supports task * of a given device is finished without finding a best plugin, this task * will get finished reporting unsupported. */ mm_dbg ("(%s) deferring support check until result suggested", info->name); info->defer_until_suggested = TRUE; } break; } }
static MMModem * grab_port (MMPluginBase *base, MMModem *existing, MMPluginBaseSupportsTask *task, GError **error) { GUdevDevice *port = NULL; MMModem *modem = NULL; const char *name, *subsys, *sysfs_path; guint32 caps; MMPortType ptype; MMAtPortFlags pflags = MM_AT_PORT_FLAG_NONE; guint16 vendor = 0, product = 0; port = mm_plugin_base_supports_task_get_port (task); g_assert (port); /* Look for port type hints */ if (g_udev_device_get_property_as_boolean (port, "ID_MM_ZTE_PORT_TYPE_MODEM")) pflags = MM_AT_PORT_FLAG_PRIMARY; else if (g_udev_device_get_property_as_boolean (port, "ID_MM_ZTE_PORT_TYPE_AUX")) pflags = MM_AT_PORT_FLAG_SECONDARY; subsys = g_udev_device_get_subsystem (port); name = g_udev_device_get_name (port); if (!mm_plugin_base_get_device_ids (base, subsys, name, &vendor, &product)) { g_set_error (error, 0, 0, "Could not get modem product ID."); return NULL; } caps = mm_plugin_base_supports_task_get_probed_capabilities (task); sysfs_path = mm_plugin_base_supports_task_get_physdev_path (task); ptype = mm_plugin_base_probed_capabilities_to_port_type (caps); if (!existing) { if (caps & MM_PLUGIN_BASE_PORT_CAP_GSM) { modem = mm_modem_zte_new (sysfs_path, mm_plugin_base_supports_task_get_driver (task), mm_plugin_get_name (MM_PLUGIN (base)), vendor, product); } else if (caps & CAP_CDMA) { modem = mm_generic_cdma_new (sysfs_path, mm_plugin_base_supports_task_get_driver (task), mm_plugin_get_name (MM_PLUGIN (base)), !!(caps & MM_PLUGIN_BASE_PORT_CAP_IS856), !!(caps & MM_PLUGIN_BASE_PORT_CAP_IS856_A), vendor, product); } if (modem) { if (!mm_modem_grab_port (modem, subsys, name, ptype, pflags, NULL, error)) { g_object_unref (modem); return NULL; } } } else if (get_level_for_capabilities (caps) || (!strcmp (subsys, "net"))) { modem = existing; if (!mm_modem_grab_port (modem, subsys, name, ptype, pflags, NULL, error)) return NULL; } return modem; }
static MMBaseModem * create_modem (MMPlugin *self, const gchar *sysfs_path, const gchar **drivers, guint16 vendor, guint16 product, GList *probes, GError **error) { /* Note: at this point we don't make any difference between different * Dell-branded QMI or MBIM modems; they may come from Novatel, Ericsson or * Sierra. */ #if defined WITH_QMI if (mm_port_probe_list_has_qmi_port (probes)) { mm_dbg ("QMI-powered Dell-branded modem found..."); return MM_BASE_MODEM (mm_broadband_modem_qmi_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); } #endif #if defined WITH_MBIM if (mm_port_probe_list_has_mbim_port (probes)) { mm_dbg ("MBIM-powered Dell-branded modem found..."); return MM_BASE_MODEM (mm_broadband_modem_mbim_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); } #endif if (port_probe_list_has_manufacturer_port (probes, DELL_MANUFACTURER_NOVATEL)) { mm_dbg ("Novatel-powered Dell-branded modem found..."); return MM_BASE_MODEM (mm_broadband_modem_novatel_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); } if (port_probe_list_has_manufacturer_port (probes, DELL_MANUFACTURER_SIERRA)) { mm_dbg ("Sierra-powered Dell-branded modem found..."); return MM_BASE_MODEM (mm_broadband_modem_sierra_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); } if (port_probe_list_has_manufacturer_port (probes, DELL_MANUFACTURER_TELIT)) { mm_dbg ("Telit-powered Dell-branded modem found..."); return MM_BASE_MODEM (mm_broadband_modem_telit_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); } mm_dbg ("Dell-branded generic modem found..."); return MM_BASE_MODEM (mm_broadband_modem_new (sysfs_path, drivers, mm_plugin_get_name (self), vendor, product)); }
static MMModem * grab_port (MMPluginBase *base, MMModem *existing, MMPluginBaseSupportsTask *task, GError **error) { GUdevDevice *port = NULL; MMModem *modem = NULL; const char *name, *subsys, *devfile, *sysfs_path; guint32 caps; guint16 vendor = 0, product = 0; MMPortType ptype; int usbif; MMAtPortFlags pflags = MM_AT_PORT_FLAG_NONE; port = mm_plugin_base_supports_task_get_port (task); g_assert (port); devfile = g_udev_device_get_device_file (port); if (!devfile) { g_set_error (error, 0, 0, "Could not get port's sysfs file."); return NULL; } subsys = g_udev_device_get_subsystem (port); name = g_udev_device_get_name (port); if (!mm_plugin_base_get_device_ids (base, subsys, name, &vendor, &product)) { g_set_error (error, 0, 0, "Could not get modem product ID."); return NULL; } usbif = g_udev_device_get_property_as_int (port, "ID_USB_INTERFACE_NUM"); if (usbif < 0) { g_set_error (error, 0, 0, "Could not get USB device interface number."); return NULL; } caps = mm_plugin_base_supports_task_get_probed_capabilities (task); ptype = mm_plugin_base_probed_capabilities_to_port_type (caps); if (usbif + 1 == GPOINTER_TO_INT (g_object_get_data (G_OBJECT (base), TAG_HUAWEI_PCUI_PORT))) pflags = MM_AT_PORT_FLAG_PRIMARY; else if (usbif + 1 == GPOINTER_TO_INT (g_object_get_data (G_OBJECT (base), TAG_HUAWEI_MODEM_PORT))) pflags = MM_AT_PORT_FLAG_PPP; else if (!g_object_get_data (G_OBJECT (base), TAG_GETPORTMODE_SUPPORTED)) { /* If GETPORTMODE is not supported, we assume usbif 0 is the modem port */ if ((usbif == 0) && (ptype == MM_PORT_TYPE_AT)) { pflags = MM_AT_PORT_FLAG_PPP; /* For CDMA modems we assume usbif0 is both primary and PPP, since * they don't have problems with talking on secondary ports. */ if (caps & CAP_CDMA) pflags |= MM_AT_PORT_FLAG_PRIMARY; } } sysfs_path = mm_plugin_base_supports_task_get_physdev_path (task); if (!existing) { if (caps & MM_PLUGIN_BASE_PORT_CAP_GSM) { modem = mm_modem_huawei_gsm_new (sysfs_path, mm_plugin_base_supports_task_get_driver (task), mm_plugin_get_name (MM_PLUGIN (base)), vendor, product); } else if (caps & CAP_CDMA) { modem = mm_modem_huawei_cdma_new (sysfs_path, mm_plugin_base_supports_task_get_driver (task), mm_plugin_get_name (MM_PLUGIN (base)), !!(caps & MM_PLUGIN_BASE_PORT_CAP_IS856), !!(caps & MM_PLUGIN_BASE_PORT_CAP_IS856_A), vendor, product); } if (modem) { if (!mm_modem_grab_port (modem, subsys, name, ptype, pflags, NULL, error)) { g_object_unref (modem); return NULL; } } } else { modem = existing; if (!mm_modem_grab_port (modem, subsys, name, ptype, pflags, NULL, error)) return NULL; } return modem; }
static MMBaseModem * grab_port (MMPluginBase *base, MMBaseModem *existing, MMPortProbe *probe, GError **error) { MMBaseModem *modem = NULL; GUdevDevice *port; MMPortType ptype; const gchar *name, *subsys; guint16 vendor = 0, product = 0; MMAtPortFlag pflags = MM_AT_PORT_FLAG_NONE; /* The Simtech plugin cannot do anything with non-AT non-QCDM ports */ if (!mm_port_probe_is_at (probe) && !mm_port_probe_is_qcdm (probe)) { g_set_error_literal (error, MM_CORE_ERROR, MM_CORE_ERROR_UNSUPPORTED, "Ignoring non-AT non-QCDM port"); return NULL; } port = mm_port_probe_get_port (probe); /* transfer none */ subsys = mm_port_probe_get_port_subsys (probe); name = mm_port_probe_get_port_name (probe); if (!mm_plugin_base_get_device_ids (base, subsys, name, &vendor, &product)) { g_set_error_literal (error, MM_CORE_ERROR, MM_CORE_ERROR_FAILED, "Could not get modem product ID"); return NULL; } /* Look for port type hints; just probing can't distinguish which port should * be the data/primary port on these devices. We have to tag them based on * what the Windows .INF files say the port layout should be. */ if (g_udev_device_get_property_as_boolean (port, "ID_MM_SIMTECH_PORT_TYPE_MODEM")) pflags = MM_AT_PORT_FLAG_PRIMARY; else if (g_udev_device_get_property_as_boolean (port, "ID_MM_SIMTECH_PORT_TYPE_AUX")) pflags = MM_AT_PORT_FLAG_SECONDARY; /* If the port was tagged by the udev rules but isn't a primary or secondary, * then ignore it to guard against race conditions if a device just happens * to show up with more than two AT-capable ports. */ if (pflags == MM_AT_PORT_FLAG_NONE && g_udev_device_get_property_as_boolean (port, "ID_MM_SIMTECH_TAGGED")) ptype = MM_PORT_TYPE_IGNORED; else ptype = mm_port_probe_get_port_type (probe); /* If this is the first port being grabbed, create a new modem object */ if (!existing) modem = MM_BASE_MODEM (mm_broadband_modem_simtech_new (mm_port_probe_get_port_physdev (probe), mm_port_probe_get_port_driver (probe), mm_plugin_get_name (MM_PLUGIN (base)), vendor, product)); if (!mm_base_modem_grab_port (existing ? existing : modem, subsys, name, ptype, pflags, error)) { if (modem) g_object_unref (modem); return NULL; } return existing ? existing : modem; }
static MMModem * grab_port (MMPluginBase *base, MMModem *existing, MMPluginBaseSupportsTask *task, GError **error) { GUdevDevice *port = NULL; MMModem *modem = NULL; const char *name, *subsys, *sysfs_path; guint32 caps; MMPortType ptype = MM_PORT_TYPE_UNKNOWN; port = mm_plugin_base_supports_task_get_port (task); g_assert (port); /* Look for port type hints; just probing can't distinguish which port should * be the data/primary port on these devices. We have to tag them based on * what the Windows .INF files say the port layout should be. */ if (g_udev_device_get_property_as_boolean (port, "ID_MM_LONGCHEER_PORT_TYPE_MODEM")) ptype = MM_PORT_TYPE_PRIMARY; else if (g_udev_device_get_property_as_boolean (port, "ID_MM_LONGCHEER_PORT_TYPE_AUX")) ptype = MM_PORT_TYPE_SECONDARY; /* If the device was tagged by the udev rules, then ignore any other ports * to guard against race conditions if a device just happens to show up * with more than two AT-capable ports. */ if ( (ptype == MM_PORT_TYPE_UNKNOWN) && g_udev_device_get_property_as_boolean (port, "ID_MM_LONGCHEER_TAGGED")) ptype = MM_PORT_TYPE_IGNORED; subsys = g_udev_device_get_subsystem (port); name = g_udev_device_get_name (port); caps = mm_plugin_base_supports_task_get_probed_capabilities (task); sysfs_path = mm_plugin_base_supports_task_get_physdev_path (task); if (!existing) { if (caps & MM_PLUGIN_BASE_PORT_CAP_GSM) { modem = mm_modem_longcheer_gsm_new (sysfs_path, mm_plugin_base_supports_task_get_driver (task), mm_plugin_get_name (MM_PLUGIN (base))); } else if (caps & CAP_CDMA) { modem = mm_generic_cdma_new (sysfs_path, mm_plugin_base_supports_task_get_driver (task), mm_plugin_get_name (MM_PLUGIN (base)), !!(caps & MM_PLUGIN_BASE_PORT_CAP_IS856), !!(caps & MM_PLUGIN_BASE_PORT_CAP_IS856_A)); } if (modem) { if (!mm_modem_grab_port (modem, subsys, name, ptype, NULL, error)) { g_object_unref (modem); return NULL; } } } else if (get_level_for_capabilities (caps)) { if (caps & MM_PLUGIN_BASE_PORT_CAP_QCDM) ptype = MM_PORT_TYPE_QCDM; modem = existing; if (!mm_modem_grab_port (modem, subsys, name, ptype, NULL, error)) return NULL; } return modem; }