OpenCores
URL https://opencores.org/ocsvn/signal_waveform_generator/signal_waveform_generator/trunk

Subversion Repositories signal_waveform_generator

[/] [signal_waveform_generator/] [trunk/] [hw/] [sources/] [WaveformGenerator/] [sources/] [WaveformGenerator.vhd] - Blame information for rev 2

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 ldalmasso
------------------------------------------------------------------------
2
-- Engineer:    Dalmasso Loic
3
-- Create Date: 30/01/2025
4
-- Module Name: WaveformGenerator
5
-- Description:
6
--      Simple ROM-based Waveform Generator Module handling Sine, Triangle, Sawtooth and Square waveform according to the selection signal.
7
--      Note that the selection signal can be updated at any time, the waveform output will immediatly switch to the selected waveform type.
8
--      The Waveform Output Frequency is defined by (i_sys_clock_freq / 2^rom_addr_bits).
9
--
10
-- Generics
11
--              rom_addr_bits: ROM Address Bits length
12
--              rom_data_bits: ROM Data Bits length
13
-- Ports
14
--              Input   -       i_sys_clock: System Input Clock
15
--              Input   -       i_waveform_select: Waveform Generator Type Selector ("00": Sine, "01": Triangle, "10": Sawtooth, "11": Square)
16
--              Input   -       i_waveform_step: Waveform Step Value (Value Range: [0;2^rom_addr_bits -1])
17
--              Output  -       o_waveform: Waveform Signal Ouput Value (Value Range: [0;2^rom_data_bits -1])
18
------------------------------------------------------------------------
19
 
20
LIBRARY IEEE;
21
USE IEEE.STD_LOGIC_1164.ALL;
22
USE IEEE.NUMERIC_STD.ALL;
23
USE IEEE.MATH_REAL.ALL;
24
 
25
ENTITY WaveformGenerator is
26
 
27
GENERIC(
28
        rom_addr_bits: INTEGER range 1 to 30 := 8;
29
        rom_data_bits: INTEGER range 1 to 31 := 8
30
);
31
 
32
PORT(
33
        i_sys_clock: IN STD_LOGIC;
34
    i_waveform_select: IN STD_LOGIC_VECTOR(1 downto 0);
35
    i_waveform_step: IN UNSIGNED(rom_addr_bits-1 downto 0);
36
        o_waveform: OUT UNSIGNED(rom_data_bits-1 downto 0)
37
);
38
 
39
END WaveformGenerator;
40
 
41
ARCHITECTURE Behavioral of WaveformGenerator is
42
 
43
------------------------------------------------------------------------
44
-- Constant Declarations
45
------------------------------------------------------------------------
46
-- ROM Type
47
type rom_type is array(INTEGER range 0 to 2**rom_addr_bits -1) of UNSIGNED(rom_data_bits-1 downto 0);
48
 
49
-- Sine ROM Initialization
50
function sine_rom_initialization return rom_type is
51
constant period: real := real((2.0 * MATH_PI) / 2.0**rom_addr_bits);
52
variable angle: real;
53
variable rom_angle: real;
54
variable rom_temp: rom_type;
55
begin
56
 
57
    for addr in INTEGER range 0 to 2**rom_addr_bits -1 loop
58
        -- Compute Angle from ROM Address
59
        angle := real(addr) * period;
60
 
61
        -- Scale ROM Angle
62
        rom_angle := (1.0 + sin(angle)) * (2.0**rom_data_bits - 1.0) / 2.0;
63
 
64
        -- Convert ROM Angle into UNSIGNED and Add to Memory
65
        rom_temp(addr) := TO_UNSIGNED(INTEGER(round(rom_angle)), rom_data_bits);
66
    end loop;
67
 
68
    return rom_temp;
69
end sine_rom_initialization;
70
 
71
-- Triangle ROM Initialization
72
function triangle_rom_initialization return rom_type is
73
    constant period: real := real(2**rom_addr_bits);
74
    variable angle: real;
75
    variable rom_angle: real;
76
    variable rom_temp: rom_type;
77
    begin
78
 
79
        for addr in INTEGER range 0 to 2**rom_addr_bits -1 loop
80
            -- Compute Angle from ROM Address
81
            angle := 2.0 * abs( (real(addr)/period) - floor( (real(addr)/period) + (1.0/2.0) ) );
82
 
83
            -- Scale ROM Angle
84
            rom_angle := angle * (2.0**rom_data_bits - 1.0);
