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

Subversion Repositories v65c816

[/] [v65c816/] [trunk/] [v65c816.vhd] - Blame information for rev 3

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 Valerio63
----------------------------------------------------------------------
2 3 Valerio63
-- 8/16 bit microprocessor (65C816) VHDL project                    -- 
3 2 Valerio63
-- Full RTL synchronous pipelined architecture                      --
4
-- Project by Valerio Venturi (Italy)                               -- 
5 3 Valerio63
-- Start date: 5/04/2020                                            --
6
-- Last revision: 5/04/2023                                         --
7 2 Valerio63
----------------------------------------------------------------------
8
 
9
 
10 3 Valerio63
 
11 2 Valerio63
You can use the codes given in this website for non-commercial purposes without my permission. But if you are using it for commercial purposes then contact me with the details of your project for my permission.
12
 
13
library IEEE;
14
use IEEE.std_logic_1164.all;                             -- defines std_logic types
15
use IEEE.STD_LOGIC_unsigned.all;
16
use IEEE.STD_LOGIC_arith.all;
17
 
18
-- global architecture 
19
entity v65c816 is
20
  port(     clk0:    in STD_LOGIC;                       -- PHASE0 clock input
21
             res:    in STD_LOGIC;                       -- reset input
22
             irq:    in STD_LOGIC;                       -- interrupt request input
23
             nmi:    in STD_LOGIC;                       -- not maskable interrupt input
24
             rdy:    in STD_LOGIC;                       -- wait state request input (read/write)
25
         rdy_out:   out STD_LOGIC;                       -- CPU in wait state (WAI instruction)
26
                        stp_out:   out STD_LOGIC;                       -- CPU in stop state (STP instruction)
27
              rw:   out STD_LOGIC;                       -- read/write out
28
             vpa:   out STD_LOGIC;                       -- vpa
29
                                 vda:   out STD_LOGIC;                       -- vda
30
                                  ml:   out STD_LOGIC;                       -- ml 
31
              vp:   out STD_LOGIC;                       -- vector pull
32
             ope:   out STD_LOGIC;                       -- microcode end 
33
                                   e:   out STD_LOGIC;                       -- emulation (1)/native mode (0) 
34
                                   m:   out STD_LOGIC;                       -- M status        
35
                                   x:   out STD_LOGIC;                       -- X status        
36
                         op_exp:   out STD_LOGIC;                                 -- two byte instruction running
37
            addr:   out STD_LOGIC_VECTOR(23 downto 0);   -- 16 bit address bus out
38
         data_in:    in STD_LOGIC_VECTOR(7 downto 0);    -- 8 bit input data bus
39
        data_out:   out STD_LOGIC_VECTOR(7 downto 0)     -- 8 bit output data bus
40
--         DEBUG                  
41
--                   a_reg:   out STD_LOGIC_VECTOR(15 downto 0);   -- 16 bit A register
42
--                   x_reg:   out STD_LOGIC_VECTOR(15 downto 0);   -- 16 bit X register
43
--                   y_reg:   out STD_LOGIC_VECTOR(15 downto 0);   -- 16 bit Y register
44
--                   s_reg:   out STD_LOGIC_VECTOR(15 downto 0);   -- 16 bit S register
45
--                       op_reg:   out STD_LOGIC_VECTOR(15 downto 0);   -- 16 bit Operand register        
46
--                   p_reg:   out STD_LOGIC_VECTOR(7 downto 0);    --  8 bit P register
47
--                   k_reg:   out STD_LOGIC_VECTOR(7 downto 0);    --  8 bit K register
48
--                   b_reg:   out STD_LOGIC_VECTOR(7 downto 0);    --  8 bit B register
49
--                   o_reg:   out STD_LOGIC_VECTOR(7 downto 0);    --  8 bit Opcode register
50
--                        mcode:   out STD_LOGIC_VECTOR(3 downto 0)     --  4 bit microcode sequence register
51
      );
52
end v65c816;
53
 
54
architecture struct of v65c816 is
55
  signal          i_res: STD_LOGIC;                      -- internal global reset RES
56
  signal          i_irq: STD_LOGIC;                      -- internal interrupt request IRQ
57
  signal          i_nmi: STD_LOGIC;                      -- internal interrupt request NMI
58
  signal          i_rdy: STD_LOGIC;                      -- internal wait request RDY
59
  signal          e_rdy: STD_LOGIC;                      -- external invertedf RDY
60
  signal           i_vp: STD_LOGIC;                      -- internal VP (vector pull)
61
  signal            int: STD_LOGIC;                      -- internal global interrupt (instruction boundary synchronized)
62
  signal             we: STD_LOGIC;                      -- write enable (combinatorial from PLA)
63
  signal           we_r: STD_LOGIC;                      -- write enable (registered)
64
  signal            ien: STD_LOGIC;                      -- interrupt IRQ enable
65
  signal            emu: STD_LOGIC;                      -- emulation mode
66
  signal    two_byte_op: STD_LOGIC;                      -- two byte instruction
67
 
68
  -- microcode signals (register control)
69
  signal          regop: STD_LOGIC_VECTOR(5 downto 0);   -- register operation microcode
70
  signal           rsel: STD_LOGIC_VECTOR(4 downto 0);   -- register select microcode
71
  signal        a_l_lsb: STD_LOGIC;                      -- A load lsb
72
  signal        a_l_msb: STD_LOGIC;                      -- A load msb
73
  signal          a_dec: STD_LOGIC;                      -- A decrement (MVN/MVP)
74
  signal        x_l_lsb: STD_LOGIC;                      -- X load lsb
75
  signal        x_l_msb: STD_LOGIC;                      -- X load msb
76
  signal            x_d: STD_LOGIC;                      -- X decrement
77
  signal            x_u: STD_LOGIC;                      -- X increment
78
  signal            y_d: STD_LOGIC;                      -- Y decrement
79
  signal            y_u: STD_LOGIC;                      -- Y increment
80
  signal        y_l_lsb: STD_LOGIC;                      -- Y load lsb
81
  signal        y_l_msb: STD_LOGIC;                      -- Y load msb
82
  signal        d_l_lsb: STD_LOGIC;                      -- D load lsb
83
  signal        d_l_msb: STD_LOGIC;                      -- D load msb
84
  signal            p_l: STD_LOGIC;                      -- P load
85
  signal            k_l: STD_LOGIC;                      -- program bank register PBR K load
86
  signal            b_l: STD_LOGIC;                      -- data bank register DBR B load
87
  signal           k_cl: STD_LOGIC;                      -- program bank register PBR K clear
88
  signal           b_cl: STD_LOGIC;                      -- data bank register DBR B clear
89
  signal            o_l: STD_LOGIC;                      -- OPE load msb & lsb
90
  signal        o_l_lsb: STD_LOGIC;                      -- OPE load lsb
91
  signal        o_l_msb: STD_LOGIC;                      -- OPE load msb
92
  signal          sp_ll: STD_LOGIC;                      -- SP load lsb
93
  signal          sp_lh: STD_LOGIC;                      -- SP load msb
94
  signal           sp_u: STD_LOGIC;                      -- SP increment
