misc: fs_loader: Switching private data allocation to DM auto allocation
authorTien Fong Chee <tien.fong.chee@intel.com>
Mon, 10 Dec 2018 13:29:44 +0000 (21:29 +0800)
committerTom Rini <trini@konsulko.com>
Tue, 15 Jan 2019 20:28:54 +0000 (15:28 -0500)
Switching private data manual allocation to driver model auto allocation
so users no longer need to deallocate themself because this would be
deallocated by driver model when the device is no longer required.

Signed-off-by: Tien Fong Chee <tien.fong.chee@intel.com>
Reviewed-by: Simon Glass <sjg@chromium.org>
doc/driver-model/fs_firmware_loader.txt
drivers/misc/fs_loader.c
include/fs_loader.h

index 290915a9598818ba31291b10781aa2dc4fe45f01..b9aee848cc5eecdcbe937a8156a9acba7669161a 100644 (file)
@@ -74,17 +74,16 @@ Firmware storage device described in device tree source
 File system firmware Loader API
 -------------------------------
 
-int request_firmware_into_buf(struct device_platdata *plat,
+int request_firmware_into_buf(struct udevice *dev,
                                 const char *name,
-                                void *buf, size_t size, u32 offset,
-                                struct firmware **firmwarep)
+                                void *buf, size_t size, u32 offset)
 --------------------------------------------------------------------
 Load firmware into a previously allocated buffer
 
 Parameters:
 
-1. struct device_platdata *plat
-       Platform data such as storage and partition firmware loading from
+1. struct udevice *dev
+       An instance of a driver
 
 2. const char *name
        name of firmware file
@@ -98,36 +97,16 @@ Parameters:
 5. u32 offset
        offset of a file for start reading into buffer
 
-6. struct firmware **firmwarep
-       pointer to firmware image
-
 return:
        size of total read
        -ve when error
 
 Description:
-       The firmware is loaded directly into the buffer pointed to by buf and
-       the @firmwarep data member is pointed at buf
-
-Note: Memory would be allocated for firmware image, hence user should
-         free() *firmwarep and *firmwarep->priv structs after usage of
-         request_firmware_into_buf(), otherwise it will always leak memory
-         while subsequent calls of request_firmware_into_buf() with the same
-         *firmwarep argument. Those arguments can be free through calling API
-         below release_firmware();
+       The firmware is loaded directly into the buffer pointed to by buf
 
 Example of creating firmware loader instance and calling
 request_firmware_into_buf API:
        if (uclass_get_device(UCLASS_FS_FIRMWARE_LOADER, 0, &dev)) {
-               request_firmware_into_buf(dev->plat, filename, buffer_location,
-                                        buffer_size, offset_ofreading, &fw);
+               request_firmware_into_buf(dev, filename, buffer_location,
+                                        buffer_size, offset_ofreading);
        }
-
-void release_firmware(struct firmware *firmware)
-------------------------------------------------
-Release the resource associated with a firmware image
-
-Parameters:
-
-1. struct firmware *firmware
-       Firmware resource to release
index baa5f8302aeb8c050cbbdacf819fc3e02e095e8d..57a14a3479a39bf0b6f9282e545e54788660da55 100644 (file)
 
 DECLARE_GLOBAL_DATA_PTR;
 
