Forum Discussion

Altera_Forum's avatar
Altera_Forum
Icon for Honored Contributor rankHonored Contributor
15 years ago

Dual port RAM shared between Nios and async interface

Hi all,

I want to upgrade an existing system and I wonder if anyone can give me hints.

I have a board with CIII device with Nios and an external Analog Device DSP: both Nios and DSP need to access a shared memory, which is FPGA onchip RAM.

The current (working) implementation is:

- sopc system with Nios and tristate bus

- external lpm ram component in dual port mode.

- Nios accesses ram through tristate bus

- dsp accesses directly to the ram through its Async Memory Interface

I'd like to eliminate the tristate bus and integrate the ram in sopc system, so that Nios can access it directly with Avalon bus.

I think I can do it by defining a new onchip ram component and exporting signals of one port; I found something similar in another thread.

But I think I'd also need some glue logic to connect to dsp AMI.

Question 1: is this way of operation viable? is there a better solution?

Question 2: is such sopc component already available anywhere?

Thank you

Regards

20 Replies

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Hi, I did not want to create a new thread because I have a very similar problem with my dual port RAM which is shared between NIOS and my async interface. Please let me know if I need to create another thread.

    First, I am using Quartus II 9.0 SP2 with a CIII device with Nios. I currently need the Nios to write data into a dpram and then my verilog logic block to access the ram to read the data in a different clock domain.

    The current (working) implementation was:

    - sopc system with Nios and pio bus

    - external lpm ram component in dual port mode.

    - Nios accesses ram through pio bus

    - my verilog logic will access the external lpm ram directly to read.

    To have a cleaner solution, I'd like the Nios to access the dpram directly with Avalon bus.

    Following this thread, I added a new onchip ram component with dual-port enabled from SOPC builder. Then using the "new component", I used the conduit to export all I/Os of one port and connected the other port to all "avalon_slave" (clk was to clk_sink). I did not add a avalon master because I still do not understand how that plays a role.

    Then, I had to tie these pins at the SOPC block diagram:

    inputs

    address2_to_the_dual_port_ram_0[10:0] = verilog logic addr output

    byteenable2_to_the_dual_port_ram_0[3:0] = pulled high

    chipselect2_to_the_dual_port_ram_0 = pulled high

    clk2_to_the_dual_port_ram_0 = clk

    clken2_to_the_dual_port_ram_0 = pulled high

    write2_to_the_dual_port_ram_0 = pulled low

    writedata2_to_the_dual_port_ram_0[31..0] = pulled low

    outputs

    readdata2_from_the_dual_port_ram_0[31..0] = verilog logic read data input

    After compilation, I created a new NIOS project and tried to write 0xAB to the ram.

    int a;

    IOWR(DUAL_PORT_RAM_0_BASE, 0, 0xAB);

    a = IORD(DUAL_PORT_RAM_0_BASE, 0);

    In debug mode, "int a" is always 0.

    I must be missing something. Attached is my .v and .tcl files.

    PS, I also tried adding a new on-chip ram component with only single port to see if I could just write to it. But during NIOS initialization through JTAG, the processor paused with an error. I am not sure why.
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    The read latency of the slave port that you connected to the CPU is wrong in the .tcl file:

    "set_interface_property avalon_slave_0 readLatency 0"

    Based on the verilog parameterization of the memory you should set that read latency to 1. There is a input register stage inside the RAM block and the output is not registered so it so the total read latency is 1 for this setup.

    By the way if you used Qsys you wouldn't need to do all this stuff to expose one of slave ports of the memory to the top level, you would just click on the 2nd slave port and tell Qsys to export it.
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Ahhhh I see the problem. In the verilog file the first clock enable is not getting hooked up (clock enable isn't part of the Avalon specification). Quartus II grounds disconnected inputs so the memory port had it's clock enable stuck low. The simple fix would be change this line (it's the comment line because that's what actually gets synthesized):

    // .clocken0 (clken),

    to

    // .clocken0 (1'b1),

    Since you generated this verilog from SOPC Builder I'm not sure what it did with that clock enable. I have been using SOPC Builder since it was first released and I don't remember clock enable being part of the Avalon-MM specification so there must have been an extra layer of extraction involved. Also it probably would be cleaner to just write verilog by hand than use machine generated code. Signals like chip select and clock enable are not necessary signals so you could have left them out if you coded the file by hand.
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Thank you so much. It all works now; I never would have thought that "the commented clk_en" to be the issue. You have made my day. Thanks!

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    You are welcome. Also as a heads up I discourage people from using the synthesis translate on/off attributes in verilog/VHDL. That is what causes the comment lines from being used as the synthesis source, so I don't recommend doing that because it's confusing. When you write your HDL if you want to have seperate synthesis and simulation code I would split those out into two file sets instead, this is much cleaner in Qsys as well.

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    The nios tightly coupled data interface does use the clock enable signal (to hold the read data from the previous address when the cycle before that stalls the cpu on an avalon tranfser).

    So there is some lurking support for it in sopc/qsys.

    Using the clock enable also stops sopc from selecting single clock mode, whereupon it silently ignores the OLDDATA flag.

    (In single clock mode 'clock enable' is replaced with the inverted 'address hold').

    The fact that the commented out lines of all the sopc generated files are the ones that are used is somewhat confusing - caused us much confusion.
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    --- Quote Start ---

    The fact that the commented out lines of all the sopc generated files are the ones that are used is somewhat confusing - caused us much confusion.

    --- Quote End ---

    Thanks for the heads up. I have not tried qsys yet. But for future reference, do all qsys generated files use commented out lines as well?
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Altera is moving away from that so I wouldn't expect many or any Qsys components to use the synthesis translate on/off functionality. Qsys generates synthesis and simualtion files into seperate directories which is a much cleaner approach.

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    After reading this post and other related posts I decided to stay away from using Dual port RAM shared between Nios and async interface in QSYS.

    If not for BadOmen's advice, then You never know what could be the problem.

    To start with I decided to try this reliable approach:

    --- Quote Start ---

    The current (working) implementation was:

    - sopc system with Nios and pio bus

    - external lpm ram component in dual port mode.

    - Nios accesses ram through pio bus

    --- Quote End ---

    To learn how to do it correctly from the start I would like to learn the way You did it although it might seem simple.

    Would You please publish it?