/** ****************************************************************************** * File Name : ADC.c * Description : This file provides code for the configuration * of the ADC instances. ****************************************************************************** ** This notice applies to any and all portions of this file * that are not between comment pairs USER CODE BEGIN and * USER CODE END. Other portions of this file, whether * inserted by the user or by software development tools * are owned by their respective copyright owners. * * COPYRIGHT(c) 2019 STMicroelectronics * * Redistribution and use in source and binary forms, with or without modification, * are permitted provided that the following conditions are met: * 1. Redistributions of source code must retain the above copyright notice, * this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright notice, * this list of conditions and the following disclaimer in the documentation * and/or other materials provided with the distribution. * 3. Neither the name of STMicroelectronics nor the names of its contributors * may be used to endorse or promote products derived from this software * without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * ****************************************************************************** */ /* Includes ------------------------------------------------------------------*/ #include "adc.h" #include "gpio.h" #include "dma.h" /* USER CODE BEGIN 0 */ #include "ntc_sensor.h" #include "tim.h" #include "hall_sensor.h" #include "MC_Globals.h" #include "gas_sensor.h" #include "torque_sensor.h" #include "math_tools.h" #include "motor_control.h" uint16_t ADC1_Result[ADC1_DATA_NUM] = {0}; uint16_t ADC1_Result_Filt[ADC1_DATA_NUM] = {0}; uint16_t ADC2_Result[ADC2_DATA_NUM] = {0}; uint16_t ADC2_Result_Filt[ADC2_DATA_NUM]= {0}; FlagStatus ADC2_ConvCpmplete_Flag = RESET; ADC_SensorData_Struct_t ADC_SensorData = {0, 0};//力矩传感器和指拨传感器 ADC_3ShuntCurrent_OffSet_Struct_t ADC_3ShuntCurrent_OffSet = {32768, 32768, 32768};//三相电流零点 ADC_3ShuntCurrent_Struct_t ADC_3ShuntCurrent = {0}; ADC_3ShuntCurrent_Struct_t ADC_3ShuntCurrent_RMSValue = {0}; uint16_t uw_current_offset = 2048;//母线电流零点 /* USER CODE END 0 */ ADC_HandleTypeDef hadc1; ADC_HandleTypeDef hadc2; DMA_HandleTypeDef hdma_adc1; /* ADC1 init function */ void MX_ADC1_Init(void) { ADC_ChannelConfTypeDef sConfig; /**Common config */ hadc1.Instance = ADC1; hadc1.Init.ScanConvMode = ADC_SCAN_ENABLE; hadc1.Init.ContinuousConvMode = DISABLE; hadc1.Init.DiscontinuousConvMode = DISABLE; hadc1.Init.ExternalTrigConv = ADC_SOFTWARE_START; hadc1.Init.DataAlign = ADC_DATAALIGN_RIGHT; hadc1.Init.NbrOfConversion = 9; if (HAL_ADC_Init(&hadc1) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } /**Configure Regular Channel PCB温度 */ sConfig.Channel = ADC_CHANNEL_10; sConfig.Rank = ADC_REGULAR_RANK_1; sConfig.SamplingTime = ADC_SAMPLETIME_239CYCLES_5; if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } /**Configure Regular Channel 母线电压 */ sConfig.Channel = ADC_CHANNEL_11; sConfig.Rank = ADC_REGULAR_RANK_2; sConfig.SamplingTime = ADC_SAMPLETIME_239CYCLES_5; if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } /**Configure Regular Channel 绕组温度 */ sConfig.Channel = ADC_CHANNEL_12; sConfig.Rank = ADC_REGULAR_RANK_3; sConfig.SamplingTime = ADC_SAMPLETIME_239CYCLES_5; if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } /**Configure Regular Channel 母线电流 */ sConfig.Channel = ADC_CHANNEL_13; sConfig.Rank = ADC_REGULAR_RANK_4; sConfig.SamplingTime = ADC_SAMPLETIME_7CYCLES_5; if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } /**Configure Regular Channel 力矩传感器 */ sConfig.Channel = ADC_CHANNEL_5; sConfig.Rank = ADC_REGULAR_RANK_5; sConfig.SamplingTime = ADC_SAMPLETIME_7CYCLES_5; if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } /**Configure Regular Channel TE工作电压 */ sConfig.Channel = ADC_CHANNEL_7; sConfig.Rank = ADC_REGULAR_RANK_6; sConfig.SamplingTime = ADC_SAMPLETIME_239CYCLES_5; if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } /**Configure Regular Channel 指拨输入 */ sConfig.Channel = ADC_CHANNEL_14; sConfig.Rank = ADC_REGULAR_RANK_7; sConfig.SamplingTime = ADC_SAMPLETIME_7CYCLES_5; if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } /**Configure Regular Channel MCU温度 */ sConfig.Channel = ADC_CHANNEL_TEMPSENSOR; sConfig.Rank = ADC_REGULAR_RANK_8; sConfig.SamplingTime = ADC_SAMPLETIME_13CYCLES_5; if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } /**Configure Regular Channel Vref */ sConfig.Channel = ADC_CHANNEL_VREFINT; sConfig.Rank = ADC_REGULAR_RANK_9; sConfig.SamplingTime = ADC_SAMPLETIME_239CYCLES_5; if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } } /* ADC2 init function */ void MX_ADC2_Init(void) { ADC_InjectionConfTypeDef sConfigInjected; /**Common config */ hadc2.Instance = ADC2; hadc2.Init.ScanConvMode = ADC_SCAN_ENABLE; hadc2.Init.ContinuousConvMode = DISABLE; hadc2.Init.DiscontinuousConvMode = DISABLE; hadc2.Init.ExternalTrigConv = ADC_EXTERNALTRIGINJECCONV_EDGE_NONE; hadc2.Init.DataAlign = ADC_DATAALIGN_RIGHT; hadc2.Init.NbrOfConversion = 1; if (HAL_ADC_Init(&hadc2) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } /**Configure Injected Channel */ sConfigInjected.InjectedChannel = ADC_CHANNEL_1; sConfigInjected.InjectedRank = ADC_INJECTED_RANK_1; sConfigInjected.InjectedNbrOfConversion = 3; sConfigInjected.InjectedSamplingTime = ADC_SAMPLETIME_1CYCLE_5; sConfigInjected.ExternalTrigInjecConv = ADC_EXTERNALTRIGINJECCONV_T1_CC4; sConfigInjected.AutoInjectedConv = DISABLE; sConfigInjected.InjectedDiscontinuousConvMode = DISABLE; sConfigInjected.InjectedOffset = 0; if (HAL_ADCEx_InjectedConfigChannel(&hadc2, &sConfigInjected) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } /**Configure Injected Channel */ sConfigInjected.InjectedChannel = ADC_CHANNEL_2; sConfigInjected.InjectedRank = ADC_INJECTED_RANK_2; if (HAL_ADCEx_InjectedConfigChannel(&hadc2, &sConfigInjected) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } /**Configure Injected Channel */ sConfigInjected.InjectedChannel = ADC_CHANNEL_3; sConfigInjected.InjectedRank = ADC_INJECTED_RANK_3; if (HAL_ADCEx_InjectedConfigChannel(&hadc2, &sConfigInjected) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } } void HAL_ADC_MspInit(ADC_HandleTypeDef* adcHandle) { GPIO_InitTypeDef GPIO_InitStruct; if(adcHandle->Instance==ADC1) { /* USER CODE BEGIN ADC1_MspInit 0 */ /* USER CODE END ADC1_MspInit 0 */ /* ADC1 clock enable */ __HAL_RCC_ADC1_CLK_ENABLE(); /**ADC1 GPIO Configuration PC0 ------> ADC1_IN10 PC1 ------> ADC1_IN11 PC2 ------> ADC1_IN12 PC3 ------> ADC1_IN13 PA5 ------> ADC1_IN5 PA7 ------> ADC1_IN7 PC4 ------> ADC1_IN14 */ GPIO_InitStruct.Pin = GPIO_PIN_0|GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_3 |GPIO_PIN_4; GPIO_InitStruct.Mode = GPIO_MODE_ANALOG; HAL_GPIO_Init(GPIOC, &GPIO_InitStruct); GPIO_InitStruct.Pin = GPIO_PIN_5|GPIO_PIN_7; GPIO_InitStruct.Mode = GPIO_MODE_ANALOG; HAL_GPIO_Init(GPIOA, &GPIO_InitStruct); /* ADC1 DMA Init */ /* ADC1 Init */ hdma_adc1.Instance = DMA1_Channel1; hdma_adc1.Init.Direction = DMA_PERIPH_TO_MEMORY; hdma_adc1.Init.PeriphInc = DMA_PINC_DISABLE; hdma_adc1.Init.MemInc = DMA_MINC_ENABLE; hdma_adc1.Init.PeriphDataAlignment = DMA_PDATAALIGN_HALFWORD; hdma_adc1.Init.MemDataAlignment = DMA_MDATAALIGN_HALFWORD; hdma_adc1.Init.Mode = DMA_CIRCULAR; hdma_adc1.Init.Priority = DMA_PRIORITY_LOW; if (HAL_DMA_Init(&hdma_adc1) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } __HAL_LINKDMA(adcHandle,DMA_Handle,hdma_adc1); /* USER CODE BEGIN ADC1_MspInit 1 */ /* USER CODE END ADC1_MspInit 1 */ } else if(adcHandle->Instance==ADC2) { /* USER CODE BEGIN ADC2_MspInit 0 */ /* USER CODE END ADC2_MspInit 0 */ /* ADC2 clock enable */ __HAL_RCC_ADC2_CLK_ENABLE(); /**ADC2 GPIO Configuration PA1 ------> ADC2_IN1 PA2 ------> ADC2_IN2 PA3 ------> ADC2_IN3 */ GPIO_InitStruct.Pin = GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_3; GPIO_InitStruct.Mode = GPIO_MODE_ANALOG; HAL_GPIO_Init(GPIOA, &GPIO_InitStruct); /* ADC2 interrupt Init */ HAL_NVIC_SetPriority(ADC1_2_IRQn, 1, 1); HAL_NVIC_EnableIRQ(ADC1_2_IRQn); /* USER CODE BEGIN ADC2_MspInit 1 */ /* USER CODE END ADC2_MspInit 1 */ } } void HAL_ADC_MspDeInit(ADC_HandleTypeDef* adcHandle) { if(adcHandle->Instance==ADC1) { /* USER CODE BEGIN ADC1_MspDeInit 0 */ /* USER CODE END ADC1_MspDeInit 0 */ /* Peripheral clock disable */ __HAL_RCC_ADC1_CLK_DISABLE(); /**ADC1 GPIO Configuration PC0 ------> ADC1_IN10 PC1 ------> ADC1_IN11 PC2 ------> ADC1_IN12 PC3 ------> ADC1_IN13 PA5 ------> ADC1_IN5 PA7 ------> ADC1_IN7 PC4 ------> ADC1_IN14 */ HAL_GPIO_DeInit(GPIOC, GPIO_PIN_0|GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_3 |GPIO_PIN_4); HAL_GPIO_DeInit(GPIOA, GPIO_PIN_5|GPIO_PIN_7); /* ADC1 DMA DeInit */ HAL_DMA_DeInit(adcHandle->DMA_Handle); /* USER CODE BEGIN ADC1_MspDeInit 1 */ /* USER CODE END ADC1_MspDeInit 1 */ } else if(adcHandle->Instance==ADC2) { /* USER CODE BEGIN ADC2_MspDeInit 0 */ /* USER CODE END ADC2_MspDeInit 0 */ /* Peripheral clock disable */ __HAL_RCC_ADC2_CLK_DISABLE(); /**ADC2 GPIO Configuration PA1 ------> ADC2_IN1 PA2 ------> ADC2_IN2 PA3 ------> ADC2_IN3 */ HAL_GPIO_DeInit(GPIOA, GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_3); /* USER CODE BEGIN ADC2_MspDeInit 1 */ /* USER CODE END ADC2_MspDeInit 1 */ } } /* USER CODE BEGIN 1 */ void ADC_Start(void) { HAL_ADCEx_Calibration_Start(&hadc1); HAL_ADCEx_Calibration_Start(&hadc2); HAL_ADC_Start(&hadc1); HAL_ADC_Start(&hadc2); HAL_ADCEx_InjectedStart_IT(&hadc2); HAL_ADC_Start_DMA(&hadc1, (uint32_t *)ADC1_Result, ADC1_DATA_NUM); __HAL_DMA_DISABLE_IT(hadc1.DMA_Handle, DMA_IT_HT); HAL_TIM_Base_Start_IT(&PWM_TIMER); HAL_TIM_PWM_Start(&PWM_TIMER, TIM_CHANNEL_4); HAL_TIMEx_PWMN_Start(&PWM_TIMER, TIM_CHANNEL_4); } //更新三相电流采样值 void HAL_ADCEx_InjectedConvCpltCallback(ADC_HandleTypeDef* hadc) { //更新3相电流采样值 ADC2_Result[ADC2_RANK_CURRENT_B] = HAL_ADCEx_InjectedGetValue(hadc,1) << 4; ADC2_Result[ADC2_RANK_CURRENT_C] = HAL_ADCEx_InjectedGetValue(hadc,2) << 4; ADC2_Result[ADC2_RANK_CURRENT_A] = HAL_ADCEx_InjectedGetValue(hadc,3) << 4; //计算三相电流 ADC_3ShuntCurrent.uw_phase_a = (int16_t)(ADC_3ShuntCurrent_OffSet.uw_phase_a_offset - ADC2_Result[ADC2_RANK_CURRENT_A]); ADC_3ShuntCurrent.uw_phase_b = (int16_t)(ADC_3ShuntCurrent_OffSet.uw_phase_b_offset - ADC2_Result[ADC2_RANK_CURRENT_B]); ADC_3ShuntCurrent.uw_phase_c = (int16_t)(ADC_3ShuntCurrent_OffSet.uw_phase_c_offset - ADC2_Result[ADC2_RANK_CURRENT_C]); ///计算三相电流有效值 PhaseCurrent_CalRMSValue(&ADC_3ShuntCurrent, &ADC_3ShuntCurrent_RMSValue); ADC2_ConvCpmplete_Flag = SET; } //更新ADC采样结果 void HAL_ADC_ConvCpltCallback(ADC_HandleTypeDef* hadc) { #if 1 static uint32_t PeriodTestCnt = 0; PeriodTestCnt++; if(PeriodTestCnt > 300) { PeriodTestCnt = 0; } #endif int32_t Temp_32; static int32_t BusVoltageFltSum = 0; static int32_t IdcFltSum = 0; static uint16_t T_Filt_Cnt = 0; static uint32_t T_Coil_Sum = 0; static uint32_t T_PCB_Sum = 0; static uint32_t T_MCU_Sum = 0; static TrueOrFalse_Flag_Struct_t T_MCU_Init_Flag = FALSE; static uint8_t T_MCU_Init = 0; static uint16_t T_MCU_Init_AD = 0; static int32_t GasSensorFltSum = 0, HardwareVersionADFltSum=0; static TrueOrFalse_Flag_Struct_t MOS_NTC_InitFinishedFlag = FALSE; //更新PCB温度,绕组温度,MCU温度 if(VersionIdentifyFinishedFlag == FALSE) //硬件版本未识别前,温度默认为25度 { MC_RunInfo.T_PCB = 65; MC_RunInfo.T_Coil = 65; MC_RunInfo.T_MCU = 65; } else { if( MC_HallSensorData.InverterExistFlag == FALSE ) { if(MOS_NTC_InitFinishedFlag == FALSE) { MOS_NTC_InitFinishedFlag = TRUE; MOS_NTC_Init(); } } T_PCB_Sum += ADC1_Result[ADC1_RANK_NTC_PCB]; T_Coil_Sum += ADC1_Result[ADC1_RANK_NTC_COIL]; T_MCU_Sum += ADC1_Result[ADC1_RANK_TP_MCU]; T_Filt_Cnt++; if(T_Filt_Cnt >= 3000) { if( MC_HallSensorData.InverterExistFlag == FALSE ) { MC_RunInfo.T_PCB = GetNTCTempera_20K(T_PCB_Sum / 3000); MC_RunInfo.T_Coil = GetNTCTempera_20K(T_Coil_Sum / 3000); MC_RunInfo.T_MCU = GetNTCTempera_20K(T_MCU_Sum / 3000); //MOS管NTC温度 } else { //计算PCB温度 MC_RunInfo.T_PCB = GetNTCTempera(T_PCB_Sum / 3000); //计算绕组温度 MC_RunInfo.T_Coil = GetNTCTempera(T_Coil_Sum / 3000); //MCU温度根据PCB初始温度进行校准 if(T_MCU_Init_Flag == FALSE) { T_MCU_Init = MC_RunInfo.T_PCB;//校准时温度 T_MCU_Init_AD = T_MCU_Sum / 3000;//校准时AD值 T_MCU_Init_Flag = TRUE; } //计算MCU温度 MC_RunInfo.T_MCU = T_MCU_Init + ((int16_t)(T_MCU_Init_AD - T_MCU_Sum / 3000) * 192 >> 10);//4.3mV/度, 3300 / 4095 / 4.3 * 1024 = 192 } T_Filt_Cnt = 0; T_PCB_Sum = 0; T_Coil_Sum = 0; T_MCU_Sum = 0; } } //更新母线电压 BusVoltageFltSum += ((ADC1_Result[ADC1_RANK_VIN] << 10) - BusVoltageFltSum) >> 9; MC_RunInfo.BusVoltage = (uint32_t)((BusVoltageFltSum >> 10) * 18382) >> 10;//3300 * 1047 / (4095 * 47) MC_RunInfo.BusVoltage += (MC_RunInfo.BusCurrent >> 7) * 8; //根据母线电流和估算的线阻进行补偿, 补偿电阻 0.2 * 128 = 25.6 if( MCUManufacturer == HK32F103RBT6 ) { MC_RunInfo.BusVoltage = ((MC_RunInfo.BusVoltage - 8100) * 1402) >> 10; } //更新母线电流 if( MC_HallSensorData.InverterExistFlag == FALSE ) { Temp_32 = (ADC1_Result[ADC1_RANK_CURRENT] - uw_current_offset) * 39449 >> 10; //3300/4095* 0.98/8.2 /0.0025 } else { Temp_32 = (ADC1_Result[ADC1_RANK_CURRENT] - uw_current_offset) * 50000 >> 11; //3300/4095* 0.98/13 /0.0025 } Temp_32 = (Temp_32 <= 0) ? 0 : ((Temp_32 >= 50000) ? 50000 : Temp_32); IdcFltSum += ((Temp_32 << 10) - IdcFltSum) >> 9; MC_RunInfo.BusCurrent = IdcFltSum >> 10; //更新力矩传感器 if(MC_TorqueCorrectParam.CalibrateEnableFlag != 0xAA) { Temp_32 = (ADC1_Result[ADC1_RANK_TORQUE_SENSOR] - TorqueOffSetData.PresentData) * 100 / MC_TorqueCorrectParam.K; Temp_32 = ((Temp_32 <= 0) ? 0 : Temp_32); } else { Temp_32 = TorqueSensorTwoPointCalibrate(ADC1_Result[ADC1_RANK_TORQUE_SENSOR], TorqueOffSetData.PresentData, &MC_TorqueCorrectParam); } #if 1 //采用原始采集值 #if NormalWork //正常运行 ADC_SensorData.TorqueSensor = Temp_32; #else //用于寿命测试,模拟输入力矩 if(HAL_GetTick() < 5000) { Temp_32 = 0; } else { static uint32_t WaveTime_Zero = 0; static uint32_t Time_Enter = 0; if((HAL_GetTick() - Time_Enter) > 10) // ??10ms???,?????????? { WaveTime_Zero = HAL_GetTick(); } Time_Enter = HAL_GetTick(); Temp_32 = TriangleWaveGenerate(WaveTime_Zero, 250, 500 ,1500); } ADC_SensorData.TorqueSensor = Temp_32; #endif #else //采用滤波值 static int32_t TorqueFltSum = 0; TorqueFltSum += ((Temp_32 << 10) - TorqueFltSum) >> 8; ADC_SensorData.TorqueSensor = TorqueFltSum >> 10; #endif //更新指拨 if(IsGasSensorConnectedFlag == TRUE) { Temp_32 = ADC1_Result[ADC1_RANK_GAS] - GasSensor_OffSet; Temp_32 = (Temp_32 <= 0) ? 0 : Temp_32; GasSensorFltSum += ((Temp_32 << 10) - GasSensorFltSum) >> 8; //滤波延时0.33*256=85.3ms ADC_SensorData.GasSensor = GasSensorFltSum >> 10; } else { ADC_SensorData.GasSensor = 0; } //更新硬件版本AD HardwareVersionADFltSum += ((ADC1_Result[ADC1_RANK_HARDWARE_VER] << 10) - HardwareVersionADFltSum) >> 9; HardwareVersion_AD = (uint16_t)(HardwareVersionADFltSum >> 10); PowerDownProtection(ADC1_Result[ADC1_RANK_VIN]); } //ADC1和ADC2数据滑动滤波 void ADC_SensorData_Filt(uint16_t* p_ADC1_Result_Filt, uint16_t* p_ADC2_Result_Filt) { static uint32_t PeriodTimeCnt = 0; static int32_t ADC1_FltSum[ADC1_DATA_NUM] = {0}; static int32_t ADC2_FltSum[ADC2_DATA_NUM] = {0}; uint8_t i; if((HAL_GetTick() - PeriodTimeCnt) >= 2) { for(i=0; i> 7; p_ADC1_Result_Filt[i] = ADC1_FltSum[i] >> 10; } for(i=0; i> 7; p_ADC2_Result_Filt[i] = ADC2_FltSum[i] >> 10; } PeriodTimeCnt = HAL_GetTick(); } } //相电流有效值计算,有效值 = 最大值 * 0.707,运行频率15K void PhaseCurrent_CalRMSValue(ADC_3ShuntCurrent_Struct_t* ADC_3ShuntCurrent, ADC_3ShuntCurrent_Struct_t* PhaseCurrent_RMS) { static int16_t PhaseCurrentA_Max = 0; static int16_t PhaseCurrentB_Max = 0; static int16_t PhaseCurrentC_Max = 0; static int16_t Count = 0; int16_t DataTemp; static int32_t PhaseCurrentA_FltSum = 0; static int32_t PhaseCurrentB_FltSum = 0; static int32_t PhaseCurrentC_FltSum = 0; //计算A相电流峰值 if(PhaseCurrentA_Max < ADC_3ShuntCurrent->uw_phase_a) { PhaseCurrentA_Max = ADC_3ShuntCurrent->uw_phase_a; } //计算B相电流峰值 if(PhaseCurrentB_Max < ADC_3ShuntCurrent->uw_phase_b) { PhaseCurrentB_Max = ADC_3ShuntCurrent->uw_phase_b; } //计算C相电流峰值 if(PhaseCurrentC_Max < ADC_3ShuntCurrent->uw_phase_c) { PhaseCurrentC_Max = ADC_3ShuntCurrent->uw_phase_c; } Count++; if(Count >= 500) { //计算A相电流有效值 DataTemp = PhaseCurrentA_Max; PhaseCurrentA_Max = 0; PhaseCurrentA_FltSum += (((abs(DataTemp) * 724)) - PhaseCurrentA_FltSum) >> 5; PhaseCurrent_RMS->uw_phase_a = PhaseCurrentA_FltSum >> 10; //计算B相电流有效值 DataTemp = PhaseCurrentB_Max; PhaseCurrentB_Max = 0; PhaseCurrentB_FltSum += (((abs(DataTemp) * 724)) - PhaseCurrentB_FltSum) >> 5; PhaseCurrent_RMS->uw_phase_b = PhaseCurrentB_FltSum >> 10; //计算C相电流有效值 DataTemp = PhaseCurrentC_Max; PhaseCurrentC_Max = 0; PhaseCurrentC_FltSum += (((abs(DataTemp) * 724)) - PhaseCurrentC_FltSum) >> 5; PhaseCurrent_RMS->uw_phase_c = PhaseCurrentC_FltSum >> 10; Count = 0; } } //PA0切换AD,采集MOS管NTC void MOS_NTC_Init( void ) { GPIO_InitTypeDef GPIO_InitStruct; ADC_ChannelConfTypeDef sConfig; GPIO_InitStruct.Pin = GPIO_PIN_0; GPIO_InitStruct.Mode = GPIO_MODE_ANALOG; HAL_GPIO_Init(GPIOA, &GPIO_InitStruct); __HAL_ADC_DISABLE(&hadc1); /**Configure Regular Channel MOS温度 */ sConfig.Channel = ADC_CHANNEL_0; sConfig.Rank = ADC_REGULAR_RANK_8; sConfig.SamplingTime = ADC_SAMPLETIME_239CYCLES_5; if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK) { _Error_Handler(__FILE__, __LINE__); } } void PowerDownProtection( uint16_t BusVoltage_AD ) { static uint16_t poweroncount=0, powerdowncount=0; static TrueOrFalse_Flag_Struct_t poweronFlag = FALSE; if(poweronFlag == FALSE) { if( BusVoltage_AD > 1671 ) //1671对应的母线电压为30V { if( ++poweroncount > 30000 ) //电压大于30V并持续10s左右 { poweroncount=0; poweronFlag = TRUE; } } else poweroncount=0; } else { if( BusVoltage_AD < 1504 ) //1504对应的母线电压为27V { if( ++powerdowncount > 60 ) //电压小于27V并连续60次,大约持续20ms左右 { Disable_PwmGpio_Out(); poweronFlag = FALSE; PowerDown_SaveFlag = TRUE; } } else { powerdowncount=0; } } } /* USER CODE END 1 */ /** * @} */ /** * @} */ /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/