Forum: FPGA, VHDL & Co. Dreieckgenerator programmieren


von VHDL Anfänger (Gast)


Lesenswert?

Wie kann ich in VHDL einen Zähler programmieren, der von 0 hoch bis 255 
zählt, und dann von 255 wieder runter auf 0 und dann wieder hoch?
Also einen Dreieckgenerator.

von kurz (Gast)


Lesenswert?

Echt gut: 2 Threads um andere für sich arbeiten zu lassen.

Also los.

von BorisM (Gast)


Lesenswert?

Hi...
gidf !
Hast du schon mal die SUCHE benutzt?

Deine Frage ist sehr offen gestellt...
Willst du nur den Zählbefehl? -> a <= a + 1
Oder den kompletten VHDL-Code? -> hier z. B. ein "hoch"-Zähler
1
library IEEE;
2
use IEEE.std_logic_1164.all;
3
use work.std_arith.all;
4
5
entity COUNT is
6
  port( CLK, ENA : in std_logic;
7
        Q        : buffer std_logic_vector(3 downto 0);
8
        UEB      : out std_logic);
9
end COUNT;
10
11
architecture A1 of COUNT is
12
begin
13
   P1: process( CLK )
14
   begin
15
      if( CLK'event and CLK = '1' ) then
16
         if( ENA = '1' ) then
17
            Q <= Q + 1;
18
         end if;
19
      end if;
20
   end process;
21
   UEB <= '1' when Q = "1111" else '0';
22
end A1;
Hast du schon VHDL-Kentnisse?
Gruß Boris

von VHDL Anfänger (Gast)


Lesenswert?

>Hast du schon VHDL-Kentnisse?

Gerade daran arbeite ich ja im Moment.

Ich würde es wahrscheinlich so programmieren:
1
  Triangle_counter: process(Takt)
2
  begin
3
    if (Takt ='1' and Takt'event) then
4
      case Counter_up_down is
5
        when 0  => Counter_up_down <= 1;
6
        when 1  => Counter_up_down <= 2;
7
        when 2  => Counter_up_down <= 3;
8
9
10
11
        when 253  => Counter_up_down <= 254;
12
        when 254  => Counter_up_down <= 255;
13
        when 255  => Counter_up_down <= 254;
14
        when 254  => Counter_up_down <= 253;
15
        when 253  => Counter_up_down <= 252;
16
        when 252  => Counter_up_down <= 251;
17
             end case;
18
    end if;
19
  end process Triangle_counter;

Das ist natürlich STUSS so, weil jede Zahl doppelt vorkommt.

Besser von 0 bis 255 hochzählen und dann von 511 auf 256 wieder 
runterzählen und das Bit8 einfach wegschmeissen.
Das kann man doch bestimmt auch anders schreiben, ohne das einem die 
Finger bluten?

von BorisM (Gast)


Lesenswert?

Den VHDL_Code den ich weiter oben als Beispiel gepostet habe kannst du 
für den Anfang vielleicht erweitern. Du musst dir nur die Zählrichtung 
"merken" und immer vergleichen ob du bei 255 bzw. 0 angekommen bist und 
dann die Richtung ändern... Ist eine schöne Übung für den Anfang:)

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

So:
1
library IEEE;
2
use IEEE.std_logic_1164.all;
3
use IEEE.numeric_std.all;
4
5
signal counter : integer range 0 to 255 := 0;
6
signal up : std_logic := '1';
7
8
process begin
9
  wait until rising_edge(clk);
10
  if (up='1') then
11
     counter <= counter + 1;
12
     if counter=254 then  up <= '0';  end if;
13
  else
14
     counter <= counter - 1;
15
     if counter=1 then    up <= '1';  end if;
16
  end if;
17
end process;
18
ausgang <= std_logic_vector(to_unsigned(counter,8));

Als Tipp: kauf dir ein Buch, z.B. VHDL-Synthese von Reichardt/Schwarz

von BorisM (Gast)


Lesenswert?

Es gibt auch schöne Lehrgänge beim PLC2 ;)

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

BorisM schrieb:
> Es gibt auch schöne Lehrgänge beim PLC2 ;)
ACK.
Da sollte man aber vorher ein/das Buch angesehen haben, sonst rauscht 
der Zug an einem vorbei...

von MaWin (Gast)


Lesenswert?

> Das ist natürlich STUSS so, weil jede Zahl doppelt vorkommt.

Natürlich, der Zustand, ob man gerade aufwärts zählen sollte, oder 
abwärts, ist ein zusätzliches Bit, von dem aus man entscheiden muss, 
wass bei CLK passiert. Ohne dieses bit, ohne diesen Zustand, kann deine 
Schaltung nicht wissen, wo's lang geht.

Wo du dieses bit unterbringt, im count selber von dem dann eben 8 als 
Zähler genutzt werden und das neunte als Richtungszustandsbit, oder ob 
du es extra Wert nimmst, bleibt dir überlassen.

Und glücklicherweise kann VHDL Arithmetik, du brauchst nicht 512 when 
Fälle zu schreiben.

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Der hier ist auch schön kompakt, er hat aber jeweils 2 Takte 0 und 255:
1
-- 0 und 255 sind jeweils 2 Takte lang
2
architecture Behavioral of CntTriangle is
3
signal cnt : unsigned (8 downto 0) := (others=>'0');
4
begin
5
   process begin
6
     wait until rising_edge(clk);
7
     cnt <= cnt + 1;
8
     if cnt(8)='1' then     
9
        counter <= std_logic_vector(    cnt(7 downto 0));
10
     else
11
        counter <= std_logic_vector(255-cnt(7 downto 0));
12
     end if;
13
   end process;
14
end Behavioral;

von GAST (Gast)


Lesenswert?

ihr überbietet euch im formulieren der lösung, aber am ende kommt doch 
immer dasselbe raus.

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

@  GAST (Gast)
> aber am ende kommt doch immer dasselbe raus.
Sicher? Oder glaubst du das nur?

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.