void CSumiNodeTesterApp::Run() { //init if(!g_oUtils.APISendCreateSocket(m_stCfg.GetUdpLocalPort(), g_u8SerialMsgId, m_poBufferedSerialLink)) return; g_u8SerialMsgId++; //receive ACK or NACK CSimpleTimer oTimer(m_stCfg.GetUDPCreateSockTimedoutSec()*1000); int nRecvLen = 0; bool bNoReply = true; while(!oTimer.IsSignaling() && bNoReply) { if( !m_poBufferedSerialLink->IsLinkOpen() || !m_poBufferedSerialLink->HaveData( WAITUS ) ) { continue; } nRecvLen = m_poBufferedSerialLink->Read( g_pucRcvBuf, BUFSIZE ); //check if (nRecvLen <= 0) continue; if (nRecvLen < (int)sizeof(API_MSG_HDR)) { NLOG_ERR("FAILED TO READ MSG HEADER ON SERIAL LINK!"); break; } //process rsp for APISendCreateSocket API_MSG_HDR *pHdr = (API_MSG_HDR*)g_pucRcvBuf; if (!API_GET_IS_RSP_FLAG(pHdr)) { NLOG_WARN("Expected a response for APISendCreateSocket but received a request!"); continue; } switch(API_GET_MSG_CLASS(pHdr)) { case API_ACK: if(API_GET_MESSAGE_ID(pHdr) == (g_u8SerialMsgId - 1)) { NLOG_INFO("UDP PORT %d SUCCESSFULLY OPENED!", m_stCfg.GetUdpLocalPort()); bNoReply = false; } break; case API_NACK: if(API_GET_MESSAGE_ID(pHdr) != (g_u8SerialMsgId - 1)) { continue; } switch(API_GET_TYPE(pHdr)) { case API_UDP_PORT_ALREADY_IN_USE: NLOG_INFO("API_UDP_PORT_ALREADY_IN_USE, UDP port=%d!", m_stCfg.GetUdpLocalPort()); bNoReply = false; break; case API_MAX_SOCKETS_NO_REACHED: NLOG_ERR("API_MAX_SOCKETS_NO_REACHED!"); return; case API_COULD_NOT_CREATE_SOCKET: NLOG_ERR("API_COULD_NOT_CREATE_SOCKET UDP port=%d!", m_stCfg.GetUdpLocalPort()); return; default: NLOG_ERR("UNKNOWN NACK MSG TYPE: %d!", API_GET_TYPE(pHdr)); return; } break; default: NLOG_ERR("UNKNOWN MSG CLASS: %d!", API_GET_MSG_CLASS(pHdr)); return; } } if( bNoReply ) { NLOG_ERR("NO REPLY TO UDP_CREATE_SOCKET!"); return; } //process every received msg CSimpleTimer oUdpSendTimer(m_stCfg.GetUdpSendIntervalSec()* 1000); CSimpleTimer oUdpSentPollTimer(m_stCfg.GetUdpSentPollIntervalSec()*1000); CSimpleTimer oStatisticsTimer(300000); CSimpleTimer oSigFileCheckTimer(m_stCfg.GetSigFileCheckIntervalSec()*1000); while (!CApp::IsStop()) { TouchPidFile(g_pApp->m_szAppPidFile); //On Send UDP EVENT if( oUdpSendTimer.IsSignaling() ) { SendUdpData(); oUdpSendTimer.SetTimer(m_stCfg.GetUdpSendIntervalSec()* 1000); } //On Receive Data EVENT ProcessRcv(); //On Poll Sent UDP Msg EVENT if( oUdpSentPollTimer.IsSignaling()) { g_oSumiStats.PollSentUdpMsg(); oUdpSentPollTimer.SetTimer(m_stCfg.GetUdpSentPollIntervalSec()*1000); } //On Log Statistics EVENT if( oStatisticsTimer.IsSignaling() ) { g_oSumiStats.LogStatistics(); oStatisticsTimer.SetTimer(300000); } //On Check SIG File EVENT if( oSigFileCheckTimer.IsSignaling() ) { CSignalsMgr::Raise( SIGHUP ); oSigFileCheckTimer.SetTimer(m_stCfg.GetSigFileCheckIntervalSec()* 1000); } //On Signals Check EVENT CheckSignals(); } NLOG_INFO("Closing the socket..."); if( !g_oUtils.APISendDeleteSocket(m_stCfg.GetUdpLocalPort(), g_u8SerialMsgId, m_poBufferedSerialLink) ) return; g_u8SerialMsgId++; //receive ACK oTimer.SetTimer(UDP_DELETE_SOCK_TIMEDOUT_MS); nRecvLen = 0; bNoReply = true; while(!oTimer.IsSignaling() && bNoReply) { if( !m_poBufferedSerialLink->IsLinkOpen() || !m_poBufferedSerialLink->HaveData( WAITUS ) ) { continue; } nRecvLen = m_poBufferedSerialLink->Read( g_pucRcvBuf, BUFSIZE ); //check if (nRecvLen <= 0) continue; if (nRecvLen < (int)sizeof(API_MSG_HDR)) { NLOG_ERR("FAILED TO READ MSG HEADER ON SERIAL LINK!"); break; } //process rsp API_MSG_HDR *pHdr = (API_MSG_HDR*)g_pucRcvBuf; if (!API_GET_IS_RSP_FLAG(pHdr)) { NLOG_WARN("Expected a response for APISendDeleteSocket but received a request!"); continue; } switch(API_GET_MSG_CLASS(pHdr)) { case API_ACK: if(API_GET_MESSAGE_ID(pHdr) == (g_u8SerialMsgId - 1)) { NLOG_INFO("UDP PORT %d SUCCESSFULLY CLOSED!", m_stCfg.GetUdpLocalPort()); bNoReply = false; } break; case API_NACK: if(API_GET_MESSAGE_ID(pHdr) != (g_u8SerialMsgId - 1)) { continue; } switch(API_GET_TYPE(pHdr)) { case API_IVALID_DELETE_SOCKET: NLOG_WARN("API_INVALID_DELETE_SOCKET UDP port=%d!", m_stCfg.GetUdpLocalPort()); bNoReply = false; break; default: NLOG_ERR("UNKNOWN NACK MSG TYPE: %d!", API_GET_TYPE(pHdr)); return; } break; default: NLOG_ERR("UNKNOWN MSG CLASS: %d!", API_GET_MSG_CLASS(pHdr)); return; } } if( bNoReply ) { NLOG_ERR("NO REPLY TO UDP_CLOSE_SOCKET!"); return; } }
EipStatus SendConnectedData(ConnectionObject *connection_object) { CipCommonPacketFormatData *common_packet_format_data; EipUint16 reply_length; EipUint8 *message_data_reply_buffer; /* TODO think of adding an own send buffer to each connection object in order to preset up the whole message on connection opening and just change the variable data items e.g., sequence number */ common_packet_format_data = &g_common_packet_format_data_item; /* TODO think on adding a CPF data item to the S_CIP_ConnectionObject in order to remove the code here or even better allocate memory in the connection object for storing the message to send and just change the application data*/ connection_object->eip_level_sequence_count_producing++; /* assembleCPFData */ common_packet_format_data->item_count = 2; if ((connection_object->transport_type_class_trigger & 0x0F) != 0) { /* use Sequenced Address Items if not Connection Class 0 */ common_packet_format_data->address_item.type_id = kCipItemIdSequencedAddressItem; common_packet_format_data->address_item.length = 8; common_packet_format_data->address_item.data.sequence_number = connection_object->eip_level_sequence_count_producing; } else { common_packet_format_data->address_item.type_id = kCipItemIdConnectionBased; common_packet_format_data->address_item.length = 4; } common_packet_format_data->address_item.data.connection_identifier = connection_object->produced_connection_id; common_packet_format_data->data_item.type_id = kCipItemIdConnectedTransportPacket; CipByteArray *producing_instance_attributes = (CipByteArray *) connection_object->producing_instance->attributes->data; common_packet_format_data->data_item.length = 0; /* notify the application that data will be sent immediately after the call */ if (BeforeAssemblyDataSend(connection_object->producing_instance)) { /* the data has changed increase sequence counter */ connection_object->sequence_count_producing++; } /* set AddressInfo Items to invalid Type */ common_packet_format_data->address_info_item[0].type_id = 0; common_packet_format_data->address_info_item[1].type_id = 0; reply_length = AssembleLinearMessage(0, common_packet_format_data, &g_message_data_reply_buffer[0]); message_data_reply_buffer = &g_message_data_reply_buffer[reply_length - 2]; common_packet_format_data->data_item.length = producing_instance_attributes ->length; if (kOpenerProducedDataHasRunIdleHeader) { common_packet_format_data->data_item.length += 4; } if ((connection_object->transport_type_class_trigger & 0x0F) == 1) { common_packet_format_data->data_item.length += 2; AddIntToMessage(common_packet_format_data->data_item.length, &message_data_reply_buffer); AddIntToMessage(connection_object->sequence_count_producing, &message_data_reply_buffer); } else { AddIntToMessage(common_packet_format_data->data_item.length, &message_data_reply_buffer); } if (kOpenerProducedDataHasRunIdleHeader) { AddDintToMessage(g_run_idle_state, &(message_data_reply_buffer)); } memcpy(message_data_reply_buffer, producing_instance_attributes->data, producing_instance_attributes->length); reply_length += common_packet_format_data->data_item.length; return SendUdpData( &connection_object->remote_address, connection_object->socket[kUdpCommuncationDirectionProducing], &g_message_data_reply_buffer[0], reply_length); }
int NetClient::WakeUpEvent() { char d = '1'; return SendUdpData(notify_socket_fd_, &d, sizeof (char), ntohl(inet_addr("127.0.0.1")), notify_socket_port_); }