GD32F190 ADC多通道DMA自动接收踩坑指南

如果条件允许的话,请不要用GD32F1x0系列。。。。

-----题记

这个系列的芯片官方连个库函数指南都没有你敢信?我都不要求中文版的了,起码英文版的得有吧??

以往stm32的ADC工作模式,一般都是配置成多个通道自动连续切换,然后通过DMA把数据读走,这次用上GD32F190Tx芯片后,怀着国产之光的心态认认真真的写代码,看库函数,结果真就是踩坑了。

我们习惯stm32的配置方式,都是给一个结构体成员赋值,然后调用xxx_init()函数,把结构体作为参数传入函数。例如,这是stm32的配置程序:

/* ADC1 configuration ------------------------------------------------------*/
    ADC_InitStructure.ADC_Mode = ADC_Mode_Independent;
    ADC_InitStructure.ADC_ScanConvMode = ENABLE;
    ADC_InitStructure.ADC_ContinuousConvMode = ENABLE;
    ADC_InitStructure.ADC_ExternalTrigConv = ADC_ExternalTrigConv_None;
    ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right;
    ADC_InitStructure.ADC_NbrOfChannel = ADC_CH_NUM;        //顺序进行规则转换的ADC通道的数目
    ADC_Init(ADC1, &ADC_InitStructure);

    /*
    ADCFinalValue[0 ]    PA0  channel0  接收CH2 AGC
    ADCFinalValue[1 ]    PA1  channel1  接收CH1 AGC

    */
    ADC_RegularChannelConfig(ADC1, ADC_Channel_0,  1,  ADC_SampleTime_71Cycles5);
    ADC_RegularChannelConfig(ADC1, ADC_Channel_1,  2,  ADC_SampleTime_71Cycles5);


    /* Enable ADC1 DMA */
    ADC_DMACmd(ADC1, ENABLE);

    /* Enable ADC1 */
    ADC_Cmd(ADC1, ENABLE);

    /* Enable ADC1 reset calibaration register */   
    ADC_ResetCalibration(ADC1);
    /* Check the end of ADC1 reset calibration register */
    while(ADC_GetResetCalibrationStatus(ADC1));

    /* Start ADC1 calibaration */
    ADC_StartCalibration(ADC1);
    /* Check the end of ADC1 calibration */
    while(ADC_GetCalibrationStatus(ADC1));

    /* Start ADC1 Software Conversion */ 
    ADC_SoftwareStartConvCmd(ADC1, ENABLE);
    //ADC end

但是,gd32的库函数都是封装成立一个个函数,初始化一个变量需要调用一次函数,但是也没有具体的步骤告诉你需要调用哪些函数,是不是很恶心?

一开始这样写:

    adc_deinit();
    /* ADC channel length config */
    adc_channel_length_config(ADC_REGULAR_CHANNEL,ADC_CH_NUM);
    /* ADC data alignment config */
    adc_data_alignment_config(ADC_DATAALIGN_RIGHT);  
    /* ADC SCAN function enable */
    adc_special_function_config(ADC_SCAN_MODE,ENABLE);
    /* ADC regular channel config */
    adc_regular_channel_config(0, ADC_CHANNEL_1, ADC_SAMPLETIME_55POINT5);
    adc_regular_channel_config(1, ADC_CHANNEL_9, ADC_SAMPLETIME_55POINT5);
    
    /* ADC external trigger source config */
    adc_external_trigger_source_config(ADC_REGULAR_CHANNEL,ADC_EXTTRIG_REGULAR_NONE);
    adc_external_trigger_config(ADC_REGULAR_CHANNEL,ENABLE);
    
    /* enable ADC interface */
    adc_enable();
    /* ADC calibration and reset calibration */
    adc_calibration_enable();
    /* ADC DMA enable */
    adc_dma_mode_enable();
    adc_software_trigger_enable(ADC_REGULAR_CHANNEL);

后来发现采集到的两个通道数据不动,似乎只有上电采集了一次就没有然后了。

这其中这个adc_external_tigger把我搞得一愣一愣的,你说我寻思dma是内部触发啊,我为什么还有配置外部触发源使能呢?我配置成none,然后再使能?我先自宫了,然后告诉我练功和自宫虽然没关系,但你就得自宫?

给gd软件工程师的脑回路跪了,但是不写这条指令又没有办法工作,采集到的数据都是0。

然后我就把adc的工作模式换咯,换成ADC_CONTINUOUS_MODE,这问题又来了,采集到的数据,数组里两个值都是第一个通道的数据,好烦有么有?

最后你猜我怎么解决的?

    adc_deinit();
    /* ADC channel length config */
    adc_channel_length_config(ADC_REGULAR_CHANNEL,ADC_CH_NUM);
    /* ADC data alignment config */
    adc_data_alignment_config(ADC_DATAALIGN_RIGHT);  
    /* ADC SCAN function enable */
    adc_special_function_config(ADC_CONTINUOUS_MODE,ENABLE);
    adc_special_function_config(ADC_SCAN_MODE,ENABLE);
    /* ADC regular channel config */
    adc_regular_channel_config(0, ADC_CHANNEL_1, ADC_SAMPLETIME_55POINT5);
    adc_regular_channel_config(1, ADC_CHANNEL_9, ADC_SAMPLETIME_55POINT5);
    
    /* ADC external trigger source config */
    adc_external_trigger_source_config(ADC_REGULAR_CHANNEL,ADC_EXTTRIG_REGULAR_NONE);
    adc_external_trigger_config(ADC_REGULAR_CHANNEL,ENABLE);
    
    /* enable ADC interface */
    adc_enable();
    /* ADC calibration and reset calibration */
    adc_calibration_enable();
    /* ADC DMA enable */
    adc_dma_mode_enable();
    adc_software_trigger_enable(ADC_REGULAR_CHANNEL);

ADC的工作模式要配置成两种!!!!!!!!!!

既要配置成scan模式,让他能够各个通道扫描,又要配置成condition模式,让他连续触发!!!

马上联系GD工程师,今晚我要扣你巨蛙

你可能感兴趣的:(stm32,gd32,C语言,stm32,gd32)