A/D转换器

一、A/D转换相关知识

1. A/D转换的技术指标

1) 分辨率,表示会触发数字量变化的最小模拟信号的变化量。分辨率又称精度,通常以数字信号的位数来表示。

2) 转换速率,指完成一次A/D转换所需的时间的倒数。积分型A/D的转换时间时毫秒级,属低速A/D;逐次比较型A/D是微秒级的,属中速A/D;全并行/串并行型A/D可达到纳秒级。

3)量化误差,指对模拟信号进行量化而产生的误差

4)偏移误差,指输入信号为零时,输出信号不为零的值。

5)满刻度误差,满刻度输出时对应的输入信号与理想输入信号值之差

 

2. 转换器类型

1积分型A/D转换器

将输入电压转换成时间(脉冲宽度信号)或频率(脉冲频率),然后由定时器/计数器获得数字值。其优点是用简单电路就能获得高分辨率,但缺点是由于转换精度依赖于积分时间,因此转换速率极低。初期的单片AD转换器大多采用积分型,现在逐次比较型已逐步成为主流

2逐次逼近型A/D

逐次逼近转换过程和用天平称物重非常相似。天平称重物过程是从最重的砝码开始试放,与被称物体进行比较,若物体重于砝码,则该砝码保留,否则移去。在加上第二个次重砝码,由物体的重量是否大于砝码的重量决定第二个砝码是否留下还是移去。以此类推,一直加到最小一个砝码为止。然后将所有留下的砝码重量相加,就得此物体的重量,按照这一思路,逐次比较型A/D转换器。,就是将输入模拟量与不同的参考电压作多次比较。使转换所得的数字量在数值上逐次逼近输入模拟量对应值。

 

3)全并行/串并行型A/D,原理无

 

3、A/D转换一般步骤

取样、保持、量化、编码

 

二、Exynos4412-A/D转换器

1. A/D转换器控制寄存器ADCCON,配置A/D转换器功能,如转换开始方式,工作模式,时钟频率,分辨等,还有一位只读位表示当前转换是否完成。该寄存器如下:

 A/D转换器_第1张图片

A/D转换器_第2张图片

2. A/D转换器通路选择寄存器(ADCMUX),用来选择当前要转换的模拟量的通路。

A/D转换器_第3张图片

 

3. A/D转换器数据寄存器(ADCDAT),存放模拟量转换为数字量的转换结果。

A/D转换器_第4张图片

 

4. CLRINTADC,清除ADC中断寄存器

A/D转换器_第5张图片

 

5. ADC中断号

A/D转换器_第6张图片

 

6. 因为ADC在第10 Combiner, 所以需要了解Combiner中的中断寄存器

A/D转换器_第7张图片


1)IESR2寄存器

A/D转换器_第8张图片

2)IECR2寄存器

A/D转换器_第9张图片

 

三、示例代码

//使用读启动方式

#define __READ_START_

/*

 *If A/D conversion start by read

 * */

//#define __READ_START_

 

/**********************************************************************

 * @brief     IRQInterrupt Service Routine program body

 * @param[in] None

 * @return        None

 **********************************************************************/

void do_irq(void )

{

    unsignedint  temp_adc = 0,temp_mv;

 

    int irq_num;

    irq_num = (CPU0.ICCIAR & 0x1FF);

 

    printf("IRQinterrupt !!\n");

 

    temp_adc = ADCDAT & 0xfff;

 

    printf("adcdat%0x\n", temp_adc);

    //temp_mv = 1800 * temp_adc / 4095;

    temp_mv = 1.8 * 1000 * temp_adc / 0xfff;

 

    printf("adcvalue: %d mv\n", temp_mv);

 

    //Clear SPI Pending,中断号为42 42 / 32 = 110

    ICDICPR.ICDICPR1 |= 0x1 << 10;

    //clear ADC pending

    INTADCCLR = 1;

    // End of interrupt

    CPU0.ICCEOIR = (CPU0.ICCEOIR & ~(0x1FF)) | irq_num;

 

}

 

/**********************************************************************

 * @brief     mydelay_msprogram body

 * @param[in] int (ms)

 * @return        None

 **********************************************************************/

void mydelay_ms(int time)

{

    int i, j;

    while(time--)

    {

       for (i = 0; i < 5; i++)

           for (j = 0; j < 514; j++);

    }

}

 

/*-------------------------MAINFUNCTION------------------------------*/

/**********************************************************************

 * @brief     Mainprogram body

 * @param[in] None

 * @return        int

 **********************************************************************/

int main(void)

{

    GPX2.CON = 0x1 << 28;//GPX2CON[7]:Output drive LED

 

    uart_init();

 

    ADC_CFG &= ~(0x1 << 16); //Bit_16:Select ADC Mux 0:General 1:MTCADC

 

    ADCMUX = 0x3; //0x3: 0011 = AIN3

 

 

    /*

     * GIC interruptcontroller:

     **/

    // Enables the corresponding interruptSPI10

 

    ICDISER.ICDISER1 |= 0x1 <<10;

    CPU0.ICCICR |= 0x1; //Global enablefor signaling of interrupts

 

    CPU0.ICCPMR = 0xFF; //The prioritymask level.Priority filter. threshold

 

    ICDDCR = 1;   //Bit1:  GICmonitors the peripheral interrupt signals and

                  //     forwards pending interrupts to the CPUinterfaces2

 

    /***** Interrupt combiner*****/

    INTCOMBINER.IESR2 |= 0x1 << 19;

 

    ICDIPTR.ICDIPTR10 = 0x01010101; //SPI8~11 interrupts are sent to processor 0

 

#ifdef__READ_START_

    //12bit A/D conversion; enable A/Dconverter prescaler; prescaler value:255; A/D conversion start byread

    ADCCON = (0x1<<16) | (0x1<<14) | (0xff<<6) |0x1<<1;

#else

    //12bit A/D conversion; enableA/D converter prescaler; prescaler value:255

    ADCCON = (0x1<<16) |(0x1<<14) | (0x01<<6);

#endif

 

#ifdef __READ_START_

    temp_adc = ADCDAT & 0xfff;

#endif

 

    printf("\n************ADC test ************\n");

 

    while(1)

    {

#ifndef    __READ_START_

       ADCCON |= 0x1;//start ADCconversion

#endif

       //Turn on LED

       GPX2.DAT |= 0x1 << 7;

 

       mydelay_ms(1000);

 

       //Turn off LED

       GPX2.DAT &= ~(0x1 << 7);

       mydelay_ms(1000);

    }

 

    return 0;

}

 


你可能感兴趣的:(ARM)