[Libguestfs] [PATCH RFC] blkid: start using libblkid directly instead
Karel Zak
kzak at redhat.com
Tue Feb 14 10:53:22 UTC 2012
On Tue, Feb 14, 2012 at 08:56:12AM +0000, Richard W.M. Jones wrote:
> On Tue, Feb 14, 2012 at 03:30:26PM +0800, Wanlong Gao wrote:
> It's one of those things that might be an improvement, but it would
> have to be distinctly better than the existing approach of calling out
> to the 'blkid' binary.
>
> Is the libblkid library interface stable? Is it meant to be used by
> programs other than the blkid binary?
Yes, for example the latest udevd is linked with libblkid.
> > +#include <blkid/blkid.h>
#include <blkid.h> if you want to use pkg-config
> > static char *
> > get_blkid_tag (const char *device, const char *tag)
> > {
> > - char *out, *err;
> > - int r;
> > + int fd, rc;
> > + const char *data = NULL;
> > + blkid_probe blkprobe;
> >
> > - r = commandr (&out, &err,
> > - "blkid",
> > - /* Adding -c option kills all caching, even on RHEL 5. */
> > - "-c", "/dev/null",
> > - "-o", "value", "-s", tag, device, NULL);
> > - if (r != 0 && r != 2) {
> > - if (r >= 0)
> > - reply_with_error ("%s: %s (blkid returned %d)", device, err, r);
> > - else
> > - reply_with_error ("%s: %s", device, err);
> > - free (out);
> > - free (err);
> > + if (!device || !tag)
> > return NULL;
> > - }
> >
> > - free (err);
> > + fd = open (device, O_RDONLY);
> > + if (fd < 0)
> > + return NULL;
> >
> > - if (r == 2) { /* means UUID etc not found */
> > - free (out);
> > - out = strdup ("");
> > - if (out == NULL)
> > - reply_with_perror ("strdup");
> > - return out;
> > - }
> > + blkprobe = blkid_new_probe ();
> > + if (!blkprobe)
> > + goto done;
> > + if (blkid_probe_set_device (blkprobe, fd, 0, 0))
> > + goto done;
> > +
> > + blkid_probe_enable_superblocks(blkprobe, 1);
You can also optionally enable
blkid_probe_enable_partitions(pr, 1);
to check for collisions between raids and partition tables (for example
RAID1 could be partitioned -- then PT could be at the begin of the device
and raid superblock at the end of the device, etc.)
> > + blkid_probe_set_superblocks_flags (blkprobe, BLKID_SUBLKS_LABEL |
> > + BLKID_SUBLKS_UUID | BLKID_SUBLKS_TYPE);
> >
> > - /* Trim trailing \n if present. */
> > - size_t len = strlen (out);
> > - if (len > 0 && out[len-1] == '\n')
> > - out[len-1] = '\0';
> > + rc = blkid_do_safeprobe (blkprobe);
> > + if (!rc)
> > + blkid_probe_lookup_value (blkprobe, tag, &data, NULL);
> >
> > - return out; /* caller frees */
> > +done:
> > + close (fd);
> > + if (blkprobe)
> > + blkid_free_probe (blkprobe);
> > + return data ? strdup ((char *) data) : NULL;
after blkid_free_probe() the "data" are deallocated, must be:
done:
close (fd);
if (data)
data = strdup ((char *) data);
blkid_free_probe (blkprobe);
return data;
Note that if-before-free is unnecessary for blkid_free_probe.
Karel
--
Karel Zak <kzak at redhat.com>
http://karelzak.blogspot.com
More information about the Libguestfs
mailing list