导航: 老古网老古论坛XMOS公共讨论区XMOS开源项目区单片机程序设计嵌入式系统广告区域
→24C02为何仅能连续存入28个字节[zhongqiu]

 *第26319篇: 24C02为何仅能连续存入28个字节

  
楼 主:zhongqiu 2004年9月29日16:43
 24C02为何仅能连续存入28个字节
各位老兄好,冒昧打搅了,我碰到了一个难题,目前非常困难,真的希望各位能给指点一下,问题这样的,通过串口接收不定数目字节的数据,我的编程思路是这样的,接收一个字节,存入24C02中,再接收,再存入,直到串口没有字节,判断串口有无字节,根据RI在一定时间内是否置位,在24C02的00H最后写入总共接收的字节数,此为其他程序读取24C02的需要,经过反复实验,串口没有问题,问题出在24C02中,问题是这样的,28个字节以内,可以正常接收,保存,超过28个字节,就不能正常保存了,我很不解,反复查阅资料,还是没有解决,所以冒昧再次跟各位请教了,谢谢!
附程序
;该程序为N个字节的串口接收程序,串口采用方式1,并将接收到的数据写到24C02的00H起始的地址中
MAINSCON:MOV 40H,#0A0H
      MOV 41H,#00H
      MOV 42H,#30H 
      SLAW EQU 40H
      NUMBYT EQU 41H
      NWD EQU 42H
      VSDA EQU P0.4
      VSCL EQU P0.5
SDL1:MOV TMOD,#20H;定时器T1作波特率发生器,工作于方式2
     MOV TL1,#0F3H;设定T1的初值确定波特率为4800
     MOV TH1,#0F3H;
     CLR ET1;T1作波特率发生器时应禁止中断
     SETB TR1;启动TR1计数
     MOV SCON,#52H;串行口设置方式1
     ORL PCON,#80H;SMOD=1
     MOV R0,NWD;待接收数据首地址
               ;待接收数据字节数量
     MOV R5,#5
     MOV R3,#50
     MOV R7,NUMBYT
     CJNE R7,#00H,WAIT
WAIT0:JBC RI,SSS
      AJMP WAIT0
WAIT:
     JBC RI,SSS

     DJNZ R5,WAIT
     DJNZ R3,WAIT
     AJMP WAIT1

SSS: CLR RI
     MOV A,SBUF
     MOV @R0,A
     MOV R7,NUMBYT
     INC R7
     MOV NUMBYT,R7

;该程序为将RAM30H-37H中的内容写到24C02的00H
      WRADD:LCALL STA
      MOV A,SLAW
      LCALL WRBYT
      LCALL CACK
      JB F0,WRADD
      MOV A,R7;写入EEPROM单元地址
      LCALL WRBYT
      LCALL CACK
      JB F0,WRADD
      MOV R0,NWD

WRDA:MOV A,@R0
     LCALL WRBYT
     LCALL CACK
     JB F0,WRADD
     LCALL STOP;至此将数据0AAH写入了EEPROM地址单元00中
PROGRAM:LCALL SDL1
        JB RI,SSS
        AJMP WAIT1

WAIT1:LCALL DIR
      CLR P1.4
      SETB P2.6
      CLR P2.6
      JB RI,SSS
      CLR P1.4
      SETB P2.6
      CLR P2.6

      AJMP WRITEONE
DIR:NOP
    NOP
    NOP
    RET
STA:SETB VSDA
    NOP
    SETB VSCL
    NOP
    NOP
    NOP
    NOP
    NOP
    CLR VSDA
    NOP
    NOP
    NOP
    NOP
    NOP
    CLR VSCL
    NOP
    RET
STOP:CLR VSDA
     NOP
     SETB VSCL
     NOP
     NOP
     NOP
     NOP
     NOP
     SETB VSDA
     NOP
     NOP
     NOP
     NOP
     NOP
     CLR VSCL
     CLR VSDA
     RET
MNACK:SETB VSDA
      SETB VSCL
      NOP
      NOP
      CLR VSCL
      CLR VSDA
      RET
MACK:CLR VSDA
     SETB VSCL
     NOP
     NOP
     CLR VSCL
     SETB VSDA
     RET
CACK:SETB VSDA
     NOP
     NOP
     SETB VSCL
     CLR F0
     NOP
     NOP
     MOV C,VSDA
     JNC CEND
     SETB F0
CEND:NOP
     CLR VSCL
     NOP
     RET
WRBYT:MOV R6,#08H
WLP:RLC A
    JC WR1
    SJMP WR0
WLP1:DJNZ R6,WLP
     NOP
     RET
