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