1 /* SPDX-License-Identifier: LGPL-2.1-or-later */
2 #pragma once
3
4 #include <inttypes.h>
5 #include <stdbool.h>
6 #include <stdio.h>
7
8 #include "sd-ipv4acd.h"
9
10 #include "conf-parser.h"
11 #include "in-addr-util.h"
12 #include "networkd-link.h"
13 #include "networkd-util.h"
14 #include "time-util.h"
15
16 typedef struct Address Address;
17 typedef struct Manager Manager;
18 typedef struct Network Network;
19 typedef struct Request Request;
20 typedef int (*address_ready_callback_t)(Address *address);
21 typedef int (*address_netlink_handler_t)(
22 sd_netlink *rtnl,
23 sd_netlink_message *m,
24 Request *req,
25 Link *link,
26 Address *address);
27
28 struct Address {
29 Link *link;
30 Network *network;
31 ConfigSection *section;
32 NetworkConfigSource source;
33 NetworkConfigState state;
34 union in_addr_union provider; /* DHCP server or router address */
35
36 int family;
37 unsigned char prefixlen;
38 unsigned char scope;
39 uint32_t flags;
40 uint32_t route_metric; /* route metric for prefix route */
41 char *label;
42
43 int set_broadcast;
44 struct in_addr broadcast;
45
46 union in_addr_union in_addr;
47 union in_addr_union in_addr_peer;
48
49 /* These are absolute points in time, and NOT timespans/durations.
50 * Must be specified with clock_boottime_or_monotonic(). */
51 usec_t lifetime_valid_usec;
52 usec_t lifetime_preferred_usec;
53
54 bool scope_set:1;
55 bool ip_masquerade_done:1;
56
57 /* duplicate_address_detection is only used by static or IPv4 dynamic addresses.
58 * To control DAD for IPv6 dynamic addresses, set IFA_F_NODAD to flags. */
59 AddressFamily duplicate_address_detection;
60 sd_ipv4acd *acd;
61
62 /* Called when address become ready */
63 address_ready_callback_t callback;
64 };
65
66 const char* format_lifetime(char *buf, size_t l, usec_t lifetime_usec) _warn_unused_result_;
67 /* Note: the lifetime of the compound literal is the immediately surrounding block,
68 * see C11 §6.5.2.5, and
69 * https://stackoverflow.com/questions/34880638/compound-literal-lifetime-and-if-blocks */
70 #define FORMAT_LIFETIME(lifetime) \
71 format_lifetime((char[FORMAT_TIMESPAN_MAX+STRLEN("for ")]){}, FORMAT_TIMESPAN_MAX+STRLEN("for "), lifetime)
72
73 int address_flags_to_string_alloc(uint32_t flags, int family, char **ret);
74
75 int address_new(Address **ret);
76 Address* address_free(Address *address);
77 int address_get(Link *link, const Address *in, Address **ret);
78 int address_configure_handler_internal(sd_netlink *rtnl, sd_netlink_message *m, Link *link, const char *error_msg);
79 int address_remove(Address *address);
80 int address_dup(const Address *src, Address **ret);
81 bool address_is_ready(const Address *a);
82 void address_set_broadcast(Address *a, Link *link);
83
84 DEFINE_SECTION_CLEANUP_FUNCTIONS(Address, address_free);
85
86 int link_drop_managed_addresses(Link *link);
87 int link_drop_foreign_addresses(Link *link);
88 int link_drop_ipv6ll_addresses(Link *link);
89 void link_foreignize_addresses(Link *link);
90 bool link_address_is_dynamic(const Link *link, const Address *address);
91 int link_get_address(Link *link, int family, const union in_addr_union *address, unsigned char prefixlen, Address **ret);
link_get_ipv6_address(Link * link,const struct in6_addr * address,unsigned char prefixlen,Address ** ret)92 static inline int link_get_ipv6_address(Link *link, const struct in6_addr *address, unsigned char prefixlen, Address **ret) {
93 assert(address);
94 return link_get_address(link, AF_INET6, &(union in_addr_union) { .in6 = *address }, prefixlen, ret);
95 }
link_get_ipv4_address(Link * link,const struct in_addr * address,unsigned char prefixlen,Address ** ret)96 static inline int link_get_ipv4_address(Link *link, const struct in_addr *address, unsigned char prefixlen, Address **ret) {
97 assert(address);
98 return link_get_address(link, AF_INET, &(union in_addr_union) { .in = *address }, prefixlen, ret);
99 }
100 int manager_get_address(Manager *manager, int family, const union in_addr_union *address, unsigned char prefixlen, Address **ret);
101 bool manager_has_address(Manager *manager, int family, const union in_addr_union *address, bool check_ready);
102
103 void address_cancel_request(Address *address);
104 int link_request_address(
105 Link *link,
106 Address *address,
107 bool consume_object,
108 unsigned *message_counter,
109 address_netlink_handler_t netlink_handler,
110 Request **ret);
111 int link_request_static_address(Link *link, Address *address, bool consume);
112 int link_request_static_addresses(Link *link);
113
114 int manager_rtnl_process_address(sd_netlink *nl, sd_netlink_message *message, Manager *m);
115
116 int network_drop_invalid_addresses(Network *network);
117
118 int address_compare_func(const Address *a1, const Address *a2);
119
120 DEFINE_NETWORK_CONFIG_STATE_FUNCTIONS(Address, address);
address_enter_probing(Address * address)121 static inline void address_enter_probing(Address *address) {
122 address_update_state(address, NETWORK_CONFIG_STATE_PROBING, NETWORK_CONFIG_STATE_PROBING);
123 }
address_cancel_probing(Address * address)124 static inline void address_cancel_probing(Address *address) {
125 address_update_state(address, NETWORK_CONFIG_STATE_PROBING, 0);
126 }
127
128 void link_mark_addresses(Link *link, NetworkConfigSource source, const struct in6_addr *router);
129
130 CONFIG_PARSER_PROTOTYPE(config_parse_address);
131 CONFIG_PARSER_PROTOTYPE(config_parse_broadcast);
132 CONFIG_PARSER_PROTOTYPE(config_parse_label);
133 CONFIG_PARSER_PROTOTYPE(config_parse_lifetime);
134 CONFIG_PARSER_PROTOTYPE(config_parse_address_flags);
135 CONFIG_PARSER_PROTOTYPE(config_parse_address_scope);
136 CONFIG_PARSER_PROTOTYPE(config_parse_address_route_metric);
137 CONFIG_PARSER_PROTOTYPE(config_parse_duplicate_address_detection);
138