Commit dcaf9bfe authored by Marcin Siodelski's avatar Marcin Siodelski
Browse files

[3173] Encapsulate the perfdhcp lease type in the new class.

parent b6c658d2
......@@ -32,6 +32,52 @@ using namespace isc;
namespace isc {
namespace perfdhcp {
CommandOptions::LeaseType::LeaseType()
: type_(ADDRESS_ONLY) {
}
CommandOptions::LeaseType::LeaseType(const Type lease_type)
: type_(lease_type) {
}
bool
CommandOptions::LeaseType::is(const Type lease_type) const {
return (lease_type == type_);
}
void
CommandOptions::LeaseType::set(const Type lease_type) {
type_ = lease_type;
}
void
CommandOptions::LeaseType::fromCommandLine(const std::string& cmd_line_arg) {
if (cmd_line_arg == "address-only") {
type_ = ADDRESS_ONLY;
} else if (cmd_line_arg == "prefix-only") {
type_ = PREFIX_ONLY;
} else {
isc_throw(isc::InvalidParameter, "value of lease-type: -e<lease-type>,"
" must be one of the following: 'address-only' or"
" 'prefix-only'");
}
}
std::string
CommandOptions::LeaseType::toText() const {
switch (type_) {
case ADDRESS_ONLY:
return ("address-only: IA_NA option added to the client's request");
case PREFIX_ONLY:
return ("prefix-only: IA_PD option added to the client's request");
default:
isc_throw(Unexpected, "internal error: undefined lease type code when"
" returning textual representation of the lease type");
}
}
CommandOptions&
CommandOptions::instance() {
static CommandOptions options;
......@@ -52,7 +98,7 @@ CommandOptions::reset() {
// will need to reset all members many times to perform unit tests
ipversion_ = 0;
exchange_mode_ = DORA_SARR;
lease_type_ = ADDRESS_ONLY;
lease_type_.set(LeaseType::ADDRESS_ONLY);
rate_ = 0;
report_delay_ = 0;
clients_num_ = 0;
......@@ -625,10 +671,11 @@ CommandOptions::validate() const {
"-6 (IPv6) must be set to use -c");
check((getExchangeMode() == DO_SA) && (getNumRequests().size() > 1),
"second -n<num-request> is not compatible with -i");
check((getIpVersion() == 4) && (getLeaseType() != ADDRESS_ONLY),
check((getIpVersion() == 4) && !getLeaseType().is(LeaseType::ADDRESS_ONLY),
"-6 option must be used if lease type other than '-e address-only'"
" is specified");
check(!getTemplateFiles().empty() && (getLeaseType() != ADDRESS_ONLY),
check(!getTemplateFiles().empty() &&
!getLeaseType().is(LeaseType::ADDRESS_ONLY),
"template files may be only used with '-e address-only'");
check((getExchangeMode() == DO_SA) && (getDropTime()[1] != 1.),
"second -d<drop-time> is not compatible with -i");
......@@ -718,17 +765,7 @@ CommandOptions::nonEmptyString(const std::string& errmsg) const {
void
CommandOptions::initLeaseType() {
std::string lease_type_arg = optarg;
if (lease_type_arg == "address-only") {
lease_type_ = ADDRESS_ONLY;
} else if (lease_type_arg == "prefix-only") {
lease_type_ = PREFIX_ONLY;
} else {
isc_throw(isc::InvalidParameter, "value of lease-type: -e<lease-type>,"
" must be one of the following: 'address-only' or"
" 'prefix-only'");
}
lease_type_.fromCommandLine(lease_type_arg);
}
void
......@@ -741,6 +778,7 @@ CommandOptions::printCommandLine() const {
std::cout << "SOLICIT-ADVERETISE only" << std::endl;
}
}
std::cout << "lease-type=" << getLeaseType().toText() << std::endl;
if (rate_ != 0) {
std::cout << "rate[1/s]=" << rate_ << std::endl;
}
......
......@@ -30,22 +30,67 @@ namespace perfdhcp {
///
class CommandOptions : public boost::noncopyable {
public:
/// \brief A class encapsulating the type of lease being requested from the
/// server.
///
/// This class comprises convenience functions to convert the lease type
/// to the textual format and to match the appropriate lease type with the
/// value of the -e<lease-type> parameter specified from the command line.
class LeaseType {
public:
/// The lease type code.
enum Type {
ADDRESS_ONLY,
PREFIX_ONLY
};
LeaseType();
/// \brief Constructor from lease type code.
///
/// \param lease_type A lease type code.
LeaseType(const Type lease_type);
/// \brief Checks if lease type has the specified code.
///
/// \param lease_type A lease type code to be checked.
///
/// \return true if lease type is matched with the specified code.
bool is(const Type lease_type) const;
/// \brief Sets the lease type code.
///
/// \param lease_type A lease type code.
void set(const Type lease_type);
/// \brief Sets the lease type from the command line argument.
///
/// \param cmd_line_arg An argument specified in the command line
/// as -e<lease-type>:
/// - address-only
/// - prefix-only
///
/// \throw isc::InvalidParameter if the specified argument is invalid.
void fromCommandLine(const std::string& cmd_line_arg);
/// \brief Return textual representation of the lease type.
///
/// \return A textual representation of the lease type.
std::string toText() const;
private:
Type type_; ///< A lease type code.
};
/// 2-way (cmd line param -i) or 4-way exchanges
enum ExchangeMode {
DO_SA,
DORA_SARR
};
/// @brief A type of lease being requested by the client.
///
/// Currently it indicates whether perfdhcp is simulating the requests
/// for IPv6 addresses or prefixes (Prefix Delegation). Note that
/// prefixes can be only requested when IPv6 mode is selected.
enum LeaseType {
ADDRESS_ONLY,
PREFIX_ONLY
};
/// CommandOptions is a singleton class. This method returns reference
/// to its sole instance.
///
......
// Copyright (C) 2012 Internet Systems Consortium, Inc. ("ISC")
// Copyright (C) 2012-2013 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
......@@ -104,8 +104,8 @@ TestControl::copyIaOptions(const Pkt6Ptr& pkt_from, Pkt6Ptr& pkt_to) {
" for the copyIaOptions function");
}
OptionPtr option;
if (CommandOptions::instance().getLeaseType() ==
CommandOptions::ADDRESS_ONLY) {
if (CommandOptions::instance().getLeaseType()
.is(CommandOptions::LeaseType::ADDRESS_ONLY)) {
option = pkt_from->getOption(D6O_IA_NA);
if (!option) {
isc_throw(OptionNotFound, "IA_NA option not found in the"
......@@ -1781,8 +1781,8 @@ TestControl::sendSolicit6(const TestControlSocket& socket,
// Depending on the lease-type option specified, we should request
// IPv6 address (with IA_NA) or IPv6 prefix (IA_PD).
if (CommandOptions::instance().getLeaseType() ==
CommandOptions::ADDRESS_ONLY) {
if (CommandOptions::instance().getLeaseType()
.is(CommandOptions::LeaseType::ADDRESS_ONLY)) {
pkt6->addOption(Option::factory(Option::V6, D6O_IA_NA));
} else {
pkt6->addOption(Option::factory(Option::V6, D6O_IA_PD));
......
......@@ -28,6 +28,57 @@ using namespace isc;
using namespace isc::perfdhcp;
using namespace boost::posix_time;
TEST(LeaseTypeTest, defaultConstructor) {
CommandOptions::LeaseType lease_type;
EXPECT_TRUE(lease_type.is(CommandOptions::LeaseType::ADDRESS_ONLY));
}
TEST(LeaseTypeTest, constructor) {
CommandOptions::LeaseType
lease_type1(CommandOptions::LeaseType::ADDRESS_ONLY);
EXPECT_TRUE(lease_type1.is(CommandOptions::LeaseType::ADDRESS_ONLY));
CommandOptions::LeaseType
lease_type2(CommandOptions::LeaseType::PREFIX_ONLY);
EXPECT_TRUE(lease_type2.is(CommandOptions::LeaseType::PREFIX_ONLY));
}
TEST(LeaseTypeTest, set) {
CommandOptions::LeaseType
lease_type(CommandOptions::LeaseType::ADDRESS_ONLY);
EXPECT_TRUE(lease_type.is(CommandOptions::LeaseType::ADDRESS_ONLY));
lease_type.set(CommandOptions::LeaseType::PREFIX_ONLY);
EXPECT_TRUE(lease_type.is(CommandOptions::LeaseType::PREFIX_ONLY));
}
TEST(LeaseTypeTest, fromCommandLine) {
CommandOptions::LeaseType
lease_type(CommandOptions::LeaseType::ADDRESS_ONLY);
ASSERT_TRUE(lease_type.is(CommandOptions::LeaseType::ADDRESS_ONLY));
lease_type.fromCommandLine("prefix-only");
ASSERT_TRUE(lease_type.is(CommandOptions::LeaseType::PREFIX_ONLY));
lease_type.fromCommandLine("address-only");
EXPECT_TRUE(lease_type.is(CommandOptions::LeaseType::ADDRESS_ONLY));
EXPECT_THROW(lease_type.fromCommandLine("bogus-parameter"),
isc::InvalidParameter);
}
TEST(LeaseTypeTest, toText) {
CommandOptions::LeaseType lease_type;
ASSERT_TRUE(lease_type.is(CommandOptions::LeaseType::ADDRESS_ONLY));
EXPECT_EQ("address-only: IA_NA option added to the client's request",
lease_type.toText());
lease_type.set(CommandOptions::LeaseType::PREFIX_ONLY);
EXPECT_EQ("prefix-only: IA_PD option added to the client's request",
lease_type.toText());
}
/// \brief Test Fixture Class
///
/// This test fixture class is used to perform
......@@ -60,7 +111,8 @@ protected:
EXPECT_NO_THROW(process("perfdhcp 192.168.0.1"));
EXPECT_EQ(4, opt.getIpVersion());
EXPECT_EQ(CommandOptions::DORA_SARR, opt.getExchangeMode());
EXPECT_EQ(CommandOptions::ADDRESS_ONLY, opt.getLeaseType());
EXPECT_TRUE(opt.getLeaseType()
.is(CommandOptions::LeaseType::ADDRESS_ONLY));
EXPECT_EQ(0, opt.getRate());
EXPECT_EQ(0, opt.getReportDelay());
EXPECT_EQ(0, opt.getClientsNum());
......@@ -188,17 +240,17 @@ TEST_F(CommandOptionsTest, LeaseType) {
ASSERT_NO_THROW(process("perfdhcp -6 -l etx -e address-only all"));
EXPECT_EQ(6, opt.getIpVersion());
EXPECT_EQ("etx", opt.getLocalName());
EXPECT_EQ(CommandOptions::ADDRESS_ONLY, opt.getLeaseType());
EXPECT_TRUE(opt.getLeaseType().is(CommandOptions::LeaseType::ADDRESS_ONLY));
// Check that the -e address-only works for IPv4.
ASSERT_NO_THROW(process("perfdhcp -4 -l etx -e address-only all"));
EXPECT_EQ(4, opt.getIpVersion());
EXPECT_EQ("etx", opt.getLocalName());
EXPECT_EQ(CommandOptions::ADDRESS_ONLY, opt.getLeaseType());
EXPECT_TRUE(opt.getLeaseType().is(CommandOptions::LeaseType::ADDRESS_ONLY));
// Check that the -e prefix-only works.
ASSERT_NO_THROW(process("perfdhcp -6 -l etx -e prefix-only all"));
EXPECT_EQ(6, opt.getIpVersion());
EXPECT_EQ("etx", opt.getLocalName());
EXPECT_EQ(CommandOptions::PREFIX_ONLY, opt.getLeaseType());
EXPECT_TRUE(opt.getLeaseType().is(CommandOptions::LeaseType::PREFIX_ONLY));
// Check that -e prefix-only must not coexist with -4 option.
EXPECT_THROW(process("perfdhcp -4 -l ethx -e prefix-only all"),
InvalidParameter);
......
......@@ -653,8 +653,8 @@ private:
boost::shared_ptr<Pkt6>
createAdvertisePkt6(uint32_t transid) const {
OptionPtr opt_ia;
if (CommandOptions::instance().getLeaseType() ==
CommandOptions::ADDRESS_ONLY) {
if (CommandOptions::instance().getLeaseType()
.is(CommandOptions::LeaseType::ADDRESS_ONLY)) {
opt_ia = Option::factory(Option::V6, D6O_IA_NA);
} else {
opt_ia = Option::factory(Option::V6, D6O_IA_PD);
......
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