主要内容:
# M4 J( f" [' p8 k- }1) IS62WV51216简介;" P/ `: @/ J9 X9 L" y o* F1 x
2) FSMC简介及相关寄存器介绍;
6 V) g Z- n" N$ h! S, p' q3) 相关实验代码解读。6 o5 L9 ?" v! W4 [# M% f$ e
硬件连接:1 l9 `; g: n5 X
IS62WV51216原理图如下所示,具体连接关系为:, B) A, }/ h- R( l2 q3 p* M
A[0:18]接FMSC_A[0:18];D[0:15]接FSMC_D[0:15];UB接FSMC_NBL1;LB接FSMC_NBL0;OE接FSMC_OE;WE接FSMC_WE;CS接FSMC_NE3。# J) o9 y/ H0 N/ m r- \6 n
9 n$ Z! h& P9 `: u
2 [3 M, @7 U% J2 Q- D) x- M8 s7 {- Z) h; \' e. L
实验功能:程序开启后,按下KEY0键,测试外部SRAM容量大小并发送至串口端;按下KEY1键,显示预存在外部SRAM的数据。DS0指示程序运行状态。
# r$ u) L$ D1 |' E( |4 E
7 Y: y! @: e" X$ G8 |0 Y1. IS62WV51216简介 x4 C2 C* s0 a: I& T1 d
1.1 IS62WV51216是ISSI(Integrated Silicon Solution, Inc)公司生产的一颗16位宽512K(512*16,即1M字节)容量的CMOS静态内存(SRAM)芯片。6 Y9 T1 B" c* V; Z& k& f
3 r- M4 H/ `* m: Q3 e0 C( D0 L
1.2 特点) ~8 x2 v* g8 q, O- b
1) 高速。具有45ns/55ns访问速度(开发版采用55ns型号);( M7 `/ t% C1 n
2) 低功耗。操作时:36mW;待机时:12uW;+ i7 G) I# f( `4 W) D& H) d
3) 兼容TTL电平,兼容5V电压;* J: V Y; C* }. t9 m6 v; e+ L
4) 全静态操作,不需要刷新和时钟电路;
2 o, _( V1 m2 H8 F0 E& F+ u4 G. j, Y5) 三态输出;
, d) E7 H, Z9 K0 Z/ T' Q- t6) 字节控制功能。支持高/低字节控制。
: S4 Z2 w9 b# S9 U
- a. G" S" y4 W# z1.3 框图2 D) N1 K' y; H% S$ F
图中A0~18为地址线,总共19根地址线(即2^19=512K,1K=1024);1 h" a: l0 n# o7 `
I/O0~15为数据线,总共16根数据线;% `+ }$ Z. T* I
CS2和CS1都是片选信号,CS2是高电平有效,CS1是低电平有效(开发板采用CS1);; @1 N S5 t, _) h* h* T
OE是输出使能信号(读信号);
" j1 A G/ ^- j: CWE为写使能信号;$ v/ h1 I t8 }$ f
UB和LB分别是高字节控制和低字节控制信号(设0有效,设1无效)。
# l) [1 U$ Z0 M4 N9 \# o
* i. P1 i: z- ^ c I. E
# p/ v) ]. _ P4 C- {
* r& r$ D' }1 h) Z9 {
1.4 IS62WV51216读时序7 z' p T- a* a) W
IS62WV51216芯片的8080并口读时序如下图所示:+ [, C: E1 l* b5 M2 ^
重点时序:读周期时间(tRC);地址建立时间(tAA);OE建立时间(tDOE)。' K! U( |" B! @& P1 i
开发板使用55ns的IS62WV51216,tRC=55ns,tAA=55ns(Max),tDOE=25ns(Max)。) u6 `6 E+ G" k: {
' u8 U. M: B- N- }, d1 Z! m
' ^! \; \6 R" o% t2 t
2 s: F. `+ @+ m* ^1 s
1.5 IS62WV51216写时序
g, i/ V0 S* E% b: xIS62WV51216芯片的8080并口写时序如下图所示:
! t* o4 Q% H$ M: B; _重点时序:写周期时间(tWC),地址建立时间(tSA),WE脉宽(tPWE)。6 s/ n6 S: a8 }& [
开发板使用55ns的IS62WV51216,tWC=55ns,tSA=0ns,tPWE=45ns(min)。
5 T/ C6 n8 M3 o" m. E0 F$ r8 [7 L$ O4 {& {. j
3 L% o* v5 J" l2 S0 m% \8 _1 f
7 B, u/ G, B' R; w2. FSMC简介
) {- `8 l; e2 m: L2 UFSMC,即灵活的静态存储控制器,能够与同步或异步存储器和16位PC存储器卡连接,STM32的FSMC接口支持包括SRAM、NAND FLASH、NOR FLASH和PSRAM等存储器(不支持SDRAM)。FSMC的框图如下图所示:6 G) ]. l+ O- o1 O/ z
: H; |0 [5 o+ h# a# Z. m6 C& }
1 D# Y) `8 j1 J& Z3 f, q( ^ | B3 u9 ~
2.1 FSMC驱动IS62WV51216原理
* R3 d, \- z: HFSMC驱动外部SRAM时,外部SRAM的控制一般有:
5 k5 p1 G0 O% X: N$ s T% R* G$ l1) 地址线(如A0~A25);8 ^% i6 _( F# N1 ~
2) 数据线(如D0~D15);
f0 j9 E: R4 y2 q* A* e3) 写信号(WE,即WR);
; o v) K6 q4 |/ T, I4) 读信号(OE,即RD);2 U+ A f z2 L0 t; ^9 {
5) 片选信号(CS);
0 \" q$ J4 Q0 F) Q" j6) 如果SRAM支持字节控制,还有UB/LB信号。" `+ D) ?% a8 T) s: c
IS62WV51216的信号包括:! l9 E' S _+ {- c% |$ G- n
1) 地址线A0~A18;
* Z3 m/ o- x7 y2 {- R2) 数据线I/O0~I/O15;
$ l2 q9 |- X8 ~6 y+ x' n3) 写信号WE;/ }# J7 U6 ~( u
4) 读信号OE;- L: n( T& m3 z( r. n& q' G
5) 片选信号CS;
+ z, ^$ }3 U/ j X6) 字节控制UB、LB等。
6 P1 w' b7 P# ]8 X& R$ a& R将这些信号依次连接STM32 FSMC接口的A0-A18、D0-D15、WE、OE、CS、UB、LB等信号即可。
4 ~5 x! u! F6 t$ h$ B% k& x) b
4 ^1 F3 C p6 a2.2 NOR / PSRAM外设接口# R5 g) U, y! ] h8 @
STM32的FSMC支持8/16位数据宽度,我们这里用到的SRAM是16位宽度的,所以在设置的时候,选择16位宽就OK了。FSMC的外部设备地址映像,STM32的FSMC将外部存储器划分为固定大小为256M字节的四个存储块(注意每个块的起始地址!)。 |) _' A* N" g7 ?% P/ n2 z; R" R0 [
6 i) ^7 s6 T% }) B/ E
/ O1 j5 k( l; L# y+ w9 k3 t% |: p: T
) x' S* S& p1 f/ E7 ]+ v2.3 NOR / PSRAM存储块1 操作简介& v! H* R G8 n* ~1 V4 h
STM32的FSMC存储块1(Bank1)用于驱动NOR FLASH/SRAM/PSRAM,被分为4个区,每个区管理64M字节空间,每个区都有独立的寄存器对所连接的存储器进行配置。Bank1的256M字节空间由28根地址线(HADDR[27:0])寻址。
, T! ^7 q( Y# C6 ]这里HADDR,是内部AHB地址总线,其中,HADDR[25:0]来自外部存储器地址FSMC_A[25:0],而HADDR[26:27]对4个区进行寻址(不能直接设置,只能选择片选间接设置)。如下表所示:
! r" d3 A) b% l( e9 h# z. B% i7 {$ o5 a% x( w% E
8 O% W/ \1 E6 l9 I" I* h& x0 |- F% [
注意!
# E0 X1 y9 X- c% d2 r7 F6 d9 a当Bank1接的是16位宽度存储器的时候:HADDR[25:1]——FSMC_A[24:0](右移一位对齐),
0 ^/ P) d2 A7 @; R: L7 Z当Bank1接的是8位宽度存储器的时候:HADDR[25:0]——FSMC_A[25:0],
# i( |& }) [9 z# U# }不论外部接8位/16位宽设备,FSMC_A[0]永远接在外部设备地址A[0]。
6 h; J; g( s+ T# U# y+ }: [# Q* r) b* H9 Z( E
2.4 NOR PSRAM存储块1 访问模式
1 k, ^2 H7 M3 E8 ~- z2 }9 c& DSTM32的FSMC存储块1 支持的异步突发访问模式包括:模式1、模式A~D等多种时序模型,驱动SRAM时一般使用模式1或者模式 A,这里使用模式A来驱动SRAM,其他模式说明详见:STM32中文参考手册-FSMC章节。
3 a* R0 q, K v+ k* Y# H% k
6 \" j! p2 o( ~. A2 w
" o" Z/ z; F6 K+ C# \8 i; U! Q- s6 Q- B- S
模式A支持读写时序分开设置!(可针对一些读写时序不一样的设备分开设置),
# r; K$ ?& T1 m; q对STM32F4仅写时序DATAST需要+1(F1按上图要求即可)。8 i) C, o" z' g& B6 ~0 e
" T }8 [ z2 i2.5 FSMC寄存器介绍
: P( q6 i* H: E$ K4 j0 Y对于NOR FLASH/PSRAM控制器(存储块1),通过FSMC_BCRx、FSMC_BTRx和FSMC_BWTRx(仅读写时序不一致时才设置)寄存器设置(其中x=1~4,对应4个区)。通过这3个寄存器,可以设置FSMC访问外部存储器的时序参数,拓宽了可选用的外部存储器的速度范围。; i3 y# @/ A& B O' A8 Z
2.5.1 SRAM/NOR闪存片选控制寄存器(FSMC_BCRx)) ]) q& z" `& L8 N( D9 P
9 q" p4 N* h+ T: C% l' s
0 [7 }, B: Y$ T* ]9 ]- F, f0 @0 I. | n9 U# ^0 ^! s! V
EXTMOD:扩展模式使能位,控制是否允许读写不同的时序,设置为0(读写相同时序);7 x+ i: V1 h5 `; v* {% \
WREN:写使能位。我们需要向SRAM写数据,故该位必须设置为1;
1 ]9 G0 P* ~4 L" I# ^1 UMWID[1:0]:存储器数据总线宽度。00,表示8位数据模式,01表示16位数据模式,10和11保留。我们的SRAM是16位数据线,所以设置WMID[1:0]=01;
) r1 Z) k. o Y! Y* UMTYP[1:0]:存储器类型。00表示SRAM、ROM,01表示PSRAM,10表示NOR FLASH,11保留。我们驱动的芯片为SRAM,所以需要设置MTYP[1:0]=00;! J) A+ L; |) y. E+ T
MBKEN:存储块使能位。需设置为1,使能相应的存储块。, M( e$ z3 K7 p( S* W4 a; T) O
6 q& U4 m# v. [( }- m! D6 a
2.5.2 SRAM/NOR闪存片选时序寄存器(FSMC_BTRx)
% l/ `$ `1 P! A. i2 X8 z( P
6 e% \5 S* A- S0 ^% K
' R0 F3 A' `# }& x7 O) L5 N, O9 r, k& G2 B$ b& ]
ACCMOD[1:0]:访问模式。00:模式A,01:模式B,10:模式C,11:模式D。& I' j' x6 C8 _5 I5 n3 Y
DATAST[7:0]:数据保持时间,等于: DATAST(+1)个HCLK时钟周期(F4只有写的时候要+1),DATAST最大为255。对IS62WV51216来说,其实就是OE/WE低电平持续时间,最大为55ns。对STM32F1,一个HCLK=13.8ns (1/72M),设置为3(13.8×(3+1)≈55.2ns)。对STM32F4,一个HCLK=6ns(1/168M),设置为8(有点超频)。; g; e+ Y! f' i
ADDSET[3:0]:地址建立时间。表示:ADDSET (+1)个HCLK周期(F1不需要+1),ADDSET最大为15。对IS62WV51216来说,访问周期最快为55ns,之前的设置,已经可以保证访问周期不小于55ns,因此这个地址建立时间,直接设置为0即可。1 s7 e$ b; x$ V' O6 S5 J8 N. k
本实验因为EXTMOD位设置为0,所以读写时序共用这个时序寄存器!
! R; F' y, z( |( a" r& l% x
3 S/ w7 M6 B6 b2.5.3 SRAM/NOR闪存写时序寄存器(FSMC_BWTRx)
8 j E0 G2 Z) I若EXTMOD位设置为1,读写时序分开,则用该寄存器设置写时序。
) l& V' e8 Q; l
, ^$ r5 T, j4 H' V! k p$ K
! b( T' o* P5 ~0 e& ]$ e) q3 S4 o
- c" w3 O; i5 @ACCMOD[1:0]:访问模式。00:模式A;01:模式B;10:模式C;11:模式D。$ n% I" P/ W% l8 r
DATAST[7:0]:数据保持时间,等于:
% }$ V6 I! O5 iDATAST(+1)个HCLK时钟周期,DATAST最大为255。
|: H) `# X9 b- d; V8 X. QADDSET[3:0]:地址建立时间。表示:ADDSET+1个HCLK周期,ADDSET最大为15。! H: N1 f: `% K6 i$ m9 j$ Y
本实验因为EXTMOD位设置为0,所以用不到该寄存器!9 G9 I* V: Y/ `/ c
0 C9 A7 }" H7 b' z- Q6 G5 i0 i2.5.4 SRAM/NOR闪存片选寄存器组合说明8 H4 ?2 q' b9 A2 q# v) J
在ST官方库提供的的寄存器定义里面,并没有定义FSMC_BCRx、FSMC_BTRx、FSMC_BWTRx等这些单独的寄存器,而是将他们进行了一些组合。规律如下:0 l5 p& G- n" [4 [- N" I. u# l
1)FSMC_BCRx和FSMC_BTRx,组合成BTCR[8]寄存器组,对应关系如下:; v4 t+ `) z' C5 M2 Y
BTCR[0]对应FSMC_BCR1,BTCR[1]对应FSMC_BTR1;4 R5 B0 B( `5 f1 v( l7 n- r
BTCR[2]对应FSMC_BCR2,BTCR[3]对应FSMC_BTR2;
L/ a2 M- J" O( f) \) NBTCR[4]对应FSMC_BCR3,BTCR[5]对应FSMC_BTR3;
( t! y5 k7 s1 t. ] d) u7 J" ZBTCR[6]对应FSMC_BCR4,BTCR[7]对应FSMC_BTR4。4 N' t% |7 Y& U& a& l* {
2)FSMC_BWTRx则组合成BWTR[7],对应关系如下:" Y5 G; s+ K2 s) A/ }
BWTR[0]对应FSMC_BWTR1,BWTR[2]对应FSMC_BWTR2,
u+ J) Q7 s2 b* V$ U8 A9 jBWTR[4]对应FSMC_BWTR3,BWTR[6]对应FSMC_BWTR4,
1 d% ^* ?! M2 t) e* F$ MBWTR[1]、BWTR[3]和BWTR[5]保留,没有用到。
: O* G* ]$ J' i$ E% k. X4 [' M; [8 J) s' v: G5 R
3. 相关代码解读
% f. C; s, I" n# `9 u1 D6 Y3.1 sram.h头文件代码解读. Y: X' u6 ^! J3 L3 t& r t
9 ^; {' \1 S8 w2 Y0 m
- /**
7 c: S+ h8 [! {7 f% N- `0 p- @: b5 s. i - ******************************** STM32F10x *********************************
- h, p; R! ^; g9 k+ P - * @文件名称: sram.h3 h: W5 F) Y1 u, R% Q/ T
- * @作者名称: Aaron
" g$ h" J3 c7 o( Q) { - * @库版本号: V3.5.0# Y, `4 h ?& e# w* s* D& [4 R
- * @工程版本: V1.0.0
* {. E' u$ g. N x2 n4 X+ M - * @开发日期: 2020年10月7日
9 ?( l9 ~5 l* O/ w) M5 g2 o# B - * @摘要简述: SRAM头文件
7 G3 |, o* P/ ~2 c$ f - ******************************************************************************// p* `7 p! p( j/ ]
- /*----------------------------------------------------------------------------8 p y' n) s ]/ G
- * @更新日志:
+ o8 w7 P* A( c# t" j - * @无) H" U! K+ D% I. y. o
- * ---------------------------------------------------------------------------*/; l+ S6 E5 x8 t& ^4 I( l
- #ifndef __SRAM_H. W; L( ?5 r2 Y7 ?7 A4 f
- #define __SRAM_H 9 p5 t" P# |' O; u: D- ]8 E! @
- /* 包含的头文件 ---------------------------------------------------------------*/8 t% Q$ g6 ~, W3 G) l: F/ {
- #include "sys.h"$ d Y7 ?. R) h& C
- /* 函数申明 -------------------------------------------------------------------*/ 2 ?3 V' G) {$ L5 Q; g, K
- void FSMC_SRAM_Init(void);2 g5 o; t7 ]% p2 e
- void FSMC_SRAM_WriteBuffer(u8* pBuffer,u32 WriteAddr,u32 NumHalfwordToWrite);, b! _6 c9 \$ N7 j
- void FSMC_SRAM_ReadBuffer(u8* pBuffer,u32 ReadAddr,u32 NumHalfwordToRead);
3 X0 z2 D0 k0 l - #endif /* __SRAM_H */
0 w3 \7 B( d' _7 _4 l0 r2 {1 R - /****** Copyright (C)2020 Aaron. All Rights Reserved ****** END OF FILE *******/
复制代码 ) g& V6 n: l# W; g* N b" Z# L
3.2 sram.c文件代码解读$ J8 ^+ Q4 ~3 x: V3 I; i
2 J2 t$ O. w: q0 g- /**7 m! ~' E! [$ J' }/ D0 z7 F! M, v3 {
- ******************************** STM32F10x ********************************** ^, n6 S8 O/ e! A
- * @文件名称: sram.c, j6 S k/ L% B# b& D
- * @作者名称: Aaron
, _9 y# W4 U' F# m$ D - * @库版本号: V3.5.0
: e- p& D1 i; G4 j - * @工程版本: V1.0.0
3 G, ^) D6 }* p - * @开发日期: 2020年10月7日1 A K! j5 m# X8 }! N' ?- s* r5 a! S
- * @摘要简述: SRAM源文件,使用NOR/SRAM的 Bank1.sector3,地址位HADDR[27,26]=10,
7 D8 }0 f1 d; |9 G; X2 l' P' r% N- ]; @ - * 对IS62WV51216,地址线范围为A0~A18
( A9 X4 z0 h* t5 h - ******************************************************************************/
' g, A* t- g" q - /*----------------------------------------------------------------------------
# G: e, D9 q8 S - * @更新日志:
/ A; T& u$ L# A - * @无8 C9 K# z. q+ o$ A5 a: F( Y: n
- * ---------------------------------------------------------------------------*/1 I Q' Z4 K$ ?! _. l
- /* 包含的头文件 --------------------------------------------------------------*/5 [. D4 S! q& a/ N$ \4 I" O
- #include "sram.h" 5 Z! j& B* ~+ b5 x7 q3 j
- #include "usart.h"
- }9 F( i1 l, L# j - /* 定义常量 ------------------------------------------------------------------*/
; W# C! b' K. n# Y% ~# n% ` - #define Bank1_SRAM3_ADDR ((u32)(0x68000000)) ( W9 m* j# k4 D: u; e! @
- /************************************************
0 W7 _4 [, X. s2 ^ - 函数名称:FSMC_SRAM_Init()* d! x: n- [* n+ }/ U ?4 ]
- 函数功能:初始化外部SRAM9 V' i& p1 R& J k5 a/ K, p
- 入口参数:无8 N" `6 z, V4 q8 C/ L G
- 返回参数:无4 C/ h& Y! H0 b! T" D6 ~& T
- 开发作者:Aaron, q' M5 L% _$ S+ R% r f
- *************************************************/% H# x: T' ~4 f
- void FSMC_SRAM_Init(void)/ A7 {) ]& K* z6 \* u6 }
- {
. W! m8 @$ ^( r: g2 m - /* 定义结构体 */
* A' l, a7 O/ a4 W X - FSMC_NORSRAMInitTypeDef FSMC_NORSRAMInitStructure;7 O- F# b, K) r1 N7 w) r) \
- FSMC_NORSRAMTimingInitTypeDef readWriteTiming;" W' L! X4 B5 X" e5 ?
- GPIO_InitTypeDef GPIO_InitStructure;
& \4 e5 B9 Z" C3 _5 I1 M1 ] - /* 使能相关IO口 */
' N0 @; P. i7 _% I2 y9 i - RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOD|RCC_APB2Periph_GPIOE|RCC_APB2Periph_GPIOF|RCC_APB2Periph_GPIOG,ENABLE);
% w5 E6 k4 K; V+ a; U" N - RCC_AHBPeriphClockCmd(RCC_AHBPeriph_FSMC,ENABLE);
7 ~$ T& k! S, o! P5 N1 D0 T - GPIO_InitStructure.GPIO_Pin = 0xFF33; /* PD0-1,PD4-5,PD8-15 */
$ K# [' A2 x ]! c0 _/ t2 c - GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; /* 复用推挽输出 */% s+ z$ k' e% s5 F) o; t
- GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
3 P1 S* u8 v$ x3 ^ - GPIO_Init(GPIOD, &GPIO_InitStructure);' E& S7 w/ V) X* `2 _& k
- GPIO_InitStructure.GPIO_Pin = 0xFF83; /* PE0-1,PE7-15 */
( ^2 Q& k) e( y4 s' p- x - GPIO_Init(GPIOE, &GPIO_InitStructure);
! S" m: b1 O$ Q' o- Y: R - GPIO_InitStructure.GPIO_Pin = 0xF03F; /* PF0-5,PF12-15 */
: E1 J5 u2 P, Z3 m - GPIO_Init(GPIOF, &GPIO_InitStructure);
& B0 }1 K. J0 C% W, L- r( J& x - GPIO_InitStructure.GPIO_Pin = 0x043F; /* PG0-5,PG10 */4 Y; J/ Z! m7 c) s3 M
- GPIO_Init(GPIOG, &GPIO_InitStructure);
- k z/ T; |# S - /* 读写时序结构体初始化 */
* J2 J( Z2 T% U( T - readWriteTiming.FSMC_AddressSetupTime = 0x00; /* 地址建立时间(ADDSET)为1个HCLK 1/36M=27ns */
P$ _1 l% V' _ - readWriteTiming.FSMC_AddressHoldTime = 0x00; /* 地址保持时间(ADDHLD)模式A未用到 */% c. \- W& J& {# ^1 M+ o
- readWriteTiming.FSMC_DataSetupTime = 0x03; /* 数据保持时间(DATAST)为3个HCLK 4/72M≈55ns(对EM的SRAM芯片) */ ' c! ^+ \* O( H
- readWriteTiming.FSMC_BusTurnAroundDuration = 0x00;
\% o) L* c( |% U# J - readWriteTiming.FSMC_CLKDivision = 0x00;
' s" {/ U+ ]7 |( ~+ _ - readWriteTiming.FSMC_DataLatency = 0x00;9 `* ^+ J. |* m' H% ?* B. q
- readWriteTiming.FSMC_AccessMode = FSMC_AccessMode_A; /* 模式A */ 5 d/ Y& v# a1 M b, b( u2 Y1 p
- FSMC_NORSRAMInitStructure.FSMC_Bank = FSMC_Bank1_NORSRAM3; /* 使用NE3,对应BTCR[4],[5] */
! D: o9 T4 i9 z) E - FSMC_NORSRAMInitStructure.FSMC_DataAddressMux = FSMC_DataAddressMux_Disable; /* 地址复用未用 */
9 H: o# \) q4 r: |- M) G. g - FSMC_NORSRAMInitStructure.FSMC_MemoryType =FSMC_MemoryType_SRAM; /* 存储器类型SRAM */
3 e; z; T3 W- }' f- e) ^$ H' Z - FSMC_NORSRAMInitStructure.FSMC_MemoryDataWidth = FSMC_MemoryDataWidth_16b; /* 存储器数据宽度为16bit */
% F( {8 Y1 H) p, V) y% r" {% K5 e - FSMC_NORSRAMInitStructure.FSMC_BurstAccessMode =FSMC_BurstAccessMode_Disable; /* 禁止突发访问模式 */
& a n y. `) n, u# T+ ~ - FSMC_NORSRAMInitStructure.FSMC_WaitSignalPolarity = FSMC_WaitSignalPolarity_Low;5 ~/ b% \6 J0 d) j
- FSMC_NORSRAMInitStructure.FSMC_AsynchronousWait=FSMC_AsynchronousWait_Disable;
$ u* H3 b% ]4 d4 ]3 Z4 Y% g: G - FSMC_NORSRAMInitStructure.FSMC_WrapMode = FSMC_WrapMode_Disable; 1 R* c8 W- ~2 M, E
- FSMC_NORSRAMInitStructure.FSMC_WaitSignalActive = FSMC_WaitSignalActive_BeforeWaitState;
- C. X; h6 ^, n - FSMC_NORSRAMInitStructure.FSMC_WriteOperation = FSMC_WriteOperation_Enable; /* 存储器写使能 */
; F( W, w, L! `% ^! j" e - FSMC_NORSRAMInitStructure.FSMC_WaitSignal = FSMC_WaitSignal_Disable;
) R! @7 t6 o; X9 A - FSMC_NORSRAMInitStructure.FSMC_ExtendedMode = FSMC_ExtendedMode_Disable; /* 不使用扩展模式,读写使用相同的时序 */3 L0 c9 x$ y" }( S
- FSMC_NORSRAMInitStructure.FSMC_WriteBurst = FSMC_WriteBurst_Disable;
. `) o. G! r! ~/ G& ` - FSMC_NORSRAMInitStructure.FSMC_ReadWriteTimingStruct = &readWriteTiming; /* 读写同样时序 */
) y( G. K# N; S0 k. q9 f% K( ` - FSMC_NORSRAMInitStructure.FSMC_WriteTimingStruct = &readWriteTiming; /* 读写同样时序 */
* k, N$ z# S% M; E - FSMC_NORSRAMInit(&FSMC_NORSRAMInitStructure); /* 初始化FSMC配置 */$ W2 j' t6 F, g
- FSMC_NORSRAMCmd(FSMC_Bank1_NORSRAM3, ENABLE); /* 使能BANK3 */ 5 ? z$ v$ g/ \/ w% t
- }
% o5 b. b. P4 j! X - /**********************************************************************
2 g0 [% \5 q0 ^6 Z - 函数名称:FSMC_SRAM_WriteBuffer(u8* pBuffer,u32 WriteAddr,u32 n)8 s# _9 k; |$ Y
- 函数功能:在指定地址开始,连续写入n个字节
: x$ n3 k9 ~& v* E1 A/ q - 入口参数:pBuffer:字节指针,首地址;WriteAddr:要写入的地址;n:要写入的字节数
- c. x& G5 r. T8 A2 {( V' T - 返回参数:无1 G5 ?7 M+ S. x+ G& Y
- 开发作者:Aaron
: e0 n6 o: B Y6 f2 f0 V - ***********************************************************************/% g" r* s* W8 f, t
- void FSMC_SRAM_WriteBuffer(u8* pBuffer,u32 WriteAddr,u32 n)
* s T. J9 O- O8 I6 q$ J. k - {
5 v4 b6 K' O; h& _- F. Q - for(;n!=0;n--)
4 z1 J( O s- x G3 E M0 {. w3 N - { . Q- }( W7 q8 e$ U% q
- *(vu8*)(Bank1_SRAM3_ADDR+WriteAddr)=*pBuffer; /* Bank1_SRAM3_ADDR ((u32)(0x68000000)) */
$ E+ `5 [" _' f; h8 T9 W4 J2 s - WriteAddr++; ; S! p0 Q1 C) e# B
- pBuffer++;
7 C9 @! e* |! q5 a/ q$ o - } - P( k% x$ [" u& l3 L& I e
- }- T( l* [# s+ l1 Y' L
- /**********************************************************************
: O; c7 j6 T. P - 函数名称:FSMC_SRAM_ReadBuffer(u8* pBuffer,u32 ReadAddr,u32 n) F; \- [4 K' o5 h; z
- 函数功能:在指定地址开始,连续读出n个字节
( w2 s/ G: P5 ^3 L7 ?1 l4 H8 l$ f - 入口参数:pBuffer:字节指针,首地址;ReadAddr:要写入的地址;n:要读出的字节数
; |6 S9 A/ P7 h - 返回参数:无) M0 Q+ @8 m) ~! u# c& S. I" o
- 开发作者:Aaron
, {% {! g8 _; C - ***********************************************************************/
+ M. U. r D4 T9 |: U - void FSMC_SRAM_ReadBuffer(u8* pBuffer,u32 ReadAddr,u32 n)5 }4 W/ x) g* {/ }& F0 @9 }. z; Q
- {. U1 ?' A7 ^( K# g/ ]9 d
- for(;n!=0;n--) 9 L) U7 ]9 w* P0 ^+ g
- {
. i; n: F1 @4 O' c3 o& G0 c - *pBuffer++=*(vu8*)(Bank1_SRAM3_ADDR+ReadAddr);
" ^$ D# r7 {0 [: a9 a6 I - ReadAddr++; ) ^$ j( Q1 j5 S
- } ( J- m: Z* L+ y7 I! I& }% U7 u6 Y
- }
, w) F) Q+ T# v/ ~ - /****** Copyright (C)2020 Aaron. All Rights Reserved ****** END OF FILE *******/
复制代码
6 T, X) Y5 Y* Q3.3 main.c文件代码解读& q; o( h! [8 G. T# |
0 E; N9 _+ S" b9 I6 b0 M
- /**# \! [% [) Q$ f3 o, O! O# r
- ******************************** STM32F10x *********************************' `; Z& h8 ~4 h: s {
- * @文件名称: main.c5 X! t9 i8 o; a4 [& i; e+ w
- * @作者名称: Aaron6 G5 F, ?% s6 ]( c
- * @库版本号: V3.5.0
f3 z! A! f9 B - * @工程版本: V1.0.0
1 M5 L5 `: \( j% m6 v8 ]) I/ K - * @开发日期: 2020年10月7日
2 q3 M/ y9 t+ R! q& {& v& W) ~9 j - * @摘要简述: 主函数6 k4 i7 ~% ]4 D
- ******************************************************************************/
7 z" D& a- N6 M7 b$ z - /*----------------------------------------------------------------------------2 O9 X- O3 T6 l2 j# u5 D
- * @更新日志:+ N( Q; A/ W; Q; c- q# S4 [
- * @无3 H1 Y+ q! p4 W$ o* C4 K6 \8 y+ I- h
- * ---------------------------------------------------------------------------*/* X, A( x0 @) v( d: P+ a8 p
- /* 包含的头文件 --------------------------------------------------------------*/$ T: a* g1 r) C' b, |6 j8 o. c5 p$ P
- #include "sram.h"
8 v& L6 P& [' a$ _2 D0 X - #include "led.h"
$ _! U- |+ I( _ - #include "key.h"1 n9 J/ i9 ]* }( ]8 Q
- #include "sys.h"
9 z# q& s$ y6 L: _, o! T. |7 M% S - #include "delay.h"
3 L0 L. \& H+ ^: L& H - #include "usart.h" " n( a5 @9 T" w& _ J0 }
- /* 定义一个数组testsram[],u32表示每个数占4个字节,数组包含250000个值,*/
) L3 u5 v2 v) i. ^( Y - /* 采用绝对地址定义,数组的起始地址在0x68000000 */8 a' X6 J6 J3 x
- u32 testsram[250000] __attribute__((at(0X68000000)));
- z$ P/ s7 o/ a% Q, V A) k5 n% p' w3 h( H - /**********************************************************************
! ?% p3 _, d& p5 T4 ?+ `' I# a. b - 函数名称:fsmc_sram_test()8 |+ e) z0 M5 x2 S! a m
- 函数功能:外部内存测试(最大支持1M字节内存测试): b) `! M7 E9 {( y' G
- 入口参数:无8 H( ^" |7 k2 _0 Q5 g+ q. D
- 返回参数:无
6 {9 A7 M1 f" V. Q# J1 I - 开发作者:Aaron
8 T1 A6 q' B y$ H - ***********************************************************************/
$ x; A* O2 b9 h$ r; n e( j3 M - void fsmc_sram_test(void)* j D8 ]# C! h. e! w+ x
- { : y7 |% L: M8 `
- u32 i=0; , P4 A% f/ X( c" C& Y+ B. l
- u8 temp=0; /* 0≤temp≤255 */
! a3 S0 k' P3 R5 g# r - u8 sval=0; /* 在地址0读到的数据 */
5 c/ m( Z* g- {7 M, {& [8 r - printf("外部内存测试:0KB\r\n"); ; V' R( q' Q, O ]
- /* 每隔4K个字节,写入一个数据,总共写入256个数据,刚好是1M字节 */5 `& s" Y2 O2 Y/ M4 E, y
- for(i=0;i<1024*1024;i+=4096)
; A+ Q8 O. m/ }. E: P1 {+ e - {
5 A; D% {# u5 e2 }0 ~4 Q# D6 S - FSMC_SRAM_WriteBuffer(&temp,i,1);2 T" k7 ?" m2 o) |! z) d9 m
- temp++; /* for循环运行完后,temp值为0 */
2 m, C# `# ^8 ] `6 G3 ` - }
! v, y: Q$ I L" p - /* 依次读出之前写入的数据,进行校验 */ ' v: b& P- ^9 q1 M I
- for(i=0;i<1024*1024;i+=4096)
" |4 r J0 n$ I V - {
: d: P/ R$ H" u; g" P+ d - FSMC_SRAM_ReadBuffer(&temp,i,1);, Z" I }* i) f6 @
- if(i==0) /* 将第一次的temp值赋给sval,即sval=temp=0 */
9 Z, r9 `* T9 o) Z- C - sval=temp;, L) D1 g2 n, j; I v
- else if(temp<=sval)) o% O; a0 D3 L
- break; /* 本程序设计思路,后面读出的数据一定比第一次读到的数据大 */
: {. h! n. ?; X0 u - printf("内存容量为:%dKB\r\n",(temp-sval+1)*4); $ }" Y! V/ D: v0 ^
- } ! z5 o1 s" R9 L/ N( b: e' t1 O6 }
- }5 U3 u- P' F& ~7 m. Y4 `. e9 }
- /**********************************************************************
: T/ c' |2 T' R: |' b - 函数名称:main()
. v) c7 Q1 B0 L, K% o - 函数功能:主函数
- v. D! Z) c: @7 S) T - 入口参数:无
$ g% {1 ^5 Y$ |# \; `% ] - 返回参数:无) l; z( X# b1 C9 b& r
- 开发作者:Aaron
. d! F( T; {5 _ - ***********************************************************************/: \/ t: S6 i( y, D7 S% J
- int main(void)! e( H& C3 ?$ _ V7 ~
- {
% {1 V3 n% [" o X5 g0 N1 Q q: w - u8 key;
$ V% T3 \9 t5 \7 }1 ]$ V, ?' l - u8 i=0;
: \% t8 q- [: k$ W0 N* C - u32 ts=0;
; D7 ]0 E" X6 i0 J+ c2 h. O - delay_init();
) I3 t' ~" s2 ]% M4 n - NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
. e" f/ t. k3 J1 J - uart_init(115200);
0 ?# X I; ^" i |/ d' X" A7 U - LED_Init();
8 [" L$ L% q, ]* p. _5 O - KEY_Init();
5 c9 c5 a. S0 C! ] - FSMC_SRAM_Init();
% w" [4 ~$ x% u( V) y - for(ts=0;ts<250000;ts++)testsram[ts]=ts; /* 预存测试数据 */% q! i5 l! s. O4 y$ m
- while(1)
, E" J( A) J0 \) b) I) Z) P - { 8 w* g' G$ o g
- key=KEY_Scan(0); /* 不支持连按 */ * R& u7 a" P7 l; g+ M8 T4 A( k; H/ K4 n$ a7 G
- if(key==KEY0_PRES)
b& c- T- F1 A- P2 \" G; _" O - fsmc_sram_test(); /* 测试SRAM容量 */
3 E& d: T r6 R- g - else if(key==KEY1_PRES) /* 打印预存测试数据 */3 L2 G: v; u: v' w5 u; F
- {
) g T. H7 r7 [" x9 j - for(ts=0;ts<250000;ts++)
/ u/ D M O# U: s, A: R/ p - printf("显示测试数据testsram[%d]=%d\r\n",ts,testsram[ts]); 5 G+ ]! N! b6 r1 T
- }
' v: e2 H2 V1 u+ s - else
6 z) ?4 B8 `6 t - delay_ms(10); ' r8 d! j! E# D z# a$ q2 w4 k5 V/ |
- i++;
, E/ q3 U0 Y/ D0 d; J - if(i==20)
. p" T9 Z! A. L6 O' S, y* P7 p - {( }8 J2 z4 q% F0 R- i
- i=0;
: s; _4 @2 V. t, A - LED0=!LED0;
* h7 z" ^$ ]+ w - }5 ~' `1 A) \/ t1 F L& x2 f* N
- }
# o; B2 I1 B4 ~& X6 e0 ?1 c - }
3 U# v- z% r% J9 I f& v) V - /****** Copyright (C)2020 Aaron. All Rights Reserved ****** END OF FILE *******/
! O0 _0 l5 ~# v
1 T% q: c" K/ J
复制代码
8 s4 L8 d$ ~& P4. 实验结果
; r; q; ]: Y Y: V) v按KEY0键:
: y+ O- |+ I* P0 C6 j; L8 B/ H. @, w$ k
$ A q/ y0 z7 ]9 w( ~
, n$ l% t @9 t1 l$ V {0 C( |# x; z
' p5 ?8 t1 p/ a7 w
3 d. g! H: \& U按KEY1键:" `' Z ~) A2 c0 d
( n! m g) \* C+ L U4 d7 y
L' u1 l8 i7 y; G9 `
! U+ ?; D8 l. p8 H3 X) Z9 K————————————————; {5 |' O' ^) [7 m
版权声明:天亮继续睡
0 e, ?! x5 t" c) m# `/ L0 ~9 P9 Q; {7 `
5 a# |5 k3 x* f* W7 J4 E4 U |