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

UART on GPIO PIN

Hello,

I am using nRF52832. My GPS is connected to GPIO pin (15, RX) and (16, TX) of nRF52832. My TCA9535 is connected to GPIO pin (8, SDA) and (7, SCL) of nRF52832. TCA9535 is providing power (3.7 V) to GPS to turn it ON and its working fine (TESTED). I am trying to print data on UART using Terminal COM PORT but unable to print GPS DATA on TERMINAL.

Main.c

#include <Wire.h>
#include <nrf_delay.h>
#include <TCA9535.h>
#include <stdbool.h>
#include <stdint.h>
#include <stdio.h>
#include "app_uart.h"
#include "app_error.h"
#include "nrf_delay.h"
#include "nrf.h"
#include "bsp.h"
#if defined (UART_PRESENT)
#include "nrf_uart.h"
#endif
#if defined (UARTE_PRESENT)
#include "nrf_uarte.h"
#endif

TCA9535 TCA9535Sensor = TCA9535();

#define MAX_TEST_DATA_BYTES (15U) /**< max number of test bytes to be used for tx and rx. */
#define UART_TX_BUF_SIZE 256 /**< UART TX buffer size. */
#define UART_RX_BUF_SIZE 256 /**< UART RX buffer size. */

void tca_init()
{

TCA9535Sensor.begin();
printf("Init complete!\n");

TCA9535Sensor.setPin(12, TCA9535Sensor.OUTPUTa);
printf("TCA9535 is ON!\n");

TCA9535Sensor.writePin(12,TCA9535Sensor.OFF);
printf("OFF!\n");

nrf_delay_ms(1000);

TCA9535Sensor.writePin(12,TCA9535Sensor.ON);
printf("ON!\n");
}

void uart_error_handle(app_uart_evt_t * p_event)
{
uint32_t err_code;
uint8_t byte;

switch (p_event->evt_type)
{
case APP_UART_DATA_READY:
err_code = app_uart_get(&byte);
APP_ERROR_CHECK(err_code);
printf("APP_UART_DATA_READY");
break;

case APP_UART_COMMUNICATION_ERROR:
APP_ERROR_HANDLER(p_event->data.error_communication);
printf("APP_UART_COMMUNICATION_ERROR");
break;

case APP_UART_FIFO_ERROR:
APP_ERROR_HANDLER(p_event->data.error_code);
printf("APP_UART_FIFO_ERROR");
break;

default:
break;
}
}

#ifdef ENABLE_LOOPBACK_TEST
/* Use flow control in loopback test. */
#define UART_HWFC APP_UART_FLOW_CONTROL_ENABLED

/** @brief Function for setting the @ref ERROR_PIN high, and then enter an infinite loop.
*/
static void show_error(void)
{

bsp_board_leds_on();
while (true)
{
// Do nothing.
}
}


/** @brief Function for testing UART loop back.
* @details Transmitts one character at a time to check if the data received from the loopback is same as the transmitted data.
* @note @ref TX_PIN_NUMBER must be connected to @ref RX_PIN_NUMBER)
*/
static void uart_loopback_test()
{
uint8_t * tx_data = (uint8_t *)("\r\nLOOPBACK_TEST\r\n");
uint8_t rx_data;

// Start sending one byte and see if you get the same
for (uint32_t i = 0; i < MAX_TEST_DATA_BYTES; i++)
{
uint32_t err_code;
while (app_uart_put(tx_data[i]) != NRF_SUCCESS);

nrf_delay_ms(10);
err_code = app_uart_get(&rx_data);

if ((rx_data != tx_data[i]) || (err_code != NRF_SUCCESS))
{
show_error();
}
}
return;
}
#else
/* When UART is used for communication with the host do not use flow control.*/
#define UART_HWFC APP_UART_FLOW_CONTROL_DISABLED
#endif

void uart_init()
{
uint32_t err_code;

const app_uart_comm_params_t comm_params =
{
//RX_PIN_NUMBER,
15,
//TX_PIN_NUMBER,
16,
false,
false,
UART_HWFC,
false,
UART_BAUDRATE_BAUDRATE_Baud9600
//#if defined (UART_PRESENT)
//NRF_UART_BAUDRATE_115200
// NRF_UART_BAUDRATE_9600
//#else
// NRF_UARTE_BAUDRATE_115200
//#endif
};


APP_UART_FIFO_INIT(&comm_params,
UART_RX_BUF_SIZE,
UART_TX_BUF_SIZE,
uart_error_handle,
APP_IRQ_PRIORITY_LOWEST,
err_code);

APP_ERROR_CHECK(err_code);

#ifndef ENABLE_LOOPBACK_TEST
printf("\r\nUART example started.\r\n");
}
/*
void app_uart_put_string(const char* s)
{
uint32_t err_code;
uint8_t len = strlen(s);
for (uint8_t i = 0; i < len; i++)
{
err_code = app_uart_put(s[i]);
APP_ERROR_CHECK(err_code);
}
}
*/

