diff options
author | Aleksander Morgado <aleksander@lanedo.com> | 2012-09-19 10:16:41 +0200 |
---|---|---|
committer | Aleksander Morgado <aleksander@lanedo.com> | 2012-09-19 10:18:38 +0200 |
commit | ee099fcd087c0960e4b6f40b251e798e53978edf (patch) | |
tree | 26b2ba11c869983f87fe250fc4a6e95721d0d099 /src | |
parent | a6faae32608833f3d26d57bc6bace4f2a9add8bd (diff) |
plugin-manager: never suggest the Generic plugin to others
Some modems, e.g. Huawei E367, will probe first the QMI port and for some reason
it doesn't report a proper VID/PID so the Generic plugin is the one finally
accepting that port. When we probe the AT ports afterwards we already got the
Generic plugin as suggestion, and we end up not grabbing the proper primary and
secondary ports as we skipped the AT^GETPORTMODE reply.
So, from now on the Generic plugin is never suggested to other probes; except
for the case where we need the suggestion to finish a probing task which was
'deferred until suggested'.
Also, the device-level plugin can now be overwritten, if and only if, the
previously set plugin was the Generic one.
Diffstat (limited to 'src')
-rw-r--r-- | src/mm-plugin-manager.c | 73 |
1 files changed, 48 insertions, 25 deletions
diff --git a/src/mm-plugin-manager.c b/src/mm-plugin-manager.c index e5a0bd9e..67fb670d 100644 --- a/src/mm-plugin-manager.c +++ b/src/mm-plugin-manager.c @@ -161,29 +161,40 @@ port_probe_context_finished (PortProbeContext *port_probe_ctx) suggest_port_probe_result (ctx, port_probe_ctx, NULL); } else { + MMPlugin *device_plugin; + + device_plugin = (MMPlugin *)mm_device_peek_plugin (ctx->device); + /* Notify the plugin to the device, if this is the first port probing - * result we got. */ - if (!mm_device_peek_plugin (ctx->device)) { - mm_dbg ("(%s/%s): found best plugin (%s) for device (%s)", - g_udev_device_get_subsystem (port_probe_ctx->port), - g_udev_device_get_name (port_probe_ctx->port), - mm_plugin_get_name (port_probe_ctx->best_plugin), - mm_device_get_path (ctx->device)); + * result we got. + * Also, if the previously suggested plugin was the GENERIC one and now + * we're reporting a more specific one, use the new one. + */ + if (!device_plugin || + (g_str_equal (mm_plugin_get_name (device_plugin), MM_PLUGIN_GENERIC_NAME) && + device_plugin != port_probe_ctx->best_plugin)) { + /* Only log best plugin if it's not the generic one */ + if (!g_str_equal (mm_plugin_get_name (port_probe_ctx->best_plugin), MM_PLUGIN_GENERIC_NAME)) + mm_dbg ("(%s/%s): found best plugin (%s) for device (%s)", + g_udev_device_get_subsystem (port_probe_ctx->port), + g_udev_device_get_name (port_probe_ctx->port), + mm_plugin_get_name (port_probe_ctx->best_plugin), + mm_device_get_path (ctx->device)); + mm_device_set_plugin (ctx->device, G_OBJECT (port_probe_ctx->best_plugin)); /* Suggest this plugin also to other port probes */ suggest_port_probe_result (ctx, port_probe_ctx, port_probe_ctx->best_plugin); } /* Warn if the best plugin found for this port differs from the - * best plugin found for the the first probed port. */ - else if (!g_str_equal (mm_plugin_get_name (MM_PLUGIN (mm_device_peek_plugin (ctx->device))), - mm_plugin_get_name (port_probe_ctx->best_plugin))) { + * best plugin found for the the first probed port */ + else if (!g_str_equal (mm_plugin_get_name (device_plugin), + mm_plugin_get_name (port_probe_ctx->best_plugin))) mm_warn ("(%s/%s): plugin mismatch error (expected: '%s', got: '%s')", g_udev_device_get_subsystem (port_probe_ctx->port), g_udev_device_get_name (port_probe_ctx->port), mm_plugin_get_name (MM_PLUGIN (mm_device_peek_plugin (ctx->device))), mm_plugin_get_name (port_probe_ctx->best_plugin)); - } } /* Remove us from the list of running probes */ @@ -222,29 +233,28 @@ suggest_port_probe_result (FindDeviceSupportContext *ctx, for (l = ctx->running_probes; l; l = g_list_next (l)) { PortProbeContext *port_probe_ctx = l->data; + /* Plugin suggestions serve two different purposes here: + * 1) Finish all the probes which were deferred until suggested. + * 2) Suggest to other probes which plugin to test next. + * + * The exception here is when we suggest the GENERIC plugin. + * In this case, only purpose (1) is applied, this is, only + * the deferred until suggested probes get finished. + */ + if (port_probe_ctx != origin && !port_probe_ctx->best_plugin && !port_probe_ctx->suggested_plugin) { - /* TODO: Cancel probing in the port if the plugin being - * checked right now is not the one being suggested. - */ - if (suggested_plugin) { - mm_dbg ("(%s): (%s/%s) suggested plugin for port", - mm_plugin_get_name (suggested_plugin), - g_udev_device_get_subsystem (port_probe_ctx->port), - g_udev_device_get_name (port_probe_ctx->port)); - port_probe_ctx->suggested_plugin = g_object_ref (suggested_plugin); - } - /* If we got a task deferred until a suggestion comes, * complete it */ if (port_probe_ctx->defer_until_suggested) { if (suggested_plugin) { - mm_dbg ("(%s): (%s/%s) deferred task completed, got suggested plugin", - mm_plugin_get_name (suggested_plugin), + mm_dbg ("(%s/%s) deferred task completed, got suggested plugin (%s)", g_udev_device_get_subsystem (port_probe_ctx->port), - g_udev_device_get_name (port_probe_ctx->port)); + g_udev_device_get_name (port_probe_ctx->port), + mm_plugin_get_name (suggested_plugin)); /* Advance to the suggested plugin and re-check support there */ + port_probe_ctx->suggested_plugin = g_object_ref (suggested_plugin); port_probe_ctx->current = g_list_find (port_probe_ctx->current, port_probe_ctx->suggested_plugin); } else { @@ -260,6 +270,19 @@ suggest_port_probe_result (FindDeviceSupportContext *ctx, port_probe_ctx->defer_id = g_idle_add ((GSourceFunc)deferred_support_check_idle, port_probe_ctx); } + /* TODO: Cancel probing in the port if the plugin being + * checked right now is not the one being suggested. + */ + else if (suggested_plugin && + /* The GENERIC plugin is NEVER suggested to others */ + !g_str_equal (mm_plugin_get_name (suggested_plugin), + MM_PLUGIN_GENERIC_NAME)) { + mm_dbg ("(%s): (%s/%s) suggested plugin for port", + mm_plugin_get_name (suggested_plugin), + g_udev_device_get_subsystem (port_probe_ctx->port), + g_udev_device_get_name (port_probe_ctx->port)); + port_probe_ctx->suggested_plugin = g_object_ref (suggested_plugin); + } } } } |