This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

CCS/EVMK2G: UART_Write only after acquiring a semaphore from SWI thread

Part Number: EVMK2G

Tool/software: Code Composer Studio

Hi,

I have the below code to achieve that UART_write should send some data only after acquiring a semaphore from a SWI thread. Below are issues I face.

Issue 1  - The UART_write does not wait for the semaphore instead it prints only once the data on console and exits. 

Issue 2 - If the below lines are commented out, then the UART_write happens continuously

1. data_to_send[34] = (0x30+((i++)%9));

2. Semaphore_pend(callbackSem, SemaphoreP_WAIT_FOREVER);

Issue 3 - clockHandler does not get executes 

// main.c

/*
* ======== main.c ========
*/

#include "typedefs.h"
#include <stdio.h>
#include <string.h>
#include <xdc/std.h>
#include <xdc/runtime/Error.h>
#include <xdc/runtime/System.h>

#include <ti/sysbios/BIOS.h>
#include <ti/sysbios/knl/Semaphore.h>
#include <ti/sysbios/knl/clock.h>
#include <ti/sysbios/knl/Idle.h>
#include <ti/sysbios/knl/Task.h>

#include <xdc/cfg/global.h>


/* CSL Header files */
#include <ti/csl/csl_chip.h>
#include <ti/csl/soc.h>

/* OSAL Header files */
#include <ti/osal/osal.h>

/* UART Header files */
#include <ti/drv/uart/UART.h>
#include <ti/drv/uart/UART_stdio.h>
#include <ti/drv/uart/soc/UART_soc.h>
#include <ti/drv/uart/test/src/UART_board.h>
#include <ti/drv/uart/src/UART_osal.h>
#include <ti/csl/csl_clec.h>


/* Global variable definitions for UART Working*/
Semaphore_Handle callbackSem;
UART_PAR uartParity = UART_PAR_NONE;
uint32_t uartTestInstance;
int16_t verifyLoopback = 0U;
EDMA3_RM_Handle gEdmaHandle = NULL;
uint32_t var=0;

/* Task Functions and Semaphores */
void init_task(UArg arg0, UArg arg1);
void task_uart(UArg arg0, UArg arg1);
void clockHandler(UArg arg);
Semaphore_Handle sem;

/* Function prototypes */
static void UART_test_write(UART_Handle uart, bool dmaMode);
static EDMA3_RM_Handle UartApp_edmaInit(void);

/*
* Initialize the edma driver and get the handle to the edma driver;
*/
static EDMA3_RM_Handle UartApp_edmaInit(void){
EDMA3_DRV_Result edmaResult = EDMA3_DRV_E_INVALID_PARAM;
uint32_t edma3Id;

uint32_t edmaEvent[2], i, chnMapping, chnMappingIdx;

/* For Keystone devices, edm3Id is UART instance and SoC specific */
UART_getEdmaInfo(uartTestInstance, &edma3Id, edmaEvent);

/* Set the RX/TX ownDmaChannels and dmaChannelHwEvtMap */
for (i = 0; i < 2; i++)
{
chnMapping = edmaEvent[i];
if (chnMapping < 32)
chnMappingIdx = 0;
else
{
chnMapping -= 32;
chnMappingIdx = 1;
}
sampleInstInitConfig[edma3Id][0].ownDmaChannels[chnMappingIdx] |= (1 << chnMapping);
sampleInstInitConfig[edma3Id][0].ownTccs[chnMappingIdx] |= (1 << chnMapping);
sampleInstInitConfig[edma3Id][0].ownPaRAMSets[chnMappingIdx] |= (1 << chnMapping);
sampleEdma3GblCfgParams[edma3Id].dmaChannelHwEvtMap[chnMappingIdx] |= (1 << chnMapping);
}

if (gEdmaHandle != NULL)
{
return(gEdmaHandle);
}

gEdmaHandle = (EDMA3_RM_Handle)edma3init(edma3Id, &edmaResult);
if (edmaResult != EDMA3_DRV_SOK) {
/* Report EDMA Error */
System_printf("\nEDMA driver initialization FAIL\n");
} else {
System_printf("\nEDMA driver initialization PASS.\n");
}
return(gEdmaHandle);
}

