访问电脑版页面

导航:老古开发网手机版其他

3.5.3 存储器访问

导读:
关键字:
  一次存储器访问把一个值读出并写入x51系统各种各样的存储空间内。

    直接存储器访问把存储器地址编码在要读写存储器的指令中。使用直接存储器存取我们可以访问存储器类型中DATA和BIT中的变量。对于251来说,还有EDATA存储器类型可以使用直接寻址访问。

    间接存储器访问使用要读写存储器的指令中的一个寄存器中的内容。使用间接寻址操作数,可以访问x51中所有类型的存储空间。

    下面的例子示出了怎样访问一个x51系统的不同存储器类型。

    DATA

    DATA中的存储器地址可以使用两种寻址方式:直接和间接存储器访问。x51的特殊功能寄存器(SFR)具有在DATA空间中0x80之上的地址。SFR只可采用直接存储器寻址。在x51微处理器中不支持对SRF的间接寻址。

    适用于所有8051版本的例子

?DT?myvar SEGMENT DATA ; 定义一个DATA类型的段
  RSEG ?DT?myvar  
VALUE: DS 1 ; 在DATA空间保留一个字节(BYTE)
       
IO_PORT2 DATA 0A0H ; 特殊功能寄存器
VALUE2 DATA 20H ; 绝对存储器地址
罗亩的笔记      
?PR?myprog SEGMENT CODE ; 为程序代码定义一个段
  RSEG ?PR?myprog  
  MOV A, IO_PORT2 ; 对DATA直接寻址
  ADD A, VALUE  
  MOV VALUE2, A  
  MOV R1, #VALUE ; 将VALUE的地址装入R1
  ADD A, @R1 ; 对VALUE间接寻址

    罗亩按:这些例程的格式,很值得我们学习,其程序的可读性、条理性非常好。“?DT?”代表DATA类型的段,“?PR?”代表程序代码段。

    BIT

    BIT类型的存储器地址使用8051的位寻址指令寻址。位于可位寻址存储器地址的特殊功能寄存器(SFR)也可以使用位指令寻址。位可寻址的SFR地址是:80H,88H,90H,98H,0A0H,0A8H,0B0H,0B8H,0C0H,0C8H,0D0H,0D8H,0E0H,0E8H,0F0H和0F8H。

    适用于所有8051版本的例子

?BI?mybits SEGMENT BIT ; 定义一个BIT类型的段
  RSEG ?BI?mybits  
FLAG: DBIT 1 ; 在BIT空间保留一位
P1 DATA 90H ; 8051 SFR端口1
GREEN_LED BIT P1.2 ; 在I/O端口1.2上的绿色LED
       
?PR?myprog SEGMENT CODE ; 为程序代码定义一个段
  RSEG ?PR?myprog  
  SETB GREEN_LED ; P1.2 = 1
  JB FLAG, is_on ; 对DATA直接寻址
  SETB FLAG  
  CLR ACC.5 ; 复位寄存器A中的位5
  ……    
is_on: CLR FLAG  
  CLR GREEN_LED ; P1.2 = 0

  EBIT(仅适用于英特尔/爱特梅尔WM251)

    251提供了EBIT存储类型,作为扩展的位可寻址空间,寻址时使用扩展的位指令。251中所有的特殊功能寄存器(SFR)都可以使用扩展的位指令寻址。

    英特尔/爱特梅尔WM251的例子

 

?EB?mybits SEGMENT EBIT ; 定义一个EBIT类型的段
  RSEG ?EB?mybits  
FLAG: DBIT 1 ; 在BIT空间保留一位
CMOD DATA 0D9H ; PCA计数器模式
CPS0 BIT CMOD.1 ; CPS0位
       
?PR?myprog SEGMENT CODE ; 为程序代码定义一个段
  RSEG ?PR?myprog  
  JB FLAG, is_on ; 直接对DATA寻址
  SETB FLAG  
  ……    
is_on: CLR FLAG  
  CLR CPS0 ; CMOD.1 = 0
   IDATA

    在该空间中的变量通过寄存器R0和R1存取。

    适用于所有8051版本的例子

 

?ID?myvars SEGMENT IDATA ; 定义一个IDATA类型的段
  RSEG ?EB?mybits ; 罗亩按:此处疑为 “RSEG   ?ID?myvars”
BUFFER: DS 100 ; 保留100字节
       
?PR?myprog SEGMENT CODE ; 为程序代码定义一个段
  RSEG ?PR?myprog  
  MOV R0, #BUFFER ; 把地址装载到R0中
  MOV A, @R0 ; 读存储器地址缓冲器所指地址的内容
  INC R0 ; R0中的存储器地址加1
  MOV @R0, A ; 写存储器地址BUFFER+1
   EDATA(只适用于英特尔/爱特梅尔WM251,菲利浦80C51MX)

    在菲利浦80C51MX中,EDATA存储器可以通过EPTR或通用指针PR0和PR1访问。通用指针可以访问16MB地址空间中的任意地址。

    适用于菲利浦80C51MX的例子

?ED?my_seg SEGMENT EDATA ; 定义一个EDATA类型的段
  RSEG ?ED?my_seg  
STRING: DS 100 ; 保留100个字节
       
