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

Subversion Repositories core_arm

[/] [core_arm/] [trunk/] [vhdl/] [bus/] [ahbmst_mp.vhd] - Blame information for rev 4

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 tarookumic
-- $(lic)
2
-- $(help_generic)
3
-- $(help_local)
4
 
5
library IEEE;
6
use IEEE.std_logic_1164.all;
7
use IEEE.std_logic_unsigned."+";
8
use IEEE.std_logic_arith.conv_unsigned;
9
use work.amba.all;
10
use work.memdef.all;
11
use work.int.all;
12
use work.bus_comp.all;
13
 
14
entity ahbmst_mp is
15
  generic ( AHBMST_PORTS : integer := 4 );
16
  port (
17
    rst   : in  std_logic;
18
    clk   : in  std_logic;
19
    i     : in  ahbmst_mp_in_a(AHBMST_PORTS-1 downto 0);
20
    o     : out ahbmst_mp_out_a(AHBMST_PORTS-1 downto 0);
21
    ahbi  : in  ahb_mst_in_type;
22
    ahbo  : out ahb_mst_out_type
23
  );
24
end;
25
 
26
architecture rtl of ahbmst_mp is
27
 
28
  constant AHBMST_PORTS_BITSZ : integer := lin_log2x(AHBMST_PORTS);
29
  constant NBO_ZERO : std_logic_vector(AHBMST_PORTS-1 downto 0) := (others => '0');
30
 
31
  type ahbmst_mp_tmp_type is record
32
    ahbo   : ahb_mst_out_type;
33
    bo_i,nbo_i   : integer;
34
    o_ready, o_grant, o_mexc : std_logic_vector(AHBMST_PORTS-1 downto 0);
35
    o_retry, o_cache, hold, nboreq : std_logic_vector(AHBMST_PORTS-1 downto 0);
36
    nbo : std_logic_vector(AHBMST_PORTS_BITSZ-1 downto 0);
37
    num : std_logic_vector(AHBMST_PORTS_BITSZ-1 downto 0);
38
  end record;
39
  type ahbmst_mp_reg_type is record
40
     retry, cache : std_logic;
41
     bo    : std_logic_vector(AHBMST_PORTS_BITSZ-1 downto 0);
42
     ba, bg : std_logic;
43
  end record;
44
  type ahbmst_mp_dbg_type is record
45
     dummy : std_logic;
46
     -- pragma translate_off
47
     dbg : ahbmst_mp_tmp_type;
48
     -- pragma translate_on
49
  end record;
50
  signal r, c       : ahbmst_mp_reg_type;
51
  signal rdbg, cdbg : ahbmst_mp_dbg_type;
52
 
53
begin
54
 
55
  p0 : process(ahbi, r, rst, i)
56
    variable v    : ahbmst_mp_reg_type;
57
    variable t    : ahbmst_mp_tmp_type;
58
    variable vdbg : ahbmst_mp_dbg_type;
59
  begin
60
 
61
    -- $(init(t:ahbmst_mp_tmp_type))
62
 
63
    v := r;
64
 
65
    t.o_ready := (others => '0');
66
    t.o_grant := (others => '0');
67
    t.o_retry := (others => '0');
68
    t.o_cache := (others => '0');
69
    t.o_mexc := (others => '0');
70
 
71
    -- owner hold 
72
    t.num := (others => '0');
73
    t.hold := (others => '0');
74
    for j in AHBMST_PORTS-1 downto 0 loop
75
      t.num := std_logic_vector(conv_unsigned(j, AHBMST_PORTS_BITSZ));
76
      if (r.ba = '1') and
77
         (i(j).req = '1') and
78
         (r.bo = t.num) then
79
        t.hold(j) := '1';
80
      end if;
81
    end loop;  -- i
82
 
83
    -- next bus owner req
84
    for k in AHBMST_PORTS-1 downto 0 loop
85
      t.nboreq(k) := i(k).req;
86
      for j in AHBMST_PORTS-1 downto 0 loop
87
        if k /= j then
88
          if t.hold(j) = '1' then
89
            t.nboreq(k) := '0';
90
          end if;
91
        end if;
92
      end loop;
93
    end loop;
94
 
95
    -- priority 
96
    t.nbo_i := 0;
97
l1: for j in AHBMST_PORTS-1 downto 0 loop
98
      if t.nboreq(j) = '1' then
99
        t.nbo_i := j;
100
        exit l1;
101
      end if;
102
    end loop;
103
 
104
    -- lock (only per ahb)
105
    t.ahbo.hlock := '0';
106
    for j in AHBMST_PORTS-1 downto 0 loop
107
      if i(j).lock = '1' then
108
        t.ahbo.hlock := '1';
109
      end if;
110
    end loop;
111
 
