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.

Task_sleep runs fine for a while, then never returns...

Other Parts Discussed in Thread: MSP430F5638, SYSBIOS

This is a very strange problem.

I have a motor control app running on an MSP430F5638.  It will run brilliantly for a while, then suddenly every single Task_sleep() fails to return.

I've grepped through the code to see if I'm stepping on any used timers, but everything appears fine.  I can't find any memory over-writes, or any stack overflows, or anything that might cause mayhem and chaos.

The fact that it'll run fine for about 2-3 minutes is suspicious.

HOWEVER -the system heartbeat timer routine still runs, so SOMETHING is still sane and doesn't kill every timer on the chip.

I looked into each tasks info using ROV, I see the blocked on Task_sleep(but the number in the parents is HUGE.  I'm passing #define values in, so this seems suspect.

Does anyone have any pointers as to where I might look next?  This is kind of a showstopper..

All help appreciated!

Ed Averill

  • Ed,

    Which version of TI-RTOS are you using?
    Can you post your .cfg file?

    Alan
  • TI-RTOS 2.10.1.38, SYS/BIOS 6.41.1.36.

    My config:

    var Defaults = xdc.useModule('xdc.runtime.Defaults');
    var Diags = xdc.useModule('xdc.runtime.Diags');
    var Error = xdc.useModule('xdc.runtime.Error');
    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.family.msp430.Hwi');
    var ti_sysbios_hal_Hwi = xdc.useModule('ti.sysbios.hal.Hwi');
    var Mailbox = xdc.useModule('ti.sysbios.knl.Mailbox');
    var Timer = xdc.useModule('ti.sysbios.hal.Timer');
    var Power = xdc.useModule('ti.sysbios.family.msp430.Power');
    var Queue = xdc.useModule('ti.sysbios.knl.Queue');
    var ClockFreqs = xdc.useModule('ti.sysbios.family.msp430.ClockFreqs');
    var Boot = xdc.useModule('ti.catalog.msp430.init.Boot');
    var ti_sysbios_family_msp430_Timer = xdc.useModule('ti.sysbios.family.msp430.Timer');
    
    /*
     * 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 = 4096;
    
    /*
     * Build a custom SYS/BIOS library from sources.
     */
    BIOS.libType = BIOS.LibType_Debug;
    
    /* System stack size (used by ISRs and Swis) */
    Program.stack = 2304;
    
    /* Circular buffer size for System_printf() */
    SysMin.bufSize = 0x200;
    
    System.SupportProxy = SysMin;
    
    ti_sysbios_hal_Hwi.dispatcherAutoNestingSupport = false;
    BIOS.cpuFreq.lo = 16000000;
    Task.defaultStackSize = 512;
    Task.idleTaskStackSize = 256;
    Task.enableIdleTask = true;
    var timer0Params = new Timer.Params();
    timer0Params.instance.name = "null";
    timer0Params.period = 100000;
    var myTimer = Timer.create(2, "&myTimerISR", timer0Params);
    BIOS.logsEnabled = false;
    var semaphore2Params = new Semaphore.Params();
    semaphore2Params.instance.name = "FLASH_sem";
    semaphore2Params.mode = Semaphore.Mode_BINARY;
    Program.global.FLASH_sem = Semaphore.create(1, semaphore2Params);
    var mailbox1Params = new Mailbox.Params();
    mailbox1Params.instance.name = "mbox_log";
    Program.global.mbox_log = Mailbox.create(24, 12, mailbox1Params);
    Task.deleteTerminatedTasks = true;
    var ti_sysbios_hal_Hwi0Params = new ti_sysbios_hal_Hwi.Params();
    ti_sysbios_hal_Hwi0Params.instance.name = "UART_A0";
    Program.global.UART_A0 = ti_sysbios_hal_Hwi.create(56, "&UART_TxRx", ti_sysbios_hal_Hwi0Params);
    BIOS.assertsEnabled = false;
    Defaults.common$.diags_ASSERT = Diags.ALWAYS_OFF;
    Error.policy = Error.UNWIND;
    Error.maxDepth = 5;
    var mailbox1Params0 = new Mailbox.Params();
    mailbox1Params0.instance.name = "mbox_cal";
    Program.global.mbox_cal = Mailbox.create(24, 2, mailbox1Params0);
    var mailbox2Params = new Mailbox.Params();
    mailbox2Params.instance.name = "mbox_ui";
    Program.global.mbox_ui = Mailbox.create(24, 4, mailbox2Params);
    var mailbox3Params = new Mailbox.Params();
    mailbox3Params.instance.name = "mbox_rs485";
    Program.global.mbox_rs485 = Mailbox.create(24, 2, mailbox3Params);
    var mailbox4Params = new Mailbox.Params();
    mailbox4Params.instance.name = "mbox_net";
    Program.global.mbox_net = Mailbox.create(24, 2, mailbox4Params);
    var task0Params = new Task.Params();
    task0Params.instance.name = "startAPP";
    task0Params.stackSize = 512;
    Program.global.startAPP = Task.create("&STARTUPTask", task0Params);
    var semaphore1Params = new Semaphore.Params();
    semaphore1Params.instance.name = "ULHealthScan_sem";
    semaphore1Params.mode = Semaphore.Mode_BINARY;
    Program.global.ULHealthScan_sem = Semaphore.create(null, semaphore1Params);
    var mailbox5Params = new Mailbox.Params();
    mailbox5Params.instance.name = "mbox_usb";
    Program.global.mbox_usb = Mailbox.create(24, 4, mailbox5Params);
    var semaphore2Params0 = new Semaphore.Params();
    semaphore2Params0.instance.name = "USBIn_sem";
    Program.global.USBIn_sem = Semaphore.create(null, semaphore2Params0);
    Power.idle = true;
    Power.allowDynamicMode = true;
    Semaphore.supportsEvents = true;
    Memory.defaultHeapSize = 3000;
    Defaults.common$.diags_INTERNAL = Diags.ALWAYS_OFF;
    var hwi0Params = new Hwi.Params();
    hwi0Params.instance.name = "RTCHwi";
    Program.global.RTCHwi = Hwi.create(42, "&RTC_Handle_Interrupts", hwi0Params);
    BIOS.customCCOpts = "-vmspx --near_data=none --code_model=large --data_model=restricted -q --advice:power=1  --program_level_compile -g";
    var ti_sysbios_hal_Hwi2Params = new ti_sysbios_hal_Hwi.Params();
    ti_sysbios_hal_Hwi2Params.instance.name = "PORT4_GPIO";
    Program.global.PORT4_GPIO = ti_sysbios_hal_Hwi.create(37, "&Port4_IRQ", ti_sysbios_hal_Hwi2Params);
    var ti_sysbios_hal_Hwi4Params = new ti_sysbios_hal_Hwi.Params();
    ti_sysbios_hal_Hwi4Params.instance.name = "PORT1_IRQ";
    Program.global.PORT1_IRQ = ti_sysbios_hal_Hwi.create(47, "&Port1_IRQ", ti_sysbios_hal_Hwi4Params);
    Clock.swiPriority = 12;
    Clock.timerId = -1;
    var ti_sysbios_hal_Hwi5Params = new ti_sysbios_hal_Hwi.Params();
    ti_sysbios_hal_Hwi5Params.instance.name = "ADC12_INT";
    Program.global.ADC12_INT = ti_sysbios_hal_Hwi.create(54, "&ADC12_IRQ", ti_sysbios_hal_Hwi5Params);
    var ti_sysbios_hal_Hwi6Params = new ti_sysbios_hal_Hwi.Params();
    ti_sysbios_hal_Hwi6Params.instance.name = "PORT2_IRQ";
    Program.global.PORT2_IRQ = ti_sysbios_hal_Hwi.create(44, "&Port2_IRQ", ti_sysbios_hal_Hwi6Params);
    var ti_sysbios_hal_Hwi7Params = new ti_sysbios_hal_Hwi.Params();
    ti_sysbios_hal_Hwi7Params.instance.name = "PORT3_IRQ";
    Program.global.PORT3_IRQ = ti_sysbios_hal_Hwi.create(38, "&Port3_IRQ", ti_sysbios_hal_Hwi7Params);
    var ti_sysbios_hal_Hwi8Params = new ti_sysbios_hal_Hwi.Params();
    ti_sysbios_hal_Hwi8Params.instance.name = "NMI_01";
    Program.global.NMI_01 = ti_sysbios_hal_Hwi.create(61, "&NMI_IRQ", ti_sysbios_hal_Hwi8Params);
    var ti_sysbios_hal_Hwi9Params = new ti_sysbios_hal_Hwi.Params();
    ti_sysbios_hal_Hwi9Params.instance.name = "System_NMI";
    Program.global.System_NMI = ti_sysbios_hal_Hwi.create(62, "&System_IRQ", ti_sysbios_hal_Hwi9Params);
    var ti_sysbios_hal_Hwi9Params0 = new ti_sysbios_hal_Hwi.Params();
    ti_sysbios_hal_Hwi9Params0.instance.name = "USBIRQ";
    ti_sysbios_hal_Hwi9Params0.enableInt = true;
    Program.global.USBIRQ = ti_sysbios_hal_Hwi.create(51, "&iUsbInterruptHandler", ti_sysbios_hal_Hwi9Params0);
    ti_sysbios_hal_Hwi.checkStackFlag = true;
    var ti_sysbios_hal_Hwi10Params = new ti_sysbios_hal_Hwi.Params();
    ti_sysbios_hal_Hwi10Params.instance.name = "TB0_IRQ";
    Program.global.TB0_IRQ = ti_sysbios_hal_Hwi.create(58, "&TB0_General", ti_sysbios_hal_Hwi10Params);
    ClockFreqs.SMCLK = 16384000;
    ClockFreqs.ACLK = 32768;
    Clock.tickPeriod = 1000;
    Clock.tickSource = Clock.TickSource_TIMER;
    var semaphore3Params = new Semaphore.Params();
    semaphore3Params.instance.name = "IOEXPANDER_sem";
    Program.global.IOEXPANDER_sem = Semaphore.create(null, semaphore3Params);
    

    I'm also looking into a potential memory/stack issue involving long math, worth a shot.

    Hope that helps!

    Ed Averill

  • Your .cfg file indicates that you are calling Clock_tick() from your own timer interrupt.

    Have you confirmed that this timer is still firing?

    Task_sleep(), and all APIs with timeouts depend on Clock_tick() getting called.

    Alan
  • Also, are you certain that Clock_tick() is being called once per millisecond?
    I couldn't tell from your configuration which timer was providing the 1KHz interrupt.
  • Sorry about the late reply - I was out sick yesterday.

    I'll dig further into the config - the weird thing is, it works for a while, then dies, which seems like a corruption issue of some kind.  Someone somewhere has some timer working right.. just need to figure out where it's coming from.

    Thanks for the help.. one I discover what's happening, I'll post iot here, it might help others!

    Ed Averill

  • Update: now moving to the latest version of TI-RTOS to make sure this isn't something previously fixed.
  • Ok, new TI-RTOS made zero difference.

    I also have the "Internally configure a timer to call ClockTick()" radio button selected in my "Timer Base" screen in the SYSBIOS/Scheduling/
    Clock Module panel of my graphic configuration utility, so that's why it works at first.

    Still no clue as to why it loses its marbles, though.
  • By turning on heap checking, stack checking, and asserts, I discovered that I was running out of heap and this was somehow corrupting Task_sleep() and locking it up forever. I've now run into a different error, so I can close this one out for now.