- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
I have a design where my data bus is tri-stated and everything seems to work correctly till the tri-state buffer. For some reason the output of the tri-state buffer is delayed by a clock from the input ? Could there be some Quartus setting that might be doing this ?
Link Copied
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
You don't say what version of Quartus or even what device you are using. Or if your tr-state bus is on chip or off chip.
That being said, physically any FPGA I am aware of does not have a true on-chip tri-state bus per se, but it is implemented with logic and multiplexors.
So logically your Verilog/VHDL may be written as a tri-state bus, but during synthesis it is turned into logic, specifically an N:1 multiplexor for the driver function.
Depending on how wide your N:1 mux is (ie, number of discrete source drivers) and how fast your clock rate is, it might just be the logic delay is longer than a clock cycle.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
We are using Quartus 15.1. FPGA: Cyclone V GX (5CGXFC4F7M11I7) and the 32 bit tri-state bus is implemented on chip and is created by a simple standard VHDL code that is instantiated in my top level design. The output of the tri-state buffer feeds directly into the bi-directional data bus. The bi-directional bus is also feed back into the design where it is clocked\latched along with the control signals to catch the read data for the read cycle process. Note my clock is 100Mhz !
Your answer that the tri-state bus in synthesis is turned into N:1 multiplexor is interesting. Besides shifting my data earlier by a clock - is there anything else I can do to fix this ?
Also this current design is based upon an earlier design from a different chip (Cyclone V 5CEFA7U19I7N) where this issue was not seen ????
I looked at the RTL of the design and a very clear straight forward tri-state buffer was created as expected. Is there another level for synthesis that changes this tri-state buffer into the N:1 multiplexor that you mentioned ? Is there anyway to view this ?
Thank you once again for all your help
Shmuel Davis
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Hello,
I presume, Technology Map Viewer shows the gate level implementation.
By the way, now you are talking about clock, previously it sounds like the "delay" occors in pure combinational circuit. It's probably better to show an exact implementation.
Regards
Frank
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Thanks for your reply,
So below is the VHDL code at the upper level
Signal usbDmuxOUT, usbDreadSMout_withbufferedZEROES :std_logic_vector(31 downto 0);
.....
usbDreadSMout is my "read cycle" output data from an internal state machine defined as :-
usbDreadSMout :out std_logic_vector(7 downto 0);
......
usbDreadCYCLEchanSELen is my open enable for usbDreadSMout from the same internal state machine
......
usbDWRSMout is my "write cycle" output data from an internal state machine defined as :-
usbDWRSMout :out std_logic_vector(31 downto 0);
......
usbDen is my open enable for usbDWRSMout from the same internal state machine
My Bi-directional bus USBD [ usbDWRSMout :out std_logic_vector(31 downto 0); ] is implemented as follows :-
usbDreadSMout_withbufferedZEROES(7 downto 0) <= usbDreadSMout; -- DEBUG USB429
usbDreadSMout_withbufferedZEROES(31 downto
usbDmuxOUT <= usbDreadSMout_withbufferedZEROES when usbDreadCYCLEchanSELen = '1' else usbDWRSMout; -- DEBUG USB429
USBD <= usbDmuxOUT when usbDen = '1' or usbDreadCYCLEchanSELen = '1' else (others => 'Z');
Below I have attached the RTL implementation of the above
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Below I have added a shot of the Technology Map Viewer and in fact there does appear to be a latch on the usbDmuxOUT signals for some reason ???
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
And in fact when I clicked on one of these Latches and asked for its location in the RTL view I in fact got the following
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Registers may be shifted forth and back along the data path during synthesis, but without changing the logic function or latency.
After seeing the RTL and technology map snippets, I wonder where registering has been originally demanded in the code, e.g. which assignments are clocked.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
If this "shifting" of registers back and forth along the data path during synthesis happens - I would understand if this was done with a known expected latch in the actual design. But as can be seen in the RTL the latching of the data occurs in the Write and Read state machine blocks ! After the data leaves these SM blocks - there are no other registers in the design !
Why does the Quartus Synthesizer add this additional latch to implement the tri state buffer AND is there any way to prevent the synthesizer from doing this ?
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Are you referencing actual clocked registers? Or latches?
Quartus can move registers around and can replicate and/or merge registers as it sees fit.
If you write some clocked logic equations where you inadvertently don't always assign a value to the output Quartus may infer a latch and insert it.
So be very specific in your terminology of register vs latch when describing your logic.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Sorry I was referring to the addition of a clocked register.
The problem can be seen clearly in the RTL representation attached : USB429 - usbD birectional output implementation - RTL.jpg
Where the Tri State buffer is connected directly to the output pin usbD[31..0]
Then in the Technology Map View shown in : USB429 - usbD birectional output implementation - Technology Map Viewer 1.jpg
and then expanded in : USB429 - usbD birectional output implementation - Technology Map Viewer 2.jpg
That a clocked register for some reason has been placed between my Mux and the Tri state buffer for some reason.
??????
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Hi,
The links below suggest some recommendations to Avoid Unintentional Latch Generation:
Thanks,
Best Regards,
Sheng
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Dear Sheng,
Thank you for your reply.
I looked at those posts and the only thing that I saw that seemed relevant to my design was "when CASE or IF statements do not cover all possible input conditions...". In my SM for both the read and write cycles I use a CASE statement and I added the code :-
when others =>
usbD <= (others => '0'); -- DEBUG USB429
end case;
However this didn't help, the clocked register shown in USB429 - usbD birectional output implementation - Technology Map Viewer 2.jpg above still exits and on the scope the output data is still delayed by 1 clock ?
Any other ideas ?
Best regards
shmuel
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Can you repost your code in a little bit easier to read format?
Clocked registers don't get magically added to a combinatorial design. There must be other code (an IP?) that has a clocked process that might be causing this.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
So I have attached a file that represents all the parts of my code that do the writes to the usbD bidirectional data bus.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Hi shmuel,
That clocked register is due to rising-edge triggered of clocked process. For example implementing a Rising Edge D Flip Flop check the code and technology map viewer images below:
If commented out if(rising_edge(Clk)) then, the clocked register is no more visible check images below:
In technology map viewer, at clocked register, you can Locate Node -> Locate in Design File
Thanks,
Best regards,
Sheng
p/s: If any answer from the community or Intel Support are helpful, please feel free to give best answer.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Hi shmuel,
I had compiled the code provided with both Quartus II 15.1 and Quartus Standard 22.1 and got the results below instead (image):
But one thing can be confirmed that clocked register is because of the clock rising-edge trigger condition in process block. For example, by commenting out the usbCLK'event (elsif usbCLK = '1' /*and usbCLK'event*/ then) in FT601niosWRITEsm. I'm getting the technology map viewer result changes below (image):
Before: After:
Thanks,
Best Regards,
Sheng
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Dear Sheng,
Thank you so much for all your help.
In the first image that you showed above, as you indicated, there is no register between Mux and the IO_OBUF as there is in my design shown in the image below
"But one thing can be confirmed that clocked register is because of the clock rising-edge trigger condition in process block. For example, by commenting out the usbCLK'event (elsif usbCLK = '1' /*and usbCLK'event*/ then) in FT601niosWRITEsm. I'm getting the technology map viewer result changes below (image)"
I see that from the Technology Map Viewer images that you show that the registers of the state machine have disappeared. However isn't this expected when you remove the clock from a clocked process that builds a statement machine - all the registers will be removed ? Also, the registers that disappeared are within the state machine block - it is not the register that I see that is implemented in the figure above associated with my tri state buffer ?
I expanded my Technology Map View of the write state machine as below and got the following :-
I am pretty sure that all the registers there will also disappear if I comment out the Clock in the clock process ?!
Bests regards
Shmuel
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Hi,
I just compiled the original code you provided and didn't make any change to the code (check previously attached test.qar). Then I got the first image result where there is no register between Mux and the IO_OBUF. (May be you have use usbDmuxOUT in any clock process and didn't provide that part of code I'm not sure)
By commenting out the usbCLK'event (elsif usbCLK = '1' /*and usbCLK'event*/ then) in FT601niosWRITEsm is just to show you that's possible to make the clocked register disappear.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Hi Shmuel,
Let me know if you have any further concern or consideration?
![](/skins/images/D3C0B914909A6564BBB97F4AD1ED1973/responsive_peak/images/icon_anonymous_message.png)
- Subscribe to RSS Feed
- Mark Topic as New
- Mark Topic as Read
- Float this Topic for Current User
- Bookmark
- Subscribe
- Printer Friendly Page