Add a method to probe a FuUsbDevice before it is opened

This allows us to further clean up device creation.
This commit is contained in:
Richard Hughes 2017-11-30 09:32:35 +00:00
parent 450f952763
commit c3476d56de
3 changed files with 51 additions and 2 deletions

View File

@ -2927,8 +2927,13 @@ fu_engine_usb_device_added_cb (GUsbContext *ctx,
for (guint j = 0; j < plugins->len; j++) {
FuPlugin *plugin_tmp = g_ptr_array_index (plugins, j);
g_autoptr(GError) error = NULL;
if (!fu_plugin_runner_usb_device_added (plugin_tmp, usb_device, &error))
if (!fu_plugin_runner_usb_device_added (plugin_tmp, usb_device, &error)) {
if (g_error_matches (error, FWUPD_ERROR, FWUPD_ERROR_NOT_SUPPORTED)) {
g_debug ("ignoring: %s", error->message);
continue;
}
g_warning ("failed to add USB device: %s", error->message);
}
}
}

View File

@ -38,6 +38,7 @@ typedef struct
{
GUsbDevice *usb_device;
FuDeviceLocker *usb_device_locker;
gboolean done_probe;
} FuUsbDevicePrivate;
G_DEFINE_TYPE_WITH_PRIVATE (FuUsbDevice, fu_usb_device, FU_TYPE_DEVICE)
@ -151,6 +152,10 @@ fu_usb_device_open (FuUsbDevice *device, GError **error)
g_usb_device_get_pid (priv->usb_device));
g_assert (ptask != NULL);
/* probe */
if (!fu_usb_device_probe (device, error))
return FALSE;
/* open */
locker = fu_device_locker_new (priv->usb_device, error);
if (locker == NULL)
@ -253,6 +258,41 @@ fu_usb_device_close (FuUsbDevice *device, GError **error)
return TRUE;
}
/**
* fu_usb_device_probe:
* @device: A #FuUsbDevice
* @error: A #GError, or %NULL
*
* Probes a USB device, setting parameters on the object that does not need
* the device open or the interface claimed.
* If the device is not compatible then an error should be returned.
*
* Returns: %TRUE for success
*
* Since: 1.0.2
**/
gboolean
fu_usb_device_probe (FuUsbDevice *device, GError **error)
{
FuUsbDevicePrivate *priv = GET_PRIVATE (device);
FuUsbDeviceClass *klass = FU_USB_DEVICE_GET_CLASS (device);
g_return_val_if_fail (FU_IS_USB_DEVICE (device), FALSE);
g_return_val_if_fail (error == NULL || *error == NULL, FALSE);
/* already done */
if (priv->done_probe)
return TRUE;
/* subclassed */
if (klass->probe != NULL) {
if (!klass->probe (device, error))
return FALSE;
}
priv->done_probe = TRUE;
return TRUE;
}
static gchar *
_bcd_version_from_uint16 (guint16 val)
{

View File

@ -39,7 +39,9 @@ struct _FuUsbDeviceClass
GError **error);
gboolean (*close) (FuUsbDevice *device,
GError **error);
gpointer __reserved[29];
gboolean (*probe) (FuUsbDevice *device,
GError **error);
gpointer __reserved[28];
};
FuDevice *fu_usb_device_new (GUsbDevice *usb_device);
@ -50,6 +52,8 @@ gboolean fu_usb_device_open (FuUsbDevice *device,
GError **error);
gboolean fu_usb_device_close (FuUsbDevice *device,
GError **error);
gboolean fu_usb_device_probe (FuUsbDevice *device,
GError **error);
G_END_DECLS