#include "master.h"
#include "log.h"
+#include <string.h>
#include <sys/wait.h>
#include "daemon.h"
#include <stdlib.h>
// One slave per CPU
for (int i = 0; i < master.nSlaves; ++i)
{
- Make_slave(i);
+
+
+ int sv[2];
+ // Possibly the best function ever
+ if (socketpair(AF_UNIX, SOCK_STREAM, 0, sv) != 0)
+ {
+ error("Make_slave", "Setting up socketpair for slave %d : %s", i, strerror(errno));
+ }
+ master.slave[i].in = sv[1];
+ master.slave[i].out = sv[1];
+ master.slave[i].socket_child_end = sv[0];
+
+ Master_shell(i);
}
}
-void Make_slave(int i)
-{
- int sv[2];
- if (socketpair(AF_UNIX, SOCK_STREAM, 0, sv) != 0)
- {
- error("Make_slave", "Setting up socketpair for slave %d : %s", i, strerror(errno));
- }
-
+void Master_shell(int i)
+{
master.slave[i].pid = fork();
if (master.slave[i].pid == 0)
{
- dup2(sv[0],fileno(stdin));
- dup2(sv[0],fileno(stdout));
+ dup2(master.slave[i].socket_child_end,fileno(stdin));
+ dup2(master.slave[i].socket_child_end,fileno(stdout));
execlp(master.o->shell, master.o->shell, NULL);
}
- master.slave[i].in = sv[1];
- master.slave[i].out = sv[1];
+
master.slave[i].running = true;
}
memset(t->output+(t->outlen), 0, sizeof(char) * t->outsiz - t->outlen);
}
- if (c == EOF || (master.o->endlen > 0 && t->outlen >= master.o->endlen
- && strcmp((t->output)+(t->outlen)-(master.o->endlen), master.o->end) == 0))
+ if (c == EOF
+ #ifdef SHELL_OUTPUT_FINISHED
+ || (t->outlen >= SHELL_OUTPUT_FINISHED_LENGTH
+ && strcmp((t->output)+(t->outlen)-(SHELL_OUTPUT_FINISHED_LENGTH), SHELL_OUTPUT_FINISHED) == 0))
+ #else
+ ) // this is totally readable
+ #endif //SHELL_OUTPUT_FINISHED
{
if (c != EOF)
{
- t->output[t->outlen - master.o->endlen] = '\0';
- t->outlen -= master.o->endlen;
+ t->output[t->outlen - SHELL_OUTPUT_FINISHED_LENGTH] = '\0';
+ t->outlen -= SHELL_OUTPUT_FINISHED_LENGTH;
}
master.slave[i].task = NULL;
if (errno != ENXIO)
error("Master_loop", "Daemon trying to reopen fifo %s : %s", DAEMON_FIFO, strerror(errno));
else
- log_print(2, "Master_loop", "Daemon couldn't reopen fifo %s : %s", DAEMON_FIFO, strerror(errno));
+ log_print(LOGWARN, "Master_loop", "Daemon couldn't reopen fifo %s : %s", DAEMON_FIFO, strerror(errno));
}
else
{
write(send_task.slave_fd, master.o->append, (len-1) * sizeof(char));
//log_print(0, "Sent append %s\n",master.o->append);
}
- if (master.o->end != NULL)
+ #ifdef SHELL_OUTPUT_FINISHED
{
static char * echo = ";echo -en \"";
static int len = -1;
if (len == -1) len = strlen(echo);
write(send_task.slave_fd, echo, len*sizeof(char));
- write(send_task.slave_fd, master.o->end, (master.o->endlen) * sizeof(char));
- write(send_task.slave_fd, "\"", 1*sizeof(char));
+ write(send_task.slave_fd, SHELL_OUTPUT_FINISHED, SHELL_OUTPUT_FINISHED_LENGTH * sizeof(char));
+ write(send_task.slave_fd, "\"", sizeof(char));
//log_print(0, "Sent end\n");
}
- write(send_task.slave_fd, "\n", 1*sizeof(char));
+ #endif //SHELL_OUTPUT_FINISHED
+ write(send_task.slave_fd, "\n", sizeof(char));
master.commands_active++;
log_print(3, "Master_sender", "Sent task %d \"%s\" on socket %d - %d tasks active", send_task.task->number, send_task.task->message, send_task.slave_fd, master.commands_active);
}
{
FILE * f = fdopen(master.remote_err[i], "r+"); setbuf(f, NULL);
- fprintf(f, "exit\n");
+ fprintf(f, SHELL_EXIT_COMMAND);
fclose(f);
}
{
static int exitlen = -1;
- if (exitlen == -1) exitlen = strlen(SHELL_EXIT_MESSAGE);
- write(master.slave[i].in, SHELL_EXIT_MESSAGE, exitlen *sizeof(char));
+ if (exitlen == -1) exitlen = strlen(SHELL_EXIT_COMMAND);
+ write(master.slave[i].in, SHELL_EXIT_COMMAND, exitlen *sizeof(char));
//usleep(0.5); //shouldn't matter too much
}
}
while (buffer[len-1] != '\n');
buffer[len-1] = '\0';
- newSlaves = atoi(buffer);
+
+ while (newSlaves == 0 && strcmp(buffer, "0") != 0)
+ {
+ newSlaves = atoi(buffer);
+ }
return;
}
- fprintf(stderr, "Unexpected exit of slave %s", master.slave[i].name);
- if (WIFSIGNALED(s))
- {
- int sig = WTERMSIG(s);
- fprintf(stderr, " due to %s", strsignal(sig));
- if (sig == SIGKILL)
- {
- printf(" - committing suicide\n");
- kill(getpid(), sig);
- }
- }
- else
- {
- fprintf(stderr, " return code %d.",s);
- }
- fprintf(stderr, " Starting replacement.\n");
- Make_slave(i);
+ sigchld_respond(s, "local", i);
+
+ Master_shell(i);
- if (master.o->end != NULL)
+ #ifdef SHELL_OUTPUT_FINISHED
{
//log_print(1, "sigchld_handler", "Trying to convince slave %d to be nice", i);
char buffer[BUFSIZ];
- sprintf(buffer, "name=%s;echo -en \"%s\"\n", master.slave[i].name, master.o->end);
- if (write(master.slave[i].in, buffer, strlen(buffer)) <= 0)
+ int len = sprintf(buffer, "name=%s;echo -en \"%s\"\n", master.slave[i].name, SHELL_OUTPUT_FINISHED);
+ if (write(master.slave[i].in, buffer, len) <= 0)
error("sigchld_handler", "Couldn't restart slave %d; it is unresponsive", i);
}
+ #endif //SHELL_OUTPUT_FINISHED
siglongjmp(env,1);