concurrent signal assignment: order can matter?

Discussion in 'VHDL' started by ralvarexo@googlemail.com, Dec 28, 2011.

  1. Guest

    Hi,

    until now I thought that with concurrent statements order does not matter. Then I wanted to demonstrate delta delay effects with several versions of an RS-FF.
    However, the simulator I use (Active HDL 8.3) produces different results for the following 3 versions:

    concurrent_1:
    qni <= not (s and qi);
    qi <= not (r and qni);

    concurrent_1:
    qi <= not (r and qni);
    qni <= not (s and qi);

    concurrent_3_with_process:
    process(s,qi)
    begin
    qni <= not (s and qi);
    end process;

    process(r, qni)
    begin
    qi <= not (r and qni);
    end process;

    I would have expected that all 3 versions fail when r and s are simultaneously change from 0 to 1.
    However, only the 3rd fails as expected, the other 2 are simulated without any warning, but different result - order matters!

    I was under the impression that a concurrent assignment is a short hand fora process with the same assigment AND all righthand signals in the sensitivity list. But according to the results it looks as if the assignments are evaluated/updated only once, i.e. no implied sensitivity list.

    While all 3 variants will produce the same HW during synthesis they behave in a different way during simulation. What is even more disturbing is that the order of concurrent statemenst matters during simulation, IMO negating the concept of delta delays.

    I am aware that the resulting HW will likely show some other behaviour (metastability) depending on the actual elements used, but this example was choosen to show the inner workings of the simulator.

    Is this behaviour of the simulator in accordance with the standard?

    Greetings,

    Mike
     
    , Dec 28, 2011
    #1
    1. Advertising

  2. KJ Guest

    On Dec 28, 3:27 pm, wrote:
    > While all 3 variants will produce the same HW during synthesis they behave in a different way during simulation. What is even more disturbing is that the order of concurrent statemenst matters during simulation, IMO negating the concept of delta delays.
    >
    > I am aware that the resulting HW will likely show some other behaviour (metastability) depending on the actual elements used, but this example was choosen to show the inner workings of the simulator.
    >
    > Is this behaviour of the simulator in accordance with the standard?
    >


    You might want to check that your simulator isn't reporting something
    after all. What I get when running your example on Modelsim is an
    infinite loop when R and S switch simultaneously. Below, I've also
    posted the full code.

    Kevin Jennings

    # Loading std.standard
    # Loading ieee.std_logic_1164(body)
    # Loading work.foo_sig_assignment(rtl)
    # ** Error: (vsim-3601) Iteration limit reached at time 1 ns.

    --- Start of code ---
    library ieee;
    use ieee.std_logic_1164.all;

    entity foo_sig_assignment is
    end foo_sig_assignment;

    architecture RTL of foo_sig_assignment is
    begin
    concurrent_1: block
    signal r: std_logic;
    signal s: std_logic;
    signal qi: std_logic;
    signal qni: std_logic;
    begin
    r <= '0', '1' after 1 ns;
    s <= '0', '1' after 1 ns;
    qni <= not (s and qi);
    qi <= not (r and qni);
    end block concurrent_1;

    concurrent_2: block
    signal r: std_logic;
    signal s: std_logic;
    signal qi: std_logic;
    signal qni: std_logic;
    begin
    r <= '0', '1' after 1 ns;
    s <= '0', '1' after 1 ns;
    qi <= not (r and qni);
    qni <= not (s and qi);
    end block concurrent_2;

    concurrent_3_with_process: block
    signal r: std_logic;
    signal s: std_logic;
    signal qi: std_logic;
    signal qni: std_logic;
    begin
    r <= '0', '1' after 1 ns;
    s <= '0', '1' after 1 ns;
    process(s,qi)
    begin
    qni <= not (s and qi);
    end process;

    process(r, qni)
    begin
    qi <= not (r and qni);
    end process;
    end block concurrent_3_with_process;
    end RTL;
    --- End of code ---
     
    KJ, Dec 29, 2011
    #2
    1. Advertising

  3. wrote:

    > Hi,
    >
    > until now I thought that with concurrent statements order does not matter.


    Your thoughts are correct.

    > Then I wanted to demonstrate delta delay effects with several versions of
    > an RS-FF. However, the simulator I use (Active HDL 8.3) produces different
    > results for the following 3 versions:
    >
    > concurrent_1:
    > qni <= not (s and qi);
    > qi <= not (r and qni);
    >
    > concurrent_1:
    > qi <= not (r and qni);
    > qni <= not (s and qi);
    >
    > concurrent_3_with_process:
    > process(s,qi)
    > begin
    > qni <= not (s and qi);
    > end process;
    >
    > process(r, qni)
    > begin
    > qi <= not (r and qni);
    > end process;


    Then Active HDL 8.3 is in error.

    > I would have expected that all 3 versions fail when r and s are
    > simultaneously change from 0 to 1. However, only the 3rd fails as
    > expected, the other 2 are simulated without any warning, but different
    > result - order matters!


    What exactly are the results?

    > I was under the impression that a concurrent assignment is a short hand
    > for a process with the same assigment AND all righthand signals in the
    > sensitivity list.


    That is correct.

    > But according to the results it looks as if the
    > assignments are evaluated/updated only once, i.e. no implied sensitivity
    > list.
    >
    > While all 3 variants will produce the same HW during synthesis they behave
    > in a different way during simulation. What is even more disturbing is that
    > the order of concurrent statemenst matters during simulation, IMO negating
    > the concept of delta delays.
    >
    > I am aware that the resulting HW will likely show some other behaviour
    > (metastability) depending on the actual elements used, but this example
    > was choosen to show the inner workings of the simulator.
    >
    > Is this behaviour of the simulator in accordance with the standard?


    As said before: no. What I would expect is an error message like Kevin
    already has shown is produced by ModelSim: "Iteration limit reached".

    It is same situation as this concurrent signal assignment, providing the
    value of s is not unknown:

    s <= not s;

    The value of s toggles every delta cycle, without any progression in "real"
    time.

    Things change if you add an "after" clause:

    s <= not s after 1 ns;

    Then you can observe the resulting wave form.

    You can do the same in your original code and observe the resulting wave
    forms. They should be identical in all three cases.

    --
    Paul Uiterlinden
    www.aimvalley.nl
    e-mail addres: remove the not.
     
    Paul Uiterlinden, Dec 30, 2011
    #3
  4. Hi Kevin and Paul,

    thanks for confirming my thoughts. I tried Kevins code and my simulator also barfed on all 3 versions - as expected. So the good news is that concurrent IS concurrent.
    Of course I now tried to find out why my experiment failed. It took quite a while but now I have hopefully narrowed it down to a more or less minimalistic version.

    (As a side note: I wanted NOT to use the example a <= not a; because everybody believes in oscillation problems here, independet of delta cycles or not).

    Well, now it looks like for HDL 8.3 there is a difference in the one-file version and the more traditional separation in testbench and unit under test.

    The one file minimalistic version fails (which is OK):

    ---
    library ieee;
    use ieee.std_logic_1164.all;

    entity rsff_tb is
    end rsff_tb;

    architecture tb of rsff_tb is
    signal i : std_logic;
    signal q : std_logic;
    signal qi, qni: std_logic;
    begin

    qi <= i nand qni;
    qni <= i nand qi;
    q <= qi;

    i <= '0', '1' after 1ns;

    end tb;
    ---

    The two file version does NOT fail in HDL 8.3!

    --- test bench (first file)
    library ieee;
    use ieee.std_logic_1164.all;

    entity rsff_tb is
    end rsff_tb;

    architecture tb of rsff_tb is
    signal i : std_logic;
    signal q : std_logic;
    begin

    UUT: entity rsff port map (i => i, q => q);
    i <= '0', '1' after 1ns;

    end tb;
    ---

    --- unit under test (second file)
    library ieee;
    use ieee.std_logic_1164.all;

    entity rsff is
    port
    ( i: in std_logic;
    q: out std_logic
    );
    end;

    architecture fail of rsff is
    signal qi, qni: std_logic;
    begin
    --process(i,qni,qi)
    --begin
    qi <= i nand qni;
    qni <= i nand qi;
    --end process;
    q <= qi;
    end;
    ---

    If I wrap the signal assignments in the UUT again by the process (comments), then the two-file version fails again, i.e. shows the expected behaviour.

    Strange! Up to a better explanation I have to believe HDL 8.3 is incorrect here.

    Mike
     
    Michael Hermann, Dec 30, 2011
    #4
  5. KJ Guest

    On Dec 30, 11:11 am, Michael Hermann <> wrote:
    > Hi Kevin and Paul,

    <snip>
    > The two file version does NOT fail in HDL 8.3!
    >
    > --- test bench (first file)


    Seems to me the test bench should be the second file, not the first.
    Inside the architecture you instantiate the entity 'raff' which hasn't
    been compiled yet if you have a completely empty work library. That
    is likely not contributing to your particular probllem, just a
    comment.

    Modelsim also had the following complaints when compiling your code
    'as-is' (other than swapping the order so that 'raff' is compiled
    first.

    ** Error: C:/Sim/Junk/Junk3.vhd(111): Unknown entity 'rsff'. Use
    expanded name.
    ** Warning: [4] C:/Sim/Junk/Junk3.vhd(112): (vcom-1207) An abstract
    literal and an identifier must have a separator between them.

    The error has to do with the following line of code
    UUT: entity rsff port map (i => i, q => q);
    which should be
    UUT: entity work.rsff port map (i => i, q => q);

    The warning is to the following line of code
    i <= '0', '1' after 1ns;
    which should be
    i <= '0', '1' after 1 ns;

    Again, these most likely have nothing to do with your problem, so this
    is just a comment but I believe in both cases Modelsim is correct to
    the LRM which would mean that Active HDL 8.3 is not correctly
    reporting non-compliant stuff that it should (unless you are disabling
    or otherwise ignoring these complaints).

    >
    > If I wrap the signal assignments in the UUT again by the process (comments), then the two-file version fails again, i.e. shows the expected behaviour.
    >


    I'm still not clear just what you mean by 'expected behaviour'. What
    I would expect for any model of an RS flip flop is an infinite loop
    and the simulator to stop if 'R' and 'S' are set at exactly the same
    time. I'm not sure if that's what you expect or not, but that would
    be the correct 'response' in this situation.

    In any case, when running the code you posted (both forms with and
    without the process) Modelsim does stop with an infinite loop
    reporting the following error:
    ** Error: (vsim-3601) Iteration limit reached at time 1 ns.

    > Strange! Up to a better explanation I have to believe HDL 8.3 is incorrect here.
    >

    The fact that you are getting different end results would indicate
    that Active HDL is not correct in one case. Does Active HDL ever
    report an infinite loop and stop for you?

    Kevin Jennings
     
    KJ, Dec 30, 2011
    #5
  6. Hi Kevin,

    sorry for the confusion:
    With "first" and "second" I did not want to imply an order, actually I just wanted to separate the two files. Could have said Unit-file and TB-file as well.
    They are actually compiled in the required order, otherwise it would not work at all.
    The missing "work" in front of the entity probably works (no pun intended), because the rsff is in the current working library which is just what work indicates.
    So it is surely cleaner to write work.rsff but I do understand why Active HDL does not complain here.
    Same for the 1ns.
    But at least for the 1ns you are still correct, that IF this is wrong according to the LRM then Active HDL should at least issue a warning.
    It does not.

    Now for the IMO more interesting stuff:
    For this particular description of a RSFF and the concept of delta cycles I would expect the oscillation. In fact this is what Active HDL probably sees in the one-file case and also in the two-file case with process().
    At least the simulation stops at 1ns because of "delta cycle limit reached" - perfect for me.
    The reason I'm digging into this is because I want to explain the working of the simulator in a lecture. I planned to show how the concept of delta cycles enables a sequential machine to simulate concurrency in a deterministic way.
    I also wanted to show some limits. Therefore the RSFF example, because a RSFF is normally a circuit which is quite well-behaved.

    Correct me if I'm wrong, but in this admittedly constructed case the oscillation is due to

    a) the specific description
    b) the delta cycle concept.

    Since my original experiment failed, revealing a potential problem in Active HDL, I have not progressed to the next step.
    This would have been to replace the two-liner by a one-liner
    like

    qi <= s nand (r nand qi);

    Same result in HW but now I would expect no oscillation during simulation, since the feedback is now calculated in a single cycle and no change of qi is detected after the update phase.

    Again, this example does not tell anything about the behaviour of the synthesized HW, it shall merely illustrate the kind of problem the delta cycle concept solves and where there are limits.

    But before I can explain this with some degree of confidence to innocent students I must make sure I understand the topic myself well enough. There I got trapped.

    For your last question:
    Yes, as I said I can get Active HDL into the loop and stop with an appropriate kernel message.
    But not as often as intended, your Modelsim seems right now the better, i.e. more standard compliant simulator!

    Mike
     
    Michael Hermann, Dec 30, 2011
    #6
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Pep
    Replies:
    6
    Views:
    826
  2. Nicolas Moreau
    Replies:
    9
    Views:
    3,188
  3. Torsten Landschoff

    Concurrent signal assignment vs. port mapping

    Torsten Landschoff, Jul 28, 2008, in forum: VHDL
    Replies:
    1
    Views:
    596
    Mike Treseler
    Jul 28, 2008
  4. dibacco73
    Replies:
    1
    Views:
    658
    joris
    Feb 12, 2009
  5. alb
    Replies:
    3
    Views:
    278
Loading...

Share This Page