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.

TMS320F28379D: PIEIER bit unexpectedly disabled

Part Number: TMS320F28379D
Other Parts Discussed in Thread: C2000WARE

Hello,

I have an application where three GPIO toggle events must be captured by their respective interrupt handlers. To enable the registers I use the following procedure (simplified):

- During startup, call the initialization function

#define GPIO_PIN_A 36
#define GPIO_PIN_B 37
#define GPIO_PIN_C 38

void init()
{
    // link xinput to xint
    InputXbarRegs.INPUT6SELECT = GPIO_PIN_A;
    InputXbarRegs.INPUT13SELECT = GPIO_PIN_B;
    InputXbarRegs.INPUT14SELECT = GPIO_PIN_C;

    // Attach isr handlers
    IntRegister(INT_XINT3, isrA);
    IntRegister(INT_XINT4, isrB);
    IntRegister(INT_XINT5, isrC);
}

- After initialization, the interrupts can be enabled or disabled by the user. The user has two interfaces to enable or disable the feature that uses the GPIOs (Start and Stop)

void start()
{
    // Disable XINT
    XINT_REGS.XINT3CR.bit.ENABLE = 0x0U;
    XINT_REGS.XINT4CR.bit.ENABLE = 0x0U;
    XINT_REGS.XINT5CR.bit.ENABLE = 0x0U;

    // Set prescaler in GPIO
    GpioCtrlRegs.GPBCTRL.bit.QUALPRD0 = 1;

    // Configure inputs as 3-Sample qualification
    GPIO_SetupPinOptions(GPIO_PIN_A, GPIO_INPUT, GPIO_QUAL3);
    GPIO_SetupPinMux(GPIO_PIN_A, GPIO_MUX_CPU1, 0);

    GPIO_SetupPinOptions(GPIO_PIN_B, GPIO_INPUT, GPIO_QUAL3);
    GPIO_SetupPinMux(GPIO_PIN_B, GPIO_MUX_CPU1, 0);

    GPIO_SetupPinOptions(GPIO_PIN_C, GPIO_INPUT, GPIO_QUAL3);
    GPIO_SetupPinMux(GPIO_PIN_C, GPIO_MUX_CPU1, 0);

    // Configure xint polarity bit
    XINT_REGS.XINT3CR.bit.POLARITY = 0x3U;
    XINT_REGS.XINT4CR.bit.POLARITY = 0x3U;
    XINT_REGS.XINT5CR.bit.POLARITY = 0x3U;

    // Enable XINT
    XINT_REGS.XINT3CR.bit.ENABLE = 0x1U;
    XINT_REGS.XINT4CR.bit.ENABLE = 0x1U;
    XINT_REGS.XINT5CR.bit.ENABLE = 0x1U;

    // Enable XINT in PIE
    IntEnable(INT_XINT3);
    IntEnable(INT_XINT4);
    IntEnable(INT_XINT5);
}

void stop()
{
    // Disable XINT in PIE
    IntDisable(INT_XINT3);
    IntDisable(INT_XINT4);
    IntDisable(INT_XINT5);

    // Disable xint
    XINT_REGS.XINT3CR.bit.ENABLE = (uint16_t)0x0U;
    XINT_REGS.XINT4CR.bit.ENABLE = (uint16_t)0x0U;
    XINT_REGS.XINT5CR.bit.ENABLE = (uint16_t)0x0U;
}

The problem is that sometimes, after startup and calling the function start(), the application seems to ignore real GPIO transitions. I configured two extra GPIOs as outputs to debug the ISR handlers and I can confirm that the ISR handler is not triggered. The user needs to call stop() and start() functions again to workaround the issue.  Besides, the isr attached to the GPIO interrupt with the last real transition is triggered. For example, if a real transition in the GPIO_PIN_B is lost, then the isrB handler is called after restarting the interrrupts.

Investigating a bit further, I discovered that when the issue appears, the PIEIER flag for the specified GPIOs is disabled at some point, and this happens without a prior call of the stop() function. That's why when the user reconfigure the interrupts with a stop()/start() process, everything works again.

I was not able to find any way in the code to disable PIEIER flags without calling the stop() function. Is there a way in which this flag can be reset for some reason?

BTW, the issue is not easy to reproduce, most of the times the startup sequence is ok. After restarting the interrupts again, the problem does not appear anymore.

