微型计算机:8255编程

1、题目

当开关合上,16个LED灯从上而下依次循环发光,每次只能点亮一个LED灯;

当开关打开,保持当前LED灯的点亮状态不变,下次开关合上时,从当前的LED灯开始点亮。

2、电路图

2.1总图

在这里插入图片描述

2.2分图

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

3、编程

;当开关合上,16个LED灯从上而下依次循环发光,每次只能点亮一个LED灯(灯亮 -> 延时 -> 灯灭(下一个亮)  ->延时...)
;当开关打开,保持当前LED灯的点亮状态不变,下次开关合上时,从当前的LED灯开始点亮。
;输入端口为IO5(0000 0010 1110 0**0B)


;定义符号常量
IOCON   EQU   02D6H ;控制口(0000 0010 1110 0110B),输出
IOA     EQU   02D0H ;端口A (0000 0010 1110 0000B),输入
IOB     EQU   02D2H ;端口B (0000 0010 1110 0010B),输入
IOC     EQU   02D4H ;端口C (0000 0010 1110 0010B),输入

CODE 	SEGMENT  
        ASSUME CS:CODE
        
        		;初始化8255A(往控制口写控制字,即对CPU而言就是输出)
START:	 		MOV AL,10001001B ;从左到右:1表示工作方式控制字 00表示工作方式选择 0端口A输出 1端口C输入 0端口B工作方式选择 0端口B输出 1端口C输入。CPU控制字经AL输出
				MOV DX,IOCON     ;口地址为16位,写入控制口输出,将控制口地址送给DX
				OUT DX,AL        ;把工作方式控制字写入控制口 
				MOV BX,0001H     ;BX的值控制哪个灯亮即为1,;初始状态PA0=1(无论开始开关断开还是闭合,总是第一个亮着的)
		
				;从上往下A端口、B端口各决定8个灯(BX = BH + BL)
NEXT:			MOV AL,BL        ;将BL(初始是01H送给AL,即端口A控   制的8个灯)
				MOV DX,IOA       ;将端口A地址送给DX 
				OUT DX,AL        ;输出端口A灯亮的情况
				
				MOV AL,BH        ;将BH(初始是00H送给AL,即端口B控制的8个灯)
				MOV DX,IOB       ;将端口B的地址送给DX
				OUT DX,AL	     ;输出端口B灯亮的情况
					
				MOV DX,IOC       ;将端口C的地址送给DX
				IN  AL,DX        ;读取PC口检测开关状态
				TEST AL,00000010B;测试PC1是0还是1
				JNZ NEXT           ;ZF=0,即PC1=1(开关断开)跳转到NEXT(ZF零标志位,结果为0ZF=1,结果不为0ZF=0),对当前BX再次输出(开关一直断开,一直重复当前灯亮的代码,就是看起来灯亮暂停了)
		 		ROL BX,1         ;开关闭合,ROL对BX循环左移,控制流水灯效果(如:第一次执行到此处,BX(0001H -> 0002H,将会(继续执行A1内容到OUT后)由第一个灯亮变成第二个灯亮)
 		
Delayed_jump:	CALL DELAY       ;调用子函数,延时控制
		     	JMP NEXT	     ;跳转到NEXT,NEXT决定下一个动作灯是亮还是灭(灯亮 -> 延时 -> 灯灭(下一个亮)  ->延时)
		
DELAY PROC    
		     	MOV CX,0FFFFH    ;LOOP 指令循环次数须放在CX 中
Null_loop:	 	NOP              ;NOP指令执行时花去一个时钟周期(多个NOP就花去多个时钟周期),可把它用在延时程序中作为循环体,用以估计一个延时时间
		     	LOOP Null_loop   ;空循环达到延时目的(这种软件延时时间上不太精准)
		     	RET      
DELAY ENDP	
		
CODE  	ENDS
	END	START








發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章