一起学mini2440裸机开发(十三)--ADC原理与实验

发布者:码农侠最新更新时间:2021-11-04 来源: eefocus关键字:mini2440  裸机开发  ADC 手机看文章 扫描二维码
随时随地手机看文章

概述

S3C2440的CMOS模拟数字转换器ADC可以对8通道模拟输入信号进行循环检测,S3C2440的ADC和触摸屏公用一个ADC转换器,所以学习ADC也是学习触摸屏的基础。


    S3C2440ADC的主要特性如下:


    ●分辨率:10位


    ●最大转换速率:500KSPS


    ●微分线性度误差:±1.0 LSB


    ●积分线性度误差:±2.0 LSB


    ●供电电压:3.3V


    ●模拟输入电压范围:0~3.3V


ADC原理

ADC是一种将模拟信号转化为数字信号的方法,一般要经过采样、保持、量化、编码4个步骤。在实际电路中,有些过程是合并进行的,如采样和保持,量化和编码在转换过程中时同时实现的。由奈奎特采样定理可知,当采样频率大于模拟信号中最高频率的2倍时,采样值才能不失真地反映原来模拟信号。


主要技术指标如下:


●  分辨率


通常以输出二进制的位数表示分辨率的高低,一般位数越多,量化单位越小,对输入信号的分辨能力就越高。例如,输入模拟电压的变化范围为0±~3.3V、分辨率为12位时,可以分辨的最小模拟电压为3.3V/2^12≈0.8mV;而分辨率为10位时,可以分辨的最小模拟电压为3.3V/2^10≈3.2mV。


●  转换误差


它是指在零点和满度都校准以后,在整个转换范围内,分别测量各个数字量所对应的模拟输入电压实测范围与理论范围之间的偏差,取其中的最大偏差作为转换误差的指标。它通常以相对误差的形式出现,并以LSB为单位表示。


●  转换速度


完成一次模数转换所需要的时间称为转换时间。在大多数情况下,转换速度是转换时间的倒数。


ADC的转换速度主要取决于转换电路的类型,并联比较型ADC的转换速度最高,逐次逼近型ADC次之,双积分型ADC转换速度最低。


S3C2440处理器ADC功能图如图1所示,其中虚线框是与触摸屏有关的功能模块,可以暂不考虑,学完ADC基本实验后,再学触摸屏部分也可以。

从图1可以看出,ADC共有8路模拟输入,其中XP、XM、YP和YM是触摸屏使用的4路,剩下的4路模拟输入A[3:0]可以用于一般的ADC输入通道。


此外还需要注意ADC的输入时钟是如何产生的。对于S3C2440处理器,ADC输入时钟是由PCLK分频得到的,如图2所示

ADC相关寄存器


使用ADC只需要对相应的寄存器进行配置,然后启动ADC即可,启动ADC有两种方法:


         ①手动启动


         ②读取完上一次转换结果后自动启动下一次ADC转换


     得到ADC是否转换完成的信息有两种方法


         ①查询法:查询寄存器ADCCON的第15位(ADC转换结束标志位)


         ②中断法:转换完成后,产生ADC中断信号,如图1中的INT_ADC信号。


当不使用触摸屏时,与ADC相关的寄存器主要有寄存器ADCCON和寄存器ADCDAT0。寄存器ADCCON主要用于ADC的启动方式、设置ADC转换时钟以及ADC转换结束标志位等,如下图3。寄存器ADCDAT0中存放了ADC转换所得到的的数据,ADC转换结束后,可以通过读该寄存器的值来得到转换结果。

     

ADC初始化

对ADC初始化只需要做好以下两个方面的工作:


① 设置ADC输入时钟。


② 选择ADC输入通道。


可以使用如下代码初始化:


#define PRSC_EN   1 //允许预分频

#define PRSCVL   19 //预分频值

#define STDBM   0  //正常工作模式

#define READ_START  0  //读数时不进行A/D转换


void ADC_Init(unsigned char channel)    