WR1:SETB VSDA
    NOP
    SETB VSCL
    NOP
    NOP
    NOP
    NOP
    NOP
    CLR VSCL
    SJMP WLP1
WR0:CLR VSDA
    NOP
    SETB VSCL
    NOP
    NOP
    NOP
    NOP
    NOP
    CLR VSCL
    SJMP WLP1
RDBYT:MOV R6,#08H
RLP:SETB VSDA
    NOP
    SETB VSCL
    NOP
    NOP
    MOV C,VSDA
    MOV A,R2
    CLR VSCL
    RLC A
    MOV R2,A
    NOP
    NOP
    NOP
    DJNZ R6,RLP
    RET
WRITEONE:
         LCALL STA
      MOV A,SLAW
      LCALL WRBYT
      LCALL CACK
      JB F0,WRITEONE
      MOV A,#00H;写入EEPROM单元地址
      LCALL WRBYT
      LCALL CACK
      JB F0,WRITEONE
         MOV A,NUMBYT
         LCALL WRBYT
         LCALL CACK
         JB F0,WRITEONE
         LCALL STOP;至此将数据0AAH写入了EEPROM地址单元00中
        NOP
LL:END

  
2楼:zhongqiu 2004年9月30日14:20
 老古,该帖子这么长时间没人理了,作为解疑
老古,该帖子这么长时间没人理了,作为解疑授惑之处,这种现象,很伤人心!!!!!!
  
3楼:middle-rui 2004年9月30日20:22
 24C02如果连续写入的话,要分页写入的,每页为8个字节
  
4楼:zhongqiu 2004年10月3日16:47
 [quote][b]以下是引用[i]mi
以下是引用middle-rui在2004-9-30 20:22:28的发言:
24C02如果连续写入的话,要分页写入的,每页为8个字节

谢谢您的指点,我对24C02理解不深,老是转不过弯,为什么可以单字节写入28个字节?

  
5楼:middle-rui 2004年10月4日15:43
 单字节写入,已经指定单个地址写入,不存在连续写入的
  
6楼:zhongqiu 2004年10月7日08:51
 [quote][b]以下是引用[i]mi
以下是引用middle-rui在2004-10-4 15:43:24的发言:
单字节写入,已经指定单个地址写入,不存在连续写入的

能否麻烦您给我一个连续写入60个字节的程序示范,我钻进牛角尖,有转不出来的感觉,谢谢您了!

  
7楼:guest 2004年10月7日15:16
 请看
LO24CXXX_ADDR EQU 08H
        RW24CXXX_TIMES EQU 09H
BEGIN:
        MOV SP,#40H
         

WRITE_XIANGXICHENGJIAO1:                ;RO,RAM为写入地址,LO24CXXX为24C02写入地址
        MOV R0,#10H
        MOV LO24CXXX_ADDR,#00H          ;写24C02 00H-08H的数据
        MOV RW24CXXX_TIMES,#08
        LCALL WRITE_24C02
WRITE_XIANGXICHENGJIAO2:
        MOV R0,#18H
        MOV LO24CXXX_ADDR,#08H          ;写24C02 08H-0FH的数据
        MOV RW24CXXX_TIMES,#08
        LCALL WRITE_24C02
                                        ;如果需要再写,则地址和,R0设置一下就可以连续写入60个BYTE
                                             
        AJMP $     
        
        
        ;这里是连续写入多字节数据
WRITE_24C02:
              
WRITE_24C02PER:
               CLR C
               LCALL START_BIT        ;初始化
               
               MOV A,#01H
               RLC A
               ADD A,#0A0H            ;
               LCALL  WRITE_BIT       ;送出写控制字
              
               MOV A,LO24CXXX_ADDR      ;把低地址送入A中
               LCALL WRITE_BIT
              
WRITE_BYTE:    MOV A,@R0           ;向24CXXX写入单个字节
               LCALL   WRITE_BIT   ;写入数据
               INC R0
               LCALL DELAY_24
               DJNZ RW24CXXX_TIMES,WRITE_BYTE
               LCALL STOP_BIT      ;停止写入数据
WRITE_ENDDING: LCALL DELAY2MS_24
               RET

START_BIT:      NOP            ;开始位
                SETB SLK_24CXXX
                SETB SDA_24CXXX
                LCALL DELAY_24
                CLR SDA_24CXXX
                LCALL DELAY_24
                RET
                


WRITE_BIT:      CLR C
                MOV   R7,#08H  ;循环次数
WRITE_LOP:      NOP
                CLR SLK_24CXXX
                NOP
                RLC A
                MOV SDA_24CXXX,C
                NOP
                SETB SLK_24CXXX
                NOP
                DJNZ R7,WRITE_LOP
                CLR SLK_24CXXX            ;应答发送请求
                lCALL DELAY_24
                SETB SLK_24CXXX
                lCALL DELAY_24
                CLR SLK_24CXXX
                LCALL DELAY_24
                RET
                
                
