|
|
EC挂接8Mbit SST25VF080B的话,可参考和学习,其它的SPI FLASH雷同。- Software Driver9 P! r4 e& l L" {) y# m" g
- ( l% b0 k8 g; H8 r
- SST25VF080B 8 Mbit(1M x 8) Serial Flash Memory
1 Y2 w8 O5 W" P
i! s" C5 B4 U4 l* t- November 4th, 2005, Rev. 1.0
( G5 k q" f& h- ~+ z1 k - 2 c; S# P3 l0 t! \( y0 [
- ABOUT THE SOFTWARE1 A; h9 W) }% K) D
- This application note provides software driver examples for SST25VF080B,
# v1 I6 ?+ K) H$ K- ^ - Serial Flash. Extensive comments are included in each routine to describe
" G8 f d- Y+ c) W: m6 b: o - the function of each routine. The interface coding uses polling method * V7 a' h. |+ T' w, n& j3 N' _2 R
- rather than the SPI protocol to interface with these serial devices. The9 v. _! V7 i( p
- functions are differentiated below in terms of the communication protocols
. L& F! L8 U& \8 B2 w* ] - (uses Mode 0) and specific device operation instructions. This code has been
6 \! @- |" _5 ]6 @2 V. x1 o* [ - designed to compile using the Keil compiler.5 w ?1 ?$ h. `3 r' ]# H
- r! r9 P+ p% X; k6 A
- + A( c4 v+ G7 h. ?
- ABOUT THE SST25VF080B
/ l& ]/ v9 T, x7 D9 ]5 ?) D L7 b/ N - ! J+ w% G( E+ N& E' B
- Companion product datasheets for the SST25VF080B should be reviewed in
4 a; ~: D% N" [. d: y5 y - conjunction with this application note for a complete understanding ; e) R/ l& q, J1 _' _, Y
- of the device.- Y5 Q$ p$ n- x b) s, M
- # \% U% A3 ?% _$ z6 n
1 w, b! k6 x3 w' @! h K- Device Communication Protocol(pinout related) functions:
% K2 z& T0 o) V6 c
+ n" h+ y( y' C, j- Functions Function
# V; |, B; L0 o/ `! k - ------------------------------------------------------------------
- u/ d( }7 {, g$ c" l - init Initializes clock to set up mode 0.4 u) u4 G7 T! j3 j5 v$ x) A
- Send_Byte Sends one byte using SI pin to send and
' j- O, }8 V n9 W5 d& \+ [ A& s - shift out 1-bit per clock rising edge. f& ^' @. ]- V1 R! ~
- Get_Byte Receives one byte using SO pin to receive and shift " ?1 I8 V( W; ]) x; ]
- in 1-bit per clock falling edge& L0 F4 q& k* m: \% e; K* J+ z
- Poll_SO Used in the polling for RY/BY# of SO during AAI programming
5 f7 G C+ w* G% D( k. R - CE_High Sets Chip Enable pin of the serial flash to high3 c9 V9 H t" t6 R
- CE_Low Clears Chip Enable of the serial flash to low
# Z- k* Z1 d% t5 z: o4 E& s9 e - Hold_Low Clears Hold pin to make serial flash hold
2 a& H0 l. Z. x( V0 z' F/ r) ~ - Unhold Unholds the serial flash1 h. O8 \. L) J: @1 U% a6 p" V
- WP_Low Clears WP pin to make serial flash write protected" ~0 a/ W0 Z- G: k
- UnWP Disables write protection pin
9 ^: \& F0 @: i1 y, m
+ s, g' ]" V$ l- Note: The pin names of the SST25VF080B are used in this application note. The associated test code
& F5 j/ P" C" w' g6 I! h - will not compile unless these pinouts (SCK, SI, SO, SO, CE, WP, Hold) are pre-defined on your
, f" f) M5 H% o, C: a - software which should reflect your hardware interfaced.
2 q/ V- x5 G# S' H6 t( X - 7 A4 R9 K/ l, z8 W7 g: W% h7 Q
- " d7 O" S5 _, w2 n7 M4 u8 z& ?. a
- Device Operation Instruction functions:
( P: s+ W( _$ x) ^4 n1 H - , L% u Z: `, E% H% B+ p. _8 \, X
- Functions Function! G7 W( D1 _4 R P6 s! H- I
- ------------------------------------------------------------------
, c4 i9 @; i7 o/ Y4 r( D) S; n0 m - Read_Status_Register Reads the status register of the serial flash
; x M5 c3 o V5 b0 P! ~ - EWSR Enables the Write Status Register
9 {: g, |, c1 s$ `9 z! z) m - WRSR Performs a write to the status register
0 ^7 n8 ?9 D5 a( v5 @2 p - WREN Write enables the serial flash
( D6 p$ d8 ]3 H% r% X# k. H& [ - WRDI Write disables the serial flash
* |% \& o2 L2 Z6 k - EBSY Enable SO to output RY/BY# status during AAI programming
0 K$ w) i5 ~4 D2 `' C! ?( e - DBSY Disable SO to output RY/BY# status during AAI programming
4 [6 a$ ^; N1 N4 ?( y! K - Read_ID Reads the manufacturer ID and device ID" F# Z# ?$ K- p9 L y M
- Jedec_ID_Read Reads the Jedec ID% m) V1 M1 ]7 ^
- Read Reads one byte from the serial flash and returns byte(max of 25 MHz CLK frequency), ~5 L$ ]3 [& p) F
- Read_Cont Reads multiple bytes(max of 25 MHz CLK frequency)
; e; m, N! K0 {* s/ B: z9 u - HighSpeed_Read Reads one byte from the serial flash and returns byte(max of 50 MHz CLK frequency)+ i3 {3 t2 Z' o' M% ]
- HighSpeed_Read_Cont Reads multiple bytes(max of 50 MHz CLK frequency)
. t- M* n* F# h( F2 X - Byte_Program Program one byte to the serial flash
. N+ b( K9 Z% M; B h$ D - Auto_Add_IncA Initial Auto Address Increment process
* ? D8 l+ p; u6 F2 ~2 P- c0 n - Auto_Add_IncB Successive Auto_Address_Increment process after AAI initiation
- ]! e E! X( N* U6 X8 K; \5 \' h - Auto_Add_IncA_EBSY Initial Auto Address Increment process with EBSY
4 d2 R, s; ~* D+ t3 Z! q, h4 _ - Auto_Add_IncB_EBSY Successive Auto_Address_Increment process after AAI initiation with EBSY and WRDI/DBSY
! d1 r% i& `: a, I - Chip_Erase Erases entire serial flash
7 S5 s( K# z' V8 ?: Z- i! u( o - Sector_Erase Erases one sector (4 KB) of the serial flash
; E4 v$ y5 k5 ~; X% z) w - Block_Erase_32K Erases 32 KByte block memory of the serial flash
- t i, `$ J7 ~0 N - Block_Erase_64K Erases 64 KByte block memory of the serial flash9 P: V, ~& G( Q! Y% B% {; Y2 Q
- Wait_Busy Polls status register until busy bit is low
+ `: F8 n% C; r. ~( @ - Wait_Busy_AAI Polls status register until busy bit is low for AAI programming
! l4 p; Z5 ?9 l) N6 t e - WREN_Check Checks to see if WEL is set& H# e* ^' v0 T
- WREN_AAI_Check Checks to see if WEL and AAI mode is set/ U: B5 x2 _6 `6 ~" J* \
& D4 K1 X7 S( K( h: z
p1 C/ E0 ]: J& a8 c8 v. s/ N9 Q
0 v* |2 j% Y4 d1 i-
0 A _) W8 V: ^' v - "C" LANGUAGE DRIVERS
$ I# e& `$ d* g+ R
' ]( A4 A% `! C: P. Z- /********************************************************************/& O! q8 ^8 H6 f$ v0 E
- /* Copyright Silicon Storage Technology, Inc. (SST), 1994-2005 */
' [3 j: J5 E# R; o" |% T0 |: I1 P% O* x - /* Example "C" language Driver of SST25VF080B Serial Flash */4 E) N; t4 l( H$ y5 F Q
- /* Conrado Canio, Silicon Storage Technology, Inc. *// g4 j3 B+ E' Z
- /* */% I+ ]# V' A8 }& ^0 X9 p2 ?- d7 L
- /* Revision 1.0, November 4th, 2005 */ : t1 E7 V' g) t+ j7 G/ _
- /* */
7 z N$ b0 O3 S' G - /* */
" S K0 l$ k* s7 Q3 Y& l s - /********************************************************************/" X I; ]5 d% K: k8 S4 o
- " s: N% ~, C1 A2 H
- #include <stdio.h>3 o' {" z! x i* ]/ L
- #include <stdlib.h>) B Q) G O2 s9 c8 ]" B
+ {$ I( y$ Z0 w/ u9 Q0 L9 T* b. u- /* Function Prototypes */
' a0 w: s% v2 S/ y1 K# I" z3 U# \; ~" ]
& ~" i( A( X4 F: Y6 ^* K- void init();+ U7 k9 l. i( \7 S8 l% g! N7 |
- void Send_Byte(unsigned char out);
) J9 K+ i( [. J# P" R - unsigned char Get_Byte();3 Z5 q. T* I5 a. ?7 n) D5 {# ~
- void Poll_SO();
7 p3 [- }, S) W+ y5 O$ v$ C - void CE_High();2 L! b+ t/ L! a. m% L$ @5 D, W
- void CE_Low();
V' F* s2 P4 o9 e9 o& r - void Hold_Low();
+ @: O6 k2 K* e8 b/ F+ V - void Unhold();% T' {6 B0 R7 Q- C
- void WP_Low();1 T" r% ^" g a3 J- s/ ]/ O
- void UnWP();
+ ?: D9 m: J, Z" f - unsigned char Read_Status_Register();
( X' }2 R O' \" @, [ - void EWSR();
8 u+ ?$ c, G' D& `% I - void WRSR(byte);; `* Q6 n' b. o5 j1 D* u
- void WREN();
, u* u* v0 C1 V/ j - void WRDI();
; V7 t t7 q* A( b) Q4 o - void EBSY();
. v6 \0 m% {# M - void DBSY();
) p, w$ e! h% b1 o) I - unsigned char Read_ID(ID_addr);
: h' E& k; |: V7 I; [, [2 s - unsigned long Jedec_ID_Read();
% j$ P% x( x* m* H# O6 R3 ~ - unsigned char Read(unsigned long Dst);3 I$ N& Q. g9 c$ G) F
- void Read_Cont(unsigned long Dst, unsigned long no_bytes);4 ~6 Q# @) z( J u
- unsigned char HighSpeed_Read(unsigned long Dst); * o5 i U2 |# O
- void HighSpeed_Read_Cont(unsigned long Dst, unsigned long no_bytes);
6 f2 l2 \. p! a n% \ - void Byte_Program(unsigned long Dst, unsigned char byte);
8 U3 ]& J4 d3 G" x5 x* P - void Auto_Add_IncA(unsigned long Dst, unsigned char byte1, unsigned char byte2);
& w8 e9 }2 i7 q1 E: J - void Auto_Add_IncB(unsigned char byte1, unsigned char byte2);2 I/ S5 }& U* ~6 h- v) J2 z
- void Auto_Add_IncA_EBSY(unsigned long Dst, unsigned char byte1, unsigned char byte2);3 P& |! r6 W: M6 c4 g: `
- void Auto_Add_IncB_EBSY(unsigned char byte1, unsigned char byte2);: X; K! h; q0 z' |2 D5 p$ v4 ?6 ]: j1 ?
- void Chip_Erase();# O7 n, s& X @8 g n
- void Sector_Erase(unsigned long Dst);
/ h' n* {5 T5 ]* o( ~ - void Block_Erase_32K(unsigned long Dst);
. I4 R" H' y) |2 t, o, i% ~5 A - void Block_Erase_64K(unsigned long Dst);( j$ \; e* Y$ l0 _9 n. W
- void Wait_Busy();
7 R- ?& v- n9 D+ o8 r8 D - void Wait_Busy_AAI();& t; s- d! ]8 @8 X* F. v
- void WREN_Check();
" B) q+ L' E3 B - void WREN_AAI_Check();
, {8 }& U8 y# G. N" N8 Z' C4 V
$ ~/ M6 o/ D& H, c+ e) f1 o7 b- void Verify(unsigned char byte, unsigned char cor_byte);" v* Q9 n) `- ~: l7 ^ F
- 1 G" H9 V, V% l- S7 w
- unsigned char idata upper_128[128]; /* global array to store read data */ [) n% S _6 h. |0 H
- /* to upper RAM area from 80H - FFH */9 Y0 {, p" x2 ~; E
d4 A" a! x& J% ^. G* E- /************************************************************************/
. C* h8 N" A4 o2 C1 ] - /* PROCEDURE: init */
! A5 |8 K+ R+ c# q0 W - /* */
H1 g8 l: I2 @+ n - /* This procedure initializes the SCK to low. Must be called prior to */
- [ g( C9 G1 T2 {( o3 { - /* setting up mode 0. */
- m% t V" o, B% v - /* */: _/ B0 L/ i2 `
- /* Input: *// Q% M/ X7 F' B: `' {5 _
- /* None */1 q! F/ C) d6 H c: w
- /* */: y# w6 V1 F. a! t: q
- /* Output: */; A, n) v: Y' J3 N) \# M
- /* SCK *// e2 a8 G n. W0 @
- /************************************************************************/
" Y5 Z& U. U2 K: l - void init(); m. o b: P. w9 y
- {
1 W! Z1 j' P F3 i- t) c, g! b" x - SCK = 0; /* set clock to low initial state */
3 {3 R. E5 g" l- z- V; r# i - }
; t4 n9 j+ Y- M4 h& J
5 F1 N5 h- C8 m- x, p& y- /************************************************************************/
4 S | K7 X6 d: U O - /* PROCEDURE: Send_Byte */% s0 K7 y: L6 O- y3 E" x- }( s4 Q5 y
- /* */0 y9 W4 d& @: W& K# D
- /* This procedure outputs a byte shifting out 1-bit per clock rising */
6 v/ c0 A9 V" m% \2 c - /* edge on the the SI pin(LSB 1st). */
* ^: g) a$ v8 O/ l - /* */* m0 O) G; T, A
- /* Input: */8 E; u2 n; j; l- v: R+ v1 w
- /* out */
* I% @: b, q& Y: ?3 q - /* */
$ N& R% Z$ ]/ f6 U% }4 X - /* Output: */+ M, Y# O4 M* q a; a( O! z! q+ M5 a
- /* SI */8 }, h' v6 Z- u- y- j/ _
- /************************************************************************/
1 S. }9 H/ b9 ~ - void Send_Byte(unsigned char out)! h) n; l/ j; X) k; a- a: g3 e
- {
$ e# F0 N/ B* ^; {3 c* y% p - $ `) C! X5 V/ j9 ^
- unsigned char i = 0;+ @6 T3 o) J4 B9 ?) u5 C$ _
- for (i = 0; i < 8; i++)
, Q( e( m' [! e' l - {
( E! @* x8 I" X& t6 a2 i - + b8 g* b" i f* ^8 m& M
- if ((out & 0x80) == 0x80) /* check if MSB is high */. ?, u3 r/ o" W" B! b4 V
- SI = 1;4 b1 G6 W1 w/ o! N8 T
- else
( R% n3 ^5 m: h) B* ~7 s - SI = 0; /* if not, set to low */
8 i. l+ a% G' u/ e, g - SCK = 1; /* toggle clock high */
1 D+ c* n" N6 `5 h$ p# r6 a6 @ - out = (out << 1); /* shift 1 place for next bit */, K0 r, p( W- u+ O! }; v( Y
- SCK = 0; /* toggle clock low */. [2 {' v9 Q$ K& r( o' @+ N
- }
8 b) i5 H+ ^4 c* l a6 J- }* c - }% J/ ^9 E, j1 N5 W
- J9 K, X6 Z' d Y& I7 t7 {# U C
- /************************************************************************/
! ~& E' I; }$ l1 t7 F' y - /* PROCEDURE: Get_Byte */$ c; G' j9 n/ o: I1 L0 b( f, n' `
- /* */
/ ^0 E2 e! `2 a% H/ h& h5 r - /* This procedure inputs a byte shifting in 1-bit per clock falling */! Y6 a! v' C- a+ [3 d
- /* edge on the SO pin(LSB 1st). */
4 }8 Y' g% Z( V4 S% f: G - /* */5 n% u7 E$ s8 x. T: a5 X$ l
- /* Input: */
* r R3 v* {- u - /* SO */
4 }/ N. T) ]" q0 k- M - /* */
( l* O# @0 } Z - /* Output: */
+ ]1 a: K# c; G% I, \% [1 h - /* None */: H- D2 ]1 L* E- Q1 e' }# ^ Z5 T
- /************************************************************************/
) e) n9 q. ?0 h. o - unsigned char Get_Byte()
# Z+ }# I7 y3 D% w - {
2 u2 P7 [0 h2 @, Y" h9 M - unsigned char i = 0, in = 0, temp = 0;$ O7 X7 p+ Q8 s5 y# O
- for (i = 0; i < 8; i++)6 [% Z, O$ r3 e& F" \$ B
- {$ r# i! d4 }: O( C! W
- in = (in << 1); /* shift 1 place to the left or shift in 0 */
; ~0 @8 _ I0 ?4 k2 M/ L s - temp = SO; /* save input */; K$ Y6 U) T8 a# t; Q* a4 O% D) w
- SCK = 1; /* toggle clock high */
& j& x C0 e O' ~' D - if (temp == 1) /* check to see if bit is high */# J m( o1 z; T1 R5 |* y# |
- in = in | 0x01; /* if high, make bit high */# E, w# V! S: B9 W
o8 {0 Q( t& t5 W: c# d- SCK = 0; /* toggle clock low */
) P0 k* @' I0 q w5 M/ l - 5 [1 x& `( K$ @0 s# ~. i1 Y
- }6 b; [4 p6 t4 T9 N/ @; i
- return in;
" J1 N+ P( A7 `0 y% s - }
/ a5 H0 N; i) B2 y# u0 d( ~
5 J0 y% ?: v: y6 e- /************************************************************************/
/ l. a ]; m4 u! E! j - /* PROCEDURE: Poll_SO */3 c; Q6 L, A" l0 V) d: S
- /* */. e: c8 p+ ~ V( x% z" H
- /* This procedure polls for the SO line during AAI programming */$ K$ E9 G4 X" V0 ~/ {
- /* waiting for SO to transition to 1 which will indicate AAI programming*/3 h! X. Z0 Y7 b5 S h# F) X! J
- /* is completed */2 V; P. `* |4 \: s I# y) |9 L$ t
- /* */
- e% W2 h1 p# v4 @9 G7 q( I - /* Input: */( e+ r% k5 U: E; s, f# ~
- /* SO */" m9 b! ]7 k$ Z+ X s, i
- /* */- T- |$ l4 M# \6 j" L& i4 d
- /* Output: */
8 |0 y" [* Q8 z! k% z - /* None */
5 i. \: P4 K8 j; d - /************************************************************************/
" w$ s4 A3 @2 _2 G, Z - void Poll_SO()
; {4 H2 j! f* N% g, z& ^ - {" F( l$ C, N3 e4 q4 R" @% x
- unsigned char temp = 0; s, e6 `, u9 Y- h8 C
- CE_Low();& n1 d3 o1 X2 I* \: S
- while (temp == 0x00) /* waste time until not busy */
0 d: ^1 I! {3 E - temp = SO;
1 x. T; a6 O7 g" V' a7 [ - CE_High();) I6 C5 Z& G+ d) H, ?
- }
6 _; A0 t) P) F: x4 Z6 j( C- t+ R - 4 y' n% s- z" R2 C* Q$ u
- /************************************************************************/
2 H) \- T+ a( |# B - /* PROCEDURE: CE_High */5 J2 l, {# W3 f( [
- /* */" t; J& \; v ]& \# K% |
- /* This procedure set CE = High. */: r4 o, d: y+ i: ?1 ^' \! ?
- /* */
* m- i6 C8 p, p9 d. t$ I - /* Input: */
8 [ H, D3 C7 p' g - /* None */
% ]; h, w. G* O; Q+ _" t& | - /* */
2 k' G: \" R$ o, U) n' g* P4 B - /* Output: */: i' g8 x0 ~3 i. ]4 W
- /* CE */2 _, x4 ~1 d0 H# |; }, @
- /* */$ a: x1 f# x& G* W% e+ R
- /************************************************************************/2 z/ J1 b1 l' m3 K. @) w
- void CE_High() / I! t. Y7 r' R+ J6 \1 u2 y
- {
1 e) {# J/ f+ L5 H, P - CE = 1; /* set CE high */% f9 f/ M& x* C/ A
- }
7 ~& w3 z' M3 [$ n8 @
. y; A2 d/ `1 q, d& N; |. H- /************************************************************************/+ `% w0 C" z1 j
- /* PROCEDURE: CE_Low */" g9 g& e9 u9 F# S9 `- q' L' M
- /* */
3 P" Q6 t4 G" h! F! X2 W" W# w - /* This procedure drives the CE of the device to low. */
0 J$ @! r% v6 M7 U - /* */. |% a& t4 k0 }: I& d
- /* Input: */7 ~9 ^. u$ T5 A9 y0 v0 f
- /* None */( k3 l0 z, s$ g- H
- /* */
" l3 \" k8 A7 ~8 o2 l - /* Output: */$ x- a$ g7 |) |
- /* CE */& A$ ~: h9 {' k& q3 |% b* ]) |3 H
- /* */6 t3 |; }" P. E7 Q
- /************************************************************************/
0 _# i8 }5 t& J& W2 s# R5 k - void CE_Low() / V, N* ]& `. i
- {
, ]: c- R' ^3 F1 v1 X2 z - CE = 0; /* clear CE low */
, b8 W$ r& p" V h( u - }
9 o! K% o) _; u8 i - / S/ v& y6 |+ |
- /************************************************************************/
9 Z3 ^+ `# R3 o- C( k+ g3 f - /* PROCEDURE: Hold() */; g: A3 u3 D% G* M7 |4 x2 K
- /* */
# v! s( |1 I/ }, I - /* This procedure clears the Hold pin to low. */
1 H- M- r+ q1 ^% ^3 X. }: t - /* */
7 x" z4 S# p# u" d2 r6 d - /* Input: */
: c' r1 Y8 }' v; T: W& S - /* None */. M# O/ Q6 O2 o
- /* */
1 y T% x, E4 X) e( ~1 @$ _ - /* Output: */8 G \) |9 c' h6 C& t) `9 E
- /* Hold */
2 T: {8 O6 W' z% B, g- b% ] - /************************************************************************/5 h! y: Y. m0 }* a( }8 ^
- void Hold_Low()- V# g$ u/ d u- Q5 O2 ?/ b
- {
' t2 {, B4 E! M% ~2 r - Hold = 0; /* clear Hold pin */5 k! b5 r7 U/ k, R
- }2 {4 n2 |& l6 I
- F( l$ e" e" I& g- /************************************************************************/
b6 {! V& [. \ - /* PROCEDURE: Unhold() */
( `0 K, g5 X1 s6 u! c4 v2 @( W" u - /* */, M( x# X( k3 x2 l& Y; h
- /* This procedure sets the Hold pin to high. */4 _# R5 b9 q& U" }$ p( }* \8 q2 [: t
- /* */
9 R* z0 Q3 i% Y) s Z) W0 T - /* Input: */
1 x& |# v' R' W - /* None */+ ?: l0 I& k* Z
- /* */: r- a8 M, D' G4 e" B O+ w
- /* Output: */6 \$ J5 H5 i' q
- /* Hold */$ a+ ?, S, N2 q
- /************************************************************************/& c a" t" e4 f
- void Unhold()
) c7 u3 t( l# {- c; x- B) O3 [ - {
) A# [' J2 _3 n) A# e: Y; o - Hold = 1; /* set Hold pin */! |# f2 Z) Y7 Y5 j6 o- n
- }3 F }# j) |7 I- e; B* M
- ( N; ^" W% _3 @/ r
- /************************************************************************/# E3 H8 ]6 ^6 c( ^, r( F
- /* PROCEDURE: WP() */# _; ~6 e. }! W( Q' r, e" P
- /* */
2 F/ Q; M$ M" E4 }, f! p! T - /* This procedure clears the WP pin to low. */
/ r# Y) [4 ^8 Y& s( w$ f3 T - /* */1 a' @ L, a1 v* I. |" }8 e
- /* Input: */2 k5 A% c+ N4 I+ `
- /* None */
) ~( w* _4 z* \9 X' }7 l& H - /* */
; f/ T# M3 ^$ D0 B - /* Output: */: u5 \+ i, w* W/ v
- /* WP */1 G; w4 r7 ~1 b# Q% d# F( S
- /************************************************************************/! E: b: Q2 d* W8 \2 ^' L r6 `
- void WP_Low()1 D8 R! n7 T1 P5 y* y% \
- {
+ k% `9 b. Q: ?" `8 g - WP = 0; /* clear WP pin */' ]8 Z; }2 M% I9 A" L2 K+ y
- }
4 H/ Y# O& }4 e. { - 4 J3 |/ b; [; V* E7 \& u5 m# B4 d
- /************************************************************************/
; s3 q v. \% K: M k c - /* PROCEDURE: UnWP() */3 `) c+ {5 ?- u+ i2 X
- /* */( g' V8 g' p6 f3 H, N; R
- /* This procedure sets the WP pin to high. */
6 c$ G+ T/ C6 b7 X* i# ^( y8 X& s k - /* */
, G/ Y9 Z6 U; ]0 }+ J' |8 ~+ a& s+ i - /* Input: */
3 \5 ^, t; R1 O- f/ ~' H) F# j6 S& X - /* None */
! x! |' I) X/ Z - /* */+ e( c& B5 X$ \' o# n2 Y# f F
- /* Output: */
3 v- Q" Y i# r8 ^! C! U! S - /* WP */
2 w4 c' [4 Z7 K' N - /************************************************************************/
% T4 f( s( F" O0 K - void UnWP()! z3 I2 X$ g3 J) m+ ^
- {
+ ^" l4 l, y6 q$ ?5 Z - WP = 1; /* set WP pin */
* O; @7 [% K7 e7 e* a - }: s& l5 ^2 ~) x' B2 a9 Z
- ( n, }' [1 J$ X. c- ]5 I
- /************************************************************************/
- ?; m, P& f# u# I' C2 f - /* PROCEDURE: Read_Status_Register */# T/ y6 W( l' R
- /* */2 Y- t( D4 F! r) l" P# f
- /* This procedure read the status register and returns the byte. */" F, W2 K" S, o: d' A, [: K3 e m
- /* */
, [$ u. G4 `) ^: A3 c - /* Input: */$ W; Y o# C/ I Y1 S" {3 d! W* ?
- /* None */7 K5 k/ N0 ?; Y4 A
- /* */
9 E3 v/ @/ ^6 m9 j( h) {8 q& V - /* Returns: */
I; k. W6 K# D* A0 }- } - /* byte */1 l4 n/ L1 C2 b$ v9 x+ m; M4 F* f l, [
- /************************************************************************/
) G8 i& d$ G3 c3 u$ f - unsigned char Read_Status_Register()
! q% i8 l$ f6 O - {1 _6 v3 q5 i6 `3 Y7 d! r# W" |* C! \
- unsigned char byte = 0;
4 O9 i+ G- U2 m3 ?: B5 g4 R% B/ D - CE_Low(); /* enable device */$ o7 p% ^& T3 v! p7 O# a
- Send_Byte(0x05); /* send RDSR command */: e0 ?( _7 N% t6 l& p+ \7 S/ W/ C
- byte = Get_Byte(); /* receive byte */0 \* X0 q* h+ O( V, y# p. D0 O
- CE_High(); /* disable device */
; l+ _; f2 Z- @4 b, O - return byte;
9 t$ ]. e8 o/ w) g2 G" ^ - }
' J; x3 H. ~5 Q H! C" x, K
% [! d P6 d0 q4 N- /************************************************************************/' d5 h* G8 p% G- Y- O4 _
- /* PROCEDURE: EWSR */
3 L3 r) Y2 S( G, K f' ^* G) N. U - /* */
6 n7 e$ H3 J4 I8 E - /* This procedure Enables Write Status Register. */
. w4 |: k5 ^8 r& x - /* */) A4 p+ V. q; y$ c" t" d, c5 ]
- /* Input: */
$ v& S6 h" l j" q+ l# z D - /* None */) t \+ ?3 f1 I$ \! T
- /* */
- ?, a, @: w8 D2 ^, O - /* Returns: */
5 O7 a% T3 m( `; o4 ?, { - /* Nothing */
9 N& u: f9 T6 s" v, Z$ ] - /************************************************************************/
2 @8 L" l) a; w9 {- ]5 p - void EWSR()
" _, G' c0 h* k- |! K/ T% | - {/ r% d5 E, I5 K S4 V `0 u3 I- O
- CE_Low(); /* enable device */
. a6 S/ o; k ], P0 o4 j - Send_Byte(0x50); /* enable writing to the status register */3 }3 T: F8 V8 A0 o! H9 i( s, K. k5 p
- CE_High(); /* disable device */- Q- P0 U: F3 }% K
- }8 O/ W4 E3 f+ U2 y9 K6 i
- + i- u; Q/ n+ z
- /************************************************************************/
. D# @. u- F- n9 |% B- E3 B+ w$ j- j! r* _ - /* PROCEDURE: WRSR */
" T. w P" w k - /* */
1 }& c1 d1 D$ h$ B: a9 Y - /* This procedure writes a byte to the Status Register. */* u2 v/ x. R: Q
- /* */' f9 f$ e2 S/ `) e: y7 \- j
- /* Input: */9 U, u: @( C! r, W
- /* byte */' u; J$ W. u7 U& a
- /* */
! b# Z* d3 Y; L - /* Returns: */
, T0 t' c3 s: K, D1 @: ^ - /* Nothing */5 F* w$ A+ P) L: I7 l2 @9 M( n
- /************************************************************************/
( G6 |0 R( G& e9 F# ?+ \& I - void WRSR(byte)
. m e. a+ [% k' Q - {
% G: O7 s! e0 v* l - CE_Low(); /* enable device */! @% O$ T- N1 m8 ~" D
- Send_Byte(0x01); /* select write to status register */$ B" z2 ^# k' r" C
- Send_Byte(byte); /* data that will change the status of BPx * Y3 c3 O% I. C# F& s6 j+ e7 b
- or BPL (only bits 2,3,4,5,7 can be written) */
! {% K& C+ z2 \0 P6 M; I - CE_High(); /* disable the device */
2 ]) E H7 A, V; X - }
- k/ @2 b1 T9 T9 C, M; F' c - 2 S9 c8 b# [8 d, ~8 d J
- /************************************************************************/( N. U; y/ v3 d
- /* PROCEDURE: WREN */
" i4 i7 l) t Y6 T% I0 @6 Z' F - /* */
! D1 w8 p- K) ~8 o' w" |+ t - /* This procedure enables the Write Enable Latch. It can also be used */9 d7 {' e) I. x. V2 f: c
- /* to Enables Write Status Register. */
( P& F8 {" C* t7 l7 H# O8 x - /* */
. [% V0 I$ I# s9 b) o# N: K - /* Input: */
+ z' K! l# m" i& z& K& F% T - /* None */2 i+ ?( g T1 e& Z$ [8 `
- /* */
7 i- D/ v8 X+ V/ ?6 E' a - /* Returns: */
5 p$ c) S( E$ y9 r( X3 d8 M2 P - /* Nothing */% {' R' {3 `/ K) O' U6 l" c4 g
- /************************************************************************/
: c3 h8 H6 {' {1 Z" j/ c8 ^- B - void WREN()
& ~ H' B- u/ R0 k' j$ A - {# A' |$ O1 {0 E
- CE_Low(); /* enable device */# M! L! G6 J! e/ S4 u$ q
- Send_Byte(0x06); /* send WREN command */1 f1 t# c* x" C$ l. E3 |# N: ]
- CE_High(); /* disable device */1 }. U1 d1 C% L6 E& D0 w
- }+ ^' |) [6 r: ?# s. Y& I
# k, b1 J- @- H( S" A6 i8 C% S- /************************************************************************/ h1 ?/ A5 S& I( z6 o
- /* PROCEDURE: WRDI */
8 A. z/ `0 n# ~ - /* */0 A8 f0 o" |$ }0 Z1 z( I
- /* This procedure disables the Write Enable Latch. */
& [; l; q: f& H& F& Z - /* */, T1 C- p }$ w9 | p& i
- /* Input: */# H2 o2 ?. {3 M. o8 C6 ]1 J
- /* None */2 x/ ^* G n, ` K8 M
- /* */
i* K( ~6 j8 b/ q( b) z - /* Returns: */8 Z8 R' Q1 q7 _& f
- /* Nothing */
7 I' r3 ^; U4 u4 G - /************************************************************************/
, m% } c0 p5 j) S8 z7 q - void WRDI()
/ R7 s5 M& U# i& [2 z$ a. n6 J - {
2 F, A- x0 {) S8 S# U) E - CE_Low(); /* enable device */: O. R' Q! P( ]4 f" M' p" P
- Send_Byte(0x04); /* send WRDI command */& Y# l2 O8 k8 X2 g& s0 m. L
- CE_High(); /* disable device */
; ]8 P. N3 Z7 U+ v! y( F% P! T - }8 W/ d+ r7 m( x/ T: m9 ~5 o1 N
/ w* z! I9 k) W% x% c- /************************************************************************/
: K; a T3 u' ` - /* PROCEDURE: EBSY */
2 |1 o, _5 {+ ?3 U& j - /* */
: P: F! V; B3 p* Z - /* This procedure enable SO to output RY/BY# status during AAI */
/ V6 H. `" Y% m! l - /* programming. */: E3 R, b0 s2 x5 l8 s L6 d- z
- /* */. Z7 k& S7 Z- }+ @/ x
- /* Input: */
( L8 K0 Z2 N J- w2 W! f - /* None */
3 Y( C8 ?% p+ r6 J - /* */
. w9 }. y: r0 {& l3 I9 u - /* Returns: */ p) J7 f& B8 s6 K& ~
- /* Nothing */' n6 K/ C- a* |* Z
- /************************************************************************/
8 }4 m6 c8 n) v8 z: @, Q5 S; P; Y" Z - void EBSY() I1 [3 @$ M# k5 d
- {1 u- ]0 {; P4 F0 D) }4 [
- CE_Low(); /* enable device */+ R9 ^8 [5 W' N" r, c7 w5 e# Y9 J k
- Send_Byte(0x70); /* send EBSY command */
4 X/ I* s6 x( @% V+ x0 K9 ]# l - CE_High(); /* disable device */1 |' O) n$ D0 v5 B
- }8 U. Z0 D3 y; @- T3 y
3 \) X9 G6 R& d/ @- ?- /************************************************************************/+ J, u6 N* a b- }" s
- /* PROCEDURE: DBSY */
/ H3 b) D5 E! J - /* */
9 v r# \) |7 o& e - /* This procedure disable SO as output RY/BY# status signal during AAI */
6 F. K9 T7 O$ A, [3 E( B4 z. \ - /* programming. */$ K/ |. A' i4 ?* O5 ^5 Z
- /* */# _" b2 _* b* M. g3 ]1 ]
- /* Input: */2 ?6 Q' P. T" C% d. ?& Y. M
- /* None */
# B: n3 F5 I( b, A8 R - /* */- x) M" ]6 s1 Q
- /* Returns: */9 r+ d9 I9 q }- c2 T6 F
- /* Nothing */
5 ~/ [$ x4 _7 ^ - /************************************************************************/: z9 V- n- p* U
- void DBSY()
7 R3 C# H) y; T6 z# s; |9 Z - {
5 r8 B, |+ O! G Z - CE_Low(); /* enable device */$ v" n$ C/ Y# d `
- Send_Byte(0x80); /* send DBSY command */
" q7 [3 c. c* [ - CE_High(); /* disable device */% m9 q m1 T6 J6 P% n. v0 S: R( [
- }6 r+ a4 F$ G# O5 {* h
- / |" [- ]( v. U0 t4 l8 }
- /************************************************************************/$ V) w) {" }1 h" _, ]/ {! u l( E; f
- /* PROCEDURE: Read_ID */
/ W4 D8 [( V# @" J$ e& k2 N - /* */
1 Q" A) I! E& ]$ q, p1 |+ L - /* This procedure Reads the manufacturer's ID and device ID. It will */% o/ W# r+ U. {0 u& o; e8 @
- /* use 90h or ABh as the command to read the ID (90h in this sample). */
3 T0 P2 _: D% Y$ p+ o6 ] - /* It is up to the user to give the last byte ID_addr to determine */) {2 d2 J! N& ^
- /* whether the device outputs manufacturer's ID first, or device ID */* C$ k \$ X* ^7 j6 T# c" |$ _3 n) k- d
- /* first. Please see the product datasheet for details. Returns ID in */
1 c# Z& A; y7 C S) s - /* variable byte. */) a% F }( G4 T. D
- /* */9 s# S4 _ x. s1 v$ ], w
- /* Input: */3 Q/ m% j, o: }9 p$ f' i/ Z
- /* ID_addr */0 S9 a! W8 M2 |4 G4 Q
- /* */
, j3 {- q& F- \$ B" Q, ]) p - /* Returns: */
. K3 ]) V- g# J4 ], s0 z8 A - /* byte: ID1(Manufacture's ID = BFh or Device ID = 8Eh) */
* \5 K5 o! X" g, e) U1 P+ X - /* */
6 j; o3 C! e. {' d( |3 F6 i - /************************************************************************/
* _; x t( I, \* ^1 G - unsigned char Read_ID(ID_addr)0 w0 A" Z: L6 J( d. I% E& [. P: v
- {
4 R: {1 o$ p3 r y3 ^ S - unsigned char byte;. ^ i4 k9 Z" W& n: E
- CE_Low(); /* enable device */
, O" _+ u+ T( Z$ l - Send_Byte(0x90); /* send read ID command (90h or ABh) */8 U7 C% n, t; s s$ c4 ?3 d
- Send_Byte(0x00); /* send address */
: {. H: Y& d* H, {' h, D - Send_Byte(0x00); /* send address */
6 N# ]& `+ U+ {( j# w - Send_Byte(ID_addr); /* send address - either 00H or 01H */) w1 p5 c6 [/ Q
- byte = Get_Byte(); /* receive byte */- t8 r: n8 o$ R0 u
- CE_High(); /* disable device */
* x0 y x; D, d5 j - return byte;
# u9 p' Q" E$ c" L) g6 L& ^ - }
! B2 f( M4 N" f/ H; F - # f' k0 y1 j5 c
- /************************************************************************/
3 ?% v. V1 a! P' A7 y - /* PROCEDURE: Jedec_ID_Read */) ^3 r H( A, p/ a: y9 Y5 @- q) c
- /* */! P7 @4 ~; G) n1 ]
- /* This procedure Reads the manufacturer's ID (BFh), memory type (25h) */5 S9 I( b+ H& y+ ?
- /* and device ID (8Eh). It will use 9Fh as the JEDEC ID command. */
7 M3 F) D0 T' @# _# A! B( h I - /* Please see the product datasheet for details. */
) w( `! i. t2 q7 B" q - /* */8 R* F2 d+ p% E1 e! T; l
- /* Input: */
4 }8 Y( h' p! m5 B - /* None */8 e2 c& [5 E$ i* S" `
- /* */4 y! f r2 g5 c; E5 H; s
- /* Returns: */
4 i5 y3 y& a) m7 c+ X - /* IDs_Read:ID1(Manufacture's ID = BFh, Memory Type (25h), */
$ l7 Y! |, u: k - /* and Device ID (8Eh) */
& ?7 P" L# X* l- i7 P# C, V - /* */
6 f0 i J% A5 r4 z; Q - /************************************************************************/9 h. R9 b+ x# A. Y! W
- unsigned long Jedec_ID_Read()
) e8 b9 {& I) f9 w+ g3 Q0 L - {
. j; ]- D0 Y: v+ M6 N! v - unsigned long temp;! R- e" Y- w& F1 h
- 9 W: n' N& ~5 I6 t G/ r) ?+ e7 W
- temp = 0;
9 r. r$ b1 D U
" K l+ R& F- Z- CE_Low(); /* enable device */ c( \- p- s2 _, m/ o
- Send_Byte(0x9F); /* send JEDEC ID command (9Fh) */
- d# F5 F2 z9 D1 x6 m - temp = (temp | Get_Byte()) << 8; /* receive byte */, c6 q; @/ E4 `% h
- temp = (temp | Get_Byte()) << 8;
. z+ H& w! h; a& ~ - temp = (temp | Get_Byte()); /* temp value = 0xBF258E */
8 l5 F. F7 n# |2 a6 U0 j4 f - CE_High(); /* disable device */
" S" c( j2 J0 {) m
( T& z: }/ ]! S. s0 {8 v' G- return temp;
( A* R. `% d/ n: X( G: e5 `$ M - }( a/ X. c$ b6 `& ~( D; B/ D
8 `9 L$ l% J( N7 H3 m- /************************************************************************/* c" x3 n" N! p+ w8 C' V
- /* PROCEDURE: Read */* `* S$ s) c! [( }0 r
- /* */ 4 ^& s! j2 l# B! ?
- /* This procedure reads one address of the device. It will return the */
. V: ]* N5 o" d$ D. i/ N* o5 |3 O3 V - /* byte read in variable byte. */5 e3 _& q3 ]6 K# f- J
- /* */* D. ^/ V% R6 g& g7 R# \& J, @
- /* */2 D: i% u4 O7 c+ T n
- /* */; q* ~. D* i+ G% k* Q
- /* Input: */
" x8 Z) U9 ^ p, j - /* Dst: Destination Address 000000H - 0FFFFFH */
7 }( L, I' W2 w7 q - /* */
; a8 A" ~" a6 ?1 O" b - /* */
: o( u& L% z* _3 P" }( C% k0 L# u - /* Returns: */
% q% J v, B" C7 H1 K - /* byte */: a$ _ ]3 P3 @
- /* */& ~! f3 b' p8 p4 I8 n( {
- /************************************************************************/! Z% b$ v% `0 w/ N# y' V* P2 \) ]2 W
- unsigned char Read(unsigned long Dst) 6 }3 D* z# L. u8 l$ E* e# q c
- {
( ~. O) e) q+ y; c% }, u8 y: J* _ - unsigned char byte = 0; & Z1 w* _" O. B! F2 Y
% [3 @: Z% F/ H4 I$ f$ c4 g: q$ `- CE_Low(); /* enable device *// i: r3 g. C9 y' O
- Send_Byte(0x03); /* read command */6 K8 a7 N2 ~0 T3 k9 B! f9 W
- Send_Byte(((Dst & 0xFFFFFF) >> 16)); /* send 3 address bytes */7 p0 L ~! Y; O7 l$ p
- Send_Byte(((Dst & 0xFFFF) >> 8));* b- u! K) I I U! V6 E
- Send_Byte(Dst & 0xFF);
4 R4 C0 ?* N9 i' f: A) m+ x - byte = Get_Byte();
* ~& P3 }! V9 `$ f5 N% O: y - CE_High(); /* disable device */ l9 `# x) }% t+ H
- return byte; /* return one byte read *// O& B- g6 |& R& t
- }
. [& A$ V6 H9 K( @ h3 a2 X3 \
w% M h3 `2 L" l+ B4 K- /************************************************************************/' P' [; ^) z1 @4 _' }
- /* PROCEDURE: Read_Cont */
: C4 r/ v$ y% M, u+ V6 u - /* */
, J" ?+ S/ U, r" e - /* This procedure reads multiple addresses of the device and stores */! S2 ~8 D; t% [" J1 z
- /* data into 128 byte buffer. Maximum byte that can be read is 128 bytes*/) m: d) N& d* t& o8 |
- /* */ Y" l; }% \9 ?. Z6 T
- /* Input: */
+ X, S8 D+ y' y$ K8 W$ d - /* Dst: Destination Address 000000H - 0FFFFFH */
8 M& D2 W- S% X - /* no_bytes Number of bytes to read (max = 128) */1 X/ p4 K. V5 |8 D
- /* */
0 M) P4 A& x8 H! R - /* Returns: */) j8 a1 h; u( c0 }# P
- /* Nothing */0 s. z# c7 x! [4 ]& @
- /* */
' U% U- h+ v4 Z# L6 m - /************************************************************************/% Q R4 l- F- q& C9 K' n) c
- void Read_Cont(unsigned long Dst, unsigned long no_bytes)$ v) X" ?" V+ @) D% G6 [0 Y3 x1 v
- {
' z% V% T& D0 Q$ h" C( ~) g4 F. G - unsigned long i = 0;' {8 ^( K- q$ t% L% Y9 u' U; ^
- CE_Low(); /* enable device */
" \3 \3 K: b; k& O3 G9 y5 J - Send_Byte(0x03); /* read command */
$ _8 b5 ]0 F8 ^2 A/ Y - Send_Byte(((Dst & 0xFFFFFF) >> 16)); /* send 3 address bytes */1 a* B' G, c3 @$ n F5 i
- Send_Byte(((Dst & 0xFFFF) >> 8));
% F# o0 m" q1 I# X - Send_Byte(Dst & 0xFF);
P; Y, ^& {; Q a' { - for (i = 0; i < no_bytes; i++) /* read until no_bytes is reached */- m4 K* v4 H& H/ L/ t \- ^
- {
, u7 X! F2 A' M( Q6 [: V; e - upper_128[i] = Get_Byte(); /* receive byte and store at address 80H - FFH *// X% L4 l* S% Y1 ~' s
- }$ _- _7 A7 P$ U. m1 K" C# c
- CE_High(); /* disable device */
2 H& i: @1 _" A: N: x9 z - 6 l- O7 z0 ]7 u" _
- }0 R7 R, i( _" J8 W' J$ v
- A! Q" ~' h8 _- ?- /************************************************************************/
, v5 t8 l1 y$ W6 U - /* PROCEDURE: HighSpeed_Read */" Q M- z! J' ~! z8 X1 r8 Y
- /* */ ! b+ c. g& h: s. z* L: `
- /* This procedure reads one address of the device. It will return the */
7 W7 y! p9 p# ~4 F - /* byte read in variable byte. */; ~/ R1 X* ]# N0 V
- /* */- x2 c) R. I) P z
- /* */
7 n$ l7 x( _$ V1 v - /* */8 d3 f+ O6 s7 _( o9 C/ ?. ?0 U
- /* Input: */
7 o+ j1 K* v& w) l: N0 E - /* Dst: Destination Address 000000H - 0FFFFFH */& a- x* r" {7 _$ |4 d
- /* */
0 C: a7 [; |! T/ j - /* */
0 e: q+ B( ?* J - /* Returns: */$ c+ J* v3 D) D' p3 l5 g0 k
- /* byte */$ ~5 L* \6 f* t2 L7 U0 s
- /* */
8 }+ R& @, \+ q+ E+ X - /************************************************************************/* |' [- Y5 O Z5 B/ |$ c. `
- unsigned char HighSpeed_Read(unsigned long Dst)
5 y8 Q- X/ W+ I8 G0 x3 ^. d- p - {6 u8 D. g0 { ^ ~- c, E3 ~6 e
- unsigned char byte = 0;
6 L& _# b; E8 g2 ^ - 8 ~1 S' S/ k. q
- CE_Low(); /* enable device */, I. G' e% Z5 \% C( E
- Send_Byte(0x0B); /* read command */: b! e9 O. T; Y& }- q1 ~
- Send_Byte(((Dst & 0xFFFFFF) >> 16)); /* send 3 address bytes */
2 U, H; I( m2 n - Send_Byte(((Dst & 0xFFFF) >> 8));# Z/ T: e- X# d* W Q1 k8 e1 q+ |6 @
- Send_Byte(Dst & 0xFF);5 [/ r4 a1 x& o: h5 a" w
- Send_Byte(0xFF); /*dummy byte*/% b) B" v8 q2 C. Y/ s" @* U
- byte = Get_Byte();$ }& l. J. U: `8 F0 ?: t3 T
- CE_High(); /* disable device *// z( v F6 n: w l. _: w
- return byte; /* return one byte read */
* q# l3 O1 T; ^& t* h8 q( r - }
# |$ E% @+ r- s* ` - . ?* q/ x- W( `8 b7 X& e: P
- /************************************************************************/3 i* Z: c' i( Y4 B8 A: i4 t+ q/ X! B
- /* PROCEDURE: HighSpeed_Read_Cont */) U' u. F e) U) b _
- /* */ q: B9 T! q9 _) L
- /* This procedure reads multiple addresses of the device and stores */
( O- t) d: H4 y2 @- X1 a6 N - /* data into 128 byte buffer. Maximum byte that can be read is 128 bytes*/
3 s! [ m" \* e+ x$ k7 b - /* */
/ a. Z( d; Z. r5 \ - /* Input: */
: [ F/ w) J1 Y) d5 j - /* Dst: Destination Address 000000H - 0FFFFFH */
- N/ p; b8 ]/ B2 F - /* no_bytes Number of bytes to read (max = 128) */3 r( C' q9 ?% g; k8 Q6 U r4 }" D
- /* */; X2 l8 X; U7 X! t
- /* Returns: */
1 f) z9 T9 e! v3 ? - /* Nothing */# k5 x- ^, m. k, K
- /* */
( W+ |& Q. U. k8 c: V9 @9 d( R - /************************************************************************/ k7 O# ^5 k, b/ M j
- void HighSpeed_Read_Cont(unsigned long Dst, unsigned long no_bytes), `8 V! R6 d1 }8 G
- {. y; K& r- ~* _8 N! v- H4 P
- unsigned long i = 0;
; H4 G6 B6 ^1 r4 V, D/ o, d - CE_Low(); /* enable device */
! d J5 p! t0 \# N8 c - Send_Byte(0x0B); /* read command */
2 n* ?% m" @. E: j, k- g4 F. T - Send_Byte(((Dst & 0xFFFFFF) >> 16)); /* send 3 address bytes */5 c U! T4 Y4 |. ]
- Send_Byte(((Dst & 0xFFFF) >> 8));
5 Q7 f$ a9 w" f* }: `9 {. O - Send_Byte(Dst & 0xFF);! W v( B- I% X7 T3 [
- Send_Byte(0xFF); /*dummy byte*/
# P) q3 @& A( m - for (i = 0; i < no_bytes; i++) /* read until no_bytes is reached */
. }2 x& o- s L - {
& g w `* V6 F& c3 S - upper_128[i] = Get_Byte(); /* receive byte and store at address 80H - FFH */
) x3 m+ Z' F4 T! Q0 T" _9 A - }! k2 j* `/ ~7 E @" t; u
- CE_High(); /* disable device */; c- b6 s" x6 u4 y! F
- }
# p/ h3 @0 U* P+ M- N
6 d9 N F6 e: I' j q7 ~: `, r- /************************************************************************/6 F' ? y: {- p/ A
- /* PROCEDURE: Byte_Program */
" `0 C$ @$ ?+ W3 j - /* */
$ G& @+ Y8 |4 m+ A5 Q- d+ t: [( n - /* This procedure programs one address of the device. */6 Y, b: B' ^. H6 [
- /* Assumption: Address being programmed is already erased and is NOT */6 c( I0 x# K7 r9 s7 ^3 x/ K0 a6 R
- /* block protected. */
: _; g5 ]" e: \ j( I4 l C# S/ A - /* */
6 l& P' F1 ~& c2 f0 K9 w' `) [ - /* */2 c5 z+ Z( n! m9 @
- /* */' n+ c* r& O X; k9 u: p
- /* Input: */5 I* x) y- C7 D
- /* Dst: Destination Address 000000H - 0FFFFFH */( ]6 R! A7 v& o2 o" e: M9 l
- /* byte: byte to be programmed */6 H; [* Q. J) d0 k% i
- /* */
: I* _3 E$ u6 Y - /* */
2 r; j w/ H/ P2 t3 ^" z2 l - /* Returns: */8 v6 I5 d0 t. d& S2 G
- /* Nothing */) v% B- p) S8 f; X% e
- /* */
/ C o5 \2 v- E% P+ L% F% C - /************************************************************************/
% |/ H# x6 x& V, Q' p( E - void Byte_Program(unsigned long Dst, unsigned char byte)
! @# O6 l% z1 t# [ - {
! N& ~; r9 {+ Q0 I - CE_Low(); /* enable device */
0 o7 Y1 i: G. `! G - Send_Byte(0x02); /* send Byte Program command */
1 ~+ a! ]; \" k' d. B: m - Send_Byte(((Dst & 0xFFFFFF) >> 16)); /* send 3 address bytes */: E/ H* P$ @7 y1 E, d( Y
- Send_Byte(((Dst & 0xFFFF) >> 8));
. l1 P+ v9 g: _ - Send_Byte(Dst & 0xFF);
" @7 x* T' z2 @2 j7 w6 O3 R5 x - Send_Byte(byte); /* send byte to be programmed */
" C& h+ t4 ^/ O1 C4 n- t - CE_High(); /* disable device */
% f5 j3 K, ~8 A - }" N: D# z: l6 z6 r
# H+ B5 q _; g' c/ [9 [- /************************************************************************/
1 T% i6 H g& ]# r4 Z - /* PROCEDURE: Auto_Add_IncA */+ E* i$ w5 H. F2 n1 d6 S* O1 a
- /* */
3 ~8 i) H: \+ [ - /* This procedure programs consecutive addresses of 2 bytes of data into*/% G6 Y% K B$ m( W3 b+ p
- /* the device: 1st data byte will be programmed into the initial */
( m3 {& B0 e8 Q - /* address [A23-A1] and with A0 = 0. The 2nd data byte will be be */$ h, c4 k" L5 n
- /* programmed into initial address [A23-A1] and with A0 = 1. This */2 F; D/ R: Q, E& B$ f
- /* is used to to start the AAI process. It should be followed by */
- W8 n3 G& |+ {* [- z - /* Auto_Add_IncB. */4 `% b9 f; C$ b' S" j6 j2 [
- /* Assumption: Address being programmed is already erased and is NOT */9 i7 Y/ P% k% F4 @) A) \: \
- /* block protected. */
9 a! q+ }( k4 E) q; q - /* */
! J' ^. I% O- p3 {$ Y: B - /* */
* M* o' K1 H. A% \ - /* Note: Only RDSR command can be executed once in AAI mode with SO */
4 b I* K0 s# q% Z" t, {, E8 P - /* disable to output RY/BY# status. Use WRDI to exit AAI mode */' Q6 H( |* `: R! Q
- /* unless AAI is programming the last address or last address of */
0 X# k- @! W5 u# u8 h - /* unprotected block, which automatically exits AAI mode. */
* U: p/ |; O" B& C( e8 K - /* */2 L. v! }: A9 O) r, M# F
- /* Input: */; i6 O7 m' G. f/ k5 B, |
- /* Dst: Destination Address 000000H - 0FFFFFH */4 B: B- [4 m1 G3 e, R" @
- /* byte1: 1st byte to be programmed */
' j9 C& h4 }) ^7 Y0 I a# K x - /* byte1: 2nd byte to be programmed */" i# C* B4 m0 s! f8 ?. @
- /* */
6 ]! o! c: z& c% G9 K) c - /* Returns: */2 F! @0 w m( f, R* {
- /* Nothing */
0 n( i Q& }4 L! h8 l' o$ D - /* */6 O% [$ T/ q1 f; Z4 X
- /************************************************************************/% c: G; q' O V: V
- void Auto_Add_IncA(unsigned long Dst, unsigned char byte1, unsigned char byte2)
6 X8 v1 I) R+ Q# D - {
" j% K& y% ~; T2 }2 ^3 Q - CE_Low(); /* enable device */
8 D2 R3 U1 }6 @" Y a - Send_Byte(0xAD); /* send AAI command */1 s2 b0 J5 p5 a0 Y- V' u5 b
- Send_Byte(((Dst & 0xFFFFFF) >> 16)); /* send 3 address bytes */2 e$ u( R) `3 S
- Send_Byte(((Dst & 0xFFFF) >> 8));
% C$ o8 Y% c% V! v& y. L5 G - Send_Byte(Dst & 0xFF);, j0 ~6 S: {8 |* Q# N; r
- Send_Byte(byte1); /* send 1st byte to be programmed */
+ `! g% ^- J' E9 l% t6 w - Send_Byte(byte2); /* send 2nd byte to be programmed */
2 ?: @: U; f. p; P7 m v! u, I - CE_High(); /* disable device */
/ ~& A) ?* T6 N- W - }
! |: g( B+ t" n
+ B" B3 P' L% a1 b5 s) K" d# i& z- /************************************************************************/
0 T2 l* }- G: H. q& E) s/ v$ c+ F - /* PROCEDURE: Auto_Add_IncB */
- i' E4 u/ A* S3 } - /* */
: f+ }8 N- j2 P( K - /* This procedure programs consecutive addresses of 2 bytes of data into*/. i8 V8 j X7 j
- /* the device: 1st data byte will be programmed into the initial */
( C& `. Z4 S6 Q/ U% S - /* address [A23-A1] and with A0 = 0. The 2nd data byte will be be */
. E# U& Z5 {2 h! u - /* programmed into initial address [A23-A1] and with A0 = 1. This */
0 a" Z* A1 N/ i- A/ c - /* is used after Auto_Address_IncA. */7 y( S! K7 E# u0 y
- /* Assumption: Address being programmed is already erased and is NOT */6 u$ E3 u6 E* p2 e6 v
- /* block protected. */. W. l5 t) M3 ?" N9 } O$ A
- /* */
5 O( m- u1 e5 B6 H - /* Note: Only WRDI and AAI command can be executed once in AAI mode */! O7 `& |5 F1 |8 ^
- /* with SO enabled as RY/BY# status. When the device is busy */1 V' V, i4 ^/ l [
- /* asserting CE# will output the status of RY/BY# on SO. Use WRDI */
9 \( g4 x& u1 X - /* to exit AAI mode unless AAI is programming the last address or */
( U) j; P2 `- W: I7 j - /* last address of unprotected block, which automatically exits */
& N8 ?- E5 u5 z3 _4 j - /* AAI mode. */
! Q" g2 L% C4 a: R" x3 B* U - /* */
9 r' N7 h/ I5 R6 R - /* Input: */3 j) B$ s1 |8 {
- /* */
0 j y4 ?6 @* k, l7 @# v6 x! E - /* byte1: 1st byte to be programmed */
7 j- _/ A" x$ A& c/ _( n6 d - /* byte2: 2nd byte to be programmed */2 t- K9 L+ q0 @+ c
- /* */5 p1 G. X) Q; E; i
- /* */
2 D5 P- n0 o3 H6 j: d( S+ f. A- L; H - /* Returns: */
1 b+ N A8 c8 I - /* Nothing */
) ~( g* f G, f L0 q% |7 ]* q - /* *// X4 F% H6 Z) t: g7 t, g. n( r
- /************************************************************************/4 W, w( e2 d$ f6 @5 v1 z2 w
- void Auto_Add_IncB(unsigned char byte1, unsigned char byte2)
$ ?% p2 F3 L' W, @& T1 m - {6 Y1 L! g9 P0 k
- CE_Low(); /* enable device */$ {! |6 ?2 y# n% i1 F1 p
- Send_Byte(0xAD); /* send AAI command */
8 `1 ]' H$ o3 J9 H0 p8 k( C - Send_Byte(byte1); /* send 1st byte to be programmed */
4 u# y) Q" \6 n2 D4 x - Send_Byte(byte2); /* send 2nd byte to be programmed */: I3 Y9 e1 z9 r
- CE_High(); /* disable device */
' }9 G: E1 {* j9 O' t! d# Z$ i. H - }
7 x' f( a; m2 E, L0 D2 o - ' d3 T4 y7 J) H8 g/ j
- /************************************************************************/
, d1 O" X ~9 r! b - /* PROCEDURE: Auto_Add_IncA_EBSY */
0 a0 ]' l$ N2 {3 x - /* */
7 e! }' c3 N4 P# _/ S - /* This procedure is the same as procedure Auto_Add_IncA except that it */
% f* s& l" ~6 z1 s- f - /* uses EBSY and Poll_SO functions to check for RY/BY. It programs */# i& V% u! \* i
- /* consecutive addresses of the device. The 1st data byte will be */: R5 X d% Z& N8 t. p0 x
- /* programmed into the initial address [A23-A1] and with A0 = 0. The */$ l l, e6 @$ e U6 S+ r& N: X) M
- /* 2nd data byte will be programmed into initial address [A23-A1] and */
R2 X$ q, u) O4 F* K7 t. V - /* with A0 = 1. This is used to to start the AAI process. It should */. N: t. S: [4 I- j3 |
- /* be followed by Auto_Add_IncB_EBSY. */
+ P3 @, V6 {9 M" P4 y - /* Assumption: Address being programmed is already erased and is NOT */
' J; s$ Z! o. y - /* block protected. */7 N4 f% Y: D: p0 S# N; ?
- /* */4 l) u( _3 A0 i& q
- /* */" s2 B( u8 |. M) @$ U- f0 s, N
- /* Note: Only WRDI and AAI command can be executed once in AAI mode */ Q% t! r/ x- O$ d8 Z
- /* with SO enabled as RY/BY# status. When the device is busy */
5 \+ \) B" }0 ^1 A: G& _ - /* asserting CE# will output the status of RY/BY# on SO. Use WRDI */
* ?) W7 u/ E% P/ m% J8 e- s - /* to exit AAI mode unless AAI is programming the last address or */# t: B" M( o' U0 q! |
- /* last address of unprotected block, which automatically exits */5 y8 i1 S. c# j1 d6 q
- /* AAI mode. */
( {+ w9 g2 i% x# F9 s5 o$ A - /* */; f9 A+ b1 n6 ` X# O
- /* Input: */' X( \: {& X/ F1 ~
- /* Dst: Destination Address 000000H - 0FFFFFH */* x3 E8 h# i5 U9 r. F- _* \
- /* byte1: 1st byte to be programmed */
# R0 U9 r& m4 C$ u6 C: O, \ - /* byte1: 2nd byte to be programmed */6 e$ }9 |+ L6 L, \2 Q4 [$ y
- /* */7 A; L7 T1 F( X# r$ q
- /* Returns: */
" C* |+ a% |0 x9 M4 a5 @ - /* Nothing */
- p1 I( v: ]& u1 G; X - /* *// `2 d: `6 V, f, B+ Z) T
- /************************************************************************/
" c9 @/ Z) L' I, _. A - void Auto_Add_IncA_EBSY(unsigned long Dst, unsigned char byte1, unsigned char byte2): }) p8 P% z5 N4 Z5 G, h# e- [
- {
. A+ u4 O1 x* y A# R5 e- O" f - EBSY(); /* enable RY/BY# status for SO in AAI */
# C l& F( p3 |+ E) D& y - + p5 l2 y# o% A, U
- CE_Low(); /* enable device */+ \, ~: u. T6 e
- Send_Byte(0xAD); /* send AAI command */+ x5 B1 W( V& w6 a3 y* H1 b
- Send_Byte(((Dst & 0xFFFFFF) >> 16)); /* send 3 address bytes */$ q! y* s, j% R$ S5 _/ t8 A
- Send_Byte(((Dst & 0xFFFF) >> 8));% b* ], }, I! `# q" B% S
- Send_Byte(Dst & 0xFF);% K* W I D/ X2 H; I' v2 b0 f# P
- Send_Byte(byte1); /* send 1st byte to be programmed */
: _; o1 c! y6 B# t. b) d% e& N0 P4 L - Send_Byte(byte2); /* send 2nd byte to be programmed */3 M7 ~ ]- w& B% F" n8 Z
- CE_High(); /* disable device */
+ Q7 | V m4 \/ p; p' c! n+ Y - & h& q; _, Q( A m: G( i% b. T+ \
- Poll_SO(); /* polls RY/BY# using SO line */* l# k' T, f1 i9 r- a/ Z, S
- ( L/ t" n; D- W# r
- }* Q( b& R' S, U) {* i$ o8 R
- I. P# }! A( v* s6 C- /************************************************************************/
. [6 p* C `* K6 | - /* PROCEDURE: Auto_Add_IncB_EBSY */2 H5 h% _; ?% [2 R( u8 @1 g& |4 S9 _
- /* */2 I" r2 w3 L$ d! ]
- /* This procedure is the same as Auto_Add_IncB except that it uses */
3 P6 o4 ]5 l7 c! b - /* Poll_SO to poll for RY/BY#. It demonstrate on how to use DBSY after */
+ a2 K" `+ P& `$ _ - /* AAI programmming is completed. It programs consecutive addresses of */
- j+ o! p" Z' n W3 Y9 z - /* the device. The 1st data byte will be programmed into the initial */5 Y: r! G! X. q- E! p1 ^
- /* address [A23-A1] and with A0 = 0. The 2nd data byte will be */
( r$ c+ z ?# s0 z - /* programmed into initial address [A23-A1] and with A0 = 1. This is */+ j' Y/ u( E) N% ^( J
- /* used after Auto_Address_IncA. */. ~% ^- G% \3 J0 }- v
- /* Assumption: Address being programmed is already erased and is NOT */( C& S# `, Q. S7 f0 j+ a
- /* block protected. */
4 c: C. S# ]1 s$ O! b7 F' c - /* */! a6 c: m B. f1 w% Q: ~
- /* Note: Only WRDI and AAI command can be executed once in AAI mode */
e; L: I q0 l0 \) c$ d- G' ` - /* with SO enabled as RY/BY# status. When the device is busy, */8 d4 j$ g3 U0 V& N. V
- /* asserting CE# will output the status of RY/BY# on SO. Use WRDI */
. `+ V* @ p8 j* {5 D U( ` - /* to exit AAI mode unless AAI is programming the last address or */
6 \: n& t! I. A; a) a3 n - /* last address of unprotected block, which automatically exits */; P2 t4 C: }) b+ j( P
- /* AAI mode. */( B0 z/ L2 y1 H7 r4 h9 ~
- /* */
! C8 F" G* P. ^$ i; {2 D - /* Input: */
V8 d5 p# H" o. V - /* */
N1 n) ?7 @6 Q' Z, `9 o - /* byte1: 1st byte to be programmed */
! [. J; S1 l6 S$ M q& n* P6 i+ d2 K. _, { - /* byte2: 2nd byte to be programmed */
' K) @& n1 O' b8 R - /* */7 G4 e+ m8 s" R2 V, z. R
- /* */- \$ r. X7 \* ]
- /* Returns: */: s5 x+ \* `# g9 |' e( y
- /* Nothing */
) {: Y* X- \% @2 q - /* */
) p( [6 V# [7 ?/ v: W( @" H7 @ - /************************************************************************/# H+ z- t d8 Y. M/ t* `( p
- void Auto_Add_IncB_EBSY(unsigned char byte1, unsigned char byte2)
( R: d. [8 [% o, G3 z1 a8 |7 W - {
8 m* V8 v5 T, H, y2 j - CE_Low(); /* enable device */
. U, ] f2 x8 ~9 Y4 b$ U1 A5 L - Send_Byte(0xAD); /* send AAI command */
6 I) d: p3 a! O7 ^6 j$ R5 B+ a7 ]: ]0 [ - Send_Byte(byte1); /* send 1st byte to be programmed */
- A0 b0 Q) j9 k/ P - Send_Byte(byte2); /* send 2nd byte to be programmed */
# N( i! {; H3 ^7 a: ], D5 x/ ` - CE_High(); /* disable device */
! u1 R* e t1 g& q
, \6 q, t& O1 U7 s* F- Poll_SO(); /* polls RY/BY# using SO line */* v4 w6 q0 m8 u
# a8 v7 h+ W' a, @, z! V" B# }% F- WRDI(); /* Exit AAI before executing DBSY */+ i3 B, x& ]# V
- DBSY(); /* disable SO as RY/BY# output if in AAI */
, T3 C& G( Z+ O: l4 z8 d - }
1 h. N9 c b4 o u8 T; t+ { - 4 K- w F4 x) S0 N% I
- /************************************************************************/+ s1 L& y* ?. y( s; `
- /* PROCEDURE: Chip_Erase */3 _0 D) Q8 q. M( L! b5 ?' w. F
- /* */
0 I' D! K8 u+ K; d& E - /* This procedure erases the entire Chip. */! g) \8 e/ L6 Y$ l6 X. Q4 S! }
- /* */% K) }7 g+ y5 J5 d( ~, g8 L8 T
- /* Input: */1 r ]5 [% D, D9 {, c5 |
- /* None */
: B7 Q/ l/ b M - /* */
. D$ b$ R. k3 [, O) n! P3 a - /* Returns: */% r. _! |7 J- Z7 q# @) s
- /* Nothing */
" v( p# P3 n! H. P% h* Z3 v1 _ - /************************************************************************/
) G$ d. X/ K0 ^% x$ n+ h5 Y! A - void Chip_Erase()
+ E. b7 F' R/ g% A, Y* T4 s: q - {
7 R% v1 o6 h a) |$ U - CE_Low(); /* enable device */
% n2 p t: A! b- h8 x - Send_Byte(0x60); /* send Chip Erase command (60h or C7h) */
# ?2 q7 ~+ K: L" A7 T - CE_High(); /* disable device */& P/ X3 |* V0 M. e( L P c
- }
- `2 V- p5 s; P* T- t5 S7 J2 d$ S
; V i' h- U9 [- /************************************************************************/4 j" o5 T, X* D: ]' K5 G
- /* PROCEDURE: Sector_Erase */
5 z% I8 L4 x0 [- ~. J3 E9 B - /* */3 N$ m, @) E2 _( [9 _- R" C# w
- /* This procedure Sector Erases the Chip. */
* ~: r% V& D4 z! O2 q - /* */5 G* _7 B$ x+ i9 M
- /* Input: */
" G- U/ S6 |1 E% R9 G8 ?$ ~1 p - /* Dst: Destination Address 000000H - 0FFFFFH */+ o# I7 ] ^; W, S# Q) H- X( q( L
- /* */$ T: l" n+ f4 U% Y3 |- D
- /* Returns: */2 s* x7 w( W0 {4 S8 F3 }- ^' @
- /* Nothing */
. \8 [' B- b7 h* _! U; a* } - /************************************************************************/2 W- ?/ [: [, F: Y- A, W5 C
- void Sector_Erase(unsigned long Dst)# g% N& u' j7 ?. Y
- {" R) t3 `1 P! K# h7 S
- / p7 T: W" x) Z- j
- w) F* Q) A( G4 F: u6 c, f! q
- CE_Low(); /* enable device */* J) q2 D; h9 P2 {& v/ N0 }
- Send_Byte(0x20); /* send Sector Erase command */% B! K# |6 _0 R7 v
- Send_Byte(((Dst & 0xFFFFFF) >> 16)); /* send 3 address bytes */! M- ]7 C/ E6 r/ @. u3 T
- Send_Byte(((Dst & 0xFFFF) >> 8));% _" [* \) X: l" t
- Send_Byte(Dst & 0xFF);7 Z( A0 e/ x3 t2 B2 p6 Q
- CE_High(); /* disable device */* N6 v" t+ d( A
- } 0 N2 s# a0 i5 I+ C, j
1 |' C9 C+ A+ u% r7 C- /************************************************************************/8 [7 L/ m* Q) l+ C ]$ {/ Y
- /* PROCEDURE: Block_Erase_32K */
# }1 [: X+ P& t) m" R: z: n( F - /* */
+ e7 x0 i6 {2 [( W) a - /* This procedure Block Erases 32 KByte of the Chip. */: G. |0 P7 F: C1 P; A6 A+ ]1 K
- /* */% @; j p+ _ s. s3 v' w2 V
- /* Input: */8 S& S- i0 c- ?0 t
- /* Dst: Destination Address 000000H - 0FFFFFH */
7 w+ R: C. K# M) u$ o( \ P - /* */) E5 h0 P9 P9 D% x* P
- /* Returns: */2 @! a( x) b/ ?2 `% h
- /* Nothing */. _2 X# i+ Z! P8 u9 p W
- /************************************************************************/
) [1 l g7 O0 V* `: e$ _! M - void Block_Erase_32K(unsigned long Dst)' Y6 t- f+ O1 h$ b9 W6 p# ~# D& |; |
- {8 ^4 s5 [" \* L' x* ~
- CE_Low(); /* enable device */" Q0 {; Z+ ]( r9 R7 y8 z5 a
- Send_Byte(0x52); /* send 32 KByte Block Erase command */+ T- K) ~: \+ Q: O7 x* m/ R
- Send_Byte(((Dst & 0xFFFFFF) >> 16)); /* send 3 address bytes */4 G* X1 q2 j5 z1 F
- Send_Byte(((Dst & 0xFFFF) >> 8));. f9 o0 X, F! q& `
- Send_Byte(Dst & 0xFF);
: y2 d+ I! k4 m1 E! x/ n - CE_High(); /* disable device */- `6 N, Z- {' V. P$ _: O- w1 d
- }
/ p) V1 L5 g" ~! q2 q - $ b+ |, s: A. h: C4 w* c) i
- /************************************************************************/2 s9 d/ ~9 i& Q( a+ W
- /* PROCEDURE: Block_Erase_64K */, k" V$ F1 B- {& Z
- /* */8 X5 i- x3 O8 K
- /* This procedure Block Erases 64 KByte of the Chip. */3 ^# L5 Q6 O! W- O& N" d
- /* */
) ?* b' F9 T- o* I( P - /* Input: */* `% Q' I! o; a; |' F
- /* Dst: Destination Address 000000H - 0FFFFFH */
! ^. n3 L- m- ]5 G# v) I - /* */
1 q' E- S/ y4 S! e, Q p+ b - /* Returns: */# |; S$ F* Q8 _" @# `5 _
- /* Nothing */( T; j1 C& y7 C
- /************************************************************************/: i7 A8 h3 R6 n# X$ t5 C
- void Block_Erase_64K(unsigned long Dst)
6 u8 x2 S4 q9 a - {) q$ z# |- j* Q6 u6 E7 x
- CE_Low(); /* enable device */, T; f/ Q, {+ {+ d
- Send_Byte(0xD8); /* send 64KByte Block Erase command */9 t! `8 c9 S. g8 l; K5 _& p
- Send_Byte(((Dst & 0xFFFFFF) >> 16)); /* send 3 address bytes */
3 j) b. `/ m* n/ ~# a/ e3 ~: u$ B - Send_Byte(((Dst & 0xFFFF) >> 8));' d* _ b5 I8 v- P6 E: y
- Send_Byte(Dst & 0xFF);
: p6 U( X3 o# q' X1 p& H/ U B - CE_High(); /* disable device */$ c+ z+ V1 w6 L0 O" U# D- b
- }
& L F) z4 i/ T" s2 i9 b - , N4 e* U+ r6 R, t3 t3 y! ]: i, S
- /************************************************************************/0 p8 L/ I+ m/ \8 J- A( ~; U9 l% O$ T
- /* PROCEDURE: Wait_Busy */
! X- U0 q% d- H - /* */
! h; \" M7 Q4 ?( L2 w - /* This procedure waits until device is no longer busy (can be used by */
W$ O% y3 E( V* k1 l- ]$ L1 k; A - /* Byte-Program, Sector-Erase, Block-Erase, Chip-Erase). */
5 w! F7 T2 f1 ^ - /* */
1 k+ N# Q. W7 C5 k6 x/ M, Z - /* Input: */
i5 q$ |. F _5 C/ ]& Y, Y - /* None */
, C7 e" @* k4 T$ E% D; d - /* */
& P1 I- d2 R# f - /* Returns: */7 b/ e9 K& ~& e7 `2 K) I
- /* Nothing */1 c3 Z/ I" y5 O7 T2 C
- /************************************************************************/9 g; y# g: w) H; o# ~, n% O
- void Wait_Busy()* ~6 A% j6 [* w0 u7 v& V+ B
- {- L! {* X+ Z" ]% H& i
- while (Read_Status_Register() == 0x03) /* waste time until not busy */" t2 f% B" t( b$ R
- Read_Status_Register();. a8 ]) L6 w P. x1 V
- }
, D1 R2 }4 }2 w7 E; I - 6 I; i& O# c0 {: g, S1 ^
- /************************************************************************/& L) c2 m1 u% m4 m* _9 {* N
- /* PROCEDURE: Wait_Busy_AAI */8 [; [" Q8 d+ n( ?' x' L+ ^/ `
- /* */
: m) i$ E; l! {: L/ V) ~! [" Q - /* This procedure waits until device is no longer busy for AAI mode. */ t; b, Y. @. r8 z3 [1 }
- /* */
B2 H6 Y" G. u - /* Input: */
6 l1 Y% j5 C7 X, N' U. \( ` - /* None */6 T* M2 ]8 [2 {/ Y C4 r9 N f
- /* */
4 {0 E0 z8 G0 _2 m+ w/ e - /* Returns: */
/ z3 x# Y# P: x$ D, T! l - /* Nothing */" r+ z1 W' t4 D% h5 Y: Y
- /************************************************************************/
4 V) f/ w `7 c/ b7 G - void Wait_Busy_AAI()* i, A1 E, a |# I# P' Y: D* A5 u* W
- {
A8 p' W( s+ A I% e - while (Read_Status_Register() == 0x43) /* waste time until not busy */
+ o9 R: |9 X7 `# @$ a - Read_Status_Register();$ P& e" f/ L) U7 z5 {6 Y. B& L- z
- }9 O% o5 l# g. K1 X8 J8 ~3 U! F. \
- + s% X0 S9 o% _$ ?, g9 J# E0 ?
- /************************************************************************/' q2 S' i( ?& }3 a
- /* PROCEDURE: WREN_Check */
/ o8 u- b; @! y) M8 E8 u- M - /* */
' v2 L, p$ M t3 m - /* This procedure checks to see if WEL bit set before program/erase. */# V8 S+ C7 M6 ]# z- x& y% o: l: F
- /* */
& Q) g7 Z( Z7 F0 j1 P - /* Input: */2 o0 Z6 ?8 u- n/ o; d/ n! {
- /* None */
. h/ f) W: Q7 q) w2 z1 N: Z - /* */2 s* X( n& \% n& j
- /* Returns: */" Q q- N% |2 b; }3 h
- /* Nothing */
/ G6 k5 S) `- `: x& Q - /************************************************************************/, v8 {4 \9 V7 |5 R5 z
- void WREN_Check() r# L$ e6 W# m8 Y h- V0 M/ @$ p8 A+ p
- {( [# A( T; w2 g9 l
- unsigned char byte;" P8 `0 f- |. @9 Y
- byte = Read_Status_Register(); /* read the status register */( S! ?: W; f7 k$ E4 c
- if (byte != 0x02) /* verify that WEL bit is set */( O" H3 H( D1 Q6 U2 ~
- {5 }- C) A6 q- c" z% \: x
- while(1)6 ?: |2 R# m0 ^" J
- /* add source code or statements for this file *// ?; v _1 \- A3 z# A
- /* to compile */
0 f- r b1 g* ]6 \) D - /* i.e. option: insert a display to view error on LED? */
# s9 R& C* s2 H" Z; b" z% l p - - x& m8 p, V$ F: h
- }2 n9 R) v; h7 F# m& V7 B$ n
- }+ M% U9 i1 c; s
- % r/ j8 {* y5 W5 Z6 Z3 H& O9 ^0 ?! d
- /************************************************************************/3 p4 C+ M7 c" w
- /* PROCEDURE: WREN_AAI_Check */
: e1 ]/ m1 X0 F5 d" A; O - /* */1 u- {& }8 X H$ W2 \1 b
- /* This procedure checks for AAI and WEL bit once in AAI mode. */
O* g% W' r! k, k- X3 t& \% e; x D - /* */
( r9 y. S& a0 S: e) m' j1 v - /* Input: */
0 G9 k. }' v" z0 G - /* None */2 t- A" a8 m: d+ c
- /* */
- B P6 e4 ]4 h" O& o& L. ` - /* Returns: */
1 g$ h1 ]$ r# b" i8 i - /* Nothing */9 }6 l9 w! ?3 Z9 j8 Q6 C! W3 P3 @
- /************************************************************************/3 w, V: \7 M3 H
- void WREN_AAI_Check()
6 q2 x* \, l- c% F g" X - {
3 ?9 r r5 N" U) S) z$ u9 N - unsigned char byte;
0 ^; ^3 x/ S0 @- W6 i! u/ }- R0 f - byte = Read_Status_Register(); /* read the status register */! p! d+ O+ C( h2 M6 V- t
- if (byte != 0x42) /* verify that AAI and WEL bit is set */
5 y Y/ T5 a. y4 b* t' h - {- b, N. M% [1 P+ v
- while(1) 8 y2 ?6 B) H. W9 K2 U
- /* add source code or statements for this file */
5 Q+ t1 }$ }+ @: y9 m X - /* to compile */
1 n2 w+ ~$ j! T - /* i.e. option: insert a display to view error on LED? */7 s' x" x4 p- x. }% g
- & k/ f5 \: P+ P) {/ |
- }" N1 a3 @: Q e) X( O8 {! _
- }6 {1 K4 B4 ~/ t5 G" f; t u
5 f, q- E4 H' g% D8 m* W- /************************************************************************/
. t; D9 s; P5 K - /* PROCEDURE: Verify */+ b! M9 m# M5 o5 Q4 t3 a% A
- /* */
' j! P. Y1 G$ ]8 X0 _& K9 x% Z% t - /* This procedure checks to see if the correct byte has be read. */
[, O8 v$ S j6 D4 e0 f; C9 l9 e - /* */' G3 S( ?. Y) m) m
- /* Input: */
0 K) Z7 W' k2 g1 ~! d$ q7 h: {7 J - /* byte: byte read */% ~9 c0 W2 N$ c9 H$ I
- /* cor_byte: correct_byte that should be read */
( J' o" t3 F- }& ]* Y - /* */" h( n* e1 B6 C% L) A
- /* Returns: */) _/ f! A& ]: X: t/ N
- /* Nothing */" _+ ~$ L5 V# `* q2 ~$ K
- /************************************************************************/
% C/ L* |; h1 {8 K' R - void Verify(unsigned char byte, unsigned char cor_byte)
9 o7 |1 ]8 I; B7 z9 b - {
. E. q2 t+ P3 x. n* a - if (byte != cor_byte)( d( S# r4 o! V
- {
3 U+ D& C4 o0 J3 X% c - while(1)
8 n4 V3 `* E: _' W. S( O - /* add source code or statement for this file */
, D) ^ M# y8 N+ t, S9 j - /* to compile */! S7 B+ o) K3 t8 t: G1 E* F; {! s( w
- /* i.e. option: insert a display to view error on LED? */, C# v! O1 O1 c( \+ V+ d
-
9 a/ J: J% J- p+ o6 z% j - }
5 y* L L$ l! e4 o - }
! W @& J( I/ w6 ~8 t1 F+ E3 d7 m
. h1 t" [5 [' a* b
8 i) ~" U: b5 c1 w* a7 K# I8 x- int main()
5 H' c: ]/ `8 Z; l, S - {( ^/ M: _4 a# P f% ^$ D T9 C- N
- + H+ R7 a2 q# K$ j- `9 s$ @/ X4 k
- return 0;$ y8 V7 f4 x6 {' D: u# p. \5 ]
- }
复制代码 |
|