{

    ADCCON&=(~((1<<14)|(0xff<<6)|(0x7<<3)|(1<<2)|(1<<1)|(1<<0)));

    ADCCON|=(PRSC_EN<<14)|(PRSCVL<<6)|(channel<<3)|(STDBM<<2)|(READ_START<<1);


}


此时,对PCLK进行50分频,则可以计算出ADC输入时钟=PCLK/50=1MHz。


ADC基础实验


在我的mini2440上有一个可调电位器,如下图所示。电位器的中间抽头部分接在ADC输入通道0上,当电位器滑动头位于最下端时,AIN0引脚电压为0V;当电位器滑动头位于最上端时,AIN0引脚电压为3.3V;当电位器上、下滑动时,AIN0引脚的电压值会在0~3.3V之间变换。因此,本实验使用ADC输入通道0对AIN0引脚电压进行A/D转换。

下图为我的ADC实验的文件布局:

下面贴出我的实验代码


main.c文件


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

* 调节mini2440上的可调电位器,然后使用ADC输入通道2对

* AIN2引脚电压尽心转换,将取得的数字量输出到串口

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


#include"adc.h"

#include"uart.h"


int main()

{

    int value;

    Uart0_Init(115200);

    ADC_Init(0);


     value=ADC_Read();   //将A/D转换值发送到串口,这里我没有使用

     Uart0_Printf("%d",value/1000);      //while()循环是为了看清楚值

     Uart0_Printf("%d",value%1000/100);   //调节电位器后,可以重启

     Uart0_Printf("%d",value%100/10);    //开发板,看到串口输出值

     Uart0_Printf("%d",value%10);     //不一样了

  

}


uart.h文件


#ifndef __UART_H__

#define __UART_H__


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

*函数名称:void Uart0_Init(unsigned int baudrate)

*参数说明:baudrate:波特率

*返 回 值:无

*全局变量: 无

*功    能:对UART0进行初始化                         

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

void Uart0_Init(unsigned int baudrate);


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

*函数名称:void putc(unsigned char c)

*参数说明:c:通过串口接收到的字符,注意这里是8位数据

*返 回 值:无

*全局变量: 无

*功    能:将通过串口接收到的字符发送给PC机并显示在

*          串口调试工具。                

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

void putc(unsigned char c);


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

*函数名称:unsigned char getc(void)

*参数说明:无

*返 回 值:c:通过串口接收到的字符,注意这里是8位数据

*全局变量: 无

*功    能:接收并保存通过串口输入的数据                         

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

unsigned char getc(void);


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

*函数名称:void Uart0_Printf(const char *fmt,...)

*参数说明:可变参数

*返 回 值:无

*全局变量: 无

*功    能:将()的内容通过串口发送并在PC机显示                

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

void Uart0_Printf(const char *fmt,...);


#endif


uart.c文件


#include

#include

#include"uart.h"


#define PCLK   50000000

#define UART_BRD     (int)((PCLK/(baudrate*16))-1)


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

*函数名称:void Uart0_Init(unsigned int baudrate)

*参数说明:baudrate:波特率

*返 回 值:无

*全局变量: 无

*功    能:对UART0进行初始化                         

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

void Uart0_Init(unsigned int baudrate)

{

 GPHCON&=~((3<<4)|(3<<6));  //GPH2--TXD0;GPH3--RXD0

 GPHCON|=((2<<4)|(2<<6));    //设置GPH2、GPH3为TXD0、RXD0功能

 GPHUP=0x00;                 //上拉电阻使能

 ULCON0|=0x03;              //设置数据发送格式:8个数据位,1个停止位,无校验位

 UCON0=0x05;                //发送模式和接收模式都使用查询模式

 UBRDIV0=UART_BRD;         //设置波特率,其中波特率作为一个参数传递到该初始化函数

 URXH0=0;          //将URXH0清零

}


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

*函数名称:void putc(unsigned char c)

