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

Subversion Repositories core_arm

[/] [core_arm/] [trunk/] [vhdl/] [arm/] [armiu_rrstg.vhd] - Blame information for rev 2

Go to most recent revision | 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 work.leon_config.all;
8
use work.leon_iface.all;
9
use work.tech_map.all;
10
use work.int.all;
11
use work.armpmodel.all;
12
use work.armdebug.all;
13
use work.armdecode.all;
14
use work.armpctrl.all;
15
use work.arm_comp.all;
16
 
17
entity armiu_rrstg is
18
  port (
19
    rst     : in  std_logic;
20
    clk     : in  std_logic;
21
    clkn    : in  std_logic;
22
    i       : in  armiu_rrstg_typ_in;
23
    o       : out armiu_rrstg_typ_out
24
    );
25
end armiu_rrstg;
26
 
27
architecture rtl of armiu_rrstg is
28
 
29
  -- regfile generic map
30
  constant RRSTG_REGF_ABITS : integer := 5;
31
  constant RRSTG_REGF_COUNT : integer := 32;
32
 
33
  type armiu_fwddata_type_a is array (natural range <>) of std_logic_vector(31 downto 0);
34
  type armiu_rrstg_tmp_type is record
35
    o       : armiu_rrstg_typ_out;
36
    commit : std_logic;
37
    r1_v, r2_v: std_logic_vector(APM_RREAL_U downto APM_RREAL_D);
38
    nextinsn, lock : std_logic;
39
    lock_cpsr, lock_reg : std_logic;  -- dbg
40
 
41
    dr_v : apc_pctrl;
42
    rr : apc_pctrl;
43
    rs : apc_pctrl;
44
    ex : apc_pctrl;
45
    dm : apc_pctrl;
46
    me : apc_pctrl;
47
    wr : apc_pctrl;
48
    fwr1 , fwr2  : armiu_fwddata_type_a(3 downto 0);
49
    fwr1b, fwr2b : std_logic_vector(3 downto 0);
50
    fwr1i, fwr2i : std_logic_vector(1 downto 0);
51
    rfi  : rf_in_type;
52
 
53
    data1, data2 : std_logic_vector(31 downto 0);  -- ld reg lock
54
    locked : std_logic_vector(31 downto 0);  -- ld reg lock
55
 
56
  end record;
57
  type armiu_rrstg_reg_type is record
58
    micro : apc_micro;
59
  end record;
60
  type armiu_rrstg_dbg_type is record
61
     dummy : std_logic;
62
     -- pragma translate_off
63
     dbg : armiu_rrstg_tmp_type;
64
     -- pragma translate_on
65
  end record;
66
  signal r, c       : armiu_rrstg_reg_type;
67
  signal rdbg, cdbg : armiu_rrstg_dbg_type;
68
 
69
  signal rfi  : rf_in_type;
70
  signal rfo  : rf_out_type;
71
 
72
begin
73
 
74
  p0: process (clk, rst, r, i, rfo )
75
    variable v    : armiu_rrstg_reg_type;
76
    variable t    : armiu_rrstg_tmp_type;
77
    variable vdbg : armiu_rrstg_dbg_type;
78
  begin
79
 
80
    -- $(init(t:armiu_rrstg_tmp_type))
81
 
82
    v := r;
83
 
84
    t.commit := not i.flush_v;
85
    t.lock_cpsr := '0';                 -- tmp for dbg
86
 
87
    v := r;
88
    t.dr_v := i.fromDR_micro_v.pctrl;
89
    t.rr := r.micro.pctrl;
90
    t.rs := i.pstate.fromRS_pctrl_r;
91
    t.ex := i.pstate.fromEX_pctrl_r;
92
    t.dm := i.pstate.fromDM_pctrl_r;
93
    t.me := i.pstate.fromME_pctrl_r;
94
    t.wr := i.pstate.fromWR_pctrl_r;
95
 
96
    -- pipeline propagation
97
    t.o.pctrl_r := r.micro.pctrl;
98
    t.o.toRS_pctrl_v := v.micro.pctrl;
99
 
100
    -- register locking
101
    t.lock := '0';
102
    if r.micro.r1_valid = '1' then
103
 
104
      if ( apc_is_rdlocked_by ( r.micro.r1, t.rs ) or
105
           apc_is_rdlocked_by ( r.micro.r1, t.ex ) or
106
           apc_is_rdlocked_by ( r.micro.r1, t.dm ) or
107
           apc_is_rdlocked_by ( r.micro.r1, t.me ) ) then
108
        t.lock := r.micro.pctrl.valid;
109
      end if;
110
 
111
      -- rsstg unused for data1  
112
      if (r.micro.r1 = t.rs.wr.wrop_rd) and apc_is_rdfromalu(t.rs) then
