artdaq  v3_00_03
TCPSocketTransfer.hh
1 #ifndef TCPSocketTransfer_hh
2 #define TCPSocketTransfer_hh
3 // This file (TCPSocketTransfer.hh) was created by Ron Rechenmacher <ron@fnal.gov> on
4 // Sep 14, 2016. "TERMS AND CONDITIONS" governing this file are in the README
5 // or COPYING file. If you do not have such a file, one can be obtained by
6 // contacting Ron or Fermi Lab in Batavia IL, 60510, phone: 630-840-3000.
7 // $RCSfile: .emacs.gnu,v $
8 // rev="$Revision: 1.30 $$Date: 2016/03/01 14:27:27 $";
9 
10 // C Includes
11 #include <stdint.h> // uint64_t
12 #include <sys/uio.h> // iovec
13 
14 // C++ Includes
15 #include <condition_variable>
16 
17 // Products includes
18 #include "fhiclcpp/fwd.h"
19 
20 // artdaq Includes
21 #include "artdaq/TransferPlugins/TransferInterface.hh"
22 #include "artdaq/TransferPlugins/detail/SRSockets.hh"
23 #include "artdaq/TransferPlugins/detail/Timeout.hh" // Timeout
24 #include "artdaq-core/Data/Fragment.hh"
25 
26 namespace artdaq
27 {
28  class TCPSocketTransfer;
29 }
30 
35 {
36 public:
54  TCPSocketTransfer(fhicl::ParameterSet const& ps, Role role);
55 
56  virtual ~TCPSocketTransfer();
57 
64  int receiveFragmentHeader(detail::RawFragmentHeader& header, size_t receiveTimeout) override;
65 
72  int receiveFragmentData(RawDataType* destination, size_t wordCount) override;
73 
80  CopyStatus copyFragment(Fragment& frag, size_t timeout_usec) override { return sendFragment_(std::move(frag), timeout_usec); }
81 
88  CopyStatus moveFragment(Fragment&& frag, size_t timeout_usec) override { return sendFragment_(std::move(frag), timeout_usec); }
89 
90 private:
91 
92  int fd_;
93  int listen_fd_;
94 
95  union
96  {
97  MessHead mh;
98  uint8_t mha[sizeof(MessHead)];
99  };
100 
101  enum class SocketState
102  {
103  Metadata,
104  Data
105  };
106 
107  SocketState state_;
108 
109  size_t offset;
110  int target_bytes;
111  size_t rcvbuf_;
112  size_t sndbuf_;
113 
114  struct DestinationInfo
115  {
116  std::string hostname;
117  int portOffset;
118  };
119 
120  std::unordered_map<size_t, DestinationInfo> hostMap_;
121 
122  volatile unsigned connect_state : 1; // 0=not "connected" (initial msg not sent)
123  unsigned blocking : 1; // compatible with bool (true/false)
124 
125 
126  Timeout tmo_;
127  bool stats_connect_stop_;
128  boost::thread stats_connect_thread_;
129  std::condition_variable stopstatscv_;
130  std::mutex stopstatscvm_; // protects 'stopcv'
131 
132  bool timeoutMessageArmed_; // don't repeatedly print about the send fd not being open...
133 
134 private: // methods
135  CopyStatus sendFragment_(Fragment&& frag, size_t timeout_usec);
136 
137  CopyStatus sendData_(const void* buf, size_t bytes, size_t tmo);
138 
139  CopyStatus sendData_(const struct iovec* iov, int iovcnt, size_t tmo);
140 
141  // Thread to drive reconnect_ requests
142  void stats_connect_();
143 
144  // Sender is responsible for connecting to receiver
145  void connect_();
146 
147  void reconnect_();
148 
149  // Receiver should listen for connections
150  void listen_();
151 
152  int calculate_port_() const { return (hostMap_.at(destination_rank())).portOffset + source_rank(); }
153 };
154 
155 #endif // TCPSocketTransfer_hh
virtual int source_rank() const
Get the source rank for this TransferInterface instance.
Role role() const
Get the TransferInterface::Role of this TransferInterface.
CopyStatus copyFragment(Fragment &frag, size_t timeout_usec) override
Copy a Fragment to the destination. Same implementation as moveFragment, as TCP is always reliable...
The Timeout class performs registered actions at specified intervals.
Definition: Timeout.hh:22
int receiveFragmentData(RawDataType *destination, size_t wordCount) override
Receive the body of a Fragment to the given destination pointer.
TCPSocketTransfer(fhicl::ParameterSet const &ps, Role role)
TCPSocketTransfer Constructor.
int receiveFragmentHeader(detail::RawFragmentHeader &header, size_t receiveTimeout) override
Receive a Fragment Header from the transport mechanism.
Role
Used to determine if a TransferInterface is a Sender or Receiver.
CopyStatus moveFragment(Fragment &&frag, size_t timeout_usec) override
Move a Fragment to the destination.
This interface defines the functions used to transfer data between artdaq applications.
virtual int destination_rank() const
Get the destination rank for this TransferInterface instance.
TransferInterface implementation plugin that sends data using TCP sockets.
This header is sent by the TCPSocket_transfer to allow for more efficient writev calls.
Definition: SRSockets.hh:15
CopyStatus
Returned from the send functions, this enumeration describes the possible return codes. If an exception occurs, it will be thrown and should be handled normally.