nRF5 SDK is not maintained anymore
More Info: Consider nRF Connect SDK for new designs

send and receive data over ble without character 0xDA (Enter)

Hi, I have a NRF52840 DK. I want to use ble_app_uart_c and my peripheral is NRF52840 Dongle and also I want to receive and transmit special frame over ble. I have a problem with BLE_NUS_C_EVT_NUS_TX_EVT becuase  this Requires special characters 0xDA (Enter) to receive data and run bluetooth handler. In my application, sometimes it is necessary to receive or send  this character. I have a special rule to understand the end of the received frame and I do not need to use this character.

Are there any solutions for this?

 Is there a solution to send and receive character by character?

Thanks,

Mohammad Amin

  • Hi Mohammad

    This behavior is set by the ble_app_uart and ble_app_uart_c examples, and you should be able to change the application code in order to change the criteria's used to send or receive data. 

    For example, in the ble_app_uart_c example it is the ble_nus_chars_received_uart_print(..) function that is used to process the data received from the peer Bluetooth device and forward it to the UART interface, while the uart_event_handle(..) function is processing the UART data and sending it over the Bluetooth connection. 

    Best regards
    Torbjørn

  • Thanks Torbjørn.

    Sorry but I can't understand correctly. for example if a frame(binary) send from LabView to Devkit, the DK won't receive this frame because The end of the frame does not have the character 0xDA and won't run ble_nus_chars_received_uart_print(..) function. This is my problem and I want to solve that.

    Can you help me?

    Best regards

    MohammadAmin

  • Hi Mohammad

    If I understand you correctly you are sending data from LabView to a DK running the ble_app_uart example, which is connected to another DK over Bluetooth running the ble_app_uart_c example, and you see here that you don't get the full message that you sent from the PC side?

    In this case it is the uart_event_handle function on the ble_app_uart side that is the problem, as it only transmits a packet if either the buffer fills up, or if the LF or CR character is received (0x0A or 0x0D):

    /**@brief   Function for handling app_uart events.
     *
     * @details This function will receive a single character from the app_uart module and append it to
     *          a string. The string will be be sent over BLE when the last character received was a
     *          'new line' '\n' (hex 0x0A) or if the string has reached the maximum data length.
     */
    /**@snippet [Handling the data received over UART] */
    void uart_event_handle(app_uart_evt_t * p_event)
    {
        static uint8_t data_array[BLE_NUS_MAX_DATA_LEN];
        static uint8_t index = 0;
        uint32_t       err_code;
    
        switch (p_event->evt_type)
        {
            case APP_UART_DATA_READY:
                UNUSED_VARIABLE(app_uart_get(&data_array[index]));
                index++;
    
                if ((data_array[index - 1] == '\n') ||
                    (data_array[index - 1] == '\r') ||
                    (index >= m_ble_nus_max_data_len))
                {
                    if (index > 1)
                    {
                        NRF_LOG_DEBUG("Ready to send data over BLE NUS");
                        NRF_LOG_HEXDUMP_DEBUG(data_array, index);
    
                        do
                        {
                            uint16_t length = (uint16_t)index;
                            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);
                    }
    
                    index = 0;
                }
                break;
    
            case APP_UART_COMMUNICATION_ERROR:
                APP_ERROR_HANDLER(p_event->data.error_communication);
                break;
    
            case APP_UART_FIFO_ERROR:
                APP_ERROR_HANDLER(p_event->data.error_code);
                break;
    
            default:
                break;
        }
    }
    /**@snippet [Handling the data received over UART] */

    What you could do is to add a timer in the ble_app_uart example that will check the status of the data_array buffer, and send it after some time even if the LF or CR characters aren't received. 

    Essentially, if the index variable is larger than 0 it means that some data has been buffered in the data_array buffer but not yet sent, and if it stays over 0 for a certain amount of time without anything happening you could just send the data_array buffer immediately and clear the index variable (similar to how it's already done in the uart_event_handle(..) function when CR or LF is received). 

    Best regards
    Torbjørn

Related