⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 wu01.asm

📁 DS18B20原理图及资料
💻 ASM
字号:
#include <reg51.h>
#include <intrins.h>

#define TEST_TIME
#undef TEST_TIME

sbit DQ =P3^3; //定义通信端口 

unsigned char data dis_digit;
unsigned char code dis_code[11]={0xc0,0xf9,0xa4,0xb0,	// 0, 1, 2, 3
				0x99,0x92,0x82,0xf8,0x80,0x90, 0xff};// 4, 5, 6, 7, 8, 9, off 
				//shixr ,共阳极接法,1表示暗的。
unsigned char data dis_buf[8];
unsigned char data dis_index;


//延时函数 
void delay(unsigned int i) //经验表明,这里i=1时约等于6.9us
{ 
	while(i--); 
} 

//初始化函数 
void Init_DS18B20(void) 
{ 
	unsigned char x=0; 
	unsigned int time = 0;
	
	DQ = 1; //DQ复位 
	delay(8); //稍做延时 
	DQ = 0; //单片机将DQ拉低 
#ifdef TEST_TIME
/*	TR0 = 0;
	TH0 = 0;
	TL0 = 0;
	TR0 = 1;
*/
#endif	
	delay(80); //精确延时 大于 480us 
#ifdef TEST_TIME
/*
	TR0 = 0;
	time = (TH0<<8) + TL0 -2;
	*/
/*here time = 0x202 ,that means
514 * 12/11.0592 = 557.73 us.
that means every delay() is 6.9us.
*/
#endif	

	DQ = 1; //拉高总线 
	delay(14); 
	x=DQ; //稍做延时后 如果x=0则初始化成功 x=1则初始化失败 
	delay(20); 
} 

//读一个字节 
unsigned char ReadOneChar(void) 
{ 
	unsigned char i=0; 
	unsigned char dat = 0; 
	for (i=8;i>0;i--) 
	{ 
		DQ = 0; // 给脉冲信号 
		dat>>=1; 
		DQ = 1; // 给脉冲信号 
		if(DQ) 
		dat|=0x80; 
		delay(4); 
	} 
	return(dat); 
} 

//写一个字节 
void WriteOneChar(unsigned char dat) 
{ 
	unsigned char i=0; 
	for (i=8; i>0; i--) 
	{ 
		DQ = 0; 
		DQ = dat&0x01; 
		delay(5); 
		DQ = 1; 
		dat>>=1; 
	} 
} 

//读取温度 
unsigned int ReadTemperature(void) 
{ 
	unsigned char a=0; 
	unsigned char b=0; 
	unsigned int t=0; 
	float tt=0; 
	Init_DS18B20(); 
	WriteOneChar(0xCC); // 跳过读序号列号的操作 
	WriteOneChar(0x44); // 启动温度转换 
	Init_DS18B20(); 
	WriteOneChar(0xCC); //跳过读序号列号的操作 
	WriteOneChar(0xBE); //读取温度寄存器等(共可读9个寄存器) 前两个就是温度 
	a = ReadOneChar(); 
	b = ReadOneChar(); 
	t=b; 
	t<<=8; 
	t=t|a; 
	tt=t *0.625; //将温度的高位与低位合并 
	t= tt*10+0.5; //对结果进行4舍5入 
	return(t); 
} 

void Delay_ms (unsigned int Nms )
{
	unsigned char i;
	while(Nms--)
		for(i=0; i<125; i++) ;
}

void main()
{
	unsigned int t = 0;
	P0 = 0xff;
	P2 = 0xff;

	//以下为定时器初始化。

	TMOD = 0x01;	// M1,M0 = 0,1 工作在方式1,为16位定时器
	TH0 = 0xFC;
	TL0 = 0x17;		// TH和TL各提供8位。
	IE = 0x82;		//开cpu中断 和 源中断 即EA =  1, ET0 = 1

	dis_buf[0] = 0xff;
	dis_buf[1] = 0xff;
	dis_buf[2] = 0xff;
	dis_buf[3] = 0xff;
	dis_buf[4] = 0x0;
	dis_buf[5] = 0x0;
	dis_buf[6] = 0x0;
	dis_buf[7] = 0x0;
	
	dis_digit = 0xfe;
	dis_index = 0;
	
	TR0 = 1;	//在 TCON 中,启动定时器0。启动工作需要放置在初始化之后,这是一个好的习惯。
	do{
			t = ReadTemperature();

			if (t>0 && t < 9999)
			{
				dis_buf[4] = dis_code[t/1000];
				dis_buf[5] = dis_code[(t%1000)/100] & 0x7f;
				dis_buf[6] = dis_code[(t%100)/10];
				dis_buf[7] = dis_code[t%10];
			}

			Delay_ms(300);
	}
	while(1);
}
void timer0() interrupt 1 using 1		//函数名字可以任意取, interrupt 1中的"1"表示定时器0的中断号为1。
// 定时器0中断服务程序, 用于数码管的动态扫描
// dis_index --- 显示索引, 用于标识当前显示的数码管和缓冲区的偏移量
// dis_digit --- 位选通值, 传送到P2口用于选通当前数码管的数值, 如等于0xfe时,
//				选通P2.0口数码管
// dis_buf   --- 显于缓冲区基地址	
{
	TH0 = 0xFC;
	TL0 = 0x17;			//在定时器中断中重新赋初始值。可以计算这里的时钟周期为
	// (0x10000- 0xfc17) * (1/(11.0592 * 10^6 / 12)) = 1.085ms
	
	P1 = 0xff;							// 先关闭所有数码管
	//P0 = dis_buf[dis_index];			// 显示代码传送到P0口
	P2 = dis_buf[dis_index];			// 显示代码传送到P2口
	P1 = dis_digit;						// 

	dis_digit = _crol_(dis_digit,1);	// 位选通值左移, 下次中断时选通下一位数码管
	dis_index++;						// 
					
	if (dis_index >= 8)
		dis_index = 0;

}


⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -