aboutsummaryrefslogtreecommitdiffstats
path: root/usrp2/sdr_lib
diff options
context:
space:
mode:
authorJosh Blum <josh@joshknows.com>2012-02-10 12:13:51 -0800
committerJosh Blum <josh@joshknows.com>2012-02-10 12:13:51 -0800
commit6d45600ada785cb50a01a17dcddf561d12501d22 (patch)
treec223f87aebf64f305b4bfe83e0ce799d01dad59a /usrp2/sdr_lib
parent34db74740704ce2de2a71447b3d202e9c4be800b (diff)
downloaduhd-6d45600ada785cb50a01a17dcddf561d12501d22.tar.gz
uhd-6d45600ada785cb50a01a17dcddf561d12501d22.tar.bz2
uhd-6d45600ada785cb50a01a17dcddf561d12501d22.zip
dsp rework: pass enables into glue, update power trig, parameterize, fix module inc
DSP enables now pass through the glue and custom modules so it can be user-controlled. Updated power trigger to current spec, and added comments Pass width from dsp into glue, and use width to parameterize wires Fix custom module includes so they will build
Diffstat (limited to 'usrp2/sdr_lib')
-rw-r--r--usrp2/sdr_lib/ddc_chain.v94
-rw-r--r--usrp2/sdr_lib/dsp_rx_glue.v11
-rw-r--r--usrp2/sdr_lib/dsp_tx_glue.v11
-rw-r--r--usrp2/sdr_lib/duc_chain.v37
4 files changed, 88 insertions, 65 deletions
diff --git a/usrp2/sdr_lib/ddc_chain.v b/usrp2/sdr_lib/ddc_chain.v
index 800bb5b13..c32c9f491 100644
--- a/usrp2/sdr_lib/ddc_chain.v
+++ b/usrp2/sdr_lib/ddc_chain.v
@@ -18,14 +18,18 @@
//! The USRP digital down-conversion chain
module ddc_chain
- #(parameter BASE = 0, parameter DSPNO = 0)
+ #(
+ parameter BASE = 0,
+ parameter DSPNO = 0,
+ parameter WIDTH = 24
+ )
(input clk, input rst, input clr,
input set_stb, input [7:0] set_addr, input [31:0] set_data,
input set_stb_user, input [7:0] set_addr_user, input [31:0] set_data_user,
// From RX frontend
- input [23:0] rx_fe_i,
- input [23:0] rx_fe_q,
+ input [WIDTH-1:0] rx_fe_i,
+ input [WIDTH-1:0] rx_fe_q,
// To RX control
output [31:0] sample,
@@ -34,21 +38,25 @@ module ddc_chain
output [31:0] debug
);
+ localparam cwidth = 25;
+ localparam zwidth = 24;
+
+ wire ddc_enb;
wire [31:0] phase_inc;
reg [31:0] phase;
wire [17:0] scale_factor;
- wire [24:0] i_cordic, q_cordic;
- wire [23:0] i_cordic_clip, q_cordic_clip;
- wire [23:0] i_cic, q_cic;
- wire [23:0] i_hb1, q_hb1;
- wire [23:0] i_hb2, q_hb2;
+ wire [cwidth-1:0] i_cordic, q_cordic;
+ wire [WIDTH-1:0] i_cordic_clip, q_cordic_clip;
+ wire [WIDTH-1:0] i_cic, q_cic;
+ wire [WIDTH-1:0] i_hb1, q_hb1;
+ wire [WIDTH-1:0] i_hb2, q_hb2;
wire strobe_cic, strobe_hb1, strobe_hb2;
wire enable_hb1, enable_hb2;
wire [7:0] cic_decim_rate;
- reg [23:0] rx_fe_i_mux, rx_fe_q_mux;
+ reg [WIDTH-1:0] rx_fe_i_mux, rx_fe_q_mux;
wire realmode;
wire swap_iq;
@@ -74,103 +82,107 @@ module ddc_chain
if(swap_iq)
begin
rx_fe_i_mux <= rx_fe_q;
- rx_fe_q_mux <= realmode ? 24'd0 : rx_fe_i;
+ rx_fe_q_mux <= realmode ? 0 : rx_fe_i;
end
else
begin
rx_fe_i_mux <= rx_fe_i;
- rx_fe_q_mux <= realmode ? 24'd0 : rx_fe_q;
+ rx_fe_q_mux <= realmode ? 0 : rx_fe_q;
end
// NCO
always @(posedge clk)
if(rst)
phase <= 0;
- else if(~run)
+ else if(~ddc_enb)
phase <= 0;
else
phase <= phase + phase_inc;
- wire [23:0] to_cordic_i, to_cordic_q;
+ //sign extension of cordic input
+ wire [WIDTH-1:0] to_ddc_chain_i, to_ddc_chain_q;
+ wire [cwidth-1:0] to_cordic_i, to_cordic_q;
+ sign_extend #(.bits_in(WIDTH), .bits_out(cwidth)) sign_extend_cordic_i (.in(to_ddc_chain_i), .out(to_cordic_i));
+ sign_extend #(.bits_in(WIDTH), .bits_out(cwidth)) sign_extend_cordic_q (.in(to_ddc_chain_q), .out(to_cordic_q));
// CORDIC 24-bit I/O
- cordic_z24 #(.bitwidth(25))
- cordic(.clock(clk), .reset(rst), .enable(run),
- .xi({to_cordic_i[23],to_cordic_i}),. yi({to_cordic_q[23],to_cordic_q}), .zi(phase[31:8]),
+ cordic_z24 #(.bitwidth(cwidth))
+ cordic(.clock(clk), .reset(rst), .enable(ddc_enb),
+ .xi(to_cordic_i),. yi(to_cordic_q), .zi(phase[31:32-zwidth]),
.xo(i_cordic),.yo(q_cordic),.zo() );
- clip_reg #(.bits_in(25), .bits_out(24)) clip_i
+ clip_reg #(.bits_in(cwidth), .bits_out(WIDTH)) clip_i
(.clk(clk), .in(i_cordic), .strobe_in(1'b1), .out(i_cordic_clip));
- clip_reg #(.bits_in(25), .bits_out(24)) clip_q
+ clip_reg #(.bits_in(cwidth), .bits_out(WIDTH)) clip_q
(.clk(clk), .in(q_cordic), .strobe_in(1'b1), .out(q_cordic_clip));
// CIC decimator 24 bit I/O
- cic_strober cic_strober(.clock(clk),.reset(rst),.enable(run),.rate(cic_decim_rate),
+ cic_strober cic_strober(.clock(clk),.reset(rst),.enable(ddc_enb),.rate(cic_decim_rate),
.strobe_fast(1),.strobe_slow(strobe_cic) );
- cic_decim #(.bw(24))
- decim_i (.clock(clk),.reset(rst),.enable(run),
+ cic_decim #(.bw(WIDTH))
+ decim_i (.clock(clk),.reset(rst),.enable(ddc_enb),
.rate(cic_decim_rate),.strobe_in(1'b1),.strobe_out(strobe_cic),
.signal_in(i_cordic_clip),.signal_out(i_cic));
- cic_decim #(.bw(24))
- decim_q (.clock(clk),.reset(rst),.enable(run),
+ cic_decim #(.bw(WIDTH))
+ decim_q (.clock(clk),.reset(rst),.enable(ddc_enb),
.rate(cic_decim_rate),.strobe_in(1'b1),.strobe_out(strobe_cic),
.signal_in(q_cordic_clip),.signal_out(q_cic));
// First (small) halfband 24 bit I/O
- small_hb_dec #(.WIDTH(24)) small_hb_i
- (.clk(clk),.rst(rst),.bypass(~enable_hb1),.run(run),
+ small_hb_dec #(.WIDTH(WIDTH)) small_hb_i
+ (.clk(clk),.rst(rst),.bypass(~enable_hb1),.run(ddc_enb),
.stb_in(strobe_cic),.data_in(i_cic),.stb_out(strobe_hb1),.data_out(i_hb1));
- small_hb_dec #(.WIDTH(24)) small_hb_q
- (.clk(clk),.rst(rst),.bypass(~enable_hb1),.run(run),
+ small_hb_dec #(.WIDTH(WIDTH)) small_hb_q
+ (.clk(clk),.rst(rst),.bypass(~enable_hb1),.run(ddc_enb),
.stb_in(strobe_cic),.data_in(q_cic),.stb_out(),.data_out(q_hb1));
// Second (large) halfband 24 bit I/O
wire [8:0] cpi_hb = enable_hb1 ? {cic_decim_rate,1'b0} : {1'b0,cic_decim_rate};
- hb_dec #(.WIDTH(24)) hb_i
- (.clk(clk),.rst(rst),.bypass(~enable_hb2),.run(run),.cpi(cpi_hb),
+ hb_dec #(.WIDTH(WIDTH)) hb_i
+ (.clk(clk),.rst(rst),.bypass(~enable_hb2),.run(ddc_enb),.cpi(cpi_hb),
.stb_in(strobe_hb1),.data_in(i_hb1),.stb_out(strobe_hb2),.data_out(i_hb2));
- hb_dec #(.WIDTH(24)) hb_q
- (.clk(clk),.rst(rst),.bypass(~enable_hb2),.run(run),.cpi(cpi_hb),
+ hb_dec #(.WIDTH(WIDTH)) hb_q
+ (.clk(clk),.rst(rst),.bypass(~enable_hb2),.run(ddc_enb),.cpi(cpi_hb),
.stb_in(strobe_hb1),.data_in(q_hb1),.stb_out(),.data_out(q_hb2));
//scalar operation (gain of 6 bits)
wire [35:0] prod_i, prod_q;
MULT18X18S mult_i
- (.P(prod_i), .A(i_hb2[23:6]), .B(scale_factor), .C(clk), .CE(strobe_hb2), .R(rst) );
+ (.P(prod_i), .A(i_hb2[WIDTH-1:WIDTH-18]), .B(scale_factor), .C(clk), .CE(strobe_hb2), .R(rst) );
MULT18X18S mult_q
- (.P(prod_q), .A(q_hb2[23:6]), .B(scale_factor), .C(clk), .CE(strobe_hb2), .R(rst) );
+ (.P(prod_q), .A(q_hb2[WIDTH-1:WIDTH-18]), .B(scale_factor), .C(clk), .CE(strobe_hb2), .R(rst) );
//pipeline for the multiplier (gain of 10 bits)
- reg [23:0] prod_reg_i, prod_reg_q;
+ reg [WIDTH-1:0] prod_reg_i, prod_reg_q;
reg strobe_mult;
always @(posedge clk) begin
strobe_mult <= strobe_hb2;
- prod_reg_i <= prod_i[33:10];
- prod_reg_q <= prod_q[33:10];
+ prod_reg_i <= prod_i[33:34-WIDTH];
+ prod_reg_q <= prod_q[33:34-WIDTH];
end
// Round final answer to 16 bits
wire [31:0] ddc_chain_out;
wire ddc_chain_stb;
- round_sd #(.WIDTH_IN(24),.WIDTH_OUT(16)) round_i
+ round_sd #(.WIDTH_IN(WIDTH),.WIDTH_OUT(16)) round_i
(.clk(clk),.reset(rst), .in(prod_reg_i),.strobe_in(strobe_mult), .out(ddc_chain_out[31:16]), .strobe_out(ddc_chain_stb));
- round_sd #(.WIDTH_IN(24),.WIDTH_OUT(16)) round_q
+ round_sd #(.WIDTH_IN(WIDTH),.WIDTH_OUT(16)) round_q
(.clk(clk),.reset(rst), .in(prod_reg_q),.strobe_in(strobe_mult), .out(ddc_chain_out[15:0]), .strobe_out());
- dsp_rx_glue #(.DSPNO(DSPNO)) custom(
+ dsp_rx_glue #(.DSPNO(DSPNO), .WIDTH(WIDTH)) custom(
.clock(clk), .reset(rst), .clear(clr), .enable(run),
.set_stb(set_stb_user), .set_addr(set_addr_user), .set_data(set_data_user),
.frontend_i(rx_fe_i_mux), .frontend_q(rx_fe_q_mux),
- .ddc_in_i(to_cordic_i), .ddc_in_q(to_cordic_q),
- .ddc_out_sample(ddc_chain_out), .ddc_out_strobe(ddc_chain_stb),
+ .ddc_in_i(to_ddc_chain_i), .ddc_in_q(to_ddc_chain_q),
+ .ddc_out_sample(ddc_chain_out), .ddc_out_strobe(ddc_chain_stb), .ddc_out_enable(ddc_enb),
.bb_sample(sample), .bb_strobe(strobe));
assign debug = {enable_hb1, enable_hb2, run, strobe, strobe_cic, strobe_hb1, strobe_hb2};
diff --git a/usrp2/sdr_lib/dsp_rx_glue.v b/usrp2/sdr_lib/dsp_rx_glue.v
index e2a1d52b1..038a67a29 100644
--- a/usrp2/sdr_lib/dsp_rx_glue.v
+++ b/usrp2/sdr_lib/dsp_rx_glue.v
@@ -44,6 +44,7 @@ module dsp_rx_glue
//strobed samples {I16,Q16} from the RX DDC chain
input [31:0] ddc_out_sample,
input ddc_out_strobe, //high on valid sample
+ output ddc_out_enable, //enables DDC module
//strobbed baseband samples {I16,Q16} from this module
output [31:0] bb_sample,
@@ -60,14 +61,15 @@ module dsp_rx_glue
assign ddc_in_q = frontend_q;
assign bb_sample = ddc_out_sample;
assign bb_strobe = ddc_out_strobe;
+ assign ddc_out_enable = enable;
`else
- RX_DSP0_MODULE rx_dsp0_custom
+ `RX_DSP0_MODULE #(.WIDTH(WIDTH)) rx_dsp0_custom
(
.clock(clock), .reset(reset), .clear(clear), .enable(enable),
.set_stb(set_stb), .set_addr(set_addr), .set_data(set_data),
.frontend_i(frontend_i), .frontend_q(frontend_q),
.ddc_in_i(ddc_in_i), .ddc_in_q(ddc_in_q),
- .ddc_out_sample(ddc_out_sample), .ddc_out_strobe(ddc_out_strobe),
+ .ddc_out_sample(ddc_out_sample), .ddc_out_strobe(ddc_out_strobe), .ddc_out_enable(ddc_out_enable),
.bb_sample(bb_sample), .bb_strobe(bb_strobe)
);
`endif
@@ -78,14 +80,15 @@ module dsp_rx_glue
assign ddc_in_q = frontend_q;
assign bb_sample = ddc_out_sample;
assign bb_strobe = ddc_out_strobe;
+ assign ddc_out_enable = enable;
`else
- RX_DSP1_MODULE rx_dsp1_custom
+ `RX_DSP1_MODULE #(.WIDTH(WIDTH)) rx_dsp1_custom
(
.clock(clock), .reset(reset), .clear(clear), .enable(enable),
.set_stb(set_stb), .set_addr(set_addr), .set_data(set_data),
.frontend_i(frontend_i), .frontend_q(frontend_q),
.ddc_in_i(ddc_in_i), .ddc_in_q(ddc_in_q),
- .ddc_out_sample(ddc_out_sample), .ddc_out_strobe(ddc_out_strobe),
+ .ddc_out_sample(ddc_out_sample), .ddc_out_strobe(ddc_out_strobe), .ddc_out_enable(ddc_out_enable),
.bb_sample(bb_sample), .bb_strobe(bb_strobe)
);
`endif
diff --git a/usrp2/sdr_lib/dsp_tx_glue.v b/usrp2/sdr_lib/dsp_tx_glue.v
index 9af13c6c1..46f6789ee 100644
--- a/usrp2/sdr_lib/dsp_tx_glue.v
+++ b/usrp2/sdr_lib/dsp_tx_glue.v
@@ -44,6 +44,7 @@ module dsp_tx_glue
//strobed samples {I16,Q16} to the TX DUC chain
output [31:0] duc_in_sample,
input duc_in_strobe, //this is a backpressure signal
+ output duc_in_enable, //enables DUC module
//strobbed baseband samples {I16,Q16} to this module
input [31:0] bb_sample,
@@ -60,14 +61,15 @@ module dsp_tx_glue
assign frontend_q = duc_out_q;
assign duc_in_sample = bb_sample;
assign bb_strobe = duc_in_strobe;
+ assign duc_in_enable = enable;
`else
- TX_DSP0_MODULE tx_dsp0_custom
+ `TX_DSP0_MODULE #(.WIDTH(WIDTH)) tx_dsp0_custom
(
.clock(clock), .reset(reset), .clear(clear), .enable(enable),
.set_stb(set_stb), .set_addr(set_addr), .set_data(set_data),
.frontend_i(frontend_i), .frontend_q(frontend_q),
.duc_out_i(duc_out_i), .duc_out_q(duc_out_q),
- .duc_in_sample(duc_in_sample), .duc_in_strobe(duc_in_strobe),
+ .duc_in_sample(duc_in_sample), .duc_in_strobe(duc_in_strobe), .duc_in_enable(duc_in_enable),
.bb_sample(bb_sample), .bb_strobe(bb_strobe)
);
`endif
@@ -78,14 +80,15 @@ module dsp_tx_glue
assign frontend_q = duc_out_q;
assign duc_in_sample = bb_sample;
assign bb_strobe = duc_in_strobe;
+ assign duc_in_enable = enable;
`else
- TX_DSP1_MODULE tx_dsp1_custom
+ `TX_DSP1_MODULE #(.WIDTH(WIDTH)) tx_dsp1_custom
(
.clock(clock), .reset(reset), .clear(clear), .enable(enable),
.set_stb(set_stb), .set_addr(set_addr), .set_data(set_data),
.frontend_i(frontend_i), .frontend_q(frontend_q),
.duc_out_i(duc_out_i), .duc_out_q(duc_out_q),
- .duc_in_sample(duc_in_sample), .duc_in_strobe(duc_in_strobe),
+ .duc_in_sample(duc_in_sample), .duc_in_strobe(duc_in_strobe), .duc_in_enable(duc_in_enable),
.bb_sample(bb_sample), .bb_strobe(bb_strobe)
);
`endif
diff --git a/usrp2/sdr_lib/duc_chain.v b/usrp2/sdr_lib/duc_chain.v
index 7a72903a6..bd3402a1f 100644
--- a/usrp2/sdr_lib/duc_chain.v
+++ b/usrp2/sdr_lib/duc_chain.v
@@ -18,14 +18,18 @@
//! The USRP digital up-conversion chain
module duc_chain
- #(parameter BASE = 0, parameter DSPNO = 0)
+ #(
+ parameter BASE = 0,
+ parameter DSPNO = 0,
+ parameter WIDTH = 24
+ )
(input clk, input rst, input clr,
input set_stb, input [7:0] set_addr, input [31:0] set_data,
input set_stb_user, input [7:0] set_addr_user, input [31:0] set_data_user,
// To TX frontend
- output [23:0] tx_fe_i,
- output [23:0] tx_fe_q,
+ output [WIDTH-1:0] tx_fe_i,
+ output [WIDTH-1:0] tx_fe_q,
// From TX control
input [31:0] sample,
@@ -34,6 +38,7 @@ module duc_chain
output [31:0] debug
);
+ wire duc_enb;
wire [17:0] scale_factor;
wire [31:0] phase_inc;
reg [31:0] phase;
@@ -61,13 +66,13 @@ module duc_chain
reg strobe_hb2 = 1;
cic_strober #(.WIDTH(8))
- cic_strober(.clock(clk),.reset(rst),.enable(run & ~rate_change),.rate(interp_rate),
+ cic_strober(.clock(clk),.reset(rst),.enable(duc_enb & ~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_change),.rate(enable_hb2 ? 2 : 1),
+ hb2_strober(.clock(clk),.reset(rst),.enable(duc_enb & ~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_change),.rate(enable_hb1 ? 2 : 1),
+ hb1_strober(.clock(clk),.reset(rst),.enable(duc_enb & ~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;
@@ -78,7 +83,7 @@ module duc_chain
always @(posedge clk)
if(rst)
phase <= 0;
- else if(~run)
+ else if(~duc_enb)
phase <= 0;
else
phase <= phase + phase_inc;
@@ -96,9 +101,9 @@ module duc_chain
// Note that max CIC rate is 128, which would give an overflow on cpo if enable_hb2 is true,
// but the default case inside hb_interp handles this
- hb_interp #(.IWIDTH(18),.OWIDTH(18),.ACCWIDTH(24)) hb_interp_i
+ hb_interp #(.IWIDTH(18),.OWIDTH(18),.ACCWIDTH(WIDTH)) hb_interp_i
(.clk(clk),.rst(rst),.bypass(~enable_hb1),.cpo(cpo),.stb_in(strobe_hb1),.data_in({bb_i, 2'b0}),.stb_out(strobe_hb2),.data_out(hb1_i));
- hb_interp #(.IWIDTH(18),.OWIDTH(18),.ACCWIDTH(24)) hb_interp_q
+ hb_interp #(.IWIDTH(18),.OWIDTH(18),.ACCWIDTH(WIDTH)) hb_interp_q
(.clk(clk),.rst(rst),.bypass(~enable_hb1),.cpo(cpo),.stb_in(strobe_hb1),.data_in({bb_q, 2'b0}),.stb_out(strobe_hb2),.data_out(hb1_q));
small_hb_int #(.WIDTH(18)) small_hb_interp_i
@@ -109,22 +114,22 @@ module duc_chain
.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_change),.rate(interp_rate),
+ cic_interp_i(.clock(clk),.reset(rst),.enable(duc_enb & ~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_change),.rate(interp_rate),
+ cic_interp_q(.clock(clk),.reset(rst),.enable(duc_enb & ~rate_change),.rate(interp_rate),
.strobe_in(strobe_cic),.strobe_out(1),
.signal_in(hb2_q),.signal_out(q_interp));
- localparam cwidth = 24; // was 18
+ localparam cwidth = WIDTH; // was 18
localparam zwidth = 24; // was 16
wire [cwidth-1:0] da_c, db_c;
cordic_z24 #(.bitwidth(cwidth))
- cordic(.clock(clk), .reset(rst), .enable(run),
+ cordic(.clock(clk), .reset(rst), .enable(duc_enb),
.xi({i_interp,{(cwidth-18){1'b0}}}),.yi({q_interp,{(cwidth-18){1'b0}}}),
.zi(phase[31:32-zwidth]),
.xo(da_c),.yo(db_c),.zo() );
@@ -147,12 +152,12 @@ module duc_chain
.R(rst) // Synchronous reset input
);
- dsp_tx_glue #(.DSPNO(DSPNO)) dsp_tx_glue(
+ dsp_tx_glue #(.DSPNO(DSPNO), .WIDTH(WIDTH)) dsp_tx_glue(
.clock(clk), .reset(rst), .clear(clr), .enable(run),
.set_stb(set_stb_user), .set_addr(set_addr_user), .set_data(set_data_user),
.frontend_i(tx_fe_i), .frontend_q(tx_fe_q),
- .duc_out_i(prod_i[33:10]), .duc_out_q(prod_q[33:10]),
- .duc_in_sample({bb_i, bb_q}), .duc_in_strobe(strobe_hb1),
+ .duc_out_i(prod_i[33:34-WIDTH]), .duc_out_q(prod_q[33:34-WIDTH]),
+ .duc_in_sample({bb_i, bb_q}), .duc_in_strobe(strobe_hb1), .duc_in_enable(duc_enb),
.bb_sample(sample), .bb_strobe(strobe));
assign debug = {strobe_cic, strobe_hb1, strobe_hb2,run};