[U-Boot, v1, 1/1] misc: fs_loader: Add request_firmware_into_buf_via_env API for environment-based firmware loading

Lucien.Jheng lucienzx159 at gmail.com
Wed Jul 2 16:47:53 CEST 2025


This commit adds request_firmware_into_buf_via_env() to the fs_loader driver,
enabling firmware loading into a buffer
using environment variables for path and size.
It supports multiple entries via indexed variable names
(e.g., "fw_dir0", "fw_size0").
This provides flexible, scriptable firmware loading without hardcoded details.

Signed-off-by: Lucien.Jheng <lucienzx159 at gmail.com>
---
 drivers/misc/fs_loader.c | 59 ++++++++++++++++++++++++++++++++++++++++
 include/fs_loader.h      | 18 ++++++++++++
 2 files changed, 77 insertions(+)

diff --git a/drivers/misc/fs_loader.c b/drivers/misc/fs_loader.c
index 66803f4b997..a4f4448f5cc 100644
--- a/drivers/misc/fs_loader.c
+++ b/drivers/misc/fs_loader.c
@@ -228,6 +228,65 @@ int request_firmware_into_buf(struct udevice *dev,
 	return ret;
 }

+/**
+ * request_firmware_into_buf_via_env - Load firmware using environment variables.
+ * @dev: An instance of a driver.
+ * @buf: Address of buffer to load firmware into.
+ * @offset: Offset of a file for start reading into buffer.
+ * @fw_index: Index of the firmware entry to load.
+ *
+ * This function loads firmware into the provided buffer using environment
+ * variables to determine the firmware file path, address, and size. It supports
+ * multiple firmware entries by using indexed environment variable names such as
+ * "fw_dir0", "fw_size0", etc.
+ *
+ * Return: Size of total read, negative value when error.
+ */
+int request_firmware_into_buf_via_env(struct udevice *dev,
+				      void *buf, u32 offset,
+				      unsigned int fw_index)
+{
+	char var_name[32];
+	size_t size;
+	int ret;
+
+	for (unsigned int index = 0; index < fw_index; index++) {
+		snprintf(var_name, sizeof(var_name), "fw_dir%u", index);
+		const char *name = env_get(var_name);
+
+		if (!name) {
+			printf("Error: env var %s not set.\n", var_name);
+			goto fail;
+		}
+
+		snprintf(var_name, sizeof(var_name), "fw_size%u", index);
+		size = env_get_hex(var_name, 0);
+		if (!size) {
+			printf("Error: env var %s is invalid or zero.\n", var_name);
+			goto fail;
+		}
+
+		ret = request_firmware_into_buf(dev, name, buf, size, offset);
+		if (ret < 0) {
+			printf("Error: Failed to load firmware %s, size 0x%zx.\n",
+			       name, size);
+			return ret;
+		}
+
+		buf = (void *)((uintptr_t)buf + size);
+	}
+
+	return 0;
+fail:
+	printf("Error: Failed to load firmware via environment variables.\n"
+	       "Set these environment variables for each firmware index:\n"
+	       "  fw_dirN   - path to firmware file (e.g., fw_dir0)\n"
+	       "  fw_sizeN  - size of firmware (e.g., fw_size0)\n"
+	       "Where N is the firmware index (0, 1, ...).\n");
+
+	return -EINVAL;
+}
+
 static int fs_loader_of_to_plat(struct udevice *dev)
 {
 	u32 phandlepart[2];
diff --git a/include/fs_loader.h b/include/fs_loader.h
index 5eb5b7ab4a1..0d130daacfc 100644
--- a/include/fs_loader.h
+++ b/include/fs_loader.h
@@ -64,4 +64,22 @@ int request_firmware_into_buf(struct udevice *dev,
  * Return: 0 on success, negative value on error
  */
 int get_fs_loader(struct udevice **dev);
+
+/**
+ * request_firmware_into_buf_via_env - Load firmware using environment variables.
+ * @dev: An instance of a driver.
+ * @buf: Address of buffer to load firmware into.
+ * @offset: Offset of a file for start reading into buffer.
+ * @fw_index: Index of the firmware entry to load.
+ *
+ * This function loads firmware into the provided buffer using environment
+ * variables to determine the firmware file path, address, and size. It supports
+ * multiple firmware entries by using indexed environment variable names such as
+ * "fw_dir0", "fw_size0", etc.
+ *
+ * Return: Size of total read, negative value when error.
+ */
+int request_firmware_into_buf_via_env(struct udevice *dev,
+				      void *buf, u32 offset,
+				      unsigned int fw_index);
 #endif
--
2.34.1



More information about the U-Boot mailing list