Forum: FPGA, VHDL & Co. Dringend Hilfe gesucht - XC9572xl


von Pete K. (pete80)


Angehängte Dateien:

Lesenswert?

Sehr geehrte Computerspezialisten,

Leider habe ich kaum Ahnung von der Materie und komme auch nicht so 
richtig damit zurecht. Nach vielen eigenen Versuchen bin ich leider 
nicht weiter gekommen. Ich wäre Ihnen ausgesprochen dankbar, wenn Sie 
sich meinem (zumindest für mich) großen Problem annehmen könnten!

Vielen Dank im Vorraus für Ihre Hilfe!

Angaben zu meinem Projekt:
folgende Aufgaben sind wie unten beschrieben zu lösen. Das Demo-Board 
ist bereits vorhanden.
Für den Aufgabenbereich steht ein Xilinx XC9672XL zur Verfügung, der
mit VHDL programmiert werden sol. Bei weiteren Fragen stehe ich Ihnen 
gern zur Verfügung.
Über eine Antwort von Ihnen würde ich mich sehr freuen.
Sie erreichen mich unter petek80[a]gmx.de

So die Aufgabenstellung:
Die beiden angegebenen Funktionen sollen gemeinsam im CPLD eines 
Demo-Boards
realisiert werden! Die Beschreibung der Funktionalität soll in VHDL oder 
als
Schaltplaneingabe erfolgen! Ein Mischung beider Varianten ist möglich!

Realisieren eines Lauflichts:
Mit dem Drehkodierschalter soll die Frequenz (Weiterschaltung von einem 
Status
in den folgenden Status) des Lauflichts im Bereich von 0Hz (Stillstand) 
bis
1,875Hz in 0,125Hz-Schritten einstellbar sein. Durch die Taster S1, S3, 
S5 und
S7 sollen die verschiedenen Darstellungen des Lauflichts ausgewählt 
werden
können. Bei drücken eines Tasters soll das nun ausgewählte Lauflicht im 
ersten
Zustand verweilen bis der zugehörige Taster losgelassen wird und nun in 
der
beschriebenen Abfolge mit der eingestellten Frequenz durchlaufen.
Diese seien wie folgt belegt2 (Anmerkung: auf Board entspricht: 
LED8..1):
S7: „+-------“ → „-+------“ → „--+-----“ → „---+----“ → „----+---“ →
„-----+--“ → „------+-“ → „-------+“ → usw. mit „+-------“
S5: „+------+“ → „-+----+-“ → „--+--+--“ → „---++---“ → „--+--+--“ →
„-+----+-“ → „+------+“ → „--------“ → usw. mit „+------+“
S3: „++------“ → „-++-----“ → „--++----“ → „---++---“ → „----++--“ →
„-----++-“ → „------++“ → „-----++-“ → „----++--“ → „---++---“ → 
„--++----“ →
„-++-----“ → usw. mit „++------“
S1: „+-------“ → „++------“ → „+++-----“ → „++++----“ → „+++++---“ →
„++++++--“ → „+++++++-“ → „++++++++“ → „-+++++++“ → „--++++++“ → 
„---+++++“ →
„----++++“ → „-----+++“ → „------++“ → „-------+“ → „--------“ → usw. 
mit
„+-------“
Grundeinstellung: Zu Beginn sei die mit S7 gewählte Variante 
voreingestellt!

Realisieren einer Uhr:
Es soll eine Uhr mit Minuten- und Sekundenanzeige realisiert werden.
Die Anzeige soll wie folgt beschaltet sein:
LD4 LD3 LD2 LD1
 7     1.    3     2
Dieses bedeutet die Anzeige zeigt 71 Minuten und 32 Sekunden an. Die
Unterteilung zwischen Minuten und Sekunden wird durch einen Punkt 
realisiert.
Der Maximalwert entspricht „99.59“.
Die Funktionen der Taster seien wie folgt belegt:
S2 Stellen den 10er-Minuten („Hochzählen im ½ Sekundentakt“)
S4 Stellen den 1er-Minuten („Hochzählen im ½ Sekundentakt“)
S6 Stellen den 10er-Sekunden („Hochzählen im ½ Sekundentakt“)
S8 Rücksetzen der Uhr auf Null
Nach dem Einschalten soll die Anzeige auf 00.00 eingestellt sein und 
beginnen
zu takten.