/*
* ======== UART init config ========
*/
/*-------------------------------------------------------------------------------------------------------------------------------------------------*/
static void UART_initConfig(bool dmaMode){
UART_HwAttrs uart_cfg;

/* Get the default UART init configurations */
UART_socGetInitCfg(uartTestInstance, &uart_cfg);

if (dmaMode == true) {
uart_cfg.edmaHandle = UartApp_edmaInit();
uart_cfg.dmaMode = TRUE;
} else {
uart_cfg.edmaHandle = NULL;
uart_cfg.dmaMode = FALSE;
}

if(verifyLoopback) {
uart_cfg.loopback = TRUE;
} else {
uart_cfg.loopback = FALSE;
}
/* Set the DMA enabled UART init configurations */
UART_socSetInitCfg(uartTestInstance, &uart_cfg);
}

/*-------------------------------------------------------------------------------------------------------------------------------------------------*/
void UART_getTestInstNum(uint32_t *instNum, bool *boardAM570x){
*instNum = UART_INSTANCE;
*boardAM570x = false;
}
/*-------------------------------------------------------------------------------------------------------------------------------------------------*/
bool Board_initUART(void){
Board_initCfg boardCfg;
Board_STATUS boardStatus;
bool boardAM570x;

boardCfg = BOARD_INIT_PINMUX_CONFIG | BOARD_INIT_MODULE_CLOCK;

boardStatus = Board_init(boardCfg);
if (boardStatus != BOARD_SOK) {
return (false);
}

UART_getTestInstNum(&uartTestInstance, &boardAM570x);

return (true);
}

/*-------------------------------------------------------------------------------------------------------------------------------------------------*/
static uintptr_t l2_global_address (uintptr_t addr){
uint32_t corenum;

/* Get the core number. */
corenum = CSL_chipReadReg (CSL_CHIP_DNUM);

/* Compute the global address. */
return (addr + (0x10000000 + (corenum * 0x1000000)));
}


/*-------------------------------------------------------------------------------------------------------------------------------------------------*/
void clockHandler(UArg arg) {
static unsigned int i=0;
// post semaphore only after a second. i increments for every 1ms
if (i++>1000)
{
System_printf("Semaphore posted\n");
Semaphore_post(callbackSem);
i=0;
}
}

/*-------------------------------------------------------------------------------------------------------------------*/
/*
* ======== UART write test ========
*
* The test function tests read/write in blocking mode
*/
static void UART_test_write(UART_Handle uart, bool dmaMode)
{
uintptr_t addrDataPrint;
unsigned char data_to_send[] = "New number filled for iteration - \r\n";
static unsigned int i=0;

//Modify the data every time the task executes
data_to_send[34] = (0x30+((i++)%9));

if (uart != NULL) {
if (dmaMode) {
addrDataPrint = l2_global_address((uintptr_t)data_to_send);
} else {
addrDataPrint = (uintptr_t)data_to_send;
}

// wait until someone posts a semaphore to send the data
Semaphore_pend(callbackSem, SemaphoreP_WAIT_FOREVER);

//Write the data packet now
UART_write(uart, (void *)addrDataPrint, sizeof(data_to_send));

} else {
//Semaphore_delete(callbackSem);
callbackSem = NULL;
}
}

/*-------------------------------------------------------------------------------------------------------------------------------------------------*/
void init_task(UArg arg0, UArg arg1) {

Task_Handle task_uarti;
Task_Params taskParams;
UART_Handle uart = NULL;
UART_Params uartParams;
Error_Block eb;
uint16 taskkey;
uint32 delay=0, i;

System_printf("\nInitialization task begins here");
//Call board init
if (Board_initUART() == false)
{
System_printf("\nBoard_init UART failed!\n");
//return(0);
}

//Call UART init
UART_init();

/* UART SoC init configuration */
UART_initConfig(true);

/* Initialize the default configuration params. */
UART_Params_init(&uartParams);
uartParams.parityType = uartParity;

uart = UART_open(uartTestInstance, &uartParams);

while (1)
{
UART_test_write(uart, true);
}
}


