Compare commits
2 Commits
67be0b2304
...
7286f33709
| Author | SHA1 | Date | |
|---|---|---|---|
| 7286f33709 | |||
| 9b4ccd63b0 |
Binary file not shown.
@ -1 +1 @@
|
||||
Subproject commit a6b27da4ce1d3cf60a251225beff3e6d0af1193e
|
||||
Subproject commit 795ebbd220fd16ba9db4d1c071ed66700c2df928
|
||||
@ -27,6 +27,8 @@
|
||||
#define UPP_DISABLE_PROTECT_BOARDPOWER ///< Отключить проверки питания плат (+24, +5 В)
|
||||
#define UPP_DISABLE_PROTECT_LOSS_PHASE ///< Отключить проверки на потерянные фазы
|
||||
|
||||
#define ZC_DISABLE_HYSTERESIS_DEBOUNCE ///< Отключить гиситерезис и дребезг на определении перехода через ноль
|
||||
|
||||
/** //UPP_PARAMS_TEST
|
||||
* @}
|
||||
*/
|
||||
|
||||
@ -7,36 +7,49 @@
|
||||
******************************************************************************/
|
||||
#include "adc_tools.h"
|
||||
|
||||
static void ADC_EnableAllFilters(ADC_Periodic_t *adc)
|
||||
{
|
||||
for(int i = 0; i < ADC_NUMB_OF_CHANNELS; i++)
|
||||
{
|
||||
Filter_Start(&adc->filter[i]);
|
||||
// FilterExpInt_Process(&adc->filter[i], adc->Coefs[i].lZero);
|
||||
}
|
||||
}
|
||||
static void ADC_InitAllFilters(ADC_Periodic_t *adc)
|
||||
{
|
||||
// Filter_Init(&adc->filter[ADC_CHANNEL_UBA], coefs_biquad_U);
|
||||
// Filter_Init(&adc->filter[ADC_CHANNEL_UAC], coefs_biquad_U);
|
||||
// Filter_Init(&adc->filter[ADC_CHANNEL_IC], coefs_biquad_I);
|
||||
// Filter_Init(&adc->filter[ADC_CHANNEL_IA], coefs_biquad_I);
|
||||
// Filter_Init(&adc->filter[ADC_CHANNEL_TEMP1], coefs_biquad_T);
|
||||
// Filter_Init(&adc->filter[ADC_CHANNEL_TEMP2], coefs_biquad_T);
|
||||
|
||||
for(int i = 0; i < ADC_NUMB_OF_CHANNELS; i++)
|
||||
// FilterBandPassDerivative_Init(&adc->u_fltr[U_AB], (50.0f*PM_FAST_PERIOD_US/1000000), 0.1);
|
||||
// FilterBandPassDerivative_Init(&adc->u_fltr[U_CA], (50.0f*PM_FAST_PERIOD_US/1000000), 0.1);
|
||||
//
|
||||
// FilterMedianInt_Init(&adc->i_fltr[I_C], 5, 2048);
|
||||
// FilterMedianInt_Init(&adc->i_fltr[I_A], 5, 2048);
|
||||
//
|
||||
// FilterLUT_Init(&adc->temp_map[TEMP_1],
|
||||
// (float *)adc_temp_quants,
|
||||
// (float *)adc_temp_vals,
|
||||
// numbof(adc_temp_quants), 1);
|
||||
// FilterLUT_Init(&adc->temp_map[TEMP_2],
|
||||
// (float *)adc_temp_quants,
|
||||
// (float *)adc_temp_vals,
|
||||
// numbof(adc_temp_quants), 1);
|
||||
|
||||
// Инициализация фильтров
|
||||
for(int i = 0; i < 2; i++)
|
||||
{
|
||||
Filter_Init(&adc->filter[i], Filter_Initializator);
|
||||
FilterBandPassDerivative_Init(&adc->u_fltr[i], (50.0f*PM_FAST_PERIOD_US/1000000), 0.1);
|
||||
FilterMedianInt_Init(&adc->i_fltr[I_C], 5, 2048);
|
||||
FilterLUT_Init(&adc->temp_map[i],
|
||||
(float *)adc_temp_quants,
|
||||
(float *)adc_temp_vals,
|
||||
numbof(adc_temp_quants), 1);
|
||||
}
|
||||
|
||||
// Запуск фильтров
|
||||
for(int i = 0; i < 2; i++)
|
||||
{
|
||||
Filter_Start(&adc->u_fltr[i]);
|
||||
Filter_Start(&adc->i_fltr[i]);
|
||||
Filter_Start(&adc->temp_map[i]);
|
||||
}
|
||||
FilterLUT_Init(&adc->temp_map[0],
|
||||
(float *)adc_temp_quants,
|
||||
(float *)adc_temp_vals,
|
||||
numbof(adc_temp_quants), 1);
|
||||
FilterLUT_Init(&adc->temp_map[1],
|
||||
(float *)adc_temp_quants,
|
||||
(float *)adc_temp_vals,
|
||||
numbof(adc_temp_quants), 1);
|
||||
}
|
||||
|
||||
__STATIC_FORCEINLINE void ADC_FilterRaw(ADC_Periodic_t *adc, int ch_start, int ch_end)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Инициализация периодического АЦП.
|
||||
* @param adc Указатель на кастомный хендл АЦП
|
||||
@ -111,17 +124,13 @@ HAL_StatusTypeDef ADC_Start(ADC_Periodic_t *adc, float PeriodUs)
|
||||
{
|
||||
return res;
|
||||
}
|
||||
// Запускаем АЦП который будет перекидывать данные в ADC_DMA_Buffer
|
||||
res = HAL_ADC_Start_DMA(adc->hadc, (uint32_t*)adc->RawData, 6); // Затем АЦП с DMA
|
||||
// Запускаем АЦП который будет перекидывать данные в DMA буфер RawData
|
||||
res = HAL_ADC_Start_DMA(adc->hadc, (uint32_t*)adc->RawData, 6);
|
||||
if(res != HAL_OK)
|
||||
{
|
||||
return res;
|
||||
}
|
||||
|
||||
ADC_EnableAllFilters(adc);
|
||||
Filter_Start(&adc->temp_map[0]);
|
||||
Filter_Start(&adc->temp_map[1]);
|
||||
|
||||
return res;
|
||||
}
|
||||
/**
|
||||
@ -139,6 +148,39 @@ HAL_StatusTypeDef ADC_Stop(ADC_Periodic_t *adc)
|
||||
return HAL_TIM_Base_Stop(adc->htim);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Обновление напряжений АЦП.
|
||||
* @return HAL Status.
|
||||
*/
|
||||
HAL_StatusTypeDef ADC_UpdateRegular(ADC_Periodic_t *adc)
|
||||
{
|
||||
if(assert_upp(adc))
|
||||
return HAL_ERROR;
|
||||
|
||||
ADC_Coefs_t *coefs = adc->Coefs;
|
||||
uint16_t *raw = adc->RawData;
|
||||
float *data = adc->Data;
|
||||
|
||||
// Фильтрация от импульсных шумов каналов токов (напряжения позже фильтруются полосовым фильтром)
|
||||
for(int i = 0; i < 2; i++)
|
||||
{
|
||||
int u_ind = ADC_U_CHANNELS_START + i;
|
||||
int i_ind = ADC_I_CHANNELS_START + i;
|
||||
// заменяем сырые данные на отфильтрованные данные
|
||||
raw[u_ind] = Filter_Process(&adc->u_fltr[i], raw[u_ind]);
|
||||
raw[i_ind] = Filter_Process(&adc->i_fltr[i], raw[i_ind]);
|
||||
}
|
||||
|
||||
// Перерасчеты Напряжений/Токов в единицы измерения
|
||||
for(int i = ADC_U_CHANNELS_START; i < ADC_NUMB_OF_REGULAR_CHANNELS; i++)
|
||||
{
|
||||
ADC_Coefs_t *coefs = &adc->Coefs[i];
|
||||
data[i] = ((float)(raw[i])-coefs->lZero) * coefs->vMax / (coefs->lMax-coefs->lZero);
|
||||
}
|
||||
|
||||
|
||||
return HAL_OK;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
@ -152,56 +194,12 @@ HAL_StatusTypeDef ADC_UpdateTemperatures(ADC_Periodic_t *adc)
|
||||
|
||||
float *data = adc->Data;
|
||||
uint16_t *raw = adc->RawData;
|
||||
|
||||
// Фильтрация от импульсных шумов для каналов напряжения/токов
|
||||
for(int i = ADC_TEMP_CHANNELS_START; i < ADC_NUMB_OF_CHANNELS; i++)
|
||||
{
|
||||
// заменяем сырые данные на отфильтрованные данные
|
||||
raw[i] = Filter_Process(&adc->filter[i], raw[i]);
|
||||
}
|
||||
|
||||
|
||||
// Преобразования температуры по таблице
|
||||
for (int i = ADC_TEMP_CHANNELS_START; i < ADC_NUMB_OF_CHANNELS; i++)
|
||||
for (int i = ADC_TEMP_CHANNELS_START; i < ADC_TEMP_CHANNELS_END; i++)
|
||||
{
|
||||
data[i] = Filter_Process(&adc->temp_map[i-ADC_TEMP_CHANNELS_START], raw[i]);
|
||||
}
|
||||
return HAL_OK;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @brief Обработка АЦП.
|
||||
* @return HAL Status.
|
||||
* @note Вызывается в DMA2_Stream0_IRQHandler() для обработки напряжений/токов,
|
||||
которые пришли по DMA.
|
||||
*/
|
||||
HAL_StatusTypeDef ADC_Handle(ADC_Periodic_t *adc)
|
||||
{
|
||||
if(assert_upp(adc))
|
||||
return HAL_ERROR;
|
||||
|
||||
ADC_Coefs_t *coefs = adc->Coefs;
|
||||
uint16_t *raw = adc->RawData;
|
||||
float *data = adc->Data;
|
||||
|
||||
// Фильтрация от импульсных шумов для каналов напряжения/токов
|
||||
for(int i = 0; i < ADC_NUMB_OF_CHANNELS; i++)
|
||||
{
|
||||
// заменяем сырые данные на отфильтрованные данные
|
||||
raw[i] = Filter_Process(&adc->filter[i], raw[i]);
|
||||
}
|
||||
|
||||
// Перерасчеты Напряжений/Токов в единицы измерения
|
||||
for(int i = 0; i < ADC_NUMB_OF_REGULAR_CHANNELS; i++)
|
||||
{
|
||||
ADC_Coefs_t *coefs = &adc->Coefs[i];
|
||||
data[i] = ((float)(raw[i])-coefs->lZero) * coefs->vMax / (coefs->lMax-coefs->lZero);
|
||||
}
|
||||
|
||||
|
||||
// if(Filter_isDataReady(&adc->filter[0]))
|
||||
// adc->f.DataReady = 1;
|
||||
|
||||
|
||||
return HAL_OK;
|
||||
}
|
||||
|
||||
@ -18,12 +18,19 @@
|
||||
#define ADC_CHANNEL_TEMP2 5
|
||||
|
||||
|
||||
#define ADC_NUMB_OF_CHANNELS 6
|
||||
#define ADC_NUMB_OF_U_CHANNELS 2
|
||||
#define ADC_NUMB_OF_I_CHANNELS 2
|
||||
#define ADC_NUMB_OF_T_CHANNELS 2
|
||||
#define ADC_NUMB_OF_CHANNELS 6
|
||||
#define ADC_NUMB_OF_U_CHANNELS 2
|
||||
#define ADC_NUMB_OF_I_CHANNELS 2
|
||||
#define ADC_NUMB_OF_T_CHANNELS 2
|
||||
#define ADC_NUMB_OF_REGULAR_CHANNELS (ADC_NUMB_OF_U_CHANNELS+ADC_NUMB_OF_I_CHANNELS)
|
||||
#define ADC_TEMP_CHANNELS_START ADC_NUMB_OF_REGULAR_CHANNELS
|
||||
|
||||
#define ADC_U_CHANNELS_START 0
|
||||
#define ADC_U_CHANNELS_END 1
|
||||
#define ADC_I_CHANNELS_START 2
|
||||
#define ADC_I_CHANNELS_END 3
|
||||
#define ADC_TEMP_CHANNELS_START 4
|
||||
#define ADC_TEMP_CHANNELS_END 5
|
||||
|
||||
|
||||
#define ADC_TEMPERATURES_QUANTS \
|
||||
{ 2188, 2197, 2206, 2216, 2226, 2236, 2247, 2259, 2271, 2283, \
|
||||
@ -50,11 +57,7 @@
|
||||
|
||||
static const float adc_temp_vals[] = ADC_TEMPERATURES;
|
||||
static const float adc_temp_quants[] = ADC_TEMPERATURES_QUANTS;
|
||||
|
||||
#define Filter_t FilterMedianInt_t
|
||||
#define Filter_Init FilterMedianInt_Init
|
||||
#define Filter_Initializator 5, 2048
|
||||
|
||||
|
||||
/**
|
||||
* @brief Коэфициенты канала АЦП для пересчета в единицы измерения
|
||||
*/
|
||||
@ -100,9 +103,9 @@ typedef struct
|
||||
uint16_t RawData[ADC_NUMB_OF_CHANNELS]; ///< Сырые значения АЦП
|
||||
ADC_Coefs_t Coefs[ADC_NUMB_OF_REGULAR_CHANNELS]; ///< Коэффициенты @ref ADC_Coefs_t для регулярных каналов (не температуры)
|
||||
|
||||
Filter_t filter[ADC_NUMB_OF_CHANNELS]; ///< Фильтр от шумов АЦП
|
||||
|
||||
FilterLUT_t temp_map[2]; ///< Коррекция нелинейности датчиков температуры
|
||||
FilterBandPassDerivative_t u_fltr[ADC_NUMB_OF_U_CHANNELS]; ///< Полосовой Фильтр Напряжений от шумов
|
||||
FilterMedianInt_t i_fltr[ADC_NUMB_OF_I_CHANNELS]; ///< Медианный Фильтр Токов от шумов
|
||||
FilterLUT_t temp_map[ADC_NUMB_OF_T_CHANNELS]; ///< Коррекция нелинейности датчиков температуры
|
||||
|
||||
float Data[ADC_NUMB_OF_CHANNELS]; ///< Пересчитанные значения АЦП (в Вольтах/Амперах)
|
||||
|
||||
@ -128,6 +131,6 @@ HAL_StatusTypeDef ADC_Stop(ADC_Periodic_t *adc);
|
||||
/* Обновление температур АЦП. */
|
||||
HAL_StatusTypeDef ADC_UpdateTemperatures(ADC_Periodic_t *adc);
|
||||
/* Обработка АЦП после получения данных. */
|
||||
HAL_StatusTypeDef ADC_Handle(ADC_Periodic_t *adc);
|
||||
HAL_StatusTypeDef ADC_UpdateRegular(ADC_Periodic_t *adc);
|
||||
|
||||
#endif //_ADC_TOOLS_H_
|
||||
|
||||
@ -125,6 +125,7 @@ void PowerMonitor_SlowCalc(PowerMonitor_t *hpm)
|
||||
|
||||
/* Расчет всякого для трех фаз отдельно */
|
||||
float fmean = 0; // средняя частота по трем фазам
|
||||
float umean = 0; // средний напряжение по трем фазам
|
||||
float imean = 0; // средний ток по трем фазам
|
||||
float iphase_mean = 0; // средний ток каждой фазы
|
||||
float uphase_mean = 0; // среднее напряжение каждой фазы
|
||||
@ -134,21 +135,15 @@ void PowerMonitor_SlowCalc(PowerMonitor_t *hpm)
|
||||
for(int i = 0; i < 3; i++)
|
||||
{
|
||||
/* Получение частоты фазы */
|
||||
meas->final.F[i] = Filter_Process(&hpm->avg[AVG_FAB+i], ZC_GetFrequency(&hpm->zc, i));
|
||||
meas->final.Offset[i] = ZC_GetOffset(&hpm->zc, i);
|
||||
meas->final.F[i] = Filter_Process(&hpm->avg[AVG_F+i], ZC_GetFrequency(&hpm->zc, i));
|
||||
// meas->final.Offset[i] = ZC_GetOffset(&hpm->zc, i);
|
||||
fmean += meas->final.F[i];
|
||||
|
||||
/* Средниее напряжение фазы */
|
||||
// uphase_mean = fabsf(meas->slow.U[i]);
|
||||
// uphase_mean = Filter_Process(&hpm->rms[RMS_UAB+i], uphase_mean);
|
||||
// meas->final.U[i] = uphase_mean*PI/2/SQRT2; /*PI/2 - получить амплитудное, SQRT2 - получить действующее */
|
||||
uphase_mean = Filter_Process(&hpm->rms[RMS_U+i], meas->slow.U[i]);
|
||||
meas->final.U[i] = Filter_Process(&hpm->rms_exp[RMS_U+i], uphase_mean);
|
||||
|
||||
/* Средний ток фазы */
|
||||
// iphase_mean = fabsf(meas->slow.I[i]);
|
||||
// iphase_mean = Filter_Process(&hpm->rms[RMS_IC+i], iphase_mean)*PI/2;
|
||||
// meas->final.I[i] = iphase_mean*PI/2/SQRT2; /*PI/2 - получить амплитудное, SQRT2 - получить действующее */
|
||||
iphase_mean = Filter_Process(&hpm->rms[RMS_I+i], meas->slow.I[i]);
|
||||
meas->final.I[i] = Filter_Process(&hpm->rms_exp[RMS_I+i], iphase_mean);
|
||||
imean += meas->final.I[i];
|
||||
@ -159,23 +154,24 @@ void PowerMonitor_SlowCalc(PowerMonitor_t *hpm)
|
||||
}
|
||||
/* Получение средней частоты по трем фазам */
|
||||
meas->final.Fmean = fmean / 3;
|
||||
/* Оределение сдвига фаз */
|
||||
static uint32_t prev_tick_phase_a = 0;
|
||||
if(prev_tick_phase_a != hpm->zc.Channel[0].PeriodStartTime)
|
||||
{ // Определяем только когда начался новый период фазы A
|
||||
prev_tick_phase_a = hpm->zc.Channel[0].PeriodStartTime;
|
||||
meas->final.Phase[0] = 0;
|
||||
meas->final.Phase[1] = ZC_GetPhaseShift(&hpm->zc, 0, 1);
|
||||
meas->final.Phase[2] = ZC_GetPhaseShift(&hpm->zc, 0, 2);
|
||||
}
|
||||
// /* Оределение сдвига фаз */
|
||||
// static uint32_t prev_tick_phase_a = 0;
|
||||
// if(prev_tick_phase_a != hpm->zc.Channel[0].PeriodStartTime)
|
||||
// { // Определяем только когда начался новый период фазы A
|
||||
// prev_tick_phase_a = hpm->zc.Channel[0].PeriodStartTime;
|
||||
// meas->final.Phase[0] = 0;
|
||||
// meas->final.Phase[1] = ZC_GetPhaseShift(&hpm->zc, 0, 1);
|
||||
// meas->final.Phase[2] = ZC_GetPhaseShift(&hpm->zc, 0, 2);
|
||||
// }
|
||||
|
||||
|
||||
/* Расчет амплитуд трехфазной сети */
|
||||
float uamp = vector_abs_linear_calc(meas->slow.U[U_AB], meas->slow.U[U_CA])/SQRT2; /* SQRT2 - получить действующее */
|
||||
// float uamp = vector_abs_linear_calc(meas->slow.U[U_AB], meas->slow.U[U_CA])/SQRT2; /* SQRT2 - получить действующее */
|
||||
// float iamp = vector_abs_phase_calc(meas->slow.I[I_A], meas->slow.I[I_C]);
|
||||
float uamp = umean / 3;
|
||||
float iamp = imean / 3;
|
||||
meas->final.Uamp = Filter_Process(&hpm->rms_exp[RMS_EXP_U], uamp);
|
||||
meas->final.Iamp = Filter_Process(&hpm->rms_exp[RMS_EXP_I], iamp);
|
||||
meas->final.Uamp = uamp;//Filter_Process(&hpm->rms_exp[RMS_EXP_U], uamp);
|
||||
meas->final.Iamp = iamp;//Filter_Process(&hpm->rms_exp[RMS_EXP_I], iamp);
|
||||
|
||||
|
||||
hpm->slow_cnt++;
|
||||
@ -197,7 +193,7 @@ void PowerMonitor_FastCalc(PowerMonitor_t *hpm)
|
||||
PowerMonitor_Measured_t *meas = &hpm->measured;
|
||||
|
||||
/* Считываем АЦП с пересчетами и медианой фильтрацией от выбросов */
|
||||
ADC_Handle(&hpm->adc);
|
||||
ADC_UpdateRegular(&hpm->adc);
|
||||
|
||||
/* Заполняем Напряжения/Токи в о.е. */
|
||||
float uba_fast = hpm->adc.Data[ADC_CHANNEL_UBA]/u_base;
|
||||
|
||||
@ -103,6 +103,7 @@ void ZC_ProcessChannel(ZeroCross_Handle_t *zc, uint8_t channel, float value, uin
|
||||
zc_ch->CurrentValue = value;
|
||||
|
||||
|
||||
#ifndef ZC_DISABLE_HYSTERESIS_DEBOUNCE
|
||||
// Фильтрация дребезга
|
||||
if(zc_ch->DebounceCounter > 0)
|
||||
{
|
||||
@ -144,6 +145,25 @@ void ZC_ProcessChannel(ZeroCross_Handle_t *zc, uint8_t channel, float value, uin
|
||||
zc_detected = -1;
|
||||
}
|
||||
}
|
||||
#else //ZC_DISABLE_HYSTERESIS_DEBOUNCE
|
||||
// Детектирование rising edge (отрицательное -> положительное)
|
||||
if ((zc_ch->LastValue < 0) &&
|
||||
(value > 0))
|
||||
{
|
||||
|
||||
if (zc_ch->EdgeType == ZC_RISING_EDGE || zc_ch->EdgeType == ZC_BOTH_EDGES) {
|
||||
zc_detected = 1;
|
||||
}
|
||||
}
|
||||
// Детектирование falling edge (положительное -> отрицательное)
|
||||
else if ((zc_ch->LastValue > 0) &&
|
||||
(value < 0))
|
||||
{
|
||||
if (zc_ch->EdgeType == ZC_FALLING_EDGE || zc_ch->EdgeType == ZC_BOTH_EDGES) {
|
||||
zc_detected = -1;
|
||||
}
|
||||
}
|
||||
#endif //ZC_DISABLE_HYSTERESIS_DEBOUNCE
|
||||
|
||||
if(zc_detected)
|
||||
{
|
||||
@ -172,11 +192,15 @@ void ZC_ProcessChannel(ZeroCross_Handle_t *zc, uint8_t channel, float value, uin
|
||||
zc_ch->CrossCount++;
|
||||
}
|
||||
|
||||
#ifndef ZC_DISABLE_HYSTERESIS_DEBOUNCE
|
||||
// Сохраняем текущее значение для следующей итерации в случае если оно не в мертвой зоне
|
||||
if((value > zc->Config.Hysteresis) || (value < -zc->Config.Hysteresis))
|
||||
{
|
||||
zc_ch->LastValue = value;
|
||||
}
|
||||
#else //ZC_DISABLE_HYSTERESIS_DEBOUNCE
|
||||
zc_ch->LastValue = value;
|
||||
#endif //ZC_DISABLE_HYSTERESIS_DEBOUNCE
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@ -87,7 +87,7 @@ int main(void)
|
||||
|
||||
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
|
||||
HAL_Init();
|
||||
|
||||
|
||||
/* USER CODE BEGIN Init */
|
||||
|
||||
#ifndef MATLAB
|
||||
|
||||
@ -323,37 +323,37 @@ static HAL_StatusTypeDef __PWM_SetOutputState(PWM_Channel_t *hCh, uint32_t state
|
||||
if (hCh->htim == NULL)
|
||||
return HAL_ERROR;
|
||||
|
||||
uint32_t ch_mode = state;
|
||||
// Если режим уже выставлен
|
||||
if(hCh->CurrentMode == state)
|
||||
{
|
||||
return HAL_OK;
|
||||
}
|
||||
|
||||
hCh->CurrentMode = state;
|
||||
|
||||
// выставляем режим каналов
|
||||
switch(hCh->ChMask)
|
||||
{
|
||||
case TIM_CHANNEL_1:
|
||||
hCh->htim->Instance->CCMR1 &= ~TIM_OCMODE_PWM2;
|
||||
hCh->htim->Instance->CCMR1 |= ch_mode;
|
||||
hCh->htim->Instance->CCMR1 |= state;
|
||||
break;
|
||||
case TIM_CHANNEL_2:
|
||||
hCh->htim->Instance->CCMR1 &= ~(TIM_OCMODE_PWM2 << 8);
|
||||
hCh->htim->Instance->CCMR1 |= (ch_mode << 8);
|
||||
hCh->htim->Instance->CCMR1 |= (state << 8);
|
||||
break;
|
||||
case TIM_CHANNEL_3:
|
||||
hCh->htim->Instance->CCMR2 &= ~TIM_OCMODE_PWM2;
|
||||
hCh->htim->Instance->CCMR2 |= ch_mode;
|
||||
hCh->htim->Instance->CCMR2 |= state;
|
||||
break;
|
||||
case TIM_CHANNEL_4:
|
||||
hCh->htim->Instance->CCMR2 &= ~(TIM_OCMODE_PWM2 << 8);
|
||||
hCh->htim->Instance->CCMR2 |= (ch_mode << 8);
|
||||
hCh->htim->Instance->CCMR2 |= (state << 8);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
// в последнюю очередь включаем выход. Перед этим настраиваем каналы на ШИМ
|
||||
if(state == PWM_ENABLE)
|
||||
{
|
||||
__HAL_TIM_MOE_ENABLE(hCh->htim);
|
||||
}
|
||||
|
||||
return HAL_OK;
|
||||
}
|
||||
|
||||
|
||||
@ -54,6 +54,7 @@ typedef struct {
|
||||
TIM_HandleTypeDef *htim; ///< указатель на соответствующий TIM (hpwm1 или hpwm2)
|
||||
uint32_t PulseCnt; ///< Счетчик кол-ва импульсов. Инициализируется из структуры @ref PWM_ThyrConfig_t
|
||||
uint32_t ChMask; ///< TIM_CHANNEL_x
|
||||
uint32_t CurrentMode; ///< Текущий режим канала
|
||||
|
||||
struct {
|
||||
unsigned Ready:1; ///< Флаг готовности тиристора к работе
|
||||
|
||||
@ -175,6 +175,9 @@ int UPP_While(void)
|
||||
|
||||
/*======= Состояние В работе =========*/
|
||||
case UPP_Work:
|
||||
// Разрешаем выход ШИМ
|
||||
__HAL_TIM_MOE_ENABLE(&hpwm1);
|
||||
__HAL_TIM_MOE_ENABLE(&hpwm2);
|
||||
// Индикация
|
||||
UPP_DO.Ready(DISABLE);
|
||||
UPP_DO.Work(ENABLE);
|
||||
|
||||
@ -385,7 +385,7 @@
|
||||
<Ww>
|
||||
<count>11</count>
|
||||
<WinNumber>1</WinNumber>
|
||||
<ItemText>\\Debug_F417\../Drivers/STM32F4xx_HAL_Driver/Src/stm32f4xx_hal.c\uwTick</ItemText>
|
||||
<ItemText>\\Debug_F417\../Drivers/STM32F4xx_HAL_Driver/Src/stm32f4xx_hal.c\uwTick,0x0A</ItemText>
|
||||
</Ww>
|
||||
<Ww>
|
||||
<count>12</count>
|
||||
@ -494,6 +494,21 @@
|
||||
<WinNumber>2</WinNumber>
|
||||
<ItemText>upp,0x0A</ItemText>
|
||||
</Ww>
|
||||
<Ww>
|
||||
<count>14</count>
|
||||
<WinNumber>2</WinNumber>
|
||||
<ItemText>htim5,0x0A</ItemText>
|
||||
</Ww>
|
||||
<Ww>
|
||||
<count>15</count>
|
||||
<WinNumber>2</WinNumber>
|
||||
<ItemText>htim3,0x0A</ItemText>
|
||||
</Ww>
|
||||
<Ww>
|
||||
<count>16</count>
|
||||
<WinNumber>2</WinNumber>
|
||||
<ItemText>htim5.Instance->CNT-2605346416,0x0A</ItemText>
|
||||
</Ww>
|
||||
</WatchWindow2>
|
||||
<Tracepoint>
|
||||
<THDelay>0</THDelay>
|
||||
@ -515,7 +530,7 @@
|
||||
<AscS3>0</AscS3>
|
||||
<aSer3>0</aSer3>
|
||||
<eProf>0</eProf>
|
||||
<aLa>1</aLa>
|
||||
<aLa>0</aLa>
|
||||
<aPa1>0</aPa1>
|
||||
<AscS4>0</AscS4>
|
||||
<aSer4>0</aSer4>
|
||||
|
||||
Loading…
Reference in New Issue
Block a user