diff --git a/doc/guide/hooks.xml b/doc/guide/hooks.xml index 645f749a3c..d68a018091 100644 --- a/doc/guide/hooks.xml +++ b/doc/guide/hooks.xml @@ -1340,13 +1340,17 @@ An example deletion by (subnet-id, identifier-type, identifier) looks as follows lease4-get - checks if an IPv4 lease with the specified parameters exists and returns it if it does; + + lease6-get - checks if an IPv6 lease with + the specified parameters exists and returns it if it does; + lease4-get-all - returns all IPv4 leases or IPv4 leases for specified subnets; - lease6-get - checks if an IPv6 lease with - the specified parameters exists and returns it if it does; + lease6-get-all - returns all IPv6 leases + or IPv6 leases for specified subnets; lease4-del - attempts to delete an IPv4 @@ -1663,11 +1667,12 @@ An example result returned when the host was found:
- lease4-get-all command - lease4-get-all is used to retrieve all IPv4 - leases or all leases for the specified set of subnets. All leases are - returned when there are no arguments specified with the command as - in the following example: + lease4-get-all, lease6-get-all commands + lease4-get-all or + lease6-get-all is used to retrieve all + IPv4 or IPv6 leases or all leases for the specified set of + subnets. All leases are returned when there are no arguments + specified with the command as in the following example: { "command": "lease4-get-all" @@ -1680,7 +1685,7 @@ An example result returned when the host was found: leases should be returned, e.g.: { - "command": "lease4-get-all", + "command": "lease6-get-all", "arguments": { "subnets": [ 1, 2, 3, 4 ] } @@ -1695,38 +1700,45 @@ An example result returned when the host was found: "arguments": { "leases": [ { - "client-id": "42:42:42:42:42:42:42:42", "cltt": 12345678, + "duid": "42:42:42:42:42:42:42:42", "fqdn-fwd": false, "fqdn-rev": true, "hostname": "myhost.example.com.", "hw-address": "08:08:08:08:08:08", - "ip-address": "192.0.2.1", + "iaid": 1, + "ip-address": "2001:db8:2::1", + "preferred-lft": 500, "state": 0, "subnet-id": 44, + "type": "IA_NA", "valid-lft": 3600 }, { - "client-id": "21:21:21:21:21:21:21:21", "cltt": 12345678, + "duid": "21:21:21:21:21:21:21:21", "fqdn-fwd": false, "fqdn-rev": true, "hostname": "", - "hw-address": "10:10:10:10:10:10", - "ip-address": "192.0.2.2", + "iaid": 1, + "ip-address": "2001:db8:0:0:2::", + "preferred-lft": 500, + "prefix-len": 80, "state": 0, "subnet-id": 44, + "type": "IA_PD", "valid-lft": 3600 } ] }, "result": 0, - "text": "2 IPv4 lease(s) found." + "text": "2 IPv6 lease(s) found." } - The lease4-get-command may result in very + The lease4-get-command or + lease6-get-command may result in very large responses. This may have negative impact on the DHCP server responsiveness while the response is generated and transmitted over the control channel, as the server imposes no restriction diff --git a/src/hooks/dhcp/lease_cmds/lease_cmds.cc b/src/hooks/dhcp/lease_cmds/lease_cmds.cc index 3eb38797d7..0c48e2046d 100644 --- a/src/hooks/dhcp/lease_cmds/lease_cmds.cc +++ b/src/hooks/dhcp/lease_cmds/lease_cmds.cc @@ -130,17 +130,18 @@ public: int leaseGetHandler(CalloutHandle& handle); - /// @brief lease4-get-all command handler + /// @brief lease4-get-all, lease6-get-all command handler /// - /// This command attempts to retrieve all IPv4 leases or all IPv4 leases - /// belonging to the particular subnets. If no subnet identifiers are - /// provided, it returns all IPv4 leases from the database. + /// This command attempts to retrieve all IPv4 or IPv6 leases, + /// or all IPv4 or all IPv6 leases belonging to the particular + /// subnets. If no subnet identifiers are provided, it returns all + /// IPv4 or IPv6 leases from the database. /// /// @param handle Callout context - which is expected to contain the /// get command JSON text in the "command" argument /// @return 0 upon success, non-zero otherwise. int - lease4GetAllHandler(CalloutHandle& handle); + leaseGetAllHandler(CalloutHandle& handle); /// @brief lease4-del command handler /// @@ -469,9 +470,11 @@ LeaseCmdsImpl::leaseGetHandler(CalloutHandle& handle) { } int -LeaseCmdsImpl::lease4GetAllHandler(CalloutHandle& handle) { +LeaseCmdsImpl::leaseGetAllHandler(CalloutHandle& handle) { + bool v4 = true; try { extractCommand(handle); + v4 = (cmd_name_ == "lease4-get-all"); ElementPtr leases_json = Element::createList(); @@ -491,11 +494,20 @@ LeaseCmdsImpl::lease4GetAllHandler(CalloutHandle& handle) { isc_throw(BadValue, "listed subnet identifiers must be numbers"); } - Lease4Collection leases = - LeaseMgrFactory::instance().getLeases4((*subnet_id)->intValue()); - for (auto lease = leases.begin(); lease != leases.end(); ++lease) { - ElementPtr lease_json = (*lease)->toElement(); - leases_json->add(lease_json); + if (v4) { + Lease4Collection leases = + LeaseMgrFactory::instance().getLeases4((*subnet_id)->intValue()); + for (auto lease = leases.begin(); lease != leases.end(); ++lease) { + ElementPtr lease_json = (*lease)->toElement(); + leases_json->add(lease_json); + } + } else { + Lease6Collection leases = + LeaseMgrFactory::instance().getLeases6((*subnet_id)->intValue()); + for (auto lease = leases.begin(); lease != leases.end(); ++lease) { + ElementPtr lease_json = (*lease)->toElement(); + leases_json->add(lease_json); + } } } @@ -505,19 +517,32 @@ LeaseCmdsImpl::lease4GetAllHandler(CalloutHandle& handle) { } else { // There is no 'subnets' argument so let's return all leases. - Lease4Collection leases = LeaseMgrFactory::instance().getLeases4(); - for (auto lease = leases.begin(); lease != leases.end(); ++lease) { - ElementPtr lease_json = (*lease)->toElement(); - leases_json->add(lease_json); + if (v4) { + Lease4Collection leases = LeaseMgrFactory::instance().getLeases4(); + for (auto lease = leases.begin(); lease != leases.end(); ++lease) { + ElementPtr lease_json = (*lease)->toElement(); + leases_json->add(lease_json); + } + } else { + Lease6Collection leases = LeaseMgrFactory::instance().getLeases6(); + for (auto lease = leases.begin(); lease != leases.end(); ++lease) { + ElementPtr lease_json = (*lease)->toElement(); + leases_json->add(lease_json); + } } } std::ostringstream s; - s << leases_json->size() << " IPv4 lease(s) found."; + s << leases_json->size() + << " IPv" << (v4 ? "4" : "6") + << " lease(s) found."; ElementPtr args = Element::createMap(); args->set("leases", leases_json); - ConstElementPtr response = createAnswer(CONTROL_RESULT_SUCCESS, - s.str(), args); + ConstElementPtr response = + createAnswer(leases_json->size() > 0 ? + CONTROL_RESULT_SUCCESS : + CONTROL_RESULT_EMPTY, + s.str(), args); setResponse(handle, response); @@ -782,8 +807,8 @@ LeaseCmds::leaseGetHandler(CalloutHandle& handle) { } int -LeaseCmds::lease4GetAllHandler(hooks::CalloutHandle& handle) { - return (impl_->lease4GetAllHandler(handle)); +LeaseCmds::leaseGetAllHandler(hooks::CalloutHandle& handle) { + return (impl_->leaseGetAllHandler(handle)); } int diff --git a/src/hooks/dhcp/lease_cmds/lease_cmds.h b/src/hooks/dhcp/lease_cmds/lease_cmds.h index 106ff92642..33d90106a6 100644 --- a/src/hooks/dhcp/lease_cmds/lease_cmds.h +++ b/src/hooks/dhcp/lease_cmds/lease_cmds.h @@ -1,4 +1,4 @@ -// Copyright (C) 2017 Internet Systems Consortium, Inc. ("ISC") +// Copyright (C) 2017-2018 Internet Systems Consortium, Inc. ("ISC") // // This Source Code Form is subject to the terms of the Mozilla Public // License, v. 2.0. If a copy of the MPL was not distributed with this @@ -131,13 +131,14 @@ public: int leaseGetHandler(hooks::CalloutHandle& handle); - /// @brief lease4-get-all command handler + /// @brief lease4-get-all, lease6-get-all command handler /// - /// This command attempts to retrieve all IPv4 leases or all IPv4 leases - /// belonging to the particular subnets. If no subnet identifiers are - /// provided, it returns all IPv4 leases from the database. + /// This command attempts to retrieve all IPv4 or IPv6 leases, + /// or all IPv4 or all IPv6 leases belonging to the particular + /// subnets. If no subnet identifiers are provided, it returns all + /// IPv4 or IPv6 leases from the database. /// - /// Example command for query by (subnet-ids): + /// Example command for IPv4 query by (subnet-ids): /// { /// "command": "lease4-get-all", /// "arguments": { @@ -145,16 +146,16 @@ public: /// } /// } /// - /// Example command for retrieving all leases: + /// Example command for retrieving all IPv6 leases: /// { - /// "command": "lease4-get-all", + /// "command": "lease6-get-all", /// } /// /// @param handle Callout context - which is expected to contain the /// get command JSON text in the "command" argument /// @return result of the operation. int - lease4GetAllHandler(hooks::CalloutHandle& handle); + leaseGetAllHandler(hooks::CalloutHandle& handle); /// @brief lease4-del command handler /// diff --git a/src/hooks/dhcp/lease_cmds/lease_cmds_callouts.cc b/src/hooks/dhcp/lease_cmds/lease_cmds_callouts.cc index 809c46d83e..2853ba55ce 100644 --- a/src/hooks/dhcp/lease_cmds/lease_cmds_callouts.cc +++ b/src/hooks/dhcp/lease_cmds/lease_cmds_callouts.cc @@ -53,17 +53,6 @@ int lease4_get(CalloutHandle& handle) { return(lease_cmds.leaseGetHandler(handle)); } -/// @brief This is a command callout for 'lease4-get-all' command. -/// -/// @param handle Callout handle used to retrieve a command and -/// provide a response. -/// @return 0 if this callout has been invoked successfully, -/// 1 otherwise. -int lease4_get_all(CalloutHandle& handle) { - LeaseCmds lease_cmds; - return (lease_cmds.lease4GetAllHandler(handle)); -} - /// @brief This is a command callout for 'lease6-get' command. /// /// @param handle Callout handle used to retrieve a command and @@ -75,6 +64,28 @@ int lease6_get(CalloutHandle& handle) { return(lease_cmds.leaseGetHandler(handle)); } +/// @brief This is a command callout for 'lease4-get-all' command. +/// +/// @param handle Callout handle used to retrieve a command and +/// provide a response. +/// @return 0 if this callout has been invoked successfully, +/// 1 if an error occurs, 2 if empty. +int lease4_get_all(CalloutHandle& handle) { + LeaseCmds lease_cmds; + return (lease_cmds.leaseGetAllHandler(handle)); +} + +/// @brief This is a command callout for 'lease6-get-all' command. +/// +/// @param handle Callout handle used to retrieve a command and +/// provide a response. +/// @return 0 if this callout has been invoked successfully, +/// 1 if an error occurs, 2 if empty. +int lease6_get_all(CalloutHandle& handle) { + LeaseCmds lease_cmds; + return (lease_cmds.leaseGetAllHandler(handle)); +} + /// @brief This is a command callout for 'lease4-del' command. /// /// @param handle Callout handle used to retrieve a command and @@ -151,6 +162,7 @@ int load(LibraryHandle& handle) { handle.registerCommandCallout("lease4-get", lease4_get); handle.registerCommandCallout("lease4-get-all", lease4_get_all); handle.registerCommandCallout("lease6-get", lease6_get); + handle.registerCommandCallout("lease6-get-all", lease6_get_all); handle.registerCommandCallout("lease4-del", lease4_del); handle.registerCommandCallout("lease6-del", lease6_del); handle.registerCommandCallout("lease4-update", lease4_update); diff --git a/src/hooks/dhcp/lease_cmds/tests/lease_cmds_unittest.cc b/src/hooks/dhcp/lease_cmds/tests/lease_cmds_unittest.cc index d60ebe8d4a..b593042c83 100644 --- a/src/hooks/dhcp/lease_cmds/tests/lease_cmds_unittest.cc +++ b/src/hooks/dhcp/lease_cmds/tests/lease_cmds_unittest.cc @@ -255,9 +255,11 @@ public: CfgMgr& cfg_mgr = CfgMgr::instance(); if (v6) { - Subnet6Ptr subnet6(new Subnet6(IOAddress("2001:db8::"), 48, 1, 2, 3, 4, 66)); + Subnet6Ptr subnet66(new Subnet6(IOAddress("2001:db8:1::"), 48, 1, 2, 3, 4, 66)); + Subnet6Ptr subnet99(new Subnet6(IOAddress("2001:db8:2::"), 48, 1, 2, 3, 4, 99)); CfgSubnets6Ptr subnets = cfg_mgr.getStagingCfg()->getCfgSubnets6(); - subnets->add(subnet6); + subnets->add(subnet66); + subnets->add(subnet99); cfg_mgr.commit(); } else { Subnet4Ptr subnet44(new Subnet4(IOAddress("192.0.2.0"), 24, 1, 2, 3, 44)); @@ -270,7 +272,10 @@ public: if (insert_lease) { if (v6) { - lmptr_->addLease(createLease6()); + lmptr_->addLease(createLease6("2001:db8:1::1", 66, 0x42)); + lmptr_->addLease(createLease6("2001:db8:1::2", 66, 0x56)); + lmptr_->addLease(createLease6("2001:db8:2::1", 99, 0x42)); + lmptr_->addLease(createLease6("2001:db8:2::2", 99, 0x56)); } else { lmptr_->addLease(createLease4("192.0.2.1", 44, 0x08, 0x42)); lmptr_->addLease(createLease4("192.0.2.2", 44, 0x09, 0x56)); @@ -287,7 +292,7 @@ public: /// /// @param ip_address IP address for the lease. /// @param subnet_id subnet identifier - /// @param hw_address_pattern value to be used for generating HW address by repating + /// @param hw_address_pattern value to be used for generating HW address by repeating /// it 6 times. /// @param client_id_pattern value to be used for generating client identifier by /// repeating it 8 times. @@ -318,24 +323,28 @@ public: /// @brief Creates an IPv6 lease /// - /// Lease parameters: ip-address = 2001:db8::1, duid = 77:77:77:77:77:77:77:77, - /// cltt = 12345678, subnet-id = 66, fqdn-fwd = false, fqdn-rev = true, - /// hostname = myhost.example.com preferred lifetime = 1800, + /// Lease parameters: cltt = 12345678, fqdn-fwd = false, fqdn-rev = true, + /// hostname = myhost.example.com, preferred lifetime = 1800, /// valid lifetime = 3600 /// + /// @param ip_address IP address for the lease. + /// @param subnet_id subnet identifier + /// @param duid_address_pattern value to be used for generating DUID by + /// repeating it 8 times /// @return Returns the lease created - Lease6Ptr createLease6() { + Lease6Ptr createLease6(const std::string& ip_address, const SubnetID& subnet_id, + const uint8_t duid_pattern) { Lease6Ptr lease(new Lease6()); - lease->addr_ = IOAddress("2001:db8::1"); + lease->addr_ = IOAddress(ip_address); lease->type_ = Lease::TYPE_NA; lease->prefixlen_ = 128; lease->iaid_ = 42; - lease->duid_ = DuidPtr(new DUID(vector(8, 0x77))); + lease->duid_ = DuidPtr(new DUID(vector(8, duid_pattern))); lease->preferred_lft_ = 1800; lease->valid_lft_ = 3600; lease->cltt_ = 12345678; - lease->subnet_id_ = 66; + lease->subnet_id_ = subnet_id;; lease->fqdn_fwd_ = true; lease->fqdn_rev_ = true; lease->hostname_ = "myhost.example.com."; @@ -415,6 +424,21 @@ public: ASSERT_TRUE(l); + // If the element is a list we need to retrieve the lease that + // we're interested in. + if (l->getType() == Element::list) { + std::vector e = l->listValue(); + for (auto it = e.begin(); it != e.end(); ++it) { + ConstElementPtr ip_address = (*it)->get("ip-address"); + if (ip_address && ip_address->stringValue() == ip) { + l = (*it); + break; + } + } + + ASSERT_TRUE(l); + } + ASSERT_TRUE(l->contains("ip-address")); EXPECT_EQ(ip, l->get("ip-address")->stringValue()); if (prefixlen != 0) { @@ -564,11 +588,11 @@ TEST_F(LeaseCmdsTest, Lease4AddBadParams) { " \"command\": \"lease4-add\",\n" " \"arguments\": {" " \"subnet-id\": 44,\n" - " \"ip-address\": \"2001:db8::1\",\n" + " \"ip-address\": \"2001:db8:1::1\",\n" " \"hw-address\": \"1a:1b:1c:1d:1e:1f\"\n" " }\n" "}"; - exp_rsp = "Non-IPv4 address specified: 2001:db8::1"; + exp_rsp = "Non-IPv4 address specified: 2001:db8:1::1"; testCommand(txt, CONTROL_RESULT_ERROR, exp_rsp); // currently defined states are 0,1 and 2. 123 is junk. @@ -695,7 +719,7 @@ TEST_F(LeaseCmdsTest, Lease6AddMissingParams) { "{\n" " \"command\": \"lease6-add\",\n" " \"arguments\": {" - " \"ip-address\": \"2001:db8::3\"\n" + " \"ip-address\": \"2001:db8:1::3\"\n" " }\n" "}"; exp_rsp = "missing parameter 'subnet-id' (:3:19)"; @@ -707,7 +731,7 @@ TEST_F(LeaseCmdsTest, Lease6AddMissingParams) { " \"command\": \"lease6-add\",\n" " \"arguments\": {" " \"subnet-id\": 66,\n" - " \"ip-address\": \"2001:db8::3\"\n" + " \"ip-address\": \"2001:db8:1::3\"\n" " }\n" "}"; exp_rsp = "missing parameter 'duid' (:3:19)"; @@ -745,7 +769,7 @@ TEST_F(LeaseCmdsTest, Lease6AddMissingParams) { " \"arguments\": {" " \"subnet-id\": 66,\n" " \"duid\": \"1a:1b:1c:1d:1e:1f\",\n" - " \"ip-address\": \"2001:db8::3\"\n" + " \"ip-address\": \"2001:db8:1::3\"\n" " }\n" "}"; exp_rsp = "missing parameter 'iaid' (:3:19)"; @@ -768,7 +792,7 @@ TEST_F(LeaseCmdsTest, Lease6AddBadParams) { " \"command\": \"lease6-add\",\n" " \"arguments\": {" " \"subnet-id\": 123,\n" - " \"ip-address\": \"2001:db8::3\",\n" + " \"ip-address\": \"2001:db8:1::3\",\n" " \"duid\": \"1a:1b:1c:1d:1e:1f\",\n" " \"iaid\": 1234\n" " }\n" @@ -787,7 +811,7 @@ TEST_F(LeaseCmdsTest, Lease6AddBadParams) { " \"iaid\": 1234\n" " }\n" "}"; - exp_rsp = "The address 3000::3 does not belong to subnet 2001:db8::/48, subnet-id=66"; + exp_rsp = "The address 3000::3 does not belong to subnet 2001:db8:1::/48, subnet-id=66"; testCommand(txt, CONTROL_RESULT_ERROR, exp_rsp); // v4? You're a time traveler from early 80s or what? @@ -810,7 +834,7 @@ TEST_F(LeaseCmdsTest, Lease6AddBadParams) { " \"command\": \"lease6-add\",\n" " \"arguments\": {" " \"subnet-id\": 66,\n" - " \"ip-address\": \"2001:db8::1\",\n" + " \"ip-address\": \"2001:db8:1::1\",\n" " \"duid\": \"1a:1b:1c:1d:1e:1f\",\n" " \"iaid\": 1234\n," " \"state\": 123\n" @@ -836,7 +860,7 @@ TEST_F(LeaseCmdsTest, Lease6Add) { " \"command\": \"lease6-add\",\n" " \"arguments\": {" " \"subnet-id\": 66,\n" - " \"ip-address\": \"2001:db8::3\",\n" + " \"ip-address\": \"2001:db8:1::3\",\n" " \"duid\": \"1a:1b:1c:1d:1e:1f\",\n" " \"iaid\": 1234\n" " }\n" @@ -845,7 +869,7 @@ TEST_F(LeaseCmdsTest, Lease6Add) { testCommand(txt, CONTROL_RESULT_SUCCESS, exp_rsp); // Now check that the lease is really there. - EXPECT_TRUE(lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8::3"))); + EXPECT_TRUE(lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8:1::3"))); } // Check that a simple, well formed prefix lease can be added. @@ -895,7 +919,7 @@ TEST_F(LeaseCmdsTest, Lease6AddFullAddr) { " \"command\": \"lease6-add\",\n" " \"arguments\": {" " \"subnet-id\": 66,\n" - " \"ip-address\": \"2001:db8::3\",\n" + " \"ip-address\": \"2001:db8:1::3\",\n" " \"duid\": \"01:02:03:04:05:06:07:08\",\n" " \"iaid\": 1234,\n" " \"hw-address\": \"1a:1b:1c:1d:1e:1f\",\n" @@ -911,10 +935,10 @@ TEST_F(LeaseCmdsTest, Lease6AddFullAddr) { testCommand(txt, CONTROL_RESULT_SUCCESS, exp_rsp); // Now check that the lease is really there. - Lease6Ptr l = lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8::3")); + Lease6Ptr l = lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8:1::3")); ASSERT_TRUE(l); EXPECT_EQ(Lease::TYPE_NA, l->type_); - EXPECT_EQ("2001:db8::3", l->addr_.toText()); + EXPECT_EQ("2001:db8:1::3", l->addr_.toText()); ASSERT_TRUE(l->hwaddr_); EXPECT_EQ("1a:1b:1c:1d:1e:1f", l->hwaddr_->toText(false)); ASSERT_TRUE(l->duid_); @@ -1013,10 +1037,10 @@ TEST_F(LeaseCmdsTest, Lease4GetByAddrBadParam) { "{\n" " \"command\": \"lease4-get\",\n" " \"arguments\": {" - " \"ip-address\": \"2001:db8::1\"" + " \"ip-address\": \"2001:db8:1::1\"" " }\n" "}"; - string exp_rsp = "Invalid IPv4 address specified: 2001:db8::1"; + string exp_rsp = "Invalid IPv4 address specified: 2001:db8:1::1"; testCommand(cmd, CONTROL_RESULT_ERROR, exp_rsp); // This is way off @@ -1126,208 +1150,6 @@ TEST_F(LeaseCmdsTest, Lease4GetByHWAddr) { checkLease4(lease, "192.0.2.1", 44, "08:08:08:08:08:08", false); } -// Checks that lease4-get-all returns all leases. -TEST_F(LeaseCmdsTest, Lease4GetAll) { - - // Initialize lease manager (false = v4, true = add a lease) - initLeaseMgr(false, true); - - // Query for all leases. - string cmd = - "{\n" - " \"command\": \"lease4-get-all\"\n" - "}"; - string exp_rsp = "4 IPv4 lease(s) found."; - ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); - - // Now check that the lease parameters were indeed returned. - ASSERT_TRUE(rsp); - - ConstElementPtr args = rsp->get("arguments"); - ASSERT_TRUE(args); - ASSERT_EQ(Element::map, args->getType()); - - ConstElementPtr leases = args->get("leases"); - ASSERT_TRUE(leases); - ASSERT_EQ(Element::list, leases->getType()); - - // Let's check if the response contains desired leases. - checkLease4(leases, "192.0.2.1", 44, "08:08:08:08:08:08", true); - checkLease4(leases, "192.0.2.2", 44, "09:09:09:09:09:09", true); - checkLease4(leases, "192.0.3.1", 88, "08:08:08:08:08:08", true); - checkLease4(leases, "192.0.3.2", 88, "09:09:09:09:09:09", true); -} - -// Checks that lease4-get-all returns empty set if no leases are found. -TEST_F(LeaseCmdsTest, Lease4GetAllNoLeases) { - - // Initialize lease manager (false = v4, false = do not add leasesxs) - initLeaseMgr(false, false); - - // Query for all leases. - string cmd = - "{\n" - " \"command\": \"lease4-get-all\"\n" - "}"; - string exp_rsp = "0 IPv4 lease(s) found."; - ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); - - // Now check that the lease parameters were indeed returned. - ASSERT_TRUE(rsp); - - ConstElementPtr args = rsp->get("arguments"); - ASSERT_TRUE(args); - ASSERT_EQ(Element::map, args->getType()); - - ConstElementPtr leases = args->get("leases"); - ASSERT_TRUE(leases); - ASSERT_EQ(Element::list, leases->getType()); - - EXPECT_EQ(0, leases->size()); -} - - -// Checks that lease4-get-all returns all leases for a subnet. -TEST_F(LeaseCmdsTest, Lease4GetAllBySubnetId) { - - // Initialize lease manager (false = v4, true = add leases) - initLeaseMgr(false, true); - - // Query for leases from subnet 44. Subnet 127 will be ignored because - // it doesn't contain any leases. - string cmd = - "{\n" - " \"command\": \"lease4-get-all\",\n" - " \"arguments\": {\n" - " \"subnets\": [ 44, 127 ]" - " }\n" - "}"; - string exp_rsp = "2 IPv4 lease(s) found."; - ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); - - // Now check that the lease parameters were indeed returned. - ASSERT_TRUE(rsp); - - ConstElementPtr args = rsp->get("arguments"); - ASSERT_TRUE(args); - ASSERT_EQ(Element::map, args->getType()); - - ConstElementPtr leases = args->get("leases"); - ASSERT_TRUE(leases); - ASSERT_EQ(Element::list, leases->getType()); - - // Let's check if the response contains desired leases. - checkLease4(leases, "192.0.2.1", 44, "08:08:08:08:08:08", true); - checkLease4(leases, "192.0.2.2", 44, "09:09:09:09:09:09", true); -} - -// Checks that lease4-get-all returns empty set when no leases are found. -TEST_F(LeaseCmdsTest, Lease4GetAllBySubnetIdNoLeases) { - - // Initialize lease manager (false = v4, true = do not add leases) - initLeaseMgr(false, false); - - // Query for leases from subnet 44. Subnet 127 will be ignored because - // it doesn't contain any leases. - string cmd = - "{\n" - " \"command\": \"lease4-get-all\",\n" - " \"arguments\": {\n" - " \"subnets\": [ 44, 127 ]" - " }\n" - "}"; - string exp_rsp = "0 IPv4 lease(s) found."; - ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); - - // Now check that the lease parameters were indeed returned. - ASSERT_TRUE(rsp); - - ConstElementPtr args = rsp->get("arguments"); - ASSERT_TRUE(args); - ASSERT_EQ(Element::map, args->getType()); - - ConstElementPtr leases = args->get("leases"); - ASSERT_TRUE(leases); - ASSERT_EQ(Element::list, leases->getType()); - - EXPECT_EQ(0, leases->size()); -} - -// Checks that lease4-get-all returns leases from multiple subnets. -TEST_F(LeaseCmdsTest, Lease4GetAllByMultipleSubnetIds) { - - // Initialize lease manager (false = v4, true = add a lease) - initLeaseMgr(false, true); - - // Query for leases from subnet 44 and 88. - string cmd = - "{\n" - " \"command\": \"lease4-get-all\",\n" - " \"arguments\": {\n" - " \"subnets\": [ 44, 88 ]" - " }\n" - "}"; - string exp_rsp = "4 IPv4 lease(s) found."; - ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); - - // Now check that the lease parameters were indeed returned. - ASSERT_TRUE(rsp); - - ConstElementPtr args = rsp->get("arguments"); - ASSERT_TRUE(args); - ASSERT_EQ(Element::map, args->getType()); - - ConstElementPtr leases = args->get("leases"); - ASSERT_TRUE(leases); - ASSERT_EQ(Element::list, leases->getType()); - - // Let's check if the response contains desired leases. - checkLease4(leases, "192.0.2.1", 44, "08:08:08:08:08:08", true); - checkLease4(leases, "192.0.2.2", 44, "09:09:09:09:09:09", true); - checkLease4(leases, "192.0.3.1", 88, "08:08:08:08:08:08", true); - checkLease4(leases, "192.0.3.2", 88, "09:09:09:09:09:09", true); -} - -// Checks that lease4-get-all checks its input arguments. -TEST_F(LeaseCmdsTest, Lease4GetBySubnetIdInvalidArguments) { - - // Initialize lease manager (false = v4, true = add a lease) - initLeaseMgr(false, true); - - // Subnets not specified in arguments. - string cmd = - "{\n" - " \"command\": \"lease4-get-all\",\n" - " \"arguments\": {" - " \"foo\": 1\n" - " }\n" - "}"; - string exp_rsp = "'subnets' parameter not specified"; - testCommand(cmd, CONTROL_RESULT_ERROR, exp_rsp); - - // Subnets are not a list. - cmd = - "{\n" - " \"command\": \"lease4-get-all\",\n" - " \"arguments\": {" - " \"subnets\": 1\n" - " }\n" - "}"; - exp_rsp = "'subnets' parameter must be a list"; - testCommand(cmd, CONTROL_RESULT_ERROR, exp_rsp); - - // Subnets list must contain numbers. - cmd = - "{\n" - " \"command\": \"lease4-get-all\",\n" - " \"arguments\": {" - " \"subnets\": [ \"x\", \"y\" ]\n" - " }\n" - "}"; - exp_rsp = "listed subnet identifiers must be numbers"; - testCommand(cmd, CONTROL_RESULT_ERROR, exp_rsp); -} - // Checks that lease6-get(addr) can handle a situation when // the query is correctly formed, but the lease is not there. TEST_F(LeaseCmdsTest, Lease6GetByAddr6NotFound) { @@ -1341,7 +1163,7 @@ TEST_F(LeaseCmdsTest, Lease6GetByAddr6NotFound) { " \"command\": \"lease6-get\",\n" " \"arguments\": {" " \"subnet-id\": 1,\n" - " \"ip-address\": \"2001:db8::2\"\n" + " \"ip-address\": \"2001:db8:1::10\"\n" " }\n" "}"; string exp_rsp = "Lease not found."; @@ -1452,7 +1274,7 @@ TEST_F(LeaseCmdsTest, Lease6GetByAddr) { "{\n" " \"command\": \"lease6-get\",\n" " \"arguments\": {\n" - " \"ip-address\": \"2001:db8::1\"\n" + " \"ip-address\": \"2001:db8:1::1\"\n" " }\n" "}"; string exp_rsp = "IPv6 lease found."; @@ -1465,7 +1287,7 @@ TEST_F(LeaseCmdsTest, Lease6GetByAddr) { ASSERT_TRUE(lease); // Now check that the lease was indeed returned. - checkLease6(lease, "2001:db8::1", 0, 66, "77:77:77:77:77:77:77:77", false); + checkLease6(lease, "2001:db8:1::1", 0, 66, "42:42:42:42:42:42:42:42", false); } // Checks that lease6-get sanitizes its input. @@ -1505,7 +1327,7 @@ TEST_F(LeaseCmdsTest, Lease6GetByAddrPrefix) { initLeaseMgr(true, false); // (true = v6, true = create a lease) // Let's start with regular address lease and make it a prefix lease. - Lease6Ptr l = createLease6(); + Lease6Ptr l = createLease6("2001:db8:1::1", 66, 0x77); l->addr_ = IOAddress("2001:db8:1234:ab::"); l->type_ = Lease::TYPE_PD; l->prefixlen_ = 56; @@ -1547,7 +1369,7 @@ TEST_F(LeaseCmdsTest, Lease6GetByDUID) { " \"subnet-id\": 66,\n" " \"iaid\": 42," " \"identifier-type\": \"duid\"," - " \"identifier\": \"77:77:77:77:77:77:77:77\"\n" + " \"identifier\": \"42:42:42:42:42:42:42:42\"\n" " }\n" "}"; string exp_rsp = "IPv6 lease found."; @@ -1560,7 +1382,411 @@ TEST_F(LeaseCmdsTest, Lease6GetByDUID) { ASSERT_TRUE(lease); // Now check that the lease was indeed returned. - checkLease6(lease, "2001:db8::1", 0, 66, "77:77:77:77:77:77:77:77", false); + checkLease6(lease, "2001:db8:1::1", 0, 66, "42:42:42:42:42:42:42:42", false); +} + +// Checks that lease4-get-all returns all leases. +TEST_F(LeaseCmdsTest, Lease4GetAll) { + + // Initialize lease manager (false = v4, true = add a lease) + initLeaseMgr(false, true); + + // Query for all leases. + string cmd = + "{\n" + " \"command\": \"lease4-get-all\"\n" + "}"; + string exp_rsp = "4 IPv4 lease(s) found."; + ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); + + // Now check that the lease parameters were indeed returned. + ASSERT_TRUE(rsp); + + ConstElementPtr args = rsp->get("arguments"); + ASSERT_TRUE(args); + ASSERT_EQ(Element::map, args->getType()); + + ConstElementPtr leases = args->get("leases"); + ASSERT_TRUE(leases); + ASSERT_EQ(Element::list, leases->getType()); + + // Let's check if the response contains desired leases. + checkLease4(leases, "192.0.2.1", 44, "08:08:08:08:08:08", true); + checkLease4(leases, "192.0.2.2", 44, "09:09:09:09:09:09", true); + checkLease4(leases, "192.0.3.1", 88, "08:08:08:08:08:08", true); + checkLease4(leases, "192.0.3.2", 88, "09:09:09:09:09:09", true); +} + +// Checks that lease4-get-all returns empty set if no leases are found. +TEST_F(LeaseCmdsTest, Lease4GetAllNoLeases) { + + // Initialize lease manager (false = v4, false = do not add leasesxs) + initLeaseMgr(false, false); + + // Query for all leases. + string cmd = + "{\n" + " \"command\": \"lease4-get-all\"\n" + "}"; + string exp_rsp = "0 IPv4 lease(s) found."; + ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_EMPTY, exp_rsp); + + // Now check that the lease parameters were indeed returned. + ASSERT_TRUE(rsp); + + ConstElementPtr args = rsp->get("arguments"); + ASSERT_TRUE(args); + ASSERT_EQ(Element::map, args->getType()); + + ConstElementPtr leases = args->get("leases"); + ASSERT_TRUE(leases); + ASSERT_EQ(Element::list, leases->getType()); + + EXPECT_EQ(0, leases->size()); +} + + +// Checks that lease4-get-all returns all leases for a subnet. +TEST_F(LeaseCmdsTest, Lease4GetAllBySubnetId) { + + // Initialize lease manager (false = v4, true = add leases) + initLeaseMgr(false, true); + + // Query for leases from subnet 44. Subnet 127 will be ignored because + // it doesn't contain any leases. + string cmd = + "{\n" + " \"command\": \"lease4-get-all\",\n" + " \"arguments\": {\n" + " \"subnets\": [ 44, 127 ]" + " }\n" + "}"; + string exp_rsp = "2 IPv4 lease(s) found."; + ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); + + // Now check that the lease parameters were indeed returned. + ASSERT_TRUE(rsp); + + ConstElementPtr args = rsp->get("arguments"); + ASSERT_TRUE(args); + ASSERT_EQ(Element::map, args->getType()); + + ConstElementPtr leases = args->get("leases"); + ASSERT_TRUE(leases); + ASSERT_EQ(Element::list, leases->getType()); + + // Let's check if the response contains desired leases. + checkLease4(leases, "192.0.2.1", 44, "08:08:08:08:08:08", true); + checkLease4(leases, "192.0.2.2", 44, "09:09:09:09:09:09", true); +} + +// Checks that lease4-get-all returns empty set when no leases are found. +TEST_F(LeaseCmdsTest, Lease4GetAllBySubnetIdNoLeases) { + + // Initialize lease manager (false = v4, true = do not add leases) + initLeaseMgr(false, false); + + // Query for leases from subnet 44. Subnet 127 will be ignored because + // it doesn't contain any leases. + string cmd = + "{\n" + " \"command\": \"lease4-get-all\",\n" + " \"arguments\": {\n" + " \"subnets\": [ 44, 127 ]" + " }\n" + "}"; + string exp_rsp = "0 IPv4 lease(s) found."; + ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_EMPTY, exp_rsp); + + // Now check that the lease parameters were indeed returned. + ASSERT_TRUE(rsp); + + ConstElementPtr args = rsp->get("arguments"); + ASSERT_TRUE(args); + ASSERT_EQ(Element::map, args->getType()); + + ConstElementPtr leases = args->get("leases"); + ASSERT_TRUE(leases); + ASSERT_EQ(Element::list, leases->getType()); + + EXPECT_EQ(0, leases->size()); +} + +// Checks that lease4-get-all returns leases from multiple subnets. +TEST_F(LeaseCmdsTest, Lease4GetAllByMultipleSubnetIds) { + + // Initialize lease manager (false = v4, true = add a lease) + initLeaseMgr(false, true); + + // Query for leases from subnet 44 and 88. + string cmd = + "{\n" + " \"command\": \"lease4-get-all\",\n" + " \"arguments\": {\n" + " \"subnets\": [ 44, 88 ]" + " }\n" + "}"; + string exp_rsp = "4 IPv4 lease(s) found."; + ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); + + // Now check that the lease parameters were indeed returned. + ASSERT_TRUE(rsp); + + ConstElementPtr args = rsp->get("arguments"); + ASSERT_TRUE(args); + ASSERT_EQ(Element::map, args->getType()); + + ConstElementPtr leases = args->get("leases"); + ASSERT_TRUE(leases); + ASSERT_EQ(Element::list, leases->getType()); + + // Let's check if the response contains desired leases. + checkLease4(leases, "192.0.2.1", 44, "08:08:08:08:08:08", true); + checkLease4(leases, "192.0.2.2", 44, "09:09:09:09:09:09", true); + checkLease4(leases, "192.0.3.1", 88, "08:08:08:08:08:08", true); + checkLease4(leases, "192.0.3.2", 88, "09:09:09:09:09:09", true); +} + +// Checks that lease4-get-all checks its input arguments. +TEST_F(LeaseCmdsTest, Lease4GetBySubnetIdInvalidArguments) { + + // Initialize lease manager (false = v4, true = add a lease) + initLeaseMgr(false, true); + + // Subnets not specified in arguments. + string cmd = + "{\n" + " \"command\": \"lease4-get-all\",\n" + " \"arguments\": {" + " \"foo\": 1\n" + " }\n" + "}"; + string exp_rsp = "'subnets' parameter not specified"; + testCommand(cmd, CONTROL_RESULT_ERROR, exp_rsp); + + // Subnets are not a list. + cmd = + "{\n" + " \"command\": \"lease4-get-all\",\n" + " \"arguments\": {" + " \"subnets\": 1\n" + " }\n" + "}"; + exp_rsp = "'subnets' parameter must be a list"; + testCommand(cmd, CONTROL_RESULT_ERROR, exp_rsp); + + // Subnets list must contain numbers. + cmd = + "{\n" + " \"command\": \"lease4-get-all\",\n" + " \"arguments\": {" + " \"subnets\": [ \"x\", \"y\" ]\n" + " }\n" + "}"; + exp_rsp = "listed subnet identifiers must be numbers"; + testCommand(cmd, CONTROL_RESULT_ERROR, exp_rsp); +} + +// Checks that lease6-get-all returns all leases. +TEST_F(LeaseCmdsTest, Lease6GetAll) { + + // Initialize lease manager (true = v6, true = add a lease) + initLeaseMgr(true, true); + + // Query for all leases. + string cmd = + "{\n" + " \"command\": \"lease6-get-all\"\n" + "}"; + string exp_rsp = "4 IPv6 lease(s) found."; + ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); + + // Now check that the lease parameters were indeed returned. + ASSERT_TRUE(rsp); + + ConstElementPtr args = rsp->get("arguments"); + ASSERT_TRUE(args); + ASSERT_EQ(Element::map, args->getType()); + + ConstElementPtr leases = args->get("leases"); + ASSERT_TRUE(leases); + ASSERT_EQ(Element::list, leases->getType()); + + // Let's check if the response contains desired leases. + checkLease6(leases, "2001:db8:1::1", 0, 66, "42:42:42:42:42:42:42:42", false); + checkLease6(leases, "2001:db8:1::2", 0, 66, "56:56:56:56:56:56:56:56", false); + checkLease6(leases, "2001:db8:2::1", 0, 99, "42:42:42:42:42:42:42:42", false); + checkLease6(leases, "2001:db8:2::2", 0, 99, "56:56:56:56:56:56:56:56", false); +} + +// Checks that lease6-get-all returns empty set if no leases are found. +TEST_F(LeaseCmdsTest, Lease6GetAllNoLeases) { + + // Initialize lease manager (true = v6, false = do not add leasesxs) + initLeaseMgr(true, false); + + // Query for all leases. + string cmd = + "{\n" + " \"command\": \"lease6-get-all\"\n" + "}"; + string exp_rsp = "0 IPv6 lease(s) found."; + ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_EMPTY, exp_rsp); + + // Now check that the lease parameters were indeed returned. + ASSERT_TRUE(rsp); + + ConstElementPtr args = rsp->get("arguments"); + ASSERT_TRUE(args); + ASSERT_EQ(Element::map, args->getType()); + + ConstElementPtr leases = args->get("leases"); + ASSERT_TRUE(leases); + ASSERT_EQ(Element::list, leases->getType()); + + EXPECT_EQ(0, leases->size()); +} + + +// Checks that lease6-get-all returns all leases for a subnet. +TEST_F(LeaseCmdsTest, Lease6GetAllBySubnetId) { + + // Initialize lease manager (true = v6, true = add leases) + initLeaseMgr(true, true); + + // Query for leases from subnet 66. Subnet 127 will be ignored because + // it doesn't contain any leases. + string cmd = + "{\n" + " \"command\": \"lease6-get-all\",\n" + " \"arguments\": {\n" + " \"subnets\": [ 66, 127 ]" + " }\n" + "}"; + string exp_rsp = "2 IPv6 lease(s) found."; + ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); + + // Now check that the lease parameters were indeed returned. + ASSERT_TRUE(rsp); + + ConstElementPtr args = rsp->get("arguments"); + ASSERT_TRUE(args); + ASSERT_EQ(Element::map, args->getType()); + + ConstElementPtr leases = args->get("leases"); + ASSERT_TRUE(leases); + ASSERT_EQ(Element::list, leases->getType()); + + // Let's check if the response contains desired leases. + checkLease6(leases, "2001:db8:1::1", 0, 66, "42:42:42:42:42:42:42:42", false); + checkLease6(leases, "2001:db8:1::2", 0, 66, "56:56:56:56:56:56:56:56", false); +} + +// Checks that lease6-get-all returns empty set when no leases are found. +TEST_F(LeaseCmdsTest, Lease6GetAllBySubnetIdNoLeases) { + + // Initialize lease manager (true = v6, true = do not add leases) + initLeaseMgr(true, false); + + // Query for leases from subnet 66. Subnet 127 will be ignored because + // it doesn't contain any leases. + string cmd = + "{\n" + " \"command\": \"lease6-get-all\",\n" + " \"arguments\": {\n" + " \"subnets\": [ 66, 127 ]" + " }\n" + "}"; + string exp_rsp = "0 IPv6 lease(s) found."; + ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_EMPTY, exp_rsp); + + // Now check that the lease parameters were indeed returned. + ASSERT_TRUE(rsp); + + ConstElementPtr args = rsp->get("arguments"); + ASSERT_TRUE(args); + ASSERT_EQ(Element::map, args->getType()); + + ConstElementPtr leases = args->get("leases"); + ASSERT_TRUE(leases); + ASSERT_EQ(Element::list, leases->getType()); + + EXPECT_EQ(0, leases->size()); +} + +// Checks that lease6-get-all returns leases from multiple subnets. +TEST_F(LeaseCmdsTest, Lease6GetAllByMultipleSubnetIds) { + + // Initialize lease manager (true = v6, true = add a lease) + initLeaseMgr(true, true); + + // Query for leases from subnet 66 and 99. + string cmd = + "{\n" + " \"command\": \"lease6-get-all\",\n" + " \"arguments\": {\n" + " \"subnets\": [ 66, 99 ]" + " }\n" + "}"; + string exp_rsp = "4 IPv6 lease(s) found."; + ConstElementPtr rsp = testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); + + // Now check that the lease parameters were indeed returned. + ASSERT_TRUE(rsp); + + ConstElementPtr args = rsp->get("arguments"); + ASSERT_TRUE(args); + ASSERT_EQ(Element::map, args->getType()); + + ConstElementPtr leases = args->get("leases"); + ASSERT_TRUE(leases); + ASSERT_EQ(Element::list, leases->getType()); + + // Let's check if the response contains desired leases. + checkLease6(leases, "2001:db8:1::1", 0, 66, "42:42:42:42:42:42:42:42", false); + checkLease6(leases, "2001:db8:1::2", 0, 66, "56:56:56:56:56:56:56:56", false); + checkLease6(leases, "2001:db8:2::1", 0, 99, "42:42:42:42:42:42:42:42", false); + checkLease6(leases, "2001:db8:2::2", 0, 99, "56:56:56:56:56:56:56:56", false); +} + +// Checks that lease6-get-all checks its input arguments. +TEST_F(LeaseCmdsTest, Lease6GetBySubnetIdInvalidArguments) { + + // Initialize lease manager (true = v6, true = add a lease) + initLeaseMgr(true, true); + + // Subnets not specified in arguments. + string cmd = + "{\n" + " \"command\": \"lease6-get-all\",\n" + " \"arguments\": {" + " \"foo\": 1\n" + " }\n" + "}"; + string exp_rsp = "'subnets' parameter not specified"; + testCommand(cmd, CONTROL_RESULT_ERROR, exp_rsp); + + // Subnets are not a list. + cmd = + "{\n" + " \"command\": \"lease6-get-all\",\n" + " \"arguments\": {" + " \"subnets\": 1\n" + " }\n" + "}"; + exp_rsp = "'subnets' parameter must be a list"; + testCommand(cmd, CONTROL_RESULT_ERROR, exp_rsp); + + // Subnets list must contain numbers. + cmd = + "{\n" + " \"command\": \"lease6-get-all\",\n" + " \"arguments\": {" + " \"subnets\": [ \"x\", \"y\" ]\n" + " }\n" + "}"; + exp_rsp = "listed subnet identifiers must be numbers"; + testCommand(cmd, CONTROL_RESULT_ERROR, exp_rsp); } // Test checks if lease4-update handler refuses calls with missing parameters. @@ -1660,11 +1886,11 @@ TEST_F(LeaseCmdsTest, Lease4UpdateBadParams) { " \"command\": \"lease4-update\",\n" " \"arguments\": {" " \"subnet-id\": 44,\n" - " \"ip-address\": \"2001:db8::1\",\n" + " \"ip-address\": \"2001:db8:1::1\",\n" " \"hw-address\": \"1a:1b:1c:1d:1e:1f\"\n" " }\n" "}"; - exp_rsp = "Non-IPv4 address specified: 2001:db8::1"; + exp_rsp = "Non-IPv4 address specified: 2001:db8:1::1"; testCommand(txt, CONTROL_RESULT_ERROR, exp_rsp); } @@ -1750,7 +1976,7 @@ TEST_F(LeaseCmdsTest, Lease6UpdateMissingParams) { "{\n" " \"command\": \"lease6-update\",\n" " \"arguments\": {" - " \"ip-address\": \"2001:db8::1\"\n" + " \"ip-address\": \"2001:db8:1::1\"\n" " }\n" "}"; exp_rsp = "missing parameter 'subnet-id' (:3:19)"; @@ -1762,7 +1988,7 @@ TEST_F(LeaseCmdsTest, Lease6UpdateMissingParams) { " \"command\": \"lease6-update\",\n" " \"arguments\": {" " \"subnet-id\": 44,\n" - " \"ip-address\": \"2001:db8::1\"\n" + " \"ip-address\": \"2001:db8:1::1\"\n" " }\n" "}"; exp_rsp = "missing parameter 'duid' (:3:19)"; @@ -1798,7 +2024,7 @@ TEST_F(LeaseCmdsTest, Lease6UpdateBadParams) { " \"command\": \"lease6-update\",\n" " \"arguments\": {" " \"subnet-id\": 123,\n" - " \"ip-address\": \"2001:db8::1\",\n" + " \"ip-address\": \"2001:db8:1::1\",\n" " \"duid\": \"88:88:88:88:88:88:88:88\"\n" " }\n" "}"; @@ -1815,7 +2041,7 @@ TEST_F(LeaseCmdsTest, Lease6UpdateBadParams) { " \"duid\": \"88:88:88:88:88:88:88:88\"\n" " }\n" "}"; - exp_rsp = "The address 3000::1 does not belong to subnet 2001:db8::/48, subnet-id=66"; + exp_rsp = "The address 3000::1 does not belong to subnet 2001:db8:1::/48, subnet-id=66"; testCommand(txt, CONTROL_RESULT_ERROR, exp_rsp); // Nope, can't do v4 address in v6 lease. @@ -1848,7 +2074,7 @@ TEST_F(LeaseCmdsTest, Lease6Update) { " \"command\": \"lease6-update\",\n" " \"arguments\": {" " \"subnet-id\": 66,\n" - " \"ip-address\": \"2001:db8::1\",\n" + " \"ip-address\": \"2001:db8:1::1\",\n" " \"iaid\": 7654321,\n" " \"duid\": \"88:88:88:88:88:88:88:88\",\n" " \"hostname\": \"newhostname.example.org\"" @@ -1858,7 +2084,7 @@ TEST_F(LeaseCmdsTest, Lease6Update) { testCommand(txt, CONTROL_RESULT_SUCCESS, exp_rsp); // Now check that the lease is really there. - Lease6Ptr l = lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8::1")); + Lease6Ptr l = lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8:1::1")); ASSERT_TRUE(l); // Make sure the lease has been updated. @@ -1885,13 +2111,13 @@ TEST_F(LeaseCmdsTest, Lease6UpdateNoLease) { " \"command\": \"lease6-update\",\n" " \"arguments\": {" " \"subnet-id\": 66,\n" - " \"ip-address\": \"2001:db8::1\",\n" + " \"ip-address\": \"2001:db8:1::1\",\n" " \"iaid\": 7654321,\n" " \"duid\": \"88:88:88:88:88:88:88:88\",\n" " \"hostname\": \"newhostname.example.org\"" " }\n" "}"; - string exp_rsp = "failed to update the lease with address 2001:db8::1 - no such lease"; + string exp_rsp = "failed to update the lease with address 2001:db8:1::1 - no such lease"; testCommand(txt, CONTROL_RESULT_ERROR, exp_rsp); } @@ -2025,10 +2251,10 @@ TEST_F(LeaseCmdsTest, Lease4DelByAddrBadParam) { "{\n" " \"command\": \"lease4-del\",\n" " \"arguments\": {" - " \"ip-address\": \"2001:db8::1\"" + " \"ip-address\": \"2001:db8:1::1\"" " }\n" "}"; - string exp_rsp = "Invalid IPv4 address specified: 2001:db8::1"; + string exp_rsp = "Invalid IPv4 address specified: 2001:db8:1::1"; testCommand(cmd, CONTROL_RESULT_ERROR, exp_rsp); // This is way off @@ -2149,7 +2375,7 @@ TEST_F(LeaseCmdsTest, Lease6DelByAddr6NotFound) { " \"command\": \"lease6-del\",\n" " \"arguments\": {" " \"subnet-id\": 1,\n" - " \"ip-address\": \"2001:db8::2\"\n" + " \"ip-address\": \"2001:db8:1::10\"\n" " }\n" "}"; string exp_rsp = "IPv6 lease not found."; @@ -2183,7 +2409,7 @@ TEST_F(LeaseCmdsTest, Lease6DelByDuidNotFound) { testCommand(cmd, CONTROL_RESULT_EMPTY, exp_rsp); // Make sure the lease is still there. - EXPECT_TRUE(lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8::1"))); + EXPECT_TRUE(lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8:1::1"))); } // Checks that lease6-del(subnet-id, addr6) can handle a situation when @@ -2198,7 +2424,7 @@ TEST_F(LeaseCmdsTest, Lease6DelByAddr) { " \"command\": \"lease6-del\",\n" " \"arguments\": {" " \"subnet-id\": 66,\n" - " \"ip-address\": \"2001:db8::1\"" + " \"ip-address\": \"2001:db8:1::1\"" " }\n" "}"; string exp_rsp = "IPv6 lease deleted."; @@ -2207,7 +2433,7 @@ TEST_F(LeaseCmdsTest, Lease6DelByAddr) { testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); // Make sure the lease is really gone. - EXPECT_FALSE(lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8::1"))); + EXPECT_FALSE(lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8:1::1"))); } // Checks that lease6-del sanitizes its input. @@ -2246,7 +2472,7 @@ TEST_F(LeaseCmdsTest, Lease6DelByAddrPrefix) { initLeaseMgr(true, false); // (true = v6, false = don't add any leases) // Let's start with regular address lease and make it a prefix lease. - Lease6Ptr l = createLease6(); + Lease6Ptr l = createLease6("2001:db8:1::1", 66, 0x77); l->addr_ = IOAddress("2001:db8:1234:ab::"); l->type_ = Lease::TYPE_PD; l->prefixlen_ = 56; @@ -2284,7 +2510,7 @@ TEST_F(LeaseCmdsTest, Lease6DelByDUID) { " \"subnet-id\": 66,\n" " \"iaid\": 42," " \"identifier-type\": \"duid\"," - " \"identifier\": \"77:77:77:77:77:77:77:77\"\n" + " \"identifier\": \"42:42:42:42:42:42:42:42\"\n" " }\n" "}"; string exp_rsp = "IPv6 lease deleted."; @@ -2293,7 +2519,7 @@ TEST_F(LeaseCmdsTest, Lease6DelByDUID) { testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); // Make sure the lease is really gone. - EXPECT_FALSE(lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8::1"))); + EXPECT_FALSE(lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8:1::1"))); } // Checks that lease4-wipe detects missing parmameter properly. @@ -2382,13 +2608,13 @@ TEST_F(LeaseCmdsTest, Lease6Wipe) { " \"subnet-id\": 66\n" " }\n" "}"; - string exp_rsp = "Deleted 1 IPv6 lease(s)."; + string exp_rsp = "Deleted 2 IPv6 lease(s)."; // The status expected is success. The lease should be deleted. testCommand(cmd, CONTROL_RESULT_SUCCESS, exp_rsp); // Make sure the lease is really gone. - EXPECT_FALSE(lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8::1"))); + EXPECT_FALSE(lmptr_->getLease6(Lease::TYPE_NA, IOAddress("2001:db8:1::1"))); } // Checks that lease4-wipe properly reports when no leases were deleted. diff --git a/src/lib/dhcpsrv/cql_lease_mgr.cc b/src/lib/dhcpsrv/cql_lease_mgr.cc index 5036044b75..5dcdfd8f9b 100644 --- a/src/lib/dhcpsrv/cql_lease_mgr.cc +++ b/src/lib/dhcpsrv/cql_lease_mgr.cc @@ -1718,6 +1718,16 @@ CqlLeaseMgr::getLeases6(Lease::Type lease_type, const DUID &duid, uint32_t iaid, return (result); } +Lease6Collection +CqlLeaseMgr::getLeases6(SubnetID) const { + isc_throw(NotImplemented, "getLeases6(subnet_id) is not implemented"); +} + +Lease6Collection +CqlLeaseMgr::getLeases6() const { + isc_throw(NotImplemented, "getLeases6() is not implemented"); +} + void CqlLeaseMgr::getExpiredLeases4(Lease4Collection &expired_leases, const size_t max_leases) const { diff --git a/src/lib/dhcpsrv/cql_lease_mgr.h b/src/lib/dhcpsrv/cql_lease_mgr.h index f8ffd82d68..af0097289c 100644 --- a/src/lib/dhcpsrv/cql_lease_mgr.h +++ b/src/lib/dhcpsrv/cql_lease_mgr.h @@ -267,6 +267,19 @@ public: const DUID& duid, uint32_t iaid, SubnetID subnet_id) const override; + + /// @brief Returns all IPv6 leases for the particular subnet identifier. + /// + /// @param subnet_id subnet identifier. + /// + /// @return Lease collection (may be empty if no IPv6 lease found). + virtual Lease6Collection getLeases6(SubnetID subnet_id) const; + + /// @brief Returns all IPv6 leases. + /// + /// @return Lease collection (may be empty if no IPv6 lease found). + virtual Lease6Collection getLeases6() const; + /// @brief Returns a collection of expired DHCPv6 leases. /// /// This method returns at most @c max_leases expired leases. The leases @@ -316,7 +329,7 @@ public: /// @param lease6 The lease to be updated. /// /// @throw isc::dhcp::NoSuchLease Attempt to update a lease that did not - /// exist. + /// @throw isc::dhcp::DbOperationError An operation on the open database has /// failed. virtual void updateLease6(const Lease6Ptr& lease6) override; diff --git a/src/lib/dhcpsrv/dhcpsrv_messages.mes b/src/lib/dhcpsrv/dhcpsrv_messages.mes index ad5a7d40f3..8e3c7cfebd 100644 --- a/src/lib/dhcpsrv/dhcpsrv_messages.mes +++ b/src/lib/dhcpsrv/dhcpsrv_messages.mes @@ -463,6 +463,10 @@ in the message. A debug message issued when the server is attempting to obtain all IPv4 leases from the memory file database. +% DHCPSRV_MEMFILE_GET6 obtaining all IPv6 leases +A debug message issued when the server is attempting to obtain all IPv6 +leases from the memory file database. + % DHCPSRV_MEMFILE_GET_ADDR4 obtaining IPv4 lease for address %1 A debug message issued when the server is attempting to obtain an IPv4 lease from the memory file database for the specified address. @@ -510,6 +514,10 @@ lease from the memory file database for a client with the specified IAID A debug message issued when the server is attempting to obtain all IPv4 leases for a given subnet identifier from the memory file database. +% DHCPSRV_MEMFILE_GET_SUBID6 obtaining IPv6 leases for subnet ID %1 +A debug message issued when the server is attempting to obtain all IPv6 +leases for a given subnet identifier from the memory file database. + % DHCPSRV_MEMFILE_GET_SUBID_CLIENTID obtaining IPv4 lease for subnet ID %1 and client ID %2 A debug message issued when the server is attempting to obtain an IPv4 lease from the memory file database for a client with the specified @@ -697,6 +705,10 @@ exit code. This is most likely due to a network issue. A debug message issued when the server is attempting to obtain all IPv4 leases from the MySQL database. +% DHCPSRV_MYSQL_GET6 obtaining all IPv6 leases +A debug message issued when the server is attempting to obtain all IPv6 +leases from the MySQL database. + % DHCPSRV_MYSQL_GET_ADDR4 obtaining IPv4 lease for address %1 A debug message issued when the server is attempting to obtain an IPv4 lease from the MySQL database for the specified address. @@ -739,6 +751,10 @@ lease from the MySQL database for a client with the specified IAID A debug message issued when the server is attempting to obtain all IPv4 leases for a given subnet identifier from the MySQL database. +% DHCPSRV_MYSQL_GET_SUBID6 obtaining IPv6 leases for subnet ID %1 +A debug message issued when the server is attempting to obtain all IPv6 +leases for a given subnet identifier from the MySQL database. + % DHCPSRV_MYSQL_GET_SUBID_CLIENTID obtaining IPv4 lease for subnet ID %1 and client ID %2 A debug message issued when the server is attempting to obtain an IPv4 lease from the MySQL database for a client with the specified subnet ID @@ -859,6 +875,10 @@ exit code. This is most likely due to a network issue. A debug message issued when the server is attempting to obtain all IPv4 leases from the PostgreSQL database. +% DHCPSRV_PGSQL_GET6 obtaining all IPv6 leases +A debug message issued when the server is attempting to obtain all IPv6 +leases from the PostgreSQL database. + % DHCPSRV_PGSQL_GET_ADDR4 obtaining IPv4 lease for address %1 A debug message issued when the server is attempting to obtain an IPv4 lease from the PostgreSQL database for the specified address. @@ -901,6 +921,10 @@ lease from the PostgreSQL database for a client with the specified IAID A debug message issued when the server is attempting to obtain all IPv4 leases for a given subnet identifier from the PostgreSQL database. +% DHCPSRV_PGSQL_GET_SUBID6 obtaining IPv6 leases for subnet ID %1 +A debug message issued when the server is attempting to obtain all IPv6 +leases for a given subnet identifier from the PostgreSQL database. + % DHCPSRV_PGSQL_GET_SUBID_CLIENTID obtaining IPv4 lease for subnet ID %1 and client ID %2 A debug message issued when the server is attempting to obtain an IPv4 lease from the PostgreSQL database for a client with the specified subnet ID diff --git a/src/lib/dhcpsrv/lease_mgr.h b/src/lib/dhcpsrv/lease_mgr.h index 9bac9e6fc3..f7775845bd 100644 --- a/src/lib/dhcpsrv/lease_mgr.h +++ b/src/lib/dhcpsrv/lease_mgr.h @@ -341,6 +341,18 @@ public: Lease6Ptr getLease6(Lease::Type type, const DUID& duid, uint32_t iaid, SubnetID subnet_id) const; + /// @brief Returns all IPv6 leases for the particular subnet identifier. + /// + /// @param subnet_id subnet identifier. + /// + /// @return Lease collection (may be empty if no IPv6 lease found). + virtual Lease6Collection getLeases6(SubnetID subnet_id) const = 0; + + /// @brief Returns all IPv6 leases. + /// + /// @return Lease collection (may be empty if no IPv6 lease found). + virtual Lease6Collection getLeases6() const = 0; + /// @brief Returns a collection of expired DHCPv6 leases. /// /// This method returns at most @c max_leases expired leases. The leases diff --git a/src/lib/dhcpsrv/memfile_lease_mgr.cc b/src/lib/dhcpsrv/memfile_lease_mgr.cc index 1a26b44668..61aaf577b1 100644 --- a/src/lib/dhcpsrv/memfile_lease_mgr.cc +++ b/src/lib/dhcpsrv/memfile_lease_mgr.cc @@ -831,6 +831,36 @@ Memfile_LeaseMgr::getLeases6(Lease::Type type, return (collection); } +Lease6Collection +Memfile_LeaseMgr::getLeases6(SubnetID subnet_id) const { + LOG_DEBUG(dhcpsrv_logger, DHCPSRV_DBG_TRACE_DETAIL, DHCPSRV_MEMFILE_GET_SUBID6) + .arg(subnet_id); + + Lease6Collection collection; + const Lease6StorageSubnetIdIndex& idx = storage6_.get(); + std::pair l = + idx.equal_range(subnet_id); + + for (auto lease = l.first; lease != l.second; ++lease) { + collection.push_back(Lease6Ptr(new Lease6(**lease))); + } + + return (collection); +} + +Lease6Collection +Memfile_LeaseMgr::getLeases6() const { + LOG_DEBUG(dhcpsrv_logger, DHCPSRV_DBG_TRACE_DETAIL, DHCPSRV_MEMFILE_GET6); + + Lease6Collection collection; + for (auto lease = storage6_.begin(); lease != storage6_.end(); ++lease ) { + collection.push_back(Lease6Ptr(new Lease6(**lease))); + } + + return (collection); +} + void Memfile_LeaseMgr::getExpiredLeases6(Lease6Collection& expired_leases, const size_t max_leases) const { diff --git a/src/lib/dhcpsrv/memfile_lease_mgr.h b/src/lib/dhcpsrv/memfile_lease_mgr.h index a82fa3cd5b..0cb5bc829b 100644 --- a/src/lib/dhcpsrv/memfile_lease_mgr.h +++ b/src/lib/dhcpsrv/memfile_lease_mgr.h @@ -271,6 +271,18 @@ public: uint32_t iaid, SubnetID subnet_id) const; + /// @brief Returns all IPv6 leases for the particular subnet identifier. + /// + /// @param subnet_id subnet identifier. + /// + /// @return Lease collection (may be empty if no IPv6 lease found). + virtual Lease6Collection getLeases6(SubnetID subnet_id) const; + + /// @brief Returns all IPv6 leases. + /// + /// @return Lease collection (may be empty if no IPv6 lease found). + virtual Lease6Collection getLeases6() const; + /// @brief Returns a collection of expired DHCPv6 leases. /// /// This method returns at most @c max_leases expired leases. The leases diff --git a/src/lib/dhcpsrv/mysql_lease_mgr.cc b/src/lib/dhcpsrv/mysql_lease_mgr.cc index 8c70a60afa..9f03556488 100644 --- a/src/lib/dhcpsrv/mysql_lease_mgr.cc +++ b/src/lib/dhcpsrv/mysql_lease_mgr.cc @@ -153,6 +153,14 @@ tagged_statements = { { "WHERE state != ? AND expire < ? " "ORDER BY expire ASC " "LIMIT ?"}, + {MySqlLeaseMgr::GET_LEASE6, + "SELECT address, duid, valid_lifetime, " + "expire, subnet_id, pref_lifetime, " + "lease_type, iaid, prefix_len, " + "fqdn_fwd, fqdn_rev, hostname, " + "hwaddr, hwtype, hwaddr_source, " + "state " + "FROM lease6"}, {MySqlLeaseMgr::GET_LEASE6_ADDR, "SELECT address, duid, valid_lifetime, " "expire, subnet_id, pref_lifetime, " @@ -181,6 +189,15 @@ tagged_statements = { { "FROM lease6 " "WHERE duid = ? AND iaid = ? AND subnet_id = ? " "AND lease_type = ?"}, + {MySqlLeaseMgr::GET_LEASE6_SUBID, + "SELECT address, duid, valid_lifetime, " + "expire, subnet_id, pref_lifetime, " + "lease_type, iaid, prefix_len, " + "fqdn_fwd, fqdn_rev, hostname, " + "hwaddr, hwtype, hwaddr_source, " + "state " + "FROM lease6 " + "WHERE subnet_id = ?"}, {MySqlLeaseMgr::GET_LEASE6_EXPIRE, "SELECT address, duid, valid_lifetime, " "expire, subnet_id, pref_lifetime, " @@ -1909,6 +1926,37 @@ MySqlLeaseMgr::getLeases6(Lease::Type lease_type, return (result); } +Lease6Collection +MySqlLeaseMgr::getLeases6(SubnetID subnet_id) const { + LOG_DEBUG(dhcpsrv_logger, DHCPSRV_DBG_TRACE_DETAIL, DHCPSRV_MYSQL_GET_SUBID6) + .arg(subnet_id); + + // Set up the WHERE clause value + MYSQL_BIND inbind[1]; + memset(inbind, 0, sizeof(inbind)); + + // Subnet ID + inbind[0].buffer_type = MYSQL_TYPE_LONG; + inbind[0].buffer = reinterpret_cast(&subnet_id); + inbind[0].is_unsigned = MLM_TRUE; + + // ... and get the data + Lease6Collection result; + getLeaseCollection(GET_LEASE6_SUBID, inbind, result); + + return (result); +} + +Lease6Collection +MySqlLeaseMgr::getLeases6() const { + LOG_DEBUG(dhcpsrv_logger, DHCPSRV_DBG_TRACE_DETAIL, DHCPSRV_MYSQL_GET6); + + Lease6Collection result; + getLeaseCollection(GET_LEASE6, 0, result); + + return (result); +} + void MySqlLeaseMgr::getExpiredLeases6(Lease6Collection& expired_leases, const size_t max_leases) const { diff --git a/src/lib/dhcpsrv/mysql_lease_mgr.h b/src/lib/dhcpsrv/mysql_lease_mgr.h index 0c274a46ed..91265cc72b 100644 --- a/src/lib/dhcpsrv/mysql_lease_mgr.h +++ b/src/lib/dhcpsrv/mysql_lease_mgr.h @@ -268,6 +268,18 @@ public: virtual Lease6Collection getLeases6(Lease::Type type, const DUID& duid, uint32_t iaid, SubnetID subnet_id) const; + /// @brief Returns all IPv6 leases for the particular subnet identifier. + /// + /// @param subnet_id subnet identifier. + /// + /// @return Lease collection (may be empty if no IPv6 lease found). + virtual Lease6Collection getLeases6(SubnetID subnet_id) const; + + /// @brief Returns all IPv6 leases. + /// + /// @return Lease collection (may be empty if no IPv6 lease found). + virtual Lease6Collection getLeases6() const; + /// @brief Returns a collection of expired DHCPv6 leases. /// /// This method returns at most @c max_leases expired leases. The leases @@ -436,9 +448,11 @@ public: GET_LEASE4_HWADDR_SUBID, // Get lease4 by HW address & subnet ID GET_LEASE4_SUBID, // Get IPv4 leases by subnet ID GET_LEASE4_EXPIRE, // Get lease4 by expiration. + GET_LEASE6, // Get all IPv6 leases GET_LEASE6_ADDR, // Get lease6 by address GET_LEASE6_DUID_IAID, // Get lease6 by DUID and IAID GET_LEASE6_DUID_IAID_SUBID, // Get lease6 by DUID, IAID and subnet ID + GET_LEASE6_SUBID, // Get IPv6 leases by subnet ID GET_LEASE6_EXPIRE, // Get lease6 by expiration. GET_VERSION, // Obtain version number INSERT_LEASE4, // Add entry to lease4 table diff --git a/src/lib/dhcpsrv/pgsql_lease_mgr.cc b/src/lib/dhcpsrv/pgsql_lease_mgr.cc index 3d8c30cfdc..c9e68499dd 100644 --- a/src/lib/dhcpsrv/pgsql_lease_mgr.cc +++ b/src/lib/dhcpsrv/pgsql_lease_mgr.cc @@ -128,6 +128,15 @@ PgSqlTaggedStatement tagged_statements[] = { "ORDER BY expire " "LIMIT $3"}, + // GET_LEASE6 + { 0, { OID_NONE }, + "get_lease6", + "SELECT address, duid, valid_lifetime, " + "extract(epoch from expire)::bigint, subnet_id, pref_lifetime, " + "lease_type, iaid, prefix_len, fqdn_fwd, fqdn_rev, hostname, " + "state " + "FROM lease6"}, + // GET_LEASE6_ADDR { 2, { OID_VARCHAR, OID_INT2 }, "get_lease6_addr", @@ -159,6 +168,16 @@ PgSqlTaggedStatement tagged_statements[] = { "WHERE lease_type = $1 " "AND duid = $2 AND iaid = $3 AND subnet_id = $4"}, + // GET_LEASE6_SUBID + { 1, { OID_INT8 }, + "get_lease6_subid", + "SELECT address, duid, valid_lifetime, " + "extract(epoch from expire)::bigint, subnet_id, pref_lifetime, " + "lease_type, iaid, prefix_len, fqdn_fwd, fqdn_rev, hostname, " + "state " + "FROM lease6 " + "WHERE subnet_id = $1"}, + // GET_LEASE6_EXPIRE { 3, { OID_INT8, OID_TIMESTAMP, OID_INT8 }, "get_lease6_expire", @@ -1205,6 +1224,38 @@ PgSqlLeaseMgr::getLeases6(Lease::Type lease_type, const DUID& duid, return (result); } +Lease6Collection +PgSqlLeaseMgr::getLeases6(SubnetID subnet_id) const { + LOG_DEBUG(dhcpsrv_logger, DHCPSRV_DBG_TRACE_DETAIL, DHCPSRV_PGSQL_GET_SUBID6) + .arg(subnet_id); + + // Set up the WHERE clause value + PsqlBindArray bind_array; + + // SUBNET_ID + std::string subnet_id_str = boost::lexical_cast(subnet_id); + bind_array.add(subnet_id_str); + + // ... and get the data + Lease6Collection result; + getLeaseCollection(GET_LEASE6_SUBID, bind_array, result); + + return (result); +} + +Lease6Collection +PgSqlLeaseMgr::getLeases6() const { + LOG_DEBUG(dhcpsrv_logger, DHCPSRV_DBG_TRACE_DETAIL, DHCPSRV_PGSQL_GET6); + + // Provide empty binding array because our query has no parameters in + // WHERE clause. + PsqlBindArray bind_array; + Lease6Collection result; + getLeaseCollection(GET_LEASE6, bind_array, result); + + return (result); +} + void PgSqlLeaseMgr::getExpiredLeases6(Lease6Collection& expired_leases, const size_t max_leases) const { diff --git a/src/lib/dhcpsrv/pgsql_lease_mgr.h b/src/lib/dhcpsrv/pgsql_lease_mgr.h index 8599d52379..54ca6df8ec 100644 --- a/src/lib/dhcpsrv/pgsql_lease_mgr.h +++ b/src/lib/dhcpsrv/pgsql_lease_mgr.h @@ -161,18 +161,6 @@ public: virtual Lease4Ptr getLease4(const ClientId& client_id, const HWAddr& hwaddr, SubnetID subnet_id) const; - /// @brief Returns all IPv4 leases for the particular subnet identifier. - /// - /// @param subnet_id subnet identifier. - /// - /// @return Lease collection (may be empty if no IPv4 lease found). - virtual Lease4Collection getLeases4(SubnetID subnet_id) const; - - /// @brief Returns all IPv4 leases. - /// - /// @return Lease collection (may be empty if no IPv4 lease found). - virtual Lease4Collection getLeases4() const; - /// @brief Returns existing IPv4 lease for specified client-id /// /// There can be at most one lease for a given HW address in a single @@ -188,6 +176,18 @@ public: virtual Lease4Ptr getLease4(const ClientId& clientid, SubnetID subnet_id) const; + /// @brief Returns all IPv4 leases for the particular subnet identifier. + /// + /// @param subnet_id subnet identifier. + /// + /// @return Lease collection (may be empty if no IPv4 lease found). + virtual Lease4Collection getLeases4(SubnetID subnet_id) const; + + /// @brief Returns all IPv4 leases. + /// + /// @return Lease collection (may be empty if no IPv4 lease found). + virtual Lease4Collection getLeases4() const; + /// @brief Returns existing IPv6 lease for a given IPv6 address. /// /// For a given address, we assume that there will be only one lease. @@ -242,6 +242,18 @@ public: virtual Lease6Collection getLeases6(Lease::Type type, const DUID& duid, uint32_t iaid, SubnetID subnet_id) const; + /// @brief Returns all IPv6 leases for the particular subnet identifier. + /// + /// @param subnet_id subnet identifier. + /// + /// @return Lease collection (may be empty if no IPv6 lease found). + virtual Lease6Collection getLeases6(SubnetID subnet_id) const; + + /// @brief Returns all IPv6 leases. + /// + /// @return Lease collection (may be empty if no IPv6 lease found). + virtual Lease6Collection getLeases6() const; + /// @brief Returns a collection of expired DHCPv6 leases. /// /// This method returns at most @c max_leases expired leases. The leases @@ -427,9 +439,11 @@ public: GET_LEASE4_HWADDR_SUBID, // Get lease4 by HW address & subnet ID GET_LEASE4_SUBID, // Get IPv4 leases by subnet ID GET_LEASE4_EXPIRE, // Get expired lease4 + GET_LEASE6, // Get all IPv6 leases GET_LEASE6_ADDR, // Get lease6 by address GET_LEASE6_DUID_IAID, // Get lease6 by DUID and IAID GET_LEASE6_DUID_IAID_SUBID, // Get lease6 by DUID, IAID and subnet ID + GET_LEASE6_SUBID, // Get IPv6 leases by subnet ID GET_LEASE6_EXPIRE, // Get expired lease6 GET_VERSION, // Obtain version number INSERT_LEASE4, // Add entry to lease4 table diff --git a/src/lib/dhcpsrv/tests/generic_lease_mgr_unittest.cc b/src/lib/dhcpsrv/tests/generic_lease_mgr_unittest.cc index e9cdcbf942..3b1850d527 100644 --- a/src/lib/dhcpsrv/tests/generic_lease_mgr_unittest.cc +++ b/src/lib/dhcpsrv/tests/generic_lease_mgr_unittest.cc @@ -1246,6 +1246,33 @@ GenericLeaseMgrTest::testGetLeases4() { ASSERT_EQ(leases.size(), returned.size()); } +void +GenericLeaseMgrTest::testGetLeases6SubnetId() { + // Get the leases to be used for the test and add to the database. + vector leases = createLeases6(); + for (size_t i = 0; i < leases.size(); ++i) { + EXPECT_TRUE(lmptr_->addLease(leases[i])); + } + + // There should be exactly two leases for the subnet id that the second + // lease belongs to. + Lease6Collection returned = lmptr_->getLeases6(leases[1]->subnet_id_); + ASSERT_EQ(2, returned.size()); +} + +void +GenericLeaseMgrTest::testGetLeases6() { + // Get the leases to be used for the test and add to the database + vector leases = createLeases6(); + for (size_t i = 0; i < leases.size(); ++i) { + EXPECT_TRUE(lmptr_->addLease(leases[i])); + } + + // All leases should be returned. + Lease6Collection returned = lmptr_->getLeases6(); + ASSERT_EQ(leases.size(), returned.size()); +} + void GenericLeaseMgrTest::testGetLeases6DuidIaid() { // Get the leases to be used for the test. diff --git a/src/lib/dhcpsrv/tests/generic_lease_mgr_unittest.h b/src/lib/dhcpsrv/tests/generic_lease_mgr_unittest.h index 07b7948cc3..b6e275d57f 100644 --- a/src/lib/dhcpsrv/tests/generic_lease_mgr_unittest.h +++ b/src/lib/dhcpsrv/tests/generic_lease_mgr_unittest.h @@ -206,6 +206,12 @@ public: /// @brief Test method which returns all IPv4 leases. void testGetLeases4(); + /// @brief Test method which returns all IPv6 leases for Subnet ID. + void testGetLeases6SubnetId(); + + /// @brief Test method which returns all IPv6 leases. + void testGetLeases6(); + /// @brief Basic Lease4 Checks /// /// Checks that the addLease, getLease4(by address), getLease4(hwaddr,subnet_id), diff --git a/src/lib/dhcpsrv/tests/lease_mgr_unittest.cc b/src/lib/dhcpsrv/tests/lease_mgr_unittest.cc index 373eb1a0b9..88ea5a064a 100644 --- a/src/lib/dhcpsrv/tests/lease_mgr_unittest.cc +++ b/src/lib/dhcpsrv/tests/lease_mgr_unittest.cc @@ -178,6 +178,22 @@ public: return (leases6_); } + /// @brief Returns all IPv6 leases for the particular subnet identifier. + /// + /// @param subnet_id subnet identifier. + /// + /// @return Lease collection (may be empty if no IPv6 lease found). + virtual Lease6Collection getLeases6(SubnetID) const { + return (Lease6Collection()); + } + + /// @brief Returns all IPv6 leases. + /// + /// @return Lease collection (may be empty if no IPv6 lease found). + virtual Lease6Collection getLeases6() const { + return (Lease6Collection()); + } + /// @brief Returns expired DHCPv6 leases. /// diff --git a/src/lib/dhcpsrv/tests/memfile_lease_mgr_unittest.cc b/src/lib/dhcpsrv/tests/memfile_lease_mgr_unittest.cc index df4d586c3b..c438f0807c 100644 --- a/src/lib/dhcpsrv/tests/memfile_lease_mgr_unittest.cc +++ b/src/lib/dhcpsrv/tests/memfile_lease_mgr_unittest.cc @@ -929,6 +929,18 @@ TEST_F(MemfileLeaseMgrTest, getLeases4) { testGetLeases4(); } +// This test checks that all IPv6 leases for a specified subnet id are returned. +TEST_F(MemfileLeaseMgrTest, getLeases6SubnetId) { + startBackend(V6); + testGetLeases6SubnetId(); +} + +// This test checks that all IPv6 leases are returned. +TEST_F(MemfileLeaseMgrTest, getLeases6) { + startBackend(V6); + testGetLeases6(); +} + /// @brief Basic Lease6 Checks /// /// Checks that the addLease, getLease6 (by address) and deleteLease (with an diff --git a/src/lib/dhcpsrv/tests/mysql_lease_mgr_unittest.cc b/src/lib/dhcpsrv/tests/mysql_lease_mgr_unittest.cc index 609ddabe6e..974d7d7951 100644 --- a/src/lib/dhcpsrv/tests/mysql_lease_mgr_unittest.cc +++ b/src/lib/dhcpsrv/tests/mysql_lease_mgr_unittest.cc @@ -331,6 +331,16 @@ TEST_F(MySqlLeaseMgrTest, getLeases4) { testGetLeases4(); } +// This test checks that all IPv6 leases for a specified subnet id are returned. +TEST_F(MySqlLeaseMgrTest, getLeases6SubnetId) { + testGetLeases6SubnetId(); +} + +// This test checks that all IPv6 leases are returned. +TEST_F(MySqlLeaseMgrTest, getLeases6) { + testGetLeases6(); +} + /// @brief Basic Lease4 Checks /// /// Checks that the addLease, getLease4(by address), getLease4(hwaddr,subnet_id), diff --git a/src/lib/dhcpsrv/tests/pgsql_lease_mgr_unittest.cc b/src/lib/dhcpsrv/tests/pgsql_lease_mgr_unittest.cc index fa84bbb99b..2087d46a18 100644 --- a/src/lib/dhcpsrv/tests/pgsql_lease_mgr_unittest.cc +++ b/src/lib/dhcpsrv/tests/pgsql_lease_mgr_unittest.cc @@ -290,6 +290,16 @@ TEST_F(PgSqlLeaseMgrTest, getLeases4) { testGetLeases4(); } +// This test checks that all IPv6 leases for a specified subnet id are returned. +TEST_F(PgSqlLeaseMgrTest, getLeases6SubnetId) { + testGetLeases6SubnetId(); +} + +// This test checks that all IPv6 leases are returned. +TEST_F(PgSqlLeaseMgrTest, getLeases6) { + testGetLeases6(); +} + /// @brief Basic Lease4 Checks /// /// Checks that the addLease, getLease4(by address), getLease4(hwaddr,subnet_id), diff --git a/src/share/database/scripts/mysql/dhcpdb_create.mysql b/src/share/database/scripts/mysql/dhcpdb_create.mysql index b1cdd1d058..921e4670f7 100644 --- a/src/share/database/scripts/mysql/dhcpdb_create.mysql +++ b/src/share/database/scripts/mysql/dhcpdb_create.mysql @@ -514,7 +514,9 @@ ALTER TABLE dhcp6_options ADD COLUMN user_context TEXT NULL; CREATE INDEX lease4_by_subnet_id ON lease4 (subnet_id); # Create for searching leases by subnet identifier and lease type. -CREATE INDEX lease6_by_subnet_id_lease_type ON lease6 (subnet_id, lease_type); +#CREATE INDEX lease6_by_subnet_id_lease_type ON lease6 (subnet_id, lease_type); +# Create for searching leases by subnet identifier. +CREATE INDEX lease6_by_subnet_id ON lease6 (subnet_id); # Update the schema version number UPDATE schema_version diff --git a/src/share/database/scripts/mysql/upgrade_5.1_to_6.0.sh.in b/src/share/database/scripts/mysql/upgrade_5.1_to_6.0.sh.in index c4e7809128..96af027884 100644 --- a/src/share/database/scripts/mysql/upgrade_5.1_to_6.0.sh.in +++ b/src/share/database/scripts/mysql/upgrade_5.1_to_6.0.sh.in @@ -28,7 +28,9 @@ ALTER TABLE dhcp6_options ADD COLUMN user_context TEXT NULL; CREATE INDEX lease4_by_subnet_id ON lease4 (subnet_id); # Create for searching leases by subnet identifier and lease type. -CREATE INDEX lease6_by_subnet_id_lease_type ON lease6 (subnet_id, lease_type); +#CREATE INDEX lease6_by_subnet_id_lease_type ON lease6 (subnet_id, lease_type); +# Create for searching leases by subnet identifier. +CREATE INDEX lease6_by_subnet_id ON lease6 (subnet_id); # Update the schema version number UPDATE schema_version diff --git a/src/share/database/scripts/pgsql/dhcpdb_create.pgsql b/src/share/database/scripts/pgsql/dhcpdb_create.pgsql index 90d1aed7da..4414bd6a03 100644 --- a/src/share/database/scripts/pgsql/dhcpdb_create.pgsql +++ b/src/share/database/scripts/pgsql/dhcpdb_create.pgsql @@ -541,7 +541,9 @@ ALTER TABLE dhcp6_options ADD COLUMN user_context TEXT; CREATE INDEX lease4_by_subnet_id ON lease4 (subnet_id); -- Create for searching leases by subnet identifier and lease type. -CREATE INDEX lease6_by_subnet_id_lease_type ON lease6 (subnet_id, lease_type); +-- CREATE INDEX lease6_by_subnet_id_lease_type ON lease6 (subnet_id, lease_type); +-- Create for searching leases by subnet identifier. +CREATE INDEX lease6_by_subnet_id ON lease6 (subnet_id); -- Set 4.0 schema version. UPDATE schema_version diff --git a/src/share/database/scripts/pgsql/upgrade_3.2_to_4.0.sh.in b/src/share/database/scripts/pgsql/upgrade_3.2_to_4.0.sh.in index c20e114f2a..236f8e312e 100644 --- a/src/share/database/scripts/pgsql/upgrade_3.2_to_4.0.sh.in +++ b/src/share/database/scripts/pgsql/upgrade_3.2_to_4.0.sh.in @@ -30,7 +30,9 @@ ALTER TABLE dhcp6_options ADD COLUMN user_context TEXT; CREATE INDEX lease4_by_subnet_id ON lease4 (subnet_id); -- Create for searching leases by subnet identifier and lease type. -CREATE INDEX lease6_by_subnet_id_lease_type ON lease6 (subnet_id, lease_type); +-- CREATE INDEX lease6_by_subnet_id_lease_type ON lease6 (subnet_id, lease_type); +-- Create for searching leases by subnet identifier. +CREATE INDEX lease6_by_subnet_id ON lease6 (subnet_id); -- Set 4.0 schema version. UPDATE schema_version