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

📄 ds18b20.c

📁 由汇编语言编写的基于DS18B20的多点温度检测程序源码
💻 C
字号:
TIMER0  EQU     9216           ;TIMER0 10mS INTERRUPT
TMSH    EQU     (65536-TIMER0)/ 256
TMSL    EQU     (65536-TIMER0)MOD 256
COUNTL   EQU    1DH     
COUNTH   EQU    1EH 
STACK   EQU     60H
BPS9600  EQU    0FDH
TIME_FLAG BIT   2FH.0
ORG     0000H
LJMP    START
ORG     000BH
JMP     T0_INT  ;[ENABLE]  TIMER0 OVERFLOW INTERRUPT
ORG     0010H
START:  MOV     SP,#STACK
LCALL   SYSTEM_INIT 
LCALL   T_INIT
LCALL   ENABLE_INT
BEGIN:  JNB   p0.7,K0           ;判断按键是否按下,如果按下程序跳至K0
LCALL  FUW  
MOV  A,#0CCH            ;直访ROM	
LCALL WRITE1820 
MOV  A,#44H             ;温度转换命令	
LCALL  WRITE1820   
LCALL INT ;温度转换完全,再次初使化ds1820
MOV A,#55H
LCALL WRITE ;送入匹配ROM命令
JNB TIME_FLAG,LOOP1
MOV R0,#4AH
JMP LOOP2
LOOP1:    MOV R0,#42H
LOOP2:	  MOV R7,#08H
LOOP3:    MOV A,@R0
          LCALL WRITE ;送入匹配ROM命令
          INC R0
          DJNZ R7,LOOP3
         MOV  A,#0BEH            ;读便笺存储器		
         LCALL  WRITE1820
;------------------------------
         LCALL  RD1820     
         LCALL  JIS1820 
         LCALL	SHU    	
         LJMP	LOP
K0:     LCALL   JPSR0           ;调用键盘输入子程序
LOP:    LJMP BEGIN
FUW:	SETB	p3.0
NOP
CLR	p3.0
        MOV     R0,#0FAH   	
        DJNZ R0,$   
        SETB	p3.0			;然后拉高数据线
	NOP
	NOP
	NOP
	MOV	R0,#18H
LOOP25:	JNB	p3.0,LOOP35		;等待DS18B20回应
	DJNZ	R0,LOOP25
	CLR	p3.5			;清标志位,表示DS1820不存在
	LJMP	LOOP55
LOOP35:	SETB	p3.5			;置标志位,表示DS1820存在
	MOV	R0,#0FAH
LOOP45:	DJNZ	R0,LOOP45		;时序要求延时一段时间
LOOP55:	SETB	p3.0
	RET
;写DS18B20的子程序(有具体的时序要求)
WRITE1820:   
        CLR     EA
        MOV	R2,#8			;一共8位数据
	CLR	C
WR11:	CLR	p3.0
	MOV	R3,#6
	DJNZ	R3,$
	RRC	A
	MOV	p3.0,C
	MOV	R3,#23
	DJNZ	R3,$
	SETB	p3.0
	NOP
	DJNZ	R2,WR11
	SETB	p3.0
	SETB    EA
	RET
;读出温度数据(低位在41H,高位在40H) 
RD1820: 
        CLR     EA
        MOV	R4,#2			;读取字节数
	MOV	R1,#41H			;低位存入41H,高位存入40H
loop70:	MOV	R2,#8			;数据一共有8位
loop12:	CLR	C
	SETB	p3.0
	NOP
	NOP
	CLR	p3.0
	NOP
	NOP
	NOP
	SETB	p3.0
	MOV	R3,#9
loop22:	DJNZ	R3,loop22
	MOV	C,p3.0
	MOV	R3,#23
loop32:	DJNZ	R3,loop32
	RRC	A
	DJNZ	R2,loop12
	MOV	@R1,A
	DEC	R1
	DJNZ	R4,loop70
	SETB    EA
	RET
;数据处理子程序
JIS1820 :
MOV	A,41H
MOV	R0,#04H
LOOP50:	RR A
	DJNZ	R0,LOOP50
	ANL	A,#0FH
	MOV	31H,A
	MOV	R0,#03H
	MOV	A,41H
