Archived
major update to lcmv, to fit hop control
1. 调零算法部分增加调零控制模块,用于各模块互联和状态控制以及数据存储,增加LCMV和DAS选通; 2. Cordic 旋转输入改为保留两个符号位,避免溢出; 3. LCMV快拍数修改为2048; 4. 修改功率计算模块,适配较小数据位宽; 5. 修改在线捕获校准程序自动校准部分VIO初值; 6. 地检新射频发端增加自动频点切换
This commit is contained in:
@@ -14,29 +14,26 @@
|
||||
// Project Name:
|
||||
// Target Devices:
|
||||
// Tool Versions: 2019.1.3
|
||||
// Description: Compute the accumulation of complex matrices. The row number
|
||||
// [ROW_NUM] and column number [ROW_NUM] are flexible parameters. The
|
||||
// accumulation number [ACC_NUM], input data width [DATA_I_WIDTH] and output
|
||||
// data width [DATA_ACC_WIDTH] are related to each other and should match the
|
||||
// Adder/Subtracter LogiCORE IP configuration.
|
||||
// Description: Compute the accumulation of complex matrices. The parameters are
|
||||
// fully adjustable.
|
||||
// Parameter:
|
||||
// ROW_NUM: Row number of input matrix.
|
||||
// COL_NUM: Column number of input matrix.
|
||||
// ACC_NUM: Accumulation number of input matrix.
|
||||
// DATA_I_WIDTH: Bit width of input matrix element.
|
||||
// DATA_ACC_WIDTH: !!!Caution!!! Accumulation adder output data width. It is
|
||||
// determined by [DATA_I_WIDTH] and [ACC_NUM], and is calculated as
|
||||
// log2(ACC_NUM*(2^DATA_I_WIDTH-1)), and should match the Adder/Subtracter
|
||||
// LogiCORE IP configuration.
|
||||
// DATA_O_WIDTH: Bit width of output matrix element. If [DATA_O_WIDTH] <
|
||||
// [DATA_ACC_WIDTH], MSB of accumulation result will be truncated. If
|
||||
// [DATA_O_WIDTH] > [DATA_ACC_WIDTH], the sign bit of accumulation result
|
||||
// will be extended.
|
||||
// DATA_O_WIDTH: Bit width of output matrix element. If [DATA_O_WIDTH] <=
|
||||
// [ACC_WIDTH], MSB of accumulation result will be truncated, or zeros will
|
||||
// be appended.
|
||||
// ACC_WIDTH (local): Accumulation adder output data width, determined by
|
||||
// [DATA_I_WIDTH] and [ACC_NUM].
|
||||
//
|
||||
// Dependencies:
|
||||
//
|
||||
// Revision:
|
||||
// Revision 0.01 - File Created
|
||||
// Revision 0.01 - File Created
|
||||
// 20230717-1552 - 修改程序使得快拍数可以大于 256,具体修改有:1. 将累加位宽
|
||||
// 改为内部参数;2. 移除加法器,变为手写加法;3. 修改 Generate 结构,always
|
||||
// 块中不应出现 generate 块。
|
||||
// Additional Comments:
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
@@ -48,7 +45,6 @@ module accum_cmplx_mat
|
||||
parameter COL_NUM = 4,
|
||||
parameter ACC_NUM = 256,
|
||||
parameter DATA_I_WIDTH = 24,
|
||||
parameter DATA_ACC_WIDTH = $clog2(ACC_NUM*(2^DATA_I_WIDTH-1)),
|
||||
parameter DATA_O_WIDTH = 32
|
||||
)
|
||||
(
|
||||
@@ -68,77 +64,72 @@ module accum_cmplx_mat
|
||||
output [ROW_NUM*COL_NUM*DATA_O_WIDTH-1:0] dout_imag
|
||||
);
|
||||
|
||||
genvar i;
|
||||
localparam ACC_WIDTH = $clog2(ACC_NUM) + DATA_I_WIDTH;
|
||||
|
||||
integer i;
|
||||
genvar m;
|
||||
|
||||
// prepare adder input & output data
|
||||
wire [DATA_I_WIDTH-1:0] add_real_a_array [0:ROW_NUM*COL_NUM-1];
|
||||
wire [DATA_I_WIDTH-1:0] add_imag_a_array [0:ROW_NUM*COL_NUM-1];
|
||||
wire [DATA_ACC_WIDTH-1:0] add_real_b_array [0:ROW_NUM*COL_NUM-1];
|
||||
wire [DATA_ACC_WIDTH-1:0] add_imag_b_array [0:ROW_NUM*COL_NUM-1];
|
||||
wire [DATA_ACC_WIDTH-1:0] add_real_s_array [0:ROW_NUM*COL_NUM-1];
|
||||
wire [DATA_ACC_WIDTH-1:0] add_imag_s_array [0:ROW_NUM*COL_NUM-1];
|
||||
wire signed [DATA_I_WIDTH-1:0] din_real_array [0:ROW_NUM*COL_NUM-1];
|
||||
wire signed [DATA_I_WIDTH-1:0] din_imag_array [0:ROW_NUM*COL_NUM-1];
|
||||
|
||||
generate
|
||||
for (i = 0; i < ROW_NUM*COL_NUM; i = i + 1) begin: cmplx_mat_accum
|
||||
assign add_real_a_array[i] = din_real[i*DATA_I_WIDTH +: DATA_I_WIDTH];
|
||||
assign add_imag_a_array[i] = din_imag[i*DATA_I_WIDTH +: DATA_I_WIDTH];
|
||||
|
||||
assign add_real_b_array[i] = add_real_s_array[i];
|
||||
assign add_imag_b_array[i] = add_imag_s_array[i];
|
||||
|
||||
if (ACC_NUM > 1) begin
|
||||
add_s24_s32_s32 u_accum_real
|
||||
(
|
||||
.A (add_real_a_array[i]), // input wire [23 : 0] A
|
||||
.B (add_real_b_array[i]), // input wire [31 : 0] B
|
||||
.CLK (clk ), // input wire CLK
|
||||
.CE (din_valid ), // input wire CE
|
||||
.SCLR (rst || acc_rst ), // input wire SCLR
|
||||
.S (add_real_s_array[i]) // output wire [31 : 0] S
|
||||
);
|
||||
|
||||
add_s24_s32_s32 u_accum_imag
|
||||
(
|
||||
.A (add_imag_a_array[i]), // input wire [23 : 0] A
|
||||
.B (add_imag_b_array[i]), // input wire [31 : 0] B
|
||||
.CLK (clk ), // input wire CLK
|
||||
.CE (din_valid ), // input wire CE
|
||||
.SCLR (rst || acc_rst ), // input wire SCLR
|
||||
.S (add_imag_s_array[i]) // output wire [31 : 0] S
|
||||
);
|
||||
for (m = 0; m < ROW_NUM*COL_NUM; m = m + 1) begin: array_conversion
|
||||
// Array split
|
||||
assign din_real_array[m] = din_real[m*DATA_I_WIDTH +: DATA_I_WIDTH];
|
||||
assign din_imag_array[m] = din_imag[m*DATA_I_WIDTH +: DATA_I_WIDTH];
|
||||
end
|
||||
|
||||
end
|
||||
endgenerate
|
||||
|
||||
// input data counter & full flag
|
||||
// accumulation counter
|
||||
reg [$clog2(ACC_NUM)-1:0] accum_cnt = 'b0;
|
||||
reg accum_full_flag = 'b0;
|
||||
reg accum_full_flag_d = 'b0; // delay of [accum_full_flag]
|
||||
reg accum_full_flag_d = 'b0;
|
||||
|
||||
// accumulation
|
||||
reg signed [ACC_WIDTH-1:0] acc_real_array [0:ROW_NUM*COL_NUM-1];
|
||||
reg signed [ACC_WIDTH-1:0] acc_imag_array [0:ROW_NUM*COL_NUM-1];
|
||||
|
||||
if (ACC_NUM > 1) begin
|
||||
always @(posedge clk) begin
|
||||
if (rst || acc_rst) begin
|
||||
accum_cnt <= 'b0;
|
||||
end
|
||||
else if (din_valid) begin
|
||||
accum_cnt <= accum_cnt + 1'b1;
|
||||
end
|
||||
else begin
|
||||
accum_cnt <= accum_cnt;
|
||||
end
|
||||
end
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst || acc_rst) begin
|
||||
accum_full_flag <= 'b0;
|
||||
end
|
||||
else begin
|
||||
accum_full_flag <= (accum_cnt == ACC_NUM - 1) ? 1'b1 : accum_full_flag;
|
||||
// accumulation counter
|
||||
always @(posedge clk) begin
|
||||
if (rst || acc_rst) begin
|
||||
accum_cnt <= 'b0;
|
||||
end
|
||||
else if (din_valid) begin
|
||||
accum_cnt <= accum_cnt + 1'b1;
|
||||
end
|
||||
else begin
|
||||
accum_cnt <= accum_cnt;
|
||||
end
|
||||
end
|
||||
|
||||
accum_full_flag_d <= accum_full_flag;
|
||||
end
|
||||
always @(posedge clk) begin
|
||||
if (rst || acc_rst) begin
|
||||
accum_full_flag <= 'b0;
|
||||
end
|
||||
else begin
|
||||
accum_full_flag <= (accum_cnt == ACC_NUM - 1) ? 1'b1 : accum_full_flag;
|
||||
end
|
||||
|
||||
accum_full_flag_d <= accum_full_flag;
|
||||
end
|
||||
|
||||
// accumulation
|
||||
for (m = 0; m < ROW_NUM*COL_NUM; m = m + 1) begin: accumulation
|
||||
always @(posedge clk) begin
|
||||
if (rst || acc_rst) begin
|
||||
acc_real_array[m] <= 'b0;
|
||||
acc_imag_array[m] <= 'b0;
|
||||
end
|
||||
else if (din_valid && ~accum_full_flag) begin
|
||||
acc_real_array[m] <= acc_real_array[m] + din_real_array[m];
|
||||
acc_imag_array[m] <= acc_imag_array[m] + din_imag_array[m];
|
||||
end
|
||||
else begin
|
||||
acc_real_array[m] <= acc_real_array[m];
|
||||
acc_imag_array[m] <= acc_imag_array[m];
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
// output control
|
||||
@@ -148,65 +139,107 @@ reg [DATA_O_WIDTH-1:0] dout_imag_array [0:ROW_NUM*COL_NUM-1];
|
||||
|
||||
assign dout_valid = dout_valid_buf;
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst || acc_rst) begin
|
||||
dout_valid_buf <= 'b0;
|
||||
end
|
||||
else begin
|
||||
if (ACC_NUM > 1) begin
|
||||
dout_valid_buf <= ~accum_full_flag_d & accum_full_flag;
|
||||
end
|
||||
else begin
|
||||
dout_valid_buf <= din_valid;
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
generate
|
||||
for (i = 0; i < ROW_NUM*COL_NUM; i = i + 1) begin: output_buf
|
||||
assign dout_real[i*DATA_O_WIDTH +: DATA_O_WIDTH] = dout_real_array[i];
|
||||
assign dout_imag[i*DATA_O_WIDTH +: DATA_O_WIDTH] = dout_imag_array[i];
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst || acc_rst) begin
|
||||
dout_real_array[i] <= 'b0;
|
||||
dout_imag_array[i] <= 'b0;
|
||||
dout_valid_buf <= 'b0;
|
||||
end
|
||||
else begin
|
||||
if (ACC_NUM > 1) begin
|
||||
if (~accum_full_flag_d & accum_full_flag) begin
|
||||
if (DATA_O_WIDTH <= DATA_ACC_WIDTH) begin
|
||||
// truncate msb
|
||||
dout_real_array[i] <= add_real_s_array[i][DATA_ACC_WIDTH-1 -: DATA_O_WIDTH];
|
||||
dout_imag_array[i] <= add_imag_s_array[i][DATA_ACC_WIDTH-1 -: DATA_O_WIDTH];
|
||||
end
|
||||
else begin // if (ACC_NUM <= 1)
|
||||
// Sign extension to fit output data width
|
||||
dout_real_array[i] <= {{(DATA_O_WIDTH-DATA_ACC_WIDTH){add_real_s_array[i][DATA_ACC_WIDTH-1]}},add_real_s_array[i]};
|
||||
dout_imag_array[i] <= {{(DATA_O_WIDTH-DATA_ACC_WIDTH){add_imag_s_array[i][DATA_ACC_WIDTH-1]}},add_real_s_array[i]};
|
||||
end
|
||||
end
|
||||
else begin
|
||||
dout_real_array[i] <= dout_real_array[i];
|
||||
dout_imag_array[i] <= dout_imag_array[i];
|
||||
end
|
||||
end // if (ACC_NUM > 1)
|
||||
else begin // if (ACC_NUM <= 1)
|
||||
if (DATA_O_WIDTH <= DATA_I_WIDTH) begin
|
||||
// truncate msb
|
||||
dout_real_array[i] <= add_real_a_array[i][DATA_I_WIDTH-1 -: DATA_O_WIDTH];
|
||||
dout_imag_array[i] <= add_imag_a_array[i][DATA_I_WIDTH-1 -: DATA_O_WIDTH];
|
||||
end
|
||||
else begin // if (DATA_O_WIDTH > DATA_I_WIDTH)
|
||||
// Sign extension to fit output data width
|
||||
dout_real_array[i] <= {{(DATA_O_WIDTH-DATA_I_WIDTH){add_real_a_array[i][DATA_I_WIDTH-1]}},add_real_a_array[i]};
|
||||
dout_imag_array[i] <= {{(DATA_O_WIDTH-DATA_I_WIDTH){add_imag_a_array[i][DATA_I_WIDTH-1]}},add_imag_a_array[i]};
|
||||
end
|
||||
end // if (ACC_NUM <= 1)
|
||||
dout_valid_buf <= ~accum_full_flag_d & accum_full_flag;
|
||||
end
|
||||
end
|
||||
end
|
||||
endgenerate
|
||||
else begin
|
||||
always @(posedge clk) begin
|
||||
if (rst || acc_rst) begin
|
||||
dout_valid_buf <= 'b0;
|
||||
end
|
||||
else begin
|
||||
dout_valid_buf <= din_valid;
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
for (m = 0; m < ROW_NUM*COL_NUM; m = m + 1) begin: output_data
|
||||
if (ACC_NUM > 1) begin
|
||||
if (DATA_O_WIDTH <= ACC_WIDTH) begin
|
||||
// truncate msb
|
||||
always @(posedge clk) begin
|
||||
if (rst || acc_rst) begin
|
||||
dout_real_array[m] <= 'b0;
|
||||
dout_imag_array[m] <= 'b0;
|
||||
end
|
||||
else if (~accum_full_flag_d & accum_full_flag) begin
|
||||
dout_real_array[m] <= acc_real_array[m][ACC_WIDTH-1 -: DATA_O_WIDTH];
|
||||
dout_imag_array[m] <= acc_imag_array[m][ACC_WIDTH-1 -: DATA_O_WIDTH];
|
||||
end
|
||||
else begin
|
||||
dout_real_array[m] <= dout_real_array[m];
|
||||
dout_imag_array[m] <= dout_imag_array[m];
|
||||
end
|
||||
end
|
||||
end
|
||||
else begin // if (DATA_O_WIDTH > ACC_WIDTH)
|
||||
// append zeros to fit output data width
|
||||
always @(posedge clk) begin
|
||||
if (rst || acc_rst) begin
|
||||
dout_real_array[m] <= 'b0;
|
||||
dout_imag_array[m] <= 'b0;
|
||||
end
|
||||
else if (~accum_full_flag_d & accum_full_flag) begin
|
||||
dout_real_array[m] <= {acc_real_array[m],{(DATA_O_WIDTH-ACC_WIDTH){1'b0}}};
|
||||
dout_imag_array[m] <= {acc_imag_array[m],{(DATA_O_WIDTH-ACC_WIDTH){1'b0}}};
|
||||
end
|
||||
else begin
|
||||
dout_real_array[m] <= dout_real_array[m];
|
||||
dout_imag_array[m] <= dout_imag_array[m];
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
else begin
|
||||
if (DATA_O_WIDTH <= DATA_I_WIDTH) begin
|
||||
// truncate msb
|
||||
always @(posedge clk) begin
|
||||
if (rst || acc_rst) begin
|
||||
dout_real_array[m] <= 'b0;
|
||||
dout_imag_array[m] <= 'b0;
|
||||
end
|
||||
else if (din_valid) begin
|
||||
dout_real_array[m] <= din_real_array[m][DATA_I_WIDTH-1 -: DATA_O_WIDTH];
|
||||
dout_imag_array[m] <= din_imag_array[m][DATA_I_WIDTH-1 -: DATA_O_WIDTH];
|
||||
end
|
||||
else begin
|
||||
dout_real_array[m] <= dout_real_array[m];
|
||||
dout_imag_array[m] <= dout_imag_array[m];
|
||||
end
|
||||
end
|
||||
end
|
||||
else begin // if (DATA_O_WIDTH > DATA_I_WIDTH)
|
||||
// append zeros to fit output data width
|
||||
always @(posedge clk) begin
|
||||
if (rst || acc_rst) begin
|
||||
dout_real_array[m] <= 'b0;
|
||||
dout_imag_array[m] <= 'b0;
|
||||
end
|
||||
else if (din_valid) begin
|
||||
dout_real_array[m] <= {din_real_array[m],{(DATA_O_WIDTH-DATA_I_WIDTH){1'b0}}};
|
||||
dout_imag_array[m] <= {din_imag_array[m],{(DATA_O_WIDTH-DATA_I_WIDTH){1'b0}}};
|
||||
end
|
||||
else begin
|
||||
dout_real_array[m] <= dout_real_array[m];
|
||||
dout_imag_array[m] <= dout_imag_array[m];
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
// output mapping
|
||||
for (m = 0; m < ROW_NUM*COL_NUM; m = m + 1) begin: output_mapping
|
||||
assign dout_real[m*DATA_O_WIDTH +: DATA_O_WIDTH] = dout_real_array[m];
|
||||
assign dout_imag[m*DATA_O_WIDTH +: DATA_O_WIDTH] = dout_imag_array[m];
|
||||
end
|
||||
|
||||
endmodule
|
||||
|
||||
@@ -259,7 +292,7 @@ endmodule
|
||||
// module tb_accum;
|
||||
|
||||
// localparam DATA_I_WIDTH = 24;
|
||||
// localparam DATA_ACC_WIDTH = 32;
|
||||
// localparam ACC_WIDTH = 32;
|
||||
// localparam DATA_O_WIDTH = 35;
|
||||
// localparam ROW_NUM = 4;
|
||||
// localparam COL_NUM = 4;
|
||||
@@ -278,7 +311,7 @@ endmodule
|
||||
// .ROW_NUM (ROW_NUM),
|
||||
// .COL_NUM (COL_NUM),
|
||||
// .DATA_I_WIDTH (DATA_I_WIDTH),
|
||||
// .DATA_ACC_WIDTH (DATA_ACC_WIDTH),
|
||||
// .ACC_WIDTH (ACC_WIDTH),
|
||||
// .DATA_O_WIDTH (DATA_O_WIDTH),
|
||||
// .ACC_NUM (1)
|
||||
// ) u_accum_cmplx_mat
|
||||
|
||||
@@ -17,33 +17,37 @@
|
||||
// Description: Compute the autocorrelation of a complex column vector. The
|
||||
// computation is conducted in fully parallel style.
|
||||
// Parameter:
|
||||
// DATA_I_WIDTH: Bit width of input vector element, the same as of complex
|
||||
// DATA_I_WIDTH: Width of input vector element, the same as of complex
|
||||
// multiplication input data.
|
||||
// DATA_MULT_FULL_WIDTH (local): Bit width of unsigned complex multiplication
|
||||
// CMPY_P_FULL_WIDTH (local): Width of unsigned complex multiplication
|
||||
// output data (The cmpy LogiCore IP does not care whether the input data
|
||||
// are signed or unsigned). It equals to (2*[DATA_MULT_WIDTH]+1).
|
||||
// DATA_MULT_VALID_WIDTH (local): Bit width of signed complex multiplication.acc_rst
|
||||
// It equals to 2*[DATA_MULT_WIDTH].
|
||||
// DATA_O_WIDTH: Bit width of output matrix element. If [DATA_O_WIDTH] <
|
||||
// [DATA_MULT_WIDTH], MSB of valid complex mutiplication output will be
|
||||
// truncated. If [DATA_O_WIDTH] > [DATA_MULT_WIDTH], the sign bit of valid
|
||||
// complex mutiplication output will be extended.
|
||||
// are signed or unsigned), which equals to (2*[DATA_MULT_WIDTH]+1).
|
||||
// CMPY_P_VALID_WIDTH (local): Width of signed complex multiplication, which
|
||||
// equals to 2*[DATA_MULT_WIDTH].
|
||||
// DATA_O_WIDTH: Width of output matrix element. If [DATA_O_WIDTH] <=
|
||||
// [DATA_MULT_WIDTH], MSB of valid complex multiplication output will be
|
||||
// truncated; or zeros will be appended.
|
||||
// Data format:
|
||||
// din_valid: Indicate [din_real/imag] data are valid.
|
||||
// din_real/imag: Suppose the input column vector x = [x1 x2 x3 x4]^T, then
|
||||
// din_real = {Re{x4}, Re{x3}, Re{x2}, Re{x1}}
|
||||
// din_imag = {Im{x4}, Im{x3}, Im{x2}, Im{x1}}
|
||||
// dout_valid: Indicate [dout_real/imag] data are valid. The latency is
|
||||
// determined by the configuration of the cmpy ip core, which is set to 6
|
||||
// determined by the configuration of the cmpy ip core, which is set to 5
|
||||
// clock cycles by default.
|
||||
// dout_real/imag:
|
||||
// dout_real = {Re{x4*x4^H}, Re{x4*x3^H}, ..., Re{x1*x2^H}, Re{x1*x1^H}}
|
||||
// dout_imag = {Im{x4*x4^H}, Im{x4*x3^H}, ..., Im{x1*x2^H}, Im{x1*x1^H}}
|
||||
//
|
||||
// Latency: 5 clock cycles for CMPY using LUTs, 6 for DSPs.
|
||||
//
|
||||
// Dependencies:
|
||||
//
|
||||
// Revision:
|
||||
// Revision 0.01 - File Created
|
||||
// Revision 0.01 - File Created
|
||||
// 20230713-1557 - 1. 增加 AXIS 格式转换前后中间变量,便于观察中间结果;2. 输
|
||||
// 出位宽大于计算位宽时从符号为扩展变为末尾补零;3. 修改部分变量名称,提升
|
||||
// 可读性。
|
||||
// Additional Comments:
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
@@ -71,59 +75,57 @@ module acorr_cmplx_col_vec
|
||||
output [COL_NUM*COL_NUM*DATA_O_WIDTH-1:0] dout_imag
|
||||
);
|
||||
|
||||
localparam DATA_MULT_FULL_WIDTH = 2*DATA_I_WIDTH+1;
|
||||
localparam DATA_MULT_VALID_WIDTH = 2*DATA_I_WIDTH;
|
||||
localparam AXIS_DATA_I_WIDTH = 8*((DATA_I_WIDTH-1)/8+1) ; // axis data width of input real/image data
|
||||
localparam AXIS_DATA_P_WIDTH = 8*((DATA_MULT_FULL_WIDTH-1)/8+1) ; // axis data width of cmpy output real/image data
|
||||
// local parameters
|
||||
localparam CMPY_P_FULL_WIDTH = 2*DATA_I_WIDTH+1;
|
||||
localparam CMPY_P_VALID_WIDTH = 2*DATA_I_WIDTH;
|
||||
localparam AXIS_CMPY_I_WIDTH = 8*((DATA_I_WIDTH-1)/8+1) ; // axis data width of input real/image data
|
||||
localparam AXIS_CMPY_P_WIDTH = 8*((CMPY_P_FULL_WIDTH-1)/8+1); // axis data width of cmpy output real/image data
|
||||
|
||||
genvar i,j;
|
||||
|
||||
|
||||
// prepare cmpy input data
|
||||
wire [AXIS_DATA_I_WIDTH-1:0] din_real_array [0:COL_NUM-1];
|
||||
wire [AXIS_DATA_I_WIDTH-1:0] din_imag_array [0:COL_NUM-1];
|
||||
wire [DATA_I_WIDTH-1:0] din_real_array [0:COL_NUM-1];
|
||||
wire [DATA_I_WIDTH-1:0] din_imag_array [0:COL_NUM-1];
|
||||
|
||||
wire [AXIS_CMPY_I_WIDTH-1:0] din_real_array_axis [0:COL_NUM-1];
|
||||
wire [AXIS_CMPY_I_WIDTH-1:0] din_imag_array_axis [0:COL_NUM-1];
|
||||
|
||||
for(i = 0; i < COL_NUM; i = i + 1) begin: array_conversion
|
||||
// Array split
|
||||
assign din_real_array[i] = din_real[i*DATA_I_WIDTH +: DATA_I_WIDTH];
|
||||
assign din_imag_array[i] = din_imag[i*DATA_I_WIDTH +: DATA_I_WIDTH];
|
||||
|
||||
generate
|
||||
for(i = 0; i < COL_NUM; i = i + 1) begin: array_convert
|
||||
// Sign extension to fit 8-bit axis data format
|
||||
assign din_real_array[i] = {{(AXIS_DATA_I_WIDTH-DATA_I_WIDTH){din_real[(i+1)*DATA_I_WIDTH-1]}},din_real[i*DATA_I_WIDTH +: DATA_I_WIDTH]};
|
||||
assign din_imag_array[i] = {{(AXIS_DATA_I_WIDTH-DATA_I_WIDTH){din_imag[(i+1)*DATA_I_WIDTH-1]}},din_imag[i*DATA_I_WIDTH +: DATA_I_WIDTH]};
|
||||
assign din_real_array_axis[i] = {{(AXIS_CMPY_I_WIDTH-DATA_I_WIDTH){din_real_array[i][DATA_I_WIDTH-1]}},din_real[i*DATA_I_WIDTH +: DATA_I_WIDTH]};
|
||||
assign din_imag_array_axis[i] = {{(AXIS_CMPY_I_WIDTH-DATA_I_WIDTH){din_imag_array[i][DATA_I_WIDTH-1]}},din_imag[i*DATA_I_WIDTH +: DATA_I_WIDTH]};
|
||||
end
|
||||
endgenerate
|
||||
|
||||
|
||||
// complex multiplication
|
||||
wire [AXIS_DATA_P_WIDTH-1:0] cmpy_real_array [0:COL_NUM*COL_NUM-1];
|
||||
wire [AXIS_DATA_P_WIDTH-1:0] cmpy_imag_array [0:COL_NUM*COL_NUM-1];
|
||||
wire [AXIS_CMPY_P_WIDTH-1:0] cmpy_real_array_axis [0:COL_NUM*COL_NUM-1];
|
||||
wire [AXIS_CMPY_P_WIDTH-1:0] cmpy_imag_array_axis [0:COL_NUM*COL_NUM-1];
|
||||
|
||||
wire [CMPY_P_VALID_WIDTH-1:0] cmpy_real_array [0:COL_NUM*COL_NUM-1];
|
||||
wire [CMPY_P_VALID_WIDTH-1:0] cmpy_imag_array [0:COL_NUM*COL_NUM-1];
|
||||
|
||||
wire [DATA_O_WIDTH-1:0] dout_real_array [0:COL_NUM*COL_NUM-1];
|
||||
wire [DATA_O_WIDTH-1:0] dout_imag_array [0:COL_NUM*COL_NUM-1];
|
||||
|
||||
generate
|
||||
for(i = 0; i < COL_NUM; i = i + 1) begin: acorr_cmpy_col
|
||||
for(j = 0; j < COL_NUM; j = j + 1) begin: acorr_cmpy_row
|
||||
wire [2*AXIS_DATA_I_WIDTH-1:0] cmpy_a;
|
||||
wire [2*AXIS_DATA_I_WIDTH-1:0] cmpy_b;
|
||||
wire [2*AXIS_DATA_P_WIDTH-1:0] cmpy_p;
|
||||
// cmpy interface
|
||||
wire [2*AXIS_CMPY_I_WIDTH-1:0] cmpy_a;
|
||||
wire [2*AXIS_CMPY_I_WIDTH-1:0] cmpy_b;
|
||||
wire [2*AXIS_CMPY_P_WIDTH-1:0] cmpy_p;
|
||||
wire cmpy_p_vld;
|
||||
|
||||
assign cmpy_a = {din_imag_array[i],din_real_array[i]};
|
||||
assign cmpy_b = {-din_imag_array[j],din_real_array[j]};
|
||||
assign {cmpy_imag_array[i*COL_NUM+j],cmpy_real_array[i*COL_NUM+j]} = cmpy_p;
|
||||
assign cmpy_a = {din_imag_array_axis[i],din_real_array_axis[i]};
|
||||
assign cmpy_b = {-din_imag_array_axis[j],din_real_array_axis[j]};
|
||||
assign {cmpy_imag_array_axis[i*COL_NUM+j],cmpy_real_array_axis[i*COL_NUM+j]} = cmpy_p;
|
||||
|
||||
if (DATA_O_WIDTH <= DATA_MULT_VALID_WIDTH) begin
|
||||
// truncate msb of the valid part
|
||||
assign dout_real_array[i*COL_NUM+j] = cmpy_real_array[i*COL_NUM+j][DATA_MULT_VALID_WIDTH-1 -: DATA_O_WIDTH];
|
||||
assign dout_imag_array[i*COL_NUM+j] = cmpy_imag_array[i*COL_NUM+j][DATA_MULT_VALID_WIDTH-1 -: DATA_O_WIDTH];
|
||||
end
|
||||
else begin
|
||||
// sign extension to fit output data width
|
||||
assign dout_real_array[i*COL_NUM+j] = {{(DATA_O_WIDTH-DATA_MULT_VALID_WIDTH){cmpy_real_array[i*COL_NUM+j][DATA_MULT_VALID_WIDTH-1]}},cmpy_real_array[i*COL_NUM+j][0 +: DATA_MULT_VALID_WIDTH]};
|
||||
assign dout_imag_array[i*COL_NUM+j] = {{(DATA_O_WIDTH-DATA_MULT_VALID_WIDTH){cmpy_imag_array[i*COL_NUM+j][DATA_MULT_VALID_WIDTH-1]}},cmpy_imag_array[i*COL_NUM+j][0 +: DATA_MULT_VALID_WIDTH]};
|
||||
end
|
||||
|
||||
assign dout_real[(i*COL_NUM+j)*DATA_O_WIDTH +: DATA_O_WIDTH] = dout_real_array[i*COL_NUM+j];
|
||||
assign dout_imag[(i*COL_NUM+j)*DATA_O_WIDTH +: DATA_O_WIDTH] = dout_imag_array[i*COL_NUM+j];
|
||||
assign cmpy_real_array[i*COL_NUM+j] = cmpy_real_array_axis[i*COL_NUM+j][0 +: CMPY_P_VALID_WIDTH];
|
||||
assign cmpy_imag_array[i*COL_NUM+j] = cmpy_imag_array_axis[i*COL_NUM+j][0 +: CMPY_P_VALID_WIDTH];
|
||||
|
||||
cmpy_12x12 u_cmpy_12x12
|
||||
(
|
||||
@@ -135,9 +137,24 @@ end
|
||||
.m_axis_dout_tvalid (cmpy_p_vld ), // output wire m_axis_dout_tvalid
|
||||
.m_axis_dout_tdata (cmpy_p ) // output wire [63 : 0] m_axis_dout_tdata
|
||||
);
|
||||
|
||||
|
||||
// output data interface
|
||||
if (DATA_O_WIDTH <= CMPY_P_VALID_WIDTH) begin
|
||||
// truncate msb of the valid part
|
||||
assign dout_real_array[i*COL_NUM+j] = cmpy_real_array[i*COL_NUM+j][CMPY_P_VALID_WIDTH-1 -: DATA_O_WIDTH];
|
||||
assign dout_imag_array[i*COL_NUM+j] = cmpy_imag_array[i*COL_NUM+j][CMPY_P_VALID_WIDTH-1 -: DATA_O_WIDTH];
|
||||
end
|
||||
else begin
|
||||
// append zeros to fit output data width
|
||||
assign dout_real_array[i*COL_NUM+j] = {cmpy_real_array[i*COL_NUM+j],{(DATA_O_WIDTH-CMPY_P_VALID_WIDTH){1'b0}}};
|
||||
assign dout_imag_array[i*COL_NUM+j] = {cmpy_imag_array[i*COL_NUM+j],{(DATA_O_WIDTH-CMPY_P_VALID_WIDTH){1'b0}}};
|
||||
end
|
||||
|
||||
assign dout_real[(i*COL_NUM+j)*DATA_O_WIDTH +: DATA_O_WIDTH] = dout_real_array[i*COL_NUM+j];
|
||||
assign dout_imag[(i*COL_NUM+j)*DATA_O_WIDTH +: DATA_O_WIDTH] = dout_imag_array[i*COL_NUM+j];
|
||||
end
|
||||
end
|
||||
endgenerate
|
||||
|
||||
// output mapping
|
||||
assign dout_valid = acorr_cmpy_col[0].acorr_cmpy_row[0].cmpy_p_vld;
|
||||
|
||||
@@ -0,0 +1,800 @@
|
||||
`timescale 1ns / 1ps
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
// Company:
|
||||
// Engineer:
|
||||
// _ _ ____
|
||||
// | | ___ ___| |__ / ___| __ _ ___
|
||||
// _ | |/ _ \/ __| '_ \ | | _ / _` |/ _ \
|
||||
// | |_| | (_) \__ \ | | | | |_| | (_| | (_) |
|
||||
// \___/ \___/|___/_| |_| \____|\__,_|\___/
|
||||
//
|
||||
// Create Date: 07/17/2023 05:26:54 PM
|
||||
// Design Name:
|
||||
// Module Name: null_ctrl
|
||||
// Project Name:
|
||||
// Target Devices:
|
||||
// Tool Versions:
|
||||
// Description:
|
||||
//
|
||||
// Dependencies:
|
||||
//
|
||||
// Revision:
|
||||
// Revision 0.01 - File Created
|
||||
// Additional Comments:
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
module null_ctrl
|
||||
#(
|
||||
parameter ADC_WIDTH = 12 ,
|
||||
parameter CH_NUM = 4 ,
|
||||
parameter SYNC_HOP_INTVL = 48*1000 , // 1 ms of 48M clock, must > 48*200
|
||||
parameter STABLE_CNT_MOD = 48*5 , // 5 us of 48M clock
|
||||
parameter SNAPSHOT_NUM = 2048 ,
|
||||
parameter GUARD_CNT_MOD = 48*50 , // 50 us of 48M clock
|
||||
parameter ACCUM_WIDTH = 32 ,
|
||||
parameter ACORR_WIDTH = 2*ADC_WIDTH,
|
||||
parameter WEIGHT_WIDTH = 16 ,
|
||||
parameter OUTPUT_WIDTH = ADC_WIDTH,
|
||||
parameter LCMV_WIDTH = ADC_WIDTH + WEIGHT_WIDTH + $clog2(CH_NUM)
|
||||
)
|
||||
(
|
||||
// ***************************************************************************
|
||||
// ***************************** clock & reset *******************************
|
||||
// ***************************************************************************
|
||||
input clk ,
|
||||
input clk_phy ,
|
||||
input rst ,
|
||||
|
||||
//
|
||||
input hop_flag_in_phy ,
|
||||
input sync_flag_phy ,
|
||||
input lcmv_en_phy ,
|
||||
output hop_flag_out ,
|
||||
// ***************************************************************************
|
||||
// **************************** ADC Input Data *******************************
|
||||
// ***************************************************************************
|
||||
input adc_din_valid ,
|
||||
input [CH_NUM*ADC_WIDTH-1 : 0] adc_din_real ,
|
||||
input [CH_NUM*ADC_WIDTH-1 : 0] adc_din_imag ,
|
||||
|
||||
// ***************************************************************************
|
||||
// **************************** Autocorrelation ******************************
|
||||
// ***************************************************************************
|
||||
output acorr_din_valid ,
|
||||
output [CH_NUM*ADC_WIDTH-1 : 0] acorr_din_real ,
|
||||
output [CH_NUM*ADC_WIDTH-1 : 0] acorr_din_imag ,
|
||||
|
||||
input acorr_dout_valid ,
|
||||
input [CH_NUM*CH_NUM*ACORR_WIDTH-1:0] acorr_dout_real ,
|
||||
input [CH_NUM*CH_NUM*ACORR_WIDTH-1:0] acorr_dout_imag ,
|
||||
|
||||
// ***************************************************************************
|
||||
// **************************** Accumulation *********************************
|
||||
// ***************************************************************************
|
||||
output accum_rst ,
|
||||
|
||||
output accum_din_valid ,
|
||||
output [CH_NUM*CH_NUM*ACORR_WIDTH-1:0] accum_din_real ,
|
||||
output [CH_NUM*CH_NUM*ACORR_WIDTH-1:0] accum_din_imag ,
|
||||
|
||||
input accum_dout_valid ,
|
||||
input [CH_NUM*CH_NUM*ACCUM_WIDTH-1:0] accum_dout_real ,
|
||||
input [CH_NUM*CH_NUM*ACCUM_WIDTH-1:0] accum_dout_imag ,
|
||||
|
||||
// ***************************************************************************
|
||||
// ************************* Parallel to Serial ******************************
|
||||
// ***************************************************************************
|
||||
output stream_fifo_rst ,
|
||||
|
||||
output stream_din_valid ,
|
||||
output [CH_NUM*CH_NUM*ACCUM_WIDTH-1 : 0] stream_din_real ,
|
||||
output [CH_NUM*CH_NUM*ACCUM_WIDTH-1 : 0] stream_din_imag ,
|
||||
|
||||
// ***************************************************************************
|
||||
// ************************* Serial to Parallel ******************************
|
||||
// ***************************************************************************
|
||||
output weight_fifo_rst ,
|
||||
|
||||
input weight_dout_valid ,
|
||||
input [CH_NUM*WEIGHT_WIDTH-1 : 0] weight_dout_real ,
|
||||
input [CH_NUM*WEIGHT_WIDTH-1 : 0] weight_dout_imag ,
|
||||
|
||||
// ***************************************************************************
|
||||
// **************************** Spatial Filter *******************************
|
||||
// ***************************************************************************
|
||||
// input weight vector
|
||||
output filter_weight_valid ,
|
||||
output [CH_NUM*WEIGHT_WIDTH-1 : 0] filter_weight_real ,
|
||||
output [CH_NUM*WEIGHT_WIDTH-1 : 0] filter_weight_imag ,
|
||||
|
||||
// input adc data
|
||||
output filter_din_valid ,
|
||||
output [CH_NUM*ADC_WIDTH-1 : 0] filter_din_real ,
|
||||
output [CH_NUM*ADC_WIDTH-1 : 0] filter_din_imag ,
|
||||
|
||||
// output data
|
||||
input filter_dout_valid ,
|
||||
input [LCMV_WIDTH-1 : 0] filter_dout_real ,
|
||||
input [LCMV_WIDTH-1 : 0] filter_dout_imag ,
|
||||
|
||||
// ***************************************************************************
|
||||
// *************************** Output Data Port ******************************
|
||||
// ***************************************************************************
|
||||
output null_dout_valid ,
|
||||
output [OUTPUT_WIDTH-1 : 0] null_dout_real ,
|
||||
output [OUTPUT_WIDTH-1 : 0] null_dout_imag
|
||||
);
|
||||
|
||||
localparam RAM_HOP_DEPTH = 9600;
|
||||
|
||||
// hop flag delay of data segment when lcmv is enabled
|
||||
// 1 for rom addr reset
|
||||
// 1 for rom read data
|
||||
// 7 for spatial filter
|
||||
// 1 for buffering spatial filter input data - whether last or current hop
|
||||
// 1 for buffering spatial filter output data - whether lcmv or das
|
||||
localparam LCMV_DELAY = RAM_HOP_DEPTH + 11;
|
||||
|
||||
// hop flag delay of data segment when lcmv is enabled
|
||||
// 2 for multi-channel addition
|
||||
// 1 for buffering output data
|
||||
localparam DAS_DELAY = 3;
|
||||
|
||||
localparam CMPLX_DIM = 2;
|
||||
localparam NULL_DELAY = RAM_HOP_DEPTH + 6;
|
||||
localparam DAS_WIDTH = ADC_WIDTH + $clog2(CH_NUM);
|
||||
// autocorrelation state machine
|
||||
localparam ACORR_STATE_NUM = 4;
|
||||
localparam ACORR_STATE_IDLE = 0;
|
||||
localparam ACORR_STATE_STABLE = 1; // wait until rf is stable
|
||||
localparam ACORR_STATE_CALC = 2; // autocorrelation calculation and formatting
|
||||
localparam ACORR_STATE_GUARD = 3; // guard for data transmission and inverse calculation
|
||||
|
||||
integer i;
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////////// Clock Domain Crossing /////////////////////////////
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
wire hop_flag_in ; // input hop flag, pulse, level detection
|
||||
wire sync_flag ; // input sync segment indicator, 1 for sync segment, 0 for
|
||||
// data segment, level, level detection
|
||||
wire lcmv_en ; // input nulling algorithm enable control, 1 for enable, 2
|
||||
// for disable, level, level detection. If frequency
|
||||
// hopping is enabled in sync segment, nulling should be
|
||||
// turned off, because spatial anti-jamming cannot work
|
||||
// properly in this scenario.
|
||||
// wire hop_flag_out; // output hop flag, pulse
|
||||
|
||||
// hop_flag_in, input
|
||||
xpm_cdc_pulse #(
|
||||
.DEST_SYNC_FF (4), // DECIMAL; range: 2-10
|
||||
.INIT_SYNC_FF (1), // DECIMAL; 0=disable simulation init values, 1=enable simulation init values
|
||||
.REG_OUTPUT (1), // DECIMAL; 0=disable registered output, 1=enable registered output
|
||||
.RST_USED (0), // DECIMAL; 0=no reset, 1=implement reset
|
||||
.SIM_ASSERT_CHK (1) // DECIMAL; 0=disable simulation messages, 1=enable simulation messages
|
||||
) u_hop_flag_in
|
||||
(
|
||||
.dest_pulse (hop_flag_in ), // 1-bit output: Outputs a pulse the size of one dest_clk period when a pulse
|
||||
// transfer is correctly initiated on src_pulse input. This output is
|
||||
// combinatorial unless REG_OUTPUT is set to 1.
|
||||
.dest_clk (clk ), // 1-bit input: Destination clock.
|
||||
.dest_rst (1'b1 ), // 1-bit input: optional; required when RST_USED = 1
|
||||
.src_clk (clk_phy ), // 1-bit input: Source clock.
|
||||
.src_pulse (hop_flag_in_phy), // 1-bit input: Rising edge of this signal initiates a pulse transfer to the
|
||||
// destination clock domain. The minimum gap between each pulse transfer must be
|
||||
// at the minimum 2*(larger(src_clk period, dest_clk period)). This is measured
|
||||
// between the falling edge of a src_pulse to the rising edge of the next
|
||||
// src_pulse. This minimum gap will guarantee that each rising edge of src_pulse
|
||||
// will generate a pulse the size of one dest_clk period in the destination
|
||||
// clock domain. When RST_USED = 1, pulse transfers will not be guaranteed while
|
||||
// src_rst and/or dest_rst are asserted.
|
||||
.src_rst (1'b1 ) // 1-bit input: optional; required when RST_USED = 1
|
||||
);
|
||||
|
||||
// sync_flag, input
|
||||
xpm_cdc_single #(
|
||||
.DEST_SYNC_FF (4), // DECIMAL; range: 2-10
|
||||
.INIT_SYNC_FF (0), // DECIMAL; 0=disable simulation init values, 1=enable simulation init values
|
||||
.SIM_ASSERT_CHK (0), // DECIMAL; 0=disable simulation messages, 1=enable simulation messages
|
||||
.SRC_INPUT_REG (1) // DECIMAL; 0=do not register input, 1=register input
|
||||
)
|
||||
u_sync_flag (
|
||||
.dest_out (sync_flag ), // 1-bit output: src_in synchronized to the destination clock domain. This output is
|
||||
// registered.
|
||||
.dest_clk (clk ), // 1-bit input: Clock signal for the destination clock domain.
|
||||
.src_clk (clk_phy ), // 1-bit input: optional; required when SRC_INPUT_REG = 1
|
||||
.src_in (sync_flag_phy ) // 1-bit input: Input signal to be synchronized to dest_clk domain.
|
||||
);
|
||||
|
||||
// lcmv_en, input
|
||||
xpm_cdc_single #(
|
||||
.DEST_SYNC_FF (4), // DECIMAL; range: 2-10
|
||||
.INIT_SYNC_FF (0), // DECIMAL; 0=disable simulation init values, 1=enable simulation init values
|
||||
.SIM_ASSERT_CHK (0), // DECIMAL; 0=disable simulation messages, 1=enable simulation messages
|
||||
.SRC_INPUT_REG (1) // DECIMAL; 0=do not register input, 1=register input
|
||||
)
|
||||
u_lcmv_en (
|
||||
.dest_out (lcmv_en ), // 1-bit output: src_in synchronized to the destination clock domain. This output is
|
||||
// registered.
|
||||
.dest_clk (clk ), // 1-bit input: Clock signal for the destination clock domain.
|
||||
.src_clk (clk_phy ), // 1-bit input: optional; required when SRC_INPUT_REG = 1
|
||||
.src_in (lcmv_en_phy ) // 1-bit input: Input signal to be synchronized to dest_clk domain.
|
||||
);
|
||||
|
||||
// hop_flag_out, output
|
||||
// xpm_cdc_pulse #(
|
||||
// .DEST_SYNC_FF (4), // DECIMAL; range: 2-10
|
||||
// .INIT_SYNC_FF (1), // DECIMAL; 0=disable simulation init values, 1=enable simulation init values
|
||||
// .REG_OUTPUT (1), // DECIMAL; 0=disable registered output, 1=enable registered output
|
||||
// .RST_USED (0), // DECIMAL; 0=no reset, 1=implement reset
|
||||
// .SIM_ASSERT_CHK (1) // DECIMAL; 0=disable simulation messages, 1=enable simulation messages
|
||||
// ) u_hop_flag_out
|
||||
// (
|
||||
// .dest_pulse (hop_flag_out_phy ),
|
||||
// .dest_clk (clk_phy ),
|
||||
// .dest_rst (1'b1 ),
|
||||
// .src_clk (clk ),
|
||||
// .src_pulse (hop_flag_out ),
|
||||
// .src_rst (1'b1 )
|
||||
// );
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/////////////////////////// Autocorrelation Control ////////////////////////////
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// <--------------------------------------------------------------------------->
|
||||
// <-------------------- sync segment hop flag generation --------------------->
|
||||
// <--------------------------------------------------------------------------->
|
||||
reg [$clog2(SYNC_HOP_INTVL)-1 : 0] sync_hop_cnt = 'b0;
|
||||
reg sync_hop_flag = 'b0;
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
sync_hop_cnt <= 'b0;
|
||||
sync_hop_flag <= 'b0;
|
||||
end
|
||||
else if (sync_flag && lcmv_en) begin
|
||||
// During sync segment and when nulling algorithm is enabled
|
||||
|
||||
// Counter period is controlled by [SYNC_HOP_INTVL]
|
||||
sync_hop_cnt <= (sync_hop_cnt == SYNC_HOP_INTVL - 1) ? 'b0 : sync_hop_cnt + 1'b1;
|
||||
// For protection, assert 10 us after entering sync segment
|
||||
sync_hop_flag <= (sync_hop_cnt == 48*10 - 1) ? 1'b1 : 'b0;
|
||||
end
|
||||
else begin
|
||||
sync_hop_cnt <= 'b0;
|
||||
sync_hop_flag <= 'b0;
|
||||
end
|
||||
end
|
||||
|
||||
// <--------------------------------------------------------------------------->
|
||||
// <---------------------- autocorrelation state machine ---------------------->
|
||||
// <--------------------------------------------------------------------------->
|
||||
reg [$clog2(ACORR_STATE_NUM)-1 : 0] acorr_curr_state = ACORR_STATE_IDLE;
|
||||
reg [$clog2(ACORR_STATE_NUM)-1 : 0] acorr_next_state = ACORR_STATE_IDLE;
|
||||
reg [$clog2(STABLE_CNT_MOD)-1 : 0] stable_cnt = 'b0;
|
||||
reg [$clog2(SNAPSHOT_NUM)-1 : 0] snapshot_cnt = 'b0;
|
||||
reg [$clog2(GUARD_CNT_MOD)-1 : 0] guard_cnt = 'b0;
|
||||
reg snapshot_valid = 'b0;
|
||||
reg accum_rst_buf = 'b0;
|
||||
reg fifo_cdc_rst_buf = 'b0;
|
||||
|
||||
// 1st always block, sequential state transition
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
acorr_curr_state <= ACORR_STATE_IDLE;
|
||||
end
|
||||
else begin
|
||||
acorr_curr_state <= acorr_next_state;
|
||||
end
|
||||
end
|
||||
|
||||
// 2nd always block, combinational condition judgment
|
||||
always @(*) begin
|
||||
case (acorr_curr_state)
|
||||
ACORR_STATE_IDLE: begin
|
||||
if (adc_din_valid && lcmv_en) begin
|
||||
// if adc data is valid & lcmv is enabled
|
||||
if ((sync_flag && sync_hop_flag) || (~sync_flag && hop_flag_in)) begin
|
||||
acorr_next_state = ACORR_STATE_STABLE;
|
||||
end
|
||||
else begin
|
||||
acorr_next_state = ACORR_STATE_IDLE;
|
||||
end
|
||||
end
|
||||
else begin
|
||||
acorr_next_state = ACORR_STATE_IDLE;
|
||||
end
|
||||
end
|
||||
ACORR_STATE_STABLE: begin
|
||||
if (stable_cnt == STABLE_CNT_MOD-1) begin
|
||||
acorr_next_state = ACORR_STATE_CALC;
|
||||
end
|
||||
else begin
|
||||
acorr_next_state = ACORR_STATE_STABLE;
|
||||
end
|
||||
end
|
||||
ACORR_STATE_CALC: begin
|
||||
if (snapshot_cnt == SNAPSHOT_NUM-1) begin
|
||||
acorr_next_state = ACORR_STATE_GUARD;
|
||||
end
|
||||
else begin
|
||||
acorr_next_state = ACORR_STATE_CALC;
|
||||
end
|
||||
end
|
||||
ACORR_STATE_GUARD: begin
|
||||
if (guard_cnt == GUARD_CNT_MOD-1) begin
|
||||
acorr_next_state = ACORR_STATE_IDLE;
|
||||
end
|
||||
else begin
|
||||
acorr_next_state = ACORR_STATE_GUARD;
|
||||
end
|
||||
end
|
||||
default: begin
|
||||
acorr_next_state = ACORR_STATE_IDLE;
|
||||
end
|
||||
endcase
|
||||
end
|
||||
|
||||
// 3rd always block, the sequential FSM output
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
stable_cnt <= 'b0;
|
||||
snapshot_cnt <= 'b0;
|
||||
guard_cnt <= 'b0;
|
||||
snapshot_valid <= 'b0;
|
||||
accum_rst_buf <= 'b0;
|
||||
end
|
||||
else begin
|
||||
case (acorr_curr_state)
|
||||
ACORR_STATE_STABLE: begin
|
||||
stable_cnt <= stable_cnt + 1'b1;
|
||||
snapshot_cnt <= 'b0;
|
||||
guard_cnt <= 'b0;
|
||||
end
|
||||
ACORR_STATE_CALC: begin
|
||||
stable_cnt <= stable_cnt;
|
||||
snapshot_cnt <= snapshot_cnt + 1'b1;
|
||||
guard_cnt <= 'b0;
|
||||
end
|
||||
ACORR_STATE_GUARD: begin
|
||||
stable_cnt <= stable_cnt;
|
||||
snapshot_cnt <= snapshot_cnt;
|
||||
guard_cnt <= guard_cnt + 1'b1;
|
||||
end
|
||||
default: begin
|
||||
stable_cnt <= 'b0;
|
||||
snapshot_cnt <= 'b0;
|
||||
guard_cnt <= 'b0;
|
||||
end
|
||||
endcase
|
||||
|
||||
case (acorr_next_state)
|
||||
ACORR_STATE_CALC: begin
|
||||
snapshot_valid <= 1'b1;
|
||||
end
|
||||
default: begin
|
||||
snapshot_valid <= 'b0;
|
||||
end
|
||||
endcase
|
||||
|
||||
case (acorr_curr_state)
|
||||
ACORR_STATE_STABLE: begin
|
||||
accum_rst_buf <= 1'b1;
|
||||
fifo_cdc_rst_buf <= 1'b1;
|
||||
end
|
||||
default: begin
|
||||
accum_rst_buf <= 'b0;
|
||||
fifo_cdc_rst_buf <= 'b0;
|
||||
end
|
||||
endcase
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////////// Data Buffering Control ////////////////////////////
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// <--------------------------------------------------------------------------->
|
||||
// <--------------- store current hop & restore last hop weight --------------->
|
||||
// <--------------------------------------------------------------------------->
|
||||
reg sync_hop_flag_d = 'b0; // wait for ram data
|
||||
reg hop_flag_in_d = 'b0; // wait for ram data
|
||||
reg curr_weight_valid = 'b0;
|
||||
reg [CH_NUM*WEIGHT_WIDTH-1 : 0] curr_weight_real = 'b0;
|
||||
reg [CH_NUM*WEIGHT_WIDTH-1 : 0] curr_weight_imag = 'b0;
|
||||
reg last_weight_valid = 'b0;
|
||||
reg [CH_NUM*WEIGHT_WIDTH-1 : 0] last_weight_real = 'b0;
|
||||
reg [CH_NUM*WEIGHT_WIDTH-1 : 0] last_weight_imag = 'b0;
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
sync_hop_flag_d <= 'b0;
|
||||
hop_flag_in_d <= 'b0;
|
||||
|
||||
curr_weight_valid <= 'b0;
|
||||
curr_weight_real <= 'b0;
|
||||
curr_weight_imag <= 'b0;
|
||||
|
||||
last_weight_valid <= 'b0;
|
||||
last_weight_real <= 'b0;
|
||||
last_weight_imag <= 'b0;
|
||||
end
|
||||
else if (lcmv_en) begin
|
||||
// If lcmv is enabled
|
||||
|
||||
// Delay 1 clock cycle for adc data read
|
||||
sync_hop_flag_d <= sync_hop_flag;
|
||||
hop_flag_in_d <= hop_flag_in;
|
||||
|
||||
curr_weight_valid <= (weight_dout_valid) ? 1'b1 : 'b0;
|
||||
curr_weight_real <= (weight_dout_valid) ? weight_dout_real : curr_weight_real;
|
||||
curr_weight_imag <= (weight_dout_valid) ? weight_dout_imag : curr_weight_imag;
|
||||
|
||||
if ((sync_flag && sync_hop_flag_d) || (~sync_flag && hop_flag_in_d)) begin
|
||||
last_weight_valid <= 1'b1;
|
||||
last_weight_real <= curr_weight_real;
|
||||
last_weight_imag <= curr_weight_imag;
|
||||
end
|
||||
else begin
|
||||
last_weight_valid <= last_weight_valid;
|
||||
last_weight_real <= last_weight_real;
|
||||
last_weight_imag <= last_weight_imag;
|
||||
end
|
||||
|
||||
end
|
||||
else begin
|
||||
sync_hop_flag_d <= 'b0;
|
||||
hop_flag_in_d <= 'b0;
|
||||
|
||||
curr_weight_valid <= 'b0;
|
||||
curr_weight_real <= 'b0;
|
||||
curr_weight_imag <= 'b0;
|
||||
|
||||
last_weight_valid <= 'b0;
|
||||
last_weight_real <= 'b0;
|
||||
last_weight_imag <= 'b0;
|
||||
end
|
||||
end
|
||||
|
||||
// <--------------------------------------------------------------------------->
|
||||
// <---------------- store current hop & restore last hop data ---------------->
|
||||
// <--------------------------------------------------------------------------->
|
||||
// address counter
|
||||
reg [$clog2(RAM_HOP_DEPTH)-1 : 0] hop_data_cnt = 'b0;
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
hop_data_cnt <= 'b0;
|
||||
end
|
||||
else if(adc_din_valid && lcmv_en && ~sync_flag) begin
|
||||
// if adc data is valid & lcmv is enabled & during data segment
|
||||
if (hop_flag_in) begin
|
||||
hop_data_cnt <= 'b0;
|
||||
end
|
||||
else begin
|
||||
hop_data_cnt <= (hop_data_cnt == RAM_HOP_DEPTH-1) ? 'b0 : hop_data_cnt + 1'b1;
|
||||
end
|
||||
end
|
||||
else begin
|
||||
hop_data_cnt <= 'b0;
|
||||
end
|
||||
end
|
||||
|
||||
// data interface
|
||||
wire [CMPLX_DIM*CH_NUM*ADC_WIDTH-1 : 0] curr_hop_data;
|
||||
wire [CMPLX_DIM*CH_NUM*ADC_WIDTH-1 : 0] last_hop_data;
|
||||
reg last_hop_valid = 'b0;
|
||||
|
||||
wire [CH_NUM*ADC_WIDTH-1 : 0] last_data_real;
|
||||
wire [CH_NUM*ADC_WIDTH-1 : 0] last_data_imag;
|
||||
|
||||
assign curr_hop_data = {adc_din_imag,adc_din_real};
|
||||
assign {last_data_imag,last_data_real} = last_hop_data;
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
last_hop_valid <= 'b0;
|
||||
end
|
||||
else if(adc_din_valid && lcmv_en && ~sync_flag) begin
|
||||
// if adc data is valid & lcmv is enabled & during data segment
|
||||
last_hop_valid <= adc_din_valid;
|
||||
end
|
||||
else begin
|
||||
last_hop_valid <= 'b0;
|
||||
end
|
||||
end
|
||||
|
||||
ram_hop_data u_ram_hop_data
|
||||
(
|
||||
.clka (clk ), // input wire clka
|
||||
.wea (adc_din_valid ), // input wire [0 : 0] wea
|
||||
.addra(hop_data_cnt ), // input wire [13 : 0] addra
|
||||
.dina (curr_hop_data ), // input wire [95 : 0] dina
|
||||
.douta(last_hop_data ) // output wire [95 : 0] douta
|
||||
);
|
||||
|
||||
// <--------------------------------------------------------------------------->
|
||||
// <----------------- hop flag buffering when lcmv is enabled ----------------->
|
||||
// <--------------------------------------------------------------------------->
|
||||
reg [$clog2(LCMV_DELAY)-1 : 0] lcmv_hop_cnt_1 = 'b0;
|
||||
reg [$clog2(LCMV_DELAY)-1 : 0] lcmv_hop_cnt_2 = 'b0;
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
lcmv_hop_cnt_1 <= 'b0;
|
||||
lcmv_hop_cnt_2 <= 'b0;
|
||||
end
|
||||
else if (lcmv_en && ~sync_flag) begin
|
||||
if (hop_flag_in) begin
|
||||
if (lcmv_hop_cnt_1 == 'b0 && lcmv_hop_cnt_2 == 'b0) begin
|
||||
lcmv_hop_cnt_1 <= 1'b1;
|
||||
lcmv_hop_cnt_2 <= 'b0;
|
||||
end
|
||||
else if (lcmv_hop_cnt_1 != 'b0 && lcmv_hop_cnt_2 == 'b0) begin
|
||||
lcmv_hop_cnt_1 <= (lcmv_hop_cnt_1 == LCMV_DELAY-1) ? 'b0 : lcmv_hop_cnt_1 + 1'b1;
|
||||
lcmv_hop_cnt_2 <= 1'b1;
|
||||
end
|
||||
else if (lcmv_hop_cnt_1 == 'b0 && lcmv_hop_cnt_2 != 'b0) begin
|
||||
lcmv_hop_cnt_1 <= 1'b1;
|
||||
lcmv_hop_cnt_2 <= (lcmv_hop_cnt_2 == LCMV_DELAY-1) ? 'b0 : lcmv_hop_cnt_2 + 1'b1;
|
||||
end
|
||||
else begin
|
||||
lcmv_hop_cnt_1 <= (lcmv_hop_cnt_1 == LCMV_DELAY-1) ? 'b0 : lcmv_hop_cnt_1 + 1'b1;
|
||||
lcmv_hop_cnt_2 <= (lcmv_hop_cnt_2 == LCMV_DELAY-1) ? 'b0 : lcmv_hop_cnt_2 + 1'b1;
|
||||
end
|
||||
end
|
||||
else begin
|
||||
// behaviour of [lcmv_hop_cnt_1] when [hop_flag_in] does not assert
|
||||
if (lcmv_hop_cnt_1 != 'b0) begin
|
||||
lcmv_hop_cnt_1 <= (lcmv_hop_cnt_1 == LCMV_DELAY-1) ? 'b0 : lcmv_hop_cnt_1 + 1'b1;
|
||||
end
|
||||
else begin
|
||||
lcmv_hop_cnt_1 <= 'b0;
|
||||
end
|
||||
// behaviour of [lcmv_hop_cnt_2] when [hop_flag_in] does not assert
|
||||
if (lcmv_hop_cnt_2 != 'b0) begin
|
||||
lcmv_hop_cnt_2 <= (lcmv_hop_cnt_2 == LCMV_DELAY-1) ? 'b0 : lcmv_hop_cnt_2 + 1'b1;
|
||||
end
|
||||
else begin
|
||||
lcmv_hop_cnt_2 <= 'b0;
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
else begin
|
||||
lcmv_hop_cnt_1 <= 'b0;
|
||||
lcmv_hop_cnt_2 <= 'b0;
|
||||
end
|
||||
end
|
||||
|
||||
// <--------------------------------------------------------------------------->
|
||||
// <----------------- hop flag buffering when das is enabled ------------------>
|
||||
// <--------------------------------------------------------------------------->
|
||||
reg [$clog2(DAS_DELAY)-1 : 0] das_hop_cnt = 'b0;
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
das_hop_cnt <= 'b0;
|
||||
end
|
||||
else if (~lcmv_en && ~sync_flag) begin
|
||||
if (hop_flag_in) begin
|
||||
das_hop_cnt <= 1'b1;
|
||||
end
|
||||
else if (das_hop_cnt != 0) begin
|
||||
das_hop_cnt <= (das_hop_cnt == DAS_DELAY-1) ? 'b0 : das_hop_cnt + 1'b1;
|
||||
end
|
||||
else begin
|
||||
das_hop_cnt <= 'b0;
|
||||
end
|
||||
end
|
||||
else begin
|
||||
das_hop_cnt <= 'b0;
|
||||
end
|
||||
end
|
||||
|
||||
reg hop_flag_out_buf = 'b0;
|
||||
|
||||
assign hop_flag_out = hop_flag_out_buf;
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
hop_flag_out_buf <= 'b0;
|
||||
end
|
||||
else if (lcmv_hop_cnt_1 == LCMV_DELAY-1 || lcmv_hop_cnt_2 == LCMV_DELAY-1 || das_hop_cnt == DAS_DELAY-1) begin
|
||||
hop_flag_out_buf <= 1'b1;
|
||||
end
|
||||
else begin
|
||||
hop_flag_out_buf <= 'b0;
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////////////// Delay and Sum /////////////////////////////////
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
wire das_valid;
|
||||
wire [DAS_WIDTH-1 : 0] das_real;
|
||||
wire [DAS_WIDTH-1 : 0] das_imag;
|
||||
|
||||
wire [LCMV_WIDTH-1 : 0] das_real_ext;
|
||||
wire [LCMV_WIDTH-1 : 0] das_imag_ext;
|
||||
|
||||
assign das_real_ext = {das_real,{(LCMV_WIDTH-DAS_WIDTH){1'b0}}};
|
||||
assign das_imag_ext = {das_imag,{(LCMV_WIDTH-DAS_WIDTH){1'b0}}};
|
||||
|
||||
adder_tree_ppl #(
|
||||
.DATA_I_WIDTH (ADC_WIDTH ),
|
||||
.DATA_NUM (CH_NUM )
|
||||
) u_das_add_ppl_real (
|
||||
// clock & reset
|
||||
.clk (clk ),
|
||||
.rst (rst ),
|
||||
|
||||
// input data
|
||||
.din_valid (adc_din_valid ),
|
||||
.din_data (adc_din_real ),
|
||||
|
||||
// output data
|
||||
.dout_valid (das_valid ),
|
||||
.dout_data (das_real )
|
||||
);
|
||||
|
||||
adder_tree_ppl #(
|
||||
.DATA_I_WIDTH (ADC_WIDTH ),
|
||||
.DATA_NUM (CH_NUM )
|
||||
) u_das_add_ppl_imag (
|
||||
// clock & reset
|
||||
.clk (clk ),
|
||||
.rst (rst ),
|
||||
|
||||
// input data
|
||||
.din_valid (adc_din_valid ),
|
||||
.din_data (adc_din_imag ),
|
||||
|
||||
// output data
|
||||
.dout_valid ( ),
|
||||
.dout_data (das_imag )
|
||||
);
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
///////////////////////////// Output Data Control //////////////////////////////
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
reg null_dout_valid_buf = 'b0;
|
||||
reg [OUTPUT_WIDTH-1 : 0] null_dout_real_buf = 'b0;
|
||||
reg [OUTPUT_WIDTH-1 : 0] null_dout_imag_buf = 'b0;
|
||||
|
||||
assign null_dout_valid = null_dout_valid_buf;
|
||||
assign null_dout_real = null_dout_real_buf ;
|
||||
assign null_dout_imag = null_dout_imag_buf ;
|
||||
|
||||
if (OUTPUT_WIDTH <= LCMV_WIDTH) begin
|
||||
// truncate msb
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
null_dout_valid_buf <= 'b0;
|
||||
null_dout_real_buf <= 'b0;
|
||||
null_dout_imag_buf <= 'b0;
|
||||
end
|
||||
else if (lcmv_en) begin
|
||||
null_dout_valid_buf <= filter_dout_valid;
|
||||
null_dout_real_buf <= filter_dout_real[LCMV_WIDTH-1 -: OUTPUT_WIDTH];
|
||||
null_dout_imag_buf <= filter_dout_imag[LCMV_WIDTH-1 -: OUTPUT_WIDTH];
|
||||
end
|
||||
else begin
|
||||
null_dout_valid_buf <= das_valid;
|
||||
null_dout_real_buf <= das_real_ext[LCMV_WIDTH-1 -: OUTPUT_WIDTH];
|
||||
null_dout_imag_buf <= das_imag_ext[LCMV_WIDTH-1 -: OUTPUT_WIDTH];
|
||||
end
|
||||
end
|
||||
end
|
||||
else begin // if (OUTPUT_WIDTH > LCMV_WIDTH)
|
||||
// append zeros to fit output data width
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
null_dout_valid_buf <= 'b0;
|
||||
null_dout_real_buf <= 'b0;
|
||||
null_dout_imag_buf <= 'b0;
|
||||
end
|
||||
else if (lcmv_en) begin
|
||||
null_dout_valid_buf <= filter_dout_valid;
|
||||
null_dout_real_buf <= {filter_dout_real,{(OUTPUT_WIDTH-LCMV_WIDTH){1'b0}}};
|
||||
null_dout_imag_buf <= {filter_dout_imag,{(OUTPUT_WIDTH-LCMV_WIDTH){1'b0}}};
|
||||
end
|
||||
else begin
|
||||
null_dout_valid_buf <= das_valid;
|
||||
null_dout_real_buf <= {das_real_ext,{(OUTPUT_WIDTH-LCMV_WIDTH){1'b0}}};
|
||||
null_dout_imag_buf <= {das_imag_ext,{(OUTPUT_WIDTH-LCMV_WIDTH){1'b0}}};
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
///////////////////////////// Submodule Interface //////////////////////////////
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// ADC Input Data -> Autocorrelation
|
||||
assign acorr_din_valid = snapshot_valid;
|
||||
assign acorr_din_real = adc_din_real;
|
||||
assign acorr_din_imag = adc_din_imag;
|
||||
|
||||
// Autocorrelation -> Accumulation
|
||||
assign accum_rst = accum_rst_buf;
|
||||
assign accum_din_valid = acorr_dout_valid;
|
||||
assign accum_din_real = acorr_dout_real;
|
||||
assign accum_din_imag = acorr_dout_imag;
|
||||
|
||||
// Accumulation -> Parallel to Serial
|
||||
assign stream_fifo_rst = fifo_cdc_rst_buf;
|
||||
assign stream_din_valid = accum_dout_valid;
|
||||
assign stream_din_real = accum_dout_real;
|
||||
assign stream_din_imag = accum_dout_imag;
|
||||
|
||||
// Serial to Parallel
|
||||
assign weight_fifo_rst = fifo_cdc_rst_buf;
|
||||
|
||||
// Spatial Filter
|
||||
reg filter_weight_valid_buf = 'b0;
|
||||
reg [CH_NUM*WEIGHT_WIDTH-1 : 0] filter_weight_real_buf = 'b0;
|
||||
reg [CH_NUM*WEIGHT_WIDTH-1 : 0] filter_weight_imag_buf = 'b0;
|
||||
|
||||
reg filter_din_valid_buf = 'b0;
|
||||
reg [CH_NUM*ADC_WIDTH-1 : 0] filter_din_real_buf = 'b0;
|
||||
reg [CH_NUM*ADC_WIDTH-1 : 0] filter_din_imag_buf = 'b0;
|
||||
|
||||
assign filter_weight_valid = filter_weight_valid_buf;
|
||||
assign filter_weight_real = filter_weight_real_buf ;
|
||||
assign filter_weight_imag = filter_weight_imag_buf ;
|
||||
|
||||
assign filter_din_valid = filter_din_valid_buf;
|
||||
assign filter_din_real = filter_din_real_buf ;
|
||||
assign filter_din_imag = filter_din_imag_buf ;
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
filter_weight_valid_buf <= 'b0;
|
||||
filter_weight_real_buf <= 'b0;
|
||||
filter_weight_imag_buf <= 'b0;
|
||||
|
||||
filter_din_valid_buf <= 'b0;
|
||||
filter_din_real_buf <= 'b0;
|
||||
filter_din_imag_buf <= 'b0;
|
||||
end
|
||||
else if (lcmv_en) begin
|
||||
if (sync_flag) begin
|
||||
filter_weight_valid_buf <= curr_weight_valid;
|
||||
filter_weight_real_buf <= curr_weight_real ;
|
||||
filter_weight_imag_buf <= curr_weight_imag ;
|
||||
|
||||
filter_din_valid_buf <= adc_din_valid ;
|
||||
filter_din_real_buf <= adc_din_real ;
|
||||
filter_din_imag_buf <= adc_din_imag ;
|
||||
end
|
||||
else begin
|
||||
filter_weight_valid_buf <= last_weight_valid;
|
||||
filter_weight_real_buf <= last_weight_real ;
|
||||
filter_weight_imag_buf <= last_weight_imag ;
|
||||
|
||||
filter_din_valid_buf <= last_hop_valid;
|
||||
filter_din_real_buf <= last_data_real ;
|
||||
filter_din_imag_buf <= last_data_imag ;
|
||||
end
|
||||
end
|
||||
else begin
|
||||
filter_weight_valid_buf <= 'b0;
|
||||
filter_weight_real_buf <= 'b0;
|
||||
filter_weight_imag_buf <= 'b0;
|
||||
|
||||
filter_din_valid_buf <= 'b0;
|
||||
filter_din_real_buf <= 'b0;
|
||||
filter_din_imag_buf <= 'b0;
|
||||
end
|
||||
end
|
||||
|
||||
endmodule
|
||||
@@ -14,7 +14,9 @@
|
||||
// Dependencies:
|
||||
//
|
||||
// Revision:
|
||||
// Revision 0.01 - File Created
|
||||
// Revision 0.01 - File Created
|
||||
// 20230713-1529 - 由于 Cordic IP 核会将输入信号进行缩放,为避免缩放后溢出,将
|
||||
// Cordic 的输入改为至少两个符号位。
|
||||
// Additional Comments:
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
@@ -24,23 +26,23 @@ module phase_comp
|
||||
#(
|
||||
parameter DATA_WIDTH = 12,
|
||||
parameter CORDIC_WIDTH = 16,
|
||||
parameter CHANNEL_NUM = 4
|
||||
parameter CH_NUM = 4
|
||||
)
|
||||
(
|
||||
// clock & reset
|
||||
input clk ,
|
||||
input rst ,
|
||||
input clk ,
|
||||
input rst ,
|
||||
|
||||
// input data
|
||||
input din_valid ,
|
||||
input [CHANNEL_NUM*CORDIC_WIDTH-1:0] phase ,
|
||||
input [CHANNEL_NUM*DATA_WIDTH-1:0] din_real ,
|
||||
input [CHANNEL_NUM*DATA_WIDTH-1:0] din_imag ,
|
||||
input din_valid ,
|
||||
input [CH_NUM*CORDIC_WIDTH-1:0] phase ,
|
||||
input [CH_NUM*DATA_WIDTH-1:0] din_real ,
|
||||
input [CH_NUM*DATA_WIDTH-1:0] din_imag ,
|
||||
|
||||
// output data
|
||||
output dout_valid ,
|
||||
output [CHANNEL_NUM*DATA_WIDTH-1:0] dout_real ,
|
||||
output [CHANNEL_NUM*DATA_WIDTH-1:0] dout_imag
|
||||
output dout_valid ,
|
||||
output [CH_NUM*DATA_WIDTH-1:0] dout_real,
|
||||
output [CH_NUM*DATA_WIDTH-1:0] dout_imag
|
||||
);
|
||||
|
||||
genvar m;
|
||||
@@ -48,86 +50,80 @@ genvar m;
|
||||
localparam AXIS_CORDIC_WIDTH = 8*((CORDIC_WIDTH-1)/8+1);
|
||||
|
||||
// prepare cordic input data
|
||||
wire [AXIS_CORDIC_WIDTH-1:0] din_real_array [0:CHANNEL_NUM-1];
|
||||
wire [AXIS_CORDIC_WIDTH-1:0] din_imag_array [0:CHANNEL_NUM-1];
|
||||
wire [AXIS_CORDIC_WIDTH-1:0] phase_array [0:CHANNEL_NUM-1];
|
||||
wire [AXIS_CORDIC_WIDTH-1:0] din_real_array [0:CH_NUM-1];
|
||||
wire [AXIS_CORDIC_WIDTH-1:0] din_imag_array [0:CH_NUM-1];
|
||||
wire [AXIS_CORDIC_WIDTH-1:0] phase_array [0:CH_NUM-1];
|
||||
|
||||
generate
|
||||
for(m = 0; m < CHANNEL_NUM; m = m + 1) begin: array_convert
|
||||
for(m = 0; m < CH_NUM; m = m + 1) begin: array_convert
|
||||
if (CORDIC_WIDTH > DATA_WIDTH+1) begin
|
||||
// append zeros to fit cordic input with, sign-bit extension to fit 8 bit axis format, keep at least 2 sign-bits for cordic scaling
|
||||
assign din_real_array[m] = {{(AXIS_CORDIC_WIDTH-CORDIC_WIDTH+1){din_real[(m+1)*DATA_WIDTH-1]}},din_real[m*DATA_WIDTH +: DATA_WIDTH],{(CORDIC_WIDTH-DATA_WIDTH-1){1'b0}}};
|
||||
assign din_imag_array[m] = {{(AXIS_CORDIC_WIDTH-CORDIC_WIDTH+1){din_imag[(m+1)*DATA_WIDTH-1]}},din_imag[m*DATA_WIDTH +: DATA_WIDTH],{(CORDIC_WIDTH-DATA_WIDTH-1){1'b0}}};
|
||||
end
|
||||
else begin
|
||||
// truncate msb, keep at least 2 sign-bits for cordic scaling
|
||||
assign din_real_array[m] = {din_real[(m+1)*DATA_WIDTH-1],din_real[(m+1)*DATA_WIDTH-1 -: (AXIS_CORDIC_WIDTH-1)]};
|
||||
assign din_imag_array[m] = {din_imag[(m+1)*DATA_WIDTH-1],din_imag[(m+1)*DATA_WIDTH-1 -: (AXIS_CORDIC_WIDTH-1)]};
|
||||
end
|
||||
|
||||
if (CORDIC_WIDTH > DATA_WIDTH) begin
|
||||
// append zeros to fit cordic input with, sign-bit extension to fit 8 bit axis format
|
||||
assign din_real_array[m] = {{(AXIS_CORDIC_WIDTH-CORDIC_WIDTH){din_real[(m+1)*DATA_WIDTH-1]}},din_real[m*DATA_WIDTH +: DATA_WIDTH],{(CORDIC_WIDTH-DATA_WIDTH){1'b0}}};
|
||||
assign din_imag_array[m] = {{(AXIS_CORDIC_WIDTH-CORDIC_WIDTH){din_imag[(m+1)*DATA_WIDTH-1]}},din_imag[m*DATA_WIDTH +: DATA_WIDTH],{(CORDIC_WIDTH-DATA_WIDTH){1'b0}}};
|
||||
if (AXIS_CORDIC_WIDTH > CORDIC_WIDTH) begin
|
||||
// sign-bit extension to fit 8 bit axis format
|
||||
assign phase_array[m] = {{(AXIS_CORDIC_WIDTH-CORDIC_WIDTH){phase[(m+1)*CORDIC_WIDTH-1]}},phase[m*CORDIC_WIDTH +: CORDIC_WIDTH]};
|
||||
end
|
||||
else begin
|
||||
// truncate msb
|
||||
assign phase_array[m] = phase[(m+1)*CORDIC_WIDTH-1 -: AXIS_CORDIC_WIDTH];
|
||||
end
|
||||
end
|
||||
else begin
|
||||
// truncate msb
|
||||
assign din_real_array[m] = din_real[(m+1)*DATA_WIDTH-1 -: AXIS_CORDIC_WIDTH];
|
||||
assign din_imag_array[m] = din_imag[(m+1)*DATA_WIDTH-1 -: AXIS_CORDIC_WIDTH];
|
||||
end
|
||||
|
||||
if (AXIS_CORDIC_WIDTH > CORDIC_WIDTH) begin
|
||||
// sign-bit extension to fit 8 bit axis format
|
||||
assign phase_array[m] = {{(AXIS_CORDIC_WIDTH-CORDIC_WIDTH){phase[(m+1)*CORDIC_WIDTH-1]}},phase[m*CORDIC_WIDTH +: CORDIC_WIDTH]};
|
||||
end
|
||||
else begin
|
||||
// truncate msb
|
||||
assign phase_array[m] = phase[(m+1)*CORDIC_WIDTH-1 -: AXIS_CORDIC_WIDTH];
|
||||
end
|
||||
|
||||
end
|
||||
endgenerate
|
||||
|
||||
// output data & cordic interface
|
||||
wire [AXIS_CORDIC_WIDTH-1:0] rotate_real_array [0:CHANNEL_NUM-1];
|
||||
wire [AXIS_CORDIC_WIDTH-1:0] rotate_imag_array [0:CHANNEL_NUM-1];
|
||||
wire [AXIS_CORDIC_WIDTH-1:0] rotate_real_array [0:CH_NUM-1];
|
||||
wire [AXIS_CORDIC_WIDTH-1:0] rotate_imag_array [0:CH_NUM-1];
|
||||
|
||||
wire [DATA_WIDTH-1:0] dout_real_array [0:CHANNEL_NUM-1];
|
||||
wire [DATA_WIDTH-1:0] dout_imag_array [0:CHANNEL_NUM-1];
|
||||
wire [DATA_WIDTH-1:0] dout_real_array [0:CH_NUM-1];
|
||||
wire [DATA_WIDTH-1:0] dout_imag_array [0:CH_NUM-1];
|
||||
|
||||
generate
|
||||
for(m = 0; m < CHANNEL_NUM; m = m + 1) begin: cordic
|
||||
for(m = 0; m < CH_NUM; m = m + 1) begin: cordic
|
||||
|
||||
wire rotate_phase_valid;
|
||||
wire [15:0] rotate_phase_data ;
|
||||
wire rotate_cart_valid ;
|
||||
wire [31:0] rotate_cart_data ;
|
||||
wire rotate_dout_valid ;
|
||||
wire [31:0] rotate_dout_data ;
|
||||
wire rotate_phase_valid;
|
||||
wire [15:0] rotate_phase_data ;
|
||||
wire rotate_cart_valid ;
|
||||
wire [31:0] rotate_cart_data ;
|
||||
wire rotate_dout_valid ;
|
||||
wire [31:0] rotate_dout_data ;
|
||||
|
||||
assign rotate_phase_valid = din_valid;
|
||||
assign rotate_phase_data = phase_array[m];
|
||||
assign rotate_cart_valid = din_valid;
|
||||
assign rotate_cart_data = {din_imag_array[m],din_real_array[m]};
|
||||
assign {rotate_imag_array[m],rotate_real_array[m]} = rotate_dout_data;
|
||||
assign rotate_phase_valid = din_valid;
|
||||
assign rotate_phase_data = phase_array[m];
|
||||
assign rotate_cart_valid = din_valid;
|
||||
assign rotate_cart_data = {din_imag_array[m],din_real_array[m]};
|
||||
assign {rotate_imag_array[m],rotate_real_array[m]} = rotate_dout_data;
|
||||
|
||||
if (DATA_WIDTH > AXIS_CORDIC_WIDTH) begin
|
||||
// append zeros
|
||||
assign dout_real_array[m] = {rotate_real_array[m],{(DATA_WIDTH-AXIS_CORDIC_WIDTH){1'b0}}};
|
||||
assign dout_imag_array[m] = {rotate_imag_array[m],{(DATA_WIDTH-AXIS_CORDIC_WIDTH){1'b0}}};
|
||||
end
|
||||
else begin
|
||||
// truncate msb
|
||||
assign dout_real_array[m] = rotate_real_array[m][AXIS_CORDIC_WIDTH-1 -: DATA_WIDTH];
|
||||
assign dout_imag_array[m] = rotate_imag_array[m][AXIS_CORDIC_WIDTH-1 -: DATA_WIDTH];
|
||||
end
|
||||
if (DATA_WIDTH > AXIS_CORDIC_WIDTH) begin
|
||||
// append zeros
|
||||
assign dout_real_array[m] = {rotate_real_array[m],{(DATA_WIDTH-AXIS_CORDIC_WIDTH){1'b0}}};
|
||||
assign dout_imag_array[m] = {rotate_imag_array[m],{(DATA_WIDTH-AXIS_CORDIC_WIDTH){1'b0}}};
|
||||
end
|
||||
else begin
|
||||
// truncate msb
|
||||
assign dout_real_array[m] = rotate_real_array[m][AXIS_CORDIC_WIDTH-1 -: DATA_WIDTH];
|
||||
assign dout_imag_array[m] = rotate_imag_array[m][AXIS_CORDIC_WIDTH-1 -: DATA_WIDTH];
|
||||
end
|
||||
|
||||
assign dout_real[m*DATA_WIDTH +: DATA_WIDTH] = dout_real_array[m];
|
||||
assign dout_imag[m*DATA_WIDTH +: DATA_WIDTH] = dout_imag_array[m];
|
||||
assign dout_real[m*DATA_WIDTH +: DATA_WIDTH] = dout_real_array[m];
|
||||
assign dout_imag[m*DATA_WIDTH +: DATA_WIDTH] = dout_imag_array[m];
|
||||
|
||||
rotate_16b u_rotate_16b
|
||||
(
|
||||
.aclk (clk ), // input wire aclk
|
||||
.s_axis_phase_tvalid (rotate_phase_valid ), // input wire s_axis_phase_tvalid
|
||||
.s_axis_phase_tdata (rotate_phase_data ), // input wire [15 : 0] s_axis_phase_tdata
|
||||
.s_axis_cartesian_tvalid(rotate_cart_valid ), // input wire s_axis_cartesian_tvalid
|
||||
.s_axis_cartesian_tdata (rotate_cart_data ), // input wire [31 : 0] s_axis_cartesian_tdata
|
||||
.m_axis_dout_tvalid (rotate_dout_valid ), // output wire m_axis_dout_tvalid
|
||||
.m_axis_dout_tdata (rotate_dout_data ) // output wire [31 : 0] m_axis_dout_tdata
|
||||
);
|
||||
rotate_16b u_rotate_16b
|
||||
(
|
||||
.aclk (clk ), // input wire aclk
|
||||
.s_axis_phase_tvalid (rotate_phase_valid ), // input wire s_axis_phase_tvalid
|
||||
.s_axis_phase_tdata (rotate_phase_data ), // input wire [15 : 0] s_axis_phase_tdata
|
||||
.s_axis_cartesian_tvalid(rotate_cart_valid ), // input wire s_axis_cartesian_tvalid
|
||||
.s_axis_cartesian_tdata (rotate_cart_data ), // input wire [31 : 0] s_axis_cartesian_tdata
|
||||
.m_axis_dout_tvalid (rotate_dout_valid ), // output wire m_axis_dout_tvalid
|
||||
.m_axis_dout_tdata (rotate_dout_data ) // output wire [31 : 0] m_axis_dout_tdata
|
||||
);
|
||||
|
||||
end
|
||||
endgenerate
|
||||
end
|
||||
|
||||
assign dout_valid = cordic[0].rotate_dout_valid;
|
||||
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
// Description: Pre-process rx data, including ad9361 mcs & implementing nulling
|
||||
// algorithm on rx data. The latency of autocorrelation is consisted of 2
|
||||
// parts: 1. [STABLE_CNT_MOD] + [SNAPSHOT_NUM] + several intermediate delay
|
||||
// of [sys_clk] clock cycles; 2. ([CHANNEL_NUM]*[CHANNEL_NUM]*[CMPLX_DIM] +
|
||||
// of [sys_clk] clock cycles; 2. ([CH_NUM]*[CH_NUM]*[CMPLX_DIM] +
|
||||
// 1 frame head + 1 frame length)*[ACCUM_WIDTH] of [clk_96m] clock cycles.
|
||||
// The simulation result shows delay of about 30us when [sys_clk] is 48m.
|
||||
//
|
||||
@@ -43,69 +43,70 @@
|
||||
|
||||
module rx_pre_process
|
||||
#(
|
||||
parameter CAL_CNT_MOD = 48 ,
|
||||
parameter CAL_PEAK_POS = 12 ,
|
||||
parameter STABLE_CNT_MOD = 48 ,
|
||||
parameter ADC_DATA_WIDTH = 12 ,
|
||||
parameter CHANNEL_NUM = 4 ,
|
||||
parameter PHASE_WIDTH = 16 ,
|
||||
parameter SNAPSHOT_NUM = 256,
|
||||
parameter PS_PL_WIDTH = 32 ,
|
||||
parameter WEIGHT_TRUNC_WIDTH = 16 ,
|
||||
parameter CMPLX_DIM = 2 ,
|
||||
parameter OUTPUT_DATA_WIDTH = ADC_DATA_WIDTH,
|
||||
parameter ACCOR_FRAME_HEAD = 32'h7E7E7E7E,
|
||||
parameter WEIGHT_FRAME_HEAD = ACCOR_FRAME_HEAD // Same head is required by [c2c_bridge] module
|
||||
parameter CAL_CNT_MOD = 48 ,
|
||||
parameter CAL_PEAK_POS = 12 ,
|
||||
parameter STABLE_CNT_MOD = 96 ,
|
||||
parameter ADC_WIDTH = 12 ,
|
||||
parameter CH_NUM = 4 ,
|
||||
parameter PHASE_WIDTH = 16 ,
|
||||
parameter SYNC_HOP_INTVL = 48*1000, // 1 ms of 48M clock, must > 48*200
|
||||
parameter SNAPSHOT_NUM = 2048,
|
||||
parameter PS_PL_WIDTH = 32 ,
|
||||
parameter WEIGHT_WIDTH = 16 ,
|
||||
parameter OUTPUT_WIDTH = ADC_WIDTH,
|
||||
parameter ACCOR_FRAME_HEAD = 32'h7E7E7E7E,
|
||||
parameter WEIGHT_FRAME_HEAD = ACCOR_FRAME_HEAD // Same head is required by [c2c_bridge] module
|
||||
)
|
||||
(
|
||||
// clock & reset
|
||||
input sys_clk , // sync to adc data
|
||||
input sys_clk_4x , // sync to adc data
|
||||
input sys_rst , // sync to [sys_clk]
|
||||
input clk_96m , // sync to c2c data
|
||||
input ant_rst , // sync to [clk_96m]
|
||||
input sys_clk , // sync to adc data
|
||||
input sys_clk_phy , // sync to adc data
|
||||
input sys_rst , // sync to [sys_clk]
|
||||
input clk_96m , // sync to c2c data
|
||||
input ant_rst , // sync to [clk_96m]
|
||||
|
||||
// input un-calibrated data
|
||||
input [ADC_DATA_WIDTH-1:0] rx_ch1_i ,
|
||||
input [ADC_DATA_WIDTH-1:0] rx_ch1_q ,
|
||||
input [ADC_DATA_WIDTH-1:0] rx_ch2_i ,
|
||||
input [ADC_DATA_WIDTH-1:0] rx_ch2_q ,
|
||||
input [ADC_DATA_WIDTH-1:0] rx_ch3_i ,
|
||||
input [ADC_DATA_WIDTH-1:0] rx_ch3_q ,
|
||||
input [ADC_DATA_WIDTH-1:0] rx_ch4_i ,
|
||||
input [ADC_DATA_WIDTH-1:0] rx_ch4_q ,
|
||||
input [ADC_WIDTH-1:0] rx_ch1_i ,
|
||||
input [ADC_WIDTH-1:0] rx_ch1_q ,
|
||||
input [ADC_WIDTH-1:0] rx_ch2_i ,
|
||||
input [ADC_WIDTH-1:0] rx_ch2_q ,
|
||||
input [ADC_WIDTH-1:0] rx_ch3_i ,
|
||||
input [ADC_WIDTH-1:0] rx_ch3_q ,
|
||||
input [ADC_WIDTH-1:0] rx_ch4_i ,
|
||||
input [ADC_WIDTH-1:0] rx_ch4_q ,
|
||||
// input channel phase
|
||||
input [PHASE_WIDTH-1:0] phase_ch1 ,
|
||||
input [PHASE_WIDTH-1:0] phase_ch2 ,
|
||||
input [PHASE_WIDTH-1:0] phase_ch3 ,
|
||||
input [PHASE_WIDTH-1:0] phase_ch4 ,
|
||||
input [PHASE_WIDTH-1:0] phase_ch1 ,
|
||||
input [PHASE_WIDTH-1:0] phase_ch2 ,
|
||||
input [PHASE_WIDTH-1:0] phase_ch3 ,
|
||||
input [PHASE_WIDTH-1:0] phase_ch4 ,
|
||||
|
||||
// ad9361 calibration interface
|
||||
input ad9361_1_cal_start ,
|
||||
output ad9361_1_cal_done ,
|
||||
input ad9361_2_cal_start ,
|
||||
output ad9361_2_cal_done ,
|
||||
output ad9361_cal_result ,
|
||||
output ad9361_cal_valid ,
|
||||
input ad9361_recal ,
|
||||
input ad9361_1_cal_start ,
|
||||
output ad9361_1_cal_done ,
|
||||
input ad9361_2_cal_start ,
|
||||
output ad9361_2_cal_done ,
|
||||
output ad9361_cal_result ,
|
||||
output ad9361_cal_valid ,
|
||||
input ad9361_recal ,
|
||||
|
||||
// nulling algotithm interface
|
||||
input hop_start_flag , // sync to [sys_clk_4x]
|
||||
output accor_stream_valid , // sync to [clk_96m]
|
||||
output accor_stream_data , // sync to [clk_96m]
|
||||
input weight_stream_data , // sync to [clk_96m]
|
||||
output rx_data_valid , // sync to [sys_clk]
|
||||
output [OUTPUT_DATA_WIDTH-1:0] rx_data_i, // sync to [sys_clk]
|
||||
output [OUTPUT_DATA_WIDTH-1:0] rx_data_q // sync to [sys_clk]
|
||||
// nulling algorithm interface
|
||||
input hop_flag_in_phy ,
|
||||
input sync_flag_phy ,
|
||||
input lcmv_en_phy ,
|
||||
output hop_flag_out ,
|
||||
|
||||
output accor_stream_valid , // sync to [clk_96m]
|
||||
output accor_stream_data , // sync to [clk_96m]
|
||||
input weight_stream_data , // sync to [clk_96m]
|
||||
output rx_data_valid , // sync to [sys_clk]
|
||||
output [OUTPUT_WIDTH-1:0] rx_data_i , // sync to [sys_clk]
|
||||
output [OUTPUT_WIDTH-1:0] rx_data_q // sync to [sys_clk]
|
||||
);
|
||||
|
||||
localparam ACORR_WIDTH = 2*ADC_DATA_WIDTH;
|
||||
localparam ACCUM_WIDTH = $clog2(SNAPSHOT_NUM)+ACORR_WIDTH; // = 32
|
||||
// autocorrelation state machine
|
||||
localparam ACORR_STATE_NUM = 3;
|
||||
localparam ACORR_STATE_IDLE = 0;
|
||||
localparam ACORR_STATE_STABLE = 1; // wait until rf is stable
|
||||
localparam ACORR_STATE_CALC = 2; // autocorrelation calculation and formatting
|
||||
localparam CMPLX_DIM = 2;
|
||||
localparam ACORR_WIDTH = 2*ADC_WIDTH;
|
||||
localparam ACCUM_WIDTH = PS_PL_WIDTH;
|
||||
localparam LCMV_WIDTH = ADC_WIDTH + WEIGHT_WIDTH + $clog2(CH_NUM);
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
///////////////////// AD9361 Rx Multi-Channel Calibration //////////////////////
|
||||
@@ -129,23 +130,23 @@ ad9361_phase_cal_coarse u_ad9361_phase_cal
|
||||
.ad9361_cal_valid (ad9361_cal_valid ), // output ad9361_cal_valid
|
||||
.ad9361_recal (ad9361_recal ), // input ad9361_recal
|
||||
// input data interface
|
||||
.rx_ch1_i (rx_ch1_i ), // input [ADC_DATA_WIDTH-1:0] rx_ch1_i
|
||||
.rx_ch1_q (rx_ch1_q ), // input [ADC_DATA_WIDTH-1:0] rx_ch1_q
|
||||
.rx_ch2_i (rx_ch2_i ), // input [ADC_DATA_WIDTH-1:0] rx_ch2_i
|
||||
.rx_ch2_q (rx_ch2_q ), // input [ADC_DATA_WIDTH-1:0] rx_ch2_q
|
||||
.rx_ch3_i (rx_ch3_i ), // input [ADC_DATA_WIDTH-1:0] rx_ch3_i
|
||||
.rx_ch3_q (rx_ch3_q ), // input [ADC_DATA_WIDTH-1:0] rx_ch3_q
|
||||
.rx_ch4_i (rx_ch4_i ), // input [ADC_DATA_WIDTH-1:0] rx_ch4_i
|
||||
.rx_ch4_q (rx_ch4_q ), // input [ADC_DATA_WIDTH-1:0] rx_ch4_q
|
||||
.rx_ch1_i (rx_ch1_i ), // input [ADC_WIDTH-1:0] rx_ch1_i
|
||||
.rx_ch1_q (rx_ch1_q ), // input [ADC_WIDTH-1:0] rx_ch1_q
|
||||
.rx_ch2_i (rx_ch2_i ), // input [ADC_WIDTH-1:0] rx_ch2_i
|
||||
.rx_ch2_q (rx_ch2_q ), // input [ADC_WIDTH-1:0] rx_ch2_q
|
||||
.rx_ch3_i (rx_ch3_i ), // input [ADC_WIDTH-1:0] rx_ch3_i
|
||||
.rx_ch3_q (rx_ch3_q ), // input [ADC_WIDTH-1:0] rx_ch3_q
|
||||
.rx_ch4_i (rx_ch4_i ), // input [ADC_WIDTH-1:0] rx_ch4_i
|
||||
.rx_ch4_q (rx_ch4_q ), // input [ADC_WIDTH-1:0] rx_ch4_q
|
||||
// output data interface
|
||||
.rx_cal_ch1_i (rx_cal_ch1_i ), // output [ADC_DATA_WIDTH-1:0] rx_cal_ch1_i
|
||||
.rx_cal_ch1_q (rx_cal_ch1_q ), // output [ADC_DATA_WIDTH-1:0] rx_cal_ch1_q
|
||||
.rx_cal_ch2_i (rx_cal_ch2_i ), // output [ADC_DATA_WIDTH-1:0] rx_cal_ch2_i
|
||||
.rx_cal_ch2_q (rx_cal_ch2_q ), // output [ADC_DATA_WIDTH-1:0] rx_cal_ch2_q
|
||||
.rx_cal_ch3_i (rx_cal_ch3_i ), // output [ADC_DATA_WIDTH-1:0] rx_cal_ch3_i
|
||||
.rx_cal_ch3_q (rx_cal_ch3_q ), // output [ADC_DATA_WIDTH-1:0] rx_cal_ch3_q
|
||||
.rx_cal_ch4_i (rx_cal_ch4_i ), // output [ADC_DATA_WIDTH-1:0] rx_cal_ch4_i
|
||||
.rx_cal_ch4_q (rx_cal_ch4_q ) // output [ADC_DATA_WIDTH-1:0] rx_cal_ch4_q
|
||||
.rx_cal_ch1_i (rx_cal_ch1_i ), // output [ADC_WIDTH-1:0] rx_cal_ch1_i
|
||||
.rx_cal_ch1_q (rx_cal_ch1_q ), // output [ADC_WIDTH-1:0] rx_cal_ch1_q
|
||||
.rx_cal_ch2_i (rx_cal_ch2_i ), // output [ADC_WIDTH-1:0] rx_cal_ch2_i
|
||||
.rx_cal_ch2_q (rx_cal_ch2_q ), // output [ADC_WIDTH-1:0] rx_cal_ch2_q
|
||||
.rx_cal_ch3_i (rx_cal_ch3_i ), // output [ADC_WIDTH-1:0] rx_cal_ch3_i
|
||||
.rx_cal_ch3_q (rx_cal_ch3_q ), // output [ADC_WIDTH-1:0] rx_cal_ch3_q
|
||||
.rx_cal_ch4_i (rx_cal_ch4_i ), // output [ADC_WIDTH-1:0] rx_cal_ch4_i
|
||||
.rx_cal_ch4_q (rx_cal_ch4_q ) // output [ADC_WIDTH-1:0] rx_cal_ch4_q
|
||||
);
|
||||
|
||||
|
||||
@@ -154,9 +155,9 @@ ad9361_phase_cal_coarse u_ad9361_phase_cal
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
// input data
|
||||
wire phase_comp_din_valid;
|
||||
wire [CHANNEL_NUM*PHASE_WIDTH-1 : 0] phase_comp_phase;
|
||||
wire [CHANNEL_NUM*ADC_DATA_WIDTH-1 : 0] phase_comp_din_real;
|
||||
wire [CHANNEL_NUM*ADC_DATA_WIDTH-1 : 0] phase_comp_din_imag;
|
||||
wire [CH_NUM*PHASE_WIDTH-1 : 0] phase_comp_phase;
|
||||
wire [CH_NUM*ADC_WIDTH-1 : 0] phase_comp_din_real;
|
||||
wire [CH_NUM*ADC_WIDTH-1 : 0] phase_comp_din_imag;
|
||||
|
||||
assign phase_comp_din_valid = ad9361_cal_valid;
|
||||
assign phase_comp_phase = {phase_ch4, phase_ch3, phase_ch2, phase_ch1};
|
||||
@@ -174,17 +175,17 @@ assign phase_comp_din_imag = {rx_cal_ch4_q, rx_cal_ch3_q, rx_cal_ch2_q, rx_cal_c
|
||||
(*dont_touch = "true"*) wire [11:0] rx_comp_ch4_q;
|
||||
|
||||
wire phase_comp_dout_valid;
|
||||
wire [CHANNEL_NUM*ADC_DATA_WIDTH-1:0] phase_comp_dout_real;
|
||||
wire [CHANNEL_NUM*ADC_DATA_WIDTH-1:0] phase_comp_dout_imag;
|
||||
wire [CH_NUM*ADC_WIDTH-1:0] phase_comp_dout_real;
|
||||
wire [CH_NUM*ADC_WIDTH-1:0] phase_comp_dout_imag;
|
||||
|
||||
// assign phase_comp_dout_valid = ad9361_cal_valid;
|
||||
assign {rx_comp_ch4_i, rx_comp_ch3_i, rx_comp_ch2_i, rx_comp_ch1_i} = phase_comp_dout_real;
|
||||
assign {rx_comp_ch4_q, rx_comp_ch3_q, rx_comp_ch2_q, rx_comp_ch1_q} = phase_comp_dout_imag;
|
||||
|
||||
phase_comp #(
|
||||
.DATA_WIDTH (ADC_DATA_WIDTH ),
|
||||
.DATA_WIDTH (ADC_WIDTH ),
|
||||
.CORDIC_WIDTH (PHASE_WIDTH ),
|
||||
.CHANNEL_NUM (CHANNEL_NUM )
|
||||
.CH_NUM (CH_NUM )
|
||||
) u_phase_comp
|
||||
(
|
||||
// clock & reset
|
||||
@@ -251,131 +252,179 @@ phase_comp #(
|
||||
// );
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////// Autocorrelation State Machine /////////////////////////
|
||||
/////////////////////////////// Nulling Control ////////////////////////////////
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
reg [$clog2(ACORR_STATE_NUM)-1 : 0] acorr_state = ACORR_STATE_IDLE;
|
||||
reg [$clog2(STABLE_CNT_MOD)-1 : 0] stable_cnt = 'b0;
|
||||
reg [$clog2(SNAPSHOT_NUM)-1 : 0] snapshot_cnt = 'b0;
|
||||
reg snapshot_valid = 'b0;
|
||||
// adc input
|
||||
wire adc_din_valid ;
|
||||
wire [CH_NUM*ADC_WIDTH-1 : 0] adc_din_real;
|
||||
wire [CH_NUM*ADC_WIDTH-1 : 0] adc_din_imag;
|
||||
|
||||
reg fifo_cdc_rst = 1'b0; // reset [fifo_accor_cdc] & [fifo_weight_cdc] at each hop
|
||||
assign adc_din_valid = phase_comp_dout_valid;
|
||||
assign adc_din_real = phase_comp_dout_real ;
|
||||
assign adc_din_imag = phase_comp_dout_imag ;
|
||||
|
||||
wire hop_start_flag_cdc;
|
||||
// autocorrelation
|
||||
wire acorr_din_valid ;
|
||||
wire [CH_NUM*ADC_WIDTH-1 : 0] acorr_din_real;
|
||||
wire [CH_NUM*ADC_WIDTH-1 : 0] acorr_din_imag;
|
||||
|
||||
xpm_cdc_pulse #(
|
||||
.DEST_SYNC_FF (4), // DECIMAL; range: 2-10
|
||||
.INIT_SYNC_FF (1), // DECIMAL; 0=disable simulation init values, 1=enable simulation init values
|
||||
.REG_OUTPUT (1), // DECIMAL; 0=disable registered output, 1=enable registered output
|
||||
.RST_USED (0), // DECIMAL; 0=no reset, 1=implement reset
|
||||
.SIM_ASSERT_CHK (1) // DECIMAL; 0=disable simulation messages, 1=enable simulation messages
|
||||
) u_hop_start_flag_cdc
|
||||
(
|
||||
.dest_pulse (hop_start_flag_cdc ), // 1-bit output: Outputs a pulse the size of one dest_clk period when a pulse
|
||||
// transfer is correctly initiated on src_pulse input. This output is
|
||||
// combinatorial unless REG_OUTPUT is set to 1.
|
||||
.dest_clk (sys_clk ), // 1-bit input: Destination clock.
|
||||
.dest_rst (1'b1 ), // 1-bit input: optional; required when RST_USED = 1
|
||||
.src_clk (sys_clk_4x ), // 1-bit input: Source clock.
|
||||
.src_pulse (hop_start_flag ), // 1-bit input: Rising edge of this signal initiates a pulse transfer to the
|
||||
// destination clock domain. The minimum gap between each pulse transfer must be
|
||||
// at the minimum 2*(larger(src_clk period, dest_clk period)). This is measured
|
||||
// between the falling edge of a src_pulse to the rising edge of the next
|
||||
// src_pulse. This minimum gap will guarantee that each rising edge of src_pulse
|
||||
// will generate a pulse the size of one dest_clk period in the destination
|
||||
// clock domain. When RST_USED = 1, pulse transfers will not be guaranteed while
|
||||
// src_rst and/or dest_rst are asserted.
|
||||
.src_rst (1'b1 ) // 1-bit input: optional; required when RST_USED = 1
|
||||
wire acorr_dout_valid ;
|
||||
wire [CH_NUM*CH_NUM*ACORR_WIDTH-1:0] acorr_dout_real;
|
||||
wire [CH_NUM*CH_NUM*ACORR_WIDTH-1:0] acorr_dout_imag;
|
||||
|
||||
// accumulation
|
||||
wire accum_rst ;
|
||||
|
||||
wire accum_din_valid ;
|
||||
wire [CH_NUM*CH_NUM*ACORR_WIDTH-1:0] accum_din_real;
|
||||
wire [CH_NUM*CH_NUM*ACORR_WIDTH-1:0] accum_din_imag;
|
||||
|
||||
wire accum_dout_valid ;
|
||||
wire [CH_NUM*CH_NUM*ACCUM_WIDTH-1:0] accum_dout_real;
|
||||
wire [CH_NUM*CH_NUM*ACCUM_WIDTH-1:0] accum_dout_imag;
|
||||
|
||||
// Parallel to Serial
|
||||
wire stream_fifo_rst ;
|
||||
|
||||
wire stream_din_valid ;
|
||||
wire [CH_NUM*CH_NUM*ACCUM_WIDTH-1 : 0] stream_din_real;
|
||||
wire [CH_NUM*CH_NUM*ACCUM_WIDTH-1 : 0] stream_din_imag;
|
||||
|
||||
// Serial to Parallel
|
||||
wire weight_fifo_rst ;
|
||||
|
||||
wire weight_dout_valid ;
|
||||
wire [CH_NUM*WEIGHT_WIDTH-1 : 0] weight_dout_real;
|
||||
wire [CH_NUM*WEIGHT_WIDTH-1 : 0] weight_dout_imag;
|
||||
|
||||
// spatial filter
|
||||
wire filter_weight_valid ;
|
||||
wire [CH_NUM*WEIGHT_WIDTH-1 : 0] filter_weight_real;
|
||||
wire [CH_NUM*WEIGHT_WIDTH-1 : 0] filter_weight_imag;
|
||||
|
||||
wire filter_din_valid ;
|
||||
wire [CH_NUM*ADC_WIDTH-1 : 0] filter_din_real;
|
||||
wire [CH_NUM*ADC_WIDTH-1 : 0] filter_din_imag;
|
||||
|
||||
wire filter_dout_valid ;
|
||||
wire [LCMV_WIDTH-1 : 0] filter_dout_real;
|
||||
wire [LCMV_WIDTH-1 : 0] filter_dout_imag;
|
||||
|
||||
// output data port
|
||||
wire null_dout_valid ;
|
||||
wire [OUTPUT_WIDTH-1 : 0] null_dout_real;
|
||||
wire [OUTPUT_WIDTH-1 : 0] null_dout_imag;
|
||||
|
||||
assign rx_data_valid = null_dout_valid;
|
||||
assign rx_data_i = null_dout_real;
|
||||
assign rx_data_q = null_dout_imag;
|
||||
|
||||
null_ctrl #(
|
||||
.ADC_WIDTH (ADC_WIDTH ),
|
||||
.CH_NUM (CH_NUM ),
|
||||
.STABLE_CNT_MOD (STABLE_CNT_MOD ),
|
||||
.SYNC_HOP_INTVL (SYNC_HOP_INTVL ),
|
||||
.SNAPSHOT_NUM (SNAPSHOT_NUM ),
|
||||
.ACCUM_WIDTH (ACCUM_WIDTH ),
|
||||
.ACORR_WIDTH (ACORR_WIDTH ),
|
||||
.WEIGHT_WIDTH (WEIGHT_WIDTH ),
|
||||
.OUTPUT_WIDTH (OUTPUT_WIDTH )
|
||||
) u_null_ctrl (
|
||||
// *************************************************************************
|
||||
// ***************************** clock & reset *****************************
|
||||
// *************************************************************************
|
||||
.clk (sys_clk ), // input clk
|
||||
.clk_phy (sys_clk_phy ), // input clk_phy
|
||||
.rst (sys_rst ), // input rst
|
||||
|
||||
//
|
||||
.hop_flag_in_phy (hop_flag_in_phy ), // input hop_flag_in_phy
|
||||
.sync_flag_phy (sync_flag_phy ), // input sync_flag_phy
|
||||
.lcmv_en_phy (lcmv_en_phy ), // input lcmv_en_phy
|
||||
.hop_flag_out (hop_flag_out ), // output hop_flag_out
|
||||
// *************************************************************************
|
||||
// **************************** ADC Input Data *****************************
|
||||
// *************************************************************************
|
||||
.adc_din_valid (adc_din_valid ), // input adc_din_valid
|
||||
.adc_din_real (adc_din_real ), // input [CH_NUM*ADC_WIDTH-1 : 0] adc_din_real
|
||||
.adc_din_imag (adc_din_imag ), // input [CH_NUM*ADC_WIDTH-1 : 0] adc_din_imag
|
||||
|
||||
// *************************************************************************
|
||||
// **************************** Autocorrelation ****************************
|
||||
// *************************************************************************
|
||||
.acorr_din_valid (acorr_din_valid ), // output acorr_din_valid
|
||||
.acorr_din_real (acorr_din_real ), // output [CH_NUM*ADC_WIDTH-1 : 0] acorr_din_real
|
||||
.acorr_din_imag (acorr_din_imag ), // output [CH_NUM*ADC_WIDTH-1 : 0] acorr_din_imag
|
||||
|
||||
.acorr_dout_valid (acorr_dout_valid ), // input acorr_dout_valid
|
||||
.acorr_dout_real (acorr_dout_real ), // input [CH_NUM*CH_NUM*ACORR_WIDTH-1:0] acorr_dout_real
|
||||
.acorr_dout_imag (acorr_dout_imag ), // input [CH_NUM*CH_NUM*ACORR_WIDTH-1:0] acorr_dout_imag
|
||||
|
||||
// *************************************************************************
|
||||
// **************************** Accumulation *******************************
|
||||
// *************************************************************************
|
||||
.accum_rst (accum_rst ), // output accum_rst
|
||||
|
||||
.accum_din_valid (accum_din_valid ), // output accum_din_valid
|
||||
.accum_din_real (accum_din_real ), // output [CH_NUM*CH_NUM*ACORR_WIDTH-1:0] accum_din_real
|
||||
.accum_din_imag (accum_din_imag ), // output [CH_NUM*CH_NUM*ACORR_WIDTH-1:0] accum_din_imag
|
||||
|
||||
.accum_dout_valid (accum_dout_valid ), // input accum_dout_valid
|
||||
.accum_dout_real (accum_dout_real ), // input [CH_NUM*CH_NUM*ACCUM_WIDTH-1:0] accum_dout_real
|
||||
.accum_dout_imag (accum_dout_imag ), // input [CH_NUM*CH_NUM*ACCUM_WIDTH-1:0] accum_dout_imag
|
||||
|
||||
// *************************************************************************
|
||||
// ************************* Parallel to Serial ****************************
|
||||
// *************************************************************************
|
||||
.stream_fifo_rst (stream_fifo_rst ), // output stream_fifo_rst
|
||||
|
||||
.stream_din_valid (stream_din_valid ), // output stream_din_valid
|
||||
.stream_din_real (stream_din_real ), // output [CH_NUM*CH_NUM*ACCUM_WIDTH-1 : 0] stream_din_real
|
||||
.stream_din_imag (stream_din_imag ), // output [CH_NUM*CH_NUM*ACCUM_WIDTH-1 : 0] stream_din_imag
|
||||
|
||||
// *************************************************************************
|
||||
// ************************* Serial to Parallel ****************************
|
||||
// *************************************************************************
|
||||
.weight_fifo_rst (weight_fifo_rst ), // output weight_fifo_rst
|
||||
|
||||
.weight_dout_valid (weight_dout_valid ), // input weight_dout_valid
|
||||
.weight_dout_real (weight_dout_real ), // input [CH_NUM*WEIGHT_WIDTH-1 : 0] weight_dout_real
|
||||
.weight_dout_imag (weight_dout_imag ), // input [CH_NUM*WEIGHT_WIDTH-1 : 0] weight_dout_imag
|
||||
|
||||
// *************************************************************************
|
||||
// **************************** Spatial Filter *****************************
|
||||
// *************************************************************************
|
||||
// input weight vector
|
||||
.filter_weight_valid (filter_weight_valid ), // output filter_weight_valid
|
||||
.filter_weight_real (filter_weight_real ), // output [CH_NUM*WEIGHT_WIDTH-1 : 0] filter_weight_real
|
||||
.filter_weight_imag (filter_weight_imag ), // output [CH_NUM*WEIGHT_WIDTH-1 : 0] filter_weight_imag
|
||||
|
||||
// input adc data
|
||||
.filter_din_valid (filter_din_valid ), // output filter_din_valid
|
||||
.filter_din_real (filter_din_real ), // output [CH_NUM*ADC_WIDTH-1 : 0] filter_din_real
|
||||
.filter_din_imag (filter_din_imag ), // output [CH_NUM*ADC_WIDTH-1 : 0] filter_din_imag
|
||||
|
||||
// output data
|
||||
.filter_dout_valid (filter_dout_valid ), // input filter_dout_valid
|
||||
.filter_dout_real (filter_dout_real ), // input [LCMV_WIDTH-1 : 0] filter_dout_real
|
||||
.filter_dout_imag (filter_dout_imag ), // input [LCMV_WIDTH-1 : 0] filter_dout_imag
|
||||
|
||||
// *************************************************************************
|
||||
// *************************** Output Data Port ****************************
|
||||
// *************************************************************************
|
||||
.null_dout_valid (null_dout_valid ), // output null_dout_valid
|
||||
.null_dout_real (null_dout_real ), // output [OUTPUT_WIDTH-1 : 0] null_dout_real
|
||||
.null_dout_imag (null_dout_imag ) // output [OUTPUT_WIDTH-1 : 0] null_dout_imag
|
||||
);
|
||||
|
||||
always @(posedge sys_clk) begin
|
||||
if (sys_rst) begin
|
||||
acorr_state <= ACORR_STATE_IDLE;
|
||||
end
|
||||
else begin
|
||||
case (acorr_state)
|
||||
ACORR_STATE_IDLE : acorr_state <= (hop_start_flag_cdc & ad9361_cal_valid) ? ACORR_STATE_STABLE : ACORR_STATE_IDLE;
|
||||
ACORR_STATE_STABLE: acorr_state <= (stable_cnt == STABLE_CNT_MOD-1) ? ACORR_STATE_CALC : ACORR_STATE_STABLE;
|
||||
ACORR_STATE_CALC : acorr_state <= (snapshot_cnt == SNAPSHOT_NUM-1) ? ACORR_STATE_IDLE : ACORR_STATE_CALC;
|
||||
default: acorr_state <= ACORR_STATE_IDLE;
|
||||
endcase
|
||||
end
|
||||
end
|
||||
|
||||
always @(posedge sys_clk) begin
|
||||
if (sys_rst) begin
|
||||
stable_cnt <= 'b0;
|
||||
end
|
||||
else begin
|
||||
case (acorr_state)
|
||||
ACORR_STATE_IDLE : stable_cnt <= 'b0;
|
||||
ACORR_STATE_STABLE: stable_cnt <= (stable_cnt == STABLE_CNT_MOD-1) ? 'b0 : stable_cnt + 1'b1;
|
||||
ACORR_STATE_CALC : stable_cnt <= 'b0;
|
||||
default: stable_cnt <= 'b0;
|
||||
endcase
|
||||
end
|
||||
end
|
||||
|
||||
always @(posedge sys_clk) begin
|
||||
if (sys_rst) begin
|
||||
snapshot_cnt <= 'b0;
|
||||
end
|
||||
else begin
|
||||
case (acorr_state)
|
||||
ACORR_STATE_IDLE : snapshot_cnt <= 'b0;
|
||||
ACORR_STATE_STABLE: snapshot_cnt <= 'b0;
|
||||
ACORR_STATE_CALC : snapshot_cnt <= (snapshot_cnt == SNAPSHOT_NUM-1) ? 'b0 : snapshot_cnt + 1'b1;
|
||||
default: snapshot_cnt <= 'b0;
|
||||
endcase
|
||||
end
|
||||
end
|
||||
|
||||
always @(posedge sys_clk) begin
|
||||
if (sys_rst) begin
|
||||
snapshot_valid <= 'b0;
|
||||
end
|
||||
else begin
|
||||
case (acorr_state)
|
||||
ACORR_STATE_IDLE : snapshot_valid <= 'b0;
|
||||
ACORR_STATE_STABLE: snapshot_valid <= 'b0;
|
||||
ACORR_STATE_CALC : snapshot_valid <= 1'b1;
|
||||
default: snapshot_valid <= 'b0;
|
||||
endcase
|
||||
end
|
||||
end
|
||||
|
||||
always @(posedge sys_clk) begin
|
||||
if (sys_rst) begin
|
||||
fifo_cdc_rst <= 'b0;
|
||||
end
|
||||
else if (acorr_state == ACORR_STATE_STABLE) begin
|
||||
fifo_cdc_rst <= 1'b1;
|
||||
end
|
||||
else begin
|
||||
fifo_cdc_rst <= 'b0;
|
||||
end
|
||||
end
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
////////////////////// Autocorrelation of Snapshot Vector //////////////////////
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
// input data
|
||||
wire acorr_din_valid;
|
||||
wire [CHANNEL_NUM*ADC_DATA_WIDTH-1 : 0] acorr_din_real;
|
||||
wire [CHANNEL_NUM*ADC_DATA_WIDTH-1 : 0] acorr_din_imag;
|
||||
|
||||
assign acorr_din_valid = snapshot_valid;
|
||||
assign acorr_din_real = phase_comp_dout_real;
|
||||
assign acorr_din_imag = phase_comp_dout_imag;
|
||||
|
||||
// output data
|
||||
wire acorr_dout_valid;
|
||||
wire [CHANNEL_NUM*CHANNEL_NUM*ACORR_WIDTH-1:0] acorr_dout_real;
|
||||
wire [CHANNEL_NUM*CHANNEL_NUM*ACORR_WIDTH-1:0] acorr_dout_imag;
|
||||
|
||||
acorr_cmplx_col_vec #(
|
||||
.DATA_I_WIDTH (ADC_DATA_WIDTH ),
|
||||
.DATA_O_WIDTH (ACORR_WIDTH ),
|
||||
.COL_NUM (CHANNEL_NUM )
|
||||
.DATA_I_WIDTH (ADC_WIDTH ),
|
||||
.DATA_O_WIDTH (ACORR_WIDTH ),
|
||||
.COL_NUM (CH_NUM )
|
||||
) u_acorr (
|
||||
// clock & reset
|
||||
.clk (sys_clk ),
|
||||
@@ -396,38 +445,18 @@ acorr_cmplx_col_vec #(
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
////////////// Accumulation of Snapshot Autocorrelation Matrices ///////////////
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
// accumulation reset
|
||||
wire acc_rst; // [acc_rst] should assert before accumulation starts
|
||||
|
||||
assign acc_rst = hop_start_flag_cdc;
|
||||
|
||||
// input data
|
||||
wire accum_din_valid;
|
||||
wire [CHANNEL_NUM*CHANNEL_NUM*ACORR_WIDTH-1:0] accum_din_real;
|
||||
wire [CHANNEL_NUM*CHANNEL_NUM*ACORR_WIDTH-1:0] accum_din_imag;
|
||||
|
||||
assign accum_din_valid = acorr_dout_valid;
|
||||
assign accum_din_real = acorr_dout_real;
|
||||
assign accum_din_imag = acorr_dout_imag;
|
||||
|
||||
// output data
|
||||
wire accum_dout_valid;
|
||||
wire [CHANNEL_NUM*CHANNEL_NUM*PS_PL_WIDTH-1:0] accum_dout_real;
|
||||
wire [CHANNEL_NUM*CHANNEL_NUM*PS_PL_WIDTH-1:0] accum_dout_imag;
|
||||
|
||||
accum_cmplx_mat #(
|
||||
.ROW_NUM (CHANNEL_NUM ),
|
||||
.COL_NUM (CHANNEL_NUM ),
|
||||
.ROW_NUM (CH_NUM ),
|
||||
.COL_NUM (CH_NUM ),
|
||||
.ACC_NUM (SNAPSHOT_NUM ),
|
||||
.DATA_I_WIDTH (ACORR_WIDTH ),
|
||||
.DATA_ACC_WIDTH (ACCUM_WIDTH ),
|
||||
.DATA_O_WIDTH (PS_PL_WIDTH ),
|
||||
.ACC_NUM (SNAPSHOT_NUM )
|
||||
.DATA_O_WIDTH (PS_PL_WIDTH )
|
||||
) u_accum_cmplx_mat
|
||||
(
|
||||
// clock & reset
|
||||
.clk (sys_clk ),
|
||||
.rst (sys_rst ),
|
||||
.acc_rst (acc_rst ), // [acc_rst] should assert before accumulation starts
|
||||
.acc_rst (accum_rst ), // [accum_rst] should assert before accumulation starts
|
||||
|
||||
// input data
|
||||
.din_valid (accum_din_valid ),
|
||||
@@ -444,15 +473,6 @@ accum_cmplx_mat #(
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/////////////// 32-bit Matrix Element to 1-bit Stream Conversion ///////////////
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
// input data
|
||||
wire stream_din_valid;
|
||||
wire [CHANNEL_NUM*CHANNEL_NUM*PS_PL_WIDTH-1 : 0] stream_din_real;
|
||||
wire [CHANNEL_NUM*CHANNEL_NUM*PS_PL_WIDTH-1 : 0] stream_din_imag;
|
||||
|
||||
assign stream_din_valid = accum_dout_valid;
|
||||
assign stream_din_real = accum_dout_real;
|
||||
assign stream_din_imag = accum_dout_imag;
|
||||
|
||||
// output data
|
||||
wire stream_dout_valid;
|
||||
wire stream_dout_data;
|
||||
@@ -461,8 +481,8 @@ assign accor_stream_valid = stream_dout_valid; // to module port
|
||||
assign accor_stream_data = stream_dout_data; // to module port
|
||||
|
||||
accor_mat_formatting #(
|
||||
.ROW_NUM (CHANNEL_NUM ),
|
||||
.COL_NUM (CHANNEL_NUM ),
|
||||
.ROW_NUM (CH_NUM ),
|
||||
.COL_NUM (CH_NUM ),
|
||||
.DATA_I_WIDTH (PS_PL_WIDTH ),
|
||||
.FRAME_HEAD (ACCOR_FRAME_HEAD )
|
||||
) u_accor_mat_stream
|
||||
@@ -477,7 +497,7 @@ accor_mat_formatting #(
|
||||
.din_valid (stream_din_valid ),
|
||||
.din_real (stream_din_real ),
|
||||
.din_imag (stream_din_imag ),
|
||||
.fifo_cdc_rst (fifo_cdc_rst ),
|
||||
.fifo_cdc_rst (stream_fifo_rst ),
|
||||
|
||||
// output data, sync to [clk_96m]
|
||||
.dout_valid (stream_dout_valid ),
|
||||
@@ -492,18 +512,11 @@ accor_mat_formatting #(
|
||||
wire weight_din_data;
|
||||
|
||||
assign weight_din_data = weight_stream_data;
|
||||
assign stream_din_real = accum_dout_real;
|
||||
assign stream_din_imag = accum_dout_imag;
|
||||
|
||||
// output data
|
||||
wire weight_dout_valid;
|
||||
wire [CHANNEL_NUM*WEIGHT_TRUNC_WIDTH-1 : 0] weight_dout_real;
|
||||
wire [CHANNEL_NUM*WEIGHT_TRUNC_WIDTH-1 : 0] weight_dout_imag;
|
||||
|
||||
weight_vec_formatting #(
|
||||
.COL_NUM (CHANNEL_NUM ),
|
||||
.COL_NUM (CH_NUM ),
|
||||
.WEIGHT_WIDTH (PS_PL_WIDTH ),
|
||||
.DATA_O_WIDTH (WEIGHT_TRUNC_WIDTH ),
|
||||
.DATA_O_WIDTH (WEIGHT_WIDTH ),
|
||||
.FRAME_HEAD (WEIGHT_FRAME_HEAD )
|
||||
) u_weight_vec_formatting
|
||||
(
|
||||
@@ -517,7 +530,7 @@ weight_vec_formatting #(
|
||||
.din_data (weight_din_data ),
|
||||
|
||||
// sync to [sys_clk]
|
||||
.fifo_cdc_rst (fifo_cdc_rst ),
|
||||
.fifo_cdc_rst (weight_fifo_rst ),
|
||||
|
||||
// output data, sync to [sys_clk]
|
||||
.dout_valid (weight_dout_valid ),
|
||||
@@ -529,38 +542,11 @@ weight_vec_formatting #(
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////////////// Spatial Filter ////////////////////////////////
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
// input weight vector
|
||||
wire filter_weight_valid;
|
||||
wire [CHANNEL_NUM*WEIGHT_TRUNC_WIDTH-1 : 0] filter_weight_real;
|
||||
wire [CHANNEL_NUM*WEIGHT_TRUNC_WIDTH-1 : 0] filter_weight_imag;
|
||||
|
||||
assign filter_weight_valid = weight_dout_valid;
|
||||
assign filter_weight_real = weight_dout_real;
|
||||
assign filter_weight_imag = weight_dout_imag;
|
||||
|
||||
// input adc data
|
||||
wire filter_adc_valid;
|
||||
wire [CHANNEL_NUM*ADC_DATA_WIDTH-1 : 0] filter_adc_real;
|
||||
wire [CHANNEL_NUM*ADC_DATA_WIDTH-1 : 0] filter_adc_imag;
|
||||
|
||||
assign filter_adc_valid = phase_comp_dout_valid;
|
||||
assign filter_adc_real = phase_comp_dout_real;
|
||||
assign filter_adc_imag = phase_comp_dout_imag;
|
||||
|
||||
// output data
|
||||
wire filter_dout_valid;
|
||||
wire [OUTPUT_DATA_WIDTH-1 : 0] filter_dout_real;
|
||||
wire [OUTPUT_DATA_WIDTH-1 : 0] filter_dout_imag;
|
||||
|
||||
assign rx_data_valid = filter_dout_valid;
|
||||
assign rx_data_i = filter_dout_real;
|
||||
assign rx_data_q = filter_dout_imag;
|
||||
|
||||
spatial_filter #(
|
||||
.CHANNEL_NUM (CHANNEL_NUM ),
|
||||
.WEIGHT_WIDTH (WEIGHT_TRUNC_WIDTH ),
|
||||
.ADC_WIDTH (ADC_DATA_WIDTH ),
|
||||
.FILTER_O_WIDTH (OUTPUT_DATA_WIDTH )
|
||||
.CH_NUM (CH_NUM ),
|
||||
.WEIGHT_WIDTH (WEIGHT_WIDTH ),
|
||||
.ADC_WIDTH (ADC_WIDTH ),
|
||||
.FILTER_O_WIDTH (OUTPUT_WIDTH )
|
||||
) u_spatial_filter
|
||||
(
|
||||
// clock & reset
|
||||
@@ -573,10 +559,9 @@ spatial_filter #(
|
||||
.din_weight_imag (filter_weight_imag ),
|
||||
|
||||
// input adc data
|
||||
.hop_start_flag (hop_start_flag_cdc ),
|
||||
.din_adc_valid (filter_adc_valid ),
|
||||
.din_adc_real (filter_adc_real ),
|
||||
.din_adc_imag (filter_adc_imag ),
|
||||
.din_adc_valid (filter_din_valid ),
|
||||
.din_adc_real (filter_din_real ),
|
||||
.din_adc_imag (filter_din_imag ),
|
||||
|
||||
// output data
|
||||
.dout_valid (filter_dout_valid ),
|
||||
|
||||
@@ -27,20 +27,21 @@
|
||||
|
||||
module rx_pre_test
|
||||
#(
|
||||
parameter ADC_DATA_WIDTH = 12,
|
||||
parameter BYPASS_CAL = 0
|
||||
parameter ADC_DATA_WIDTH = 12,
|
||||
parameter BYPASS_CAL = 0 ,
|
||||
parameter PHY_CLK_MULT = 3
|
||||
)
|
||||
(
|
||||
// clock & reset
|
||||
input sys_clk ,
|
||||
input sys_clk_4x ,
|
||||
input sys_rst ,
|
||||
input clk ,
|
||||
input clk_phy ,
|
||||
input rst ,
|
||||
// calc result
|
||||
input ad9361_cal_result ,
|
||||
input ad9361_cal_valid ,
|
||||
input ad9361_cal_result ,
|
||||
input ad9361_cal_valid ,
|
||||
//
|
||||
input hop_trigger ,
|
||||
input hop_trigger_en ,
|
||||
input hop_trigger ,
|
||||
input hop_trigger_en ,
|
||||
// output test data
|
||||
output [ADC_DATA_WIDTH-1:0] rx_ch1_i ,
|
||||
output [ADC_DATA_WIDTH-1:0] rx_ch1_q ,
|
||||
@@ -50,10 +51,10 @@ module rx_pre_test
|
||||
output [ADC_DATA_WIDTH-1:0] rx_ch3_q ,
|
||||
output [ADC_DATA_WIDTH-1:0] rx_ch4_i ,
|
||||
output [ADC_DATA_WIDTH-1:0] rx_ch4_q ,
|
||||
output hop_start_flag
|
||||
output hop_start_flag
|
||||
);
|
||||
|
||||
localparam HOP_CNT_MOD_192M = 192*200;
|
||||
localparam HOP_CNT_MOD_PHY = 48*200*PHY_CLK_MULT;
|
||||
localparam HOP_CNT_MOD_48M = 48*200;
|
||||
|
||||
// data valid cdc
|
||||
@@ -68,26 +69,26 @@ xpm_cdc_single #(
|
||||
(
|
||||
.dest_out (ad9361_cal_valid_cdc ), // 1-bit output: src_in synchronized to the destination clock domain. This output is
|
||||
// registered.
|
||||
.dest_clk (sys_clk_4x ), // 1-bit input: Clock signal for the destination clock domain.
|
||||
.src_clk (sys_clk ), // 1-bit input: optional; required when SRC_INPUT_REG = 1
|
||||
.dest_clk (clk_phy ), // 1-bit input: Clock signal for the destination clock domain.
|
||||
.src_clk (clk ), // 1-bit input: optional; required when SRC_INPUT_REG = 1
|
||||
.src_in (ad9361_cal_valid ) // 1-bit input: Input signal to be synchronized to dest_clk domain.
|
||||
);
|
||||
|
||||
// auto hop flag generation
|
||||
reg [$clog2(HOP_CNT_MOD_192M)-1 : 0] hop_cnt_192m = 'b0;
|
||||
reg [$clog2(HOP_CNT_MOD_PHY)-1 : 0] hop_cnt_phy = 'b0;
|
||||
reg hop_flag_auto = 'b0;
|
||||
|
||||
always @(posedge sys_clk_4x) begin
|
||||
if (sys_rst) begin
|
||||
hop_cnt_192m = 'b0;
|
||||
always @(posedge clk_phy) begin
|
||||
if (rst) begin
|
||||
hop_cnt_phy = 'b0;
|
||||
hop_flag_auto = 'b0;
|
||||
end
|
||||
else if (ad9361_cal_valid_cdc) begin
|
||||
hop_cnt_192m <= (hop_cnt_192m == HOP_CNT_MOD_192M-1) ? 'b0 : hop_cnt_192m + 1'b1;
|
||||
hop_flag_auto <= (hop_cnt_192m == 20) ? 1'b1 : 1'b0;
|
||||
hop_cnt_phy <= (hop_cnt_phy == HOP_CNT_MOD_PHY-1) ? 'b0 : hop_cnt_phy + 1'b1;
|
||||
hop_flag_auto <= (hop_cnt_phy == 20) ? 1'b1 : 1'b0;
|
||||
end
|
||||
else begin
|
||||
hop_cnt_192m <= 'b0;
|
||||
hop_cnt_phy <= 'b0;
|
||||
hop_flag_auto = 'b0;
|
||||
end
|
||||
end
|
||||
@@ -96,12 +97,12 @@ end
|
||||
reg hop_flag_manual = 'b0;
|
||||
reg hop_trigger_d1 = 'b0;
|
||||
|
||||
always @(posedge sys_clk_4x) begin
|
||||
always @(posedge clk_phy) begin
|
||||
hop_trigger_d1 <= hop_trigger;
|
||||
end
|
||||
|
||||
always @(posedge sys_clk_4x) begin
|
||||
if (sys_rst) begin
|
||||
always @(posedge clk_phy) begin
|
||||
if (rst) begin
|
||||
hop_flag_manual <= 'b0;
|
||||
end
|
||||
else if (ad9361_cal_valid_cdc) begin
|
||||
@@ -122,8 +123,8 @@ reg hop_start_flag_buf = 'b0;
|
||||
|
||||
assign hop_start_flag = hop_start_flag_buf;
|
||||
|
||||
always @(posedge sys_clk_4x) begin
|
||||
if (sys_rst) begin
|
||||
always @(posedge clk_phy) begin
|
||||
if (rst) begin
|
||||
hop_start_flag_buf <= 'b0;
|
||||
end
|
||||
else begin
|
||||
@@ -150,9 +151,9 @@ xpm_cdc_pulse #(
|
||||
.dest_pulse (hop_flag_cdc ), // 1-bit output: Outputs a pulse the size of one dest_clk period when a pulse
|
||||
// transfer is correctly initiated on src_pulse input. This output is
|
||||
// combinatorial unless REG_OUTPUT is set to 1.
|
||||
.dest_clk (sys_clk ), // 1-bit input: Destination clock.
|
||||
.dest_rst (sys_rst ), // 1-bit input: optional; required when RST_USED = 1
|
||||
.src_clk (sys_clk_4x ), // 1-bit input: Source clock.
|
||||
.dest_clk (clk ), // 1-bit input: Destination clock.
|
||||
.dest_rst (rst ), // 1-bit input: optional; required when RST_USED = 1
|
||||
.src_clk (clk_phy ), // 1-bit input: Source clock.
|
||||
.src_pulse (hop_start_flag_buf ), // 1-bit input: Rising edge of this signal initiates a pulse transfer to the
|
||||
// destination clock domain. The minimum gap between each pulse transfer must be
|
||||
// at the minimum 2*(larger(src_clk period, dest_clk period)). This is measured
|
||||
@@ -161,14 +162,14 @@ xpm_cdc_pulse #(
|
||||
// will generate a pulse the size of one dest_clk period in the destination
|
||||
// clock domain. When RST_USED = 1, pulse transfers will not be guaranteed while
|
||||
// src_rst and/or dest_rst are asserted.
|
||||
.src_rst (sys_rst ) // 1-bit input: optional; required when RST_USED = 1
|
||||
.src_rst (rst ) // 1-bit input: optional; required when RST_USED = 1
|
||||
);
|
||||
|
||||
// data rom address counter
|
||||
reg [$clog2(HOP_CNT_MOD_48M)-1 : 0] hop_cnt_48m = 'b0;
|
||||
|
||||
always @(posedge sys_clk) begin
|
||||
if (sys_rst) begin
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
hop_cnt_48m <= 2'd2;
|
||||
end
|
||||
else if (ad9361_cal_valid) begin
|
||||
@@ -195,7 +196,7 @@ assign {rom_ch1_i,rom_ch2_i,rom_ch3_i,rom_ch4_i,
|
||||
|
||||
rom_hop_data u_rom_hop_data
|
||||
(
|
||||
.clka (sys_clk ), // input wire clka
|
||||
.clka (clk ), // input wire clka
|
||||
.addra (hop_cnt_48m), // input wire [13 : 0] addra
|
||||
.douta (hop_data ) // output wire [95 : 0] douta
|
||||
);
|
||||
@@ -212,7 +213,7 @@ assign rx_ch3_q = rom_ch3_q_buf;
|
||||
assign rx_ch4_i = rom_ch4_i_buf;
|
||||
assign rx_ch4_q = rom_ch4_q_buf;
|
||||
|
||||
always @(posedge sys_clk) begin
|
||||
always @(posedge clk) begin
|
||||
if (BYPASS_CAL) begin
|
||||
rom_ch1_i_buf <= rom_ch1_i;
|
||||
rom_ch1_q_buf <= rom_ch1_q;
|
||||
|
||||
@@ -14,7 +14,31 @@
|
||||
// Project Name:
|
||||
// Target Devices:
|
||||
// Tool Versions:
|
||||
// Description:
|
||||
// Description: Perform vector multiplication of data vector and weight vector,
|
||||
// to get spatial filtered output.
|
||||
// Parameters:
|
||||
// CH_NUM: Number of signal channels, i.e. the row number of signal vector and
|
||||
// the column number of weight vector.
|
||||
// WEIGHT_WIDTH: Bit width of input weight vector element.
|
||||
// ADC_WIDTH: Bit width of input signal vector element.
|
||||
// FILTER_O_WIDTH: Bit width of spatial filter output signal.
|
||||
// Data format:
|
||||
// din_weight_valid: Indicate [din_weight_real/imag] data are valid.
|
||||
// din_weight_real/imag: Suppose the input weight vector is w = [w1, w2, w3,
|
||||
// w4]^T, then
|
||||
// din_weight_real = {Re{w4}, Re{w3}, Re{w2}, Re{w1}}
|
||||
// din_weight_imag = {Im{w4}, Im{w3}, Im{w2}, Im{w1}}
|
||||
// din_adc_valid: Indicate [din_adc_real/imag] data are valid.
|
||||
// din_adc_real/imag: Suppose the input signal vector is x = [x1, x2, x3, x4],
|
||||
// then
|
||||
// din_adc_real = {Re{x4}, Re{x3}, Re{x2}, Re{x1}}
|
||||
// din_adc_imag = {Im{x4}, Im{x3}, Im{x2}, Im{x1}}
|
||||
// dout_valid: Indicate [dout_real/imag] data are valid.
|
||||
// dout_real/imag: Output spatial filtered signal.
|
||||
//
|
||||
// Latency: 7 clock cycles for CMPY using LUTs, 8 for DSPs, including 5/6 clock
|
||||
// cycles for complex multiplication and floor(log2(CH_NUM))=2 clock cycles
|
||||
// for addition.
|
||||
//
|
||||
// Dependencies:
|
||||
//
|
||||
@@ -22,6 +46,8 @@
|
||||
// Revision 0.01 - File Created
|
||||
// 20230404-1037 - 将权矢量和数据对齐,增加 [last_hop_weight_d1] 补偿 RAM 读数
|
||||
// 的延迟。
|
||||
// 20230723-0947 - 大修模块,将缓存数据缓存移至 [null_ctrl] 模块,本模块只负责
|
||||
// 信号加权和求和。
|
||||
// Additional Comments:
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
@@ -29,7 +55,7 @@
|
||||
|
||||
module spatial_filter
|
||||
#(
|
||||
parameter CHANNEL_NUM = 4,
|
||||
parameter CH_NUM = 4,
|
||||
parameter WEIGHT_WIDTH = 16,
|
||||
parameter ADC_WIDTH = 12,
|
||||
parameter FILTER_O_WIDTH = ADC_WIDTH
|
||||
@@ -41,14 +67,13 @@ module spatial_filter
|
||||
|
||||
// input weight vector
|
||||
input din_weight_valid,
|
||||
input [CHANNEL_NUM*WEIGHT_WIDTH-1 : 0] din_weight_real,
|
||||
input [CHANNEL_NUM*WEIGHT_WIDTH-1 : 0] din_weight_imag,
|
||||
input [CH_NUM*WEIGHT_WIDTH-1 : 0] din_weight_real,
|
||||
input [CH_NUM*WEIGHT_WIDTH-1 : 0] din_weight_imag,
|
||||
|
||||
// input adc data
|
||||
input hop_start_flag,
|
||||
input din_adc_valid,
|
||||
input [CHANNEL_NUM*ADC_WIDTH-1 : 0] din_adc_real,
|
||||
input [CHANNEL_NUM*ADC_WIDTH-1 : 0] din_adc_imag,
|
||||
input [CH_NUM*ADC_WIDTH-1 : 0] din_adc_real,
|
||||
input [CH_NUM*ADC_WIDTH-1 : 0] din_adc_imag,
|
||||
|
||||
// output data
|
||||
output dout_valid,
|
||||
@@ -59,157 +84,82 @@ module spatial_filter
|
||||
localparam RAM_HOP_DEPTH = 9728;
|
||||
localparam CMPLX_DIM = 2;
|
||||
|
||||
localparam FILTER_MULT_FULL_WIDTH = WEIGHT_WIDTH+ADC_WIDTH+1;
|
||||
localparam FILTER_MULT_VALID_WIDTH = WEIGHT_WIDTH+ADC_WIDTH;
|
||||
localparam FILTER_SUM_WIDTH = FILTER_MULT_VALID_WIDTH+$clog2(CHANNEL_NUM);
|
||||
localparam CMPY_P_FULL_WIDTH = WEIGHT_WIDTH+ADC_WIDTH+1;
|
||||
localparam CMPY_P_VALID_WIDTH = WEIGHT_WIDTH+ADC_WIDTH;
|
||||
localparam FILTER_SUM_WIDTH = CMPY_P_VALID_WIDTH+$clog2(CH_NUM);
|
||||
localparam AXIS_WEIGHT_WIDTH = 8*((WEIGHT_WIDTH-1)/8+1); // axis data width of input weight vector real/image data
|
||||
localparam AXIS_ADC_I_WIDTH = 8*((ADC_WIDTH-1)/8+1) ; // axis data width of input adc real/image data
|
||||
localparam AXIS_FILTER_WIDTH = 8*((FILTER_MULT_FULL_WIDTH-1)/8+1) ; // axis data width of cmpy output real/image data
|
||||
localparam AXIS_ADC_WIDTH = 8*((ADC_WIDTH-1)/8+1); // axis data width of input adc real/image data
|
||||
localparam AXIS_FILTER_WIDTH = 8*((CMPY_P_FULL_WIDTH-1)/8+1) ; // axis data width of cmpy output real/image data
|
||||
|
||||
genvar i;
|
||||
|
||||
|
||||
// store current hop & restore last hop weight
|
||||
reg [CMPLX_DIM*CHANNEL_NUM*WEIGHT_WIDTH-1 : 0] current_hop_weight = 'b0;
|
||||
reg [CMPLX_DIM*CHANNEL_NUM*WEIGHT_WIDTH-1 : 0] last_hop_weight = 'b0;
|
||||
reg [CMPLX_DIM*CHANNEL_NUM*WEIGHT_WIDTH-1 : 0] last_hop_weight_d1 = 'b0; // wait for ram data
|
||||
|
||||
wire [CHANNEL_NUM*WEIGHT_WIDTH-1 : 0] last_weight_real;
|
||||
wire [CHANNEL_NUM*WEIGHT_WIDTH-1 : 0] last_weight_imag;
|
||||
|
||||
assign {last_weight_imag,last_weight_real} = last_hop_weight_d1;
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
current_hop_weight <= 'b0;
|
||||
end
|
||||
else begin
|
||||
current_hop_weight <= (din_weight_valid) ? {din_weight_imag,din_weight_real} : current_hop_weight;
|
||||
end
|
||||
end
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
last_hop_weight <= 'b0;
|
||||
end
|
||||
else begin
|
||||
last_hop_weight <= (hop_start_flag) ? current_hop_weight : last_hop_weight;
|
||||
end
|
||||
end
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
last_hop_weight_d1 <= 'b0;
|
||||
end
|
||||
else begin
|
||||
last_hop_weight_d1 <= last_hop_weight;
|
||||
end
|
||||
end
|
||||
|
||||
// store current hop & restore last hop data
|
||||
wire [CMPLX_DIM*CHANNEL_NUM*ADC_WIDTH-1 : 0] current_hop_data;
|
||||
reg last_hop_valid = 'b0;
|
||||
wire [CMPLX_DIM*CHANNEL_NUM*ADC_WIDTH-1 : 0] last_hop_data;
|
||||
|
||||
wire [CHANNEL_NUM*ADC_WIDTH-1 : 0] last_data_real;
|
||||
wire [CHANNEL_NUM*ADC_WIDTH-1 : 0] last_data_imag;
|
||||
|
||||
reg [$clog2(RAM_HOP_DEPTH)-1 : 0] hop_data_cnt = 'b0;
|
||||
|
||||
assign current_hop_data = {din_adc_imag,din_adc_real};
|
||||
assign {last_data_imag,last_data_real} = last_hop_data;
|
||||
|
||||
always @(posedge clk) begin
|
||||
last_hop_valid <= din_adc_valid;
|
||||
end
|
||||
|
||||
always @(posedge clk) begin
|
||||
if (rst) begin
|
||||
hop_data_cnt <= 'b0;
|
||||
end
|
||||
else if(din_adc_valid) begin
|
||||
if (hop_start_flag) begin
|
||||
hop_data_cnt <= 'b0;
|
||||
end
|
||||
else if (hop_data_cnt == RAM_HOP_DEPTH-1) begin
|
||||
hop_data_cnt <= 'b0;
|
||||
end
|
||||
else begin
|
||||
hop_data_cnt <= hop_data_cnt + 1'b1;
|
||||
end
|
||||
end
|
||||
else begin
|
||||
hop_data_cnt <= hop_data_cnt;
|
||||
end
|
||||
end
|
||||
|
||||
ram_hop_data u_ram_hop_data
|
||||
(
|
||||
.clka (clk ), // input wire clka
|
||||
.wea (din_adc_valid ), // input wire [0 : 0] wea
|
||||
.addra(hop_data_cnt ), // input wire [13 : 0] addra
|
||||
.dina (current_hop_data ), // input wire [95 : 0] dina
|
||||
.douta(last_hop_data ) // output wire [95 : 0] douta
|
||||
);
|
||||
genvar m;
|
||||
|
||||
// prepare cmpy input data
|
||||
wire [AXIS_WEIGHT_WIDTH-1:0] din_weight_real_array [0:CHANNEL_NUM-1];
|
||||
wire [AXIS_WEIGHT_WIDTH-1:0] din_weight_imag_array [0:CHANNEL_NUM-1];
|
||||
wire [WEIGHT_WIDTH-1:0] din_weight_real_array [0:CH_NUM-1];
|
||||
wire [WEIGHT_WIDTH-1:0] din_weight_imag_array [0:CH_NUM-1];
|
||||
|
||||
wire [AXIS_ADC_I_WIDTH-1:0] din_adc_real_array [0:CHANNEL_NUM-1];
|
||||
wire [AXIS_ADC_I_WIDTH-1:0] din_adc_imag_array [0:CHANNEL_NUM-1];
|
||||
wire [ADC_WIDTH-1:0] din_adc_real_array [0:CH_NUM-1];
|
||||
wire [ADC_WIDTH-1:0] din_adc_imag_array [0:CH_NUM-1];
|
||||
|
||||
wire [AXIS_WEIGHT_WIDTH-1:0] din_weight_real_array_axis [0:CH_NUM-1];
|
||||
wire [AXIS_WEIGHT_WIDTH-1:0] din_weight_imag_array_axis [0:CH_NUM-1];
|
||||
|
||||
wire [AXIS_ADC_WIDTH-1:0] din_adc_real_array_axis [0:CH_NUM-1];
|
||||
wire [AXIS_ADC_WIDTH-1:0] din_adc_imag_array_axis [0:CH_NUM-1];
|
||||
|
||||
for(m = 0; m < CH_NUM; m = m + 1) begin: array_conversion
|
||||
// Array split
|
||||
assign din_weight_real_array[m] = din_weight_real[m*WEIGHT_WIDTH +: WEIGHT_WIDTH];
|
||||
assign din_weight_imag_array[m] = din_weight_imag[m*WEIGHT_WIDTH +: WEIGHT_WIDTH];
|
||||
|
||||
assign din_adc_real_array[m] = din_adc_real[m*ADC_WIDTH +: ADC_WIDTH];
|
||||
assign din_adc_imag_array[m] = din_adc_imag[m*ADC_WIDTH +: ADC_WIDTH];
|
||||
|
||||
generate
|
||||
for(i = 0; i < CHANNEL_NUM; i = i + 1) begin: weight_array_convert
|
||||
// Sign extension to fit 8-bit axis data format
|
||||
assign din_weight_real_array[i] = {{(AXIS_WEIGHT_WIDTH-WEIGHT_WIDTH){last_weight_real[(i+1)*WEIGHT_WIDTH-1]}},last_weight_real[i*WEIGHT_WIDTH +: WEIGHT_WIDTH]};
|
||||
assign din_weight_imag_array[i] = {{(AXIS_WEIGHT_WIDTH-WEIGHT_WIDTH){last_weight_imag[(i+1)*WEIGHT_WIDTH-1]}},last_weight_imag[i*WEIGHT_WIDTH +: WEIGHT_WIDTH]};
|
||||
assign din_weight_real_array_axis[m] = {{(AXIS_WEIGHT_WIDTH-WEIGHT_WIDTH){din_weight_real_array[m][WEIGHT_WIDTH-1]}},din_weight_real_array[m]};
|
||||
assign din_weight_imag_array_axis[m] = {{(AXIS_WEIGHT_WIDTH-WEIGHT_WIDTH){din_weight_imag_array[m][WEIGHT_WIDTH-1]}},din_weight_imag_array[m]};
|
||||
|
||||
assign din_adc_real_array[i] = {{(AXIS_ADC_I_WIDTH-ADC_WIDTH){last_data_real[(i+1)*ADC_WIDTH-1]}},last_data_real[i*ADC_WIDTH +: ADC_WIDTH]};
|
||||
assign din_adc_imag_array[i] = {{(AXIS_ADC_I_WIDTH-ADC_WIDTH){last_data_imag[(i+1)*ADC_WIDTH-1]}},last_data_imag[i*ADC_WIDTH +: ADC_WIDTH]};
|
||||
assign din_adc_real_array_axis[m] = {{(AXIS_ADC_WIDTH-ADC_WIDTH){din_adc_real_array[m][ADC_WIDTH-1]}},din_adc_real_array[m]};
|
||||
assign din_adc_imag_array_axis[m] = {{(AXIS_ADC_WIDTH-ADC_WIDTH){din_adc_imag_array[m][ADC_WIDTH-1]}},din_adc_imag_array[m]};
|
||||
end
|
||||
endgenerate
|
||||
|
||||
// complex multiplication, spatial filtering
|
||||
wire [AXIS_FILTER_WIDTH-1:0] cmpy_real_array [0:CHANNEL_NUM-1];
|
||||
wire [AXIS_FILTER_WIDTH-1:0] cmpy_imag_array [0:CHANNEL_NUM-1];
|
||||
wire [AXIS_FILTER_WIDTH-1:0] cmpy_real_array [0:CH_NUM-1];
|
||||
wire [AXIS_FILTER_WIDTH-1:0] cmpy_imag_array [0:CH_NUM-1];
|
||||
|
||||
wire [FILTER_MULT_VALID_WIDTH-1:0] weight_adc_real_array [0:CHANNEL_NUM-1];
|
||||
wire [FILTER_MULT_VALID_WIDTH-1:0] weight_adc_imag_array [0:CHANNEL_NUM-1];
|
||||
wire [CMPY_P_VALID_WIDTH-1:0] weight_adc_real_array [0:CH_NUM-1];
|
||||
wire [CMPY_P_VALID_WIDTH-1:0] weight_adc_imag_array [0:CH_NUM-1];
|
||||
|
||||
wire weight_adc_valid;
|
||||
wire [CHANNEL_NUM*FILTER_MULT_VALID_WIDTH-1:0] weight_adc_real;
|
||||
wire [CHANNEL_NUM*FILTER_MULT_VALID_WIDTH-1:0] weight_adc_imag;
|
||||
wire [CH_NUM*CMPY_P_VALID_WIDTH-1:0] weight_adc_real;
|
||||
wire [CH_NUM*CMPY_P_VALID_WIDTH-1:0] weight_adc_imag;
|
||||
|
||||
generate
|
||||
for(i = 0; i < CHANNEL_NUM; i = i + 1) begin: spatial_filter_cmpy
|
||||
for(m = 0; m < CH_NUM; m = m + 1) begin: spatial_filter_cmpy
|
||||
wire [2*AXIS_WEIGHT_WIDTH-1:0] cmpy_a;
|
||||
wire [2*AXIS_ADC_I_WIDTH-1:0] cmpy_b;
|
||||
wire [2*AXIS_ADC_WIDTH-1:0] cmpy_b;
|
||||
wire [2*AXIS_FILTER_WIDTH-1:0] cmpy_p;
|
||||
wire cmpy_p_vld;
|
||||
|
||||
assign cmpy_a = {-din_weight_imag_array[i],din_weight_real_array[i]};
|
||||
assign cmpy_b = {din_adc_imag_array[i],din_adc_real_array[i]};
|
||||
assign {cmpy_imag_array[i],cmpy_real_array[i]} = cmpy_p;
|
||||
assign cmpy_a = {-din_weight_imag_array_axis[m],din_weight_real_array_axis[m]};
|
||||
assign cmpy_b = {din_adc_imag_array_axis[m],din_adc_real_array_axis[m]};
|
||||
assign {cmpy_imag_array[m],cmpy_real_array[m]} = cmpy_p;
|
||||
|
||||
assign weight_adc_real_array[i] = cmpy_real_array[i][0 +: FILTER_MULT_VALID_WIDTH];
|
||||
assign weight_adc_imag_array[i] = cmpy_imag_array[i][0 +: FILTER_MULT_VALID_WIDTH];
|
||||
assign weight_adc_real_array[m] = cmpy_real_array[m][0 +: CMPY_P_VALID_WIDTH];
|
||||
assign weight_adc_imag_array[m] = cmpy_imag_array[m][0 +: CMPY_P_VALID_WIDTH];
|
||||
|
||||
assign weight_adc_real[i*FILTER_MULT_VALID_WIDTH +: FILTER_MULT_VALID_WIDTH] = weight_adc_real_array[i];
|
||||
assign weight_adc_imag[i*FILTER_MULT_VALID_WIDTH +: FILTER_MULT_VALID_WIDTH] = weight_adc_imag_array[i];
|
||||
assign weight_adc_real[m*CMPY_P_VALID_WIDTH +: CMPY_P_VALID_WIDTH] = weight_adc_real_array[m];
|
||||
assign weight_adc_imag[m*CMPY_P_VALID_WIDTH +: CMPY_P_VALID_WIDTH] = weight_adc_imag_array[m];
|
||||
|
||||
cmpy_16x12 u_cmpy_16x12
|
||||
(
|
||||
.aclk (clk ), // input wire aclk
|
||||
.s_axis_a_tvalid (last_hop_valid ), // input wire s_axis_a_tvalid
|
||||
.s_axis_a_tdata (cmpy_a ), // input wire [31 : 0] s_axis_a_tdata
|
||||
.s_axis_b_tvalid (last_hop_valid ), // input wire s_axis_b_tvalid
|
||||
.s_axis_b_tdata (cmpy_b ), // input wire [31 : 0] s_axis_b_tdata
|
||||
.m_axis_dout_tvalid (cmpy_p_vld ), // output wire m_axis_dout_tvalid
|
||||
.m_axis_dout_tdata (cmpy_p ) // output wire [63 : 0] m_axis_dout_tdata
|
||||
.aclk (clk ), // input wire aclk
|
||||
.s_axis_a_tvalid (din_weight_valid ), // input wire s_axis_a_tvalid
|
||||
.s_axis_a_tdata (cmpy_a ), // input wire [31 : 0] s_axis_a_tdata
|
||||
.s_axis_b_tvalid (din_adc_valid ), // input wire s_axis_b_tvalid
|
||||
.s_axis_b_tdata (cmpy_b ), // input wire [31 : 0] s_axis_b_tdata
|
||||
.m_axis_dout_tvalid (cmpy_p_vld ), // output wire m_axis_dout_tvalid
|
||||
.m_axis_dout_tdata (cmpy_p ) // output wire [63 : 0] m_axis_dout_tdata
|
||||
);
|
||||
end
|
||||
endgenerate
|
||||
|
||||
assign weight_adc_valid = spatial_filter_cmpy[0].cmpy_p_vld;
|
||||
|
||||
@@ -219,8 +169,8 @@ wire [FILTER_SUM_WIDTH-1 : 0] weight_adc_sum_real;
|
||||
wire [FILTER_SUM_WIDTH-1 : 0] weight_adc_sum_imag;
|
||||
|
||||
adder_tree_ppl #(
|
||||
.DATA_I_WIDTH (FILTER_MULT_VALID_WIDTH),
|
||||
.DATA_NUM (CHANNEL_NUM )
|
||||
.DATA_I_WIDTH (CMPY_P_VALID_WIDTH),
|
||||
.DATA_NUM (CH_NUM )
|
||||
) u_multi_ch_add_ppl_i (
|
||||
// clock & reset
|
||||
.clk (clk ),
|
||||
@@ -236,8 +186,8 @@ adder_tree_ppl #(
|
||||
);
|
||||
|
||||
adder_tree_ppl #(
|
||||
.DATA_I_WIDTH (FILTER_MULT_VALID_WIDTH),
|
||||
.DATA_NUM (CHANNEL_NUM )
|
||||
.DATA_I_WIDTH (CMPY_P_VALID_WIDTH),
|
||||
.DATA_NUM (CH_NUM )
|
||||
) u_multi_ch_add_ppl_q (
|
||||
// clock & reset
|
||||
.clk (clk ),
|
||||
@@ -256,12 +206,14 @@ adder_tree_ppl #(
|
||||
assign dout_valid = weight_adc_sum_valid;
|
||||
|
||||
if (FILTER_O_WIDTH <= FILTER_SUM_WIDTH) begin
|
||||
// truncate msb
|
||||
assign dout_real = weight_adc_sum_real[FILTER_SUM_WIDTH-1 -: FILTER_O_WIDTH];
|
||||
assign dout_imag = weight_adc_sum_imag[FILTER_SUM_WIDTH-1 -: FILTER_O_WIDTH];
|
||||
end
|
||||
else begin
|
||||
assign dout_real = {{(FILTER_O_WIDTH-FILTER_SUM_WIDTH){weight_adc_sum_real[FILTER_SUM_WIDTH-1]}},weight_adc_sum_real};
|
||||
assign dout_imag = {{(FILTER_O_WIDTH-FILTER_SUM_WIDTH){weight_adc_sum_imag[FILTER_SUM_WIDTH-1]}},weight_adc_sum_imag};
|
||||
// append zeros to fit output data width
|
||||
assign dout_real = {weight_adc_sum_real,{(FILTER_O_WIDTH-FILTER_SUM_WIDTH){1'b0}}};
|
||||
assign dout_imag = {weight_adc_sum_imag,{(FILTER_O_WIDTH-FILTER_SUM_WIDTH){1'b0}}};
|
||||
end
|
||||
|
||||
|
||||
|
||||
@@ -613,6 +613,7 @@ wire [29:0] rx_data_i, rx_data_q;
|
||||
wire hop_trigger;
|
||||
wire hop_trigger_en;
|
||||
wire rx_test_en;
|
||||
wire lcmv_en;
|
||||
|
||||
wire hop_start_flag ;
|
||||
// wire accor_stream_valid ;
|
||||
@@ -689,12 +690,12 @@ ad9361_rx_map_cmos_dual u_ad9361_2_rx_map
|
||||
);
|
||||
|
||||
rx_pre_process #(
|
||||
.OUTPUT_DATA_WIDTH (30 )
|
||||
.OUTPUT_WIDTH (30 )
|
||||
) u_rx_pre_process
|
||||
(
|
||||
// clock & reset
|
||||
.sys_clk (sys_clk ), // sync to adc data
|
||||
.sys_clk_4x (sys_clk_4x ), // sync to physical layer
|
||||
.sys_clk_phy (sys_clk_3x ), // sync to physical layer
|
||||
.sys_rst (sys_rst ), // sync to [sys_clk]
|
||||
.clk_96m (clk_96m ), // sync to c2c data
|
||||
.ant_rst (ant_rst ), // sync to [clk_96m]
|
||||
@@ -720,8 +721,12 @@ rx_pre_process #(
|
||||
.ad9361_cal_result (ad9361_cal_result ),
|
||||
.ad9361_cal_valid (ad9361_cal_valid ),
|
||||
.ad9361_recal (ad9361_recal ),
|
||||
// nulling algorithm interface
|
||||
.hop_start_flag (hop_start_flag ), // sync to [sys_clk_4x]
|
||||
// nulling algotithm interface
|
||||
.hop_flag_in_phy (hop_start_flag ), // sync to [sys_clk_3x]
|
||||
.sync_flag_phy (1'b0 ), // sync to [sys_clk_3x]
|
||||
.lcmv_en_phy (lcmv_en ), // sync to [sys_clk_3x]
|
||||
.hop_flag_out ( ), // sync to [sys_clk]
|
||||
|
||||
.accor_stream_valid (accor_stream_valid ), // sync to [clk_96m]
|
||||
.accor_stream_data (accor_stream_data ), // sync to [clk_96m]
|
||||
.weight_stream_data (weight_stream_data ), // sync to [clk_96m]
|
||||
@@ -734,9 +739,9 @@ rx_pre_process #(
|
||||
rx_pre_test u_rx_pre_test
|
||||
(
|
||||
// clock & reset
|
||||
.sys_clk (sys_clk ),
|
||||
.sys_clk_4x (sys_clk_4x ),
|
||||
.sys_rst (sys_rst ),
|
||||
.clk (sys_clk ),
|
||||
.clk_phy (sys_clk_3x ),
|
||||
.rst (sys_rst ),
|
||||
.hop_trigger (hop_trigger ),
|
||||
.hop_trigger_en (hop_trigger_en ),
|
||||
// calc result
|
||||
@@ -758,10 +763,14 @@ rx_pre_test u_rx_pre_test
|
||||
// <----------------------- insert receiver logic below ----------------------->
|
||||
// <--------------------------------------------------------------------------->
|
||||
wire var_cal_start;
|
||||
wire cal_auto_en;
|
||||
wire var_cal_auto_en;
|
||||
wire var_cal_busy;
|
||||
wire var_valid;
|
||||
wire [31:0] var;
|
||||
wire [31:0] var_ch1;
|
||||
wire [31:0] var_ch2;
|
||||
wire [31:0] var_ch3;
|
||||
wire [31:0] var_ch4;
|
||||
|
||||
var_cal #(
|
||||
.ACCUM_NUM (16384 ),
|
||||
@@ -773,7 +782,7 @@ var_cal #(
|
||||
.rst (sys_rst ),
|
||||
|
||||
.cal_start (var_cal_start ),
|
||||
.cal_auto_en(cal_auto_en ),
|
||||
.cal_auto_en(var_cal_auto_en),
|
||||
.cal_busy (var_cal_busy ),
|
||||
|
||||
.din_valid (rx_data_valid ),
|
||||
@@ -784,6 +793,90 @@ var_cal #(
|
||||
.var (var )
|
||||
);
|
||||
|
||||
var_cal #(
|
||||
.ACCUM_NUM (16384 ),
|
||||
.DATA_I_WIDTH (12 ),
|
||||
.DATA_O_WIDTH (32 )
|
||||
) u_var_cal_ch1
|
||||
(
|
||||
.clk (sys_clk ),
|
||||
.rst (sys_rst ),
|
||||
|
||||
.cal_start (var_cal_start ),
|
||||
.cal_auto_en(var_cal_auto_en),
|
||||
.cal_busy ( ),
|
||||
|
||||
.din_valid (rx_data_valid ),
|
||||
.din_real (rx_ch1_i ),
|
||||
.din_imag (rx_ch1_q ),
|
||||
|
||||
.var_valid ( ),
|
||||
.var (var_ch1 )
|
||||
);
|
||||
|
||||
var_cal #(
|
||||
.ACCUM_NUM (16384 ),
|
||||
.DATA_I_WIDTH (12 ),
|
||||
.DATA_O_WIDTH (32 )
|
||||
) u_var_cal_ch2
|
||||
(
|
||||
.clk (sys_clk ),
|
||||
.rst (sys_rst ),
|
||||
|
||||
.cal_start (var_cal_start ),
|
||||
.cal_auto_en(var_cal_auto_en),
|
||||
.cal_busy ( ),
|
||||
|
||||
.din_valid (rx_data_valid ),
|
||||
.din_real (rx_ch2_i ),
|
||||
.din_imag (rx_ch2_q ),
|
||||
|
||||
.var_valid ( ),
|
||||
.var (var_ch2 )
|
||||
);
|
||||
|
||||
var_cal #(
|
||||
.ACCUM_NUM (16384 ),
|
||||
.DATA_I_WIDTH (12 ),
|
||||
.DATA_O_WIDTH (32 )
|
||||
) u_var_cal_ch3
|
||||
(
|
||||
.clk (sys_clk ),
|
||||
.rst (sys_rst ),
|
||||
|
||||
.cal_start (var_cal_start ),
|
||||
.cal_auto_en(var_cal_auto_en),
|
||||
.cal_busy ( ),
|
||||
|
||||
.din_valid (rx_data_valid ),
|
||||
.din_real (rx_ch3_i ),
|
||||
.din_imag (rx_ch3_q ),
|
||||
|
||||
.var_valid ( ),
|
||||
.var (var_ch3 )
|
||||
);
|
||||
|
||||
var_cal #(
|
||||
.ACCUM_NUM (16384 ),
|
||||
.DATA_I_WIDTH (12 ),
|
||||
.DATA_O_WIDTH (32 )
|
||||
) u_var_cal_ch4
|
||||
(
|
||||
.clk (sys_clk ),
|
||||
.rst (sys_rst ),
|
||||
|
||||
.cal_start (var_cal_start ),
|
||||
.cal_auto_en(var_cal_auto_en),
|
||||
.cal_busy ( ),
|
||||
|
||||
.din_valid (rx_data_valid ),
|
||||
.din_real (rx_ch4_i ),
|
||||
.din_imag (rx_ch4_q ),
|
||||
|
||||
.var_valid ( ),
|
||||
.var (var_ch4 )
|
||||
);
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////////////// ILAs and VIOs /////////////////////////////////
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
@@ -963,8 +1056,8 @@ ila_cal u_ila_cal
|
||||
ila_rx_pre_sys u_ila_rx_pre_sys
|
||||
(
|
||||
.clk (sys_clk ), // input wire clk
|
||||
.probe0 (u_rx_pre_process.hop_start_flag_cdc ), // input wire [0:0] probe0
|
||||
.probe1 (u_rx_pre_process.fifo_cdc_rst ), // input wire [0:0] probe1
|
||||
.probe0 (u_rx_pre_process.u_null_ctrl.hop_flag_in ), // input wire [0:0] probe0
|
||||
.probe1 (u_rx_pre_process.stream_fifo_rst ), // input wire [0:0] probe1
|
||||
.probe2 (u_rx_pre_process.u_accor_mat_stream.fifo_wr_en ), // input wire [0:0] probe2
|
||||
.probe3 (u_rx_pre_process.u_accor_mat_stream.fifo_din ), // input wire [31:0] probe3
|
||||
.probe4 (u_rx_pre_process.u_accor_mat_stream.fifo_full ), // input wire [0:0] probe4
|
||||
@@ -977,11 +1070,11 @@ ila_rx_pre_sys u_ila_rx_pre_sys
|
||||
ila_rx_pre_ant u_ila_rx_pre_ant
|
||||
(
|
||||
.clk (clk_96m ), // input wire clk
|
||||
.probe0 (u_rx_pre_process.hop_start_flag_cdc ), // input wire [0:0] probe0
|
||||
.probe0 (u_rx_pre_process.u_null_ctrl.hop_flag_in ), // input wire [0:0] probe0
|
||||
.probe1 (accor_stream_valid ), // input wire [0:0] probe1
|
||||
.probe2 (accor_stream_data ), // input wire [0:0] probe2
|
||||
.probe3 (weight_stream_data ), // input wire [0:0] probe3
|
||||
.probe4 (u_rx_pre_process.fifo_cdc_rst ), // input wire [0:0] probe4
|
||||
.probe4 (u_rx_pre_process.weight_fifo_rst ), // input wire [0:0] probe4
|
||||
.probe5 (u_rx_pre_process.u_accor_mat_stream.fifo_rd_en ), // input wire [0:0] probe5
|
||||
.probe6 (u_rx_pre_process.u_accor_mat_stream.fifo_dout ), // input wire [31:0] probe6
|
||||
.probe7 (u_rx_pre_process.u_accor_mat_stream.fifo_empty ), // input wire [0:0] probe7
|
||||
@@ -1005,16 +1098,21 @@ vio_manual_ctrl u_vio_manual_ctrl
|
||||
vio_phase_comp u_vio_phase_comp
|
||||
(
|
||||
.clk (sys_clk ), // input wire clk
|
||||
.probe_in0 (var ), // output wire [31 : 0] probe_in0
|
||||
.probe_in1 (var_cal_busy ), // output wire [0 : 0] probe_in1
|
||||
.probe_out0 (var_cal_start ), // output wire [0 : 0] probe_out0
|
||||
.probe_out1 (cal_auto_en ), // output wire [0 : 0] probe_out1
|
||||
.probe_out2 (hop_trigger_en ), // output wire [0 : 0] probe_out2
|
||||
.probe_out3 (hop_trigger ), // output wire [0 : 0] probe_out3
|
||||
.probe_out4 (phase_ch1 ), // output wire [15 : 0] probe_out4
|
||||
.probe_out5 (phase_ch2 ), // output wire [15 : 0] probe_out5
|
||||
.probe_out6 (phase_ch3 ), // output wire [15 : 0] probe_out6
|
||||
.probe_out7 (phase_ch4 ) // output wire [15 : 0] probe_out7
|
||||
.probe_in0 (var_cal_busy ), // output wire [0 : 0] probe_in0
|
||||
.probe_in1 (var ), // output wire [31 : 0] probe_in1
|
||||
.probe_in2 (var_ch1 ), // output wire [31 : 0] probe_in2
|
||||
.probe_in3 (var_ch2 ), // output wire [31 : 0] probe_in3
|
||||
.probe_in4 (var_ch3 ), // output wire [31 : 0] probe_in4
|
||||
.probe_in5 (var_ch4 ), // output wire [31 : 0] probe_in5
|
||||
.probe_out0 (phase_ch1 ), // output wire [15 : 0] probe_out0
|
||||
.probe_out1 (phase_ch2 ), // output wire [15 : 0] probe_out1
|
||||
.probe_out2 (phase_ch3 ), // output wire [15 : 0] probe_out2
|
||||
.probe_out3 (phase_ch4 ), // output wire [15 : 0] probe_out3
|
||||
.probe_out4 (var_cal_start ), // output wire [0 : 0] probe_out4
|
||||
.probe_out5 (var_cal_auto_en), // output wire [0 : 0] probe_out5
|
||||
.probe_out6 (hop_trigger_en ), // output wire [0 : 0] probe_out6
|
||||
.probe_out7 (hop_trigger ), // output wire [0 : 0] probe_out7
|
||||
.probe_out8 (lcmv_en ) // output wire [0 : 0] probe_out8
|
||||
);
|
||||
|
||||
endmodule
|
||||
|
||||
Reference in New Issue
Block a user