Altera_Forum
Honored Contributor
13 years agoFixed Point VHDL Support in Quartus
I am asking how people have found the synthesis results with the new VHDL2008 package for fixed point. I have created a design that is a cascaded filter simulating a three phase RL load for a motor control application. I haven't synthesized it into quartus yet, but even if it compiles just fine, I am wondering if anyone in the community at large has had any issues with the implementation of these packages in Quartus?
This will be very influential in doing various types of controllers; PI, sliding mode, model reference adaptive control, etc . . . Thanks, James
library IEEE;
use IEEE.STD_LOGIC_1164.all;
use ieee.numeric_std.all;
use ieee.math_real.all;
use ieee.fixed_pkg.all;
entity ModelVoltage is
port(
MCLK : in STD_LOGIC;
HRST : in STD_LOGIC;
START : in std_logic;
VA : in STD_LOGIC;
VB : in STD_LOGIC;
VC : in STD_LOGIC;
DCBUSVOLTS : in STD_LOGIC_VECTOR(11 downto 0);
VAx : out sfixed(16 downto -16);
VBx : out sfixed(16 downto -16);
VCx : out sfixed(16 downto -16);
Vn : out sfixed(16 downto -16);
IA : out sfixed(16 downto -16);
IB : out sfixed(16 downto -16);
IC : out sfixed(16 downto -16);
DONE : out std_logic
);
end ModelVoltage;
architecture RTL of ModelVoltage is
type stateType is (S0,S1,S2,S3,S4,S5,S6,S7,S8);
signal state : stateType;
constant Cx: integer := 8;
constant Dx: integer := 16;
constant R : integer := 16;
constant N : integer := 16;
constant P : integer := 16;
constant M : integer := 40;
type abcType is record
a : sfixed(R downto -N);
b : sfixed(R downto -N);
c : sfixed(R downto -N);
n : sfixed(R downto -N);
nX : sfixed(R downto -N);
aR : sfixed(P downto -M);
bR : sfixed(P downto -M);
cR : sfixed(P downto -M);
aV : sfixed(R downto -N);
bV : sfixed(R downto -N);
cV : sfixed(R downto -N);
aVk1 : sfixed(R downto -N);
bVk1 : sfixed(R downto -N);
cVk1 : sfixed(R downto -N);
ak : sfixed(P downto -M);
bk : sfixed(P downto -M);
ck : sfixed(P downto -M);
ak1 : sfixed(P downto -M);
bk1 : sfixed(P downto -M);
ck1 : sfixed(P downto -M);
end record;
signal v : abcType;
signal i : abcType;
constant RecipThree : sfixed(8 downto -8) := to_sfixed(0.333,8,-8);
constant Rx : sfixed(8 downto -8) := to_sfixed(0.55,8,-8);
constant Ts2 : sfixed(8 downto -24) := to_sfixed(0.0004,8,-24);
begin
process(all) begin
if HRST then
v.a <= to_sfixed(0,R,-N);
v.b <= to_sfixed(0,R,-N);
v.c <= to_sfixed(0,R,-N);
elsif rising_edge(MCLK) then
if START then
if VA then
v.a <= to_sfixed(signed(DCBUSVOLTS),R,-N);
else
v.a <= to_sfixed(-200,R,-N);
end if;
if VB then
v.b <= to_sfixed(signed(DCBUSVOLTS),R,-N);
else
v.b <= to_sfixed(-200,R,-N);
end if;
if VC then
v.c <= to_sfixed(signed(DCBUSVOLTS),R,-N);
else
v.c <= to_sfixed(-200,R,-N);
end if;
end if;
end if;
end process;
VAx <= v.Av;
VBx <= v.Bv;
VCx <= v.Cv;
process(all) begin
if HRST then
v.n <= to_sfixed(0,R,-N);
elsif rising_edge(MCLK) then
if state = S2 then
v.n <= resize((v.a + v.b + v.c),R,-N);
end if;
end if;
end process;
process(all) begin
if HRST then
v.nX <= to_sfixed(0,R,-N);
elsif rising_edge(MCLK) then
if state = S3 then
v.nX <= resize(RecipThree*v.n,R,-N);
end if;
end if;
end process;
/*--------------------------------
Resistive voltage drop
--------------------------------*/
process(all) begin
if HRST then
v.aR <= to_sfixed(0,P,-M);
v.bR <= to_sfixed(0,P,-M);
v.cR <= to_sfixed(0,P,-M);
elsif rising_edge(MCLK) then
if state = S4 then
v.aR <= resize(Rx*i.ak,P,-M);
v.bR <= resize(Rx*i.bk,P,-M);
v.cR <= resize(Rx*i.ck,P,-M);
end if;
end if;
end process;
process(all) begin
if HRST then
v.aV <= to_sfixed(0,R,-N);
v.bV <= to_sfixed(0,R,-N);
v.cV <= to_sfixed(0,R,-N);
elsif rising_edge(MCLK) then
if state = S5 then
v.aV <= resize((v.a - v.aR - v.nX),R,-N);
v.bV <= resize((v.b - v.bR - v.nX),R,-N);
v.cV <= resize((v.c - v.cR - v.nX),R,-N);
end if;
end if;
end process;
process(all) begin
if HRST then
i.ak <= to_sfixed(0,P,-M);
i.bk <= to_sfixed(0,P,-M);
i.ck <= to_sfixed(0,P,-M);
elsif rising_edge(MCLK) then
if state = S6 then
i.ak <= resize(((v.aV + v.aVk1)*Ts2 + i.ak1),P,-M);
i.bk <= resize(((v.bV + v.bVk1)*Ts2 + i.bk1),P,-M);
i.ck <= resize(((v.cV + v.cVk1)*Ts2 + i.ck1),P,-M);
end if;
end if;
end process;
process(all) begin
if HRST then
i.ak1 <= to_sfixed(0,P,-M);
i.bk1 <= to_sfixed(0,P,-M);
i.ck1 <= to_sfixed(0,P,-M);
v.aVk1 <= to_sfixed(0,R,-N);
v.bVk1 <= to_sfixed(0,R,-N);
v.cVk1 <= to_sfixed(0,R,-N);
elsif rising_edge(MCLK) then
if state = S7 then
i.ak1 <= i.ak;
i.bk1 <= i.bk;
i.ck1 <= i.ck;
v.aVk1 <= v.aV;
v.bVk1 <= v.bV;
v.cVk1 <= v.cV;
end if;
end if;
end process;
IA <= i.ak(16 downto -16);
IB <= i.bk(16 downto -16);
IC <= i.ck(16 downto -16);
process(all) begin
if HRST then
state <= S0;
done <= '0';
elsif rising_edge(MCLK) then
case state is
when S0 =>
if START then
state <= S1;
else
state <= S0;
end if;
done <= '0';
when S1 =>
state <= S2;
when S2 =>
state <= S3;
when S3 =>
state <= S4;
when S4 =>
state <= S5;
when S5 =>
state <= S6;
when S6 =>
state <= S7;
when S7 =>
state <= S0;
done <= '1';
when others =>
null;
end case;
end if;
end process;
end RTL;