Skip to content

Commit

Permalink
Adding auto-connect disabled UTs
Browse files Browse the repository at this point in the history
  • Loading branch information
LeStarch committed Jan 17, 2025
1 parent ab8d466 commit dab2053
Show file tree
Hide file tree
Showing 10 changed files with 133 additions and 22 deletions.
2 changes: 1 addition & 1 deletion Drv/Ip/IpSocket.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ enum SocketIpStatus {
SOCK_FAILED_TO_READ_BACK_PORT = -15, //!< Failed to read back port from connection
SOCK_NO_DATA_AVAILABLE = -16, //!< No data available or read operation would block
SOCK_ANOTHER_THREAD_OPENING = -17, //!< Another thread is opening
SOCK_AUTOCONNECT_DISABLED = -18 //!< Automatic connections are disabled
SOCK_AUTO_CONNECT_DISABLED = -18 //!< Automatic connections are disabled
};

/**
Expand Down
4 changes: 2 additions & 2 deletions Drv/Ip/SocketComponentHelper.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -93,7 +93,7 @@ SocketIpStatus SocketComponentHelper::reconnect() {
}
// Open a network connection if it has not already been open
if (not reconnect) {
status = SOCK_AUTOCONNECT_DISABLED;
status = SOCK_AUTO_CONNECT_DISABLED;
} else {
status = this->open();
if (status == SocketIpStatus::SOCK_ANOTHER_THREAD_OPENING) {
Expand Down Expand Up @@ -182,7 +182,7 @@ void SocketComponentHelper::readLoop() {
if ((not this->isOpened()) and this->running()) {
status = this->reconnect();
// When reconnect is disabled, just break as this is a exit condition for the loop
if (status == SOCK_AUTOCONNECT_DISABLED) {
if (status == SOCK_AUTO_CONNECT_DISABLED) {
break;
}
// If the reconnection failed in any other way, warn, wait, and retry
Expand Down
10 changes: 10 additions & 0 deletions Drv/TcpClient/test/ut/TcpClientTestMain.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,16 @@ TEST(Reconnect, TcpClientReceiveThreadReconnect) {
tester.test_advanced_reconnect();
}

TEST(AutoConnect, AutoConnectOnSendOff) {
Drv::TcpClientTester tester;
tester.test_no_automatic_send_connection();
}

TEST(AutoConnect, AutoConnectOnRecvOff) {
Drv::TcpClientTester tester;
tester.test_no_automatic_recv_connection();
}

int main(int argc, char** argv) {
::testing::InitGoogleTest(&argc, argv);
return RUN_ALL_TESTS();
Expand Down
47 changes: 39 additions & 8 deletions Drv/TcpClient/test/ut/TcpClientTester.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -23,17 +23,11 @@ namespace Drv {
// Construction and destruction
// ----------------------------------------------------------------------

void TcpClientTester ::test_with_loop(U32 iterations, bool recv_thread) {
U8 buffer[sizeof(m_data_storage)] = {};
Drv::SocketIpStatus status1 = Drv::SOCK_SUCCESS;
Drv::SocketIpStatus status2 = Drv::SOCK_SUCCESS;
void TcpClientTester ::setup_helper(Drv::TcpServerSocket& server, Drv::SocketDescriptor& server_fd, bool recv_thread, bool reconnect) {
Drv::SocketIpStatus serverStat = Drv::SOCK_SUCCESS;

U16 port = 0;

Drv::TcpServerSocket server;
server.configure("127.0.0.1", port, 0, 100);
Drv::SocketDescriptor server_fd;

serverStat = server.startup(server_fd);
this->component.configure("127.0.0.1", server.getListenPort(), 0, 100);
Expand All @@ -45,8 +39,19 @@ void TcpClientTester ::test_with_loop(U32 iterations, bool recv_thread) {
// Start up a receive thread
if (recv_thread) {
Os::TaskString name("receiver thread");
this->component.start(name, true, Os::Task::TASK_DEFAULT, Os::Task::TASK_DEFAULT);
this->component.start(name, reconnect, Os::Task::TASK_DEFAULT, Os::Task::TASK_DEFAULT);
}
}


void TcpClientTester ::test_with_loop(U32 iterations, bool recv_thread) {
U8 buffer[sizeof(m_data_storage)] = {};
Drv::SocketIpStatus status1 = Drv::SOCK_SUCCESS;
Drv::SocketIpStatus status2 = Drv::SOCK_SUCCESS;

Drv::TcpServerSocket server;
Drv::SocketDescriptor server_fd;
setup_helper(server, server_fd, recv_thread, true);

// Loop through a bunch of client disconnects
for (U32 i = 0; i < iterations; i++) {
Expand Down Expand Up @@ -147,6 +152,32 @@ void TcpClientTester ::test_advanced_reconnect() {
test_with_loop(10, true); // Up to 10 * RECONNECT_MS
}

void TcpClientTester ::test_no_automatic_send_connection() {
Drv::TcpServerSocket server;
Drv::SocketDescriptor server_fd;
this->setup_helper(server, server_fd, false, false);
this->component.setAutoConnect(false);
ASSERT_EQ(this->component.send(reinterpret_cast<const U8*>("a"), 1), Drv::SOCK_AUTO_CONNECT_DISABLED);
ASSERT_FALSE(this->component.isOpened());
// Clean-up even if the send worked
Drv::Test::drain(server, server_fd);
server.terminate(server_fd);
}

void TcpClientTester ::test_no_automatic_recv_connection() {
Drv::TcpServerSocket server;
Drv::SocketDescriptor server_fd;
this->setup_helper(server, server_fd, true, false);
// Wait for connection to not start
EXPECT_FALSE(this->wait_on_change(this->component.getSocketHandler(), true, Drv::Test::get_configured_delay_ms()/10 + 1));
ASSERT_FALSE(this->component.isOpened());
// Clean-up even if the thread (incorrectly) started
this->component.stop();
this->component.join();
Drv::Test::drain(server, server_fd);
server.terminate(server_fd);
}

// ----------------------------------------------------------------------
// Handlers for typed from ports
// ----------------------------------------------------------------------
Expand Down
6 changes: 6 additions & 0 deletions Drv/TcpClient/test/ut/TcpClientTester.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,8 @@ namespace Drv {
// Tests
// ----------------------------------------------------------------------

void setup_helper(Drv::TcpServerSocket& server, Drv::SocketDescriptor& server_fd, bool recv_thread, bool reconnect);

void test_basic_messaging();

void test_multiple_messaging();
Expand All @@ -59,6 +61,10 @@ namespace Drv {

void test_advanced_reconnect();

void test_no_automatic_send_connection();

void test_no_automatic_recv_connection();

void test_with_loop(U32 iterations, bool recv_thread=false);

private:
Expand Down
4 changes: 2 additions & 2 deletions Drv/TcpServer/TcpServerComponentImpl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -115,9 +115,9 @@ void TcpServerComponentImpl::readLoop() {
if (this->running() && status == SOCK_SUCCESS) {
// Perform the nominal read loop
SocketComponentHelper::readLoop();
// Terminate the server
this->terminate();
}
// Terminate the server
this->terminate();
}

// ----------------------------------------------------------------------
Expand Down
2 changes: 1 addition & 1 deletion Drv/TcpServer/TcpServerComponentImpl.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ class TcpServerComponentImpl : public TcpServerComponentBase, public SocketCompo
const U16 port,
const U32 send_timeout_seconds = SOCKET_SEND_TIMEOUT_SECONDS,
const U32 send_timeout_microseconds = SOCKET_SEND_TIMEOUT_MICROSECONDS,
FwSizeType buffer_size = 1024);
FwSizeType buffer_size = 1024);

/**
* \brief is started
Expand Down
11 changes: 11 additions & 0 deletions Drv/TcpServer/test/ut/TcpServerTestMain.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,17 @@ TEST(Reconnect, TcpServerReceiveThreadReconnect) {
tester.test_advanced_reconnect();
}

TEST(AutoConnect, AutoConnectOnSendOff) {
Drv::TcpServerTester tester;
tester.test_no_automatic_send_connection();
}

TEST(AutoConnect, AutoConnectOnRecvOff) {
Drv::TcpServerTester tester;
tester.test_no_automatic_recv_connection();
}


int main(int argc, char** argv) {
::testing::InitGoogleTest(&argc, argv);
return RUN_ALL_TESTS();
Expand Down
64 changes: 56 additions & 8 deletions Drv/TcpServer/test/ut/TcpServerTester.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -23,23 +23,31 @@ namespace Drv {
// Construction and destruction
// ----------------------------------------------------------------------

void TcpServerTester ::test_with_loop(U32 iterations, bool recv_thread) {
U8 buffer[sizeof(m_data_storage)] = {};
void TcpServerTester ::setup_helper(bool recv_thread, bool reconnect) {
Drv::SocketIpStatus status1 = Drv::SOCK_SUCCESS;
Drv::SocketIpStatus status2 = Drv::SOCK_SUCCESS;

U16 port = 0;
Drv::SocketDescriptor client_fd;
EXPECT_FALSE(component.isStarted());
status1 = this->component.configure("127.0.0.1", port, 0, 100);
EXPECT_EQ(status1, Drv::SOCK_SUCCESS);

// Start up a receive thread
if (recv_thread) {
Os::TaskString name("receiver thread");
this->component.start(name, true, Os::Task::TASK_DEFAULT, Os::Task::TASK_DEFAULT);
EXPECT_TRUE(this->wait_on_started(true, Drv::Test::get_configured_delay_ms()/10 + 1));
this->component.start(name, reconnect, Os::Task::TASK_DEFAULT, Os::Task::TASK_DEFAULT);
}
// Component should always launch the listening server on configure
// The thread will retry if the configure fails
EXPECT_TRUE(this->wait_on_started(true, Drv::Test::get_configured_delay_ms()/10 + 1));
EXPECT_TRUE(component.isStarted());
}

void TcpServerTester ::test_with_loop(U32 iterations, bool recv_thread) {
U8 buffer[sizeof(m_data_storage)] = {};
Drv::SocketIpStatus status1 = Drv::SOCK_SUCCESS;
Drv::SocketIpStatus status2 = Drv::SOCK_SUCCESS;
Drv::SocketDescriptor client_fd;

this->setup_helper(recv_thread, recv_thread);

// Loop through a bunch of client disconnects
for (U32 i = 0; i < iterations && status1 == SOCK_SUCCESS; i++) {
Drv::TcpClientSocket client;
Expand Down Expand Up @@ -165,6 +173,46 @@ void TcpServerTester ::test_advanced_reconnect() {
test_with_loop(10, true); // Up to 10 * RECONNECT_MS
}

void TcpServerTester ::test_no_automatic_send_connection() {
Drv::TcpClientSocket client;
Drv::SocketDescriptor client_fd;

// Set up the server without automatic connection
this->setup_helper(false, true);
this->component.setAutoConnect(false);
Drv::Test::force_recv_timeout(client_fd.fd, client);

// Connect a client to the server so it is waiting in the "listen" queue
client.configure("127.0.0.1", this->component.getListenPort(), 0, 100);
ASSERT_EQ(client.open(client_fd), Drv::SOCK_SUCCESS);

// Send a message from the server and ensure that the server is not opened
ASSERT_EQ(this->component.send(reinterpret_cast<const U8*>("a"), 1), Drv::SOCK_AUTO_CONNECT_DISABLED);
ASSERT_FALSE(this->component.isOpened());

// Clean-up even if the send worked
client.close(client_fd);
this->component.terminate();
}

void TcpServerTester ::test_no_automatic_recv_connection() {
Drv::TcpClientSocket client;
Drv::SocketDescriptor client_fd;

// Set up the server without automatic connection
this->setup_helper(true, false);

// Connect a client to the server so it is waiting in the "listen" queue
// The read thread should not automatically connect and will thus exit with a failure
client.configure("127.0.0.1", this->component.getListenPort(), 0, 100);
ASSERT_EQ(client.open(client_fd), Drv::SOCK_FAILED_TO_CONNECT);
ASSERT_FALSE(this->component.isOpened());

// Clean-up even if the receive worked
client.close(client_fd);
this->component.terminate();
}

// ----------------------------------------------------------------------
// Handlers for typed from ports
// ----------------------------------------------------------------------
Expand Down
5 changes: 5 additions & 0 deletions Drv/TcpServer/test/ut/TcpServerTester.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,7 @@ namespace Drv {
// Tests
// ----------------------------------------------------------------------

void setup_helper(bool recv_thread, bool reconnect);

//! Test basic messaging
//!
Expand All @@ -70,6 +71,10 @@ namespace Drv {

// Helpers
void test_with_loop(U32 iterations, bool recv_thread=false);

void test_no_automatic_send_connection();

void test_no_automatic_recv_connection();

bool wait_on_change(bool open, U32 iterations);
bool wait_on_started(bool open, U32 iterations);
Expand Down

0 comments on commit dab2053

Please sign in to comment.