BIND 10 trac1956, updated. 6643603e8bc40fed0bab6d6a4ca6b6d585be6001 [1956] Unit tests updated, added duid option.
BIND 10 source code commits
bind10-changes at lists.isc.org
Wed May 30 16:11:56 UTC 2012
The branch, trac1956 has been updated
via 6643603e8bc40fed0bab6d6a4ca6b6d585be6001 (commit)
via 689b286631a39e2c3273982c8ab5d527f7d6211b (commit)
via a6a3d1b172cfd5ba9db4ddb3b8ffcbf673d8e31f (commit)
from 908b273b78455fc4893d3e9d3dd9c4ca42e934c6 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit 6643603e8bc40fed0bab6d6a4ca6b6d585be6001
Author: Marcin Siodelski <marcin at isc.org>
Date: Wed May 30 18:11:07 2012 +0200
[1956] Unit tests updated, added duid option.
commit 689b286631a39e2c3273982c8ab5d527f7d6211b
Author: Marcin Siodelski <marcin at isc.org>
Date: Wed May 30 18:10:20 2012 +0200
[1956] Cleanup of the code in PerfPkt6.
Options moved away from PerfPkt6 to different class. Raw pack/unpack functions resturn bool.
commit a6a3d1b172cfd5ba9db4ddb3b8ffcbf673d8e31f
Author: Marcin Siodelski <marcin at isc.org>
Date: Wed May 30 14:59:28 2012 +0200
[1956] Basic unit tests added for PerfPkt6 class.
-----------------------------------------------------------------------
Summary of changes:
src/lib/dhcp/option.cc | 12 ++
src/lib/dhcp/option.h | 9 ++
tests/tools/perfdhcp/localized_option.h | 101 ++++++++++++++
tests/tools/perfdhcp/perf_pkt6.cc | 123 ++++++++---------
tests/tools/perfdhcp/perf_pkt6.h | 131 +++++-------------
tests/tools/perfdhcp/tests/Makefile.am | 6 +-
tests/tools/perfdhcp/tests/perf_pkt6_unittest.cc | 157 ++++++++++++++++++++++
7 files changed, 372 insertions(+), 167 deletions(-)
create mode 100644 tests/tools/perfdhcp/localized_option.h
create mode 100644 tests/tools/perfdhcp/tests/perf_pkt6_unittest.cc
-----------------------------------------------------------------------
diff --git a/src/lib/dhcp/option.cc b/src/lib/dhcp/option.cc
index 03b4a3d..ed3f9dd 100644
--- a/src/lib/dhcp/option.cc
+++ b/src/lib/dhcp/option.cc
@@ -270,6 +270,18 @@ void Option::setUint32(uint32_t value) {
writeUint32(value, &data_[0]);
}
+void Option::setData(const OptionBufferConstIter first,
+ const OptionBufferConstIter last) {
+ // We will copy entire option buffer, so we have to resize data_.
+ data_.resize(last - first);
+ OptionBufferConstIter x = first;
+ while (x != last) {
+ data_[x - first] = *x;
+ ++x;
+ }
+}
+
+
Option::~Option() {
}
diff --git a/src/lib/dhcp/option.h b/src/lib/dhcp/option.h
index c7f5d10..4e086e5 100644
--- a/src/lib/dhcp/option.h
+++ b/src/lib/dhcp/option.h
@@ -244,6 +244,15 @@ public:
/// @param value value to be set
void setUint32(uint32_t value);
+ /// @brief Sets content of this option from buffer.
+ ///
+ /// Option will be resized to length of buffer.
+ ///
+ /// @param first iterator pointing begining of buffer to copy.
+ /// @param last iterator pointing to end of buffer to copy.
+ void setData(OptionBufferConstIter first,
+ OptionBufferConstIter last);
+
/// just to force that every option has virtual dtor
virtual ~Option();
diff --git a/tests/tools/perfdhcp/localized_option.h b/tests/tools/perfdhcp/localized_option.h
new file mode 100644
index 0000000..9f89c47
--- /dev/null
+++ b/tests/tools/perfdhcp/localized_option.h
@@ -0,0 +1,101 @@
+// Copyright (C) 2011 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 notice and this permission notice appear in all copies.
+//
+// THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
+// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+// AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
+// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
+// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
+// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+// PERFORMANCE OF THIS SOFTWARE.
+
+#ifndef __LOCALIZED_OPTION_H
+#define __LOCALIZED_OPTION_H
+
+#include <dhcp/pkt6.h>
+
+namespace isc {
+namespace perfdhcp {
+
+/// \brief DHCPv6 option at specific offset
+///
+/// This class represents DHCPv6 option at specified
+/// offset in DHCPv6 message.
+///
+class LocalizedOption : public dhcp::Option {
+public:
+ /// \brief Constructor, sets default (0) option offset
+ ///
+ /// \param u specifies universe (V4 or V6)
+ /// \param type option type (0-255 for V4 and 0-65535 for V6)
+ /// \param data content of the option
+ LocalizedOption(dhcp::Option::Universe u, uint16_t type, const dhcp::OptionBuffer& data) :
+ dhcp::Option(u, type, data),
+ offset_(0) {
+ }
+
+
+ /// \brief Constructor, used to create localized option from buffer
+ ///
+ /// \param u specifies universe (V4 or V6)
+ /// \param type option type (0-255 for V4 and 0-65535 for V6)
+ /// \param data content of the option
+ /// \param offset location of option in a packet (zero is default)
+ LocalizedOption(dhcp::Option::Universe u, uint16_t type, const dhcp::OptionBuffer& data,
+ const size_t offset) :
+ dhcp::Option(u, type, data),
+ offset_(offset) {
+ }
+
+ /// \brief Constructor, sets default (0) option offset
+ ///
+ /// This contructor is similar to the previous one, but it does not take
+ /// the whole vector<uint8_t>, but rather subset of it.
+ ///
+ /// \param u specifies universe (V4 or V6)
+ /// \param type option type (0-255 for V4 and 0-65535 for V6)
+ /// \param first iterator to the first element that should be copied
+ /// \param last iterator to the next element after the last one
+ /// to be copied.
+ LocalizedOption(dhcp::Option::Universe u, uint16_t type, dhcp::OptionBufferConstIter first,
+ dhcp::OptionBufferConstIter last) :
+ dhcp::Option(u, type, first, last),
+ offset_(0) {
+ }
+
+
+ /// \brief Constructor, used to create positioned option from buffer iterators
+ ///
+ /// This contructor is similar to the previous one, but it does not take
+ /// the whole vector<uint8_t>, but rather subset of it.
+ ///
+ /// \param u specifies universe (V4 or V6)
+ /// \param type option type (0-255 for V4 and 0-65535 for V6)
+ /// \param first iterator to the first element that should be copied
+ /// \param last iterator to the next element after the last one
+ /// to be copied.
+ /// \param offset location of option in a packet (zero is default)
+ LocalizedOption(dhcp::Option::Universe u, uint16_t type, dhcp::OptionBufferConstIter first,
+ dhcp::OptionBufferConstIter last, const size_t offset) :
+ dhcp::Option(u, type, first, last),
+ offset_(offset) {
+ }
+
+ /// \brief Returns absolute position (offset) of an option in a
+ /// DHCPv6 packet.
+ ///
+ /// \return option offset in a packet
+ size_t getOffset() const { return offset_; };
+
+private:
+ size_t offset_; ///< Offset of DHCPv6 option in a packet
+};
+
+
+} // namespace perfdhcp
+} // namespace isc
+
+#endif // __LOCALIZED_OPTION_H
diff --git a/tests/tools/perfdhcp/perf_pkt6.cc b/tests/tools/perfdhcp/perf_pkt6.cc
index 6a149e8..bb65b83 100644
--- a/tests/tools/perfdhcp/perf_pkt6.cc
+++ b/tests/tools/perfdhcp/perf_pkt6.cc
@@ -12,8 +12,8 @@
// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
// PERFORMANCE OF THIS SOFTWARE.
-#include <boost/shared_ptr.hpp>
-
+#include <iostream>
+#include <exceptions/exceptions.h>
#include <dhcp/libdhcp++.h>
#include <dhcp/dhcp6.h>
@@ -25,25 +25,7 @@ using namespace isc;
namespace isc {
namespace perfdhcp {
-
-PerfPkt6::PositionedOption::PositionedOption(dhcp::Option::Universe u,
- uint16_t type,
- const dhcp::OptionBuffer& data,
- const OptionPosition& position) :
- dhcp::Option(u, type, data),
- position_(position) {
-}
-
-PerfPkt6::PositionedOption::PositionedOption(dhcp::Option::Universe u,
- uint16_t type,
- dhcp::OptionBufferConstIter first,
- dhcp::OptionBufferConstIter last,
- const OptionPosition& position) :
- dhcp::Option(u, type, first, last),
- position_(position) {
-}
-
-PerfPkt6::PerfPkt6(const uint8_t* buf, uint32_t len, const OptionPosition& transid_offset) :
+PerfPkt6::PerfPkt6(const uint8_t* buf, uint32_t len, size_t transid_offset) :
Pkt6(buf, len, dhcp::Pkt6::UDP),
transid_offset_(transid_offset) {
@@ -51,32 +33,8 @@ PerfPkt6::PerfPkt6(const uint8_t* buf, uint32_t len, const OptionPosition& trans
memset(static_cast<void*>(&time_stamp_), 0, sizeof(time_stamp_));
}
-void
-PerfPkt6::stampedPack() {
- // This function simply wraps pack() function from parent class
- // and then updates timestamp.
- if (!pack()) {
- isc_throw(isc::Unexpected, "Failed to prepare packet to send");
- }
- // Update pack time for RTT calculations.
- updateTimestamp();
-}
-
-void
-PerfPkt6::stampedUnpack() {
- // Update timestamp of the packet for RTT calculations.
- // We do this before unpacking the packet so as unpack
- // time will not affect the timestamp.
- updateTimestamp();
-
- // Unpack the incoming packet.
- if (!unpack()) {
- isc_throw(isc::Unexpected, "Failed to unpack incoming packet");
- }
-}
-
-void
-PerfPkt6::stampedRawPack() {
+bool
+PerfPkt6::rawPack() {
try {
// Always override the packet if function is called.
bufferOut_.clear();
@@ -85,41 +43,43 @@ PerfPkt6::stampedRawPack() {
// We already have packet template stored in out buffer
// but still some options have to be updated if client
// specified them along with their offsets in the buffer.
- updateOptions();
- } catch (Exception& e) {
- isc_throw(isc::Unexpected, "Failed to build packet from buffer");
+ rawPackOptions();
+ } catch (isc::Unexpected& e) {
+ cout << "Failed to build packet: " << e.what() << endl;
+ return (false);
}
- // Update packet timestamp for RTT calculations - do not include pack time.
- updateTimestamp();
+ return (true);
}
-void
-PerfPkt6::stampedRawUnpack() {
- // Update packet timestamp for RTT calculations but do not include unpack time.
- updateTimestamp();
-
- // Get transaction id offset.
- int transid_offset = transid_offset_.get();
+bool
+PerfPkt6::rawUnpack() {
// Read transaction id from the packet at the given offset.
- transid_ = ( (data_[transid_offset]) << 16 ) +
- ((data_[transid_offset + 1]) << 8) + (data_[transid_offset + 2]);
+ transid_ = ( (data_[transid_offset_]) << 16 ) +
+ ((data_[transid_offset_ + 1]) << 8) + (data_[transid_offset_ + 2]);
transid_ = transid_ & 0xffffff;
// Get message type - assume it is first octet in the packet.
msg_type_ = data_[0];
+ try {
+ rawUnpackOptions();
+ } catch (isc::Unexpected& e) {
+ cout << "Packet parsing failed: " << e.what() << endl;
+ return (false);
+ }
+ return (true);
}
+
void
-PerfPkt6::updateOptions() {
+PerfPkt6::rawPackOptions() {
try {
// If there are any options on the list we will use provided options offsets
// to override them in the output buffer with new contents.
for (dhcp::Option::OptionCollection::const_iterator it = options_.begin();
it != options_.end(); ++it) {
// Get options with their position (offset).
- boost::shared_ptr<PositionedOption> option = boost::dynamic_pointer_cast<PositionedOption>(it->second);
- uint32_t position = option->getOptionPosition();
- // If position is specified w need to seek to it.
+ boost::shared_ptr<LocalizedOption> option = boost::dynamic_pointer_cast<LocalizedOption>(it->second);
+ uint32_t position = option->getOffset();
if (position > 0) {
bufferOut_.clear();
bufferOut_.skip(position);
@@ -127,6 +87,9 @@ PerfPkt6::updateOptions() {
// Replace existing option with new value.
option->pack(bufferOut_);
}
+ // Seek to the end of the end of the buffer
+ bufferOut_.clear();
+ bufferOut_.skip(data_.size());
}
catch (const Exception&) {
isc_throw(isc::Unexpected, "Failed to build packet (Option build failed");
@@ -134,6 +97,36 @@ PerfPkt6::updateOptions() {
}
void
+PerfPkt6::rawUnpackOptions() {
+ for (dhcp::Option::OptionCollection::const_iterator it = options_.begin();
+ it != options_.end(); ++it) {
+
+ LocalizedOptionPtr option = boost::dynamic_pointer_cast<LocalizedOption>(it->second);
+ size_t opt_pos = option->getOffset();
+
+ if (opt_pos == 0) {
+ isc_throw(isc::BadValue, "Failed to unpack packet from raw buffer "
+ "(Option position not specified)");
+ } else if (opt_pos + 4 > data_.size()) {
+ isc_throw(isc::BadValue, "Failed to unpack options from from raw buffer "
+ "(Option position out of bounds)");
+ }
+
+ size_t offset = opt_pos;
+ // uint16_t opt_type = data_[offset] * 256 + data_[offset + 1];
+ offset += 2;
+ uint16_t opt_len = data_[offset] * 256 + data_[offset + 1];
+ offset += 2;
+
+ if (offset + opt_len > data_.size()) {
+ isc_throw(isc::BadValue,
+ "Failed to unpack option from raw buffer (Option truncated)");
+ }
+ option->setData(data_.begin() + offset, data_.begin() + offset + opt_len);
+ }
+}
+
+void
PerfPkt6::updateTimestamp() {
if (clock_gettime(CLOCK_REALTIME, &time_stamp_) < 0) {
isc_throw(isc::Unexpected, "Failed to get timestamp for packet");
diff --git a/tests/tools/perfdhcp/perf_pkt6.h b/tests/tools/perfdhcp/perf_pkt6.h
index f3118d2..8d3c442 100644
--- a/tests/tools/perfdhcp/perf_pkt6.h
+++ b/tests/tools/perfdhcp/perf_pkt6.h
@@ -16,9 +16,11 @@
#define __PERF_PKT6_H
#include <time.h>
-
+#include <boost/shared_ptr.hpp>
#include <dhcp/pkt6.h>
+#include "localized_option.h"
+
namespace isc {
namespace perfdhcp {
@@ -43,7 +45,7 @@ namespace perfdhcp {
/// in a template packet, we need to add these selected options
/// to packet object using addOption() method. Please note
/// that options must be of the
-/// \ref isc::perfdhcp::PerfPkt6::PositionedOption type.
+/// \ref isc::perfdhcp::LocalizedOption type.
///
/// This class also records timestamps of last pack/unpack
/// operation on the packet. This is to track DHCP server
@@ -54,70 +56,8 @@ namespace perfdhcp {
///
class PerfPkt6 : public dhcp::Pkt6 {
public:
-
- /// \brief Class represents position of DHCP option in a packet
- class OptionPosition {
- public:
- /// \brief Class constructor
- ///
- /// Applies default value of option position
- explicit OptionPosition() : position_(0) { };
-
- /// \brief Class constructor
- ///
- /// \param position position of option in DHCP packet
- explicit OptionPosition(size_t position) : position_(position) { };
-
- /// \brief Returns position of DHCP option in a packet
- ///
- /// \return position of DHCP option in packet
- size_t get() const { return position_; }
- private:
- size_t position_; ///< position of option in a packet
- ///< Zero is default position
- };
-
- /// \brief DHCPv6 option at specific offset
- ///
- /// This class represents DHCPv6 option at specified
- /// offset in DHCPv6 message.
- ///
- class PositionedOption : public dhcp::Option {
- public:
- /// \brief Constructor, used to create positioned option from buffer
- ///
- ///
- /// \param u specifies universe (V4 or V6)
- /// \param type option type (0-255 for V4 and 0-65535 for V6)
- /// \param data content of the option
- /// \param position absolute position of option in a packet (zero is default)
- PositionedOption(dhcp::Option::Universe u, uint16_t type, const dhcp::OptionBuffer& data,
- const OptionPosition& position);
-
- /// \brief Constructor, used to create positioned option from buffer iterators
- ///
- /// This contructor is similar to the previous one, but it does not take
- /// the whole vector<uint8_t>, but rather subset of it.
- ///
- /// \param u specifies universe (V4 or V6)
- /// \param type option type (0-255 for V4 and 0-65535 for V6)
- /// \param first iterator to the first element that should be copied
- /// \param last iterator to the next element after the last one
- /// to be copied.
- /// \param position absolute position of option in a packet (zero is default)
- PositionedOption(dhcp::Option::Universe u, uint16_t type, dhcp::OptionBufferConstIter first,
- dhcp::OptionBufferConstIter last, const OptionPosition& position);
-
-
- /// \brief Returns absolute position (offset) of an option in a
- /// DHCPv6 packet.
- ///
- /// \return absolute position (offset) of an option in a packet
- size_t getOptionPosition() const { return position_.get(); };
-
- private:
- OptionPosition position_; ///< Absolute position of DHCPv6 option in a packet
- };
+ /// Localized option pointer type.
+ typedef boost::shared_ptr<LocalizedOption> LocalizedOptionPtr;
/// Constructor, used in message transmission
///
@@ -126,7 +66,7 @@ public:
/// options at custom offsets (e.g. if packet was read from
/// template file) additional information about options'
/// offsets has to be provided - see
- /// \ref isc::perfdhcp::PositionedOption for details.
+ /// \ref isc::perfdhcp::LocalizedOption for details.
///
/// Transaction id is not considered DHCP option so
/// we pass it to constructor as extra argument. This is
@@ -143,30 +83,17 @@ public:
/// \param xid_off transaction id offset in a packet
PerfPkt6(const uint8_t* buf,
uint32_t len,
- const OptionPosition& transid_offset);
+ size_t transid_offset_);
- /// \brief Prepare on-wire packet format and record timestamp
+ /// \brief Returns transaction id offset in packet buffer
///
- /// Prepares on-wire format of packet and all its options.
- /// This method wraps dhcp::Pkt6::pack() function to
- /// update packet timestamp.
- ///
- /// \note Use this function if you don't use template files
- /// to construct DHCPv6 packets.
- ///
- /// \throw isc::Unexpected if pack and timestamp update failed
- void stampedPack();
+ /// return transaction id offset in packet buffer
+ size_t getTransIdOffset() const { return transid_offset_; };
- /// \brief Handles binary packet parsing and updates timestamp
- ///
- /// This method wraps dhcp::Pkt6::unpack() function to
- /// update packet timestamp.
- ///
- /// \note Use this function if you don't use template files
- /// and custom options offsets to construct DHCPv6 packets.
+ /// \brief Returns current packet timestamp
///
- /// \throw isc::Unexpected if function failed
- void stampedUnpack();
+ /// \return current packet timestamp
+ timespec getTimestamp() const { return time_stamp_; }
/// \brief Prepares on-wire format from raw buffer
///
@@ -179,8 +106,8 @@ public:
/// when you use template packets that require replacement
/// of selected options contents before sending.
///
- /// \throw isc::Unexepected if function failed
- void stampedRawPack();
+ /// \retrun false, id pack operation failed.
+ bool rawPack();
/// \brief Handles limited binary packet parsing for packets with
/// custom offsets of options and transaction id
@@ -188,11 +115,16 @@ public:
/// Function handles reception of packets that have non-default values
/// of options or transaction id offsets. Use
/// \ref isc::dhcp::Pkt6::addOption to specify which options to parse.
- /// Each option should be of the: isc::perfdhcp::PerfPkt6::PositionedOption
+ /// Each option should be of the: isc::perfdhcp::LocalizedOption
/// type with offset value indicated.
///
- /// \throw isc::Unexpected if function failed
- void stampedRawUnpack();
+ /// \return false, if unpack operation failed.
+ bool rawUnpack();
+
+ /// \brief Update packet timestamp with current time
+ ///
+ /// \throw isc::Unexpected if timestamp update failed
+ void updateTimestamp();
private:
@@ -202,19 +134,16 @@ private:
/// with the ones provided with
/// \ref isc::dhcp::Pkt6::addOption. It is expected
/// that these options will be of the
- /// \ref isc::perfdhcp::PerfPkt6::PositionedOption type
+ /// \ref isc::perfdhcp::LocalizedOption type
/// with their position (offset) specified.
///
- /// throw isc::Unexpected if options update fails
- void updateOptions();
+ /// \throw isc::Unexpected if options update failed.
+ void rawPackOptions();
- /// \brief Update packet timestamp with current time
- ///
- /// \throw isc::Unexpected if timestamp update failed
- void updateTimestamp();
+ void rawUnpackOptions();
- OptionPosition transid_offset_; ///< transaction id offset
- timespec time_stamp_; ///< time stamp of last pack or unpack
+ size_t transid_offset_; ///< transaction id offset
+ timespec time_stamp_; ///< time stamp of last pack or unpack
};
diff --git a/tests/tools/perfdhcp/tests/Makefile.am b/tests/tools/perfdhcp/tests/Makefile.am
index c94ecba..ed5348d 100644
--- a/tests/tools/perfdhcp/tests/Makefile.am
+++ b/tests/tools/perfdhcp/tests/Makefile.am
@@ -4,8 +4,9 @@ AM_CPPFLAGS = -I$(top_builddir)/src/lib -I$(top_srcdir)/src/lib
AM_CPPFLAGS += $(BOOST_INCLUDES)
AM_CXXFLAGS = $(B10_CXXFLAGS)
+AM_LDFLAGS = $(CLOCK_GETTIME_LDFLAGS)
if USE_STATIC_LINK
-AM_LDFLAGS = -static
+AM_LDFLAGS += -static
endif
CLEANFILES = *.gcno *.gcda
@@ -15,7 +16,9 @@ if HAVE_GTEST
TESTS += run_unittests
run_unittests_SOURCES = run_unittests.cc
run_unittests_SOURCES += command_options_unittest.cc
+run_unittests_SOURCES += perf_pkt6_unittest.cc
run_unittests_SOURCES += $(top_builddir)/tests/tools/perfdhcp/command_options.cc
+run_unittests_SOURCES += $(top_builddir)/tests/tools/perfdhcp/perf_pkt6.cc
run_unittests_CPPFLAGS = $(AM_CPPFLAGS) $(GTEST_INCLUDES)
run_unittests_LDFLAGS = $(AM_LDFLAGS) $(GTEST_LDFLAGS)
@@ -23,6 +26,7 @@ run_unittests_LDFLAGS = $(AM_LDFLAGS) $(GTEST_LDFLAGS)
run_unittests_LDADD = $(GTEST_LDADD)
run_unittests_LDADD += $(top_builddir)/src/lib/util/libutil.la
run_unittests_LDADD += $(top_builddir)/src/lib/exceptions/libexceptions.la
+run_unittests_LDADD += $(top_builddir)/src/lib/dhcp/libdhcp++.la
run_unittests_LDADD += $(top_builddir)/src/lib/util/unittests/libutil_unittests.la
endif
diff --git a/tests/tools/perfdhcp/tests/perf_pkt6_unittest.cc b/tests/tools/perfdhcp/tests/perf_pkt6_unittest.cc
new file mode 100644
index 0000000..0acda00
--- /dev/null
+++ b/tests/tools/perfdhcp/tests/perf_pkt6_unittest.cc
@@ -0,0 +1,157 @@
+// Copyright (C) 2011-2012 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 notice and this permission notice appear in all copies.
+//
+// THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
+// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+// AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
+// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
+// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
+// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+// PERFORMANCE OF THIS SOFTWARE.
+
+#include <config.h>
+#include <iostream>
+#include <sstream>
+#include <arpa/inet.h>
+#include <gtest/gtest.h>
+
+#include <asiolink/io_address.h>
+#include <dhcp/option.h>
+#include <dhcp/dhcp6.h>
+
+#include "../localized_option.h"
+#include "../perf_pkt6.h"
+
+using namespace std;
+using namespace isc;
+using namespace isc::dhcp;
+using namespace isc::perfdhcp;
+
+typedef PerfPkt6::LocalizedOptionPtr LocalizedOptionPtr;
+
+namespace {
+class PerfPkt6Test : public ::testing::Test {
+public:
+ PerfPkt6Test() {
+ }
+
+ /// @brief returns captured actual SOLICIT packet
+ ///
+ /// Captured SOLICIT packet with transid=0x3d79fb and options: client-id,
+ /// in_na, dns-server, elapsed-time, option-request
+ /// This code was autogenerated (see src/bin/dhcp6/tests/iface_mgr_unittest.c),
+ /// but we spent some time to make is less ugly than it used to be.
+ ///
+ /// @return pointer to Pkt6 that represents received SOLICIT
+ PerfPkt6* capture1() {
+ uint8_t data[98];
+ data[0] = 1;
+ data[1] = 1; data[2] = 2; data[3] = 3; data[4] = 0;
+ data[5] = 1; data[6] = 0; data[7] = 14; data[8] = 0;
+ data[9] = 1; data[10] = 0; data[11] = 1; data[12] = 21;
+ data[13] = 158; data[14] = 60; data[15] = 22; data[16] = 0;
+ data[17] = 30; data[18] = 140; data[19] = 155; data[20] = 115;
+ data[21] = 73; data[22] = 0; data[23] = 3; data[24] = 0;
+ data[25] = 40; data[26] = 0; data[27] = 0; data[28] = 0;
+ data[29] = 1; data[30] = 255; data[31] = 255; data[32] = 255;
+ data[33] = 255; data[34] = 255; data[35] = 255; data[36] = 255;
+ data[37] = 255; data[38] = 0; data[39] = 5; data[40] = 0;
+ data[41] = 24; data[42] = 32; data[43] = 1; data[44] = 13;
+ data[45] = 184; data[46] = 0; data[47] = 1; data[48] = 0;
+ data[49] = 0; data[50] = 0; data[51] = 0; data[52] = 0;
+ data[53] = 0; data[54] = 0; data[55] = 0; data[56] = 18;
+ data[57] = 52; data[58] = 255; data[59] = 255; data[60] = 255;
+ data[61] = 255; data[62] = 255; data[63] = 255; data[64] = 255;
+ data[65] = 255; data[66] = 0; data[67] = 23; data[68] = 0;
+ data[69] = 16; data[70] = 32; data[71] = 1; data[72] = 13;
+ data[73] = 184; data[74] = 0; data[75] = 1; data[76] = 0;
+ data[77] = 0; data[78] = 0; data[79] = 0; data[80] = 0;
+ data[81] = 0; data[82] = 0; data[83] = 0; data[84] = 221;
+ data[85] = 221; data[86] = 0; data[87] = 8; data[88] = 0;
+ data[89] = 2; data[90] = 0; data[91] = 100; data[92] = 0;
+ data[93] = 6; data[94] = 0; data[95] = 2; data[96] = 0;
+ data[97] = 23;
+
+ PerfPkt6* pkt = new PerfPkt6(data, sizeof(data), 0);
+
+ return (pkt);
+ }
+
+};
+
+TEST_F(PerfPkt6Test, Constructor) {
+ uint8_t data[] = { 0, 1, 2, 3, 4, 5 };
+ timespec zero_t_spec;
+ memset(&zero_t_spec, 0, sizeof(zero_t_spec));
+
+ boost::scoped_ptr<PerfPkt6> pkt1(new PerfPkt6(data, sizeof(data), 1));
+ timespec packet_t_spec = pkt1->getTimestamp();
+
+ EXPECT_EQ(6, pkt1->getData().size());
+ EXPECT_EQ(0, memcmp( &pkt1->getData()[0], data, sizeof(data)));
+ EXPECT_EQ(1, pkt1->getTransIdOffset());
+ EXPECT_EQ(0, memcmp(&packet_t_spec, &zero_t_spec, sizeof(zero_t_spec)));
+}
+
+TEST_F(PerfPkt6Test, RawPackUnpack) {
+ // Create first packet.
+ boost::scoped_ptr<PerfPkt6> pkt1(capture1());
+
+ // Create some input buffers to initialize options.
+ uint8_t buf_elapsed_time[] = { 1, 1 };
+ uint8_t buf_duid[14] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14 };
+
+ // Create options.
+ dhcp::OptionBuffer vec_elapsed_time(buf_elapsed_time, buf_elapsed_time + 2);
+ dhcp::OptionBuffer vec_duid(buf_duid, buf_duid + 14);
+ LocalizedOptionPtr pkt1_elapsed_time(new LocalizedOption(Option::V6, 8, vec_elapsed_time, 86));
+ LocalizedOptionPtr pkt1_duid(new LocalizedOption(Option::V6, D6O_CLIENTID, vec_duid, 4));
+
+ // Add option to packet and create on-wire format from added options.
+ // Contents of options will override contents of packet buffer.
+ ASSERT_NO_THROW(pkt1->addOption(pkt1_elapsed_time));
+ ASSERT_NO_THROW(pkt1->addOption(pkt1_duid));
+ ASSERT_TRUE(pkt1->rawPack());
+
+ // Reset so as we can reuse them for another packet.
+ vec_elapsed_time.clear();
+ vec_duid.clear();
+
+ // Get output buffer from packet 1 to create new packet
+ // that will be later validated.
+ isc::util::OutputBuffer pkt1_output = pkt1->getBuffer();
+ ASSERT_EQ(pkt1_output.getLength(), pkt1->getData().size());
+ boost::scoped_ptr<PerfPkt6> pkt2(new PerfPkt6(static_cast<const uint8_t*>(pkt1_output.getData()),
+ pkt1_output.getLength(), 1));
+
+ // Create objects specifying options offset in a packet.
+ // Offsets will inform pkt2 object where to read data from.
+ LocalizedOptionPtr pkt2_elapsed_time(new LocalizedOption(Option::V6, D6O_ELAPSED_TIME, vec_elapsed_time, 86));
+ LocalizedOptionPtr pkt2_duid(new LocalizedOption(Option::V6, D6O_CLIENTID, vec_duid, 4));
+ // Add options to packet to pass their offsets.
+ pkt2->addOption(pkt2_elapsed_time);
+ pkt2->addOption(pkt2_duid);
+
+ // Unpack: get relevant parts of buffer data into option objects.
+ ASSERT_TRUE(pkt2->rawUnpack());
+
+ // Once option data is stored in options objects we pull it out.
+ pkt2_elapsed_time = boost::dynamic_pointer_cast<LocalizedOption>(pkt2->getOption(D6O_ELAPSED_TIME));
+ pkt2_duid = boost::dynamic_pointer_cast<LocalizedOption>(pkt2->getOption(D6O_CLIENTID));
+
+ // Check if options are present. They have to be there since
+ // we have added them ourselfs.
+ ASSERT_TRUE(pkt2_elapsed_time);
+ ASSERT_TRUE(pkt2_duid);
+
+ // Expecting option contents be the same as original.
+ OptionBuffer pkt2_elapsed_time_data = pkt2_elapsed_time->getData();
+ OptionBuffer pkt2_duid_data = pkt2_duid->getData();
+ EXPECT_EQ(0x0101, pkt2_elapsed_time->getUint16());
+ EXPECT_TRUE(std::equal(pkt2_duid_data.begin(), pkt2_duid_data.end(), buf_duid));
+}
+
+}
More information about the bind10-changes
mailing list