/*
* ======== main ========
*/
/*-------------------------------------------------------------------------------------------------------------------*/
Int main()
{
Task_Params taskParams;
Task_Handle init_taski, dummy_taski;
SemaphoreP_Params semParams;
Clock_Params clkParams;
Clock_Handle myclk;
Error_Block eb;

// Initialization of Error block
Error_init(&eb);

System_printf("enter main()\n");

//Initialize the task parameters
Task_Params_init(&taskParams);
taskParams.stackSize = 1024;
taskParams.priority = 5;
init_taski = Task_create((Task_FuncPtr)init_task, &taskParams, &eb);
if (init_taski == NULL){
System_printf("\n Init Task creation failed\n");
}

Clock_Params_init(&clkParams);
// I believe this gives one msecond period
clkParams.period = 1000;
clkParams.startFlag = TRUE;
myclk = Clock_create((Clock_FuncPtr)clockHandler, clkParams.period, &clkParams, &eb);

/* Create call back semaphore */
callbackSem = Semaphore_create(0, NULL, &eb);

if(callbackSem == NULL){
System_abort("Semaphore create failed!\n");
}

BIOS_start(); /* does not return */
return(0);
}

config file is as below

app.cfg


var Defaults = xdc.useModule('xdc.runtime.Defaults');
var Diags = xdc.useModule('xdc.runtime.Diags');
var Error = xdc.useModule('xdc.runtime.Error');
var Log = xdc.useModule('xdc.runtime.Log');
var LoggerBuf = xdc.useModule('xdc.runtime.LoggerBuf');
var Main = xdc.useModule('xdc.runtime.Main');
var Memory = xdc.useModule('xdc.runtime.Memory')
var SysMin = xdc.useModule('xdc.runtime.SysMin');
var System = xdc.useModule('xdc.runtime.System');
var Text = xdc.useModule('xdc.runtime.Text');

var BIOS = xdc.useModule('ti.sysbios.BIOS');
var Clock = xdc.useModule('ti.sysbios.knl.Clock');
var Swi = xdc.useModule('ti.sysbios.knl.Swi');
var Task = xdc.useModule('ti.sysbios.knl.Task');
var Semaphore = xdc.useModule('ti.sysbios.knl.Semaphore');
var Hwi = xdc.useModule('ti.sysbios.hal.Hwi');

/*
* Uncomment this line to globally disable Asserts.
* All modules inherit the default from the 'Defaults' module. You
* can override these defaults on a per-module basis using Module.common$.
* Disabling Asserts will save code space and improve runtime performance.
Defaults.common$.diags_ASSERT = Diags.ALWAYS_OFF;
*/

/*
* Uncomment this line to keep module names from being loaded on the target.
* The module name strings are placed in the .const section. Setting this
* parameter to false will save space in the .const section. Error and
* Assert messages will contain an "unknown module" prefix instead
* of the actual module name.
Defaults.common$.namedModule = false;
*/

/*
* Minimize exit handler array in System. The System module includes
* an array of functions that are registered with System_atexit() to be
* called by System_exit().
*/
System.maxAtexitHandlers = 4;

/*
* Uncomment this line to disable the Error print function.
* We lose error information when this is disabled since the errors are
* not printed. Disabling the raiseHook will save some code space if
* your app is not using System_printf() since the Error_print() function
* calls System_printf().
Error.raiseHook = null;
*/

/*
* Uncomment this line to keep Error, Assert, and Log strings from being
* loaded on the target. These strings are placed in the .const section.
* Setting this parameter to false will save space in the .const section.
* Error, Assert and Log message will print raw ids and args instead of
* a formatted message.
Text.isLoaded = false;
*/

/*
* Uncomment this line to disable the output of characters by SysMin
* when the program exits. SysMin writes characters to a circular buffer.
* This buffer can be viewed using the SysMin Output view in ROV.
SysMin.flushAtExit = false;
*/

/*
* The BIOS module will create the default heap for the system.
* Specify the size of this default heap.
*/
BIOS.heapSize = 0x2000;

/*
* Build a custom SYS/BIOS library from sources.
*/
BIOS.libType = BIOS.LibType_Custom;

/* System stack size (used by ISRs and Swis) */
Program.stack = 0x1000;

/* Circular buffer size for System_printf() */
SysMin.bufSize = 0x1000;

