]> www.infradead.org Git - mtd-utils.git/commitdiff
mtd-utils: Add new syntax to get devices by name
authorBrandon Maier <brandon.maier@collins.com>
Mon, 12 Dec 2022 18:01:58 +0000 (12:01 -0600)
committerDavid Oberhollenzer <david.oberhollenzer@sigma-star.at>
Tue, 30 May 2023 09:12:12 +0000 (11:12 +0200)
This introduces a new feature to the MTD command line utilities that
allows MTD devices to be referenced by name instead of device node. For
example this looks like:

> # Display info for the MTD device with name "data"
> mtdinfo mtd:data
> # Copy file to MTD device with name "data"
> flashcp /my/file mtd:data

This follows the syntax supported by the kernel which allows MTD
device's to be mounted by name[1].

Add the function mtd_find_dev_node() that accepts an MTD "identifier"
and returns the MTD's device node. The function accepts a string
starting with "mtd:" which it treats as the MTD's name. It then attempts
to search for the MTD, and if found maps it back to the /dev/mtdX device
node. If the string does not start with "mtd:", then assume it's the old
style and refers directly to a MTD device node.

The function is then hooked into existing tools like flashcp, mtdinfo,
flash_unlock, etc. To load in the new MTD parsing code in a consistent
way across programs.

[1] http://www.linux-mtd.infradead.org/faq/jffs2.html#L_mtdblock

Signed-off-by: Brandon Maier <brandon.maier@collins.com>
Signed-off-by: David Oberhollenzer <david.oberhollenzer@sigma-star.at>
13 files changed:
include/common.h
lib/common.c
misc-utils/Makemodule.am
misc-utils/flash_erase.c
misc-utils/flash_unlock.c
misc-utils/flashcp.c
misc-utils/mtd_debug.c
misc-utils/mtdpart.c
tests/mtd-tests/flash_readtest.c
tests/mtd-tests/flash_speed.c
tests/mtd-tests/flash_stress.c
tests/mtd-tests/flash_torture.c
ubi-utils/mtdinfo.c

