On 2/8/2011 11:55 AM, Tricky wrote:
Well, there's original sin(), concurrent sin(), sequential (serial?)
sin(), procedural sin(), functional sin()
Let's not forget monadic err... unary sin() and dyadic sin().
Or just "Go Forth and sin() no more."
I've tried a few to solve this problem. The LUT turned out to be the
easiest. My second choice, and the one I used in the floating point
packages was the taylor series done below.
I can approximate both the behavioral and structural model with:
e ^ sin (x) with the polynomial P (x) = 1 + x + x ^ 2 / 2! - 3 / 4! x
^ 4 - 8 / 5! x ^ 5 - 3 / 6! x ^ 6
(in the structural relationship, the coefficients are processed in fixed
point and the polynomial is calculated using fixed-point operations).
thanks again in advance
First of all, why not look into the new IEEE fixed point package. For
VHDL '93 compatible version, see here:
http://www.vhdl.org/fphdl/
Then you can do nice things like:
port (x: in sfixed (2 downto -13), y: out sfixed(2 downto -13) etc
So the bit numbers represent the real powers of 2 in the fixed point
numbers.
Then for a behavioural model, you can do this:
use ieee.math_real.all;
...
port (clk : in std_logic;
x: in sfixed (2 downto -13);
y: out sfixed(2 downto -13));
....
process
variable x_rl : real;
variable y_rl : real;
begin
wait until rising_edge(clk);
x_rl := to_real(x);
y_rl := math_e ** sin(x_rl);
y<= to_sfixed(y_rl, y'high, y'low);
end process;
This wont be synthesisable, but it is a nice simple behavioural model.
For a synthesisable implementation, a look up table is usually the
best approach, but at 16 bits thats a fair chunk of memory!
Create a look up table for 0 - PI/2, then just reflect it for the other
3 quadrants.