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

Subversion Repositories vhld_tb

[/] [vhld_tb/] [trunk/] [examples/] [packet_gen/] [vhdl/] [packet_gen.vhd] - Blame information for rev 19

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 19 sckoarn
----------------
2
--  simple packet generator
3
--
4
------------------------------------------------------------------------------
5
--  First we start of with the definition of the packet array type
6
--    and the pack_out record for pins on the entity and comp.
7
--  The size of the whole system can be changed by changing the
8
--    array and record types.
9
library IEEE;
10
use IEEE.STD_LOGIC_1164.all;
11
 
12
package pgen is
13
 
14
  type arr128x8 is array(0 to 127) of std_logic_vector(7 downto 0);
15
 
16
  type pack_out is record
17
    dout  :  arr128x8;
18
    drdy  :  std_logic;
19
  end record;
20
end package pgen;
21
 
22
------------------------------------------------------------------------------
23
-- this is an example packet generator for BFM's
24
--  for details of the full functionality, see the accomaning documentation
25
--
26
--  the packet_gen implementation demonstrates:
27
--    self generating data, incrementing and random
28
--    data loading from a file and file opening
29
--    setting a text entity from the stimulus file, i.e. the file name
30
--    direct setting of text data from the stimulus file.
31
--    use of the new stimulus port definition.
32
library IEEE;
33
use IEEE.STD_LOGIC_1164.all;
34
use IEEE.STD_LOGIC_ARITH.all;
35
use std.textio.all;
36
use work.tb_pkg.all;
37
library synthworks;
38
  use SynthWorks.RandomBasePkg.all;
39
  use SynthWorks.RandomPkg.all;
40
use work.pgen.all;
41
 
42
entity packet_gen is
43
  generic (
44
    pgen_id   :   integer := 0
45
  );
46
  port (
47
        packet_out  : out pack_out;
48
        request     : in  std_logic;
49
        fname       : in  stm_text;
50
        --  env access port
51
        STM_IN       : in    stm_sctl;
52
        STM_OUT      : out   stm_sack
53
    );
54
end packet_gen;
55
 
56
architecture bhv of packet_gen is
57
 
58
  -- create the file handle for loading data from file.
59
  file load_file  :  text;
60
 
61
  -----------------------------------------------------------------------------
62
  -- driven by STIM_access
63
  signal stim_addr:       std_logic_vector(31 downto 0);
64
  signal stim_write_dat:  std_logic_vector(31 downto 0);
65
  signal rd_req:          std_logic  := '0';
66
  signal wr_req:          std_logic  := '0';
67
  -----------------------------------------------------------------------------
68
  -- driven by REG_access
69
  signal stim_read_dat:   std_logic_vector(31 downto 0);
70
  signal req_ack:         std_logic  := '0';
71
  signal open_lfile    :  std_logic  := '0';
72
  -- the addressable register set
73
  signal cnt_reg:         std_logic_vector(31 downto 0);
74
  signal seed_reg:        std_logic_vector(31 downto 0) := "00010001000111000011000010000100";
75
  signal config_reg:      std_logic_vector(31 downto 0);
76
  signal errors_reg:      std_logic_vector(31 downto 0);
77
  signal stm_idx        : integer;
78
  signal stm_wdata      : std_logic_vector(7 downto 0);
79
  signal stm_w          : std_logic;
80
 
81
  signal clear_trig:      std_logic  := '0';
82
  signal ready          : std_logic;
83
 
84
 
85
begin
86
 
87
output_drive:
88
  process (STM_IN.rst_n, seed_reg, request, open_lfile, stm_w)
89
    variable v_dat_array : arr128x8;  --<< array type from pgen package
90
    variable v_tmp_dat   : unsigned(7 downto 0);
91
    variable v_randv     : RandomPType;
92
    variable v_tmp_int   : integer;
93
    variable v_stat      : file_open_status;
94
    variable rline       : line;
95
    variable j           : integer;
96
    variable incp        : std_logic;
97
    variable v_fisopen     : boolean := false;
98
  begin
99
    -- if we get a request and are enabled