95
  signal           sp_d: STD_LOGIC;                      -- SP decrement
96
  signal       dmux_sel: STD_LOGIC_VECTOR(2 downto 0);   -- ALU operand #2 data multiplexer
97
  signal       kr_clear: STD_LOGIC;                      -- K clear
98
  signal       br_clear: STD_LOGIC;                      -- B clear
99
  signal         sp_emu: STD_LOGIC;                      -- '1' when S must be set in emulation mode
100
 
101
  -- microcode signals (ALU control)
102
  signal          aluop: STD_LOGIC_VECTOR(4 downto 0);    -- ALU operation code    
103
 
104
  -- microcode signals CPU control logic
105
  signal        mc_addr: STD_LOGIC_VECTOR(12 downto 0);  -- microcode PLA address
106
  signal        opfetch: STD_LOGIC;                      -- opcode fetch 
107
  signal         i_sync: STD_LOGIC;                      -- internal SYNC not latched
108
  signal         m_sync: STD_LOGIC;                      -- internal SYNC latched
109
  signal          opdec: STD_LOGIC;                      -- opcode decode
110
  signal           pcmp: STD_LOGIC_VECTOR(2 downto 0);   -- PC/MP out control effective
111
  signal        pcmp_mc: STD_LOGIC_VECTOR(2 downto 0);   -- PC/MP out control microcode
112
  signal          pcinc: STD_LOGIC;                      -- PC increment
113
  signal          e_eop: STD_LOGIC;                      -- early microcode sequence end (for some opcodes)
114
  signal         mc_eop: STD_LOGIC;                      -- microcode sequence end
115
  signal            eop: STD_LOGIC;                      -- microcode sequence end (effective)
116
  signal          we_mc: STD_LOGIC;                      -- microcode write enable
117
  signal        we_mc_l: STD_LOGIC;                      -- microcode write enable to latch
118
  signal           fbrk: STD_LOGIC;                      -- force BRK opcode (used by hardware interrupts) 
119
  signal          opbrk: STD_LOGIC;                      -- BRK opcode (used for distinguish between hardware/software interrupts) 
120
  signal          opcop: STD_LOGIC;                      -- COP opcode
121
  signal         sw_int: STD_LOGIC;                      -- software interrupt request
122
  signal   branch_taken: STD_LOGIC;                      -- branch condition resolved
123
  signal            pcc: STD_LOGIC;                      -- PC carry
124
  signal           clri: STD_LOGIC;                      -- clear interrupt request pending microcode
125
  signal         mc_vda: STD_LOGIC;                      -- microcode VDA
126
  signal         mc_vpa: STD_LOGIC;                      -- microcode VPA
127
  signal          mc_ml: STD_LOGIC;                      -- microcode ML
128
  signal     adc_sbc_mc: STD_LOGIC;                      -- ADC/SBC opcode (used for decimal adjustment)
129
  signal          ai_op: STD_LOGIC;                      -- opcode with absolute indexed addressing mode
130
  signal        daa_req: STD_LOGIC;                      -- DAA required
131
  signal           mcad: STD_LOGIC_VECTOR(11 downto 0);  -- microcode address
132
  signal         mcscan: STD_LOGIC_VECTOR(3 downto 0);   -- microcode pointer control
133
  signal           p_op: STD_LOGIC_VECTOR(4 downto 0);   -- microcode control bits register P
134
  signal         pcr_fc: STD_LOGIC_VECTOR(3 downto 0);   -- microcode control PC 
135
  signal         mpr_fc: STD_LOGIC_VECTOR(4 downto 0);   -- microcode control MP 
136
  signal          mcbit: STD_LOGIC_VECTOR(44 downto 0);  -- microcode control bits
137
  signal         regbit: STD_LOGIC_VECTOR(29 downto 0);  -- microcode control bits on registers
138
  signal         ivoffs: STD_LOGIC_VECTOR(7 downto 0);   -- interrupt vector offset encoding
139
  signal            mcn: STD_LOGIC;                      -- microcode does NOPs
140
  signal     add_sub_op: STD_LOGIC;                      -- ADC/SBC opcode
141
  signal          m_bit: STD_LOGIC;                      -- M bit of status register   
142
  signal          x_bit: STD_LOGIC;                      -- X bit of status register   
143
  signal     index_size: STD_LOGIC;                      -- index register size: 1 = 8 bit, 0 = 16 bit
144
  signal        m_size8: STD_LOGIC;                      -- memory operation size: 1 = 8 bit
145
  signal       m_size16: STD_LOGIC;                      -- memory operation size: 1 = 16 bit
146
  signal       s_size16: STD_LOGIC;                      -- memory operation size: 1 = 16 bit for special cases 
147
  signal         m_size: STD_LOGIC;                      -- memory operation size: 1 = 8 bit, 0 = 16 bit
148
  signal       acc_size: STD_LOGIC;                      -- accumulator C size: 1 = 8 bit, 0 = 16 bit
149
  signal        mov_end: STD_LOGIC;                      -- MVN/MVP end transfer
150
  signal         ld_acc: STD_LOGIC;                      -- load accumulator C register (16 bit) 
151
  signal          ld_xy: STD_LOGIC;                      -- load X/Y registers (16 bit)
152
 
153
  -- ALU signals 
154
  signal          c_flg: STD_LOGIC;                      -- ALU carry flag
155
  signal          z_flg: STD_LOGIC;                      -- ALU zero flag  
156
  signal          v_flg: STD_LOGIC;                      -- ALU overflow flag  
157
  signal          n_flg: STD_LOGIC;                      -- ALU negative flag  
158
  signal   pc_c_alu_flg: STD_LOGIC;                      -- ALU PC carry flag  
159
  signal        acr_reg: STD_LOGIC;                      -- ALU auxiliary carry (registered)
160
 
161
  -- multiplier signals
162
  signal       mul_init: STD_LOGIC;                      -- multiplier initialize
163
  signal    mul_start_u: STD_LOGIC;                      -- multiplier unsigned start
164
  signal    mul_start_s: STD_LOGIC;                      -- multiplier signed start 
165
  signal       mul_busy: STD_LOGIC;                      -- multiplier busy
166
  signal      mul_r_lsb: STD_LOGIC_VECTOR(15 downto 0);  -- multiplier lsb result
167
  signal      mul_r_msb: STD_LOGIC_VECTOR(15 downto 0);  -- multiplier msb result
168
  signal      mul_l_res: STD_LOGIC;                      -- load multiplier lsb result on register A/B and multiplier msb result on register X
169
  signal      mul_z_flg: STD_LOGIC;                      -- multiplier Z flag
170
  signal      mul_n_flg: STD_LOGIC;                      -- multiplier N flag
171
 
172
  -- WAI/STP signals
173
  signal         wai_ff: STD_LOGIC;                      -- WAI instruction flipflop
174
  signal         stp_ff: STD_LOGIC;                      -- STP instruction flipflop
175
  signal        wai_set: STD_LOGIC;                      -- WAI flipflop set
176
  signal        stp_set: STD_LOGIC;                      -- STP flipflop set
177
 
178
  -- bus