index 31b6cd1cdd60c9efcb8907a400200973360e9684..303d30da5baac55dcd496375c7733eaa800c09bf 100644 (file)
@@ -236,6 +236,7 @@ do { \
 long long util_get_bytes(const char *str);
 void util_print_bytes(long long bytes, int bracket);
 int util_srand(void);
+char *mtd_find_dev_node(const char *id);
 
 /*
  * The following helpers are here to avoid compiler complaints about unchecked
index 804187866363f1f2b8162e4fc802d73b72f35c46..e27859331197c72ef3a439ffa8ae32f467620b26 100644 (file)
@@ -33,6 +33,9 @@
 #include <stdlib.h>
 #include <unistd.h>
 #include "common.h"
+#include "libmtd.h"
+
+#define MTD_DEV_PATT  "/dev/mtd%d"
 
 /**
  * get_multiplier - convert size specifier to an integer multiplier.
@@ -162,3 +165,46 @@ int util_srand(void)
        srand(seed);
        return 0;
 }
+
+/**
+ * mtd_find_dev_node - Find the device node for an MTD
+ * @id:  Identifier for the MTD. this can be the device node itself, or
+ *       "mtd:<name>" to look up MTD by name
+ *
+ * This is a helper function to convert MTD device identifiers into their
+ * device node.
+ *
+ * Returns a pointer to a string containing the device node that must be
+ * free'd, or NULL on failure.
+ */
+char *mtd_find_dev_node(const char *id)
+{
+       struct mtd_dev_info info;
+       struct libmtd_t *lib_mtd;
+       char *node;
+       int ret;
+
+       if (strncmp(id, "mtd:", 4)) {
+               /* Assume @id is the device node */
+               return strdup(id);
+       }
+
+       /* Search for MTD matching name */
+       id += 4;
+
+       lib_mtd = libmtd_open();
+       if (!lib_mtd)
+               return NULL;
+
+       ret = mtd_get_dev_info2(lib_mtd, id, &info);
+       libmtd_close(lib_mtd);
+       if (ret < 0)
+               return NULL;
+
+       node = malloc(strlen(MTD_DEV_PATT) + 20);
+       if (!node)
+               return NULL;
+
+       sprintf(node, MTD_DEV_PATT, info.mtd_num);
+       return node;
+}
index bc69b1c591954c921482e0b832a77d87ef1c99a7..1ce1a68efd68a3dc7b9502de8d2946605238036b 100644 (file)
@@ -7,8 +7,10 @@ ftl_check_SOURCES = misc-utils/ftl_check.c include/mtd_swab.h
 ftl_check_SOURCES += include/mtd/ftl-user.h
 
 mtd_debug_SOURCES = misc-utils/mtd_debug.c
+mtd_debug_LDADD = libmtd.a
 
 mtdpart_SOURCES = misc-utils/mtdpart.c
+mtdpart_LDADD = libmtd.a
 
 docfdisk_SOURCES = misc-utils/docfdisk.c include/mtd_swab.h
 docfdisk_SOURCES += include/mtd/inftl-user.h include/mtd/ftl-user.h
@@ -23,8 +25,10 @@ fectest_SOURCES = misc-utils/fectest.c misc-utils/mcast_image.h
 fectest_LDADD = libmtd.a
 
 flash_lock_SOURCES = misc-utils/flash_lock.c
+flash_lock_LDADD = libmtd.a
 
 flash_unlock_SOURCES = misc-utils/flash_unlock.c
+flash_unlock_LDADD = libmtd.a
 
 flash_otp_info_SOURCES = misc-utils/flash_otp_info.c
 
@@ -37,6 +41,7 @@ flash_otp_erase_SOURCES = misc-utils/flash_otp_erase.c
 flash_otp_write_SOURCES = misc-utils/flash_otp_write.c
 
 flashcp_SOURCES = misc-utils/flashcp.c
+flashcp_LDADD = libmtd.a
 
 flash_erase_SOURCES = misc-utils/flash_erase.c
 flash_erase_LDADD = libmtd.a
index 49a880fc28bd390ac18fb4751c3491462e15a493..000f94acf65dac0186d951f06b1531ac74d80df7 100644 (file)
@@ -71,6 +71,8 @@ static void display_help (void)
                        "      --silent      same as --quiet\n"
                        "      --help        display this help and exit\n"
                        "      --version     output version information and exit\n",
+                       "\n"
+                       "  MTD_DEVICE  MTD device node or 'mtd:<name>'\n"
                        PROGRAM_NAME);
 }
 
@@ -169,7 +171,9 @@ int main(int argc, char *argv[])
        }
        switch (argc - optind) {
        case 3:
-               mtd_device = argv[optind];
+               mtd_device = mtd_find_dev_node(argv[optind]);
+               if (!mtd_device)
+                       return errmsg("Can't find MTD device %s", argv[optind]);
                start = simple_strtoull(argv[optind + 1], &error);
                eb_cnt = simple_strtoul(argv[optind + 2], &error);
                break;
index fbbfa5177c94c9b12a4f0bee803f11b66f36e201..fa5decbc5586c30f3539c248b4021f788e372fc8 100644 (file)
@@ -51,6 +51,8 @@ static NORETURN void usage(int status)
                " -l         --lock              Lock a region of flash\n"
                " -u         --unlock            Unlock a region of flash\n"
                "\n"
+               " <mtd device>  MTD device node or 'mtd:<name>'\n"
+               "\n"
                "If offset is not specified, it defaults to 0.\n"
                "If block count is not specified, it defaults to all blocks.\n"
                "A block count of -1 means all blocks.\n",
@@ -125,7 +127,12 @@ static void process_args(int argc, char *argv[])
        }
 
        /* First non-option argument */
