Commit 450867e6 authored by Marcin Siodelski's avatar Marcin Siodelski
Browse files

[master] Merge branch 'trac3636'

parents ad0a3772 fe668b6d
// Copyright (C) 2011-2014 Internet Systems Consortium, Inc. ("ISC")
// Copyright (C) 2011-2015 Internet Systems Consortium, Inc. ("ISC")
//
// Permission to use, copy, modify, and/or distribute this software for any
// purpose with or without fee is hereby granted, provided that the above
......@@ -816,8 +816,12 @@ Dhcpv4Srv::processHostnameOption(const OptionStringPtr& opt_hostname,
} else if (label_count == 2) {
// If there are two labels, it means that the client has specified
// the unqualified name. We have to concatenate the unqalified name
// with the domain name.
opt_hostname_resp->setValue(d2_mgr.qualifyName(hostname));
// with the domain name. The false value passed as a second argument
// indicates that the trailing dot should not be appended to the
// hostname. We don't want to append the trailing dot because
// we don't know whether the hostname is partial or not and some
// clients do not handle the hostnames with the trailing dot.
opt_hostname_resp->setValue(d2_mgr.qualifyName(hostname, false));
}
answer->addOption(opt_hostname_resp);
......@@ -1072,8 +1076,13 @@ Dhcpv4Srv::assignLease(const Pkt4Ptr& question, Pkt4Ptr& answer) {
// generating the entire hostname for the client. The example of the
// client's name, generated from the IP address is: host-192-0-2-3.
if ((fqdn || opt_hostname) && lease->hostname_.empty()) {
lease->hostname_ = CfgMgr::instance()
.getD2ClientMgr().generateFqdn(lease->addr_);
// Note that if we have received the hostname option, rather than
// Client FQDN the trailing dot is not appended to the generated
// hostname because some clients don't handle the trailing dot in
// the hostname. Whether the trailing dot is appended or not is
// controlled by the second argument to the generateFqdn().
lease->hostname_ = CfgMgr::instance().getD2ClientMgr()
.generateFqdn(lease->addr_, static_cast<bool>(fqdn));
// The operations below are rather safe, but we want to catch
// any potential exceptions (e.g. invalid lease database backend
......
// Copyright (C) 2013-2014 Internet Systems Consortium, Inc. ("ISC")
// Copyright (C) 2013-2015 Internet Systems Consortium, Inc. ("ISC")
//
// Permission to use, copy, modify, and/or distribute this software for any
// purpose with or without fee is hereby granted, provided that the above
......@@ -136,10 +136,15 @@ public:
/// names are correct.
///
/// @param addr IP address used in the lease.
/// @param trailing_dot A boolean flag which indicates whether the
/// trailing dot should be appended to the end of the hostname.
/// The defatult value is "true" which means that it should.
///
/// @return An std::string contained the generated FQDN.
std::string generatedNameFromAddress(const IOAddress& addr) {
return(CfgMgr::instance().getD2ClientMgr().generateFqdn(addr));
std::string generatedNameFromAddress(const IOAddress& addr,
const bool trailing_dot = true) {
return(CfgMgr::instance().getD2ClientMgr()
.generateFqdn(addr, trailing_dot));
}
// Get the Client FQDN Option from the given message.
......@@ -617,7 +622,7 @@ TEST_F(NameDhcpv4SrvTest, serverUpdateUnqualifiedHostname) {
ASSERT_NO_THROW(hostname = processHostname(query));
ASSERT_TRUE(hostname);
EXPECT_EQ("myhost.example.com.", hostname->getValue());
EXPECT_EQ("myhost.example.com", hostname->getValue());
}
......
// Copyright (C) 2011-2014 Internet Systems Consortium, Inc. ("ISC")
// Copyright (C) 2011-2015 Internet Systems Consortium, Inc. ("ISC")
//
// Permission to use, copy, modify, and/or distribute this software for any
// purpose with or without fee is hereby granted, provided that the above
......
// Copyright (C) 2013 Internet Systems Consortium, Inc. ("ISC")
// Copyright (C) 2013, 2015 Internet Systems Consortium, Inc. ("ISC")
//
// Permission to use, copy, modify, and/or distribute this software for any
// purpose with or without fee is hereby granted, provided that the above
......@@ -220,6 +220,9 @@ NameChangeRequest::NameChangeRequest(const NameChangeType change_type,
dhcid_(dhcid), lease_expires_on_(lease_expires_on),
lease_length_(lease_length), status_(ST_NEW) {
// User setter to validate fqdn.
setFqdn(fqdn);
// User setter to validate address.
setIpAddress(ip_address);
......
// Copyright (C) 2014 Internet Systems Consortium, Inc. ("ISC")
// Copyright (C) 2014-2015 Internet Systems Consortium, Inc. ("ISC")
//
// Permission to use, copy, modify, and/or distribute this software for any
// purpose with or without fee is hereby granted, provided that the above
......@@ -171,26 +171,42 @@ D2ClientMgr::analyzeFqdn(const bool client_s, const bool client_n,
}
std::string
D2ClientMgr::generateFqdn(const asiolink::IOAddress& address) const {
D2ClientMgr::generateFqdn(const asiolink::IOAddress& address,
const bool trailing_dot) const {
std::string hostname = address.toText();
std::replace(hostname.begin(), hostname.end(),
(address.isV4() ? '.' : ':'), '-');
std::ostringstream gen_name;
gen_name << d2_client_config_->getGeneratedPrefix() << "-" << hostname;
return (qualifyName(gen_name.str()));
return (qualifyName(gen_name.str(), trailing_dot));
}
std::string
D2ClientMgr::qualifyName(const std::string& partial_name) const {
D2ClientMgr::qualifyName(const std::string& partial_name,
const bool trailing_dot) const {
std::ostringstream gen_name;
gen_name << partial_name << "." << d2_client_config_->getQualifyingSuffix();
// Tack on a trailing dot in case suffix doesn't have one.
std::string str = gen_name.str();
size_t len = str.length();
if ((len > 0) && (str[len - 1] != '.')) {
gen_name << ".";
if(trailing_dot) {
// If trailing dot should be added but there is no trailing dot,
// append it.
if ((len > 0) && (str[len - 1] != '.')) {
gen_name << ".";
}
} else {
// If the trailing dot should not be appended but it is present,
// remove it.
if ((len > 0) && (str[len - 1] == '.')) {
gen_name.str(str.substr(0,len-1));
}
}
return (gen_name.str());
......
......@@ -172,9 +172,12 @@ public:
/// ('.' for IPv4 or ':' for IPv6) replaced with a hyphen, '-'.
///
/// @param address IP address from which to derive the name (IPv4 or IPv6)
/// @param trailing_dot A boolean value which indicates whether trailing
/// dot should be appended (if true) or not (false).
///
/// @return std::string containing the generated name.
std::string generateFqdn(const asiolink::IOAddress& address) const;
std::string generateFqdn(const asiolink::IOAddress& address,
const bool trailing_dot = true) const;
/// @brief Adds a qualifying suffix to a given domain name
///
......@@ -182,13 +185,14 @@ public:
/// a partial domain name as follows:
///
/// <partial_name>.<qualifying-suffix>.
/// Note it will add a trailing '.' should qualifying-suffix not end with
/// one.
///
/// @param partial_name domain name to qualify
/// @param trailing_dot A boolean value which indicates whether trailing
/// dot should be appended (if true) or not (false).
///
/// @return std::string containing the qualified name.
std::string qualifyName(const std::string& partial_name) const;
std::string qualifyName(const std::string& partial_name,
const bool trailing_dot) const;
/// @brief Set server FQDN flags based on configuration and a given FQDN
///
......@@ -465,7 +469,7 @@ D2ClientMgr::adjustDomainName(const T& fqdn, T& fqdn_resp) {
} else {
// If the supplied name is partial, qualify it by adding the suffix.
if (fqdn.getDomainNameType() == T::PARTIAL) {
fqdn_resp.setDomainName(qualifyName(fqdn.getDomainName()), T::FULL);
fqdn_resp.setDomainName(qualifyName(fqdn.getDomainName(),true), T::FULL);
}
}
}
......
......@@ -601,6 +601,8 @@ TEST(D2ClientMgr, qualifyName) {
// Create enabled configuration.
D2ClientConfigPtr cfg;
//append suffix and dot
ASSERT_NO_THROW(cfg.reset(new D2ClientConfig(true,
isc::asiolink::IOAddress("127.0.0.1"), 477,
isc::asiolink::IOAddress("127.0.0.1"), 478,
......@@ -612,9 +614,38 @@ TEST(D2ClientMgr, qualifyName) {
// Verify that the qualifying suffix gets appended with trailing dot added.
std::string partial_name = "somehost";
std::string qualified_name = mgr.qualifyName(partial_name);
std::string qualified_name = mgr.qualifyName(partial_name,true);
EXPECT_EQ("somehost.suffix.com.", qualified_name);
//append suffix but dot
ASSERT_NO_THROW(cfg.reset(new D2ClientConfig(true,
isc::asiolink::IOAddress("127.0.0.1"), 477,
isc::asiolink::IOAddress("127.0.0.1"), 478,
1024,
dhcp_ddns::NCR_UDP, dhcp_ddns::FMT_JSON,
false, false, true, false,
"prefix", "suffix.com")));
ASSERT_NO_THROW(mgr.setD2ClientConfig(cfg));
partial_name = "somehost";
qualified_name = mgr.qualifyName(partial_name,false); //false means no dot
EXPECT_EQ("somehost.suffix.com", qualified_name);
//append no suffix and not dot
ASSERT_NO_THROW(cfg.reset(new D2ClientConfig(true,
isc::asiolink::IOAddress("127.0.0.1"), 477,
isc::asiolink::IOAddress("127.0.0.1"), 478,
1024,
dhcp_ddns::NCR_UDP, dhcp_ddns::FMT_JSON,
false, false, true, false,
"prefix", ""))); //empty suffix
ASSERT_NO_THROW(mgr.setD2ClientConfig(cfg));
partial_name = "somehost";
qualified_name = mgr.qualifyName(partial_name,false); //false means no dot
EXPECT_EQ("somehost", qualified_name);
// Verify that the qualifying suffix gets appended with trailing dot added.
ASSERT_NO_THROW(cfg.reset(new D2ClientConfig(true,
isc::asiolink::IOAddress("127.0.0.1"), 477,
isc::asiolink::IOAddress("127.0.0.1"), 478,
......@@ -625,7 +656,7 @@ TEST(D2ClientMgr, qualifyName) {
ASSERT_NO_THROW(mgr.setD2ClientConfig(cfg));
// Verify that the qualifying suffix gets appended without dot added.
qualified_name = mgr.qualifyName(partial_name);
qualified_name = mgr.qualifyName(partial_name,true);
EXPECT_EQ("somehost.hasdot.com.", qualified_name);
}
......@@ -647,19 +678,19 @@ TEST(D2ClientMgr, generateFqdn) {
// Verify that it works with an IPv4 address.
asiolink::IOAddress v4address("192.0.2.75");
EXPECT_EQ("prefix-192-0-2-75.suffix.com.", mgr.generateFqdn(v4address));
EXPECT_EQ("prefix-192-0-2-75.suffix.com.", mgr.generateFqdn(v4address,true));
// Verify that it works with an IPv6 address.
asiolink::IOAddress v6address("2001:db8::2");
EXPECT_EQ("prefix-2001-db8--2.suffix.com.", mgr.generateFqdn(v6address));
EXPECT_EQ("prefix-2001-db8--2.suffix.com.", mgr.generateFqdn(v6address,true));
// Create a disabled config.
ASSERT_NO_THROW(cfg.reset(new D2ClientConfig()));
ASSERT_NO_THROW(mgr.setD2ClientConfig(cfg));
// Verify names generate properly with a disabled configuration.
EXPECT_EQ("myhost-192-0-2-75.example.com.", mgr.generateFqdn(v4address));
EXPECT_EQ("myhost-2001-db8--2.example.com.", mgr.generateFqdn(v6address));
EXPECT_EQ("myhost-192-0-2-75.example.com.", mgr.generateFqdn(v4address,true));
EXPECT_EQ("myhost-2001-db8--2.example.com.", mgr.generateFqdn(v6address,true));
}
/// @brief Tests adjustDomainName template method with Option4ClientFqdn
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment