From 2fa34085e28992dd7409496709af822776bd8fc6 Mon Sep 17 00:00:00 2001 From: Michael Brown Date: Fri, 8 Nov 2013 14:35:29 +0000 Subject: [dhcpv6] Add basic support for stateful and stateless DHCPv6 Add support for the stateful and stateless variants of the DHCPv6 protocol. The resulting settings block is registered as "net.dhcpv6", and DHCPv6 options can be obtained using e.g. "${net0.dhcpv6/23:ipv6}" to obtain the IPv6 DNS server address. IPv6 addresses obtained via stateful DHCPv6 are not yet applied to the network device. Signed-off-by: Michael Brown --- src/include/ipxe/dhcpv6.h | 215 +++++++++++++++++++++++++++++++++++++++++++++ src/include/ipxe/errfile.h | 1 + 2 files changed, 216 insertions(+) create mode 100644 src/include/ipxe/dhcpv6.h (limited to 'src/include/ipxe') diff --git a/src/include/ipxe/dhcpv6.h b/src/include/ipxe/dhcpv6.h new file mode 100644 index 000000000..7a1a2b07f --- /dev/null +++ b/src/include/ipxe/dhcpv6.h @@ -0,0 +1,215 @@ +#ifndef _IPXE_DHCPV6_H +#define _IPXE_DHCPV6_H + +/** @file + * + * Dynamic Host Configuration Protocol for IPv6 + * + */ + +FILE_LICENCE ( GPL2_OR_LATER ); + +#include +#include + +/** DHCPv6 server port */ +#define DHCPV6_SERVER_PORT 547 + +/** DHCPv6 client port */ +#define DHCPV6_CLIENT_PORT 546 + +/** + * A DHCPv6 option + * + */ +struct dhcpv6_option { + /** Code */ + uint16_t code; + /** Length of the data field */ + uint16_t len; + /** Data */ + uint8_t data[0]; +} __attribute__ (( packed )); + +/** DHCP unique identifier based on link-layer address (DUID-LL) */ +struct dhcpv6_duid_ll { + /** Type */ + uint16_t type; + /** Hardware type */ + uint16_t htype; + /** Link-layer address */ + uint8_t ll_addr[0]; +} __attribute__ (( packed )); + +/** DHCP unique identifier based on link-layer address (DUID-LL) */ +#define DHCPV6_DUID_LL 3 + +/** DHCPv6 client or server identifier option */ +struct dhcpv6_duid_option { + /** Option header */ + struct dhcpv6_option header; + /** DHCP unique identifier (DUID) */ + uint8_t duid[0]; +} __attribute__ (( packed )); + +/** DHCPv6 client identifier option */ +#define DHCPV6_CLIENT_ID 1 + +/** DHCPv6 server identifier option */ +#define DHCPV6_SERVER_ID 2 + +/** DHCPv6 identity association for non-temporary address (IA_NA) option */ +struct dhcpv6_ia_na_option { + /** Option header */ + struct dhcpv6_option header; + /** Identity association identifier (IAID) */ + uint32_t iaid; + /** Renew time (in seconds) */ + uint32_t renew; + /** Rebind time (in seconds) */ + uint32_t rebind; + /** IA_NA options */ + struct dhcpv6_option options[0]; +} __attribute__ (( packed )); + +/** DHCPv6 identity association for non-temporary address (IA_NA) option */ +#define DHCPV6_IA_NA 3 + +/** DHCPv6 identity association address (IAADDR) option */ +struct dhcpv6_iaaddr_option { + /** Option header */ + struct dhcpv6_option header; + /** IPv6 address */ + struct in6_addr address; + /** Preferred lifetime (in seconds) */ + uint32_t preferred; + /** Valid lifetime (in seconds) */ + uint32_t valid; + /** IAADDR options */ + struct dhcpv6_option options[0]; +} __attribute__ (( packed )); + +/** DHCPv6 identity association address (IAADDR) option */ +#define DHCPV6_IAADDR 5 + +/** DHCPv6 option request option */ +struct dhcpv6_option_request_option { + /** Option header */ + struct dhcpv6_option header; + /** Requested options */ + uint16_t requested[0]; +} __attribute__ (( packed )); + +/** DHCPv6 option request option */ +#define DHCPV6_OPTION_REQUEST 6 + +/** DHCPv6 elapsed time option */ +struct dhcpv6_elapsed_time_option { + /** Option header */ + struct dhcpv6_option header; + /** Elapsed time, in centiseconds */ + uint16_t elapsed; +} __attribute__ (( packed )); + +/** DHCPv6 elapsed time option */ +#define DHCPV6_ELAPSED_TIME 8 + +/** DHCPv6 status code option */ +struct dhcpv6_status_code_option { + /** Option header */ + struct dhcpv6_option header; + /** Status code */ + uint16_t status; + /** Status message */ + char message[0]; +} __attribute__ (( packed )); + +/** DHCPv6 status code option */ +#define DHCPV6_STATUS_CODE 13 + +/** DHCPv6 user class */ +struct dhcpv6_user_class { + /** Length */ + uint16_t len; + /** User class string */ + char string[0]; +} __attribute__ (( packed )); + +/** DHCPv6 user class option */ +struct dhcpv6_user_class_option { + /** Option header */ + struct dhcpv6_option header; + /** User class */ + struct dhcpv6_user_class user_class[0]; +} __attribute__ (( packed )); + +/** DHCPv6 user class option */ +#define DHCPV6_USER_CLASS 15 + +/** DHCPv6 DNS recursive name server option */ +#define DHCPV6_DNS_SERVER 23 + +/** DHCPv6 domain search list option */ +#define DHCPV6_DOMAIN_SEARCH 24 + +/** + * Any DHCPv6 option + * + */ +union dhcpv6_any_option { + struct dhcpv6_option header; + struct dhcpv6_duid_option duid; + struct dhcpv6_ia_na_option ia_na; + struct dhcpv6_iaaddr_option iaaddr; + struct dhcpv6_option_request_option option_request; + struct dhcpv6_elapsed_time_option elapsed_time; + struct dhcpv6_status_code_option status_code; + struct dhcpv6_user_class_option user_class; +}; + +/** + * A DHCPv6 header + * + */ +struct dhcpv6_header { + /** Message type */ + uint8_t type; + /** Transaction ID */ + uint8_t xid[3]; + /** Options */ + struct dhcpv6_option options[0]; +} __attribute__ (( packed )); + +/** DHCPv6 solicitation */ +#define DHCPV6_SOLICIT 1 + +/** DHCPv6 advertisement */ +#define DHCPV6_ADVERTISE 2 + +/** DHCPv6 request */ +#define DHCPV6_REQUEST 3 + +/** DHCPv6 reply */ +#define DHCPV6_REPLY 7 + +/** DHCPv6 information request */ +#define DHCPV6_INFORMATION_REQUEST 11 + +/** DHCPv6 settings block name */ +#define DHCPV6_SETTINGS_NAME "dhcpv6" + +/** + * Construct all-DHCP-relay-agents-and-servers multicast address + * + * @v addr Zeroed address to construct + */ +static inline void ipv6_all_dhcp_relay_and_servers ( struct in6_addr *addr ) { + addr->s6_addr16[0] = htons ( 0xff02 ); + addr->s6_addr[13] = 1; + addr->s6_addr[15] = 2; +} + +extern int start_dhcpv6 ( struct interface *job, struct net_device *netdev, + int stateful ); + +#endif /* _IPXE_DHCPV6_H */ diff --git a/src/include/ipxe/errfile.h b/src/include/ipxe/errfile.h index 1db94466a..8e5e30f0a 100644 --- a/src/include/ipxe/errfile.h +++ b/src/include/ipxe/errfile.h @@ -219,6 +219,7 @@ FILE_LICENCE ( GPL2_OR_LATER ); #define ERRFILE_socket ( ERRFILE_NET | 0x00380000 ) #define ERRFILE_icmp ( ERRFILE_NET | 0x00390000 ) #define ERRFILE_ping ( ERRFILE_NET | 0x003a0000 ) +#define ERRFILE_dhcpv6 ( ERRFILE_NET | 0x003b0000 ) #define ERRFILE_image ( ERRFILE_IMAGE | 0x00000000 ) #define ERRFILE_elf ( ERRFILE_IMAGE | 0x00010000 ) -- cgit v1.2.3-55-g7522