113
        t.o.toRS_pctrl_v.rs.rsop_op1_src := apc_opsrc_alures;
114
      end if;
115
 
116
    end if;
117
    if r.micro.r2_valid = '1' then
118
 
119
      if ( apc_is_rdlocked_by ( r.micro.r2, t.rs ) or
120
           apc_is_rdlocked_by ( r.micro.r2, t.ex ) or
121
           apc_is_rdlocked_by ( r.micro.r2, t.dm ) or
122
           apc_is_rdlocked_by ( r.micro.r2, t.me ) ) then
123
        t.lock := r.micro.pctrl.valid;
124
      end if;
125
 
126
      -- lock rsstg alu forward only on data2 shieft
127
      if (r.micro.r2 = t.rs.wr.wrop_rd) and apc_is_rdfromalu(t.rs) then
128
        if  apc_is_rswillshieft(t.rr) then
129
          t.lock := r.micro.pctrl.valid;
130
        else
131
          -- no shiefting, rsstg unused
132
          t.o.toRS_pctrl_v.rs.rsop_op2_src := apc_opsrc_alures;
133
        end if;
134
      end if;
135
    end if;
136
 
137
    t.lock_reg := t.lock;             -- tmp for dbg
138
 
139
    -- cpsr locking
140
    if apc_is_usecpsr(t.rr) then
141
      if apc_is_exwillsetcpsr(t.rs) then
142
        t.lock := r.micro.pctrl.valid;
143
        t.lock_cpsr := r.micro.pctrl.valid;             -- tmp for dbg
144
      end if;
145
    end if;
146
 
147
    if i.fromCPEX_lock = '1' then
148
      t.lock := '1';
149
    end if;
150
 
151
    -- forwarding r1
152
    t.fwr1b := (others => '0');
153
    if ( r.micro.r1 = t.ex.wr.wrop_rd ) and apc_is_rdfromalu (t.ex) then t.fwr1b(0) := '1'; end if;
154
    if ( r.micro.r1 = t.dm.wr.wrop_rd ) and apc_is_rdfromalu (t.dm) then t.fwr1b(1) := '1'; end if;
155
    if ( r.micro.r1 = t.me.wr.wrop_rd ) and apc_is_rdfromalu (t.me) then t.fwr1b(2) := '1'; end if;
156
    if ( r.micro.r1 = t.wr.wr.wrop_rd ) and apc_is_rdfromalu (t.wr) then t.fwr1b(3) := '1'; end if;
157
 
158
    t.fwr1(0) := i.fromEX_alures_v;
159
    t.fwr1(1) := t.dm.data1;
160
    t.fwr1(2) := t.me.data1;
161
    t.fwr1(3) := t.wr.data1;
162
 
163
    -- priority encoder r1
164
    t.fwr1i(0) := (t.fwr1b(3) and not ( t.fwr1b(2) or t.fwr1b(1) or t.fwr1b(0))) or
165
                  (t.fwr1b(1) and not t.fwr1b(0));
166
    t.fwr1i(1) := (t.fwr1b(2) or t.fwr1b(3)) and not
167
                  (t.fwr1b(0) or t.fwr1b(1));
168
 
169
    if r.micro.r1 = APM_RREAL_PC then
170
      t.data1 := r.micro.pctrl.insn.pc_8;             -- pc + 8
171
    else
172
      if t.fwr1b = "0000" then
173
        t.data1 := rfo.data1;                      -- no forward
174
      else
175
        t.data1 := t.fwr1( lin_convint(t.fwr1i) ); -- forward
176
      end if;
177
    end if;
178
 
179
    -- forwarding r2
180
    t.fwr2b := (others => '0');
181
    if ( r.micro.r2 = t.ex.wr.wrop_rd ) and apc_is_rdfromalu (t.ex) then t.fwr2b(0) := '1'; end if;
182
    if ( r.micro.r2 = t.dm.wr.wrop_rd ) and apc_is_rdfromalu (t.dm) then t.fwr2b(1) := '1'; end if;
183
    if ( r.micro.r2 = t.me.wr.wrop_rd ) and apc_is_rdfromalu (t.me) then t.fwr2b(2) := '1'; end if;
184
    if ( r.micro.r2 = t.wr.wr.wrop_rd ) and apc_is_rdfromalu (t.wr) then t.fwr2b(3) := '1'; end if;
185
 
186
    t.fwr2(0) := i.fromEX_alures_v;
187
    t.fwr2(1) := t.dm.data1;
188
    t.fwr2(2) := t.me.data1;
189
    t.fwr2(3) := t.wr.data1;
190
 
191
    -- priority encoder r2
