最近在做汇编 有几行代码不懂 请大牛讲解 用的是8255芯片

最近在做汇编 有几行代码不懂 请大牛讲解 用的是8255芯片,第1张

mov dx,PortA --DX是PortA的接口地址

mov dx,PortA+1--DX是PortB的接口地址

……

mov dx, PortA+3--DX是控制寄存器的接口地址

mov al,80H

out dx,al ;PA、PB口初始化为基本输出方式

编程实现对 8 个 LED 的输出控制 将实验箱中的 8255 片选信号连接到 218H~21FH,将 8255 的 4 个寄存器地址(A、B、 C 端口及控制字寄存器端口)设置为 218H~21BH。将 8255 的端口 A 的 8 个引脚:PA0~PA7 与 8 个 LED 对应相连,然后打开实验箱电源,最后编程对 8 个 LED 进行显示控制。

程序清单:

CODE SEGMENT

ASSUME CS:CODE

START: MOV DX,21BH

MOV AL,80H

OUT DX,AL ;工作方式初始化

MOV DX,218H

MOV AL,0FEH ;设置输出数据,即显示模式

MOV CX,80 ;设置循环次数

LN: OUT DX,AL

ROL AL,1

CALL DELAY ;调用延迟程序

LOOP LN

MOV AH,4CH

INT 21H ;返回 dos

DELAY PROC ;延迟子程序

PUSH CX

MOV BX,2000

A0: MOV CX,3000

A1: LOOP A1

DEC BX

JNZ A0

POP CX

RET DELAY

ENDP

CODE ENDS

END START。吴鉴鹰单片机开发板。

从刚开始接触单片机,到现在已经有4年的时间了,在这期间学习和使用了51单片机、飞思卡尔单片机,LPC2138,PIC16F887等系列的单片机,每接触一款单片机,都会经历熟悉其基本开发,然后将其用于项目中的过程,对于如何学习一款单片机,自己做了如下的总结。

大家都知道,51单片机是最容易入门的,不仅因为其编程简单,更重要的是网上的资料非常丰富。所以一般学习单片机开发的都将51单片机作为入门开发的首选。我学习51单片机的时候是采用这样的一个步骤进行学习的:

第一步(熟悉的过程):买了一款51单片机开发板,然后就开始了我的学习之旅,刚开始的时候没有去看视频教程,而是对着一本实验教材进行学习,那本实验教材的名字记不清楚了,但是其内容就是围绕单片机的LED灯进行控制,将51单片机内部的各个功能部件全部都使用到了,这样就能使我在很短的时间内,通过控制LED灯的亮、灭熟悉了51单片机的内部的各种资源,这时对51单片机也就没有感到陌生了。所以,个人觉得,学习单片机,要从实验入手,先熟悉单片机再说,开发语言开始使用的是C语言。

第二步(进阶的过程):有了第一步的基础之后,接下来的便是进阶的过程,当时,我看的是郭天祥十天学会单片机的视频教程,因为这个教程从基础到复杂的编程慢慢深入,讲的比较的全面,而且也生动,所以那一阶段,也是我学习单片机进步最快的阶段,每次听课的时候,按照上面的实验,以及课堂上面调试程序时出现的一些问题,自己认真的在电脑上进行调试,并分析产生故障的原因,让我有了一定的开发基础。在看完了视频教程之后,后面又对基础的知识进行了下补习,主要是看单片机原理性的教材,因为有些细节性的东西还是要从教材上面获得。

主程序:

push ds ;保存数据段

mov ax,0000

mov ds,ax ;数据段清零

mov ax,offset irq7 ;取中断程序入口地址

add ax,2000 ;加装时IP=2000地址

mov si,003c ;填8259中断7中断矢量

mov w[si],ax ;填偏移量矢量

mov ax,0000 ;段地址CS=0000H

mov si,003e

mov w[si],ax ;填段地址矢量

pop ds ;d栈

