forked from achamaikin/CCSModuleSW30Web
if it breaks, I’m in the mountains
This commit is contained in:
115
Core/Src/cp.c
Normal file
115
Core/Src/cp.c
Normal file
@@ -0,0 +1,115 @@
|
||||
#include "cp.h"
|
||||
#include "adc.h"
|
||||
#include "board.h"
|
||||
#include "tim.h"
|
||||
#include <stdint.h>
|
||||
|
||||
#define MAX_DUTY 450
|
||||
|
||||
static int32_t cp_voltage_mv = 0;
|
||||
static uint8_t cp_duty = 0;
|
||||
CP_State_t fake_cp_state = EV_STATE_ACQUIRING;
|
||||
|
||||
static uint32_t CP_ReadAdcChannel(uint32_t ch) {
|
||||
uint32_t adc = 0;
|
||||
|
||||
ADC_Select_Channel(ch);
|
||||
HAL_ADC_Start(&hadc1);
|
||||
HAL_ADC_PollForConversion(&hadc1, 10);
|
||||
adc = HAL_ADC_GetValue(&hadc1);
|
||||
HAL_ADC_Stop(&hadc1);
|
||||
|
||||
return adc;
|
||||
}
|
||||
#define VREFINT_CAL_ADDR ((uint16_t*)0x1FFFF7BA) // для STM32F1!
|
||||
|
||||
static int32_t CP_ReadVoltageMv(void)
|
||||
{
|
||||
uint32_t adc = 0;
|
||||
int32_t v_adc_mv = 0;
|
||||
int32_t v_out_mv = 0;
|
||||
|
||||
adc = CP_ReadAdcChannel((uint32_t)4u);
|
||||
v_adc_mv = (int32_t)((adc * 3300u) / 4095u);
|
||||
v_out_mv = ((v_adc_mv - 1723) * 1000) / 130;
|
||||
|
||||
return v_out_mv;
|
||||
}
|
||||
|
||||
void CP_Init(void) {
|
||||
/* TIM3_CH2 (PA7): set 1kHz PWM like original CCS logic. */
|
||||
htim3.Instance->PSC = 160 - 1;
|
||||
htim3.Instance->ARR = MAX_DUTY - 1;
|
||||
|
||||
#if DUTY_INVERT == 0
|
||||
htim3.Instance->CCR2 = MAX_DUTY;
|
||||
htim3.Instance->CCR1 = MAX_DUTY + 5;
|
||||
#else
|
||||
htim3.Instance->CCR2 = 0;
|
||||
htim3.Instance->CCR1 = 0;
|
||||
#endif
|
||||
|
||||
HAL_TIM_PWM_Start(&htim3, TIM_CHANNEL_2);
|
||||
HAL_TIM_OC_Start_IT(&htim3, TIM_CHANNEL_1);
|
||||
}
|
||||
|
||||
void CP_SetDuty(uint8_t percentage) {
|
||||
uint32_t pwmduty = MAX_DUTY * percentage / 100;
|
||||
cp_duty = percentage;
|
||||
|
||||
#if DUTY_INVERT == 0
|
||||
htim3.Instance->CCR2 = pwmduty;
|
||||
htim3.Instance->CCR1 = 0 + 1;
|
||||
#else
|
||||
htim3.Instance->CCR2 = MAX_DUTY - pwmduty;
|
||||
htim3.Instance->CCR1 = MAX_DUTY - pwmduty + 5;
|
||||
#endif
|
||||
}
|
||||
|
||||
uint8_t CP_GetDuty(void) {
|
||||
return cp_duty;
|
||||
}
|
||||
|
||||
int32_t CP_GetVoltage(void) {
|
||||
return cp_voltage_mv;
|
||||
}
|
||||
|
||||
CP_State_t CP_GetState(void) {
|
||||
int32_t voltage_real = cp_voltage_mv;
|
||||
|
||||
if(fake_cp_state != EV_STATE_ACQUIRING) {
|
||||
return fake_cp_state;
|
||||
}
|
||||
|
||||
if (voltage_real >= (12000-1000)) {
|
||||
return EV_STATE_A_IDLE;
|
||||
} else if (voltage_real >= (9000-1000) && voltage_real <= (9000+1000)) {
|
||||
return EV_STATE_B_CONN_PREP;
|
||||
} else if (voltage_real >= (6000-1000) && voltage_real <= (6000+1000)) {
|
||||
return EV_STATE_C_CONN_ACTIVE;
|
||||
} else if (voltage_real >= (3000-1000) && voltage_real <= (3000 + 1000)) {
|
||||
return EV_STATE_D_CONN_ACT_VENT;
|
||||
} else if (voltage_real >= (0-1000) && voltage_real <= (0+2000)){
|
||||
return EV_STATE_E_NO_POWER;
|
||||
} else if (voltage_real <= (-12000+1000)) {
|
||||
return EV_STATE_F_ERROR;
|
||||
} else {
|
||||
return EV_STATE_ACQUIRING;
|
||||
}
|
||||
}
|
||||
|
||||
void CP_Loop(void) {
|
||||
(void)CP_GetState();
|
||||
}
|
||||
|
||||
void HAL_TIM_OC_DelayElapsedCallback(TIM_HandleTypeDef *htim)
|
||||
{
|
||||
if (htim->Instance == TIM3 && htim->Channel == HAL_TIM_ACTIVE_CHANNEL_1) {
|
||||
if (ADC_TryLock() == 0u) {
|
||||
return;
|
||||
}
|
||||
cp_voltage_mv = CP_ReadVoltageMv();
|
||||
ADC_Unlock();
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user