Docs

You are here:
Endpoint message exchange

Endpoints

All user messages within the RCM protocol are exchanged through endpoints, which can be considered logical channels. Each endpoint is identified by an 8-bit number ranging from 1 to 239.

In order to communicate, the user needs to first register an endpoint through the RCM_RegisterEndpoint function. Once the endpoint is registered in both the sending and receiving node, a message can be exchanged.

The sending node uses RCM_SendMessage function to send a message described by a RCMMessage structure (see Messages). The most basic method of gaining access to the received messages in the receiving node is to poll the connection using RCM_GetPendingMessage function. This function returns a pointer to a received RCMMessage structure. Once obtained, the user is responsible for freeing the message structure using RCM_UnlockMessage function.

Exemplary code that sends messages

The following example illustrates how to send messages, using three types :

#include "rcm.h"
// Structure holding information about the connection
static RCMConnection rcm;
// Declare a structure named frameBuffer, that will fit infinite SCOM packets
static SCOM_DECLARE_FRAME_BUFFER_USING_HEAP(frameBufferInHeap);
// Declare a structure named messageBufferInHeap that can fit unlimited number of RCM messages
static RCM_DECLARE_MESSAGE_BUFFER_USING_HEAP(messageBufferInHeap);
int rcm_message_exchange_sender_example(IODevice iodevice)
{
int result = 0;
RCMMessage outgoingMessage;
// try to open the connection using specified IODevice
if (RCM_RESULT_OK == RCM_Open(&rcm, iodevice, &frameBufferInHeap, &messageBufferInHeap, OS_GetSystemTime)) {
// connection opened, run it
if (RCM_RESULT_OK == RCM_Run(&rcm)) {
// threads run successfully
// configure the RCM module
RCM_SetUID(&rcm, 0x0123456789abcdee);
// Register an endpoint: EP1
if (RCM_RESULT_OK == RCM_StartNetworking(&rcm)) {
// network established successfully
// prepare the message to send using short destination addressing mode
// message = outgoingMessage : message structure
// dstAddr = 0 : destination address in short form (16 bit) - 0 is the address of the coordinator
// dstEndpoint = 1 : destination endpoint
// srcEndpoint = 1 : source endpoint
// profileId = 1 : not used
// clusterId = 1 : not used
// radius = 0 : no limit on radius
// data = "Hello! (shortAddr)" : data to send
// dataSize = 18 : size of data to send in number of bytes
// reqAck = true : the message should be acknowledged
RCMMSG_InitOutgoingMessageUsingShortAddrMode(&outgoingMessage, 0, 1, 1, 1, 1, 0, "Hello! (shortAddr)", 18, true);
// send the message
if (RCM_RESULT_OK != RCM_SendMessage(&rcm, &outgoingMessage)) {
// unable to send the message
result = 5;
}
// some delay
OS_Sleep(1000);
// prepare the message to send using UID destination addressing mode
// message = outgoingMessage : message structure
// dstUID = 0x0x0123456789abcdef : destination UID, should be the UID of the coordinator
// dstEndpoint = 1 : destination endpoint
// srcEndpoint = 1 : source endpoint
// profileId = 1 : not used
// clusterId = 1 : not used
// radius = 0 : no limit on radius
// data = "Hello! (uid)" : data to send
// dataSize = 12 : size of data to send in number of bytes
// reqAck = true : the message should be acknowledged
// RCMMSG_InitOutgoingMessageUsingUID(&outgoingMessage, 0x0123456789abcdef, 1, 1, 1, 1, 0, "Hello! (uid)", 12, true);
//
// // send the message
// if (RCM_RESULT_OK != RCM_SendMessage(&rcm, &outgoingMessage)) {
// // unable to send the message
// result = 5;
// }
//
// // some delay
// OS_Sleep(1000);
// prepare the message to send using broadcast
// message = outgoingMessage : message structure
// dstEndpoint = 1 : destination endpoint
// srcEndpoint = 1 : source endpoint
// profileId = 1 : not used
// clusterId = 1 : not used
// radius = 0 : no limit on radius
// data = "Hello! (broadcast)" : data to send
// dataSize = 18 : size of data to send in number of bytes
// reqAck = true : the message should be acknowledged
RCMMSG_InitOutgoingMessageUsingBroadcast(&outgoingMessage, 1, 1, 1, 1, 0, "Hello! (broadcast)", 18);
// send the message
if (RCM_RESULT_OK != RCM_SendMessage(&rcm, &outgoingMessage)) {
// unable to send the message
result = 5;
}
// some delay
OS_Sleep(1000);
// check connection
if (RCM_RESULT_OK != RCM_GetConnectionState(&rcm)) {
// connection broke down (hardware error?)
// exit with error code
result = 4;
}
} else {
// failed to join the network
// exit with error code
result = 3;
}
// stop the RCM threads
RCM_Stop(&rcm);
} else {
// error
result = 2;
}
// finally close the connection
RCM_Close(&rcm);
} else {
// error
result = 1;
}
return result;
}

Exemplary code that receives messages

The following example illustrates how to receive messages:

#include "rcm.h"
#include "rcm_log.h"
// Structure holding information about the connection
static RCMConnection rcm;
// Declare a structure named frameBuffer, that will fit infinite SCOM packets
static SCOM_DECLARE_FRAME_BUFFER_USING_HEAP(frameBufferInHeap);
// Declare a structure named messageBufferInHeap that can fit unlimited number of RCM messages
static RCM_DECLARE_MESSAGE_BUFFER_USING_HEAP(messageBufferInHeap);
int rcm_message_exchange_receiver_example(IODevice iodevice)
{
int result = 0;
RCMMessage* receivedMessage;
OSTime startTime;
// get current time
startTime = OS_GetSystemTime();
// try to open the connection using specified IODevice
if (RCM_RESULT_OK == RCM_Open(&rcm, iodevice, &frameBufferInHeap, &messageBufferInHeap, OS_GetSystemTime)) {
// connection opened, run it
if (RCM_RESULT_OK == RCM_Run(&rcm)) {
// threads run successfully
// configure the RCM module
RCM_SetUID(&rcm, 0x0123456789abcdef);
// Register an endpoint: EP1
if (RCM_RESULT_OK == RCM_StartNetworking(&rcm)) {
// network established successfully
while (0 == result) {
// poll the connection for messages
receivedMessage = RCM_GetPendingMessage(&rcm);
if (receivedMessage) {
// we have received a message!
RCM_LOG_LOCK();
RCM_LOG_HEADER();
RCM_LOG_MSG("Got message from shortAddr=");
RCM_LOG_UINT(receivedMessage->srcAddr.shortAddr, 10);
RCM_LOG_MSG(" saying: ");
receivedMessage->payload[receivedMessage->dataSize] = 0;
RCM_LOG_MSG((const char*)receivedMessage->payload);
RCM_LOG_NL();
RCM_LOG_UNLOCK();
// message not needed anymore - unlock it
RCM_UnlockMessage(&rcm, receivedMessage);
}
// some delay
OS_Sleep(100);
// check connection
if (RCM_RESULT_OK != RCM_GetConnectionState(&rcm)) {
// connection broke down (hardware error?)
// exit with error code
result = 4;
}
// check timeout
if (OS_GetSystemTime() - startTime > 10000) {
// timeout
break;
}
}
} else {
result = 3;
}
// stop the RCM threads
RCM_Stop(&rcm);
} else {
// error
result = 2;
}
// finally close the connection
RCM_Close(&rcm);
} else {
// error
result = 1;
}
return result;
}
Go to Top