1000字范文,内容丰富有趣,学习的好帮手!
1000字范文 > STC51单片机学习笔记8——stc12c56 串口显示AD(多路ad)

STC51单片机学习笔记8——stc12c56 串口显示AD(多路ad)

时间:2021-05-25 10:04:42

相关推荐

STC51单片机学习笔记8——stc12c56 串口显示AD(多路ad)

stc12c56 串口显示AD(多路ad).

AD中断设置

AUXR:

ADC_CONTR:

//#define ADC_POWER 0x80后面不能加分号,不然就会错。其他定义必须加分号!!!

//烧写程序时,一定要选用外部晶振(烧写软件默认为内部晶振(5M~6M))

//烧写时,有时候写不进去,尝试断开地线,然后接上上电

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

关于以下两个问题的说明

a=ADC_LOW2&0x03;//如果是dat=ADC_DATA<<2+ADC_LOW2&0x03;就会出错!莫名其妙!

dat=ADC_DATA*4+a; //如果是dat=ADC_DATA<<2+a 。就乱窜,一直飚过1024!而且串口老死!

从这两个问题可以看出,如果直接对某个8位寄存器进行操作,它会将中间产生的值,直接

放到该寄存器里,对于寄存器里的的数据不要直接操作,应该先读出来,在内存中处理数据 。

对寄存器的操作不要用<<、>>等等,也不要使用很长的公式(dat=ADC_DATA<<2+ADC_LOW2&0x03)

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

#include<reg51.h>

#include<intrins.h>

sfr ADC_CONTR = 0xc5;

sfr ADC_DATA =0xc6;

sfr ADC_LOW2 =0xbe;

sfr P1M0 =0x91;

sfr P1M1= 0x92;

sfr AUXR=0x8e;

//sfr AUXR1=0xA2;

//sfr BRT=0x9c;

sbit Led=P1^4;

#define ADC_POWER 0x80

#define ADC_FLAG 0x10

#define ADC_START 0x08

#define ADC_SPEEDLL 0x00

#define ADC_SPEEDL 0x20

#define ADC_SPEEDH 0x40 //这个速度,读出的数据噪声很大

#define ADC_SPEEDHH 0x60

#define RELOAD_COUNT 0xf3 //4M晶振,smod=0,9600bps 实际波特率=4000000/(256-243)/32=9615.误差=15/9600=0.16%

//具体计算看《STC12C5A60S2》第79页及其之后

unsigned char ch=0; //用于ad通道选择

unsigned char ch_times=0; //选中某一个ad通道时,前几次采样值不稳定,噪声太大,需要去除

void serial_port_initial(void);

void send_UART(unsigned char i);

void UART_Interrupt_Receive(void);

void delay(unsigned char n);

void initADC(void);

void print_uint(unsigned int num);

void Long_delay();

void main()

{

Long_delay();//防止pc运行串口驱动时,与本程序自行向pc发送数据产生冲突,从而产生的混乱

Led=0;

serial_port_initial();

initADC();

AUXR=0x50; //T1定时器不分频,1T的速度,设置EADCI中断允许

IE=0xa0;//设置EADC_SPI中断和EA总中断允许

while(1)

;

}

void serial_port_initial(void) // 使用独立波特率发生器作为波特率发生器

{

SCON=0x50;//8位可变波特率,无奇偶校验位

TMOD=0X21;

AUXR=0x40; //T1定时器不分频,1T的速度

TH1=RELOAD_COUNT;

TL1=RELOAD_COUNT;

//TR1=1;

EA=1; // 开总中断

}

void send_UART(unsigned char i)

{

ES=0; // 关串口中断

TI=0; // 清零串口发送完成中断请求标志

SBUF=i;

while(TI==0); // 等待发送完成

TI=0; // 清零串口发送完成中断请求标志

//ES=1; // 允许串口中断

}

void print_uint(unsigned int num)

{

unsigned char w5,w4,w3,w2,w1;

w5=num/10000;

w4=num%10000/1000;

w3=num%1000/100;

w2=num%100/10;

w1=num%10;

send_UART('0'+w5);

send_UART('0'+w4);

send_UART('0'+w3);

send_UART('0'+w2);

send_UART('0'+w1);

send_UART(' ');

}

void delay(unsigned char n)

{

unsigned char x;

while(n--)

{

x=100;

while(x--);

}

}

void initADC()

{

ch=0;

//P1=P1M0=P1M1=0xff; //P1口设置为开漏型,做AD

P1=P1M0=0xef;

P1M1=0x00; //P1.0/2/3口设置为高阻输入,做AD. P1.4作准双向口,做led指示灯

ADC_DATA=0;

//此句不对,不能用或。ADC_CONTR=ADC_POWER|ADC_SPEEDL|ADC_START|ch|0xef;

ADC_CONTR=0x88;//ADC_CONTR=ADC_POWER|ADC_SPEEDL|ADC_START|ch|0xef

delay(2);

}

void adc_isr() interrupt 5

{

unsigned int dat;

unsigned char a;

AUXR=0x40; //T1定时器不分频,1T的速度,设置EADCI中断禁止

if(ch_times==10)

{

a=ADC_LOW2;//如果是dat=ADC_DATA<<8+ADC_LOW2&0x03;就会出错!莫名其妙!(在看到这的时候,忽然觉得好像是先算的8+ADC_LOW2&0x03···)

a=a&0x03;

dat=ADC_DATA*4+a; //如果是dat=ADC_DATA<<2+a 。就他妈的乱窜,一直飚过1024!

TR1=1;//开启定时器1 ,开启串口

send_UART(ch+0x30);

send_UART(':');

print_uint(dat);

delay(2); //如果没有延时,串口就会混乱!

TR1=0;//关闭定时器1

ch_times=0;

ch++;

if(ch==4)

ch=0;

}

ADC_CONTR=0x88+ch; //开启下一次转换

ch_times++;

AUXR=0x10; //设置EADCI中断允许

}

void Long_delay()

{

unsigned char i,j,k;

for(k=0;k<50;k++)

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

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

;

}

完整资料打包:

STC51单片机学习笔记8-stc12c56串口显示AD(多路ad)资源-单片机文档类资源-CSDN下载

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。