Forth http://fforum.winglion.ru/ |
|
Простой контролер SD-RAM на AHDL http://fforum.winglion.ru/viewtopic.php?f=11&t=341 |
Страница 1 из 2 |
Автор: | WingLion [ Сб ноя 18, 2006 11:33 ] |
Заголовок сообщения: | Простой контролер SD-RAM на AHDL |
Код: -----------------------------------
-- Simple SDRAM controller ver 2.00 -- page mode burst read/write -- latensy = 3, frq = 50..100MHz -- 2004 (c) Ivan Mak -- E-mail: ivan_mak@mail.ru -- http://winglion.ru/ ----------------------------------- TITLE "SDRAM_controller"; PARAMETERS ( WIDTH = 16, -- SDRAM data WIDTH ADR_RG = "YES", -- "YES" -- input adress register OUT_SH = "YES", -- "YES" -- 1/2 clk data shift M_REG = "YES" ); SUBDESIGN sdram ( CLK : INPUT; RESET : INPUT; -- dir signals DI[WIDTH-1..0] : INPUT; -- input data DO[WIDTH-1..0] : OUTPUT; -- output data A[23..0] : INPUT; -- adress RAM CS : INPUT = VCC; -- select WR : INPUT = VCC; -- write RD : INPUT = VCC; -- read STOP : INPUT = VCC; -- for sinhronize cycle -- sdram signals MD[WIDTH-1..0] : BIDIR; -- RAM data bus MWE : OUTPUT; -- RAM signal WE MRAS : OUTPUT; -- RAM signal RAS MCAS : OUTPUT; -- RAM signal CAS MCS : OUTPUT; -- RAM signal CS MBS[1..0] : OUTPUT; -- RAM signals BS1,BS0 MCKE : OUTPUT; -- RAM signal CKE MCLK : BIDIR; -- RAM signal CLK MA[13..0] : OUTPUT; -- RAM adress bus MDQM : OUTPUT; -- return signals MEM_C : OUTPUT; -- memory cycle WRITE : OUTPUT; -- write data READ : OUTPUT; -- data read VALID : OUTPUT; ) VARIABLE ARGX[23..0] : DFFE; ARG[23..0] : NODE; CTT[5..0] : DFFE; TAB[5..0] : DFF; CTT_2 : NODE; CTT_3 : NODE; CTT_4 : NODE; CT[3..0] : DFFE; -- counter MX[13..0] : DFF; -- adress mux MY[5..3] : DFF; -- dir mux MDR[WIDTH-1..0] : DFF; -- data reg MDRX[WIDTH-1..0]: DFF; -- data reg MDRY[WIDTH-1..0]: DFF; -- data reg PA : NODE; RWC_FIX[2..0] : DFFE; R/W : NODE; WRITE_2 : NODE; MCLKX : NODE; MCLKY : NODE; RX_MA[13..0]: DFF; RX_MCKE : DFF; RX_MBS[1..0]: DFF; RX_MCS : DFF; RX_MRAS : DFF; RX_MCAS : DFF; RX_MWE : DFF; BEGIN -- input address register ARGX[].clk = CLK; -- ARGX[].ena = VCC; -- fixed adress when bank active ARGX[].ena = MEM_C; ARGX[].d = A[]; RWC_FIX[].clk = CLK; RWC_FIX[].ena = MEM_C; RWC_FIX[] = (RD,WR,CS); IF (ADR_RG == "YES") GENERATE ARG[] = ARGX[]; ELSE GENERATE ARG[] = A[]; END GENERATE; -- micro count CTT[].clk = CLK; CTT[].clrn = RESET; CTT[].ena = DFF((!(CT[] == 8) or STOP),CLK,,); CTT_2 = DFF(CTT[] == 2,CLK,,); CTT_3 = DFF(CTT[] == 3,CLK,,); CTT_4 = DFF(CTT[] == 4,CLK,,); IF CTT_2 THEN CTT[] = TAB[]; -- one command period ELSE CTT[] = CTT[] - 1; END IF; -- SDRAM data -- mode sdram bit2..0 - 000 - 1byte -- 001 - 2byte -- 010 - 4byte -- 011 - 8byte -- 111 - page -- other - reserved -- bit3 - 0 - seqential -- 1 - interleave -- bit6..4 - 010 - cas latency = 2 -- 011 - cas latency = 3 -- other - reserved -- bit7 - 0 (?test?) -- bit8 - 0 reserved -- bit9 - 0 burst read & burst write -- 1 burst read & single write -- bit11..10 - 00 reserved -- BS[1..0] - 00 reserved -- sdram commands RAS,CAS,WE -- 000 - mode register write -- 001 - auto refresh -- cken=0 -> self refresh -- -- CS=H -> SR exit -- RCW=110 -> SR exit -- 010 - bank precharge -- A10=0 precharge bank -- -- A10=1 precharge all -- 011 - bank active -- 100 - write -- A10=1 - auto precharge -- 101 - read -- A10=1 - auto precharge -- 110 - burst stop -- 111 - no operation R/W = DFFE((!(RWC_FIX[] == B"X00") or !(MY[5..3] == B"011")),CLK,,,CTT_2); -- comand counter CT[].clk = CLK; CT[].clrn = RESET; CT[].ena = CTT_2; IF DFF((CT[3..0] == 12),CLK,,) THEN CT[] = 8; ELSE CT[] = CT[]+1; END IF; -- SDRAM command & times table TAB[].clk = CLK; MY[].clk = CLK; CASE CT[3..0] IS -- MY[] -- RAS,CAS,WE -- init commands WHEN 0 => TAB[] = 4; MY[] = B"010"; -- precharge ALL WHEN 1 => TAB[] = 4; MY[] = B"000"; -- set mode register WHEN 2 => TAB[] = 8; MY[] = B"001"; -- autorefresh WHEN 3 => TAB[] = 8; MY[] = B"001"; -- autorefresh WHEN 4 => TAB[] = 8; MY[] = B"001"; -- autorefresh WHEN 5 => TAB[] = 8; MY[] = B"001"; -- autorefresh WHEN 6 => TAB[] = 8; MY[] = B"001"; -- autorefresh WHEN 7 => TAB[] = 8; MY[] = B"001"; -- autorefresh -- cycle commands (realy 5 items) WHEN 8 => TAB[] = 4; MY[] = B"011"; -- bank active -- ! words count (0->64) WHEN 9 => TAB[] = 0; MY[] = (B"10",R/W); -- bank read/write WHEN 10 => TAB[] = 4; MY[] = B"110"; -- burst stop! WHEN 11 => TAB[] = 4; MY[] = B"010"; -- bank precharge WHEN 12 => TAB[] = 8; MY[] = B"001"; -- autorefresh WHEN 13 => TAB[] = 4; MY[] = B"111"; -- NOP no executed WHEN 14 => TAB[] = 4; MY[] = B"111"; -- NOP no executed WHEN 15 => TAB[] = 4; MY[] = B"111"; -- NOP no executed END CASE; MCLKY = LCELL(CLK); MCLKX = LCELL(MCLKY); MCLK = TRI(MCLKX,VCC); -- address MUX PA = DFF(!(CT[2..0] == 0),CLK,,); MX[].clk = CLK; CASE (CT3,PA) IS WHEN 0 => MX[] = (B"00010000000000"); -- precharge all WHEN 1 => MX[] = (B"00000000110111"); -- SDRAM mode WHEN 2 => MX[] = (B"00",ARG[21..10]); -- adress RAS -- 4k WHEN 3 => MX[] = (B"0000",ARG[9..0]); -- adress CAS -- 1k END CASE; -- input register MDR[].clk = CLK; MDR[].d = DI[]; -- WRITE_2 = (DFF(DFF(DFF(WRITE,CLK,,),CLK,,),CLK,,)); WRITE_2 = DFF(DFF(WRITE or DFF(WRITE,CLK,,),CLK,,),CLK,,); -- WRITE_2 = DFF(WRITE,CLK,,); FOR i IN 0 TO WIDTH-1 GENERATE MD[i] = TRI(MDR[i],WRITE_2); END GENERATE; -- output register' -- for 1/2 shift -- MDRX[].clk = !CLK; -- MDRX[].clk = !LCELL(CLK); MDRX[].clk = MCLK; MDRX[].d = MD[]; -- output register MDRY[].clk = CLK; IF (OUT_SH == "YES") GENERATE MDRY[].d = MDRX[]; -- 1/2 clk data shift ELSE GENERATE MDRY[].d = MD[]; -- no 1/2 clk data shift END GENERATE; DO[] = MDRY[]; IF (M_REG == "YES") GENERATE MA[] = RX_MA[13..0]; -- MCKE = RX_MCKE; MCKE = VCC; MBS[1..0] = RX_MBS[1..0]; MCS = RX_MCS; MRAS = DFF(RX_MRAS,CLK,,); MCAS = DFF(RX_MCAS,CLK,,); MWE = DFF(RX_MWE,CLK,,); MDQM = GND; ELSE GENERATE MA[] = MX[]; -- (MDQM,MCKE,MRAS,MCAS,MWE,MBS1,MBS0) = (GND,VCC,MY[5..3],ARG[23..22]); (MDQM,MCKE,MRAS,MCAS,MWE,MBS1,MBS0) = (GND,VCC,RX_MRAS,RX_MCAS,RX_MWE,ARG[23..22]); MCS = DFF((!(CTT[] == 1)),CLK,,); END GENERATE; -- (MDQM,MCKE,MRAS,MCAS,MWE,MBS1,MBS0) = (GND,VCC,MY[5..3],ARG[23..22]); RX_MA[13..0]= MX[]; RX_MCKE = VCC; RX_MBS[1..0]= ARG[23..22]; RX_MA[13..0].clk = CLK; RX_MCKE.clk = CLK; RX_MBS[1..0].clk = CLK; RX_MCS = DFF((!(CTT[] == 1)),CLK,,); RX_MCS.clk = CLK; RX_MRAS = MY5; RX_MRAS.clk = CLK; RX_MCAS = MY4; RX_MCAS.clk = CLK; RX_MWE = MY3; RX_MWE.clk = CLK; -- return signals -- write cycle -- WRITE = DFFE((MY[5..3] == B"100"),CLK,,,CTT_3); WRITE = DFFE((MY[5..3] == B"100"),CLK,,,CTT_4); -- mem cycle MEM_C = DFFE((MY[5..3] == B"001"),CLK,,,VCC); -- MEM_C = PA; -- read sysle READ = DFFE(((RWC_FIX[] == B"010") & (MY[5..3] == B"101")),CLK,,,CTT_3); -- data valid VALID = DFF(DFF(DFF(DFF(DFF(READ,CLK,,),CLK,,),CLK,,),CLK,,),CLK,,); END; |
Автор: | Hishnik [ Сб ноя 18, 2006 23:21 ] |
Заголовок сообщения: | |
Ух, сколько кода! |
Автор: | WingLion [ Вс ноя 19, 2006 08:22 ] |
Заголовок сообщения: | |
Код из конкретного проекта работающего устройства. Что-то лишнее в нем есть, но оно просто было необходимо. Ну, и комменты еще создают видимость большого кода... А при компиляции данный контроллер занимает ~145 LCELL Из них фактически около 50 вспомогательных, не относящихся собственно, к контроллеру. Защелки для адреса и данных, например. Регистры сдвига для создания задержек выходных сигналов. Короче, этот вот код да на VHDL перевести надо бы, посмотреть разницу. |
Автор: | Hishnik [ Вс ноя 19, 2006 12:03 ] |
Заголовок сообщения: | |
С приездом! (?) Да, я заметил, что тут много выписано руками для достижения заданных характеристик. Поведенческое описание вряд ли сократит ячейки, но возможно, будет покомпактнее. Кстати, генераторы контроллеров Xilinx точно раздает бесплатно. Altera - не знаю. |
Автор: | WingLion [ Чт апр 22, 2010 18:58 ] |
Заголовок сообщения: | Re: Простой контролер SD-RAM на AHDL |
Цитата: Что нужно переделать в Вашем контроллере SDRAM (viewtopic.php?f=11&t=341) для работы с чипом от Микрона,типа MT48LC4M32B2 (http://download.micron.com/pdf/datashee ... RAMx32.pdf)? 1. В первую очередь выставить параметр WIDTH =32. 2. Прогнать схему в симуляторе, в конкретном месте (с назначениями пинов), с конкретной ПЛИС, там где предполагается ее использовать. 3. "Поиграться" с установкой дополнительных задержек (на логических ячейках) для сигнала MCLK - синхронизации, подаваемой на SD-RAM с целью получения попадания фронта сигнала синхронизации в серединку импульса сигнала MCS. В идеальном варианте, если используемая ПЛИС имеет PLL, сделать на нем сигналы синхронизации CLK и MCLK со смещением по фазе относительно друг друга. |
Автор: | WingLion [ Чт апр 22, 2010 19:40 ] |
Заголовок сообщения: | Re: Обсуждение переезда на phpbb3 |
Последний вариант AHDL кода этого же контроллера. Главное отличие в том, что сигнал синхронизации для SD-RAM формируется снаружи относительно этой схемы, и в организации раздельных каналов адреса для записи и для чтения (так было нужно для проекта) Код: ----------------------------------- -- Simple SDRAM controller -- page mode burst read/write -- latensy = 3, frq = 50..150MHz -- 2002-2010 (c) Ivan Mak -- E-mail: ivan_mak@mail.ru aka admin@winglion.ru -- http://winglion.ru ----------------------------------- TITLE "SDRAM_controller"; PARAMETERS ( WIDTH = 16, -- SDRAM data WIDTH OUT_SH = "YES", -- "YES" -- 1/2 clk data shift PRIORITY = "WRITE" -- "READ" или "WRITE" ); SUBDESIGN sdram ( CLK : INPUT; CLKs : input; RESET : INPUT; -- dir signals DI[WIDTH-1..0] : INPUT = GND; -- input data DO[WIDTH-1..0] : OUTPUT; -- output data RA[23..0] : INPUT = GND; -- adress RAM WA[23..0] : INPUT = GND; -- adress RAM CS : INPUT = GND; -- select WR : INPUT = VCC; -- write RD : INPUT = VCC; -- read STOP : INPUT = VCC; -- for sinhronize cycle -- sdram signals MD[WIDTH-1..0] : BIDIR; -- RAM data bus MWE : OUTPUT; -- RAM signal WE MRAS : OUTPUT; -- RAM signal RAS MCAS : OUTPUT; -- RAM signal CAS MCS : OUTPUT; -- RAM signal CS MBS[1..0] : OUTPUT; -- RAM signals BS1,BS0 MCKE : OUTPUT; -- RAM signal CKE MCLK : BIDIR; -- RAM signal CLK MA[11..0] : OUTPUT; -- RAM adress bus MDQM : OUTPUT; -- return signals MEM_C : OUTPUT; -- memory cycle WRITE : OUTPUT; -- write data READ : OUTPUT; -- data read VALID : OUTPUT; ) VARIABLE ARGX[23..0] : DFFE; ARG[23..0] : NODE; CTT[5..0] : DFFE; TAB[5..0] : DFF; CTT_2 : NODE; CTT_3 : NODE; CTT_4 : NODE; CT[3..0] : DFFE; -- counter MX[11..0] : DFF; -- adress mux MY[5..3] : DFF; -- dir mux MDR[WIDTH-1..0] : DFF; -- data reg MDRX[WIDTH-1..0]: DFF; -- data reg MDRY[WIDTH-1..0]: DFF; -- data reg PA : NODE; RWC_FIX[2..0] : DFFE; R/W : NODE; WRITE_2 : NODE; -- MCLKX : NODE; -- MCLKY : NODE; -- MCLKZ : NODE; -- RX_MA[13..0]: DFF; -- RX_MCKE : DFF; -- RX_MBS[1..0]: DFF; -- -- RX_MCS : DFF; -- RX_MRAS : DFF; RX_MCAS : DFF; RX_MWE : DFF; BEGIN -- input address register ARGX[].clk = CLK; -- ARGX[].ena = VCC; -- fixed adress when bank active ARGX[].ena = MEM_C; -- fixed adress when bank active -- IF (PRIORITY != "READ") and (PRIORITY != "WRITE") THEN -- ASSERT "PRIORITY parametr muast be READ or WRITE!"; -- END IF; IF PRIORITY == "WRITE" GENERATE CASE (RD,WR) IS WHEN 3 => ARGX[] = GND; WHEN 1 => ARGX[] = RA[]; WHEN 2,0 => ARGX[] = WA[]; END CASE; R/W = DFFE((!(RWC_FIX[] == B"X00") or !(MY[5..3] == B"011")),CLK,,,CTT_2); END GENERATE; IF PRIORITY == "READ" GENERATE CASE (RD,WR) IS WHEN 3 => ARGX[] = GND; WHEN 1,0 => ARGX[] = RA[]; WHEN 2 => ARGX[] = WA[]; END CASE; R/W = DFFE(!(!(RWC_FIX[] == B"0X0") or !(MY[5..3] == B"011")),CLK,,,CTT_2); END GENERATE; ARG[] = ARGX[]; -- ARGX[].d = A[]; RWC_FIX[].clk = CLK; RWC_FIX[].ena = MEM_C; RWC_FIX[] = (RD,WR,CS); -- micro count CTT[].clk = CLK; CTT[].clrn = RESET; CTT[].ena = DFF((!(CT[] == 8) or STOP),CLK,,); CTT_2 = DFF(CTT[] == 2,CLK,,); CTT_3 = DFF(CTT[] == 3,CLK,,); CTT_4 = DFF(CTT[] == 4,CLK,,); IF CTT_2 THEN CTT[] = TAB[]; -- one command period ELSE CTT[] = CTT[] - 1; END IF; -- SDRAM data -- mode sdram bit2..0 - 000 - 1byte -- 001 - 2byte -- 010 - 4byte -- 011 - 8byte -- 111 - page -- other - reserved -- bit3 - 0 - seqential -- 1 - interleave -- bit6..4 - 010 - cas latency = 2 -- 011 - cas latency = 3 -- other - reserved -- bit7 - 0 (?test?) -- bit8 - 0 reserved -- bit9 - 0 burst read & burst write -- 1 burst read & single write -- bit11..10 - 00 reserved -- BS[1..0] - 00 reserved -- sdram commands RAS,CAS,WE -- 000 - mode register write -- 001 - auto refresh -- cken=0 -> self refresh -- -- CS=H -> SR exit -- RCW=110 -> SR exit -- 010 - bank precharge -- A10=0 precharge bank -- -- A10=1 precharge all -- 011 - bank active -- 100 - write -- A10=1 - auto precharge -- 101 - read -- A10=1 - auto precharge -- 110 - burst stop -- 111 - no operation -- R/W = DFFE((!(RWC_FIX[] == B"X00") or !(MY[5..3] == B"011")),CLK,,,CTT_2); -- comand counter CT[].clk = CLK; CT[].clrn = RESET; CT[].ena = CTT_2; IF DFF((CT[3..0] == 12),CLK,,) THEN CT[] = 8; ELSE CT[] = CT[]+1; END IF; -- SDRAM command & times table TAB[].clk = CLK; MY[].clk = CLK; CASE CT[3..0] IS -- MY[] -- RAS,CAS,WE -- init commands WHEN 0 => TAB[] = 4; MY[] = B"010"; -- precharge ALL WHEN 1 => TAB[] = 4; MY[] = B"000"; -- set mode register WHEN 2 => TAB[] = 8; MY[] = B"001"; -- autorefresh WHEN 3 => TAB[] = 8; MY[] = B"001"; -- autorefresh WHEN 4 => TAB[] = 8; MY[] = B"001"; -- autorefresh WHEN 5 => TAB[] = 8; MY[] = B"001"; -- autorefresh WHEN 6 => TAB[] = 8; MY[] = B"001"; -- autorefresh WHEN 7 => TAB[] = 8; MY[] = B"001"; -- autorefresh -- cycle commands (realy 5 items) WHEN 8 => TAB[] = 4; MY[] = B"011"; -- bank active -- ! words count (0->64) WHEN 9 => TAB[] = 0; MY[] = (B"10",R/W); -- bank read/write WHEN 10 => TAB[] = 4; MY[] = B"110"; -- burst stop! WHEN 11 => TAB[] = 4; MY[] = B"010"; -- bank precharge WHEN 12 => TAB[] = 8; MY[] = B"001"; -- autorefresh WHEN 13 => TAB[] = 4; MY[] = B"111"; -- NOP no executed WHEN 14 => TAB[] = 4; MY[] = B"111"; -- NOP no executed WHEN 15 => TAB[] = 4; MY[] = B"111"; -- NOP no executed END CASE; MCLK = TRI(LCELL(!CLKs),VCC); -- address MUX PA = DFF(!(CT[2..0] == 0),CLK,,); MX[].clk = CLK; CASE (CT3,PA) IS WHEN 0 => MX[] = (B"010000000000"); -- precharge all WHEN 1 => MX[] = (B"000000110111"); -- SDRAM mode WHEN 2 => MX[] = (ARG[21..10]); -- adress RAS -- 4k WHEN 3 => MX[] = (B"00",ARG[9..0]); -- adress CAS -- 1k END CASE; -- input register MDR[].clk = CLK; MDR[].d = DI[]; -- WRITE_2 = (DFF(DFF(DFF(WRITE,CLK,,),CLK,,),CLK,,)); WRITE_2 = DFF(DFF(WRITE or DFF(WRITE,CLK,,),CLK,,),CLK,,); -- WRITE_2 = DFF(WRITE,CLK,,); FOR i IN 0 TO WIDTH-1 GENERATE MD[i] = TRI(MDR[i],WRITE_2); END GENERATE; -- output register' -- for 1/2 shift -- MDRX[].clk = !CLK; -- MDRX[].clk = !LCELL(CLK); MDRX[].clk = MCLK; MDRX[].d = MD[]; -- output register MDRY[].clk = CLK; IF (OUT_SH == "YES") GENERATE MDRY[].d = MDRX[]; -- 1/2 clk data shift ELSE GENERATE MDRY[].d = MD[]; -- no 1/2 clk data shift END GENERATE; DO[] = MDRY[]; -- IF (M_REG == "YES") GENERATE -- MA[] = RX_MA[13..0]; ---- MCKE = RX_MCKE; -- MCKE = VCC; -- MBS[1..0] = RX_MBS[1..0]; -- MCS = RX_MCS; -- ---- MRAS = RX_MRAS; ---- MCAS = RX_MCAS; ---- MWE = RX_MWE; -- -- MRAS = DFF(DFF(RX_MRAS,CLK,,),CLK,,); -- MCAS = DFF(DFF(RX_MCAS,CLK,,),CLK,,); -- MWE = DFF(DFF(RX_MWE,CLK,,),CLK,,); -- -- MDQM = GND; -- ELSE GENERATE MA[] = MX[]; -- (MDQM,MCKE,MRAS,MCAS,MWE,MBS1,MBS0) = (GND,VCC,MY[5..3],ARG[23..22]); (MDQM,MCKE,MRAS,MCAS,MWE,MBS1,MBS0) = (GND,VCC,RX_MRAS,RX_MCAS,RX_MWE,ARG[23..22]); -- RX_MRAS,RX_MCAS,RX_MWE MCS = DFF((!(CTT[] == 1)),CLK,,); -- END GENERATE; -- (MDQM,MCKE,MRAS,MCAS,MWE,MBS1,MBS0) = (GND,VCC,MY[5..3],ARG[23..22]); -- RX_MA[13..0]= MX[]; -- RX_MCKE = VCC; -- RX_MBS[1..0]= ARG[23..22]; -- -- RX_MA[13..0].clk = CLK; -- RX_MCKE.clk = CLK; -- RX_MBS[1..0].clk = CLK; -- -- RX_MCS = DFF((!(CTT[] == 1)),CLK,,); RX_MCS.clk = CLK; -- RX_MRAS = MY5; RX_MRAS.clk = CLK; RX_MCAS = MY4; RX_MCAS.clk = CLK; RX_MWE = MY3; RX_MWE.clk = CLK; -- return signals -- write cycle -- WRITE = DFFE((MY[5..3] == B"100"),CLK,,,CTT_3); WRITE = DFFE((MY[5..3] == B"100"),CLK,,,CTT_4); -- mem cycle MEM_C = DFFE((MY[5..3] == B"001"),CLK,,,VCC); -- MEM_C = PA; -- read sysle READ = DFFE(((RWC_FIX[] == B"010") & (MY[5..3] == B"101")),CLK,,,CTT_3); -- data valid VALID = DFF(DFF(DFF(DFF(DFF(READ,CLK,,),CLK,,),CLK,,),CLK,,),CLK,,); END; Проверялся в работе на реальном проекте на Cyclone-II с рабочей частотой до 150MHz |
Автор: | WingLion [ Чт апр 22, 2010 20:11 ] |
Заголовок сообщения: | Re: Простой контролер SD-RAM на AHDL |
Вот так примерно должна выглядеть картинка симуляции для контроллера SD-RAM: А это в увеличенном виде - как должно выглядеть соотношение MCLK и MCS: к первой картинке: Сначала, в районе 820ns идет процедура инициализации после включения питания: - цикл "предзаряда" (освобождение/сброс банков); - запись управляющего слова; - затем несколько циклов регенерации. после этого SD-RAM готова к работе здесь эта работа показана в виде цикла чтения пакета (из 64) слов и цикла записи пакета слов. Для режима чтения/записи по одному слову контроллер надо существенно перекапывать. Но для этого может оказаться проще использовать готовый Альтеровский контроллер SD-RAM, который сейчас раздается просто так вместе с последней версией Quartus-II |
Автор: | LasyUser [ Пн авг 23, 2010 17:27 ] |
Заголовок сообщения: | Re: Простой контролер SD-RAM на AHDL |
... мои познания в области ПЛИС невелики - немного поделок на WinCupl и MaxPlus. Есть пару десятков корпусов DRAM типа 256Kx4, 256Kx16 - подскажите хватит ли ресурсов какого-нибудь ATF1502, ATF1504 чтобы слепить на нем контроллер регенерации? |
Автор: | WingLion [ Пн авг 23, 2010 18:53 ] |
Заголовок сообщения: | Re: Простой контролер SD-RAM на AHDL |
LasyUser писал(а): одскажите хватит ли ресурсов какого-нибудь ATF1502, ATF1504 чтобы слепить на нем контроллер регенерации? Я с этими ПЛИС не работал, потому не смогу подсказать точно. Хотя, для контроллера регенерации (если не включать в него мультиплексор адресов) должно по идее хватить любой современной ПЛИС. |
Автор: | LasyUser [ Пн авг 23, 2010 20:03 ] |
Заголовок сообщения: | Re: Простой контролер SD-RAM на AHDL |
ATF1502, ATF1504 это Atmel-овские аналоги EPM7032, EPM7064 Alter-ы, только стоят раза в 2 дешевле. После того как что-нибудь "сваяешь" в MaxPlus, остается "скормить" *.pof-файл утилите pof2jed.exe и можно заливать jed-файл в Atmel. |
Автор: | Ronin [ Вт авг 24, 2010 10:11 ] |
Заголовок сообщения: | Re: Простой контролер SD-RAM на AHDL |
LasyUser писал(а): DRAM типа 256Kx4, 256Kx16 ... контроллер регенерации? с 99.99% вероятностью эти чипы поддерживают режим автоматической регенерации (со встроенным счётчиком) CAS Before RAS, т.о. остаётся только в свободные от доступа хоста промежутки времени формировать соответствующий цикл, для чего 7032 более чем избыточна )) |
Автор: | Hishnik [ Вт авг 24, 2010 19:12 ] |
Заголовок сообщения: | Re: Простой контролер SD-RAM на AHDL |
Судя по объему памяти, эти чипы (part number?) вполне могут попадать в оставшиеся 0.01% |
Автор: | WingLion [ Вт авг 24, 2010 21:00 ] |
Заголовок сообщения: | Re: Простой контролер SD-RAM на AHDL |
Хищник писал(а): Судя по объему памяти, эти чипы (part number?) вполне могут попадать в оставшиеся 0.01% Врядли. Режим регенерации "CAS перед RAS" работал и в советских 565РУ7 (256Кx1). |
Автор: | Hishnik [ Вт авг 24, 2010 21:09 ] |
Заголовок сообщения: | Re: Простой контролер SD-RAM на AHDL |
А в РУ5 я этого не помню, в Z80 был специальный выход, чтобы на регенерацию переключаться. |
Автор: | WingLion [ Вт авг 24, 2010 21:36 ] |
Заголовок сообщения: | Re: Простой контролер SD-RAM на AHDL |
В РУ5-х режима регенерации по "CAS перед RAS" и не было, для них надо было все столбцы "ручками перебирать" - в смысле отдельным счетчиком. В Z80 для этого есть регистр R, но он годится только для регенерации микросхем с организацией 16Kx1, потому что перебирает только 128 столбцов. |
Страница 1 из 2 | Часовой пояс: UTC + 3 часа [ Летнее время ] |
Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group http://www.phpbb.com/ |