]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
network/routing-policy-rule: use in_addr_prefix for From= and To=
authorYu Watanabe <watanabe.yu+github@gmail.com>
Sun, 22 Sep 2024 16:51:43 +0000 (01:51 +0900)
committerYu Watanabe <watanabe.yu+github@gmail.com>
Fri, 11 Oct 2024 18:26:06 +0000 (03:26 +0900)
Also, this makes the settings parsed independently, and the
inconsistency will be checked in the section verifier.

No functional change, just refactoring.

src/network/networkd-json.c
src/network/networkd-network-gperf.gperf
src/network/networkd-routing-policy-rule.c
src/network/networkd-routing-policy-rule.h

index d1a7bd586cd8b0adaa084f178eb9574eb48a513b..452df9a17fee53fa31cc501e3754a68065831ee5 100644 (file)
@@ -298,12 +298,12 @@ static int routing_policy_rule_append_json(RoutingPolicyRule *rule, sd_json_vari
         return sd_json_variant_append_arraybo(
                         array,
                         SD_JSON_BUILD_PAIR_INTEGER("Family", rule->family),
-                        JSON_BUILD_PAIR_IN_ADDR_NON_NULL("FromPrefix", &rule->from, rule->family),
-                        SD_JSON_BUILD_PAIR_CONDITION(in_addr_is_set(rule->family, &rule->from),
-                                                     "FromPrefixLength", SD_JSON_BUILD_UNSIGNED(rule->from_prefixlen)),
-                        JSON_BUILD_PAIR_IN_ADDR_NON_NULL("ToPrefix", &rule->to, rule->family),
-                        SD_JSON_BUILD_PAIR_CONDITION(in_addr_is_set(rule->family, &rule->to),
-                                                     "ToPrefixLength", SD_JSON_BUILD_UNSIGNED(rule->to_prefixlen)),
+                        JSON_BUILD_PAIR_IN_ADDR_NON_NULL("FromPrefix", &rule->from.address, rule->family),
+                        SD_JSON_BUILD_PAIR_CONDITION(in_addr_is_set(rule->family, &rule->from.address),
+                                                     "FromPrefixLength", SD_JSON_BUILD_UNSIGNED(rule->from.prefixlen)),
+                        JSON_BUILD_PAIR_IN_ADDR_NON_NULL("ToPrefix", &rule->to.address, rule->family),
+                        SD_JSON_BUILD_PAIR_CONDITION(in_addr_is_set(rule->family, &rule->to.address),
+                                                     "ToPrefixLength", SD_JSON_BUILD_UNSIGNED(rule->to.prefixlen)),
                         SD_JSON_BUILD_PAIR_UNSIGNED("Protocol", rule->protocol),
                         SD_JSON_BUILD_PAIR_STRING("ProtocolString", protocol),
                         SD_JSON_BUILD_PAIR_UNSIGNED("TOS", rule->tos),
index 1f9e6eafc0ed482fe14b94fe92fb0da6a1a364a5..d91a15d085cd44f6babc3e66361cb569a6d32ba4 100644 (file)
@@ -177,12 +177,12 @@ Neighbor.Address,                            config_parse_neighbor_section,
 Neighbor.LinkLayerAddress,                   config_parse_neighbor_section,                            NEIGHBOR_LINK_LAYER_ADDRESS,   0
 Neighbor.MACAddress,                         config_parse_neighbor_section,                            NEIGHBOR_LINK_LAYER_ADDRESS,   0 /* deprecated */
 RoutingPolicyRule.TypeOfService,             config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_TOS,       0
-RoutingPolicyRule.Priority,                  config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_PRIORITY, 0
+RoutingPolicyRule.Priority,                  config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_PRIORITY,  0
 RoutingPolicyRule.GoTo,                      config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_GOTO,      0
 RoutingPolicyRule.Table,                     config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_TABLE,     0
 RoutingPolicyRule.FirewallMark,              config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_FWMARK,    0
-RoutingPolicyRule.From,                      config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_PREFIX,    0
-RoutingPolicyRule.To,                        config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_PREFIX,    0
+RoutingPolicyRule.From,                      config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_FROM,      0
+RoutingPolicyRule.To,                        config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_TO,        0
 RoutingPolicyRule.IncomingInterface,         config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_IIF,       0
 RoutingPolicyRule.OutgoingInterface,         config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_OIF,       0
 RoutingPolicyRule.IPProtocol,                config_parse_routing_policy_rule,                         ROUTING_POLICY_RULE_IP_PROTOCOL, 0
index c03493b7e0ba018cd92094c6a26b883b1edc826d..ec050e3a2d6d950bd1ee336699a1326fbf8dad3c 100644 (file)
@@ -215,12 +215,12 @@ static void routing_policy_rule_hash_func(const RoutingPolicyRule *rule, struct
         siphash24_compress_typesafe(rule->dport, state);
 
         /* See fib4_rule_compare() in net/ipv4/fib_rules.c, and fib6_rule_compare() in net/ipv6/fib6_rules.c. */
-        siphash24_compress_typesafe(rule->from_prefixlen, state);
-        siphash24_compress_typesafe(rule->to_prefixlen, state);
+        siphash24_compress_typesafe(rule->from.prefixlen, state);
+        siphash24_compress_typesafe(rule->to.prefixlen, state);
         siphash24_compress_typesafe(rule->tos, state);
         siphash24_compress_typesafe(rule->realms, state);
-        in_addr_hash_func(&rule->from, rule->family, state);
-        in_addr_hash_func(&rule->to, rule->family, state);
+        in_addr_hash_func(&rule->from.address, rule->family, state);
+        in_addr_hash_func(&rule->to.address, rule->family, state);
 }
 
 static int routing_policy_rule_compare_func_full(const RoutingPolicyRule *a, const RoutingPolicyRule *b, bool all) {
@@ -301,11 +301,11 @@ static int routing_policy_rule_compare_func_full(const RoutingPolicyRule *a, con
         if (r != 0)
                 return r;
 
-        r = CMP(a->from_prefixlen, b->from_prefixlen);
+        r = CMP(a->from.prefixlen, b->from.prefixlen);
         if (r != 0)
                 return r;
 
-        r = CMP(a->to_prefixlen, b->to_prefixlen);
+        r = CMP(a->to.prefixlen, b->to.prefixlen);
         if (r != 0)
                 return r;
 
@@ -318,11 +318,11 @@ static int routing_policy_rule_compare_func_full(const RoutingPolicyRule *a, con
                 return r;
 
         if (all) {
-                r = memcmp(&a->from, &b->from, FAMILY_ADDRESS_SIZE(a->family));
+                r = memcmp(&a->from.address, &b->from.address, FAMILY_ADDRESS_SIZE(a->family));
                 if (r != 0)
                         return r;
 
-                r = memcmp(&a->to, &b->to, FAMILY_ADDRESS_SIZE(a->family));
+                r = memcmp(&a->to.address, &b->to.address, FAMILY_ADDRESS_SIZE(a->family));
                 if (r != 0)
                         return r;
         }
@@ -544,8 +544,8 @@ static void log_routing_policy_rule_debug(const RoutingPolicyRule *rule, const c
                        "%s %s routing policy rule (%s): priority: %"PRIu32", %s -> %s, iif: %s, oif: %s, table: %s",
                        str, strna(network_config_source_to_string(rule->source)), strna(state),
                        rule->priority,
-                       IN_ADDR_PREFIX_TO_STRING(rule->family, &rule->from, rule->from_prefixlen),
-                       IN_ADDR_PREFIX_TO_STRING(rule->family, &rule->to, rule->to_prefixlen),
+                       IN_ADDR_PREFIX_TO_STRING(rule->family, &rule->from.address, rule->from.prefixlen),
+                       IN_ADDR_PREFIX_TO_STRING(rule->family, &rule->to.address, rule->to.prefixlen),
                        strna(rule->iif), strna(rule->oif), strna(table));
 }
 
@@ -555,22 +555,22 @@ static int routing_policy_rule_set_netlink_message(const RoutingPolicyRule *rule
         assert(rule);
         assert(m);
 
-        if (rule->from_prefixlen > 0) {
-                r = netlink_message_append_in_addr_union(m, FRA_SRC, rule->family, &rule->from);
+        if (rule->from.prefixlen > 0) {
+                r = netlink_message_append_in_addr_union(m, FRA_SRC, rule->family, &rule->from.address);
                 if (r < 0)
                         return r;
 
-                r = sd_rtnl_message_routing_policy_rule_set_src_prefixlen(m, rule->from_prefixlen);
+                r = sd_rtnl_message_routing_policy_rule_set_src_prefixlen(m, rule->from.prefixlen);
                 if (r < 0)
                         return r;
         }
 
-        if (rule->to_prefixlen > 0) {
-                r = netlink_message_append_in_addr_union(m, FRA_DST, rule->family, &rule->to);
+        if (rule->to.prefixlen > 0) {
+                r = netlink_message_append_in_addr_union(m, FRA_DST, rule->family, &rule->to.address);
                 if (r < 0)
                         return r;
 
-                r = sd_rtnl_message_routing_policy_rule_set_dst_prefixlen(m, rule->to_prefixlen);
+                r = sd_rtnl_message_routing_policy_rule_set_dst_prefixlen(m, rule->to.prefixlen);
                 if (r < 0)
                         return r;
         }
@@ -1100,24 +1100,24 @@ int manager_rtnl_process_rule(sd_netlink *rtnl, sd_netlink_message *message, Man
                 return 0;
         }
 
-        r = netlink_message_read_in_addr_union(message, FRA_SRC, tmp->family, &tmp->from);
+        r = netlink_message_read_in_addr_union(message, FRA_SRC, tmp->family, &tmp->from.address);
         if (r < 0 && r != -ENODATA) {
                 log_warning_errno(r, "rtnl: could not get FRA_SRC attribute, ignoring: %m");
                 return 0;
         } else if (r >= 0) {
-                r = sd_rtnl_message_routing_policy_rule_get_src_prefixlen(message, &tmp->from_prefixlen);
+                r = sd_rtnl_message_routing_policy_rule_get_src_prefixlen(message, &tmp->from.prefixlen);
                 if (r < 0) {
                         log_warning_errno(r, "rtnl: received rule message without valid source prefix length, ignoring: %m");
                         return 0;
                 }
         }
 
-        r = netlink_message_read_in_addr_union(message, FRA_DST, tmp->family, &tmp->to);
+        r = netlink_message_read_in_addr_union(message, FRA_DST, tmp->family, &tmp->to.address);
         if (r < 0 && r != -ENODATA) {
                 log_warning_errno(r, "rtnl: could not get FRA_DST attribute, ignoring: %m");
                 return 0;
         } else if (r >= 0) {
-                r = sd_rtnl_message_routing_policy_rule_get_dst_prefixlen(message, &tmp->to_prefixlen);
+                r = sd_rtnl_message_routing_policy_rule_get_dst_prefixlen(message, &tmp->to.prefixlen);
                 if (r < 0) {
                         log_warning_errno(r, "rtnl: received rule message without valid destination prefix length, ignoring: %m");
                         return 0;
@@ -1469,46 +1469,6 @@ static int config_parse_routing_policy_rule_fwmark(
         return 1;
 }
 
-static int config_parse_routing_policy_rule_prefix(
-                const char *unit,
-                const char *filename,
-                unsigned line,
-                const char *section,
-                unsigned section_line,
-                const char *lvalue,
-                int ltype,
-                const char *rvalue,
-                void *data,
-                void *userdata) {
-
-        RoutingPolicyRule *rule = ASSERT_PTR(userdata);
-        union in_addr_union *buffer;
-        uint8_t *prefixlen;
-        int r;
-
-        assert(rvalue);
-
-        if (streq_ptr(lvalue, "To")) {
-                buffer = &rule->to;
-                prefixlen = &rule->to_prefixlen;
-        } else if (streq_ptr(lvalue, "From")) {
-                buffer = &rule->from;
-                prefixlen = &rule->from_prefixlen;
-        } else
-                assert_not_reached();
-
-        if (rule->family == AF_UNSPEC)
-                r = in_addr_prefix_from_string_auto(rvalue, &rule->family, buffer, prefixlen);
-        else
-                r = in_addr_prefix_from_string(rvalue, rule->family, buffer, prefixlen);
-        if (r < 0) {
-                log_syntax(unit, LOG_WARNING, filename, line, r, "RPDB rule prefix is invalid, ignoring assignment: %s", rvalue);
-                return 0;
-        }
-
-        return 1;
-}
-
 static int config_parse_routing_policy_rule_port_range(
                 const char *unit,
                 const char *filename,
@@ -1662,7 +1622,8 @@ int config_parse_routing_policy_rule(
                 [ROUTING_POLICY_RULE_L3MDEV]             = { .parser = config_parse_bool,                           .ltype = 0,               .offset = offsetof(RoutingPolicyRule, l3mdev),             },
                 [ROUTING_POLICY_RULE_SPORT]              = { .parser = config_parse_routing_policy_rule_port_range, .ltype = 0,               .offset = offsetof(RoutingPolicyRule, sport),              },
                 [ROUTING_POLICY_RULE_DPORT]              = { .parser = config_parse_routing_policy_rule_port_range, .ltype = 0,               .offset = offsetof(RoutingPolicyRule, dport),              },
-                [ROUTING_POLICY_RULE_PREFIX]             = { .parser = config_parse_routing_policy_rule_prefix,     .ltype = 0,               .offset = 0,                                               },
+                [ROUTING_POLICY_RULE_FROM]               = { .parser = config_parse_in_addr_prefix,                 .ltype = 0,               .offset = offsetof(RoutingPolicyRule, from),               },
+                [ROUTING_POLICY_RULE_TO]                 = { .parser = config_parse_in_addr_prefix,                 .ltype = 0,               .offset = offsetof(RoutingPolicyRule, to),                 },
                 [ROUTING_POLICY_RULE_PRIORITY]           = { .parser = config_parse_routing_policy_rule_priority,   .ltype = 0,               .offset = 0,                                               },
                 [ROUTING_POLICY_RULE_SUPPRESS_IFGROUP]   = { .parser = config_parse_routing_policy_rule_suppress,   .ltype = INT32_MAX,       .offset = offsetof(RoutingPolicyRule, suppress_ifgroup),   },
                 [ROUTING_POLICY_RULE_SUPPRESS_PREFIXLEN] = { .parser = config_parse_routing_policy_rule_suppress,   .ltype = 128,             .offset = offsetof(RoutingPolicyRule, suppress_prefixlen), },
@@ -1707,6 +1668,12 @@ static int routing_policy_rule_section_verify(RoutingPolicyRule *rule) {
         if (section_is_invalid(rule->section))
                 return -EINVAL;
 
+        rule->family = rule->from.family;
+        if (rule->family == AF_UNSPEC)
+                rule->family = rule->to.family;
+        else if (rule->to.family != AF_UNSPEC && rule->to.family != rule->family)
+                return log_rule_section(rule, "From= and To= settings for routing policy rule contradict each other.");
+
         if ((rule->family == AF_INET && FLAGS_SET(rule->address_family, ADDRESS_FAMILY_IPV6)) ||
             (rule->family == AF_INET6 && FLAGS_SET(rule->address_family, ADDRESS_FAMILY_IPV4)))
                 return log_rule_section(rule, "Address family specified by Family= conflicts with To= and/or From=.");
index 443df39dd20f1f9451c53e8bccff5d5de013b5b3..3b106c11d3331993b6b3c31e694d5480ea02aefe 100644 (file)
@@ -6,7 +6,7 @@
 #include <stdbool.h>
 
 #include "conf-parser.h"
-#include "in-addr-util.h"
+#include "in-addr-prefix-util.h"
 #include "networkd-util.h"
 
 typedef struct Link Link;
@@ -23,17 +23,15 @@ typedef struct RoutingPolicyRule {
         unsigned n_ref;
 
         /* struct fib_rule_hdr */
-        AddressFamily address_family; /* Specified by Family= */
-        int family; /* Automatically determined by From= or To= */
-        uint8_t to_prefixlen;
-        uint8_t from_prefixlen;
+        AddressFamily address_family; /* Used when parsing Family= */
+        int family; /* Automatically determined by From=, To=, and Family= */
         uint8_t tos;
         uint8_t action;
         uint32_t flags;
 
         /* attributes */
-        union in_addr_union to; /* FRA_DST */
-        union in_addr_union from; /* FRA_SRC */
+        struct in_addr_prefix to; /* FRA_DST */
+        struct in_addr_prefix from; /* FRA_SRC */
         char *iif; /* FRA_IIFNAME */
         uint32_t priority_goto; /* FRA_GOTO */
         bool priority_set;
@@ -88,7 +86,8 @@ typedef enum RoutingPolicyRuleConfParserType {
         ROUTING_POLICY_RULE_L3MDEV,
         ROUTING_POLICY_RULE_SPORT,
         ROUTING_POLICY_RULE_DPORT,
-        ROUTING_POLICY_RULE_PREFIX,
+        ROUTING_POLICY_RULE_FROM,
+        ROUTING_POLICY_RULE_TO,
         ROUTING_POLICY_RULE_PRIORITY,
         ROUTING_POLICY_RULE_SUPPRESS_IFGROUP,
         ROUTING_POLICY_RULE_SUPPRESS_PREFIXLEN,