Add to your testbench a monitor process that watches the output and compares it to the expected value, allowing for the delays through the filter.
Your VHDL style is better than some - even better than some textbook examples I have seen, but still: a few comments :
Using named rather than positional assignment for the "dff"
component instantiations would save possible confusion between inputs
and outputs for anyone trying to follow the pipeline. This doesn't
really matter here, because :
you can eliminate the dffs altogether; replace them with lines
of the form Q1 <= MCM3;
in the same clocked process as Yout <=
add_out3;
that greatly simplifies the whole filter.
You can reduce number of conversion functions by making H0..3 integer types; and if they are constant, make them constants! As multiplication between signed and integer is defined,no other changes are required.
type coefficient is new integer range -128 .. 127;
constant H0 : coefficient := -2;
Lose the redundant parentheses in if ( rising_edge(Clk) ) then
- this isn't C!
The DRY principle applies in VHDL too... there are several ways to apply it to the testbench : my choice would be a local procedure.
stim_proc: process
procedure Input(D : in integer range -128 .. 127) is
begin
Xin <= to_signed(D,8);
wait for clk_period*1;
end Input;
begin
wait for Clk_period*2;
Input(-3);
Input( 1);
The output of a register whose input does not change within a specified margin of the clock will switch within a specified period of time of the clock. The output of a register whose input changes too close to a clock may change at some arbitrary time in future which might, though is generally not likely to, be near the next clock.
If a register's input is derived from signals that are all clocked by the same signal as the register itself, and if the maximum propagation time is sufficiently shorter than the time between clocks, then provided the earlier registers switch as specified, the derived input will not change within the forbidden window. If the maximum propagation time is longer than the time between clocks, however, a bad situation will arise. When latching truly asynchronous events, it's possible that events may occasionally put a latch into a metastable state, but feeding the output from that latch into a second latch will usually clear things up. If the first latch goes into a metastable state about once a minute, and one in ten million metastability events on the first latch will cause the second latch to go metastable, problems on the second latch will only occur about once every twenty years. If rather than being asynchronous, however, the signals arriving at a latch switch at times which combinatorial logic delays by a time close to a clock period, it's possible that rather the first latch going metastable once a minute, it may go metastable millions of times per second. Adding a second latch may improve things, but even a with 10,000,000:1 improvement the downstream latch would still go metastable many times per minute.
If your propagation time is too long relative to your clock period, you need to either add registers to ensure that the propagated result will be consistently seen some number of clock periods after the earlier-stage latches change, or else add logic to ensure that nothing will do anything with the output from a register which may have gone metastable. The former approach would be better if one wishes to handle one data item per clock cycle but can accept the pipeline delay. The latter approach may be better if there's lots of parallel data and it won't be necessary to have multiple calculations in the pipe simultaneously [the amount of logic required would be independent of the number of data paths]. The latter approach may be especially advantageous if the required number of delay cycles may be variable [e.g. if a circuit may operate at 100MHz, 50Mhz, or 32MHz and the logic's propagation time is 25ns, one may use a two-cycle delay at 100Mhz, a one cycle at 50MHz, and no delay at 32Mhz or below].
Best Answer
No they aren't.
They are imported from
work.amba
andvendorname.amba
. Theall
in the use clauses simply pollutes your namespace with everything in both of those libraries.So, don't do that.
Instead, use fully qualified names
and the two signals will coexist quite happily. Note they are completely different types, so you'll probably have to write type conversion functions between them if they should ever meet.
If most of your code involves the Work library with a few rare exceptions from the other, then you can happily
use work.amba.all;
to reduce the number of fully qualified names, only using them for the other library.