FMC擴展SDRAM

開發平臺

  • F429
  • 標準庫

SDARM

在這裏插入圖片描述

如何控制SDRAM
  • 控制線:控制SDRAM需要命令去控制,控制線在不同狀態下形成不同的命令
  • 地址線:用來選取地址的,分成A類線和BA類,A是行和列的地址總線,BA是用來選取BANK的獨立地線(一般的SDRAM都有4個BANK)。
    如何選取地址:首先選擇BANK的序號,然後再選行和列
  • 數據線:用來輸入輸出數據(一共有16位),這個型號的SDRAM,數據線寬位16,當我們寫入數據的時候不一定會寫入16位,這個時候就會用到DQM來控制,8位有效還是16位有效
SDRAM的命令
  • 禁止命令
  • 空操作
  • 行有效
  • 列讀寫
  • 預充電:重新發送行列地址,A10這條線可以進行單獨控制,A10高電平時對所有BANK進行預充電,爲低電平時對BA線選定的BANK進行預充電。(所有的BANK都要預充電)
  • 自動刷新和自我刷新:CKE時鐘線爲低電平時,使用自動刷新,否者使用自我刷新。一般進入低功耗時,纔會使用自我刷新(刷新週期爲64ms)
  • 加載模式寄存器:在SDRAM啓動時需要配置(寄存器如下圖)
    (A0-A2)BL突發長度:在同一行中連續讀寫的存儲單元,一般長度有1、2、4、8
    (A3)BT突發類型:順序突發和間隔突發(一般選擇順序突發)
    (A4-A6):CL列選通後的延遲時間:一般是2、3個週期
    (A7-A8):00正常模式
    (A9):選擇突發模式還是非突發模式

在這裏插入圖片描述

FMC

在這裏插入圖片描述

  • FMC引腳:MCU上的引腳與SDRAM上面對應的引腳相連
  • FMC寄存器的配置
  • 設置SDRAM通訊的頻率(SDRAM通訊最高頻率爲90MHZ)
SDRAM啓動
  • 開啓時鐘 等待至少100us
  • 對所有的BANK進行預充電
  • 自動刷新
  • 設置加載模式寄存器(如何配置,根據實際情況填寫寄存器的值)
  • 設置刷新計數器的值:SDRAM的刷新週期爲64ms、行數爲4096
    計算公式:在這裏插入圖片描述
static void SDARM_Init(void)
{
    uint32_t tmpr=0;
    FMC_SDRAMCommandTypeDef FMC_SDRAMCommandStruct;
    /*開啓芯片時鐘*/
    FMC_SDRAMCommandStruct.FMC_CommandMode=FMC_Command_Mode_CLK_Enabled;
    FMC_SDRAMCommandStruct.FMC_CommandTarget=FMC_Command_Target_bank2;
    FMC_SDRAMCommandStruct.FMC_AutoRefreshNumber=0;
    FMC_SDRAMCommandStruct.FMC_ModeRegisterDefinition=0;
    while(FMC_GetFlagStatus(FMC_Bank2_SDRAM,FMC_FLAG_Busy)!=RESET)
    {

    }
    FMC_SDRAMCmdConfig(&FMC_SDRAMCommandStruct);
	
    DELAY_us(1000);
    /*對所有bank預充電*/
    FMC_SDRAMCommandStruct.FMC_CommandMode=FMC_Command_Mode_PALL;
    FMC_SDRAMCommandStruct.FMC_CommandTarget=FMC_Command_Target_bank2;
    FMC_SDRAMCommandStruct.FMC_AutoRefreshNumber=0;
    FMC_SDRAMCommandStruct.FMC_ModeRegisterDefinition=0;
    while(FMC_GetFlagStatus(FMC_Bank2_SDRAM,FMC_FLAG_Busy)!=RESET)
    {

    }
    FMC_SDRAMCmdConfig(&FMC_SDRAMCommandStruct);
    /*自動刷新*/
    FMC_SDRAMCommandStruct.FMC_CommandMode=FMC_Command_Mode_AutoRefresh;
    FMC_SDRAMCommandStruct.FMC_CommandTarget=FMC_Command_Target_bank2;
    FMC_SDRAMCommandStruct.FMC_AutoRefreshNumber=2;
    FMC_SDRAMCommandStruct.FMC_ModeRegisterDefinition=0;
    while(FMC_GetFlagStatus(FMC_Bank2_SDRAM,FMC_FLAG_Busy)!=RESET)
    {

    }
    FMC_SDRAMCmdConfig(&FMC_SDRAMCommandStruct);
    /*設置SDRAM寄存器*/
    tmpr=(uint32_t)SDRAM_MODEREG_BURST_LENGTH_4         |
                   SDRAM_MODEREG_BURST_TYPE_SEQUENTIAL  |
                   SDRAM_MODEREG_CAS_LATENCY_2          |
                   SDRAM_MODEREG_OPERATING_MODE_STANDARD|
                   SDRAM_MODEREG_WRITEBURST_MODE_SINGLE ;
    
    FMC_SDRAMCommandStruct.FMC_CommandMode=FMC_Command_Mode_LoadMode;
    FMC_SDRAMCommandStruct.FMC_CommandTarget=FMC_Command_Target_bank2;
    FMC_SDRAMCommandStruct.FMC_AutoRefreshNumber=1;
    FMC_SDRAMCommandStruct.FMC_ModeRegisterDefinition=tmpr;
    while(FMC_GetFlagStatus(FMC_Bank2_SDRAM,FMC_FLAG_Busy)!=RESET)
    {

    }
    FMC_SDRAMCmdConfig(&FMC_SDRAMCommandStruct);
    /*設置刷新計數器*/
    FMC_SetRefreshCount(1386);
    while(FMC_GetFlagStatus(FMC_Bank2_SDRAM,FMC_FLAG_Busy)!=RESET)
    {

    }
}
FMC初始化
  • SDRAM的時序參數,需要看手冊去配置
    一個時鐘週期爲1/90M=11.11ns
    在這裏插入圖片描述
  • 配置FMC_SDRAM的參數
