mirror of https://gitee.com/openkylin/libvirt.git
util: hash: Use virHashForEachSafe in places which might delete the element
Convert all calls to virHashForEach where it's not obvious that the callback is _not_ deleting the current element from the hash to virHashForEachSafe which will be deemed safe to do such operation. Now that no iterator used with virHashForEach deletes current element we can document that virHashForEach must not touch the hash table in any way. Signed-off-by: Peter Krempa <pkrempa@redhat.com> Reviewed-by: Daniel Henrique Barboza <danielhb413@gmail.com> Reviewed-by: Matt Coleman <matt@datto.com>
This commit is contained in:
parent
80f3af5fd8
commit
247460ab41
|
@ -299,7 +299,7 @@ void virChrdevFree(virChrdevsPtr devs)
|
|||
return;
|
||||
|
||||
virMutexLock(&devs->lock);
|
||||
virHashForEach(devs->hash, virChrdevFreeClearCallbacks, NULL);
|
||||
virHashForEachSafe(devs->hash, virChrdevFreeClearCallbacks, NULL);
|
||||
virHashFree(devs->hash);
|
||||
virMutexUnlock(&devs->lock);
|
||||
virMutexDestroy(&devs->lock);
|
||||
|
|
|
@ -475,7 +475,7 @@ virDomainMomentForEach(virDomainMomentObjListPtr moments,
|
|||
virHashIterator iter,
|
||||
void *data)
|
||||
{
|
||||
return virHashForEach(moments->objs, iter, data);
|
||||
return virHashForEachSafe(moments->objs, iter, data);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -837,7 +837,7 @@ virDomainObjListForEach(virDomainObjListPtr doms,
|
|||
virObjectRWLockWrite(doms);
|
||||
else
|
||||
virObjectRWLockRead(doms);
|
||||
virHashForEach(doms->objs, virDomainObjListHelper, &data);
|
||||
virHashForEachSafe(doms->objs, virDomainObjListHelper, &data);
|
||||
virObjectRWUnlock(doms);
|
||||
return data.ret;
|
||||
}
|
||||
|
|
|
@ -1468,7 +1468,7 @@ virNetworkObjListForEach(virNetworkObjListPtr nets,
|
|||
struct virNetworkObjListForEachHelperData data = {
|
||||
.callback = callback, .opaque = opaque, .ret = 0};
|
||||
virObjectRWLockRead(nets);
|
||||
virHashForEach(nets->objs, virNetworkObjListForEachHelper, &data);
|
||||
virHashForEachSafe(nets->objs, virNetworkObjListForEachHelper, &data);
|
||||
virObjectRWUnlock(nets);
|
||||
return data.ret;
|
||||
}
|
||||
|
@ -1841,7 +1841,7 @@ virNetworkObjPortForEach(virNetworkObjPtr obj,
|
|||
void *opaque)
|
||||
{
|
||||
virNetworkObjPortListForEachData data = { iter, opaque, false };
|
||||
virHashForEach(obj->ports, virNetworkObjPortForEachCallback, &data);
|
||||
virHashForEachSafe(obj->ports, virNetworkObjPortForEachCallback, &data);
|
||||
if (data.err)
|
||||
return -1;
|
||||
return 0;
|
||||
|
|
|
@ -364,7 +364,7 @@ virNWFilterBindingObjListForEach(virNWFilterBindingObjListPtr bindings,
|
|||
callback, opaque, 0,
|
||||
};
|
||||
virObjectRWLockRead(bindings);
|
||||
virHashForEach(bindings->objs, virNWFilterBindingObjListHelper, &data);
|
||||
virHashForEachSafe(bindings->objs, virNWFilterBindingObjListHelper, &data);
|
||||
virObjectRWUnlock(bindings);
|
||||
return data.ret;
|
||||
}
|
||||
|
|
|
@ -465,7 +465,7 @@ virStoragePoolObjListForEach(virStoragePoolObjListPtr pools,
|
|||
struct _virStoragePoolObjListForEachData data = { .iter = iter,
|
||||
.opaque = opaque };
|
||||
|
||||
virHashForEach(pools->objs, virStoragePoolObjListForEachCb, &data);
|
||||
virHashForEachSafe(pools->objs, virStoragePoolObjListForEachCb, &data);
|
||||
}
|
||||
|
||||
|
||||
|
@ -753,7 +753,7 @@ virStoragePoolObjForEachVolume(virStoragePoolObjPtr obj,
|
|||
.iter = iter, .opaque = opaque };
|
||||
|
||||
virObjectRWLockRead(obj->volumes);
|
||||
virHashForEach(obj->volumes->objsKey, virStoragePoolObjForEachVolumeCb,
|
||||
virHashForEachSafe(obj->volumes->objsKey, virStoragePoolObjForEachVolumeCb,
|
||||
&data);
|
||||
virObjectRWUnlock(obj->volumes);
|
||||
return 0;
|
||||
|
|
|
@ -490,7 +490,9 @@ virHashRemoveEntry(virHashTablePtr table, const char *name)
|
|||
*
|
||||
* The elements are iterated in arbitrary order.
|
||||
*
|
||||
* virHashForEach, virHashForEachSafe allow the callback to remove the current
|
||||
* virHashForEach prohibits @iter from modifying @table
|
||||
*
|
||||
* virHashForEachSafe allows the callback to remove the current
|
||||
* element using virHashRemoveEntry but calling other virHash* functions is
|
||||
* prohibited. Note that removing the entry invalidates @key and @payload in
|
||||
* the callback.
|
||||
|
|
|
@ -218,7 +218,7 @@ testHashRemoveForEach(const void *data)
|
|||
if (!(hash = testHashInit()))
|
||||
return -1;
|
||||
|
||||
if (virHashForEach(hash, (virHashIterator) info->data, hash)) {
|
||||
if (virHashForEachSafe(hash, (virHashIterator) info->data, hash)) {
|
||||
VIR_TEST_VERBOSE("\nvirHashForEach didn't go through all entries");
|
||||
goto cleanup;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue