OpenCores
URL https://opencores.org/ocsvn/rsa_512/rsa_512/trunk

Subversion Repositories rsa_512

Compare Revisions

  • This comparison shows the changes necessary to convert path
    /rsa_512
    from Rev 2 to Rev 3
    Reverse comparison

Rev 2 → Rev 3

/trunk/bench/test_512.vhd
0,0 → 1,442
--------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 17:40:28 12/13/2009
-- Design Name:
-- Module Name:
-- Project Name: ciosspartan
-- Target Device:
-- Tool versions:
-- Description:
--
-- VHDL Test Bench Created by ISE for module: rsa_top
--
-- Dependencies:
--
-- Revision:
-- Revision 0.01 - File Created
-- Additional Comments:
--
-- Notes:
-- This testbench has been automatically generated using types std_logic and
-- std_logic_vector for the ports of the unit under test. Xilinx recommends
-- that these types always be used for the top-level I/O of a design in order
-- to guarantee that the testbench will bind correctly to the post-implementation
-- simulation model.
--------------------------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.std_logic_unsigned.all;
use ieee.numeric_std.all;
 
entity test_rsa_512 is
end test_rsa_512;
 
architecture behavior of test_rsa_512 is
 
-- Component Declaration for the Unit Under Test (UUT)
 
component rsa_top
port(
clk : in std_logic;
reset : in std_logic;
valid_in : in std_logic;
x : in std_logic_vector(15 downto 0);
y : in std_logic_vector(15 downto 0);
m : in std_logic_vector(15 downto 0);
r_c : in std_logic_vector(15 downto 0);
n_c : in std_logic_vector(15 downto 0);
s : out std_logic_vector(15 downto 0);
valid_out : out std_logic;
bit_size : in std_logic_vector(15 downto 0)
);
end component;
 
 
--Inputs
signal clk : std_logic := '0';
signal reset : std_logic := '0';
signal valid_in : std_logic := '0';
signal x : std_logic_vector(15 downto 0) := (others => '0');
signal y : std_logic_vector(15 downto 0) := (others => '0');
signal m : std_logic_vector(15 downto 0) := (others => '0');
signal r_c : std_logic_vector(15 downto 0) := (others => '0');
signal n_c : std_logic_vector(15 downto 0) := (others => '0');
signal bit_size : std_logic_vector(15 downto 0) := x"0200";
--Outputs
signal s : std_logic_vector(15 downto 0);
signal valid_out : std_logic;
 
-- Clock period definitions
constant clk_period : time := 1ns;
 
begin
 
-- Instantiate the Unit Under Test (UUT)
uut : rsa_top port map (
clk => clk,
reset => reset,
valid_in => valid_in,
x => x,
y => y,
m => m,
r_c => r_c,
n_c => n_c,
s => s,
valid_out => valid_out,
bit_size => bit_size
);
 
-- Clock process definitions
clk_process : process
begin
clk <= '0';
wait for clk_period/2;
clk <= '1';
wait for clk_period/2;
end process;
 
 
-- Stimulus process
stim_proc : process
begin
valid_in <= '0';
-- hold reset state for 100ms.
reset <= '1';
wait for 10ns;
reset <= '0';
wait for clk_period*10;
 
-- insert stimulus here
 
--n_c and valid signal and the r_c constant are also required
n_c <= x"738f";
valid_in <= '1';
x <= x"f3ad";
y <= x"42b1";
m <= x"b491";
r_c <= x"f579";
wait for clk_period;
x <= x"8e40";
y <= x"1ad3";
m <= x"1417";
r_c <= x"6ee9";
wait for clk_period;
x <= x"6af9";
y <= x"a827";
m <= x"b498";
r_c <= x"972d";
wait for clk_period;
x <= x"4e63";
y <= x"0d64";
m <= x"e1b7";
r_c <= x"5052";
wait for clk_period;
x <= x"9600";
y <= x"3f76";
m <= x"e47c";
r_c <= x"1dca";
wait for clk_period;
x <= x"68f4";
y <= x"6670";
m <= x"b186";
r_c <= x"bc81";
wait for clk_period;
x <= x"5a12";
y <= x"5a1c";
m <= x"93f0";
r_c <= x"377e";
wait for clk_period;
x <= x"d62e";
y <= x"4844";
m <= x"b183";
r_c <= x"04ef";
wait for clk_period;
x <= x"8fc1";
y <= x"d5f2";
m <= x"f8f1";
r_c <= x"3a2a";
wait for clk_period;
x <= x"031d";
y <= x"b65a";
m <= x"eed1";
r_c <= x"291b";
wait for clk_period;
x <= x"f496";
y <= x"034f";
m <= x"0083";
r_c <= x"c159";
wait for clk_period;
x <= x"1268";
y <= x"9635";
m <= x"981c";
r_c <= x"9336";
wait for clk_period;
x <= x"2e5a";
y <= x"386e";
m <= x"6441";
r_c <= x"1bd0";
wait for clk_period;
x <= x"c1d6";
y <= x"fb73";
m <= x"fcd8";
r_c <= x"317d";
wait for clk_period;
x <= x"cd8f";
y <= x"5623";
m <= x"cbf0";
r_c <= x"64b4";
wait for clk_period;
x <= x"e4d2";
y <= x"9041";
m <= x"e3ca";
r_c <= x"8793";
wait for clk_period;
x <= x"36c6";
y <= x"99da";
m <= x"41d9";
r_c <= x"85f5";
wait for clk_period;
x <= x"df4a";
y <= x"cd68";
m <= x"b7a0";
r_c <= x"7c8d";
wait for clk_period;
x <= x"8e40";
y <= x"9a94";
m <= x"146e";
r_c <= x"64d9";
wait for clk_period;
x <= x"6af9";
y <= x"ccc8";
m <= x"4776";
r_c <= x"c7f6";
wait for clk_period;
x <= x"4e63";
y <= x"ed49";
m <= x"ec50";
r_c <= x"fba0";
wait for clk_period;
x <= x"9600";
y <= x"4d25";
m <= x"c07c";
r_c <= x"e3e0";
wait for clk_period;
x <= x"68f4";
y <= x"3b8e";
m <= x"e698";
r_c <= x"b567";
wait for clk_period;
x <= x"5a12";
y <= x"36d5";
m <= x"d85f";
r_c <= x"3172";
wait for clk_period;
x <= x"d62e";
y <= x"3a75";
m <= x"729c";
r_c <= x"111a";
wait for clk_period;
x <= x"8fc1";
y <= x"77a3";
m <= x"19b6";
r_c <= x"1971";
wait for clk_period;
x <= x"d2cd";
y <= x"367f";
m <= x"05d3";
r_c <= x"9f9b";
wait for clk_period;
x <= x"c6e4";
y <= x"68de";
m <= x"cacd";
r_c <= x"b574";
wait for clk_period;
x <= x"4a36";
y <= x"59a4";
m <= x"e16f";
r_c <= x"4a50";
wait for clk_period;
x <= x"f6df";
y <= x"9f89";
m <= x"f67b";
r_c <= x"6d56";
wait for clk_period;
x <= x"061c";
y <= x"ed71";
m <= x"7066";
r_c <= x"bdc6";
wait for clk_period;
x <= x"06c8";
y <= x"059f";
m <= x"08de";
r_c <= x"0400";
wait for clk_period;
valid_in <= '0';
 
