core compiles

This commit is contained in:
aiden 2022-06-05 22:24:23 +01:00
parent b8f465f87f
commit 89cbc0b2ec
No known key found for this signature in database
GPG Key ID: 0D87FF3415416DB1
12 changed files with 106 additions and 130 deletions

@ -9,29 +9,33 @@
#include "../src/headers/bdd_event.h"
#include "../src/headers/bdd_service.h"
#include "../src/headers/bdd_name_descs.h"
#include "../src/headers/bdd_cont.h"
#include "../src/headers/bdd_shutdown_status.h"
#include "../src/headers/bidirectiond_n_io.h"
struct bdd_conversation;
__attribute__((warn_unused_result)) ssize_t bdd_io_read(
struct bdd_conversation *conversation,
uint8_t io_id,
bdd_io_id io_id,
void *buf,
ssize_t sz
);
__attribute__((warn_unused_result)) ssize_t bdd_io_write(
struct bdd_conversation *conversation,
uint8_t io_id,
bdd_io_id io_id,
void *buf,
ssize_t sz
);
bool bdd_connect(struct bdd_conversation *conversation, int address_family, struct sockaddr *addr, socklen_t addrlen);
bool bdd_prep_ssl(
bool bdd_io_obtain(struct bdd_conversation *conversation, bdd_io_id *io_id)
bool bdd_io_connect(struct bdd_conversation *conversation, bdd_io_id io_id, struct sockaddr *addr, socklen_t addrlen);
bool bdd_io_prep_ssl(
struct bdd_conversation *conversation,
char *ssl_name,
char *alp
);
void bdd_set_associated(
void bdd_io_set_associated(
struct bdd_conversation *conversation,
void *data,
void (*destructor)(void *)
@ -45,6 +49,6 @@ bool bdd_name_descs_add_service_instance(
const void **instance_info
);
bool bdd_io_shutdown(struct bdd_conversation *conversation, uint8_t io_id);
enum bdd_shutdown_status bdd_io_shutdown(struct bdd_conversation *conversation, bdd_io_id io_id);
#endif

@ -263,7 +263,7 @@ enum bdd_cont bdd_connect_continue(struct bdd_io *io) {
}
void bdd_accept(struct bdd_worker_data *worker_data) {
struct bdd_conversation *conversation = bdd_conversation_obtain();
struct bdd_conversation *conversation = bdd_conversation_obtain(worker_data->epoll_fd);
if (conversation == NULL) {
return;
}

@ -12,6 +12,7 @@
#include "headers/conversations.h"
#include "headers/bdd_service.h"
#include "headers/bdd_io.h"
#include "headers/bdd_event.h"
void *bdd_get_associated(struct bdd_conversation *conversation) {
return conversation->aopn.associated.data;
@ -39,13 +40,13 @@ int bdd_conversation_id(struct bdd_conversation *conversation) {
return (((char *)conversation - (char *)(bdd_gv.conversations)) / sizeof(struct bdd_conversation));
}
struct bdd_ev *bdd_ev(struct bdd_conversation *conversation, typeof(BIDIRECTIOND_N_IO) idx) {
struct bdd_ev *bdd_ev(struct bdd_conversation *conversation, bdd_io_id idx) {
if (idx >= conversation->n_ev) {
abort();
}
return &(((struct bdd_ev *)&(conversation->io_array[BIDIRECTIOND_N_IO]))[idx]);
}
typeof(BIDIRECTIOND_N_IO) bdd_n_ev(struct bdd_conversation *conversation) {
bdd_io_id bdd_n_ev(struct bdd_conversation *conversation) {
return conversation->n_ev;
}
@ -84,7 +85,7 @@ struct bdd_conversation *bdd_conversation_obtain(int epoll_fd) {
conversation->aopn.pn.cstr_protocol_name = NULL;
return conversation;
}
void bdd_conversation_discard(struct bdd_conversation *conversation, int epoll_fd) {
void bdd_conversation_discard(struct bdd_conversation *conversation) {
if (conversation->state == bdd_conversation_established) {
bdd_set_associated(conversation, NULL, NULL);
}

@ -2,16 +2,11 @@
#define bidirectiond_core__accept__h
#include <hashmap/hashmap.h>
#include "bdd_cont.h"
struct bdd_conversation;
struct bdd_io;
enum bdd_cont {
bdd_cont_discard,
bdd_cont_inprogress,
bdd_cont_established,
};
int bdd_alpn_cb(
SSL *client_ssl,
const unsigned char **out,

@ -0,0 +1,10 @@
#ifndef bidirectiond_core__bdd_cont__h
#define bidirectiond_core__bdd_contt__h
enum bdd_cont {
bdd_cont_discard,
bdd_cont_inprogress,
bdd_cont_established,
};
#endif

@ -6,7 +6,7 @@
#define bdd_ev_removed 4
struct bdd_ev {
enum bdd_ev ev;
uint8_t events;
uint8_t io_id;
};

@ -8,7 +8,7 @@
struct bdd_conversation;
struct bdd_name_descs;
struct bdd_service {
void (*handle_events)(struct bdd_conversation *conversation, uint8_t io_id, uint8_t events);
void (*handle_events)(struct bdd_conversation *conversation);
bool (*conversation_init)(
struct bdd_conversation *conversation,

@ -0,0 +1,6 @@
#ifndef BIDIRECTIOND_N_IO
#define BIDIRECTIOND_N_IO 2
#endif
#ifndef bdd_io_id
#define bdd_io_id typeof(BIDIRECTIOND_N_IO)
#endif

@ -8,6 +8,8 @@
#include <sys/socket.h>
#include "bdd_io.h"
#include "bdd_shutdown_status.h"
#include "bidirectiond_n_io.h"
struct bdd_service;
struct bdd_io;
@ -39,10 +41,10 @@ struct bdd_conversation {
struct bdd_io *io_array;
typeof(BIDIRECTIOND_N_IO) n_connecting;
typeof(BIDIRECTIOND_N_IO) n_in_epoll_with_events;
bdd_io_id n_connecting;
bdd_io_id n_in_epoll_with_events;
typeof(BIDIRECTIOND_N_IO) n_ev;
bdd_io_id n_ev;
union {
struct bdd_associated associated;
@ -70,12 +72,19 @@ enum bdd_conversation_init_status bdd_conversation_init(
int bdd_io_fd(struct bdd_io *io);
struct bdd_conversation *bdd_conversation_obtain(int epoll_fd);
void bdd_conversation_discard(struct bdd_conversation *conversation);
typeof(BIDIRECTIOND_N_IO) bdd_io_obtain(struct bdd_conversation *conversation);
void bdd_io_discard(struct bdd_io *io);
typeof(BIDIRECTIOND_N_IO) bdd_io_id(struct bdd_io *io);
struct bdd_io *bdd_io(struct bdd_conversation *conversation, typeof(BIDIRECTIOND_N_IO) io_id);
bdd_io_id bdd_io_id_of(struct bdd_io *io);
struct bdd_io *bdd_io(struct bdd_conversation *conversation, bdd_io_id io_id);
enum bdd_shutdown_status bdd_ssl_shutdown_continue(struct bdd_io *io);
void bdd_io_epoll_mod(struct bdd_io *io, uint32_t add_events, uint32_t remove_events, bool edge_trigger);
void bdd_io_epoll_add(struct bdd_io *io);
void bdd_io_epoll_remove(struct bdd_io *io);
bool bdd_io_hup(struct bdd_io *io, bool rdhup);
void bdd_io_state(struct bdd_io *io, enum bdd_io_state new_state);
struct bdd_ev *bdd_ev(struct bdd_conversation *conversation, bdd_io_id io_id);
#endif

@ -111,7 +111,8 @@ void bdd_destroy(void) {
++idx
) {
struct bdd_conversation *conversation = &(bdd_gv.conversations[idx]);
bdd_conversation_discard(conversation, -1);
conversation->epoll_fd = -1;
bdd_conversation_discard(conversation);
}
free(bdd_gv.conversations);

@ -14,13 +14,14 @@
#include "headers/conversations.h"
#include "headers/bdd_service.h"
#include "headers/bdd_io.h"
#include "headers/bidirectiond_n_io.h"
typeof(BIDIRECTIOND_N_IO) bdd_io_id(struct bdd_io *io) {
bdd_io_id bdd_io_id_of(struct bdd_io *io) {
struct bdd_conversation *conversation = io->conversation;
return (((char *)io - (char *)conversation->io_array) / sizeof(struct bdd_io));
}
struct bdd_io *bdd_io(struct bdd_conversation *conversation, typeof(BIDIRECTIOND_N_IO) io_id) {
struct bdd_io *bdd_io(struct bdd_conversation *conversation, bdd_io_id io_id) {
if (conversation == NULL || io_id >= BIDIRECTIOND_N_IO) {
return NULL;
}
@ -36,14 +37,14 @@ int bdd_io_fd(struct bdd_io *io) {
}
}
void bdd_io_epoll_mod(struct bdd_io *io, uint32_t remove_flags, uint32_t add_flags, bool edge_trigger) {
void bdd_io_epoll_mod(struct bdd_io *io, uint32_t add_events, uint32_t remove_events, bool edge_trigger) {
uint32_t old_events = io->epoll_events;
io->epoll_events &= ~remove_flags;
io->epoll_events &= ~remove_events;
if (io->rdhup) {
add_flags &= ~EPOLLIN;
add_events &= ~EPOLLIN;
}
io->epoll_events |= add_events;
if (io->edge_trigger) {
if (edge_trigger) {
io->epoll_events |= EPOLLET;
} else {
io->epoll_events &= ~EPOLLET;
@ -54,7 +55,7 @@ void bdd_io_epoll_mod(struct bdd_io *io, uint32_t remove_flags, uint32_t add_fla
}
#endif
if (io->in_epoll) {
if (((old_events & ~EPOLLET) == 0) {
if ((old_events & ~EPOLLET) == 0) {
if ((io->epoll_events & ~EPOLLET) != 0) {
io->conversation->n_in_epoll_with_events += 1;
}
@ -87,7 +88,7 @@ void bdd_io_epoll_add(struct bdd_io *io) {
}
void bdd_io_epoll_remove(struct bdd_io *io) {
if (!io->in_epoll) {
if (!io->in_epoll || io->conversation->epoll_fd < 0) {
return;
}
io->in_epoll = 0;
@ -114,8 +115,8 @@ void bdd_io_state(struct bdd_io *io, enum bdd_io_state new_state) {
if (state == bdd_io_connecting) {
if (conversation->n_connecting) {
for (typeof(BIDIRECTIOND_N_IO) idx = 0; idx <= conversation->n_servers; ++idx) {
struct bdd_io *idx_io = bdd_io(idx);
for (bdd_io_id idx = 0; idx < BIDIRECTIOND_N_IO; ++idx) {
struct bdd_io *idx_io = bdd_io(conversation, idx);
if (idx_io == io || (idx_io->state != bdd_io_est && idx_io->state != bdd_io_ssl_shutting)) {
continue;
}
@ -134,8 +135,8 @@ void bdd_io_state(struct bdd_io *io, enum bdd_io_state new_state) {
if (new_state == bdd_io_connecting) {
if (conversation->n_connecting == 0) {
for (typeof(BIDIRECTIOND_N_IO) idx = 0; idx <= conversation->n_servers; ++idx) {
struct bdd_io *idx_io = bdd_io(idx);
for (bdd_io_id idx = 0; idx < BIDIRECTIOND_N_IO; +idx) {
struct bdd_io *idx_io = bdd_io(conversation, idx);
if (idx_io == io || idx_io->state == bdd_io_connecting) {
continue;
}
@ -147,24 +148,24 @@ void bdd_io_state(struct bdd_io *io, enum bdd_io_state new_state) {
}
}
conversation->n_connecting += 1;
bdd_io_epoll_mod(idx_io, 0, EPOLLIN | EPOLLOUT, true);
bdd_io_epoll_add(idx_io);
bdd_io_epoll_mod(io, 0, EPOLLIN | EPOLLOUT, true);
bdd_io_epoll_add(io);
} else if (new_state == bdd_io_est) {
uint32_t epollin = EPOLLIN;
if (io->rdhup) {
epollin = 0;
}
bdd_io_epoll_mod(idx_io, EPOLLOUT, epollin, false);
bdd_io_epoll_mod(io, EPOLLOUT, epollin, false);
if (conversation->n_connecting == 0) {
bdd_io_epoll_add(idx_io);
bdd_io_epoll_add(io);
} else {
bdd_io_epoll_remove(idx_io);
bdd_io_epoll_remove(io);
}
} else if (new_state == bdd_io_ssl_shutting) {
bdd_io_epoll_mod(idx_io, 0, EPOLLOUT, false);
bdd_io_epoll_add(idx_io);
bdd_io_epoll_mod(io, 0, EPOLLOUT, false);
bdd_io_epoll_add(io);
} else {
bdd_io_epoll_remove(idx_io);
bdd_io_epoll_remove(io);
}
return;
@ -173,7 +174,7 @@ void bdd_io_state(struct bdd_io *io, enum bdd_io_state new_state) {
// returns the number of bytes read (where 0 is a possible value), returns -3 on rdhup, returns -2 if IO discarded, returns -1 on err,
__attribute__((warn_unused_result)) ssize_t bdd_io_read(
struct bdd_conversation *conversation,
typeof(BIDIRECTIOND_N_IO) io_id,
bdd_io_id io_id,
void *buf,
ssize_t sz
) {
@ -205,7 +206,7 @@ __attribute__((warn_unused_result)) ssize_t bdd_io_read(
} else if (err == SSL_ERROR_WANT_WRITE) {
abort(); // fuck re-negotiation
} else if (err == SSL_ERROR_ZERO_RETURN /* received close_notify */) {
if (bdd_io_set_hup(io, true)) {
if (bdd_io_hup(io, true)) {
bdd_io_discard(io);
return -2;
}
@ -234,7 +235,7 @@ __attribute__((warn_unused_result)) ssize_t bdd_io_read(
return -2;
}
if (r == 0) {
if (bdd_io_set_hup(io, true)) {
if (bdd_io_hup(io, true)) {
bdd_io_discard(io);
return -2;
}
@ -247,7 +248,7 @@ __attribute__((warn_unused_result)) ssize_t bdd_io_read(
// returns the number of bytes written, returns -2 if IO discarded, returns -1 on err
__attribute__((warn_unused_result)) ssize_t bdd_io_write(
struct bdd_conversation *conversation,
typeof(BIDIRECTIOND_N_IO) io_id,
bdd_io_id io_id,
void *buf,
ssize_t sz
) {
@ -279,7 +280,7 @@ __attribute__((warn_unused_result)) ssize_t bdd_io_write(
bdd_io_epoll_mod(io, 0, EPOLLOUT, false);
return 0;
}
if (bdd_io_set_hup(io, false)) {
if (bdd_io_hup(io, false)) {
return -2;
}
return -1;
@ -294,7 +295,7 @@ __attribute__((warn_unused_result)) ssize_t bdd_io_write(
bdd_io_epoll_mod(io, 0, EPOLLOUT, false);
return 0;
}
if (bdd_io_set_hup(io, false)) {
if (bdd_io_hup(io, false)) {
return -2;
}
return -1;
@ -306,6 +307,18 @@ __attribute__((warn_unused_result)) ssize_t bdd_io_write(
return r;
}
bool bdd_io_obtain(struct bdd_conversation *conversation, bdd_io_id *io_id) {
for (size_t idx = 0; idx < BIDIRECTIOND_N_IO; ++idx) {
struct bdd_io *io = &(conversation->io_array[idx]);
if (io->state == bdd_io_unused) {
bdd_io_state(io, bdd_io_obtained);
*io_id = (bdd_io_id)idx;
return true;
}
}
return false;
}
enum bdd_shutdown_status bdd_ssl_shutdown_continue(struct bdd_io *io) {
int r = SSL_shutdown(io->io.ssl);
if (r < 0) {
@ -323,7 +336,7 @@ enum bdd_shutdown_status bdd_ssl_shutdown_continue(struct bdd_io *io) {
return bdd_shutdown_complete;
}
enum bdd_shutdown_status bdd_io_shutdown(struct bdd_conversation *conversation, typeof(BIDIRECTIOND_N_IO) io_id) {
enum bdd_shutdown_status bdd_io_shutdown(struct bdd_conversation *conversation, bdd_io_id io_id) {
struct bdd_io *io = bdd_io(conversation, io_id);
if (io == NULL) {
fputs("programming error: bdd_io_shutdown called with invalid arguments\n", stderr);
@ -335,11 +348,9 @@ enum bdd_shutdown_status bdd_io_shutdown(struct bdd_conversation *conversation,
}
if (io->ssl) {
bdd_io_state(io, bdd_io_ssl_shutdown);
if (bdd_io_shutdown_continue(io)): {
case (bdd_shutdown_inprogress): {
return bdd_shutdown_inprogress;
}
bdd_io_state(io, bdd_io_ssl_shutting);
if (bdd_ssl_shutdown_continue(io) == bdd_shutdown_inprogress) {
return bdd_shutdown_inprogress;
}
} else {
shutdown(bdd_io_fd(io), SHUT_WR);
@ -366,7 +377,7 @@ void bdd_io_discard(struct bdd_io *io) {
io->ssl &&
io->rdhup &&
io->wrhup &&
(SSL_get_shutdown(io->io.ssl) & SSL_SENT_SHUT)
(SSL_get_shutdown(io->io.ssl) & SSL_SENT_SHUTDOWN)
) {
SSL_shutdown(io->io.ssl);
shutdown(fd, SHUT_WR);
@ -379,8 +390,8 @@ void bdd_io_discard(struct bdd_io *io) {
return;
}
bool bdd_io_prep_ssl(struct bdd_conversation *conversation, typeof(BIDIRECTIOND_N_IO) io_id, char *ssl_name, char *alp) {
struct bdd_io *io = bdd_io(conversation, io);
bool bdd_io_prep_ssl(struct bdd_conversation *conversation, bdd_io_id io_id, char *ssl_name, char *alp) {
struct bdd_io *io = bdd_io(conversation, io_id);
if (io == NULL || io->state != bdd_io_obtained) {
fputs("programming error: bdd_io_prep_ssl called with an io_id which is in an invalid state\n", stderr);
abort();
@ -439,11 +450,11 @@ bool bdd_io_prep_ssl(struct bdd_conversation *conversation, typeof(BIDIRECTIOND_
enum bdd_cont bdd_io_connect(
struct bdd_conversation *conversation,
typeof(BIDIRECTIOND_N_IO) io_id,
bdd_io_id io_id,
struct sockaddr *sockaddr,
socklen_t addrlen
) {
struct bdd_io *io = bdd_io(conversation, io);
struct bdd_io *io = bdd_io(conversation, io_id);
if (io == NULL || (io->state != bdd_io_obtained && io->state != bdd_io_prepd_ssl)) {
fputs("programming error: bdd_io_connect called with an io_id which is in an invalid state\n", stderr);
abort();

@ -5,6 +5,7 @@
#include <unistd.h>
#include <pthread.h>
#include <stdatomic.h>
#include <string.h>
#include <stdbool.h>
#include "headers/instance.h"
@ -15,71 +16,11 @@
#include "headers/unlikely.h"
#include "headers/bdd_event.h"
#include "headers/bdd_io.h"
#include "headers/bidirectiond_n_io.h"
#include "headers/bdd_service.h"
#include "headers/bdd_stop.h"
enum handle_io_status {
handle_io_discard,
handle_io_hup,
handle_io_lt,
};
static enum handle_io_status handle_io(struct bdd_io *io, uint32_t revents) {
struct bdd_conversation *conversation = io->conversation;
unsigned char bdd_revents = 0;
if (revents & EPOLLERR) {
io->state = BDD_IO_ERR;
} else if (io->state == BDD_IO_SSL_SHUTTING) {
if (bdd_ssl_shutdown_continue(io) == bdd_cont_discard) {
io->state = BDD_IO_ERR;
}
}
if ((revents & EPOLLIN) && !io->rdhup) {
bdd_revents |= BDDEV_IN;
}
if (revents & EPOLLOUT) {
if (io->state == bdd_io_est) {
bdd_revents |= bdd_ev_out;
bdd_io_epoll_flags(io, EPOLLOUT, 0);
} else if (io->state == BDD_IO_SSL_SHUTTING) {
switch (bdd_ssl_shutdown_continue(io)) {
case (bdd_cont_established): {
bdd_io_epoll_flags(io, EPOLLOUT, 0);
break;
}
case (bdd_cont_discard): {
bdd_io_epoll_remove(io);
break;
}
}
} else {
abort();
}
}
if (io->state == BDD_IO_ERR) {
bdd_revents |= BDDEV_NOOUT;
}
if (bdd_revents & ~BDDEV_NOOUT) {
conversation->sosi.service->handle_events(conversation, bdd_io_id(conversation, io), bdd_revents);
}
assert(conversation->client.state >= bdd_io_est);
if (conversation->client.state >= bdd_io_err) {
// discard conversation
}
if (
((
conversation->client.rdhup &&
!(conversation->client.epoll_flags & EPOLLOUT)
) || !conversation->client.in_epoll) &&
conversation->n_servers_in_epoll == 0
) {
abort();
}
}
#include "headers/bdd_event.h"
#include "headers/bdd_shutdown_status.h"
static void process_link(struct bdd_conversation **list, struct bdd_conversation *conversation) {
if (conversation->n_ev == 1) {
@ -129,16 +70,14 @@ void *bdd_serve(struct bdd_worker_data *worker_data) {
}
switch (conversation->state) {
case (bdd_conversation_accept): {
switch (bdd_accept_continue(conversation)) {
case (bdd_cont_discard): {
bdd_conversation_discard(conversation, epoll_fd);
}
if (bdd_accept_continue(conversation) == bdd_cont_discard) {
bdd_conversation_discard(conversation);
}
break;
}
case (bdd_conversation_established): {
struct bdd_ev *ev = bdd_ev(conversation, conversation->n_ev++);
ev->io_id = bdd_io_id(io);
ev->io_id = bdd_io_id_of(io);
ev->events = (
(event->events & EPOLLIN ? bdd_ev_in : 0) |
(event->events & EPOLLOUT ? bdd_ev_out : 0) |