mirror of
https://gitlab.nic.cz/labs/bird.git
synced 2025-01-03 15:41:54 +00:00
Container runner basics
This commit is contained in:
parent
fab5458476
commit
4bc6d4f466
@ -6,17 +6,168 @@
|
|||||||
|
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
|
|
||||||
void
|
static void
|
||||||
container_start(struct birdsock *s, struct flock_machine_container_config *cfg)
|
container_mainloop(struct flock_machine_container_config *cfg, int fd)
|
||||||
{
|
{
|
||||||
log(L_INFO "Requested to start a container, name %s, base %s, work %s",
|
log(L_INFO "container mainloop");
|
||||||
cfg->cf.name, cfg->basedir, cfg->workdir);
|
/* TODO cleanup the loops from the forked process */
|
||||||
|
while (1)
|
||||||
|
{
|
||||||
|
pause();
|
||||||
|
log(L_INFO "woken up!");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
struct linpool *lp = lp_new(s->pool);
|
struct container_start_callback {
|
||||||
struct cbor_writer *cw = cbor_init(s->tbuf, s->tbsize, lp);
|
callback cb;
|
||||||
|
sock *s, *skm;
|
||||||
|
struct birdloop *loop;
|
||||||
|
pool *pool;
|
||||||
|
|
||||||
|
/* Stored socket hooks */
|
||||||
|
int (*rx_hook)(sock *, uint size);
|
||||||
|
void (*err_hook)(sock *, int);
|
||||||
|
void *data;
|
||||||
|
|
||||||
|
/* Actual config */
|
||||||
|
struct flock_machine_container_config cfg;
|
||||||
|
};
|
||||||
|
|
||||||
|
static void
|
||||||
|
container_start_sk_err(sock *s, int e)
|
||||||
|
{
|
||||||
|
struct container_start_callback *cb = s->data;
|
||||||
|
|
||||||
|
cb->skm->data = NULL;
|
||||||
|
s->data = cb->data;
|
||||||
|
s->err_hook = cb->err_hook;
|
||||||
|
|
||||||
|
mb_free(cb);
|
||||||
|
s->err_hook(s, e);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
container_parent_rx(sock *skm, uint size)
|
||||||
|
{
|
||||||
|
bug("container_parent_rx");
|
||||||
|
ASSERT_DIE(size >= 3);
|
||||||
|
|
||||||
|
ASSERT_DIE(skm->rbuf[0] == 0xa1);
|
||||||
|
|
||||||
|
switch (skm->rbuf[1])
|
||||||
|
{
|
||||||
|
case 0:
|
||||||
|
{
|
||||||
|
pid_t pid;
|
||||||
|
if (skm->rbuf[2] < 24)
|
||||||
|
pid = skm->rbuf[2];
|
||||||
|
else if (skm->rbuf[2] == 24)
|
||||||
|
pid = skm->rbuf[3];
|
||||||
|
else if (skm->rbuf[2] == 25)
|
||||||
|
pid = skm->rbuf[3] << 8 + skm->rbuf[4];
|
||||||
|
else if (skm->rbuf[3] == 26)
|
||||||
|
pid = skm->rbuf[3] << 32 + skm->rbuf[4] << 24 + skm->rbuf[5] << 16 + skm->rbuf[6];
|
||||||
|
else
|
||||||
|
bug("not implemented");
|
||||||
|
|
||||||
|
log(L_INFO "Machine started with PID %d", pid);
|
||||||
|
|
||||||
|
if (!skm->data)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
struct container_start_callback *cb = skm->data;
|
||||||
|
struct linpool *lp = lp_new(cb->s->pool);
|
||||||
|
struct cbor_writer *cw = cbor_init(cb->s->tbuf, cb->s->tbsize, lp);
|
||||||
cbor_open_block_with_length(cw, 1);
|
cbor_open_block_with_length(cw, 1);
|
||||||
cbor_add_int(cw, -1);
|
cbor_add_int(cw, -1);
|
||||||
cbor_add_string(cw, "OK");
|
cbor_add_string(cw, "OK");
|
||||||
sk_send(s, cw->pt);
|
sk_send(cb->s, cw->pt);
|
||||||
rfree(lp);
|
rfree(lp);
|
||||||
|
|
||||||
|
cb->s->data = cb->data;
|
||||||
|
cb->s->err_hook = cb->err_hook;
|
||||||
|
sk_resume_rx(cb->s->loop, cb->s, cb->rx_hook);
|
||||||
|
|
||||||
|
mb_free(cb);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
default:
|
||||||
|
bug("unimplemented");
|
||||||
|
}
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
container_parent_err(sock *s, int e)
|
||||||
|
{
|
||||||
|
log(L_ERR "Container parent error hook not implemented: %d (%s)", e, strerror(e));
|
||||||
|
sk_close(s);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
container_start_callback(struct callback *_cb)
|
||||||
|
{
|
||||||
|
SKIP_BACK_DECLARE(struct container_start_callback, cb, cb, _cb);
|
||||||
|
|
||||||
|
ASSERT_DIE(birdloop_inside(&main_birdloop));
|
||||||
|
|
||||||
|
log(L_INFO "Requested to start a container, name %s, base %s, work %s",
|
||||||
|
cb->cfg.cf.name, cb->cfg.basedir, cb->cfg.workdir);
|
||||||
|
|
||||||
|
/* create socketpair before forking to do communication */
|
||||||
|
int fds[2];
|
||||||
|
int e = socketpair(AF_UNIX, SOCK_STREAM, 0, fds);
|
||||||
|
if (e < 0)
|
||||||
|
die("Failed to create internal socketpair: %m");
|
||||||
|
|
||||||
|
pid_t pid = fork();
|
||||||
|
if (pid < 0)
|
||||||
|
die("Failed to fork exposed: %m");
|
||||||
|
|
||||||
|
if (!pid)
|
||||||
|
{
|
||||||
|
close(fds[0]);
|
||||||
|
container_mainloop(&cb->cfg, fds[1]); /* this never returns */
|
||||||
|
bug("container_mainloop has returned");
|
||||||
|
}
|
||||||
|
|
||||||
|
close(fds[1]);
|
||||||
|
|
||||||
|
birdloop_enter(cb->loop);
|
||||||
|
sock *skm = sk_new(cb->pool);
|
||||||
|
skm->type = SK_MAGIC;
|
||||||
|
skm->fd = fds[0];
|
||||||
|
skm->rx_hook = container_parent_rx;
|
||||||
|
skm->err_hook = container_parent_err;
|
||||||
|
skm->data = cb;
|
||||||
|
cb->skm = skm;
|
||||||
|
|
||||||
|
if (sk_open(skm, cb->loop) < 0)
|
||||||
|
bug("Container listener: sk_open failed");
|
||||||
|
|
||||||
|
birdloop_leave(cb->loop);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
container_start(struct birdsock *s, struct flock_machine_container_config *cfg)
|
||||||
|
{
|
||||||
|
struct container_start_callback *cb = mb_alloc(s->pool, sizeof *cb);
|
||||||
|
*cb = (struct container_start_callback) {
|
||||||
|
.cb = callback_init(&cb->cb, container_start_callback, &main_birdloop),
|
||||||
|
.s = s,
|
||||||
|
.loop = s->loop,
|
||||||
|
.pool = s->pool,
|
||||||
|
.rx_hook = s->rx_hook,
|
||||||
|
.err_hook = s->err_hook,
|
||||||
|
.data = s->data,
|
||||||
|
.cfg = *cfg,
|
||||||
|
};
|
||||||
|
|
||||||
|
sk_pause_rx(s->loop, s);
|
||||||
|
s->err_hook = container_start_sk_err;
|
||||||
|
s->data = cb;
|
||||||
|
|
||||||
|
callback_activate(&cb->cb);
|
||||||
}
|
}
|
||||||
|
@ -510,7 +510,7 @@ hexp_get_telnet(sock *s, const char *name)
|
|||||||
rfree(lp);
|
rfree(lp);
|
||||||
}
|
}
|
||||||
|
|
||||||
s->rx_hook = NULL;
|
sk_pause_rx(s->loop, s);
|
||||||
s->err_hook = hexp_sock_err;
|
s->err_hook = hexp_sock_err;
|
||||||
|
|
||||||
struct hexp_telnet_requestor *req = mb_allocz(hcs_pool, sizeof *req);
|
struct hexp_telnet_requestor *req = mb_allocz(hcs_pool, sizeof *req);
|
||||||
@ -537,7 +537,7 @@ static void hexp_received_telnet(void *_data)
|
|||||||
|
|
||||||
WALK_TLIST_DELSAFE(hexp_telnet_requestor, r, &hrt->p->requestors)
|
WALK_TLIST_DELSAFE(hexp_telnet_requestor, r, &hrt->p->requestors)
|
||||||
{
|
{
|
||||||
r->s->rx_hook = hcs_rx;
|
sk_resume_rx(r->s->loop, r->s, hcs_rx);
|
||||||
r->s->err_hook = hcs_err;
|
r->s->err_hook = hcs_err;
|
||||||
memcpy(r->s->tbuf, outbuf, cw->pt);
|
memcpy(r->s->tbuf, outbuf, cw->pt);
|
||||||
sk_send(r->s, cw->pt);
|
sk_send(r->s, cw->pt);
|
||||||
|
Loading…
Reference in New Issue
Block a user