85
 
86
            -- Convert ROM Angle into UNSIGNED and Add to Memory
87
            rom_temp(addr) := TO_UNSIGNED(INTEGER(round(rom_angle)), rom_data_bits);
88
        end loop;
89
 
90
        return rom_temp;
91
end triangle_rom_initialization;
92
 
93
-- Sawtooth ROM Initialization
94
function sawtooth_rom_initialization return rom_type is
95
    variable rom_angle: real;
96
    variable rom_temp: rom_type;
97
    begin
98
 
99
        for addr in INTEGER range 0 to 2**rom_addr_bits -1 loop
100
            -- Compute ROM Angle from ROM Address & Scale it
101
            rom_angle := round( real(addr) * ((2.0**rom_data_bits -1.0) / (2.0**rom_addr_bits -1.0)) );
102
 
103
            -- Convert ROM Angle into UNSIGNED and Add to Memory
104
            rom_temp(addr) := TO_UNSIGNED(INTEGER(round(rom_angle)), rom_data_bits);
105
        end loop;
106
 
107
        return rom_temp;
108
end sawtooth_rom_initialization;
109
 
110
-- ROM Memories
111
constant SINE_ROM: rom_type := sine_rom_initialization;
112
constant TRIANGLE_ROM: rom_type := triangle_rom_initialization;
113
constant SAWTOOTH_ROM: rom_type := sawtooth_rom_initialization;
114
 
115
-- Max ROM Address
116
constant ROM_ADDR_MAX: UNSIGNED(rom_addr_bits -1 downto 0) := (others => '1');
117
 
118
-- Waveform Types (Sine, Triangle, Sawtooth and Square)
119
constant SINE_WAVEFORM: STD_LOGIC_VECTOR(1 downto 0) := "00";
120
constant TRIANGLE_WAVEFORM: STD_LOGIC_VECTOR(1 downto 0) := "01";
121
constant SAWTOOTH_WAVEFORM: STD_LOGIC_VECTOR(1 downto 0) := "10";
122
 
123
------------------------------------------------------------------------
124
-- Signal Declarations
125
------------------------------------------------------------------------
126
-- Waveform Selector Register
127
signal waveform_select_reg: STD_LOGIC_VECTOR(1 downto 0) := (others => '0');
128
 
129
-- Waveform Output Register
130
signal waveform_output_reg: UNSIGNED(rom_data_bits-1 downto 0) := (others => '0');
131
 
132
------------------------------------------------------------------------
133
-- Module Implementation
134
------------------------------------------------------------------------
135
begin
136
 
137
        -------------------------------------
138
        -- Waveform Selector Input Handler --
139
        -------------------------------------
140
        process(i_sys_clock)
141
        begin
142
                if rising_edge(i_sys_clock) then
143
 
144
                        -- Apply New Selected Waveform Type
145
                        waveform_select_reg <= i_waveform_select;
146
                end if;
147
        end process;
148
 
149
    -----------------------
150
        -- Waveform Selector --
151
        -----------------------
152
        process(i_sys_clock)
153
        begin
154
                if rising_edge(i_sys_clock) then
155
 
156
            -- Waveform 0: Sine
157
            if (waveform_select_reg = SINE_WAVEFORM) then
158
                waveform_output_reg <= SINE_ROM(TO_INTEGER(i_waveform_step));
159
 
160
            -- Waveform 1: Triangle
161
            elsif (waveform_select_reg = TRIANGLE_WAVEFORM) then
162
                waveform_output_reg <= TRIANGLE_ROM(TO_INTEGER(i_waveform_step));
163
 
164
            -- Waveform 2: Sawtooth
165
            elsif (waveform_select_reg = SAWTOOTH_WAVEFORM) then
166
                waveform_output_reg <= SAWTOOTH_ROM(TO_INTEGER(i_waveform_step));
167
 
168
            -- Waveform 3: Square
169
            else
170
                -- Maximum Value
171
                if (i_waveform_step <= ROM_ADDR_MAX/2) then
172
                    waveform_output_reg <= (others => '1');
173
 
174
                -- Minimum Value
175
                else
176
                    waveform_output_reg <= (others => '0');
177
                end if;
178
            end if;
179
                end if;
180
        end process;
181
    o_waveform <= waveform_output_reg;
182
 
183
end Behavioral;

powered by: WebSVN 2.1.0

© copyright 1999-2025 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.