*参数说明:c:通过串口接收到的字符,注意这里是8位数据

*返 回 值:无

*全局变量: 无

*功    能:将通过串口接收到的字符发送给PC机并显示在

*          串口调试工具。                

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

void putc(unsigned char c)

{

 UTXH0=c;

 while(!(UTRSTAT0&(1<<2)));    //等待发送完成

}


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

*函数名称:unsigned char getc(void)

*参数说明:无

*返 回 值:c:通过串口接收到的字符,注意这里是8位数据

*全局变量: 无

*功    能:接收并保存通过串口输入的数据                         

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

unsigned char getc(void)

{

 unsigned char c;

 while(!(UTRSTAT0&(1<<0)));     //查询是否接收到有效数据

 c=URXH0;

 return c;

}

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

*函数名称:static void Uart0_SendByte(int data)

*参数说明:data:一个字节的数据

*返 回 值:无

*全局变量: 无

*功    能:向串口发送一个字节的数据。这个函数只在本

*          C文件内使用,不被其他文件所调用,故使用

*     static来修饰。                 

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


static void Uart0_SendByte(int data)

{

    if(data=='n')      //注意,在超级终端中使用的换行符是'r',因此当遇到'n'时

    {                      //需要将其转换为'r'

     while(!(UTRSTAT0&(1<<2)));    //等待发送完成

     UTXH0='r';  

    }

    while(!(UTRSTAT0&(1<<2)));    //等待发送完成完成后,将新发送

    UTXH0=data;                            //的数据写入发送寄存器

}

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

*函数名称:static void Uart0_SendString(char *pt)

*参数说明:pt:指针,指向将要发送的数据所在数组的地址

*返 回 值:无

*全局变量: 无

*功    能:发送字符串                 

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

static void Uart0_SendString(char *pt)

{

  while(*pt)

  {

       Uart0_SendByte(*pt++); 

  }

}

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

*函数名称:void Uart0_Printf(const char *fmt,...)

*参数说明:可变参数

*返 回 值:无

*全局变量: 无

*功    能:将()的内容通过串口发送并在PC机显示                

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

void Uart0_Printf(const char *fmt,...)

{

 va_list ap;      //定义了一个指向可变参数列表指针

 char string[50];  //存储要发送的内容


 va_start(ap,fmt);   //是参数列表指针ap指向函数参数列表中的第一个可变参数

 vsprintf(string,fmt,ap);

 va_end(ap);         //清空参数列表

 Uart0_SendString(string);   //将该缓冲区中的数据打印到串口中

}

//详细讲解请看博客:http://blog.csdn.net/mybelief321/article/details/8934635


adc.h文件


#ifndef __ADC_H__

#define __ADC_H__

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

*函数名称:void ADC_Init(unsigned char channel)

*参数说明:channel:通道

*返 回 值:无

*全局变量: 无

*功    能:ADC初始化,手动启动ADC,ADC输入时钟为1MHz                       

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

void ADC_Init(unsigned char channel);


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

*函数名称:void ADC_Init(unsigned char channel)

*参数说明:channel:通道

*返 回 值:无

*全局变量: 无

*功    能:ADC初始化,手动启动ADC,ADC输入时钟为1MHz                       

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

int ADC_Read(void);

#endif


adc.c文件


#include

#include"adc.h"


#define PRSC_EN   1 //允许预分频

#define PRSCVL   19 //预分频值

#define STDBM   0  //正常工作模式

#define READ_START  0  //读数时不进行A/D转换

#define Adc_Start()  {ADCCON|=1;}


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

*函数名称:void ADC_Init(unsigned char channel)

*参数说明:channel:通道

*返 回 值:无

*全局变量: 无

*功    能:ADC初始化,手动启动ADC,ADC输入时钟为1MHz                       

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

void ADC_Init(unsigned char channel)    

