~ruther/vhdl-i2c

ref: cb7143c0b0bf4ac603f4e0ddf705e88474afc496 vhdl-i2c/tb/i2c/model/i2c_slave_pkg.vhd -rw-r--r-- 4.0 KiB
cb7143c0 — Rutherther tests: i2c bus model 1 year, 3 months ago
                                                                                
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
library ieee;
use ieee.std_logic_1164.all;

library vunit_lib;
context vunit_lib.vunit_context;
context vunit_lib.com_context;

use work.i2c_bus_pkg;

-- all procedures here take 0 simulation time
-- call i2c_bus_pkg.wait_until_idle to wait
-- until the operation is performed.

package i2c_slave_pkg is

  procedure write (
    signal net : inout network_t;
    constant address  : in std_logic_vector(6 downto 0);
    constant exp_data : in std_logic_vector;
    constant timeout  : in time;
    constant actor    : in actor_t);

  procedure read (
    signal net : inout network_t;
    constant address  : in std_logic_vector(6 downto 0);
    constant data     : in std_logic_vector;
    constant timeout  : in time;
    constant actor : in actor_t);

  procedure write_read (
    signal net : inout network_t;
    constant address  : in std_logic_vector(6 downto 0);
    constant exp_data : in std_logic_vector;
    constant data     : in std_logic_vector;
    constant timeout  : in time;
    constant actor : in actor_t);

end package i2c_slave_pkg;

package body i2c_slave_pkg is

  procedure write (
    signal net : inout network_t;
    constant address  : in std_logic_vector(6 downto 0);
    constant exp_data : in std_logic_vector;
    constant timeout  : in time;
    constant actor    : in actor_t) is
  begin
    if exp_data'length mod 8 /= 0 then
      failure("The number of bits to be written to the slave have to be divisible by 8.");
    end if;

    i2c_bus_pkg.wait_for_start_cond(net, timeout, actor);
    i2c_bus_pkg.check_data(net, address & '0', timeout, actor);

    for i in 0 to exp_data'length/8 - 1 loop
      i2c_bus_pkg.check_data(net, exp_data(exp_data'left - i*8 downto exp_data'left - 7 - i*8), timeout, actor);
      i2c_bus_pkg.send_ack(net, timeout, actor);
    end loop;  -- i

    i2c_bus_pkg.wait_for_stop_cond(net, timeout, actor);
  end procedure write;

  procedure read (
    signal net : inout network_t;
    constant address  : in std_logic_vector(6 downto 0);
    constant data     : in std_logic_vector;
    constant timeout  : in time;
    constant actor    : in actor_t) is
  begin
    if data'length mod 8 /= 0 then
      failure("The number of bits to be read from the slave have to be divisible by 8.");
    end if;

    i2c_bus_pkg.wait_for_start_cond(net, timeout, actor);
    i2c_bus_pkg.check_data(net, address & '1', timeout, actor);

    for i in 0 to data'length/8 - 1 loop
      i2c_bus_pkg.send_data(net, data(data'left - i*8 downto data'left - 7 - i*8), timeout, actor);
      i2c_bus_pkg.check_ack(net, '1', timeout, actor);
    end loop;  -- i

    i2c_bus_pkg.wait_for_stop_cond(net, timeout, actor);
  end procedure read;

  procedure write_read (
    signal net : inout network_t;
    constant address  : in std_logic_vector(6 downto 0);
    constant exp_data : in std_logic_vector;
    constant data     : in std_logic_vector;
    constant timeout  : in time;
    constant actor : in actor_t) is
  begin
    if exp_data'length mod 8 /= 0 then
      failure("The number of bits to be written to the slave have to be divisible by 8.");
    end if;
    if data'length mod 8 /= 0 then
      failure("The number of bits to be read from the slave have to be divisible by 8.");
    end if;

    i2c_bus_pkg.wait_for_start_cond(net, timeout, actor);
    i2c_bus_pkg.send_data_and_clock(net, address & '0', timeout, actor);

    for i in 0 to exp_data'length/8 - 1 loop
      i2c_bus_pkg.check_data(net, exp_data(exp_data'left - i*8 downto exp_data'left - 7 - i*8), timeout, actor);
      i2c_bus_pkg.send_ack(net, timeout, actor);
    end loop;  -- i

    i2c_bus_pkg.wait_for_start_cond(net, timeout, actor);
    i2c_bus_pkg.send_data_and_clock(net, address & '1', timeout, actor);

    for i in 0 to data'length/8 - 1 loop
      i2c_bus_pkg.send_data(net, data(data'left - i*8 downto data'left - 7 - i*8), timeout, actor);
      i2c_bus_pkg.check_ack(net, '1', timeout, actor);
    end loop;  -- i

    i2c_bus_pkg.wait_for_stop_cond(net, timeout, actor);
  end procedure write_read;


end package body i2c_slave_pkg;
Do not follow this link