void FMC_Init(void)
{
    FMC_SDRAMTimingInitTypeDef FMC_SDRAMTimingStruct;
    FMC_SDRAMInitTypeDef FMC_SDRAMInitStruct;

    FMC_GPIO_Init();
    RCC_AHB3PeriphClockCmd(RCC_AHB3Periph_FMC,ENABLE);

    FMC_SDRAMTimingStruct.FMC_ExitSelfRefreshDelay=7;
    FMC_SDRAMTimingStruct.FMC_LoadToActiveDelay=2;
    FMC_SDRAMTimingStruct.FMC_RCDDelay=2;
    FMC_SDRAMTimingStruct.FMC_RowCycleDelay=7;
    FMC_SDRAMTimingStruct.FMC_RPDelay=2;
    FMC_SDRAMTimingStruct.FMC_SelfRefreshTime=4;
    FMC_SDRAMTimingStruct.FMC_WriteRecoveryTime=2;

    FMC_SDRAMInitStruct.FMC_Bank=FMC_Bank2_SDRAM;
    FMC_SDRAMInitStruct.FMC_CASLatency=FMC_CAS_Latency_2;
    FMC_SDRAMInitStruct.FMC_ColumnBitsNumber=FMC_ColumnBits_Number_8b;
    FMC_SDRAMInitStruct.FMC_InternalBankNumber=FMC_InternalBank_Number_4;
    FMC_SDRAMInitStruct.FMC_ReadBurst=FMC_Read_Burst_Enable;
    FMC_SDRAMInitStruct.FMC_ReadPipeDelay=FMC_ReadPipe_Delay_0;
    FMC_SDRAMInitStruct.FMC_RowBitsNumber=FMC_RowBits_Number_12b;
    FMC_SDRAMInitStruct.FMC_SDClockPeriod=FMC_SDClock_Period_2;
    FMC_SDRAMInitStruct.FMC_SDMemoryDataWidth=FMC_SDMemory_Width_16b;
    FMC_SDRAMInitStruct.FMC_WriteProtection=FMC_Write_Protection_Disable;
    FMC_SDRAMInitStruct.FMC_SDRAMTimingStruct=&FMC_SDRAMTimingStruct;

    FMC_SDRAMInit(&FMC_SDRAMInitStruct);
	DELAY_us(50000);
    /*SDRAM初始化*/
    SDARM_Init();
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章