From: Alan T. DeKok Date: Wed, 6 Mar 2024 21:22:10 +0000 (-0500) Subject: allocate tracking table at the start X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=4451ca3bc65e781431a40ccd36f695191a2cf10f;p=thirdparty%2Ffreeradius-server.git allocate tracking table at the start --- diff --git a/src/protocols/radius/client.c b/src/protocols/radius/client.c index 9ee85557ba4..fe170eead79 100644 --- a/src/protocols/radius/client.c +++ b/src/protocols/radius/client.c @@ -52,6 +52,7 @@ static int _radius_client_fd_bio_free(fr_radius_client_fd_bio_t *my) fr_radius_client_fd_bio_t *fr_radius_client_fd_bio_alloc(TALLOC_CTX *ctx, size_t read_size, fr_radius_client_config_t *cfg, fr_bio_fd_config_t const *fd_cfg) { + int i; fr_radius_client_fd_bio_t *my; fr_bio_t *fd, *mem; @@ -60,6 +61,16 @@ fr_radius_client_fd_bio_t *fr_radius_client_fd_bio_alloc(TALLOC_CTX *ctx, size_t my = talloc_zero(ctx, fr_radius_client_fd_bio_t); if (!my) return NULL; + /* + * Allocate tracking for all of the packets. + */ + for (i = 1; i < FR_RADIUS_CODE_MAX; i++) { + if (!cfg->allowed[i]) continue; + + my->codes[i] = fr_radius_id_alloc(my); + if (!my->codes[i]) goto fail; + } + my->fd = fd = fr_bio_fd_alloc(my, NULL, fd_cfg, 0); if (!fd) { fail: @@ -68,7 +79,7 @@ fr_radius_client_fd_bio_t *fr_radius_client_fd_bio_alloc(TALLOC_CTX *ctx, size_t } my->fd = fd; - my->mem = mem = fr_bio_mem_alloc(ctx, read_size, 2 * 4096, fd); + my->mem = mem = fr_bio_mem_alloc(my, read_size, 2 * 4096, fd); if (!mem) goto fail; my->cfg = *cfg; @@ -91,12 +102,16 @@ int fr_radius_client_fd_bio_write(fr_radius_client_fd_bio_t *my, UNUSED void *pa fr_assert(packet->code > 0); fr_assert(packet->code < FR_RADIUS_CODE_MAX); - /* - * @todo - Allocate when the socket is opened, so we don't check it for every packet. - */ - if (!my->codes[packet->code] && !(my->codes[packet->code] = fr_radius_id_alloc(my))) return -1; + if (!my->codes[packet->code]) { + fr_strerror_printf("Outgoing packet code %s is disallowed by the configuration", + fr_radius_packet_names[packet->code]); + return -1; + } - if (fr_radius_code_id_pop(my->codes, packet) < 0) return -1; + if (fr_radius_code_id_pop(my->codes, packet) < 0) { + fr_strerror_const("All IDs are in use"); + return -1; + } /* * Encode the packet. @@ -145,7 +160,6 @@ int fr_radius_client_fd_bio_read(fr_bio_packet_t *bio, UNUSED void *packet_ctx, if (slen < 0) { fr_assert(slen != fr_bio_error(IO_WOULD_BLOCK)); - return slen; } @@ -177,14 +191,7 @@ int fr_radius_client_fd_bio_read(fr_bio_packet_t *bio, UNUSED void *packet_ctx, } /* - * @todo - if we already have a reply then don't decode - * it. Just return "whoops, no packet". - * - * @todo - provide an API to expire the outgoing packet. - * - * @todo - provide an API to run timers for a particular packet. - * - * Any retries, etc. are part of packet->uctx + * Return the code to the free list. */ if (fr_radius_code_id_push(my->codes, packet) < 0) { fr_assert(0); diff --git a/src/protocols/radius/client.h b/src/protocols/radius/client.h index 4805dceb163..451b885885c 100644 --- a/src/protocols/radius/client.h +++ b/src/protocols/radius/client.h @@ -33,7 +33,9 @@ RCSIDH(radius_client_h, "$Id$") typedef struct { fr_radius_bio_verify_t verify; - fr_retry_config_t retry[FR_RADIUS_CODE_MAX]; + bool allowed[FR_RADIUS_CODE_MAX]; //!< allowed outgoing packet types + + fr_retry_config_t retry[FR_RADIUS_CODE_MAX]; //!< default retry configuration for each packet type } fr_radius_client_config_t; fr_bio_packet_t *fr_radius_client_bio_alloc(TALLOC_CTX *ctx, fr_radius_client_config_t *cfg, fr_bio_fd_config_t const *fd_cfg) CC_HINT(nonnull);