Das Lauflich hab ich schon irgendwie zum laufen bekommen, jedoch kann 
ich es nur in einem Modus laufen lassen, da ich nicht weiß (bzw. es 
nicht hin bekomme) es mittels den Schaltern umzuschalten. Außerdem hab 
ich absolut keine Ahnung wie ich die Tacktzeit anpassen kann, etc.

HILFE!!!

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


Lesenswert?

> Das Lauflich hab ich schon irgendwie zum laufen bekommen...
Wie sieht dein VHDL-Code dazu aus?

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


Lesenswert?

> Mit dem Drehkodierschalter soll die Frequenz ...
> im Bereich von 0Hz (Stillstand) bis
> 1,875Hz in 0,125Hz-Schritten einstellbar sein.
Das allein ist ganz schön sportlich...
Wie genau müssen die Frequenzen sein?
Wenn du 0,875Hz willst, müsstest du die 8MHz durch 9142857,14286 teilen.
Bei 1,125Hz wären das 7111111,11111. Das hat was :-/
Hat die Aufgabe schon mal jemand auf dem Board realisiert?

von Pete K. (pete80)


Lesenswert?

Ja, klar. Der VHDL Code sieht bisher wie folgt aus. Bis zur architecture 
war er schon vorgegeben, das Lauflicht hab ich dann im Prozess danach 
irgendwie hineingearbeitet. Aber jetzte weiß ich echt nicht weiter...


-- Lösung Teil 1 -- CPLD

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;

---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
library UNISIM;
use UNISIM.VComponents.all;

entity xc9572_demo is
  port(
    -- Clock-Erzeugung
    clk_in:    in  std_logic;
    clk_speed:  out std_logic;

    -- Displays
    seg:  out std_logic_vector(7 downto 0);
    disp:  out std_logic_vector(3 downto 0);

    -- Taster
    key:  in std_logic_vector(7 downto 0);

    --  Codier-Schalter
    hex_switch:  in std_logic_vector(3 downto 0);

    -- LED's
    led:  out std_logic_vector(7 downto 0)
);

end xc9572_demo;

architecture Behavioral of xc9572_demo is



  -- Zähler -> Ausgang
  signal q:      STD_LOGIC_VECTOR(29 downto 0)  := 
"000000000000000000000000000000";

  -- Zähler -> Folgezustand
  signal fnext:    STD_LOGIC_VECTOR(29 downto 0)  := 
"000000000000000000000000000000";

  -- Zähler -> vorangegangene Zustände (maximaler Wert erreicht?)
  signal fand:    STD_LOGIC_VECTOR(29 downto 0)  := 
"000000000000000000000000000000";

  -- Zähler-Rückstellung -> Sekunden und Minuten
  signal sec1:  STD_LOGIC := '0';
  signal sec10:  STD_LOGIC := '0';
  signal min1:  STD_LOGIC := '0';
  signal min10:  STD_LOGIC := '0';

  -- Aktuell ausgegebener Wert auf 7-Segment-Anzeige
  signal disp_out:  STD_LOGIC_VECTOR(3 downto 0);

  -- Lauflicht
  signal loop_mode:  STD_LOGIC_VECTOR(1 downto 0):= "00";
  signal loop_hold:  STD_LOGIC_VECTOR(1 downto 0):= "00";
  signal loop_cnt:  STD_LOGIC_VECTOR(3 downto 0):= x"0";
  signal loop_and:  STD_LOGIC_VECTOR(3 downto 0):= x"0";
  signal loop_max:  STD_LOGIC_VECTOR(3 downto 0):= x"7";
  signal loop_xmax:  STD_LOGIC := '0';
  signal loop_res:  STD_LOGIC := '0';
  signal loop_clk:  STD_LOGIC_VECTOR(3 downto 0):= x"0";
  signal loop_next:  STD_LOGIC := '0';