-struct firmware_priv {
-       const char *name;       /* Filename */
-       u32 offset;             /* Offset of reading a file */
+/**
+ * struct firmware - A place for storing firmware and its attribute data.
+ *
+ * This holds information about a firmware and its content.
+ *
+ * @size: Size of a file
+ * @data: Buffer for file
+ * @priv: Firmware loader private fields
+ * @name: Filename
+ * @offset: Offset of reading a file
+ */
+struct firmware {
+       size_t size;
+       const u8 *data;
+       const char *name;
+       u32 offset;
 };
 
 #ifdef CONFIG_CMD_UBIFS
@@ -88,74 +101,42 @@ static int select_fs_dev(struct device_platdata *plat)
 /**
  * _request_firmware_prepare - Prepare firmware struct.
  *
+ * @dev: An instance of a driver.
  * @name: Name of firmware file.
  * @dbuf: Address of buffer to load firmware into.
  * @size: Size of buffer.
  * @offset: Offset of a file for start reading into buffer.
- * @firmwarep: Pointer to pointer to firmware image.
  *
  * Return: Negative value if fail, 0 for successful.
  */
-static int _request_firmware_prepare(const char *name, void *dbuf,
-                                   size_t size, u32 offset,
-                                   struct firmware **firmwarep)
+static int _request_firmware_prepare(struct udevice *dev,
+                                   const char *name, void *dbuf,
+                                   size_t size, u32 offset)
 {
        if (!name || name[0] == '\0')
                return -EINVAL;
 
-       /* No memory allocation is required if *firmwarep is allocated */
-       if (!(*firmwarep)) {
-               (*firmwarep) = calloc(1, sizeof(struct firmware));
-               if (!(*firmwarep))
-                       return -ENOMEM;
+       struct firmware *firmwarep = dev_get_priv(dev);
 
-               (*firmwarep)->priv = calloc(1, sizeof(struct firmware_priv));
-               if (!(*firmwarep)->priv) {
-                       free(*firmwarep);
-                       return -ENOMEM;
-               }
-       } else if (!(*firmwarep)->priv) {
-               (*firmwarep)->priv = calloc(1, sizeof(struct firmware_priv));
-               if (!(*firmwarep)->priv) {
-                       free(*firmwarep);
-                       return -ENOMEM;
-               }
-       }
+       if (!firmwarep)
+               return -ENOMEM;
 
-       ((struct firmware_priv *)((*firmwarep)->priv))->name = name;
-       ((struct firmware_priv *)((*firmwarep)->priv))->offset = offset;
-       (*firmwarep)->data = dbuf;
-       (*firmwarep)->size = size;
+       firmwarep->name = name;
+       firmwarep->offset = offset;
+       firmwarep->data = dbuf;
+       firmwarep->size = size;
 
        return 0;
 }
 
-/**
- * release_firmware - Release the resource associated with a firmware image
- * @firmware: Firmware resource to release
- */
-void release_firmware(struct firmware *firmware)
-{
-       if (firmware) {
-               if (firmware->priv) {
-                       free(firmware->priv);
-                       firmware->priv = NULL;
-               }
-               free(firmware);
-       }
-}
-
 /**
  * fw_get_filesystem_firmware - load firmware into an allocated buffer.
- * @plat: Platform data such as storage and partition firmware loading from.
- * @firmware: pointer to firmware image.
+ * @dev: An instance of a driver.
  *
  * Return: Size of total read, negative value when error.
  */
-static int fw_get_filesystem_firmware(struct device_platdata *plat,
-                                    struct firmware *firmware)
+static int fw_get_filesystem_firmware(struct udevice *dev)
 {
-       struct firmware_priv *fw_priv = NULL;
        loff_t actread;
        char *storage_interface, *dev_part, *ubi_mtdpart, *ubi_volume;
        int ret;
@@ -178,20 +159,23 @@ static int fw_get_filesystem_firmware(struct device_platdata *plat,
                else
                        ret = -ENODEV;
        } else {
-               ret = select_fs_dev(plat);
+               ret = select_fs_dev(dev->platdata);
        }
 
        if (ret)
                goto out;
 
-       fw_priv = firmware->priv;
+       struct firmware *firmwarep = dev_get_priv(dev);
+
+       if (!firmwarep)
+               return -ENOMEM;
 
-       ret = fs_read(fw_priv->name, (ulong)map_to_sysmem(firmware->data),
-                       fw_priv->offset, firmware->size, &actread);
+       ret = fs_read(firmwarep->name, (ulong)map_to_sysmem(firmwarep->data),
+                       firmwarep->offset, firmwarep->size, &actread);
 
        if (ret) {
                debug("Error: %d Failed to read %s from flash %lld != %zu.\n",
-                     ret, fw_priv->name, actread, firmware->size);
+                     ret, firmwarep->name, actread, firmwarep->size);
        } else {
                ret = actread;
        }
@@ -205,33 +189,30 @@ out:
 
 /**
  * request_firmware_into_buf - Load firmware into a previously allocated buffer.
- * @plat: Platform data such as storage and partition firmware loading from.
+ * @dev: An instance of a driver.
  * @name: Name of firmware file.
  * @buf: Address of buffer to load firmware into.
  * @size: Size of buffer.
  * @offset: Offset of a file for start reading into buffer.
- * @firmwarep: Pointer to firmware image.
  *
- * The firmware is loaded directly into the buffer pointed to by @buf and
- * the @firmwarep data member is pointed at @buf.
+ * The firmware is loaded directly into the buffer pointed to by @buf.
  *
  * Return: Size of total read, negative value when error.
  */
-int request_firmware_into_buf(struct device_platdata *plat,
+int request_firmware_into_buf(struct udevice *dev,
                              const char *name,
-                             void *buf, size_t size, u32 offset,
-                             struct firmware **firmwarep)
+                             void *buf, size_t size, u32 offset)
 {
        int ret;
 
-       if (!plat)
+       if (!dev)
                return -EINVAL;
 
-       ret = _request_firmware_prepare(name, buf, size, offset, firmwarep);
+       ret = _request_firmware_prepare(dev, name, buf, size, offset);
        if (ret < 0) /* error */
                return ret;
 
-       ret = fw_get_filesystem_firmware(plat, *firmwarep);
+       ret = fw_get_filesystem_firmware(dev);
 
        return ret;
 }
@@ -286,6 +267,7 @@ U_BOOT_DRIVER(fs_loader) = {
        .probe                  = fs_loader_probe,
        .ofdata_to_platdata     = fs_loader_ofdata_to_platdata,
        .platdata_auto_alloc_size       = sizeof(struct device_platdata),
+       .priv_auto_alloc_size   = sizeof(struct firmware),
 };
 
 UCLASS_DRIVER(fs_loader) = {
index 0be4f17e6320d8385650f4921c20d2536e92dfbf..b728c06fcff3eaa5c990a6437358ef6684d57736 100644 (file)
@@ -8,21 +8,6 @@
 
 #include <dm.h>
 
-/**
- * struct firmware - A place for storing firmware and its attribute data.
- *
- * This holds information about a firmware and its content.
- *
- * @size: Size of a file
- * @data: Buffer for file
- * @priv: Firmware loader private fields
- */
-struct firmware {
-       size_t size;
-       const u8 *data;
-       void *priv;
-};
-
 /**
  * struct phandle_part - A place for storing phandle of node and its partition
  *
@@ -52,28 +37,19 @@ struct device_platdata {
        char *ubivol;
 };
 
-/**
- * release_firmware - Release the resource associated with a firmware image
- * @firmware: Firmware resource to release
- */
-void release_firmware(struct firmware *firmware);
-
 /**
  * request_firmware_into_buf - Load firmware into a previously allocated buffer.
- * @plat: Platform data such as storage and partition firmware loading from.
+ * @dev: An instance of a driver.
  * @name: Name of firmware file.
  * @buf: Address of buffer to load firmware into.
  * @size: Size of buffer.
  * @offset: Offset of a file for start reading into buffer.
- * @firmwarep: Pointer to firmware image.
  *
- * The firmware is loaded directly into the buffer pointed to by @buf and
- * the @firmwarep data member is pointed at @buf.
+ * The firmware is loaded directly into the buffer pointed to by @buf.
  *
  * Return: Size of total read, negative value when error.
  */
-int request_firmware_into_buf(struct device_platdata *plat,
+int request_firmware_into_buf(struct udevice *dev,
                              const char *name,
-                             void *buf, size_t size, u32 offset,
-                             struct firmware **firmwarep);
+                             void *buf, size_t size, u32 offset);
 #endif