51单片机作的电子钟程序在很多地方已经有了介绍, 对于单片机学习者而言这个程序基本上是一道门槛,掌握了电子钟程序, 基本上可以说51单片机就掌握了80%。常见的电子钟程序由显示部分, 计算部分, 时钟调整部分构成。 : F3 O: p) S9 q# C8 n
时钟的基本显示原理:时钟开始显示为0时0分0秒,也就是数码管显示000000,然后每秒秒位加1 ,到9后,10秒位加1,秒位回0。10秒位到5后,即59秒 ,分钟加1,10秒位回0。依次类推,时钟最大的显示值为23小时59分59秒。这里只要确定了1秒的定时时间, 其他位均以此为基准往上累加。
( N0 w t* @+ K) A6 Q 开始程序定义了秒, 十秒, 分, 十分,小时, 十小时,共6位的寄存器, 分别存在30h,31h,32h,33h,34h,35h单元,便于程序以后调用和理解。
( m8 Z0 p# p/ ^. y 6个数码管分别显示时、分、秒,一个功能键,可以切换调整时分秒、增加数值、熄灭节电等功能全部集一键。 & s8 }4 K6 L& ~- b) x& \
" D0 [+ N; I- a# x: r: S% N# ]
8 a+ T# T. }$ J
# p( t1 Y e; Z/ g. V M 以下是部分汇编源程序,购买我们产品后我们用光盘将完整的单片机汇编源程序和烧写文件送给客户。- m. f% Q& s4 r
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
: u! |' A+ I+ z$ ^8 h/ [: D;; 中断入口程序 ;; (仅供参考)
# G' Y9 I4 i3 l4 D6 e& X7 A7 b9 L# W;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; L. B* }8 T: M: V! M9 ~/ L6 C7 k
;
; H) O& f% D2 F6 l9 D( F4 [* yORG 0000H ;程序执行开始地址
5 [3 _4 z0 k0 u, gLJMP START ;跳到标号START执行
: I5 u/ O8 _& p& Q* L, ?* FORG 0003H ;外中断0中断程序入口# t& z& M* u' d6 ?# J
RETI ;外中断0中断返回5 ~0 F: ~$ {6 C. o
ORG 000BH ;定时器T0中断程序入口* t0 t* L4 L: p2 f
LJMP INTT0 ;跳至INTTO执行
. p3 F$ {0 W3 n( gORG 0013H ;外中断1中断程序入口
6 n9 c1 d0 u0 vRETI ;外中断1中断返回7 p* {7 d. A# C- R+ \5 u c" m
ORG 001BH ;定时器T1中断程序入口
2 s: a4 ]8 O$ J+ O5 |# uLJMP INTT1 ;跳至INTT1执行 B Y; ]% \# S( [3 e) l" \
ORG 0023H ;串行中断程序入口地址
0 H% i- K8 Y" Y8 X6 T$ X# _3 \0 G' @RETI ;串行中断程序返回
/ ~% | L) h, `4 A& F;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
. N; t& u6 P& K t: ?;; 主 程 序 ;;
3 P, v' F: _0 W* g( k- u;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2 }; r6 _7 R; n0 j;
& _) C. @& L+ k, q. C" G" _ xSTART: MOV R0,#70H ;清70H-7AH共11个内存单元
5 P- h. m; v, G" s; G: ]& d; @, jMOV R7,#0BH
" a; N, ?( _$ E; q5 x, k. q;clr P3.7 ;
2 n H- E4 d1 N6 m; G* rCLEARDISP: MOV @R0,#00H ;
# V* ^( L$ E6 u; QINC R0 ;
5 H& o1 q# q* j* Z% LDJNZ R7,CLEARDISP ;# Q+ Z3 G1 C! i5 l9 i
MOV 20H,#00H ;清20H(标志用)
8 D( w# M+ T# `+ @0 cMOV 7AH,#0AH ;放入"熄灭符"数据! j* i$ U" p; N( P0 y3 t' ^
MOV TMOD,#11H ;设T0、T1为16位定时器$ T/ D y9 ]+ } S0 H8 L7 ?
MOV TL0,#0B0H ;50MS定时初值(T0计时用)
7 \* y5 }: X& \+ f- V+ E+ T* \; \. \& XMOV TH0,#3CH ;50MS定时初值
2 ]6 B" |% y' OMOV TL1,#0B0H ;50MS定时初值(T1闪烁定时用)
* i! n! V( i# w0 A mMOV TH1,#3CH ;50MS定时初值( U* r/ k! Y- y
SETB EA ;总中断开放
# _/ R" x- k& [' sSETB ET0 ;答应T0中断* V" D, b d/ j& c( w
SETB TR0 ;开启T0定时器+ R& j' j- @% H! q8 \* Z
MOV R4,#14H ;1秒定时用初值(50MS×20)$ _" ~# }" C: F; \ Y/ ]! x; W
START1: LCALL DISPLAY ;调用显示子程序
$ b* ~$ x+ c" @+ w" l5 QJNB P3.7,SETMM1 ;P3.7口为0时转时间调整程序
1 z. Z9 C7 r5 Y$ G# rSJMP START1 ;P3.7口为1时跳回START1
) f& t& D, s+ z* A1 YSETMM1: LJMP SETMM ;转到时间调整程序SETMM4 ~6 \7 q: R% a2 i
;* \' S! D# ^, s. ]
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
r- \1 g& r+ V3 @" H* ~% l;; 1秒计时程序 ;;
3 D% o5 d: a" [;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;3 S, o! k* F& X* s! C- R5 ?
;T0中断服务程序! |" r0 M$ U4 n) C3 n
INTT0: PUSH ACC ;累加器入栈保护% G1 k0 }! T: X
PUSH PSW ;状态字入栈保护) W0 J. L) i9 Z& J& a
CLR ET0 ;关T0中断答应2 w$ o2 b4 s7 Y9 ~
CLR TR0 ;封闭定时器T0" m* p3 k1 O0 G
MOV A,#0B7H ;中断响应时间同步修正
( Y5 P& K' E" |$ B; |$ u& UADD A,TL0 ;低8位初值修正
& T4 z P% E8 x- B$ E1 _. P0 B* t8 vMOV TL0,A ;重装初值(低8位修正值)
# B. o. u& j4 E9 oMOV A,#3CH ;高8位初值修正
. A) p7 [! `; P- yADDC A,TH0 ;
" {( x* {' @. l; F% W' [MOV TH0,A ;重装初值(高8位修正值)
( n! C2 Y- a6 jSETB TR0 ;开启定时器T0
6 Y. V M4 Z: m' X8 G4 A9 v# k. qDJNZ R4, OUTT0 ;20次中断未到中断退出& z, q c2 Z+ n, ~$ S+ \
ADDSS: MOV R4,#14H ;20次中断到(1秒)重赋初值
! A2 I) D) {6 m5 z$ [6 c+ a, uMOV R0,#71H ;指向秒计时单元(71H-72H)( e9 B+ E' p8 _& h
ACALL ADD1 ;调用加1程序(加1秒操作)
7 j/ t# j! p% a: i, |MOV A,R3 ;秒数据放入A(R3为2位十进制数组合)# r% w! q5 Y/ q$ R) {. m p0 w5 K/ M( z
CLR C ;清进位标志
- Y$ b2 u; ^ {0 [CJNE A,#60H,ADDMM ;
* X, n7 ?/ V+ t) I3 w/ T1 j# m, SADDMM: JC OUTT0 ;小于60秒时中断退出
) x8 U- Q* I& e n% XACALL CLR0 ;大于或即是60秒时对秒计时单元清0
. ?5 O5 Y& F, O5 \( M T0 J& s4 TMOV R0,#77H ;指向分计时单元(76H-77H); ?" U9 B$ F/ L$ r' |6 v5 g& q
ACALL ADD1 ;分计时单元加1分钟: j2 G3 \ z/ h0 q% I
MOV A,R3 ;分数据放入A9 g# c( I# W, [5 [. n6 I, t* l
CLR C ;清进位标志$ m* |( O1 j7 s
CJNE A,#60H,ADDHH ;
( S% x7 J: I4 ^' \& aADDHH: JC OUTT0 ;小于60分时中断退出: w; G0 c& {8 ?
ACALL CLR0 ;大于或即是60分时分计时单元清0
6 e4 E% A$ f# ?; R) eMOV R0,#79H ;指向小时计时单(78H-79H)3 D' a4 v; u/ o' @* m# A
ACALL ADD1 ;小时计时单元加1小时
. n& b) B4 o8 J) i& tMOV A,R3 ;时数据放入A; I( o# ]/ r9 P% G; D
CLR C ;清进位标志% V* Y8 B" F+ Z1 R
CJNE A,#24H,HOUR ;, |. v' J( b, F8 K. \
HOUR: JC OUTT0 ;小于24小时中断退出
2 W) c; T7 [& ?, |! W: ^ACALL CLR0 ;大于或即是24小时小时计时单元清0
. I7 D* l/ L' U* ?OUTT0: MOV 72H,76H ;中断退出时将分、时计时单元数据移
/ j+ r# R6 N5 P' J* \4 e/ ~MOV 73H,77H ;入对应显示单元# ] i4 m0 O4 @; E
MOV 74H,78H ;/ c6 N! b: N) T0 S
MOV 75H,79H ;
; c8 r2 [# q: M3 [9 o# R. KPOP PSW ;恢复状态字(出栈)
; t6 y+ C- D! R0 q+ O6 g" hPOP ACC ;恢复累加器
) k( f. G, q. @) D& [# BSETB ET0 ;开放T0中断
( x9 F7 q) b# K& N3 SRETI ;中断返回
9 f1 N$ V0 V, g! a;
5 z- x( b% f1 H* i5 f S;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;- F- i" J. a- H* J
;; 闪动调时 程 序 ;;
" c: E) R" A ~) X/ T;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
9 Y5 D- q" N0 [: `' O7 h;T1中断服务程序,用作时间调整时调整单元闪烁指示
) P" S. H3 x6 I0 U5 S8 }& FINTT1: PUSH ACC ;中断现场保护
! |# o# b- ?% D( J1 kPUSH PSW ;* q3 W' A6 J% e# i' J% g
MOV TL1, #0B0H ;装定时器T1定时初值
. H) V& Z: U4 E# h- {, u+ y5 aMOV TH1, #3CH ;
4 ^, r+ B5 e/ y1 w# i7 z) b% eDJNZ R2,INTT1OUT ;0.3秒未到退出中断(50MS中断6次)
# F1 `# H# j- P: E5 ~) I, x) AMOV R2,#06H ;重装0.3秒定时用初值
9 [0 E. L' `: g' {0 E$ aCPL 02H ;0.3秒定时到对闪烁标志取反
* j6 v( A, d3 p" Y! U$ ?JB 02H,FLASH1 ;02H位为1时显示单元"熄灭"
' Q, V2 ~6 I: L" U& q, ?* h' OMOV 72H,76H ;02H位为0时正常显示
: n8 Z6 u. e. w9 {# ?MOV 73H,77H ;
3 `5 `; k3 n' |* K! f- D. h6 m- bMOV 74H,78H ;
; P8 e! f) @% M! I" e4 CMOV 75H,79H ;
+ m* o3 v8 [7 M/ P/ ?* eINTT1OUT: POP PSW ;恢复现场
: f4 Z) X2 j+ s" u* P8 ^POP ACC ;3 C3 k b: ?& ~% j a ?8 I7 i
RETI ;中断退出
5 D5 X: |6 q0 _* A- t, ]2 HFLASH1: JB 01H,FLASH2 ;01H位为1时,转小时熄灭控制" T- U7 C" f8 V3 x. N
MOV 72H,7AH ;01H位为0时,"熄灭符"数据放入分# j- x& e# H- E1 S8 V, i5 F
MOV 73H,7AH ;显示单元(72H-73H),将不显示分数据
- f5 p5 h- M' a# y( R" |MOV 74H,78H ;7 k3 |% i: x0 ^: D
MOV 75H,79H ;
3 B% i2 e: S4 f; PAJMP INTT1OUT ;转中断退出
2 s- t2 x4 @, XFLASH2: MOV 72H,76H ;01H位为1时,"熄灭符"数据放入小时; [" {- ?; @* B7 N# O- U
MOV 73H,77H ;显示单元(74H-75H),小时数据将不显示
' {7 w8 K0 D$ d% i) o' hMOV 74H,7AH ;6 R7 l6 l. E- P6 }& \ l
MOV 75H,7AH ;3 D+ d/ M8 d* D0 T* K
AJMP INTT1OUT ;转中断退出% ?6 b* l( I+ U t
;
5 m/ S& v; W+ x' ~; g;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
6 W! i4 E5 B3 n0 F0 Q7 z;; 加1子 程 序 ;;" ^$ O% W/ {' `2 ]
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;/ n5 b- E: U- O6 N7 J- B
;
- ^) r9 n: u. X) W" mADD1: MOV A,@R0 ;取当前计时单元数据到A/ I# d) R% q4 x" z
DEC R0 ;指向前一地址
" l, W' D: f0 |- |. SSWAP A ;A中数据高四位与低四位交换$ g9 ~6 J# X; x0 @/ N
ORL A,@R0 ;前一地址中数据放入A中低四位0 i2 K: J: _8 T5 R
ADD A,#01H ;A加1操作9 A/ M6 O0 A j0 d9 F
DA A ;十进制调整) ~ b- \7 d$ z' O
MOV R3,A ;移入R3寄存器
; u% ^4 I0 e+ N' k+ W7 Y& p; YANL A,#0FH ;高四位变0, R: D# `" {4 S2 \; u" y
MOV @R0,A ;放回前一地址单元8 r E$ ^, D" [* @! x
MOV A,R3 ;取回R3中暂存数据 o9 s/ p6 n9 L# e" x3 Q
INC R0 ;指向当前地址单元" O$ R: o; s1 y0 O
SWAP A ;A中数据高四位与低四位交换
. A) {$ N; o! k7 LANL A,#0FH ;高四位变0
4 @) b7 a b7 X5 h# k* g8 gMOV @R0,A ;数据放入当削地址单元中. o8 B% ~9 @& M
RET ;子程序返回
( s) E3 q& L; ~+ k;
9 g: C$ e0 h) X& w8 t/ V0 _;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
4 z' \6 v K) ?;; 清零程序 ;;
$ v6 {& Y4 C; Z( y% s: l* J;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;) x; O- t9 r; A, _: I" V
;.............
1 @4 u) \- u# P; e# z6 G, K7 y;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;8 Y3 D% c+ a6 |$ v3 a) m
;; 时钟调整程序 ;;, B6 ]8 {: K' Z
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;( o q: T; } N, C9 T1 U2 [
;当调时按键按下时进入此程序6 G7 ?; q/ l* r. N% ^ ^; k
SETMM: cLR ET0 ;关定时器T0中断# ` O7 z- R, G h; d4 h! R" ]! T4 A
CLR TR0 ;封闭定时器T0
- I4 T* `/ x w+ [LCALL DL1S ;调用1秒延时程序2 G- i: \6 v- ~$ D% Q
JB P3.7,CLOSEDIS ;键按下时间小于1秒,封闭显示(省电)
" A, m5 [- I6 F& g0 JMOV R2,#06H ;进入调时状态,赋闪烁定时初值
9 F+ d e" R: C9 t! u- }SETB ET1 ;答应T1中断
" ]- Q( u+ H) {3 W3 I& q1 USETB TR1 ;开启定时器T14 R6 o9 K' Z" G# Y& Q
SET2: JNB P3.7,SET1 ;P3.7口为0(键未开释),等待. N Z( ^; K! v# O( k6 M0 t! o
SETB 00H ;键开释,分调整闪烁标志置1( Q2 w* M1 O+ T8 g
SET4: JB P3.7,SET3 ;等待键按下! I# e/ q E- r6 c, Z
LCALL DL05S ;有键按下,延时0.5秒( i3 J8 A* c6 |. ^' H. K# e; }
JNB P3.7,SETHH ;按下时间大于0.5秒转调小时状态) W& r- e( q) v0 \) h k/ ^' c q% L
MOV R0,#77H ;按下时间小于0.5秒加1分钟操作
) }! B E P9 wLCALL ADD1 ;调用加1子程序3 f! U" r+ ?, T' Q
MOV A,R3 ;取调整单元数据4 Y8 {8 t2 L4 v: z
CLR C ;清进位标志
/ a$ o8 o# s$ o r8 c! iCJNE A,#60H,HHH ;调整单元数据与60比较
( t0 [4 Q0 F6 ]7 ~' r0 KHHH: JC SET4 ;调整单元数据小于60转SET4循环
: H$ f j' V. N* {LCALL CLR0 ;调整单元数据大于或即是60时清0
' A: w- S4 X: ] G% _, z4 SCLR C ;清进位标志
) O; F8 Z( X9 ~5 b& l- SAJMP SET4 ;跳转到SET4循环2 h/ X: |! f* P8 D3 d+ P
CLOSEDIS: SETB ET0 ;省电(LED不显示)状态。开T0中断: Y# }/ o' D! s, ?# s
SETB TR0 ;开启T0定时器(开时钟)
+ D x0 }! D) z5 K2 c, nCLOSE: JB P3.7,CLOSE ;无按键按下,等待。
* z7 U- }5 ]/ |LCALL DISPLAY ;有键按下,调显示子程序延时削抖
, M. M! c& t; k9 WJB P3.7,CLOSE ;是干扰返回CLOSE等待. e' ]2 g7 H2 P$ [9 P* c
WAITH: JNB P3.7,WAITH ;等待键开释$ ~6 }. }, ~# Q Q
LJMP START1 ;返回主程序(LED数据显示亮)# W. y9 f4 W$ d c4 r: h
SETHH: CLR 00H ;分闪烁标志清除(进入调小时状态)# i7 X, d, g6 e
SETHH1: JNB P3.7,SET5 ;等待键开释& P- |$ r; y: i) x
SETB 01H ;小时调整标志置1
0 C/ s% a' x: J" |7 CSET6: JB P3.7,SET7 ;等待按键按下8 m! O! n+ ~# C9 f) E$ Y8 i
LCALL DL05S ;有键按下延时0.5秒9 c2 v, O L( Z- u& \+ I9 K$ J
JNB P3.7,SETOUT ;按下时间大于0.5秒退出时间调整
1 P% J$ W; C: e$ g. uMOV R0,#79H ;按下时间小于0.5秒加1小时操作6 l3 S: i o3 n5 q
LCALL ADD1 ;调加1子程序
$ R' D1 f% h/ f: p# b- l7 h3 kMOV A,R3 ; `- ~7 H5 w5 b: D) ]' B) s
CLR C ;& z: k' e+ M, v, r- `
CJNE A,#24H,HOUU ;计时单元数据与24比较
$ w* c5 D/ u7 j5 L$ D. ZHOUU: JC SET6 ;小于24转SET6循环$ x ~% l1 r1 S5 M2 S D* L
LCALL CLR0 ;大于或即是24时清0操作
$ Y. S+ l5 r. I; Z# ?7 H7 VAJMP SET6 ;跳转到SET6循环 h0 k" G. P' F4 h
SETOUT: JNB P3.7,SETOUT1 ;调时退出程序。等待键开释
1 {/ E9 x" p2 ^* G. j( G. v6 ?; }LCALL DISPLAY ;延时削抖
, G y0 n Y3 Y8 F/ o$ _JNB P3.7,SETOUT ;是抖动,返回SETOUT再等待. j9 k6 d- l9 v# T
CLR 01H ;清调小时标志; r! ?3 g: E' k9 a
CLR 00H ;清调分标志) c- w' p$ @9 c" d" W# T+ T% T
CLR 02H ;清闪烁标志
+ a0 p3 h0 B/ \5 z l% p% A9 W% yCLR TR1 ;封闭定时器T1* L# N- q6 U: `3 Z* {, G- H+ x8 U
CLR ET1 ;关定时器T1中断6 n/ t7 k! C) p8 @. P
SETB TR0 ;开启定时器T0
# J4 q8 @8 D( KSETB ET0 ;开定时器T0中断(计时开始)6 G% P# d# I. V2 @
LJMP START1 ;跳回主程序) f* K* x8 O; J& J' `
SET1: LCALL DISPLAY ;键开释等待时调用显示程序(调分) A5 b: v# e* G' K- Q7 z7 ~
AJMP SET2 ;防止键按下时无时钟显示5 f) S6 }* q: e' D+ C
SET3: LCALL DISPLAY ;等待调分按键时时钟显示用
/ b; o6 R1 |5 oAJMP SET41 m, g9 b( c( x1 m8 r ]
SET5: LCALL DISPLAY ;键开释等待时调用显示程序(调小时)
+ N! W0 f8 E( }, L6 ?AJMP SETHH1 ;防止键按下时无时钟显示5 ^* M5 o/ @: \9 c3 z
SET7: LCALL DISPLAY ;等待调小时按键时时钟显示用+ I% W( Q# }4 Q* M5 N! M( S
AJMP SET6# N- T B$ r% E. L: K
SETOUT1: LCALL DISPLAY ;退出时钟调整时键开释等待
: T# c) X0 j8 p6 s: T: X3 r: lAJMP SETOUT ;防止键按下时无时钟显示
8 w2 T2 [) l" ?8 G$ V0 I( b;( ?& s6 n/ @8 D: C: @* Y! N5 ^1 f
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;3 m; V' f4 G+ |1 T7 y% [
;; 显示程序 ;;( p D) {. ~7 e0 M" @- ~5 @/ F6 V
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;% B8 r: B$ F! \2 V
$$$$$$$$$$$$$$$$$$$$$$$$$$$7 U+ _* G! k! z; [) R+ Q
;1MS延时程序,LED显示程序用
- ~( p* d- `7 e, wDL1MS: MOV R6,#14H' z0 }8 t4 Y7 r; W
DL1: MOV R7,#19H
' F6 c6 b' `/ X' fDL2: DJNZ R7,DL2
0 k- ~4 s, N% i; C, WDJNZ R6,DL1$ x, f% F5 _) b4 v
RET0 x: e$ G" Q$ T9 K* v: R: h7 x2 d
;20MS延时程序,采用调用显示子程序以改善LED的显示闪烁现象. z9 U9 x) |: z( {+ `
DS20MS: ACALL DISPLAY
) ?3 S: c. B, r8 P) `ACALL DISPLAY( T! A8 t+ a ?" B. b0 O) L$ a
ACALL DISPLAY
$ ^7 u8 @& L4 Z* C' m4 MRET. ?7 R! \ I1 f6 U' f5 Q7 _) ]! s0 B
;延时程序,用作按键时间的长短判定
0 U2 ~5 o0 R0 X% i# r& x) tDL1S: LCALL DL05S
O! m: o! u* S; A* r# F7 {4 x8 c7 eLCALL DL05S9 @' h+ T5 z' h& g5 L: [" E; F
RET, b0 c& [& J+ i! E
DL05S: MOV R3,#20H ;8毫秒*32=0.196秒' Z3 X$ O! h; B l M5 d
DL05S1: LCALL DISPLAY! \1 M; a) S3 a4 f
DJNZ R3,DL05S1. O2 O" l5 ]% q8 @" J
RET
9 y4 Z/ }; ]6 X5 e7 UEND ;程序结束- M6 z/ {6 y, w- G4 y
|