//#warning --> make eo_transmitter_occasional_rops_Load obsolete ............. DO IT extern eOresult_t eo_transmitter_occasional_rops_Load_without_data(EOtransmitter *p, eOropdescriptor_t* ropdesc, uint8_t itisobsolete)//eOropcode_t ropcode, eOnvEP_t nvep, eOnvID_t nvid, eOropconfig_t ropcfg) { // eo_transm_regrop_info_t regropinfo; eOresult_t res; uint16_t usedbytes; uint16_t ropsize; uint16_t remainingbytes; if(NULL == p) { return(eores_NOK_nullpointer); } eov_mutex_Take(p->mtx_occasionals, eok_reltimeINFINITE); // prepare the rop in p->roptmp res = eo_agent_OutROPinit(p->theagent, p->nvscfg, p->ipv4addr, ropdesc, p->roptmp, &usedbytes); if(eores_OK != res) { eov_mutex_Release(p->mtx_occasionals); return(res); } // put the rop inside the ropframe res = eo_ropframe_ROP_Add(p->ropframeoccasionals, p->roptmp, NULL, &ropsize, &remainingbytes); eov_mutex_Release(p->mtx_occasionals); return(res); }
extern eOresult_t eo_transmitter_occasional_rops_Load(EOtransmitter *p, eOropdescriptor_t* ropdesc) //eOropcode_t ropcode, eOnvEP_t nvep, eOnvID_t nvid, eOropconfig_t ropcfg, uint8_t* data) { // eo_transm_regrop_info_t regropinfo; eOnvOwnership_t nvownership; eOresult_t res; uint16_t usedbytes; uint16_t ropsize; uint16_t remainingbytes; uint16_t ondevindex; uint16_t onendpointindex; uint16_t onidindex; EOtreenode* treenode; EOnv nv; eObool_t hasdata2send = eobool_false; if((NULL == p) || (NULL == ropdesc)) { return(eores_NOK_nullpointer); } if(NULL == ropdesc->data) { return(eo_transmitter_occasional_rops_Load_without_data(p, ropdesc, 0)); } if((eo_ropcode_say == ropdesc->ropcode) || (eo_ropcode_sig == ropdesc->ropcode) || (eo_ropcode_set == ropdesc->ropcode)) { hasdata2send = eobool_true; } nvownership = eo_rop_hid_GetOwnership(ropdesc->ropcode, eo_ropconf_none, eo_rop_dir_outgoing); // retrieve the indices inside the nvscfg given the triple (ip, ep, id) res = eo_nvscfg_GetIndices( (p->nvscfg), (eo_nv_ownership_local == nvownership) ? (eok_ipv4addr_localhost) : (p->ipv4addr), ropdesc->ep, ropdesc->id, &ondevindex, &onendpointindex, &onidindex); // if the nvscfg does not have the triple (ip, ep, id) then we return an error because we cannot form the rop if(eores_OK != res) { return(eores_NOK_generic); } // we need a treenode of the nv //treenode = eo_nvscfg_GetTreeNode(&(p->cfg.nvscfg), ondevindex, onendpointindex, onidindex); // we need the nv (but only if the rop needs data). treenode = NULL; // eo_nvscfg_GetNV() internally calls eo_nvscfg_GetTreeNode() eo_nvscfg_GetNV((p->nvscfg), ondevindex, onendpointindex, onidindex, treenode, &nv); // now we have the nv. we set its value in local ram if(eobool_true == hasdata2send) { eo_nv_Set(&nv, ropdesc->data, eobool_true, eo_nv_upd_dontdo); } eov_mutex_Take(p->mtx_occasionals, eok_reltimeINFINITE); // prepare the rop in p->roptmp // eOropconfig_t ropcfg; // ropcfg.confrqst = ropdesc->configuration.confrqst; // ropcfg.timerqst = ropdesc->configuration.timerqst; // ropcfg.plussign = ropdesc->configuration.plussign; // ropcfg.plustime = ropdesc->configuration.plustime; res = eo_agent_OutROPfromNV(p->theagent, &nv, ropdesc, p->roptmp, &usedbytes); if(eores_OK != res) { eov_mutex_Release(p->mtx_occasionals); return(res); } // put the rop inside the ropframe res = eo_ropframe_ROP_Add(p->ropframeoccasionals, p->roptmp, NULL, &ropsize, &remainingbytes); eov_mutex_Release(p->mtx_occasionals); return(res); }
extern eOresult_t eo_transmitter_regular_rops_Load(EOtransmitter *p, eOropdescriptor_t* ropdesc)//eOropcode_t ropcode, eOnvEP_t nvep, eOnvID_t nvid, eOropconfig_t ropcfg) { eo_transm_regrop_info_t regropinfo; eOropdescriptor_t ropdescriptor; eOresult_t res; uint16_t usedbytes; uint16_t remainingbytes; uint16_t ropstarthere; uint16_t ropsize; EOnv* tmpnvptr = NULL; if((NULL == p) || (NULL == ropdesc)) { return(eores_NOK_nullpointer); } if(NULL == p->listofregropinfo) { // in such a case there is room for regular rops (for instance because the cfg->maxnumberofregularrops is zero) return(eores_NOK_generic); } eov_mutex_Take(p->mtx_regulars, eok_reltimeINFINITE); // work on the list ... if(eobool_true == eo_list_Full(p->listofregropinfo)) { eov_mutex_Release(p->mtx_regulars); return(eores_NOK_generic); } // for searching inside listofregropinfo we need only those three fields: ropcode, id, ep ropdescriptor.ropcode = ropdesc->ropcode; ropdescriptor.ep = ropdesc->ep; ropdescriptor.id = ropdesc->id; // search for ropcode+ep+id. if found, then ... return OK and dont do anything because it means that the rop is already inside if(NULL != eo_list_Find(p->listofregropinfo, s_eo_transmitter_ropmatchingrule_rule, &ropdescriptor)) { // it is already inside ... eov_mutex_Release(p->mtx_regulars); return(eores_NOK_generic); } // else ... prepare a temporary variable eo_transm_regrop_info_t to be put inside the list. // and wait success of rop + insetrtion in frame // 1. prepare the rop to be put inside the ropframe. the rop contains also a reference to the associated netvar res = eo_agent_OutROPinit(p->theagent, p->nvscfg, p->ipv4addr, ropdesc, p->roptmp, &usedbytes); // if we cannot prepare the rop ... we quit if(eores_OK != res) { eov_mutex_Release(p->mtx_regulars); return(res); } // extract the reference to the associated netvar tmpnvptr = eo_rop_hid_NV_Get(p->roptmp); // 2. put the rop inside the ropframe res = eo_ropframe_ROP_Add(p->ropframeregulars, p->roptmp, &ropstarthere, &ropsize, &remainingbytes); // if we cannot add the rop we quit if(eores_OK != res) { eov_mutex_Release(p->mtx_regulars); return(res); } // 3. prepare a regropinfo variable to be put inside the list regropinfo.ropcode = ropdesc->ropcode; regropinfo.hasdata2update = eo_rop_hid_DataField_is_Present(&(p->roptmp->stream.head)); regropinfo.ropstarthere = ropstarthere; regropinfo.ropsize = ropsize; regropinfo.timeoffsetinsiderop = (0 == p->roptmp->stream.head.ctrl.plustime) ? (EOK_uint16dummy) : (ropsize - 8); //if we have time, then it is in teh last 8 bytes memcpy(®ropinfo.thenv, tmpnvptr, sizeof(EOnv)); // 4. finally push back regropinfo inside the list. eo_list_PushBack(p->listofregropinfo, ®ropinfo); eov_mutex_Release(p->mtx_regulars); return(eores_OK); }
extern eOresult_t eo_receiver_Process(EOreceiver *p, EOpacket *packet, uint16_t *numberofrops, eObool_t *thereisareply, eOabstime_t *transmittedtime) { uint16_t rxremainingbytes = 0; uint16_t txremainingbytes = 0; uint8_t* payload; uint16_t size; uint16_t capacity; uint16_t nrops; uint16_t i; eOresult_t res; eOipv4addr_t remipv4addr; eOipv4port_t remipv4port; uint64_t rec_seqnum; uint64_t rec_ageoframe; uint16_t numofprocessedrops = 0; if((NULL == p) || (NULL == packet)) { return(eores_NOK_nullpointer); } // clear the ropframereply w/ eo_ropframe_Clear(). the clear operation also makes it safe to manipulate p->ropframereplay with *_quickversion eo_ropframe_Clear(p->ropframereply); // we get the ip address and port of the incoming packet. // the remaddr can be any. however, if the eo_receiver_Process() is called by the EOtransceiver, it will be only the one of the remotehost eo_packet_Addressing_Get(packet, &remipv4addr, &remipv4port); // then we assign them to the ones of the EOreceiver. by doing so we force the receive to accept packets from everyboby. //p->ipv4addr = remipv4addr; //p->ipv4port = remipv4port; // retrieve payload from the incoming packet and load the ropframe with it eo_packet_Payload_Get(packet, &payload, &size); eo_packet_Capacity_Get(packet, &capacity); eo_ropframe_Load(p->ropframeinput, payload, size, capacity); // verify if the ropframeinput is valid w/ eo_ropframe_IsValid() if(eobool_false == eo_ropframe_IsValid(p->ropframeinput)) { #if defined(USE_DEBUG_EORECEIVER) { // DEBUG p->debug.rxinvalidropframes ++; } #endif p->error_invalidframe.remipv4addr = remipv4addr; p->error_invalidframe.ropframe = p->ropframeinput; s_eo_receiver_on_error_invalidframe(p); if(NULL != thereisareply) { *thereisareply = eobool_false; } return(eores_NOK_generic); } // check sequence number rec_seqnum = eo_ropframe_seqnum_Get(p->ropframeinput); rec_ageoframe = eo_ropframe_age_Get(p->ropframeinput); if(p->rx_seqnum == eok_uint64dummy) { //this is the first received ropframe or ... the sender uses dummy seqnum p->rx_seqnum = rec_seqnum; p->tx_ageofframe = rec_ageoframe; } else { if(rec_seqnum != (p->rx_seqnum+1)) { #if defined(USE_DEBUG_EORECEIVER) { p->debug.errorsinsequencenumber ++; } #endif // must set values p->error_seqnumber.remipv4addr = remipv4addr; p->error_seqnumber.rec_seqnum = rec_seqnum; p->error_seqnumber.exp_seqnum = p->rx_seqnum+1; p->error_seqnumber.timeoftxofcurrent = rec_ageoframe; p->error_seqnumber.timeoftxofprevious = p->tx_ageofframe; s_eo_receiver_on_error_seqnumber(p); } p->rx_seqnum = rec_seqnum; p->tx_ageofframe = rec_ageoframe; } nrops = eo_ropframe_ROP_NumberOf_quickversion(p->ropframeinput); for(i=0; i<nrops; i++) { // - get the rop w/ eo_ropframe_ROP_Parse() // if we have a valid ropinput the following eo_ropframe_ROP_Parse() returns OK. // in all cases rxremainingbytes contains the number of bytes we still need to parse. in case of // unrecoverable error in the ropframe res is NOK and rxremainingbytes is 0. res = eo_ropframe_ROP_Parse(p->ropframeinput, p->ropinput, &rxremainingbytes); if(eores_OK == res) { // we have a valid ropinput numofprocessedrops++; // - use the agent w/ eo_agent_InpROPprocess() and retrieve the ropreply. eo_agent_InpROPprocess(p->agent, p->ropinput, remipv4addr, p->ropreply); // - if ropreply is ok w/ eo_rop_GetROPcode() then add it to ropframereply w/ eo_ropframe_ROP_Add() if(eo_ropcode_none != eo_rop_GetROPcode(p->ropreply)) { res = eo_ropframe_ROP_Add(p->ropframereply, p->ropreply, NULL, NULL, &txremainingbytes); #if defined(USE_DEBUG_EORECEIVER) { // DEBUG if(eores_OK != res) { p->debug.lostreplies ++; } } #endif } } // we stop the decoding if rxremainingbytes has reached zero if(0 == rxremainingbytes) { break; } } if(NULL != numberofrops) { *numberofrops = numofprocessedrops; } // if any rop inside ropframereply w/ eo_ropframe_ROP_NumberOf() then sets thereisareply if(NULL != thereisareply) { *thereisareply = (0 == eo_ropframe_ROP_NumberOf(p->ropframereply)) ? (eobool_false) : (eobool_true); // dont use the quickversion because it may be that ropframereply is dummy //*thereisareply = (0 == eo_ropframe_ROP_NumberOf_quickversion(p->ropframereply)) ? (eobool_false) : (eobool_true); } if(NULL != transmittedtime) { *transmittedtime = eo_ropframe_age_Get(p->ropframeinput); } return(eores_OK); }