qemu: Delete thread-context objects at domain startup

While technically thread-context objects can be reused, we only
use them (well, will use them) to pin memory allocation threads.
Therefore, once we connect to QEMU monitor, all memory (with
prealloc=yes) was allocated and thus these objects are no longer
needed and can be removed. For on demand allocation the TC object
is left behind.

Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
This commit is contained in:
Michal Privoznik 2022-11-04 13:52:43 +01:00
parent b03386d148
commit ba92b86b4f
5 changed files with 60 additions and 0 deletions

View File

@ -3613,6 +3613,7 @@ qemuBuildThreadContextProps(virJSONValue **tcProps,
g_autoptr(virJSONValue) nodemaskCopy = NULL;
g_autofree char *tcAlias = NULL;
const char *memalias = NULL;
bool prealloc = false;
*tcProps = NULL;
@ -3645,6 +3646,12 @@ qemuBuildThreadContextProps(virJSONValue **tcProps,
NULL) < 0)
return -1;
if (virJSONValueObjectGetBoolean(*memProps, "prealloc", &prealloc) >= 0 &&
prealloc) {
priv->threadContextAliases = g_slist_prepend(priv->threadContextAliases,
g_steal_pointer(&tcAlias));
}
*tcProps = g_steal_pointer(&props);
return 0;
}

View File

@ -1811,6 +1811,8 @@ qemuDomainObjPrivateDataClear(qemuDomainObjPrivate *priv)
priv->preMigrationMemlock = 0;
virHashRemoveAll(priv->statsSchema);
g_slist_free_full(g_steal_pointer(&priv->threadContextAliases), g_free);
}

View File

@ -251,6 +251,8 @@ struct _qemuDomainObjPrivate {
* briefly when starting a guest. Don't save/parse into XML. */
pid_t schedCoreChildPID;
pid_t schedCoreChildFD;
GSList *threadContextAliases; /* List of IDs of thread-context objects */
};
#define QEMU_DOMAIN_PRIVATE(vm) \

View File

@ -7500,6 +7500,50 @@ qemuProcessSetupLifecycleActions(virDomainObj *vm,
}
int
qemuProcessDeleteThreadContext(virDomainObj *vm)
{
qemuDomainObjPrivate *priv = vm->privateData;
GSList *next = priv->threadContextAliases;
int ret = -1;
if (!next)
return 0;
for (; next; next = next->next) {
if (qemuMonitorDelObject(priv->mon, next->data, true) < 0)
goto cleanup;
}
ret = 0;
cleanup:
g_slist_free_full(g_steal_pointer(&priv->threadContextAliases), g_free);
return ret;
}
static int
qemuProcessDeleteThreadContextHelper(virDomainObj *vm,
virDomainAsyncJob asyncJob)
{
qemuDomainObjPrivate *priv = vm->privateData;
int ret = -1;
if (!priv->threadContextAliases)
return 0;
VIR_DEBUG("Deleting thread context objects");
if (qemuDomainObjEnterMonitorAsync(vm, asyncJob) < 0)
return -1;
ret = qemuProcessDeleteThreadContext(vm);
qemuDomainObjExitMonitor(vm);
return ret;
}
/**
* qemuProcessLaunch:
*
@ -7860,6 +7904,9 @@ qemuProcessLaunch(virConnectPtr conn,
if (qemuProcessSetupLifecycleActions(vm, asyncJob) < 0)
goto cleanup;
if (qemuProcessDeleteThreadContextHelper(vm, asyncJob) < 0)
goto cleanup;
ret = 0;
cleanup:

View File

@ -123,6 +123,8 @@ int qemuProcessPrepareHost(virQEMUDriver *driver,
virDomainObj *vm,
unsigned int flags);
int qemuProcessDeleteThreadContext(virDomainObj *vm);
int qemuProcessLaunch(virConnectPtr conn,
virQEMUDriver *driver,
virDomainObj *vm,