Forum: FPGA, VHDL & Co. TaktTeiler


von VHDL-Neuling (Gast)


Lesenswert?

Hallo,

ich habe folgendes Problem:
bei einem Zählerüberlauf (10-Bit) soll ein zweiter Signal
entstehen z.B. slow_clk, der durch den ersten Takt clk
getaktet wird

Wieviele Bitstellen muß dieser zweite Zähler besitzen, damit die 
niederwertigste Bitstelle des 10-Bit-Zählers ungefähr drei mal pro 
Sekunde schaltet?

(clk besitzt eine Taktfrequenz von 25 MHz)


wie kann ich das in VHDL implementieren?

kann mir jemand helfen?

Danke im Voraus

von bigr (Gast)


Lesenswert?

23bit

von tester (Gast)


Lesenswert?

Greif in vhdl einfachen das 23. Bit deines Zählers ab und verwende das 
als dein slow_clk.
Nicht vergessen deinen 23 bit Zähler wieder zurückzusetzen, nachdem das 
23 bit 1 wurde.
Die Funktionsweise eines Frequenzteilers find ich hier:
[[http://www.elektronik-kompendium.de/sites/dig/0212221.htm]]
schön erklärt.

von VHDL-Neuling (Gast)


Lesenswert?

danke für die schnelle antwort,

währe noch nett kurz zu sagen wie man darauf kommt,

kurz noch eine andere Frage:
ich möchte folgendes machen:

wenn zählvariable > 10 Bit, soll ein anderer Takt benutzt werden,
der muss zum Beispiel 23Bit gross sein,
wie kann ich clk zum bespiel sozusagen annulieren und mit slow_clk 
weiterarbeiten ? bzw. denTakt an slow_clk übergeben
(ein code-schnipsel währe hilfreich)


danke nochmal

von Schlumpf (Gast)


Lesenswert?

Das was du da vor hast, ist böööööööse! ;-)

Versuche am besten nie, Takte hin und herzusschalten, oder mehrere Takte 
in einem System zu verwenden. Auch einfach den den "Ausgang" eines 
Zählers als Takt zu verwenden ist keine gute Idee.
Funktional ist das alles okay, nur bei der Synthese kann das Probleme 
geben.

Problem dabei ist, dass die Synthese keine vernünftige 
Laufzeitberechnungen mehr durchführen kann und somit mit ziemlicher 
Sicherheit dein Chip aus "unerklärlichen" Gründen verrückt spielt.
Stichwort "Setup-Zeit-Verletzung"

Daher versuche lieber sicherzustellen, dass ALLE Register mit demselben 
Takt versorgt werden. Um etwas "langsamer" laufen zu lassen, generiere 
dir lieber ein Enable-Signal, das eben z.B. alle Sekunde einmal kommt 
und dein "langsamer" Zähler zählt immer nur weiter, wenn zum Zeitpunkt 
der Clocks dieser Enable anliegt...

von VHDL-Neuling (Gast)


Lesenswert?

ok,

@bigr:

jetzt bin ich auch au die 23Bit gekommen:
25 MHz = Zykelzeit von 40 ns
3 Hz (niederwertigste Bitstelle) = Zykelzeit von 1/3 s

Der Zykel von slow_clk muss jetzt 0.3333 / ( 4 * 10^-8 ) = 8333333.25 
mal länger sein als von clk

->  ln 8333333 / ln 2 ergibt die gesuchte Grösse,
leider einwenig spät ;)

@tester

Greif in vhdl einfachen das 23. Bit deines Zählers ab und verwende das
als dein slow_clk.
kannst du das mal in code zusammenfassen?

danke für die tollen antworten

von Mike (Gast)


Lesenswert?

@Schlumpf: wieso soll man den Ausgang Zählers nicht aus Taktquelle 
benutzen können? Ich habe es mir gerade noch mal im ISE angeschaut: dort 
wird der Zähler (wie erwartet) als Synchronzähler umgesetzt. Der 
versorgt alle FF mit dem gleichen Takt und die Antwortzeit lässt sich so 
sehr gut vorhersagen.

von VHDL-Neuling (Gast)


Lesenswert?

der 10-Bit-Binärzähler, der durch zwei Tasten gesteuert werden kann:
Button1 Button2 Zähler
'1'  '1'  steht
'0'  '1'  zählt aufwärts
'1'  '0'  zählt abwärts
'0'  '0'  steht


Der Takt für den Zähler ist das Signal 'clk', das Signal 'RButton' kann 
als Reset-Signal genutzt werden:

entity TenBitCounter is
  generic (size: integer := 23);
  port(clk: in std_logic;
      RButton: in std_logic;
      Rbutton1: in std_logic;
      RButton2: in std_logic;
      o_Count: out std_logic_vector(size-1 downto 0));
end TenBitCounter;

architecture behaviour of TenBitCounter is
  signal countRegister: std_logic_vector(size-1 downto 0);
  signal slow_clk: std_logic;
begin
  process(clk,RButton)
  begin
  --
  if(rising_edge(clk)) then
    if(RButton = '0') then
      countRegister <= (others => '0');
    elsif((RButton1='0' and RButton2='1') or (RButton1='1' and 
RButton2='0')) then
      if(RButton1='0' and RButton2='1') then
        countRegister <= countRegister + 1;
      else
        countRegister <= countRegister - 1;
      end if;
      -- Zaehlerueberlauf
      if(countRegister > "1111111111") then
        slow_clk <= countRegister(22); -- das 23ste Bit an slow_clk 
zuweisen
        if(countRegister(22) = '1') then
          countRegister <= (others => '0');
        end if;
      end if;
    end if;
  end if;
end process;
o_Count <= countRegister;
end behaviour;


ist das so richtig ?

gruss
VHDL-Neuling

von bigr (Gast)


Lesenswert?

Sieht fast ganz gut aus.

Vergiss nicht die Taster einzusynchronisieren. (Metastabilität)

Hier vergleichst du aber nur auf 10 Bit ! Das heisst, wenn dein 
Zählerwert größer als die "1111111111" (1023d) ist wird dein slow_clk <= 
countreg(22).
1
 if(countRegister > "1111111111") then
Was passiert mit slow_clk, wenn dein Zähler kleiner als 1023 ist?
Ich denke -so auf die schnelle-, dass du an deinem slow_clk immer nur 
'0' anliegen hast. Simmulier das mal.

von Schlumpf (Gast)


Lesenswert?

@ Mike:

Der Ausgang des Zählers, den du als langsamen Takt verwendest, hat 
gegenüber des ursprünglichen Taktes einen Phasenversatz (aufgrund der 
Einschwingzeit deiner Register des Zählers)
Nun verwendest du dieses genaugenommen kombinatorische Signal, als Takt 
für deine weitere Schaltung. Das heisst doch, dass die Register des 
"langsameren" Schaltungsteils ihre Takte nicht mehr phasengleich zum 
Systemtakt (schnell) bekommen.
Wenn du die von deinem "langsamen" Schaltungsteil erzeugten Signale 
wieder in einem mit dem schnellen Takt versorten Schaltungsteil 
weiterverarbeitest, können diese Probleme auftreten.

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.