192
    t.fwr2i(0) := (t.fwr2b(3) and not ( t.fwr2b(2) or t.fwr2b(1) or t.fwr2b(0))) or
193
                  (t.fwr2b(1) and not t.fwr2b(0));
194
    t.fwr2i(1) := (t.fwr2b(2) or t.fwr2b(3)) and not
195
                  (t.fwr2b(0) or t.fwr2b(1));
196
 
197
    if r.micro.r2 = APM_RREAL_PC then
198
      t.data2 := r.micro.pctrl.insn.pc_8;             -- pc + 8
199
    else
200
      if t.fwr2b = "0000" then
201
        t.data2 := rfo.data2;                      -- no forward
202
      else
203
        t.data2 := t.fwr2( lin_convint(t.fwr2i) ); -- forward
204
      end if;
205
    end if;
206
 
207
    -- pctrl.data1 and pctrl.data2
208
    case r.micro.pctrl.rs.rsop_op1_src is
209
      when apc_opsrc_through => t.o.toRS_pctrl_v.data1 := t.data1;
210
      when apc_opsrc_buf     => t.o.toRS_pctrl_v.data1 := t.data1;
211
      when apc_opsrc_alures  => t.o.toRS_pctrl_v.data1 := t.data1;
212
      when apc_opsrc_none    =>
213
      when others => null;
214
    end case;
215
 
216
    case r.micro.pctrl.rs.rsop_op2_src is
217
      when apc_opsrc_through => t.o.toRS_pctrl_v.data2 := t.data2;
218
      when apc_opsrc_buf     => t.o.toRS_pctrl_v.data2 := t.data2;
219
      when apc_opsrc_alures  => t.o.toRS_pctrl_v.data2 := t.data2;
220
      when apc_opsrc_none    =>
221
      when others => null;
222
    end case;
223
 
224
    case r.micro.pctrl.insn.decinsn is
225
      when type_arm_mrc => t.o.toRS_pctrl_v.data1 := i.fromCPEX_data;
226
                           t.lock := t.lock or i.fromCPEX_lock;
227
      when type_arm_stc => t.o.toRS_pctrl_v.data2 := i.fromCPEX_data;
228
                           t.lock := t.lock or i.fromCPEX_lock;
229
      when others => null;
230
    end case;
231
 
232
    -- pipeline flush
233
    if not (t.commit = '1') then
234
      t.o.toRS_pctrl_v.valid := '0';
235
      t.lock := '0';
236
    end if;
237
 
238
    if t.lock = '1' then
239
      t.o.toRS_pctrl_v.valid := '0';
240
    end if;
241
 
242
    -- reset
243
    if ( rst = '0' ) then
244
    end if;
245
 
246
    if t.lock = '1' then
247
      t.o.toDR_nextmicro_v := '0';
248
    else
249
      t.o.toDR_nextmicro_v := '1';
250
      if i.pstate.hold_r.hold = '0' then
251
        v.micro := i.fromDR_micro_v;
252
        v.micro.pctrl.valid := i.fromDR_micro_v.valid;
253
      end if;
254
    end if;
255
 
256
    -- regfile input
257
    t.rfi.rd1addr := (others => '0');
258
    t.rfi.rd1addr(APM_RREAL_U downto APM_RREAL_D) := r.micro.r1;
259
    t.rfi.rd2addr := (others => '0');
260
    t.rfi.rd2addr(APM_RREAL_U downto APM_RREAL_D) := r.micro.r2;
261
    t.rfi.wraddr  := (others => '0');
262
    t.rfi.wraddr(APM_RREAL_U downto APM_RREAL_D)  := i.fromWR_rd_v;
263
    t.rfi.wrdata  := i.fromWR_rd_data_v;
264
    t.rfi.ren1  := '1';
265
    t.rfi.ren2  := '1';
266
    t.rfi.wren  := i.fromWR_rd_valid_v;
267
 
268
    c <= v;
269
 
270
    o <= t.o;
271
    rfi <= t.rfi;
272
 
273
    -- pragma translate_off
274
    vdbg := rdbg;
275
    vdbg.dbg := t;
276
    cdbg <= vdbg;
277
    -- pragma translate_on  
278
 
279
  end process p0;
280
 
281
  pregs : process (clk, c)
282
  begin
283
    if rising_edge(clk) then
284
      r <= c;
285
      -- pragma translate_off
286
      rdbg <= cdbg;
287
      -- pragma translate_on
288
    end if;
289
  end process;
290
 
291
  rf0 : regfile_iu generic map (RFIMPTYPE, RRSTG_REGF_ABITS, 32, RRSTG_REGF_COUNT)
292
    port map (rst, clk, clkn, rfi, rfo);
293
 
294
end rtl;

powered by: WebSVN 2.1.0

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