• No se han encontrado resultados

Modelado mediante bloque process

3.7. Unidad aritm´etico l´ ogica (ALU)

3.7.2. Modelado mediante bloque process

El comportamiento de la ALU tambi´en puede ser descrito empleando un bloque process sensible a tres se˜nales: los dos operandos y la se˜nal de selecci´on de la operaci´on.

--- -- ALU

-- architecture: bloque process

library IEEE;

use IEEE.std_logic_1164.all;

use IEEE.numeric_std.all;

use work.ALU_CONSTANTS.all;

architecture ALU_bloqueProcess of ALU is begin

begin

case mode is

when "000" => C <= std_logic_vector(signed(A)+signed(A));

when "001" => C <= std_logic_vector(signed(A)+signed(B));

when "010" => C <= std_logic_vector(signed(A)-signed(B));

when "011" => C <= std_logic_vector(-signed(A));

when "100" => C <= A and B;

when "101" => C <= A or B;

when "110" => C <= A xor B;

when others => C <= not A;

end case;

end process;

end architecture ALU_bloqueProcess;

---

3.7.3 Programación del banco de pruebas

Como hemos visto en otros ejemplos, el banco de pruebas est´a t´ıpicamente for- mado por las tres partes siguientes: el dispositivo que va a ser probado (UUT), el c´odigo para la generaci´on de los vectores de test y el c´odigo para comprobar los resultados del test.

A´un en el caso de una ALU sencilla como esta, examinar que la ALU realiza correctamente las operaciones para todos los posibles valores de los operadores consumir´ıa bastante tiempo. En la pr´actica esta t´ecnica ser´ıa inviable, por lo cual debe seleccionarse un conjunto de vectores de test, por ejemplo, atendiendo a los criterios siguientes:

– Se escogen valores de los operandos entorno al cero. Por ejemplo: −2, −1, 0, 1 y 2.

– Se escogen valores de los operandos en el l´ımite inferior de su rango. Si

MIN_NEG_DATA representa el valor m´ınimo que puede tomar el operando, entonces se escogen los valoresMIN_NEG_DATA, . . . ,MIN_NEG_DATA+4 para cada uno de los operandos.

– Se escogen valores de los operandos en el l´ımite superior de su rango. Si

MAX_POS_DATA representa el valor m´aximo que puede tomar el operando, entonces se escogen los valoresMAX_POS_DATA-4, . . . ,MAX_POS_DATApara cada uno de los operandos.

– Finalmente, se escogen algunos valores “al azar”, m´as o menos distribuidos uniformemente en el rango de los operandos.

Se ha definido un package con las constantes globales del banco de pruebas, cuyo valor es calculado a partir de las constantes globales de la ALU.

--- -- Definici´on de constantes globales

-- del banco de pruebas de la ALU

use work.ALU_CONSTANTS.all;

package TB_ALU_CONSTANTS is

constant SEL_MAX : integer := 2**SEL_BITS - 1;

constant MAX_POS_DATA : integer := 2**(WIDTH-1) - 1;

constant MIN_NEG_DATA : integer := -2**(WIDTH-1);

constant DELAY : time := 10 ns;

end package TB_ALU_CONSTANTS;

---

A continuaci´on se muestra el c´odigo del banco de pruebas.

--- -- Banco de pruebas para la ALU

library IEEE;

use IEEE.std_logic_1164.all;

use IEEE.numeric_std.all;

use work.ALU_CONSTANTS.all;

use work.TB_ALU_CONSTANTS.all;

entity TB_ALU is

constant PERIOD : time := 100 ns;

end entity TB_ALU;

architecture TB_ALU of TB_ALU is

signal A,B,C : std_logic_vector (WIDTH-1 downto 0);

signal mode : std_logic_vector (SEL_BITS-1 downto 0);

component ALU is

port ( C : out std_logic_vector (WIDTH-1 downto 0); A, B : in std_logic_vector (WIDTH-1 downto 0); mode : in std_logic_vector (SEL_BITS-1 downto 0) );

end component ALU;

-- Procedure que calcula C (expected_C) y lo compara con el -- valor de C que se pasa como argumento (actual_C)

-- Si ambos valores no coinciden, se muestra un mensaje y se -- incrementa el contador de errores (error_count)

procedure check_ALU

( i, j, k : in integer;

actual_C : in std_logic_vector (WIDTH-1 downto 0); error_count : inout integer ) is

