diff options
Diffstat (limited to 'ubi-utils/src')
-rw-r--r-- | ubi-utils/src/libubi.c | 127 | ||||
-rw-r--r-- | ubi-utils/src/libubi_int.h | 1 | ||||
-rw-r--r-- | ubi-utils/src/ubiattach.c | 35 | ||||
-rw-r--r-- | ubi-utils/src/ubidetach.c | 57 | ||||
-rw-r--r-- | ubi-utils/src/ubiformat.c | 2 | ||||
-rw-r--r-- | ubi-utils/src/ubinfo.c | 34 |
6 files changed, 211 insertions, 45 deletions
diff --git a/ubi-utils/src/libubi.c b/ubi-utils/src/libubi.c index fd97774..2f19bd7 100644 --- a/ubi-utils/src/libubi.c +++ b/ubi-utils/src/libubi.c @@ -677,35 +677,120 @@ void libubi_close(libubi_t desc) free(lib); } -int ubi_attach_mtd(libubi_t desc, const char *node, - struct ubi_attach_request *req) +/** + * do_attach - perform the actual attach operation. + * @node: name of the UBI control character device node + * @r: attach request + * + * This function performs the actual UBI attach operation. Returns %0 in case of + * success and %-1 in case of failure. @r->ubi_num contains newly created UBI + * device number. + */ +static int do_attach(const char *node, const struct ubi_attach_req *r) { int fd, ret; - struct ubi_attach_req r; - - memset(&r, 0, sizeof(struct ubi_attach_req)); - - desc = desc; - r.ubi_num = req->dev_num; - r.mtd_num = req->mtd_num; - r.vid_hdr_offset = req->vid_hdr_offset; fd = open(node, O_RDONLY); if (fd == -1) return sys_errmsg("cannot open \"%s\"", node); - ret = ioctl(fd, UBI_IOCATT, &r); + ret = ioctl(fd, UBI_IOCATT, r); close(fd); if (ret == -1) return -1; - req->dev_num = r.ubi_num; - #ifdef UDEV_SETTLE_HACK // if (system("udevsettle") == -1) // return -1; usleep(100000); #endif + return ret; +} + +int ubi_attach_mtd(libubi_t desc, const char *node, + struct ubi_attach_request *req) +{ + struct ubi_attach_req r; + int ret; + + (void)desc; + + memset(&r, 0, sizeof(struct ubi_attach_req)); + r.ubi_num = req->dev_num; + r.mtd_num = req->mtd_num; + r.vid_hdr_offset = req->vid_hdr_offset; + + ret = do_attach(node, &r); + if (ret == 0) + req->dev_num = r.ubi_num; + + return ret; +} + +#ifndef MTD_CHAR_MAJOR +/* + * This is taken from kernel <linux/mtd/mtd.h> and is unlikely to change anytime + * soon. + */ +#define MTD_CHAR_MAJOR 90 +#endif + +/** + * dev_to_mtdnum - converts device node to MTD number. + * @dev: path to device node to convert + * + * This function converts given @dev to MTD device number. @dev should contain + * path to the MTD device node. Returns MTD device number in case of success and + * %-1 in case of failure (errno is set). + */ +static int dev_to_mtdnum(const char *dev) +{ + int major, minor; + struct stat sb; + + if (stat(dev, &sb) < 0) + return sys_errmsg("cannot stat \"%s\"", dev); + + if (!S_ISCHR(sb.st_mode)) { + errno = EINVAL; + return sys_errmsg("\"%s\" is not a character device", dev); + } + + major = major(sb.st_rdev); + minor = minor(sb.st_rdev); + + if (major != MTD_CHAR_MAJOR) { + errno = EINVAL; + return sys_errmsg("\"%s\" is not an MTD device", dev); + } + + return minor / 2; +} + +int ubi_attach(libubi_t desc, const char *node, struct ubi_attach_request *req) +{ + struct ubi_attach_req r; + int ret; + + if (!req->dev) + /* Fallback to opening by mtd_num */ + return ubi_attach_mtd(desc, node, req); + + memset(&r, 0, sizeof(struct ubi_attach_req)); + r.ubi_num = req->dev_num; + r.vid_hdr_offset = req->vid_hdr_offset; + + /* + * User has passed path to device node. Lets find out MTD device number + * of the device and pass it to the kernel. + */ + r.mtd_num = dev_to_mtdnum(req->dev); + if (r.mtd_num == -1) + return -1; + + ret = do_attach(node, &r); + if (ret == 0) + req->dev_num = r.ubi_num; return ret; } @@ -723,6 +808,22 @@ int ubi_detach_mtd(libubi_t desc, const char *node, int mtd_num) return ubi_remove_dev(desc, node, ubi_dev); } +int ubi_detach(libubi_t desc, const char *node, const char *dev) +{ + int mtd_num; + + if (!dev) { + errno = EINVAL; + return -1; + } + + mtd_num = dev_to_mtdnum(dev); + if (mtd_num == -1) + return -1; + + return ubi_detach_mtd(desc, node, mtd_num); +} + int ubi_remove_dev(libubi_t desc, const char *node, int ubi_dev) { int fd, ret; diff --git a/ubi-utils/src/libubi_int.h b/ubi-utils/src/libubi_int.h index 6d17d57..c3aa37a 100644 --- a/ubi-utils/src/libubi_int.h +++ b/ubi-utils/src/libubi_int.h @@ -83,6 +83,7 @@ extern "C" { * handling * @dev_max_vols: maximum volumes number count sysfs path pattern * @dev_min_io_size: minimum I/O unit size sysfs path pattern + * @dev_mtd_num: MTD device number * @ubi_vol: UBI volume sysfs directory pattern * @vol_type: volume type sysfs path pattern * @vol_dev: volume major/minor numbers file pattern diff --git a/ubi-utils/src/ubiattach.c b/ubi-utils/src/ubiattach.c index a935b42..67f8c85 100644 --- a/ubi-utils/src/ubiattach.c +++ b/ubi-utils/src/ubiattach.c @@ -39,6 +39,7 @@ struct args { int mtdn; int vidoffs; const char *node; + const char *dev; }; static struct args args = { @@ -46,6 +47,7 @@ static struct args args = { .mtdn = -1, .vidoffs = 0, .node = NULL, + .dev = NULL, }; static const char *doc = PROGRAM_NAME " version " PROGRAM_VERSION @@ -55,7 +57,9 @@ static const char *optionsstr = "-d, --devn=<UBI device number> the number to assign to the newly created UBI device\n" " (the number is assigned automatically if this is not\n" " specified\n" -"-m, --mtdn=<MTD device number> MTD device number to attach\n" +"-p, --dev-path=<path to device> path to MTD device node to attach\n" +"-m, --mtdn=<MTD device number> MTD device number to attach (alternative method, e.g\n" +" if the character device node does not exist)\n" "-O, --vid-hdr-offset VID header offset (do not specify this unless you\n" " really know what you do and the optimal defaults will\n" " be used)\n" @@ -63,14 +67,18 @@ static const char *optionsstr = "-V, --version print program version"; static const char *usage = -"Usage: " PROGRAM_NAME " <UBI control device node file name> [-m <MTD device number>] [-d <UBI device number>]\n" -"\t\t[--mtdn=<MTD device number>] [--devn <UBI device number>]\n" -"Example 1: " PROGRAM_NAME " /dev/ubi_ctrl -m 0 - attach MTD device 0 (mtd0) to UBI\n" -"Example 2: " PROGRAM_NAME " /dev/ubi_ctrl -m 0 -d 3 - attach MTD device 0 (mtd0) to UBI and\n" +"Usage: " PROGRAM_NAME " <UBI control device node file name>\n" +"\t[-m <MTD device number>] [-d <UBI device number>] [-p <path to device>]\n" +"\t[--mtdn=<MTD device number>] [--devn=<UBI device number>]\n" +"\t[--dev-path=<path to device>]\n" +"Example 1: " PROGRAM_NAME " /dev/ubi_ctrl -p /dev/mtd0 - attach /dev/mtd0 to UBI\n" +"Example 2: " PROGRAM_NAME " /dev/ubi_ctrl -m 0 - attach MTD device 0 (mtd0) to UBI\n" +"Example 3: " PROGRAM_NAME " /dev/ubi_ctrl -m 0 -d 3 - attach MTD device 0 (mtd0) to UBI and\n" " and create UBI device number 3 (ubi3)"; static const struct option long_options[] = { { .name = "devn", .has_arg = 1, .flag = NULL, .val = 'd' }, + { .name = "dev-path", .has_arg = 1, .flag = NULL, .val = 'p' }, { .name = "mtdn", .has_arg = 1, .flag = NULL, .val = 'm' }, { .name = "vid-hdr-offset", .has_arg = 1, .flag = NULL, .val = 'O' }, { .name = "help", .has_arg = 0, .flag = NULL, .val = 'h' }, @@ -84,11 +92,14 @@ static int parse_opt(int argc, char * const argv[]) int key; char *endp; - key = getopt_long(argc, argv, "m:d:O:hV", long_options, NULL); + key = getopt_long(argc, argv, "p:m:d:O:hV", long_options, NULL); if (key == -1) break; switch (key) { + case 'p': + args.dev = optarg; + break; case 'd': args.devn = strtoul(optarg, &endp, 0); if (*endp != '\0' || endp == optarg || args.devn < 0) @@ -134,8 +145,8 @@ static int parse_opt(int argc, char * const argv[]) else if (optind != argc - 1) return errmsg("more then one UBI control device specified (use -h for help)"); - if (args.mtdn == -1) - return errmsg("MTD device number was not specified (use -h for help)"); + if (args.mtdn == -1 && args.dev == NULL) + return errmsg("MTD device to attach was not specified (use -h for help)"); args.node = argv[optind]; return 0; @@ -177,10 +188,14 @@ int main(int argc, char * const argv[]) req.dev_num = args.devn; req.mtd_num = args.mtdn; req.vid_hdr_offset = args.vidoffs; + req.dev = args.dev; - err = ubi_attach_mtd(libubi, args.node, &req); + err = ubi_attach(libubi, args.node, &req); if (err) { - sys_errmsg("cannot attach mtd%d", args.mtdn); + if (args.dev) + sys_errmsg("cannot attach \"%s\"", args.dev); + else + sys_errmsg("cannot attach mtd%d", args.mtdn); goto out_libubi; } diff --git a/ubi-utils/src/ubidetach.c b/ubi-utils/src/ubidetach.c index 83584cd..335486d 100644 --- a/ubi-utils/src/ubidetach.c +++ b/ubi-utils/src/ubidetach.c @@ -38,12 +38,14 @@ struct args { int devn; int mtdn; const char *node; + const char *dev; }; static struct args args = { .devn = UBI_DEV_NUM_AUTO, .mtdn = -1, .node = NULL, + .dev = NULL, }; static const char *doc = PROGRAM_NAME " version " PROGRAM_VERSION @@ -51,22 +53,26 @@ static const char *doc = PROGRAM_NAME " version " PROGRAM_VERSION static const char *optionsstr = "-d, --devn=<UBI device number> UBI device number to delete\n" -"-m, --mtdn=<MTD device number> or altrnatively, MTD device number to detach -\n" -" this will delete corresponding UBI device\n" +"-p, --dev-path=<path to device> or alternatively, MTD device node path to detach\n" +"-m, --mtdn=<MTD device number> or alternatively, MTD device number to detach\n" "-h, --help print help message\n" "-V, --version print program version"; static const char *usage = -"Usage: " PROGRAM_NAME "<UBI control device node file name> [-d <UBI device number>] [-m <MTD device number>]\n" -"\t\t[--devn <UBI device number>] [--mtdn=<MTD device number>]\n" -"Example 1: " PROGRAM_NAME " /dev/ubi_ctrl -d 2 - delete UBI device 2 (ubi2)\n" -"Example 2: " PROGRAM_NAME " /dev/ubi_ctrl -m 0 - detach MTD device 0 (mtd0)"; +"Usage: " PROGRAM_NAME " <UBI control device node file name>\n" +"\t[-d <UBI device number>] [-m <MTD device number>] [-p <path to device>]\n" +"\t[--devn=<UBI device number>] [--mtdn=<MTD device number>]\n" +"\t[--dev-path=<path to device>]\n" +"Example 1: " PROGRAM_NAME " /dev/ubi_ctrl -p /dev/mtd0 - detach MTD device /dev/mtd0\n" +"Example 2: " PROGRAM_NAME " /dev/ubi_ctrl -d 2 - delete UBI device 2 (ubi2)\n" +"Example 3: " PROGRAM_NAME " /dev/ubi_ctrl -m 0 - detach MTD device 0 (mtd0)"; static const struct option long_options[] = { - { .name = "devn", .has_arg = 1, .flag = NULL, .val = 'd' }, - { .name = "mtdn", .has_arg = 1, .flag = NULL, .val = 'm' }, - { .name = "help", .has_arg = 0, .flag = NULL, .val = 'h' }, - { .name = "version", .has_arg = 0, .flag = NULL, .val = 'V' }, + { .name = "devn", .has_arg = 1, .flag = NULL, .val = 'd' }, + { .name = "dev-path", .has_arg = 1, .flag = NULL, .val = 'p' }, + { .name = "mtdn", .has_arg = 1, .flag = NULL, .val = 'm' }, + { .name = "help", .has_arg = 0, .flag = NULL, .val = 'h' }, + { .name = "version", .has_arg = 0, .flag = NULL, .val = 'V' }, { NULL, 0, NULL, 0}, }; @@ -76,11 +82,14 @@ static int parse_opt(int argc, char * const argv[]) int key; char *endp; - key = getopt_long(argc, argv, "m:d:hV", long_options, NULL); + key = getopt_long(argc, argv, "p:m:d:hV", long_options, NULL); if (key == -1) break; switch (key) { + case 'p': + args.dev = optarg; + break; case 'd': args.devn = strtoul(optarg, &endp, 0); if (*endp != '\0' || endp == optarg || args.devn < 0) @@ -119,11 +128,15 @@ static int parse_opt(int argc, char * const argv[]) else if (optind != argc - 1) return errmsg("more then one UBI control device specified (use -h for help)"); - if (args.mtdn == -1 && args.devn == -1) + if (args.mtdn == -1 && args.devn == -1 && args.dev == NULL) return errmsg("neither MTD nor UBI devices were specified (use -h for help)"); - if (args.mtdn != -1 && args.devn != -1) - return errmsg("specify either MTD or UBI device (use -h for help)"); + if (args.devn != -1) { + if (args.mtdn != -1 || args.dev != NULL) + return errmsg("specify either MTD or UBI device (use -h for help)"); + + } else if (args.mtdn != -1 && args.dev != NULL) + return errmsg("specify either MTD number or device node (use -h for help)"); args.node = argv[optind]; return 0; @@ -167,10 +180,18 @@ int main(int argc, char * const argv[]) goto out_libubi; } } else { - err = ubi_detach_mtd(libubi, args.node, args.mtdn); - if (err) { - sys_errmsg("cannot detach mtd%d", args.mtdn); - goto out_libubi; + if (args.dev != NULL) { + err = ubi_detach(libubi, args.node, args.dev); + if (err) { + sys_errmsg("cannot detach \"%s\"", args.dev); + goto out_libubi; + } + } else { + err = ubi_detach_mtd(libubi, args.node, args.mtdn); + if (err) { + sys_errmsg("cannot detach mtd%d", args.mtdn); + goto out_libubi; + } } } diff --git a/ubi-utils/src/ubiformat.c b/ubi-utils/src/ubiformat.c index 2316d67..8ad5051 100644 --- a/ubi-utils/src/ubiformat.c +++ b/ubi-utils/src/ubiformat.c @@ -44,7 +44,7 @@ #include "crc32.h" #include "common.h" -#define PROGRAM_VERSION "1.4" +#define PROGRAM_VERSION "1.5" #define PROGRAM_NAME "ubiformat" /* The variables below are set by command line arguments */ diff --git a/ubi-utils/src/ubinfo.c b/ubi-utils/src/ubinfo.c index 8c5a1a9..8f84382 100644 --- a/ubi-utils/src/ubinfo.c +++ b/ubi-utils/src/ubinfo.c @@ -39,6 +39,7 @@ struct args { int vol_id; int all; const char *node; + const char *vol_name; }; static struct args args = { @@ -46,6 +47,7 @@ static struct args args = { .devn = -1, .all = 0, .node = NULL, + .vol_name = NULL, }; static const char *doc = PROGRAM_NAME " version " PROGRAM_VERSION @@ -54,6 +56,7 @@ static const char *doc = PROGRAM_NAME " version " PROGRAM_VERSION static const char *optionsstr = "-d, --devn=<UBI device number> UBI device number to get information about\n" "-n, --vol_id=<volume ID> ID of UBI volume to print information about\n" +"-N, --name=<volume name> name of UBI volume to print information about\n" "-a, --all print information about all devices and volumes,\n" " or about all volumes if the UBI device was\n" " specified\n" @@ -61,8 +64,8 @@ static const char *optionsstr = "-V, --version print program version"; static const char *usage = -"Usage 1: " PROGRAM_NAME " [-d <UBI device number>] [-n <volume ID>] [-a] [-h] [-V] [--vol_id=<volume ID>]\n" -"\t\t[--devn <UBI device number>] [--all] [--help] [--version]\n" +"Usage 1: " PROGRAM_NAME " [-d <UBI device number>] [-n <volume ID> | -N <volume name>] [-a] [-h] [-V]\n" +"\t\t[--vol_id=<volume ID> | --name <volume name>] [--devn <UBI device number>] [--all] [--help] [--version]\n" "Usage 2: " PROGRAM_NAME " <UBI device node file name> [-a] [-h] [-V] [--all] [--help] [--version]\n" "Usage 3: " PROGRAM_NAME " <UBI volume node file name> [-h] [-V] [--help] [--version]\n\n" "Example 1: " PROGRAM_NAME " - (no arguments) print general UBI information\n" @@ -75,6 +78,7 @@ static const char *usage = static const struct option long_options[] = { { .name = "devn", .has_arg = 1, .flag = NULL, .val = 'd' }, { .name = "vol_id", .has_arg = 1, .flag = NULL, .val = 'n' }, + { .name = "name", .has_arg = 1, .flag = NULL, .val = 'N' }, { .name = "all", .has_arg = 0, .flag = NULL, .val = 'a' }, { .name = "help", .has_arg = 0, .flag = NULL, .val = 'h' }, { .name = "version", .has_arg = 0, .flag = NULL, .val = 'V' }, @@ -87,7 +91,7 @@ static int parse_opt(int argc, char * const argv[]) int key; char *endp; - key = getopt_long(argc, argv, "an:d:hV", long_options, NULL); + key = getopt_long(argc, argv, "an:N:d:hV", long_options, NULL); if (key == -1) break; @@ -102,6 +106,10 @@ static int parse_opt(int argc, char * const argv[]) return errmsg("bad volume ID: " "\"%s\"", optarg); break; + case 'N': + args.vol_name = optarg; + break; + case 'd': args.devn = strtoul(optarg, &endp, 0); if (*endp != '\0' || endp == optarg || args.devn < 0) @@ -174,6 +182,20 @@ static int translate_dev(libubi_t libubi, const char *node) return 0; } +static int get_vol_id_by_name(libubi_t libubi, int dev_num, const char *name) +{ + int err; + struct ubi_vol_info vol_info; + + err = ubi_get_vol_info1_nm(libubi, dev_num, name, &vol_info); + if (err) + return sys_errmsg("cannot get information about volume \"%s\" on ubi%d\n", name, dev_num); + + args.vol_id = vol_info.vol_id; + + return 0; +} + static int print_vol_info(libubi_t libubi, int dev_num, int vol_id) { int err; @@ -377,6 +399,12 @@ int main(int argc, char * const argv[]) goto out_libubi; } + if (args.vol_name) { + err = get_vol_id_by_name(libubi, args.devn, args.vol_name); + if (err) + goto out_libubi; + } + if (args.vol_id != -1 && args.devn == -1) { errmsg("volume ID is specified, but UBI device number is not " "(use -h for help)\n"); |