1 /* SPDX-License-Identifier: BSD-2-Clause */ 2 /* 3 * dhcpcd - DHCP client daemon 4 * Copyright (c) 2006-2021 Roy Marples <roy@marples.name> 5 * All rights reserved 6 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 17 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 19 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 20 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 22 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 24 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26 * SUCH DAMAGE. 27 */ 28 29 #ifndef DHCP6_H 30 #define DHCP6_H 31 32 #include "dhcpcd.h" 33 34 #define IN6ADDR_LINKLOCAL_ALLDHCP_INIT \ 35 {{{ 0xff, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, \ 36 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x02 }}} 37 38 /* UDP port numbers for DHCP */ 39 #define DHCP6_CLIENT_PORT 546 40 #define DHCP6_SERVER_PORT 547 41 42 /* DHCP message type */ 43 #define DHCP6_SOLICIT 1 44 #define DHCP6_ADVERTISE 2 45 #define DHCP6_REQUEST 3 46 #define DHCP6_CONFIRM 4 47 #define DHCP6_RENEW 5 48 #define DHCP6_REBIND 6 49 #define DHCP6_REPLY 7 50 #define DHCP6_RELEASE 8 51 #define DHCP6_DECLINE 9 52 #define DHCP6_RECONFIGURE 10 53 #define DHCP6_INFORMATION_REQ 11 54 #define DHCP6_RELAY_FLOW 12 55 #define DHCP6_RELAY_REPL 13 56 #define DHCP6_RECONFIGURE_REQ 18 57 #define DHCP6_RECONFIGURE_REPLY 19 58 59 #ifdef DHCP6 60 61 #define D6_OPTION_CLIENTID 1 62 #define D6_OPTION_SERVERID 2 63 #define D6_OPTION_IA_NA 3 64 #define D6_OPTION_IA_TA 4 65 #define D6_OPTION_ORO 6 66 #define D6_OPTION_IA_ADDR 5 67 #define D6_OPTION_PREFERENCE 7 68 #define D6_OPTION_ELAPSED 8 69 #define D6_OPTION_AUTH 11 70 #define D6_OPTION_UNICAST 12 71 #define D6_OPTION_STATUS_CODE 13 72 #define D6_OPTION_RAPID_COMMIT 14 73 #define D6_OPTION_USER_CLASS 15 74 #define D6_OPTION_VENDOR_CLASS 16 75 #define D6_OPTION_VENDOR_OPTS 17 76 #define D6_OPTION_INTERFACE_ID 18 77 #define D6_OPTION_RECONF_MSG 19 78 #define D6_OPTION_RECONF_ACCEPT 20 79 #define D6_OPTION_SIP_SERVERS_NAME 21 80 #define D6_OPTION_SIP_SERVERS_ADDRESS 22 81 #define D6_OPTION_DNS_SERVERS 23 82 #define D6_OPTION_DOMAIN_LIST 24 83 #define D6_OPTION_IA_PD 25 84 #define D6_OPTION_IAPREFIX 26 85 #define D6_OPTION_NIS_SERVERS 27 86 #define D6_OPTION_NISP_SERVERS 28 87 #define D6_OPTION_NIS_DOMAIN_NAME 29 88 #define D6_OPTION_NISP_DOMAIN_NAME 30 89 #define D6_OPTION_SNTP_SERVERS 31 90 #define D6_OPTION_INFO_REFRESH_TIME 32 91 #define D6_OPTION_BCMS_SERVER_D 33 92 #define D6_OPTION_BCMS_SERVER_A 34 93 #define D6_OPTION_FQDN 39 94 #define D6_OPTION_POSIX_TIMEZONE 41 95 #define D6_OPTION_TZDB_TIMEZONE 42 96 #define D6_OPTION_PD_EXCLUDE 67 97 #define D6_OPTION_SOL_MAX_RT 82 98 #define D6_OPTION_INF_MAX_RT 83 99 #define D6_OPTION_MUDURL 112 100 101 #define D6_FQDN_PTR 0x00 102 #define D6_FQDN_BOTH 0x01 103 #define D6_FQDN_NONE 0x04 104 105 #include "dhcp.h" 106 #include "ipv6.h" 107 108 #define D6_STATUS_OK 0 109 #define D6_STATUS_FAIL 1 110 #define D6_STATUS_NOADDR 2 111 #define D6_STATUS_NOBINDING 3 112 #define D6_STATUS_NOTONLINK 4 113 #define D6_STATUS_USEMULTICAST 5 114 115 #define SOL_MAX_DELAY 1 116 #define SOL_TIMEOUT 1 117 #define SOL_MAX_RT 3600 /* RFC7083 */ 118 #define SOL_MAX_RC 0 119 #define REQ_MAX_DELAY 0 120 #define REQ_TIMEOUT 1 121 #define REQ_MAX_RT 30 122 #define REQ_MAX_RC 10 123 #define CNF_MAX_DELAY 1 124 #define CNF_TIMEOUT 1 125 #define CNF_MAX_RT 4 126 #define CNF_MAX_RC 0 127 #define CNF_MAX_RD 10 128 #define REN_MAX_DELAY 0 129 #define REN_TIMEOUT 10 130 #define REN_MAX_RT 600 131 #define REB_MAX_DELAY 0 132 #define REB_TIMEOUT 10 133 #define REB_MAX_RT 600 134 #define INF_MAX_DELAY 1 135 #define INF_TIMEOUT 1 136 #define INF_MAX_RD CNF_MAX_RD /* NOT RFC defined */ 137 #define INF_MAX_RT 3600 /* RFC7083 */ 138 #define REL_MAX_DELAY 0 139 #define REL_TIMEOUT 1 140 #define REL_MAX_RT 0 141 #define REL_MAX_RC 5 142 #define DEC_MAX_DELAY 0 143 #define DEC_TIMEOUT 1 144 #define DEC_MAX_RC 5 145 #define REC_MAX_DELAY 0 146 #define REC_TIMEOUT 2 147 #define REC_MAX_RC 8 148 #define HOP_COUNT_LIMIT 32 149 150 /* RFC4242 3.1 */ 151 #define IRT_DEFAULT 86400 152 #define IRT_MINIMUM 600 153 154 /* These should give -.1 to .1 randomness */ 155 #define DHCP6_RAND_MIN -100 156 #define DHCP6_RAND_MAX 100 157 #define DHCP6_RAND_DIV 1000.0f 158 159 enum DH6S { 160 DH6S_INIT, 161 DH6S_DISCOVER, 162 DH6S_REQUEST, 163 DH6S_BOUND, 164 DH6S_RENEW, 165 DH6S_REBIND, 166 DH6S_CONFIRM, 167 DH6S_INFORM, 168 DH6S_INFORMED, 169 DH6S_RENEW_REQUESTED, 170 DH6S_PROBE, 171 DH6S_DECLINE, 172 DH6S_DELEGATED, 173 DH6S_RELEASE, 174 DH6S_RELEASED, 175 }; 176 177 struct dhcp6_state { 178 enum DH6S state; 179 struct timespec started; 180 181 /* Message retransmission timings in seconds */ 182 unsigned int IMD; 183 unsigned int RTC; 184 unsigned int IRT; 185 unsigned int MRC; 186 unsigned int MRT; 187 void (*MRCcallback)(void *); 188 unsigned int sol_max_rt; 189 unsigned int inf_max_rt; 190 unsigned int RT; /* retransmission timer in milliseconds 191 * maximal RT is 1 day + RAND, 192 * so should be enough */ 193 194 struct dhcp6_message *send; 195 size_t send_len; 196 struct dhcp6_message *recv; 197 size_t recv_len; 198 struct dhcp6_message *new; 199 size_t new_len; 200 struct dhcp6_message *old; 201 size_t old_len; 202 203 struct timespec acquired; 204 uint32_t renew; 205 uint32_t rebind; 206 uint32_t expire; 207 struct in6_addr unicast; 208 struct ipv6_addrhead addrs; 209 uint32_t lowpl; 210 /* The +3 is for the possible .pd extension for prefix delegation */ 211 char leasefile[sizeof(LEASEFILE6) + IF_NAMESIZE + (IF_SSIDLEN * 4) +3]; 212 const char *reason; 213 uint16_t lerror; /* Last error received from DHCPv6 reply. */ 214 bool has_no_binding; 215 bool failed; /* Entered the failed state - used to rate limit log. */ 216 bool new_start; /* New external start, to determine log type. */ 217 #ifdef AUTH 218 struct authstate auth; 219 #endif 220 }; 221 222 #define D6_STATE(ifp) \ 223 ((struct dhcp6_state *)(ifp)->if_data[IF_DATA_DHCP6]) 224 #define D6_CSTATE(ifp) \ 225 ((const struct dhcp6_state *)(ifp)->if_data[IF_DATA_DHCP6]) 226 #define D6_STATE_RUNNING(ifp) \ 227 (D6_CSTATE((ifp)) && \ 228 D6_CSTATE((ifp))->reason && dhcp6_dadcompleted((ifp))) 229 230 int dhcp6_openraw(void); 231 int dhcp6_openudp(unsigned int, struct in6_addr *); 232 void dhcp6_recvmsg(struct dhcpcd_ctx *, struct msghdr *, struct ipv6_addr *); 233 void dhcp6_printoptions(const struct dhcpcd_ctx *, 234 const struct dhcp_opt *, size_t); 235 const struct ipv6_addr *dhcp6_iffindaddr(const struct interface *ifp, 236 const struct in6_addr *addr, unsigned int flags); 237 struct ipv6_addr *dhcp6_findaddr(struct dhcpcd_ctx *, const struct in6_addr *, 238 unsigned int); 239 size_t dhcp6_find_delegates(struct interface *); 240 int dhcp6_start(struct interface *, enum DH6S); 241 void dhcp6_reboot(struct interface *); 242 void dhcp6_renew(struct interface *); 243 ssize_t dhcp6_env(FILE *, const char *, const struct interface *, 244 const struct dhcp6_message *, size_t); 245 void dhcp6_free(struct interface *); 246 void dhcp6_handleifa(int, struct ipv6_addr *, pid_t); 247 bool dhcp6_dadcompleted(const struct interface *); 248 void dhcp6_abort(struct interface *); 249 void dhcp6_drop(struct interface *, const char *); 250 int dhcp6_dump(struct interface *); 251 #endif /* DHCP6 */ 252 253 #endif /* DHCP6_H */ 254