MINOR: quic: Redefine control layer callbacks which are QUIC specific.
We add src/quic_sock.c QUIC specific socket management functions as callbacks
for the control layer: ->accept_conn, ->default_iocb and ->rx_listening.
accept_conn() will have to be defined. The default I/O handler only recvfrom()
the datagrams received. Furthermore, ->rx_listening callback always returns 1 at
this time but should returns 0 when reloading the processus.
diff --git a/include/haproxy/quic_sock.h b/include/haproxy/quic_sock.h
new file mode 100644
index 0000000..78623e8
--- /dev/null
+++ b/include/haproxy/quic_sock.h
@@ -0,0 +1,43 @@
+/*
+ * include/haproxy/quic_sock.h
+ * This file contains declarations for QUIC sockets.
+ *
+ * Copyright 2020 Frédéric Lécaille <flecaille@haproxy.com>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation, version 2.1
+ * exclusively.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+#ifndef _HAPROXY_QUIC_SOCK_H
+#define _HAPROXY_QUIC_SOCK_H
+
+#include <sys/socket.h>
+#include <sys/types.h>
+
+#include <haproxy/api.h>
+#include <haproxy/connection-t.h>
+#include <haproxy/listener-t.h>
+
+int quic_sock_accepting_conn(const struct receiver *rx);
+struct connection *quic_sock_accept_conn(struct listener *l, int *status);
+void quic_sock_fd_iocb(int fd);
+
+#endif /* _HAPROXY_QUIC_SOCK_H */
+
+/*
+ * Local variables:
+ * c-indent-level: 8
+ * c-basic-offset: 8
+ * End:
+ */
diff --git a/src/proto_quic.c b/src/proto_quic.c
index bde3e48..751fc49 100644
--- a/src/proto_quic.c
+++ b/src/proto_quic.c
@@ -41,6 +41,7 @@
#include <haproxy/proto_udp.h>
#include <haproxy/proxy-t.h>
#include <haproxy/sock.h>
+#include <haproxy/quic_sock.h>
#include <haproxy/sock_inet.h>
#include <haproxy/tools.h>
@@ -63,7 +64,7 @@
.unbind = default_unbind_listener,
.suspend = default_suspend_listener,
.resume = default_resume_listener,
- .accept_conn = sock_accept_conn,
+ .accept_conn = quic_sock_accept_conn,
.connect = quic_connect_server,
/* binding layer */
@@ -79,8 +80,8 @@
.rx_enable = sock_enable,
.rx_disable = sock_disable,
.rx_unbind = sock_unbind,
- .rx_listening = sock_accepting_conn,
- .default_iocb = sock_accept_iocb,
+ .rx_listening = quic_sock_accepting_conn,
+ .default_iocb = quic_sock_fd_iocb,
.receivers = LIST_HEAD_INIT(proto_quic4.receivers),
.nb_receivers = 0,
};
@@ -100,7 +101,7 @@
.unbind = default_unbind_listener,
.suspend = default_suspend_listener,
.resume = default_resume_listener,
- .accept_conn = sock_accept_conn,
+ .accept_conn = quic_sock_accept_conn,
.connect = quic_connect_server,
/* binding layer */
@@ -116,8 +117,8 @@
.rx_enable = sock_enable,
.rx_disable = sock_disable,
.rx_unbind = sock_unbind,
- .rx_listening = sock_accepting_conn,
- .default_iocb = sock_accept_iocb,
+ .rx_listening = quic_sock_accepting_conn,
+ .default_iocb = quic_sock_fd_iocb,
.receivers = LIST_HEAD_INIT(proto_quic6.receivers),
.nb_receivers = 0,
};
diff --git a/src/quic_sock.c b/src/quic_sock.c
new file mode 100644
index 0000000..374e97b
--- /dev/null
+++ b/src/quic_sock.c
@@ -0,0 +1,72 @@
+/*
+ * QUIC socket management.
+ *
+ * Copyright 2020 HAProxy Technologies, Frédéric Lécaille <flecaille@haproxy.com>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ *
+ */
+
+#include <errno.h>
+
+#include <sys/socket.h>
+#include <sys/types.h>
+
+#include <haproxy/connection.h>
+#include <haproxy/listener.h>
+
+/* Tests if the receiver supports accepting connections. Returns positive on
+ * success, 0 if not possible
+ */
+int quic_sock_accepting_conn(const struct receiver *rx)
+{
+ return 1;
+}
+
+/* Accept an incoming connection from listener <l>, and return it, as well as
+ * a CO_AC_* status code into <status> if not null. Null is returned on error.
+ * <l> must be a valid listener with a valid frontend.
+ */
+struct connection *quic_sock_accept_conn(struct listener *l, int *status)
+{
+ /* TO DO */
+ return NULL;
+}
+
+/* Function called on a read event from a listening socket. It tries
+ * to handle as many connections as possible.
+ */
+void quic_sock_fd_iocb(int fd)
+{
+ ssize_t ret;
+ struct buffer *buf;
+ struct listener *l = objt_listener(fdtab[fd].owner);
+ /* Source address */
+ struct sockaddr_storage saddr = {0};
+ socklen_t saddrlen;
+
+ if (!l)
+ ABORT_NOW();
+
+ if (!(fdtab[fd].ev & FD_POLL_IN) || !fd_recv_ready(fd))
+ return;
+
+ buf = get_trash_chunk();
+ saddrlen = sizeof saddr;
+ do {
+ ret = recvfrom(fd, buf->area, buf->size, 0,
+ (struct sockaddr *)&saddr, &saddrlen);
+ if (ret < 0) {
+ if (errno == EINTR)
+ continue;
+ if (errno == EAGAIN)
+ fd_cant_recv(fd);
+ return;
+ }
+ } while (0);
+
+ buf->data = ret;
+}