[LEDE-DEV] [PATCH v2] mount_root: implement overlay= boot option

josua.mayer97 at gmail.com josua.mayer97 at gmail.com
Tue May 10 05:45:32 PDT 2016


From: Josua Mayer <josua.mayer97 at gmail.com>

This change adds code to handle a new option on cmdline: overlay=
This is used to find the rootfs_data partition / disk when it has a
non-standard name or location.

It takes either the device node name, or the partition name:
i.e. /dev/mmcblk0p3, mmcblk0p3, rootfs_data

This option has precedence over the default name "rootfs_data", and extroot.

Signed-off-by: Josua Mayer <josua.mayer97 at gmail.com>.
---
 libfstools/ext4.c |  4 +--
 mount_root.c      | 90 +++++++++++++++++++++++++++++++++++++++++++++++++++++--
 2 files changed, 90 insertions(+), 4 deletions(-)

diff --git a/libfstools/ext4.c b/libfstools/ext4.c
index f648aa8..2c6dd91 100644
--- a/libfstools/ext4.c
+++ b/libfstools/ext4.c
@@ -77,8 +77,8 @@ ext4_part_match(char *dev, char *name, char *filename)
 			strcpy(devname, buf + strlen("DEVNAME="));
 			continue;
 		}
-		/* Match partition name */
-		if (strstr(buf, name))  {
+		/* Match either partition name or device node name */
+		if (strstr(buf, name) || strstr(devname, name))  {
 			ret = 0;
 			break;
 		}
diff --git a/mount_root.c b/mount_root.c
index 47a3409..9bc3356 100644
--- a/mount_root.c
+++ b/mount_root.c
@@ -28,11 +28,56 @@ static int
 start(int argc, char *argv[1])
 {
 	struct volume *root;
-	struct volume *data = volume_find("rootfs_data");
+	struct volume *data = NULL;
 
 	if (!getenv("PREINIT"))
 		return -1;
 
+	/*
+	 * Check cmdline for a hint about overlay device
+	 * e.g. /dev/mmcblk0p3
+	 */
+	{
+		FILE *fp;
+		struct stat fs = {0};
+		char *buffer;
+
+		fp = fopen("/proc/cmdline", "r");
+		fstat(fileno(fp), &fs);
+		buffer = calloc(1, fs.st_size+1);
+		while (!feof(fp)) {
+			if(fscanf(fp, "overlay=%s", buffer))
+				break;
+
+			fseek(fp, 1, SEEK_CUR);
+		}
+		fclose(fp);
+
+		/*
+		 * If an overlay= argument was found, look for a volume with that name
+		 */
+		if (buffer[0]) {
+			/*
+			 * strip /dev/ prefix if any
+			 */
+			int offset = 0;
+			if (strstr(buffer, "/dev/"))
+				offset = 5;
+
+			ULOG_NOTE("Looking for overlay device given on commandline\n");
+			data = volume_find(buffer + offset);
+		}
+		free(buffer);
+	}
+
+	/*
+	 * Look for default rootfs_data partition name
+	 */
+	data = volume_find("rootfs_data");
+
+	/*
+	 * In case rootfs_data doesn't exist, only mount /dev/root for now
+	 */
 	if (!data) {
 		root = volume_find("rootfs");
 		volume_init(root);
@@ -95,8 +140,49 @@ stop(int argc, char *argv[1])
 static int
 done(int argc, char *argv[1])
 {
-	struct volume *v = volume_find("rootfs_data");
+	struct volume *v = NULL;
+	FILE *fp;
+	struct stat fs = {0};
+	char *buffer;
 
+	/*
+	 * First check if there is an overlay device hint in cmdline
+	 */
+	fp = fopen("/proc/cmdline", "r");
+	fstat(fileno(fp), &fs);
+	buffer = calloc(1, fs.st_size+1);
+	while (!feof(fp)) {
+		if (fscanf(fp, "overlay=%s", buffer))
+			break;
+
+		fseek(fp, 1, SEEK_CUR);
+	}
+	fclose(fp);
+
+	/*
+	 * If an overlay= argument was found, look for a volume with that name
+	 */
+	if (buffer[0]) {
+		/*
+		 * strip /dev/ prefix if any
+		 */
+		int offset = 0;
+		if (strstr(buffer, "/dev/"))
+			offset = 5;
+
+		v = volume_find(buffer + offset);
+	}
+	free(buffer);
+
+	/*
+	 * Now look for standard overlay partition name
+	 */
+	if (!v)
+		v = volume_find("rootfs_data");
+
+	/*
+	 * If no overlay device exists, then there is nothing to do here
+	 */
 	if (!v)
 		return -1;
 
-- 
2.6.6




More information about the Lede-dev mailing list