--valid_in <='0';
wait for clk_period*200000;
 
--Now with the public key x"10001";
 
bit_size <= x"0011";
valid_in <= '1';
x <= x"f3ad";
y <= x"0001";
m <= x"b491";
r_c <= x"f579";
wait for clk_period;
x <= x"8e40";
y <= x"0001";
m <= x"1417";
r_c <= x"6ee9";
wait for clk_period;
x <= x"6af9";
y <= x"0000";
m <= x"b498";
r_c <= x"972d";
wait for clk_period;
x <= x"4e63";
m <= x"e1b7";
r_c <= x"5052";
wait for clk_period;
x <= x"9600";
m <= x"e47c";
r_c <= x"1dca";
wait for clk_period;
x <= x"68f4";
m <= x"b186";
r_c <= x"bc81";
wait for clk_period;
x <= x"5a12";
m <= x"93f0";
r_c <= x"377e";
wait for clk_period;
x <= x"d62e";
m <= x"b183";
r_c <= x"04ef";
wait for clk_period;
x <= x"8fc1";
m <= x"f8f1";
r_c <= x"3a2a";
wait for clk_period;
x <= x"031d";
m <= x"eed1";
r_c <= x"291b";
wait for clk_period;
x <= x"f496";
m <= x"0083";
r_c <= x"c159";
wait for clk_period;
x <= x"1268";
 
m <= x"981c";
r_c <= x"9336";
wait for clk_period;
x <= x"2e5a";
 
m <= x"6441";
r_c <= x"1bd0";
wait for clk_period;
x <= x"c1d6";
 
m <= x"fcd8";
r_c <= x"317d";
wait for clk_period;
x <= x"cd8f";
 
m <= x"cbf0";
r_c <= x"64b4";
wait for clk_period;
x <= x"e4d2";
 
m <= x"e3ca";
r_c <= x"8793";
wait for clk_period;
x <= x"36c6";
 
m <= x"41d9";
r_c <= x"85f5";
wait for clk_period;
x <= x"df4a";
 
m <= x"b7a0";
r_c <= x"7c8d";
wait for clk_period;
x <= x"8e40";
 
m <= x"146e";
r_c <= x"64d9";
wait for clk_period;
x <= x"6af9";
 
m <= x"4776";
r_c <= x"c7f6";
wait for clk_period;
x <= x"4e63";
 
m <= x"ec50";
r_c <= x"fba0";
wait for clk_period;
x <= x"9600";
 
m <= x"c07c";
r_c <= x"e3e0";
wait for clk_period;
x <= x"68f4";
 
m <= x"e698";
r_c <= x"b567";
wait for clk_period;
x <= x"5a12";
 
m <= x"d85f";
r_c <= x"3172";
wait for clk_period;
x <= x"d62e";
 
m <= x"729c";
r_c <= x"111a";
wait for clk_period;
x <= x"8fc1";
 
m <= x"19b6";
r_c <= x"1971";
wait for clk_period;
x <= x"d2cd";
 
m <= x"05d3";
r_c <= x"9f9b";
wait for clk_period;
x <= x"c6e4";
m <= x"cacd";
r_c <= x"b574";
wait for clk_period;
x <= x"4a36";
m <= x"e16f";
r_c <= x"4a50";
wait for clk_period;
x <= x"f6df";
m <= x"f67b";
r_c <= x"6d56";
wait for clk_period;
x <= x"061c";
m <= x"7066";
r_c <= x"bdc6";
wait for clk_period;
x <= x"06c8";
m <= x"08de";
r_c <= x"0400";
wait for clk_period;
valid_in <= '0';
wait;
end process;
END;
/trunk/rtl/montgomery_mult.vhd
0,0 → 1,366
----------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 20:03:35 11/02/2009
-- Design Name:
-- Module Name: etapas - Behavioral
-- Project Name:
-- Target Devices:
-- Tool versions:
-- Description:
--
-- Dependencies:
--
-- Revision:
-- Revision 0.01 - File Created
-- Additional Comments:
--
----------------------------------------------------------------------------------
library IEEE;
use IEEE.STD_LOGIC_1164.all;
use IEEE.STD_LOGIC_ARITH.all;
use IEEE.STD_LOGIC_UNSIGNED.all;
 
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
 
entity montgomery_mult is
 
port(
clk : in std_logic;
reset : in std_logic;
valid_in : in std_logic;
a : in std_logic_vector(15 downto 0);
b : in std_logic_vector(15 downto 0);
n : in std_logic_vector(15 downto 0);
s_prev : in std_logic_vector(15 downto 0);
n_c : in std_logic_vector(15 downto 0);
s : out std_logic_vector( 15 downto 0);
valid_out : out std_logic -- es le valid out TODO : cambiar nombre
);
 
end montgomery_mult;
 
architecture Behavioral of montgomery_mult is
 
component montgomery_step is
port(
clk : in std_logic;
reset : in std_logic;
valid_in : in std_logic;
a : in std_logic_vector(15 downto 0);
b : in std_logic_vector(15 downto 0);
n : in std_logic_vector(15 downto 0);
s_prev : in std_logic_vector(15 downto 0);
n_c : in std_logic_vector(15 downto 0);
s : out std_logic_vector( 15 downto 0);
valid_out : out std_logic; -- es le valid out TODO : cambiar nombre
busy : out std_logic;
b_req : out std_logic;
a_out : out std_logic_vector(15 downto 0);
 
c_step : out std_logic; --genera un pulso cuando termina su computo para avisar al modulo superior
stop : in std_logic
);
end component;
 
component fifo_512_bram
port (
clk : in std_logic;
rst : in std_logic;
din : in std_logic_vector(15 downto 0);
wr_en : in std_logic;
rd_en : in std_logic;
dout : out std_logic_vector(15 downto 0);
full : out std_logic;
empty : out std_logic);
end component;
 
component fifo_256_feedback
port (
clk : in std_logic;
rst : in std_logic;
din : in std_logic_vector(48 downto 0);
wr_en : in std_logic;
rd_en : in std_logic;
dout : out std_logic_vector(48 downto 0);
full : out std_logic;
empty : out std_logic);
end component;
 
type arr_dat_out is array(0 to 7) of std_logic_vector(15 downto 0);
type arr_val is array(0 to 7) of std_logic;
type arr_b is array(0 to 7) of std_logic_vector(15 downto 0);
 
signal b_reg, next_b_reg : arr_b;
signal valid_mid, fifo_reqs, fifo_reqs_reg, next_fifo_reqs_reg, stops : arr_val;
signal a_out_mid, n_out_mid, s_out_mid : arr_dat_out; --std_logic_vector(15 downto 0);
 
 
signal wr_en, rd_en, empty : std_logic;
signal fifo_out : std_logic_vector(15 downto 0);
 
signal fifo_out_feedback, fifo_in_feedback : std_logic_vector(48 downto 0);
signal read_fifo_feedback, empty_feedback : std_logic;
 
 
signal a_in, s_in, n_in : std_logic_vector(15 downto 0);
signal f_valid, busy_pe : std_logic;
 
--salida c_step del primer PE para ir contando y saber cuando sacar el valor correcto.
signal c_step, reg_c_step : std_logic;
 
 
signal count, next_count : std_logic_vector(7 downto 0);
 
 
signal wr_fifofeed : std_logic;
 
