1 // Copyright (C) 2014-2019,2021 Internet Systems Consortium, Inc. ("ISC") 2 // 3 // This Source Code Form is subject to the terms of the Mozilla Public 4 // License, v. 2.0. If a copy of the MPL was not distributed with this 5 // file, You can obtain one at http://mozilla.org/MPL/2.0/. 6 7 #ifndef HOST_H 8 #define HOST_H 9 10 #include <asiolink/io_address.h> 11 #include <cc/data.h> 12 #include <cc/user_context.h> 13 #include <dhcp/classify.h> 14 #include <dhcp/duid.h> 15 #include <dhcp/hwaddr.h> 16 #include <dhcpsrv/cfg_option.h> 17 #include <dhcpsrv/subnet_id.h> 18 #include <boost/shared_ptr.hpp> 19 #include <boost/algorithm/string.hpp> 20 #include <list> 21 #include <map> 22 #include <string> 23 #include <utility> 24 25 namespace isc { 26 namespace dhcp { 27 28 /// @brief Maximum size of an IPv6 address represented as a text string. 29 /// 30 /// This is 32 hexadecimal characters written in 8 groups of four, plus seven 31 /// colon separators. 32 const size_t ADDRESS6_TEXT_MAX_LEN = 39; 33 34 /// @brief Maximum length of classes stored in a dhcp4/6_client_classes 35 /// columns. 36 const size_t CLIENT_CLASSES_MAX_LEN = 255; 37 38 /// @brief Maximum length of the hostname stored in DNS. 39 /// 40 /// This length is restricted by the length of the domain-name carried 41 /// in the Client FQDN %Option (see RFC4702 and RFC4704). 42 const size_t HOSTNAME_MAX_LEN = 255; 43 44 /// @brief Maximum length of option value. 45 const size_t OPTION_VALUE_MAX_LEN = 4096; 46 47 /// @brief Maximum length of option value specified in textual format. 48 const size_t OPTION_FORMATTED_VALUE_MAX_LEN = 8192; 49 50 /// @brief Maximum length of option space name. 51 const size_t OPTION_SPACE_MAX_LEN = 128; 52 53 /// @brief Maximum length of user context. 54 const size_t USER_CONTEXT_MAX_LEN = 8192; 55 56 /// @brief Maximum length of the server hostname. 57 const size_t SERVER_HOSTNAME_MAX_LEN = 64; 58 59 /// @brief Maximum length of the boot file name. 60 const size_t BOOT_FILE_NAME_MAX_LEN = 128; 61 62 /// @brief Maximum length of authentication keys - 128 bits. 63 const uint8_t AUTH_KEY_LEN = 16; 64 65 /// @brief Maximum length of authentication keys (coded in hexadecimal). 66 const size_t TEXT_AUTH_KEY_LEN = AUTH_KEY_LEN * 2; 67 68 /// @brief HostID (used only when storing in MySQL, PostgreSQL or Cassandra) 69 typedef uint64_t HostID; 70 71 /// @brief Authentication keys. 72 /// 73 /// This class represents authentication keys to be used for 74 /// calculating HMAC in the authentication field of the reconfigure message. 75 class AuthKey { 76 public: 77 /// @brief Constructor. 78 /// 79 /// Constructor for assigning auth keys in host reservation. 80 /// Ensures the key length is not greater than 16 bytes. 81 /// @param key auth key in binary to be stored. 82 AuthKey(const std::vector<uint8_t>& key); 83 84 /// @brief Constructor. 85 /// 86 /// Constructor for assigning auth keys in host reservation. 87 /// Ensures the key length is not greater than AUTH_KEY_LEN (16) bytes 88 /// so TEXT_AUTH_KEY_LEN (32) hexadecimal digits. 89 /// See @c setKey for constraints on its input format. 90 /// 91 /// @param key auth key in hexadecimal to be stored. 92 AuthKey(const std::string& key); 93 94 /// @brief Constructor. 95 /// 96 /// Constructor for generating auth keys, with no argument. 97 /// shall use the internal function for generationg random keys. 98 AuthKey(); 99 100 // @brief Get random string. 101 /// 102 /// Random string is generated by default will be used for 103 /// the keys to be used for signing Reconfigure Message. 104 /// @return Random binary string of 16 bytes. 105 static std::vector<uint8_t> getRandomKeyString(); 106 107 /// @brief Set auth key value from binary. 108 /// 109 /// Set the key value. 110 // If the size is greater than 16 bytes, we resize to 16 bytes. 111 /// Doesn't throw an exception. 112 /// @param key auth key in binary to be stored 113 void setAuthKey(const std::vector<uint8_t>& key); 114 115 /// @brief Set auth key value from hexadecimal. 116 /// 117 /// Set the key value. 118 /// If the size is greater than 16 bytes, we resize to 16 bytes. 119 /// @param key auth key in hexadecimal to be stored. 120 /// @throw BadValue if the string is not a valid hexadecimal encoding, 121 /// for instance has a not hexadecimal or odd number of digits. 122 void setAuthKey(const std::string& key); 123 124 /// @brief Return auth key. 125 /// 126 /// @return auth key in binary. getAuthKey()127 const std::vector<uint8_t>& getAuthKey() const { 128 return authKey_; 129 } 130 131 /// @brief Return text format for keys. 132 /// 133 /// @return auth key as a string of hexadecimal digits. 134 std::string toText() const; 135 136 /// 137 /// @brief Equality operator. 138 /// 139 /// equality operator to compare two AuthKey objects. 140 /// @param other Authkey to be compared against. 141 bool operator==(const AuthKey& other) const; 142 143 /// @brief Inequality operator. 144 /// 145 /// inequality operator to compare two AuthKey objects. 146 /// @param other Authkey to be compared against. 147 bool operator!=(const AuthKey& other) const; 148 149 private: 150 std::vector<uint8_t> authKey_; 151 }; 152 153 /// @brief IPv6 reservation for a host. 154 /// 155 /// This class represents a reservation for a host of a single IPv6 156 /// address or prefix (in @c Host object). 157 /// 158 /// The class holds the address and prefix length, a value of 128 159 /// for the latter implying that the reservation is for a single 160 /// IPv6 address. 161 class IPv6Resrv { 162 public: 163 164 /// @brief Type of the reservation. 165 /// 166 /// Currently supported types are NA and PD. 167 enum Type { 168 TYPE_NA, 169 TYPE_PD 170 }; 171 172 /// @brief Constructor. 173 /// 174 /// Creates a reservation from the IPv6 address and prefix length 175 /// value. If the prefix length is not specified, the default value 176 /// of 128 is used. This value indicates that the reservation is made 177 /// for an IPv6 address. 178 /// 179 /// @param type Reservation type: NA or PD. 180 /// @param prefix Address or prefix to be reserved. 181 /// @param prefix_len Prefix length. 182 /// 183 /// @throw isc::BadValue if prefix is not IPv6 prefix, is a 184 /// multicast address or the prefix length is greater than 128. 185 IPv6Resrv(const Type& type, 186 const asiolink::IOAddress& prefix, 187 const uint8_t prefix_len = 128); 188 189 /// @brief Returns prefix for the reservation. getPrefix()190 const asiolink::IOAddress& getPrefix() const { 191 return (prefix_); 192 } 193 194 /// @brief Returns prefix length. getPrefixLen()195 uint8_t getPrefixLen() const { 196 return (prefix_len_); 197 } 198 199 /// @brief Returns reservation type. 200 /// 201 /// The type of reservation is determined using a prefix length. 202 /// 203 /// @return NA for prefix length equal to 128, PD otherwise. getType()204 Type getType() const { 205 return (type_); 206 } 207 208 /// @brief Sets a new prefix and prefix length. 209 /// 210 /// @param type Reservation type: NA or PD. 211 /// @param prefix New prefix. 212 /// @param prefix_len New prefix length. 213 /// 214 /// @throw isc::BadValue if prefix is not IPv6 prefix, is a 215 /// multicast address or the prefix length is greater than 128. 216 void set(const Type& type, const asiolink::IOAddress& prefix, 217 const uint8_t prefix_len); 218 219 /// @brief Returns information about the reservation in the textual format. 220 std::string toText() const; 221 222 /// @brief Equality operator. 223 /// 224 /// @param other Reservation to compare to. 225 bool operator==(const IPv6Resrv& other) const; 226 227 /// @brief Inequality operator. 228 /// 229 /// @param other Reservation to compare to. 230 bool operator!=(const IPv6Resrv& other) const; 231 232 private: 233 234 Type type_; ///< Reservation type. 235 asiolink::IOAddress prefix_; ///< Prefix 236 uint8_t prefix_len_; ///< Prefix length. 237 }; 238 239 /// @brief Collection of IPv6 reservations for the host. 240 typedef std::multimap<IPv6Resrv::Type, IPv6Resrv> IPv6ResrvCollection; 241 typedef IPv6ResrvCollection::const_iterator IPv6ResrvIterator; 242 typedef std::pair<IPv6Resrv::Type, IPv6Resrv> IPv6ResrvTuple; 243 typedef std::pair<IPv6ResrvIterator, IPv6ResrvIterator> IPv6ResrvRange; 244 245 /// @brief Represents a device with IPv4 and/or IPv6 reservations. 246 /// 247 /// This class represents a network device which can be identified 248 /// by a unique property, such as MAC address on the interface or 249 /// client identifier (DUID), and for which some resources are statically 250 /// assigned: 251 /// - IPv4 address which the device obtains when it contacts a DHCPv4 server 252 /// - IPv6 address(es) which the device obtains when it contacts a DHCPv6 253 /// server 254 /// - IPv6 prefix(es) obtained when the device contacts the DHCPv6 server 255 /// and requests allocation of prefixes using prefix delegation mechanism 256 /// - hostname which is used for dynamic DNS updates for both DHCPv4 and 257 /// DHCPv6 exchanges. 258 /// - client classes which the client is associated with 259 /// - DHCP options specifically configured for the device 260 /// 261 /// Note, that "host" in this context has a different meaning from 262 /// host construed as device attached to a network with (possibly) multiple 263 /// interfaces. For the MAC address based reservations, each interface on a 264 /// network device maps to a single @c Host object as each @c Host object 265 /// contains at most one MAC address. So, it is possible that a single 266 /// device is associated with multiple distinct @c Host objects if the 267 /// device has multiple interfaces. Under normal circumstances, a non-mobile 268 /// dual stack device using one interface should be represented by a single 269 /// @c Host object. 270 /// 271 /// A DHCPv6 DUID is common for all interfaces on a device. Therefore, for 272 /// DUID based reservations a @c Host object may represent a network device with 273 /// multiple interfaces. However, since @c Host objects are grouped by 274 /// subnets to which device's interfaces are connected a single instance of 275 /// @c Host object usually defines reservations for a single interface. 276 /// 277 /// The @c Host object combines reservations for both IPv4 and IPv6 resources 278 /// to allow for correlation of the information about the dual stack devices 279 /// using DHCPv4 and DHCPv6 respectively. For example: both the DHCPv4 and 280 /// DHCPv6 servers may use the same database for storing host reservations, so 281 /// the information about the DHCPv4 reservations are available for the 282 /// DHCPv6 server and vice versa. Also, this approach allows for reserving 283 /// common resources such as host name for DHCPv4 and DHCPv6 clients. 284 /// 285 /// This class also holds pointers to specific DHCP options reserved 286 /// for a host. Options instances are held in @c CfgOption objects. 287 /// There are two @c CfgOption objects in this class, one holding 288 /// DHCPv4 options, another one holding DHCPv6 options. 289 /// 290 /// @todo This class offers basic functionality for storing host information. 291 /// It will need to be extended to allow for the following operations: 292 /// - remove and replace IPv6 reservations 293 /// - remove and replace client classes 294 /// - disable IPv4 reservation without a need to set it to the 0.0.0.0 address 295 /// Note that the last three operations are mainly required for managing 296 /// host reservations which will be implemented later. 297 class Host : public data::UserContext { 298 public: 299 300 /// @brief Type of the host identifier. 301 /// 302 /// Currently supported identifiers are: 303 /// - hardware address (DHCPv4 and DHCPv6) (identifier name: "hw-address"), 304 /// - DUID (DHCPv4 and DHCPv6) (identifier name: "duid"), 305 /// - circuit identifier (DHCPv4) (identifier name: "circuit-id"), 306 /// - client identifier (DHCPv4) (identifier name: "client-id") 307 enum IdentifierType { 308 IDENT_HWADDR, 309 IDENT_DUID, 310 IDENT_CIRCUIT_ID, 311 IDENT_CLIENT_ID, 312 IDENT_FLEX, ///< Flexible host identifier. 313 }; 314 315 /// @brief Constant pointing to the last identifier of the 316 /// @ref IdentifierType enumeration. 317 static const IdentifierType LAST_IDENTIFIER_TYPE = IDENT_FLEX; 318 319 /// @brief Constructor. 320 /// 321 /// Creates a @c Host object using an identifier in a binary format. This 322 /// is most useful in cases where the identifier is obtained from the 323 /// database. The constructor will create an instance of the @c HWAddr 324 /// or @c DUID object depending on the identifier type. 325 /// 326 /// @param identifier Pointer to the binary value holding an identifier. 327 /// @param identifier_len Length of the identifier. 328 /// @param identifier_type Type of the identifier (hardware address or 329 /// DUID). 330 /// @param ipv4_subnet_id Identifier of the IPv4 subnet to which the host 331 /// is connected. 332 /// @param ipv6_subnet_id Identifier of the IPv6 subnet to which the host 333 /// is connected. 334 /// @param ipv4_reservation An IPv4 address reserved for the client. If 335 /// this address is set to 0, there is no reservation. 336 /// @param hostname Hostname to be allocated to both DHCPv4 and DHCPv6 337 /// clients. This is empty string if hostname is not allocated. 338 /// @param dhcp4_client_classes A string holding DHCPv4 client class names 339 /// separated by commas. The names get trimmed by this constructor. 340 /// @param dhcp6_client_classes A string holding DHCPv6 client class names 341 /// separated by commas. The names get trimmed by this constructor. 342 /// @param next_server IPv4 address of next server (siaddr). 343 /// @param server_host_name Server host name (a.k.a. sname). 344 /// @param boot_file_name Boot file name (a.k.a. file). 345 /// @param auth_key Authentication key. 346 /// 347 /// @throw BadValue if the provided values are invalid. In particular, 348 /// if the identifier is invalid. 349 Host(const uint8_t* identifier, const size_t identifier_len, 350 const IdentifierType& identifier_type, 351 const SubnetID ipv4_subnet_id, const SubnetID ipv6_subnet_id, 352 const asiolink::IOAddress& ipv4_reservation, 353 const std::string& hostname = "", 354 const std::string& dhcp4_client_classes = "", 355 const std::string& dhcp6_client_classes = "", 356 const asiolink::IOAddress& next_server = asiolink::IOAddress::IPV4_ZERO_ADDRESS(), 357 const std::string& server_host_name = "", 358 const std::string& boot_file_name = "", 359 const AuthKey& auth_key = AuthKey("")); 360 361 /// @brief Constructor. 362 /// 363 /// Creates @c Host object using an identifier in a textual format. This 364 /// is useful in cases when the reservation is specified in the server 365 /// configuration file. Identifiers can be specified in the following 366 /// formats: 367 /// - "yy:yy:yy:yy:yy:yy" 368 /// - "yyyyyyyyyy", 369 /// - "0xyyyyyyyyyy", 370 /// - "'some identifier'". 371 /// where y is a hexadecimal digit. 372 /// 373 /// Note that it is possible to use textual representation, e.g. 'some identifier', 374 /// which is converted to a vector of ASCII codes representing characters in a 375 /// given string, excluding quotes. This is useful in cases when specific 376 /// identifiers, e.g. circuit-id are manually assigned user friendly values. 377 /// 378 /// @param identifier Identifier in the textual format. The expected formats 379 /// for the hardware address and other identifiers are provided above. 380 /// @param identifier_name One of the supported identifiers in the text form as 381 /// described for @ref IdentifierType. 382 /// @param ipv4_subnet_id Identifier of the IPv4 subnet to which the host 383 /// is connected. 384 /// @param ipv6_subnet_id Identifier of the IPv6 subnet to which the host 385 /// is connected. 386 /// @param ipv4_reservation An IPv4 address reserved for the client. If 387 /// this address is set to 0, there is no reservation. 388 /// @param hostname Hostname to be allocated to both DHCPv4 and DHCPv6 389 /// clients. This is empty string if hostname is not allocated. 390 /// @param dhcp4_client_classes A string holding DHCPv4 client class names 391 /// separated by commas. The names get trimmed by this constructor. 392 /// @param dhcp6_client_classes A string holding DHCPv6 client class names 393 /// separated by commas. The names get trimmed by this constructor. 394 /// @param next_server IPv4 address of next server (siaddr). 395 /// @param server_host_name Server host name (a.k.a. sname). 396 /// @param boot_file_name Boot file name (a.k.a. file). 397 /// @param auth_key Authentication key. 398 /// 399 /// @throw BadValue if the provided values are invalid. In particular, 400 /// if the identifier is invalid. 401 Host(const std::string& identifier, const std::string& identifier_name, 402 const SubnetID ipv4_subnet_id, const SubnetID ipv6_subnet_id, 403 const asiolink::IOAddress& ipv4_reservation, 404 const std::string& hostname = "", 405 const std::string& dhcp4_client_classes = "", 406 const std::string& dhcp6_client_classes = "", 407 const asiolink::IOAddress& next_server = asiolink::IOAddress::IPV4_ZERO_ADDRESS(), 408 const std::string& server_host_name = "", 409 const std::string& boot_file_name = "", 410 const AuthKey& auth_key = AuthKey("")); 411 412 /// @brief Replaces currently used identifier with a new identifier. 413 /// 414 /// This method sets a new identifier type and value for a host. 415 /// This method is called by the @c Host constructor. 416 /// 417 /// @param identifier Pointer to a buffer holding an identifier. 418 /// @param len Length of the identifier that the @c identifier points to. 419 /// @param type Identifier type. 420 /// 421 /// @throw BadValue if the identifier is invalid. 422 void setIdentifier(const uint8_t* identifier, const size_t len, 423 const IdentifierType& type); 424 425 /// @brief Replaces currently used identifier with a new identifier. 426 /// 427 /// This method sets a new identifier type and value for a host. 428 /// This method is called by the @c Host constructor. 429 /// 430 /// @param identifier Reference to a new identifier in the textual format. 431 /// @param name One of the supported identifiers in the text form as 432 /// described for @ref IdentifierType. 433 /// 434 /// @throw BadValue if the identifier is invalid. 435 void setIdentifier(const std::string& identifier, const std::string& name); 436 437 /// @brief Returns hardware address for which the reservations are made. 438 /// 439 /// @return Pointer to the @c HWAddr structure or null if the reservation 440 /// is not associated with a hardware address. 441 HWAddrPtr getHWAddress() const; 442 443 /// @brief Returns DUID for which the reservations are made. 444 /// 445 /// @return Pointer to the @c DUID structure or null if the reservation 446 /// is not associated with a DUID. 447 DuidPtr getDuid() const; 448 449 /// @brief Returns the identifier in a binary form. 450 /// 451 /// @return const reference to a vector<uint8_t> holding an identifier 452 /// value. 453 const std::vector<uint8_t>& getIdentifier() const; 454 455 /// @brief Returns the identifier type. 456 /// 457 IdentifierType getIdentifierType() const; 458 459 /// @brief Converts identifier name to identifier type. 460 /// 461 /// @param identifier_name Identifier name. 462 /// @return Identifier type. 463 static IdentifierType getIdentifierType(const std::string& identifier_name); 464 465 /// @brief Returns host identifier in a textual form. 466 /// 467 /// @return Identifier in the form of type=value. 468 std::string getIdentifierAsText() const; 469 470 /// @brief Returns name of the identifier of a specified type. 471 static std::string getIdentifierName(const IdentifierType& type); 472 473 /// @brief Returns host identifier in textual form. 474 /// 475 /// @param type Identifier type. 476 /// @param value Pointer to a buffer holding identifier. 477 /// @param length Length of the identifier. 478 /// @return Identifier in the form of type=value. 479 static std::string getIdentifierAsText(const IdentifierType& type, 480 const uint8_t* value, 481 const size_t length); 482 483 /// @brief Sets new IPv4 subnet identifier. 484 /// 485 /// @param ipv4_subnet_id New subnet identifier. setIPv4SubnetID(const SubnetID ipv4_subnet_id)486 void setIPv4SubnetID(const SubnetID ipv4_subnet_id) { 487 ipv4_subnet_id_ = ipv4_subnet_id; 488 } 489 490 /// @brief Sets new IPv6 subnet identifier. 491 /// 492 /// @param ipv6_subnet_id New subnet identifier. setIPv6SubnetID(const SubnetID ipv6_subnet_id)493 void setIPv6SubnetID(const SubnetID ipv6_subnet_id) { 494 ipv6_subnet_id_ = ipv6_subnet_id; 495 } 496 497 /// @brief Returns subnet identifier for IPv4 reservation. getIPv4SubnetID()498 SubnetID getIPv4SubnetID() const { 499 return (ipv4_subnet_id_); 500 } 501 502 /// @brief Returns subnet identifier for IPv6 reservations. getIPv6SubnetID()503 SubnetID getIPv6SubnetID() const { 504 return (ipv6_subnet_id_); 505 } 506 507 /// @brief Sets new IPv4 reservation. 508 /// 509 /// The new reservation removes a previous reservation. 510 /// 511 /// @param address Address to be reserved for the client. 512 /// 513 /// @throw isc::BadValue if the provided address is not an IPv4 address, 514 /// is a 0 address or broadcast address. 515 void setIPv4Reservation(const asiolink::IOAddress& address); 516 517 /// @brief Removes the IPv4 reservation. 518 /// 519 /// Sets the IPv4 reserved address to 0. 520 void removeIPv4Reservation(); 521 522 /// @brief Returns reserved IPv4 address. 523 /// 524 /// @return IPv4 address or 0.0.0.0 if no IPv4 reservation specified. getIPv4Reservation()525 const asiolink::IOAddress& getIPv4Reservation() const { 526 return (ipv4_reservation_); 527 } 528 529 /// @brief Adds new IPv6 reservation. 530 /// 531 /// @param reservation New IPv6 reservation to be appended. 532 void addReservation(const IPv6Resrv& reservation); 533 534 /// @brief Returns IPv6 reservations of a specified type. 535 /// 536 /// @param type Type of the reservations to be returned (NA or PD). 537 /// 538 /// @return A range of iterators pointing to the reservations of 539 /// the specified type. 540 IPv6ResrvRange getIPv6Reservations(const IPv6Resrv::Type& type) const; 541 542 /// @brief Returns all IPv6 reservations. 543 /// 544 /// @return A range of iterators pointing to the reservations of 545 /// the specified type. 546 IPv6ResrvRange getIPv6Reservations() const; 547 548 /// @brief Checks if there is at least one IPv6 reservation for this host. 549 /// 550 /// @return true if there is a reservation for the host, false otherwise. 551 bool hasIPv6Reservation() const; 552 553 /// @brief Checks if specified IPv6 reservation exists for the host. 554 /// 555 /// @param reservation A reservation to be checked for the host. 556 /// 557 /// @return true if the reservation already exists for the host, false 558 /// otherwise. 559 bool hasReservation(const IPv6Resrv& reservation) const; 560 561 /// @brief Sets new hostname. 562 /// 563 /// @param hostname New hostname. setHostname(const std::string & hostname)564 void setHostname(const std::string& hostname) { 565 hostname_ = hostname; 566 } 567 568 /// @brief Returns reserved hostname. getHostname()569 const std::string& getHostname() const { 570 return (hostname_); 571 } 572 573 /// @brief Returns reserved hostname in lower case. getLowerHostname()574 std::string getLowerHostname() const { 575 return (boost::algorithm::to_lower_copy(hostname_)); 576 } 577 578 /// @brief Adds new client class for DHCPv4. 579 /// 580 /// @param class_name Class name. 581 void addClientClass4(const std::string& class_name); 582 583 /// @brief Returns classes which DHCPv4 client is associated with. getClientClasses4()584 const ClientClasses& getClientClasses4() const { 585 return (dhcp4_client_classes_); 586 } 587 588 /// @brief Adds new client class for DHCPv6. 589 /// 590 /// @param class_name Class name. 591 void addClientClass6(const std::string& class_name); 592 593 /// @brief Returns classes which DHCPv6 client is associated with. getClientClasses6()594 const ClientClasses& getClientClasses6() const { 595 return (dhcp6_client_classes_); 596 } 597 598 /// @brief Sets new value for next server field (siaddr). 599 /// 600 /// @param next_server New address of a next server. 601 /// 602 /// @throw isc::BadValue if the provided address is not an IPv4 address, 603 /// is broadcast address. 604 void setNextServer(const asiolink::IOAddress& next_server); 605 606 /// @brief Returns value of next server field (siaddr). getNextServer()607 const asiolink::IOAddress& getNextServer() const { 608 return (next_server_); 609 } 610 611 /// @brief Sets new value for server hostname (sname). 612 /// 613 /// @param server_host_name New value for server hostname. 614 /// 615 /// @throw BadValue if hostname is longer than 63 bytes. 616 void setServerHostname(const std::string& server_host_name); 617 618 /// @brief Returns value of server hostname (sname). getServerHostname()619 const std::string& getServerHostname() const { 620 return (server_host_name_); 621 } 622 623 /// @brief Sets new value for boot file name (file). 624 /// 625 /// @param boot_file_name New value of boot file name. 626 /// 627 /// @throw BadValue if boot file name is longer than 128 bytes. 628 void setBootFileName(const std::string& boot_file_name); 629 630 /// @brief Returns value of boot file name (file). getBootFileName()631 const std::string& getBootFileName() const { 632 return (boot_file_name_); 633 } 634 635 /// @brief Returns pointer to the DHCPv4 option data configuration for 636 /// this host. 637 /// 638 /// Returned pointer can be used to add, remove and update options 639 /// reserved for a host. getCfgOption4()640 CfgOptionPtr getCfgOption4() { 641 return (cfg_option4_); 642 } 643 644 /// @brief Returns const pointer to the DHCPv4 option data configuration for 645 /// this host. getCfgOption4()646 ConstCfgOptionPtr getCfgOption4() const { 647 return (cfg_option4_); 648 } 649 650 /// @brief Returns pointer to the DHCPv6 option data configuration for 651 /// this host. 652 /// 653 /// Returned pointer can be used to add, remove and update options 654 /// reserved for a host. getCfgOption6()655 CfgOptionPtr getCfgOption6() { 656 return (cfg_option6_); 657 } 658 659 /// @brief Returns const pointer to the DHCPv6 option data configuration for 660 /// this host. getCfgOption6()661 ConstCfgOptionPtr getCfgOption6() const { 662 return (cfg_option6_); 663 } 664 665 /// @brief Returns information about the host in the textual format. 666 std::string toText() const; 667 668 /// @brief Sets Host ID (primary key in MySQL, PostgreSQL and Cassandra backends) 669 /// @param id HostId value setHostId(HostID id)670 void setHostId(HostID id) { 671 host_id_ = id; 672 } 673 674 /// @brief Returns Host ID (primary key in MySQL, PostgreSQL and Cassandra backends) 675 /// @return id HostId value (or 0 if not set) getHostId()676 HostID getHostId() const { 677 return (host_id_); 678 } 679 680 /// @brief Sets the negative cached flag. 681 /// 682 /// @param negative sets whether this is a negative cached host, 683 /// i.e. a fake host in the cache which indicates non-existence 684 /// and avoids to lookup in a slow backend. setNegative(bool negative)685 void setNegative(bool negative) { 686 negative_ = negative; 687 } 688 689 /// @brief Return the negative cache flag value. 690 /// When true standard lookup methods return null host pointer instead. getNegative()691 bool getNegative() const { 692 return (negative_); 693 } 694 695 /// @brief Unparses (converts to Element representation) IPv4 host 696 /// 697 /// @return Element representation of the host 698 isc::data::ElementPtr toElement4() const; 699 700 /// @brief Unparses (converts to Element representation) IPv6 host 701 /// 702 /// @return Element representation of the host 703 isc::data::ElementPtr toElement6() const; 704 705 /// @brief sets key. 706 /// 707 /// Keys are used for signing the Reconfigure Message. setKey(const AuthKey & key)708 void setKey(const AuthKey& key) { 709 key_ = key; 710 } 711 712 /// @brief Returns the key. 713 /// 714 /// Keys are used for signing the Reconfigure Message. getKey()715 AuthKey getKey() const { 716 return(key_); 717 } 718 719 private: 720 721 /// @brief Adds new client class for DHCPv4 or DHCPv6. 722 /// 723 /// This method is called internally by the @c addClientClass4 and 724 /// @c addClientClass6 functions. It adds the class of the specified name 725 /// to the supplied class set. The class names are trimmed before they are 726 /// added. Empty class names are ignored. 727 /// 728 /// @param [out] classes Set of classes to which the new class should be 729 /// inserted. 730 /// @param class_name Class name. 731 void addClientClassInternal(ClientClasses& classes, 732 const std::string& class_name); 733 734 /// @brief Identifier type. 735 IdentifierType identifier_type_; 736 /// @brief Vector holding identifier value. 737 std::vector<uint8_t> identifier_value_; 738 /// @brief Subnet identifier for the DHCPv4 client. 739 SubnetID ipv4_subnet_id_; 740 /// @brief Subnet identifier for the DHCPv6 client. 741 SubnetID ipv6_subnet_id_; 742 /// @brief Reserved IPv4 address. 743 asiolink::IOAddress ipv4_reservation_; 744 /// @brief Collection of IPv6 reservations for the host. 745 IPv6ResrvCollection ipv6_reservations_; 746 /// @brief Name reserved for the host. 747 std::string hostname_; 748 /// @brief Collection of classes associated with a DHCPv4 client. 749 ClientClasses dhcp4_client_classes_; 750 /// @brief Collection of classes associated with a DHCPv6 client. 751 ClientClasses dhcp6_client_classes_; 752 /// @brief Next server (a.k.a. siaddr, carried in DHCPv4 message). 753 asiolink::IOAddress next_server_; 754 /// @brief Server host name (a.k.a. sname, carried in DHCPv4 message). 755 std::string server_host_name_; 756 /// @brief Boot file name (a.k.a. file, carried in DHCPv4 message) 757 std::string boot_file_name_; 758 759 /// @brief HostID (a unique identifier assigned when the host is stored in 760 /// MySQL, PostgreSQL or Cassandra) 761 uint64_t host_id_; 762 763 /// @brief Pointer to the DHCPv4 option data configuration for this host. 764 CfgOptionPtr cfg_option4_; 765 /// @brief Pointer to the DHCPv6 option data configuration for this host. 766 CfgOptionPtr cfg_option6_; 767 768 /// @brief Negative cached flag. 769 /// 770 /// This flag determines whether this object is a negative cache, i.e. 771 /// we queried other backends for specific host and there was no 772 /// entry for it. 773 bool negative_; 774 775 /// @brief key for authentication . 776 /// 777 /// key is a 16 byte value to be used in the authentication field. 778 /// Server replies will contain the below key in authentication field 779 /// as specified in the RFC 8415. While sending reconfigure message 780 /// authentication field shall contain MD5 hash computed using this key. 781 AuthKey key_; 782 }; 783 784 /// @brief Pointer to the @c Host object. 785 typedef boost::shared_ptr<Host> HostPtr; 786 787 /// @brief Const pointer to the @c Host object. 788 typedef boost::shared_ptr<const Host> ConstHostPtr; 789 790 /// @brief Collection of the const Host objects. 791 typedef std::vector<ConstHostPtr> ConstHostCollection; 792 793 /// @brief Collection of the @c Host objects. 794 typedef std::vector<HostPtr> HostCollection; 795 796 } 797 } 798 799 #endif // HOST_H 800