1 /** 2 * Copyright (C) 2012-2014 Steven Barth <steven@midlink.org> 3 * Copyright (C) 2018 Hans Dedecker <dedeckeh@gmail.com> 4 * 5 * This program is free software; you can redistribute it and/or modify 6 * it under the terms of the GNU General Public License v2 as published by 7 * the Free Software Foundation. 8 * 9 * This program is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 * GNU General Public License for more details. 13 * 14 */ 15 16 #ifndef _ODHCP6C_H_ 17 #define _ODHCP6C_H_ 18 19 #include <netinet/in.h> 20 #include <stdbool.h> 21 #include <stdint.h> 22 #include <syslog.h> 23 24 #ifndef _o_aligned 25 #define _o_aligned(n) __attribute__((aligned(n))) 26 #endif /* _o_aligned */ 27 28 #ifndef _o_fallthrough 29 #define _o_fallthrough __attribute__((__fallthrough__)) 30 #endif /* _o_fallthrough */ 31 32 #ifndef _o_packed 33 #define _o_packed __attribute__((packed)) 34 #endif /* _o_packed */ 35 36 #ifndef _o_unused 37 #define _o_unused __attribute__((unused)) 38 #endif /* _o_unused */ 39 40 #define ARRAY_SIZE(arr) (sizeof(arr) / sizeof((arr)[0])) 41 42 void __iflog(int lvl, const char *fmt, ...); 43 #define debug(fmt, ...) __iflog(LOG_DEBUG, fmt __VA_OPT__(, ) __VA_ARGS__) 44 #define info(fmt, ...) __iflog(LOG_INFO, fmt __VA_OPT__(, ) __VA_ARGS__) 45 #define notice(fmt, ...) __iflog(LOG_NOTICE, fmt __VA_OPT__(, ) __VA_ARGS__) 46 #define warn(fmt, ...) __iflog(LOG_WARNING, fmt __VA_OPT__(, ) __VA_ARGS__) 47 #define error(fmt, ...) __iflog(LOG_ERR, fmt __VA_OPT__(, ) __VA_ARGS__) 48 #define critical(fmt, ...) __iflog(LOG_CRIT, fmt __VA_OPT__(, ) __VA_ARGS__) 49 #define alert(fmt, ...) __iflog(LOG_ALERT, fmt __VA_OPT__(, ) __VA_ARGS__) 50 #define emergency(fmt, ...) __iflog(LOG_EMERG, fmt __VA_OPT__(, ) __VA_ARGS__) 51 52 #define ND_OPT_RECURSIVE_DNS 25 53 #define ND_OPT_DNSSL 31 54 55 #define DHCPV6_MAX_DELAY 1 56 #define DHCPV6_IRT_DEFAULT 86400 57 #define DHCPV6_IRT_MIN 600 58 #define DHCPV6_RAND_FACTOR 100 59 60 #define DHCPV6_SOL_INIT_RT 1 61 #define DHCPV6_SOL_MAX_RT 120 62 63 #define DHCPV6_REQ_INIT_RT 1 64 #define DHCPV6_REQ_MAX_RT 30 65 #define DHCPV6_REQ_MAX_RC 10 66 67 #define DHCPV6_REN_INIT_RT 10 68 #define DHCPV6_REN_MAX_RT 600 69 70 #define DHCPV6_REB_INIT_RT 10 71 #define DHCPV6_REB_MAX_RT 600 72 73 #define DHCPV6_INF_INIT_RT 1 74 #define DHCPV6_INF_MAX_RT 3600 75 76 #define DHCPV6_REL_INIT_RT 1 77 #define DHCPV6_REL_MAX_RC 4 78 79 #define DHCPV6_DEC_INIT_RT 1 80 #define DHCPV6_DEC_MAX_RC 4 81 82 #define DHCPV6_IFACEID_EUI64 "eui64" 83 #define DHCPV6_IFACEID_RANDOM "random" 84 85 #define RA_MIN_ADV_INTERVAL 3 /* RFC 4861 paragraph 6.2.1 */ 86 87 /* RFC8910 §2 */ 88 static const uint8_t URN_IETF_CAPT_PORT_UNRESTR[] = "urn:ietf:params:capport:unrestricted"; 89 #define CAPT_PORT_URI_STR "CAPTIVE_PORTAL_URI" 90 91 enum dhcvp6_opt { 92 /* RFC8415(bis) */ 93 DHCPV6_OPT_CLIENTID = 1, 94 DHCPV6_OPT_SERVERID = 2, 95 DHCPV6_OPT_IA_NA = 3, 96 DHCPV6_OPT_IA_TA = 4, 97 DHCPV6_OPT_IA_ADDR = 5, 98 DHCPV6_OPT_ORO = 6, 99 DHCPV6_OPT_PREF = 7, 100 DHCPV6_OPT_ELAPSED = 8, 101 DHCPV6_OPT_RELAY_MSG = 9, 102 DHCPV6_OPT_AUTH = 11, 103 DHCPV6_OPT_UNICAST = 12, 104 DHCPV6_OPT_STATUS = 13, 105 DHCPV6_OPT_RAPID_COMMIT = 14, 106 DHCPV6_OPT_USER_CLASS = 15, 107 DHCPV6_OPT_VENDOR_CLASS = 16, 108 DHCPV6_OPT_INTERFACE_ID = 18, 109 DHCPV6_OPT_RECONF_MESSAGE = 19, 110 DHCPV6_OPT_RECONF_ACCEPT = 20, 111 /* RFC3319 */ 112 DHCPV6_OPT_SIP_SERVER_D = 21, 113 DHCPV6_OPT_SIP_SERVER_A = 22, 114 /* RFC3646 */ 115 DHCPV6_OPT_DNS_SERVERS = 23, 116 DHCPV6_OPT_DNS_DOMAIN = 24, 117 /* RFC8415(bis) */ 118 DHCPV6_OPT_IA_PD = 25, 119 DHCPV6_OPT_IA_PREFIX = 26, 120 /* RFC4075 */ 121 DHCPV6_OPT_SNTP_SERVERS = 31, 122 /* RFC4242 */ 123 DHCPV6_OPT_INFO_REFRESH = 32, 124 /* RFC4649 */ 125 DHCPV6_OPT_REMOTE_ID = 37, 126 /* RFC4580 */ 127 DHCPV6_OPT_SUBSCRIBER_ID = 38, 128 /* RFC4704 */ 129 DHCPV6_OPT_FQDN = 39, 130 /* RFC4994 */ 131 DHCPV6_OPT_ERO = 43, 132 /* RFC5007 */ 133 DHCPV6_OPT_LQ_QUERY = 44, 134 DHCPV6_OPT_CLIENT_DATA = 45, 135 DHCPV6_OPT_CLT_TIME = 46, 136 DHCPV6_OPT_LQ_RELAY_DATA = 47, 137 DHCPV6_OPT_LQ_CLIENT_LINK = 48, 138 /* RFC5460 */ 139 DHCPV6_OPT_RELAY_ID = 53, 140 /* RFC5908 */ 141 DHCPV6_OPT_NTP_SERVER = 56, 142 /* RFC5970 */ 143 DHCPV6_OPT_CLIENT_ARCH_TYPE = 61, 144 /* RFC6334 */ 145 DHCPV6_OPT_AFTR_NAME = 64, 146 /* RFC6422 */ 147 DHCPV6_OPT_RSOO = 66, 148 /* RFC6603 */ 149 DHCPV6_OPT_PD_EXCLUDE = 67, 150 /* RFC6607 */ 151 DHCPV6_OPT_VSS = 68, 152 /* RFC6939 */ 153 DHCPV6_OPT_LINK_LAYER_ADDRESS = 79, 154 /* RFC6977 */ 155 DHCPV6_OPT_LINK_ADDRESS = 80, 156 /* RFC7037 */ 157 DHCPV6_OPT_RADIUS = 81, 158 /* RFC8415(bis) */ 159 DHCPV6_OPT_SOL_MAX_RT = 82, 160 DHCPV6_OPT_INF_MAX_RT = 83, 161 /* RFC8415(bis) */ 162 DHCPV6_OPT_DHCPV4_MSG = 87, 163 /* RFC7598 */ 164 DHCPV6_OPT_S46_RULE = 89, 165 DHCPV6_OPT_S46_BR = 90, /* & RFC8539 */ 166 DHCPV6_OPT_S46_DMR = 91, 167 DHCPV6_OPT_S46_V4V6BIND = 92, 168 DHCPV6_OPT_S46_PORTPARAMS = 93, 169 DHCPV6_OPT_S46_CONT_MAPE = 94, 170 DHCPV6_OPT_S46_CONT_MAPT = 95, 171 DHCPV6_OPT_S46_CONT_LW = 96, 172 /* RFC7653 */ 173 DHCPV6_OPT_LQ_BASE_TIME = 100, 174 DHCPV6_OPT_LQ_START_TIME = 101, 175 DHCPV6_OPT_LQ_END_TIME = 102, 176 /* RFC8910 */ 177 DHCPV6_OPT_CAPTIVE_PORTAL = 103, 178 /* RFC7839 */ 179 DHCPV6_OPT_ANI_ATT = 105, 180 DHCPV6_OPT_ANI_NETWORK_NAME = 106, 181 DHCPV6_OPT_ANI_AP_NAME = 107, 182 DHCPV6_OPT_ANI_AP_BSSID = 108, 183 DHCPV6_OPT_ANI_OPERATOR_ID = 109, 184 DHCPV6_OPT_ANI_OPERATOR_REALM = 110, 185 /* RFC8520 */ 186 DHCPV6_OPT_MUD_URL_V6 = 112, 187 /* RFC8156 */ 188 DHCPV6_OPT_F_BINDING_STATUS = 114, 189 DHCPV6_OPT_F_CONNECT_FLAGS = 115, 190 DHCPV6_OPT_F_DNS_REMOVAL_INFO = 116, 191 DHCPV6_OPT_F_DNS_HOST_NAME = 117, 192 DHCPV6_OPT_F_DNS_ZONE_NAME = 118, 193 DHCPV6_OPT_F_DNS_FLAGS = 119, 194 DHCPV6_OPT_F_EXPIRATION_TIME = 120, 195 DHCPV6_OPT_F_MAX_UNACKED_BNDUPD = 121, 196 DHCPV6_OPT_F_MCLT = 122, 197 DHCPV6_OPT_F_PARTNER_LIFETIME = 123, 198 DHCPV6_OPT_F_PARTNER_LIFETIME_SENT = 124, 199 DHCPV6_OPT_F_PARTNER_DOWN_TIME = 125, 200 DHCPV6_OPT_F_PARTNER_RAW_CLT_TIME = 126, 201 DHCPV6_OPT_F_PROTOCOL_VERSION = 127, 202 DHCPV6_OPT_F_KEEPALIVE_TIME = 128, 203 DHCPV6_OPT_F_RECONFIGURE_DATA = 129, 204 DHCPV6_OPT_F_RELATIONSHIP_NAME = 130, 205 DHCPV6_OPT_F_SERVER_FLAGS = 131, 206 DHCPV6_OPT_F_SERVER_STATE = 132, 207 DHCPV6_OPT_F_START_TIME_OF_STATE = 133, 208 DHCPV6_OPT_F_STATE_EXPIRATION_TIME = 134, 209 /* RFC8357 */ 210 DHCPV6_OPT_RELAY_PORT = 135, 211 }; 212 213 enum dhcpv6_opt_npt { 214 NTP_SRV_ADDR = 1, 215 NTP_MC_ADDR = 2, 216 NTP_SRV_FQDN = 3 217 }; 218 219 enum dhcpv6_msg { 220 /* RFC8415(bis) */ 221 DHCPV6_MSG_UNKNOWN = 0, 222 DHCPV6_MSG_SOLICIT = 1, 223 DHCPV6_MSG_ADVERT = 2, 224 DHCPV6_MSG_REQUEST = 3, 225 DHCPV6_MSG_RENEW = 5, 226 DHCPV6_MSG_REBIND = 6, 227 DHCPV6_MSG_REPLY = 7, 228 DHCPV6_MSG_RELEASE = 8, 229 DHCPV6_MSG_DECLINE = 9, 230 DHCPV6_MSG_RECONF = 10, 231 DHCPV6_MSG_INFO_REQ = 11, 232 _DHCPV6_MSG_MAX 233 }; 234 235 enum dhcpv6_state { 236 DHCPV6_INIT, 237 DHCPV6_SOLICIT, 238 DHCPV6_SOLICIT_PROCESSING, 239 DHCPV6_ADVERT, 240 DHCPV6_REQUEST, 241 DHCPV6_REQUEST_PROCESSING, 242 DHCPV6_REPLY, 243 DHCPV6_BOUND, 244 DHCPV6_BOUND_PROCESSING, 245 DHCPV6_BOUND_REPLY, 246 DHCPV6_RECONF, 247 DHCPV6_RECONF_PROCESSING, 248 DHCPV6_RECONF_REPLY, 249 DHCPV6_RENEW, 250 DHCPV6_RENEW_PROCESSING, 251 DHCPV6_RENEW_REPLY, 252 DHCPV6_REBIND, 253 DHCPV6_REBIND_PROCESSING, 254 DHCPV6_REBIND_REPLY, 255 DHCPV6_INFO, 256 DHCPV6_INFO_PROCESSING, 257 DHCPV6_INFO_REPLY, 258 DHCPV6_EXIT, 259 DHCPV6_RESET 260 }; 261 262 enum dhcpv6_status { 263 /* RFC8415(bis) */ 264 DHCPV6_Success = 0, 265 DHCPV6_UnspecFail = 1, 266 DHCPV6_NoAddrsAvail = 2, 267 DHCPV6_NoBinding = 3, 268 DHCPV6_NotOnLink = 4, 269 DHCPV6_UseMulticast = 5, 270 DHCPV6_NoPrefixAvail = 6, 271 _DHCPV6_Status_Max 272 }; 273 274 enum dhcpv6_config { 275 DHCPV6_STRICT_OPTIONS = 1, 276 DHCPV6_CLIENT_FQDN = 2, 277 DHCPV6_ACCEPT_RECONFIGURE = 4, 278 DHCPV6_IGNORE_OPT_UNICAST = 8, 279 }; 280 281 typedef int(reply_handler)(enum dhcpv6_msg orig, const int rc, 282 const void *opt, const void *end, const struct sockaddr_in6 *from); 283 284 // retransmission strategy 285 struct dhcpv6_retx { 286 uint8_t max_delay; // Delay before starting transaction 287 uint8_t init_timeo; 288 uint16_t max_timeo; 289 uint8_t max_rc; // Max Retry Count 290 char name[8]; 291 reply_handler *handler_reply; 292 int(*handler_finish)(void); 293 bool is_retransmit; 294 uint64_t timeout; // Maximum duration (in seconds) for the entire DHCPv6 transaction. Varies based on the message type 295 uint8_t rc; // Retry Count 296 uint64_t start; // Transaction start time (in milliseconds) 297 uint8_t tr_id[3]; // Transaction ID 298 int64_t rto; // Retransmission TimeOut 299 uint64_t round_start; // the (RTT) time when a request was sent (in milliseconds) 300 uint64_t round_end; // the (RTT) time when a response was expected to arrive (in milliseconds) 301 int reply_ret; // Reply handler return value 302 uint64_t delay_msec; // Delay before starting the transaction 303 }; 304 305 #define DHCPV6_OPT_HDR_SIZE 4 306 #define DHCPV6_OPT_HDR_SIZE_U 4U 307 #define DHCPV6_DUID_MAX_LEN 130 // 2-byte type + 128-byte DUID, RFC8415, §11.1 308 309 // DHCPv6 Protocol Headers 310 struct dhcpv6_header { 311 uint8_t msg_type; 312 uint8_t tr_id[3]; 313 } _o_packed; 314 315 struct dhcpv6_ia_hdr { 316 uint16_t type; 317 uint16_t len; 318 uint32_t iaid; 319 uint32_t t1; 320 uint32_t t2; 321 } _o_packed; 322 323 struct dhcpv6_ia_addr { 324 uint16_t type; 325 uint16_t len; 326 struct in6_addr addr; 327 uint32_t preferred; 328 uint32_t valid; 329 } _o_packed; 330 331 struct dhcpv6_ia_prefix { 332 uint16_t type; 333 uint16_t len; 334 uint32_t preferred; 335 uint32_t valid; 336 uint8_t prefix; 337 struct in6_addr addr; 338 } _o_packed; 339 340 struct dhcpv6_duid { 341 uint16_t type; 342 uint16_t len; 343 uint16_t duid_type; 344 uint8_t data[128]; 345 } _o_packed; 346 347 struct dhcpv6_auth { 348 uint16_t type; 349 uint16_t len; 350 uint8_t protocol; 351 uint8_t algorithm; 352 uint8_t rdm; 353 uint64_t replay; 354 uint8_t data[]; 355 } _o_packed; 356 357 struct dhcpv6_auth_reconfigure { 358 uint8_t reconf_type; 359 uint8_t key[16]; 360 } _o_packed; 361 362 struct dhcpv6_s46_portparams { 363 uint8_t offset; 364 uint8_t psid_len; 365 uint16_t psid; 366 } _o_packed; 367 368 struct dhcpv6_s46_v4v6bind { 369 struct in_addr ipv4_address; 370 uint8_t bindprefix6_len; 371 uint8_t bind_ipv6_prefix[]; 372 } _o_packed; 373 374 struct dhcpv6_s46_dmr { 375 uint8_t dmr_prefix6_len; 376 uint8_t dmr_ipv6_prefix[]; 377 } _o_packed; 378 379 struct dhcpv6_s46_rule { 380 uint8_t flags; 381 uint8_t ea_len; 382 uint8_t prefix4_len; 383 struct in_addr ipv4_prefix; 384 uint8_t prefix6_len; 385 uint8_t ipv6_prefix[]; 386 } _o_packed; 387 388 #define dhcpv6_for_each_option(start, end, otype, olen, odata)\ 389 for (uint8_t *_o = (uint8_t*)(start); _o + 4 <= (uint8_t*)(end) &&\ 390 ((otype) = _o[0] << 8 | _o[1],\ 391 (odata) = (void*)&_o[4],\ 392 (olen) = _o[2] << 8 | _o[3],\ 393 (odata) + (olen) <= (uint8_t*)(end)); \ 394 _o += 4 + (_o[2] << 8 | _o[3])) 395 396 397 struct dhcpv6_server_cand { 398 bool has_noaddravail; 399 bool wants_reconfigure; 400 int16_t preference; 401 uint8_t duid_len; 402 uint8_t duid[DHCPV6_DUID_MAX_LEN]; 403 struct in6_addr server_addr; 404 uint32_t sol_max_rt; 405 uint32_t inf_max_rt; 406 void *ia_na; 407 void *ia_pd; 408 size_t ia_na_len; 409 size_t ia_pd_len; 410 }; 411 412 struct dhcpv6_stats { 413 uint64_t solicit; 414 uint64_t advertise; 415 uint64_t request; 416 uint64_t confirm; 417 uint64_t renew; 418 uint64_t rebind; 419 uint64_t reply; 420 uint64_t release; 421 uint64_t decline; 422 uint64_t reconfigure; 423 uint64_t information_request; 424 uint64_t discarded_packets; 425 uint64_t transmit_failures; 426 }; 427 428 enum odhcp6c_state { 429 STATE_CLIENT_ID, 430 STATE_SERVER_ID, 431 STATE_OUR_FQDN, 432 STATE_SERVER_CAND, 433 STATE_SERVER_ADDR, 434 STATE_ORO, 435 STATE_DNS, 436 STATE_SEARCH, 437 STATE_IA_NA, 438 STATE_IA_PD, 439 STATE_IA_PD_INIT, 440 STATE_CUSTOM_OPTS, 441 STATE_SNTP_IP, 442 STATE_NTP_IP, 443 STATE_NTP_FQDN, 444 STATE_SIP_IP, 445 STATE_SIP_FQDN, 446 STATE_RA_ROUTE, 447 STATE_RA_PREFIX, 448 STATE_RA_DNS, 449 STATE_RA_SEARCH, 450 STATE_AFTR_NAME, 451 STATE_OPTS, 452 STATE_S46_MAPT, 453 STATE_S46_MAPE, 454 STATE_S46_LW, 455 STATE_CAPT_PORT_RA, 456 STATE_CAPT_PORT_DHCPV6, 457 STATE_PASSTHRU, 458 _STATE_MAX 459 }; 460 461 struct icmp6_opt { 462 uint8_t type; 463 uint8_t len; 464 uint8_t data[6]; 465 }; 466 467 468 enum dhcpv6_mode { 469 DHCPV6_UNKNOWN = -1, 470 DHCPV6_STATELESS, 471 DHCPV6_STATEFUL 472 }; 473 474 enum ra_config { 475 RA_RDNSS_DEFAULT_LIFETIME = 1, 476 }; 477 478 enum odhcp6c_ia_mode { 479 IA_MODE_NONE, 480 IA_MODE_TRY, 481 IA_MODE_FORCE, 482 }; 483 484 enum odhcp6c_auth_protocol { 485 AUTH_PROT_NONE = -1, 486 /* RFC3118 */ 487 AUTH_PROT_TOKEN = 0, 488 /* RFC8415(bis) */ 489 AUTH_PROT_RKAP = 3, 490 }; 491 492 enum odhcp6c_auth_algorithm { 493 /* RFC3118 */ 494 AUTH_ALG_TOKEN = 0, 495 /* RFC8415(bis) */ 496 AUTH_ALG_HMACMD5 = 1 497 }; 498 499 enum odhcp6c_rkap_type { 500 /* RFC8415(bis) */ 501 RKAP_TYPE_KEY = 1, 502 RKAP_TYPE_HMACMD5 = 2, 503 }; 504 505 struct odhcp6c_entry { 506 struct in6_addr router; 507 uint8_t auxlen; 508 uint8_t length; 509 uint8_t ra_flags; 510 uint8_t exclusion_length; 511 struct in6_addr target; 512 int16_t priority; 513 uint32_t valid; 514 uint32_t preferred; 515 uint32_t t1; 516 uint32_t t2; 517 uint32_t iaid; 518 uint8_t auxtarget[]; 519 }; 520 521 // Include padding after auxtarget to align the next entry 522 #define odhcp6c_entry_size(entry) \ 523 (sizeof(struct odhcp6c_entry) + (((entry)->auxlen + 3) & ~3)) 524 525 #define odhcp6c_next_entry(entry) \ 526 ((struct odhcp6c_entry *)((uint8_t *)(entry) + odhcp6c_entry_size(entry))) 527 528 529 struct odhcp6c_request_prefix { 530 uint32_t iaid; 531 uint8_t length; 532 struct in6_addr addr; 533 }; 534 535 enum odhcp6c_opt_flags { 536 OPT_U8 = 0, 537 OPT_IP6, 538 OPT_STR, 539 OPT_DNS_STR, 540 OPT_USER_CLASS, 541 OPT_MASK_SIZE = 0x0F, 542 OPT_ARRAY = 0x10, 543 OPT_INTERNAL = 0x20, 544 OPT_NO_PASSTHRU = 0x40, 545 OPT_ORO = 0x80, 546 OPT_ORO_STATEFUL = 0x100, 547 OPT_ORO_STATELESS = 0x200, 548 OPT_ORO_SOLICIT = 0x400 549 }; 550 551 struct odhcp6c_opt { 552 uint16_t code; 553 uint16_t flags; 554 const char *str; 555 }; 556 557 struct odhcp6c_opt_cfg { 558 int strict_rfc7550; 559 }; 560 561 int init_dhcpv6(const char *ifname); 562 int dhcpv6_get_ia_mode(void); 563 int dhcpv6_promote_server_cand(void); 564 int dhcpv6_send_request(enum dhcpv6_msg type); 565 int dhcpv6_receive_response(enum dhcpv6_msg type); 566 enum dhcpv6_state dhcpv6_get_state(void); 567 void dhcpv6_set_state(enum dhcpv6_state state); 568 int dhcpv6_get_socket(void); 569 struct dhcpv6_stats dhcpv6_get_stats(void); 570 void dhcpv6_reset_stats(void); 571 int dhcpv6_state_processing(enum dhcpv6_msg type); 572 int dhcpv6_get_state_timeout(void); 573 void dhcpv6_set_state_timeout(int timeout); 574 void dhcpv6_reset_state_timeout(void); 575 const char *dhcpv6_state_to_str(enum dhcpv6_state state); 576 577 int init_rtnetlink(void); 578 int set_rtnetlink_addr(int ifindex, const struct in6_addr *addr, 579 uint32_t pref, uint32_t valid); 580 581 int ra_get_hoplimit(void); 582 int ra_get_mtu(void); 583 int ra_get_reachable(void); 584 int ra_get_retransmit(void); 585 586 void notify_state_change(const char *status, int delay, bool resume); 587 588 int script_init(const char *path, const char *ifname); 589 ssize_t script_unhexlify(uint8_t *dst, size_t len, const char *src); 590 void script_hexlify(char *dst, const uint8_t *src, size_t len); 591 void script_call(const char *status, int delay, bool resume); 592 593 bool odhcp6c_signal_process(void); 594 uint64_t odhcp6c_get_milli_time(void); 595 int odhcp6c_random(void *buf, size_t len); 596 bool odhcp6c_is_bound(void); 597 bool odhcp6c_addr_in_scope(const struct in6_addr *addr); 598 599 // State manipulation 600 void odhcp6c_clear_state(enum odhcp6c_state state); 601 int odhcp6c_add_state(enum odhcp6c_state state, const void *data, size_t len); 602 void odhcp6c_append_state(enum odhcp6c_state state, const void *data, size_t len); 603 int odhcp6c_insert_state(enum odhcp6c_state state, size_t offset, const void *data, size_t len); 604 size_t odhcp6c_remove_state(enum odhcp6c_state state, size_t offset, size_t len); 605 void* odhcp6c_move_state(enum odhcp6c_state state, size_t *len); 606 void* odhcp6c_get_state(enum odhcp6c_state state, size_t *len); 607 608 // Entry manipulation 609 bool odhcp6c_update_entry(enum odhcp6c_state state, struct odhcp6c_entry *new, 610 unsigned int holdoff_interval); 611 612 void odhcp6c_expire(bool expire_ia_pd); 613 uint32_t odhcp6c_elapsed(void); 614 struct odhcp6c_opt *odhcp6c_find_opt(const uint16_t code); 615 struct odhcp6c_opt *odhcp6c_find_opt_by_name(const char *name); 616 617 static inline bool odhcp6c_is_multicast_ether_addr(const uint8_t *addr) 618 { 619 return addr[0] & 0x01; 620 } 621 622 static inline bool odhcp6c_is_zero_ether_addr(const uint8_t *addr) 623 { 624 return (addr[0] | addr[1] | addr[2] | 625 addr[3] | addr[4] | addr[5]) == 0; 626 } 627 628 static inline bool odhcp6c_is_valid_ether_addr(const uint8_t *addr) 629 { 630 return !odhcp6c_is_multicast_ether_addr(addr) && 631 !odhcp6c_is_zero_ether_addr(addr); 632 } 633 634 #endif /* _ODHCP6C_H_ */ 635
This page was automatically generated by LXR 0.3.1. • OpenWrt