This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

Transferring large data over TWIS and send it via Bluetooth

Hello,

I am developing a project with a host processor and Minew BT module with NRF52811. The module and the host processor are communicating via I2C (TWIS). The host processor is a master and the BT module is a slave.

We have a main application on the BT module (based on NUS example) which connects to an Android application and the Android app and the module are communicating by writing to a characteristic (similar to TX/RX). When the phone has written some specific data to the module, the module sends that data to the host processor (the host processor queries every 2ms whether there is something that the module needs to send) and then a HTTP request by the host processor is made. The response from the HTTP request is stored in the GSM module's RAM and can be retrieved in chunks with RTS hardware flow control signal, because the response can be up to 100KB long.

For now, the logic is as follows:
The module gets the first 244 bytes from the HTTP response and sends a notification to the Android app. After that, the module will get the next chunk of 244 bytes of data whenever the module receives BLE_GATTS_EVT_HVN_TX_COMPLETE event (there is a little delay of ~12ms for the host processor to query information that chunk needs to be sent, and get the next chunk with RTS signal and send it via I2C).

However, the throughput is really slow: ~70KB/37s (depends on the connection interval).

I've done some tests with the code snippet below in the main function for test:

      if(s_index>0){
                        s_index++;
                        if(s_index==570){
                          s_index=0;
                          
                        }
        static uint8_t data_array[BLE_NUS_MAX_DATA_LEN];
        for(int i=0;i<244;i++){
          data_array[i]=i;
        }
                    do
                    {
                        uint16_t length = 244;
                        err_code = ble_nus_data_send(&m_nus, data_array, &length, m_conn_handle);
                        if ((err_code != NRF_ERROR_INVALID_STATE) &&
                            (err_code != NRF_ERROR_RESOURCES) &&
                            (err_code != NRF_ERROR_NOT_FOUND))
                        {
                            APP_ERROR_CHECK(err_code);
                        }

                    } while (err_code == NRF_ERROR_RESOURCES);
      }
and the results are pretty good.

SoftDevice S112 - NRF52811 (Minew)
Android
100KB (569*180 bytes) - 3971ms / 45ms connection interval
135.6KB (569*244 bytes) - 5632ms / 45ms connection interval
iPhone
100KB (569*180 bytes) - 8s / 30ms connection interval
My question is: how can I improve the throughput considering all of the above explained. I thought of getting data in several buffers (5-6) and using the test code to send data. The logic is to send data as long as some of the buffers are full, and get data from the host processor as long as some of the buffers are empty. Is that a good way or is there something else that can be improved in the logic that is now implemented?
Thanks in advance.
Best regards
Parents
  • Hi,

    Do you have room for the bigger S140 softdevice? It supports the Data length Extension feature that can be used for sending larger data packets.

    regards

    Jared 

  • Hey Jared,

    unfortunately, the bigger S140 SD is not an option for us.
    The main question is for the logic implementation and maybe some other implementation suggestion, since I've got good results for the throughput with the S112 if I send notifications with the test code snippet from above.

  • Hi,

    kj_sk995 said:
    unfortunately, the bigger S140 SD is not an option for us.
    The main question is for the logic implementation and maybe some other implementation suggestion, since I've got good results for the throughput with the S112 if I send notifications with the test code snippet from above.

     I understand. 

     

    The module gets the first 244 bytes from the HTTP response and sends a notification to the Android app. After that, the module will get the next chunk of 244 bytes of data whenever the module receives BLE_GATTS_EVT_HVN_TX_COMPLETE event (there is a little delay of ~12ms for the host processor to query information that chunk needs to be sent, and get the next chunk with RTS signal and send it via I2C).

    I think the bottleneck in your program is here. I agree on using multiple buffers so that you can collect data while you send the other buffers over BLE would improve the throughput significantly. It's a good idea. 

    regards

    Jared 

Reply
  • Hi,

    kj_sk995 said:
    unfortunately, the bigger S140 SD is not an option for us.
    The main question is for the logic implementation and maybe some other implementation suggestion, since I've got good results for the throughput with the S112 if I send notifications with the test code snippet from above.

     I understand. 

     

    The module gets the first 244 bytes from the HTTP response and sends a notification to the Android app. After that, the module will get the next chunk of 244 bytes of data whenever the module receives BLE_GATTS_EVT_HVN_TX_COMPLETE event (there is a little delay of ~12ms for the host processor to query information that chunk needs to be sent, and get the next chunk with RTS signal and send it via I2C).

    I think the bottleneck in your program is here. I agree on using multiple buffers so that you can collect data while you send the other buffers over BLE would improve the throughput significantly. It's a good idea. 

    regards

    Jared 

Children
No Data
Related