DELAY_25:      MOV R4,#00H               ;以下为延时
               MOV R5,#04H
               AJMP DELAY2_24

DELAY_24:      MOV R4,#03H
               MOV R5,#01H
               AJMP DELAY2_24

DELAY2MS_24:
               MOV    R4,#00H
               MOV    R5,#06H                   ;20ms延时
DELAY2_24:     DJNZ   R4,DELAY2_24
               DJNZ   R5,DELAY2_24
               RET

  
8楼:zhongqiu 2004年10月8日11:04
 老兄这么帮忙,我真是太感激了,不过我还没
老兄这么帮忙,我真是太感激了,不过我还没有理解,我看后再请教,谢谢!
  
9楼:zhongqiu 2004年10月9日11:23
 承蒙各位老兄关照,我编了一个程序,请务必
承蒙各位老兄关照,我编了一个程序,请务必指教一下
该程序的问题在24C02的连续写入出现的问题,传口没有问题,目前如果仅向24C02写入00H-07H(即块写入中的第一块)则正常接收,计数正常,但一旦写入第二块,第三块等等,则往后每块丢一个字节,目前写入之后,根据写入80H的字节数再读出来(此为对应的另一个程序,本程序不包括),则从第二块开始,每块丢一个字节,但是读出的字节确实连续的,就是末尾的字节数读不出来,可能是程序循环过程中出现的问题,因为第一块没在循环程序中,也可能是计数参数NUMBYT出现了问题。
   另外,该程序不稳定,有时能写进去,有时写不进去,还有时候丢掉从第三块开始的首字节,但这些问题在关掉防真器后重启动程序便没有了,但调试时间长了便又出现了,就是不稳定。程序如下
;该程序为N个字节的串口接收程序,串口采用方式1,并将接收到的数据写到24C02的00H起始的地址中
;采用块写入,NUMBYT为总的计数器,写入后将写入的字节数NUMBYT+1写入80H
MAINSCON:MOV 40H,#0A0H
      MOV 41H,#00H
      MOV 42H,#30H;
      MOV 43H,#38H
      NUM EQU 44H;此为24C02每块写中的计数00H-07H
      
      SLAW EQU 40H
      NUMBYT EQU 41H;此为写入24C02中总的字节数,00H开始,最后加一即为总数
      NWD EQU 42H
      VSDA EQU P0.4
      VSCL EQU P0.5
      MOV R0,NWD
      MOV R1,#00H;块写入中的低字节
SDL1:
     MOV TMOD,#20H;定时器T1作波特率发生器,工作于方式2
     MOV TL1,#0F3H;设定T1的初值确定波特率为4800
     MOV TH1,#0F3H;
     CLR ET1;T1作波特率发生器时应禁止中断
     SETB TR1;启动TR1计数
     MOV SCON,#52H;串行口设置方式1
     ORL PCON,#80H;SMOD=1
     
     MOV R5,#5
     MOV R3,#50

     MOV R7,NUMBYT
     CJNE R7,#00H,WAIT
WAIT0:JBC RI,SSS
      LJMP WAIT0
WAIT:
     JBC RI,SSS
     DJNZ R5,WAIT
     DJNZ R3,WAIT
     MOV A,NUMBYT
     DEC A
     MOV NUMBYT,A
     AJMP WRB08

SSS: CLR RI
     MOV A,SBUF
     MOV @R0,A
     MOV R7,NUMBYT
     CJNE R7,#07H,SSS1
     LJMP WRB08
SSS1:INC R0
     INC R7
     MOV NUMBYT,R7
     LJMP SDL1
;该程序为将30H-37H的内容写到24C02的01H-08H中
WRB08:
WRADD:MOV A,NUMBYT
      INC A
      MOV R7,A
      LCALL STA
      MOV A,SLAW
      LCALL WRBYT
      LCALL CACK
      JB F0,WRADD
      MOV A,#00h
      LCALL WRBYT
      LCALL CACK
      JB F0,WRADD
      MOV R0,NWD
WRDA:MOV A,@R0
     LCALL WRBYT
     LCALL CACK
     JB F0,WRADD
     INC R0
     DJNZ R7,WRDA
     LCALL DIR
     LCALL STOP
     MOV R0,NWD
     MOV A,R1
     ADD A,#08H
     MOV R1,A
     MOV NUM,#00H
SDL3:MOV TMOD,#20H;定时器T1作波特率发生器,工作于方式2
     MOV TL1,#0F3H;设定T1的初值确定波特率为4800
     MOV TH1,#0F3H;
     CLR ET1;T1作波特率发生器时应禁止中断
     SETB TR1;启动TR1计数
     MOV SCON,#52H;串行口设置方式1
     ORL PCON,#80H;SMOD=1
     ;待接收数据首地址
               ;待接收数据字节数量
     MOV R5,#5
     MOV R3,#50
     MOV R7,NUMBYT
WAIT3:
     JBC RI,SSS3
     DJNZ R5,WAIT3
     DJNZ R3,WAIT3
     LJMP WRB083N
SSS13:INC R0
     INC R7
     INC R2
     MOV NUMBYT,R7
     LJMP SDL3
SSS3:CLR RI
     MOV A,SBUF
     MOV @R0,A
     MOV R7,NUMBYT
     CJNE R2,#07H,SSS13

;该程序为将30H-37H的内容写到24C02的01H-08H中
WRB083:
WRADD3:
      MOV R4,#08H
      LCALL STA
      MOV A,SLAW
      LCALL WRBYT
      LCALL CACK
      JB F0,WRADD3
      MOV A,R1
      LCALL WRBYT
      LCALL CACK
      JB F0,WRADD3
      MOV R0,NWD
WRDA3:MOV A,@R0
     LCALL WRBYT
     LCALL CACK
     JB F0,WRADD3
     INC R0
     DJNZ R4,WRDA3
     LCALL DIR
     LCALL STOP
     MOV R0,NWD
     MOV A,R1
     ADD A,#08H
     MOV R1,A
     MOV R2,#00H

     LCALL SDL3
WRB083N:
WRADD3N:
      MOV R4,#08H;该段子程序为当没有串口数据传输要求后的最后写入24C02的字节,字节数在八个以内,写完后进入最后写
                   NUMBYT子程序,然后退出                
      LCALL STA
      MOV A,SLAW
      LCALL WRBYT
      LCALL CACK
      JB F0,WRADD3N
      MOV A,R1
      LCALL WRBYT
      LCALL CACK
      JB F0,WRADD3N
      MOV R0,NWD
WRDA3N:MOV A,@R0
     LCALL WRBYT
     LCALL CACK
     JB F0,WRADD3N
     INC R0
     DJNZ R4,WRDA3N
     LCALL DIR
     LCALL STOP

WAIT1:LCALL DIR;该段子程序为让蜂鸣器响的子程序,有响声表明字节写入完毕
      CLR P1.4
      SETB P2.6
      CLR P2.6
      CLR P1.4
      SETB P2.6
      CLR P2.6

      AJMP WRITEONE
DIR:NOP
    NOP
    NOP
    RET
STA:SETB VSDA
    SETB VSCL
    NOP
    NOP
    CLR VSDA
    NOP
    NOP
    CLR VSCL
    RET
STOP:CLR VSDA
     SETB VSCL
     NOP
     NOP
     SETB VSDA
     NOP
     NOP
     CLR VSCL
     CLR VSDA
     RET
MNACK:SETB VSDA
      SETB VSCL
      NOP
      NOP
      CLR VSCL
      CLR VSDA
      RET
MACK:CLR VSDA
     SETB VSCL
     NOP
     NOP
     CLR VSCL
     SETB VSDA
     RET
CACK:SETB VSDA
     SETB VSCL
     CLR F0
     MOV C,VSDA
     JNC CEND
     SETB F0
CEND:CLR VSCL
     RET
WRBYT:MOV R6,#08H
WLP:RLC A
    MOV VSDA,C
    SETB VSCL
    NOP
    NOP
    CLR VSCL
    DJNZ R6,WLP
    RET
RDBYT:MOV R6,#08H
RLP:SETB VSDA
    SETB VSCL
    MOV C,VSDA
    MOV A,R2
    RLC A
    MOV R2,A
    CLR VSCL
    DJNZ R6,RLP
    RET
WRITEONE:
         LCALL STA
      MOV A,SLAW
      LCALL WRBYT
      LCALL CACK
      JB F0,WRITEONE
      MOV A,#80H;写入EEPROM单元地址
      LCALL WRBYT
      LCALL CACK
      JB F0,WRITEONE
         MOV A,NUMBYT
         INC A
         LCALL WRBYT
         LCALL CACK
         JB F0,WRITEONE
         LCALL STOP;至此将数据0AAH写入了EEPROM地址单元00中
        NOP
LL:END



>>>>>>对该主题发表你的看法

本主题贴数9,分页: [第1页]


[上一篇主题]:谁知道信号隔离器ADUM1400CRW的电路?请帮帮忙!!!!

[下一篇主题]:[求助]VC高手指点