in al,21 ;读8259中断屏蔽字

and al,7f ;开8259中断7

out 21,al

mov al,b4 ;8253的计数器2为方式2,采用二进制计数,先低后高写入计数值 10110100

out 43,al ;写入方式控制字

mov ax,2e9c 0010 1110 1001 1100B 11932D

out 42,al ;写入低字节计数值 1001 1100

mov al,ah

out 42,al ;写入高字节计数值 0010 1110

mov al,81 ;8255的A口为方式0输出,B口为方式0输出,C口下部输入 1000 0001

out 63,al ;写方式控制字

call first ;调用first子程序,赋计数初值

begi:hlt 延时等待

sti ;开中断

mov ah,01

int 16 ;检测是否按了键盘

jz begi

mov ah,00 ;读键值

int 16

cmp al,0d ;是否按了回车

jnz A1

mov si,4000

not [si+04] ;偏移地址为4004的内存单元内容取反

jmp begi

A1:cmp al,1b ;是否按了ESC键

jnz A2

call first ;重新赋初值,相当于清零

A2:jmp begi

中断程序:

irq7:call disp ;调用disp子程序,用来在数码管显示数据

mov si,4000

cmp [si+04],00 ;判断是否按了第2次回车键

je A4

call addn ;调用addn子程序,用来计数

A4:mov al,20

out 20,al

cli ;关中断

iret ;返回

addn程序:

addn:mov si,4000

add [si+03],01 ;百分之一秒加1

cmp [si+03],0a ;判断是否大于10

jz A5

jmp A9

A5:mov [si+03],00

Add [si+02],01 ;十分之一秒加1

cmp [si+02],0a ;判断是否大于10

jz A6

jmp A9

A6:mov [si+02],00

add [si+01],01 ;秒位加1

cmp [si+01],0a ;判断是否大于10

jz A7

jmp A9

A7:mov [si+01],00

add [si],01 ;十秒位加1

cmp [si],06 ;判断是否大于6

jz A8

jmp A9

A8:mov [si],00 ;大于60:00重新开始

A9: ret

赋初值程序:

first:mov si,4000

mov al,00

mov [si],al

mov [si+01],al

mov [si+02],al

mov [si+03],al

mov [si+04],al

ret

显示程序:

disp:push ax ;保存AX

mov si,4000 ;指向数据缓冲区

mov dl,f7 ;1111 0111 指向数码管

mov al,dl ;al=1111 0111

again:out 60,al ;写端口A

mov al,[si]

mov bx,4100 ;指向数码缓冲区 bx=0100 0001 0000 0000

and ax,00ff ; ax=0000 0000 al

add bx,ax ;得到显示代码 bx=0100 0001 al

mov al,[bx]

out 61,al ;写端口B

call dally :调用延时程序dally

inc si

mov al,dl

test al,01

jz out

ror al,1 ;指向下一个数码管

mov dl,al

jmp again

out: pop ax ;d出AX

ret

dally:push cx ;延时程序

push ax

mov cx,0010

t1 :mov ax,0010

t2 dec ax

jnz t2

loop t1

pop ax

pop cx

ret

数码缓冲区:

0000:4000 3f,06,5b4f,66,6d,7d,07,7f,6f

二、 设计思想

电子秒表要实现的功能:用键盘中断来控制整个程序,按一下回车键启动电子秒表,再按一下暂停,按一下ESC键清零,用七段数码管显示时间。整个程序涉及到8255、8253与8259三个芯片。8253的OUT2,CLK2分别连接8259的IRQ7与PCLK,8253的GATE2连接正5伏电压,采用计数器2每隔001秒产生一次中断并且计数,写入以偏移地址4000H开始的4个内存单元,然后利用8255将内存单元的数据输出到七段数码管。由于键盘中断优先于8259的7号中断,所以程序只有在按一下回车键才启动电子秒表,再按一下暂停,按一下ESC键清零,如果超出了60秒,整个程序自动重新开始。

