[libvirt] [PATCH 10/11] util: Add a util to guess the scsi host name with specified "parent"
Osier Yang
jyang at redhat.com
Thu Jun 20 03:25:40 UTC 2013
On 20/06/13 02:53, John Ferlan wrote:
> On 06/07/2013 01:03 PM, Osier Yang wrote:
>> Not really guessing, it returns host name of the scsi host which has
>> smallest unique_id.
>> ---
>> src/libvirt_private.syms | 1 +
>> src/util/virutil.c | 122 +++++++++++++++++++++++++++++++++++++++++++++++
>> src/util/virutil.h | 4 ++
>> tests/utiltest.c | 27 +++++++++++
>> 4 files changed, 154 insertions(+)
>>
>> diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
>> index 27fb0b5..ec85079 100644
>> --- a/src/libvirt_private.syms
>> +++ b/src/libvirt_private.syms
>> @@ -1948,6 +1948,7 @@ virGetUserDirectory;
>> virGetUserID;
>> virGetUserName;
>> virGetUserRuntimeDirectory;
>> +virGuessStableScsiHostName;
>> virHexToBin;
>> virIndexToDiskName;
>> virIsCapableFCHost;
>> diff --git a/src/util/virutil.c b/src/util/virutil.c
>> index a80574f..7f36e27 100644
>> --- a/src/util/virutil.c
>> +++ b/src/util/virutil.c
>> @@ -2256,6 +2256,120 @@ cleanup:
>> }
>> return ret;
>> }
>> +
>> +static int
>> +virGuessStableScsiHostNameCallback(const char *fpath,
>> + void *opaque)
>> +{
>> + const char *filename = opaque;
>> + char *p = NULL;
>> +
>> + p = strrchr(fpath, '/');
>> + p++;
>> +
>> + if (STREQ(p, filename))
>> + return 0;
>> + return -1;
>> +}
>> +
>> +/**
>> + * virGuessStableScsiHostName:
>> + * @sysfs_prefix: The directory path where starts to traverse, defaults
>> + * to SYSFS_BUS_PCI_DEVICES.
>> + * @addr: The parent's PCI address
>> + *
>> + * Returns the host name (e.g. host10) of the scsi host whose parent
>> + * has address @addr, and "unique_id" has the smallest value on success.
>> + * Or NULL on failure.
> It is up to the caller to free the memory returned.
Yes, will add
>
>> + */
>> +char *
>> +virGuessStableScsiHostName(const char *sysfs_prefix,
>> + const char *address)
>> +{
>> + const char *prefix = sysfs_prefix ? sysfs_prefix : SYSFS_BUS_PCI_DEVICES;
>> + unsigned int flags = 0;
>> + char **paths = NULL;
>> + int npaths = 0;
>> + char *smallest_path = NULL;
>> + unsigned int smallest;
>> + char *dir = NULL;
>> + char *buf = NULL;
>> + char *p1 = NULL;
>> + char *p2 = NULL;
>> + char *ret = NULL;
>> + int i;
>> +
>> + const char *filename = "unique_id";
>> +
>> + if (virAsprintf(&dir, "%s/%s", prefix, address) < 0) {
>> + virReportOOMError();
>> + return NULL;
>> + }
>> +
>> + flags |= (VIR_TRAVERSE_DIRECTORY_IGNORE_HIDDEN_FILES |
>> + VIR_TRAVERSE_DIRECTORY_FALL_THROUGH);
>> +
>> + if ((npaths = virTraverseDirectory(dir, 4, flags,
>> + virGuessStableScsiHostNameCallback,
>> + NULL, (void *)filename, &paths)) < 0)
>> + goto cleanup;
>> +
> From here...
>
>> + smallest_path = paths[0];
>> + if (virFileReadAll(paths[0], 1024, &buf) < 0)
>> + goto cleanup;
>> +
>> + if ((p1 = strchr(buf, '\n')))
>> + *p1 = '\0';
>> +
>> + if (virStrToLong_ui(buf, NULL, 10, &smallest) < 0)
>> + goto cleanup;
>> +
>> + VIR_FREE(buf);
>> + buf = NULL;
> ...to here isn't necessary... and if you keep it, then the loop below
> goes from 1 to npaths since 0 is already covered...
Hm, stupid mistake... Thanks.
Osier
More information about the libvir-list
mailing list