方法一:
ORG 0000H
LJMP START
ORG 000BH //定时器0中断向量地址
LJMP TIME0 //跳至中断服务函数
ORG 30H
START:
MOV A,#0feH //一般LED是用灌电流,这里初值赋0xfe,灌电流接法,拉电流改成0x01
MOV P1,A //输出到P1口
MOV TMOD,#01H //方式1,16位定时器,须手动重新赋定时值
MOV TH0 ,#00H //根据需要来修改定时值,这里赋值0,计数65536次
MOV TL0 ,#00H
SETB EA //开全局中断
SETB ET0 //开定时器0中断
SETB TR0 //启动定时器0,开始计数
LOOP:
LJMP LOOP //死循环等待定时器溢出中断
TIME0:
MOV TH0 ,#00H //重新赋计时器初值,这里是0x0000,实际上可以省略,计数溢出
//后,会自动从0开始计数
MOV TL0 ,#00H
RL A //累加器内容循环左移,C编译器一般没有此类指令,但貌似Keil里
//有个头文件有函数可以实现某变量循环移位
MOV P1,A //移位后输出到P1口,驱动LED
RETI //中断函数返回
END
//总结:采用了循环移位指令,省略判断分支;移位时间:65536*晶振周期*12,使人眼辨别得到。
//*******************************************************************
方法二:
ORG 0000H
LJMP START
ORG 100H
START:
MOV A,#0feH //一般LED是用灌电流,这里初值赋0xfe,灌电流接法
//拉电流改成0x01
LOOP:
MOV P1,A //输出到P1口
CALL Delay //调用延时,是人眼辨别得到
RL A //累加器内容循环左移,C编译器一般没有此类指令
//但貌似Keil里有个头文件有函数可以实现某变量循环移位
SJMP LOOP //死循环,循环移位输出驱动LED
Delay: //延时时间决定于R0*R1
MOV R0,#200
DelayH:
MOV R1,#200
DelayL:
DJNZ R1,DelayL //减1非零跳转,Decrease JMP Not Zero
DJNZ R0,DelayH
RET
END
//总结:没有用到中断,节省了定时器