variable expected_C : integer;

begin case k is

when 0 => expected_C := i*2;

when 1 => expected_C := i+j;

when 2 => expected_C := i-j;

when 3 => expected_C := -i;

when 4 => expected_C := TO_INTEGER(signed(

std_logic_vector(TO_SIGNED(i,WIDTH)) and std_logic_vector(TO_SIGNED(j,WIDTH)) ));

when 5 => expected_C := TO_INTEGER(signed(

std_logic_vector(TO_SIGNED(i,WIDTH)) or std_logic_vector(TO_SIGNED(j,WIDTH)) ));

when 6 => expected_C := TO_INTEGER(signed(

std_logic_vector(TO_SIGNED(i,WIDTH)) xor std_logic_vector(TO_SIGNED(j,WIDTH)) ));

when others => expected_C := TO_INTEGER(signed(

not std_logic_vector(TO_SIGNED(i,WIDTH)) ));

end case;

expected_C := TO_INTEGER(TO_SIGNED(expected_C,WIDTH));

-- Trunca el resultado a WIDTH bits

assert( expected_C = TO_INTEGER(signed(actual_C)) )

report "ERROR. Ops: " & integer’image(i) & "," & integer’image(j) & ", Operacion: " & integer’image(k) &

", resultado esperado: " &

integer’image(expected_C) & ", resultado actual: " &

integer’image(TO_INTEGER(signed(actual_C))) & "en el instante " &

time’image(now);

if (expected_C /= TO_INTEGER(signed(actual_C))) then

error_count := error_count + 1;

end if;

end procedure check_ALU;

-- Fin de la definici´on del procedure

begin

UUT : component ALU port map (C, A, B, mode);

-- bloque process para generar los vectores de test y -- comprobar el resultado

main : process is

variable error_count : integer := 0;

report "Comienza la simulaci´on";

-- Vectores de test: operandos con valor pr´oximo a cero

for i in -2 to 2 loop for j in -2 to 2 loop

for k in 0 to SEL_MAX loop

A <= std_logic_vector(TO_SIGNED(i,WIDTH)); b <= std_logic_vector(TO_SIGNED(j,WIDTH)); mode <= std_logic_vector(TO_SIGNED(k,SEL_BITS));

wait for DELAY;

check_ALU(i, j, k, C, error_count);

end loop;

end loop;

end loop;

-- Vectores de test: operandos con valor pr´oximo al m´ınimo

for i in MIN_NEG_DATA to MIN_NEG_DATA+4 loop for j in MIN_NEG_DATA to MIN_NEG_DATA+4 loop

for k in 0 to SEL_MAX loop

A <= std_logic_vector(TO_SIGNED(i,WIDTH)); b <= std_logic_vector(TO_SIGNED(j,WIDTH)); mode <= std_logic_vector(TO_SIGNED(k,SEL_BITS));

wait for DELAY;

check_ALU(i, j, k, C, error_count);

end loop;

end loop;

end loop;

-- Vectores de test: operandos con valor pr´oximo al m´aximo

for i in MAX_POS_DATA-4 to MAX_POS_DATA loop for j in MAX_POS_DATA-4 to MAX_POS_DATA loop

for k in 0 to SEL_MAX loop

A <= std_logic_vector(TO_SIGNED(i,WIDTH)); b <= std_logic_vector(TO_SIGNED(j,WIDTH)); mode <= std_logic_vector(TO_SIGNED(k,SEL_BITS));

wait for DELAY;

check_ALU(i, j, k, C, error_count);

end loop;

end loop;

end loop;

-- Vectores de test: operandos con valores al azar

for i in 0 to 9 loop for j in 0 to 9 loop

A <= std_logic_vector(TO_SIGNED(41*i-273,WIDTH)); b <= std_logic_vector(TO_SIGNED(89*j-384,WIDTH)); mode <= std_logic_vector(TO_SIGNED(k,SEL_BITS));

wait for DELAY;

check_ALU(41*i-273, 89*j-384, k, C, error_count);

end loop;

end loop;

end loop;

wait for DELAY;

-- Informe mostrando el resultado del test

if (error_count=0) then

report "Finaliza la simulaci´on: 0 errores";

else

report "Finaliza la simulaci´on: " & integer’image(error_count) & "errores";

end if;

wait; -- Termina la simulaci´on

end process main;

end architecture TB_ALU;

---

Documento similar