Forum Discussion

Altera_Forum's avatar
Altera_Forum
Icon for Honored Contributor rankHonored Contributor
12 years ago

May I use a reg variable to indicate the bus bit ?

I have a design, I want to use a reg variable to control another bus bit like:

reg [2:0] a;

reg [7:0] b;

reg c;

reg [2:0] d;

case 1:

c <= b[a];

case 2:

d <= b[a:a-2];

It seems case 1 is feasible but case 2 I confronted the errors, which complains that "a" is not a constant, why?

Thanks.

6 Replies

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Review your Verilog text book or Verilog LRM about indexed part-select syntax

    --- Quote Start ---

    An indexed part-select is given with the following syntax:

    logic [15:0] down_vect;

    logic [0:15] up_vect;

    down_vect[lsb_base_expr +: width_expr]

    up_vect[msb_base_expr +: width_expr]

    down_vect[msb_base_expr -: width_expr]

    up_vect[lsb_base_expr -: width_expr]

    --- Quote End ---

    e.g.

    d <= b; 
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    --- Quote Start ---

    Review your Verilog text book or Verilog LRM about indexed part-select syntax

    e.g.

    d <= b; 

    --- Quote End ---

    Thanks very much, FvM. But based on your explanation, I think it should be :

    d <= b[a-:3]

    since 'd' is 3 bits wide.

    Correct?

    Thanks.
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    d <= b[a-:3] is correct. See 7.4.6 indexing and slicing of arrays in the 1800-2012 LRM. All Verilog bit vector widths must be determined at compile time. Even though it seems that you could prove that [a:a-2] would have a constant width, that's too much work for a compiler to verify for general expressions.

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    --- Quote Start ---

    d <= b[a-:3] is correct. See 7.4.6 Indexing and slicing of arrays in the 1800-2012 LRM. All Verilog bit vector widths must be determined at compile time. Even though it seems that you could prove that [a:a-2] would have a constant width, that's too much work for a compiler to verify for general expressions.

    --- Quote End ---

    Thanks for the correction.

    I don't think that it's too much for a compiler to verify, VHDL e.g. accepts similar expressions where both range limits are calculated. I believe that those people who designed Verilog tried to avoid unnecessary compiler effort with the explicite indexed part-select syntax. The construct also fits the Verilog typical shorthand style (in contrast to verbose VHDL). Now it's convention and has to be learned when picking up Verilog.
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    --- Quote Start ---

    I don't think that it's too much for a compiler to verify, VHDL e.g. accepts similar expressions where both range limits are calculated. I believe that those people who designed Verilog tried to avoid unnecessary compiler effort with the explicite indexed part-select syntax.

    --- Quote End ---

    It is one thing to be able to calculate indexes at runtime using actual values, but it still much more complex to calculate the width symbolically at compile time. VHDL treats logic vectors as strings with resolution functions for all operators that get called at runtime. Verilog, on the other hand, with all of its implicit type conversions does all of this resolution at compile time. This helps Verilog calculate expressions faster than VHDL.

    SystemVerilog allows you to use the streaming operator where the width does not need to be constant.

    d <= {<<{b with [a:a-2}};
    The bits of b that are assigned to d are calculated at run time.