diff options
author | Linus Nordberg <linus@nordu.net> | 2011-03-06 15:53:58 +0100 |
---|---|---|
committer | Linus Nordberg <linus@nordu.net> | 2011-03-06 15:53:58 +0100 |
commit | 5c60297a1eaab7b10d6f584ba329493a41b812d0 (patch) | |
tree | ec1eef1d6adb859ef94e5aeeff8f190d35e63215 /lib/udp.c | |
parent | 7636505962a348d9564e53922834dc6df1274653 (diff) |
Restructure code, moving most code out of packet.c
Also, move copyright notice out of COPYING and into every file.
Diffstat (limited to 'lib/udp.c')
-rw-r--r-- | lib/udp.c | 85 |
1 files changed, 85 insertions, 0 deletions
diff --git a/lib/udp.c b/lib/udp.c new file mode 100644 index 0000000..3573033 --- /dev/null +++ b/lib/udp.c @@ -0,0 +1,85 @@ +/* Copyright 2011 NORDUnet A/S. All rights reserved. + See the file COPYING for licensing information. */ + +#if defined HAVE_CONFIG_H +#include <config.h> +#endif + +#include <assert.h> +#include <event2/event.h> +#include <radsec/radsec.h> +#include <radsec/radsec-impl.h> +#include "debug.h" +#include "event.h" +#include "compat.h" +#include "udp.h" + +/* Callback for conn->wev and conn->rev. FIXME: Rename. */ +static void +_evcb (evutil_socket_t fd, short what, void *user_data) +{ + //rs_debug (("%s: fd=%d what=0x%x\n", __func__, fd, what)); + if (what & EV_TIMEOUT) + { + struct rs_connection *conn = (struct rs_connection *) user_data; + assert (conn); + conn->is_connecting = 0; + rs_debug (("%s: UDP timeout NYI", __func__)); + } + else if (what & EV_READ) + { + struct rs_connection *conn = (struct rs_connection *) user_data; + assert (conn); + /* read a single UDP packet and stick it in a new struct + rs_packet */ + + rs_debug (("%s: UDP read NYI", __func__)); + } + else if (what & EV_WRITE) + { + struct rs_packet *pkt = (struct rs_packet *) user_data; + assert (pkt); + /* Socket ready for writing, possibly as a result of a + successful connect. */ + if (!pkt->conn->is_connected) + event_on_connect (pkt->conn, pkt); + if (pkt->conn->out_queue) + { + /* Send one packet, the first. */ + ssize_t r = 0; + struct rs_packet *p = pkt->conn->out_queue; + + assert (p->rpkt); + assert (p->rpkt->data); + r = compat_send (fd, p->rpkt->data, p->rpkt->data_len, 0); + if (r == -1) + { + int sockerr = evutil_socket_geterror (p->conn->fd); + if (sockerr != EAGAIN) + rs_err_conn_push_fl (p->conn, RSE_SOCKERR, __FILE__, __LINE__, + "%d: send: %d (%s)", fd, sockerr, + evutil_socket_error_to_string (sockerr)); + return; /* Don't unlink packet. */ + } + pkt->conn->out_queue = p->next; + } + } +} + +int +udp_init (struct rs_connection *conn, struct rs_packet *pkt) +{ + assert (!conn->bev); + + conn->rev = event_new (conn->evb, conn->fd, EV_READ|EV_PERSIST, _evcb, conn); + conn->wev = event_new (conn->evb, conn->fd, EV_WRITE|EV_PERSIST, _evcb, pkt); + if (!conn->rev || !conn->wev) + { + if (conn->rev) + event_free (conn->rev); + /* ENOMEM _or_ EINVAL but EINVAL only if we use EV_SIGNAL, at + least for now (libevent-2.0.5). */ + return rs_err_conn_push_fl (conn, RSE_NOMEM, __FILE__, __LINE__, NULL); + } + return RSE_OK; +} |