?PR?myprog SEGMENT CODE ; 为程序代码定义一个段
  RSEG ?PR?myprog  
  MOV R1, #BYTE0 STRING ; 把STRING的地址装入PR0
  MOV R2, #BYTE1 STRING  
  MOV R3, #BYTE2 STRING  
  MOV A, @PR0 ; 把STRING中的第一个字节装入A
    在251中,EDATA存储器可以使用直接寻址模式寻址,也可以通过寄存器WR0 .. WR30间接寻址。IDATA和DATA也可以使用这种寻址模式寻址。

    适用于英特尔/爱特梅尔的WM251的例子

 

?ED?my_seg SEGMENT EDATA ; 定义一个EDATA类型的段
  RSEG ?ED?my_seg  
STRING: DS 100 保留100个字节
       
?PR?myprog SEGMENT CODE ; 为程序代码定义一个段
  RSEG ?PR?myprog  
  MOV R11, STRING+2 ; 装载位于STRING[2]中的字符
  MOV WR4, #STRING ; 装载STRING的地址
  MOV R6, @WR4 ; 间接寻址
  MOV @WR4+2, R6 ; 使用常量偏移访问
   XDATA

    XDATA存储器类型可以通过寄存器DPTR使用指令MOVX访问。单页XDATA存储空间也可以通过R0,R1访问。在C编译器级,该内存类型叫做pdata,段前缀使用?PD?。该pdata页的高地址典型地用P2寄存器设置。但在新型8051微处理器中,也有专用的特殊功能寄存器用于定义XDATA页地址。

    适用于所有8051微处理器的例子

 

?XD?my_seg SEGMENT XDATA ; 定义一个XDATA类型的段
  RSEG ?ED?my_seg  
XBUFFER: DS 100 ; 保留100个字节
       
?PD?myvars SEGMENT XDATA INPAGE ; 定义一个页的XDATA段
  RSEG ?PD?myvars  
VAR1: DS 1 ; 保留一个字节
       
?PR?myprog SEGMENT CODE ; 为程序代码定义一个段
  RSEG ?PR?myprog  
  MOV P2, #HIGH ?PD?myvars ; 装载页地址寄存器
  ……    
  MOV DPTR, #XBUFFER ; 装载地址
  MOVX A, @DPTR ; 通过DPTR访问
  MOV R1, #VAR1 ; 装载地址
  MOVX @R1, A ; 通过R0或R1访问
   CODE和CONST

    CODE和CONST存储器可以使用DPTR寄存器通过指令MOVC访问。存储类型CONST不适用于A51和BL51。

    适用于所有8051微处理器的例子

  

?CO?my_seg SEGMENT CODE ; 定义一个CODE类型的段
  RSEG ?CO?my_seg  
TABLE: DB 1, 2, 4, 8, 0x10 ; 一个常量表
       
?PR?myprog SEGMENT CODE ; 为程序代码定义一个段
  RSEG ?PR?myprog  
  MOV DPTR, #TABLE ; 装载表的地址
  MOV A, #3 ; 把偏移量装入表中
  MOVC A, @A+DPTR ; 通过MOVC指令访问
  HDATA和HCONST

    HDATA和HCONST存储器仅可以通过菲利浦80C51MX和251架构的CPU指令访问。在传统8051器件上,可以使用存储器堆模拟HDATA和HCONST存储器。HDATA和HCONST存储器类型不适用于A51和BL51。

    在菲利浦80C51MX中,HDATA和HCONST存储器可以通过EPTR或通用指针(全局指针)PR0和PR1访问。通用指针可以访问16MB存储器空间中的任意地址。

    适用于80C51MX的例子

?HD?my_seg SEGMENT HDATA ; 定义一个HDATA类型的段
  RSEG ?HD?my_seg  
ARRAY: DS 100 ; 保留100字节
       
?PR?myprog SEGMENT CODE ; 为程序代码定义一个段
  RSEG ?PR?myprog  
  MOV R1, #BYTE0 ARRAY ; 把ARRAY的地址装载到PR0中
  MOV R2, #BYTE1 ARRAY  
  MOV R3, #BYTE2 ARRAY  
  MOV A, @PR0 ; 把ARRAY的第一个字节装载到A中
    在251中,HDATA和HCONST存储器可以通过寄存器DR0 .. DR28和DR56访问。任意存储器位置都可以使用这些寄存器访问。

    适用于英特尔/爱特梅尔WM251的例子

?HD?my_seg SEGMENT HDATA ; 定义一个HDATA类型的段
  RSEG ?HD?my_seg  
ARRAY: DS 100 ; 保留100个字节
       
?PR?myprog SEGMENT CODE ; 为程序代码定义一个段
  RSEG ?PR?myprgog  
  MOV WR8, #WORD2 ARRAY ; 装载ARRAY的地址到DR8中
  MOV WR10, #WORD0 ARRAY  
  MOV R4, @DR8 ; 间接寻址
  MOV @DR8+50H, R4 ; 使用常量偏移访问

来源:   作者:  2006/9/25 16:50:53
栏目: [ ]

相关阅读

安森美推出新的高功率图腾柱PFC控制器,满足具挑战的能效标准

动态功耗低至60μA/MHz!助力设备超长续航,首选国民技术低功耗MCU!