2012-10-30 03:52:39 +00:00
# include "cmPrefix.h"
# include "cmGlobal.h"
# include "cmRpt.h"
# include "cmErr.h"
# include "cmCtx.h"
# include "cmMem.h"
# include "cmMallocDebug.h"
# include "cmUdpPort.h"
# include "cmJson.h"
# include "cmUdpNet.h"
# include "cmTime.h"
typedef struct cmUdpNode_str
{
cmChar_t * label ;
unsigned id ;
struct sockaddr_in addr ;
cmUdpPort_t port ;
struct cmUdpNode_str * link ;
} cmUdpNode_t ;
typedef struct
{
cmErr_t err ;
cmUdpNetCallback_t cbFunc ;
void * cbArg ;
unsigned timeOutMs ;
unsigned nodeId ;
cmChar_t * nodeLabel ;
cmUdpNode_t * list ;
cmUdpH_t udpH ;
} cmUdpNet_t ;
cmUdpNetH_t cmUdpNetNullHandle = cmSTATIC_NULL_HANDLE ;
cmUdpNet_t * _cmUnHandleToPtr ( cmUdpNetH_t h )
{
cmUdpNet_t * p = ( cmUdpNet_t * ) h . h ;
assert ( p ! = NULL ) ;
return p ;
}
cmUnRC_t _cmUdpNetFinal ( cmUdpNet_t * p )
{
// release the node list
while ( p - > list ! = NULL )
{
cmUdpNode_t * np = p - > list - > link ;
cmMemFree ( p - > list - > label ) ;
cmMemFree ( p - > list ) ;
p - > list = np ;
}
cmMemFree ( p - > nodeLabel ) ;
p - > nodeLabel = NULL ;
p - > cbFunc = NULL ;
p - > cbArg = NULL ;
p - > nodeId = cmInvalidId ;
return kOkUnRC ;
}
cmUnRC_t _cmUdpNetFree ( cmUdpNet_t * p )
{
cmUnRC_t rc ;
if ( ( rc = _cmUdpNetFinal ( p ) ) ! = kOkUnRC )
return rc ;
// release the UDP port
if ( cmUdpFree ( & p - > udpH ) ! = kOkUdpRC )
return cmErrMsg ( & p - > err , kUdpPortFailUnRC , " The UDP port release failed. " ) ;
cmMemFree ( p ) ;
return kOkUnRC ;
}
cmUdpNode_t * _cmUnFindLabel ( cmUdpNet_t * p , const cmChar_t * label )
{
cmUdpNode_t * np = p - > list ;
for ( ; np ! = NULL ; np = np - > link )
if ( strcmp ( np - > label , label ) = = 0 )
return np ;
return NULL ;
}
cmUdpNode_t * _cmUnFindId ( cmUdpNet_t * p , unsigned id )
{
cmUdpNode_t * np = p - > list ;
for ( ; np ! = NULL ; np = np - > link )
if ( np - > id = = id )
return np ;
return NULL ;
}
void _cmUdpNetCallback ( void * cbArg , const char * data , unsigned dataByteCnt , const struct sockaddr_in * fromAddr )
{
cmUdpNet_t * p = ( cmUdpNet_t * ) cbArg ;
if ( p - > cbFunc ! = NULL )
{
cmUdpNetH_t h ;
cmUdpNode_t * np = p - > list ;
h . h = p ;
// locate the source node in the node list to get the source node id
for ( ; np ! = NULL ; np = np - > link )
if ( np - > addr . sin_addr . s_addr = = fromAddr - > sin_addr . s_addr )
{
// forward the call to the networks callback function
p - > cbFunc ( p - > cbArg , h , data , dataByteCnt , np - > id ) ;
break ;
}
if ( np = = NULL )
cmErrMsg ( & p - > err , kNodeNotFoundUnRC , " A callback source node could not be identified. " ) ;
}
}
cmUnRC_t cmUdpNetAlloc ( cmCtx_t * ctx , cmUdpNetH_t * hp )
{
cmUnRC_t rc ;
if ( ( rc = cmUdpNetFree ( hp ) ) ! = kOkUnRC )
return rc ;
cmUdpNet_t * p = cmMemAllocZ ( cmUdpNet_t , 1 ) ;
cmErrSetup ( & p - > err , & ctx - > rpt , " UDP Network " ) ;
if ( cmUdpAlloc ( ctx , & p - > udpH ) ! = kOkUdpRC )
return cmErrMsg ( & p - > err , kUdpPortFailUnRC , " UDP port allocation failed. " ) ;
p - > nodeId = cmInvalidId ;
hp - > h = p ;
return kOkUnRC ;
}
cmUnRC_t cmUdpNetAllocJson (
cmCtx_t * ctx ,
cmUdpNetH_t * hp ,
cmJsonH_t jsH ,
cmUdpNetCallback_t cbFunc ,
void * cbArg ,
unsigned flags )
{
cmUnRC_t rc ;
if ( ( rc = cmUdpNetAlloc ( ctx , hp ) ) ! = kOkUnRC )
return rc ;
if ( ( rc = cmUdpNetInitJson ( * hp , jsH , cbFunc , cbArg ) ) ! = kOkUnRC )
{
if ( cmIsFlag ( flags , kNetOptionalUnFl ) )
rc = kOkUnRC ;
goto errLabel ;
}
if ( ( rc = cmUdpNetEnableListen ( * hp , cmIsFlag ( flags , kListenUnFl ) ) ) ! = kOkUnRC )
goto errLabel ;
errLabel :
if ( rc ! = kOkUnRC )
cmUdpNetFree ( hp ) ;
return rc ;
}
cmUnRC_t cmUdpNetFree ( cmUdpNetH_t * hp )
{
cmUnRC_t rc = kOkUnRC ;
if ( hp = = NULL | | cmUdpNetIsValid ( * hp ) = = false )
return kOkUnRC ;
cmUdpNet_t * p = _cmUnHandleToPtr ( * hp ) ;
if ( ( rc = _cmUdpNetFree ( p ) ) ! = kOkUnRC )
return rc ;
hp - > h = NULL ;
return rc ;
}
cmUnRC_t cmUdpNetInit (
cmUdpNetH_t h ,
const cmChar_t * nodeLabel ,
unsigned nodeId ,
cmUdpPort_t nodeSocketPort ,
cmUdpNetCallback_t cbFunc ,
void * cbArg ,
unsigned recvBufByteCnt ,
unsigned socketRecvTimeOutMs )
{
cmUnRC_t rc ;
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
if ( ( rc = _cmUdpNetFinal ( p ) ) ! = kOkUnRC )
return rc ;
// create the UDP port
if ( cmUdpInit ( p - > udpH , nodeSocketPort , kBlockingUdpFl , _cmUdpNetCallback , p , NULL , 0 , recvBufByteCnt , socketRecvTimeOutMs ) ! = kOkUdpRC )
{
rc = cmErrMsg ( & p - > err , kUdpPortFailUnRC , " The UDP port create failed. " ) ;
goto errLabel ;
}
p - > cbFunc = cbFunc ;
p - > cbArg = cbArg ;
p - > timeOutMs = socketRecvTimeOutMs ;
p - > nodeId = nodeId ;
p - > nodeLabel = cmMemAllocStr ( nodeLabel ) ;
p - > list = NULL ;
errLabel :
if ( rc ! = kOkUnRC )
_cmUdpNetFinal ( p ) ;
return rc ;
}
cmUnRC_t _cmUnParseMemberErr ( cmUdpNet_t * p , cmJsRC_t jsRC , const cmChar_t * errLabel , const cmChar_t * objectLabel )
{
if ( jsRC = = kNodeNotFoundJsRC & & errLabel ! = NULL )
return cmErrMsg ( & p - > err , kJsonFailUnRC , " The required field '%s'was not found in the UDP network resource tree in the object '%s'. " , errLabel , cmStringNullGuard ( objectLabel ) ) ;
return cmErrMsg ( & p - > err , kJsonFailUnRC , " JSON parsing failed on the UDP network resource object '%s'. " , cmStringNullGuard ( objectLabel ) ) ;
}
cmUnRC_t cmUdpNetInitJson (
cmUdpNetH_t h ,
cmJsonH_t jsH ,
cmUdpNetCallback_t cbFunc ,
void * cbArg )
{
cmUnRC_t rc ;
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
cmJsonNode_t * unp ;
cmJsonNode_t * nap ;
const cmChar_t * errLabelPtr = NULL ;
cmJsRC_t jsRC ;
unsigned port , recvBufByteCnt , timeOutMs ;
const cmChar_t * localLabel ;
const cmChar_t * topLabel = " udpnet " ;
unsigned nodeCnt = 0 ;
unsigned i ;
typedef struct
{
const cmChar_t * label ;
const cmChar_t * addr ;
unsigned id ;
} unNode_t ;
unNode_t * a = NULL ;
unNode_t * localPtr = NULL ;
if ( ( rc = _cmUdpNetFinal ( p ) ) ! = kOkUnRC )
return rc ;
if ( ( unp = cmJsonFindValue ( jsH , topLabel , NULL , kObjectTId ) ) = = NULL )
{
return cmErrMsg ( & p - > err , kJsonFailUnRC , " The JSON 'udpnet' element was not found. " ) ;
}
if ( ( jsRC = cmJsonMemberValues ( unp , & errLabelPtr ,
" port " , kIntTId , & port ,
" recvBufByteCnt " , kIntTId , & recvBufByteCnt ,
" timeOutMs " , kIntTId , & timeOutMs ,
" local " , kStringTId , & localLabel ,
" nodeArray " , kArrayTId , & nap ,
NULL ) ) ! = kOkJsRC )
{
rc = _cmUnParseMemberErr ( p , jsRC , errLabelPtr , topLabel ) ;
goto errLabel ;
}
// get a count of the number of nodes
if ( ( nodeCnt = cmJsonChildCount ( nap ) ) = = 0 )
{
rc = cmErrMsg ( & p - > err , kJsonFailUnRC , " The JSON 'udpnet' node array appears to be empty. " ) ;
goto errLabel ;
}
// allocate a temporary array to hold the node list
a = cmMemAllocZ ( unNode_t , nodeCnt ) ;
// for each remote node
for ( i = 0 ; i < nodeCnt ; + + i )
{
const cmJsonNode_t * naep = cmJsonArrayElementC ( nap , i ) ;
// read the JSON recd
if ( ( jsRC = cmJsonMemberValues ( naep , & errLabelPtr ,
" label " , kStringTId , & a [ i ] . label ,
" id " , kIntTId , & a [ i ] . id ,
" addr " , kStringTId , & a [ i ] . addr ,
NULL ) ) ! = kOkJsRC )
{
rc = _cmUnParseMemberErr ( p , jsRC , errLabelPtr , " nodeArray " ) ;
goto errLabel ;
}
// track which node is the local node
if ( strcmp ( localLabel , a [ i ] . label ) = = 0 )
localPtr = a + i ;
}
// if no local node was located
if ( localPtr = = NULL )
{
rc = cmErrMsg ( & p - > err , kJsonFailUnRC , " The local node label '%s' was not found. " , cmStringNullGuard ( localLabel ) ) ;
goto errLabel ;
}
// initialize the network object
if ( ( rc = cmUdpNetInit ( h , localPtr - > label , localPtr - > id , port , cbFunc , cbArg , recvBufByteCnt , timeOutMs ) ) ! = kOkUnRC )
goto errLabel ;
// register each remote node
for ( i = 0 ; i < nodeCnt ; + + i )
if ( a + i ! = localPtr )
if ( ( rc = cmUdpNetRegisterRemote ( h , a [ i ] . label , a [ i ] . id , a [ i ] . addr , port ) ) ! = kOkUnRC )
goto errLabel ;
errLabel :
cmMemFree ( a ) ;
if ( rc ! = kOkUnRC )
_cmUdpNetFinal ( p ) ;
return rc ;
}
bool cmUdpNetIsInitialized ( cmUdpNetH_t h )
{
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
return p - > nodeId ! = cmInvalidId ;
}
cmUnRC_t cmUdpNetFinal ( cmUdpNetH_t h )
{
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
return _cmUdpNetFinal ( p ) ;
}
cmUnRC_t cmUdpNetEnableListen ( cmUdpNetH_t h , bool enableFl )
{
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
if ( cmUdpEnableListen ( p - > udpH , enableFl ) ! = kOkUdpRC )
return cmErrMsg ( & p - > err , kUdpPortFailUnRC , " UDP port listen %s failed. " , enableFl ? " enable " : " disable " ) ;
return kOkUnRC ;
}
bool cmUdpNetIsValid ( cmUdpNetH_t h )
{ return h . h ! = NULL ; }
unsigned cmUdpNetLocalNodeId ( cmUdpNetH_t h )
{
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
return p - > nodeId ;
}
const cmChar_t * cmUdpNetLocalNodeLabel ( cmUdpNetH_t h )
{
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
return p - > nodeLabel ;
}
unsigned cmUdpNetNodeLabelToId ( cmUdpNetH_t h , const cmChar_t * label )
{
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
// if the network was not initialized then nodeLabel == NULL
if ( p - > nodeLabel = = NULL )
return cmInvalidId ;
// if 'label' refers to the local node
if ( strcmp ( label , p - > nodeLabel ) = = 0 )
return p - > nodeId ;
// otherwise search the remote node list
cmUdpNode_t * np = p - > list ;
for ( ; np ! = NULL ; np = np - > link )
if ( strcmp ( np - > label , label ) = = 0 )
return np - > id ;
return cmInvalidId ;
}
const cmChar_t * cmUdpNetNodeIdToLabel ( cmUdpNetH_t h , unsigned id )
{
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
// if 'id' refers to the local node
if ( id = = p - > nodeId )
return p - > nodeLabel ;
// otherwise search the remote node list
cmUdpNode_t * np = p - > list ;
for ( ; np ! = NULL ; np = np - > link )
if ( np - > id = = id )
return np - > label ;
return NULL ;
}
unsigned cmUdpNetNodeCount ( cmUdpNetH_t h )
{
unsigned cnt = 0 ;
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
cmUdpNode_t * np = p - > list ;
for ( ; np ! = NULL ; np = np - > link )
+ + cnt ;
return cnt ;
}
unsigned cmUdpNetNodeId ( cmUdpNetH_t h , unsigned nodeIdx )
{
unsigned cnt = 0 ;
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
cmUdpNode_t * np = p - > list ;
for ( ; np ! = NULL ; np = np - > link )
if ( cnt = = nodeIdx )
return np - > id ;
return cmInvalidId ;
}
cmUnRC_t cmUdpNetRegisterRemote (
cmUdpNetH_t h ,
const cmChar_t * remoteNodeLabel ,
unsigned remoteNodeId ,
const char * remoteNodeSockAddr ,
cmUdpPort_t remoteNodePort )
{
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
struct sockaddr_in addr ;
if ( remoteNodeLabel = = NULL | | strlen ( remoteNodeLabel ) = = 0 )
return cmErrMsg ( & p - > err , kInvalidNodeLabelUnRC , " The node label must contain a non-empty string. " ) ;
if ( _cmUnFindLabel ( p , remoteNodeLabel ) ! = NULL )
return cmErrMsg ( & p - > err , kDuplicateNodeLabelUnRC , " The node label '%s' is already in use. " , cmStringNullGuard ( remoteNodeLabel ) ) ;
if ( _cmUnFindId ( p , remoteNodeId ) ! = NULL )
return cmErrMsg ( & p - > err , kDuplicateNodeIdUnRC , " The node id '%i' is already in use. " , remoteNodeId ) ;
if ( cmUdpInitAddr ( p - > udpH , remoteNodeSockAddr , remoteNodePort , & addr ) ! = kOkUdpRC )
return cmErrMsg ( & p - > err , kInvalidNodeAddrUnRC , " The node address '%s' port:%i is not valid. " , cmStringNullGuard ( remoteNodeSockAddr ) , remoteNodePort ) ;
cmUdpNode_t * np = cmMemAllocZ ( cmUdpNode_t , 1 ) ;
np - > label = cmMemAllocStr ( remoteNodeLabel ) ;
np - > id = remoteNodeId ;
np - > addr = addr ;
np - > port = remoteNodePort ;
np - > link = p - > list ;
p - > list = np ;
return kOkUnRC ;
}
cmUnRC_t cmUdpNetSendById ( cmUdpNetH_t h , unsigned remoteNodeId , const void * data , unsigned dataByteCnt )
{
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
cmUdpNode_t * np ;
if ( ( np = _cmUnFindId ( p , remoteNodeId ) ) = = NULL )
return cmErrMsg ( & p - > err , kNodeNotFoundUnRC , " The remote node (id=%i) was not found . " ,remoteNodeId) ;
if ( cmUdpSendTo ( p - > udpH , data , dataByteCnt , & np - > addr ) ! = kOkUdpRC )
return cmErrMsg ( & p - > err , kSendFailUnRC , " An attempt to send to a remote node with id=%i failed. " , remoteNodeId ) ;
return kOkUnRC ;
}
cmUnRC_t cmUdpNetSendByLabel ( cmUdpNetH_t h , const cmChar_t * remoteNodeLabel , const void * data , unsigned dataByteCnt )
{
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
cmUdpNode_t * np ;
if ( ( np = _cmUnFindLabel ( p , remoteNodeLabel ) ) = = NULL )
return cmErrMsg ( & p - > err , kNodeNotFoundUnRC , " The remote node (label=%s) was not found . " ,cmStringNullGuard(remoteNodeLabel)) ;
if ( cmUdpSendTo ( p - > udpH , data , dataByteCnt , & np - > addr ) ! = kOkUdpRC )
return cmErrMsg ( & p - > err , kSendFailUnRC , " An attempt to send to the remote node labeled:%s failed. " , cmStringNullGuard ( remoteNodeLabel ) ) ;
return kOkUnRC ;
}
cmUnRC_t cmUdpNetReceive ( cmUdpNetH_t h , unsigned * msgCntPtr )
{
cmUnRC_t rc = kOkUnRC ;
unsigned maxMsgCnt = 0 ;
unsigned msgCnt = 0 ;
if ( msgCntPtr = = NULL )
maxMsgCnt = cmInvalidCnt ;
else
maxMsgCnt = * msgCntPtr ;
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
if ( cmUdpIsValid ( p - > udpH ) )
{
for ( msgCnt = 0 ; ( maxMsgCnt = = cmInvalidCnt | | msgCnt < maxMsgCnt ) & & cmUdpAvailDataByteCount ( p - > udpH ) ; + + msgCnt )
{
if ( cmUdpGetAvailData ( p - > udpH , NULL , NULL , NULL ) ! = kOkUdpRC )
{
rc = cmErrMsg ( & p - > err , kGetDataFailUnRC , " An attempt to get available message data failed. " ) ;
break ;
}
}
}
if ( msgCntPtr ! = NULL )
* msgCntPtr = msgCnt ;
return rc ;
}
cmUnRC_t cmUdpNetPrintNodes ( cmUdpNetH_t h , cmRpt_t * rpt )
{
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
cmUdpNode_t * np = p - > list ;
unsigned i ;
for ( i = 0 ; np ! = NULL ; np = np - > link , + + i )
cmRptPrintf ( rpt , " %5i %5i %s \n " , i , np - > id , np - > label ) ;
return kOkUnRC ;
}
void cmUdpNetReport ( cmUdpNetH_t h , cmRpt_t * rpt )
{
cmUdpNet_t * p = _cmUnHandleToPtr ( h ) ;
cmUdpReport ( p - > udpH , rpt ) ;
}
//=========================================================================================
typedef struct
{
cmTimeSpec_t t ;
unsigned localNodeId ;
cmUdpNetH_t h ;
} _cmUdpNetTestMsg_t ;
void _cmUdpNetTestCb ( void * cbArg , cmUdpNetH_t h , const char * data , unsigned dataByteCnt , unsigned remoteNodeId )
{
cmRpt_t * rpt = ( cmRpt_t * ) cbArg ;
cmRptPrintf ( rpt , " recv - id:%i %s \n " , remoteNodeId , data ) ;
}
void _cmUdpNetTestCb2 ( void * cbArg , cmUdpNetH_t h , const char * data , unsigned dataByteCnt , unsigned remoteNodeId )
{
_cmUdpNetTestMsg_t * m = ( _cmUdpNetTestMsg_t * ) data ;
cmRpt_t * rpt = ( cmRpt_t * ) cbArg ;
assert ( dataByteCnt = = sizeof ( _cmUdpNetTestMsg_t ) ) ;
if ( m - > localNodeId = = cmUdpNetLocalNodeId ( h ) )
{
cmTimeSpec_t t ;
cmTimeGet ( & t ) ;
cmRptPrintf ( rpt , " elapsed:%i \n " , cmTimeElapsedMicros ( & m - > t , & t ) ) ;
}
else
{
cmRptPrintf ( rpt , " echo \n " ) ;
cmUdpNetSendById ( h , m - > localNodeId , & m , sizeof ( * m ) ) ;
}
}
2014-12-06 22:24:16 +00:00
const cmChar_t * _cmUdpNetTestGetOpt ( int argc , const char * argv [ ] , const char * opt )
2012-10-30 03:52:39 +00:00
{
unsigned i ;
for ( i = 0 ; i < argc ; + + i )
if ( strcmp ( argv [ i ] , opt ) = = 0 )
return argv [ i + 1 ] ;
return NULL ;
}
2014-12-06 22:24:16 +00:00
cmRC_t cmUdpNetTest ( cmCtx_t * ctx , int argc , const char * argv [ ] )
2012-10-30 03:52:39 +00:00
{
cmUdpNetH_t h = cmUdpNetNullHandle ;
cmJsonH_t jsH = cmJsonNullHandle ;
cmErr_t err ;
cmRC_t rc = cmOkRC ;
unsigned i = 0 ;
const cmChar_t * jsonFn ;
const cmChar_t * remoteNodeLabel ;
unsigned strCharCnt = 31 ;
cmChar_t str [ strCharCnt + 1 ] ;
bool msgFl = false ;
enum { kUdpNetTestErrRC = 1 } ;
cmErrSetup ( & err , & ctx - > rpt , " UDP Net Test " ) ;
// get the JSON file name
if ( ( jsonFn = _cmUdpNetTestGetOpt ( argc , argv , " -j " ) ) = = NULL )
return cmErrMsg ( & err , kUdpNetTestErrRC , " No JSON file name was given. " ) ;
// get the remote node label to send too
if ( ( remoteNodeLabel = _cmUdpNetTestGetOpt ( argc , argv , " -n " ) ) = = NULL )
return cmErrMsg ( & err , kUdpNetTestErrRC , " No remote node label was given. " ) ;
// create the JSON tree
if ( cmJsonInitializeFromFile ( & jsH , jsonFn , ctx ) ! = kOkJsRC )
{
rc = cmErrMsg ( & err , kUdpNetTestErrRC , " JSON file init failed on '%s'. " , cmStringNullGuard ( jsonFn ) ) ;
goto errLabel ;
}
if ( msgFl )
{
// alloc/init and put the network into listening mode
if ( cmUdpNetAllocJson ( ctx , & h , jsH , _cmUdpNetTestCb2 , & ctx - > rpt , kListenUnFl ) ! = kOkUnRC )
{
rc = cmErrMsg ( & err , kUdpNetTestErrRC , " UDP alloc/init/listen failed. " ) ;
goto errLabel ;
}
}
else
{
if ( cmUdpNetAlloc ( ctx , & h ) ! = kOkUnRC )
return cmErrMsg ( & err , kUdpNetTestErrRC , " UDP alloc failed. " ) ;
if ( cmUdpNetInitJson ( h , jsH , _cmUdpNetTestCb , & ctx - > rpt ) ! = kOkUnRC )
{
rc = cmErrMsg ( & err , kUdpNetTestErrRC , " UDP net init failed. " ) ;
goto errLabel ;
}
if ( cmUdpNetEnableListen ( h , true ) ! = kOkUnRC )
{
rc = cmErrMsg ( & err , kUdpNetTestErrRC , " UDP listen enable failed. " ) ;
goto errLabel ;
}
}
cmRptPrintf ( & ctx - > rpt , " s=send p=print r=report \n " ) ;
char c ;
while ( ( c = getchar ( ) ) ! = ' q ' )
{
bool promptFl = true ;
switch ( c )
{
case ' s ' :
{
// form the emessage
snprintf ( str , strCharCnt , " msg=%i " , i ) ;
// send a message to the remote node
if ( ! msgFl )
if ( cmUdpNetSendByLabel ( h , remoteNodeLabel , str , strlen ( str ) + 1 ) ! = kOkUnRC )
cmErrMsg ( & err , kUdpNetTestErrRC , " UDP net send failed. " ) ;
+ + i ;
}
break ;
case ' t ' :
{
_cmUdpNetTestMsg_t m ;
cmTimeGet ( & m . t ) ;
m . localNodeId = cmUdpNetLocalNodeId ( h ) ;
m . h = h ;
// send a message to the remote node
if ( msgFl )
if ( cmUdpNetSendByLabel ( h , remoteNodeLabel , & m , sizeof ( m ) ) ! = kOkUnRC )
cmErrMsg ( & err , kUdpNetTestErrRC , " UDP net send failed. " ) ;
}
break ;
case ' p ' :
cmUdpNetPrintNodes ( h , & ctx - > rpt ) ;
break ;
case ' r ' :
cmUdpNetReport ( h , & ctx - > rpt ) ;
break ;
default :
promptFl = false ;
}
cmUdpNetReceive ( h , NULL ) ;
if ( promptFl )
cmRptPrintf ( & ctx - > rpt , " %i> " , i ) ;
}
errLabel :
if ( cmUdpNetFree ( & h ) ! = kOkUnRC )
rc = cmErrMsg ( & err , kUdpNetTestErrRC , " UDP free failed. " ) ;
if ( cmJsonFinalize ( & jsH ) ! = kOkJsRC )
rc = cmErrMsg ( & err , kUdpNetTestErrRC , " JSON final fail. " ) ;
return rc ;
}