network: ndisc - Allow to use ICMP6 rate limit from received RA

This commit is contained in:
Susant Sahani 2023-08-16 18:25:17 +05:30 committed by Zbigniew Jędrzejewski-Szmek
parent 41712cd1c0
commit 9175002864
8 changed files with 38 additions and 0 deletions

View file

@ -2652,6 +2652,14 @@ Token=prefixstable:2002:da8:1::</programlisting></para>
</listitem>
</varlistentry>
<varlistentry>
<term><varname>UseICMP6RateLimit=</varname></term>
<listitem>
<para>Takes a boolean. When true, the ICMP6 rate limit received in the Router Advertisement will be set to ICMP6
rate limit based on the advertisement. Defaults to true.</para>
</listitem>
</varlistentry>
<varlistentry>
<term><varname>UseGateway=</varname></term>
<listitem>

View file

@ -95,6 +95,7 @@ int ndisc_router_parse(sd_ndisc *nd, sd_ndisc_router *rt) {
rt->hop_limit = a->nd_ra_curhoplimit;
rt->flags = a->nd_ra_flags_reserved; /* the first 8 bits */
rt->lifetime = be16toh(a->nd_ra_router_lifetime);
rt->icmp6_ratelimit_msec = be32toh(a->nd_ra_retransmit);
rt->preference = (rt->flags >> 3) & 3;
if (!IN_SET(rt->preference, SD_NDISC_PREFERENCE_LOW, SD_NDISC_PREFERENCE_HIGH))
@ -221,6 +222,14 @@ int sd_ndisc_router_get_hop_limit(sd_ndisc_router *rt, uint8_t *ret) {
return 0;
}
int sd_ndisc_router_get_icmp6_ratelimit(sd_ndisc_router *rt, uint32_t *ret) {
assert_return(rt, -EINVAL);
assert_return(ret, -EINVAL);
*ret = rt->icmp6_ratelimit_msec;
return 0;
}
int sd_ndisc_router_get_flags(sd_ndisc_router *rt, uint64_t *ret_flags) {
assert_return(rt, -EINVAL);
assert_return(ret_flags, -EINVAL);

View file

@ -27,6 +27,7 @@ struct sd_ndisc_router {
uint8_t hop_limit;
uint32_t mtu;
uint32_t icmp6_ratelimit_msec;
};
static inline void* NDISC_ROUTER_RAW(const sd_ndisc_router *rt) {

View file

@ -23,6 +23,7 @@
#include "string-table.h"
#include "string-util.h"
#include "strv.h"
#include "sysctl-util.h"
#define NDISC_DNSSL_MAX 64U
#define NDISC_RDNSS_MAX 64U
@ -272,6 +273,7 @@ static int ndisc_request_address(Address *in, Link *link, sd_ndisc_router *rt) {
static int ndisc_router_process_default(Link *link, sd_ndisc_router *rt) {
usec_t lifetime_usec, timestamp_usec;
uint32_t icmp6_ratelimit = 0;
struct in6_addr gateway;
uint16_t lifetime_sec;
unsigned preference;
@ -352,6 +354,20 @@ static int ndisc_router_process_default(Link *link, sd_ndisc_router *rt) {
return log_link_warning_errno(link, r, "Could not request gateway: %m");
}
r = sd_ndisc_router_get_icmp6_ratelimit(rt, &icmp6_ratelimit);
if (r < 0)
log_link_debug(link, "Failed to get default router preference from RA: %m");
if (icmp6_ratelimit > 0 && link->network->ipv6_accept_ra_use_icmp6_ratelimit) {
char buf[DECIMAL_STR_MAX(unsigned)];
xsprintf(buf, "%u", icmp6_ratelimit);
r = sysctl_write("net/ipv6/icmp/ratelimit", buf);
if (r < 0)
log_link_warning_errno(link, r, "Could not configure icmp6 rate limit: %m");
}
return 0;
}

View file

@ -286,6 +286,7 @@ IPv6AcceptRA.UseDNS, config_parse_bool,
IPv6AcceptRA.UseDomains, config_parse_ipv6_accept_ra_use_domains, 0, offsetof(Network, ipv6_accept_ra_use_domains)
IPv6AcceptRA.UseMTU, config_parse_bool, 0, offsetof(Network, ipv6_accept_ra_use_mtu)
IPv6AcceptRA.UseHopLimit, config_parse_bool, 0, offsetof(Network, ipv6_accept_ra_use_hop_limit)
IPv6AcceptRA.UseICMP6RateLimit, config_parse_bool, 0, offsetof(Network, ipv6_accept_ra_use_icmp6_ratelimit)
IPv6AcceptRA.DHCPv6Client, config_parse_ipv6_accept_ra_start_dhcp6_client, 0, offsetof(Network, ipv6_accept_ra_start_dhcp6_client)
IPv6AcceptRA.RouteTable, config_parse_dhcp_or_ra_route_table, AF_INET6, 0
IPv6AcceptRA.RouteMetric, config_parse_ipv6_accept_ra_route_metric, 0, 0

View file

@ -487,6 +487,7 @@ int network_load_one(Manager *manager, OrderedHashmap **networks, const char *fi
.ipv6_accept_ra_use_onlink_prefix = true,
.ipv6_accept_ra_use_mtu = true,
.ipv6_accept_ra_use_hop_limit = true,
.ipv6_accept_ra_use_icmp6_ratelimit = true,
.ipv6_accept_ra_route_table = RT_TABLE_MAIN,
.ipv6_accept_ra_route_metric_high = IPV6RA_ROUTE_METRIC_HIGH,
.ipv6_accept_ra_route_metric_medium = IPV6RA_ROUTE_METRIC_MEDIUM,

View file

@ -320,6 +320,7 @@ struct Network {
bool ipv6_accept_ra_use_onlink_prefix;
bool ipv6_accept_ra_use_mtu;
bool ipv6_accept_ra_use_hop_limit;
bool ipv6_accept_ra_use_icmp6_ratelimit;
bool ipv6_accept_ra_quickack;
bool ipv6_accept_ra_use_captive_portal;
bool active_slave;

View file

@ -90,6 +90,7 @@ int sd_ndisc_router_get_timestamp(sd_ndisc_router *rt, clockid_t clock, uint64_t
int sd_ndisc_router_get_raw(sd_ndisc_router *rt, const void **ret, size_t *size);
int sd_ndisc_router_get_hop_limit(sd_ndisc_router *rt, uint8_t *ret);
int sd_ndisc_router_get_icmp6_ratelimit(sd_ndisc_router *rt, uint32_t *ret);
int sd_ndisc_router_get_flags(sd_ndisc_router *rt, uint64_t *ret_flags);
int sd_ndisc_router_get_preference(sd_ndisc_router *rt, unsigned *ret);
int sd_ndisc_router_get_lifetime(sd_ndisc_router *rt, uint16_t *ret_lifetime);