179
  signal           dbin: STD_LOGIC_VECTOR(7 downto 0);   -- input data bus D0..D7 
180
  signal          dbout: STD_LOGIC_VECTOR(7 downto 0);   -- output data bus D0..D7
181
  signal          a_bus: STD_LOGIC_VECTOR(15 downto 0);  -- accumulator register A/B/C bus
182
  signal          x_bus: STD_LOGIC_VECTOR(15 downto 0);  -- index register X bus
183
  signal          y_bus: STD_LOGIC_VECTOR(15 downto 0);  -- index register Y bus
184
  signal          k_bus: STD_LOGIC_VECTOR(7 downto 0);   -- program bank PBR K bus
185
  signal          b_bus: STD_LOGIC_VECTOR(7 downto 0);   -- program data DBR B bus
186
  signal          d_bus: STD_LOGIC_VECTOR(15 downto 0);  -- zero page/direct register D bus
187
  signal         sp_bus: STD_LOGIC_VECTOR(15 downto 0);  -- stack pointer register S bus
188
  signal          p_bus: STD_LOGIC_VECTOR(7 downto 0);   -- status register P bus
189
  signal         op_bus: STD_LOGIC_VECTOR(7 downto 0);   -- opcode register bus
190
  signal          o_bus: STD_LOGIC_VECTOR(15 downto 0);  -- operand register bus