int main() {

tca_init();
uart_init();

while (true)
{
//app_uart_put_string("HELLO");
uint8_t cr;
//app_uart_get(&cr);
while (app_uart_get(&cr) != NRF_SUCCESS);
printf("%c \n",cr);
//app_uart_put(cr);
while (app_uart_put(cr) != NRF_SUCCESS);
printf("%c \n",cr);
}
#else

// This part of the example is just for testing the loopback .
while (true)
{
uart_loopback_test();
}
#endif
}

  • Ok. If you use your UART for the GPS, you can't use the UART for the debug window. You can use NRF_LOG module, with NRF_LOG_INFO(); but you must use the RTT backend, and not UART.

    I suggest that you try to set the backend to RTT, and see if you get that up and running before you print the UART values over the RTT log. You can use Segger's RTT Viewer to see the RTT log.

    I don't know whether you intend to use Bluetooth Low Energy (BLE) in your application in the end. If you do, I suggest you check out the examples\ble_peripheral\ble_app_uart example.

    Unfortunately, the uart example that you are using, requires a bit work to set up the RTT log (but it is possible). But if you haven't used it before, I would start with another example, to see that you have the rest of the setup correct.

    If you don't intend to use BLE, you can start with the uart example, but copy all the text from:

    // <h> nRF_Log

    to 

    #ifndef NRF_TWI_SENSOR_CONFIG_DEBUG_COLOR
    #define NRF_TWI_SENSOR_CONFIG_DEBUG_COLOR 0
    #endif

    // </e>

    // </h>
    //==========================================================

    // </h>
    //==========================================================

    // </h>
    //==========================================================

    // </h>
    //==========================================================

    And replace all your nRF_Log defines in your sdk_config.h with this.

    So from the ble_app_uart example, copy the lines 7239 - 9538 (in SDK15.0.0)

    Then you will probably get some compiler errors. You must find and include all the files that are missing for RTT logging.

    If you use the ble_app_uart example, it will have RTT logging enabled by default. The RTT log will contain everything written in NRF_LOG_INFO();

    Best regards,

    Edvin

  • to printf on debug console, you can use the semihosting.  See the section semihosting at then end of this blog http://embeddedsoftdev.blogspot.com/p/idap-link.html.  It redirects your printf to debug console over SWD without using UART.  The drawback is that it is a bit slow.

  • Hey Edvin,

    Thanks for your reply.

    I already add NRF_LOG_RTT in CMSIS config file and in the Backend its using RTT instead of UART. But still, i am unable to print data using NRF_LOG. I am getting an error below:

    undefined symbol: __start_log_const_data

    undefined symbol: __start_log_dynamic_data

    undefined symbol: __stop_log_const_data

    i have attached my main.cpp for APP_UART

    -----------------------------------------------------------------------------------------------------------------------------------

    I tried with Nrf_Serial_Uart as well and i can able to initialize multiple serial instances.

    I am using TCA to turn on GPS and CELL. Both (GPS, CELL) are conected on UART with different pins.

    NOW, i  just want to read and write data on serial. (I wanted to see data on the terminal as well as debug window). It just prints one character on debug window but I want to print that continues. 

    I have attached my main.cpp for NRF_SERIAL

    -----------------------------------------------------------------------------------------------------------------------------------

    As you mentioned, I can use BLE_UART.

    I wanted to use that as well. I tried default example. but when i change default pins to my UART pins. I unable to see GPS data on my BLE app.

    If you have an example code running that shows GPS data on BLE app when GPS is connected to non-default pins then Please share with me.

    -------------------------------------------------------------------------------------------------------------------------------------

    Main.cpp for APP_UART

    #include <Wire.h>
    #include <nrf_delay.h>
    #include <TCA9535.h>
    #include <stdbool.h>
    #include <stdint.h>
    #include <stdio.h>
    #include "app_uart.h"
    #include "app_error.h"
    #include "nrf_delay.h"
    #include "nrf.h"
    #include "bsp.h"
    #include "nrf_log.h"
    #include "nrf_log_ctrl.h"
    #include "nrf_log_default_backends.h"
    #if defined (UART_PRESENT)
    #include "nrf_uart.h"
    #endif
    #if defined (UARTE_PRESENT)
    #include "nrf_uarte.h"
    #endif
    
    TCA9535 TCA9535Sensor = TCA9535();
    
    #define MAX_TEST_DATA_BYTES     (15U)                /**< max number of test bytes to be used for tx and rx. */
    #define UART_TX_BUF_SIZE 256                         /**< UART TX buffer size. */
    #define UART_RX_BUF_SIZE 256                         /**< UART RX buffer size. */
    
    void tca_init()
    {
    
        TCA9535Sensor.begin();
        //printf("Init complete!\n");
        NRF_LOG_INFO("Init complete!\n");
        
    
        TCA9535Sensor.setPin(12, TCA9535Sensor.OUTPUTa);
        //printf("TCA9535 is ON!\n");
        NRF_LOG_INFO("TCA9535 is ON!\n");
        
    
        TCA9535Sensor.writePin(12,TCA9535Sensor.OFF);
        //printf("OFF!\n");
        NRF_LOG_INFO("TCA9535 is OFF!\n");
    
        nrf_delay_ms(1000);
    
        TCA9535Sensor.writePin(12,TCA9535Sensor.ON);
        //printf("ON!\n");
        NRF_LOG_INFO("ON!\n");
        NRF_LOG_FLUSH();
    }
    /*
    void uart_error_handle(app_uart_evt_t * p_event)
    {
        uint32_t	err_code;
        uint8_t	byte;
    
        switch (p_event->evt_type)
        {
            case APP_UART_DATA_READY:
    	    err_code = app_uart_get(&byte);
    	    APP_ERROR_CHECK(err_code);
                printf("APP_UART_DATA_READY");
                break;
    
            case APP_UART_COMMUNICATION_ERROR:
                APP_ERROR_HANDLER(p_event->data.error_communication);
                printf("APP_UART_COMMUNICATION_ERROR");
                break;
    
            case APP_UART_FIFO_ERROR:
                APP_ERROR_HANDLER(p_event->data.error_code);
                printf("APP_UART_FIFO_ERROR");
                break;
    
            default:
                break;
        }
    }
    
    */
    
    #ifdef ENABLE_LOOPBACK_TEST
    /* Use flow control in loopback test. */
    #define UART_HWFC APP_UART_FLOW_CONTROL_ENABLED
    
    /** @brief Function for setting the @ref ERROR_PIN high, and then enter an infinite loop.
     */
    static void show_error(void)
    {
    
        bsp_board_leds_on();
        while (true)
        {
            // Do nothing.
        }
    }
    
    
    /** @brief Function for testing UART loop back.
     *  @details Transmitts one character at a time to check if the data received from the loopback is same as the transmitted data.
     *  @note  @ref TX_PIN_NUMBER must be connected to @ref RX_PIN_NUMBER)
     */
    static void uart_loopback_test()
    {
        uint8_t * tx_data = (uint8_t *)("\r\nLOOPBACK_TEST\r\n");
        uint8_t   rx_data;
    
        // Start sending one byte and see if you get the same
        for (uint32_t i = 0; i < MAX_TEST_DATA_BYTES; i++)
        {
            uint32_t err_code;
            while (app_uart_put(tx_data[i]) != NRF_SUCCESS);
    
            nrf_delay_ms(10);
            err_code = app_uart_get(&rx_data);
    
            if ((rx_data != tx_data[i]) || (err_code != NRF_SUCCESS))
            {
                show_error();
            }
        }
        return;
    }
    #else
    /* When UART is used for communication with the host do not use flow control.*/
    #define UART_HWFC APP_UART_FLOW_CONTROL_DISABLED
    #endif
    
    void uart_init()
    {
        uint32_t err_code;
    
        const app_uart_comm_params_t comm_params =
          {
               //RX_PIN_NUMBER,
               15,
               //TX_PIN_NUMBER,
               16,
               false,
               false,
               UART_HWFC,
               false,
               UART_BAUDRATE_BAUDRATE_Baud9600
    //#if defined (UART_PRESENT)
             //NRF_UART_BAUDRATE_115200
        //       NRF_UART_BAUDRATE_9600
    //#else
      //        NRF_UARTE_BAUDRATE_115200
    //#endif
          };
    
        
        APP_UART_FIFO_INIT(&comm_params,
                             UART_RX_BUF_SIZE,
                             UART_TX_BUF_SIZE,
                             NULL,
                             //uart_error_handle,
                             APP_IRQ_PRIORITY_LOWEST,
                             err_code);
        
        APP_ERROR_CHECK(err_code);
    
    #ifndef ENABLE_LOOPBACK_TEST
        NRF_LOG_INFO("UART Init\n");
        NRF_LOG_FLUSH();
    }
    /*
    void app_uart_put_string(const char* s)
    {
        uint32_t err_code;
        uint8_t len = strlen(s);
        for (uint8_t i = 0; i < len; i++)
        {
            err_code = app_uart_put(s[i]);
            APP_ERROR_CHECK(err_code);
        }
    }
    */
    
    int main() {
    
        APP_ERROR_CHECK(NRF_LOG_INIT(NULL));
        NRF_LOG_DEFAULT_BACKENDS_INIT();
        tca_init();
        uart_init();
       
        while (true)
        {
           //app_uart_put_string("HELLO");
            uint8_t cr;
            //app_uart_get(&cr);
            while (app_uart_get(&cr) != NRF_SUCCESS);
            NRF_LOG_INFO("Data", cr);
            NRF_LOG_FLUSH();
            //app_uart_put(cr);
            //while (app_uart_put(cr) != NRF_SUCCESS);
            
        }
    #else
    
        // This part of the example is just for testing the loopback .
        while (true)
        {
            uart_loopback_test();
        }
    #endif
    }
    

    Main.cpp for NRF_SERIAL_UART

    /**
     * Copyright (c) 2016 - 2018, Nordic Semiconductor ASA
     * 
     * All rights reserved.
     * 
     * Redistribution and use in source and binary forms, with or without modification,
     * are permitted provided that the following conditions are met:
     * 
     * 1. Redistributions of source code must retain the above copyright notice, this
     *    list of conditions and the following disclaimer.
     * 
     * 2. Redistributions in binary form, except as embedded into a Nordic
     *    Semiconductor ASA integrated circuit in a product or a software update for
     *    such product, must reproduce the above copyright notice, this list of
     *    conditions and the following disclaimer in the documentation and/or other
     *    materials provided with the distribution.
     * 
     * 3. Neither the name of Nordic Semiconductor ASA nor the names of its
     *    contributors may be used to endorse or promote products derived from this
     *    software without specific prior written permission.
     * 
     * 4. This software, with or without modification, must only be used with a
     *    Nordic Semiconductor ASA integrated circuit.
     * 
     * 5. Any software provided in binary form under this license must not be reverse
     *    engineered, decompiled, modified and/or disassembled.
     * 
     * THIS SOFTWARE IS PROVIDED BY NORDIC SEMICONDUCTOR ASA "AS IS" AND ANY EXPRESS
     * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
     * OF MERCHANTABILITY, NONINFRINGEMENT, AND FITNESS FOR A PARTICULAR PURPOSE ARE
     * DISCLAIMED. IN NO EVENT SHALL NORDIC SEMICONDUCTOR ASA OR CONTRIBUTORS BE
     * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
     * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
     * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
     * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
     * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
     * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     * 
     */
    //#include <Wire.h>
    #include "TCA9535.h"
    
    #include <stdint.h>
    #include <stdbool.h>
    #include <stddef.h>
    
    #include "nrf.h"
    #include "nrf_drv_clock.h"
    #include "nrf_gpio.h"
    #include "nrf_delay.h"
    #include "nrf_log.h"
    #include "nrf_log_ctrl.h"
    #include "nrf_drv_power.h"
    #include "nrf_serial.h"
    #include "app_timer.h"
    
    
    #include "app_error.h"
    #include "app_util.h"
    #include "boards.h"
    
    /** @file
     * @defgroup nrf_serial_example main.c
     * @{
     * @ingroup nrf_serial_example
     * @brief Example of @ref nrf_serial usage. Simple loopback.
     *
     */
    TCA9535 TCA9535Sensor = TCA9535();
    
    #define OP_QUEUES_SIZE          3
    #define APP_TIMER_PRESCALER     NRF_SERIAL_APP_TIMER_PRESCALER
    
    static void sleep_handler(void)
    {
        __WFE();
        __SEV();
        __WFE();
    }
    
    
    NRF_SERIAL_DRV_UART_CONFIG_DEF(m_uart0_drv_config,
                          15, 16,
                          NULL, NULL,
                          NRF_UART_HWFC_DISABLED, NRF_UART_PARITY_EXCLUDED,
                          NRF_UART_BAUDRATE_9600,
                          UART_DEFAULT_CONFIG_IRQ_PRIORITY);
    
    NRF_SERIAL_DRV_UART_CONFIG_DEF(m_uart1_drv_config,
                          8, 6,
                          NULL, NULL,
                          NRF_UART_HWFC_DISABLED, NRF_UART_PARITY_EXCLUDED,
                          NRF_UART_BAUDRATE_9600,
                          UART_DEFAULT_CONFIG_IRQ_PRIORITY);
    
    #define SERIAL_FIFO_TX_SIZE 32
    #define SERIAL_FIFO_RX_SIZE 32
    
    NRF_SERIAL_QUEUES_DEF(serial_queues, SERIAL_FIFO_TX_SIZE, SERIAL_FIFO_RX_SIZE);
    
    
    #define SERIAL_BUFF_TX_SIZE 1
    #define SERIAL_BUFF_RX_SIZE 1
    
    NRF_SERIAL_BUFFERS_DEF(serial_buffs, SERIAL_BUFF_TX_SIZE, SERIAL_BUFF_RX_SIZE);
    
    NRF_SERIAL_CONFIG_DEF(serial_config, NRF_SERIAL_MODE_POLLING,
                          &serial_queues, &serial_buffs, NULL, sleep_handler);
    
    
    NRF_SERIAL_UART_DEF(serial_uart, 0);
    
    void tca_init()
    {
        TCA9535Sensor.begin();
        TCA9535Sensor.setPin(8, TCA9535Sensor.OUTPUTa);
        TCA9535Sensor.writePin(8,TCA9535Sensor.ON);
        printf("TCA Init, PIN <8> ON!\n");
        
    }
    
    void drv_init()
    {
        ret_code_t drv_ret;
        drv_ret = nrf_drv_clock_init();
        APP_ERROR_CHECK(drv_ret);
        drv_ret = nrf_drv_power_init(NULL);
        APP_ERROR_CHECK(drv_ret);
        nrf_drv_clock_lfclk_request(NULL);
        drv_ret = app_timer_init();
        APP_ERROR_CHECK(drv_ret);
    
        printf("Driver Init....!!! \n");
    }
    
    int main(void)
    {
        
        //size_t bytesRead = 0;
        //char c[20] = {' '};
        ret_code_t ret;
        //size_t data_size = 2;
    
        tca_init();
        drv_init();
    
        ret = nrf_serial_init(&serial_uart, &m_uart0_drv_config, &serial_config);
        APP_ERROR_CHECK(ret);
        printf("Serial Uart Init...!!! \n");
        static char tx_message[] = "Hello nrf_serial!\n\r";
    
        ret = nrf_serial_write(&serial_uart,
                               tx_message,
                               strlen(tx_message),
                               NULL,
                               NRF_SERIAL_MAX_TIMEOUT);
        APP_ERROR_CHECK(ret);
        
        //nrf_serial_flush(&serial_uart, 0);
        while (true)
        {
            //for(int i=0;i<11;i++)
            //{
            char c;
            ret = nrf_serial_read(&serial_uart, &c, sizeof(c), NULL, 500);
            APP_ERROR_CHECK(ret);
            //uart_buf[cnt++] = c;
            printf("%c \n",c);
            //}
            (void)nrf_serial_write(&serial_uart, &c, sizeof(c), NULL, 0);
            
            (void)nrf_serial_flush(&serial_uart, 0);
            //(void)nrf_serial_rx_drain(&serial_uart);
            nrf_serial_uninit(&serial_uart);
            nrf_delay_ms(100);
            ret = nrf_serial_init(&serial_uart, &m_uart1_drv_config, &serial_config);
            APP_ERROR_CHECK(ret);
            (void)nrf_serial_write(&serial_uart, &c, sizeof(c), NULL, 0);
            //(void)nrf_serial_write(&serial_uart, &d, sizeof(c), NULL, 0);
            //(void)nrf_serial_write(&serial_uart, &f, sizeof(c), NULL, 0);
            (void)nrf_serial_flush(&serial_uart, 0);
            //(void)nrf_serial_rx_drain(&serial_uart);
            nrf_serial_uninit(&serial_uart);
            nrf_delay_ms(100);
            ret = nrf_serial_init(&serial_uart, &m_uart0_drv_config, &serial_config);
            APP_ERROR_CHECK(ret);
            printf("%c %c \n", c, d);
          //  (void)nrf_serial_flush(&serial_uart, 0);
        }
    }
    
    /** @} */
    

  • Thanks for your reply.

    I am using MBN52832 DK and still, i am not able to get anything on TERMINAL or DEBUG WINDOW.

  • Yes, that is working with Default Pins (8,6). Did you try with PIN (15,16) or any non-default pins? VDD level is fine with the GPIO pins. I checked. 

Related