#include "drv_adc.h" #include "drv_clk.h" #include "drv_dma.h" #include "kit_data.h" #include "kit_debug.h" #define CR1_SCAN_Set ((uint32_t)0x00000100) #define CR2_DMA_Set ((uint32_t)0x00000100) #define CR2_RSTCAL_Set ((uint32_t)0x00000008) #define CR2_CAL_Set ((uint32_t)0x00000004) #define CR2_SWSTART_Set ((uint32_t)0x00500000) #define CR2_CONT_Set ((uint32_t)0x00000002) #define CR2_ADON_Set ((uint32_t)0x00000001) #define CFGR_ADCPRE_Reset_Mask ((uint32_t)0xFFFF3FFF) #define RCC_PCLK2_Div8 ((uint32_t)0x0000C000) #define SMPR_SMP_Set ((uint32_t)0x00000007) #define SQR_SQ_Set ((uint32_t)0x0000001F) #define ADC_ExternalTrigConv_None ((uint32_t)0x000E0000) /*!< For ADC1, ADC2 and ADC3 */ typedef struct { DmaStream dma_stream; DmaChannel dma_channel; ADC_TypeDef* reg; }STM32AdcProp; STM32AdcProp stm32_adc_prop[kAdcDev_End] = { {kDma2Stream_0, kDmaChannel_0, ADC1}, {kDma2Stream_3, kDmaChannel_1, ADC2}, {kDma2Stream_0, kDmaChannel_2, ADC3}, }; typedef struct { uint16_t arr_len; uint16_t sample_cnt; uint16_t *dma_buf; }AdcItem; AdcItem adc1_item; uint8_t drv_adc_init(AdcDev dev, const AdcArray *adc_arr, uint16_t len, uint16_t* dma_buf, uint8_t sample_cnt) { uint8_t tmp1_8u, tmp2_8u; uint32_t i; __IO uint32_t *sqr[3]; __IO uint32_t *smpr[2]; ADC_TypeDef *reg; if(dev < kAdcDev_End) { adc1_item.arr_len = len; adc1_item.dma_buf = dma_buf; adc1_item.sample_cnt = sample_cnt; reg = stm32_adc_prop[dev].reg; //dma init drv_dma_init(stm32_adc_prop[dev].dma_stream, stm32_adc_prop[dev].dma_channel, DMA_CFG_DATA_DIR_P2M | DMA_CFG_CYCLE_EXE | DMA_CFG_DATA_M_I|DMA_CFG_DATA_P_N|DMA_CFG_DATA_LEN_2B, (uint32_t)®->DR); drv_dma_set_buf(stm32_adc_prop[dev].dma_stream, (uint8_t*)dma_buf, len * sample_cnt); RCC->APB2ENR |= (RCC_APB2ENR_ADC1EN << dev); //开启时钟 //设置ADC通道的转换顺序和采样时间 sqr[0] = ®->SQR3; sqr[1] = ®->SQR2; sqr[2] = ®->SQR1; smpr[0] = ®->SMPR2; smpr[1] = ®->SMPR1; for(i = 0; i < len ; i++) { tmp1_8u = adc_arr[i].channel / 10; tmp2_8u = adc_arr[i].channel % 10 * 3; *smpr[tmp1_8u] &= ~(SMPR_SMP_Set << tmp2_8u); *smpr[tmp1_8u] |= (adc_arr[i].cycle << tmp2_8u); tmp1_8u = i / 6; tmp2_8u = i % 6 * 5; *sqr[tmp1_8u] &= ~(SQR_SQ_Set << tmp2_8u); *sqr[tmp1_8u] |= (adc_arr[i].channel << tmp2_8u); } //设置规则通道数目 reg->SQR1 &= ~KIT_BIT_MASK_32S(20, 23); reg->SQR1 |= (uint32_t)(len - 1 ) << 20; KIT_CLR_BIT_32(reg->SR, 5); //设置ADC频率 reg->CR1 |= ADC_CR1_SCAN; ADC->CCR |= 0x30000; //PCLK2 8分频 //calibration reg->CR2 |= ADC_CR2_ADON | ADC_CR2_CONT | ADC_CR2_DDS | ADC_CR2_DMA; reg->CR2 |= ADC_CR2_SWSTART; } return true; } bool drv_adc_is_overflow(AdcDev dev) { return ((stm32_adc_prop[dev].reg->SR & 0x20) != 0); } uint16_t drv_adc_get_data(uint8_t idx) { uint16_t res = 0; KIT_ASSERT_PARAM(idx < adc1_item.arr_len); if(idx < adc1_item.arr_len) { res = kit_get_dma_avg_filter_min_max(adc1_item.dma_buf, adc1_item.arr_len, idx, adc1_item.sample_cnt); } return res; }