summaryrefslogtreecommitdiffstats
path: root/fpga/usrp2/sdr_lib
diff options
context:
space:
mode:
Diffstat (limited to 'fpga/usrp2/sdr_lib')
-rw-r--r--fpga/usrp2/sdr_lib/dsp_core_tx.v15
-rw-r--r--fpga/usrp2/sdr_lib/small_hb_dec.v10
2 files changed, 14 insertions, 11 deletions
diff --git a/fpga/usrp2/sdr_lib/dsp_core_tx.v b/fpga/usrp2/sdr_lib/dsp_core_tx.v
index f02c63b42..4e0163e0a 100644
--- a/fpga/usrp2/sdr_lib/dsp_core_tx.v
+++ b/fpga/usrp2/sdr_lib/dsp_core_tx.v
@@ -36,7 +36,8 @@ module dsp_core_tx
wire [7:0] interp_rate;
wire [3:0] dacmux_a, dacmux_b;
wire enable_hb1, enable_hb2;
-
+ wire rate_change;
+
setting_reg #(.my_addr(BASE+0)) sr_0
(.clk(clk),.rst(rst),.strobe(set_stb),.addr(set_addr),
.in(set_data),.out(phase_inc),.changed());
@@ -47,7 +48,7 @@ module dsp_core_tx
setting_reg #(.my_addr(BASE+2), .width(10)) sr_2
(.clk(clk),.rst(rst),.strobe(set_stb),.addr(set_addr),
- .in(set_data),.out({enable_hb1, enable_hb2, interp_rate}),.changed());
+ .in(set_data),.out({enable_hb1, enable_hb2, interp_rate}),.changed(rate_change));
// Strobes are all now delayed by 1 cycle for timing reasons
wire strobe_cic_pre, strobe_hb1_pre, strobe_hb2_pre;
@@ -56,13 +57,13 @@ module dsp_core_tx
reg strobe_hb2 = 1;
cic_strober #(.WIDTH(8))
- cic_strober(.clock(clk),.reset(rst),.enable(run),.rate(interp_rate),
+ cic_strober(.clock(clk),.reset(rst),.enable(run & ~rate_change),.rate(interp_rate),
.strobe_fast(1),.strobe_slow(strobe_cic_pre) );
cic_strober #(.WIDTH(2))
- hb2_strober(.clock(clk),.reset(rst),.enable(run),.rate(enable_hb2 ? 2 : 1),
+ hb2_strober(.clock(clk),.reset(rst),.enable(run & ~rate_change),.rate(enable_hb2 ? 2 : 1),
.strobe_fast(strobe_cic_pre),.strobe_slow(strobe_hb2_pre) );
cic_strober #(.WIDTH(2))
- hb1_strober(.clock(clk),.reset(rst),.enable(run),.rate(enable_hb1 ? 2 : 1),
+ hb1_strober(.clock(clk),.reset(rst),.enable(run & ~rate_change),.rate(enable_hb1 ? 2 : 1),
.strobe_fast(strobe_hb2_pre),.strobe_slow(strobe_hb1_pre) );
always @(posedge clk) strobe_hb1 <= strobe_hb1_pre;
@@ -104,12 +105,12 @@ module dsp_core_tx
.output_rate(interp_rate),.stb_out(strobe_cic),.data_out(hb2_q));
cic_interp #(.bw(18),.N(4),.log2_of_max_rate(7))
- cic_interp_i(.clock(clk),.reset(rst),.enable(run),.rate(interp_rate),
+ cic_interp_i(.clock(clk),.reset(rst),.enable(run & ~rate_change),.rate(interp_rate),
.strobe_in(strobe_cic),.strobe_out(1),
.signal_in(hb2_i),.signal_out(i_interp));
cic_interp #(.bw(18),.N(4),.log2_of_max_rate(7))
- cic_interp_q(.clock(clk),.reset(rst),.enable(run),.rate(interp_rate),
+ cic_interp_q(.clock(clk),.reset(rst),.enable(run & ~rate_change),.rate(interp_rate),
.strobe_in(strobe_cic),.strobe_out(1),
.signal_in(hb2_q),.signal_out(q_interp));
diff --git a/fpga/usrp2/sdr_lib/small_hb_dec.v b/fpga/usrp2/sdr_lib/small_hb_dec.v
index a7f93e056..c05a48b81 100644
--- a/fpga/usrp2/sdr_lib/small_hb_dec.v
+++ b/fpga/usrp2/sdr_lib/small_hb_dec.v
@@ -103,22 +103,24 @@ module small_hb_dec
wire [17:0] coeff = go_d1 ? coeff_b : coeff_a;
wire [35:0] prod;
MULT18X18S mult(.C(clk), .CE(go_d1 | go_d2), .R(rst), .P(prod), .A(coeff), .B(sum) );
+
+ localparam ACCWIDTH = 30;
+ reg [ACCWIDTH-1:0] accum;
- reg [35:0] accum;
always @(posedge clk)
if(rst)
accum <= 0;
else if(go_d2)
- accum <= {middle_d1[17],middle_d1[17],middle_d1,16'd0} + {prod};
+ accum <= {middle_d1[17],middle_d1[17],middle_d1,{(16+ACCWIDTH-36){1'b0}}} + {prod[35:36-ACCWIDTH]};
else if(go_d3)
- accum <= accum + {prod};
+ accum <= accum + {prod[35:36-ACCWIDTH]};
wire [WIDTH:0] accum_rnd;
wire [WIDTH-1:0] accum_rnd_clip;
wire stb_round;
- round_sd #(.WIDTH_IN(36),.WIDTH_OUT(WIDTH+1)) round_acc
+ round_sd #(.WIDTH_IN(ACCWIDTH),.WIDTH_OUT(WIDTH+1)) round_acc
(.clk(clk), .reset(rst), .in(accum), .strobe_in(go_d4), .out(accum_rnd), .strobe_out(stb_round));
clip #(.bits_in(WIDTH+1),.bits_out(WIDTH)) clip (.in(accum_rnd), .out(accum_rnd_clip));