刚开始学习MSP430单片机,参考网上修改的程序, DS18B20总是初始化失败,端口读入的值总是FFFF。延时用示波器测的,满足500,改为600US也不好用,请教各位达人,可能是什么原因,谢谢。
/***************DS18B20 Reset&Init*********************/
void Reset_18B20(void)
{
int zxc;
P4DIR|=0x01 ;
OUT_0;//Set output 0 主机首先发出一个480-960微秒的低电平脉冲
DelayNus(70); //500us
OUT_1; //释放数据线(将数据线拉高)
DelayNus(10); //90us
P4DIR&=~BIT0; //BIT0=0X01 P4.0=input
zxc=P4IN;
if((P4IN&BIT0)==BIT0)
{ Err_Flag=1; } //失败,一直都是高电平说明总线上无器件应答
else
{
Err_Flag=0; // 有低电平出现说明总线上有器件已做出应答
OUT_1;
}
P4DIR|=BIT0 ; //BIT0=0X01 P4.0=output
}
[
本帖最后由 黑加仑 于 2011-6-17 09:54 编辑 ]
此帖出自
小平头技术问答
我是外接的8M晶振,上拉电阻为4.7K,你的意思我的上拉电阻太大了吗?
下面是我的程序
#include"msp430x14x.h"
/*****************DS18B20**************************/
/***************P4.0-DS18B20**********************/
#define OUT_0 P4OUT&=~BIT0 //BIT0=0X01 P4.0=0
#define OUT_1 P4OUT|=BIT0 //BIT0=0X01 P4.0=1
unsigned char Err_Flag=1;
int temperature;
float Temper;
void Init_IO(void);
void Reset_18B20(void);
void Write_cmd(unsigned char cmd);
unsigned char Read_data(void);
void GetTemp(void);
void ReadTemp(void);
void DelayNus(unsigned int n);
/************************************************************/
void main()
{
WDTCTL = WDTPW + WDTHOLD; // Stop watchdog timer
P3SEL|=BIT4; //SET P3.4 UTXD0
P4DIR|=BIT0 ; //BIT0=0X01 P4.0=output
while(1)
{
GetTemp();
}
}
/***************DS18B20 Reset&Init*********************/
void Reset_18B20(void)
{
while( Err_Flag==1)
{
P4DIR|=0x01 ;
OUT_0;//Set output 0 主机首先发出一个480-960微秒的低电平脉冲
DelayNus(50); //500us
OUT_1; //释放数据线(将数据线拉高)
DelayNus(6); //60us
P4DIR&=~BIT0; //BIT0=0X01 P4.0=input
if((P4IN&BIT0)==BIT0)
{ Err_Flag=1; } //失败,一直都是高电平说明总线上无器件应答
else
{
Err_Flag=0; // 有低电平出现说明总线上有器件已做出应答
OUT_1;
}
}
P4DIR|=BIT0 ; //BIT0=0X01 P4.0=output
}
/******************Get Temperature*******************/
void GetTemp(void)
{
Reset_18B20();
Write_cmd(0xcc); //跳过ROM
Write_cmd(0x44); //温度变换,结果存入内部9字节RAM中去
DelayNus(60000);
DelayNus(60000);
DelayNus(60000);//延时1S以上
Reset_18B20();
Write_cmd(0xcc);
Write_cmd(0xBE); //读暂存器,内部9字节RAM
ReadTemp();
}
/*****************Read Temperature*******************/
void ReadTemp(void)
{
char temp_low,temp_high; // 温度值
int sign;
temp_low=Read_data();//读低位
temp_high=Read_data();//读高位
if((temp_high&0xf8)==0xf8) //判断符号位
{
char temp_mid=0xff; // 前五位为1,温度为负,需取反+1
sign=1;
temp_mid&=~temp_high; //高八位取反
temperature=(temp_mid&0x0f);
temp_mid=0xff;
temp_mid&=~temp_low;//低八位取反
temperature<<=8;
temperature|=temp_mid;
temperature+=0x0001;
}
else
{
sign=0;
temperature=(temp_high&0x0f);
temperature<<=8; //将高位移到高八位 (temperature16位)
temperature|=temp_low;}
Temper=(float)(temperature*0.0625);
}
/***************DS18B20 Write_cmd*********************/
//每个命令字节在写的时候都是低字节先写
//例如CCH的二进制为11001100,在写到总线上时00110011
void Write_cmd(unsigned char cmd)
{
unsigned char i;
for(i=0;i<8;i++)
{
OUT_0;
DelayNus(1);//延时13us
if((cmd&0x01)==0x01) OUT_1; //利用与运算取出要写的某位二进制数据
else OUT_0;
cmd=cmd>>1; //右移
DelayNus(5);//延时50us
OUT_1;
P4DIR|=BIT0;
}
}
/***************DS18B20 Read_data*********************/
unsigned char Read_data(void)
{
unsigned char data,i;
for(i=0;i<8;i++)
{
data=data>>1;
OUT_0;
_NOP(); //延时1us
OUT_1; //读时隙是从主机把单总线拉低之后,在1微秒之后就得释放单总线为高电平
_NOP();_NOP();_NOP();_NOP();_NOP(); //延时5us
P4DIR&=~BIT0; //输入
if((P4IN&BIT0)==0) //利用与运算取出要写的某位二进制数据
{data=data&0x7f;}
else {data=data|0x80;}
// if(P4IN&BIT0) data|=0x80;
DelayNus(4);
OUT_1;
P4DIR|=BIT0;
}
return data;
}
/***************us级别延迟*********************/
//delay=n*5+6; n=10,则延时10*5+6=56us
void DelayNus(unsigned int n)
{
while(n--){};
}
/********************************************/
一周热门 更多>