diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-05-30 02:49:40 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-05-30 02:49:40 +0000 |
commit | c96f16e8103783f6b98d9f844ea3a7f2195e4834 (patch) | |
tree | 479bef5e7eb5d4f04ba171931c8b47335734e161 /debian/vendor-h2o/examples/libh2o/latency-optimization.c | |
parent | Merging upstream version 1.9.4. (diff) | |
download | dnsdist-debian/1.9.4-1.tar.xz dnsdist-debian/1.9.4-1.zip |
Adding debian version 1.9.4-1.debian/1.9.4-1
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'debian/vendor-h2o/examples/libh2o/latency-optimization.c')
-rw-r--r-- | debian/vendor-h2o/examples/libh2o/latency-optimization.c | 381 |
1 files changed, 0 insertions, 381 deletions
diff --git a/debian/vendor-h2o/examples/libh2o/latency-optimization.c b/debian/vendor-h2o/examples/libh2o/latency-optimization.c deleted file mode 100644 index de34bc9..0000000 --- a/debian/vendor-h2o/examples/libh2o/latency-optimization.c +++ /dev/null @@ -1,381 +0,0 @@ -/* - * Copyright (c) 2014 DeNA Co., Ltd. - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to - * deal in the Software without restriction, including without limitation the - * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or - * sell copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING - * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS - * IN THE SOFTWARE. - */ -#include <errno.h> -#include <getopt.h> -#include <inttypes.h> -#include <netdb.h> -#include <netinet/in.h> -#include <stdio.h> -#include <sys/socket.h> -#include <sys/types.h> -#include <openssl/err.h> -#include <openssl/ssl.h> -#include "h2o/socket.h" -#include "h2o/string_.h" - -/* configuration */ -static char *host, *port; -static SSL_CTX *ssl_ctx; -static int mode_server, server_flag_received; -static h2o_socket_latency_optimization_conditions_t latopt_cond = {.min_rtt = 50, .max_additional_delay = 10, .max_cwnd = 65535}; -size_t write_block_size = 65536; - -/* globals */ -static h2o_loop_t *loop; -static h2o_socket_t *sock; -static struct { - uint64_t resp_start_at; - uint64_t sig_received_at; - uint64_t bytes_received; - uint64_t bytes_before_sig; -} client_stats; - -static void server_write(h2o_socket_t *sock); - -static h2o_iovec_t prepare_write_buf(void) -{ - static h2o_iovec_t buf; - if (buf.base == NULL) { - buf.base = h2o_mem_alloc(write_block_size); - buf.len = write_block_size; - memset(buf.base, '0', buf.len); - } - return buf; -} - -static void server_on_write_ready(h2o_socket_t *sock, const char *err) -{ - if (err != NULL) { - fprintf(stderr, "socket unexpected closed by peer:%s\n", err); - exit(1); - return; - } - server_write(sock); -} - -static void server_on_write_complete(h2o_socket_t *sock, const char *err) -{ - if (err != NULL) { - fprintf(stderr, "write failed:%s\n", err); - exit(1); - return; - } - h2o_socket_notify_write(sock, server_on_write_ready); -} - -void server_write(h2o_socket_t *sock) -{ - size_t sz = h2o_socket_prepare_for_latency_optimized_write(sock, &latopt_cond); - h2o_iovec_t buf = prepare_write_buf(); - - if (server_flag_received) - buf.base[0] = '1'; - if (sz < buf.len) - buf.len = sz; - - fprintf(stderr, "writing %zu bytes\n", buf.len); - h2o_socket_write(sock, &buf, 1, server_on_write_complete); -} - -static void server_on_read_second(h2o_socket_t *sock, const char *err) -{ - if (err != NULL) { - fprintf(stderr, "connection closed unexpectedly:%s\n", err); - exit(1); - return; - } - - fprintf(stderr, "received the flag\n"); - server_flag_received = 1; -} - -static void server_on_read_first(h2o_socket_t *sock, const char *err) -{ - if (err != NULL) { - fprintf(stderr, "connection closed unexpectedly:%s\n", err); - exit(1); - return; - } - - server_write(sock); - h2o_socket_read_start(sock, server_on_read_second); -} - -static void client_on_write_complete(h2o_socket_t *sock, const char *err) -{ - if (err == NULL) - return; - /* handle error */ - fprintf(stderr, "write failed:%s\n", err); - h2o_socket_close(sock); - exit(1); -} - -static void client_on_read_second(h2o_socket_t *sock, const char *err) -{ - size_t i; - - if (err != NULL) { - fprintf(stderr, "connection closed unexpectedly:%s\n", err); - exit(1); - return; - } - - if (client_stats.sig_received_at == 0) { - for (i = 0; i != sock->input->size; ++i) { - if (sock->input->bytes[i] != '0') { - client_stats.sig_received_at = h2o_now(h2o_socket_get_loop(sock)); - break; - } - ++client_stats.bytes_before_sig; - } - } - client_stats.bytes_received += sock->input->size; - h2o_buffer_consume(&sock->input, sock->input->size); - - if (client_stats.bytes_received >= 1024 * 1024) { - uint64_t now = h2o_now(h2o_socket_get_loop(sock)); - printf("Delay: %" PRIu64 " octets, %" PRIu64 " ms\n", client_stats.bytes_before_sig, - client_stats.sig_received_at - client_stats.resp_start_at); - printf("Total: %" PRIu64 " octets, %" PRIu64 " ms\n", client_stats.bytes_received, now - client_stats.resp_start_at); - exit(0); - } -} - -static void client_on_read_first(h2o_socket_t *sock, const char *err) -{ - if (err != NULL) { - fprintf(stderr, "connection closed unexpectedly:%s\n", err); - exit(1); - return; - } - - client_stats.resp_start_at = h2o_now(h2o_socket_get_loop(sock)); - client_stats.bytes_before_sig = sock->input->size; - client_stats.bytes_received = sock->input->size; - h2o_buffer_consume(&sock->input, sock->input->size); - - h2o_iovec_t data = {H2O_STRLIT("!")}; - h2o_socket_write(sock, &data, 1, client_on_write_complete); - h2o_socket_read_start(sock, client_on_read_second); -} - -static void on_handshake_complete(h2o_socket_t *sock, const char *err) -{ - if (err != NULL && err != h2o_socket_error_ssl_cert_name_mismatch) { - /* TLS handshake failed */ - fprintf(stderr, "TLS handshake failure:%s\n", err); - ERR_print_errors_fp(stderr); - h2o_socket_close(sock); - exit(1); - return; - } - - if (mode_server) { - h2o_socket_read_start(sock, server_on_read_first); - } else { - h2o_iovec_t buf = {H2O_STRLIT("0")}; - h2o_socket_write(sock, &buf, 1, client_on_write_complete); - h2o_socket_read_start(sock, client_on_read_first); - } -} - -static void on_connect(h2o_socket_t *sock, const char *err) -{ - if (err != NULL) { - /* connection failed */ - fprintf(stderr, "failed to connect to host:%s\n", err); - h2o_socket_close(sock); - exit(1); - return; - } - - if (ssl_ctx != NULL) { - h2o_socket_ssl_handshake(sock, ssl_ctx, mode_server ? NULL : "blahblah", on_handshake_complete); - } else { - on_handshake_complete(sock, NULL); - } -} - -static void on_accept(h2o_socket_t *listener, const char *err) -{ - if (err != NULL) - return; - - if ((sock = h2o_evloop_socket_accept(listener)) != NULL) { - h2o_socket_close(listener); - if (ssl_ctx != NULL) { - h2o_socket_ssl_handshake(sock, ssl_ctx, mode_server ? NULL : "blahblah", on_handshake_complete); - } else { - on_handshake_complete(sock, NULL); - } - } -} - -static void usage(const char *cmd) -{ - fprintf(stderr, "Usage: %s [opts] [<host>:]<port>\n" - "Options: --listen if set, waits for incoming connection. Otherwise,\n" - " connects to the server running at given address\n" - " --reverse-role if set, reverses the role bet. server and the\n" - " client once the connection is established\n" - " --tls use TLS\n" - " --block-size=octets default write block size\n" - " --min-rtt=ms minimum RTT to enable latency optimization\n" - " --max-cwnd=octets maximum size of CWND to enable latency\n" - " optimization\n", - cmd); - exit(1); -} - -int main(int argc, char **argv) -{ - static const struct option longopts[] = {{"listen", no_argument, NULL, 'l'}, - {"reverse-role", no_argument, NULL, 'r'}, - {"tls", no_argument, NULL, 't'}, - {"block-size", no_argument, NULL, 'b'}, - {"min-rtt", required_argument, NULL, 'R'}, - {"max-cwnd", required_argument, NULL, 'c'}, - {}}; - int opt_ch, mode_listen = 0, mode_reverse_role = 0, mode_tls = 0; - struct addrinfo hints, *res = NULL; - int err; - - while ((opt_ch = getopt_long(argc, argv, "lrtb:R:c:", longopts, NULL)) != -1) { - switch (opt_ch) { - case 'l': - mode_listen = 1; - break; - case 'r': - mode_reverse_role = 1; - break; - case 't': - mode_tls = 1; - break; - case 'b': - if (sscanf(optarg, "%zu", &write_block_size) != 1) { - fprintf(stderr, "write block size (-b) must be a non-negative number of octets\n"); - exit(1); - } - break; - case 'R': - if (sscanf(optarg, "%u", &latopt_cond.min_rtt) != 1) { - fprintf(stderr, "min RTT (-m) must be a non-negative number in milliseconds\n"); - exit(1); - } - break; - case 'c': - if (sscanf(optarg, "%u", &latopt_cond.max_cwnd) != 1) { - fprintf(stderr, "max CWND size must be a non-negative number of octets\n"); - exit(1); - } - break; - default: - usage(argv[0]); - break; - } - } - mode_server = mode_listen; - if (mode_reverse_role) - mode_server = !mode_server; - - if (argc == optind) { - usage(argv[0]); - } else { - char *hostport = argv[optind], *colon; - if ((colon = strchr(hostport, ':')) != NULL) { - hostport = argv[optind]; - host = strdup(hostport); - host[colon - hostport] = '\0'; - port = colon + 1; - } else { - host = "0.0.0.0"; - port = argv[optind]; - } - } - - if (mode_tls) { - SSL_load_error_strings(); - SSL_library_init(); - OpenSSL_add_all_algorithms(); - if (mode_server) { - ssl_ctx = SSL_CTX_new(SSLv23_server_method()); - SSL_CTX_use_certificate_file(ssl_ctx, "examples/h2o/server.crt", SSL_FILETYPE_PEM); - SSL_CTX_use_PrivateKey_file(ssl_ctx, "examples/h2o/server.key", SSL_FILETYPE_PEM); - } else { - ssl_ctx = SSL_CTX_new(SSLv23_client_method()); - } - int nid = NID_X9_62_prime256v1; - EC_KEY *key = EC_KEY_new_by_curve_name(nid); - if (key == NULL) { - fprintf(stderr, "Failed to create curve \"%s\"\n", OBJ_nid2sn(nid)); - exit(1); - } - SSL_CTX_set_tmp_ecdh(ssl_ctx, key); - EC_KEY_free(key); - SSL_CTX_set_options(ssl_ctx, SSL_OP_ALL | SSL_OP_NO_SSLv2 | SSL_OP_NO_SSLv3); - SSL_CTX_set_cipher_list(ssl_ctx, "ECDHE-RSA-AES128-GCM-SHA256"); - } - -#if H2O_USE_LIBUV - loop = uv_loop_new(); -#else - loop = h2o_evloop_create(); -#endif - - /* resolve host:port (FIXME use the function supplied by the loop) */ - memset(&hints, 0, sizeof(hints)); - hints.ai_socktype = SOCK_STREAM; - hints.ai_protocol = IPPROTO_TCP; - hints.ai_flags = AI_ADDRCONFIG; - if ((err = getaddrinfo(host, port, &hints, &res)) != 0) { - fprintf(stderr, "failed to resolve %s:%s:%s\n", host, port, gai_strerror(err)); - exit(1); - } - - if (mode_listen) { - int fd, reuseaddr_flag = 1; - if ((fd = socket(AF_INET, SOCK_STREAM, 0)) == -1 || - setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &reuseaddr_flag, sizeof(reuseaddr_flag)) != 0 || - bind(fd, res->ai_addr, res->ai_addrlen) != 0 || listen(fd, SOMAXCONN) != 0) { - fprintf(stderr, "failed to listen to %s:%s:%s\n", host, port, strerror(errno)); - exit(1); - } - h2o_socket_t *listen_sock = h2o_evloop_socket_create(loop, fd, H2O_SOCKET_FLAG_DONT_READ); - h2o_socket_read_start(listen_sock, on_accept); - } else { - if ((sock = h2o_socket_connect(loop, res->ai_addr, res->ai_addrlen, on_connect)) == NULL) { - fprintf(stderr, "failed to create socket:%s\n", strerror(errno)); - exit(1); - } - } - - while (1) { -#if H2O_USE_LIBUV - uv_run(loop, UV_RUN_DEFAULT); -#else - h2o_evloop_run(loop, INT32_MAX); -#endif - } - - return 0; -} |