#include <sys/un.h>
#include <sys/mman.h>
#include <sys/syscall.h>
+#include <sys/wait.h>
#include <stdio.h>
#include <errno.h>
#include <string.h>
{
struct supertype *c = v;
- mon_tid = syscall(SYS_gettid);
do_monitor(c);
return 0;
}
int clone_monitor(struct supertype *container)
{
static char stack[4096];
- int rv;
-
- rv = clone(run_child, stack+4096-64,
+ mon_tid = clone(run_child, stack+4096-64,
CLONE_FS|CLONE_FILES|CLONE_VM|CLONE_SIGHAND|CLONE_THREAD,
container);
mgr_tid = syscall(SYS_gettid);
-
- return rv;
+
+ return mon_tid;
}
static struct superswitch *find_metadata_methods(char *vers)
struct mdinfo *mdi, *di;
struct supertype *container;
sigset_t set;
+ struct sigaction act;
+ int pfd[2];
+ int status;
if (argc != 2) {
fprintf(stderr, "Usage: md-manage /device/name/for/container\n");
exit(1);
}
+ /* Fork, and have the child tell us when they are ready */
+ pipe(pfd);
+ switch(fork()){
+ case -1:
+ fprintf(stderr, "mdmon: failed to fork: %s\n",
+ strerror(errno));
+ exit(1);
+ case 0: /* child */
+ close(pfd[0]);
+ break;
+ default: /* parent */
+ close(pfd[1]);
+ if (read(pfd[0], &status, sizeof(status)) != sizeof(status)) {
+ wait(&status);
+ status = WEXITSTATUS(status);
+ }
+ exit(status);
+ }
/* hopefully it is a container - we'll check later */
container = malloc(sizeof(*container));
argv[1]);
exit(3);
}
- close(mdfd);
- close(mdfd);
+
+ /* Ok, this is close enough. We can say goodbye to our parent now.
+ */
+ status = 0;
+ write(pfd[1], &status, sizeof(status));
+ close(pfd[1]);
+
+ chdir("/");
+ setsid();
+ close(0);
+ open("/dev/null", O_RDWR);
+ close(1);
+ dup(0);
+#ifndef DEBUG
+ close(2);
+ dup(0);
+#endif
mlockall(MCL_FUTURE);
sigemptyset(&set);
sigaddset(&set, SIGUSR1);
sigprocmask(SIG_BLOCK, &set, NULL);
- signal(SIGUSR1, wake_me);
+ act.sa_handler = wake_me;
+ act.sa_flags = 0;
+ sigaction(SIGUSR1, &act, NULL);
+ act.sa_handler = SIG_IGN;
+ sigaction(SIGPIPE, &act, NULL);
if (clone_monitor(container) < 0) {
fprintf(stderr, "md-manage: failed to start monitor process: %s\n",