Subroutine in VHDL?

D

Dan Kuechle

Guest
I'm trying to use a subroutine (subprogram procedure) in my testbench to
(eventually) simulate processor reads and writes. When I compile and try to
simulate(Xilinx ISE 6.1i and Modelsim) I get "# ERROR: testbench.vhd(34):
Cannot drive signal in3 from this subprogram." Any idea why? Can it be
corrected?

Thanks

Dan


LIBRARY ieee;
USE ieee.std_logic_1164.ALL;
USE ieee.numeric_std.ALL;

ENTITY testbench IS
END testbench;

ARCHITECTURE behavior OF testbench IS
COMPONENT tb_subroutine
PORT( clk : IN std_logic;
reset : IN std_logic;
in1 : IN std_logic;
in2 : IN std_logic;
in3 : IN std_logic;
out1 : OUT std_logic;
out2 : OUT std_logic;
out3 : OUT std_logic
);
END COMPONENT;

SIGNAL clk : std_logic;
SIGNAL reset : std_logic;
SIGNAL in1 : std_logic;
SIGNAL in2 : std_logic;
SIGNAL in3 : std_logic;
SIGNAL out1 : std_logic;
SIGNAL out2 : std_logic;
SIGNAL out3 : std_logic;

procedure set_in3
--subroutine
begin
in3 <= '1';
end procedure set_in3;

BEGIN

gen_clk : process(clk)
begin
if (clk = '0') then
clk <= '1' after 6.25 ns; --12.5 period = 80mhz
else
clk <= '0' after 6.25 ns;
end if;
end process;

uut: tb_subroutine PORT MAP(
clk => clk,
reset => reset,
in1 => in1,
in2 => in2,
in3 => in3,
out1 => out1,
out2 => out2,
out3 => out3
);

-- *** Test Bench - User Defined Section ***
tb : PROCESS
BEGIN
reset <= '1';
in1 <= '0';
in2 <= '0';
in3 <= '0';
wait for 50 ns;
reset <= '0';
wait for 50 ns;
in2 <= '1';
wait for 50 ns;
in1 <= '1';
wait for 50 ns;
set_in3; --call
subroutine
wait for 50 ns;
in3 <= '0';
in2 <= '0';
in1 <= '0';
wait for 50 ns;

END PROCESS;
-- *** End Test Bench - User Defined Section ***

END;
 
Dan Kuechle wrote:
I'm trying to use a subroutine (subprogram procedure) in my testbench to
(eventually) simulate processor reads and writes. When I compile and try to
simulate(Xilinx ISE 6.1i and Modelsim) I get "# ERROR: testbench.vhd(34):
Cannot drive signal in3 from this subprogram."
The procedure may be out of the scope
of the signals it is trying to drive. Related thread:
http://groups.google.com/groups?q=vhdl+procedure+scope+wiggling

-- Mike Treseler
 
If you want to make a general purpose subprogram for
testbenches and put it in a pacakge, you must have
all of the IO on the subprogram interface. As a
general rule of thumb for subprogram IO class
use the following:

