David,
I have a few small corrections to your counter example below.
> Now, when we extend this functionality to the fixed point packages:
> variable a8r : ufixed (-1 to 7) := "010011100"; -- 78.0
> variable a8 : ufixed (7 downto -1) := "000000000"; -- 0
> begin
> a8 := a8r + a8;
> assert (a8 = 78)
>
> With the above proposal, we will get 57.
You're right, we will get 57.0. And I think that's the right answer. I
think your comment after your "a8r" declaration is wrong. That bit literal
does not have a value of 78.0 with my proposal.
-- descending --
descending range: ufixed(7 downto -1)
descending value: "00111001_0" = 57.0
-- old ascending --
ascending range: ufixed(-1 to 7)
descending range: ufixed(1 downto -7)
ascending value: "0_01110010" = 78.0
descending value: "00_1110010" = 0.890625
-- proposed ascending --
ascending range: ufixed(-1 to 7)
descending range: ufixed(7 downto -1)
ascending value: "0_10011100" = 57.0 ***** 57.0, not 78.0 as commented
descending value: "00111001_0" = 57.0
Notice that I reversed the bits in the "descending" section so everything
comes out right. You admitted we already have to type cast the literal to
provide a range. This range also gives a value to each bit. My proposal is
the only way I know of to maintain the value of the bits. This means that
"01011" has a different value if assigned to a "ufixed(-1 to 3)" instead of
a "ufixed(3 downto -1)". However, "01011" also has a different value if
assigned to a "ufixed(3 downto -1)" versus a "ufixed(2 downto -2)". In my
mind, these ranges _mean_ something. These ranges give value to a
previously meaningless string of bits.
Maybe I don't understand the value interpretation of a "UNSIGNED(1 to 5)".
Can someone who uses this notation straighten me out? Here is my current
best guess (confirmed by a simulator).
-- descending --
descending range: unsigned(5 downto 1)
descending value: "01011" = 11
-- old ascending --
ascending range: unsigned(1 to 5)
descending range: unsigned(5 downto 1)
ascending value: "01011" = 11
descending value: "01011" = 11
To have the ascending value match the descending value, you need to assign a
value to each ascending bit something like 2**(var'HIGH - index). This has
the fun side-effect that bit 1 has a different value in an "unsigned(1 to
5)" and an "unsigned(1 to 2)". I guess we could carry this over to the
fixed point packages, but I would be interested to hear a good reason why
(besides consistency).
Jim,
I'm not excited about breaking convention, either. But the fixed point
package is breaking numeric_std convention from the start.
As David pointed out, in numeric_std every object and value is equivalent to
"UN/SIGNED(a'LENGTH-1 downto 0)". The whole purpose of the fixed point
package is to use this extra degree of freedom to assign value to bits. In
other words, "UFIXED(5 downto 1)" is different from "UFIXED(4 downto 0)".
If you add UNSIGNED objects with these ranges, you get a different result
than if you add UFIXED objects with these ranges. WE ARE ALREADY DOING
SOMETHING IRRECONCILABLY DIFFERENT. Namely, we are using the index range to
assign value to bits. Consequently, bit value needs to be maintained in
fixed_pkg in favor of numeric_std conventions. Otherwise we may as well
kill the whole thing because we can't do "+".
I see three numeric_std properties to maintain.
1. Flipped bounds. "Unsigned(a to b)" is equivalent to "unsigned(b downto
a)".
2. Identical value interpretation of bit literals.
3. The MSB is always on the left.
The new, critical property is (0) consistent bit value equation. So here
are the options I see for reversing direction.
A. Negate bounds. I believe this is the old rule. This preserves the MSB
on the left (natural VHDL matching), but converts a "ufixed(1 to 5)" to a
"ufixed(-1 downto -5)". This solution satisfies property (3), but violates
(0), (1) and (2).
B. Flip bounds, match bits. This is the numeric_std rule. This rule
converts "ufixed(-5 to 1)" to "ufixed(1 downto -5)". This solution
satisfies (1), (2) and (3), but violates (0).
C. Flip bounds, maintain bit value. This is my proposed rule. This rule
converts "ufixed(1 to 5)" to "ufixed(5 downto 1)" and reverses the bits.
This rule satisfies (1) and (0), but violates (2) and (3).
Now does my proposal make more sense? It is the best way I see to maintain
bit value--the new fixed_pkg invariant. We could make ascending/descending
conversion consistent with numeric_std, but I would rather have it
consistent with the rest of fixed_pkg.
--- Ryan Hinton L-3 Communications / Communication Systems - West ryan.w.hinton@L-3com.com -----Original Message----- From: Jim Lewis [mailto:Jim@SynthWorks.com] Sent: Tuesday, July 06, 2004 3:39 PM To: dbishop@vhdl.org; Hinton, Ryan W @ CSW-SLC Cc: 'vhdl-200x-ft@eda.org'; vhdlsynth@vhdl.org Subject: Re: [vhdl-200x-ft] Bit directions David and Ryan, I am not excited about breaking the direction rules of numeric_std unless there is a compelling reason to do so. Can you elaborate the benefits of doing this? Thanks, Jim -- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Jim Lewis Director of Training mailto:Jim@SynthWorks.com SynthWorks Design Inc. http://www.SynthWorks.com 1-503-590-4787 Expert VHDL Training for Hardware Design and Verification ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~Received on Tue Jul 6 16:26:46 2004
This archive was generated by hypermail 2.1.8 : Tue Jul 06 2004 - 16:26:52 PDT