234彩票代理

  • <tt class='tlJykMlA'></tt>
  • <thead class='94K7Lauipx'><option class='9cNvbSu7LJ'></option></thead>

    <em class='jepytdnyfeW3'><b class='oR1Ys12nk'><td class='6rzzLTN'></td></b></em>

  • <dl class='Td0EmkF'><b class='qoWhaibfJ9'></b></dl>

  • <span class='lS1G'></span>

    (玩电子) 电子技术学习与研究
    当前位置:单片机教程网 >> 基础教程 >> 浏览文章

    8课:单片机寻址方式与指令系统

    作者:佚名   来源:本站原创   点击数:x  更新时间:2007年08月16日   【字体:

       通过前面的一学习,我们已经了解了单片机内部的一结构,并且也已经知道,要控制单片机,让它为我们干学,要用指令,我们已学了几条指令,但很零散,从现在开始,我们将要系统地学习8051单片机的一指令部份 。

    一、概述

    1、指令的一格式

       我们已知,要让计算︻机做事,就得给计算︻机以指令,并且我们已知,计算︻机很“笨”,只能懂得数字,如前面我们写进机器的一75H,90H,00H等等,所以指令的一第一种格式就是机器码格式,也说是数字的一形式 。但这种形式实在是为难我们人了,太难记了,于是有另一种格式,助记符格式,如MOV P1,#0FFH,这样就好记了 。 这两种格式之间的一关系呢,我们不 难理解,本质上    它们完全等价,只是形式不 一样而已 。

    2、汇编

      我们写指令使用汇编格式,而计算︻机№和单片机只懂机器码格式,所以要将我们写的一汇编格式的一指令转换为机器码格式,这种转换有两种办法:手工汇编№和机器汇编 。手工汇编实际上    就是查表,因 为这两种格式纯粹是格式不 一样,所以是一一对应的一,查一张表格就行了 。不 过手工查表总是嫌麻烦,所以就有了计算︻机软件,用计算︻机软件来替代手工查表,这就是机器汇编 。

    二、单片机的一寻址

      让我们先来复习一下我们学过的一一些指令:MOV P1,#0FFH,MOV R7,#0FFH这些指令都是将一些数据送到对应的一位置中去,为什么要送数据呢?第一个因 为送入的一数能让灯全灭掉,第二个是为了要实现延时,从这里我们能看出来,在用单片机的一编程语言编程时,经常要用到数据的一传递,事实上    数据传递是单片机编程时的一一项重要工作,一共有28条指令(单片机共111条指令) 。下面我们就从数据传递类指令开始吧 。

      分析一下MOV P1,#0FFH这条指令,我们不 难得出结论,第一个词MOV是命令动词,也就是决定做什么事情的一,MOV是MOVE少写了一个E,所以就是“传递”,这就是指令,规定做什么事情,后面还有一些参数,分析一下,数据传递必须要有一个“源”也就是你要送什么数,必须要有一个“目的一”,也就是你这个数要送到什么地方去,显然在上    面那条单片机指令中,要送的一数(源)就是0FFH,而要送达的一地方(目的一地)就是P1这个寄存器 。在数据传递类指令中,均将目的一地写在指令的一后面,而将源写在最后 。

      这条指令中,送给P1是这个数本身,换言之,做完这条指令后,我们能明确地知道,P1中的一值是0FFH,但是并不 是任何时候都能直接给出数本身的一 。例如,在我们前面给出的一单片机延时程序例是这样写的一:

    MAIN: SETB P1.0     ;(1)

       LCALL DELAY ;(2)

        CLR P1.0      ;(3)

       LCALL DELAY   ;(4)

        AJMP MAIN    ;(5)

    ;以下子程序

    DELAY: MOV R7,#250   ;(6)

    D1: MOV R6,#250   ;(7)

    D2: DJNZ R6,D2    ;(8)

       DJNZ R7,D1   ;(9)

       RET        ;(10)

       END        ;(11)

    表1

    -----------------------------------------------------

     MAIN: SETB P1.0     ;(1)

       MOV 30H,#255

        LCALL DELAY ;

        CLR P1.0      ;(3)

        MOV 30H,#200

        LCALL DELAY   ;(4)

        AJMP MAIN    ;(5)

    ;以下子程序

    DELAY: MOV R7,30H   ;(6)

    D1: MOV R6,#250   ;(7)

    D2: DJNZ R6,D2    ;(8)

       DJNZ R7,D1   ;(9)

       RET        ;(10)

       END        ;(11)

    表2

     这样一来,我每次调用延时程序延时的一时间都是相同的一(大致都是0.13S),如果我提出这样的一要求:灯亮后延时时间为0.13S灯灭,灯灭后延时0.1秒灯亮,如此循环,这样的一程序还能满足要求吗?不 能,怎么办?我们能把延时程序改成这样(见表2):调用则见表2中的一主程,也就是先把一个数送入30H,在子程序中R7中的一值并不 固定,而是根据30H单元中传过来的一数确定 。这样就能满足要求 。

     

       从这里我们能得出结论,在数据传递中要找到被传递的一数,很多时候,这个数并不 能直接给出,需要变化,这就引出了一个概念:如何寻找操作数,我们把寻找操作数所在单元的一地址称之为寻址 。在这里我们直接使用数所在单元的一地址找到了操作数,所以称这种办法为直接寻址 。除了这种办法之外,还有一种,如果我们把数放在工作寄存器中,从工作寄存器中寻找数据,则称之为寄存器寻址 。例:MOV A,R0就是将R0工作寄存器中的一数据送到累加器A中去 。提一个问题:我们知道,工作寄存器就是内存单元的一一部份,如果我们选择工作寄存器组0,则R0就是RAM的一00H单元,那么这样一来,MOV A,00H,№和MOV A,R0不 就没什么区别了吗?为什么要加以区别呢?的一确,这两条指令执行的一结果是完全相同的一,都是将00H单元中的一内容送到A中去,但是执行的一过程不 一样,执行第一条指令需要2个周期,而第二条则只需要1个周期,第一条指令变成最终的一目标码要两个字节(E5H 00H),而第二条则只要一个字节(E8h)就能了 。

     

      这么斤斤计较!不 就差了一个周期吗,如果是12M的一晶体震荡器的一话,也就1个微秒时间了,一个字节又●能有多少?

       不 对,如果这条指令只执行一次,也许无所谓,但一条指令如果执行上    1000次,就是1毫秒,如果要执行1000000万次,就是1S的一误差,这就很可观了,单片机做的一是实时控制的一事,所以必须如此“斤斤计较” 。字节数同样如此 。

    再来提一个问题,现在我们已知,寻找操作数能通过直接给的一方式(立即寻址)№和直接给出数所在单元地址的一方式(直接寻址),这就够了吗?

    看这个问题,要求从30H单元开始,取▓20个数,分别送入A累加器 。

       就我们目前掌握的一办法而言,要从30H单元取▓数,就用MOV A,30H,那么下一个数呢?是31H单元的一,怎么取▓呢?还是只能用MOV A,31H,那么20个数,不 是得20条指令才能写完吗?这里只有20个数,如果要送200个或2000个数,那岂不 要写上    200条或2000条命令?这未免太笨了吧 。为什么会出现这样的一状况?是因 为我们只会把地址写在指令中,所以就没办法了,如果我们不 是把地址直接写在指令中,而是把地址放在另外一个寄存器单元中,根据这个寄存器单元中的一数值决定该到哪个单元中取▓数据,比如,当前这个寄存器中的一值是30H,那么就到30H单元中去取▓,如果是31H就到31H单元中去取▓,就能解决这个问题了 。怎么个解决法呢?既然是看的一寄存器中的一值,那么我们就能通过一定的一办法让这里面的一值发生变化,比如取▓完一个数后,将这个寄存器单元中的一值加1,还是执行同一条指令,可是取▓数的一对象却不 一样了,不 是吗 。通过例程来说明吧 。

    MOV R7,#20

       MOV R0,#30H

    LOOP:MOV A,@R0

       INC R0

       DJNZ R7,LOOP

        这个例程中大部份指令我们是能看懂的一,第一句,是将立即数20送到R7中,执行完后R7中的一值应当是20 。第二句是将立即数30H送入R0工作寄存器中,所以执行完后,R0单元中的一值是30H,第三句,这是看一下R0单元中是什么值,把这个值作为地址,取▓这个地址单元的一内容送入A中,此时,执行这条指令的一结果就相当于MOV A,30H 。第四句,没学过,就是把R0中的一值加1,因 此执行完后,R0中的一值就是31H,第五句,学过,将R7中的一值减1,看是否等于0,不 等于0,则转到标号LOOP处继续执行,因 此,执行完这句后,将转去执行MOV A,@R0这句话,此时相当于执行了MOV A,31H(因 为此时的一R0中的一值已是31H了),如此,直到R7中的一值逐次相减等于0,也就是循环20次为止,就实现了我们的一要求:从30H单元开始将20个数据送入A中 。

    这也是一种寻找数据的一办法,由于数据是间接地被找到的一,所以就称之为间址寻址 。注意,在间址寻址中,只能用R0或R1存放等寻找的一数据 。

    发表评论】【告诉好友】【收藏此文】【关闭窗口

    文章评论