Thanks for your help

Regards,

Luis

  • Hello Luis,

    Can you confirm that the entirety of your program is as described here (i.e. there is no other peripherals/functions used)? Also, can you show your ISR and how the interrupt flag gets cleared? The only way the PIEIER register would disable the interrupt is if either it was performed somewhere in software or the device was reset.

    Additionally, could you try and set a watchpoint to watch when the register changes? I believe it should be possible using the hardware watchpoint.

    Best regards,

    Omer Amir

  • Hi Omer,

    "Can you confirm that the entirety of your program is as described here (i.e. there is no other peripherals/functions used)? Also, can you show your ISR and how the interrupt flag gets cleared?"

    The application is much more complex and the codebase is too large to share. The code I shared is a simplification of the process, without the logic of the module that uses the interrupts. Many peripherals and other interrupts are used, but none in the PIE channel 12.

    Simplifying the ISR, it is something like this:

    void isrA()
    {
        // Some calculations but no handling of PIE registers or
        // other interrupt-related registers
        
        // Clear ACK bit
        PieCtrlRegs.PIEACK.all = PIEACK_GROUP12;
    }

    "The only way the PIEIER register would disable the interrupt is if either it was performed somewhere in software or the device was reset."

    That was the first suspicion, but I couldn't find other places in the code where the flag could be reset.

    "Additionally, could you try and set a watchpoint to watch when the register changes?"

    Another piece of information I forgot to say, is that the issue only appears when the device is mounted on the final application, because of this, is not possible to debug with JTAG, only with GPIOs.

    The issue happens about 5% of the time the device is power-cycled, and the startup sequence is always the same, I think it might be related to the external hardware (something with the power supply maybe?), but I don't know how the MCU could be affected internally by that.

  • Hello Luis,

    The application is much more complex and the codebase is too large to share.

    So in the example you provided there is nothing else running in your code except this GPIO interrupt problem correct? You want to make sure that the issue is as isolated as possible so you can find where the problem is coming from. Otherwise, it can be difficult to locate.

    Another piece of information I forgot to say, is that the issue only appears when the device is mounted on the final application, because of this, is not possible to debug with JTAG, only with GPIOs.

    You can monitor the external pins such as the XRSn to check for when resets are occurring.

    The issue happens about 5% of the time the device is power-cycled, and the startup sequence is always the same, I think it might be related to the external hardware (something with the power supply maybe?), but I don't know how the MCU could be affected internally by that.

    Yes, if there are times when the power supply isn't meeting our datasheet specifications then issues like resets and other problems can occur. You will need to scope your supplies and verify this with the datasheet.

    Best regards,

    Omer Amir

  • Hi Omer,

    So in the example you provided there is nothing else running in your code except this GPIO interrupt problem correct? You want to make sure that the issue is as isolated as possible so you can find where the problem is coming from. Otherwise, it can be difficult to locate.

    Correct, I am simplifying the code flow to isolate the issue. Still, the application is running with no modifications more than the GPIOs I am using to debug.

    Yes, if there are times when the power supply isn't meeting our datasheet specifications then issues like resets and other problems can occur. You will need to scope your supplies and verify this with the datasheet.

    Ok! will try that. In any case, do you have any other idea of some other event that could cause undefined behavior in the MCU or something like that?

    Regards,

    Luis

  • Hello Luis,

    In any case, do you have any other idea of some other event that could cause undefined behavior in the MCU or something like that?

    Unfortunately this is a very vague question with many possible answers; operating a device outside what is specified in the device's datasheet is one of the main factors that can produce undesirable behavior (you can look at the Absolute Maximum Ratings, Recommended Operating Conditions, and Electrical Characteristics tables for the more clear guidelines). Besides that, I'm not familiar with many other things that could cause a specific situation (unless there is something laid out in the errata for this, which you can always take a look at). This would have to be done on a case-by-case basis.

    If you suspect there is something in your setup (physically or in software) that may be causing undefined behavior, you can try setting up a project with a known working C2000Ware example and a normal physical setup that follows the datasheet (i.e. room temperature, no noisy devices or sources of ESD nearby, using a F2837xD ControlCARD, etc.). Then one-by-one you can add in the factors of your real setup that you plan to deploy the device in, this should help locate any possible sources of undesirable behavior.

    Best regards,

    Omer Amir