libblkid: make probing data structures more dynamic

* replace static probing result array with list
* use allocated buffers for probing result variables

[kzak@redhat.com: - rename some functions
                  - clean up \0 terminator usage in variables
                  - remove never used code to convert UUID to lower-case
                  - remove possible memory leaks on errors]

Signed-off-by: Ondrej Oprala <ooprala@redhat.com>
Signed-off-by: Karel Zak <kzak@redhat.com>
This commit is contained in:
Ondrej Oprala 2015-02-03 16:30:15 +01:00 committed by Karel Zak
parent 85589c4c49
commit 6c4a7811f8
5 changed files with 275 additions and 192 deletions

View File

@ -118,24 +118,14 @@ struct blkid_chaindrv {
/*
* Low-level probe result
*/
#define BLKID_PROBVAL_BUFSIZ 128
#define BLKID_NVALS_SUBLKS 18
#define BLKID_NVALS_TOPLGY 5
#define BLKID_NVALS_PARTS 13
/* Max number of all values in probing result */
#define BLKID_NVALS (BLKID_NVALS_SUBLKS + \
BLKID_NVALS_TOPLGY + \
BLKID_NVALS_PARTS)
struct blkid_prval
{
const char *name; /* value name */
unsigned char data[BLKID_PROBVAL_BUFSIZ]; /* value data */
size_t len; /* length of value data */
const char *name; /* value name */
unsigned char *data; /* value data */
size_t len; /* length of value data */
struct blkid_chain *chain; /* owner */
struct list_head prvals; /* list of results */
};
/*
@ -208,8 +198,7 @@ struct blkid_struct_probe
struct blkid_chain chains[BLKID_NCHAINS]; /* array of chains */
struct blkid_chain *cur_chain; /* current chain */
struct blkid_prval vals[BLKID_NVALS]; /* results */
int nvals; /* number of assigned vals */
struct list_head vals; /* results */
struct blkid_struct_probe *parent; /* for clones */
struct blkid_struct_probe *disk_probe; /* whole-disk probing */
@ -432,8 +421,7 @@ extern void blkid_probe_chain_reset_vals(blkid_probe pr, struct blkid_chain *chn
__attribute__((nonnull));
extern int blkid_probe_chain_copy_vals(blkid_probe pr,
struct blkid_chain *chn,
struct blkid_prval *vals,
int nvals)
struct list_head *vals)
__attribute__((nonnull));
extern struct blkid_prval *blkid_probe_assign_value(blkid_probe pr,
@ -441,17 +429,19 @@ extern struct blkid_prval *blkid_probe_assign_value(blkid_probe pr,
__attribute__((nonnull))
__attribute__((warn_unused_result));
extern int blkid_probe_reset_last_value(blkid_probe pr)
__attribute__((nonnull));
extern void blkid_probe_free_val(struct blkid_prval *v);
extern void blkid_probe_append_vals(blkid_probe pr,
struct blkid_prval *vals,
int nvals)
struct list_head *vals)
__attribute__((nonnull));
extern struct blkid_chain *blkid_probe_get_chain(blkid_probe pr)
__attribute__((nonnull))
__attribute__((warn_unused_result));
extern struct blkid_prval *blkid_probe_last_value(blkid_probe pr);
extern struct blkid_prval *__blkid_probe_get_value(blkid_probe pr, int num)
__attribute__((nonnull))
__attribute__((warn_unused_result));
@ -475,9 +465,14 @@ extern void *blkid_probe_get_binary_data(blkid_probe pr, struct blkid_chain *chn
__attribute__((nonnull))
__attribute__((warn_unused_result));
extern struct blkid_prval *blkid_probe_new_val(void)
__attribute__((warn_unused_result));
extern int blkid_probe_set_value(blkid_probe pr, const char *name,
unsigned char *data, size_t len)
__attribute__((nonnull));
extern int blkid_probe_value_set_data(struct blkid_prval *v,
unsigned char *data, size_t len)
__attribute__((nonnull));
extern int blkid_probe_vsprintf_value(blkid_probe pr, const char *name,
const char *fmt, va_list ap)
@ -535,6 +530,7 @@ extern void blkid_probe_use_wiper(blkid_probe pr, blkid_loff_t off, blkid_loff_t
(blkid_bmp_nwords(max_items) * sizeof(unsigned long))
/* encode.c */
extern unsigned char *blkid_encode_alloc(size_t count, size_t *reslen);
extern size_t blkid_encode_to_utf8(int enc, unsigned char *dest, size_t len,
const unsigned char *src, size_t count)
__attribute__((nonnull));

View File

@ -268,6 +268,12 @@ size_t blkid_encode_to_utf8(int enc, unsigned char *dest, size_t len,
return j;
}
unsigned char *blkid_encode_alloc(size_t count, size_t *reslen)
{
*reslen = (count * 3) + 1;
return calloc(1, *reslen);
}
/**
* blkid_encode_string:
* @str: input string to be encoded

View File

@ -1098,11 +1098,18 @@ int blkid_partitions_set_ptuuid(blkid_probe pr, unsigned char *uuid)
return 0;
v = blkid_probe_assign_value(pr, "PTUUID");
if (!v)
return -ENOMEM;
blkid_unparse_uuid(uuid, (char *) v->data, sizeof(v->data));
v->len = 37;
v->data = calloc(1, v->len);
if (v->data) {
blkid_unparse_uuid(uuid, (char *) v->data, v->len);
return 0;
}
return 0;
blkid_probe_free_val(v);
return -ENOMEM;
}
/* set PTUUID variable for non-binary API for tables where
@ -1110,27 +1117,14 @@ int blkid_partitions_set_ptuuid(blkid_probe pr, unsigned char *uuid)
int blkid_partitions_strcpy_ptuuid(blkid_probe pr, char *str)
{
struct blkid_chain *chn = blkid_probe_get_chain(pr);
struct blkid_prval *v;
size_t len;
if (chn->binary || !str || !*str)
return 0;
len = strlen((char *) str);
if (len > BLKID_PROBVAL_BUFSIZ)
len = BLKID_PROBVAL_BUFSIZ;
if (!blkid_probe_set_value(pr, "PTUUID", (unsigned char *) str, strlen(str) + 1))
return -ENOMEM;
v = blkid_probe_assign_value(pr, "PTUUID");
if (v) {
if (len == BLKID_PROBVAL_BUFSIZ)
len--; /* make a space for \0 */
memcpy((char *) v->data, str, len);
v->data[len] = '\0';
v->len = len + 1;
return 0;
}
return -1;
return 0;
}
/**

View File

@ -113,6 +113,7 @@
#include "all-io.h"
#include "sysfs.h"
#include "strutils.h"
#include "list.h"
/* chains */
extern const struct blkid_chaindrv superblocks_drv;
@ -128,6 +129,7 @@ static const struct blkid_chaindrv *chains_drvs[] = {
[BLKID_CHAIN_PARTS] = &partitions_drv
};
static struct blkid_prval *blkid_probe_new_value(void);
static void blkid_probe_reset_vals(blkid_probe pr);
static void blkid_probe_reset_buffer(blkid_probe pr);
@ -155,6 +157,7 @@ blkid_probe blkid_new_probe(void)
pr->chains[i].enabled = chains_drvs[i]->dflt_enabled;
}
INIT_LIST_HEAD(&pr->buffers);
INIT_LIST_HEAD(&pr->vals);
return pr;
}
@ -265,29 +268,34 @@ void blkid_free_probe(blkid_probe pr)
free(pr);
}
void blkid_probe_free_val(struct blkid_prval *v)
{
if (!v)
return;
list_del(&v->prvals);
free(v->data);
free(v);
}
/*
* Removes chain values from probing result.
*/
void blkid_probe_chain_reset_vals(blkid_probe pr, struct blkid_chain *chn)
{
int nvals = pr->nvals;
int i, x;
for (x = 0, i = 0; i < pr->nvals; i++) {
struct blkid_prval *v = &pr->vals[i];
struct list_head *p, *pnext;
if (v->chain != chn && x == i) {
x++;
continue;
}
if (v->chain == chn) {
--nvals;
continue;
}
memcpy(&pr->vals[x++], v, sizeof(struct blkid_prval));
if (!pr || list_empty(&pr->vals))
return;
list_for_each_safe(p, pnext, &pr->vals) {
struct blkid_prval *v = list_entry(p,
struct blkid_prval, prvals);
if (v->chain == chn)
blkid_probe_free_val(v);
}
pr->nvals = nvals;
}
static void blkid_probe_chain_reset_position(struct blkid_chain *chn)
@ -296,42 +304,56 @@ static void blkid_probe_chain_reset_position(struct blkid_chain *chn)
chn->idx = -1;
}
static struct blkid_prval *blkid_probe_deep_copy_val(struct blkid_prval *dest,
struct blkid_prval *src)
{
memcpy(dest, src, sizeof(struct blkid_prval));
dest->data = malloc(src->len);
if (!dest->data)
return NULL;
memcpy(dest->data, src->data, src->len);
INIT_LIST_HEAD(&dest->prvals);
return dest;
}
/*
* Copies chain values from probing result to @vals, the max size of @vals is
* @nvals and returns real number of values.
* Copies chain values from probing result to @vals.
*/
int blkid_probe_chain_copy_vals(blkid_probe pr, struct blkid_chain *chn,
struct blkid_prval *vals, int nvals)
struct list_head *vals)
{
int i, x;
struct list_head *p;
struct blkid_prval *new_v, *v;
for (x = 0, i = 0; i < pr->nvals && x < nvals; i++) {
struct blkid_prval *v = &pr->vals[i];
list_for_each(p, &pr->vals) {
v = list_entry(p, struct blkid_prval, prvals);
new_v = blkid_probe_new_value();
if (!new_v)
break;
if (v->chain != chn)
continue;
memcpy(&vals[x++], v, sizeof(struct blkid_prval));
if (!blkid_probe_deep_copy_val(new_v, v))
break;
list_add_tail(&new_v->prvals, vals);
}
return x;
return 0;
}
/*
* Appends values from @vals to the probing result
*/
void blkid_probe_append_vals(blkid_probe pr, struct blkid_prval *vals, int nvals)
void blkid_probe_append_vals(blkid_probe pr, struct list_head *vals)
{
int i = 0;
while (i < nvals && pr->nvals < BLKID_NVALS) {
memcpy(&pr->vals[pr->nvals++], &vals[i++],
sizeof(struct blkid_prval));
}
}
static void blkid_probe_reset_vals(blkid_probe pr)
{
memset(pr->vals, 0, sizeof(pr->vals));
pr->nvals = 0;
list_splice(vals, &pr->vals);
}
struct blkid_chain *blkid_probe_get_chain(blkid_probe pr)
@ -615,7 +637,6 @@ unsigned char *blkid_probe_get_buffer(blkid_probe pr,
return off ? bf->data + (off - bf->off) : bf->data;
}
static void blkid_probe_reset_buffer(blkid_probe pr)
{
uint64_t read_ct = 0, len_ct = 0;
@ -641,6 +662,22 @@ static void blkid_probe_reset_buffer(blkid_probe pr)
INIT_LIST_HEAD(&pr->buffers);
}
static void blkid_probe_reset_vals(blkid_probe pr)
{
if (!pr || list_empty(&pr->vals))
return;
DBG(LOWPROBE, ul_debug("resetting results pr=%p", pr));
while (!list_empty(&pr->vals)) {
struct blkid_prval *v = list_entry(pr->vals.next,
struct blkid_prval, prvals);
blkid_probe_free_val(v);
}
INIT_LIST_HEAD(&pr->vals);
}
/*
* Small devices need a special care.
*/
@ -1273,37 +1310,47 @@ struct blkid_prval *blkid_probe_assign_value(
blkid_probe pr, const char *name)
{
struct blkid_prval *v;
if (!name)
return NULL;
if (pr->nvals >= BLKID_NVALS)
v = blkid_probe_new_value();
if (!v)
return NULL;
v = &pr->vals[pr->nvals];
v->name = name;
v->chain = pr->cur_chain;
pr->nvals++;
list_add_tail(&v->prvals, &pr->vals);
DBG(LOWPROBE, ul_debug("assigning %s [%s]", name, v->chain->driver->name));
return v;
}
int blkid_probe_reset_last_value(blkid_probe pr)
static struct blkid_prval *blkid_probe_new_value(void)
{
struct blkid_prval *v;
struct blkid_prval *v = calloc(1, sizeof(struct blkid_prval));
if (!v)
return NULL;
if (pr == NULL || pr->nvals == 0)
return -1;
INIT_LIST_HEAD(&v->prvals);
v = &pr->vals[pr->nvals - 1];
return v;
}
DBG(LOWPROBE, ul_debug("un-assigning %s [%s]", v->name, v->chain->driver->name));
memset(v, 0, sizeof(struct blkid_prval));
pr->nvals--;
/* Note that value data is always terminated by zero to keep things robust,
* this extra zero is not count to the value lenght. It's caller responsibility
* to set proper value lenght (for strings we count terminator to the lenght,
* for binary data it's without terminator).
*/
int blkid_probe_value_set_data(struct blkid_prval *v,
unsigned char *data, size_t len)
{
v->data = calloc(1, len + 1); /* always terminate by \0 */
if (!v->data)
return -ENOMEM;
memcpy(v->data, data, len);
v->len = len;
return 0;
}
int blkid_probe_set_value(blkid_probe pr, const char *name,
@ -1311,16 +1358,11 @@ int blkid_probe_set_value(blkid_probe pr, const char *name,
{
struct blkid_prval *v;
if (len > BLKID_PROBVAL_BUFSIZ)
len = BLKID_PROBVAL_BUFSIZ;
v = blkid_probe_assign_value(pr, name);
if (!v)
return -1;
memcpy(v->data, data, len);
v->len = len;
return 0;
return blkid_probe_value_set_data(v, data, len);
}
int blkid_probe_vsprintf_value(blkid_probe pr, const char *name,
@ -1331,13 +1373,13 @@ int blkid_probe_vsprintf_value(blkid_probe pr, const char *name,
v = blkid_probe_assign_value(pr, name);
if (!v)
return -1;
return -ENOMEM;
len = vsnprintf((char *) v->data, sizeof(v->data), fmt, ap);
len = vasprintf((char **) &v->data, fmt, ap);
if (len <= 0 || (size_t) len >= sizeof(v->data)) {
blkid_probe_reset_last_value(pr);
return -1;
if (len <= 0) {
blkid_probe_free_val(v);
return len == 0 ? -EINVAL : -ENOMEM;
}
v->len = len + 1;
return 0;
@ -1586,9 +1628,14 @@ blkid_loff_t blkid_probe_get_sectors(blkid_probe pr)
*/
int blkid_probe_numof_values(blkid_probe pr)
{
int i = 0;
struct list_head *p;
if (!pr)
return -1;
return pr->nvals;
list_for_each(p, &pr->vals)
++i;
return i;
}
/**
@ -1662,23 +1709,41 @@ int blkid_probe_has_value(blkid_probe pr, const char *name)
return 0;
}
struct blkid_prval *__blkid_probe_get_value(blkid_probe pr, int num)
struct blkid_prval *blkid_probe_last_value(blkid_probe pr)
{
if (!pr || num < 0 || num >= pr->nvals)
if (!pr || list_empty(&pr->vals))
return NULL;
return &pr->vals[num];
return list_last_entry(&pr->vals, struct blkid_prval, prvals);
}
struct blkid_prval *__blkid_probe_get_value(blkid_probe pr, int num)
{
int i = 0;
struct list_head *p;
if (!pr || num < 0)
return NULL;
list_for_each(p, &pr->vals) {
if (i++ != num)
continue;
return list_entry(p, struct blkid_prval, prvals);
}
return NULL;
}
struct blkid_prval *__blkid_probe_lookup_value(blkid_probe pr, const char *name)
{
int i;
struct list_head *p;
if (!pr || !pr->nvals || !name)
if (!pr || list_empty(&pr->vals) || !name)
return NULL;
for (i = 0; i < pr->nvals; i++) {
struct blkid_prval *v = &pr->vals[i];
list_for_each(p, &pr->vals) {
struct blkid_prval *v = list_entry(p, struct blkid_prval,
prvals);
if (v->name && strcmp(name, v->name) == 0) {
DBG(LOWPROBE, ul_debug("returning %s value", v->name));

View File

@ -451,13 +451,14 @@ static int superblocks_probe(blkid_probe pr, struct blkid_chain *chn)
*/
static int superblocks_safeprobe(blkid_probe pr, struct blkid_chain *chn)
{
struct blkid_prval vals[BLKID_NVALS_SUBLKS];
int nvals = BLKID_NVALS_SUBLKS;
struct list_head vals;
int idx = -1;
int count = 0;
int intol = 0;
int rc;
INIT_LIST_HEAD(&vals);
if (pr->flags & BLKID_FL_NOSCAN_DEV)
return BLKID_PROBE_NONE;
@ -478,7 +479,7 @@ static int superblocks_safeprobe(blkid_probe pr, struct blkid_chain *chn)
if (count == 1) {
/* save the first result */
nvals = blkid_probe_chain_copy_vals(pr, chn, vals, nvals);
blkid_probe_chain_copy_vals(pr, chn, &vals);
idx = chn->idx;
}
}
@ -498,7 +499,7 @@ static int superblocks_safeprobe(blkid_probe pr, struct blkid_chain *chn)
if (idx != -1) {
/* restore the first result */
blkid_probe_chain_reset_vals(pr, chn);
blkid_probe_append_vals(pr, vals, nvals);
blkid_probe_append_vals(pr, &vals);
chn->idx = idx;
}
@ -566,28 +567,28 @@ int blkid_probe_set_id_label(blkid_probe pr, const char *name,
{
struct blkid_chain *chn = blkid_probe_get_chain(pr);
struct blkid_prval *v;
int rc = 0;
if (!(chn->flags & BLKID_SUBLKS_LABEL))
return 0;
v = blkid_probe_assign_value(pr, name);
if (!v)
return -1;
return -ENOMEM;
if (len >= BLKID_PROBVAL_BUFSIZ)
len = BLKID_PROBVAL_BUFSIZ - 1; /* make a space for \0 */
rc = blkid_probe_value_set_data(v, data, len);
if (!rc) {
/* remove white spaces */
v->len = blkid_rtrim_whitespace(v->data) + 1;
if (v->len > 1)
v->len = blkid_ltrim_whitespace(v->data) + 1;
if (v->len > 1)
return 0;
}
memcpy(v->data, data, len);
v->data[len] = '\0';
blkid_probe_free_val(v);
return rc;
/* remove white spaces */
v->len = blkid_rtrim_whitespace(v->data) + 1;
if (v->len > 1)
v->len = blkid_ltrim_whitespace(v->data) + 1;
if (v->len <= 1)
blkid_probe_reset_last_value(pr); /* ignore empty */
return 0;
}
int blkid_probe_set_utf8_id_label(blkid_probe pr, const char *name,
@ -595,50 +596,58 @@ int blkid_probe_set_utf8_id_label(blkid_probe pr, const char *name,
{
struct blkid_chain *chn = blkid_probe_get_chain(pr);
struct blkid_prval *v;
int rc = 0;
if (!(chn->flags & BLKID_SUBLKS_LABEL))
return 0;
v = blkid_probe_assign_value(pr, name);
if (!v)
return -1;
return -ENOMEM;
blkid_encode_to_utf8(enc, v->data, sizeof(v->data), data, len);
v->len = blkid_rtrim_whitespace(v->data) + 1;
if (v->len > 1)
v->len = blkid_ltrim_whitespace(v->data) + 1;
v->data = blkid_encode_alloc(len, &v->len);
if (!v->data)
rc = -ENOMEM;
if (v->len <= 1)
blkid_probe_reset_last_value(pr);
return 0;
if (!rc) {
blkid_encode_to_utf8(enc, v->data, v->len, data, len);
v->len = blkid_rtrim_whitespace(v->data) + 1;
if (v->len > 1)
v->len = blkid_ltrim_whitespace(v->data) + 1;
if (v->len > 1)
return 0;
}
blkid_probe_free_val(v);
return rc;
}
int blkid_probe_set_label(blkid_probe pr, unsigned char *label, size_t len)
{
struct blkid_chain *chn = blkid_probe_get_chain(pr);
struct blkid_prval *v;
if (len > BLKID_PROBVAL_BUFSIZ)
len = BLKID_PROBVAL_BUFSIZ;
int rc = 0;
if ((chn->flags & BLKID_SUBLKS_LABELRAW) &&
blkid_probe_set_value(pr, "LABEL_RAW", label, len) < 0)
return -1;
(rc = blkid_probe_set_value(pr, "LABEL_RAW", label, len)) < 0)
return rc;
if (!(chn->flags & BLKID_SUBLKS_LABEL))
return 0;
v = blkid_probe_assign_value(pr, "LABEL");
if (!v)
return -1;
return -ENOMEM;
if (len == BLKID_PROBVAL_BUFSIZ)
len--; /* make a space for \0 */
rc = blkid_probe_value_set_data(v, label, len);
if (!rc) {
v->len = blkid_rtrim_whitespace(v->data) + 1;
if (v->len > 1)
return 0;
}
memcpy(v->data, label, len);
v->data[len] = '\0';
v->len = blkid_rtrim_whitespace(v->data) + 1;
if (v->len == 1)
blkid_probe_reset_last_value(pr);
return 0;
blkid_probe_free_val(v);
return rc;
}
int blkid_probe_set_utf8label(blkid_probe pr, unsigned char *label,
@ -646,39 +655,47 @@ int blkid_probe_set_utf8label(blkid_probe pr, unsigned char *label,
{
struct blkid_chain *chn = blkid_probe_get_chain(pr);
struct blkid_prval *v;
int rc = 0;
if ((chn->flags & BLKID_SUBLKS_LABELRAW) &&
blkid_probe_set_value(pr, "LABEL_RAW", label, len) < 0)
return -1;
(rc = blkid_probe_set_value(pr, "LABEL_RAW", label, len)) < 0)
return rc;
if (!(chn->flags & BLKID_SUBLKS_LABEL))
return 0;
v = blkid_probe_assign_value(pr, "LABEL");
if (!v)
return -1;
return -ENOMEM;
blkid_encode_to_utf8(enc, v->data, sizeof(v->data), label, len);
v->len = blkid_rtrim_whitespace(v->data) + 1;
if (v->len == 1)
blkid_probe_reset_last_value(pr);
return 0;
v->data = blkid_encode_alloc(len, &v->len);
if (!v->data)
rc = -ENOMEM;
if (!rc) {
blkid_encode_to_utf8(enc, v->data, v->len, label, len);
v->len = blkid_rtrim_whitespace(v->data) + 1;
if (v->len > 1)
return 0;
}
blkid_probe_free_val(v);
return rc;
}
int blkid_probe_sprintf_uuid(blkid_probe pr, unsigned char *uuid,
size_t len, const char *fmt, ...)
{
struct blkid_chain *chn = blkid_probe_get_chain(pr);
int rc = -1;
va_list ap;
if (len > BLKID_PROBVAL_BUFSIZ)
len = BLKID_PROBVAL_BUFSIZ;
int rc = 0;
if (blkid_uuid_is_empty(uuid, len))
return 0;
if ((chn->flags & BLKID_SUBLKS_UUIDRAW) &&
blkid_probe_set_value(pr, "UUID_RAW", uuid, len) < 0)
return -1;
(rc = blkid_probe_set_value(pr, "UUID_RAW", uuid, len)) < 0)
return rc;
if (!(chn->flags & BLKID_SUBLKS_UUID))
return 0;
@ -686,17 +703,6 @@ int blkid_probe_sprintf_uuid(blkid_probe pr, unsigned char *uuid,
rc = blkid_probe_vsprintf_value(pr, "UUID", fmt, ap);
va_end(ap);
/* convert to lower case (..be paranoid) */
if (!rc) {
size_t i;
struct blkid_prval *v = __blkid_probe_get_value(pr,
blkid_probe_numof_values(pr));
if (v) {
for (i = 0; i < v->len; i++)
if (v->data[i] >= 'A' && v->data[i] <= 'F')
v->data[i] = (v->data[i] - 'A') + 'a';
}
}
return rc;
}
@ -705,31 +711,34 @@ int blkid_probe_strncpy_uuid(blkid_probe pr, unsigned char *str, size_t len)
{
struct blkid_chain *chn = blkid_probe_get_chain(pr);
struct blkid_prval *v;
int rc = 0;
if (str == NULL || *str == '\0')
return -1;
return -EINVAL;
if (!len)
len = strlen((char *) str);
if (len > BLKID_PROBVAL_BUFSIZ)
len = BLKID_PROBVAL_BUFSIZ;
if ((chn->flags & BLKID_SUBLKS_UUIDRAW) &&
blkid_probe_set_value(pr, "UUID_RAW", str, len) < 0)
return -1;
(rc = blkid_probe_set_value(pr, "UUID_RAW", str, len)) < 0)
return rc;
if (!(chn->flags & BLKID_SUBLKS_UUID))
return 0;
v = blkid_probe_assign_value(pr, "UUID");
if (v) {
if (len == BLKID_PROBVAL_BUFSIZ)
len--; /* make a space for \0 */
memcpy((char *) v->data, str, len);
v->data[len] = '\0';
v->len = len + 1;
return 0;
if (!v)
rc= -ENOMEM;
if (!rc)
rc = blkid_probe_value_set_data(v, str, len);
if (!rc) {
v->len = blkid_rtrim_whitespace(v->data) + 1;
if (v->len > 1)
return 0;
}
return -1;
blkid_probe_free_val(v);
return rc;
}
/* default _set_uuid function to set DCE UUIDs */
@ -737,14 +746,16 @@ int blkid_probe_set_uuid_as(blkid_probe pr, unsigned char *uuid, const char *nam
{
struct blkid_chain *chn = blkid_probe_get_chain(pr);
struct blkid_prval *v;
int rc = 0;
if (blkid_uuid_is_empty(uuid, 16))
return 0;
if (!name) {
if ((chn->flags & BLKID_SUBLKS_UUIDRAW) &&
blkid_probe_set_value(pr, "UUID_RAW", uuid, 16) < 0)
return -1;
(rc = blkid_probe_set_value(pr, "UUID_RAW", uuid, 16)) < 0)
return rc;
if (!(chn->flags & BLKID_SUBLKS_UUID))
return 0;
@ -752,10 +763,21 @@ int blkid_probe_set_uuid_as(blkid_probe pr, unsigned char *uuid, const char *nam
} else
v = blkid_probe_assign_value(pr, name);
blkid_unparse_uuid(uuid, (char *) v->data, sizeof(v->data));
v->len = 37;
if (!v)
return -ENOMEM;
return 0;
v->len = 37;
v->data = calloc(1, v->len);
if (!v->data)
rc = -ENOMEM;
if (!rc) {
blkid_unparse_uuid(uuid, (char *) v->data, v->len);
return 0;
}
blkid_probe_free_val(v);
return rc;
}
int blkid_probe_set_uuid(blkid_probe pr, unsigned char *uuid)