Hallo,
ich habe das Beispiel vom Herrn Miller implementiert, in dem er das
Trägersignal auf 1 kHz reduziert (prescaled):
1 | library IEEE;
|
2 | use IEEE.STD_LOGIC_1164.ALL;
|
3 | use IEEE.NUMERIC_STD.ALL;
|
4 |
|
5 | entity PWM is
|
6 | Generic ( width: natural := 8; -- Breite
|
7 | fclk : integer := 50000000; -- Taktfrequenz
|
8 | fpwm : integer := 1000 -- PWM-Frequenz
|
9 | );
|
10 | Port ( clk : in std_logic;
|
11 | pwmvalue : in std_logic_vector (width-1 downto 0);
|
12 | pwmout : out std_logic
|
13 | );
|
14 | end PWM;
|
15 |
|
16 | architecture Behavioral of PWM is
|
17 | signal cnt : integer range 0 to 2**width-2 := 0;
|
18 | signal pre : integer range 0 to fclk/(fpwm*(2**width-2)) := 0;
|
19 | begin
|
20 | -- Vorteiler teilt FPGA-Takt auf PWM-Frequenz*Zählschritte
|
21 | process begin
|
22 | wait until rising_edge(clk);
|
23 | if (pre<fclk/(fpwm*(2**width))) then
|
24 | pre <= pre+1;
|
25 | else
|
26 | pre <= 0;
|
27 | end if;
|
28 | end process;
|
29 |
|
30 | -- PWM-Zähler
|
31 | process begin
|
32 | wait until rising_edge(clk);
|
33 | if (pre=0) then
|
34 | if (cnt<2**width-2) then cnt <= cnt+1;
|
35 | else cnt <= 0;
|
36 | end if;
|
37 | end if;
|
38 | end process;
|
39 |
|
40 | -- Vergleicher, registriert für Ausgabe auf IO-Pin ohne Glitches
|
41 | process begin
|
42 | wait until rising_edge(clk);
|
43 | if (cnt>=to_integer(unsigned(pwmvalue))) then pwmout <= '0';
|
44 | else pwmout <= '1';
|
45 | end if;
|
46 | end process;
|
47 | end Behavioral;
|
Die Simulation (siehe Anhang) zeigt jedoch unterschiedliche Frequenzen
des pwmout und nicht die gewünschte 1 kHz. Es scheint, als ob man hier
keine Pulsweitenmodulation beabsichtigt, sondern eine
Pulsfrequenzmodulation. Obwohl der code eigentlich nachvollziebar ist
und genau das tut, was er tuen muss, gibt es trotzdem irgendwo noch
einen Fehler! Hat jemand bereits damit Erfahrung gemacht?
Für jede Hilfe wäre ich dankbar