type state_type is (wait_start, process_data, dump_feed);
signal state, next_state : state_type;
signal reg_busy : std_logic;
signal reset_fifos : std_logic;
signal count_feedback, next_count_feedback : std_logic_vector(15 downto 0);
 
begin
 
--Fifo para almacenar b
fifo_b : fifo_512_bram port map (
clk => clk,
rst => reset_fifos,
din => b,
wr_en => wr_en,
rd_en => rd_en,
dout => fifo_out,
empty => empty
);
 
--Fifo para el feedback al primer PE
fifo_feed : fifo_256_feedback port map (
clk => clk,
rst => reset_fifos,
din => fifo_in_feedback,
wr_en => wr_fifofeed,
rd_en => read_fifo_feedback,
dout => fifo_out_feedback,
empty => empty_feedback
);
 
 
 
--Primer PE
et_first : montgomery_step port map(
clk => clk,
reset => reset,
valid_in => f_valid,
a => a_in,
b => b_reg(0),
n => n_in,
s_prev => s_in,
n_c => n_c,
s => s_out_mid(0),
valid_out => valid_mid(0),
busy => busy_pe,
b_req => fifo_reqs(0),
a_out => a_out_mid(0),
n_out => n_out_mid(0),
c_step => c_step,
stop => stops(0)
);
 
--Ultimo PE
et_last : montgomery_step port map(
clk => clk,
reset => reset,
valid_in => valid_mid(6),
a => a_out_mid(6),
b => b_reg(7),
n => n_out_mid(6),
s_prev => s_out_mid(6),
n_c => n_c,
s => s_out_mid(7),
valid_out => valid_mid(7),
b_req => fifo_reqs(7),
a_out => a_out_mid(7),
n_out => n_out_mid(7),
stop => stops(7)
);
 
g1 : for i in 1 to 6 generate
et_i : montgomery_step port map(
clk => clk,
reset => reset,
valid_in => valid_mid(i-1),
a => a_out_mid(i-1),
b => b_reg(i),
n => n_out_mid(i-1),
s_prev => s_out_mid(i-1),
n_c => n_c,
s => s_out_mid(i),
valid_out => valid_mid(i),
b_req => fifo_reqs(i),
a_out => a_out_mid(i),
n_out => n_out_mid(i),
stop => stops(i)
);
 
end generate g1;
 
 
process(clk, reset)
begin
 