begin

  --Oszillator an/aus
  clk_speed <= '1';


  -- Zähler

  Process(clk_in)

  begin

    if clk_in'event and clk_in = '1' then

    -- Zähler erhöhen
    q <= q + '1';


    -- Anhand Bit 18 wechseln
    case q( 21 downto 18 ) is

    -- S7 Schleife
    --when "000" => led <= x"7f";
    --when "001" => led <= x"bf";
    --when "010" => led <= x"df";
    --when "011" => led <= x"ef";
    --when "100" => led <= x"f7";
    --when "101" => led <= x"fb";
    --when "110" => led <= x"fd";
    --when "111" => led <= x"fe";
    --when others => led <= x"00";

    -- S5 Schleife
    --when "000" => led <= x"7e";
    --when "001" => led <= x"bd";
    --when "010" => led <= x"db";
    --when "011" => led <= x"e7";
    --when "100" => led <= x"db";
    --when "101" => led <= x"bd";
    --when "110" => led <= x"7e";
    --when "111" => led <= x"ff";
    --when others => led <= x"00";

    -- S3 Schleife
    --when "0000" => led <= x"3f";
    --when "0001" => led <= x"9f";
    --when "0010" => led <= x"cf";
    --when "0011" => led <= x"e7";
    --when "0100" => led <= x"f3";
    --when "0101" => led <= x"f9";
    --when "0110" => led <= x"fc";
    --when "0111" => led <= x"f9";
    --when "1000" => led <= x"f3";
    --when "1001" => led <= x"e7";
    --when "1010" => led <= x"cf";
    --when "1011" => led <= x"9f";
    --when "1100" => led <= x"3f";
    --when others => led <= x"ff";

    -- S1 Schleife
    when "0000" => led <= x"7f";
    when "0001" => led <= x"3f";
    when "0010" => led <= x"1f";
    when "0011" => led <= x"0f";
    when "0100" => led <= x"07";
    when "0101" => led <= x"03";
    when "0110" => led <= x"01";
    when "0111" => led <= x"00";
    when "1000" => led <= x"01";
    when "1001" => led <= x"03";
    when "1010" => led <= x"07";
    when "1011" => led <= x"0f";
    when "1100" => led <= x"1f";
    when "1101" => led <= x"3f";
    when "1111" => led <= x"7f";
    when others => led <= x"ff";

    end case;
  end if;
 End Process;

end Behavioral;


Die dazugehörige .ucf sieht wie folgt aus:


# Clock-Erzeugung

NET "clk_in"    LOC = "P43" ;
NET "clk_speed"  LOC = "P5" ;

# displays

NET "seg<0>"  LOC = "P3" ;  # segment A
NET "seg<1>"  LOC = "P1" ;  # segment B
NET "seg<2>"  LOC = "P42" ;  # segment C
NET "seg<3>"  LOC = "P39" ;  # segment D
NET "seg<4>"  LOC = "P41" ;  # segment E
NET "seg<5>"  LOC = "P44" ;  # segment F
NET "seg<6>"  LOC = "P2" ;  # segment G
NET "seg<7>"  LOC = "P40" ;  # segment DP

NET "disp<0>"  LOC = "P22" ;
NET "disp<1>"  LOC = "P20" ;
NET "disp<2>"  LOC = "P19" ;
NET "disp<3>"  LOC = "P21" ;

# Taster

NET "key<0>"  LOC = "P30" ;
NET "key<1>"  LOC = "P31" ;
NET "key<2>"  LOC = "P32" ;
NET "key<3>"  LOC = "P33" ;
NET "key<4>"  LOC = "P34" ;
NET "key<5>"  LOC = "P36" ;
NET "key<6>"  LOC = "P37" ;
NET "key<7>"  LOC = "P38" ;

# Codier-Schalter

NET "hex_switch<0>"  LOC = "P27" ;
NET "hex_switch<1>"  LOC = "P29" ;
NET "hex_switch<2>"  LOC = "P28" ;
NET "hex_switch<3>"  LOC = "P23" ;

# led's

NET "led<0>"  LOC = "P6" ;
NET "led<1>"  LOC = "P7" ;
NET "led<2>"  LOC = "P8" ;
NET "led<3>"  LOC = "P12" ;
NET "led<4>"  LOC = "P13" ;
NET "led<5>"  LOC = "P14" ;
NET "led<6>"  LOC = "P16" ;
NET "led<7>"  LOC = "P18" ;

von Falk B. (falk)


Lesenswert?

@  Pete Konze (pete80)

