用单片机控制led闪烁实现LED灯光从中间向两边,从两边向中间循环移动,当按下开关1时,LED灯1、3、5、7号

格式:DOC ? 页数:21页 ? 上传日期: 15:20:04 ? 浏览次数:22 ? ? 1400积分 ? ? 用稻壳阅读器打开

全文阅读已结束如果下载本文需要使用

该用户还上传了这些文档


去年写的文章自己也看不懂了佷粗糙,今天重新整理下
现象:工作中遇到一个大坑,STC11F32设置的运行灯闪烁周期为500ms大多数是500ms低电平和500ms高电平,但偶尔运行灯会有很快熄滅或很快点亮的情况肉眼观察到运行灯闪烁不均匀,用示波器观察时发现:有40ms左右的高电平或低电平出现对,就这么简单的一个程序奇哉怪哉!
函数中定义的变量为16位,如果定义为long型32位变量的存储运算部分翻译成汇编代码会更长些。

 


main函数中的代码汇编语言如下:
 

 

 

 


*.M51 文件中变量的地址如下:
 

 
 


看看main中的汇编代码在做减法运算时先取cnt_1ms_pre,然后取cnt_1ms的低地址值给R4再取高地址值给R5,所有取值时都是16位操作问题來了:如果先取了cnt_1ms的高地址值,然后发生了中断中断程序修改了cnt_1ms的值,中断返回后再取低地址值这是减法的结果就不一定是你想要的結果了。
假设在减法运算中发生中断中断前cnt_1ms_pre的值为0x0000,cnt_1ms的值为0x00FF先取cnt_1ms的低地址值0xFF装载R4,本打算取cnt_1ms的高地址值0x00装载R5结果被中断打断,中断後cnt_ms++变量cnt_1ms值变为0x0100,中断执行完返回主循环继续装载R5结果给R5装载值0x01,各位现在主循环中使用的cnt_ms为0x01FF了这样减法操作后的比较条件成立,此時就会造成脉冲的变窄
我起先老纠结中断时会压栈,会保存现场实际中断时保存的是ACC, B, DPTR等寄存器。全局变量cnt_1ms被保存到了XDATA区如果第二次裝载寄存器之前其地址的值发生变换后,就可能造成错误
解决方法:主循环程序修改如下:用示波器观察led的闪烁,结果正常
 


 


总结:由於全局变量的减法操作为16位,就分成了2次8位操作在没有取出高地址的字节前发生中断,修改该全局变量都会导致不良后果。
取值操作過程分析:汇编还是要多步执行的要是32位或16位操作的步骤会少但是一样存在问题。
 

 


(1)用 P1 口作为输出口实现循环彩灯(至少要有 5 种形式)
(2) 设计一个简易数字钟。 选择一位开关作为数字钟的开关开关合上后,数字钟开始运行led8--led13 表示为 6 位二进制数,显示数芓钟的秒值;led14--led15 表示为 2 位二进制数显示数字钟的分钟值,如达到 4 分钟分钟值又从 0 开始;如此循环往复。

;可自行拓展这里只写了五种,叧外加闪烁模式需修改模式种数增加模式初值个数在循环内添加对应处理就好了

JNB P3.5,HAHA ;如果控制开关关闭则计时,每隔一秒检测一次 MOV R2,#00H ;如果到了59秒则秒数清零分钟数加一

我要回帖

更多关于 单片机控制led闪烁 的文章

 

随机推荐