dhcp6.dox 18.2 KB
 Marcin Siodelski committed May 22, 2014 1 // Copyright (C) 2012-2014 Internet Systems Consortium, Inc. ("ISC")  Jeremy C. Reed committed Feb 13, 2013 2 3 4 5 6 7 8 9 10 11 12 13 14 // // Permission to use, copy, modify, and/or distribute this software for any // purpose with or without fee is hereby granted, provided that the above // copyright notice and this permission notice appear in all copies. // // THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH // REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY // AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT, // INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM // LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE // OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR // PERFORMANCE OF THIS SOFTWARE.  Tomek Mrugalski committed Oct 01, 2012 15 /**  Tomek Mrugalski committed Oct 12, 2012 16  @page dhcp6 DHCPv6 Server Component  Tomek Mrugalski committed Oct 01, 2012 17   Tomek Mrugalski committed Jun 18, 2014 18  Kea offers DHCPv6 server implementation. It is implemented as  Marcin Siodelski committed Jul 02, 2014 19  kea-dhcp6 component. Its primary code is located in  Tomek Mrugalski committed Oct 01, 2012 20 21 22 23 24 25 26 27 28 29 30  isc::dhcp::Dhcpv6Srv class. It uses \ref libdhcp extensively, especially lib::dhcp::Pkt6, isc::dhcp::Option and isc::dhcp::IfaceMgr classes. Currently this code offers skeleton functionality, i.e. it is able to receive and process incoming requests and trasmit responses. However, it does not have database management, so it returns only one, hardcoded lease to whoever asks for it. DHCPv6 server component does not support relayed traffic yet, as support for relay decapsulation is not implemented yet.  Tomek Mrugalski committed Jun 18, 2014 31  @section dhcpv6Session Bundy message queue integration  Tomek Mrugalski committed Oct 01, 2012 32   Tomek Mrugalski committed Jun 18, 2014 33 34 DHCPv4 server now has two configuration backends: JSON and Bundy. The following section applies only to the Bundy backend.  Tomek Mrugalski committed Oct 01, 2012 35   Tomek Mrugalski committed Jun 18, 2014 36  DHCPv6 server component is now integrated with Bundy/BIND10 message queue.  Tomek Mrugalski committed Oct 01, 2012 37 38 39  It follows the same principle as DHCPv4. See \ref dhcpv4Session for details.  Stephen Morris committed Dec 10, 2012 40  @section dhcpv6ConfigParser Configuration Parser in DHCPv6  Tomek Mrugalski committed Oct 01, 2012 41   Tomek Mrugalski committed Jul 14, 2014 42  kea-dhcp6 compiled with Bundy backend uses Bundy cfgmgr for commands and  Tomek Mrugalski committed Jun 18, 2014 43  configuration. During initial configuration (See \ref  Tomek Mrugalski committed Jul 14, 2014 44 45  isc::dhcp::ControlledDhcpv6Srv::init() in bundy_controller.cc), the configuration handler callback is installed (see bundyConfigHandler().  Tomek Mrugalski committed Oct 01, 2012 46 47 48 49  It is called every time there is a new configuration. In particular, it is called every time during daemon start process. It contains a isc::data::ConstElementPtr to a new configuration. This simple handler calls \ref isc::dhcp::configureDhcp6Server() method that processes received configuration.  Tomek Mrugalski committed Oct 01, 2012 50   Tomek Mrugalski committed Oct 01, 2012 51 52  This method iterates over list of received configuration elements and creates a list of parsers for each received entry. Parser is an object that is derived  Marcin Siodelski committed Dec 21, 2012 53  from a DhcpConfigParser class. Once a parser is created  Tomek Mrugalski committed Oct 01, 2012 54  (constructor), its value is set (using build() method). Once all parsers are  Jeremy C. Reed committed Mar 06, 2013 55  build, the configuration is then applied ("committed") and commit() method is  Tomek Mrugalski committed Oct 01, 2012 56  called.  Tomek Mrugalski committed Oct 01, 2012 57   Marcin Siodelski committed Sep 12, 2014 58 59 60 61 62 63  \note With the implementation of the Kea ticket #3534 we're moving away from the concept of commit being called for individual parsers. When this ticket and a couple of followup tickets are implemented, the commit will be a single operation executed for the whole configuration received from many parsers.  Tomek Mrugalski committed Oct 01, 2012 64  All parsers are defined in src/bin/dhcp6/config_parser.cc file. Some of them  Marcin Siodelski committed Dec 21, 2012 65 66 67 68 69 70 71  are generic (e.g. Uint32Parser that is able to handle any unsigned 32 bit integer), but some are very specialized (e.g. Subnets6ListConfigParser parses definitions of Subnet6 lists). In some cases, e.g. subnet6 definitions, the configuration entry is not a simple value, but a map or a list itself. In such case, the parser iterates over all elements and creates parsers for a given scope. This process may be repeated (sort of) recursively.  Tomek Mrugalski committed Oct 01, 2012 72   Stephen Morris committed Dec 10, 2012 73  @section dhcpv6ConfigInherit DHCPv6 Configuration Inheritance  Tomek Mrugalski committed Oct 01, 2012 74   Tomek Mrugalski committed Oct 25, 2012 75  One notable useful feature of DHCP configuration is its parameter inheritance.  Tomek Mrugalski committed Oct 01, 2012 76 77 78  For example, renew-timer value may be specified at a global scope and it then applies to all subnets. However, some subnets may have it overwritten with more specific values that takes precedence over global values that are considered  Marcin Siodelski committed Dec 21, 2012 79 80 81 82 83 84 85  defaults. Some parsers (e.g. Uint32Parser and StringParser) implement that inheritance. By default, they store values in global uint32_defaults and string_defaults storages. However, it is possible to instruct them to store parsed values in more specific storages. That capability is used, e.g. in Subnet6ConfigParser that has its own storage that is unique for each subnet. Finally, during commit phase (commit() method), appropriate parsers can use apply parameter inheritance.  Tomek Mrugalski committed Oct 01, 2012 86 87  Debugging configuration parser may be confusing. Therefore there is a special  Marcin Siodelski committed Dec 21, 2012 88  class called DebugParser. It does not configure anything, but just  Tomek Mrugalski committed Oct 01, 2012 89 90  accepts any parameter of any type. If requested to commit configuration, it will print out received parameter name and its value. This class is not currently used,  Tomek Mrugalski committed Oct 01, 2012 91 92 93 94 95 96 97 98 99  but it is convenient to have it every time a new parameter is added to DHCP configuration. For that purpose it should be left in the code. Parameter inheritance is done during reconfiguration phase, as reconfigurations are rare, so extra logic here is not a problem. On the other hand, values of those parameters may be used thousands times per second, so its use must be as simple as possible. In fact, currently the code has to call Subnet6->getT1() and do not implement any fancy inheritance logic.  Marcin Siodelski committed Aug 02, 2013 100 101 102 @section dhcpv6DDNSIntegration DHCPv6 Server Support for the Dynamic DNS Updates The DHCPv6 server supports processing of the DHCPv6 Client FQDN Option described in  Marcin Siodelski committed Aug 14, 2013 103 the RFC4704. This Option is sent by the DHCPv6 client to instruct the server to  Marcin Siodelski committed Aug 02, 2013 104 105 106 107 108 update the DNS mappings for the acquired lease. A client may send its fully qualified domain name, a partial name or it may choose that server will generate the name. In the last case, the client sends an empty domain-name field in the DHCPv6 Client FQDN Option.  Marcin Siodelski committed Aug 14, 2013 109 As described in RFC4704, client may choose that the server delegates the forward  Marcin Siodelski committed Aug 02, 2013 110 111 112 113 DNS update to the client and that the server performs the reverse update only. Current version of the DHCPv6 server does not support delegation of the forward update to the client. The implementation of this feature is planned for the future releases.  Marcin Siodelski committed Jul 02, 2014 114 115 The kea-dhcp-ddns process is responsible for the actual communication with the DNS server, i.e. to send DNS Update messages. The kea-dhcp6 module is responsible  Marcin Siodelski committed Aug 13, 2013 116 for generating so called @ref isc::dhcp_ddns::NameChangeRequest and sending it to the  Marcin Siodelski committed Jul 02, 2014 117 kea-dhcp-ddns module. The @ref isc::dhcp_ddns::NameChangeRequest object represents changes to the  Tomek Mrugalski committed Jul 14, 2014 118 DNS bindings, related to acquisition, renewal or release of the lease. The kea-dhcp6  Marcin Siodelski committed Aug 02, 2013 119 120 121 122 123 124 125 module implements the simple FIFO queue of the NameChangeRequest objects. The module logic, which processes the incoming DHCPv6 Client FQDN Options puts these requests into the FIFO queue. @todo Currently the FIFO queue is not processed after the NameChangeRequests are generated and added to it. In the future implementation steps it is planned to create a code which will check if there are any outstanding requests in the queue and  Marcin Siodelski committed Jul 02, 2014 126 send them to the kea-dhcp-ddns module when server is idle waiting for DHCP messages.  Marcin Siodelski committed Aug 02, 2013 127   Marcin Siodelski committed Aug 14, 2013 128 In the simplest case, when client gets one address from the server, a DHCPv6 server  Tomek Mrugalski committed Jun 18, 2014 129 may generate 0, 1 or 2 NameChangeRequests during single message processing.  Marcin Siodelski committed Aug 14, 2013 130 131 Server generates no NameChangeRequests if it is not configured to update DNS or it rejects the DNS update for any other reason.  Marcin Siodelski committed Aug 02, 2013 132   Marcin Siodelski committed Sep 10, 2013 133 Server may generate 1 NameChangeRequest in a situation when a client acquires a  Marcin Siodelski committed Aug 02, 2013 134 new lease or it releases an existing lease. In the former case, the NameChangeRequest  Marcin Siodelski committed Jul 02, 2014 135 type is CHG_ADD, which indicates that the kea-dhcp-ddns module should add a new DNS  Marcin Siodelski committed Aug 02, 2013 136 137 binding for the client, and it is assumed that there is no DNS binding for this client already. In the latter case, the NameChangeRequest type is CHG_REMOVE to  Marcin Siodelski committed Jul 02, 2014 138 indicate to the kea-dhcp-ddns module that the existing DNS binding should be removed  Marcin Siodelski committed Aug 02, 2013 139 140 from the DNS. The binding consists of the forward and reverse mapping. A server may only remove the mapping which it had added. Therefore, the lease database  Marcin Siodelski committed Aug 14, 2013 141 142 143 144 holds an information which updates (no update, reverse only update, forward only update, both reverse and forward update) have been performed when the lease was acquired. Server checks this information to make a decision which mapping it is supposed to remove when a lease is released.  Marcin Siodelski committed Aug 02, 2013 145 146 147 148 149  Server may generate 2 NameChangeRequests in case the client is renewing a lease and it already has a DNS binding for that lease. Note, that renewal may be triggered as a result of sending a RENEW message as well as the REQUEST message. In both cases DHCPv6 server will check if there is an existing lease for the client which has sent  Marcin Siodelski committed Sep 10, 2013 150 a message, and it will check in the lease database if the DNS Updates had  Marcin Siodelski committed Aug 02, 2013 151 152 153 154 155 156 157 been performed for this client. If the notion of client's FQDN changes comparing to the information stored in the lease database, the DHCPv6 has to remove an existing binding from the DNS and then add a new binding according to the new FQDN information received from the client. If the FQDN sent in the message which triggered a renewal doesn't change (comparing to the information in the lease database) the NameChangeRequest is not generated.  Marcin Siodelski committed Aug 14, 2013 158 159 160 161 In the more complex scenarios, when server sends multiple IA_NA options, each holding multiple IAADDR options, server will generate more NameChangeRequests for a single message being processed. That is 0, 1, 2 for the individual IA_NA. Generation of the distinct NameChangeRequests for each IADDR is not supported yet.  Marcin Siodelski committed Aug 02, 2013 162   Marcin Siodelski committed Aug 14, 2013 163 The DHCPv6 Client FQDN Option comprises "NOS" flags which communicate to the  Marcin Siodelski committed Sep 10, 2013 164 server what updates (if any) client expects the server to perform. Server  Marcin Siodelski committed Aug 02, 2013 165 166 167 168 169 170 171 172 173 174 may be configured to obey client's preference or do FQDN processing in a different way. If the server overrides client's preference it will communicate it by sending the DHCPv6 Client FQDN Option in its responses to a client, with appropriate flags set. @todo Note, that current implementation doesn't allow configuration of the server's behaviour with respect to DNS Updates. This is planned for the future. The default behaviour is constituted by the set of constants defined in the (upper part of) dhcp6_srv.cc file. Once the configuration is implemented, these constants will be removed.  Marcin Siodelski committed Oct 30, 2012 175 176  @todo Add section about setting up options and their definitions with bindctl.  Marcin Siodelski committed Oct 07, 2013 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 @section dhcpv6OptionsParse Custom functions to parse message options The DHCPv6 server implementation provides a generic support to define option formats and set option values. A number of options formats have been defined for standard options in libdhcp++. However, the formats for vendor specific options are dynamically configured by the server's administrator and thus can't be stored in libdhcp++. Such option formats are stored in the @c isc::dhcp::CfgMgr. The libdhcp++ provides functions for recursive parsing of options which may be encapsulated by other options up to the any level of encapsulation but these functions are unaware of the option formats defined in the @c isc::dhcp::CfgMgr because they belong to a different library. Therefore, the generic functions @c isc::dhcp::LibDHCP::unpackOptions4 and @c isc::dhcp::LibDHCP::unpackOptions6 are only useful to parse standard options which definitions are provided in the libdhcp++. In order to overcome this problem a callback mechanism has been implemented in @c Option and @c Pkt6 classes. By installing a callback function on the instance of the @c Pkt6 the server may provide a custom implementation of the options parsing algorithm. This callback function will take precedence over the @c LibDHCP::unpackOptions6 and @c LibDHCP::unpackOptions4 functions. With this approach, the callback is implemented within the context of the server and it has access to all objects which define its configuration (including dynamically created option definitions).  Tomek Mrugalski committed Jan 03, 2014 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 @section dhcpv6Classifier DHCPv6 Client Classification Kea DHCPv6 server currently supports simplified client classification. It is called "simplified", because the incoming packets are classified based on the content of the vendor class (16) option. More flexible classification is planned, but there are no specific development dates agreed. For each incoming packet, @ref isc::dhcp::Dhcpv6Srv::classifyPacket() method is called. It attempts to extract content of the vendor class option and interprets as a name of the class. Although the RFC3315 says that the vendor class may contain more than one chunk of data, the existing code handles only one data block, because that is what actual devices use. For now, the code has been tested with two classes used in cable modem networks: eRouter1.0 and docsis3.0, but any other content of the vendor class option will be interpreted as a class name. In principle any given packet can belong to zero or more classes. As the current classifier is very modest, there's only one way to assign a class (based on vendor class option), the ability to assign more than one class to a packet is not yet exercised. Neverthless, there is such a possibility and it will be used in a near future. To check whether a packet belongs to given class, isc::dhcp::Pkt6::inClass method should be used. Currently there is no class behaviour coded in DHCPv6, hence no v6 equivalent of @ref isc::dhcp::Dhcpv4Srv::classSpecificProcessing. Should any need for such a code arise, it will be conducted in an external hooks library.  Tomek Mrugalski committed Feb 04, 2014 227 It is possible to define class restrictions in subnet, so a given subnet is only  Tomek Mrugalski committed Feb 06, 2014 228 229 accessible to clients that belong to a given class. That is implemented as isc::dhcp::Pkt6::classes_ being passed in isc::dhcp::Dhcpv6Srv::selectSubnet() to isc::dhcp::CfgMgr::getSubnet6().  Tomek Mrugalski committed Feb 04, 2014 230 231 232 Currently this capability is usable, but the number of scenarios it supports is limited.  Tomek Mrugalski committed Apr 23, 2014 233 234 235  @section dhcpv6ConfigBackend Configuration backend for DHCPv6 There are many theoretical ways in which server configuration can be stored. Kea 0.8 and  Tomek Mrugalski committed Jun 18, 2014 236 earlier versions used Bundy/BIND10 framework and its internal storage for DHCPv6 server configuration.  Tomek Mrugalski committed Apr 23, 2014 237 238 239 240 241 The legacy ISC-DHCP implementation uses flat files. Configuration stored in JSON files is becoming more and more popular among various projects. There are unofficial patches for ISC-DHCP that keep parts of the configuration in LDAP. It was also suggested that in some cases it would be convenient to keep configuration in XML files.  Wlodzimierz Wencel committed Feb 18, 2015 242 Kea 0.9 has introduced configuration backends that are switchable during compilation phase.  Tomek Mrugalski committed Apr 23, 2014 243 There is a new parameter for configure script: --with-kea-config. It currently supports  Tomek Mrugalski committed May 23, 2014 244 two values: BUNDY and JSON.  Tomek Mrugalski committed Apr 23, 2014 245   Tomek Mrugalski committed May 23, 2014 246 BUNDY (which is the default value as of April 2014) means that Kea6 is linked with the  Tomek Mrugalski committed Jun 18, 2014 247 Bundy (former BIND10) configuration backend that connects to the Bundy/BIND10 framework and in general works  Tomek Mrugalski committed Apr 23, 2014 248 exactly the same as Kea 0.8 and earlier versions. The benefits of that backend are uniform  Tomek Mrugalski committed May 23, 2014 249 250 251 integration with Bundy/BIND10 framework, easy on-line reconfiguration using bindctl, available RESTful API. On the other hand, it requires the whole heavy Bundy framework that requires Python3 to be present. That framework is going away with the release of Kea 0.9.  Tomek Mrugalski committed Apr 23, 2014 252 253 254 255  JSON is a new configuration backend that causes Kea to read JSON configuration file from disk. It does not require any framework and thus is considered more lightweight. It will allow dynamic on-line reconfiguration, but will lack remote capabilities (i.e. no RESTful  Tomek Mrugalski committed May 23, 2014 256 257 API). This configuration backend is expected to be the default for upcoming Kea 0.9. It requires -c config-file command-line option.  Tomek Mrugalski committed Apr 23, 2014 258 259  Internally, configuration backends are implemented as different implementations of the  Tomek Mrugalski committed May 23, 2014 260 isc::dhcp::ControlledDhcpv6Srv class, stored in {kea,bundy}_controller.cc files. Depending on  Tomek Mrugalski committed Apr 23, 2014 261 the choice made by ./configure script, only one of those files is compiled and linked.  Tomek Mrugalski committed May 23, 2014 262 There are backend specific tests in src/bin/dhcp6/tests/{kea,bundy}_controller_unittest.cc.  Tomek Mrugalski committed Apr 23, 2014 263 264 265 266 267 268 269 270 271 272 Only tests specific to selected backend are linked and executed during make distcheck. While it is unlikely that ISC will support more than one backend at any given time, there are several aspects that make that approach appealing in the long term. First, having two backends is essential during transition time, where both old and new backend is used. Second, there are external organizations that develop and presumably maintain LDAP backend for ISC-DHCP. Is at least possible that similar will happen for Kea. Finally, if we ever extend the isc::dhcp::CfgMgr with configuration export, this approach could be used as a migration tool.  Marcin Siodelski committed May 22, 2014 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 @section dhcpv6SignalBasedReconfiguration Reconfiguring DHCPv6 server with SIGHUP signal Online reconfiguration (reconfiguration without a need to restart the server) is an important feature which is supported by all modern DHCP servers. When using the JSON configuration backend, a configuration file name is specified with a command line option of the DHCP server binary. The configuration file is used to configure the server at startup. If the initial configuration fails, the server will fail to start. If the server starts and configures successfully it will use the initial configuration until it is reconfigured. The reconfiguration request can be triggered externally (from other process) by editing a configuration file and sending a SIGHUP signal to DHCP server process. After receiving the SIGHUP signal, the server will re-read the configuration file specified at startup. If the reconfiguration fails, the server will continue to run and use the last good configuration.  Marcin Siodelski committed Jun 03, 2014 289 The signal handler for SIGHUP (also for SIGTERM and SIGINT) are installed in the  Marcin Siodelski committed Jun 04, 2014 290 kea_controller.cc using the @c isc::util::SignalSet class. The  Marcin Siodelski committed Jun 03, 2014 291 292 293 294 295 296 297 298 299 300 301 302 @c isc::dhcp::Dhcp6Srv calls @c isc::dhcp::Daemon::handleSignal on each pass through the main loop. This method fetches the last received signal and calls a handler function defined in the kea_controller.cc. The handler function calls a static function @c configure defined in the kea_controller.cc. In order for the signal handler to know the location of the configuration file (specified at process startup), the location of this file needs to be stored in a static variable so as it may be directly accessed by the signal handler. This static variable is stored in the @c dhcp::Daemon class and all Kea processes can use it (all processes derive from this class). The configuration file location is initialized when the @c Daemon::init method is called. Therefore, derived classes should call it in their implementations of the @c init method.  Marcin Siodelski committed May 22, 2014 303   Tomek Mrugalski committed Jul 16, 2013 304 305 306 307  @section dhcpv6Other Other DHCPv6 topics For hooks API support in DHCPv6, see @ref dhcpv6Hooks.  Tomek Mrugalski committed Oct 01, 2012 308  */