radius_host_data_source.h 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311
  1. // Copyright (C) 2015-2017 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. #ifndef RADIUS_HOST_DATA_SOURCE_H
  7. #define RADIUS_HOST_DATA_SOURCE_H
  8. #include <dhcpsrv/base_host_data_source.h>
  9. #include <dhcpsrv/database_connection.h>
  10. #include <dhcpsrv/db_exceptions.h>
  11. #include <radcli/radcli.h>
  12. namespace isc {
  13. namespace dhcp {
  14. /// @brief MySQL Host Data Source
  15. ///
  16. /// This class implements the @ref isc::dhcp::BaseHostDataSource interface to
  17. /// a radius protocol.
  18. class RadiusHostDataSource: public BaseHostDataSource {
  19. public:
  20. /// @brief Constructor
  21. ///
  22. /// Uses the following keywords in the parameters passed to it to
  23. /// connect to the database:
  24. /// - password - Password for radius
  25. /// - host - Host to which to connect (optional, defaults to "localhost")
  26. /// - port - Port to witch to connect (optional, defaults to 1812)
  27. ///
  28. /// @param parameters A data structure relating keywords and values
  29. /// concerned with the database.
  30. ///
  31. /// @throw isc::dhcp::NoPassword Mandatory password not given
  32. /// @throw isc::dhcp::DbOpenError Error opening the database
  33. /// @throw isc::dhcp::DbOperationError An operation on the open database has
  34. /// failed.
  35. RadiusHostDataSource(const DatabaseConnection::ParameterMap& parameters);
  36. /// @brief Virtual destructor.
  37. ///
  38. virtual ~RadiusHostDataSource();
  39. /// @brief Return all hosts for the specified HW address or DUID.
  40. ///
  41. /// This method returns all @c Host objects which represent reservations
  42. /// for the specified HW address or DUID. Note, that this method may
  43. /// return multiple reservations because a particular client may have
  44. /// reservations in multiple subnets and the same client may be identified
  45. /// by HW address or DUID. The server is unable to verify that the specific
  46. /// DUID and HW address belong to the same client, until the client sends
  47. /// a DHCP message.
  48. ///
  49. /// Specifying both hardware address and DUID is allowed for this method
  50. /// and results in returning all objects that are associated with hardware
  51. /// address OR duid. For example: if one host is associated with the
  52. /// specified hardware address and another host is associated with the
  53. /// specified DUID, two hosts will be returned.
  54. ///
  55. /// @param hwaddr HW address of the client or NULL if no HW address
  56. /// available.
  57. /// @param duid client id or NULL if not available, e.g. DHCPv4 client case.
  58. ///
  59. /// @return Collection of const @c Host objects.
  60. virtual ConstHostCollection
  61. getAll(const HWAddrPtr& hwaddr, const DuidPtr& duid = DuidPtr()) const;
  62. /// @brief Return all hosts connected to any subnet for which reservations
  63. /// have been made using a specified identifier.
  64. ///
  65. /// This method returns all @c Host objects which represent reservations
  66. /// for a specified identifier. This method may return multiple hosts
  67. /// because a particular client may have reservations in multiple subnets.
  68. ///
  69. /// @param identifier_type Identifier type.
  70. /// @param identifier_begin Pointer to a beginning of a buffer containing
  71. /// an identifier.
  72. /// @param identifier_len Identifier length.
  73. ///
  74. /// @return Collection of const @c Host objects.
  75. virtual ConstHostCollection
  76. getAll(const Host::IdentifierType& identifier_type,
  77. const uint8_t* identifier_begin, const size_t identifier_len) const;
  78. /// @brief Returns a collection of hosts using the specified IPv4 address.
  79. ///
  80. /// This method may return multiple @c Host objects if they are connected
  81. /// to different subnets.
  82. ///
  83. /// @param address IPv4 address for which the @c Host object is searched.
  84. ///
  85. /// @return Collection of const @c Host objects.
  86. virtual ConstHostCollection
  87. getAll4(const asiolink::IOAddress& address) const;
  88. /// @brief Returns a host connected to the IPv4 subnet.
  89. ///
  90. /// Implementations of this method should guard against the case when
  91. /// multiple instances of the @c Host are present, e.g. when two
  92. /// @c Host objects are found, one for the DUID, another one for the
  93. /// HW address. In such case, an implementation of this method
  94. /// should throw an MultipleRecords exception.
  95. ///
  96. /// @param subnet_id Subnet identifier.
  97. /// @param hwaddr HW address of the client or NULL if no HW address
  98. /// available.
  99. /// @param duid client id or NULL if not available.
  100. ///
  101. /// @return Const @c Host object using a specified HW address or DUID.
  102. virtual ConstHostPtr
  103. get4(const SubnetID& subnet_id, const HWAddrPtr& hwaddr,
  104. const DuidPtr& duid = DuidPtr()) const;
  105. /// @brief Returns a host connected to the IPv4 subnet.
  106. ///
  107. /// @param subnet_id Subnet identifier.
  108. /// @param identifier_type Identifier type.
  109. /// @param identifier_begin Pointer to a beginning of a buffer containing
  110. /// an identifier.
  111. /// @param identifier_len Identifier length.
  112. ///
  113. /// @return Const @c Host object for which reservation has been made using
  114. /// the specified identifier.
  115. virtual ConstHostPtr
  116. get4(const SubnetID& subnet_id, const Host::IdentifierType& identifier_type,
  117. const uint8_t* identifier_begin, const size_t identifier_len) const;
  118. /// @brief Returns a host connected to the IPv4 subnet and having
  119. /// a reservation for a specified IPv4 address.
  120. ///
  121. /// One of the use cases for this method is to detect collisions between
  122. /// dynamically allocated addresses and reserved addresses. When the new
  123. /// address is assigned to a client, the allocation mechanism should check
  124. /// if this address is not reserved for some other host and do not allocate
  125. /// this address if reservation is present.
  126. ///
  127. /// Implementations of this method should guard against invalid addresses,
  128. /// such as IPv6 address.
  129. ///
  130. /// @param subnet_id Subnet identifier.
  131. /// @param address reserved IPv4 address.
  132. ///
  133. /// @return Const @c Host object using a specified IPv4 address.
  134. virtual ConstHostPtr
  135. get4(const SubnetID& subnet_id, const asiolink::IOAddress& address) const;
  136. /// @brief Returns a host connected to the IPv6 subnet.
  137. ///
  138. /// Implementations of this method should guard against the case when
  139. /// multiple instances of the @c Host are present, e.g. when two
  140. /// @c Host objects are found, one for the DUID, another one for the
  141. /// HW address. In such case, an implementation of this method
  142. /// should throw an MultipleRecords exception.
  143. ///
  144. /// @param subnet_id Subnet identifier.
  145. /// @param hwaddr HW address of the client or NULL if no HW address
  146. /// available.
  147. /// @param duid DUID or NULL if not available.
  148. ///
  149. /// @return Const @c Host object using a specified HW address or DUID.
  150. virtual ConstHostPtr
  151. get6(const SubnetID& subnet_id, const DuidPtr& duid,
  152. const HWAddrPtr& hwaddr = HWAddrPtr()) const;
  153. /// @brief Returns a host connected to the IPv6 subnet.
  154. ///
  155. /// @param subnet_id Subnet identifier.
  156. /// @param identifier_type Identifier type.
  157. /// @param identifier_begin Pointer to a beginning of a buffer containing
  158. /// an identifier.
  159. /// @param identifier_len Identifier length.
  160. ///
  161. /// @return Const @c Host object for which reservation has been made using
  162. /// the specified identifier.
  163. virtual ConstHostPtr
  164. get6(const SubnetID& subnet_id, const Host::IdentifierType& identifier_type,
  165. const uint8_t* identifier_begin, const size_t identifier_len) const;
  166. /// @brief Returns a host using the specified IPv6 prefix.
  167. ///
  168. /// @param prefix IPv6 prefix for which the @c Host object is searched.
  169. /// @param prefix_len IPv6 prefix length.
  170. ///
  171. /// @return Const @c Host object using a specified HW address or DUID.
  172. virtual ConstHostPtr
  173. get6(const asiolink::IOAddress& prefix, const uint8_t prefix_len) const;
  174. /// @brief Returns a host connected to the IPv6 subnet and having
  175. /// a reservation for a specified IPv6 address or prefix.
  176. ///
  177. /// @param subnet_id Subnet identifier.
  178. /// @param address reserved IPv6 address/prefix.
  179. ///
  180. /// @return Const @c Host object using a specified IPv6 address/prefix.
  181. virtual ConstHostPtr
  182. get6(const SubnetID& subnet_id, const asiolink::IOAddress& address) const;
  183. /// @brief Adds a new host to the collection.
  184. ///
  185. /// It is not possible to add a new host in radius backend.
  186. //
  187. /// The implementations of this method should guard against duplicate
  188. /// reservations for the same host, where possible. For example, when the
  189. /// reservation for the same HW address and subnet id is added twice, the
  190. /// addHost method should throw an DuplicateEntry exception. Note, that
  191. /// usually it is impossible to guard against adding duplicated host, where
  192. /// one instance is identified by HW address, another one by DUID.
  193. ///
  194. /// @param host Pointer to the new @c Host object being added.
  195. virtual void add(const HostPtr& host);
  196. /// @brief Attempts to delete a host by (subnet-id, address)
  197. ///
  198. /// It is not possible to delete a host in radius backend.
  199. ///
  200. /// This method supports both v4 and v6.
  201. ///
  202. /// @param subnet_id subnet identifier.
  203. /// @param addr specified address.
  204. /// @return true if deletion was successful, false if the host was not there.
  205. /// @throw various exceptions in case of errors
  206. virtual bool del(const SubnetID& subnet_id, const asiolink::IOAddress& addr);
  207. /// @brief Attempts to delete a host by (subnet4-id, identifier type, identifier)
  208. ///
  209. /// It is not possible to delete a host in radius backend.
  210. ///
  211. /// This method supports v4 hosts only.
  212. ///
  213. /// @param subnet_id subnet identifier.
  214. /// @param addr specified address.
  215. /// @return true if deletion was successful, false if the host was not there.
  216. /// @throw various exceptions in case of errors
  217. virtual bool del4(const SubnetID& subnet_id,
  218. const Host::IdentifierType& identifier_type,
  219. const uint8_t* identifier_begin, const size_t identifier_len);
  220. /// @brief Attempts to delete a host by (subnet6-id, identifier type, identifier)
  221. ///
  222. /// It is not possible to delete a host in radius backend.
  223. ///
  224. /// This method supports v6 hosts only.
  225. ///
  226. /// @param subnet_id subnet identifier.
  227. /// @param addr specified address.
  228. /// @return true if deletion was successful, false if the host was not there.
  229. /// @throw various exceptions in case of errors
  230. virtual bool del6(const SubnetID& subnet_id,
  231. const Host::IdentifierType& identifier_type,
  232. const uint8_t* identifier_begin, const size_t identifier_len);
  233. /// @brief Return backend type
  234. ///
  235. /// Returns the type of the backend (e.g. "radius", "memfile" etc.)
  236. ///
  237. /// @return Type of the backend.
  238. virtual std::string getType() const {
  239. return (std::string("radius"));
  240. }
  241. /// @brief Returns backend name.
  242. ///
  243. /// Each backend have specific name.
  244. ///
  245. /// @return "radius".
  246. virtual std::string getName() const;
  247. /// @brief Returns description of the backend.
  248. ///
  249. /// This description may be multiline text that describes the backend.
  250. ///
  251. /// @return Description of the backend.
  252. virtual std::string getDescription() const;
  253. /// @brief Returns backend version.
  254. ///
  255. /// @return Version number stored in the database, as a pair of unsigned
  256. /// integers. "first" is the major version number, "second" the
  257. /// minor number.
  258. ///
  259. /// @throw isc::dhcp::DbOperationError An operation on the open database
  260. /// has failed.
  261. virtual std::pair<uint32_t, uint32_t> getVersion() const;
  262. /// @brief Commit Transactions
  263. ///
  264. /// Not relevant for radius backend.
  265. ///
  266. /// Commits all pending database operations.
  267. virtual void commit();
  268. /// @brief Rollback Transactions
  269. ///
  270. /// Not relevant for radius backend.
  271. ///
  272. /// Rolls back all pending database operations.
  273. virtual void rollback();
  274. private:
  275. /// @brief Pointer to a Radius Client Handle
  276. rc_handle *rh;
  277. };
  278. }
  279. }
  280. #endif // RADIUS_HOST_DATA_SOURCE_H