00001 #include "artdaq/DAQdata/Globals.hh"
00002 #include "artdaq/ArtModules/NetMonTransportService.h"
00003 #include "artdaq/DAQrate/DataSenderManager.hh"
00004 #include "artdaq-core/Core/GlobalQueue.hh"
00005
00006 #include "artdaq-core/Data/Fragment.hh"
00007 #include "artdaq/DAQdata/NetMonHeader.hh"
00008 #include "artdaq-core/Data/RawEvent.hh"
00009
00010 #include "art/Framework/Services/Registry/ActivityRegistry.h"
00011 #include "canvas/Utilities/Exception.h"
00012 #include "cetlib/container_algorithms.h"
00013 #include "cetlib/exception.h"
00014 #include "fhiclcpp/ParameterSet.h"
00015 #include "fhiclcpp/ParameterSetRegistry.h"
00016
00017 #include "TClass.h"
00018 #include "TBufferFile.h"
00019
00020 #include <iomanip>
00021 #include <iostream>
00022 #include <string>
00023 #include <vector>
00024
00025 using namespace cet;
00026 using namespace fhicl;
00027 using namespace std;
00028
00029 static ParameterSet empty_pset;
00030
00031 NetMonTransportService::
00032 ~NetMonTransportService()
00033 {
00034 NetMonTransportService::disconnect();
00035 }
00036
00037 NetMonTransportService::
00038 NetMonTransportService(ParameterSet const& pset, art::ActivityRegistry&)
00039 : NetMonTransportServiceInterface()
00040 , data_pset_(pset)
00041 , sender_ptr_(nullptr)
00042 , incoming_events_(artdaq::getGlobalQueue())
00043 , recvd_fragments_(nullptr)
00044 {
00045 if(pset.has_key("rank")) my_rank = pset.get<int>("rank");
00046 incoming_events_.setReaderIsReady();
00047 }
00048
00049 void
00050 NetMonTransportService::
00051 connect()
00052 {
00053 sender_ptr_.reset(new artdaq::DataSenderManager(data_pset_));
00054 }
00055
00056 void
00057 NetMonTransportService::
00058 listen()
00059 {
00060 return;
00061 }
00062
00063 void
00064 NetMonTransportService::
00065 disconnect()
00066 {
00067 if (sender_ptr_) sender_ptr_.reset(nullptr);
00068 }
00069
00070 void
00071 NetMonTransportService::
00072 sendMessage(uint64_t sequenceId, uint8_t messageType, TBufferFile& msg)
00073 {
00074 if (sender_ptr_ == nullptr)
00075 {
00076 TLOG_DEBUG("NetMonTransportService") << "Reconnecting DataSenderManager" << TLOG_ENDL;
00077 connect();
00078 }
00079
00080 TLOG_DEBUG("NetMonTransportService") << "Sending message" << TLOG_ENDL;
00081 artdaq::NetMonHeader header;
00082 header.data_length = static_cast<uint64_t>(msg.Length());
00083 artdaq::Fragment
00084 fragment(std::ceil(msg.Length() /
00085 static_cast<double>(sizeof(artdaq::RawDataType))),
00086 sequenceId, 0, messageType, header);
00087
00088 memcpy(&*fragment.dataBegin(), msg.Buffer(), msg.Length());
00089 sender_ptr_->sendFragment(std::move(fragment));
00090 }
00091
00092 void
00093 NetMonTransportService::
00094 receiveMessage(TBufferFile*& msg)
00095 {
00096 if (recvd_fragments_ == nullptr)
00097 {
00098 std::shared_ptr<artdaq::RawEvent> popped_event;
00099 incoming_events_.deqWait(popped_event);
00100
00101 if (popped_event == nullptr)
00102 {
00103 msg = nullptr;
00104 return;
00105 }
00106
00107 recvd_fragments_ = popped_event->releaseProduct();
00108
00109
00110
00111 std::sort(recvd_fragments_->begin(), recvd_fragments_->end(),
00112 artdaq::fragmentSequenceIDCompare);
00113 }
00114
00115 artdaq::Fragment topFrag = std::move(recvd_fragments_->at(0));
00116 recvd_fragments_->erase(recvd_fragments_->begin());
00117 if (recvd_fragments_->size() == 0)
00118 {
00119 recvd_fragments_.reset(nullptr);
00120 }
00121
00122 auto header = topFrag.metadata<artdaq::NetMonHeader>();
00123 auto buffer = static_cast<char *>(malloc(header->data_length));
00124 memcpy(buffer, &*topFrag.dataBegin(), header->data_length);
00125 msg = new TBufferFile(TBuffer::kRead, header->data_length, buffer, kTRUE, 0);
00126 }
00127
00128 DEFINE_ART_SERVICE_INTERFACE_IMPL(NetMonTransportService, NetMonTransportServiceInterface)