Inputs:
------
From UUT: Make them signals
In general:
If you use signal property ('event) must be a signal,
otherwise make it a variable.

Outputs, InOuts:
----------------
To UUT: Make it a signal
To process/other subprogram: variable (so value updates immediately)
For synthesis:
usually used directly in architecture, so make it a signal

You can cheat temporarily by putting the subprogram declaration
in the process, but once you have more than one test architecture
this means you will have to multiple copies of your testbench.

Cheers,
Jim Lewis
p.s. We have are offering our Comprehensive VHDL Introduction
class in Huntsville, AL next week and we cover stuff just like
the above. Details are at:
http://www.synthworks.com/public_vhdl_courses.htm
--
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Jim Lewis
Director of Training mailto:Jim@SynthWorks.com
SynthWorks Design Inc. http://www.SynthWorks.com
1-503-590-4787

Expert VHDL Training for Hardware Design and Verification
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~




Dan Kuechle wrote:

I'm trying to use a subroutine (subprogram procedure) in my testbench to
(eventually) simulate processor reads and writes. When I compile and try to
simulate(Xilinx ISE 6.1i and Modelsim) I get "# ERROR: testbench.vhd(34):
Cannot drive signal in3 from this subprogram." Any idea why? Can it be
corrected?

Thanks

Dan


LIBRARY ieee;
USE ieee.std_logic_1164.ALL;
USE ieee.numeric_std.ALL;

ENTITY testbench IS
END testbench;

ARCHITECTURE behavior OF testbench IS
COMPONENT tb_subroutine
PORT( clk : IN std_logic;
reset : IN std_logic;
in1 : IN std_logic;
in2 : IN std_logic;
in3 : IN std_logic;
out1 : OUT std_logic;
out2 : OUT std_logic;
out3 : OUT std_logic
);
END COMPONENT;

SIGNAL clk : std_logic;
SIGNAL reset : std_logic;
SIGNAL in1 : std_logic;
SIGNAL in2 : std_logic;
SIGNAL in3 : std_logic;
SIGNAL out1 : std_logic;
SIGNAL out2 : std_logic;
SIGNAL out3 : std_logic;

procedure set_in3
--subroutine
begin
in3 <= '1';
end procedure set_in3;

BEGIN

gen_clk : process(clk)
begin
if (clk = '0') then
clk <= '1' after 6.25 ns; --12.5 period = 80mhz
else
clk <= '0' after 6.25 ns;
end if;
end process;

uut: tb_subroutine PORT MAP(
clk => clk,
reset => reset,
in1 => in1,
in2 => in2,
in3 => in3,
out1 => out1,
out2 => out2,
out3 => out3
);

-- *** Test Bench - User Defined Section ***
tb : PROCESS
BEGIN
reset <= '1';
in1 <= '0';
in2 <= '0';
in3 <= '0';
wait for 50 ns;
reset <= '0';
wait for 50 ns;
in2 <= '1';
wait for 50 ns;
in1 <= '1';
wait for 50 ns;
set_in3; --call
subroutine
wait for 50 ns;
in3 <= '0';
in2 <= '0';
in1 <= '0';
wait for 50 ns;

END PROCESS;
-- *** End Test Bench - User Defined Section ***

END;
 
Try use TBGenerator (www.hightech-td.com).



Jim Lewis <Jim@SynthWorks.com> wrote in message news:<3F9443C2.1060804@SynthWorks.com>...
If you want to make a general purpose subprogram for
testbenches and put it in a pacakge, you must have
all of the IO on the subprogram interface. As a
general rule of thumb for subprogram IO class
use the following:

Inputs:
------
From UUT: Make them signals
In general:
If you use signal property ('event) must be a signal,
otherwise make it a variable.

Outputs, InOuts:
----------------
To UUT: Make it a signal
To process/other subprogram: variable (so value updates immediately)
For synthesis:
usually used directly in architecture, so make it a signal

You can cheat temporarily by putting the subprogram declaration
in the process, but once you have more than one test architecture
this means you will have to multiple copies of your testbench.

Cheers,
Jim Lewis
p.s. We have are offering our Comprehensive VHDL Introduction
class in Huntsville, AL next week and we cover stuff just like
the above. Details are at:
http://www.synthworks.com/public_vhdl_courses.htm
--
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Jim Lewis
Director of Training mailto:Jim@SynthWorks.com
SynthWorks Design Inc. http://www.SynthWorks.com
1-503-590-4787

Expert VHDL Training for Hardware Design and Verification
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~




Dan Kuechle wrote:

I'm trying to use a subroutine (subprogram procedure) in my testbench to
(eventually) simulate processor reads and writes. When I compile and try to
simulate(Xilinx ISE 6.1i and Modelsim) I get "# ERROR: testbench.vhd(34):
Cannot drive signal in3 from this subprogram." Any idea why? Can it be
corrected?

Thanks

Dan


LIBRARY ieee;
USE ieee.std_logic_1164.ALL;
USE ieee.numeric_std.ALL;

ENTITY testbench IS
END testbench;

ARCHITECTURE behavior OF testbench IS
COMPONENT tb_subroutine
PORT( clk : IN std_logic;
reset : IN std_logic;
in1 : IN std_logic;
in2 : IN std_logic;
in3 : IN std_logic;
out1 : OUT std_logic;
out2 : OUT std_logic;
out3 : OUT std_logic
);
END COMPONENT;

SIGNAL clk : std_logic;
SIGNAL reset : std_logic;
SIGNAL in1 : std_logic;
SIGNAL in2 : std_logic;
SIGNAL in3 : std_logic;
SIGNAL out1 : std_logic;
SIGNAL out2 : std_logic;
SIGNAL out3 : std_logic;

procedure set_in3
--subroutine
begin
in3 <= '1';
end procedure set_in3;

BEGIN

gen_clk : process(clk)
begin
if (clk = '0') then
clk <= '1' after 6.25 ns; --12.5 period = 80mhz
else
clk <= '0' after 6.25 ns;
end if;
end process;

uut: tb_subroutine PORT MAP(
clk => clk,
reset => reset,
in1 => in1,
in2 => in2,
in3 => in3,
out1 => out1,
out2 => out2,
out3 => out3
);

-- *** Test Bench - User Defined Section ***
tb : PROCESS
BEGIN
reset <= '1';
in1 <= '0';
in2 <= '0';
in3 <= '0';
wait for 50 ns;
reset <= '0';
wait for 50 ns;
in2 <= '1';
wait for 50 ns;
in1 <= '1';
wait for 50 ns;
set_in3; --call
subroutine
wait for 50 ns;
in3 <= '0';
in2 <= '0';
in1 <= '0';
wait for 50 ns;

END PROCESS;
-- *** End Test Bench - User Defined Section ***

END;
 

Welcome to EDABoard.com

Sponsor

Back
Top