mirror of
https://gitlab.com/libvirt/libvirt.git
synced 2024-12-23 06:05:27 +00:00
lxc: Don't pass a local variable address randomly
So, recently I was testing the LXC driver. You know, startup some domains. But to my surprise, I was not able to start a single one: virsh # start --console test error: Reconnected to the hypervisor error: Failed to start domain test error: internal error: guest failed to start: unexpected exit status 125 So I've start digging. It turns out, that in virExec(), when I printed out the @cmd, I got strange values: *(cmd->outfdptr) was certainly not valid FD number: it has random value of several millions. This obviously made prepareStdFd(childout, STDOUT_FILENO) fail (line 611). But outfdptr is set in virCommandSetOutputFD(). The only place within LXC driver where the function is called is in virLXCProcessBuildControllerCmd(). If you take a closer look at the function it looks like this: static virCommandPtr virLXCProcessBuildControllerCmd(virLXCDriverPtr driver, .. int logfd, const char *pidfile) { ... virCommandSetOutputFD(cmd, &logfd); virCommandSetErrorFD(cmd, &logfd); ... } Yes, you guessed it. @logfd is passed into the function by value. However, in the function we try to get its address (an address of a local variable) which is no longer valid once function is finished and stack is cleaned. Therefore when cmd->outfdptr is evaluated at any point after this function, we may get a random number, depending on what's currently on the stack. Of course, this may work sometimes too - it depends on the compiler how it arranges the code, when the stack is wiped out. In order to fix this, lets pass a pointer to @logfd instead of figuring out (wrong) its value in a function. The bug was introduced ine1de5521
. Signed-off-by: Michal Privoznik <mprivozn@redhat.com> (cherry picked from commit302146b16d
)
This commit is contained in:
parent
030e966499
commit
1f15a5d4b2
@ -749,7 +749,7 @@ virLXCProcessBuildControllerCmd(virLXCDriverPtr driver,
|
||||
int *files,
|
||||
size_t nfiles,
|
||||
int handshakefd,
|
||||
int logfd,
|
||||
int * const logfd,
|
||||
const char *pidfile)
|
||||
{
|
||||
size_t i;
|
||||
@ -819,8 +819,8 @@ virLXCProcessBuildControllerCmd(virLXCDriverPtr driver,
|
||||
virCommandPassFD(cmd, handshakefd, 0);
|
||||
virCommandDaemonize(cmd);
|
||||
virCommandSetPidFile(cmd, pidfile);
|
||||
virCommandSetOutputFD(cmd, &logfd);
|
||||
virCommandSetErrorFD(cmd, &logfd);
|
||||
virCommandSetOutputFD(cmd, logfd);
|
||||
virCommandSetErrorFD(cmd, logfd);
|
||||
/* So we can pause before exec'ing the controller to
|
||||
* write the live domain status XML with the PID */
|
||||
virCommandRequireHandshake(cmd);
|
||||
@ -1207,7 +1207,7 @@ int virLXCProcessStart(virConnectPtr conn,
|
||||
ttyFDs, nttyFDs,
|
||||
files, nfiles,
|
||||
handshakefds[1],
|
||||
logfd,
|
||||
&logfd,
|
||||
pidfile)))
|
||||
goto cleanup;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user