libperfdhcp_la_SOURCES += stats_mgr.h
libperfdhcp_la_SOURCES += test_control.cc test_control.h
libperfdhcp_la_SOURCES += receiver.cc receiver.h
-libperfdhcp_la_SOURCES += better_socket.cc better_socket.h
+libperfdhcp_la_SOURCES += perf_socket.cc perf_socket.h
sbin_PROGRAMS = perfdhcp
perfdhcp_SOURCES = main.cc
" with the exchange rate (given by -r<rate>). Furthermore the sum of\n"
" this value and the release-rate (given by -F<rate) must be equal\n"
" to or less than the exchange rate.\n"
- "-g Select thread mode: 'single' or 'multi'. In multi-thread mode packets\n"
- " are received in separate thread. This allows better utilisation of CPUs."
- " If more than 1 CPU is present then multi-thread mode is the default,"
- " otherwise single-thread is the default."
+ "-g: Select thread mode: 'single' or 'multi'. In multi-thread mode packets\n"
+ " are received in separate thread. This allows better utilisation of CPUs.\n"
+ " If more than 1 CPU is present then multi-thread mode is the default,\n"
+ " otherwise single-thread is the default.\n"
"-h: Print this help.\n"
"-i: Do only the initial part of an exchange: DO or SA, depending on\n"
" whether -6 is given.\n"
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
-#include <perfdhcp/better_socket.h>
+#include <perfdhcp/perf_socket.h>
#include <dhcp/iface_mgr.h>
namespace isc {
namespace perfdhcp {
-BetterSocket::BetterSocket(const int socket) :
+PerfSocket::PerfSocket(const int socket) :
SocketInfo(asiolink::IOAddress("127.0.0.1"), 0, socket),
ifindex_(0), valid_(true) {
try {
}
}
-BetterSocket::~BetterSocket() {
+PerfSocket::~PerfSocket() {
IfacePtr iface = IfaceMgr::instance().getIface(ifindex_);
if (iface) {
iface->delSocket(sockfd_);
}
void
-BetterSocket::initSocketData() {
+PerfSocket::initSocketData() {
BOOST_FOREACH(IfacePtr iface, IfaceMgr::instance().getIfaces()) {
BOOST_FOREACH(SocketInfo s, iface->getSockets()) {
if (s.sockfd_ == sockfd_) {
-// Copyright (C) 2012-2018 Internet Systems Consortium, Inc. ("ISC")
+// Copyright (C) 2012-2019 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
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
-#ifndef BETTER_SOCKET_H
-#define BETTER_SOCKET_H
+#ifndef PERF_SOCKET_H
+#define PERF_SOCKET_H
#include <dhcp/socket_info.h>
/// when exception occurs). This structure extends parent
/// structure with new field ifindex_ that holds interface
/// index where socket is bound to.
-struct BetterSocket : public dhcp::SocketInfo {
+struct PerfSocket : public dhcp::SocketInfo {
/// Interface index.
uint16_t ifindex_;
/// Is socket valid. It will not be valid if the provided socket
/// valid_ field is set to false;
///
/// \param socket socket descriptor.
- BetterSocket(const int socket);
+ PerfSocket(const int socket);
/// \brief Destructor of the socket wrapper class.
///
/// Destructor closes wrapped socket.
- virtual ~BetterSocket();
+ virtual ~PerfSocket();
private:
/// \brief Initialize socket data.
}
}
-#endif /* BETTER_SOCKET_H */
+#endif /* PERF_SOCKET_H */
#include <perfdhcp/receiver.h>
#include <perfdhcp/command_options.h>
-#include <util/threads/thread.h>
#include <dhcp/iface_mgr.h>
return readPktFromSocket();
} else {
// In multi thread mode read packet from the queue which is feed by Receiver thread.
- unique_lock<mutex> lock(pkt_queue_mutex_);
+ util::thread::Mutex::Locker lock(pkt_queue_mutex_);
if (pkt_queue_.empty()) {
if (CommandOptions::instance().getIpVersion() == 4) {
return Pkt4Ptr();
if (pkt->getType() == DHCPOFFER || pkt->getType() == DHCPACK ||
pkt->getType() == DHCPV6_ADVERTISE || pkt->getType() == DHCPV6_REPLY) {
// Otherwise push the packet to the queue, to main thread.
- unique_lock<mutex> lock(pkt_queue_mutex_);
+ util::thread::Mutex::Locker lock(pkt_queue_mutex_);
pkt_queue_.push(pkt);
}
}
#ifndef PERFDHCP_RECEIVER_H
#define PERFDHCP_RECEIVER_H
-#include <perfdhcp/better_socket.h>
+#include <perfdhcp/perf_socket.h>
#include <perfdhcp/command_options.h>
#include <dhcp/pkt.h>
#include <util/threads/thread.h>
+#include <util/threads/sync.h>
#include <queue>
#include <thread>
-#include <mutex>
#include <boost/atomic.hpp>
namespace isc {
class Receiver {
public:
/// \brief Socket for receiving.
- const BetterSocket& socket_;
+ const PerfSocket& socket_;
private:
/// \brief Flag indicating if thread should run (true) or not (false).
std::queue<dhcp::PktPtr> pkt_queue_;
/// \brief Mutex for controlling access to the queue.
- std::mutex pkt_queue_mutex_;
+ util::thread::Mutex pkt_queue_mutex_;
/// \brief Single- or thread-mode indicator.
bool single_threaded_;
/// \brief Receiver constructor.
///
/// \param socket A socket for receiving packets.
- Receiver(const BetterSocket& socket) :
+ Receiver(const PerfSocket& socket) :
socket_(socket),
single_threaded_(CommandOptions::instance().isSingleThreaded()) {
}
}
void
-TestControl::sendPackets(const BetterSocket& socket,
+TestControl::sendPackets(const PerfSocket& socket,
const uint64_t packets_num,
const bool preload /* = false */) {
CommandOptions& options = CommandOptions::instance();
}
uint64_t
-TestControl::sendMultipleRequests(const BetterSocket& socket,
+TestControl::sendMultipleRequests(const PerfSocket& socket,
const uint64_t msg_num) {
for (uint64_t i = 0; i < msg_num; ++i) {
if (!sendRequestFromAck(socket)) {
}
uint64_t
-TestControl::sendMultipleMessages6(const BetterSocket& socket,
+TestControl::sendMultipleMessages6(const PerfSocket& socket,
const uint32_t msg_type,
const uint64_t msg_num) {
for (uint64_t i = 0; i < msg_num; ++i) {
}
void
-TestControl::processReceivedPacket4(const BetterSocket& socket,
+TestControl::processReceivedPacket4(const PerfSocket& socket,
const Pkt4Ptr& pkt4) {
if (pkt4->getType() == DHCPOFFER) {
Pkt4Ptr discover_pkt4(stats_mgr4_->passRcvdPacket(StatsMgr4::XCHG_DO,
}
void
-TestControl::processReceivedPacket6(const BetterSocket& socket,
+TestControl::processReceivedPacket6(const PerfSocket& socket,
const Pkt6Ptr& pkt6) {
uint8_t packet_type = pkt6->getType();
if (packet_type == DHCPV6_ADVERTISE) {
}
unsigned int
-TestControl::consumeReceivedPackets(Receiver& receiver, const BetterSocket& socket) {
+TestControl::consumeReceivedPackets(Receiver& receiver, const PerfSocket& socket) {
unsigned int pkt_count = 0;
PktPtr pkt;
while ((pkt = receiver.getPkt())) {
printDiagnostics();
// Option factories have to be registered.
registerOptionFactories();
- BetterSocket socket(openSocket());
+ PerfSocket socket(openSocket());
if (!socket.valid_) {
isc_throw(Unexpected, "invalid socket descriptor");
}
// CPU idle for a moment, to not consume 100% CPU all the time
// but only if it is not that high request rate expected.
if (options.getRate() < 10000 && packets_due == 0 && pkt_count == 0) {
+ // @todo: need to implement adaptive time here, so the sleep time is not fixed, but adjusts to current situation.
usleep(1);
}
}
void
-TestControl::sendDiscover4(const BetterSocket& socket,
+TestControl::sendDiscover4(const PerfSocket& socket,
const bool preload /*= false*/) {
// Generate the MAC address to be passed in the packet.
uint8_t randomized = 0;
}
void
-TestControl::sendDiscover4(const BetterSocket& socket,
+TestControl::sendDiscover4(const PerfSocket& socket,
const std::vector<uint8_t>& template_buf,
const bool preload /* = false */) {
// Get the first argument if multiple the same arguments specified
}
bool
-TestControl::sendRequestFromAck(const BetterSocket& socket) {
+TestControl::sendRequestFromAck(const PerfSocket& socket) {
// Get one of the recorded DHCPACK messages.
Pkt4Ptr ack = ack_storage_.getRandom();
if (!ack) {
bool
TestControl::sendMessageFromReply(const uint16_t msg_type,
- const BetterSocket& socket) {
+ const PerfSocket& socket) {
// We only permit Release or Renew messages to be sent using this function.
if (msg_type != DHCPV6_RENEW && msg_type != DHCPV6_RELEASE) {
isc_throw(isc::BadValue, "invalid message type " << msg_type
}
void
-TestControl::sendRequest4(const BetterSocket& socket,
+TestControl::sendRequest4(const PerfSocket& socket,
const dhcp::Pkt4Ptr& discover_pkt4,
const dhcp::Pkt4Ptr& offer_pkt4) {
// Use the same transaction id as the one used in the discovery packet.
}
void
-TestControl::sendRequest4(const BetterSocket& socket,
+TestControl::sendRequest4(const PerfSocket& socket,
const std::vector<uint8_t>& template_buf,
const dhcp::Pkt4Ptr& discover_pkt4,
const dhcp::Pkt4Ptr& offer_pkt4) {
}
void
-TestControl::sendRequest6(const BetterSocket& socket,
+TestControl::sendRequest6(const PerfSocket& socket,
const Pkt6Ptr& advertise_pkt6) {
const uint32_t transid = generateTransid();
Pkt6Ptr pkt6(new Pkt6(DHCPV6_REQUEST, transid));
}
void
-TestControl::sendRequest6(const BetterSocket& socket,
+TestControl::sendRequest6(const PerfSocket& socket,
const std::vector<uint8_t>& template_buf,
const Pkt6Ptr& advertise_pkt6) {
// Get the second argument if multiple the same arguments specified
}
void
-TestControl::sendSolicit6(const BetterSocket& socket,
+TestControl::sendSolicit6(const PerfSocket& socket,
const bool preload /*= false*/) {
// Generate DUID to be passed to the packet
uint8_t randomized = 0;
}
void
-TestControl::sendSolicit6(const BetterSocket& socket,
+TestControl::sendSolicit6(const PerfSocket& socket,
const std::vector<uint8_t>& template_buf,
const bool preload /*= false*/) {
const int arg_idx = 0;
void
-TestControl::setDefaults4(const BetterSocket& socket,
+TestControl::setDefaults4(const PerfSocket& socket,
const Pkt4Ptr& pkt) {
CommandOptions& options = CommandOptions::instance();
// Interface name.
}
void
-TestControl::setDefaults6(const BetterSocket& socket,
+TestControl::setDefaults6(const PerfSocket& socket,
const Pkt6Ptr& pkt) {
CommandOptions& options = CommandOptions::instance();
// Interface name.
/// \brief Pull packets from receiver and process them.
/// It runs in a loop until there are no packets in receiver.
- unsigned int consumeReceivedPackets(Receiver& receiver, const BetterSocket& socket);
+ unsigned int consumeReceivedPackets(Receiver& receiver, const PerfSocket& socket);
/// \brief Process received DHCPv4 packet.
///
/// \param [in] pkt4 object representing DHCPv4 packet received.
/// \throw isc::BadValue if unknown message type received.
/// \throw isc::Unexpected if unexpected error occurred.
- void processReceivedPacket4(const BetterSocket& socket,
+ void processReceivedPacket4(const PerfSocket& socket,
const dhcp::Pkt4Ptr& pkt4);
/// \brief Process received DHCPv6 packet.
/// \param [in] pkt6 object representing DHCPv6 packet received.
/// \throw isc::BadValue if unknown message type received.
/// \throw isc::Unexpected if unexpected error occurred.
- void processReceivedPacket6(const BetterSocket& socket,
+ void processReceivedPacket6(const PerfSocket& socket,
const dhcp::Pkt6Ptr& pkt6);
/// \brief Register option factory functions for DHCPv4
/// \throw isc::Unexpected if failed to create new packet instance.
/// \throw isc::BadValue if MAC address has invalid length.
/// \throw isc::dhcp::SocketWriteError if failed to send the packet.
- void sendDiscover4(const BetterSocket& socket,
+ void sendDiscover4(const PerfSocket& socket,
const bool preload = false);
/// \brief Send DHCPv4 DISCOVER message from template.
///
/// \throw isc::OutOfRange if randomization offset is out of bounds.
/// \throw isc::dhcp::SocketWriteError if failed to send the packet.
- void sendDiscover4(const BetterSocket& socket,
+ void sendDiscover4(const PerfSocket& socket,
const std::vector<uint8_t>& template_buf,
const bool preload = false);
/// \throw isc::Unexpected if thrown by packet sending method.
/// \throw isc::InvalidOperation if thrown by packet sending method.
/// \throw isc::OutOfRange if thrown by packet sending method.
- void sendPackets(const BetterSocket &socket,
+ void sendPackets(const PerfSocket &socket,
const uint64_t packets_num,
const bool preload = false);
/// \param msg_num A number of messages to be sent.
///
/// \return A number of messages actually sent.
- uint64_t sendMultipleRequests(const BetterSocket& socket,
+ uint64_t sendMultipleRequests(const PerfSocket& socket,
const uint64_t msg_num);
/// \brief Send number of DHCPv6 Renew or Release messages to the server.
/// \param msg_num A number of messages to be sent.
///
/// \return A number of messages actually sent.
- uint64_t sendMultipleMessages6(const BetterSocket& socket,
+ uint64_t sendMultipleMessages6(const PerfSocket& socket,
const uint32_t msg_type,
const uint64_t msg_num);
/// a packet.
///
/// \return true if the message has been sent, false otherwise.
- bool sendRequestFromAck(const BetterSocket& socket);
+ bool sendRequestFromAck(const PerfSocket& socket);
/// \brief Send DHCPv6 Renew or Release message using specified socket.
///
///
/// \return true if the message has been sent, false otherwise.
bool sendMessageFromReply(const uint16_t msg_type,
- const BetterSocket& socket);
+ const PerfSocket& socket);
/// \brief Send DHCPv4 REQUEST message.
///
/// \throw isc::InvalidOperation if Statistics Manager has not been
/// initialized.
/// \throw isc::dhcp::SocketWriteError if failed to send the packet.
- void sendRequest4(const BetterSocket& socket,
+ void sendRequest4(const PerfSocket& socket,
const dhcp::Pkt4Ptr& discover_pkt4,
const dhcp::Pkt4Ptr& offer_pkt4);
/// \param offer_pkt4 OFFER packet received.
///
/// \throw isc::dhcp::SocketWriteError if failed to send the packet.
- void sendRequest4(const BetterSocket& socket,
+ void sendRequest4(const PerfSocket& socket,
const std::vector<uint8_t>& template_buf,
const dhcp::Pkt4Ptr& discover_pkt4,
const dhcp::Pkt4Ptr& offer_pkt4);
/// initialized.
///
/// \throw isc::dhcp::SocketWriteError if failed to send the packet.
- void sendRequest6(const BetterSocket& socket,
+ void sendRequest6(const PerfSocket& socket,
const dhcp::Pkt6Ptr& advertise_pkt6);
/// \brief Send DHCPv6 REQUEST message from template.
/// \param advertise_pkt6 ADVERTISE packet object.
///
/// \throw isc::dhcp::SocketWriteError if failed to send the packet.
- void sendRequest6(const BetterSocket& socket,
+ void sendRequest6(const PerfSocket& socket,
const std::vector<uint8_t>& template_buf,
const dhcp::Pkt6Ptr& advertise_pkt6);
///
/// \throw isc::Unexpected if failed to create new packet instance.
/// \throw isc::dhcp::SocketWriteError if failed to send the packet.
- void sendSolicit6(const BetterSocket& socket,
+ void sendSolicit6(const PerfSocket& socket,
const bool preload = false);
/// \brief Send DHCPv6 SOLICIT message from template.
/// \param preload mode, packets not included in statistics.
///
/// \throw isc::dhcp::SocketWriteError if failed to send the packet.
- void sendSolicit6(const BetterSocket& socket,
+ void sendSolicit6(const PerfSocket& socket,
const std::vector<uint8_t>& template_buf,
const bool preload = false);
///
/// \param socket socket used to send the packet.
/// \param pkt reference to packet to be configured.
- void setDefaults4(const BetterSocket& socket,
+ void setDefaults4(const PerfSocket& socket,
const dhcp::Pkt4Ptr& pkt);
/// \brief Set default DHCPv6 packet parameters.
///
/// \param socket socket used to send the packet.
/// \param pkt reference to packet to be configured.
- void setDefaults6(const BetterSocket& socket,
+ void setDefaults6(const PerfSocket& socket,
const dhcp::Pkt6Ptr& pkt);
/// @brief Inserts extra options specified by user.
CommandOptionsHelper::process("perfdhcp -g single -l 127.0.0.1 all");
ASSERT_TRUE(CommandOptions::instance().isSingleThreaded());
- BetterSocket sock(123);
+ PerfSocket sock(123);
Receiver receiver(sock);
CommandOptionsHelper::process("perfdhcp -g multi -l 127.0.0.1 all");
ASSERT_FALSE(CommandOptions::instance().isSingleThreaded());
- BetterSocket sock(123);
+ PerfSocket sock(123);
Receiver receiver(sock);
tc.setTransidGenerator(generator);
// Socket is needed to send packets through the interface.
ASSERT_NO_THROW(sock_handle = tc.openSocket());
- BetterSocket sock(sock_handle);
+ PerfSocket sock(sock_handle);
for (int i = 0; i < iterations_num; ++i) {
// Get next transaction id, without actually using it. The same
// id wll be used by the TestControl class for DHCPDISCOVER.
tc.setTransidGenerator(generator);
// Socket is needed to send packets through the interface.
ASSERT_NO_THROW(sock_handle = tc.openSocket());
- BetterSocket sock(sock_handle);
+ PerfSocket sock(sock_handle);
uint32_t transid = 0;
for (int i = 0; i < iterations_num; ++i) {
// Do not simulate responses for packets later
// Socket has to be created so as we can actually send packets.
int sock_handle = 0;
ASSERT_NO_THROW(sock_handle = tc.openSocket());
- BetterSocket sock(sock_handle);
+ PerfSocket sock(sock_handle);
// Send a number of DHCPDISCOVER messages. Each generated message will
// be assigned a different transaction id, starting from 1 to 10.
// Socket has to be created so as we can actually send packets.
int sock_handle = 0;
ASSERT_NO_THROW(sock_handle = tc.openSocket());
- BetterSocket sock(sock_handle);
+ PerfSocket sock(sock_handle);
// Send a number of Solicit messages. Each generated Solicit will be
// assigned a different transaction id, starting from 1 to 10.
// We have to create the socket to setup some parameters of
// outgoing packet.
ASSERT_NO_THROW(sock_handle = tc.openSocket());
- BetterSocket sock(sock_handle);
+ PerfSocket sock(sock_handle);
uint32_t transid = 123;
boost::shared_ptr<Pkt4> pkt4(new Pkt4(DHCPDISCOVER, transid));
// Set parameters on outgoing packet.
// Create the socket. It will be needed to set packet's
// parameters.
ASSERT_NO_THROW(sock_handle = tc.openSocket());
- BetterSocket sock(sock_handle);
+ PerfSocket sock(sock_handle);
uint32_t transid = 123;
boost::shared_ptr<Pkt6> pkt6(new Pkt6(DHCPV6_SOLICIT, transid));
// Set packet's parameters.
// Create the socket. It will be needed to set packet's
// parameters.
ASSERT_NO_THROW(sock_handle = tc.openSocket());
- BetterSocket sock(sock_handle);
+ PerfSocket sock(sock_handle);
uint32_t transid = 123;
boost::shared_ptr<Pkt6> pkt6(new Pkt6(DHCPV6_SOLICIT, transid));
// Set packet's parameters.
// Socket is needed to send packets through the interface.
int sock_handle = 0;
ASSERT_NO_THROW(sock_handle = tc.openSocket());
- BetterSocket sock(sock_handle);
+ PerfSocket sock(sock_handle);
// Make tc send the packet. The first packet of each type is saved in templates.
ASSERT_NO_THROW(tc.sendDiscover4(sock));