diff options
author | Michael Brown | 2013-11-08 15:35:29 +0100 |
---|---|---|
committer | Michael Brown | 2013-11-14 13:35:43 +0100 |
commit | 2fa34085e28992dd7409496709af822776bd8fc6 (patch) | |
tree | 39a5bccb33c9b67eb2c93c950be39927f146a543 /src/include/ipxe | |
parent | [ipv6] Add "ipv6" setting type (diff) | |
download | ipxe-2fa34085e28992dd7409496709af822776bd8fc6.tar.gz ipxe-2fa34085e28992dd7409496709af822776bd8fc6.tar.xz ipxe-2fa34085e28992dd7409496709af822776bd8fc6.zip |
[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<x>.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 <mcb30@ipxe.org>
Diffstat (limited to 'src/include/ipxe')
-rw-r--r-- | src/include/ipxe/dhcpv6.h | 215 | ||||
-rw-r--r-- | src/include/ipxe/errfile.h | 1 |
2 files changed, 216 insertions, 0 deletions
diff --git a/src/include/ipxe/dhcpv6.h b/src/include/ipxe/dhcpv6.h new file mode 100644 index 00000000..7a1a2b07 --- /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 <stdint.h> +#include <ipxe/in.h> + +/** 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 1db94466..8e5e30f0 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 ) |