Alistair Delva has uploaded this change for review. ( https://gem5-review.googlesource.com/c/public/gem5/+/51307 )

Change subject: WIP: arm: Add support for initrd/initramfs to fs
......................................................................

WIP: arm: Add support for initrd/initramfs to fs

Patch the DTB with the linux,initrd-{start,end} nodes

Change-Id: I21602e8e676e8841185ea41e7370f4302ca12c2c
---
M src/arch/arm/linux/fs_workload.cc
M src/base/loader/dtb_file.cc
M src/base/loader/dtb_file.hh
M configs/example/arm/starter_fs.py
M src/arch/arm/ArmFsWorkload.py
M src/dev/arm/RealView.py
6 files changed, 82 insertions(+), 7 deletions(-)



diff --git a/configs/example/arm/starter_fs.py b/configs/example/arm/starter_fs.py
index 11190db..7195af4 100644
--- a/configs/example/arm/starter_fs.py
+++ b/configs/example/arm/starter_fs.py
@@ -150,6 +150,9 @@
             os.path.join(m5.options.outdir, 'system.dtb')
         system.generateDtb(system.workload.dtb_filename)

+    if args.initrd:
+        system.workload.initrd_filename = args.initrd
+
     # Linux boot command flags
     kernel_cmd = [
         # Tell Linux to use the simulated serial port as a console
@@ -198,6 +201,8 @@
                         help="DTB file to load")
     parser.add_argument("--kernel", type=str, default=default_kernel,
                         help="Linux kernel")
+    parser.add_argument("--initrd", type=str, default=None,
+                        help="initrd/initramfs file to load")
     parser.add_argument("--disk-image", type=str,
                         default=default_disk,
                         help="Disk to instantiate")
diff --git a/src/arch/arm/ArmFsWorkload.py b/src/arch/arm/ArmFsWorkload.py
index 974600b..43bbd16 100644
--- a/src/arch/arm/ArmFsWorkload.py
+++ b/src/arch/arm/ArmFsWorkload.py
@@ -58,6 +58,9 @@
     dtb_filename = Param.String("",
         "File that contains the Device Tree Blob. Don't use DTB if empty.")
     dtb_addr = Param.Addr(0, "DTB or ATAGS address")
+    initrd_filename = Param.String("",
+ "File that contains the initial ramdisk. Don't use initrd if empty.")
+    initrd_addr = Param.Addr(0, "initrd/initramfs address")
     cpu_release_addr = Param.Addr(0, "cpu-release-addr property")

     machine_type = Param.ArmMachineType('DTOnly',
diff --git a/src/arch/arm/linux/fs_workload.cc b/src/arch/arm/linux/fs_workload.cc
index d512067..e724eb1 100644
--- a/src/arch/arm/linux/fs_workload.cc
+++ b/src/arch/arm/linux/fs_workload.cc
@@ -91,6 +91,21 @@
     bool dtb_file_specified = params().dtb_filename != "";

     if (kernel_has_fdt_support && dtb_file_specified) {
+        bool initrd_file_specified = params().initrd_filename != "";
+        size_t initrd_len = 0;
+
+        if (initrd_file_specified) {
+            inform("Loading initrd file: %s at address %#x\n",
+                    params().initrd_filename, params().initrd_addr);
+
+            loader::ImageFileDataPtr initrd_file_data(
+                new loader::ImageFileData(params().initrd_filename));
+            system->physProxy.writeBlob(params().initrd_addr,
+                                        initrd_file_data->data(),
+                                        initrd_file_data->len());
+            initrd_len = initrd_file_data->len();
+        }
+
         // Kernel supports flattened device tree and dtb file specified.
         // Using Device Tree Blob to describe system configuration.
inform("Loading DTB file: %s at address %#x\n", params().dtb_filename,
@@ -98,8 +113,8 @@

         auto *dtb_file = new loader::DtbFile(params().dtb_filename);

-        if (!dtb_file->addBootCmdLine(
-                    commandLine.c_str(), commandLine.size())) {
+        if (!dtb_file->addBootData(commandLine.c_str(), commandLine.size(),
+                                   params().initrd_addr, initrd_len)) {
             warn("couldn't append bootargs to DTB file: %s\n",
                  params().dtb_filename);
         }
diff --git a/src/base/loader/dtb_file.cc b/src/base/loader/dtb_file.cc
index f89b1ae..c3aa9b4 100644
--- a/src/base/loader/dtb_file.cc
+++ b/src/base/loader/dtb_file.cc
@@ -63,12 +63,15 @@
 }

 bool
-DtbFile::addBootCmdLine(const char *_args, size_t len)
+DtbFile::addBootData(const char *_cmdline, size_t cmdline_len,
+                     off_t initrd_start, size_t initrd_len)
 {
     const char *root_path = "/";
     const char *node_name = "chosen";
     const char *full_path_node_name = "/chosen";
-    const char *property_name = "bootargs";
+    const char *bootargs_property_name = "bootargs";
+    const char *linux_initrd_start_property_name = "linux,initrd-start";
+    const char *linux_initrd_end_property_name = "linux,initrd-end";

     // Make a new buffer that has extra space to add nodes/properties
     int newLen = 2 * length;
@@ -102,8 +105,8 @@
     }

     // Set the bootargs property in the /chosen node
-    ret = fdt_setprop((void *)fdt_buf_w_space, offset, property_name,
-                      (const void *)_args, len+1);
+ ret = fdt_setprop((void *)fdt_buf_w_space, offset, bootargs_property_name,
+                      (const void *)_cmdline, cmdline_len+1);
     if (ret < 0) {
warn("Error setting \"bootargs\" property to flattened device tree, "
              "errno: %d\n", ret);
@@ -111,6 +114,30 @@
         return false;
     }

+    if (initrd_len != 0) {
+        // Set the linux,initrd-start property in the /chosen node
+        ret = fdt_setprop_u64((void *)fdt_buf_w_space, offset,
+                              linux_initrd_start_property_name,
+                              (uint64_t)initrd_start);
+        if (ret < 0) {
+ warn("Error setting \"linux,initrd-start\" property to flattened "
+                 "device tree, errno: %d\n", ret);
+            delete [] fdt_buf_w_space;
+            return false;
+        }
+
+        // Set the computed linux,initrd-end property in the /chosen node
+        ret = fdt_setprop_u64((void *)fdt_buf_w_space, offset,
+                              linux_initrd_end_property_name,
+                              (uint64_t)initrd_start + initrd_len + 1);
+        if (ret < 0) {
+ warn("Error setting \"linux,initrd-len\" property to flattened "
+                 "device tree, errno: %d\n", ret);
+            delete [] fdt_buf_w_space;
+            return false;
+        }
+    }
+
     // Repack the dtb for kernel use
     ret = fdt_pack((void *)fdt_buf_w_space);
     if (ret < 0) {
diff --git a/src/base/loader/dtb_file.hh b/src/base/loader/dtb_file.hh
index f0a211f..b336c5d 100644
--- a/src/base/loader/dtb_file.hh
+++ b/src/base/loader/dtb_file.hh
@@ -58,13 +58,26 @@
     DtbFile(const std::string &name);
     ~DtbFile();

+    /** Adds the passed in Command Line options and initrd for the kernel
+      * to the proper location in the device tree.
+      * @param _cmdline command line to append
+      * @param cmdline_len length of the command line string
+      * @param initrd_addr starting physical address of initrd
+      * @param initrd_len length of initrd data in memory
+      * @return returns true on success, false otherwise
+      */
+    bool addBootData(const char* _cmdline, size_t cmdline_len,
+                     off_t initrd_addr, size_t initrd_len);
+
     /** Adds the passed in Command Line options for the kernel
       * to the proper location in the device tree.
       * @param _args command line to append
       * @param len length of the command line string
       * @return returns true on success, false otherwise
       */
-    bool addBootCmdLine(const char* _args, size_t len);
+    inline bool addBootCmdLine(const char* _args, size_t len) {
+        return addBootData(_args, len, 0, 0);
+    }

     /** Parse the DTB file enough to find the provided release
      * address and return it.
diff --git a/src/dev/arm/RealView.py b/src/dev/arm/RealView.py
index 919ff63..4aed3de 100644
--- a/src/dev/arm/RealView.py
+++ b/src/dev/arm/RealView.py
@@ -749,6 +749,7 @@
         cur_sys.workload.boot_loader = boot_loader
         cur_sys.workload.load_addr_offset = load_offset
         cur_sys.workload.dtb_addr = load_offset + dtb_addr
+        cur_sys.workload.initrd_addr = load_offset + dtb_addr + 0x200000
         cur_sys.workload.cpu_release_addr = cur_sys.workload.dtb_addr - 8

     def generateDeviceTree(self, state):

--
To view, visit https://gem5-review.googlesource.com/c/public/gem5/+/51307
To unsubscribe, or for help writing mail filters, visit https://gem5-review.googlesource.com/settings

Gerrit-Project: public/gem5
Gerrit-Branch: develop
Gerrit-Change-Id: I21602e8e676e8841185ea41e7370f4302ca12c2c
Gerrit-Change-Number: 51307
Gerrit-PatchSet: 1
Gerrit-Owner: Alistair Delva <[email protected]>
Gerrit-MessageType: newchange
_______________________________________________
gem5-dev mailing list -- [email protected]
To unsubscribe send an email to [email protected]
%(web_page_url)slistinfo%(cgiext)s/%(_internal_name)s

Reply via email to