LOOP01:	RR A
	DJNZ    R0,LOOP01
	ANL	A,#01H
	MOV	B,#05H
	MUL     AB
	MOV	32H,A
	MOV	A,40H
	ANL	A,#07H
	MOV	B,#16
	MUL	AB
	ADD	A,31H
	MOV	B,#10
	DIV	AB
	MOV	34H,A
	MOV	A,B
	MOV	33H,A
	MOV	A,34H
	MOV	B,#10
	DIV	AB
	JNZ	ERROR
	MOV	A,40H
	JB	ACC.7,LOOP30
	MOV	35H,#0AH
	LJMP	LOOP40
LOOP30:	MOV	35H,#0BH
	LJMP	LOOP40
ERROR:	MOV 33H,#0CH
	MOV 34H,#0CH
	MOV 35H,#0CH
	MOV 32H,#0CH
BAOJ:   MOV     R0,#250
BAO:	SETB	P3.7
	LCALL   DALLY
	CLR	P3.7
	LCALL   DALLY
	DJNZ    R0,BAO
LOOP40:	RET
;键盘输入子程序
JPSR0:	MOV	33H,#0AH
	MOV     34H,#0AH
	MOV	R1,#34H
	MOV     35H,#0AH
	MOV	32H,#0AH
JPSR:	ACALL	KS1
	JNZ	LK1
	AJMP	JPSR
LK1:	ACALL	TM12S
	ACALL	KS1
	JNZ	LK2
	AJMP	JPSR
LK2:	MOV	R2,#0EFH
	MOV	R4,#00H
LK4:	MOV	A,R2
	MOV	P2,A
	JB	P0.0,LONE
	MOV	A,#00H
	AJMP	LKP
LONE:	JB	P0.1,LTWO
	MOV	A,#04H
	AJMP	LKP
LTWO:	JB	P0.2,NEXT
	MOV	A,#08H
LKP:	ADD	A,R4
	PUSH	ACC
LK3:	ACALL	KS1
	JNZ	LK3
	POP	ACC
	LJMP	KEND
NEXT:	INC	R4
	MOV	A,R2
JNB	P2.7,JPSR
	RL	A
	MOV	R2,A
	AJMP	LK4
KEND:	MOV	@R1,A
	DEC	R1
	CJNE	R1,#31H,JPSR
	MOV	38H,34H
	MOV	37H,33H
	MOV	36H,32H
LM:	LCALL	DSPLAY
	JB	P0.7,LM
	LCALL	TM12S
MC:	JNB	P0.7,MC
	RET
KS1:	MOV	P2,#00H
	MOV	A,P0
	CPL	A
	ANL	A,#0FH
	RET
;延时子程序
TM12S:	MOV	R7,#18H
TM9:	MOV	R6,#0FFH
TM6:	DJNZ	R6,TM6
	DJNZ	R7,TM9
	RET
;数据比较子程序
SHU:	CLR	C
	MOV	A,38H
	CJNE	A,34H,L1
	CLR	C
	MOV	A,37H
	CJNE	A,33H,L2
	CLR	C
	MOV	A,36H
	CJNE	A,32H,L3
JG:	LCALL	BJ
	LJMP	WW
L1:	JC JG
L2:	JC JG
L3:	JC JG
WW:	NOP
	RET
;报警子程序
BJ:	MOV	33H,#0CH
	MOV	34H,#0CH
	MOV	35H,#0CH
	MOV	32H,#0CH
JING:	MOV	R3,#250
J0G:	SETB	P3.7
	LCALL	DALLY
	CLR	P3.7
	LCALL	DALLY
	DJNZ	R3,J0G
	RET
;动态显示子程序
DSPLAY: MOV	DPTR,#TAB	;指定查表启始地址
	MOV	R0,#1