{

   ADCCON&=(~((1<<14)|(0xff<<6)|(0x7<<3)|(1<<2)|(1<<1)|(1<<0)));

   ADCCON|=(PRSC_EN<<14)|(PRSCVL<<6)|(channel<<3)|(STDBM<<2)|(READ_START<<1);


}


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

*函数名称:int ADC_Read(void)

[1] [2]
关键字:mini2440  裸机开发  ADC 引用地址:一起学mini2440裸机开发(十三)--ADC原理与实验

上一篇:mini2440也即S3C2440地址分配问题
下一篇:一起学mini2440裸机开发(十二)--mini2440的串口中断实验

推荐阅读最新更新时间:2024-11-07 10:17

ADI发布业界首款集成真轨到轨输入缓冲器的Σ-Δ型ADC
超低噪声ADC,具有快速而灵活的输出数据速率,适合高精度仪器仪表和过程控制应用。 中国,北京 — Analog Devices, Inc. (NASDAQ: ADI)最近推出业界首款完全集成真轨到轨输入缓冲器的Σ-Δ型转换器,吞吐速率达250 kSPS,可为设计人员提供业界领先的噪声性能。 AD7175-2 Σ-Δ型ADC在20 SPS时具有24个无噪声位,250 kSPS时具有17.2个无噪声位,为设计人员提供了更宽的动态范围,可实现实验室分析仪器系统所需的较小信号测量偏差。 与竞争型解决方案相比,AD7175-2在相同功耗下的吞吐速率高一倍,可实现更快、响应更迅速的测量系统,提供每通道50 kSPS的扫描
[模拟电子]
ADI发布业界首款集成真轨到轨输入缓冲器的Σ-Δ型<font color='red'>ADC</font>
在PCB级采用时间交替超高速模数转换器
采用时间交替模数转换器(ADC),以每秒数十亿次的速度采集同步采样模拟信号,对于设计工程师来说,这是一项极大的技术挑战,需要非常完善的混合信号电路。时间交替的根本目标是通过增加转换器,在不影响分辨率和动态性能的前提下使采样频率增倍。 本文探讨时间交替模数转换器的主要技术难点,并提供切实可行的系统设计指导,包括可解决上述问题的创新性元件功能和设计方法。本文还提供从7Gsps双转换器芯片“交替解决方案”测得的FFT结果。最后,文章还描述了实现高性能所需的应用支持电路,包括时钟源和驱动放大器。 对更高采样速度的需求不断增加 何时提高采样频率会更加有益,其中的原因又是什么呢?这个问题有多种答案。模数转换器的采样速度基本上直接决定了可
[电源管理]
在PCB级采用时间交替超高速<font color='red'>模数转换器</font>
STM32学习日志——ADC实验
一、ADC简介: STM32有1~3个ADC,我使用的STM32F103ZET6有3个ADC,是12位逼近的数字模拟转换器,它有18个通道,包括16个外部通道和2个内部信号源。每个ADC有4种模式:单次、连续、扫描、间断。存储方式分为左对齐或右对齐,一般选择右对齐。ADC将转换分为两个通道组:规则通道与注入通道,规则通道相当于正常执行的程序,注入通道相当于中断。规则通道最多包含16个,注入通道最多位4个。 本次介绍仅介绍规则通道的单次转换, 二、软件配置: 1)开启PA口的时钟和ADC1的时钟,设置PA1为模拟输入; 2)复位ADC1,同时设置分频因子;要保证ADC的时钟不超过14MHZ,否则可能不准,而APB2的时钟为7
[单片机]
STM32学习日志——<font color='red'>ADC</font>实验
德州仪器推出同步采样ADC 实现16位无丢码性能
      日前,德州仪器 (TI) 宣布推出支持高压输入的16位、14位 与 12 位同步采样逐次逼近寄存器 (SAR) 模数转换器 (ADC) 系列产品。ADS8556、ADS8557 以及 ADS8558 不但提供 730 kSPS 的采样范围,高达 91.5 dB的信噪比 (SNR),而且还包含业界独有的同步采样 ADC,可实现真正的 16 位无丢码 (NMC) 性能。       这些全新 ADC 使设计人员能够在连接各种输入或传感器时,最大限度地提高性能,充分满足包括多轴电机控制、同步数据采集、机器人、电源质量管理以及电源保护在内的多种应用需求。如欲了解产品详情,敬请问: http://focus.ti.co
