灵动微MM32的FSMC接口驱动TFT_LCD屏幕

FSMC存储区域说明(挂载在AHB3总线)

在这里插入图片描述

BANK1的基地址是0x60000000,不同的子bank地址不同,通过HADDR[27:26]这两位的值确定。

HADDR[27:26]BANK SELECT(可挂载4个设备)
00 (0x0)BANK1-NOR/PSARM [NE1]
01 (0x1)BANK1-NOR/PSARM [NE2]
10 (0x2)BANK1-NOR/PSARM [NE3]
11 (0x3)BANK1-NOR/PSARM [NE4]
HADDR27:262524:0

Bank1的256M字节空间由 28 根地址线(HADDR[27:0])寻址(注意:这里的HADDR是内部AHB的地址线,它的地址是按字节进行“编号”的)。
这里HADDR[25:0]来自外部存储器地址FSMC_A[25:0],而HADDR[27:26]对4个区进行寻址
注意:DATA长度为16位情况下,由地址线FSMC_A[24:0]决定)

Exp: 若我们选择了第四个,这两位是11,所以子bank的基地址是:0x60000000+(0x3<<23)=0x6C000000。注:FSMC_A[23]作为 RS 控制信号

若要写指令,RS =0(根据实际外接设备的时序标准)

当 数据宽度 设置为 16bit 时,向地址(FSMC_BANK1_BASE+(0x0«23))写入命令CMD,则 FSMC_A[23]作为 RS 控制信号;
当 数据宽度 设置为 8bit 时,向地址(FSMC_BANK1_BASE+(0x0«23)) 写入命令CMD,则 FSMC_A[22]作为 RS 控制信号。

若要写数据,RS =1(根据实际外接设备的时序标准)

当 数据宽度 设置为 16bit 时,向地址(FSMC_BANK1_BASE+(0x1«23))写入数据DATA,则 FSMC_A[23]作为 RS 控制信号
当 数据宽度 设置为 8bit 时,向地址(FSMC_BANK1_BASE+(0x1«23))写入数据DATA, 则 FSMC_A[22]作为 RS 控制信号。

#define FSM_BANK_PSRAM_ADDR ((unsigned int)0x60000000) //BANK1的首地址

.硬件接口初始化

/*硬件接口*/
void mm32_fsmc_gpio_init(void)
{
    GPIO_InitTypeDef GPIO_InitStructure;

    RCC_AHBPeriphClockCmd(RCC_AHBENR_GPIOD, ENABLE);
    RCC_AHBPeriphClockCmd(RCC_AHBENR_GPIOE, ENABLE);  
	
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_SYSCFG, ENABLE);
//AF12--FSMC复用
    GPIO_PinAFConfig(GPIOD, GPIO_PinSource4, GPIO_AF_12);//PD4-FSMC_NOE [nRD]	
    GPIO_PinAFConfig(GPIOD, GPIO_PinSource5, GPIO_AF_12);//PD5-FSMC_NWE [nWR]
    GPIO_PinAFConfig(GPIOD, GPIO_PinSource7, GPIO_AF_12);//PD7-FSMC_NE1 [nCS] 即挂载在BANK1上
    GPIO_PinAFConfig(GPIOD, GPIO_PinSource13, GPIO_AF_12);//PD13-FSMC_A18[R/S] -->RS接到了A18线
    
    GPIO_PinAFConfig(GPIOD, GPIO_PinSource14, GPIO_AF_12);//PD14-FSMC_D00
    GPIO_PinAFConfig(GPIOD, GPIO_PinSource15, GPIO_AF_12);//PD15-FSMC_D01
    GPIO_PinAFConfig(GPIOD, GPIO_PinSource0, GPIO_AF_12);//PD0-FSMC_D02
    GPIO_PinAFConfig(GPIOD, GPIO_PinSource1, GPIO_AF_12);//PD1-FSMC_D03
    GPIO_PinAFConfig(GPIOE, GPIO_PinSource7, GPIO_AF_12);//PE7-FSMC_D04
    GPIO_PinAFConfig(GPIOE, GPIO_PinSource8, GPIO_AF_12);//PE8-FSMC_D05
    GPIO_PinAFConfig(GPIOE, GPIO_PinSource9, GPIO_AF_12);//PE9-FSMC_D06
    GPIO_PinAFConfig(GPIOE, GPIO_PinSource10, GPIO_AF_12);//PE10-FSMC_D07
    GPIO_PinAFConfig(GPIOE, GPIO_PinSource11, GPIO_AF_12);//PE11-FSMC_D08
    GPIO_PinAFConfig(GPIOE, GPIO_PinSource12, GPIO_AF_12);//PE12-FSMC_D09
    GPIO_PinAFConfig(GPIOE, GPIO_PinSource13, GPIO_AF_12);//PE13-FSMC_D10
    GPIO_PinAFConfig(GPIOE, GPIO_PinSource14, GPIO_AF_12);//PE14-FSMC_D11
    GPIO_PinAFConfig(GPIOE, GPIO_PinSource15, GPIO_AF_12);//PE15-FSMC_D12
    GPIO_PinAFConfig(GPIOD, GPIO_PinSource8, GPIO_AF_12);//PD8-FSMC_D13
    GPIO_PinAFConfig(GPIOD, GPIO_PinSource9, GPIO_AF_12);//PD9-FSMC_D14
    GPIO_PinAFConfig(GPIOD, GPIO_PinSource10, GPIO_AF_12);//PD10-FSMC_D15    