LOOP00:	MOV	R5,#5	        ;显示1000次
LOOP10:	MOV	A,32H           ;显示小数位
        MOVC	A,@A+DPTR	;查小位数的7段代码
	MOV	P1,A	        ;送出小位的7段代码
	CLR	P3.1	        ;开小位显示
	ACALL	DALLY	        ;显示1MS
	SETB	P3.1
	MOV	A,33H	        ;取个位数
	MOVC	A,@A+DPTR	;查个位数的7段代码
	MOV	P1,A	        ;送出个位的7段代码
	CLR	P3.2	        ;开个位显示
	ACALL	DALLY	        ;显示1MS
	SETB	P3.2
	MOV	A,34H	        ;取十位数
	MOVC	A,@A+DPTR	;查十位数的7段代码
	MOV	P1,A
	CLR	P3.3
	ACALL	DALLY
	SETB	P3.3
	MOV	A,35H
	MOVC	A,@A+DPTR
	MOV	P1,A
	CLR	P3.4
	ACALL	DALLY
	SETB	P3.4
	DJNZ	R5,LOOP10	;1000次没完循环
	DJNZ	R0,LOOP00	;4个1000次没完循环
        RET
DALLY:  MOV     14h,#6AH         ;延时1MS子程序
LOOP:   NOP
	DJNZ    14h,LOOP
	RET
TAB:	  DB        3FH      ;0 P1.0  接数码管段码的A
        DB        06H		;1 P1.1  接数码管段码的B
        DB        5BH		;2 P1.2  接数码管段码的C
        DB        4FH		;3 P1.3  接数码管段码的D
        DB        66H		;4 P1.4  接数码管段码的E
        DB        6DH		;5 P1.5  接数码管段码的F
        DB        7DH		;6 P1.6  接数码管段码的G
        DB        07H		;7 P1.7  接数码管段码的H
        DB        7FH		;8
        DB        6FH		;9       采用共阴的数码管三位
        DB	  00H		;        不显示数 
	DB	  40H		;        显示负号
	DB	  71H		;	 显示F
;//------------------------------------------------------------------------
INT:                    ;初始化ds1820子程序
        CLR EA
     L0:CLR P3.0        ;ds1820总线为低复位电平
        MOV R2,#200
  L111: CLR P3.0
        DJNZ R2,L111      ;总线复位电平保持400us
        SETB P3.0       ;释放ds1820总线
        MOV R2,#30
     L4:DJNZ R2,L4      ;释放ds1820总线保持60us
        CLR C           ;清存在信号(存在C=1,不存在c=0)
        ORL C,P3.0
        JC L0           ;存在吗?不存在则重新来
        MOV R6,#80
     L5:ORL C,P3.0
        JC L333
        DJNZ R6,L5      
        SJMP L0
  L333: MOV R2,#240
  L222: DJNZ R2,L222
        RET
;
WRITE:                  ;向ds1820写操作命令子程序
        CLR EA
        MOV R3,#8       ;写入ds1820的bit数,一个字节8个bit
 WR1:   SETB P3.0
        MOV R4,#8
        RRC A           ;把一个字节data(A)分成8个bit环移给 C
        CLR P3.0        ;开始写入ds1820总线要处于复位(低)状态
 WR21:  DJNZ R4,WR21     ;ds1820总线复位保持16us
        MOV P3.0,C      ;写入一个bit
        MOV R4,#20
 WR3:   DJNZ R4,WR3     ;等待40us
        DJNZ R3,WR1     ;写入下一个bit
        SETB P3.0       ;重新释放ds1820总线
        RET
READ:
        CLR EA
        MOV R6,#8       ;连续读8个bit
 RE1:   CLR P3.0        ;读前总线保持为低
        MOV R4,#4
        NOP
        SETB P3.0       ;开始读,总线释放
 RE2:   DJNZ R4,RE2     ;持续8us
        MOV C,P3.0      ;从ds1820总线读得一个bit
        RRC A           ;把读得的位值环移给 A
        MOV R5,#30
 RE3:   DJNZ R5,RE3     ;持续60us
        DJNZ R6,RE1     ;读下一个bit
        SETB P3.0       ;重新释放ds1820总线
        RET
