0
\$\begingroup\$

What is the best practice for creating a bus, which is just extraction of certain bits of a larger bus. I do not want to store the index numbers to make the lookup in the generate-for if it could be avoided....I was hoping for something like following code which is of course not valid. Can we take advantage of the fact somehow that the extracted shorter bus is always consecutive bits from the larger bus?

localparam logic [7:0] VALID = {1'b0, 1'b1, 1'b1, 1'b1, 1'b1, 1'b0, 1'b0, 1'b0}; 
 genvar m, j;
 generate
 for (m=0; m<8; m++) begin
 if (VALID[m]) begin
 assign short_bus[j] = large_bus[m];
 j++;
 end
 endgenerate
asked Nov 29, 2018 at 15:28
\$\endgroup\$
7
  • \$\begingroup\$ Do you know in advance which bits are going to be valid? If so, you could just use assign short_bus = VALID[6:3]; - although I don't think that's what you're asking... \$\endgroup\$ Commented Nov 29, 2018 at 15:31
  • \$\begingroup\$ VALID only tells which bits of the large_bus go onto the short_bus \$\endgroup\$ Commented Nov 29, 2018 at 15:37
  • \$\begingroup\$ Think hardware instead of Verilog. The dumbest way is a set of multiplexers. The smartest way is shift register (but will require a number of cycles). \$\endgroup\$ Commented Nov 29, 2018 at 16:15
  • \$\begingroup\$ @Anonymous, the smartest way is just connect to the wires you want to connect to and not the other wires. No register involved (and OP doesn't seem to want the signals syncronized to a clock the way a register-based solution would require) \$\endgroup\$ Commented Nov 29, 2018 at 16:52
  • \$\begingroup\$ @frank_010, if the wanted bits are always consecutive why not just use assign short_bus[4:0] = large_bus[first_index+4:first_index]; ? Sorry I don't know enough SystemVerilog to make this a full answer. \$\endgroup\$ Commented Nov 29, 2018 at 16:54

2 Answers 2

1
\$\begingroup\$

I would use an array with the length of the short bus that maps short bus indices to large bus ones:

// Large Bus Width
localparam int LBW = 8;
localparam logic [LBW-1:0] VALID = {1'b0, 1'b1, 1'b1, 1'b1, 1'b1, 1'b0, 1'b0, 1'b0};
// 1. Function returning the width of the short bus
function automatic int get_short_width();
 automatic int si = 0;
 for (int li=0; li<LBW; li++)
 if (VALID[li])
 si++;
 return si;
endfunction
// Short Bus Width
localparam int SBW = get_short_width();
typedef int t_idx_arr[SBW];
// 2. Function returing the large-to-short array index mapping
function automatic t_idx_arr get_short_indices();
 t_idx_arr idx_ret;
 automatic int si = 0;
 for (int li=0; li<LBW; li++) begin
 if (VALID[li]) begin
 idx_ret[si] = li;
 si++;
 end
 end
 return idx_ret;
endfunction
// Large 2 Short Index Array
localparam t_idx_arr L2S_IDX = get_short_indices();
// 3. Assign
logic[LBW-1:0] large_bus;
logic[SBW-1:0] short_bus;
// note: loop on the SHORT bus width!
for (genvar si=0; si<SBW; si++) begin
 assign short_bus[si] = large_bus[L2S_IDX[si]];
end
assign large_bus = 8'b1101_1011;
// short_bus = 4'b1011

This works for non-consecutive valid bit positions on the large bus as well.

answered Dec 28, 2018 at 20:14
\$\endgroup\$
0
\$\begingroup\$

You have several options in SystemVerilog.

If your busses are nets, you can use an alias construct (See section 10.11 of the 1800-2017 LRM)

alias long_bus[M:N] = short_bus;
alias long_bus[O:+W] = short_bus;

M,N,O, and W must all be constant expressions of literals or parameters. For variables or nets, you can use the let construct (See section 11.12)

let short_bus = long_bus[M:N];
let short_bus = long_bus[O+:W]; // O does not need to be a constant

The benefits of these constructs over the assign construct is that its possible to use short_bus on both the LHS and RHS of an assignment.

answered Nov 29, 2018 at 17:40
\$\endgroup\$

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.