[电源管理]
德州仪器推出同步采样<font color='red'>ADC</font> 实现16位无丢码性能
基于51单片机的1602+ADC0832烟雾报警系统
本设计基于51单片机,共有ADC0832数模转换模块,1602液晶显示模块,按键控制与声光报警模块4大模块组成!可实现对烟雾浓度的实时监测与反应 之后是仿真目录 下面是部分代码,想要了解,可以下载文末完整附件! //基于1602+ADC0832的烟雾/温度报警系统 //作者:科技小宅神 //创作时间:2020/09/20 //版权:科技小宅神原创!抄袭必究,仅供参考学习! #include reg51.h //包含51单片机寄存器的头文件 #include 1602.h //调用1602.h文件 #include intrins.h //包含_nop_函数定义的头文件 #define uchar unsigned char #
[单片机]
基于51单片机的1602+<font color='red'>ADC</font>0832烟雾报警系统
A/D转换器(ADC
1、概述 D/A转换器(Digital to Analog Converter)——能把数字量转换为模拟量的电子器件(简称为DAC)。 A/D转换器(Analog to Digital Converter)——能把模拟量转换成相应数字量的电子器件(简称为ADC)。 A/D转换器把模拟量转换成数字量,以便于单片机进行数据处理。A/D转换一般要经过采样、保持、量化及编码4个过程。在实际电路中,有些过程是合并进行的,如采样和保持,量化和编码在转换过程中是同时实现的。 目前单片的ADC芯片较多,对设计者来说,只需合理的选择芯片即可。现在部分的单片机片内集成了A/D转换器,仅在片内A/D转换器不能满足需要的情况下,需外扩。当然作
[单片机]
A/D转换器(<font color='red'>ADC</font>)
STM8学习笔记--ADC
STM8的ADC转换器有10位的分辨率。STM8的特殊之处在于,如果用户可接受较低的分辨率,则读转换结果的速度会加快;用户可通过选择相应的寄存器对齐方式,只读10位中的8位。配置左对齐或右对齐的寄存器ADC_CR2。 ADC开-关控制:通过置位ADC_CR1寄存器的ADON位来开启ADC。当首次置位ADON位时,ADC从低功耗模式唤醒。为了启动转换必须第二次使用写指令来置位ADC_CR1寄存器的ADON位。如果转换频繁,就一直保持ADC上电,这样就省去了7us上电稳定时间,如果ADON位清零进入低功耗模式,则需要两次写ADON来开启转换。 写程序按以下时序图操作: 单次转换模式:这种模式下,AD
[单片机]
理解时钟抖动对高速ADC的影响
对高速信号进行高分辨率的数字化处理需审慎选择时钟,才不至于使其影响模数转换器( ADC )的性能。借助本文,我们将使读者更好地理解 时钟抖动 问题及其对高速ADC性能的影响。 我们将以凌力尔特(LTC)最新推出的高性能16位、160Msps的ADC LTC2209为例进行说明。LTC2209具有77.4dB的信噪比(SNR),100dB 基带无寄生动态范围(SFDR)。 与当今市场上的许多高速ADC一样,LTC2209也使用采样-保持(S&H)电路,该电路本质上是对ADC输入的点取(Snapshot)。当采样-保持开关闭合后,ADC输入网络被连至采样电容。在开关打开的那一刻(1/2时钟周期后),采样电
[模拟电子]
理解时钟抖动对高速<font color='red'>ADC</font>的影响
小广播
设计资源 培训 开发板 精华推荐

最新单片机文章
何立民专栏 单片机及嵌入式宝典

北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

换一换 更多 相关热搜器件

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved