AT93Cxx 系列串行EEPROM
 

 

; This collection of routines allows an AT89Cx051 microcontroller to =ead
; and write the AT93Cxx family of serial CMOS EEPROMS. The code is =niversal,
; supporting both 8-bit and 16-bit accesses to all members of the =T93Cxx
; family. The code meets all AT93Cxx family timing requirements when run
; on a processor with a 12 MHz clock. Code modifications may be required
; if a faster clock is substituted.
;
; All seven AT93Cxx functions are supported: read, write, write all, =rase,
; erase all, erase/write enable and erase/write disable. Each function =as
; its own entry point. The calling procedure is:
;
; 1) Load the address (if required) into register ADDR_LO (eight bits
; or less) or register pair ADDR_HI:ADDR_LO (more than eight bits).
; 2) Load the data (if required) into register DATA_LO (byte) or
; register pair DATA_HI:DATA_LO (word).
; 3) Call the function (READ, WRITE, WRAL, ERASE, ERAL, EWEN, EWDS).
;
; If the function returns data, it will be returned in register DATA_LO
; if SIZE=0 or in register pair DATA_HI:DATA_LO if SIZE=1.
;
; Some functions (WRITE, WRAL, ERASE, ERAL) return the carry flag set
; to indicate an error, cleared to indicate success.
;
; The following table shows the number of valid address bits for each
; member of the AT93Cxx family when strapped for 8-bit and 16-bit data:
;
; 93C46 93C56 93C57 93C66
;------------------------------------------------------------------------=---
; Data bits: 8 16 8 16 8 16 8 16
; Address bits: 7 6 9 8 8 7 9 8
;
; The SIZE flag is used to specify eight-bit or sixteen-bit data and =ust
; follow the state of the AT93Cxx ORG pin: one (set) indicates 16-bit =ata
; (ORG tied to Vcc or floating), zero (reset) indicates 8-bit data (ORG
; grounded). General purpose bit F0 in the PSW is used for the SIZE =lag,
; but any addressable bit may be substituted.
;
; To specify the member of the AT93Cxx family in use, set the value of =ADDR
; to the number of address lines required by the device. This =nformation is
; provided in the table above. The number of device address lines =epends on
; the data size as determined by the strapping of the ORG pin.
;
; The AT93Cxx control lines (CS, SK, DI, DO) are mapped to =icrocontroller
; I/O port pins in lines 63-66. To specify the three-wire configuration,
; assign DI and DO to the same pin. To specify the four-wire =onfiguration,
; assign DI and DO to different pins. No other code changes are =equired.
; Code to initialize the AT93Cxx control lines should be included in the
; user's application in the reset or initialization area.

; Number of valid address bits for the device in use (reference table =bove).

NADDR EQU 7 ; e.g. AT93C46 strapped for 8-bit data
;NADDR EQU 6 ; e.g. AT93C46 strapped for 16-bit data

; Data size.

size EQU f0 ; 0 = 8-bit data, 1 = 16-bit data

; Register definitions.

data_lo EQU r0 ; register for byte data
data_hi EQU r1 ; extension register for word data
addr_lo EQU r2 ; register for short address
addr_hi EQU r3 ; extension register for long address

; Microcontroller connections to AT93Cxx control pins.
; For a three-wire interface, define DI and DO to be the same pin.
; For a four-wire interface, define DI and DO to be different pins.
; No other code changes are required.

CS BIT p1.2 ; AT93Cxx chip select
SK BIT p1.3 ; serial data clock
DI BIT p1.4 ; serial data input
DO BIT p1.5 ; serial data output


DSEG AT 20H

ORG 20H ; stack origin
stack: DS 20H ; stack depth


CSEG

ORG 0000H ; power on/reset vector
jmp on_reset

ORG 0003H ; external interrupt 0 vector
reti ; undefined

ORG 000BH ; timer 0 overflow vector
reti ; undefined

ORG 0013H ; external interrupt 1 vector
reti ; undefined

ORG 001BH ; timer 1 overflow vector
reti ; undefined

ORG 0023H ; serial I/O interrupt vector
reti ; undefined

ORG 0080H ; begin code space
USING 0 ; register bank zero
on_reset:
mov sp, #(stack-1) ; initialize stack pointer

; Initialize AT93Cxx control lines.

clr CS ; low
clr SK ; low
setb DI ; high
setb DO ; high

; Initialize SIZE flag.

clr size ; specify 8-bit data
; setb size ; specify 16-bit data

;
; Sample function calls.
;

; Read (byte if SIZE/ORG=0, word if SIZE/ORG=1).

mov addr_lo, #0 ; address
call read

; Write byte (SIZE/ORG=0).

mov addr_lo, #7fh ; address
mov data_lo, #55h ; data
call write ; check carry after return

; Write word (SIZE/ORG=1).

mov addr_lo, #3fh ; address
mov data_lo, #55h ; data
mov data_hi, #0aah ; data
call write ; check carry after return

; Fill with byte (SIZE/ORG=0).

mov data_lo, #55h ; data
call wral ; check carry after return

; Fill with word (SIZE/ORG=1).

mov data_lo, #55h ; data
mov data_hi, #0aah ; data
call wral ; check carry after return

; Erase address (byte if SIZE/ORG=0, word if SIZE/ORG=1).

mov addr_lo, #0 ; address
call erase ; check carry after return

; Erase device.

call eral ; check carry after return

; Enable write.

call ewen

; Disable write.

call ewds


read:
; Read data from addressed byte or word.
; Called with address in register ADDR_HI:ADDR_LO.
; Returns data in register DATA_LO if SIZE flag is low,
; in register pair DATA_HI:DATA_LO if SIZE flag is high.
; Destroys B, DPTR.

setb CS ; raise CS

; Shift out start bit (1) and op code (10).

mov dpl, #110b
mov b, #3
call outdata

; Shift out address, MSB first.

mov dpl, addr_lo ; low byte
mov dph, addr_hi ; high byte (may be undefined)
mov b, #NADDR ; bit count
call outdata

; Read output data.

call indata ; get return data

clr CS ; drop CS
ret


write:
; Write data into the addressed byte or word.
; ERASE is not required before WRITE.
; Called with address in registers ADDR_HI:ADDR_LO,
; data in registers DATA_HI:DATA_LO.
; SIZE flag low indicates valid data in DATA_LO only;
; high indicates valid data in both DATA_HI and DATA_LO.
; Returns CY set to indicate error. Destroys B, DPTR.

setb CS ; raise CS

; Shift out start bit (1) and op code (01).

mov dpl, #101b
mov b, #3
call outdata

; Shift out address, MSB first.

mov dpl, addr_lo ; low byte
mov dph, addr_hi ; high byte (may be undefined)
mov b, #NADDR ; bit count
call outdata

; Shift out data, MSB first.
; Number of bytes varies according to SIZE flag.

mov dpl, data_lo
jb size, ee61
mov b, #8
jmp ee62
ee61:
mov dph, data_hi
mov b, #16
ee62:
call outdata

clr CS ; drop CS

; Poll device status.

call status ; returns CY
ret


wral:
; Write data into all addresses (fill).
; Valid only when Vcc is 5.0 Volts +/- 10 percent.
; Called with data in registers DATA_HI:DATA_LO.
; SIZE flag low indicates valid data in DATA_LO only;
; high indicates valid data in both DATA_HI and DATA_LO.
; Returns CY set to indicate error. Destroys B, DPTR.

setb CS ; raise CS

; Shift out start bit (1), op code (00) and 01,
; followed by a device-specific number of undefined bits.

mov dptr, #(10001b SHL (NADDR-2))
mov b, #(NADDR+3)
call outdata

; Shift out data, MSB first.
; Number of bytes varies according to SIZE flag.

mov dpl, data_lo
jb size, ee71
mov b, #8
jmp ee72
ee71:
mov dph, data_hi
mov b, #16
ee72:
call outdata

clr CS ; drop CS

; Poll device status.

call status ; returns CY
ret


erase:
; Erase addressed location.
; An erased byte reads as all ones (FF hex).
; Called with address in registers ADDR_HI:ADDR_LO.
; Returns CY set to indicate error. Destroys B, DPTR.

setb CS ; raise CS

; Shift out start bit (1) and op code (11).

mov dptr, #111b
mov b, #3
call outdata

; Shift out address, MSB first.

mov dpl, addr_lo ; low byte
mov dph, addr_hi ; high byte (may be undefined)
mov b, #NADDR ; bit count
call outdata

clr CS ; drop CS

; Poll device status.

call status ; returns CY
ret


eral:
; Erase all addresses.
; All data will read as all ones (FF hex).
; Valid only when Vcc is 5.0 Volts +/- 10 percent.
; Returns CY set to indicate error. Destroys B, DPTR.

setb CS ; raise CS

; Shift out start bit (1), op code (00) and 10.

mov dptr, #(10010b SHL (NADDR-2))
mov b, #(NADDR+3)
call outdata

clr CS ; drop CS

; Poll device status.

call status ; returns CY
ret


ewen:
; Enable erase/write.
; Erase/write remains enabled until disabled with EWDS.
; Returns nothing. Destroys B, DPTR.

setb CS ; raise CS

; Shift out start bit (1), op code (00) and 11.

mov dptr, #(10011b SHL (NADDR-2))
mov b, #(NADDR+3)
call outdata

clr CS ; drop CS
ret


ewds:
; Disable erase/write.
; Returns nothing. Destroys B, DPTR.

setb CS ; raise CS

; Shift out start bit (1), op code (00) and 00.

mov dptr, #(10000b SHL (NADDR-2))
mov b, #(NADDR+3)
call outdata

clr CS ; drop CS
ret


status:
; Read device status.
; The device output is sampled every 50 microseconds until timeout
; or ready. Allows a total of approximately 10 milliseconds for
; the device to signal ready before timing out.
; The DO pin is allowed to float before status polling begins.
; Returns CY cleared to indicate ready, set to indicate timeout.
; All registers preserved (except flags).

push b

setb DO ; float pin
setb CS ; select device

mov b, #220 ; 220 * 50 uS = 11 mS

; Delay 50 microseconds.
ee40:
push b ; 2 uS
mov b, #22 ; 2 uS
djnz b, $ ; 2 uS * 22
pop b ; 2 uS

jb DO, ee41 ; jump if DO is high (READY)

djnz b, ee40 ; next pass
setb c ; flag error
jmp ee42 ; return
ee41:
clr c ; clear error flag
ee42:
clr CS ; deselect device

pop b
ret


indata:
; Fetch data from the AT93Cxx.
; The AT93Cxx family presents data most significant bit first.
; The bit stream is assembled into bytes by function SHIN.
; The CS pin is controlled by the caller.
; The DO pin is allowed to float before data is read.
; If the SIZE flag is cleared, one byte is returned in register
; DATA_LO. If the SIZE flag is set, two bytes are returned in
; register pair DATA_HI:DATA_LO.
; Destroys A.

setb DO ; float pin

; Read and assemble first data byte.

call shin
jnb size, ee21 ; jump if data is only one byte wide

mov data_hi, a ; save high byte

; Read and assemble second data byte.

call shin
ee21:
mov data_lo, a ; save low byte
ret


shin:
; Shift in eight bits from the AT93Cxx, most significant bit first,
; and assemble them into a byte. On return, the SK pin is left low.
; Returns assembled byte in A.

push b

clr SK ; drop clock
mov b, #8 ; init loop / delay min one uS
ee30:
setb SK ; raise clock
nop ; delay min one uS
mov c, DO ; read serial data output
rlc a ; shift in bit / delay min one uS
clr SK ; drop clock
djnz b, ee30 ; next bit / delay min one uS

pop b
ret


outdata:
; Massage data and move it out to the AT93Cxx.
; This function accepts from one to sixteen bits of data and
; formats it to be shifted out to the AT93Cxx by function SHOUT.
; The CS pin is controlled by the caller.
; On entry, expects from one to sixteen bits of data in DPTR,
; right-justified, and a count of the number of valid bits in B.
; Returns nothing. Destroys A, DPTR.

push b

mov a, b ; get bit count
clr c ; compare count to eight
subb a, #8 ;
jc ee6 ; jump if count less than eight
jz ee5 ; jump if count equals eight

; Bit count greater than eight.
; Use result of first subtraction in compares.

mov b, a ; save adjusted bit count
clr c ; compare adjusted count to eight
subb a, #8 ;
jc ee2 ; jump if count less than eight
jnz ee9 ; jump if count greater than eight

; Bit count equals eight.

mov a, dph
jmp ee4

; Bit count less than eight.
; Use count to position data.
ee2:
push b ; save count
mov a, dph ; get data
ee3:
rr a ; shift data
djnz b, ee3 ;
pop b ; restore count
ee4:
call shout

; Did high byte. Do low byte, count equals eight.

mov b, #8

; Bit count equals eight.
ee5:
mov a, dpl
jmp ee8

; Bit count less than eight.
; Use count to position data.
ee6:
push b ; save count
mov a, dpl ; get data
ee7:
rr a ; shift data
djnz b, ee7 ;
pop b ; restore count
ee8:
call shout
ee9:
setb DO ; leave pin floating

pop b
ret


shout:
; Shift out a byte to the AT93Cxx, most significant bit first.
; On return, the SK pin is left low.
; Returns nothing. Destroys A, B.

ee50:
clr SK ; drop clock
rlc a ; move bit into CY
mov DI, c ; output bit
nop ; delay min 400 nS
setb SK ; raise clock
djnz b, ee50 ; next bit / delay min one uS

clr SK ; drop clock
ret


END


返回首页