-       dev = argv[arg_idx++];
+       dev = mtd_find_dev_node(argv[arg_idx]);
+       if (!dev) {
+               errmsg("MTD device not found %s", argv[arg_idx]);
+               usage(EXIT_FAILURE);
+       }
+       arg_idx++;
 
        /* Second non-option argument */
        if (arg_idx < argc)
index 50f8c04f267e535438dddd4203e0e2a049d47b1e..e1be29273dddc6c3d6508eaeab5fa4a1da1f7d68 100644 (file)
@@ -110,7 +110,7 @@ static NORETURN void showusage(bool error)
                        "   -A | --erase-all Erases the whole device regardless of the image size\n"
                        "   -V | --version   Show version information and exit\n"
                        "   <filename>       File which you want to copy to flash\n"
-                       "   <device>         Flash device to write to (e.g. /dev/mtd0, /dev/mtd1, etc.)\n"
+                       "   <device>         Flash device node or 'mtd:<name>' to write to (e.g. /dev/mtd0, /dev/mtd1, mtd:data, etc.)\n"
                        "\n",
                        PROGRAM_NAME);
 
@@ -275,7 +275,10 @@ int main (int argc,char *argv[])
                DEBUG("Got filename: %s\n",filename);
 
                flags |= FLAG_DEVICE;
-               device = argv[optind+1];
+               device = mtd_find_dev_node(argv[optind+1]);
+               if (!device)
+                       log_failure("Failed to find device %s\n", argv[optind+1]);
+
                DEBUG("Got device: %s\n",device);
        }
 
index c0b710945c9e62fbb6d67a6e89561807956c6c73..abee5e3670e5606ac99ff5a3174a3c35a171de37 100644 (file)
@@ -348,6 +348,7 @@ int main(int argc, char *argv[])
 {
        int err = 0, fd;
        int open_flag;
+       char *dev;
 
        enum {
                OPT_INFO,
@@ -369,8 +370,12 @@ int main(int argc, char *argv[])
                showusage();
 
        /* open device */
+       dev = mtd_find_dev_node(argv[2]);
+       if (!dev)
+               errmsg_die("Failed to find MTD device %s", argv[2]);
+
        open_flag = (option == OPT_INFO || option == OPT_READ) ? O_RDONLY : O_RDWR;
-       if ((fd = open(argv[2], O_SYNC | open_flag)) < 0)
+       if ((fd = open(dev, O_SYNC | open_flag)) < 0)
                errmsg_die("open()");
 
        switch (option) {
index c8cd79bb69c37d70c5f5c190a2e66b95dd327926..a341148a4a4595ae3c8f098b6439efd9c76ed431 100644 (file)
@@ -36,6 +36,8 @@ static void display_help(int status)
 "  -h, --help    Display this help and exit\n"
 "  -V, --version Output version information and exit\n"
 "\n"
+"  <MTD_DEVICE>  MTD device node or 'mtd:<name>'\n"
+"\n"
 "START location and SIZE of the partition are in bytes. They should align on\n"
 "eraseblock size. If SIZE is 0 the partition will go to end of MTD device.\n",
        PROGRAM_NAME
@@ -106,7 +108,10 @@ static void process_options(int argc, char * const argv[])
                display_help(EXIT_FAILURE);
 
        const char *s_command = argv[optind++];
-       mtddev = argv[optind++];
+       mtddev = mtd_find_dev_node(argv[optind]);
+       if (!mtddev)
+               errmsg_die("MTD device not found %s", argv[optind]);
+       optind++;
 
        if (strcmp(s_command, "del") == 0 && (argc - optind) == 1) {
                const char *s_part_no = argv[optind++];
index b4f4e104ebf176386a49e2c15bc925da31fbee5c..519ff896c7b6997a299a820567370272d4d2840e 100644 (file)
@@ -125,10 +125,14 @@ static void process_options(int argc, char **argv)
                }
        }
 
-       if (optind < argc)
-               mtddev = argv[optind++];
-       else
+       if (optind < argc) {
+               mtddev = mtd_find_dev_node(argv[optind]);
+               if (!mtddev)
+                       errmsg_die("Can't find MTD device %s", argv[optind]);
+               optind++;
+       } else {
                errmsg_die("No device specified!\n");
+       }
 
        if (optind < argc)
                usage(EXIT_FAILURE);
index 0f820474cc5060de4eaf04def80f8b5dfc268c02..5721dfba755565e7a669a6401c093d1d9b2e81f9 100644 (file)
@@ -141,10 +141,14 @@ static void process_options(int argc, char **argv)
                }
        }
 
