10.1. Component Fails Only In Simulation
Comparing Floating Point Results
Use an epsilon when comparing floating point value results in the testbench. Floating points results from the RTL hardware are different from the x86 emulation flow.
Using #pragma ivdep to Ignore Memory Dependencies
The #pragma ivdep compiler pragma can cause functional incorrectness in your component if your component has a memory dependency that you attempted to ignore with the pragma. You can try to use the safelen modifier to control how many memory accesses that you can permit before a memory dependency occurs.
See Loop-Carried Dependencies (ivdep Pragma) in Intel® High Level Synthesis Compiler Pro Edition Reference Manual for a description of this pragma.
To see an example of using the ivdep pragma, review the tutorial in <quartus_installdir>/hls/examples/tutorials/best_practices/loop_memory_dependency.
Check for Uninitialized Variables
Many coding practices can result in behavior that is undefined by the C++ specification. Sometimes this undefined behavior works one way in emulation and a different way in simulation.
A common example of this situation occurs when your design reads from uninitialized variables, especially uninitialized struct variables.
Check your code for uninitialized values with the -Wuninitialized compiler flag, or debug your emulation testbench with the valgrind debugging tool. The -Wuninitialized compiler flag does not show uninitialized struct variables.
You can also check for misbehaving variables by using one or more stream interfaces as debug streams. You can add one or more ihc::stream_out interfaces to your component to have the component write out its internal state variables as it executes. By comparing the output of the emulation flow and the simulation flow, you can see where the RTL behavior diverges from the emulator behavior.
Non-blocking Stream Accesses
The emulation model of tryRead() is not cycle-accurate, so the behavior of tryRead() might differ between emulation and simulation.
If you have a non-blocking stream access (for example, tryRead()) from a stream with a FIFO (that is, the ihc::buffer<> template parameter), then the first few iterations of tryRead() might return false in simulation, but return true in emulation.
In this case, invoke your component a few extra times from the testbench to guarantee that it consumes all data in the stream. These extra invocations should not cause functional problems because tryRead() returns false.
Invoking Component With ihc_hls_enqueue() Or ihc_hls_enqueue_noret()
If you invoke your component with ihc_hls_enqueue() Or ihc_hls_enqueue_noret(), ensure that you are also calling ihc_hls_component_run_all().
If you do not call ihc_hls_component_run_all(), simulation of your component fails.
Did you find the information on this page useful?