Für den Anfang OK, wenn gleich sehr aufwändig. Die Umschaltung der 
verschiedenen Modi ist auch nur ein Case Konstukt. Oder mit mehreren If 
then.

MFG
Falk

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


Lesenswert?

Ich sagte schon: das mit dem Takt ist nicht trivial.
Hier eine mögliche Lösung.
1
  signal counter : integer range 0 to 32000000; -- (8000000/0.125)/2
2
  signal reload  : integer range 0 to 32000000;
3
  signal clkdiv  : std_logic := '0';
4
:
5
:
6
:
7
  reload <=   (32000000)-1 when hex_switch=x"1" -- (8000000/0.125)/2
8
         else (16000000)-1 when hex_switch=x"2" -- (8000000/0.25 )/2
9
         else (10666667)-1 when hex_switch=x"3" -- (8000000/0.375)/2
10
         else ( 8000000)-1 when hex_switch=x"4" -- (8000000/0.5  )/2
11
         else ( 6400000)-1 when hex_switch=x"5" --  :
12
         else ( 5333333)-1 when hex_switch=x"6" --  :
13
         else ( 4571428)-1 when hex_switch=x"7" 
14
         else ( 4000000)-1 when hex_switch=x"8" 
15
         else ( 3555555)-1 when hex_switch=x"9" 
16
         else ( 3200000)-1 when hex_switch=x"a" 
17
         else ( 2909091)-1 when hex_switch=x"b" 
18
         else ( 2666667)-1 when hex_switch=x"c" 
19
         else ( 2461538)-1 when hex_switch=x"d" 
20
         else ( 2285714)-1 when hex_switch=x"e" 
21
         else ( 2133333)-1 when hex_switch=x"f" 
22
         else 0;
23
24
  process (clk_in) begin
25
    if rising_edge(clk_in) then
26
       if (counter = 0) then
27
          counter <= reload;
28
          clkdiv  <= not clkdiv;
29
       else
30
          counter <= counter-1;
31
       end if;
32
       if (dip=x"0") then -- Sonderfall f=0
33
          clkdiv <= '0'; 
34
       end if;
35
    end if;
36
  end process;
Du musst dann natürlich in deinem Zählerregister den clkdiv als 
Eingangstakt verwenden.
1
  Process(clkdiv)
2
  begin
3
    if rising_edge(clkdiv) then
4
      -- Zähler erhöhen
5
      q <= q + '1'; -- 4 Bits
6
7
      -- Taster abfragen
8
      if (key(7)='1') then      
9
        case q(2 downto 0) is
10
        when "000" => led <= x"7f";
11
        when "001" => led <= x"bf";
12
        when "010" => led <= x"df";
13
         :
14
        when others => led <= x"00";
15
      end if;
16
17
      if (key(5)='1') then      
18
        case q(2 downto 0) is
19
        when "000" => led <= x"7e";
20
         :
21
        when others => led <= x"00";
22
      end if;
23
      
24
      if (key(3)='1') then      
25
        case q is
26
        when "0000" => led <= x"3f";
27
         :
28
        when others => led <= x"00";
29
      end if;
30
   end process;

Zur Beruhigung:
Für die Uhr wird die Eingangstakterzeugung einfacher, da gibt es nur die 
2Hz. Allerdings kommt die Multiplex-Ansteuerung dazu.
Für einen blutigen Anfänger durchaus anspruchsvolle Aufgaben... :-/

von Pete K. (pete80)


Lesenswert?

vielen Dank, leider bekomme ich ich die Fehlermeldungen nicht weg (siehe 
im Anhang die Kommentare - ganz unten).

Vielleicht kann ja noch mal jemand drüber schauen und mir auf die 
Sprünge helfen.

von Pete K. (pete80)


Angehängte Dateien:

Lesenswert?

> ...(siehe im Anhang die Kommentare - ganz unten).

Jetzt aber mit Anhang ;)

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


Lesenswert?

> Insufficient number of product terms.
Das CPLD ist zu klein...  :-o
Allein der Vorteiler braucht einiges, und dann kommen die Muster dazu.
- Mach mal nur 1 Muster, dann 2 usw.
- Stell mal testweise auf ein 95144 um.

Das war meine Frage:
hat schon jemand genau diese Aufgabe mit diesem CPLD gelöst?

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.