DELAY:MOV R0,#100
DEL2:MOV R1,#10
DEL1:MOV R2,#250
DEL3:NOP
NOP
DJNZ R2,DEL3
DJNZ R1,DEL1
DJNZ R0,DEL2
RET
;//////////////////////////////////////////////////////////////////////////
;//INIT
SYSTEM_INIT:
        CLR     TIME_FLAG
        MOV	32H,#0AH
	MOV	33H,#0AH
	MOV	34H,#0AH
	MOV	35H,#0AH
	MOV	38H,#0FFH
	MOV	37H,#0FFH
	MOV	36H,#0FFH
	CLR	P3.7		;初始化	
MOV     COUNTL,#0F4H
	MOV     COUNTH,#01H
MOV     42H,#28H
	MOV     43H,#49H
	MOV     44H,#0C1H
	MOV     45H,#0D6H
	MOV     46H,#00H
	MOV     47H,#00H
	MOV     48H,#00H
	MOV     49H,#1AH
	MOV     4AH,#28H
	MOV     4BH,#0CAH
	MOV     4CH,#5EH
	MOV     4DH,#0F7H
	MOV     4EH,#00H
	MOV     4FH,#00H
	MOV     50H,#00H
	MOV     51H,#8EH
        RET
;--------------------------------------------------------------------------
NOP
NOP
NOP
NOP
LJMP    START
;--------------------------------------------------------------------------
T_INIT:                         ;定时器0初始化
        MOV     TMOD,#21H       ;TIMER0 16 BIT COUNT,TIMER1 9600BPS
        MOV     TH0,#TMSH
        MOV     TL0,#TMSL
        MOV     TH1,#BPS9600
	RET
;--------------------------------------------------------------------------
NOP
NOP
NOP
NOP
LJMP    START
;--------------------------------------------------------------------------
T0_INT:                         ;TIMER1 OVERFLOW INTERRUPT
   ;     CLR     EA
        MOV     TH0,#TMSH
        MOV     TL0,#TMSL
        PUSH    PSW
        PUSH    ACC
        PUSH    DPL
        PUSH    DPH
        PUSH    00H
        PUSH    01H
        PUSH    02H
        PUSH    03H
        PUSH    04H
        PUSH    05H
        PUSH    06H
        PUSH    07H
LCALL   TIMING
	       LCALL	DSPLAY
        POP     07H
        POP     06H
        POP     05H
        POP     04H
        POP     03H
        POP     02H
        POP     01H
        POP     00H
        POP     DPH
        POP     DPL
        POP     ACC
        POP     PSW
	       SETB    EA
        RETI
;--------------------------------------------------------------------------
NOP
NOP
NOP
NOP
LJMP    START
;--------------------------------------------------------------------------
ENABLE_INT:
;ENABLE TIMER0 INTERRUPT
;TCON(8 BITS) SETTING
        CLR     TF1
        CLR     TF0             ;CLEAR TF0
        SETB    TR0             ;TIMER0 START COUNT(16 BITS)
        CLR     IE1
        CLR     IT1             ;INT1 EXTERNAL INTERRUPT DISABLE
        CLR     IE0             ;CLEAR INT0 FLAG
        SETB    IT0             ;INT0 NEGATIVE RISING TRIGGER
;SCON(8 BITS) SETTING
        CLR     RI
        CLR     TI              ;DISABLE TRANSMIT
;IP(8 BITS) SETTING
        SETB    PX0             ;INT0 HIGHER PRIORITY
;IE(8 BITS) SETTING
        SETB    ET0             ;ENABLE TIMER0 INTERRUPT
;ENABLE SYSTEM INTERRUPT
        SETB    EA              ;ENABLE SYSTEM INTERRUPT
        RET
;--------------------------------------------------------------------------
TIMING:        
MOV     R0,#COUNTL
	MOV     R1,#COUNTH
DEC     @R0
L42:	MOV     A,@R0
	CJNE    A,#0FFH,L44
	DEC     @R1
	MOV     A,@R1
	CJNE    A,#0FFH,L44
	MOV     @R0,#0F4H
MOV     @R1,#01H     ;计数一秒钟:0x0064,计数五秒钟:0x01f4,计数一分钟:0x1770
	CPL    TIME_FLAG
L44:    RET
END	

⌨️ 快捷键说明

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