초보의 아웅다웅 설계하기/STM32

STM32 PID 제어

로망와니 2020. 1. 16. 19:58

 

ADC로 전류값을 읽어온 후 180mA로 타겟값을 맞췄습니다. (미제어시 125mA ~ 170mA 정도 소요)

=> arm에서 제공하는 arm_cortexMxxx_math.lib를 사용

 

 

#define TAGET_ADC 1000

 

void PID_ADC(uint8_t *chpADC, uint8_t chSize)
{
Get_RAWADC(s_chpBuf[s_ADCpointer++]);
PID_CurrentControl(Average(s_chpBuf, ADCCNT, 1), TAGET_ADC);

if(s_ADCpointer >= ADCCNT){
s_ADCpointer = 0;
}
}

 

/*******************************************************************************
* Function Name : 
* Parameters    : None
* Return        : None
* Description   : 
*******************************************************************************/
void Display(void)
{
DEBUGPRINT("ADC_Volt %d, %fV, ", Average(s_chpBuf, ADCCNT, 0), Voltage_Calc(Average(s_chpBuf, ADCCNT, 0)));
DEBUGPRINT("ADC_Curr %d, %fA, ", Average(s_chpBuf, ADCCNT, 1), Current_Calc(Average(s_chpBuf, ADCCNT, 1)));
DEBUGPRINT("ADC_Temp %d, %d \r\n", Average(s_chpBuf, ADCCNT, 2), __LL_ADC_CALC_TEMPERATURE(3300, Average(s_chpBuf, ADCCNT, 2), LL_ADC_RESOLUTION));
}

 

/*******************************************************************************
* Function Name : 
* Parameters    : None
* Return        : None
* Description   : 
*******************************************************************************/
void Set_DutyCycle(uint32_t D)
{
  uint32_t P;    /* Pulse duration */

if(D == 0){
LL_TIM_OC_SetCompareCH1(TIM1, PWMRANGE);
}
else{
P = PWMRANGE - D;
LL_TIM_OC_SetCompareCH1(TIM1, P);
}
}

 


/* Includes ------------------------------------------------------------------*/
#include "usr_pid.h"
#include "usr_usart.h"
#include "usr_timer.h"
#include "usr_system.h"

/* Private variables ---------------------------------------------------------*/
arm_pid_instance_f32 PID_Current;

/* Current */
#define PID_PARAM_KP 100         /* Proporcional */
#define PID_PARAM_KI 0.2        /* Integral */
#define PID_PARAM_KD 10            /* Derivative */

/* Private macro -------------------------------------------------------------*/
/* Private typedef -----------------------------------------------------------*/
/* Private define ------------------------------------------------------------*/
/* Private function prototypes -----------------------------------------------*/

 


/*******************************************************************************
* Function Name : 
* Parameters    : None
* Return        : None
* Description   : 
*******************************************************************************/
void Config_PID(void)
{
/* Set this for your needs */
PID_Current.Kp = PID_PARAM_KP;        /* Proporcional */
PID_Current.Ki = PID_PARAM_KI;        /* Integral */
PID_Current.Kd = PID_PARAM_KD;        /* Derivative */
/* Initialize PID system, float32_t format */
arm_pid_init_f32(&PID_Current, 1);
}


/*******************************************************************************
* Function Name : 
* Parameters    : None
* Return        : None
* Description   : 
*******************************************************************************/
void PID_CurrentControl(float a_fCurr, float a_fTargetCurr)
{
float pid_error = 0;
/* Duty cycle for PWM */
float duty = 0;

/* Calculate error */
pid_error = a_fTargetCurr - a_fCurr; 

/* Calculate PID here, argument is error */
/* Output data will be returned, we will use it as duty cycle parameter */
duty = arm_pid_f32(&PID_Current, pid_error);

Set_DutyCycle(duty);
}