//FSMC
    GPIO_InitStructure.GPIO_Pin     =  GPIO_Pin_0|GPIO_Pin_1|GPIO_Pin_4\
                                       |GPIO_Pin_5|GPIO_Pin_7|GPIO_Pin_8\
                                       |GPIO_Pin_9|GPIO_Pin_10|GPIO_Pin_13\
                                       |GPIO_Pin_14|GPIO_Pin_15;
    GPIO_InitStructure.GPIO_Speed   = GPIO_Speed_50MHz;
    GPIO_InitStructure.GPIO_Mode    = GPIO_Mode_AF_PP;
    GPIO_Init(GPIOD, &GPIO_InitStructure);
    GPIO_InitStructure.GPIO_Pin     =  GPIO_Pin_7|GPIO_Pin_8|GPIO_Pin_9\
                                       |GPIO_Pin_10|GPIO_Pin_11|GPIO_Pin_12\
                                       |GPIO_Pin_13|GPIO_Pin_14|GPIO_Pin_15;
    GPIO_InitStructure.GPIO_Speed   = GPIO_Speed_50MHz;
    GPIO_InitStructure.GPIO_Mode    = GPIO_Mode_AF_PP;
    GPIO_Init(GPIOE, &GPIO_InitStructure);
}
/*
**FSMC外设初始化
*/
void mm32_fsmc_init(void)
{
    FSMC_InitTypeDef                FSMC_InitStructure;
    FSMC_NORSRAM_Bank_InitTypeDef   FSMC_BankInitStructure;
    
    RCC_AHB3PeriphClockCmd(RCC_AHB3ENR_FSMC, ENABLE);
//	FSMC_NORSRAM_BankStructInit(&FSMC_BankInitStructure);
//  FSMC_NORSRAMStructInit(&FSMC_InitStructure);
//5.95ns@168MHz
//10.4ns@96MHz
/*
**SM_READ_PIPE:读数据延迟周期数,
**即从 SRAM 读数据输出端到FSMC 内部读数据端之间的寄存器数,默认为 0。
*/		
    FSMC_BankInitStructure.FSMC_SMReadPipe    = 0;//数据延迟
/*READY_MODE:选择是否采用外部设备 FSMC_NWAIT 信号。
**0:不采用外部 FSMC_NWAIT 信号,而采用内部相关信号;
**1:采用外部设备 FSMC_NWAIT 信号。
*/
    FSMC_BankInitStructure.FSMC_ReadyMode     = 0;//0: Internal FSMC 1: External DEVICE (ie from FSMC_NWAIT)
/*
**t_wp:写操作周期,取值范围 0~63,对应写脉冲宽度 1~64 个时钟周期
*/		
    FSMC_BankInitStructure.FSMC_WritePeriod   = 0x8;//写周期(OMA=66ns)	
/*
**t_rc 读操作周期,取值范围 2~63,对应读操作周期 1~62 个时钟周期
*/
    FSMC_BankInitStructure.FSMC_ReadPeriod    = 0x8;//读周期(OMA=160ns)   
/*
**t_wr:写操作时地址的保持时间,取值范围 0~3,对应写操作时地址的保持时间0~3 个时钟周期
*/	
    FSMC_BankInitStructure.FSMC_WriteHoldTime = 0x02;//写保持时间设置(OMA=10ns)
/*
**t_as:写操作时地址的建立时间,取值范围 0~3,对应写操作时地址的建立时间0~3 个时钟周期
*/		
    FSMC_BankInitStructure.FSMC_AddrSetTime   = 0x02;//地址建立时间设置(OMA=0ns)
/*
**存储器数据总线位宽设置(与寄存器 SMTMGR_SETx 设置的时序相匹配)
*/		
    FSMC_BankInitStructure.FSMC_DataWidth     = FSMC_DataWidth_16bits;
    FSMC_NORSRAM_Bank_Init(&FSMC_BankInitStructure, FSMC_NORSRAM_BANK0);
/*
**SYSCFG 配置寄存器(SYSCFG_CFGR)
**[30:29] 
**FSMC 模式选择
**01:兼容 8080 协议接口
**00:兼容 NOR FLASH 接口
**1x:保留
*/
    FSMC_InitStructure.FSMC_Mode            = FSMC_Mode_8080;
/*
**REG_SELECT[2:0]:时序参数配置寄存器组选择
**000:选择 SMTMGR_SET0 寄存器来配置 BANK1 传输的时序参数
**001:选择 SMTMGR_SET1 寄存器来配置 BANK1 传输的时序参数
**010:选择 SMTMGR_SET2 寄存器来配置 BANK1 传输的时序参数
**其它:保留
*/
    FSMC_InitStructure.FSMC_TimingRegSelect = FSMC_TimingRegSelect_0;
/*
**MEM_SIZE[4:0]:外接设备容量
**00000:未连接任何设备
**00001: 64KB
**00010 :128KB
**00011:256KB
**00100:512KB
**00101:1MB
**00110:2MB
**00111:4MB
**01000:8MB
**01001:16MB
**01010:32MB
**01011:64MB
**其它:保留
*/		
    FSMC_InitStructure.FSMC_MemSize         = FSMC_MemSize_64MB;
/*
**MEM_TYPE[2:0]:外接设备类型
**001:SRAM
**010:NOR FLASH
**其他:保留
*/		
    FSMC_InitStructure.FSMC_MemType         = FSMC_MemType_NorSRAM;
/*
**FC_ODATAEN 
**FSMC 地址数据复用引脚只能作为数据使用
**1:仅作为数据引脚使用
**0:允许作为数据地址使用
*/		
    FSMC_InitStructure.FSMC_AddrDataMode    = FSMC_AddrDataMUX; 
    FSMC_NORSRAMInit(&FSMC_InitStructure);			
}

.LCD读写操作

/*
**当RS=0时,表示读写REG
**当RS=1时,表示读写RAM
*/
/*
**写指令
*/
/*加__inline为了优化代码,可以不需要 */
__inline void lcd_write_index(void *arg,unsigned short int index)
{
	(*(volatile unsigned short int *)FSM_BANK_PSRAM_ADDR)=index; 
}
/*
**写数据
*/
__inline void lcd_write_data(void *arg,unsigned short int data)
{
	//(0x1<<(An+1) @16bit_width  ->  1<<(18+1)=0x80000
	(*(volatile unsigned short int *)(FSM_BANK_PSRAM_ADDR|0x80000))=data; 
}
/*
**写寄存器
*/
void lcd_write_register(void *arg,unsigned short int index,unsigned short int data)
{
  lcd_write_index(0,index);
  lcd_write_data(0,data);
}
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值