112
    -- ahb signals
113
    t.ahbo.hbusreq := '0';
114
    t.ahbo.htrans  := HTRANS_IDLE;
115
    t.ahbo.haddr   := i(0).address;
116
 
117
    if not (t.nboreq = NBO_ZERO) then
118
 
119
      t.nbo := std_logic_vector(conv_unsigned(t.nbo_i, AHBMST_PORTS_BITSZ));
120
      t.ahbo.hbusreq := i(t.nbo_i).req;
121
      t.ahbo.haddr   := i(t.nbo_i).address;
122
      t.ahbo.htrans  := HTRANS_NONSEQ;
123
      t.ahbo.hwrite  := not i(t.nbo_i).read;
124
      t.ahbo.hsize   := lmd_toamba(i(t.nbo_i).size);
125
      t.ahbo.hburst := HBURST_SINGLE;
126
      if i(t.nbo_i).burst = '1' then
127
        t.ahbo.hburst := HBURST_INCR;
128
      end if;
129
 
130
      -- burst
131
      if (r.bo = t.nbo) then
132
        if (i(t.nbo_i).req = '1') and (r.ba = '1')  then
133
          if ((not r.retry) = '1') then
134
            if i(t.nbo_i).burst = '1' then
135
              t.ahbo.htrans := HTRANS_SEQ;
136
              -- todo: 1k boundary check
137
              t.ahbo.hburst := HBURST_INCR;
138
            end if;
139
          end if;
140
        end if;
141
      end if;
142
 
143
      -- grant
144
      if (r.bg = '1') then
145
        if (ahbi.hready = '1') and (i(t.nbo_i).req = '1') then
146
          if ((not r.retry) = '1') then
147
            t.o_grant(t.nbo_i) := '1';
148
          end if;
149
        end if;
150
      end if;
151
 
152
    end if;
153
 
154
    -- retry
155
    v.retry := '0';
156
    if (r.ba = '1') and
157
       ((ahbi.hresp = HRESP_RETRY) or
158
        (ahbi.hresp = HRESP_SPLIT))
159
    then
160
      v.retry := not ahbi.hready;
161
    end if;
162
    if r.retry = '1' then
163
      t.ahbo.htrans := HTRANS_IDLE;
164
    end if;
165
 
166
    -- ahb return
167
    t.bo_i := lin_convint(r.bo);
168
    t.ahbo.hwdata := i(t.bo_i).data;
169
    if r.ba = '1' then
170
      t.o_cache(t.bo_i) := r.cache;
171
      if ahbi.hready = '1' then
172
        case ahbi.hresp is
173
          when HRESP_OKAY => t.o_ready(t.bo_i) := '1';
174
          when HRESP_RETRY | HRESP_SPLIT=> t.o_retry(t.bo_i) := '1';
175
          when others => t.o_ready(t.bo_i) := '1'; t.o_mexc(t.bo_i) := '1';
176
        end case;
177
      end if;
178
    end if;
179
 
180
    -- next
181
    if ahbi.hready = '1' then
182
      v.bo := t.nbo;
183
      v.bg := ahbi.hgrant;
184
      v.ba := '0';
185
      if (t.ahbo.htrans = HTRANS_NONSEQ) or (t.ahbo.htrans = HTRANS_SEQ) then
186
        v.ba := r.bg;
187
      end if;
188
    end if;
189
 
190
    -- reset
191
    if rst = '0' then
192
      v.retry := '0';
193
      v.cache := '0';
194
      v.bo := (others => '0');
195
      v.ba := '0';
196
      v.bg := '0';
197
    end if;
198
 
199
    c <= v;
200
 
201
    for i in AHBMST_PORTS-1 downto 0 loop
202
      o(i).grant <= t.o_grant(i);
203
      o(i).ready <= t.o_ready(i);
204
      o(i).mexc <=  t.o_mexc(i);
205
      o(i).retry <= t.o_retry(i);
206
      o(i).data  <= ahbi.hrdata;
207
    end loop;
208
 
209
    ahbo   <= t.ahbo;
210
 
211
    -- pragma translate_off
212
    vdbg := rdbg;
213
    vdbg.dbg := t;
214
    cdbg <= vdbg;
215
    -- pragma translate_on  end process p0;
216
 
217
  end process p0;
218
 
219
 
220
  pregs : process (clk, c)
221
  begin
222
    if rising_edge(clk) then
223
      r <= c;
224
      -- pragma translate_off
225
      rdbg <= cdbg;
226
      -- pragma translate_on
227
    end if;
228
  end process;
229
 
230
 
231
end;
232
 
233
 
234
 
235
 
236
 
237
 
238
 
239
 
240
 
241
 
242
 
243
 
244
 
245
 

powered by: WebSVN 2.1.0

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