1 //****************************************************************// 2 // DHT21使用范例 3 //单片机 : AT89S52 或 STC89C52RC 4 // 功能 :串口发送温湿度数据 波特率 9600 5 //硬件连接: P2.0口为通讯口连接DHT11,DHT11的电源和地连接单片机的电源和地,单片机串口加MAX232连接电脑 6 // 公司 :奥松电子 7 //****************************************************************// 8 9 #include <reg51.h> 10 #include <intrins.h> 11 // 12 typedef unsigned char U8; /* defined for unsigned 8-bits integer variable 无符号8位整型变量 */ 13 typedef signed char S8; /* defined for signed 8-bits integer variable 有符号8位整型变量 */ 14 typedef unsigned int U16; /* defined for unsigned 16-bits integer variable 无符号16位整型变量 */ 15 typedef signed int S16; /* defined for signed 16-bits integer variable 有符号16位整型变量 */ 16 typedef unsigned long U32; /* defined for unsigned 32-bits integer variable 无符号32位整型变量 */ 17 typedef signed long S32; /* defined for signed 32-bits integer variable 有符号32位整型变量 */ 18 typedef float F32; /* single precision floating point variable (32bits) 单精度浮点数(32位长度) */ 19 typedef double F64; /* double precision floating point variable (64bits) 双精度浮点数(64位长度) */ 20 // 21 #define uchar unsigned char 22 #define uint unsigned int 23 #define Data_0_time 4 24 25 //----------------------------------------------// 26 //----------------IO口定义区--------------------// 27 //----------------------------------------------// 28 sbit P2_0 = P2^0 ; 29 sbit P2_1 = P2^1 ; 30 sbit P2_2 = P2^2 ; 31 sbit P2_3 = P2^3 ; 32 //----------------------------------------------// 33 //----------------定义区--------------------// 34 //----------------------------------------------// 35 U8 U8FLAG,k; 36 U8 U8count,U8temp; 37 U8 U8T_data_H,U8T_data_L,U8RH_data_H,U8RH_data_L,U8checkdata; 38 U8 U8T_data_H_temp,U8T_data_L_temp,U8RH_data_H_temp,U8RH_data_L_temp,U8checkdata_temp; 39 U8 U8comdata; 40 U8 outdata[5]; //定义发送的字节数 41 U8 indata[5]; 42 U8 count, count_r=0; 43 U8 str[5]={"RS232"}; 44 U16 U16temp1,U16temp2; 45 SendData(U8 *a) 46 { 47 outdata[0] = a[0]; 48 outdata[1] = a[1]; 49 outdata[2] = a[2]; 50 outdata[3] = a[3]; 51 outdata[4] = a[4]; 52 count = 1; 53 SBUF=outdata[0]; 54 } 55 56 void Delay(U16 j) 57 { U8 i; 58 for(;j>0;j--) 59 { 60 for(i=0;i<27;i++); 61 62 } 63 } 64 void Delay_10us(void) 65 { 66 U8 i; 67 i--; 68 i--; 69 i--; 70 i--; 71 i--; 72 i--; 73 } 74 75 void COM(void) 76 { 77 78 U8 i; 79 for(i=0;i<8;i++) 80 { 81 82 U8FLAG=2; 83 //---------------------- 84 P2_1=0 ; //T 85 P2_1=1 ; //T 86 //---------------------- 87 88 while((!P2_0)&&U8FLAG++); 89 Delay_10us(); 90 Delay_10us(); 91 // Delay_10us(); 92 U8temp=0; 93 if(P2_0)U8temp=1; 94 U8FLAG=2; 95 while((P2_0)&&U8FLAG++); 96 97 //---------------------- 98 P2_1=0 ; //T 99 P2_1=1 ; //T 100 //---------------------- 101 //超时则跳出for循环 102 if(U8FLAG==1)break; 103 //判断数据位是0还是1 104 105 // 如果高电平高过预定0高电平值则数据位为 1 106 107 U8comdata<<=1; 108 U8comdata|=U8temp; //0 109 }//rof 110 111 } 112 113 //-------------------------------- 114 //-----湿度读取子程序 ------------ 115 //-------------------------------- 116 //----以下变量均为全局变量-------- 117 //----温度高8位== U8T_data_H------ 118 //----温度低8位== U8T_data_L------ 119 //----湿度高8位== U8RH_data_H----- 120 //----湿度低8位== U8RH_data_L----- 121 //----校验 8位 == U8checkdata----- 122 //----调用相关子程序如下---------- 123 //---- Delay();, Delay_10us();,COM(); 124 //-------------------------------- 125 126 void RH(void) 127 { 128 //主机拉低18ms 129 P2_0=0; 130 Delay(180); 131 P2_0=1; 132 //总线由上拉电阻拉高 主机延时20us 133 Delay_10us(); 134 Delay_10us(); 135 Delay_10us(); 136 Delay_10us(); 137 //主机设为输入 判断从机响应信号 138 P2_0=1; 139 //判断从机是否有低电平响应信号 如不响应则跳出,响应则向下运行 140 if(!P2_0) //T ! 141 { 142 U8FLAG=2; 143 //判断从机是否发出 80us 的低电平响应信号是否结束 144 while((!P2_0)&&U8FLAG++); 145 U8FLAG=2; 146 //判断从机是否发出 80us 的高电平,如发出则进入数据接收状态 147 while((P2_0)&&U8FLAG++); 148 //数据接收状态 149 COM(); 150 U8RH_data_H_temp=U8comdata; 151 COM(); 152 U8RH_data_L_temp=U8comdata; 153 COM(); 154 U8T_data_H_temp=U8comdata; 155 COM(); 156 U8T_data_L_temp=U8comdata; 157 COM(); 158 U8checkdata_temp=U8comdata; 159 P2_0=1; 160 //数据校验 161 162 U8temp=(U8T_data_H_temp+U8T_data_L_temp+U8RH_data_H_temp+U8RH_data_L_temp); 163 if(U8temp==U8checkdata_temp) 164 { 165 U8RH_data_H=U8RH_data_H_temp; 166 U8RH_data_L=U8RH_data_L_temp; 167 U8T_data_H=U8T_data_H_temp; 168 U8T_data_L=U8T_data_L_temp; 169 U8checkdata=U8checkdata_temp; 170 }//fi 171 }//fi 172 173 } 174 175 //---------------------------------------------- 176 //main()功能描述: AT89C51 11.0592MHz 串口发 177 //送温湿度数据,波特率 9600 178 //---------------------------------------------- 179 void main() 180 { 181 U8 i,j; 182 183 //uchar str[6]={"RS232"}; 184 /* 系统初始化 */ 185 TMOD = 0x20; //定时器T1使用工作方式2 186 TH1 = 253; // 设置初值 187 TL1 = 253; 188 TR1 = 1; // 开始计时 189 SCON = 0x50; //工作方式1,波特率9600bps,允许接收 190 ES = 1; 191 EA = 1; // 打开所以中断 192 TI = 0; 193 RI = 0; 194 SendData(str) ; //发送到串口 195 Delay(1); //延时100US(12M晶振) 196 while(1) 197 { 198 199 //------------------------ 200 //调用温湿度读取子程序 201 RH(); 202 //串口显示程序 203 //-------------------------- 204 205 str[0]=U8RH_data_H; 206 str[1]=U8RH_data_L; 207 str[2]=U8T_data_H; 208 str[3]=U8T_data_L; 209 str[4]=U8checkdata; 210 SendData(str) ; //发送到串口 211 //读取模块数据周期不易小于 2S 212 Delay(20000); 213 }//elihw 214 215 }// main 216 217 void RSINTR() interrupt 4 using 2 218 { 219 U8 InPut3; 220 if(TI==1) //发送中断 221 { 222 TI=0; 223 if(count!=5) //发送完5位数据 224 { 225 SBUF= outdata[count]; 226 count++; 227 } 228 } 229 230 if(RI==1) //接收中断 231 { 232 InPut3=SBUF; 233 indata[count_r]=InPut3; 234 count_r++; 235 RI=0; 236 if (count_r==5)//接收完4位数据 237 { 238 //数据接收完毕处理。 239 count_r=0; 240 str[0]=indata[0]; 241 str[1]=indata[1]; 242 str[2]=indata[2]; 243 str[3]=indata[3]; 244 str[4]=indata[4]; 245 P0=0; 246 } 247 } 248 }