unittest_modbus_check_ip_connection.cpp
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2020 Pilz GmbH & Co. KG
3  *
4  * This program is free software: you can redistribute it and/or modify
5  * it under the terms of the GNU Lesser General Public License as published by
6  * the Free Software Foundation, either version 3 of the License, or
7  * (at your option) any later version.
8 
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  * GNU Lesser General Public License for more details.
13 
14  * You should have received a copy of the GNU Lesser General Public License
15  * along with this program. If not, see <http://www.gnu.org/licenses/>.
16  */
17 
18 #include <gtest/gtest.h>
19 
20 #include <numeric>
21 #include <modbus/modbus.h>
22 
28 
30 {
31 using namespace prbt_hardware_support;
32 
33 // Each testcase should have its own port in order to avoid conflicts between them
34 constexpr unsigned int START_PORT{ 20600 };
35 constexpr unsigned int END_PORT{ 20700 };
36 constexpr unsigned int DEFAULT_REGISTER_SIZE{ 514 };
37 constexpr unsigned int DEFAULT_WRITE_IDX{ 512 };
38 constexpr unsigned int WRONG_PORT = 4711;
39 
40 class ModbusConnectionCheckTestsuite : public testing::Test
41 {
42 public:
43  static void SetUpTestCase(); // NOLINT
44  void SetUp() override;
45  void TearDown() override;
46 
47 protected:
48  void shutdownModbusServer(PilzModbusServerMock* server, LibModbusClient& client);
49 
50 protected:
51  static unsigned int testPort();
52 
53 protected:
55  std::unique_ptr<PilzModbusServerMock> server_{ new PilzModbusServerMock(DEFAULT_REGISTER_SIZE) };
56 
57 protected:
58  static unsigned int ACTIVE_PORT_IDX_;
59  static std::vector<unsigned int> PORTS_FOR_TEST_;
60 };
61 
63 std::vector<unsigned int> ModbusConnectionCheckTestsuite::PORTS_FOR_TEST_ =
64  std::vector<unsigned int>(END_PORT - START_PORT);
65 
67 {
68  EXPECT_FALSE(checkIPConnection(LOCALHOST, testPort())) << "No Server";
69  server_->startAsync(LOCALHOST, testPort());
70 
71  // Needed to make sure server is actually present. (Not optimal,
72  // needs adaption inside the server mock)
73  EXPECT_TRUE(client_.init(LOCALHOST, testPort())) << "Server not present";
74 }
75 
77 {
78  // Use next port on next test
79  ACTIVE_PORT_IDX_++;
80  shutdownModbusServer(server_.get(), client_);
81  client_.close();
82 }
83 
85 {
86  return PORTS_FOR_TEST_.at(ACTIVE_PORT_IDX_ % PORTS_FOR_TEST_.size());
87 }
88 
90 {
91  std::iota(PORTS_FOR_TEST_.begin(), PORTS_FOR_TEST_.end(), START_PORT);
92 }
93 
95 {
96  server->setTerminateFlag();
97  RegCont reg_to_write_by_client{ 1 };
98  try
99  {
100  client.writeReadHoldingRegister(DEFAULT_REGISTER_SIZE, reg_to_write_by_client, DEFAULT_WRITE_IDX,
102  }
103  catch (const ModbusExceptionDisconnect& /* ex */)
104  {
105  // Tolerated exception
106  }
107 
108  server->terminate();
109 }
110 
111 TEST_F(ModbusConnectionCheckTestsuite, testReactionToCorrectConnection)
112 {
113  EXPECT_TRUE(checkIPConnection(LOCALHOST, testPort()))
114  << "Unexpected reaction to proper connection (ip address and port number correct).";
115 }
116 
117 TEST_F(ModbusConnectionCheckTestsuite, testReactionToIncorrectPort)
118 {
119  EXPECT_FALSE(checkIPConnection(LOCALHOST, WRONG_PORT)) << "Unexpected reaction to incorrect port number.";
120 }
121 
122 TEST_F(ModbusConnectionCheckTestsuite, testReactionToIncorrectIP)
123 {
124  EXPECT_FALSE(checkIPConnection("192.192.192.192", testPort())) << "Unexpected reaction to incorrect ip address.";
125 }
126 
127 TEST_F(ModbusConnectionCheckTestsuite, testReactionToIncorrectPortAndIncorrectIP)
128 {
129  ASSERT_NE(WRONG_PORT, testPort());
130  EXPECT_FALSE(checkIPConnection("192.192.192.192", WRONG_PORT))
131  << "Unexpected reaction to incorrect port number and ip address.";
132 }
133 
134 } // namespace modbus_socket_connection_check_test
135 
136 int main(int argc, char* argv[])
137 {
138  testing::InitGoogleTest(&argc, argv);
139  return RUN_ALL_TESTS();
140 }
Offers a modbus server and read/write functionality via subscription/publication. ...
void shutdownModbusServer(PilzModbusServerMock *server, LibModbusClient &client)
std::vector< uint16_t > RegCont
Convenience data type defining the data type for a collection of registers.
RegCont writeReadHoldingRegister(const int write_addr, const RegCont &write_reg, const int read_addr, const int read_nb) override
See base class.
TEST_F(ModbusConnectionCheckTestsuite, testReactionToCorrectConnection)
int main(int argc, char *argv[])
void terminate()
Terminate the Server. Reading or connecting to it will fail.
bool checkIPConnection(const char *ip, const unsigned int &port)
Test the ip connection by connecting to the modbus server.
constexpr const char *const LOCALHOST
Wrapper around libmodbus, see https://libmodbus.org/.
Expection thrown by prbt_hardware_support::LibModbusClient::readHoldingRegister if a disconnect from ...


prbt_hardware_support
Author(s):
autogenerated on Mon Feb 28 2022 23:14:34