mirror of
https://gitlab.com/libvirt/libvirt.git
synced 2025-01-03 19:45:21 +00:00
lxc_container: Increase stack size for lxcContainerChild()
When spawning a new container (via clone()) we allocate stack for lxcContainerChild(). So far, we allocate 4 pages for the stack and this used to be enough until we started rewriting everything to glib. With glib we switched to g_strerror() which localizes errno strings and thus increases stack usage, while the previously used strerror_r() was more compact. Fortunately, the solution is easy - just increase how much stack the child can use (16 pages ought to be enough for anybody). And while at it, lets use mmap() for allocation which offer some nice features: MAP_STACK - align allocation to be suitable for stack (even though, currently ignored on Linux), MAP_GROWSDOWN - kernel guards out of bounds access from child Resolves: https://gitlab.com/libvirt/libvirt/-/issues/511 Signed-off-by: Michal Privoznik <mprivozn@redhat.com> Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
This commit is contained in:
parent
3d2f3fb72b
commit
11b767d110
@ -26,6 +26,7 @@
|
|||||||
#include <sys/ioctl.h>
|
#include <sys/ioctl.h>
|
||||||
#include <sys/mount.h>
|
#include <sys/mount.h>
|
||||||
#include <sys/stat.h>
|
#include <sys/stat.h>
|
||||||
|
#include <sys/mman.h>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <mntent.h>
|
#include <mntent.h>
|
||||||
#include <sys/reboot.h>
|
#include <sys/reboot.h>
|
||||||
@ -2132,9 +2133,10 @@ int lxcContainerStart(virDomainDef *def,
|
|||||||
{
|
{
|
||||||
pid_t pid;
|
pid_t pid;
|
||||||
int cflags;
|
int cflags;
|
||||||
int stacksize = getpagesize() * 4;
|
int stacksize = getpagesize() * 16;
|
||||||
g_autofree char *stack = NULL;
|
char *stack = NULL;
|
||||||
char *stacktop;
|
char *stacktop;
|
||||||
|
int ret = -1;
|
||||||
lxc_child_argv_t args = {
|
lxc_child_argv_t args = {
|
||||||
.config = def,
|
.config = def,
|
||||||
.securityDriver = securityDriver,
|
.securityDriver = securityDriver,
|
||||||
@ -2150,7 +2152,14 @@ int lxcContainerStart(virDomainDef *def,
|
|||||||
};
|
};
|
||||||
|
|
||||||
/* allocate a stack for the container */
|
/* allocate a stack for the container */
|
||||||
stack = g_new0(char, stacksize);
|
stack = mmap(NULL, stacksize, PROT_READ | PROT_WRITE,
|
||||||
|
MAP_PRIVATE | MAP_ANONYMOUS | MAP_GROWSDOWN | MAP_STACK,
|
||||||
|
-1, 0);
|
||||||
|
if (stack == MAP_FAILED) {
|
||||||
|
virReportSystemError(errno, "%s",
|
||||||
|
_("Unable to allocate stack"));
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
stacktop = stack + stacksize;
|
stacktop = stack + stacksize;
|
||||||
|
|
||||||
@ -2160,7 +2169,7 @@ int lxcContainerStart(virDomainDef *def,
|
|||||||
if (virProcessNamespaceAvailable(VIR_PROCESS_NAMESPACE_USER) < 0) {
|
if (virProcessNamespaceAvailable(VIR_PROCESS_NAMESPACE_USER) < 0) {
|
||||||
virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
|
virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
|
||||||
_("Kernel doesn't support user namespace"));
|
_("Kernel doesn't support user namespace"));
|
||||||
return -1;
|
goto cleanup;
|
||||||
}
|
}
|
||||||
VIR_DEBUG("Enable user namespace");
|
VIR_DEBUG("Enable user namespace");
|
||||||
cflags |= CLONE_NEWUSER;
|
cflags |= CLONE_NEWUSER;
|
||||||
@ -2175,7 +2184,7 @@ int lxcContainerStart(virDomainDef *def,
|
|||||||
virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
|
virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
|
||||||
_("Config asks for inherit net namespace "
|
_("Config asks for inherit net namespace "
|
||||||
"as well as private network interfaces"));
|
"as well as private network interfaces"));
|
||||||
return -1;
|
goto cleanup;
|
||||||
}
|
}
|
||||||
VIR_DEBUG("Inheriting a net namespace");
|
VIR_DEBUG("Inheriting a net namespace");
|
||||||
}
|
}
|
||||||
@ -2199,10 +2208,15 @@ int lxcContainerStart(virDomainDef *def,
|
|||||||
if (pid < 0) {
|
if (pid < 0) {
|
||||||
virReportSystemError(errno, "%s",
|
virReportSystemError(errno, "%s",
|
||||||
_("Failed to run clone container"));
|
_("Failed to run clone container"));
|
||||||
return -1;
|
goto cleanup;
|
||||||
}
|
}
|
||||||
|
|
||||||
return pid;
|
ret = pid;
|
||||||
|
cleanup:
|
||||||
|
if (munmap(stack, stacksize) < 0)
|
||||||
|
VIR_WARN("Unable to munmap() stack: %s", g_strerror(errno));
|
||||||
|
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int lxcContainerChown(virDomainDef *def, const char *path)
|
int lxcContainerChown(virDomainDef *def, const char *path)
|
||||||
|
Loading…
Reference in New Issue
Block a user