Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
79 changes: 68 additions & 11 deletions daemon/c_run.c
Original file line number Diff line number Diff line change
Expand Up @@ -50,9 +50,10 @@
#include "container.h"
#include "cmld.h"

//TODO define in container.h?
#define CLONE_STACK_SIZE 8192

#define SESSION_WBUF_SIZE 1024

typedef struct c_run {
container_t *container;
list_t *sessions;
Expand All @@ -71,6 +72,10 @@ typedef struct c_run_session {
char *cmd;
ssize_t argc;
char **argv;
char *console_sock_container_wbuf;
int console_sock_container_wbuf_count;
char *pty_master_wbuf;
int pty_master_wbuf_count;
} c_run_session_t;

static void *
Expand Down Expand Up @@ -135,6 +140,11 @@ c_run_session_new(c_run_t *run, int create_pty, char *cmd, ssize_t argc, char **
}
session->argv[i] = NULL;

session->console_sock_container_wbuf = mem_new0(char, SESSION_WBUF_SIZE);
session->pty_master_wbuf = mem_new0(char, SESSION_WBUF_SIZE);
session->console_sock_container_wbuf_count = 0;
session->pty_master_wbuf_count = 0;

return session;
}

Expand All @@ -147,6 +157,10 @@ c_run_session_free(c_run_session_t *session)
if (session->pty_slave_name)
mem_free0(session->pty_slave_name);
mem_free_array((void *)session->argv, session->argc);
if (session->console_sock_container_wbuf)
mem_free0(session->console_sock_container_wbuf);
if (session->pty_master_wbuf)
mem_free0(session->pty_master_wbuf);
mem_free0(session);
}

Expand Down Expand Up @@ -191,6 +205,12 @@ c_run_session_cleanup(c_run_session_t *session)
shutdown(session->console_sock_container, SHUT_RDWR);
shutdown(session->console_sock_cmld, SHUT_RDWR);
}

session->console_sock_container_wbuf_count = 0;
session->pty_master_wbuf_count = 0;

mem_memset0(session->console_sock_container_wbuf, SESSION_WBUF_SIZE);
mem_memset0(session->pty_master_wbuf, SESSION_WBUF_SIZE);
}

static void
Expand Down Expand Up @@ -445,26 +465,60 @@ do_pty_exec(void *data)
}

static int
readloop(int from_fd, int to_fd)
readloop(int from_fd, int to_fd, char *buf, int *count)
{
TRACE("[EXEC] Starting read loop in process %d; from fd %d, to fd %d, PPID: %d", getpid(),
from_fd, to_fd, getppid());

int count = 0;
char buf[1024];
// write pending null
if (*count == -1) {
if (write(to_fd, "\0", 1) < 0) {
TRACE_ERRNO("[READLOOP] write failed.");
return -1;
}
*count = 0;
}

// write pending data
if (*count > 0) {
TRACE("[READLOOP] Pending %d bytes from fd: %d: %s", *count, from_fd, buf);
IF_TRUE_RETVAL(*count + 1 > SESSION_WBUF_SIZE, -1);

if (write(to_fd, buf, *count + 1) < 0) {
if (errno == EAGAIN)
return 0; // try again;
Comment thread
jwsbck marked this conversation as resolved.

while (0 < (count = read(from_fd, &buf, sizeof(buf) - 1))) {
buf[count] = 0;
TRACE("[READLOOP] Read %d bytes from fd: %d: %s", count, from_fd, buf);
if (write(to_fd, buf, count + 1) < 0) {
TRACE_ERRNO("[READLOOP] write failed.");
return -1;
}
}
if (count < 0 && errno != EAGAIN) {

while (0 < (*count = read(from_fd, buf, SESSION_WBUF_SIZE - 1))) {
buf[*count] = 0;
TRACE("[READLOOP] Read %d bytes from fd: %d: %s", *count, from_fd, buf);
int written = write(to_fd, buf, *count + 1);
if (written < 0) {
if (errno == EAGAIN)
return 0; // try again;
Comment thread
jwsbck marked this conversation as resolved.

TRACE_ERRNO("[READLOOP] write failed.");
return -1;
}
if (written == *count) {
*count = -1;
} else if (written < *count + 1) {
*count -= written;
memmove(buf, buf + written, written);
}
}
if (*count < 0 && errno != EAGAIN) {
TRACE_ERRNO("[READLOOP] read failed.");
return -1;
}

// all pending data written to to_fd, reset input/output parameter count
*count = 0;

return 0;
}

Expand All @@ -483,7 +537,9 @@ c_run_cb_read_pty(int fd, unsigned events, UNUSED event_io_t *io, void *data)
}

TRACE("Entering PTY master reading loop");
if (-1 == readloop(session->pty_master, session->console_sock_container)) {
if (-1 == readloop(session->pty_master, session->console_sock_container,
session->console_sock_container_wbuf,
&session->console_sock_container_wbuf_count)) {
ERROR("Readloop returned an error, cleanup!");
c_run_session_cleanup(session);
}
Expand All @@ -504,7 +560,8 @@ c_run_cb_write_pty(int fd, unsigned events, UNUSED event_io_t *io, void *data)
}

TRACE("Entering console sock reading loop");
if (-1 == readloop(session->console_sock_container, session->pty_master)) {
if (-1 == readloop(session->console_sock_container, session->pty_master,
session->pty_master_wbuf, &session->pty_master_wbuf_count)) {
ERROR("Readloop returned an error, cleanup!");
c_run_session_cleanup(session);
}
Expand Down