1 /* 2 * dhcpcd - DHCP client daemon 3 * Copyright (c) 2006-2018 Roy Marples <roy@marples.name> 4 * All rights reserved 5 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 16 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 18 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 19 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 20 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 21 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 23 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 24 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 25 * SUCH DAMAGE. 26 */ 27 28 #ifndef DHCPCD_H 29 #define DHCPCD_H 30 31 #include <sys/socket.h> 32 #include <net/if.h> 33 34 #include "config.h" 35 #ifdef HAVE_SYS_QUEUE_H 36 #include <sys/queue.h> 37 #endif 38 39 #include "defs.h" 40 #include "control.h" 41 #include "if-options.h" 42 43 #define HWADDR_LEN 20 44 #define IF_SSIDLEN 32 45 #define PROFILE_LEN 64 46 #define SECRET_LEN 64 47 48 #define IF_INACTIVE 0 49 #define IF_ACTIVE 1 50 #define IF_ACTIVE_USER 2 51 52 #define LINK_UP 1 53 #define LINK_UNKNOWN 0 54 #define LINK_DOWN -1 55 56 #define IF_DATA_IPV4 0 57 #define IF_DATA_ARP 1 58 #define IF_DATA_IPV4LL 2 59 #define IF_DATA_DHCP 3 60 #define IF_DATA_IPV6 4 61 #define IF_DATA_IPV6ND 5 62 #define IF_DATA_DHCP6 6 63 #define IF_DATA_MAX 7 64 65 /* If the interface does not support carrier status (ie PPP), 66 * dhcpcd can poll it for the relevant flags periodically */ 67 #define IF_POLL_UP 100 /* milliseconds */ 68 69 #ifdef __QNX__ 70 /* QNX carries defines for, but does not actually support PF_LINK */ 71 #undef IFLR_ACTIVE 72 #endif 73 74 struct interface { 75 struct dhcpcd_ctx *ctx; 76 TAILQ_ENTRY(interface) next; 77 char name[IF_NAMESIZE]; 78 unsigned int index; 79 unsigned int active; 80 unsigned int flags; 81 sa_family_t family; 82 unsigned char hwaddr[HWADDR_LEN]; 83 uint8_t hwlen; 84 unsigned short vlanid; 85 unsigned int metric; 86 int carrier; 87 int wireless; 88 uint8_t ssid[IF_SSIDLEN + 1]; /* NULL terminated */ 89 unsigned int ssid_len; 90 91 char profile[PROFILE_LEN]; 92 struct if_options *options; 93 void *if_data[IF_DATA_MAX]; 94 }; 95 TAILQ_HEAD(if_head, interface); 96 97 98 #ifdef INET6 99 /* dhcpcd requires CMSG_SPACE to evaluate to a compile time constant. */ 100 #if defined(__QNX) || \ 101 (defined(__NetBSD_Version__) && __NetBSD_Version__ < 600000000) 102 #undef CMSG_SPACE 103 #endif 104 105 #ifndef ALIGNBYTES 106 #define ALIGNBYTES (sizeof(int) - 1) 107 #endif 108 #ifndef ALIGN 109 #define ALIGN(p) (((unsigned int)(p) + ALIGNBYTES) & ~ALIGNBYTES) 110 #endif 111 #ifndef CMSG_SPACE 112 #define CMSG_SPACE(len) (ALIGN(sizeof(struct cmsghdr)) + ALIGN(len)) 113 #endif 114 115 #define IP6BUFLEN (CMSG_SPACE(sizeof(struct in6_pktinfo)) + \ 116 CMSG_SPACE(sizeof(int))) 117 #endif 118 119 struct dhcpcd_ctx { 120 char pidfile[sizeof(PIDFILE) + IF_NAMESIZE + 1]; 121 const char *cffile; 122 unsigned long long options; 123 char *logfile; 124 int argc; 125 char **argv; 126 int ifac; /* allowed interfaces */ 127 char **ifav; /* allowed interfaces */ 128 int ifdc; /* denied interfaces */ 129 char **ifdv; /* denied interfaces */ 130 int ifc; /* listed interfaces */ 131 char **ifv; /* listed interfaces */ 132 int ifcc; /* configured interfaces */ 133 char **ifcv; /* configured interfaces */ 134 unsigned char *duid; 135 size_t duid_len; 136 struct if_head *ifaces; 137 138 struct rt_head routes; /* our routes */ 139 struct rt_head kroutes; /* all kernel routes */ 140 struct rt_head froutes; /* free routes for re-use */ 141 142 int pf_inet_fd; 143 #ifdef IFLR_ACTIVE 144 int pf_link_fd; 145 #endif 146 void *priv; 147 int link_fd; 148 int seq; /* route message sequence no */ 149 int sseq; /* successful seq no sent */ 150 struct iovec iov[1]; /* generic iovec buffer */ 151 152 #ifdef USE_SIGNALS 153 sigset_t sigset; 154 #endif 155 struct eloop *eloop; 156 157 int control_fd; 158 int control_unpriv_fd; 159 struct fd_list_head control_fds; 160 char control_sock[sizeof(CONTROLSOCKET) + IF_NAMESIZE]; 161 gid_t control_group; 162 163 /* DHCP Enterprise options, RFC3925 */ 164 struct dhcp_opt *vivso; 165 size_t vivso_len; 166 167 char *randomstate; /* original state */ 168 169 /* Used to track the last routing message, 170 * so we can ignore messages the parent process sent 171 * but the child receives when forking. 172 * getppid(2) is unreliable because we detach. */ 173 pid_t ppid; /* parent pid */ 174 int pseq; /* last seq in parent */ 175 176 #ifdef INET 177 struct dhcp_opt *dhcp_opts; 178 size_t dhcp_opts_len; 179 180 int udp_fd; 181 182 /* Our aggregate option buffer. 183 * We ONLY use this when options are split, which for most purposes is 184 * practically never. See RFC3396 for details. */ 185 uint8_t *opt_buffer; 186 size_t opt_buffer_len; 187 #endif 188 #ifdef INET6 189 uint8_t *secret; 190 size_t secret_len; 191 192 unsigned char ctlbuf[IP6BUFLEN]; 193 struct sockaddr_in6 from; 194 struct msghdr sndhdr; 195 struct iovec sndiov[1]; 196 unsigned char sndbuf[CMSG_SPACE(sizeof(struct in6_pktinfo))]; 197 struct msghdr rcvhdr; 198 char ntopbuf[INET6_ADDRSTRLEN]; 199 const char *sfrom; 200 201 int nd_fd; 202 struct ra_head *ra_routers; 203 204 int dhcp6_fd; 205 206 struct dhcp_opt *nd_opts; 207 size_t nd_opts_len; 208 struct dhcp_opt *dhcp6_opts; 209 size_t dhcp6_opts_len; 210 211 #ifndef __linux__ 212 int ra_global; 213 #endif 214 #endif /* INET6 */ 215 216 #ifdef PLUGIN_DEV 217 char *dev_load; 218 int dev_fd; 219 struct dev *dev; 220 void *dev_handle; 221 #endif 222 }; 223 224 #ifdef USE_SIGNALS 225 extern const int dhcpcd_signals[]; 226 extern const size_t dhcpcd_signals_len; 227 #endif 228 229 int dhcpcd_ifafwaiting(const struct interface *); 230 int dhcpcd_afwaiting(const struct dhcpcd_ctx *); 231 pid_t dhcpcd_daemonise(struct dhcpcd_ctx *); 232 233 void dhcpcd_linkoverflow(struct dhcpcd_ctx *); 234 int dhcpcd_handleargs(struct dhcpcd_ctx *, struct fd_list *, int, char **); 235 void dhcpcd_handlecarrier(struct dhcpcd_ctx *, int, unsigned int, const char *); 236 int dhcpcd_handleinterface(void *, int, const char *); 237 void dhcpcd_handlehwaddr(struct dhcpcd_ctx *, const char *, 238 const void *, uint8_t); 239 void dhcpcd_dropinterface(struct interface *, const char *); 240 int dhcpcd_selectprofile(struct interface *, const char *); 241 242 void dhcpcd_startinterface(void *); 243 void dhcpcd_activateinterface(struct interface *, unsigned long long); 244 245 #endif 246