-       if (optind < argc)
-               mtddev = argv[optind++];
-       else
+       if (optind < argc) {
+               mtddev = mtd_find_dev_node(argv[optind]);
+               if (!mtddev)
+                       errmsg_die("Can't find MTD device %s", argv[optind]);
+               optind++;
+       } else {
                errmsg_die("No device specified!\n");
+       }
 
        if (optind < argc)
                usage(EXIT_FAILURE);
index b7a0fec2b8d812777285709cc8cdc277666b71f1..da39e1408ed3fc12c629d744c844a3c349ad4912 100644 (file)
@@ -126,10 +126,14 @@ static void process_options(int argc, char **argv)
                }
        }
 
-       if (optind < argc)
-               mtddev = argv[optind++];
-       else
+       if (optind < argc) {
+               mtddev = mtd_find_dev_node(argv[optind]);
+               if (!mtddev)
+                       errmsg_die("Can't find MTD device %s", argv[optind]);
+               optind++;
+       } else {
                errmsg_die("No device specified!\n");
+       }
 
        if (optind < argc)
                usage(EXIT_FAILURE);
index 5aad8e0964fd31a420b7f22765ca6c7597876784..6363f9e0f8663b08b843099ca70a1078bad0695a 100644 (file)
@@ -144,10 +144,14 @@ static void process_options(int argc, char **argv)
                }
        }
 
-       if (optind < argc)
-               mtddev = argv[optind++];
-       else
+       if (optind < argc) {
+               mtddev = mtd_find_dev_node(argv[optind]);
+               if (!mtddev)
+                       errmsg_die("Can't find MTD device %s", argv[optind]);
+               optind++;
+       } else {
                errmsg_die("No device specified!\n");
+       }
 
        if (optind < argc)
                usage(EXIT_FAILURE);
index 8bd0fc8d3c3c5ae521392a14f0ac0b5a1389a6fa..154872ded3171ec76758c6ad1b01b31664af1239 100644 (file)
@@ -54,7 +54,7 @@ static void display_help(void)
        printf(
                "%1$s version %2$s - a tool to print MTD information.\n"
                "\n"
-               "Usage: %1$s <MTD node file path> [--map | -M] [--ubi-info | -u]\n"
+               "Usage: %1$s <mtd device> [--map | -M] [--ubi-info | -u]\n"
                "       %1$s --all [--ubi-info | -u]\n"
                "       %1$s [--help | --version]\n"
                "\n"
@@ -68,6 +68,8 @@ static void display_help(void)
                "-h, --help                      print help message\n"
                "-V, --version                   print program version\n"
                "\n"
+               "<mtd device>  MTD device node or 'mtd:<name>'\n"
+               "\n"
                "Examples:\n"
                "  %1$s /dev/mtd0             print information MTD device /dev/mtd0\n"
                "  %1$s /dev/mtd0 -u          print information MTD device /dev/mtd0\n"
@@ -124,10 +126,13 @@ static int parse_opt(int argc, char * const argv[])
                }
        }
 
-       if (optind == argc - 1)
-               args.node = argv[optind];
-       else if (optind < argc)
+       if (optind == argc - 1) {
+               args.node = mtd_find_dev_node(argv[optind]);
+               if (!args.node)
+                       return errmsg("Failed to find MTD device %s", argv[optind]);
+       } else if (optind < argc) {
                return errmsg("more then one MTD device specified (use -h for help)");
+       }
 
        if (args.all && args.node)
                args.node = NULL;