Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

IO Timeout? #99

Closed
nicktramp opened this issue Aug 14, 2023 · 1 comment
Closed

IO Timeout? #99

nicktramp opened this issue Aug 14, 2023 · 1 comment
Labels
bug Something isn't working

Comments

@nicktramp
Copy link

nicktramp commented Aug 14, 2023

When establishing implicit comms with a Brooks SLA5800-series MFC, IO packets are sent back and forth (per Wireshark), but the receiving data listener isn't called and the connection times out before a Forward_Close request is made. Examining the Wireshark trace, the O->T connection uses a randomly chosen source port and udp/2222 for destination port, but the device uses udp/2222 for both source and destination ports. Does this mean the library is listening for connections on the randomly chosen UDP port, rather than udp/2222? I realize there are 2 connections being made (O->T & T->O); how can I check which port the library is listening on?

Here's the code, only a slightly modified version of the implicit messaging example:

  /* Implicit Messaging Exmple */
#include <sstream>
#include <cip/connectionManager/NetworkConnectionParams.h>
#include "SessionInfo.h"
#include "ConnectionManager.h"
#include "utils/Logger.h"
#include "utils/Buffer.h"
#include "cip/Types.h"

using namespace eipScanner::cip;
using eipScanner::SessionInfo;
using eipScanner::MessageRouter;
using eipScanner::ConnectionManager;
using eipScanner::cip::connectionManager::ConnectionParameters;
using eipScanner::cip::connectionManager::NetworkConnectionParams;
using eipScanner::utils::Buffer;
using eipScanner::utils::Logger;
using eipScanner::utils::LogLevel;

int main() {
        Logger::setLogLevel(LogLevel::DEBUG);
        ConnectionManager connectionManager;
        auto si = std::make_shared<SessionInfo>("192.168.1.100", 0xAF12);

        ConnectionParameters parameters;
        parameters.connectionPath = {0x20, 0x04, 0x2C, 0x65, 0x2C, 0xC9}; // output Assm101, intput Assm201
        parameters.o2tRealTimeFormat = true;
        parameters.originatorVendorId = 342;
        parameters.originatorSerialNumber = 32423;
        parameters.t2oNetworkConnectionParams |= NetworkConnectionParams::P2P;
        parameters.t2oNetworkConnectionParams |= NetworkConnectionParams::SCHEDULED_PRIORITY;
        parameters.t2oNetworkConnectionParams |= 28; //size of Assm201
        parameters.o2tNetworkConnectionParams |= NetworkConnectionParams::P2P;
        parameters.o2tNetworkConnectionParams |= NetworkConnectionParams::SCHEDULED_PRIORITY;
        parameters.o2tNetworkConnectionParams |= 24; //size of Assm101
        parameters.originatorSerialNumber = 0x12345;
        parameters.o2tRPI = 1000000;
        parameters.t2oRPI = 1000000;
        parameters.transportTypeTrigger |= NetworkConnectionParams::CLASS1;

        auto io = connectionManager.forwardOpen(si, parameters);
        if (auto ptr = io.lock()) {
            Buffer assm101;
            CipReal setpoint = 10.0;
            CipDint valveOverrideMode = 0;
            CipDint controlMode = 0;        // auto
            CipReal controlVal = 0.0;      // not used for auto
            CipDint totalizerControl = 2;   // 1:run, 2:stop, reset:3
            CipDint calInstance = 1;        // calibration instance
            assm101 << setpoint << valveOverrideMode << controlMode << controlVal << totalizerControl << calInstance;
            ptr->setDataToSend(assm101.data());
            ptr->setReceiveDataListener([](auto realTimeHeader, auto sequence, auto data) {
                    std::ostringstream ss;
                    ss << "secNum=" << sequence << " data=";
                    for (auto &byte : data) {
                            ss << "[" << std::hex << (int) byte << "]";
                    }
                    Logger(LogLevel::INFO) << "Received: " << ss.str();
            });
            ptr->setCloseListener([]() {
                    Logger(LogLevel::INFO) << "Closed";
            });
        }
        int count = 200;
        while (connectionManager.hasOpenConnections() && count-- > 0) {
            connectionManager.handleConnections(std::chrono::milliseconds(100));
        }
        connectionManager.forwardClose(si, io);
        return 0;
}

I don't see any Socket Address Info Items being sent to the device, so I expected spec-defined defaults to be used and a Forward Close request after seeing the received data logged from the listener/callback.

Logs
[DEBUG] Opened TCP socket fd=3
[DEBUG] Connecting to 192.168.1.100:44818
[INFO] Registered session 1
[INFO] Send request: service=0x54 epath=[classId=6 objectId=1]
[INFO] Open IO connection O2T_ID=7798808 T2O_ID=3790471169 SerialNumber 1
[DEBUG] Opened UDP socket fd=4
[INFO] Open UDP socket to send data to 192.168.1.100:2222
[DEBUG] Opened UDP socket fd=5
[WARNING] Connection SeriaNumber=1 is closed by timeout
[INFO] Closed
[DEBUG] Close UDP socket fd=4
[WARNING] Attempt to close an already closed connection
[INFO] Unregistered session 1
[DEBUG] Close TCP socket fd=3
[DEBUG] Close UDP socket fd=5

Environment:

  • OS: Linux Mint 21.1
  • Compiler: g++ 11.4.0
  • Library Version 1.3.0

IO_notClosing.pcapng.txt

@nicktramp nicktramp added the bug Something isn't working label Aug 14, 2023
@nicktramp
Copy link
Author

Since I'm seeing a similar (maybe even the exact same) problem as in #64 (though the fix there did not work), I'll close this in favor of that one. If I can find a fix, I'll update that thread and submit a PR for it.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

1 participant