statement is not synthesizable since it does not hold its value underNOT(clock-edge) condition

Discussion in 'VHDL' started by Trygve Laugstøl, Jan 24, 2011.

  1. Hello!

    I'm trying to get the following snippet to work and I'm 1) wondering
    what's wrong and 2) wondering if I'm going about this the right way.

    I have two clocks, one CPU clock (at 48MHz) and a LCD clock (200kHz)
    which control the CPU and the output to the LCD (obviously enough). What
    I want to happen is that the CPU will set trigger on the leading edge of
    the CPU clock and clear it on the falling edge of the LCD clock (which
    should ensure that it has been picked up by the 'main' process).

    The error message I'm getting is "statement is not synthesizable since
    it does not hold its value under NOT(clock-edge) condition".

    The code:

    trigger_xfer: process(reset, clk, clk_200kHz, output_trigger)
    begin
    trigger <= '0';
    if reset = '1' then
    trigger <= '0';
    elsif clk'event and clk = '1' and output_trigger = '1' then
    trigger <= '1';
    elsif clk_200kHz'event and clk_200kHz = '0' then
    trigger <= '0';
    end if;
    end process;

    main: process(...)
    if reset
    ...
    elsif clk_200kHz'event and clk_200kHz = '1' then
    ...
    end if;
    end process;
     
    Trygve Laugstøl, Jan 24, 2011
    #1
    1. Advertising

  2. Trygve Laugstøl

    Gabor Guest

    Re: statement is not synthesizable since it does not hold its valueunder NOT(clock-edge) condition

    On Jan 24, 3:32 pm, Trygve Laugstøl <> wrote:
    > Hello!
    >
    > I'm trying to get the following snippet to work and I'm 1) wondering
    > what's wrong and 2) wondering if I'm going about this the right way.
    >
    > I have two clocks, one CPU clock (at 48MHz) and a LCD clock (200kHz)
    > which control the CPU and the output to the LCD (obviously enough). What
    > I want to happen is that the CPU will set trigger on the leading edge of
    > the CPU clock and clear it on the falling edge of the LCD clock (which
    > should ensure that it has been picked up by the 'main' process).
    >
    > The error message I'm getting is "statement is not synthesizable since
    > it does not hold its value under NOT(clock-edge) condition".
    >
    > The code:
    >
    >      trigger_xfer: process(reset, clk, clk_200kHz, output_trigger)
    >      begin
    >          trigger <= '0';
    >          if reset = '1' then
    >              trigger <= '0';
    >          elsif clk'event and clk = '1' and output_trigger = '1' then
    >              trigger <= '1';
    >          elsif clk_200kHz'event and clk_200kHz = '0' then
    >              trigger <= '0';
    >          end if;
    >      end process;
    >
    >      main: process(...)
    >          if reset
    >              ...
    >          elsif clk_200kHz'event and clk_200kHz = '1' then
    >              ...
    >          end if;
    >      end process;


    First, I know of no FPGA that has dual-clocked flip-flops available in
    the internal
    fabric. So it's no wonder that the code is not synthesizable.

    Second, 200 KHz is really slow, so you should probably just sample it
    with the
    48 MHz CPU clock and use the sampled signal with another flip-flop
    delay
    to detect edges instead of trying to create a dual-clocked process.

    Third. It's not clear to me that you are taking care of
    synchronization properly
    here. If the intent is for a single event on the CPU clock to create
    an output
    that can be sampled at the falling edge of the 200 KHz clock, then I
    don't
    see how you will ensure any minimum setup time unless the event was
    already somehow synchronous to the 200 KHz clock.

    -- Gabor
     
    Gabor, Jan 24, 2011
    #2
    1. Advertising

  3. Re: statement is not synthesizable since it does not hold its valueunder NOT(clock-edge) condition

    [Note that I'm quite a newbie to VHDL]

    On 1/24/11 9:41 PM, Gabor wrote:
    > On Jan 24, 3:32 pm, Trygve Laugstøl<> wrote:
    >> Hello!
    >>
    >> I'm trying to get the following snippet to work and I'm 1) wondering
    >> what's wrong and 2) wondering if I'm going about this the right way.
    >>
    >> I have two clocks, one CPU clock (at 48MHz) and a LCD clock (200kHz)
    >> which control the CPU and the output to the LCD (obviously enough). What
    >> I want to happen is that the CPU will set trigger on the leading edge of
    >> the CPU clock and clear it on the falling edge of the LCD clock (which
    >> should ensure that it has been picked up by the 'main' process).
    >>
    >> The error message I'm getting is "statement is not synthesizable since
    >> it does not hold its value under NOT(clock-edge) condition".
    >>
    >> The code:
    >>
    >> trigger_xfer: process(reset, clk, clk_200kHz, output_trigger)
    >> begin
    >> trigger<= '0';
    >> if reset = '1' then
    >> trigger<= '0';
    >> elsif clk'event and clk = '1' and output_trigger = '1' then
    >> trigger<= '1';
    >> elsif clk_200kHz'event and clk_200kHz = '0' then
    >> trigger<= '0';
    >> end if;
    >> end process;
    >>
    >> main: process(...)
    >> if reset
    >> ...
    >> elsif clk_200kHz'event and clk_200kHz = '1' then
    >> ...
    >> end if;
    >> end process;

    >
    > First, I know of no FPGA that has dual-clocked flip-flops available in
    > the internal
    > fabric. So it's no wonder that the code is not synthesizable.


    Hm, I though this should synthesize a S/R+reset flip flop but I guess
    because of the 'event it will become clocks instead.

    > Second, 200 KHz is really slow, so you should probably just sample it
    > with the
    > 48 MHz CPU clock and use the sampled signal with another flip-flop
    > delay
    > to detect edges instead of trying to create a dual-clocked process.


    How would that work? It is generated from the 48MHz clock already just
    on the outside of the entity.

    > Third. It's not clear to me that you are taking care of
    > synchronization properly
    > here. If the intent is for a single event on the CPU clock to create
    > an output
    > that can be sampled at the falling edge of the 200 KHz clock, then I
    > don't
    > see how you will ensure any minimum setup time unless the event was
    > already somehow synchronous to the 200 KHz clock.


    Hm, I'm not really seeing the problem but that's probably because of my
    lack of understanding. Could you elaborate or show/point me some code
    that does what I want to do? I've been trying to read up on links from
    searches like "clock synchronization" and "clock domains" but haven't
    found something that really applies to my case (and makes sense to me).

    --
    Trygve
     
    Trygve Laugstøl, Jan 24, 2011
    #3
  4. Re: statement is not synthesizable since it does not hold its value under NOT(clock-edge) condition

    Trygve Laugstøl wrote:

    > Hello!
    >
    > I'm trying to get the following snippet to work and I'm 1) wondering
    > what's wrong


    The first assignment to "trigger" (right after the "begin") cannot be right.

    What you have described here is something like: "reset trigger on any event
    on signals reset, clk, clk_200kHz and output_trigger, unless there is a
    rising edge on clk while output_trigger is '1'. In the latter case, set
    trigger."

    If you leave out the first assignment, things perhaps start looking what you
    want. If it will be synthesisable, I don't know (I don't do synthesis).

    Have you simulated this code at all?

    > The code:
    >
    > trigger_xfer: process(reset, clk, clk_200kHz, output_trigger)
    > begin
    > trigger <= '0';
    > if reset = '1' then
    > trigger <= '0';
    > elsif clk'event and clk = '1' and output_trigger = '1' then
    > trigger <= '1';
    > elsif clk_200kHz'event and clk_200kHz = '0' then
    > trigger <= '0';
    > end if;
    > end process;
    >


    --
    Paul Uiterlinden
    www.aimvalley.nl
    e-mail addres: remove the not.
     
    Paul Uiterlinden, Jan 24, 2011
    #4
  5. Trygve Laugstøl

    rickman Guest

    Re: statement is not synthesizable since it does not hold its valueunder NOT(clock-edge) condition

    On Jan 24, 3:47 pm, Trygve Laugstøl <> wrote:
    > [Note that I'm quite a newbie to VHDL]
    >
    > On 1/24/11 9:41 PM, Gabor wrote:
    >
    >
    >
    > > On Jan 24, 3:32 pm, Trygve Laugstøl<> wrote:
    > >> Hello!

    >
    > >> I'm trying to get the following snippet to work and I'm 1) wondering
    > >> what's wrong and 2) wondering if I'm going about this the right way.

    >
    > >> I have two clocks, one CPU clock (at 48MHz) and a LCD clock (200kHz)
    > >> which control the CPU and the output to the LCD (obviously enough). What
    > >> I want to happen is that the CPU will set trigger on the leading edge of
    > >> the CPU clock and clear it on the falling edge of the LCD clock (which
    > >> should ensure that it has been picked up by the 'main' process).

    >
    > >> The error message I'm getting is "statement is not synthesizable since
    > >> it does not hold its value under NOT(clock-edge) condition".

    >
    > >> The code:

    >
    > >> trigger_xfer: process(reset, clk, clk_200kHz, output_trigger)
    > >> begin
    > >> trigger<= '0';
    > >> if reset = '1' then
    > >> trigger<= '0';
    > >> elsif clk'event and clk = '1' and output_trigger = '1' then
    > >> trigger<= '1';
    > >> elsif clk_200kHz'event and clk_200kHz = '0' then
    > >> trigger<= '0';
    > >> end if;
    > >> end process;

    >
    > >> main: process(...)
    > >> if reset
    > >> ...
    > >> elsif clk_200kHz'event and clk_200kHz = '1' then
    > >> ...
    > >> end if;
    > >> end process;

    >
    > > First, I know of no FPGA that has dual-clocked flip-flops available in
    > > the internal
    > > fabric. So it's no wonder that the code is not synthesizable.

    >
    > Hm, I though this should synthesize a S/R+reset flip flop but I guess
    > because of the 'event it will become clocks instead.
    >
    > > Second, 200 KHz is really slow, so you should probably just sample it
    > > with the
    > > 48 MHz CPU clock and use the sampled signal with another flip-flop
    > > delay
    > > to detect edges instead of trying to create a dual-clocked process.

    >
    > How would that work? It is generated from the 48MHz clock already just
    > on the outside of the entity.
    >
    > > Third. It's not clear to me that you are taking care of
    > > synchronization properly
    > > here. If the intent is for a single event on the CPU clock to create
    > > an output
    > > that can be sampled at the falling edge of the 200 KHz clock, then I
    > > don't
    > > see how you will ensure any minimum setup time unless the event was
    > > already somehow synchronous to the 200 KHz clock.

    >
    > Hm, I'm not really seeing the problem but that's probably because of my
    > lack of understanding. Could you elaborate or show/point me some code
    > that does what I want to do? I've been trying to read up on links from
    > searches like "clock synchronization" and "clock domains" but haven't
    > found something that really applies to my case (and makes sense to me).
    >
    > --
    > Trygve


    Here is how I do it. I cut this from a program and ripped out all the
    other code to just highlight the edge detection. Replace TT_B2 with
    your LCD clock and add your code where indicated. The function
    NegEdge() just ANDs TT_DD with not TT_D to make it clear what the IF
    statement is doing. There will be a delay of one to two clock cycles
    from the edge of your slow clock before the code in the IF statement
    is executed, but with your app, I expect this doesn't matter.

    CTPData: process (SysClk, SysRst) begin
    if (SysRst = '1') then
    TT_D <= '0';
    TT_DD <= '0';
    elsif (rising_edge(SysClk)) then
    TT_D <= TT_B2;
    TT_DD <= TT_D;
    -- RD output interface
    if (NegEdge(TT_D, TT_DD)) then -- falling edge of TT data strobe
    -- This is where you put your LCD code
    end if; -- NegEdge(TT
    end if; -- elsif (rising_edge(SysClk
    end process CTPData;

    This approach solves a lot of problems. It gets rid of communication
    issues between clock domains and the two FFs handle metastability
    issues, which you can still have even though the two frequencies are
    locked, the phase is likely not. If you really want to be sure of
    dealing with meta stability, combine the two delay FFs and register
    that. With only one LUT, 20 ns will be lots of settling time.

    Rick
     
    rickman, Jan 24, 2011
    #5
    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. Nicolas Matringe

    Synthesizable (kind of) dual-edge FF

    Nicolas Matringe, Sep 27, 2004, in forum: VHDL
    Replies:
    1
    Views:
    964
    Ralf Hildebrandt
    Oct 12, 2004
  2. =?iso-8859-1?q?Guilherme_Corr=EAa?=

    "signal does not hold its value outside clock edge"

    =?iso-8859-1?q?Guilherme_Corr=EAa?=, Jan 23, 2006, in forum: VHDL
    Replies:
    5
    Views:
    6,183
    =?iso-8859-1?q?Guilherme_Corr=EAa?=
    Jan 23, 2006
  3. Replies:
    4
    Views:
    759
    Peter Alfke
    Apr 27, 2006
  4. Ferdi Smit
    Replies:
    0
    Views:
    802
    Ferdi Smit
    Oct 10, 2005
  5. denish
    Replies:
    5
    Views:
    5,823
Loading...

Share This Page