www.mikrocontroller.net

Forum: FPGA, VHDL & Co. Couldn't implement registers for assignments on this clock edge


Autor: Psycho Dad (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Bei dem nachfolgenden Programm findet sich der oben genannte Fehler. Der 
Fehler ligt in der Flankendetektion. Was habe ich da falsch gemacht?
-- Dateiname: flanke.vhd
-- Beschreibung: Definition einer Funktion zur Detektion
-- einer ansteigenden Flanke

library ieee;
use ieee.std_logic_1164.all;

entity flanke is

  port (d, clk : in std_logic;
      q  : out std_logic);
  
  function pos_flanke (signal s : std_logic)
    return boolean is
      variable result : boolean; -- Rückgabevariable
      begin
        if (s'event) and (s = '1') and -- Flankendetektion
           (s'last_value = '0') then result := true; -- Wert vor letzter Signaländerung
        else result := false;
        end if;
    return result; -- Rückgabe  
  end function pos_flanke;
  
end entity flanke;

architecture verhalten of flanke is
begin
  process(clk)
  begin
    if pos_flanke(clk) then q <= d; -- Funktionsaufruf
    end if;
  end process;
end architecture verhalten;

Autor: Lothar Miller (lkmiller) (Moderator) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Die Funktion "rising_edge()" ist in der IEEE-Library definiert:
    -------------------------------------------------------------------    
    -- edge detection
    -------------------------------------------------------------------    
    FUNCTION rising_edge  (SIGNAL s : std_ulogic) RETURN BOOLEAN IS
    BEGIN
        RETURN (s'EVENT AND (To_X01(s) = '1') AND 
                            (To_X01(s'LAST_VALUE) = '0'));
    END;

In der praktischen Anwendung sieht das dann so aus:
library ieee;
use ieee.std_logic_1164.all;
entity flanke is
  port (d, clk : in std_logic;
        q      : out std_logic);
architecture verhalten of flanke is
begin
  process(clk)
  begin
    if rising_edge(clk) then q <= d; -- FF einbauen
    end if;
  end process;
end architecture verhalten;

Aber Achtung: Das ist nicht einfach so eine Flankenerkennung. Damit wird 
ein getaktetes Speicherelement (also ein Flipflop) beschrieben.

Siehe auch im http://www.mikrocontroller.net/articles/VHDL

Autor: Lothar Miller (lkmiller) (Moderator) Benutzerseite
Datum:
Angehängte Dateien:

Bewertung
0 lesenswert
nicht lesenswert
rising_edge()
und
clk'event and clk'last_value = '0' and clk='1'
sind Schlüsselformulierungen für die Synthese.
Daran wird erkannt, dass ein FF eingebaut werden soll.

Mit der folgenden Beschreibung wird zwar alles korrekt simuliert (Bild). 
Die Synthese macht aber nur aus den ersten beiden Beschreibungen FFs 
(v1, v2). Die beiden Prozesse v3 und v4 werden gar nicht erst 
implementiert (Bild RTL-Schematics).
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;

entity flanke is

   port (clk   : in std_logic;
         d,e,f,g : in std_logic;
         q,p,r,s : out std_logic);

   -- Funktion rising_edge() aus IEEE, aber mit anderem Namen
   FUNCTION pos_edge  (SIGNAL s : std_ulogic) RETURN BOOLEAN IS
   BEGIN
     RETURN (s'EVENT AND (To_X01(s) = '1') AND 
                         (To_X01(s'LAST_VALUE) = '0'));
   END;  

   -- aus Post von  Psycho Dad
   function pos_flanke (signal s : std_logic)
     return boolean is
       variable result : boolean; -- Rückgabevariable
       begin
         if (s'event) and (s = '1') and               -- Flankendetektion
            (s'last_value = '0') then result := true; -- Wert vor letzter Signaländerung
         else result := false;
         end if;
     return result; -- Rückgabe  
   end function pos_flanke;
  
end entity flanke;

architecture verhalten of flanke is
begin
-- Synthese OK
  v1: process(clk)
  begin
    if rising_edge(clk) then p <= e; -- IEEE-Funktionsaufruf
    end if;
  end process;

  v2: process(clk)
  begin
    if clk'event and clk'last_value = '0' and clk='1' then r <= f; -- händisch
    end if;
  end process;


-- Synthese nicht brauchbar
  v3: process(clk)
  begin
    if pos_edge(clk) then q <= d;    -- Funktionsaufruf
    end if;
  end process;
  
  v4: process(clk)
  begin
    if pos_flanke(clk) then s <= g;   -- Funktionsaufruf
    end if;
  end process;

end architecture verhalten;

Die verwendetete Testbench:
   clk <= not clk after 10 ns;

   tb : PROCESS
     BEGIN
     d<='1';
     wait for 100 ns;
     e<='1';
     wait for 100 ns;
     f<='1';
     wait for 100 ns;
     g<='1';
     wait for 100 ns;

     d<='0';
     wait for 100 ns;
     e<='0';
     wait for 100 ns;
     f<='0';
     wait for 100 ns;
     g<='0';
     wait for 100 ns;
  END PROCESS;

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [vhdl]VHDL-Code[/vhdl]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.