/*
* Create and install logger for the whole system
*/
var loggerBufParams = new LoggerBuf.Params();
loggerBufParams.numEntries = 16;
var logger0 = LoggerBuf.create(loggerBufParams);
Defaults.common$.logger = logger0;
Main.common$.diags_INFO = Diags.ALWAYS_ON;

System.SupportProxy = SysMin;

/* install a BIOS startup function */
//BIOS.addUserStartupFunction('&myBiosStartup');
Clock.timerId = 0;


/////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////////////////////
var Edma = xdc.loadPackage ("ti.sdo.edma3.drv.sample");
var drv = xdc.loadPackage ("ti.sdo.edma3.drv");
var rm = xdc.loadPackage ("ti.sdo.edma3.rm");
var CpIntc = xdc.useModule('ti.sysbios.family.c66.tci66xx.CpIntc');
var Hwi = xdc.useModule('ti.sysbios.family.c64p.Hwi');
var ECM = xdc.useModule('ti.sysbios.family.c64p.EventCombiner');
var Cache = xdc.useModule('ti.sysbios.hal.Cache');
var HeapMem = xdc.useModule('ti.sysbios.heaps.HeapMem');
var HeapBuf = xdc.useModule('ti.sysbios.heaps.HeapBuf');
var devType = "k2g"

/* Load the OSAL package */
var osType = "tirtos"
var Osal = xdc.useModule('ti.osal.Settings');
Osal.osType = osType;
Osal.socType = devType;

/* Load CSL settings */
var Csl = xdc.loadPackage('ti.csl');
Csl.Settings.deviceType = devType;

/* Create a default system heap using ti.bios.HeapMem. */
var heapMemParams1 = new HeapMem.Params;
heapMemParams1.size = 8192 * 25;
heapMemParams1.sectionName = ".systemHeap";
Program.global.heap0 = HeapMem.create(heapMemParams1);

/* Load the Board package and set the board name */
var Board = xdc.loadPackage('ti.board');
Board.Settings.boardName = "evmK2G";

/* Load Profiling package */
//var Utils = xdc.loadPackage('ti.utils.profiling');

/* Load the uart package */
var Uart = xdc.loadPackage('ti.drv.uart');
//Uart.Settings.enableProfiling = true;
Uart.Settings.socType = devType;
Uart.Settings.useDma = "true";

/* No runtime stack checking is performed */
Task.checkStackFlag = false;

/* Enable BIOS Task Scheduler */
BIOS.taskEnabled = true;

ECM.eventGroupHwiNum[0] = 7;
ECM.eventGroupHwiNum[1] = 8;
ECM.eventGroupHwiNum[2] = 9;
ECM.eventGroupHwiNum[3] = 10;

