Very fast PWM in Cyclone III FPGA

S

Steffen Koepf

Hello,

i need a very fast PWM in a Cyclone III FPGA.
If necessary, a Cyclone IV will do it too.

I need a 80 KHz PWM for direct Gate Control in a Switchmode Power Supply.

At the moment the Cyclone III is running at 400 MHz, which gives at 80 KHz
5000 Steps. I made it to be able to use the falling edge in my PWM-
Comparator, too, so i have now 10000 Steps at 80 KHz.

But the resolution is still not enough, i would like to have more steps.

Using a -6 speed grade Cyclone III would allow 600 MHz, which gives around
15000 Steps.

Does one know a way to get even more?
Is there a way to use the SERDES LVDS to get a fast PWM?

Is it possible to use the PLL to generate higher frequencies and use them
for example by ANDing them for 4 sub-steps (two more bits)?


Thanks in advance,

Steffen
 
K

kclo4

Hello,

i need a very fast PWM in a Cyclone III FPGA.
If necessary, a Cyclone IV will do it too.

I need a 80 KHz PWM for direct Gate Control in a Switchmode Power Supply.

At the moment the Cyclone III is running at 400 MHz, which gives at 80 KHz
5000 Steps. I made it to be able to use the falling edge in my PWM-
Comparator, too, so i have now 10000 Steps at 80 KHz.
Why don't you use a NCO? you can have resolution under 1Hz
 
T

Topi

I need a 80 KHz PWM for direct Gate Control in a Switchmode Power Supply.

At the moment the Cyclone III is running at 400 MHz, which gives at 80 KHz
5000 Steps. I made it to be able to use the falling edge in my PWM-
Comparator, too, so i have now 10000 Steps at 80 KHz.

Here is an example of PWM generator with sub-cycle (average) accuracy:

input_max is the resolution of pwm you want.
count_num defines the pwm frequency.

Does it fit to your needs?

- Topi

********
library ieee;
use ieee.std_logic_1164.all;

entity pwm_gen_fast is
generic(
input_max: integer := 1e6; -- PWM input range max value.
count_num: integer := 100e6/80e3 -- number of clk cycles of one PWM
cycle.
);
port(
clk_in: in std_logic;
pwm_in: in integer range 0 to input_max;
pwm_out: out std_logic
);
end;

architecture synth of pwm_gen_fast is
constant rat_val: integer := (input_max)/(count_num);
signal store: integer range 0 to input_max := 0;
signal counter: integer range 0 to count_num-1 := 0;
signal pwm: std_logic;
begin
process(clk_in)
variable new_store: integer range 0 to input_max+rat_val := 0;
variable rst_counter: boolean;
variable new_pwm: std_logic;
variable new_counter : integer;
begin
if rising_edge(clk_in) then
rst_counter := false;
new_pwm := pwm;

new_store := store;
if new_store < pwm_in then
new_store := new_store + rat_val;
end if;

if counter = count_num-1 then
new_counter := 0;
rst_counter := true;
else
new_counter := counter + 1;
end if;

if rst_counter then
new_store := new_store - pwm_in;
store <= new_store;
end if;

if new_counter = 0 then
new_pwm := '1';
end if;
if new_store >= pwm_in then
new_pwm := '0';
end if;

pwm <= new_pwm;
counter <= new_counter;
store <= new_store;
end if;
end process;

pwm_out <= pwm;
end;

library ieee;
use ieee.std_logic_1164.all;

entity tb_pwm_gen_fast is
end;

architecture tb of tb_pwm_gen_fast is
signal clk: std_logic;
signal pwm_in: integer range 0 to 100 := 0;
signal pwm_out: std_logic;
begin
DUT: entity work.pwm_gen_fast
generic map(
input_max => 100,
count_num => 10
)
port map(
clk_in => clk,
pwm_in => pwm_in,
pwm_out => pwm_out
);

process
begin
clk <= '0';
wait for 500 ns;
clk <= '1';
wait for 500 ns;
end process;

process
begin
pwm_in <= 1;
wait for 5000 us;
pwm_in <= 80;
wait for 1000 us;
pwm_in <= 82;
wait for 1000 us;
pwm_in <= 100;
wait for 1000 us;
pwm_in <= 99;
wait for 1000 us;
assert false report "all done" severity failure;
wait;
end process;
end;
********
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,744
Messages
2,569,482
Members
44,900
Latest member
Nell636132

Latest Threads

Top