Problem with aggregates

R

romulo.white.94

Why x2 did not receive the value (d c b a x y z k) ?

Many thanks,
Romulo


entity aggregate is
port (x1, x2 : out string (8 downto 1));
end aggregate;

architecture funny of aggregate is
constant fix : string (4 downto 1):= "xyzk" ;
begin
-- result = expected: x1= d,c,b,a,x,y,z,k
x1 <= ( 8 => 'd', 7 => 'c', 6 => 'b', 5 => 'a', 4 => 'x', 3 =>
'y', 2 => 'z', 1 => 'k');

-- result: x2= a,b,c,d,x,y,z,k
-- expected: x2= d,c,b,a,x,y,z,k
x2 <= ( 8 => 'd', 7 => 'c', 6 => 'b', 5 => 'a') & fix;
end funny;
 
A

Andy

Why x2 did not receive the value (d c b a x y z k) ?

Many thanks,
Romulo

entity aggregate is
port (x1, x2 : out string (8 downto 1));
end aggregate;

architecture funny of aggregate is
constant fix : string (4 downto 1):= "xyzk" ;
begin
-- result = expected: x1= d,c,b,a,x,y,z,k
x1 <= ( 8 => 'd', 7 => 'c', 6 => 'b', 5 => 'a', 4 => 'x', 3 =>
'y', 2 => 'z', 1 => 'k');

-- result: x2= a,b,c,d,x,y,z,k
-- expected: x2= d,c,b,a,x,y,z,k
x2 <= ( 8 => 'd', 7 => 'c', 6 => 'b', 5 => 'a') & fix;
end funny;

It probably has to do with the default direction of an anonymous
string type (to vs downto). In the case of x1, the compiler can
(maybe?) assume that the direction of the aggregate matches the
direction of x1 since the indices match, but in x2, the aggregate is
concatenated with another string before being assigned, and thus it
cannot tell whether 8 is leftmost or rightmost. Named notation is just
that; not positional.


Andy
 
B

Brad Smallridge

This part ( 8 => 'd', 7 => 'c', 6 => 'b', 5 => 'a')
isn't defined so maybe you need

variable fox : string(8 downto 5);
.. . .
fox <= ( 8 => 'd', 7 => 'c', 6 => 'b', 5 => 'a');
x2 <= fox & fix;

Brad Smallridge
Ai Vision
 
R

romulo.white.94

Many thanks for your help, but I am not sure if I get your point.
I thought that, in a named association, we specify the value of an
element by an index; i.e. (8 => 'd') refers to the element 8 of the
composite type.

I made another description that makes me more confused. For signals
x_to3, x_dow3 and x_dow4 I would expect a compile error. As you
commented, it seems that the compiler first join the elements.

entity aggregate2 is
port (x_dow1, x_dow2, x_dow3 : out string (8 downto 1);
x_to1, x_to2, x_to3, x_to4 : out string (1 to 8));
end aggregate2;

architecture funny of aggregate2 is
constant fix_dow : string (4 downto 1):= "4321" ;
constant fix_to : string (1 to 4) := "5678";
begin
-- result = expected: x_dow1= 87654321
x_dow1 <= (8 => '8', 7 => '7', 6 => '6', 5 => '5', 4 => '4', 3 =>
'3', 2 => '2', 1 => '1');

-- result: x_dow2= 56784321 ???
-- expected: x_dow2= 87654321
x_dow2 <= (8 => '8', 7 => '7', 6 => '6', 5 => '5') & fix_dow;

-- result: x_dow2= 43215678 ???
-- expected: x_dow2= ???????????????
x_dow3 <= fix_dow &(8 => '8', 7 => '7', 6 => '6', 5 => '5');


-- result = expected: x_to1= 12345678
x_to1 <= (1 => '1', 2 => '2', 3 => '3', 4 => '4', 5 => '5', 6 =>
'6', 7 => '7', 8 => '8');

-- result = expected: x_to2= 12345678
x_to2 <= (1 => '1', 2 => '2', 3 => '3', 4 => '4') & fix_to;

-- result: x_to3= 56781234 ???
-- expected: x_to3= ???????????????
x_to3 <= fix_to & (1 => '1', 2 => '2', 3 => '3', 4 => '4');

-- result: x_to4= 12341234 ???
-- expected: x_to4= ???????????????
x_to4 <= (1 => '1', 2 => '2', 3 => '3', 4 => '4') & (1 => '1', 2
=> '2', 3 => '3', 4 => '4');
end funny;
 
J

James Unterburger

The aggregate also has direction TO because
its context is unconstrained STRING, the type of the left operand
of the implicit "&" operator.

The implicit "&"[string,string RETURN string] operator
returns an array with the direction of the index subtype
of the base array type (the index subtype of STRING is
POSITIVE), so the direction of the result of the concatenation
is TO.


Thus the expression (8=>'d',7=>'c',6=>'b',5=>'a') & fix
is the concatenation of two STRINGs:
string(5 TO 8) "abcd"
string(4 DOWNTO 1) "xyzk"

The result is a string(1 TO 8) with value "abcdxyzk"
because the concatenation rules say to use POSITIVE'LEFT
as the left bound (1), the direction of POSITIVE (TO),
and the number of elements in the array (8)to compute the
right bound using l+(r-1) (which is 1+(8-1) = 8).

See 7.3.2.2 Array aggregates.

The subtype of the target x1 *is* used when figuring out
the index range of the aggregate expression on the right;
the direction is DOWNTO because x1 has that direction;
the left bound is 1 because that's the smallest (index)
choice appearing in the aggregate; the right bound is
8 becuase that's the largest (index) choice appearing
in the aggregate.

The subtype of the target x2 *is not* used when figuring
out the index range of the concat expression; the concatenation
rules are for that. And x2's subtype certainly won't enter
the picture when figuring out the aggregate (left operand
of "&") bounds.
 
A

Andy

Many thanks for your help, but I am not sure if I get your point.
I thought that, in a named association, we specify the value of an
element by an index; i.e. (8 => 'd') refers to the element 8 of the
composite type.

I made another description that makes me more confused. For signals
x_to3, x_dow3 and x_dow4 I would expect a compile error. As you
commented, it seems that the compiler first join the elements.

entity aggregate2 is
port (x_dow1, x_dow2, x_dow3 : out string (8 downto 1);
x_to1, x_to2, x_to3, x_to4 : out string (1 to 8));
end aggregate2;

architecture funny of aggregate2 is
constant fix_dow : string (4 downto 1):= "4321" ;
constant fix_to : string (1 to 4) := "5678";
begin
-- result = expected: x_dow1= 87654321
x_dow1 <= (8 => '8', 7 => '7', 6 => '6', 5 => '5', 4 => '4', 3 =>
'3', 2 => '2', 1 => '1');

-- result: x_dow2= 56784321 ???
-- expected: x_dow2= 87654321
x_dow2 <= (8 => '8', 7 => '7', 6 => '6', 5 => '5') & fix_dow;

-- result: x_dow2= 43215678 ???
-- expected: x_dow2= ???????????????
x_dow3 <= fix_dow &(8 => '8', 7 => '7', 6 => '6', 5 => '5');

-- result = expected: x_to1= 12345678
x_to1 <= (1 => '1', 2 => '2', 3 => '3', 4 => '4', 5 => '5', 6 =>
'6', 7 => '7', 8 => '8');

-- result = expected: x_to2= 12345678
x_to2 <= (1 => '1', 2 => '2', 3 => '3', 4 => '4') & fix_to;

-- result: x_to3= 56781234 ???
-- expected: x_to3= ???????????????
x_to3 <= fix_to & (1 => '1', 2 => '2', 3 => '3', 4 => '4');

-- result: x_to4= 12341234 ???
-- expected: x_to4= ???????????????
x_to4 <= (1 => '1', 2 => '2', 3 => '3', 4 => '4') & (1 => '1', 2
=> '2', 3 => '3', 4 => '4');
end funny;

Just because you assigned something to element 8 in an anonymous
string composite, does not mean you assigned that something to the
leftmost element of that composite. The default ordering for strings
is 1 to ..., as James points out.

Andy
 

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,535
Members
45,007
Latest member
obedient dusk

Latest Threads

Top