100
    if((STM_IN.rst_n'event and STM_IN.rst_n = '0') or seed_reg'event) then
101
      v_tmp_int  :=  to_uninteger(seed_reg);
102
      v_randv.InitSeed(v_tmp_int);
103
      packet_out.dout  <= (others => (others => '0'));
104
      packet_out.drdy  <=  '0';
105
      incp             :=  '0';
106
      if(v_fisopen = true) then
107
        file_close(load_file);
108
        v_fisopen  := false;
109
      end if;
110
    elsif(request'event and request = '1' and cnt_reg(0) = '1') then
111
      case config_reg(3 downto 0) is
112
        -- inc pattern
113
        when "0000" =>
114
          if(incp  = '0') then
115
            v_tmp_dat  :=  (others => '0');
116
            for i in 0 to v_dat_array'length-1 loop
117
              v_dat_array(i) := std_logic_vector(v_tmp_dat);
118
              v_tmp_dat  :=  v_tmp_dat + 1;
119
            end loop;
120
            incp             :=  '1';
121
          end if;
122
        -- random pattern
123
        when "0001" =>
124
          v_tmp_dat  :=  (others => '0');
125
          for i in 0 to v_dat_array'length-1 loop
126
--            v_tmp_int  :=  v_randv.RandInt(0, 255);
127
            v_dat_array(i) := std_logic_vector(conv_unsigned(v_randv.RandInt(0, 255),8));
128
          end loop;
129
          incp             :=  '0';
130
        -- file load
131
        when "0010" =>
132
          j :=  0;
133
          while(not endfile(load_file) and j < v_dat_array'length-1) loop
134
            readline(load_file, rline);
135
            v_dat_array(j)(7 downto 4) :=  c2std_vec(rline(1));
136
            v_dat_array(j)(3 downto 0) :=  c2std_vec(rline(2));
137
            j  :=  j + 1;
138
          end loop;
139
          incp             :=  '0';
140
        -- user input mode, do not generate as user filled through stimulus
141
        when "0011" =>
142
          null;
143
          incp             :=  '0';
144
        when others =>
145
          -- do an assert here
146
          assert(false)
147
            report "Invalid control mode for Patern Generator, nothing done." & LF
148
          severity note;
149
      end case;
150
      packet_out.dout  <=  v_dat_array;
151
    -- if there was an open file event
152
    elsif(open_lfile'event and open_lfile = '1') then
153
      -- if a file is open, close it first
154
      if(v_fisopen = true) then
155
        file_close(load_file);
156
      end if;
157
      -- open the file
158
      file_open(v_stat, load_file, fname, read_mode);
159
      assert(v_stat = open_ok)
160
        report LF & "Error: Unable to open data file  " & fname
161
      severity failure;
162
      v_fisopen  := true;
163
    -- if there was a stumuls write, write the array index
164
    elsif(stm_w'event and stm_w = '1') then
165
        v_dat_array(stm_idx) := stm_wdata;
166
    end if;
167
end process output_drive;
168
 
169
-------------------------------------------------------------------------------
170
-------------------------------------------------------------------------------
171
-- STIM Reg Access process
172
REG_access:
173
  process
174
 
175
    variable v_temp_int: integer;
176
    variable v_reload:   integer  := 0;
177
    variable v_tmp_int:  integer;
178
 
179
  begin
180
    -- reset from stimulus system
181
    if(STM_IN.rst_n'event and STM_IN.rst_n = '0') then
182
      v_reload        := 0;
183
      stm_w           <= '0';
184
      -- standard registers
185
      stim_read_dat   <= (others => '0');
186
      req_ack         <=  '0';
187
      cnt_reg         <= (others => '0');
188
      config_reg      <= (others => '0');
189
      errors_reg      <= (others => '0');
190
 
191
    -- if is a write access
192
    elsif(wr_req' event and wr_req = '1') then
193
      -- create index 0 to 63
194
      v_temp_int := conv_integer(unsigned(stim_addr(6 downto 0)));
195
      -- create first level of addressing
196
      case stim_addr(31 downto 12) is
197
        -- first level decode
198
        when "00000000000000000000" =>
199
          -- create register access level of addressing
200
          -- seconde level of decode
201
          case stim_addr(11 downto 0) is
202
            when "000000000000" =>
203
              cnt_reg     <=  stim_write_dat;
204
              open_lfile  <=  stim_write_dat(1);
205
            when "000000000001" =>
206
              config_reg  <=  stim_write_dat;
207
            when "000000000010" =>
208
              assert(false)
209
                report ">>>> ERROR:  The errors register is read only!!" & LF
210
              severity note;
211
--              errors_reg  <=  stim_write_dat;
212
            when "000000000011" =>
213
              seed_reg    <=  stim_write_dat;
214
 
215
--            when "000000000100" =>
216
--              access0_word   <=  stim_write_dat;
217
--              action_trig    <=  '1';
218
--            when "000000000101" =>
219
--              access1_word   <=  stim_write_dat;
220
 
221
            when others =>
222
              assert(false)
223
                report "Out of bounds write attempt in packet_gen " & integer'image(pgen_id) &
224
                   ", noting done." & LF
225
              severity note;
226
          end case;
227
        -- array addressing
228
        when "00000000000000000001" =>
229
          if(stim_addr(11 downto 7) /= "00000") then
230
            assert(false)
231
              report "Out of bounds write attempt in packet_gen " & integer'image(pgen_id) &
232
                   ", noting done." & LF
233
            severity note;
234
          else
235
            stm_idx  <=  v_temp_int;
236
            stm_wdata <=  stim_write_dat(7 downto 0);
237
            stm_w       <=  '1';
238
          end if;
239
        when others =>
240
          assert(false)
241
            report "Out of bounds write attempt in packet_gen " & integer'image(pgen_id) &
242
                   ", noting done." & LF
243
          severity note;
244
      end case;
245
      -- acknowlage the request
246
      req_ack  <=  '1';
247
      wait until wr_req'event and wr_req = '0';
248
      req_ack  <=  '0';
249
 
250
    -- if is a read
251
    elsif (rd_req' event and rd_req = '1') then
252
      -- create first level of addressing
253
      case stim_addr(31 downto 12) is
254
        -- first level decode
255
        when "00000000000000000000" =>
256
          -- create register access level of addressing
257
          -- seconde level of decode
258
          case stim_addr(11 downto 0) is
259
             when "000000000010" =>
260
               stim_read_dat  <=  errors_reg;
261
               errors_reg     <=  (others => '0');
262
             when "000000000011" =>
263
               stim_read_dat  <= seed_reg;
264
 
265
             when others =>
266
               assert(false)
267
                 report "Read Location access ERROR: packet_gen" & integer'image(pgen_id) &
268
                   ", noting done." & LF
269
               severity note;
270
           end case;
271
        when others =>
272
          assert(false)
273
            report "Read Location access ERROR: packet_gen" & integer'image(pgen_id) &
274
                   ", noting done." & LF
275
          severity note;
276
      end case;
277
      -- acknowlage the request
278
      req_ack  <=  '1';
279
      wait until rd_req'event and rd_req = '0';
280
      req_ack  <=  '0';
281
 
282
    end if;
283
    --  clear the trigger signals
284
    cnt_reg(1)  <=  '0';
285
    open_lfile  <=  '0';
286
    stm_w       <=  '0';
287
 
288
    wait on rd_req, wr_req, STM_IN.rst_n, clear_trig;
289
  end process REG_access;
290
 
291
-------------------------------------------------------------------------------
292
-- STIM Access port processes
293
--
294
STIM_access:
295
  process
296
  begin
297
    if(STM_IN.rst_n' event and STM_IN.rst_n = '0') then
298
      STM_OUT   <=   stm_neut;
299
    -- if read cycle
300
    elsif(STM_IN.req_n' event and STM_IN.req_n  = '0' and STM_IN.rwn = '1') then
301
      stim_addr      <=  STM_IN.addr;
302
      rd_req         <=  '1';
303
      wait until req_ack' event and req_ack = '1';
304
      STM_OUT.rdat       <=   stim_read_dat;
305
      rd_req         <=  '0';
306
      wait for 1 ps;
307
      STM_OUT.ack_n  <=  '0';
308
      wait until STM_IN.req_n' event and STM_IN.req_n = '1';
309
      wait for 1 ps;
310
      STM_OUT  <=  stm_neut;
311
 
312
    -- if Write
313
    elsif(STM_IN.req_n' event and STM_IN.req_n  = '0' and STM_IN.rwn = '0') then
314
      stim_addr      <=  STM_IN.addr;
315
      stim_write_dat <=  STM_IN.wdat;
316
      wr_req         <=  '1';
317
      wait until req_ack' event and req_ack = '1';
318
      wait for 1 ps;
319
      wr_req         <=  '0';
320
      wait for 1 ps;
321
      STM_OUT.ack_n  <=  '0';
322
      wait until STM_IN.req_n' event and STM_IN.req_n = '1';
323
      wait for 1 ps;
324
      STM_OUT  <=  stm_neut;
325
    end if;
326
 
327
    STM_OUT.rdy_n   <=  ready;
328
    wait on STM_IN.req_n, STM_IN.rst_n, ready;
329
  end process STIM_access;
330
 
331
end bhv;

powered by: WebSVN 2.1.0

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