1 /* SPDX-License-Identifier: LGPL-2.1-or-later */
4 #include "conf-parser.h"
5 #include "networkd-util.h"
6 #include "parse-util.h"
7 #include "string-table.h"
8 #include "string-util.h"
11 static const char* const address_family_table
[_ADDRESS_FAMILY_MAX
] = {
12 [ADDRESS_FAMILY_NO
] = "no",
13 [ADDRESS_FAMILY_YES
] = "yes",
14 [ADDRESS_FAMILY_IPV4
] = "ipv4",
15 [ADDRESS_FAMILY_IPV6
] = "ipv6",
18 static const char* const routing_policy_rule_address_family_table
[_ADDRESS_FAMILY_MAX
] = {
19 [ADDRESS_FAMILY_YES
] = "both",
20 [ADDRESS_FAMILY_IPV4
] = "ipv4",
21 [ADDRESS_FAMILY_IPV6
] = "ipv6",
24 static const char* const duplicate_address_detection_address_family_table
[_ADDRESS_FAMILY_MAX
] = {
25 [ADDRESS_FAMILY_NO
] = "none",
26 [ADDRESS_FAMILY_YES
] = "both",
27 [ADDRESS_FAMILY_IPV4
] = "ipv4",
28 [ADDRESS_FAMILY_IPV6
] = "ipv6",
31 static const char* const dhcp_deprecated_address_family_table
[_ADDRESS_FAMILY_MAX
] = {
32 [ADDRESS_FAMILY_NO
] = "none",
33 [ADDRESS_FAMILY_YES
] = "both",
34 [ADDRESS_FAMILY_IPV4
] = "v4",
35 [ADDRESS_FAMILY_IPV6
] = "v6",
38 static const char* const dhcp_lease_server_type_table
[_SD_DHCP_LEASE_SERVER_TYPE_MAX
] = {
39 [SD_DHCP_LEASE_DNS
] = "DNS servers",
40 [SD_DHCP_LEASE_NTP
] = "NTP servers",
41 [SD_DHCP_LEASE_SIP
] = "SIP servers",
42 [SD_DHCP_LEASE_POP3
] = "POP3 servers",
43 [SD_DHCP_LEASE_SMTP
] = "SMTP servers",
44 [SD_DHCP_LEASE_LPR
] = "LPR servers",
47 DEFINE_STRING_TABLE_LOOKUP_WITH_BOOLEAN(address_family
, AddressFamily
, ADDRESS_FAMILY_YES
);
49 AddressFamily
link_local_address_family_from_string(const char *s
) {
50 if (streq_ptr(s
, "fallback")) /* compat name */
51 return ADDRESS_FAMILY_YES
;
52 if (streq_ptr(s
, "fallback-ipv4")) /* compat name */
53 return ADDRESS_FAMILY_IPV4
;
54 return address_family_from_string(s
);
57 DEFINE_STRING_TABLE_LOOKUP(routing_policy_rule_address_family
, AddressFamily
);
58 DEFINE_STRING_TABLE_LOOKUP(duplicate_address_detection_address_family
, AddressFamily
);
59 DEFINE_CONFIG_PARSE_ENUM(config_parse_link_local_address_family
, link_local_address_family
,
60 AddressFamily
, "Failed to parse option");
61 DEFINE_STRING_TABLE_LOOKUP_FROM_STRING(dhcp_deprecated_address_family
, AddressFamily
);
62 DEFINE_STRING_TABLE_LOOKUP(dhcp_lease_server_type
, sd_dhcp_lease_server_type
);
64 static AddressFamily
address_family_compat_from_string(const char *s
) {
65 if (streq_ptr(s
, "yes")) /* compat name */
66 return ADDRESS_FAMILY_IPV4
;
67 if (streq_ptr(s
, "both"))
68 return ADDRESS_FAMILY_YES
;
69 return address_family_from_string(s
);
71 DEFINE_CONFIG_PARSE_ENUM(config_parse_address_family_compat
, address_family_compat
,
72 AddressFamily
, "Failed to parse option");
74 int config_parse_address_family_with_kernel(
79 unsigned section_line
,
86 AddressFamily
*fwd
= data
, s
;
93 /* This function is mostly obsolete now. It simply redirects
94 * "kernel" to "no". In older networkd versions we used to
95 * distinguish IPForward=off from IPForward=kernel, where the
96 * former would explicitly turn off forwarding while the
97 * latter would simply not touch the setting. But that logic
98 * is gone, hence silently accept the old setting, but turn it
101 s
= address_family_from_string(rvalue
);
103 if (streq(rvalue
, "kernel"))
104 s
= ADDRESS_FAMILY_NO
;
106 log_syntax(unit
, LOG_WARNING
, filename
, line
, 0, "Failed to parse IPForward= option, ignoring: %s", rvalue
);
116 /* Router lifetime can be set with netlink interface since kernel >= 4.5
117 * so for the supported kernel we don't need to expire routes in userspace */
118 int kernel_route_expiration_supported(void) {
119 static int cached
= -1;
124 .type
= CONDITION_KERNEL_VERSION
,
125 .parameter
= (char *) ">= 4.5"
127 r
= condition_test(&c
, NULL
);
136 static void network_config_hash_func(const NetworkConfigSection
*c
, struct siphash
*state
) {
137 siphash24_compress_string(c
->filename
, state
);
138 siphash24_compress(&c
->line
, sizeof(c
->line
), state
);
141 static int network_config_compare_func(const NetworkConfigSection
*x
, const NetworkConfigSection
*y
) {
144 r
= strcmp(x
->filename
, y
->filename
);
148 return CMP(x
->line
, y
->line
);
151 DEFINE_HASH_OPS(network_config_hash_ops
, NetworkConfigSection
, network_config_hash_func
, network_config_compare_func
);
153 int network_config_section_new(const char *filename
, unsigned line
, NetworkConfigSection
**s
) {
154 NetworkConfigSection
*cs
;
156 cs
= malloc0(offsetof(NetworkConfigSection
, filename
) + strlen(filename
) + 1);
160 strcpy(cs
->filename
, filename
);
168 unsigned hashmap_find_free_section_line(Hashmap
*hashmap
) {
169 NetworkConfigSection
*cs
;
173 HASHMAP_FOREACH_KEY(entry
, cs
, hashmap
)