Forum Discussion
Different results on hardware compared to simulator
I'm having trouble when I run my code on the actual Cyclone III FPGA. In the simulator it works fine. I have set up state machines to make sure that clock signals to registers are occurring after plenty of data setup time has passed. I'm running the chip with just a 14 MHz clock so its not very fast.
In ModelSim everything works perfectly. My code is modular so I am building up the final code one module at a time. I can put in several modules, test, and everything works as expected. But at some point when I add in another module everything starts to go wrong. Modules that worked earlier no longer work. I added in some ports on the modules to bring out the data to some external LEDS so I can see what the signals are doing. Often that causes the code to just start working again properly. The results are very inconsistent as I make changes to the code. What am I missing here that makes the code work incorrectly on the actual hardware?25 Replies
- Altera_Forum
Honored Contributor
--- Quote Start --- What am I missing here that makes the code work incorrectly on the actual hardware? --- Quote End --- Missing synchronization logic between clock domains? Missing reset synchronizer logic. Timing constraints? Does Quartus warn you about anything? Make sure all synthesis warning messages are resolved. Does TimeQuest indicate all timing is met? Rather than using LEDs to probe your design, use SignalTap II - this logic analyzer allows you to see much more of the internals of the design. Cheers, Dave - Altera_Forum
Honored Contributor
Its a single clock domain. I am using a reset synchronizer design that was recommended by Altera (reset does not appear to be the problem). As far as warnings, I have warnings about objects that are assigned but never read (features not yet implemented).
I have some "inferring latches for variable ... which holds its previous value in one or more paths through the always construct". I have some bits that I'm not using yet which have no driver (using default initial value of 0) I have some Tri-state nodes which do not directly drive top level pins. In my internal modules there are some bi-directional busses, which is why there are tri-states that don't drive the outside world. Clock multiplexers found and protected. All the warnings seem non-consequential to me. I have not done timing. Since the chip is running at such a slow clock rate (14 MHz, about 70 ns period) and I am setting up data and then waiting at least one clock cycle before I clock it into the next register I thought there would be no problem with that. Could it be that I need to provide more setup time? Delay it another clock cycle? At this point SignalTap would be difficult because I don't have access to the JTAG port without hacking the board (a flaw which I will correct on the board in the future). - Altera_Forum
Honored Contributor
--- Quote Start --- I have not done timing. Since the chip is running at such a slow clock rate (14 MHz, about 70 ns period) --- Quote End --- Try including a minimal .sdc file, eg., here's one I've copied and then edited to reflect your clock, edit the port name for the clock, and then edit the names of the reset and outputs that you do not care about (with regards to meeting clock-to-output delays):
The latch warning is also a worry. Fix your logic so that registers are used, not latches. --- Quote Start --- At this point SignalTap would be difficult because I don't have access to the JTAG port without hacking the board (a flaw which I will correct on the board in the future). --- Quote End --- Lesson learned then, eh :) Cheers, Dave# -----------------------------------------------------------------# Clock# -----------------------------------------------------------------# # 14MHz clock (70ns period) set clk_period 70 # External clock (internal logic clock) set clk clkin_14MHz create_clock -period $clk_period -name $clk # -----------------------------------------------------------------# Cut timing paths# -----------------------------------------------------------------# # The timing for the I/Os in this design is arbitrary, so cut all# paths to the I/Os, even the ones that are used in the design,# i.e., reset and the LEDs.# # External asynchronous reset set_false_path -from -to * # LED output path set_false_path -from * -to - Altera_Forum
Honored Contributor
I did try setting up timing yesterday and used the wizard to generate an sdc file. It looks much like what you sent me, but with a couple of different set_false_path statements that I don't fully understand:
TimeQuest does not indicate any failures. I will work on the latches. Also I see there is a new version 12.0 SP1 for Quartus. I'm going to download and try that.set_false_path -from -to set_false_path -from -to - Altera_Forum
Honored Contributor
I was able to eliminate the latch warnings. Code running on the hardware is still working illogically (or rather not working).
Is this warning a real concern: Warning (13004): Presettable and clearable registers converted to equivalent circuits with latches. Registers power-up to an undefined state, and DEVCLRn places the registers in an undefined state. I eliminated this warning on a couple of registers at a lower level. Should I pursue this more? I also get a bunch of warnings in the timing analysis of this type: Warning (332060): Node: uart:rs485_port|baud_clk[0] was determined to be a clock but was found without an associated clock assignment. It seems to occur for every signal that is used as an edge trigger to a always_ff block, like this: always_ff @ (posedge reset_n, posedge baud_clk[0]) begin blah,.... end In that particular example the baud_clk is a 4 bit counter that is just being clocked by the main system clock (after it goes through another counter I use for deriving the desired baud rate * 16). Is there a quick and easy way to set up the timing analysis so that it checks things properly? - Altera_Forum
Honored Contributor
--- Quote Start --- I was able to eliminate the latch warnings. Code running on the hardware is still working illogically (or rather not working). Is this warning a real concern: Warning (13004): Presettable and clearable registers converted to equivalent circuits with latches. Registers power-up to an undefined state, and DEVCLRn places the registers in an undefined state. I eliminated this warning on a couple of registers at a lower level. Should I pursue this more? --- Quote End --- I've never seen this one, so I suspect your code is just not particular synthesizeable. Create a minimal code example that generates this error, and post it, or just post the section of code you're getting the error with, and members of the forum can review it. --- Quote Start --- I also get a bunch of warnings in the timing analysis of this type: Warning (332060): Node: uart:rs485_port|baud_clk[0] was determined to be a clock but was found without an associated clock assignment. It seems to occur for every signal that is used as an edge trigger to a always_ff block, like this: always_ff @ (posedge reset_n, posedge baud_clk[0]) begin blah,.... end --- Quote End --- Right, all 'clocks' need clock constraints. What you want for this one, is the create_generated_clock constraint. Alternatively, you could code your UART to operate at the FPGA clock frequency, and use the baud-rate divider as an enable to that logic. The code ultimately works the same, however, there's one less clock ... but the logic has to operate at a faster clock rate ... Nothing comes for free :) Older generation FPGAs did not have PLLs and could not route logic element outputs back into the clock network, so your only coding option was to use enable pulses. In your case, creating a slow clock for the UART is fine, you just need to use create_generated_clock to tell TimeQuest the characteristics of that clock. --- Quote Start --- Is there a quick and easy way to set up the timing analysis so that it checks things properly? --- Quote End --- Not so much 'quick and easy', but you can set it up to properly analyze the timing. The way you are doing it is fine, i.e., iteratively ... synthesize -> look at warnings -> add constraints -> repeat Where you repeat until there are no warnings, or at least until you understand why the warnings are occurring and that they can be ignored, eg., signal assigned a value that is not read, and warnings like that. Cheers, Dave - Altera_Forum
Honored Contributor
This will be because the registers in the cyclone III have no asynchronous set and preset inputs, unlike earlier chips. So this behavious has to be emulated.
I suspect the problem is nothing to do with timing exactly, but poor design practice in the source code. If latches are being created then the problem will be timing issues that occur with such designs that cannot be looked at with time quest. Latches and asynchronous logic will also make the design unreliable and suseptable to temperature variations. - Altera_Forum
Honored Contributor
The set_false_path constraints look like they're for a DCFIFO.
- Altera_Forum
Honored Contributor
--- Quote Start --- I have some "inferring latches for variable ... which holds its previous value in one or more paths through the always construct". --- Quote End --- Don't use latches. --- Quote Start --- I have some Tri-state nodes which do not directly drive top level pins. In my internal modules there are some bi-directional busses, which is why there are tri-states that don't drive the outside world. --- Quote End --- There's no tri-state functionaltiy in the FPGA so why code as if there is and rely on the tools 'fixing' things for you? Convert to multiple busses, one for each Tx point. --- Quote Start --- Clock multiplexers found and protected. --- Quote End --- If you're using a single clock domain why is it being multiplexed? Use clock enables instead! --- Quote Start --- I am setting up data and then waiting at least one clock cycle before I clock it into the next register --- Quote End --- That isn't the usual approach for synchronous design. If you're using the same clock to launch and capture signals and the tools know how fast the clock is things _should_ work. (You can have multi-cycle paths but that's the exception rather than rule). You're not doing board design, let the tools worry about timing while you worry about finctionality. Can you get some input from an experienced FPGA designer? When you've seen how things should be done (no latches, proper synchronous process templates, clock enables etc) it's much easier to get things working. As long as you're getting signals into and out of the FPGA OK your simulation results should match real world results. I hope this helps a bit, Nial. - Altera_Forum
Honored Contributor
I have eliminated the latches.
I'm a bit puzzled about your comment about not using tristate nodes inside the design. I am trying to implement bi-directional data busses. Of course at the ports of the device that is required to interface with a multiplexed address/data bus. But inside when communicating with the modules are you suggesting that it would be better to implement it as data_input bus and data_output bus? Keep them separate (which doubles the interface pins for the data between modules). I can do that if you believe that is a recommended better practice. Clock multiplexers are created by the synthesis, I did not code them. Its probably because I have so many different registers being clocked by the main input clock, but I don't really know. When I talked about setting up data and clocking it one cycle later I was not referring to coding it down at the lowest registers. I meant that I have data coming in that is enabled by an external write signal. The rising edge of that write signal should clock the data into an input register. Then internally I need to decode that data (it can be an address). So to give the decode logic time to operate I wait one clock cycle then clock it into the internal register where I need to put it. I assume that you cannot expect to clock data, decode it with comb logic and then clock it into a final register all at the same external clock edge. So thats why I created state machines to sequence the logic in a well defined manner. Am I wrong in this? I wish I had an experienced FPGA designer around. We are a very small startup company and I do all the hardware engineering and just got my first FPGA boards back about 3 weeks ago. I have a design that needs to get shipped by the end of this weekend so I'm up against a real time pressure to figure this out. This is actually the second FPGA design. The first one I did a week ago and got it working but I cannot predict what happens when I make a small change in the logic. I know now that its because I did not do the timing and that affects the fitter results tremendously. So, here I am learning timing.