if(clk = '1' and clk'event) then
 
if(reset = '1')then
state <= wait_start;
count_feedback <= (others => '0');
reg_busy <= '0';
for i in 0 to 7 loop
b_reg(i) <= (others => '0');
fifo_reqs_reg (i) <= '0';
count <= (others => '0');
reg_c_step <= '0';
 
end loop;
else
state <= next_state;
reg_busy <= busy_pe;
count_feedback <= next_count_feedback;
for i in 0 to 7 loop
b_reg(i) <= next_b_reg(i);
fifo_reqs_reg (i) <= next_fifo_reqs_reg(i);
count <= next_count;
reg_c_step <= c_step;
end loop;
end if;
end if;
 
end process;
 
 
--Proceso combinacional que controla las lecturas a la fifo
process(fifo_reqs_reg, fifo_out, b, fifo_reqs, b_reg, state, empty)
begin
 
 
for i in 0 to 7 loop
next_b_reg(i) <= b_reg(i);
next_fifo_reqs_reg(i) <= fifo_reqs(i);
end loop;
 
if(state = wait_start) then
next_b_reg(0) <= b;
next_fifo_reqs_reg(0) <= '0'; --anulamos la peticion de b
for i in 1 to 7 loop
next_b_reg(i) <= (others => '0');
next_fifo_reqs_reg(i) <= '0';
end loop;
else
for i in 0 to 7 loop
if(fifo_reqs_reg(i) = '1' and empty = '0') then
next_b_reg(i) <= fifo_out;
end if;
end loop;
end if;
end process;
 
--Proceso combinacional fsm principal
process( valid_in, b, state, fifo_reqs, a_out_mid, n_out_mid, s_out_mid, valid_mid, a, s_prev, n, busy_pe, empty_feedback, fifo_out_feedback, count, reg_c_step, reset, reg_busy, count_feedback )
begin
 
--las peticiones a la fifo son las or de los modulos
rd_en <= fifo_reqs(0) or fifo_reqs(1) or fifo_reqs(2) or fifo_reqs(3) or fifo_reqs(4) or fifo_reqs(5) or fifo_reqs(6) or fifo_reqs(7);
next_state <= state;
wr_en <= '0';
fifo_in_feedback <= a_out_mid(7)&n_out_mid(7)&s_out_mid(7)&valid_mid(7);
read_fifo_feedback <= '0';
wr_fifofeed <= '0';
--Controlamos el primer PE
a_in <= a;
s_in <= s_prev;
n_in <= n;
f_valid <= valid_in;
reset_fifos <= reset;
--ponemos las salidas
s <= (others => '0');
valid_out <= '0';
 
--Incrementamos el contador solo cuando el primer PE termina su cuenta
next_count <= count;
next_count_feedback <= count_feedback;
 
if(reg_c_step = '1') then
next_count <= count + 8;
end if;
--durante el ciclo de la pipeline que sea considerado el ultimo, sacamos los datos
if( count = x"20") then
s <= s_out_mid(0);
valid_out <= valid_mid(0);
end if;
 
for i in 0 to 7 loop
stops(i) <= '0';
end loop;
 
case state is
--Esperamos a que tengamos un input y vamos cargando las b's
when wait_start =>
reset_fifos <= '1';
if(valid_in = '1') then
reset_fifos <= '0';
--next_b_reg(0) <= b;
next_state <= process_data;
--wr_en <= '1';
end if;
 
when process_data =>
wr_fifofeed <= valid_mid(7);
if(valid_in = '1') then
wr_en <= '1';
end if;
--Miramos si hay que volver a meter datos a la b
if(empty_feedback = '0' and reg_busy = '0') then
read_fifo_feedback <= '1';
next_state <= dump_feed;
next_count_feedback <= x"0000";
end if;
--Si ya hemos sobrepasado el limite paramos y volvemos a la espera
if( count > x"23") then
next_state <= wait_start;
--y
for i in 0 to 7 loop
stops(i) <= '1';
end loop;
next_count <= (others => '0');
end if;
 
--Vacia la fifo de feedback
when dump_feed =>
if(empty_feedback='0')
then
next_count_feedback <= count_feedback+1;
end if;
wr_fifofeed <= valid_mid(7);
read_fifo_feedback <= '1';
a_in <= fifo_out_feedback(48 downto 33);
n_in <= fifo_out_feedback(32 downto 17);
s_in <= fifo_out_feedback(16 downto 1);
f_valid <= fifo_out_feedback(0);
if(empty_feedback='1') then
next_state <= process_data;
end if;
if(count_feedback = x"22") then
read_fifo_feedback <= '0';
next_state <= process_data;
end if;
end case;
end process;
end Behavioral;
 
/trunk/rtl/pe.vhd
0,0 → 1,133
----------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 20:36:31 10/27/2009
-- Design Name:
-- Module Name: PE - Behavioral
-- Project Name:
-- Target Devices:
-- Tool versions:
-- Description:
--
-- Dependencies:
--
-- Revision:
-- Revision 0.01 - File Created
-- Additional Comments:
--
----------------------------------------------------------------------------------
library IEEE;
use IEEE.STD_LOGIC_1164.all;
use IEEE.STD_LOGIC_ARITH.all;
use IEEE.STD_LOGIC_UNSIGNED.all;
 
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
 
entity pe is
port ( clk : in std_logic;
reset : in std_logic;
a_j : in std_logic_vector(15 downto 0);
b_i : in std_logic_vector(15 downto 0);
s_prev : in std_logic_vector(15 downto 0); --entrada de la s anterior para la suma
m : in std_logic_vector(15 downto 0);
n_j : in std_logic_vector(15 downto 0);
s_next : out std_logic_vector(15 downto 0); --salida con la siguiente s
aj_bi : out std_logic_vector(15 downto 0); --salida de multiplicador reutilizado para calcular a*b
ab_valid_in : in std_logic; --indica que los datos de entrada en el multiplicador son validos
 
ab_valid_out : out std_logic; --indica que la multiplicacion de un a y b validos se ha realizado con exito
valid_out : out std_logic;
fifo_req : out std_logic); --peticion de las siguientes entradas a, b, s, m
end pe;
 
architecture Behavioral of pe is
 
signal prod_aj_bi, next_prod_aj_bi, mult_aj_bi : std_logic_vector(31 downto 0); -- registros para la primera mult
signal prod_nj_m, next_prod_nj_m, mult_nj_m, mult_nj_m_reg : std_logic_vector(31 downto 0);
signal sum_1, next_sum_1 : std_logic_vector(31 downto 0);
signal sum_2, next_sum_2 : std_logic_vector(31 downto 0);
signal ab_valid_reg, valid_out_reg, valid_out_reg2, valid_out_reg3 : std_logic;
signal n_reg, next_n_reg, s_prev_reg, next_s_prev_reg, ab_out_reg : std_logic_vector(15 downto 0);
--signal prod_aj_bi_out, next_prod_aj_bi_out : std_logic_vector(15 downto 0);
 
begin
 
 
mult_aj_bi <= a_j * b_i;
mult_nj_m <= n_reg *m;
 
 
process(clk, reset)
begin
 
if(clk = '1' and clk'event)
then
if(reset = '1') then
prod_aj_bi <= (others => '0');
prod_nj_m <= (others => '0');
sum_1 <= (others => '0');
sum_2 <= (others => '0');
ab_valid_reg <= '0';
n_reg <= (others => '0');
valid_out_reg <= '0';
valid_out_reg2 <= '0';
valid_out_reg3 <= '0';
s_prev_reg <= (others => '0');
else
--prod_aj_bi_out <= next_prod_aj_bi_out;
prod_aj_bi <= next_prod_aj_bi;
prod_nj_m <= next_prod_nj_m;
sum_1 <= next_sum_1;
sum_2 <= next_sum_2;
ab_valid_reg <= ab_valid_in;
ab_out_reg <= mult_aj_bi(15 downto 0);
n_reg <= next_n_reg;
valid_out_reg <= valid_in; --registramos el valid out para sacarle al tiempo de los datos validos
valid_out_reg2 <= valid_out_reg;
valid_out_reg3 <= valid_out_reg2;
s_prev_reg <= next_s_prev_reg;
--mult_nj_m_reg <= mult_nj_m;
end if;
end if;
 
end process;
 
process(s_prev, prod_aj_bi, prod_nj_m, sum_1, sum_2, mult_aj_bi, mult_nj_m, valid_in, ab_valid_reg, n_j, n_reg, valid_out_reg3, s_prev_reg, ab_out_reg)
begin
ab_valid_out <= ab_valid_reg;
aj_bi <= ab_out_reg(15 downto 0); --Sacamos uno de los dos registros de la multiplicacion fuera para el calculo de la constante
s_next <= sum_2(15 downto 0); --salida de la pipe
fifo_req <= valid_in;
valid_out <= valid_out_reg3;
next_sum_1 <= sum_1;
next_sum_2 <= sum_2;
next_prod_nj_m <= prod_nj_m;
next_prod_aj_bi <= prod_aj_bi;
next_n_reg <= n_reg;
next_s_prev_reg <= s_prev_reg;
if(valid_in = '1') then
next_s_prev_reg <= s_prev;
next_n_reg <= n_j;
next_prod_aj_bi <= mult_aj_bi;
next_prod_nj_m <= mult_nj_m; --registramos la multiplicacion de n_j,m
next_sum_1 <= prod_aj_bi+sum_1(31 downto 16)+s_prev_reg;
next_sum_2 <= prod_nj_m+sum_2(31 downto 16) + sum_1(15 downto 0);
else
next_s_prev_reg <= (others => '0');
next_n_reg <= (others => '0');
next_prod_aj_bi <= (others => '0');
next_prod_nj_m <= (others => '0');
next_sum_1 <= (others =>'0');
next_sum_2 <= (others=>'0');
end if;
end process;
 
end Behavioral;
 
/trunk/rtl/pe_wrapper.vhd
0,0 → 1,137
----------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 19:08:19 10/29/2009
-- Design Name:
-- Module Name: montgomery - Behavioral
-- Project Name:
-- Target Devices:
-- Tool versions:
-- Description:
--
-- Dependencies:
--
-- Revision:
-- Revision 0.01 - File Created
-- Additional Comments:
--
----------------------------------------------------------------------------------
library IEEE;
use IEEE.STD_LOGIC_1164.all;
use IEEE.STD_LOGIC_ARITH.all;
use IEEE.STD_LOGIC_UNSIGNED.all;
 
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
 
entity pe_wrapper is
 
port(
clk : in std_logic;
reset : in std_logic;
ab_valid : in std_logic;
valid_in : in std_logic;
a : in std_logic_vector(15 downto 0);
b : in std_logic_vector(15 downto 0);
n : in std_logic_vector(15 downto 0);
s_prev : in std_logic_vector(15 downto 0);
n_c : in std_logic_vector(15 downto 0);
s : out std_logic_vector( 15 downto 0);
data_ready : out std_logic;
fifo_req : out std_logic;
m_val : out std_logic;
reset_the_PE : in std_logic); -- estamos preparados para aceptar el siguiente dato
 
end pe_wrapper;
 
architecture Behavioral of pe_wrapper is
 
component pe is
port ( clk : in std_logic;
reset : in std_logic;
a_j : in std_logic_vector(15 downto 0);
b_i : in std_logic_vector(15 downto 0);
s_prev : in std_logic_vector(15 downto 0); --entrada de la s anterior para la suma
m : in std_logic_vector(15 downto 0);
n_j : in std_logic_vector(15 downto 0);
s_next : out std_logic_vector(15 downto 0); --salida con la siguiente s
aj_bi : out std_logic_vector(15 downto 0); --salida de multiplicador reutilizado para calcular a*b
ab_valid_in : in std_logic; --indica que los datos de entrada en el multiplicador son validos
 
ab_valid_out : out std_logic; --indica que la multiplicacion de un a y b validos se ha realizado con exito
valid_out : out std_logic;
fifo_req : out std_logic);
end component;
 
component m_calc is
port(
clk : in std_logic;
reset : in std_logic;
ab : in std_logic_vector (15 downto 0);
t : in std_logic_vector (15 downto 0);
n_cons : in std_logic_vector (15 downto 0);
m : out std_logic_vector (15 downto 0);
mult_valid : in std_logic;
m_valid : out std_logic);
end component;
 
signal aj_bi, m, next_m, m_out : std_logic_vector(15 downto 0);
signal mult_valid, valid_m, valid_m_reg : std_logic; --lo registro para compararlos
 
begin
 
pe_0 : pe port map(
clk => clk,
reset => reset,
a_j => a,
b_i => b,
s_prev => s_prev,
m => m,
n_j => n,
s_next => s,
aj_bi => aj_bi,
ab_valid_in => ab_valid,
valid_in => valid_in,
ab_valid_out => mult_valid,
valid_out => data_ready,
fifo_req => fifo_req);
 
mcons_0 : m_calc port map(
clk => clk,
reset => reset,
ab => aj_bi,
t => s_prev,
n_cons => n_c,
m => m_out,
mult_valid => mult_valid,
m_valid => valid_m);
 
process(clk, reset)
begin
if(clk='1' and clk'event) then
if(reset='1')then
m <= (others=> '0' );
valid_m_reg <= '0';
else
m <= next_m;
valid_m_reg <= valid_m;
end if;
end if;
end process;
process(m_out,valid_m, valid_m_reg, m)
begin
m_val <= valid_m_reg;
if(valid_m = '1' and valid_m_reg ='0') then
next_m <= m_out;
else
next_m <= m;
end if;
end process;
end Behavioral;
 
/trunk/rtl/rsa_top.vhd
0,0 → 1,496
----------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 16:01:04 12/13/2009
-- Design Name:
-- Module Name: rsa_top - Behavioral
-- Project Name:
-- Target Devices:
-- Tool versions:
-- Description:
--
-- Dependencies:
--
-- Revision:
-- Revision 0.01 - File Created
-- Additional Comments:
--
----------------------------------------------------------------------------------
library IEEE;
use IEEE.STD_LOGIC_1164.all;
use IEEE.STD_LOGIC_ARITH.all;
use IEEE.STD_LOGIC_UNSIGNED.all;
-- synthesis translate_off
library UNISIM;
use UNISIM.VCOMPONENTS.all;
-- synthesis translate_on
 
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
 
entity rsa_top is
port(
clk : in std_logic;
reset : in std_logic;
valid_in : in std_logic;
x : in std_logic_vector(15 downto 0); -- estos 3 son x^y mod m
y : in std_logic_vector(15 downto 0);
m : in std_logic_vector(15 downto 0);
r_c : in std_logic_vector(15 downto 0); --constante de montgomery r^2 mod m
n_c : in std_logic_vector(15 downto 0); --constante necesaria en la multiplicacion
s : out std_logic_vector( 15 downto 0);
valid_out : out std_logic;
bit_size : in std_logic_vector(15 downto 0) --tamano bit del exponente y (log2(y))
);
end rsa_top;
 
architecture Behavioral of rsa_top is
 
 
--Multiplicador de Montgomery que sera instanciado 2 veces
component montgomery_mult is
port(
clk : in std_logic;
reset : in std_logic;
valid_in : in std_logic;
a : in std_logic_vector(15 downto 0);
b : in std_logic_vector(15 downto 0);
n : in std_logic_vector(15 downto 0);
s_prev : in std_logic_vector(15 downto 0);
n_c : in std_logic_vector(15 downto 0);
s : out std_logic_vector( 15 downto 0);
valid_out : out std_logic -- es le valid out TODO : cambiar nombre
);
end component;
 
--Memoria para guardar el exponente y el modulo
component Mem_b
port (
clka : in std_logic;
wea : in std_logic_vector(0 downto 0);
addra : in std_logic_vector(5 downto 0);
dina : in std_logic_vector(15 downto 0);
douta : out std_logic_vector(15 downto 0));
end component;
 
 
--fifos para los resultados de las mult parciales
component res_out_fifo
port (
clk : in std_logic;
rst : in std_logic;
din : in std_logic_vector(31 downto 0);
wr_en : in std_logic;
rd_en : in std_logic;
dout : out std_logic_vector(31 downto 0);
full : out std_logic;
empty : out std_logic);
end component;
 
 
signal valid_in_mon_1, valid_in_mon_2, valid_out_mon_1, valid_out_mon_2, fifo_1_rd, fifo_1_wr : std_logic;
 
signal a_mon_1, b_mon_1, n_mon_1, s_p_mon_1, s_out_mon_1, a_mon_2, b_mon_2, n_mon_2, s_p_mon_2, s_out_mon_2, fifo_1_in, fifo_2_in, fifo_1_out, exp_out, n_out : std_logic_vector(15 downto 0);
 
signal fifo_out, fifo_in : std_logic_vector(31 downto 0);
 
signal addr_exp, addr_n, next_addr_exp, next_addr_n : std_logic_vector(5 downto 0);
 
type state_type is (wait_start, prepare_data, wait_constants, writting_cts_fifo, processing_data_0, processing_data_1, wait_results, transition, prepare_next, writting_results, final_mult, show_final, prepare_final, wait_final);
signal state, next_state : state_type;
signal w_numb, next_w_numb : std_logic_vector(7 downto 0);
 
signal n_c_reg, next_n_c_reg : std_logic_vector(15 downto 0);
--Cuenta los datos que se van metiendo al multiplicador para generar el padding por si solo.
signal count_input, next_count_input, bit_counter, next_bit_counter : std_logic_vector(15 downto 0);
 
signal bsize_reg, next_bsize_reg : std_logic_vector (15 downto 0);
signal write_b_n : std_logic_vector(0 downto 0);
 
begin
 
 
mon_1 : montgomery_mult port map(
clk => clk,
reset => reset,
valid_in => valid_in_mon_1,
a => a_mon_1,
b => b_mon_1,
n => n_mon_1,
s_prev => s_p_mon_1,
n_c => n_c_reg,
s => s_out_mon_1,
valid_out => valid_out_mon_1
);
 
mon_2 : montgomery_mult port map(
clk => clk,
reset => reset,
valid_in => valid_in_mon_2,
a => a_mon_2,
b => b_mon_2,
n => n_mon_2,
s_prev => s_p_mon_2,
n_c => n_c_reg,
s => s_out_mon_2,
valid_out => valid_out_mon_2
);
 
 
fifo_mon_out : res_out_fifo
port map (
clk => clk,
rst => reset,
din => fifo_in,
wr_en => fifo_1_wr,
rd_en => fifo_1_rd,
dout => fifo_out
);
 
exp : Mem_b port map (
clka => clk,
wea => write_b_n,
addra => addr_exp,
dina => y,
douta => exp_out);
 
n_mod : Mem_b port map (
clka => clk,
wea => write_b_n,
addra => addr_n,
dina => m,
douta => n_out);
 
 
 
process(clk, reset)
begin
 
if(clk = '1' and clk'event) then
 
if(reset = '1')then
state <= wait_start;
n_c_reg <= (others => '0');
w_numb <= (others => '0');
count_input <= (others => '0');
addr_exp <= (others => '0');
addr_n <= (others => '0');
bit_counter <= (others => '0');
bsize_reg <= (others => '0');
else
state <= next_state;
n_c_reg <= next_n_c_reg;
w_numb <= next_w_numb;
count_input <= next_count_input;
addr_exp <= next_addr_exp;
addr_n <= next_addr_n;
bit_counter <= next_bit_counter;
bsize_reg <= next_bsize_reg;
end if;
end if;
end process;
 
process(state, bsize_reg, n_c_reg, valid_in, x, n_c, r_c, m, y, w_numb, count_input, addr_exp, addr_n, s_out_mon_1, s_out_mon_2, bit_size, valid_out_mon_1, bit_counter, exp_out, fifo_out, n_out)
 
variable mask : std_logic_vector(3 downto 0);
 
begin
 
--Registers update
next_state <= state;
next_n_c_reg <= n_c_reg;
next_w_numb <= w_numb;
next_count_input <= count_input;
next_bsize_reg <= bsize_reg;
--Entradas de los montgomerys.
valid_in_mon_1 <= '0';
valid_in_mon_2 <= '0';
a_mon_1 <= (others => '0');
b_mon_1 <= (others => '0');
n_mon_1 <= (others => '0');
a_mon_2 <= (others => '0');
b_mon_2 <= (others => '0');
n_mon_2 <= (others => '0');
s_p_mon_1 <= (others => '0');
s_p_mon_2 <= (others => '0');
--Control de las fifos
fifo_1_rd <= '0';
fifo_in <= (others => '0');
fifo_1_wr <= '0';
--Control de memorias de exp y modulo
write_b_n <= b"0";
next_addr_exp <= addr_exp;
next_addr_n <= addr_n;
next_bit_counter <= bit_counter;
--Outputs
valid_out <= '0';
s <= (others => '0');
case state is
 
when wait_start =>
 
valid_in_mon_1 <= valid_in;
valid_in_mon_2 <= valid_in;
if(valid_in = '1') then
a_mon_1 <= x;
b_mon_1 <= r_c;
n_mon_1 <= m;
 
a_mon_2 <= x"0001";
b_mon_2 <= r_c;
n_mon_2 <= m;
next_w_numb <= x"23"; --Se extiende en 3 para poder usar las multiplicaciones modulares
next_n_c_reg <= n_c;
next_state <= prepare_data;
next_count_input <= x"0001";
 
write_b_n <= b"1"; --Notificamos que hay que guardar el exponente y modulo
next_addr_exp <= "000001";
next_addr_n <= "000001";
next_bsize_reg <= bit_size-1;
end if;
 
when prepare_data =>
next_count_input <= count_input+1;
valid_in_mon_1 <= '1';
valid_in_mon_2 <= '1';
--Esto es solo mientras los datos en la entrada son validos, cuando no lo son
--se meten 0s para la extension de 3 palabras en los montgomerys
if(valid_in = '1') then
a_mon_1 <= x;
b_mon_1 <= r_c;
n_mon_1 <= m;
b_mon_2 <= r_c;
n_mon_2 <= m;
 
write_b_n <= b"1";
next_addr_exp <= addr_exp+1;
next_addr_n <= addr_n+1;
end if;
if(count_input = w_numb) then
next_state <= wait_constants;
next_addr_n <= (others => '0');
 
next_addr_exp <= bsize_reg(9 downto 4);
--Decodificador para establecer la mascara
mask := bsize_reg(3 downto 0);
case (mask) is
when "0000" => next_bit_counter <= "0000000000000001";
when "0001" => next_bit_counter <= "0000000000000010";
when "0010" => next_bit_counter <= "0000000000000100";
when "0011" => next_bit_counter <= "0000000000001000";
when "0100" => next_bit_counter <= "0000000000010000";
when "0101" => next_bit_counter <= "0000000000100000";
when "0110" => next_bit_counter <= "0000000001000000";
when "0111" => next_bit_counter <= "0000000010000000";
when "1000" => next_bit_counter <= "0000000100000000";
when "1001" => next_bit_counter <= "0000001000000000";
when "1010" => next_bit_counter <= "0000010000000000";
when "1011" => next_bit_counter <= "0000100000000000";
when "1100" => next_bit_counter <= "0001000000000000";
when "1101" => next_bit_counter <= "0010000000000000";
when "1110" => next_bit_counter <= "0100000000000000";
when "1111" => next_bit_counter <= "1000000000000000";
when others =>
end case;
next_count_input <= (others => '0');
end if;
 
--Esperamos los valores validos de la salida de los montgomery
when wait_constants =>
 
--Comienzo a escribir en la fifo de datos
if(valid_out_mon_1 = '1') then
fifo_1_wr <= '1';
fifo_in <= s_out_mon_1 & s_out_mon_2;
next_count_input <= count_input+1;
next_state <= writting_cts_fifo;
end if;
 
--Escribimos las dos constantes iniciales en las fifos
when writting_cts_fifo =>
fifo_1_wr <= valid_out_mon_1;
next_count_input <= count_input+1;
if(count_input < x"20") then
fifo_in <= s_out_mon_1 & s_out_mon_2;
end if;
 
--Pedimos el siguiente input para la multiplicacion
if(valid_out_mon_1 = '0') then
next_count_input <= (others => '0');
next_state <= transition;
end if;
 
when transition =>
 
next_count_input <= count_input+1;
 
if(count_input > 2) then
next_count_input <= (others => '0');
--fifo_1_rd <= '1';
--next_addr_n <= addr_n+1;
if((bit_counter and exp_out) = x"0000") then
next_state <= processing_data_0;
else
next_state <= processing_data_1;
end if;
 
end if;
 
--se van ejecutando las multiplicaciones sucesivas
when processing_data_1 =>
 
 
if(count_input > x"0000")then
valid_in_mon_1 <= '1';
valid_in_mon_2 <= '1';
end if;
 
 
fifo_1_rd <= '1';
 
a_mon_1 <= fifo_out(31 downto 16);
b_mon_1 <= fifo_out(15 downto 0);
n_mon_1 <= n_out;
 
a_mon_2 <= fifo_out(31 downto 16);
b_mon_2 <= fifo_out(31 downto 16);
n_mon_2 <= n_out;
 
next_addr_n <= addr_n+1;
next_count_input <= count_input +1;
 
--Cuando llego al final cambio de estado a esperar resultados
if(count_input = w_numb) then
next_state <= wait_results;
end if;
 
when processing_data_0 =>
 
if(count_input > x"0000")then
valid_in_mon_1 <= '1';
valid_in_mon_2 <= '1';
end if;
 
fifo_1_rd <= '1';
 
a_mon_1 <= fifo_out(15 downto 0);
b_mon_1 <= fifo_out(15 downto 0);
n_mon_1 <= n_out;
 
a_mon_2 <= fifo_out(31 downto 16);
b_mon_2 <= fifo_out(15 downto 0);
n_mon_2 <= n_out;
 
next_addr_n <= addr_n+1;
next_count_input <= count_input +1;
 
--Cuando llego al final cambio de estado a esperar resultados
if(count_input = w_numb) then
next_state <= wait_results;
next_count_input <= (others => '0');
end if;
 
when wait_results =>
 
--Comienzo a escribir en la fifo de datos
if(valid_out_mon_1 = '1') then
fifo_1_wr <= '1';
fifo_in <= s_out_mon_2 & s_out_mon_1;
next_count_input <= x"0001";
next_state <= writting_results;
end if;
 
when writting_results =>
 
next_addr_n <= (others => '0');
fifo_1_wr <= valid_out_mon_1;
next_count_input <= count_input+1;
if(count_input < x"20") then
fifo_in <= s_out_mon_2 & s_out_mon_1;
end if;
 
--Pedimos el siguiente input para la multiplicacion
if(valid_out_mon_1 = '0') then
next_count_input <= (others => '0');
next_state <= prepare_next;
--Calculo del siguiente bit del exponente
--Shifto uno la mascara
next_bit_counter <= '0'&bit_counter(15 downto 1);
if(bit_counter = x"0001")
then
next_addr_exp <= addr_exp -1;
next_bit_counter <= "1000000000000000";
end if;
if((bit_counter = x"0001") and addr_exp = "000000000")
then
next_state <= final_mult;
next_count_input <= (others => '0');
next_addr_exp <= (others => '0');
end if;
end if;
when prepare_next =>
next_state <= transition;
next_count_input <= (others => '0');
fifo_1_rd <= '0';
when final_mult =>
next_count_input <= count_input+1;
if(count_input > 2) then
next_count_input <= (others => '0');
next_state <= prepare_final;
end if;
when prepare_final =>
if(count_input > x"0000")then
valid_in_mon_1 <= '1';
end if;
fifo_1_rd <= '1';
a_mon_1 <= fifo_out(15 downto 0);
if(count_input = x"0001") then
b_mon_1 <= x"0001";
end if;
n_mon_1 <= n_out;
next_addr_n <= addr_n+1;
next_count_input <= count_input +1;
--Cuando llego al final cambio de estado a esperar resultados
if(count_input = w_numb) then
next_state <= wait_final;
next_count_input <= (others =>'0');
end if;
when wait_final =>
if(valid_out_mon_1 = '1') then
valid_out <= '1';
s <= s_out_mon_1;
next_state <= show_final;
next_count_input <= count_input +1;
end if;
when show_final =>
valid_out <= '1';
s <= s_out_mon_1;
next_count_input <= count_input +1;
--Cuando llego al final cambio de estado a esperar resultados
if(count_input = x"20") then
valid_out <= '0';
next_state <= wait_start;
end if;
end case;
end process;
 
end Behavioral;
 
/trunk/rtl/montgomery_step.vhd
0,0 → 1,255
----------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 10:40:41 11/01/2009
-- Design Name:
-- Module Name: module_with_fifo - Behavioral
-- Project Name:
-- Target Devices:
-- Tool versions:
-- Description:
--
-- Dependencies:
--
-- Revision:
-- Revision 0.01 - File Created
-- Additional Comments:
--
----------------------------------------------------------------------------------
library IEEE;
use IEEE.STD_LOGIC_1164.all;
use IEEE.STD_LOGIC_ARITH.all;
use IEEE.STD_LOGIC_UNSIGNED.all;
 
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
 
entity montgomery_step is
port(
clk : in std_logic;
reset : in std_logic;
valid_in : in std_logic;
a : in std_logic_vector(15 downto 0);
b : in std_logic_vector(15 downto 0);
n : in std_logic_vector(15 downto 0);
s_prev : in std_logic_vector(15 downto 0);
n_c : in std_logic_vector(15 downto 0);
s : out std_logic_vector( 15 downto 0);
valid_out : out std_logic; -- es le valid out TODO : cambiar nombre
busy : out std_logic;
b_req : out std_logic;
a_out : out std_logic_vector(15 downto 0);
 
c_step : out std_logic; --genera un pulso cuando termina su computo para avisar al modulo superior
stop : in std_logic
);
end montgomery_step;
 
architecture Behavioral of montgomery_step is
 
component pe_wrapper
port(
clk : in std_logic;
reset : in std_logic;
ab_valid : in std_logic;
valid_in : in std_logic;
a : in std_logic_vector(15 downto 0);
b : in std_logic_vector(15 downto 0);
n : in std_logic_vector(15 downto 0);
s_prev : in std_logic_vector(15 downto 0);
n_c : in std_logic_vector(15 downto 0);
s : out std_logic_vector( 15 downto 0);
data_ready : out std_logic;
fifo_req : out std_logic;
m_val : out std_logic;
reset_the_PE : in std_logic); -- estamos preparados para aceptar el siguiente dato
end component;
 
--Inputs
 
signal ab_valid : std_logic;
signal valid_mont, fifo_read, m_val, valid_mont_out, reset_pe : std_logic;
--Outputs
 
 
--definimos los estados
type state_type is (wait_valid, wait_m, mont_proc, getting_results, prep_m, b_stable);
signal state, next_state : state_type;
signal counter, next_counter : std_logic_vector(7 downto 0); -- cuenta las palabras que han salido para ir cortando
 
 
 
signal mont_input_a, mont_input_n, mont_input_s : std_logic_vector(15 downto 0);
signal reg_constant, next_reg_constant, next_reg_input, reg_input : std_logic_vector(47 downto 0);
signal reg_out, reg_out_1, reg_out_2, reg_out_3, reg_out_4 : std_logic_vector(31 downto 0);
signal next_reg_out : std_logic_vector(31 downto 0);
 
--Cadena de registros hacia fuera
signal reg_input_1, reg_input_2, reg_input_3, reg_input_4, reg_input_5 : std_logic_vector(47 downto 0);
 
 
begin
 
mont : pe_wrapper port map (
clk => clk,
reset => reset,
ab_valid => ab_valid,
a => mont_input_a,
b => b,
n => mont_input_n,
s_prev => mont_input_s,
n_c => n_c,
s => s,
valid_in => valid_mont,
data_ready => valid_mont_out,
m_val => m_val,
reset_the_PE => reset_pe
);
 
process(clk, reset)
begin
if(clk = '1' and clk'event) then
 
if(reset = '1')then
state <= wait_valid;
counter <= (others => '0');
reg_constant <= (others => '0');
reg_input <= (others => '0');
reg_input_1 <= (others => '0');
reg_input_2 <= (others => '0');
reg_input_3 <= (others => '0');
reg_input_4 <= (others => '0');
 
reg_out <= (others => '0');
reg_out_1 <= (others => '0');
reg_out_2 <= (others => '0');
reg_out_3 <= (others => '0');
reg_out_4 <= (others => '0');
 
else
reg_input <= next_reg_input;
reg_input_1 <= reg_input;
reg_input_2 <= reg_input_1;
reg_input_3 <= reg_input_2;
reg_input_4 <= reg_input_3;
reg_input_5 <= reg_input_4;
 
reg_out <= reg_input_4(47 downto 32) & reg_input_4(31 downto 16);
reg_out_1 <= reg_out;
reg_out_2 <= reg_out_1;
reg_out_3 <= reg_out_2;
reg_out_4 <= reg_out_3;
 
state <= next_state;
counter <= next_counter;
reg_constant <= next_reg_constant;
end if;
end if;
end process;
 
process(state, valid_in, m_val, a, n, s_prev, counter, valid_mont_out, stop, reg_constant, reg_input_5, reg_out_4)
begin
--reset_fifo <= '0';
 
--next_reg_out <= a&n; --Vamos retrasando la entrada TODO add variable
 
 
a_out <= reg_out_4(31 downto 16);
n_out <= reg_out_4(15 downto 0);
 
next_state <= state;
next_counter <= counter;
--write_fifos <= valid_in;
ab_valid <= '0';
valid_mont <= '0';
valid_out <= '0';
reset_pe <= '0';
busy <= '1';
b_req <= '0';
c_step <= '0';
 
--Todo esto es nuevo
mont_input_a <= (others => '0');
mont_input_n <= (others => '0');
mont_input_s <= (others => '0');
next_reg_constant <= reg_constant;
 
case state is
when wait_valid =>
busy <= '0'; --esperamos la peticion
reset_pe <= '1';
if(valid_in = '1') then
 
b_req <= '1'; --Solicitamos al modulo externo la b
next_state <= b_stable;
next_reg_constant <= a&n&s_prev; --TODO add variable
end if;
when b_stable =>
next_state <= prep_m;
when prep_m =>
mont_input_a <= reg_constant(47 downto 32); --TODO add this to sensitivity
mont_input_n <= reg_constant(31 downto 16);
mont_input_s <= reg_constant(15 downto 0);
ab_valid <= '1';
next_state <= wait_m;
when wait_m =>
 
--Mantenemos las entradas para que nos calcule m correctamente
mont_input_a <= reg_constant(47 downto 32); --TODO add this to sensitivity
mont_input_n <= reg_constant(31 downto 16);
mont_input_s <= reg_constant(15 downto 0);
 
 
if (m_val = '1') then
 
valid_mont <= '1';
next_state <= mont_proc;
mont_input_a <= reg_input_5(47 downto 32);
mont_input_n <= reg_input_5(31 downto 16);
mont_input_s <= reg_input_5(15 downto 0);
 
end if;
 
when mont_proc =>
 
valid_mont <= '1';
mont_input_a <= reg_input_5(47 downto 32);
mont_input_n <= reg_input_5(31 downto 16);
mont_input_s <= reg_input_5(15 downto 0);
 
if(valid_mont_out = '1') then
 
next_counter <= x"00";
next_state <= getting_results;
end if;
 
when getting_results =>
 
valid_out <= '1';
next_counter <= counter+1;
valid_mont <= '1';
 
mont_input_a <= reg_input_5(47 downto 32);
mont_input_n <= reg_input_5(31 downto 16);
mont_input_s <= reg_input_5(15 downto 0);
if(counter = (x"22")) then
next_state <= wait_valid;
c_step <= '1';
reset_pe <= '1';
end if;
end case;
if(stop='1') then
next_state <= wait_valid;
--reset_fifo <= '1';
reset_pe <= '1';
end if;
end process;
end Behavioral;
/trunk/rtl/m_calc.vhd
0,0 → 1,83
----------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 20:33:10 10/29/2009
-- Design Name:
-- Module Name: m_calc - Behavioral
-- Project Name:
-- Target Devices:
-- Tool versions:
-- Description:
--
-- Dependencies:
--
-- Revision:
-- Revision 0.01 - File Created
-- Additional Comments:
--
----------------------------------------------------------------------------------
library IEEE;
use IEEE.STD_LOGIC_1164.all;
use IEEE.STD_LOGIC_ARITH.all;
use IEEE.STD_LOGIC_UNSIGNED.all;
 
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
 
entity m_calc is
 
port(
clk : in std_logic;
reset : in std_logic;
ab : in std_logic_vector (15 downto 0);
t : in std_logic_vector (15 downto 0);
n_cons : in std_logic_vector (15 downto 0);
m : out std_logic_vector (15 downto 0);
mult_valid : in std_logic; -- indica que los datos de entrada son validos
m_valid : out std_logic); -- la m calculada es valida
end m_calc;
 
architecture Behavioral of m_calc is
 
 
 
signal sum_res, next_sum_res : std_logic_vector(15 downto 0);
signal mult_valid_1, mult_valid_2 : std_logic; --delay del valido a lo largo del calculo
signal mult : std_logic_vector(31 downto 0);
begin
 
 
mult <= sum_res * n_cons;
 
process(clk, reset)
begin
 
if(clk = '1' and clk'event) then
 
if(reset = '1') then
sum_res <= (others => '0');
mult_valid_1 <= '0';
mult_valid_2 <= '0';
else
sum_res <= next_sum_res;
mult_valid_1 <= mult_valid;
mult_valid_2 <= mult_valid_1;
 
end if;
 
end if;
 
end process;
 
process(ab, t, mult_valid_2)
begin
m <= mult(15 downto 0);
next_sum_res <= ab+t;
m_valid <= mult_valid_2;
end process;
 
end Behavioral;
 
/trunk/doc/rsa 512.pdf Cannot display: file marked as a binary type. svn:mime-type = application/octet-stream
trunk/doc/rsa 512.pdf Property changes : Added: svn:mime-type ## -0,0 +1 ## +application/octet-stream \ No newline at end of property Index: trunk/src/constant_gen.c =================================================================== --- trunk/src/constant_gen.c (nonexistent) +++ trunk/src/constant_gen.c (revision 3) @@ -0,0 +1,64 @@ +#include +#include +#include +#include +#include +#include +#include +#include + +#define uint16 unsigned short int +#define uint32 unsigned int +#define uint64 unsigned long long int +#define WORD_SIZE 32 + + +uint32 getMpzSize(mpz_t n) +{ + + return (mpz_size(n)*2); + +} + +uint16 getlimb(mpz_t n, int i) +{ + uint32 aux=mpz_getlimbn(n,i/2); + if(i%2 == 0) + return (uint16) (aux&0xffff); + return (uint16) (aux>>16); + +} + + + +int main() +{ + + int i; + + mpz_t m,x,y,r,r_aux, n_cons, zero, recons; + + char *template; + + mpz_init_set_str(m,"8de7066f67be16fcacd05d319b6729cd85fe698c07cec504776146eb7a041d9e3cacbf0fcd86441981c0083eed1f8f1b18393f0b186e47ce1b7b4981417b491",16); //mpz_init_set_str(m,"c3217fff",16); + + mpz_init(r); + mpz_init(r_aux); + mpz_init(n_cons); + mpz_init_set_ui(zero,0); + + //Calculo de la constante para salir de la representacion de montgomery + mpz_ui_pow_ui(r,2,16*(getMpzSize(m)+1)); + mpz_mul(r_aux,r,r); + mpz_mod(r_aux,r_aux,m); + + mpz_sub(n_cons,zero,m); + mpz_invert(n_cons,n_cons,r); + + + + printf ("n_c <= %x;\n\n", (uint32)mpz_getlimbn(n_cons,0)&0xffff); + gmp_printf("r_c <= %Zx\n\n", r_aux); + + return 0; +} Index: trunk/src/Makefile =================================================================== --- trunk/src/Makefile (nonexistent) +++ trunk/src/Makefile (revision 3) @@ -0,0 +1,3 @@ +all: + gcc constant_gen.c -lgmp -o constant_gen + constant_gen Index: trunk/sim/transcript =================================================================== --- trunk/sim/transcript (nonexistent) +++ trunk/sim/transcript (revision 3) @@ -0,0 +1,10 @@ +# // ModelSim SE-64 6.5d Nov 18 2009 Linux 2.6.18-164.11.1.el5.centos.plus +# // +# // Copyright 1991-2009 Mentor Graphics Corporation +# // All Rights Reserved. +# // +# // THIS WORK CONTAINS TRADE SECRET AND +# // PROPRIETARY INFORMATION WHICH IS THE PROPERTY +# // OF MENTOR GRAPHICS CORPORATION OR ITS LICENSORS +# // AND IS SUBJECT TO LICENSE TERMS. +# //

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.