Electronic – Altera’s DRAM Controller with UniPHY

intel-fpgaquartus-ii

I am trying to port a design from Xilinx to Altera, and I have issues with the DRAM controller IP (for a Cyclone-V and a LPDDR2 mem).

I have managed to generate the IP, but I don't understand which clock should be used for the Avalon-MM interface.

I have looked at a sample design which uses Qsys, the avl_0 bus is marked with associated clock = mp_cmd_clk0, not the clock used by the NIOSII CPU, which is pll_ref_clock used by the memory controller's PLL.

As my design only uses VHDL, no NIOS nor any other Altera IP, I would like to avoid Qsys for wiring the blocks together.

So :

  • What is the reference clock for the Avalon bus ? pll_ref_clk, afi_clk, afi_half_clk, something else ?

  • Can I choose the frequency, or is it a fixed ratio based on the DRAM datarate, the bus width ?

(As comparison, the Xilinx MIG DRAM controller has internal FIFOs, clocks are inputs and can have any frequency)


EDIT

I have eventually found some relevant information.

https://www.altera.com/literature/hb/external-memory/emi.pdf (10MB !)

Volume III, Chapter 4 : Hard Memory Interface.

The Avalon bus[ses] are managed by the "Multi-Port Front End (MPFE)"

The Avalon busses are associated with the mp_cmd_xxx_clk, mp_rfifo_xxx_clk, mp_wfifo_xxx_clk signals, and there is some internal resynchronisation in the memory controller so that any clock can be used :
"The MPFE handles the clock crossing between user logic and the hard memory interface."

Not all Altera FPGA families seems to have that feature available, or they use different controllers. This Altera DRAM controller for Cyclone V has finally very similar features to the Xilinx MIG IP.

Best Answer

The clocks are used as follows:

pll_ref_clk = The clock which is fed in to the input of the PLL. This has to match whatever setting you have in the IP core so that the correct memory clock frequency will be generated.

afi_clk = This is the clock used for the Avalon-MM interface. There is a corresponding reset signal afi_reset which is synchronous (on Deassert I think) with afi_clk.

afi_half_clk = This is optional and is enabled by a parameter on the IP core. Basically this is a clock synchronous to afi_clk but at half the frequency.

So when you are interfacing the Avalon-MM interface you should be using the afi_clk for your logic.


The frequency of the clocks is dependent on your IP core settings. Basically you specify the memory frequency which is the clock speed used for the physical memory. There is then a parameter which allows you to select a mode of operation for the Avalon-MM interface. You have the following options:

Full Rate = The Avalon-MM interface operates at the same frequency as the memory. For DDR RAM, you have data clocked on both edges, but internally you cannot do that, so to achieve the same data rate, the output interface is twice the width of the memory.

Half Rate = The clock frequency of the Avalon-MM interface is half the frequency of the memory. Consequently the output interface is now quadruple the width of the memory.

Quarter Rate = You get the pattern by now. Quarter the clock frequency, so data width is 8 times the width of the memory.

These different rate settings allow you to run the memory much faster than the core logic of the FPGA can run at (the periphery of the FPGA is much faster than the core). So for example you can have a 32bit 800MHz DDR chip which presents itself internally as a 200MHz 256bit wide data bus.


As to why they were using the PLL reference clock for the Nios processor in the reference design, who knows. There are many little mistakes here and there that you will find with the documentation and example designs from Altera.