191
  signal       oper_bus: STD_LOGIC_VECTOR(15 downto 0);  -- operand bus (ALU operand #2 bus)
192
  signal          r_bus: STD_LOGIC_VECTOR(15 downto 0);  -- general register bus (ALU operand #2 bus)
193
  signal        alu_bus: STD_LOGIC_VECTOR(15 downto 0);  -- ALU output bus
194
  signal         pc_bus: STD_LOGIC_VECTOR(15 downto 0);  -- program counter register PC bus
195
  signal         mp_bus: STD_LOGIC_VECTOR(23 downto 0);  -- memory data pointer register bus
196
  signal         ad_bus: STD_LOGIC_VECTOR(15 downto 0);  -- address bus
197
  signal     i_addr_bus: STD_LOGIC_VECTOR(23 downto 0);  -- internal 24 bit address bus  
198
 
199
  -- 16 bit program counter register (PC)
200
  component pcr
201
    port(       clk:  in STD_LOGIC;                        -- clock
202
                  i:  in STD_LOGIC;                        -- increment 
203
              fwait:  in STD_LOGIC;                        -- wait
204
                            brk_op:  in STD_LOGIC;                        -- forced BRK (by interrupt request) 
205
                   branch_flg:  in STD_LOGIC;                        -- branch flag   
206
                             mov_f:  in STD_LOGIC;                        -- MVN/MVP end transfer
207
                 fc:  in STD_LOGIC_VECTOR(3 downto 0);     -- function code
208
               din1:  in STD_LOGIC_VECTOR(7 downto 0);     -- input
209
               din2:  in STD_LOGIC_VECTOR(15 downto 0);    -- input
210
               dout: out STD_LOGIC_VECTOR(15 downto 0)     -- output
211
        );
212
  end component;
213
 
214
  -- 8 bit PBR program bank register K 
215
  component kr
216
    port(    clk:  in STD_LOGIC;                       -- clock       
217
             clr:  in STD_LOGIC;                       -- reset  
218
           fwait:  in STD_LOGIC;
219
              ld:  in STD_LOGIC;                       -- load
220
             din:  in STD_LOGIC_VECTOR(7 downto 0);    -- input 
221
            dout: out STD_LOGIC_VECTOR(7 downto 0)     -- output
222
        );
223
  end component;
224
 
225
  -- 8 bit DBR program bank register B 
226
  component br
227
    port(    clk:  in STD_LOGIC;                       -- clock       
228
             clr:  in STD_LOGIC;                       -- reset  
229
           fwait:  in STD_LOGIC;
230
              ld:  in STD_LOGIC;                       -- load
231
             din:  in STD_LOGIC_VECTOR(7 downto 0);    -- input 
232
            dout: out STD_LOGIC_VECTOR(7 downto 0)     -- output
233
        );
234
  end component;
235
 
236
  -- 16 bit memory pointer register (MP)
237
  component mpr
238
    port(   clk:  in STD_LOGIC;                       -- clock
239
          fwait:  in STD_LOGIC;                       -- wait
240
         dbr_ld:  in STD_LOGIC;                       -- load DBR
241
                        c:  in STD_LOGIC;                       -- carry 
242
             fc:  in STD_LOGIC_VECTOR(4 downto 0);    -- function code
243
          din_l:  in STD_LOGIC_VECTOR(7 downto 0);    -- input LSB
244
          din_h:  in STD_LOGIC_VECTOR(7 downto 0);    -- input MSB
245
            dbr:  in STD_LOGIC_VECTOR(7 downto 0);
246
             dr:  in STD_LOGIC_VECTOR(15 downto 0);
247
                            op:  in STD_LOGIC_VECTOR(15 downto 0);
248
                            xr:  in STD_LOGIC_VECTOR(15 downto 0);
249
                            yr:  in STD_LOGIC_VECTOR(15 downto 0);
250
                            sr:  in STD_LOGIC_VECTOR(15 downto 0);
251
              v:  in STD_LOGIC_VECTOR(7 downto 0);    -- vector offset input
252
           dout: out STD_LOGIC_VECTOR(23 downto 0)    -- output
253
        );
254
  end component;
255
 
256
  -- 8 bit opcode register opr (pipeline opcode prefetch register)
257
  component opr
258
    port(   clk:  in STD_LOGIC;                        -- clock
259
            clr:  in STD_LOGIC;                        -- force BRK opcode
260
          fwait:  in STD_LOGIC;                        -- wait
261
             ld:  in STD_LOGIC;                        -- load
262
            din:  in STD_LOGIC_VECTOR(7 downto 0);     -- input 
263
          brk_f: out STD_LOGIC;                        -- BRK opcode         
264
          cop_f: out STD_LOGIC;                        -- COP opcode
265
           dout: out STD_LOGIC_VECTOR(7 downto 0)      -- output
266
        );
267
  end component;
268
 
269
  -- 16 bit operand hold register oper
270
  component oper
271
    port(    clk:  in STD_LOGIC;                       -- clock
272
                  clr:  in STD_LOGIC;                       -- clear
273
           fwait:  in STD_LOGIC;                       -- wait
274
              ld:  in STD_LOGIC;
275
          ld_lsb:  in STD_LOGIC;                       -- load lsb
276
          ld_msb:  in STD_LOGIC;                       -- load msb
277
             din:  in STD_LOGIC_VECTOR(15 downto 0);   -- input 
278
            dout: out STD_LOGIC_VECTOR(15 downto 0)    -- output
279
        );
280
  end component;
281
 
282
  -- 16 bit accumulator register A
283
  component ar
284
    port(       clk:  in STD_LOGIC;                    -- clock                      
285
              fwait:  in STD_LOGIC;
286
                         size:  in STD_LOGIC;                      -- accumulator register size: 1 = 8 bit, 0 = 16 bit
287
             ld_lsb:  in STD_LOGIC;                    -- load lsb
288
             ld_msb:  in STD_LOGIC;                    -- load msb 
289
              ld_mul_lsb:  in STD_LOGIC;                    -- load multiplication lsb result
290
                            d:  in STD_LOGIC;                    -- decrement
291
                    end_count: out STD_LOGIC;                    -- '1' when a is 0xFF or 0xFFFF 
292
                din:  in STD_LOGIC_VECTOR(15 downto 0); -- input
293
                           mul_lsb:  in STD_LOGIC_VECTOR(15 downto 0); -- input multiplication lsb result          
294
               dout: out STD_LOGIC_VECTOR(15 downto 0)  -- output
295
        );
296
  end component;
297
 
298
  -- 16 bit index register X 
299
  component xr
300
    port(       clk:  in STD_LOGIC;                       -- clock                         
301
              fwait:  in STD_LOGIC;
302
                         size:  in STD_LOGIC;                         -- index register size: 1 = 8 bit, 0 = 16 bit
303
             ld_lsb:  in STD_LOGIC;                       -- load lsb
304
             ld_msb:  in STD_LOGIC;                       -- load msb
305
              ld_mul_msb:  in STD_LOGIC;
306
                            u:  in STD_LOGIC;                       -- increment
307
                            d:  in STD_LOGIC;                       -- decrement
308
                din:  in STD_LOGIC_VECTOR(15 downto 0);   -- input 
309
                      mul_msb:  in STD_LOGIC_VECTOR(15 downto 0);   -- input multiplication msb result     
310
               dout: out STD_LOGIC_VECTOR(15 downto 0)    -- output
311
        );
312
  end component;
313
 
314
  -- 16 bit index register Y 
315
  component yr
316
    port(    clk:  in STD_LOGIC;                       -- clock
317
           fwait:  in STD_LOGIC;
318
                      size:  in STD_LOGIC;                            -- index register size: 1 = 8 bit, 0 = 16 bit
319
          ld_lsb:  in STD_LOGIC;                       -- load lsb
320
          ld_msb:  in STD_LOGIC;                       -- load msb
321
                         u:  in STD_LOGIC;                       -- increment
322
                         d:  in STD_LOGIC;                       -- decrement
323
             din:  in STD_LOGIC_VECTOR(15 downto 0);   -- input 
324
            dout: out STD_LOGIC_VECTOR(15 downto 0)    -- output
325
        );
326
  end component;
327
 
328
  -- 16 bit zero page/direct register D 
329
  component dr
330
    port(     clk:  in STD_LOGIC;                      -- clock
331
              clr:  in STD_LOGIC;                      -- reset
332
            fwait:  in STD_LOGIC;
333
           ld_lsb:  in STD_LOGIC;                      -- load lsb
334
           ld_msb:  in STD_LOGIC;                      -- load msb
335
              din:  in STD_LOGIC_VECTOR(15 downto 0);  -- input 
336
             dout: out STD_LOGIC_VECTOR(15 downto 0)   -- output
337
        );
338
  end component;
339
 
340
  -- 16 bit stack pointer SP 
341
  component spr
342
    port(   clk:  in STD_LOGIC;                        -- clock
343
          fwait:  in STD_LOGIC;                        -- wait
344
                       em:   in STD_LOGIC;                       -- emulation mode (1)/native mode (0)
345
            clr:  in STD_LOGIC;                        -- load init value
346
           ld_l:  in STD_LOGIC;                        -- load lsb
347
           ld_h:  in STD_LOGIC;                        -- load msb
348
              u:  in STD_LOGIC;                        -- increment
349
              d:  in STD_LOGIC;                        -- decrement
350
            din:  in STD_LOGIC_VECTOR(15 downto 0);    -- input
351
           dout: out STD_LOGIC_VECTOR(15 downto 0)     -- output
352
      );
353
  end component;
354
 
355
-- 8 bit processor status register P
356
-- NV1BDIZC    
357
-- 76543210
358
-- ||||||||
359
-- ||||||||--- C/E = carry/borrow flag (emulation bit: 1 = emulation mode, 0 = native mode)
360
-- |||||||---- Z = zero flag
361
-- ||||||----- I = interrupt mask
362
-- |||||------ D = decimal/binary alu mode
363
-- ||||------- B/X = index reg. select (1 = 8 bit, 0 = 16 bit) (B Break: 0 on stack after interrupt if E emulation mode = 1)
364
-- |||-------- M = memory/acc. select (1 = 8 bit, 0 = 16 bit) (always 1 if E = 1) 
365
-- ||--------- V = overflow flag
366
-- |---------- N = negative flag
367
  -- The P register also contains an additional carry/borrow flag (ACR) used for effective address calculation but
368
  -- it is not visible at program level
369
  component pr
370
    port(      clk:  in STD_LOGIC;                        -- clock
371
               clr:  in STD_LOGIC;                        -- clear
372
             fwait:  in STD_LOGIC;                        -- wait
373
                 n:  in STD_LOGIC;                        -- N input
374
                 v:  in STD_LOGIC;                        -- V input
375
                 z:  in STD_LOGIC;                        -- Z input
376
                 c:  in STD_LOGIC;                        -- C input
377
                       mpy_z:  in STD_LOGIC;                        -- Z input from multiplier                  
378
                       mpy_n:  in STD_LOGIC;                        -- N input from multiplier                  
379
               swi:  in STD_LOGIC;                        -- software interrupt (BRK/COP opcode)
380
            acr_in:  in STD_LOGIC;                        -- auxiliary carry in   
381
                fc:  in STD_LOGIC_VECTOR(4 downto 0);     -- function code 
382
               din:  in STD_LOGIC_VECTOR(7 downto 0);     -- input
383
              dout: out STD_LOGIC_VECTOR(7 downto 0);     -- output
384
           acr_out: out STD_LOGIC;                        -- auxiliary carry out   
385
                               em: out STD_LOGIC;                        -- emulation (1)/native mode (0)
386
                      two_op: out STD_LOGIC                         -- two byte instruction                              
387
        );
388
  end component;
389
 
390
  -- 16 bit (binary/bcd) two-way through pass ALU   
391
  component alu_bin
392
    port( alu_byp:  in STD_LOGIC;                      -- ALU bypass (no operation)    
393
              bcd:  in STD_LOGIC;                      -- BCD mode 
394
                            size:  in STD_LOGIC;                           -- ALU size operation: 1 = 8 bit, 0 = 16 bit
395
              cin:  in STD_LOGIC;                      -- carry/borrow in
396
              vin:  in STD_LOGIC;                      -- overflow in
397
              op1:  in STD_LOGIC_VECTOR(15 downto 0);  -- 16 bit operand #1
398
              op2:  in STD_LOGIC_VECTOR(15 downto 0);  -- 16 bit operand #2
399
               fc:  in STD_LOGIC_VECTOR(4 downto 0);   -- function code
400
               cf: out STD_LOGIC;                      -- carry/borrow (byte) out 
401
               zf: out STD_LOGIC;                      -- zero flag out
402
               nf: out STD_LOGIC;                      -- negative flag out
403
               vf: out STD_LOGIC;                      -- overflow flag out
404
            pc_cf: out STD_LOGIC;                      -- carry/borrow out for PC operation 
405
             dout: out STD_LOGIC_VECTOR(15 downto 0)   -- 16 bit result out
406
        );
407
  end component;
408
 
409
  -- PC/MP address multiplexer
410
  component addrmux
411
    port(  sel:  in STD_LOGIC_VECTOR(2 downto 0);
412
             a:  in STD_LOGIC_VECTOR(23 downto 0);
413
             b:  in STD_LOGIC_VECTOR(23 downto 0);
414
                          dbr:  in STD_LOGIC_VECTOR(7 downto 0);
415
             s:  in STD_LOGIC_VECTOR(15 downto 0);
416
                           xr:  in STD_LOGIC_VECTOR(15 downto 0);
417
                           yr:  in STD_LOGIC_VECTOR(15 downto 0);
418
             y: out STD_LOGIC_VECTOR(23 downto 0)
419
        );
420
  end component;
421
 
422
  -- register multiplexer
423
  component regmux
424
    port(  sel:  in STD_LOGIC_VECTOR(4 downto 0);
425
             a:  in STD_LOGIC_VECTOR(7 downto 0);
426
             b:  in STD_LOGIC_VECTOR(15 downto 0);
427
             c:  in STD_LOGIC_VECTOR(15 downto 0);
428
             d:  in STD_LOGIC_VECTOR(15 downto 0);
429
             e:  in STD_LOGIC_VECTOR(15 downto 0);
430
             g:  in STD_LOGIC_VECTOR(7 downto 0);
431
             h:  in STD_LOGIC_VECTOR(7 downto 0);
432
             i:  in STD_LOGIC_VECTOR(7 downto 0);
433
             j:  in STD_LOGIC_VECTOR(15 downto 0);
434
             k:  in STD_LOGIC_VECTOR(15 downto 0);
435
             l:  in STD_LOGIC_VECTOR(7 downto 0);
436
             m:  in STD_LOGIC_VECTOR(7 downto 0);
437
             y: out STD_LOGIC_VECTOR(15 downto 0)
438
        );
439
  end component;
440
 
441
  -- data multiplexer (register "O" bypass)
442
  component dmux is
443
    port(  sel:  in STD_LOGIC_VECTOR(2 downto 0);
444
             a:  in STD_LOGIC_VECTOR(15 downto 0);
445
             b:  in STD_LOGIC_VECTOR(7 downto 0);
446
             y: out STD_LOGIC_VECTOR(15 downto 0)
447
        );
448
  end component dmux;
449
 
450
  -- microcode sequencer logic
451
  component mcseq
452
    port(    clk:  in STD_LOGIC;
453
             clr:  in STD_LOGIC;
454
          mc_nop:  in STD_LOGIC;
455
           fwait:  in STD_LOGIC;
456
               q: out STD_LOGIC_VECTOR(3 downto 0)
457
        );
458
  end component;
459
 
460
  -- micropla logic
461
  -- output fields format:
462
  -- a[12]    is two byte instruction bit
463
  -- a[11..4] is 8 bit opcode  
464
  -- a[3..0]  is 4 bit microinstruction counter
465
  component mcpla
466
    port(    em:  in STD_LOGIC;                           -- emulation mode (1)/native mode (0)
467
              m:  in STD_LOGIC;                           -- M memory/acc. 8 bit (1), M memory/acc. 16 bit (0)  
468
              x:  in STD_LOGIC;                           -- X index reg. 8 bit (1), X index reg. 16 bit (0)  
469
                   a:  in STD_LOGIC_VECTOR(12 downto 0);       -- two byte bit & 8 bit opcode & 4 bit microinstruction counter
470
              q: out STD_LOGIC_VECTOR(44 downto 0)        -- microcode output
471
        );
472
  end component;
473
 
474
  -- register operation decoding logic
475
  component decreg
476
    port(    r:  in STD_LOGIC_VECTOR(5 downto 0);
477
             y: out STD_LOGIC_VECTOR(29 downto 0)
478
        );
479
  end component;
480
 
481
  -- cpu main state machine
482
  component cpufsm
483
    port(     clk:  in STD_LOGIC;
484
              clr:  in STD_LOGIC;
485
            fwait:  in STD_LOGIC;
486
             ireq:  in STD_LOGIC;
487
              aim:  in STD_LOGIC;
488
           bcarry:  in STD_LOGIC;
489
           icarry:  in STD_LOGIC;
490
               p1:  in STD_LOGIC_VECTOR(2 downto 0);
491
             e_ei:  in STD_LOGIC;
492
            mc_ei:  in STD_LOGIC;
493
           addsub:  in STD_LOGIC;
494
         dec_mode:  in STD_LOGIC;
495
            fetch: out STD_LOGIC;
496
          op_sync: out STD_LOGIC;
497
              pci: out STD_LOGIC;
498
               pq: out STD_LOGIC_VECTOR(2 downto 0);
499
               fb: out STD_LOGIC;
500
               od: out STD_LOGIC;
501
           mc_nop: out STD_LOGIC
502
        );
503
  end component;
504
 
505
  -- interrupt logic
506
  component intlog
507
  port(    clk:  in STD_LOGIC;
508
          iack:  in STD_LOGIC;                    -- interrupt acknowledge by microcode 
509
             r:  in STD_LOGIC;                    -- RESET request
510
             n:  in STD_LOGIC;                    -- NMI request
511
             i:  in STD_LOGIC;                    -- IRQ request
512
           brk:  in STD_LOGIC;                    -- BRK opcode
513
                          cop:  in STD_LOGIC;                    -- COP opcode
514
                            e:  in STD_LOGIC;                    -- native\emulation mode
515
                        gmask:  in STD_LOGIC;                    -- interrupt mask valid for IRQ and NMI (used by two byte instruction)  
516
         imask:  in STD_LOGIC;                    -- interrupt mask (valid only for IRQ)
517
         ioffs:  in STD_LOGIC_VECTOR(7 downto 0); -- interrupt servicing offset
518
          ireq: out STD_LOGIC;                    -- global interrupt requestb (IRQ/NMI)
519
         voffs: out STD_LOGIC_VECTOR(7 downto 0)  -- interrupt vector offset 
520
        );
521
  end component;
522
 
523
  -- branch logic
524
  component branch
525
    port(    op:  in STD_LOGIC_VECTOR(3 downto 0);
526
              n:  in STD_LOGIC;
527
              v:  in STD_LOGIC;
528
              z:  in STD_LOGIC;
529
              c:  in STD_LOGIC;
530
           bres: out STD_LOGIC
531
        );
532
  end component;
533
 
534
  -- opcode decimal instructions and prefetch prediction logic
535
  component pre_dec
536
    port(    op:  in STD_LOGIC_VECTOR(7 downto 0);
537
          fetch:  in STD_LOGIC;
538
             ei: out STD_LOGIC;
539
            dec: out STD_LOGIC
540
        );
541
  end component;
542
 
543
  -- 16X16->32 bit multiplier signed/unsigned
544
  component multiplier
545
    port(     clk:   in STD_LOGIC;
546
              clr:   in STD_LOGIC;
547
             init:   in STD_LOGIC;
548
          start_u:   in STD_LOGIC;
549
               start_s:   in STD_LOGIC;
550
           mpcand:   in STD_LOGIC_VECTOR(15 downto 0);
551
                          mplier:   in STD_LOGIC_VECTOR(15 downto 0);
552
                            busy:  out STD_LOGIC;
553
          res_lsb:  out STD_LOGIC_VECTOR(15 downto 0);
554
          res_msb:  out STD_LOGIC_VECTOR(15 downto 0);
555
                           z_flg:  out STD_LOGIC;
556
                                n_flg:  out STD_LOGIC
557
      );
558
  end component;
559
 
560
  begin
561
    u1:pcr      port map(clk=>clk0,
562
                         i=>pcinc,
563
                         fwait=>i_rdy,
564
                                                                 brk_op=>opbrk,
565
                                                                 branch_flg=>branch_taken,
566
                                                                 mov_f=>mov_end,
567
                         fc=>pcr_fc,
568
                         din1=>alu_bus(7 downto 0),
569
                         din2=>o_bus,
570
                         dout=>pc_bus
571
                        );
572
 
573
    u2:kr       port map(clk=>clk0,
574
                              clr=>kr_clear,
575
                         fwait=>i_rdy,
576
                         ld=>k_l,
577
                         din=>alu_bus(7 downto 0),
578
                         dout=>k_bus
579
                        );
580
 
581
    u3:br       port map(clk=>clk0,
582
                              clr=>br_clear,
583
                         fwait=>i_rdy,
584
                         ld=>b_l,
585
                         din=>alu_bus(7 downto 0),
586
                         dout=>b_bus
587
                        );
588
 
589
    u4:mpr      port map(clk=>clk0,
590
                         fwait=>i_rdy,
591
                         dbr_ld=>opfetch,
592
                         c=>acr_reg,
593
                         fc=>mpr_fc,
594
                         din_l=>alu_bus(7 downto 0),
595
                         din_h=>dbin,
596
                         dbr=>b_bus,
597
                         dr=>d_bus,
598
                                        op=>o_bus,
599
                                        xr=>x_bus,
600
                                        yr=>y_bus,
601
                                        sr=>sp_bus,
602
                         v=>ivoffs,
603
                         dout=>mp_bus
604
                        );
605
 
606
    u5:ar       port map(clk=>clk0,
607
                         fwait=>i_rdy,
608
                                                                 size=>acc_size,
609
                         ld_lsb=>a_l_lsb,
610
                         ld_msb=>a_l_msb,
611
                                                                 ld_mul_lsb=>mul_l_res,
612
                                                                 d=>a_dec,
613
                                                                 end_count=>mov_end,
614
                         din=>alu_bus,
615
                                                                 mul_lsb=>mul_r_lsb,
616
                         dout=>a_bus
617
                        );
618
 
619
    u6:xr       port map(clk=>clk0,
620
                         fwait=>i_rdy,
621
                                                                 size=>index_size,
622
                         ld_lsb=>x_l_lsb,
623
                         ld_msb=>x_l_msb,
624
                                                                 ld_mul_msb=>mul_l_res,
625
                                                                 u=>x_u,
626
                                                                 d=>x_d,
627
                         din=>alu_bus,
628
                                                                 mul_msb=>mul_r_msb,
629
                         dout=>x_bus
630
                        );
631
 
632
    u7:yr       port map(clk=>clk0,
633
                         fwait=>i_rdy,
634
                                                                 size=>index_size,
635
                         ld_lsb=>y_l_lsb,
636
                         ld_msb=>y_l_msb,
637
                                                                 u=>y_u,
638
                                                                 d=>y_d,
639
                         din=>alu_bus,
640
                         dout=>y_bus
641
                        );
642
 
643
    u8:dr       port map(clk=>clk0,
644
                         clr=>i_res,
645
                         fwait=>i_rdy,
646
                         ld_lsb=>d_l_lsb,
647
                         ld_msb=>d_l_msb,
648
                         din=>alu_bus,
649
                         dout=>d_bus
650
                        );
651
 
652
    u9:spr      port map(clk=>clk0,
653
                         clr=>i_res,
654
                         fwait=>i_rdy,
655
                                                                 em=>sp_emu,
656
                         ld_l=>sp_ll,
657
                         ld_h=>sp_lh,
658
                         u=>sp_u,
659
                         d=>sp_d,
660
                         din=>alu_bus,
661
                         dout=>sp_bus
662
                        );
663
 
664
    u10:pr      port map(clk=>clk0,
665
                         clr=>i_res,
666
                         fwait=>i_rdy,
667
                         n=>n_flg,
668
                         v=>v_flg,
669
                         z=>z_flg,
670
                         c=>c_flg,
671
                                                                 mpy_z=>mul_z_flg,
672
                                                                 mpy_n=>mul_n_flg,
673
                         swi=>sw_int,
674
                         acr_in=>pc_c_alu_flg,
675
                         fc=>p_op,
676
                         din=>dbin,
677
                         dout=>p_bus,
678
                         acr_out=>acr_reg,
679
                                                                 em=>emu,
680
                                                                 two_op=>two_byte_op
681
                        );
682
 
683
    u11:opr     port map(clk=>clk0,
684
                         clr=>fbrk,
685
                         fwait=>i_rdy,
686
                         ld=>opfetch,
687
                         din=>dbin,
688
                         brk_f=>opbrk,
689
                                                                 cop_f=>opcop,
690
                         dout=>op_bus
691
                        );
692
 
693
    u12:oper    port map(clk=>clk0,
694
                              clr=>opfetch,
695
                         fwait=>i_rdy,
696
                                                                 ld=>o_l,
697
                         ld_lsb=>o_l_lsb,
698
                         ld_msb=>o_l_msb,
699
                         din=>alu_bus,
700
                         dout=>o_bus
701
                        );
702
 
703
    u13:alu_bin port map(alu_byp=>acr_reg,
704
                              bcd=>p_bus(3),
705
                                                                 size=>m_size,
706
                         cin=>p_bus(0),
707
                         vin=>p_bus(6),
708
                         op1=>r_bus,
709
                         op2=>oper_bus,
710
                         fc=>aluop,
711
                         cf=>c_flg,
712
                         zf=>z_flg,
713
                         nf=>n_flg,
714
                         vf=>v_flg,
715
                         pc_cf=>pc_c_alu_flg,
716
                         dout=>alu_bus
717
                        );
718
 
719
    u14:addrmux port map(sel=>pcmp,
720
                         a=>i_addr_bus,
721
                         b=>mp_bus,
722
                                                                 dbr=>b_bus,
723
                         s=>sp_bus,
724
                                                                 xr=>x_bus,
725
                                                                 yr=>y_bus,
726
                         y=>addr
727
                        );
728
 
729
    u15:regmux  port map(sel=>rsel,
730
                         a=>dbin,
731
                         b=>a_bus,
732
                         c=>x_bus,
733
                         d=>y_bus,
734
                         e=>sp_bus,
735
                         g=>p_bus,
736
                         h=>pc_bus(7 downto 0),
737
                         i=>pc_bus(15 downto 8),
738
                         j=>o_bus,
739
                         k=>d_bus,
740
                                                                 l=>k_bus,
741
                                                                 m=>b_bus,
742
                         y=>r_bus
743
                        );
744
 
745
    u16:dmux    port map(sel=>dmux_sel,
746
                         a=>o_bus,
747
                         b=>dbin,
748
                         y=>oper_bus
749
                        );
750
 
751
    u17:mcseq   port map(clk=>clk0,
752
                         clr=>opdec,
753
                         mc_nop=>mcn,
754
                         fwait=>i_rdy or mul_busy,
755
                         q=>mcscan
756
                        );
757
 
758
    u18:mcpla   port map(em=>emu,
759
                              m=>m_bit,
760
                              x=>x_bit,
761
                              a=>mc_addr,
762
                         q=>mcbit
763
                        );
764
 
765
    u19:decreg  port map(r=>regop,
766
                         y=>regbit
767
                        );
768
 
769
    u20:cpufsm  port map(clk=>clk0,
770
                         clr=>i_res,
771
                         fwait=>i_rdy,
772
                         ireq=>int,
773
                         aim=>ai_op,
774
                         bcarry=>pcc,
775
                         icarry=>acr_reg,
776
                         p1=>pcmp_mc,
777
                         e_ei=>e_eop,
778
                         mc_ei=>mc_eop,
779
                         addsub=>add_sub_op,
780
                         dec_mode=>p_bus(3),
781
                         fetch=>opfetch,
782
                         op_sync=>i_sync,
783
                         pci=>pcinc,
784
                         pq=>pcmp,
785
                         fb=>fbrk,
786
                         od=>opdec,
787
                         mc_nop=>mcn
788
                        );
789
 
790
    u21:intlog  port map(clk=>clk0,
791
                         iack=>clri,
792
                         r=>i_res,
793
                         n=>i_nmi,
794
                         i=>i_irq,
795
                         brk=>opbrk,
796
                                                                 cop=>opcop,
797
                                                                 e=>emu,
798
                         gmask=>two_byte_op,
799
                         imask=>ien,
800
                         ioffs=>mp_bus(7 downto 0),
801
                         ireq=>int,
802
                         voffs=>ivoffs
803
                        );
804
 
805
    u22:branch  port map(op=>op_bus(7 downto 4),
806
                         n=>p_bus(7),
807
                         v=>p_bus(6),
808
                         z=>p_bus(1),
809
                         c=>p_bus(0),
810
                         bres=>branch_taken
811
                        );
812
 
813
    u23:pre_dec port map(op=>dbin,
814
                         fetch=>opfetch,
815
                         ei=>e_eop,
816
                         dec=>add_sub_op
817
                        );
818
 
819
    u24:multiplier port map(clk=>clk0,
820
                                 clr=>i_res,
821
                            init=>mul_init,
822
                            start_u=>mul_start_u,
823
                                                                         start_s=>mul_start_s,
824
                            mpcand=>a_bus,
825
                                           mplier=>x_bus,
826
                                           busy=>mul_busy,
827
                            res_lsb=>mul_r_lsb,
828
                            res_msb=>mul_r_msb,
829
                                                                         z_flg=>mul_z_flg,
830
                                                                         n_flg=>mul_n_flg
831
                                                                   );
832
 
833
    -- asynchronous CPU link section 
834
         mc_addr    <= two_byte_op & mcad;
835
         e          <= emu;                                     -- emulation mode
836
    ien        <= p_bus(2);                                -- P(I) flag 
837
    i_res      <= not res;                                 -- internal reset
838
    i_nmi      <= not nmi;                                 -- internal NMI
839
    i_irq      <= not irq;                                 -- internal IRQ
840
    e_rdy      <= not rdy;                                 -- external RDY inverted
841
         i_rdy      <= e_rdy or wai_ff or stp_ff;               -- internal RDY
842
    mcad       <= op_bus & mcscan;                         -- microcode address
843
    rsel       <= mcbit(4 downto 0);                       -- registers read microcode
844
    regop      <= mcbit(10 downto 5);                      -- registers operation microcode
845
    aluop      <= mcbit(15 downto 11);                     -- ALU microcode
846
    p_op       <= mcbit(20 downto 16);                     -- register P microcode 
847
    mpr_fc     <= mcbit(25 downto 21);                     -- MPR microcode
848
    pcr_fc     <= mcbit(29 downto 26);                     -- PCR microcode
849
    pcmp_mc    <= mcbit(32 downto 30);                     -- PCR/MPR multiplexer microcode
850
    clri       <= mcbit(33);                               -- clear interrupt request
851
    we_mc      <= mcbit(34);                               -- write enable (combinatorial) microcode
852
    we_mc_l    <= mcbit(35);                               -- write enable (latched) microcode
853
    mc_eop     <= mcbit(36);                               -- end of instruction reached                             
854
    mc_vda     <= mcbit(37);                               -- microcode VDA
855
         mc_vpa     <= mcbit(38);                               -- microcode VPA
856
         mc_ml      <= mcbit(39);                               -- microcode ML
857
    i_vp       <= mcbit(40);                               -- vector pull 
858
    ai_op      <= mcbit(41);                               -- opcode with addressing indexed microcode
859
    dmux_sel   <= mcbit(44 downto 42);                     -- data multiplexer microcode
860
    ope        <= eop;
861
         i_addr_bus <= k_bus & pc_bus;
862
    eop <= '1' when mc_eop = '1' or e_eop = '1' else '0';
863
    vp <= not i_vp;
864
         op_exp <= two_byte_op;
865
         vda <= m_sync or mc_vda;
866
    vpa <= m_sync or mc_vpa;
867
         ml <= mc_ml;
868
         sw_int <= opbrk or opcop;
869
 
870
         -- ALU/memory size 
871
    m_size8  <= '1' when emu = '1' or m_bit = '1' else
872
                     '1' when op_bus = x"EB" or op_bus = x"AB" else                     -- when XBA and PLB opcodes the ALU size is always 8 bit
873
                     '1' when (op_bus = x"AA" or op_bus = x"A8") and x_bit = '1' else   -- when TAX and TAY opcodes and X is '1' the ALU size is 8 bit
874
                     '1' when (op_bus = x"8A" or op_bus = x"98") and m_bit = '1' else   -- when TXA and TXA opcodes and M is '1' the ALU size is 8 bit
875
                     '1' when op_bus = x"68" and m_bit = '1' else                       -- when PLA opcode and M is '1' the ALU size is 8 bit
876
                     '1' when (op_bus = x"FA" or op_bus = x"7A") and x_bit = '1' else   -- when PLX or PLY opcode and X = '1' the ALU size is 8 bit
877
                                         '0';
878
         m_size16 <= '0' when (op_bus = x"5B" or op_bus = x"7B") else                   -- when TCD or TDC opcodes the transfer size is always 16 bit
879
                     '0' when (op_bus = x"1B" or op_bus = x"3B") else                   -- when TCS or TSC opcodes the transfer size is always 16 bit
880
                     '0' when (op_bus = x"82" or op_bus = x"62") else                   -- when BRL or PER opcodes the transfer size is always 16 bit
881
                     '0' when op_bus = x"2B" else                                       -- when PLD opcode the transfer size is always 16 bit
882
                                         '0' when (op_bus = x"AB" and two_byte_op = '1') and emu = '0' else -- when PLR opcode and native mode
883
                                         '0' when ld_acc = '1' and m_bit = '0' else                         -- when load accumulator C register 
884
                                         '0' when ld_xy = '1' and x_bit = '0' else                          -- when load X/Y registers (16 bit size)   
885
                                    '1';
886
         s_size16 <= '0' when op_bus = x"EB" else '1';                                  -- special case for XBA: accumulator size is 16 bit so it can reloads itself swapped in only one cycle                                                    
887
         m_size <= m_size8 and m_size16;                                                       -- ALU size                       
888
         acc_size <= m_size8 and m_size16 and s_size16;                                 -- accumulator register C size
889
    index_size <= emu or x_bit;                                                    -- index registers size 
890
 
891
         -- S native/emulation mode (set by XCE opcode and E bit)
892
    sp_emu <= p_bus(0) when op_bus = x"FB" else emu;
893
 
894
    -- register operations
895
    a_l_lsb     <= regbit(0);                               -- A load lsb
896
    a_l_msb     <= regbit(1);                               -- A load msb
897
    a_dec       <= regbit(2);                               -- A decrement
898
    x_l_lsb     <= regbit(3);                               -- X load lsb
899
    x_l_msb     <= regbit(4);                               -- X load msb
900
         x_d         <= regbit(5);                               -- X -= 1
901
         x_u         <= regbit(6);                               -- X += 1
902
    y_l_lsb     <= regbit(7);                               -- Y load lsb
903
    y_l_msb     <= regbit(8);                               -- Y load msb
904
         y_d         <= regbit(9);                               -- Y -= 1
905
         y_u         <= regbit(10);                              -- Y += 1
906
    d_l_lsb     <= regbit(11);                              -- D load lsb
907
    d_l_msb     <= regbit(12);                              -- D load msb
908
    o_l         <= regbit(13);                              -- O load msb & lsb
909
    o_l_lsb     <= regbit(14);                              -- O load lsb
910
    o_l_msb     <= regbit(15);                              -- O load msb
911
    sp_ll       <= regbit(16);                              -- S load lsb
912
    sp_lh       <= regbit(17);                              -- S load msb
913
    sp_u        <= regbit(18);                              -- S += 1
914
    sp_d        <= regbit(19);                              -- S -= 1
915
    k_l         <= regbit(20);                              -- PBR K load
916
    b_l         <= regbit(21);                              -- DBR B load
917
    k_cl        <= regbit(22);                              -- PBR K clear
918
    b_cl        <= regbit(23);                              -- DBR B clear
919
         mul_l_res   <= regbit(24);                              -- load multiplication result on A/B and X
920
         mul_init    <= regbit(25);                              -- init multiplier
921
         mul_start_u <= regbit(26);                              -- start multiplier unsigned 
922
         mul_start_s <= regbit(27);                              -- start multiplier signed
923
         wai_set     <= regbit(28);                              -- WAI enter wait
924
         stp_set     <= regbit(29);                              -- STP enter wait
925
    we          <= we_mc or opfetch;                        -- write enable
926
    m_bit       <= p_bus(5) or emu;                         -- M bit
927
    x_bit       <= p_bus(4) or emu;                         -- X bit
928
    m           <= m_bit;
929
    x           <= x_bit;
930
         kr_clear    <= i_res or k_cl;
931
         br_clear    <= i_res or b_cl;
932
         ld_acc      <= regbit(0) and regbit(1);
933
    ld_xy       <= (regbit(3) and regbit(4)) or (regbit(7) and regbit(8));
934
    -- VPA latched
935
    process(clk0)
936
    begin
937
      if (clk0'event and clk0 = '1') then
938
        if i_rdy = '0' then
939
          m_sync <= i_sync;
940
        else
941
          m_sync <= m_sync;
942
        end if;
943
      end if;
944
    end process;
945
 
946
    -- PC carry logic
947
    process(o_bus,pc_c_alu_flg)
948
    begin
949
      if o_bus(7) = '0' then              -- check for positive/negative branch offset (bit 7)
950
        pcc <= pc_c_alu_flg;
951
      else
952
        pcc <= not pc_c_alu_flg;
953
      end if;
954
    end process;
955
 
956
    -- write enable registered
957
    process(clk0)
958
    begin
959
      if (clk0'event and clk0 = '1') then
960
        if i_res = '1' then
961
          we_r <= '1';
962
        else
963
          if i_rdy = '0' then
964
            we_r <= we_mc_l;
965
          else
966
            we_r <= we_r;
967
          end if;
968
        end if;
969
      end if;
970
    end process;
971
 
972
    rw <= we and we_r;
973
 
974
         -- WAI 
975
         process(clk0)
976
         begin
977
      if (clk0'event and clk0 = '1') then
978
             if wai_ff = '0' then
979
          if wai_set then
980
             wai_ff <= '1';
981
          else
982
             wai_ff <= wai_ff;
983
          end if;
984
                  else
985
          if i_res = '1' or i_nmi = '1' or i_irq = '1' then
986
                       wai_ff <= '0';
987
          else
988
                       wai_ff <= wai_ff;
989
          end if;
990
        end if;
991
                end if;
992
    end process;
993
    rdy_out <= not wai_ff;
994
 
995
         -- STP 
996
         process(clk0)
997
         begin
998
      if (clk0'event and clk0 = '1') then
999
             if stp_ff = '0' then
1000
          if stp_set then
1001
             stp_ff <= '1';
1002
          else
1003
             stp_ff <= stp_ff;
1004
          end if;
1005
                  else
1006
          if i_res = '1' then
1007
                       stp_ff <= '0';
1008
          else
1009
                       stp_ff <= stp_ff;
1010
          end if;
1011
        end if;
1012
                end if;
1013
    end process;
1014
    stp_out <= not stp_ff;
1015
 
1016
 
1017
    -- data bus tristate (buffer ring gated) control logic
1018
    --process(clk0,we,we_r,alu_bus)
1019
    --begin
1020
    --  if clock = '0' and (we = '0' or we_r = '0') then
1021
    --    data <= alu_bus;
1022
    --  else
1023
    --    data <= "ZZZZZZZZ";
1024
    --  end if;
1025
    --end process;
1026
 
1027
 
1028
    data_out <= alu_bus(7 downto 0);
1029
    dbin <= data_in or "00000000";
1030
         -- DEBUG
1031
--  a_reg <= a_bus;
1032
--  x_reg <= x_bus;
1033
--  y_reg <= y_bus;
1034
--       s_reg <= sp_bus;
1035
--       op_reg <= o_bus;
1036
--       p_reg <= p_bus;
1037
--       k_reg <= k_bus;
1038
--       b_reg <= b_bus;
1039
--       o_reg <= op_bus;
1040
--       mcode <= mcscan;
1041
 
1042
end struct;
1043
 
1044
 
1045
 

powered by: WebSVN 2.1.0

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