Using Generics to Define Ranges

R

rickman

I thought it would be a good idea to use Generics to define the ranges
on std_logic_vector and unsigned signals. However, when I try to then
create aggregates I get errors of "Choices for an array aggregate
(DownTo) must be locally static unless there is only one choice."

Carry <= (SPWTH-1 downto 1 => Pop, 0 => PassN);

I understand what this is saying, but it seems to be a major
difficulty. If I replace the generic with an attribute such as
Carry'high, I still get the error. I suppose because this is still
defined by the generic.

So is it barking up the wrong tree to use generics to define data path
widths or is there another way to then use these paths in aggregates
that I am missing?

Funny that this didn't seem to be a problem using the Lattice tools
(Synplify), but it is flagged by XST.

Rick
 
K

KJ

rickman said:
I thought it would be a good idea to use Generics to define the ranges
on std_logic_vector and unsigned signals. However, when I try to then
create aggregates I get errors of "Choices for an array aggregate
(DownTo) must be locally static unless there is only one choice."

Carry <= (SPWTH-1 downto 1 => Pop, 0 => PassN);

I understand what this is saying, but it seems to be a major
difficulty. If I replace the generic with an attribute such as
Carry'high, I still get the error. I suppose because this is still
defined by the generic.

So is it barking up the wrong tree to use generics to define data path
widths or is there another way to then use these paths in aggregates
that I am missing?

For this particular instance, you should turn it around a bit and avoid the
generic in the assignment.

Carry <= (0 => PassN, others => Pop);

For other cases, if the vector is representing some form of number you might
want to express carry something like this...

X <= std_logic_vector(to_unsigned(55, SPWTH));

Or if the assignment is particularly complicated, use a function.

Kevin Jennings
 
R

rickman

For this particular instance, you should turn it around a bit and avoid the
generic in the assignment.

Carry <= (0 => PassN, others => Pop);

For other cases, if the vector is representing some form of number you might
want to express carry something like this...

X <= std_logic_vector(to_unsigned(55, SPWTH));

Or if the assignment is particularly complicated, use a function.

Kevin Jennings

Certainly I could write it differently, but I do this in several
places and it is just a PITA to have to do this. I also find that it
is not consistent as to what it rejects, unless I just don't
understand what is wrong.

(MSByte => '1', others => '0')

This gets flagged because MSByte is a generic.

DatZero <= '1' when (DatAdd = (DatAdd'high downto 0 => '0')) else
'0';

This is not flagged even though DatAdd'high is defined by a generic.
I tried to work around the problem elsewhere by using the attribute
and still got a yellow card.

(IPWTH-1 downto IVWTH => '0') & IVEC when IPSR_IVEC,

This is also not flagged where IPWTH and IVWTH are generics. The only
difference between 1) and 3) is that 1) assigns different parts of the
vector separately.

Can anyone explain why these are all different or is the XST tool just
missing them? Synplify didn't have a problem with any of this, but
then I guess this is something that might be more of a problem in
simulation than synthesis. I haven't tried that yet.

Rick
 
J

JimLewis

Rickman,
In your second example, I see you using an aggregate in an expression.
I recommend only using aggregates when you are assigning directly to
an
object without an expression.

Consider:

library ieee ;
use ieee.std_logic_1164.all ;
use std.textio.all ;

entity aggregate_issues is
end entity aggregate_issues ;
architecture behavioral of aggregate_issues is
signal X_slv : std_logic_vector (0 to 7) ;
signal Y_slv : std_logic_vector (7 downto 0) ;
begin

testproc : process
begin
X_slv <= (0 => '1', others => '0') ; -- set left bit to a 1
Y_slv <= (7 => '1', others => '0') ;

wait for 10 ns ;

if X_slv = (0 => '1', 1 to 7 => '0') then -- compare left bit 1?
write(Output, "X SLV: True" & LF) ;
else
write(Output, "X SLV: FALSE" & LF) ;
end if ;

if Y_slv = (7 => '1', 6 downto 0 => '0') then -- compare left bit
1?
-- if Y_slv = (7 => '1', others => '0') then -- error as
aggregate does not size the array
write(Output, "Y SLV: True" & LF) ;
else
write(Output, "Y SLV: FALSE" & LF) ;
end if ;

wait ;
end process ;
end behavioral ;

Result:
# X SLV: True
# Y SLV: FALSE

The assignment is ok since it is coerced by the range of the type.
However, once it is put in an expression, some how the range of the
aggregate needs to be derived and it is not from the aggregate itself.
Instead it is based on the index range for the type which is
constrained
to be a natural which starts with 0 and goes to the highest integer.
Hence the default range for std_logic_vector (and all std_logic based
vectors) is "0 to ...".

So when I write something like this:
DatZero <= '1' when (DatAdd = (DatAdd'high downto 0 => '0')) else '0';

I use a math package (numeric_std if DatAddr is unsigned) and compare
with integers:
DatZero <= '1' when (DatAdd = 0) else '0';

If DatAddr is std_logic_vector either use std_logic_unsigned or add
type conversion:
DatZero <= '1' when (unsigned(DatAdd) = 0) else '0';


Cheers,
Jim
 
R

rickman

Thanks for your reply. You pointed out a few things I had forgotten,
like being able to compare unsigned to integers. I don't agree with
the general rule of avoiding aggregates in expressions however. Yes,
they have to have a defined range, but that was not an issue in my
case. The problem was that the range was defined by a generic which
is not defined at compile time.

This problem is made tricky because of the need to have some uses
defined at compile time, (aggregate ranges) but not other uses (array
ranges).

I've got workarounds, I just don't like some of them.

Rick
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,755
Messages
2,569,536
Members
45,014
Latest member
BiancaFix3

Latest Threads

Top