47 #include <sys/socket.h> 60 if(thread_.joinable())
70 localAddress_ = localAddress;
71 remoteAddress_ = remoteAddress;
78 udp_.
open(localAddress_,
true);
84 std::stringstream sstream;
90 <<
": Unable to open receive socket to transport: '" 95 <<
"Possible reason(s):" 99 <<
" is not this host." 108 thread_ = std::thread{&BoundaryMessageManager::processNetworkMessageUDP,
this};
112 thread_ = std::thread{&BoundaryMessageManager::processNetworkMessageTCP,
this};
122 if(thread_.joinable())
149 const void * pPacketData,
150 size_t packetDataLength,
162 size_t packetDataLength,
170 memset(&dataMessage,0,
sizeof(dataMessage));
181 memset(&header,0,
sizeof(header));
185 sizeof(dataMessage) +
195 vectorIO.push_back({&header,
sizeof(header)});
196 vectorIO.push_back({&dataMessage,
sizeof(dataMessage)});
198 vectorIO.insert(vectorIO.end(),
202 vectorIO.insert(vectorIO.end(),
203 controlVectorIO.begin(),
204 controlVectorIO.end());
208 if((len = udp_.
send(&vectorIO[0],
209 static_cast<int>(vectorIO.size()),
210 remoteAddress_)) == -1)
213 ERROR_LEVEL,
"NEM %03d BoundaryMessageManager error " 214 "on message send (expected:%zu actual:%zd)",
223 memset(&msg,0,
sizeof(msg));
224 msg.msg_iov =
const_cast<iovec *
>(&vectorIO[0]);
225 msg.msg_iovlen = vectorIO.size();
227 std::lock_guard<std::mutex> m(mutex_);
231 if((len = sendmsg(iSessionSockFd_,&msg,0)) == -1)
234 ERROR_LEVEL,
"NEM %03d BoundaryMessageManager error " 235 "on message send (expected:%zu actual:%zd)",
250 std::for_each(msgs.begin(),msgs.end(),[](
const ControlMessage * p){
delete p;});
260 memset(&header,0,
sizeof(header));
275 vectorIO.push_back({&header,
sizeof(header)});
276 vectorIO.push_back({&controlMessage,
sizeof(controlMessage)});
281 vectorIO.insert(vectorIO.end(),
282 controlMessageVectorIO.begin(),
283 controlMessageVectorIO.end());
287 if((len = udp_.
send(&vectorIO[0],
288 static_cast<int>(vectorIO.size()),
289 remoteAddress_)) == -1)
293 "error on control message send (expected:%u actual:%zu)",
302 memset(&msg,0,
sizeof(msg));
304 msg.msg_iov =
const_cast<iovec *
>(&vectorIO[0]);
305 msg.msg_iovlen = vectorIO.size();
307 std::lock_guard<std::mutex> m(mutex_);
311 if((len = sendmsg(iSessionSockFd_,&msg,0)) == -1)
315 "error on control message send (expected:%u actual:%zu)",
330 std::for_each(msgs.begin(),msgs.end(),[](
const ControlMessage * p){
delete p;});
334 void EMANE::BoundaryMessageManager::handleNetworkMessage(
void * buf,
size_t len)
344 if(static_cast<size_t>(len) == pHeader->
u32Length_)
401 "NEM %03d BoundaryMessageManager::processNetworkMessage " 402 "processUpstreamPacket exception caught",
410 "NEM %03d BoundaryMessageManager::processNetworkMessage " 411 "processUpstreamPacket size too small for control message data",
422 "NEM %03d BoundaryMessageManager::processNetworkMessage " 423 "processUpstreamPacket size too small for data message",
431 "NEM %03d BoundaryMessageManager::processNetworkMessage " 432 "processUpstreamPacket size too small for packet data message",
467 "NEM %03d BoundaryMessageManager::processNetworkMessage " 468 "processDownstreamControl exception caught",
476 "NEM %03d BoundaryMessageManager control message size mismatch",
486 "NEM %03d BoundaryMessageManager Received unknown message type: %d",
496 "NEM %03d BoundaryMessageManager Message mismatch expected %hd got %zd",
506 "NEM %03d BoundaryMessageManager Message Header mismatch expected %zu got %zd",
513 void EMANE::BoundaryMessageManager::processNetworkMessageUDP()
515 unsigned char buf[65536];
520 "NEM %03d BoundaryMessageManager::processNetworkMessage",
525 if((len = udp_.
recv(buf,
sizeof(buf),0)) > 0)
529 "NEM %03d BoundaryMessageManager Pkt Rcvd len: %zd",
532 handleNetworkMessage(buf,len);
539 "NEM %03d BoundaryMessageManager Message Header read error",
547 void EMANE::BoundaryMessageManager::processNetworkMessageTCP()
549 unsigned char buf[1024];
550 std::uint32_t u32MessageSizeBytes{};
551 std::vector<uint8_t> message{};
552 bool bLocalConnected{};
558 "NEM %03d BoundaryMessageManager::processNetworkMessageTCP",
564 if((iSockFd = socket(localAddress_.
getFamily(),
570 "NEM %03d BoundaryMessageManager socket open error: %s",
579 if(setsockopt(iSockFd,
582 reinterpret_cast<void*>(&iOption),
583 sizeof(iOption)) < 0)
587 "NEM %03d BoundaryMessageManager socket SO_REUSEADDR error: %s",
600 "NEM %03d BoundaryMessageManager socket bind error: %s",
608 if(listen(iSockFd,1) < 0)
612 "NEM %03d BoundaryMessageManager socket listen error: %s",
622 std::lock_guard<std::mutex> m(mutex_);
626 int iConnectionSockFd{};
628 while(!bLocalConnected)
632 if((iConnectionSockFd = accept(iSockFd_,
nullptr,
nullptr)) > 0)
634 bLocalConnected =
true;
659 bLocalConnected =
true;
667 bConnected_ = bLocalConnected;
671 iSessionSockFd_ = iConnectionSockFd;
675 iSessionSockFd_ = iSockFd_;
676 iConnectionSockFd = iSockFd_;
683 "NEM %03d BoundaryMessageManager connected",
685 while(bLocalConnected)
687 bool bDoDisconnect{};
690 if(u32MessageSizeBytes == 0)
695 length = recv(iConnectionSockFd,buf,6 - message.size(),0);
700 message.insert(message.end(),&buf[0],&buf[length]);
703 if(message.size() == 6)
705 u32MessageSizeBytes = ntohl(*reinterpret_cast<std::uint32_t *>(&message[2]));
708 if(!u32MessageSizeBytes)
712 "NEM %03d BoundaryMessageManager Message Header read error",
714 bDoDisconnect =
true;
722 "NEM %03d BoundaryMessageManager Message Header read error",
724 bDoDisconnect =
true;
732 length = recv(iConnectionSockFd,
734 u32MessageSizeBytes - message.size() >
sizeof(buf) ?
735 sizeof(buf) : u32MessageSizeBytes - message.size(),
740 message.insert(message.end(),&buf[0],&buf[length]);
743 if(message.size() == u32MessageSizeBytes)
747 "NEM %03d BoundaryMessageManager Pkt Rcvd len: %zd",
751 handleNetworkMessage(&message[0],message.size());
754 u32MessageSizeBytes = 0;
761 "NEM %03d BoundaryMessageManager Message Header read error",
764 bDoDisconnect =
true;
771 u32MessageSizeBytes = 0;
772 bLocalConnected =
false;
776 std::lock_guard<std::mutex> m(mutex_);
789 "NEM %03d BoundaryMessageManager disconnected",
NetAdapterHeader * NetAdapterHeaderToHost(NetAdapterHeader *pMsg)
A Packet class that allows upstream processing to strip layer headers as the packet travels up the st...
data shared between network adapter and nem.
socklen_t getAddrLength() const
virtual void doProcessControlMessage(const ControlMessages &msgs)=0
void open(const INETAddr &address, bool bReuseAddress=false)
#define LOGGER_VERBOSE_LOGGING(logger, level, fmt, args...)
NetAdapterControlMessage * NetAdapterControlMessageToHost(NetAdapterControlMessage *ctrl)
std::list< const ControlMessage * > ControlMessages
void sendPacketMessage(const PacketInfo &packetInfo, const void *pPacketData, size_t packetLength, const ControlMessages &msgs)
information shared between network adapter and nem.
virtual void doProcessPacketMessage(const PacketInfo &, const void *pPacketData, size_t packetLength, const ControlMessages &msgs)=0
void open(const INETAddr &localAddress, const INETAddr &remoteAddress, Protocol protocol)
NEMId getDestination() const
sockaddr * getSockAddr() const
constexpr NEMId NEM_BROADCAST_MAC_ADDRESS
ssize_t send(const iovec *iov, int iovcnt, const INETAddr &remoteAddress, int flags=0) const
std::vector< iovec > VectorIO
NetAdapterDataMessage * NetAdapterDataMessageToNet(NetAdapterDataMessage *pkt)
converts netadapter data message from host to network byte order.
BoundaryMessageManager(NEMId id)
void sendControlMessage(const ControlMessages &msgs)
Store source, destination, creation time and priority information for a packet.
static ControlMessages create(const void *pData, size_t length)
std::string str(bool bWithPort=true) const
int cancel(std::thread &thread)
std::uint32_t u32CtrlLen_
ControlMessage interface is the base for all control messages.
Priority getPriority() const
Exception thrown by the during BoundaryMessageManagerException to indicate connection failure...
ssize_t recv(void *buf, size_t len, int flags=0)
NetAdapterControlMessage * NetAdapterControlMessageToNet(NetAdapterControlMessage *ctrl)
const std::uint16_t NETADAPTER_DATA_MSG
virtual ~BoundaryMessageManager()
std::uint32_t u32CtrlLen_
#define LOGGER_STANDARD_LOGGING(logger, level, fmt, args...)
const std::uint16_t NETADAPTER_CTRL_MSG
NetAdapterHeader * NetAdapterHeaderToNet(NetAdapterHeader *pMsg)
static LogService * instance()
NetAdapterDataMessage * NetAdapterDataMessageToHost(NetAdapterDataMessage *pkt)
converts netadapter data message from network to host byte order.
const std::uint16_t NETADAPTER_BROADCAST_ADDRESS
definition of the broadcast address used between network adapter and nem.
const Utils::VectorIO & getVectorIO() const
std::uint32_t u32DataLen_