SM3_core/rtl/sm3_cmprss_core.v

385 lines
12 KiB
Coq
Raw Normal View History

2020-07-28 22:19:22 +08:00
`timescale 1ns / 1ps
`include "sm3_cfg.v"
2020-07-27 13:18:35 +08:00
//////////////////////////////////////////////////////////////////////////////////
// Author: ljgibbs / lf_gibbs@163.com
// Create Date: 2020/07/27
// Design Name: sm3
// Module Name: sm3_cmprss_core
// Description:
// SM3 迭代压缩模块-SM3 迭代压缩核心单元
// 输入位宽INPT_DW1 定义支持32/64bit
// 输出位宽与输入位宽对应
// 特性 64bit 位宽下采用二度展开结构暂未
// Dependencies:
// inc/sm3_cfg.v
// Revision:
// Revision 0.01 - File Created
//////////////////////////////////////////////////////////////////////////////////
module sm3_cmprss_core (
input clk,
input rst_n,
input [`INPT_DW1:0] expnd_inpt_wj_i,
input [`INPT_DW1:0] expnd_inpt_wjj_i,
input expnd_inpt_lst_i,
input expnd_inpt_vld_i,
2020-07-28 16:47:39 +08:00
output [255:0] cmprss_otpt_res_o,
output cmprss_otpt_vld_o
);
2020-07-27 13:18:35 +08:00
2020-07-28 16:47:39 +08:00
//每时钟输入的数据字数量 32bit位宽1 64bit位宽2
`ifdef SM3_INPT_DW_32
localparam [1:0] INPT_WORD_NUM = 2'd1;
`elsif SM3_INPT_DW_64
localparam [1:0] INPT_WORD_NUM = 2'd2;
`endif
localparam [6:0] CMPRSS_RND_NUM = 7'd64;
//A-H 字寄存器
reg [31 : 0] reg_a;
reg [31 : 0] reg_b;
reg [31 : 0] reg_c;
reg [31 : 0] reg_d;
reg [31 : 0] reg_e;
reg [31 : 0] reg_f;
reg [31 : 0] reg_g;
reg [31 : 0] reg_h;
reg [31 : 0] reg_tj;
reg [5 : 0] reg_cmprss_round;
reg cmprss_round_sm_16;
//结果寄存器
reg sm3_res_valid;
reg sm3_res_valid_r1;
reg [255:0] sm3_res;
reg cmprss_blk_res_finish;
//A-H 字运算中间值
wire [31 : 0] reg_a_new;
wire [31 : 0] reg_b_new;
wire [31 : 0] reg_c_new;
wire [31 : 0] reg_d_new;
wire [31 : 0] reg_e_new;
wire [31 : 0] reg_f_new;
wire [31 : 0] reg_g_new;
wire [31 : 0] reg_h_new;
`ifdef SM3_INPT_DW_64
wire [31 : 0] reg_a_mid;
wire [31 : 0] reg_b_mid;
wire [31 : 0] reg_c_mid;
wire [31 : 0] reg_d_mid;
wire [31 : 0] reg_e_mid;
wire [31 : 0] reg_f_mid;
wire [31 : 0] reg_g_mid;
wire [31 : 0] reg_h_mid;
//两轮运算的 tj
wire [31 : 0] reg_tj_rnd_odd;
wire [31 : 0] reg_tj_rnd_even;
`endif
//块迭代标志
wire cmprss_new_round_valid;
wire cmprss_blk_start;
wire cmprss_blk_finish;
//对输入的 wj 值打拍或者分离
reg sm3_wj_wjj_vld_r;
reg sm3_wj_wjj_lst_r;
`ifdef SM3_INPT_DW_32
reg [31:0] wj_rnd_r;
reg [31:0] wjj_rnd_r;
`elsif SM3_INPT_DW_64
reg [31:0] wj_rnd_odd_r;
reg [31:0] wjj_rnd_odd_r;
reg [31:0] wj_rnd_even_r;
reg [31:0] wjj_rnd_even_r;
`endif
//输入每数据块所属数据字计数
reg [5:0] inpt_wrd_of_blk_cntr;
wire inpt_wrd_of_blk_cntr_add;
wire inpt_wrd_of_blk_cntr_clr;
//管理tj寄存器
always @(posedge clk or negedge rst_n) begin
if(~rst_n |cmprss_blk_res_finish) begin
2020-07-28 16:47:39 +08:00
reg_tj <= 32'h79cc4519;
end
else if(sm3_wj_wjj_vld_r)begin
if(reg_cmprss_round == 6'd16 - INPT_WORD_NUM)
reg_tj <= 32'h9d8a7a87;
2020-07-28 16:47:39 +08:00
else begin
`ifdef SM3_INPT_DW_32
reg_tj <= {reg_tj[30:0],reg_tj[31]};
`elsif SM3_INPT_DW_64 //每次循环左移两位
reg_tj <= {reg_tj[29:0],reg_tj[31:30]};
`endif
end
end
end
`ifdef SM3_INPT_DW_64
//两轮运算的 tj
assign reg_tj_rnd_odd = {reg_tj[30:0],reg_tj[31]};
assign reg_tj_rnd_even = reg_tj;
`endif
//对输入的 wj 值打拍或者分离
always @(posedge clk or negedge rst_n) begin
if(~rst_n) begin
sm3_wj_wjj_vld_r <= 1'b0;
sm3_wj_wjj_lst_r <= 1'b0;
end
else begin
sm3_wj_wjj_vld_r <= expnd_inpt_vld_i;
sm3_wj_wjj_lst_r <= expnd_inpt_lst_i;
2020-07-28 16:47:39 +08:00
end
end
`ifdef SM3_INPT_DW_32
always @(posedge clk or negedge rst_n) begin
if(~rst_n) begin
wj_rnd_r <= 32'd0;
wjj_rnd_r <= 32'd0;
end
else begin
wj_rnd_r <= expnd_inpt_wj_i;
wjj_rnd_r <= expnd_inpt_wjj_i;
2020-07-28 16:47:39 +08:00
end
end
`elsif SM3_INPT_DW_64
always @(posedge clk or negedge rst_n) begin
if(~rst_n) begin
wj_rnd_odd_r <= 32'd0;
wjj_rnd_odd_r <= 32'd0;
wj_rnd_even_r <= 32'd0;
wjj_rnd_even_r <= 32'd0;
end
else begin
2020-07-29 23:14:40 +08:00
{wj_rnd_even_r,wj_rnd_odd_r} <= expnd_inpt_wj_i;
{wjj_rnd_even_r,wjj_rnd_odd_r} <= expnd_inpt_wjj_i;
2020-07-28 16:47:39 +08:00
end
end
`endif
//标记最后一块
assign cmprss_new_round_valid = sm3_wj_wjj_vld_r;
assign cmprss_blk_finish = inpt_wrd_of_blk_cntr_clr;
//块运算完成信号
always @(posedge clk or negedge rst_n) begin
if(~rst_n) begin
cmprss_blk_res_finish <= 1'b0;
end
else begin
cmprss_blk_res_finish <= inpt_wrd_of_blk_cntr_clr;
end
end
//输入每数据块所属数据字计数
always @(posedge clk or negedge rst_n) begin
if(~rst_n) begin
inpt_wrd_of_blk_cntr <= 6'b0;
end else if(inpt_wrd_of_blk_cntr_add)begin
inpt_wrd_of_blk_cntr <= inpt_wrd_of_blk_cntr + INPT_WORD_NUM;
end else if(inpt_wrd_of_blk_cntr_clr)begin
inpt_wrd_of_blk_cntr <= 6'b0;
end
end
assign inpt_wrd_of_blk_cntr_add = sm3_wj_wjj_vld_r;
assign inpt_wrd_of_blk_cntr_clr = sm3_wj_wjj_vld_r
&& inpt_wrd_of_blk_cntr == (CMPRSS_RND_NUM - INPT_WORD_NUM);
//压缩迭代轮计数
always @(posedge clk or negedge rst_n) begin
if(~rst_n) begin
reg_cmprss_round <= 6'd0;
end
else if(cmprss_blk_finish)begin
reg_cmprss_round <= 6'd0;
end
else if(cmprss_new_round_valid)begin
reg_cmprss_round <= reg_cmprss_round + INPT_WORD_NUM;
end
end
//产生16轮内标记
always @(posedge clk or negedge rst_n) begin
if(~rst_n) begin
cmprss_round_sm_16 <= 1'b0;
end else begin
cmprss_round_sm_16 <= reg_cmprss_round < 6'd16 - INPT_WORD_NUM; //标识当前小于
end
end
//寄存器组初值装填与迭代
always @(posedge clk or negedge rst_n) begin
if((~rst_n) || sm3_res_valid_r1) begin
reg_a <= 32'h7380166f;//0;
reg_b <= 32'h4914b2b9;//0;
reg_c <= 32'h172442d7;//0;
reg_d <= 32'hda8a0600;//0;
reg_e <= 32'ha96f30bc;//0;
reg_f <= 32'h163138aa;//0;
reg_g <= 32'he38dee4d;//0;
reg_h <= 32'hb0fb0e4e;//0;
end
else if(cmprss_new_round_valid)begin
reg_a <= reg_a_new;
reg_b <= reg_b_new;
reg_c <= reg_c_new;
reg_d <= reg_d_new;
reg_e <= reg_e_new;
reg_f <= reg_f_new;
reg_g <= reg_g_new;
reg_h <= reg_h_new;
end
else if(cmprss_blk_res_finish)begin
reg_a <= reg_a ^ sm3_res[255-:32];
reg_b <= reg_b ^ sm3_res[223-:32];
reg_c <= reg_c ^ sm3_res[191-:32];
reg_d <= reg_d ^ sm3_res[159-:32];
reg_e <= reg_e ^ sm3_res[127-:32];
reg_f <= reg_f ^ sm3_res[95 -:32];
reg_g <= reg_g ^ sm3_res[63 -:32];
reg_h <= reg_h ^ sm3_res[31 -:32];
end
end
//消息所属块均计算完毕输出计算结果
always @(posedge clk or negedge rst_n) begin
if(~rst_n) begin
sm3_res_valid <= 1'b0;
sm3_res_valid_r1 <= 1'b0;
end
else begin
sm3_res_valid <= sm3_wj_wjj_lst_r;
sm3_res_valid_r1 <= sm3_res_valid;
end
end
always @(posedge clk or negedge rst_n) begin
if((~rst_n) || sm3_res_valid_r1) begin
sm3_res <= {32'h7380166f, 32'h4914b2b9, 32'h172442d7, 32'hda8a0600, 32'ha96f30bc, 32'h163138aa, 32'he38dee4d, 32'hb0fb0e4e};
end
else if(cmprss_blk_res_finish)begin
sm3_res <= {reg_a,reg_b,reg_c,reg_d,reg_e,reg_f,reg_g,reg_h} ^ sm3_res;
end
end
`ifdef SM3_INPT_DW_32
sm3_cmprss_ceil_comb U_sm3_cmprss_ceil_comb
(
.cmprss_round_sm_16_i (cmprss_round_sm_16),
.tj_i (reg_tj),
.reg_a_i (reg_a),
.reg_b_i (reg_b),
.reg_c_i (reg_c),
.reg_d_i (reg_d),
.reg_e_i (reg_e),
.reg_f_i (reg_f),
.reg_g_i (reg_g),
.reg_h_i (reg_h),
.wj_i (wj_rnd_r),
.wjj_i (wjj_rnd_r),
.reg_a_o (reg_a_new),
.reg_b_o (reg_b_new),
.reg_c_o (reg_c_new),
.reg_d_o (reg_d_new),
.reg_e_o (reg_e_new),
.reg_f_o (reg_f_new),
.reg_g_o (reg_g_new),
.reg_h_o (reg_h_new)
);
`elsif SM3_INPT_DW_64
sm3_cmprss_ceil_comb U_sm3_cmprss_ceil_comb
(
.cmprss_round_sm_16_i (cmprss_round_sm_16),
.tj_i (reg_tj_rnd_even),
.reg_a_i (reg_a),
.reg_b_i (reg_b),
.reg_c_i (reg_c),
.reg_d_i (reg_d),
.reg_e_i (reg_e),
.reg_f_i (reg_f),
.reg_g_i (reg_g),
.reg_h_i (reg_h),
.wj_i (wj_rnd_even_r),
.wjj_i (wjj_rnd_even_r),
.reg_a_o (reg_a_mid),
.reg_b_o (reg_b_mid),
.reg_c_o (reg_c_mid),
.reg_d_o (reg_d_mid),
.reg_e_o (reg_e_mid),
.reg_f_o (reg_f_mid),
.reg_g_o (reg_g_mid),
.reg_h_o (reg_h_mid)
);
sm3_cmprss_ceil_comb U_sm3_cmprss_ceil_comb_1
(
.cmprss_round_sm_16_i (cmprss_round_sm_16),
.tj_i (reg_tj_rnd_odd),
.reg_a_i (reg_a_mid),
.reg_b_i (reg_b_mid),
.reg_c_i (reg_c_mid),
.reg_d_i (reg_d_mid),
.reg_e_i (reg_e_mid),
.reg_f_i (reg_f_mid),
.reg_g_i (reg_g_mid),
.reg_h_i (reg_h_mid),
.wj_i (wj_rnd_odd_r),
.wjj_i (wjj_rnd_odd_r),
.reg_a_o (reg_a_new),
.reg_b_o (reg_b_new),
.reg_c_o (reg_c_new),
.reg_d_o (reg_d_new),
.reg_e_o (reg_e_new),
.reg_f_o (reg_f_new),
.reg_g_o (reg_g_new),
.reg_h_o (reg_h_new)
);
`endif
//输出控制
assign cmprss_otpt_vld_o = sm3_res_valid_r1;
assign cmprss_otpt_res_o = sm3_res;
`ifdef SM3_CMPRS_SIM_DBG
`ifdef SM3_CMPRS_SIM_FILE_LOG
integer file;
initial begin:inital_file
file = $fopen("wj.txt","w");
end
`endif
generate
if(1) begin
always@(*) begin
2020-08-04 23:11:26 +08:00
if(cmprss_otpt_vld_o)
2020-07-28 16:47:39 +08:00
begin
`ifdef SM3_CMPRS_SIM_FILE_LOG
2020-08-04 23:11:26 +08:00
$fdisplay(file,"LOG: res : %64h",cmprss_otpt_res_o);
2020-07-28 16:47:39 +08:00
`else
2020-08-04 23:11:26 +08:00
$display("LOG: res : %64h",cmprss_otpt_res_o);
2020-07-28 16:47:39 +08:00
`endif
end
end
end
endgenerate
`endif
endmodule