三、 所用芯片工作原理

8255:接口电路在CPU和I/O设备之间起着信号的变换和传输的作用。 任何接口电路与CPU之间的信息传输方式都是并行的,即CPU与接口电路之间以数据字节/字为单位传送信息。接口电路与I/O设备之间的信息传送方式,有并行和串行两种,相应的接口电路称为并行接口和串行接口。

并行接口是在多根数据线上,以数据字节/字与I/O设备交换信息。在输入过程中,输入设备把数据送给接口,并且使状态线“输入准备好”有效。接口把数据存放在“输入缓冲寄存器”中,同时使“输入回答”线有效,作为对外设的响应。外设在收到这个回答信号后,就撤消数据和“输入准备好”信号。数据到达接口中后,接口会在“状态寄存器”中设置输入准备好标志,或者向CPU发一个中断请求。CPU可用查询方式或中断方式从接口中读取数据。接口中的数据被读取后,接口会自动清除状态寄存器中的标志,且撤消对CPU的中断请求。

在输出过程中,每当输出寄存器可以接收数据,接口就会将状态寄存器中“输出准备好”状态置1或向CPU发一个中断请求,CPU可用查询或中断方式向接口输出数据。当CPU输出的数据到达接口后,接口会清除“输出准备好”状态,把数据送往外设,并向外设发一个“数据输出准备好”信号。外设受到驱动后,便接收数据,并向接口电路发一个“输出回答”信号,接口收到该回答信号后,又将状态寄存器中“输出准备好”置位,以便CPU输出下一个数据。

8253:对CLK信号进行“减1计数”。首先CPU把“控制字”,写入“控制寄存器”,把“计数初始值”写入“初值寄存器”,然后, 定时/计数器按控制字要求计数。计数从“计数初始值 开始,每当CLK信号出现一次,计数值减1,当计数值减为0时,从OUT端输出规定的信号(具体形式与工作模式有关)。当CLK信号出现时,计数值是否减1(即是否计数),受到“门控信号”GATE的影响,一般,仅当GATE有效时,才减1门控信号GATE如何影响计数 *** 作,以及输出端OUT在各种情况下输出的信号形式与定时/计数器的工作模式有关。

8259:1 IR线上提出了中断请求的中断源,即出现请求,IRR中断请求寄存器(共有8位D7~D0)对应于连接在IR0~IR7线上的外设的中断请求,哪一根输入线有请求,哪一根输入线就置1。

2 若OCW1(IMR中断屏蔽寄存器)未使该中断请求屏蔽(对应位为0时不屏蔽),该请求被送入PR(优先权分析器)比较。否则,不送入PR比较。

3 PR把新进入的请求与ISR(服务中寄存器)中正在被处理的中断进行比较。如果新进入的请求优先级较低,则8259不向CPU提出请求。如果新进入的请求优先级较高,则8259使INT引脚输出高电平,向CPU提出请求。

4 如果CPU内部的标志寄存器中的IF(中断允许标志)为0,CPU不响应该请求。若IF=1,CPU在执行完当前指令后,从CPU的INTA引脚上向8259发出两个负脉冲。

5第一个 INTA负脉冲到达8259时,8259完成以下三项工作:

a使IRR(中断请求寄存器)的锁存功能失效。这样一来,在IR7~IR0上的请求信号就不会被8259接收。直到第二个INTA负脉冲到达8259时,才又使IRR的锁存功能有效。

b使ISR(服务中寄存器)中的相应位置1。

c使IRR中的相应位清0。

6第二个INTA负脉冲到达8259时,8259完成以下工作:

a将中断类型码(ICW2中的值)送到数据总线上,CPU将其保存在“内部暂存器”中。

b如果ICW4(它设定级中断联方式之特定完全嵌套方式,将在8259的工作方式中详述ICW4)中设置了中断自动结束方式,则将ISR的相应位清0。

