cancel
Showing results for 
Search instead for 
Did you mean: 

Hi, I have an application with STM32G431RB, using both ADCs. How can I tell which one of the two ADCs called an interruption like this: void HAL_ADCEx_InjectedConvCpltCallback(ADC_HandleTypeDef *hadc)

JFRAN.1
Associate II
1 ACCEPTED SOLUTION

Accepted Solutions
JFRAN.1
Associate II

Hello, thanks a lot for your answers, I implement it in a different way with your recommendations and is now working fine:

void HAL_ADCEx_InjectedConvCpltCallback(ADC_HandleTypeDef *hadc)

{

// Voltage1 = HAL_ADCEx_InjectedGetValue(&hadc1, ADC_INJECTED_RANK_2); // L1 VOLTAGE

if (hadc->Instance == ADC1)

{

Line1[0] += ADC1->JDR1; // Gets L1 Current. ADC1 Channel 1. PA0 pin

Line1[1] += ADC1->JDR2; // Gets L1 Voltage. ADC1 Channel 9. PC3 pin

Line1[2] += ADC1->JDR3; // Gets IGBT Temperature. ADC1 Channel 7. PC1 pin

Line1[3] += ADC1->JDR4; // Gets BUS Voltage. ADC1 Channel 2. PA1 pin

samples1++;

if (samples1 >= L1_SAMP)

{

samples1 = 0;

CalcLine1AVG();

}

HAL_ADCEx_InjectedStop_IT(&hadc1);

}

else if (hadc->Instance == ADC2)

{

Line2[0] += ADC2->JDR1; // Gets L1 Voltage. ADC1 Channel 9. PC3 pin

HAL_ADCEx_InjectedStop_IT(&hadc2);

samples2++;

if (samples2 >= L2_SAMP)

{

samples2 = 0;

CalcLine2AVG();

}

}

}

View solution in original post

5 REPLIES 5
TDK
Guru

Check if the value of hadc->Instance is ADC1 or ADC2.

If you feel a post has answered your question, please click "Accept as Solution".
JFRAN.1
Associate II

Hello TDK, thanks a lot for your answer, I don'T know what is wrong or if I didn't undestood you; but I tried what you said and it didn't worked. ADC1 is triggered with a PWM signal generated by timer 1 and ADC2 is is triggered with a PWM signal generated by timer 8. I have something like this:

HAL_ADCEx_InjectedStart_IT(&hadc1); // Enables ADC1 to start convertion when timer 1 triggered it

HAL_ADCEx_InjectedStart_IT(&hadc2); // Enables ADC2 to start convertion when timer 8 triggered it

void HAL_ADCEx_InjectedConvCpltCallback(ADC_HandleTypeDef *hadc)

{

HAL_UART_Transmit_IT(&huart2, "CALLED \r\n", 9); //Just to know if enters here

if (hadc->Instance == ADC1)

{

Line1[0] += ADC1->JDR1; // Gets L1 Current. ADC1 Channel 1. PA0 pin

Line1[1] += ADC1->JDR2; // Gets L1 Voltage. ADC1 Channel 9. PC3 pin

Line1[2] += ADC1->JDR3; // Gets IGBT Temperature. ADC1 Channel 7. PC1 pin

samples1++;

HAL_UART_Transmit_IT(&huart2, "PROCESSED1\r\n", 11); //Just to know if enters here

HAL_ADCEx_InjectedStop_IT(&hadc1);

}

else if (hadc->Instance == ADC2)

{

Line2[0] += ADC2 ->JDR1; // Gets L1 Current. ADC1 Channel 1. PA0 pin

Line2[1] += ADC2->JDR2; // Gets L1 Voltage. ADC1 Channel 9. PC3 pin

samples2++;

HAL_UART_Transmit_IT(&huart2, "PROCESSED2\r\n", 11); //Just to know if enters here

HAL_ADCEx_InjectedStop_IT(&hadc1);

}

}

I have a signal connected to EXTI15 to simulate. When I run the code it prints "CALLED". It indicates that injected conversion was complete. But never prints "PROCESSED1", neither "PROCESSED2". If I take out the if statement: if (hadc->Instance == ADC1)

it works fine (and I can see the converted values), but I need some way to know wich one of the two ADCs called the interruption.

TDK
Guru

That is what I suggested.

> It didn't worked.

> But never prints "PROCESSED1", neither "PROCESSED2" 

If by "didn't worked" you mean it's not outputting PROCESSED1 or PROCESSED2:

You're calling HAL_UART_Transmit_IT multiple times in succession. The later ones have no effect because the peripheral is still busy processing the first call. You could use blocking mode instead but doing long things within an interrupt is not ideal.

Use a better method to determine what the code is doing. Set a breakpoint in HAL_ADCEx_InjectedConvCpltCallback and step through. Verify hadc->Instance refers to ADC1 or ADC2.

Also:

else if (hadc->Instance == ADC2)
{
...
HAL_ADCEx_InjectedStop_IT(&hadc1);
}

You're using the wrong hadc here, which suggests it either isn't needed or your code won't work the way you intend.

If you feel a post has answered your question, please click "Accept as Solution".
Piranha
Chief II

And if ADC1 and ADC2 have different interrupt priorities or UART functions are also called from any other interrupt with different priority, then, because HAL bloatware is not interrupt safe, such code will mess up UART state completely...

JFRAN.1
Associate II

Hello, thanks a lot for your answers, I implement it in a different way with your recommendations and is now working fine:

void HAL_ADCEx_InjectedConvCpltCallback(ADC_HandleTypeDef *hadc)

{

// Voltage1 = HAL_ADCEx_InjectedGetValue(&hadc1, ADC_INJECTED_RANK_2); // L1 VOLTAGE

if (hadc->Instance == ADC1)

{

Line1[0] += ADC1->JDR1; // Gets L1 Current. ADC1 Channel 1. PA0 pin

Line1[1] += ADC1->JDR2; // Gets L1 Voltage. ADC1 Channel 9. PC3 pin

Line1[2] += ADC1->JDR3; // Gets IGBT Temperature. ADC1 Channel 7. PC1 pin

Line1[3] += ADC1->JDR4; // Gets BUS Voltage. ADC1 Channel 2. PA1 pin

samples1++;

if (samples1 >= L1_SAMP)

{

samples1 = 0;

CalcLine1AVG();

}

HAL_ADCEx_InjectedStop_IT(&hadc1);

}

else if (hadc->Instance == ADC2)

{

Line2[0] += ADC2->JDR1; // Gets L1 Voltage. ADC1 Channel 9. PC3 pin

HAL_ADCEx_InjectedStop_IT(&hadc2);

samples2++;

if (samples2 >= L2_SAMP)

{

samples2 = 0;

CalcLine2AVG();

}

}

}