From: Karel Zak Date: Mon, 21 Sep 2009 11:41:10 +0000 (+0200) Subject: libblkid: add DM topology support (for old kernels) X-Git-Url: https://err.no/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=4c4d3988f65bb19e2e4265e092590373218f5180;p=util-linux libblkid: add DM topology support (for old kernels) Signed-off-by: Karel Zak --- diff --git a/shlibs/blkid/src/topology/Makefile.am b/shlibs/blkid/src/topology/Makefile.am index 7464d2a8..06927b28 100644 --- a/shlibs/blkid/src/topology/Makefile.am +++ b/shlibs/blkid/src/topology/Makefile.am @@ -7,4 +7,5 @@ noinst_LTLIBRARIES = libblkid_topology.la libblkid_topology_la_SOURCES = topology.c \ topology.h \ sysfs.c \ - md.c + md.c \ + dm.c diff --git a/shlibs/blkid/src/topology/dm.c b/shlibs/blkid/src/topology/dm.c new file mode 100644 index 00000000..138c9f4b --- /dev/null +++ b/shlibs/blkid/src/topology/dm.c @@ -0,0 +1,143 @@ +/* + * device-mapper (dm) topology + * -- this is fallback for old systems where the toplogy information are not + * exported by sysfs + * + * Copyright (C) 2009 Karel Zak + * + * This file may be redistributed under the terms of the + * GNU Lesser General Public License. + * + */ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "topology.h" + + +static int is_dm_device(dev_t devno) +{ + if (blkid_driver_has_major("device-mapper", major(devno))) + return 1; + return 0; +} + +static int probe_dm_tp(blkid_probe pr, const struct blkid_idmag *mag) +{ + const char *paths[] = { + "/usr/local/sbin/dmsetup", + "/usr/sbin/dmsetup", + "/sbin/dmsetup" + }; + int i, dmpipe[] = { -1, -1 }, stripes, stripesize; + char *cmd = NULL; + FILE *stream; + long long offset, size; + dev_t devno = blkid_probe_get_devno(pr); + + if (!devno) + goto nothing; /* probably not a block device */ + if (!is_dm_device(devno)) + goto nothing; + + for (i = 0; i < ARRAY_SIZE(paths); i++) { + struct stat sb; + if (stat(paths[i], &sb) == 0) { + cmd = (char *) paths[i]; + break; + } + } + + if (!cmd) + goto nothing; + if (pipe(dmpipe) < 0) { + DBG(DEBUG_LOWPROBE, + printf("Failed to open pipe: errno=%d", errno)); + goto nothing; + } + + switch (fork()) { + case 0: + { + char *dmargv[7], maj[16], min[16]; + + /* Plumbing */ + close(dmpipe[0]); + + if (dmpipe[1] != STDOUT_FILENO) + dup2(dmpipe[1], STDOUT_FILENO); + + /* The libblkid library could linked with setuid programs */ + if (setgid(getgid()) < 0) + exit(1); + if (setuid(getuid()) < 0) + exit(1); + + snprintf(maj, sizeof(maj), "%d", major(devno)); + snprintf(min, sizeof(min), "%d", minor(devno)); + + dmargv[0] = cmd; + dmargv[1] = "table"; + dmargv[2] = "-j"; + dmargv[3] = maj; + dmargv[4] = "-m"; + dmargv[5] = min; + dmargv[6] = NULL; + + execv(dmargv[0], dmargv); + + DBG(DEBUG_LOWPROBE, + printf("Failed to execute %s: errno=%d", cmd, errno)); + exit(1); + } + case -1: + DBG(DEBUG_LOWPROBE, + printf("Failed to forking: errno=%d", errno)); + goto nothing; + default: + break; + } + + close(dmpipe[1]); + dmpipe[1] = -1; + + stream = fdopen(dmpipe[0], "r"); + if (!stream) + goto nothing; + + i = fscanf(stream, "%lld %lld striped %d %d ", + &offset, &size, &stripes, &stripesize); + fclose(stream); + dmpipe[0] = -1; + + if (i != 4) + goto nothing; + + blkid_topology_set_minimum_io_size(pr, stripesize << 9); + blkid_topology_set_optimal_io_size(pr, (stripes * stripesize) << 9); + + return 0; + +nothing: + if (dmpipe[0] != -1) + close(dmpipe[0]); + if (dmpipe[1] != -1) + close(dmpipe[1]); + return 1; +} + +const struct blkid_idinfo dm_tp_idinfo = +{ + .name = "dm", + .probefunc = probe_dm_tp, + .magics = BLKID_NONE_MAGIC +}; + diff --git a/shlibs/blkid/src/topology/topology.c b/shlibs/blkid/src/topology/topology.c index adb59f12..d6132a8f 100644 --- a/shlibs/blkid/src/topology/topology.c +++ b/shlibs/blkid/src/topology/topology.c @@ -60,7 +60,8 @@ struct blkid_struct_topology { static const struct blkid_idinfo *idinfos[] = { &sysfs_tp_idinfo, - &md_tp_idinfo + &md_tp_idinfo, + &dm_tp_idinfo }; diff --git a/shlibs/blkid/src/topology/topology.h b/shlibs/blkid/src/topology/topology.h index ecebb330..8cfcaf98 100644 --- a/shlibs/blkid/src/topology/topology.h +++ b/shlibs/blkid/src/topology/topology.h @@ -12,6 +12,7 @@ extern int blkid_topology_set_optimal_io_size(blkid_probe pr, unsigned long val) */ extern const struct blkid_idinfo sysfs_tp_idinfo; extern const struct blkid_idinfo md_tp_idinfo; +extern const struct blkid_idinfo dm_tp_idinfo; #endif /* BLKID_TOPOLOGY_H */