1、程序结构问题,call leddisp指令后紧接子程序,在执行call指令后,会再次进入;

2、si指向的数据均为0,自然用xlat从bx地址处换出的al([bx+al] 对应的)都是第一个数据。

编写子程序的步骤如下:

1、先在头脑中想清楚子程序的功能,并理清子程序的前置条件、后置条件。2、给子程序起一个好的名字。这是一个好子程序的标志。3、写测试用例。4、编写并优化伪代码。书写伪代码时不应该出现具体语言的方法元素;编写伪代码时,也站在一个比较高的层次,比较详细的书写。5、将伪代码转化成具体语言的语句。

6、子程序书写完后,首先也是最重要的就是先在自己的脑海中执行子程序,检查子程序的所有可能执行路径、端点和所有异常条件。通常这一过程可以发现绝大部分的错误。7、编译子程序。在编译的过程中将编译器的警告级别调到最高,并注意编译器产生的每个警告信息。8、在调试器逐行执行子程序9、执行单元测试。在这个过程中也用到第3步所写的测试用例。10、修改测试发现的问题,如果发现问题很多,则不修改子程序,而是直接重写子程序。11、检查子程序是否符合软件过程的一些基本思想。比如耦合度、变量的命名、语句的布局、注释等。

我刚好做过,但是不是彩灯,用开关控制正反转,并通过灯来现在状态,

还可以调速, 希望对你有帮助

REP:MOV R0,#0

;;;;;;按键判断;;;;;;;;

LOOP:CALL ZHFA ;正反DPTR

CALL SPEED ;速度R1

JBC F0,OFFL ;无效/有效 *** 作

MOV P0,P2 ;开提示灯

JMP NEXT

OFFL:MOV P0,#0FFH ;关闭指示灯

JMP LOOP

;;;;;;电机输出;;;;;;;;

NEXT:CALL DELAY

MOV A,R0

MOVC A,@A+DPTR

MOV P1,A

INC R0

CJNE R0,#4,LOOP

JMP REP

;;;;;;正反转;;;;;;;;;;;

ZHFA:MOV A,P2

ORL A,#3FH

ZHE:CJNE A,#0BFH,FAN

MOV DPTR,#TAB1

JMP ZFOK

FAN:CJNE A,#7FH,STOP1

MOV DPTR,#TAB2

JMP ZFOK

STOP1:SETB F0

ZFOK:RET

;;;;;;;速度设置;;;;;;;;

SPEED:MOV A,P2

ORL A,#0C0H

SD1:CJNE A,#0FEH,SD2

MOV R1,#5

JMP SDOK

SD2:CJNE A,#0FDH,SD3

MOV R1,#45

JMP SDOK

SD3:CJNE A,#0FBH,SD4

MOV R1,#90

JMP SDOK

SD4:CJNE A,#0F7H,SD5

MOV R1,#135

JMP SDOK

SD5:CJNE A,#0EFH,SD6

MOV R1,#180

JMP SDOK

SD6:CJNE A,#0DFH,STOP2

MOV R1,#225

JMP SDOK

STOP2:SETB F0

SDOK:RET

;;;;;;延时子程序;;;;;;;

DELAY:MOV R4,#249

DL: NOP

NOP

DJNZ R4,DL

DJNZ R1,DELAY

RET

;;;;;;转序表;;;;;;;;;;;;

TAB1:DB 03H,06H,0CH,09H

TAB2:DB 09H,0CH,06H,03H

END

以上就是关于最近在做汇编 有几行代码不懂 请大牛讲解 用的是8255芯片全部的内容,包括:最近在做汇编 有几行代码不懂 请大牛讲解 用的是8255芯片、绘制一单片机最小系统电路图,编写程序控制P1.7口输出低电平,并点亮发光二极管。求大神解答哇

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/zz/10142210.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-05-05
下一篇 2023-05-05

发表评论

登录后才能评论

评论列表(0条)

保存