[libvirt] [PATCH v5 06/13] conf: Introduce address caching for PCI extensions

Yi Min Zhao zyimin at linux.ibm.com
Wed Sep 12 07:35:33 UTC 2018



在 2018/9/11 下午7:34, Andrea Bolognani 写道:
> On Tue, 2018-09-04 at 16:39 +0800, Yi Min Zhao wrote:
>> This patch provides a caching mechanism for the device address
>> extensions uid and fid on S390. For efficient sparse address allocation,
>> we introduce two hash tables for uid/fid which hold the address set
>> information per domain. Also in order to improve performance of
>> searching available value, we introduce our own callbacks for the two
>> hashtables. In this way, uid/fid is saved in hash key and hash value
>> could be any non-NULL pointer due to no operation on hash value. That is
>> also the reason why we don't introduce hash value free callback.
>>
>> Signed-off-by: Yi Min Zhao <zyimin at linux.ibm.com>
>> Reviewed-by: Boris Fiuczynski <fiuczy at linux.vnet.ibm.com>
>> Reviewed-by: Bjoern Walk <bwalk at linux.vnet.ibm.com>
>> Reviewed-by: Ján Tomko <jtomko at redhat.com>
>> ---
>>   src/conf/domain_addr.c         | 85 ++++++++++++++++++++++++++++++++++++++++++
>>   src/conf/domain_addr.h         |  9 +++++
>>   src/libvirt_private.syms       |  1 +
>>   src/qemu/qemu_domain_address.c |  7 ++++
>>   4 files changed, 102 insertions(+)
> Okay, I've spent some time actually digging into the hash table
> implementation this time around :)
>
> [...]
>> +static uint32_t
>> +virZPCIAddrCode(const void *name,
>> +                uint32_t seed)
>> +{
>> +    unsigned int value = *((unsigned int *)name);
>> +    return virHashCodeGen(&value, sizeof(value), seed);
>> +}
>> +
>> +
>> +static bool
>> +virZPCIAddrEqual(const void *namea,
>> +                 const void *nameb)
>> +{
>> +    return *((unsigned int *)namea) == *((unsigned int *)nameb);
>> +}
>> +
>> +
>> +static void *
>> +virZPCIAddrCopy(const void *name)
>> +{
>> +    unsigned int *copy;
>> +
>> +    if (VIR_ALLOC(copy) < 0)
>> +        return NULL;
>> +
>> +    *copy = *((unsigned int *)name);
>> +    return (void *)copy;
>> +}
>> +
>> +
>> +static void
>> +virZPCIAddrKeyFree(void *name)
>> +{
>> +    VIR_FREE(name);
>> +}
> This makes sense and seems to work just fine; however, you are
> allocating and releasing a bunch of small integers, which seems
> a bit wasteful.
>
> vircgroup is AFAICT avoiding all that extra memory management by
> stuffing the values straight into the pointers themselves, which
> you should also be able to do since the biggest legal ID is a
> 32-bit integer.
>
> That said, I haven't been able to get that to actually work, at
> least with a quick attempt :( Would you mind exploring that route
> and figuring out whether it's feasible at all?
I'm testing this. Actually I wanted to do so like vircgroup. I 
remembered there's
error due to the previous code logic. I will reply to you later.
>
> [...]
>> +int
>> +virDomainPCIAddressSetExtensionAlloc(virDomainPCIAddressSetPtr addrs,
>> +                                     virDomainPCIAddressExtensionFlags extFlags)
>> +{
>> +    if (extFlags & VIR_PCI_ADDRESS_EXTENSION_ZPCI) {
>> +        if (addrs->zpciIds)
>> +            return 0;
> This check doesn't look necessary.
All right.
>
> [...]
>> +typedef struct {
>> +    virHashTablePtr uids, fids;
>> +} virDomainZPCIAddressIds;
> One member per line, please.
ok
>
> [...]
>> +    /* create zpci address set for s390 domain */
>> +    if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE_ZPCI) &&
>> +        virDomainPCIAddressSetExtensionAlloc(addrs,
>> +                                             VIR_PCI_ADDRESS_EXTENSION_ZPCI)) {
>> +        goto error;
>> +    }
> You should check for
>
>    virDomainPCIAddressSetExtensionAlloc() < 0
>
> here.
>
Thanks for your comments.

-- 
Yi Min




More information about the libvir-list mailing list