/*
* Enable Event Groups here and registering of ISR for specific GEM INTC is done
* using EventCombiner_dispatchPlug() and Hwi_eventMap() APIs
*/
var exception = xdc.useModule('ti.sysbios.family.c64p.Exception');
exception.enablePrint = true;

  • Nagaraju,

    Can you please indicate how are you continuously posting a semaphore in a SWI. SWI unlike Task will run to completion, do you have some kind of HWI that launches the SWI_post to post subsequent semaphores ? Are you using the UART driver in blocking or callback mode in the test. 

    We would recommend that you run the UART Example or test to understand the baseline and confirm the UART setup and then look to modify the code. Also, please try to attach the source code files in the post instead of posting your code in the forum as your post is not very readable with Text and code mixed together.

    Regards,

    Rahul

  • Rahul,

    I have followed an example given in sys/bios user guide and updated the code for this. 

    I have created a clock object(clockHanlder) which runs at every 1ms. I have a static counter incremented for every 1ms inside the clockHandler. Once the static counter reaches 1000 (i.e. 1 second) I have posted a semaphore and reset the counter back to 0. I am using UART in blocking mode with DMA enabled (did not change the default configuration). 

    I have added the source code files here.  Please have a look.

    2287.app.cfg

    /*
     *  ======== main.c ========
     */
    
    #include "typedefs.h"
    #include <stdio.h>
    #include <string.h>
    #include <xdc/std.h>
    #include <xdc/runtime/Error.h>
    #include <xdc/runtime/System.h>
    
    #include <ti/sysbios/BIOS.h>
    #include <ti/sysbios/knl/Semaphore.h>
    #include <ti/sysbios/knl/clock.h>
    #include <ti/sysbios/knl/Idle.h>
    #include <ti/sysbios/knl/Task.h>
    
    #include <xdc/cfg/global.h>
    
    
    /* CSL Header files */
    #include <ti/csl/csl_chip.h>
    #include <ti/csl/soc.h>
    
    /* OSAL Header files */
    #include <ti/osal/osal.h>
    
    /* UART Header files */
    #include <ti/drv/uart/UART.h>
    #include <ti/drv/uart/UART_stdio.h>
    #include <ti/drv/uart/soc/UART_soc.h>
    #include <ti/drv/uart/test/src/UART_board.h>
    #include <ti/drv/uart/src/UART_osal.h>
    #include <ti/csl/csl_clec.h>
    
    
    void init_task(UArg arg0, UArg arg1);
    void task_uart(UArg arg0, UArg arg1);
    void clockHandler(UArg arg);
    Semaphore_Handle sem;
    uint16 count=0;
    
    
    /* Define the UART test interface */
    typedef struct UART_Tests_s
    {
        bool     (*testFunc)(bool);
        bool     dmaMode;
        int16_t  testId;
        char     testDesc[80];
    
    } UART_Tests;
    
    /* UART test ID definitions */
    #define UART_TEST_ID_DMA         0   /* UART DMA read write test in block mode */
    #define UART_TEST_ID_INT         1   /* UART non-DMA read write test in block mode */
    #define UART_TEST_ID_DMA_CB      2   /* UART DMA read write test in callback mode */
    #define UART_TEST_ID_CB          3   /* UART non-DMA read write test in callback mode */
    #define UART_TEST_ID_DMA_TO      4   /* UART DMA timeout test */
    #define UART_TEST_ID_TO          5   /* UART non DMA timeout test */
    #define UART_TEST_ID_DMA_RXERR   6   /* UART DMA RX error test */
    #define UART_TEST_ID_RXERR       7   /* UART non-DMA RX error test */
    #define UART_TEST_ID_DMA_CANCEL  8   /* UART DMA read write cancel test */
    #define UART_TEST_ID_CANCEL      9   /* UART non-DMA read write cancel test */
    #define UART_TEST_ID_DMA_RW      10  /* UART DMA simultaneous read write test */
    #define UART_TEST_ID_RW          11  /* UART non-DMA simultaneous read write test */
    #define UART_TEST_ID_DMA_TRGLVL  12  /* UART DMA TX/RX FIFO trigger level test */
    #define UART_TEST_ID_PRINTF      13  /* UART stdio printf and scanf test */
    #define UART_TEST_ID_TRGLVL      14  /* UART non-DMA TX/RX FIFO trigger level test */
    #define UART_TEST_ID_POLL_TO     15  /* UART read write polling timeout test */
    #define UART_TEST_ID_STDIOPARAMS 16  /* UART stdio printf and scanf test, with configurable params(Default params) */
    #define UART_TEST_ID_INT_DISABLE 17  /* UART read write test with interrupt disabled */
    #define UART_TEST_ID_RDVERIFY    18  /* UART non-DMA read API Test in loopback mode */
    #define UART_TEST_ID_MULTI_INSTS 19  /* UART DMA multiple instances test in loopback mode */
    
    #define UART_NUM_TRIG_LVL           (4U)
    
    /* Length of the input in number of characters */
    #define UART_TEST_READ_LEN     (16U)
    #define UART_RDVERIFY_READ_LEN (4U)
    
    /* Timeout value of read and write */
    #define UART_TEST_TIMEOUT      (5000U)
    
    /* Max number of instances to test in multiple instance test case */
    #define UART_TEST_NUM_INSTS    (2U)
    #define UART_TEST_CACHE_LINE_SIZE (128U)
    
    #pragma DATA_ALIGN (scanPrompt, UART_TEST_CACHE_LINE_SIZE)
    char scanPrompt[256];
    char echoPrompt[40] = "\n\r Data entered is as follows \r\n";
    char dataPrint[40] = "\r\n enter the data of 16 character \r\n";
    char readTimeoutPrompt[60] = "\r\n Read timed out \r\n";
    char breakErrPrompt[60] = "\r\n Received a break condition error \r\n";
    char rdCancelPrompt[60] = "\r\n Previous read canceled \r\n";
    char wrCancelPrompt[60] = "\r\n Previous write canceled \r\n";
    char fifoTrgLvlData[256] = "0123456789112345678921234567893123456789412345678951234567896123456789712345678981234567899123456789";
    char stdioPrint[64] = "\r\n enter the data of 16 character and press ENTER \r\n";
    char new_data_print[40] = "\r\nIteration - \r\n";
    
    /* Global variable definitions for UART Working*/
    Semaphore_Handle callbackSem;
    UART_PAR uartParity = UART_PAR_NONE;
    uint32_t uartTestInstance;
    int16_t verifyLoopback = 0U;
    EDMA3_RM_Handle gEdmaHandle = NULL;
    uint32_t var=0;
    
    /* Function prototypes */
    //static bool UART_test_callback(bool dmaMode);
    static void UART_test_print_test_desc(UART_Tests *test);
    static void UART_test_write(UART_Handle uart, bool dmaMode, unsigned char * data_to_send, uint16_t len);
    static EDMA3_RM_Handle UartApp_edmaInit(void);
    
    /* UART Test functions array */
    UART_Tests Uart_tests[] =
    {
     //{UART_test_write, true, UART_TEST_ID_DMA, "\r\n UART DMA read write test in block mode"},
     //{UART_test_callback, false, UART_TEST_ID_DMA, "\n UARTread write test in block mode\n"},
     {NULL, }
    };
    
    /*
     * Initialize the edma driver and get the handle to the edma driver;
     */
    static EDMA3_RM_Handle UartApp_edmaInit(void){
        EDMA3_DRV_Result edmaResult = EDMA3_DRV_E_INVALID_PARAM;
        uint32_t edma3Id;
    
        uint32_t edmaEvent[2], i, chnMapping, chnMappingIdx;
    
        /* For Keystone devices, edm3Id is UART instance and SoC specific */
        UART_getEdmaInfo(uartTestInstance, &edma3Id, edmaEvent);
    
        /* Set the RX/TX ownDmaChannels and dmaChannelHwEvtMap */
        for (i = 0; i < 2; i++)
        {
            chnMapping = edmaEvent[i];
            if (chnMapping < 32)
                chnMappingIdx = 0;
            else
            {
                chnMapping -= 32;
                chnMappingIdx = 1;
            }
            sampleInstInitConfig[edma3Id][0].ownDmaChannels[chnMappingIdx] |= (1 << chnMapping);
            sampleInstInitConfig[edma3Id][0].ownTccs[chnMappingIdx] |= (1 << chnMapping);
            sampleInstInitConfig[edma3Id][0].ownPaRAMSets[chnMappingIdx] |= (1 << chnMapping);
            sampleEdma3GblCfgParams[edma3Id].dmaChannelHwEvtMap[chnMappingIdx] |= (1 << chnMapping);
        }
    
        if (gEdmaHandle != NULL)
        {
            return(gEdmaHandle);
        }
    
        gEdmaHandle = (EDMA3_RM_Handle)edma3init(edma3Id, &edmaResult);
        if (edmaResult != EDMA3_DRV_SOK) {
            /* Report EDMA Error */
            System_printf("\nEDMA driver initialization FAIL\n");
        } else {
            System_printf("\nEDMA driver initialization PASS.\n");
        }
        return(gEdmaHandle);
    }
    
    /*
     *  ======== UART init config ========
     */
    /*-------------------------------------------------------------------------------------------------------------------------------------------------*/
    static void UART_initConfig(bool dmaMode){
        UART_HwAttrs uart_cfg;
    
        /* Get the default UART init configurations */
        UART_socGetInitCfg(uartTestInstance, &uart_cfg);
    
        if (dmaMode == true) {
            uart_cfg.edmaHandle = UartApp_edmaInit();
            uart_cfg.dmaMode    = TRUE;
        } else {
            uart_cfg.edmaHandle = NULL;
            uart_cfg.dmaMode    = FALSE;
        }
    
        if(verifyLoopback) {
            uart_cfg.loopback   = TRUE;
        } else {
            uart_cfg.loopback   = FALSE;
        }
        /* Set the DMA enabled UART init configurations */
        UART_socSetInitCfg(uartTestInstance, &uart_cfg);
    }
    
    /*-------------------------------------------------------------------------------------------------------------------------------------------------*/
    void UART_getTestInstNum(uint32_t *instNum, bool *boardAM570x){
        *instNum = UART_INSTANCE;
        *boardAM570x = false;
    }
    /*-------------------------------------------------------------------------------------------------------------------------------------------------*/
    bool Board_initUART(void){
        Board_initCfg boardCfg;
        Board_STATUS  boardStatus;
        bool          boardAM570x;
    
        boardCfg = BOARD_INIT_PINMUX_CONFIG | BOARD_INIT_MODULE_CLOCK;
    
        boardStatus = Board_init(boardCfg);
        if (boardStatus != BOARD_SOK) {
            return (false);
        }
    
        UART_getTestInstNum(&uartTestInstance, &boardAM570x);
    
        return (true);
    }
    
    /*-------------------------------------------------------------------------------------------------------------------------------------------------*/
    static uintptr_t l2_global_address (uintptr_t addr){
        uint32_t corenum;
    
        /* Get the core number. */
        corenum = CSL_chipReadReg (CSL_CHIP_DNUM);
    
        /* Compute the global address. */
        return (addr + (0x10000000 + (corenum * 0x1000000)));
    }
    
    
    /*-------------------------------------------------------------------------------------------------------------------------------------------------*/
    void clockHandler(UArg arg) {
        static unsigned int i=0;
        // post semaphore only after a second. i increments for every 1ms
        if (i++>1000)
        {
            System_printf("\r\nSemaphore posted\n");
            Semaphore_post(callbackSem);
            i=0;
            //System_printf("++Var %d\n", var);
        }
    }
    
    /*-------------------------------------------------------------------------------------------------------------------*/
    /*
     *  ======== UART write test ========
     *
     *  The test function tests read/write in blocking mode
     */
    static void UART_test_write(UART_Handle uart, bool dmaMode, unsigned char * data_to_send, uint16_t len)
    {
        uintptr_t        addrDataPrint;
    
        // Below data_to_send is a placeholder now.
        // later when UART has to send data it has to provide pointer of source to this and
        // code down takes care of sending the data with support of DMA
        //unsigned char   data_to_send[] = "New number filled for iteration -  \r\n";
        //static unsigned int i=0;
    
        //Modify the data every time the task executes
        //data_to_send[34] = (0x30+((i++)%9));
    
        if (uart != NULL) {
            if (dmaMode) {
                addrDataPrint = l2_global_address((uintptr_t)data_to_send);
            } else {
                addrDataPrint = (uintptr_t)data_to_send;
            }
    
            // wait until someone posts a semaphore to send the data
            //Semaphore_pend(callbackSem, SemaphoreP_WAIT_FOREVER);
    
            //Write the data packet now
            UART_write(uart, (void *)addrDataPrint, len);
    
        } else {
            //Not sure of the below code
            //Semaphore_delete(callbackSem);
            callbackSem = NULL;
        }
    }
    
    /*-------------------------------------------------------------------------------------------------------------------------------------------------*/
    void init_task(UArg arg0, UArg arg1) {
    
        Task_Handle task_uarti;
        Task_Params taskParams;
        UART_Handle      uart = NULL;
        UART_Params      uartParams;
        Error_Block eb;
        uint16 taskkey;
        uint32 delay=0, i=0;
        unsigned char data_to_tx[] = "New number filled for iteration -  \r\n";
        //uint32 data_to_tx = 0;
    
        System_printf("\nInitialization task begins here");
        //Call board init
        if (Board_initUART() == false)
        {
            System_printf("\nBoard_init UART failed!\n");
            //return(0);
        }
    
        //Call UART init
        UART_init();
    
        /* UART SoC init configuration */
        UART_initConfig(true);
    
        /* Initialize the default configuration params. */
        UART_Params_init(&uartParams);
        uartParams.parityType = uartParity;
    
        uart = UART_open(uartTestInstance, &uartParams);
    
        while (1)
        {
            data_to_tx[34] = (0x30+((i++)%9));
            //data_to_tx++;
            UART_test_write(uart, true, data_to_tx, sizeof(data_to_tx));
            /*Semaphore_pend(callbackSem, BIOS_WAIT_FOREVER);
            if(i++>10){
                System_printf("Exiting");
                System_exit(0);
            }*/
        }
    }
    
    /*-------------------------------------------------------------------------------------------------------------------------------------------------*/
    static void UART_test_print_test_desc(UART_Tests *test)
    {
        UART_Handle uart = NULL;
        UART_Params uartParams;
        char        testIdPrompt[] = "\r\nUART UT-r2-";
        char        crPrompt[] = "\r\n---------";
        char        testId[] = {0};
    
        /* UART SoC init configuration */
        UART_initConfig(false);
    
        /* Initialize the default configuration params. */
        UART_Params_init(&uartParams);
        uartParams.parityType = uartParity;
        uart = UART_open(uartTestInstance, &uartParams);
    
        /* Print unit test ID */
        sprintf(testId, "%d", test->testId);
        UART_write(uart, (void *)(uintptr_t)crPrompt, sizeof(crPrompt));
        UART_write(uart, (void *)(uintptr_t)testIdPrompt, sizeof(testIdPrompt));
        UART_write(uart, (void *)(uintptr_t)testId, sizeof(testId));
        UART_write(uart, (void *)(uintptr_t)crPrompt, sizeof(crPrompt));
    
        /* Print test description */
        UART_write(uart, (void *)(uintptr_t)test->testDesc, sizeof(test->testDesc));
        UART_write(uart, (void *)(uintptr_t)crPrompt, sizeof(crPrompt));
    
        UART_close(uart);
    }
    
    /*
     *  ======== main ========
     */
    /*-------------------------------------------------------------------------------------------------------------------*/
    Int main()
    {
        Task_Params taskParams;
        Task_Handle  init_taski, dummy_taski;
        SemaphoreP_Params semParams;
        Clock_Params clkParams;
        Clock_Handle myclk;
        Error_Block eb;
    
        // Initialization of Error block
        Error_init(&eb);
    
        System_printf("enter main()\n");
    
        //Initialize the task parameters
        Task_Params_init(&taskParams);
        taskParams.stackSize = 1024;
        taskParams.priority = 5;
        init_taski = Task_create((Task_FuncPtr)init_task, &taskParams, &eb);
        if (init_taski == NULL){
            System_printf("\n Init Task creation failed\n");
        }
    
    
        Clock_Params_init(&clkParams);
        // I believe this gives one msecond period
        clkParams.period = 1000;
        clkParams.startFlag = TRUE;
        myclk = Clock_create((Clock_FuncPtr)clockHandler, clkParams.period, &clkParams, &eb);
    
        /* Create call back semaphore */
        callbackSem = Semaphore_create(0, NULL, &eb);
    
        if(callbackSem == NULL){
            System_abort("Semaphore create failed!\n");
        }
    
        BIOS_start();    /* does not return */
        return(0);
    }
    

  • Rahul

    I made few changes to the code as specified below

    1. dmaMode is set to FALSE

    2. clkParams.period is changed to 100;

    3. removed the condition if (i++>10) in clockHandler function

    With these above changes I was able to send the data over UART and I could see the data on PuTTY as expected. I have few questions

    1. Enabling DMA with this setup does not cause the task to wait for sempahore

    2. ClkParams.period = 1 - as per documentation it gives in 1us resolution but I observed it to give 1ms resolution. is that right?

    Thanks in advance

  • Rahul,

    any update on the query?

    Regards,

    Nagaraju S

  • Nagaraju,

    With DMA mode enabled can you set a break point on the place where you are posting the semaphore to see if that is being called. you may also look at enabling system analyzer to see why  semaphore post is not working when DMA mode is enabled. System analyzer provides visualization of the RTOS scheduler and may help understand what is running after the semaphore post is done.

    I am not sure if this is caused due to some priority setting in your setup where the Task after the semaphore post is not able to pre-empt and start running since it is always at a lower priority.

    Regards,

    Rahul