Mesh Vendor Specific App - Message Handling

Tip / Sign in to post questions, reply, level up, and achieve exciting badges. Know more

cross mob
LUAB_4724786
Level 4
Level 4
25 replies posted 10 likes received 10 replies posted

Hi there,

Currently we successfully creating based application that simulating sending a custom message payload (device mac address) with certain interval of time (every 10 seconds) on top of the sample code (mesh_vendor_specific_app). In this application, we program two devices as a Server (connected to the PC) and as a Node (auto send message with timer implementation, detail as below :

  • All devices provisioned.
  • Since it is provisioned, we can see the address and hardcoded the Destination Address to the Node Device (B) when sending message to the Server Device (A).
  • All devices use sample app based on mesh_vendor_specific_app, disabled all handling when receiving a message since the app give the sample to reply message automatically.
  • Server Device (A) connected to PC and print incoming message to serial terminal.
  • Illustration like below :

Screen Shot 2020-08-12 at 16.34.56.png

This implementation working properly ! every 10 seconds we received the message on Node A and the content of the message also complete, mac address + some fix payload data constantly received.

Then, we provisioned two more devices, the illustration like this :

Screen Shot 2020-08-12 at 16.35.09.png

  • Same code like B previously.
  • The arrow in there, we assume between B1, B2 and B3 the message they keep on relaying the message along the path.
  • The target still the same, destination address being used, which is A.

PROBLEM :

  • Message received constantly (as expected) from every node BUT Node A always received the same message 3 times from each device.
  • For example, Node B1 send "12345678" ... this data is received on Node A but 3 times.

Based on the spec it is said like this ...

Screen Shot 2020-08-12 at 16.34.39.png

So ... we rely on that implementation and assume that the device should act like that as well, could you help us what we did wrong or missed in here (some config or something else), our target is the Node A should only received message ONCE from each node. OR ... that Message Caching thingy, should we implemented by our self ? OR ... should we calculate TTL as well ?

Best Regards and Thanks.

LUTHFI AD

0 Likes
1 Solution

HI,

The message caching is done on the network layer. When a node sends a message, it can be re-transmitted several times, but each of the message is sent with the same source and sequence number. When a node receives a message, it checks the cache, and, if the same SRC and SEQ number is already present in the cache, it drops the message.

The re-transmission in your experiment is happening at the access layer, where each message is sent with it's own SEQ number. Please print p_event->retrans_cnt just before wiced_bt_mesh_core_send() to know the configured value for retrans_cnt. If you are receiving total 3 messages each time then the configured value of retrans_cnt could be 2. (The number of transmissions is the retrans_cnt + 1).

You can set the value of p_event->retrans_cnt=0 to stop this re-transmissions. Otherwise, you can include/append a transaction_id for each message to detect the duplicate messages.

Thanks,

-Dheeraj

View solution in original post

0 Likes
10 Replies
LUAB_4724786
Level 4
Level 4
25 replies posted 10 likes received 10 replies posted

Hi there,

I am adding the updates about this issue, it seems with one to one node also the same, it always received or triggering 3 times as well, the implementation still the same, like below :

Screen Shot 2020-08-12 at 16.34.56.png

and the message being sent have this characteristic :

  • Have a counter for each message being sent.
  • Message send every 10 secs.
  • At node A, I put the log on the function mesh_vendor_server_process_data() at the p_event->opcode == MESH_VENDOR_OPCODE4, the rest of the code in there when processing opcode4 disabled, so only print when message for opcode4 detected.
  • At node B, the message sent with the same opcode and the destination address is Node A.
  • Both nodes using code sample from mesh_vendor_specific_app.

The result as below,

Screen Shot 2020-08-13 at 17.31.59.png

As you can see, it seems the function mesh_vendor_server_process_data() being called 3 times (constantly) and you can see as well that the message have counter to make sure its different from another message.

Would you kindly help me to to understand this, why it behave like this or how to avoid this ... I try to search all the setting but still cannot find it why the function being called 3 times, I also add wiced_bt_mesh_release_event() but no luck, thanks.

Best Regards,

LUTHFI AD

0 Likes

HI,

The message caching is done on the network layer. When a node sends a message, it can be re-transmitted several times, but each of the message is sent with the same source and sequence number. When a node receives a message, it checks the cache, and, if the same SRC and SEQ number is already present in the cache, it drops the message.

The re-transmission in your experiment is happening at the access layer, where each message is sent with it's own SEQ number. Please print p_event->retrans_cnt just before wiced_bt_mesh_core_send() to know the configured value for retrans_cnt. If you are receiving total 3 messages each time then the configured value of retrans_cnt could be 2. (The number of transmissions is the retrans_cnt + 1).

You can set the value of p_event->retrans_cnt=0 to stop this re-transmissions. Otherwise, you can include/append a transaction_id for each message to detect the duplicate messages.

Thanks,

-Dheeraj

0 Likes

Hi,

One more additional info.

By default, the value of retrans_cnt should be 0. But currently it is getting set to 2. That why by default you are observing 3 transmission each time. This bug will be fixed in the next SDK release. For now, a quick workaround is to set retrans_cnt=0 just before calling core_send as below.

void mesh_vendor_server_send_data(wiced_bt_mesh_event_t *p_event, uint16_t opcode, uint8_t *p_data, uint16_t data_len)

{

    p_event->opcode = opcode;

    p_event->retrans_cnt = 0;

    wiced_bt_mesh_core_send(p_event, p_data, data_len, NULL);

}

Thanks,

-Dheeraj

0 Likes
lock attach
Attachments are accessible only for community members.

Dear Dheeraj,

Thanks a lot ! I test it and it works properly ! now I only received 1 message, see below :

Screen Shot 2020-08-17 at 21.10.54.png

But I encounter another problem, after several iteration (I counted and tested several times), after receiving total message of (32) 0x20, WICED_BT_TRACE() function looks like stop, it wont print anymore as you can see below. Well ... It is either WICED_BT_TRACE() function or the callback mesh_vendor_server_process_data() failed/stop. But ... as you can see in the log, the system keep receiving correct message (I mean I can see company ID and its opcode printed in there).

Screen Shot 2020-08-17 at 21.11.27.png

I also attached the log just in case you need it. This experiment actually based on some prospect business related with BLE that the company want to propose and the printing of each message becoming crucial for connected application later on the PC, please help me (again ... sorry) on this, since I tried to check the code or modify it with short msg on WICED_BT_TRACE() but it return no result, its still the same ... its stop printing.

By the way, where that "company_id:131 opcode:4" and "pool size/cur/max/total ..." message coming from ? I tried to search in the code but cannot find it.

Best Regards,

LUTHFI AD

0 Likes

Hi,

Please release the mesh event at appropriate times/places. The application should call wiced_bt_mesh_release_event() function when it receives the mesh event in the callback and the reply value is set to 0.

Eg: wiced_bt_mesh_release_event(p_event);

Check the logs. The buffers are fully occupied.

Screen+Shot+2020-08-17+at+21.11.27.png

FYI. Mesh application is implemented in mesh_application.c (wiced_btsdk\dev-kit\libraries\btsdk-mesh\COMPONENT_mesh_app_lib). Please have a look.

Thanks,

-Dheeraj

0 Likes

Hi Dheeraj !

Thank youuu ! it is working well ! you are awesome ! see below ... I ran it a few hours and still stable and working well, see below ! the next thing I will do is monitor its performance on receiving message from several nodes, the feasibility checking for our existing project looks promising !

Screen Shot 2020-08-18 at 15.07.52.png

By the way, your information about mesh_application.c really help me, a lot of information that I want are there. by the way my understanding on how on the application level coding now better and I want to ask and clarify something, this is related with the project as well.

mesh_vendor_specific_app define core config model in here (screenshot below) and its the entry for vendor to create something upon reeceiving message (mesh_vendor_server_message_handler()).

Screen Shot 2020-08-18 at 13.23.06.png

And ... if I need the callback on something related with "important" BT Wiced Mesh, I can define callback function in here :

Screen Shot 2020-08-18 at 13.23.41.png

Then I saw in mesh_application.c the structure that I want (see below) :

Screen Shot 2020-08-18 at 13.24.27.png

Here is the reason why I need that :

  • I want a device (too) that work on LPN.
  • mesh_vendor_specific_app sample already provides me on how to managing message now, its smooth.
  • wiced_mesh_app_func_table_t only support callback during LPN Sleep but not LPN Wake.
  • LPN feature is really good, it is talking "checking message" only to 1 friend (node) only, so I know where that node close to its friend area/zone.
  • And ... I need this address of the friend node so I can use it as a destination when sending the message.

My problem (since I am still new and too limited knowledge on this .. sadly) :

  1. I dont see mesh app table function related with LPN Wake (only LPN Sleep based on my test on LPN) or ... maybe I didnt think about it, LPN Sleep ... hmmm ... I can do something before sleeping, yes yes you are right ! I think I have to try this.
  2. Ok, so another problem ... even though I can do something before going to sleep with that LPN Sleep function, in there (based on my experience on low power led) mostly only max_sleep_duration parameter in the function but I dont have access to wiced_bt_mesh_core_state structure, so I can use friend node address in there to send message before sleeping.

Is there a way to solve the problem above ? I can only think of modifying main_application.c for now but ... a bit hesitate to do that since it is being use globally by other application sample.

Best Regards,

LUTHFI AD

0 Likes

I found something ...

can I just call this function wiced_bt_mesh_core_lpn_get_friend_addr() by extern it on mesh_vendor_specific_app ? I am just afraid its making some state changes or something else ...

0 Likes

Hi,

I don't think you need to get the friend node address to communicate with LPN. You can use the LPN address itself to send messages to it. The Friend node will automatically cache the messages for the LPN (dst addr), and deliver to the LPN when it polls (when it wakes up).

Friend & LPN feature and friendship logic as per the spec are implemented in the core libraries which is not exposed publicly.

You can try to define a post sleep callback in wiced_sleep_config_t.

change app_state.lpn_sleep_config.post_sleep_cback_handler = NULL; in low_power_led.c.

Thanks,

-Dheeraj

0 Likes

Dear Dheeraj,

Thanks for the support, I will test suggestion and do some experiment a bit about the message handling in LPN state, definitely will share you the result later.

Actually ... what I am trying to do is not sending the message to LPN, I test this before and it works great. What I want actually the LPN it self sending the message to specific node address that is why I am touching a bit LPN sleep callback, in short the idea is like this ...

  • LPN need to send message to specific node address when it wakes up, not checking the message from its friend ... instead sending a message and sleep.
  • And ... that specific node address, lets call it server node, server node need to know where that LPN send the message via its friend.
  • in my mind ... when friend node received message from LPN, friend node will relay the message to server node (via mesh) and add its address (before relaying) in the message content, so the server node will get the info where that LPN is "laying" around from its friend node (since it is LPN and will only talk to 1 node, friend node), that is why I need that friend address previously.

Anyway, I received lots of info from you, will do some experiment on it, thanks Dheeraj.

Best Regards,

LUTHFI AD

0 Likes

Hi,

I think you are asking about the configuration part of Low Power Node. The provisioner can set the publish period, publish address, timers, etc...  for the LPN after provisioning.  Please have a look at the "sensor_temperature" demo application for reference.

The basic behavior of LPN or Friend node cannot be changed from the application, since it is coded in the core library as per the mesh specification.

I would prefer you to create new threads in the community for each new topic, so that other community users can also easily search and find useful information.

Thanks,

-Dheeraj

0 Likes