From e1d708a4ff21405fdfcc52a26a14d428d668e17f Mon Sep 17 00:00:00 2001 From: Sergii Dmytruk Date: Tue, 19 Apr 2022 23:21:17 +0300 Subject: [PATCH] plugins/flashrom: manage flashrom context at plugin level Signed-off-by: Sergii Dmytruk --- plugins/flashrom/fu-flashrom-device.c | 74 ++++++++++----------------- plugins/flashrom/fu-flashrom-device.h | 4 +- plugins/flashrom/fu-plugin-flashrom.c | 42 ++++++++++++++- 3 files changed, 72 insertions(+), 48 deletions(-) diff --git a/plugins/flashrom/fu-flashrom-device.c b/plugins/flashrom/fu-flashrom-device.c index 10bd8a8a5..8e999324f 100644 --- a/plugins/flashrom/fu-flashrom-device.c +++ b/plugins/flashrom/fu-flashrom-device.c @@ -28,12 +28,11 @@ struct _FuFlashromDevice { FuUdevDevice parent_instance; FuIfdRegion region; struct flashrom_flashctx *flashctx; - struct flashrom_programmer *flashprog; }; G_DEFINE_TYPE(FuFlashromDevice, fu_flashrom_device, FU_TYPE_UDEV_DEVICE) -enum { PROP_0, PROP_REGION, PROP_LAST }; +enum { PROP_0, PROP_FLASHCTX, PROP_REGION, PROP_LAST }; static gboolean fu_flashrom_device_set_quirk_kv(FuDevice *device, @@ -81,37 +80,6 @@ static gboolean fu_flashrom_device_open(FuDevice *device, GError **error) { FuFlashromDevice *self = FU_FLASHROM_DEVICE(device); - gint rc; - - if (flashrom_programmer_init(&self->flashprog, "internal", NULL)) { - g_set_error_literal(error, - FWUPD_ERROR, - FWUPD_ERROR_NOT_SUPPORTED, - "programmer initialization failed"); - return FALSE; - } - rc = flashrom_flash_probe(&self->flashctx, self->flashprog, NULL); - if (rc == 3) { - g_set_error_literal(error, - FWUPD_ERROR, - FWUPD_ERROR_NOT_SUPPORTED, - "flash probe failed: multiple chips were found"); - return FALSE; - } - if (rc == 2) { - g_set_error_literal(error, - FWUPD_ERROR, - FWUPD_ERROR_NOT_SUPPORTED, - "flash probe failed: no chip was found"); - return FALSE; - } - if (rc != 0) { - g_set_error_literal(error, - FWUPD_ERROR, - FWUPD_ERROR_NOT_SUPPORTED, - "flash probe failed: unknown error"); - return FALSE; - } /* get the flash size from the device if not already been quirked */ if (fu_device_get_firmware_size_max(device) == 0) { @@ -129,15 +97,6 @@ fu_flashrom_device_open(FuDevice *device, GError **error) return TRUE; } -static gboolean -fu_flashrom_device_close(FuDevice *device, GError **error) -{ - FuFlashromDevice *self = FU_FLASHROM_DEVICE(device); - flashrom_flash_release(self->flashctx); - flashrom_programmer_shutdown(self->flashprog); - return TRUE; -} - static gboolean fu_flashrom_device_prepare(FuDevice *device, FuProgress *progress, @@ -326,6 +285,9 @@ fu_flashrom_device_get_property(GObject *object, guint prop_id, GValue *value, G { FuFlashromDevice *self = FU_FLASHROM_DEVICE(object); switch (prop_id) { + case PROP_FLASHCTX: + g_value_set_pointer(value, self->flashctx); + break; case PROP_REGION: g_value_set_uint(value, self->region); break; @@ -343,6 +305,9 @@ fu_flashrom_device_set_property(GObject *object, { FuFlashromDevice *self = FU_FLASHROM_DEVICE(object); switch (prop_id) { + case PROP_FLASHCTX: + self->flashctx = g_value_get_pointer(value); + break; case PROP_REGION: self->region = g_value_get_uint(value); fu_device_set_logical_id(FU_DEVICE(self), fu_ifd_region_to_string(self->region)); @@ -383,22 +348,39 @@ fu_flashrom_device_class_init(FuFlashromDeviceClass *klass) G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY | G_PARAM_STATIC_NAME); g_object_class_install_property(object_class, PROP_REGION, pspec); + /** + * FuFlashromDevice:flashctx: + * + * The JSON root member for the device. + */ + pspec = + g_param_spec_pointer("flashctx", + NULL, + NULL, + G_PARAM_CONSTRUCT_ONLY | G_PARAM_READWRITE | G_PARAM_STATIC_NAME); + g_object_class_install_property(object_class, PROP_FLASHCTX, pspec); + object_class->constructed = fu_flashrom_device_constructed; object_class->finalize = fu_flashrom_device_finalize; klass_device->set_quirk_kv = fu_flashrom_device_set_quirk_kv; klass_device->probe = fu_flashrom_device_probe; klass_device->open = fu_flashrom_device_open; - klass_device->close = fu_flashrom_device_close; klass_device->set_progress = fu_flashrom_device_set_progress; klass_device->prepare = fu_flashrom_device_prepare; klass_device->write_firmware = fu_flashrom_device_write_firmware; } FuDevice * -fu_flashrom_device_new(FuContext *ctx, FuIfdRegion region) +fu_flashrom_device_new(FuContext *ctx, struct flashrom_flashctx *flashctx, FuIfdRegion region) { - return FU_DEVICE( - g_object_new(FU_TYPE_FLASHROM_DEVICE, "context", ctx, "region", region, NULL)); + return FU_DEVICE(g_object_new(FU_TYPE_FLASHROM_DEVICE, + "context", + ctx, + "flashctx", + flashctx, + "region", + region, + NULL)); } FuIfdRegion diff --git a/plugins/flashrom/fu-flashrom-device.h b/plugins/flashrom/fu-flashrom-device.h index 9984a64f9..2ad1951e8 100644 --- a/plugins/flashrom/fu-flashrom-device.h +++ b/plugins/flashrom/fu-flashrom-device.h @@ -12,8 +12,10 @@ #define FU_TYPE_FLASHROM_DEVICE (fu_flashrom_device_get_type()) G_DECLARE_FINAL_TYPE(FuFlashromDevice, fu_flashrom_device, FU, FLASHROM_DEVICE, FuUdevDevice) +struct flashrom_flashctx; + FuDevice * -fu_flashrom_device_new(FuContext *ctx, FuIfdRegion region); +fu_flashrom_device_new(FuContext *ctx, struct flashrom_flashctx *flashctx, FuIfdRegion region); FuIfdRegion fu_flashrom_device_get_region(FuFlashromDevice *self); diff --git a/plugins/flashrom/fu-plugin-flashrom.c b/plugins/flashrom/fu-plugin-flashrom.c index adaa5fa02..3955600c5 100644 --- a/plugins/flashrom/fu-plugin-flashrom.c +++ b/plugins/flashrom/fu-plugin-flashrom.c @@ -18,6 +18,8 @@ #define SELFCHECK_TRUE 1 struct FuPluginData { + struct flashrom_flashctx *flashctx; + struct flashrom_programmer *flashprog; gchar *guid; /* GUID from quirks that activated this plugin */ }; @@ -35,6 +37,10 @@ static void fu_plugin_flashrom_destroy(FuPlugin *plugin) { FuPluginData *data = fu_plugin_get_data(plugin); + if (data->flashctx != NULL) + flashrom_flash_release(data->flashctx); + if (data->flashprog != NULL) + flashrom_programmer_shutdown(data->flashprog); g_free(data->guid); } @@ -162,12 +168,13 @@ fu_plugin_flashrom_add_device(FuPlugin *plugin, GError **error) { FuContext *ctx = fu_plugin_get_context(plugin); + FuPluginData *data = fu_plugin_get_data(plugin); const gchar *dmi_vendor; const gchar *product = fu_context_get_hwid_value(ctx, FU_HWIDS_KEY_PRODUCT_NAME); const gchar *vendor = fu_context_get_hwid_value(ctx, FU_HWIDS_KEY_MANUFACTURER); const gchar *region_str = fu_ifd_region_to_string(region); g_autofree gchar *name = g_strdup_printf("%s (%s)", product, region_str); - g_autoptr(FuDevice) device = fu_flashrom_device_new(ctx, region); + g_autoptr(FuDevice) device = fu_flashrom_device_new(ctx, data->flashctx, region); fu_device_set_name(device, name); fu_device_set_vendor(device, vendor); @@ -261,6 +268,7 @@ fu_plugin_flashrom_find_guid(FuPlugin *plugin, GError **error) static gboolean fu_plugin_flashrom_startup(FuPlugin *plugin, GError **error) { + gint rc; const gchar *guid; FuPluginData *data = fu_plugin_get_data(plugin); @@ -278,6 +286,38 @@ fu_plugin_flashrom_startup(FuPlugin *plugin, GError **error) return FALSE; } flashrom_set_log_callback(fu_plugin_flashrom_debug_cb); + + if (flashrom_programmer_init(&data->flashprog, "internal", NULL)) { + g_set_error_literal(error, + FWUPD_ERROR, + FWUPD_ERROR_NOT_SUPPORTED, + "programmer initialization failed"); + return FALSE; + } + + rc = flashrom_flash_probe(&data->flashctx, data->flashprog, NULL); + if (rc == 3) { + g_set_error_literal(error, + FWUPD_ERROR, + FWUPD_ERROR_NOT_SUPPORTED, + "flash probe failed: multiple chips were found"); + return FALSE; + } + if (rc == 2) { + g_set_error_literal(error, + FWUPD_ERROR, + FWUPD_ERROR_NOT_SUPPORTED, + "flash probe failed: no chip was found"); + return FALSE; + } + if (rc != 0) { + g_set_error_literal(error, + FWUPD_ERROR, + FWUPD_ERROR_NOT_SUPPORTED, + "flash probe failed: unknown error"); + return FALSE; + } + return TRUE; }