From: Alan T. DeKok Date: Wed, 12 Feb 2025 15:58:50 +0000 (-0500) Subject: add home_server_lifetime, and update docs X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=b79fea791e0799861a8938d0028e86fa7b9746d6;p=thirdparty%2Ffreeradius-server.git add home_server_lifetime, and update docs --- diff --git a/raddb/mods-available/radius b/raddb/mods-available/radius index 770d33cf767..4923950e7b7 100644 --- a/raddb/mods-available/radius +++ b/raddb/mods-available/radius @@ -587,7 +587,7 @@ radius { # # - # ### Access requests packets + # ### Access Request packets # Access-Request { # @@ -767,14 +767,42 @@ radius replicate { } # -# A dynamic proxy module +# ## Dynamic Proxying +# +# This module supports dynamic proxying via a run-time function: +# +# %proxy.sendto.ipaddr(127.0.0.1, 1812, "testing123") +# +# The first part of the function name (e.g. `proxy`) is taken from +# the module name. The rest is fixed as `sendto.ipaddr()` +# +# The arguments to the function are: +# +# * destination IP address. +# * destination port +# * shared secret +# +# The function will return the type of response packet if it receives +# as a response, or else the function all will fail. +# +# if (%proxy.sendto.ipaddr(127.0.0.1, 1812, "testing123") == 'Access-Accept') { +# ... +# } +# +# The packet name must be a quoted string. +# +# The proxying is done asynchronously. i.e. the packet is sent, and +# the server goes on to do other work. At some point in the future, +# a response is received, the module processes it, and the server +# continues. +# +# The timeouts are controlled as described above. # radius proxy { type = Access-Request # - # We are not opening a socket from our server to their - # server. We are replicating packets. + # The mode. # mode = dynamic-proxy @@ -813,12 +841,12 @@ radius proxy { # These two configuratiuon items can only be used for # UDP sockets. # -# src_port_start = 10000 + src_port_start = 10000 # # src_port_end:: End of source port range. # -# src_port_end = 11000 + src_port_end = 11000 # # `src_port` cannot be used. If it is used here, the @@ -830,6 +858,55 @@ radius proxy { # } + # + # Dynamic proxying does *not* support the `status_check` + # section. + # + + # + # home_server_lifetime:: The lifetime of the home server. + # + # When a new dynamic home server is used, the module caches + # information about it. So long as the home server is still + # being used, it will not expire. But if it has received all + # expected responses (or timeouts), _and_ it has reached its + # expected lifetime, then the home server will be deleted. + # + # This process allows for the secret to change over time. + # However, the secret can only be changed if there are no + # outstanding packets. Otherwise, changing the secret would + # involve having multiple packets outstanding which have + # different secrets. That doesn't work, and can't be fixed + # through any code changes on the server. + # + # The solution to that is to switch to using TLS. + # + home_server_lifetime = 3600 + + # + # These are allowed, but are less useful. If the home server + # doesn't respond, it will often just hit the home server + # lifetime, and be deleted. + # + response_window = 15 + zombie_period = 10 + revive_interval = 3600 + + + # + # ## Timeouts + # + # Timeouts for proxying are controlled in sections named for + # the packet type. See the examples above for full + # documentation. + # + Access-Request { + initial_rtx_time = 2 + max_rtx_time = 16 + max_rtx_count = 5 + max_rtx_duration = 30 + } + # # ## Connection trunking # diff --git a/src/modules/rlm_radius/bio.c b/src/modules/rlm_radius/bio.c index 5c6c120b9b7..3a1a4c99de8 100644 --- a/src/modules/rlm_radius/bio.c +++ b/src/modules/rlm_radius/bio.c @@ -2439,11 +2439,8 @@ static int mod_thread_instantiate(module_thread_inst_ctx_t const *mctx) switch (inst->mode) { case RLM_RADIUS_MODE_XLAT_PROXY: - /* - * @todo - make lifetime configurable? - */ fr_rb_expire_inline_talloc_init(&thread->bio.expires, home_server_t, expire, home_server_cmp, home_server_free, - fr_time_delta_from_sec(60)); + inst->home_server_lifetime); FALL_THROUGH; default: diff --git a/src/modules/rlm_radius/rlm_radius.c b/src/modules/rlm_radius/rlm_radius.c index 48e081d32c4..f7eadc37bf5 100644 --- a/src/modules/rlm_radius/rlm_radius.c +++ b/src/modules/rlm_radius/rlm_radius.c @@ -162,6 +162,8 @@ static conf_parser_t const module_config[] = { { FR_CONF_OFFSET("revive_interval", rlm_radius_t, revive_interval) }, + { FR_CONF_OFFSET("home_server_lifetime", rlm_radius_t, home_server_lifetime) }, + CONF_PARSER_TERMINATOR }; @@ -721,6 +723,12 @@ check_others: FR_INTEGER_BOUND_CHECK("trunk.per_connection_max", inst->trunk_conf.max_req_per_conn, >=, 2); FR_INTEGER_BOUND_CHECK("trunk.per_connection_max", inst->trunk_conf.max_req_per_conn, <=, 255); FR_INTEGER_BOUND_CHECK("trunk.per_connection_target", inst->trunk_conf.target_req_per_conn, <=, inst->trunk_conf.max_req_per_conn / 2); + + /* + * This only applies for XLAT_PROXY, but what the heck. + */ + FR_TIME_DELTA_BOUND_CHECK("home_server_lifetime", inst->home_server_lifetime, >=, fr_time_delta_from_sec(10)); + FR_TIME_DELTA_BOUND_CHECK("home_server_lifetime", inst->home_server_lifetime, <=, fr_time_delta_from_sec(3600)); break; case RLM_RADIUS_MODE_UNCONNECTED_REPLICATE: diff --git a/src/modules/rlm_radius/rlm_radius.h b/src/modules/rlm_radius/rlm_radius.h index 8d6a2f9195f..02b3b3e0925 100644 --- a/src/modules/rlm_radius/rlm_radius.h +++ b/src/modules/rlm_radius/rlm_radius.h @@ -59,6 +59,8 @@ struct rlm_radius_s { fr_time_delta_t zombie_period; fr_time_delta_t revive_interval; + fr_time_delta_t home_server_lifetime; //!< for XLAT_PROXY + char const *secret; //!< Shared secret. uint32_t max_packet_size; //!< Maximum packet size.