cancel
Showing results for 
Search instead for 
Did you mean: 

HardFault Exception

za kia
Associate II

Can someone translate this, and dumb it down for me a little please?

I am just trying to get my very basic, very simple SPI slave to receive a bunch of bytes from a PC application using interrupts.

After receiving the first byte the code goes into the infinite loop in the HardFault_Handler() function.

If I pause the program before any bytes have come, then the program acts normally. However, if I pause execution after 6 bytes of data, then I find myself inside that infinite loop. And I can see that only a single byte has been read.

But then why is PC zero?

I did not touch any HAL libraries. And I will paste you my code at the end.

I am using:

. STM32L4R7VIT

. IAR for ARM 8.30.1.17148

Thank you very much.

Fault Exception Viewer:

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

The processor has escalated a configurable-priority exception to HardFault.

An instruction executed with an invalid EPSR.T or EPSR.IT field (CFSR.INVSTATE).

Exception occured at PC = 0x0, LR = 0x80066b7

See the call stack for more information.

Call Stack:

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

HardFault_Handler

<Exception frame>

[PC = 0x00000000]

My Code:

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

extern SPI_HandleTypeDef hspi1;
 
void init_spi(void)
{
    hspi1.Instance                  = SPI1;
    hspi1.Init.Mode                 = SPI_MODE_SLAVE;
    hspi1.Init.Direction            = SPI_DIRECTION_2LINES;
    hspi1.Init.DataSize             = SPI_DATASIZE_8BIT;
    hspi1.Init.CLKPolarity          = SPI_POLARITY_HIGH;
    hspi1.Init.CLKPhase             = SPI_PHASE_2EDGE;
    hspi1.Init.NSS                  = SPI_NSS_HARD_INPUT;
 // hspi1.Init.BaudRatePrescaler    = SPI_BAUDRATEPRESCALER_128;
    hspi1.Init.FirstBit             = SPI_FIRSTBIT_MSB;
    hspi1.Init.TIMode               = SPI_TIMODE_DISABLE;
    hspi1.Init.CRCCalculation       = SPI_CRCCALCULATION_DISABLE;
    hspi1.Init.CRCPolynomial        = 7;
    hspi1.Init.CRCLength            = SPI_CRC_LENGTH_DATASIZE;
    hspi1.Init.NSSPMode             = SPI_NSS_PULSE_DISABLE;
    hspi1.RxISR                     = spi1_int_handler;
    if (HAL_SPI_Init(&hspi1) != HAL_OK)
    {
        _Error_Handler(__FILE__, __LINE__);
    }
 
    SET_BIT((hspi1.Instance->CR2), SPI_RXFIFO_THRESHOLD_QF);
    
    __HAL_SPI_ENABLE(&hspi1);
 
    __HAL_SPI_ENABLE_IT (&hspi1, SPI_IT_RXNE);
    __HAL_SPI_DISABLE_IT(&hspi1, SPI_IT_TXE);
    __HAL_SPI_ENABLE_IT (&hspi1, SPI_IT_ERR);
 
    // Enable the SPI global interrupt.
       HAL_NVIC_EnableIRQ(SPI1_IRQn);
}
 
void spi1_int_handler(SPI_HandleTypeDef *hspi)
{
    HAL_SPI_Receive(hspi, &rx_byte, 1, 1000);
    debug_buf[debug_buf_ix++] = rx_byte;
}

3 REPLIES 3

Suggests you don't have a SPI1_IRQHandler() function set up properly.

Likely not the code you're actually showing..

but would scope the access to debug_buf[] so it doesn't go off the reservation.

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
za kia
Associate II

Thanks very much for your attention.

I already made this correction to my original post, and in the code:

__HAL_SPI_ENABLE_IT (&hspi1, SPI_IT_RXNE);

 ...

However, I changed the code to read data in a while loop, which for my application makes more sense than interrupts and which alleviates the problem. Besides, I wasn't able to get the interrupts working anyway. I wish there was a code example on the ST site that showed basic SPI operation.

Later on I will experiment with the code again and let you know if the problem shows up again.

Thanks a lot,

Za

T J
Lead

Yes, I agree with @Community member​ this line looks suspect..

debug_buf[debug_buf_ix++] = rx_byte;

where do you check that debug_buf_ix is not out of range ?

normally:

debug_buf_ix++;

if ( debug_buf_ix > 1000) debug_buf_ix =0; //circular buffer.