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

Subversion Repositories t51

[/] [t51/] [trunk/] [rtl/] [vhdl/] [T51.vhd] - Blame information for rev 51

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 jesus
--
2
-- 8051 compatible microcontroller core
3
--
4 30 andreas
-- Version : 0300
5 2 jesus
--
6
-- Copyright (c) 2001-2002 Daniel Wallner (jesus@opencores.org)
7 44 andreas
--           (c) 2004-2005 Andreas Voggeneder (andreas.voggeneder@fh-hagenberg.at)
8 2 jesus
--
9
-- All rights reserved
10
--
11
-- Redistribution and use in source and synthezised forms, with or without
12
-- modification, are permitted provided that the following conditions are met:
13
--
14
-- Redistributions of source code must retain the above copyright notice,
15
-- this list of conditions and the following disclaimer.
16
--
17
-- Redistributions in synthesized form must reproduce the above copyright
18
-- notice, this list of conditions and the following disclaimer in the
19
-- documentation and/or other materials provided with the distribution.
20
--
21
-- Neither the name of the author nor the names of other contributors may
22
-- be used to endorse or promote products derived from this software without
23
-- specific prior written permission.
24
--
25
-- THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
26
-- AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
27
-- THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
28
-- PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE
29
-- LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
30
-- CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
31
-- SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
32
-- INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
33
-- CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
34
-- ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
35
-- POSSIBILITY OF SUCH DAMAGE.
36
--
37
-- Please report bugs to the author, but before you do so, please
38
-- make sure that this is not a derivative work and that
39
-- you have the latest version of this file.
40
--
41
-- The latest version of this file can be found at:
42
--      http://www.opencores.org/cvsweb.shtml/t51/
43
--
44
-- Limitations :
45
--
46
-- File history :
47
--
48 35 andreas
-- 16-Dec-05 : Bugfix for JBC instruction
49
-- 21-Jan-06 : Bugfix for INC DPTR instruction for special cases
50 43 andreas
-- 19-Feb-06 : Bugfix for Interrupts at stalled instructions
51 2 jesus
 
52
library IEEE;
53
use IEEE.std_logic_1164.all;
54
use IEEE.numeric_std.all;
55
use work.T51_Pack.all;
56
 
57
entity T51 is
58
        generic(
59 30 andreas
                DualBus         : integer := 1; -- FALSE: single bus movx 
60
                RAMAddressWidth : integer := 8;
61
                SecondDPTR      : integer := 0;
62 39 andreas
                t8032           : integer := 0; -- 0== advanced movx timing, not compatible to T8032
63 30 andreas
                tristate        : integer := 1;
64 32 andreas
                simenv          : integer := 0
65 2 jesus
        );
66
        port(
67 30 andreas
                Clk                          : in std_logic;
68
                Rst_n                : in std_logic;
69
                Ready                : in std_logic;
70
                ROM_Addr           : out std_logic_vector(15 downto 0);
71
                ROM_Data           : in std_logic_vector(7 downto 0);
72
                RAM_Addr           : out std_logic_vector(15 downto 0);
73
                RAM_RData          : in std_logic_vector(7 downto 0);
74
                RAM_WData          : out std_logic_vector(7 downto 0);
75
                RAM_Cycle          : out std_logic;
76
                RAM_Rd             : out std_logic;
77
                RAM_Wr             : out std_logic;
78
                Int_Trig           : in std_logic_vector(6 downto 0);
79
                Int_Acc            : out std_logic_vector(6 downto 0);
80
                SFR_Rd_RMW       : out std_logic;
81
                SFR_Wr             : out std_logic;
82
                SFR_Addr           : out std_logic_vector(6 downto 0);
83
                SFR_WData          : out std_logic_vector(7 downto 0);
84
                SFR_RData_in : in  std_logic_vector(7 downto 0);
85
                IRAM_Wr      : out std_logic;
86
                IRAM_Addr          : out std_logic_vector(7 downto 0);
87
                IRAM_WData   : out std_logic_vector(7 downto 0)
88 2 jesus
        );
89
end T51;
90
 
91
architecture rtl of T51 is
92 30 andreas
  constant Altera_IRAM_c : boolean :=false;
93 35 andreas
  -- speeds up instructions "mov @Ri,direct" and "mov Ri,direct" by one cycle
94
  -- but not fully testet. So use it with care
95
  constant fast_cpu_c    : integer := 0;
96
 
97 2 jesus
        -- Registers
98
        signal  ACC                             : std_logic_vector(7 downto 0);
99 35 andreas
        signal  B                                 : std_logic_vector(7 downto 0);
100 2 jesus
        signal  PSW                             : std_logic_vector(7 downto 1); -- Bit 0 is parity
101
        signal  PSW0                    : std_logic;
102
        signal  IP                              : std_logic_vector(7 downto 0);
103
        signal  SP                              : unsigned(7 downto 0);
104 30 andreas
        signal  DPL0                    : std_logic_vector(7 downto 0);  -- DPTR 0
105
        signal  DPH0                    : std_logic_vector(7 downto 0);  -- DPTR 0
106
  signal        DPL1                    : std_logic_vector(7 downto 0);  -- DPTR 1
107
        signal  DPH1                    : std_logic_vector(7 downto 0);  -- DPTR 1
108
        signal  DPL                       : std_logic_vector(7 downto 0);        -- current DPTR
109
        signal  DPH                       : std_logic_vector(7 downto 0);        -- current DPTR
110
        signal  DPS,next_DPS  : std_logic;
111 35 andreas
        signal  dptr_inc  : std_logic_vector(15 downto 0);
112 30 andreas
        signal  DPS_r     : std_logic;
113 2 jesus
        signal  PC                              : unsigned(15 downto 0);
114
        signal  P2R                             : std_logic_vector(7 downto 0);
115
 
116
        signal  PCC                             : std_logic_vector(15 downto 0);
117
        signal  NPC                             : unsigned(15 downto 0);
118
        signal  OPC                             : unsigned(15 downto 0);
119
 
120
        -- ALU signals
121
        signal  Op_A                    : std_logic_vector(7 downto 0);
122
        signal  Op_B                    : std_logic_vector(7 downto 0);
123
        signal  Mem_A                   : std_logic_vector(7 downto 0);
124
        signal  Mem_B                   : std_logic_vector(7 downto 0);
125
        signal  Old_Mem_B               : std_logic_vector(7 downto 0);
126
        signal  ACC_Q                   : std_logic_vector(7 downto 0);
127
        signal  B_Q                             : std_logic_vector(7 downto 0);
128
        signal  Res_Bus                 : std_logic_vector(7 downto 0);
129
        signal  Status_D                : std_logic_vector(7 downto 5);
130
        signal  Status_Wr               : std_logic_vector(7 downto 5);
131
 
132
        -- Misc signals
133
        signal  Int_AddrA               : std_logic_vector(7 downto 0);
134
        signal  Int_AddrA_r             : std_logic_vector(7 downto 0);
135
        signal  Int_AddrB               : std_logic_vector(7 downto 0);
136
 
137
        signal  MCode                   : std_logic_vector(3 downto 0);
138
        signal  FCycle                  : std_logic_vector(1 downto 0);
139
 
140
        signal  RET_r                   : std_logic;
141
        signal  RET                             : std_logic;
142
 
143 30 andreas
  signal  Stall_pipe  : std_logic;
144 2 jesus
        signal  Ri_Stall                : std_logic;
145
        signal  PSW_Stall               : std_logic;
146 30 andreas
        signal  ACC_Stall   : std_logic;
147
        signal  SP_Stall    : std_logic;
148 32 andreas
        signal  movx_Stall  : std_logic;
149 30 andreas
        signal  iReady      : std_logic;
150 2 jesus
 
151
        signal  Next_PSW7               : std_logic;
152
        signal  Next_ACC_Z              : std_logic;
153
        signal  ACC_Wr                  : std_logic;
154 30 andreas
        signal  B_Wr        : std_logic;
155 2 jesus
 
156
        signal  SFR_RData_r             : std_logic_vector(7 downto 0);
157 30 andreas
        signal  SFR_RData               : std_logic_vector(7 downto 0);
158 2 jesus
 
159
        signal  Mem_Din                 : std_logic_vector(7 downto 0);
160
 
161
        signal  Bit_Pattern             : std_logic_vector(7 downto 0);
162
 
163
        -- Registered instruction words.
164
        signal  Inst                    : std_logic_vector(7 downto 0);
165
        signal  Inst1                   : std_logic_vector(7 downto 0);
166
        signal  Inst2                   : std_logic_vector(7 downto 0);
167
 
168
        -- Control signals
169
        signal  Rst_r_n                 : std_logic;
170
        signal  Last                    : std_logic;
171
        signal  SFR_Wr_i                : std_logic;
172
        signal  Mem_Wr                  : std_logic;
173
        signal  J_Skip                  : std_logic;
174
        signal  IPending                : std_logic;
175
        signal  Int_Trig_r              : std_logic_vector(6 downto 0);
176
        signal  IStart                  : std_logic;
177
        signal  ICall                   : std_logic;
178
        signal  HPInt                   : std_logic;
179
        signal  LPInt                   : std_logic;
180
        signal  PCPaused                : std_logic_vector(3 downto 0);
181
        signal  PCPause                 : std_logic;
182
        signal  Inst_Skip               : std_logic;
183
        signal  Div_Rdy                 : std_logic;
184
        signal  RAM_Rd_i                : std_logic;
185 32 andreas
        signal  RAM_Wr_i                : std_logic;
186 2 jesus
        signal  INC_DPTR                : std_logic;
187 4 jesus
        signal  CJNE                    : std_logic;
188
        signal  DJNZ                    : std_logic;
189 2 jesus
 
190
        -- Mux control
191
        signal  AMux_SFR                : std_logic;
192
        signal  BMux_Inst2              : std_logic;
193
        signal  RMux_PCL                : std_logic;
194
        signal  RMux_PCH                : std_logic;
195
 
196 30 andreas
  signal  next_Mem_Wr : std_logic;
197
 
198
  signal rd_flag,xxx_flag : std_logic;
199
  signal rd_flag_r        : std_ulogic;
200
  signal rd_sfr_flag      : std_logic;
201
  signal Do_ACC_Wr        : std_logic;
202 32 andreas
 
203
  signal ramc,ramc_r,ramrw_r : std_logic;
204 2 jesus
begin
205
 
206 30 andreas
  iReady <= Ready and not xxx_flag;
207 32 andreas
  ram_cycle <= ramc;
208
 
209 2 jesus
        Last <= '1' when ICall = '1' and FCycle = "11" else
210
                        '0' when ICall = '1' else
211 30 andreas
                        '1' when MCode(1 downto 0) = FCycle and iReady = '1' else
212
                        '0';
213 2 jesus
 
214 30 andreas
  --      (ROM_Data, ICall, Inst, Inst1, Inst2, Last, FCycle, PSW, Mem_B, SP, Old_Mem_B, Ready, Int_AddrA_r)
215
        process (FCycle, ICall, Inst, Inst1, Inst2, Int_AddrA_r, Last, Mem_B, Old_Mem_B, PSW,
216
             ROM_Data, Ready, SP, SFR_Wr_i, Res_Bus)
217 2 jesus
        begin
218
                Int_AddrA <= "--------";
219 30 andreas
--              Int_AddrB <= "--------";
220
    Int_AddrB <= "000" & PSW(4 downto 3) & "00" & Inst(0);
221
          rd_flag     <= '0';
222
          rd_sfr_flag <= '0';
223
 
224 2 jesus
                if Inst(3 downto 0) = "0000" or Inst(3 downto 0) = "0010" then
225
                        if Inst(3 downto 0) = "0000" or (Inst(3 downto 0) = "0010" and (Inst(7) = '1' or Inst(6 downto 4) = "111")) then
226
                                if Inst1(7) = '0' then
227
                                        Int_AddrA <= "0010" & Inst1(6 downto 3);
228
                                else
229
                                        Int_AddrA <= "1" & Inst1(6 downto 3) & "000";
230
                                end if;
231
                        else
232
                                Int_AddrA <= Inst1;
233
                        end if;
234
                        if Inst = "00010010" or ICall = '1' then
235
                                -- LCALL
236
                                if FCycle = "01" then
237
                                        Int_AddrA <= std_logic_vector(SP + 1);
238
                                else
239
                                        Int_AddrA <= std_logic_vector(SP + 2);
240
                                end if;
241
                        end if;
242
                        if Inst = "11000000" then
243
                                -- 11000000 2 PUSH  data addr           INC SP: MOV "@SP",<src>
244
                                if FCycle = "10" then
245
                                        Int_AddrA <= std_logic_vector(SP);
246
                                else
247
                                        Int_AddrA <= Inst1;
248
                                end if;
249
                        end if;
250
                        if Inst = "11010000" then
251
                                -- 11010000 2 POP   data addr           MOV <dest>,"@SP": DEC SP
252
                                if FCycle = "10" then
253
                                        Int_AddrA <= Inst1;
254
                                else
255
                                        Int_AddrA <= std_logic_vector(SP);
256
                                end if;
257
                        end if;
258
                        if Inst(7 downto 5) = "001" and Inst(3 downto 0) = "0010" then
259
                                -- RET, RETI
260
                                Int_AddrA <= std_logic_vector(SP);
261
                                Int_AddrB <= std_logic_vector(SP - 1);
262
                        end if;
263
                elsif Inst(4 downto 0) = "10001" then
264
                        -- ACALL
265
                        if FCycle = "01" then
266
                                Int_AddrA <= std_logic_vector(SP + 1);
267
                        else
268
                                Int_AddrA <= std_logic_vector(SP + 2);
269
                        end if;
270
                elsif Inst(3 downto 0) = "0011" then
271
                        Int_AddrA <= inst1;
272
                elsif Inst(3 downto 0) = "0100" then
273
                elsif Inst(3 downto 0) = "0101" then
274
                        if Inst(7 downto 4) = "1000" and FCycle = "11" then
275
                                Int_AddrA <= Inst2;
276
                        else
277
                                Int_AddrA <= Inst1;
278
                        end if;
279 30 andreas
                elsif Inst(3 downto 1) = "011" then   -- @Ri Adressing mode
280 2 jesus
                        if FCycle(1 downto 0) = "01" then
281
                                Int_AddrA <= Mem_B;
282
                        else
283
                                Int_AddrA <= Old_Mem_B;
284
                        end if;
285
                        if Inst(7 downto 4) = "1000" and FCycle = "10" then
286 30 andreas
                                Int_AddrA <= Inst1;   -- mov direct,@Ri
287 2 jesus
                        end if;
288
                        if Inst(7 downto 4) = "1010" and FCycle = "01" then
289 30 andreas
                          Int_AddrA <= ROM_Data;  -- mov @Ri,direct
290
                                rd_flag   <= '1';
291 2 jesus
                        end if;
292
                elsif Inst(3) = '1' then
293
                        Int_AddrA <= "000" & PSW(4 downto 3) & Inst(2 downto 0);
294
                        if Inst(7 downto 4) = "1000" and FCycle = "10" then
295
                                Int_AddrA <= Inst1;
296
                        end if;
297
                        if Inst(7 downto 4) = "1010" and FCycle = "01" then
298 30 andreas
                  Int_AddrA <= ROM_Data;  -- mov Ri,data
299
                                rd_flag   <= '1';
300 2 jesus
                        end if;
301
                end if;
302 30 andreas
 
303
--              if Last = '1' then
304
     -- Modified by AVG
305
      if (Inst(7 downto 5) /= "001" or Inst(3 downto 0) /= "0010") and -- not a RET, RETI
306
        (ROM_Data(3 downto 1) = "011" or -- Next or current Instruction has @Ri Addressing Mode
307
         Inst(3 downto 1) = "011" or
308
         ROM_Data(7 downto 1)="1110001" or ROM_Data(7 downto 1)="1111001") then  -- MOVX @Ri,A ; MOVX A,@Ri
309
        if Last = '1' then
310
                                  Int_AddrB   <= "000" & PSW(4 downto 3) & "00" & ROM_Data(0);
311
                                -- write to psw is in progress => forward argument
312
                                -- decreases timing !!!
313 35 andreas
                                if fast_cpu_c/=0 and SFR_Wr_i = '1' and Int_AddrA_r = "11010000" then
314 30 andreas
                                  Int_AddrB <= "000" & Res_Bus(4 downto 3) & "00" & ROM_Data(0);
315
                                end if;
316
                                end if;
317
                                rd_sfr_flag <= '1';
318
 
319 2 jesus
                        end if;
320 30 andreas
--              end if;
321
--              if Inst(7 downto 1) = "1011011" then  -- cjne @ri,#im
322
--                Int_AddrB <= "000" & PSW(4 downto 3) & "00" & Inst(0);
323
--              end if;
324
 
325 4 jesus
                if Ready = '0' then
326
                        Int_AddrA <= Int_AddrA_r;
327
                end if;
328 2 jesus
        end process;
329 30 andreas
 
330
        Op_A <= SFR_RData_r when AMux_SFR = '1' else
331
                Mem_A;
332
 
333
        Op_B <= Inst2 when BMux_Inst2 = '1' else
334
                Inst1;
335
 
336
        -- Store return Address to mem (Stack) when a call (or interrupt) occured
337 2 jesus
        Mem_Din <= PCC(7 downto 0) when RMux_PCL = '1' else
338
                        PCC(15 downto 8) when RMux_PCH = '1' else
339
                        Res_Bus;
340 30 andreas
 
341
 
342 2 jesus
        process (Clk)
343
        begin
344
                if Clk'event and Clk = '1' then
345
                        AMux_SFR <= '0';
346
                        BMux_Inst2 <= '0';
347
                        RMux_PCL <= '0';
348
                        RMux_PCH <= '0';
349
 
350
                        if Int_AddrA(7) = '1' then
351
                                AMux_SFR <= '1';
352
                        end if;
353 30 andreas
                        if Inst(3 downto 1) = "011" then -- relative addressing mode
354
                          -- not "mov @ri,direct"
355
                                if not (Inst(7 downto 4) = "1010") then -- and FCycle = "10") then
356 2 jesus
                                        -- Indirect addressing
357
                                        AMux_SFR <= '0';
358
                                end if;
359
                        end if;
360
                        if Inst = "11010000" then
361
                                -- 11010000 2 POP   data addr           MOV <dest>,"@SP": DEC SP
362 30 andreas
--                              if FCycle = "10" then
363 2 jesus
                                        AMux_SFR <= '0';
364 30 andreas
--                              end if;
365 2 jesus
                        end if;
366
 
367
                        if Inst(3 downto 0) = "0011" or Inst(3 downto 0) = "0101" then
368
                                BMux_Inst2 <= '1';
369
                        end if;
370
 
371
                        -- LCALL, ACALL, Int
372
                        if (Inst = "00010010" or Inst(4 downto 0) = "10001" or ICall = '1') then
373
                                if FCycle = "01" then
374
                                        RMux_PCL <= '1';
375
                                elsif FCycle = "10" then
376
                                        RMux_PCH <= '1';
377
                                end if;
378
                        end if;
379
                end if;
380
        end process;
381 30 andreas
 
382 2 jesus
        SFR_Wr <= SFR_Wr_i;
383
        SFR_Addr <= Int_AddrA(6 downto 0);
384
        SFR_WData <= Res_Bus;
385 30 andreas
 
386
        SFR_Rd_RMW <= '1' when Last = '1' and MCode(3) = '1' and Int_AddrA(7) = '1' and
387
                               (Inst(7 downto 4) = "1000" or Inst(3 downto 1) /= "011") and
388
                               Inst /= "11000000" else -- no push
389
                      '0';
390
 
391
        next_Mem_Wr <= '1' when Last = '1' and MCode(3) = '1' and
392
                                (Int_AddrA(7) = '0' or
393
                                -- Instruction is no MOV and indirect addressing mode
394
                                (Inst(7 downto 4) /= "1000" and Inst(3 downto 1) = "011") or
395
                                Inst = "11000000" ) else  -- PUSH Instruction
396
                       '0';
397
 
398
 
399 2 jesus
        process (Clk)
400
        begin
401
                if Clk'event and Clk = '1' then
402
                        SFR_Wr_i <= '0';
403
                        Mem_Wr <= '0';
404
                        if Last = '1' and MCode(3) = '1' then
405 30 andreas
                          -- MOV or no indirect addressing
406
                                if Int_AddrA(7) = '1' and (Inst(7 downto 4) = "1000" or Inst(3 downto 1) /= "011") and
407
                                   Inst /= "11000000"  then
408 2 jesus
                                        -- Direct addressing
409 33 andreas
                                        if(Inst = "00010000") then -- JBC, write result only back if jump is taken
410
                                          SFR_Wr_i <= J_Skip;
411
                                        else
412
                                          -- Direct addressing
413
                                          SFR_Wr_i <= '1';
414
          end if;
415 2 jesus
                                else
416
                                        Mem_Wr <= '1';
417
                                end if;
418
                        end if;
419
 
420
                        -- LCALL, ACALL, Int
421 30 andreas
                        if iReady = '1' and (Inst = "00010010" or Inst(4 downto 0) = "10001" or ICall = '1') then
422 2 jesus
                                if FCycle /= "11" then -- LCALL
423
                                        Mem_Wr <= '1';
424
                                end if;
425
                        end if;
426
                end if;
427
        end process;
428
 
429
        -- Instruction register
430 4 jesus
        Inst_Skip <= RET_r or J_Skip; -- '1' when (RET_r = '1' and unsigned(Mem_B) /= PC(15 downto 8)) else J_Skip; ????????????
431 30 andreas
--      Ri_Stall <= '1' when Inst /= "00000000" and
432
--                              Int_AddrA = "000" & PSW(4 downto 3) & Inst(2 downto 0) and  --Write to Ri in Progress
433
--                              ROM_Data(3 downto 1) = "011" and  --@Ri at next opcode
434
--                              Last = '1' and MCode(3) = '1' else '0';
435
 
436
-- WHEN MCODE(3)==1 => Write to Memory or FSR is in Progress
437
 
438
  -- Modified by AVG
439
  Ri_Stall <= '1' when Inst /= "00000000" and
440
                      next_Mem_Wr ='1' and
441
                      (Int_AddrA = "000" & PSW(4 downto 3) & "00"&ROM_Data(0) and
442
                       (ROM_Data(3 downto 1) = "011" or -- @Ri at next opcode 
443
                        ROM_Data(7 downto 1)="1110001" or -- movx a,@ri at next opcode
444
                        ROM_Data(7 downto 1)="1111001")) -- movx @ri,a at next opcod
445
              else '0';
446
 
447
-- WHEN MCODE(3)==1 => Write to Memory or FSR is in Progress                    
448
  -- Modified by AVG
449
        PSW_Stall <= '1' when Int_AddrA = "11010000" and
450
                              next_Mem_Wr='0' and -- PSW Adressed and no memory write
451
                                          (ROM_Data(3 downto 1) = "011" or  -- @Ri at next opcode
452
                                           ROM_Data(3) = '1') and           -- Rx at next opcode
453
                                          Last = '1' and
454
                                          MCode(3) = '1' else
455
              '0';
456
 
457
-- WHEN MCODE(2)==1 => Write to ACC in Progress 
458
-- Stall Pipe when Write to ACC is in Progress and next Instruction is JMP @A+DPTR      
459
-- Modified by AVG
460
        ACC_Stall <= '1' when ROM_Data = "01110011" and
461
                              Last = '1' and MCode(2) = '1' else
462
                     '0';
463
 
464
        -- when a write to SP is in progress
465
        -- and next opcode is a call or interrupt
466
        -- -> stall pipe (nop insertion)                      
467
        -- Modified by AVG
468
        SP_Stall <= '1' when Last = '1' and MCode(3) = '1' and
469
                                          Int_AddrA = "10000001" and
470
                                          (Inst(7 downto 4) = "1000" or     -- mov opcode
471
                                           Inst(3 downto 1) /= "011") and   -- and no indirect addressing
472
                                           Inst /= "11000000" and           -- and not PUSH
473
                                          (ROM_Data = "00010010" or
474
                                           ROM_Data(4 downto 0) = "10001" or
475
                                           IStart = '1') else -- LCALL, ACALL, Int
476
                                     '0';
477 32 andreas
 
478
  -- to subsequent movx instructions
479
  movx_Stall <= '1' when Last = '1' and
480
                        -- movx opcode at current instruction
481
                        Inst(7 downto 5) = "111" and Inst(3 downto 2) = "00" and
482
                              Inst(1 downto 0) /= "01" and
483
                              -- movx opcode at next instruction
484
                              ROM_Data(7 downto 5) = "111" and ROM_Data(3 downto 2) = "00" and
485
                              ROM_Data(1 downto 0) /= "01" else
486
                       '0';
487 30 andreas
 
488 43 andreas
        Stall_pipe <= (Ri_Stall or PSW_Stall or ACC_Stall or SP_Stall or movx_Stall) and not IStart;
489 30 andreas
 
490 2 jesus
        process (Rst_n, Clk)
491 30 andreas
          variable bitnr_v : natural range 0 to 7;
492 2 jesus
        begin
493
                if Rst_n = '0' then
494
                        Rst_r_n <= '0';
495
                        Inst <= (others => '0'); -- Force NOP at reset.
496
                        Inst1 <= (others => '0');
497
                        Inst2 <= (others => '0');
498
                        Bit_Pattern <= "00000000";
499
                elsif Clk'event and Clk = '1' then
500
                        Rst_r_n <= '1';
501 30 andreas
                        if iReady = '0' then
502
                        elsif Rst_r_n = '0' or
503
                              Inst_Skip = '1' or IStart = '1' or
504
                              Stall_pipe = '1' then
505
--                            Ri_Stall = '1' or PSW_Stall = '1' or ACC_Stall = '1' then
506 2 jesus
                                -- Skip/Stall/Flush: NOP insertion
507
                                Inst <= (others => '0');
508 32 andreas
                        elsif Inst = "10000100" and PCPause = '1' then  -- DIV
509 2 jesus
                        else
510
                                if Last = '1' then
511
                                        Inst <= ROM_Data;
512
                                end if;
513
                                if FCycle = "01" then
514
                                        Inst1 <= ROM_Data;
515
                                end if;
516
                                if FCycle = "10" then
517
                                        Inst2 <= ROM_Data;
518
                                end if;
519
                        end if;
520
                        if FCycle = "01" then
521 30 andreas
                          Bit_Pattern <= "00000000";
522
                          bitnr_v := to_integer(unsigned(ROM_Data(2 downto 0)));
523
                          Bit_Pattern(bitnr_v) <= '1';
524
 
525
--                              case ROM_Data(2 downto 0) is
526
--                              when "000" =>
527
--                                      Bit_Pattern <= "00000001";
528
--                              when "001" =>
529
--                                      Bit_Pattern <= "00000010";
530
--                              when "010" =>
531
--                                      Bit_Pattern <= "00000100";
532
--                              when "011" =>
533
--                                      Bit_Pattern <= "00001000";
534
--                              when "100" =>
535
--                                      Bit_Pattern <= "00010000";
536
--                              when "101" =>
537
--                                      Bit_Pattern <= "00100000";
538
--                              when "110" =>
539
--                                      Bit_Pattern <= "01000000";
540
--                              when others =>
541
--                                      Bit_Pattern <= "10000000";
542
--                              end case;
543 2 jesus
                        end if;
544
                end if;
545
        end process;
546
 
547
        -- Accumulator, B and status register
548 30 andreas
        tristate_mux: if tristate/=0 generate
549
        SFR_RData <= PSW & PSW0 when Int_AddrA = "11010000" else "ZZZZZZZZ";
550
        SFR_RData <= ACC when Int_AddrA = "11100000" else "ZZZZZZZZ";
551
        SFR_RData <= B when Int_AddrA = "11110000" else "ZZZZZZZZ";
552
        -- Stack pointer
553
        SFR_RData <= std_logic_vector(SP) when Int_AddrA = "10000001" else "ZZZZZZZZ";
554
 
555 35 andreas
        SFR_RData <= dptr_inc(7 downto 0) when (SecondDPTR/=0 and (INC_DPTR and next_DPS) = '1' and Int_AddrA = "10000100") or
556
                                               ((INC_DPTR and not next_DPS) = '1' and Int_AddrA = "10000010") else "ZZZZZZZZ";
557
    SFR_RData <= dptr_inc(15 downto 8) when (SecondDPTR/=0 and (INC_DPTR and next_DPS) = '1' and Int_AddrA = "10000101") or
558
                                                ((INC_DPTR and not next_DPS) = '1' and Int_AddrA = "10000011") else "ZZZZZZZZ";
559
 
560
    SFR_RData <= DPL1 when SecondDPTR/=0 and INC_DPTR='0' and Int_AddrA = "10000100" else "ZZZZZZZZ";
561
        SFR_RData <= DPH1 when SecondDPTR/=0 and INC_DPTR='0' and Int_AddrA = "10000101" else "ZZZZZZZZ";
562 30 andreas
        SFR_RData <= "0000000"&DPS when SecondDPTR/=0 and Int_AddrA = "10000110" else "ZZZZZZZZ";
563
 
564 37 andreas
        SFR_RData <= DPL0 when INC_DPTR='0' and Int_AddrA = "10000010" else "ZZZZZZZZ";
565
        SFR_RData <= DPH0 when INC_DPTR='0' and Int_AddrA = "10000011" else "ZZZZZZZZ";
566 30 andreas
        SFR_RData <= IP when Int_AddrA = "10111000" else "ZZZZZZZZ";
567
        SFR_RData <= SFR_RData_in;
568
  end generate;
569
 
570
        std_mux: if tristate=0 generate
571
          SFR_RData <= PSW & PSW0 when Int_AddrA = "11010000" else
572
                     ACC when Int_AddrA = "11100000" else
573
                     B when Int_AddrA = "11110000" else
574
                     std_logic_vector(SP) when Int_AddrA = "10000001" else
575
 
576 35 andreas
                     dptr_inc(7 downto 0) when (SecondDPTR/=0 and (INC_DPTR and next_DPS) = '1' and Int_AddrA = "10000100") or
577
                                               ((INC_DPTR and not next_DPS) = '1' and Int_AddrA = "10000010") else
578
                 dptr_inc(15 downto 8) when (SecondDPTR/=0 and (INC_DPTR and next_DPS) = '1' and Int_AddrA = "10000101") or
579 38 andreas
                                                ((INC_DPTR and not next_DPS) = '1' and Int_AddrA = "10000011") else
580
                 DPL1 when SecondDPTR/=0 and INC_DPTR='0' and Int_AddrA = "10000100" else
581
                     DPH1 when SecondDPTR/=0 and INC_DPTR='0' and Int_AddrA = "10000101" else
582 30 andreas
                     "0000000"&DPS when SecondDPTR/=0 and Int_AddrA = "10000110" else
583
 
584 38 andreas
                     DPL0 when INC_DPTR='0' and Int_AddrA = "10000010" else
585
                     DPH0 when INC_DPTR='0' and Int_AddrA = "10000011" else
586 30 andreas
                     IP when Int_AddrA = "10111000" else
587
                     SFR_RData_in;
588
 
589
 --     -- is it an internal or external read                 
590
 --   Int_Read <= '1' when Int_AddrA = "11010000" or 
591
 --                          Int_AddrA = "11100000" or 
592
 --                          Int_AddrA = "11110000" or 
593
 --                          Int_AddrA = "10000001" or 
594
 --                          
595
 --                        (SecondDPTR and Int_AddrA = "10000100") or 
596
 --                          (SecondDPTR and Int_AddrA = "10000101") or 
597
 --                          (SecondDPTR and Int_AddrA = "10000110") or 
598
 --                          
599
 --                          Int_AddrA = "10000010" or 
600
 --                          Int_AddrA = "10000011" or 
601
 --                          Int_AddrA = "10111000" else 
602
 --                 '0';
603
 
604
        end generate;
605
 
606 2 jesus
        PSW0 <= ACC(7) xor ACC(6) xor ACC(5) xor ACC(4) xor ACC(3) xor ACC(2) xor ACC(1) xor ACC(0);
607
        Next_PSW7 <= Res_Bus(7) when SFR_Wr_i = '1' and Int_AddrA_r = "11010000" else
608
                                Status_D(7) when Status_Wr(7) = '1' else
609
                                PSW(7);
610
        Next_ACC_Z <= '1' when ACC_Q = "00000000" and ACC_Wr = '1' else
611
                                '1' when ACC = "00000000" else '0';
612 30 andreas
 
613 2 jesus
        process (Rst_n, Clk)
614 30 andreas
--              variable B_Wr : std_logic;
615 2 jesus
        begin
616
                if Rst_n = '0' then
617
                        PSW <= "0000000";
618
                        ACC <= "00000000";
619
                        B <= "00000000";
620
                        ACC_Wr <= '0';
621 30 andreas
                        B_Wr <= '0';
622 2 jesus
                elsif Clk'event and Clk = '1' then
623
                        if ACC_Wr = '1' then
624
                                ACC <= ACC_Q;
625
                        end if;
626
                        if B_Wr = '1' then
627
                                B <= B_Q;
628
                        end if;
629
                        if (MCode(2) and Last) = '1' or (Inst = "10000100" and PCPause = '0') then
630
                                ACC_Wr <= '1';
631
                        else
632
                                ACC_Wr <= '0';
633
                        end if;
634
                        if ((Inst = "10000100" and PCPause = '0') or Inst = "10100100") and Last = '1' then --  DIV, MUL
635 30 andreas
                                B_Wr <= '1';
636 2 jesus
                        else
637 30 andreas
                                B_Wr <= '0';
638 2 jesus
                        end if;
639
 
640
                        if SFR_Wr_i = '1' and Int_AddrA_r = "11100000" then
641
                                ACC <= Res_Bus;
642
                        end if;
643
 
644
                        if RAM_Rd_i = '1' then
645
                                ACC <= RAM_RData;
646
                        end if;
647
 
648
                        if SFR_Wr_i = '1' and Int_AddrA_r = "11110000" then
649
                                B <= Res_Bus;
650
                        end if;
651
 
652
                        if Inst(7 downto 5) = "100" and Inst(3 downto 0) = "0011" then -- MOVC
653
                                if FCycle = "11" then
654
                                        ACC <= ROM_Data;
655
                                end if;
656
                        end if;
657
 
658
                        if SFR_Wr_i = '1' and Int_AddrA_r = "11010000" then
659
                                PSW <= Res_Bus(7 downto 1);
660
                        end if;
661
                        -- CY
662
                        if Status_Wr(7) = '1' then PSW(7) <= Status_D(7); end if;
663
                        -- AC
664
                        if Status_Wr(6) = '1' then PSW(6) <= Status_D(6); end if;
665
                        -- OV
666
                        if Status_Wr(5) = '1' then PSW(2) <= Status_D(5); end if;
667
                end if;
668
        end process;
669
 
670 30 andreas
 
671 2 jesus
        process (Rst_n, Clk)
672
        begin
673
                if Rst_n = '0' then
674
                        SP <= "00000111";
675
                elsif Clk'event and Clk = '1' then
676
                        if SFR_Wr_i = '1' and Int_AddrA_r = "10000001" then
677
                                SP <= unsigned(Res_Bus);
678
                        end if;
679 30 andreas
                        if iReady = '1' then
680 4 jesus
                                if Inst(7 downto 5) = "001" and Inst(3 downto 0) = "0010" then
681
                                        SP <= SP - 2;
682
                                end if;
683
                                if (Inst = "00010010" or Inst(4 downto 0) = "10001" or ICall = '1') and Last = '1' then
684
                                        -- LCALL, ACALL, ICall
685
                                        SP <= SP + 2;
686
                                end if;
687
                                if Inst = "11000000" and PCPaused(0) = '1' then
688
                                        -- 11000000 2 PUSH  data addr           INC SP: MOV "@SP",<src>
689
                                        SP <= SP + 1;
690
                                end if;
691
                                if Inst = "11010000" and Last = '1' then
692
                                        -- 11010000 2 POP   data addr           MOV <dest>,"@SP": DEC SP
693
                                        SP <= SP - 1;
694
                                end if;
695 2 jesus
                        end if;
696
                end if;
697
        end process;
698
 
699 30 andreas
  twoDPTR: if SecondDPTR/=0 generate
700
    next_DPS <= Res_Bus(0) when SFR_Wr_i = '1' and Int_AddrA_r = "10000110" else
701
                DPS;
702
 
703
    DPL <= DPL0 when next_DPS='0' else
704
           DPL1;
705
    DPH <= DPH0 when next_DPS='0' else
706
           DPH1;
707
--      SFR_RData <= DPL1 when Int_AddrA = "10000100" else "ZZZZZZZZ";
708
--      SFR_RData <= DPH1 when Int_AddrA = "10000101" else "ZZZZZZZZ";
709
--      SFR_RData <= "0000000"&DPS when Int_AddrA = "10000110" else "ZZZZZZZZ";
710
  end generate;
711
  oneDPTR: if SecondDPTR=0 generate
712
    DPL <= DPL0;
713
    DPH <= DPH0;
714
    next_DPS <= '0';
715
  end generate;
716
 
717 2 jesus
        -- DPTR/RAM_Addr
718
        RAM_WData <= ACC;
719 30 andreas
    --(Inst, P2R, DPH, DPL, Int_AddrA_r, SFR_Wr_i, Res_Bus, INC_DPTR, Mem_B)
720 35 andreas
        process (DPH, DPL, INC_DPTR, dptr_inc, Inst, Int_AddrA_r, Mem_B, P2R, Res_Bus, SFR_Wr_i, DPS)
721 2 jesus
        begin
722
                RAM_Addr <= DPH & DPL;
723
                if Inst(1) = '0' then
724 30 andreas
                        if (SFR_Wr_i = '1' and Int_AddrA_r = "10000010" and DPS = '0') or
725
                           (SecondDPTR/=0 and SFR_Wr_i = '1' and Int_AddrA_r = "10000100"  and DPS = '1')
726
                        then
727 2 jesus
                                RAM_Addr(7 downto 0) <= Res_Bus;
728
                        end if;
729 30 andreas
                        if (SFR_Wr_i = '1' and Int_AddrA_r = "10000011" and DPS = '0') or
730
                           (SecondDPTR/=0 and SFR_Wr_i = '1' and Int_AddrA_r = "10000101" and DPS = '1')
731
                        then
732 2 jesus
                                RAM_Addr(15 downto 8) <= Res_Bus;
733
                        end if;
734
                        -- 10100011 1 INC   DPTR
735
                        if INC_DPTR = '1' then
736 35 andreas
--                              RAM_Addr <= std_logic_vector(unsigned(DPH) & unsigned(DPL) + 1);
737
        RAM_Addr <= dptr_inc;
738 2 jesus
                        end if;
739 30 andreas
                else -- movx a,@ri or movx @ri,a
740 2 jesus
                        RAM_Addr <= P2R & Mem_B;
741
                        if SFR_Wr_i = '1' and Int_AddrA_r = "10100000" then
742
                                RAM_Addr(15 downto 8) <= Res_Bus;
743
                        end if;
744
                end if;
745
        end process;
746 30 andreas
 
747 32 andreas
        --if Inst(7 downto 2) = "111000" and Inst(1 downto 0) /= "01" then
748 30 andreas
        -- MOVX Instruction
749 32 andreas
        ramc <= '1' when Inst(7 downto 5) = "111" and Inst(3 downto 2) = "00" and
750 30 andreas
                              Inst(1 downto 0) /= "01" and
751
                              PCPaused(0) = '0' else
752 32 andreas
                '0';
753 30 andreas
 
754 32 andreas
--      RAM_Rd <= RAM_Rd_i and ramc and not ramrw_r when DualBus=0 else
755
--                RAM_Rd_i and ramc;
756 39 andreas
  RAM_Rd <= RAM_Rd_i and ramc when t8032=0 else
757
            RAM_Rd_i;
758 32 andreas
 
759
        RAM_Wr <= RAM_Wr_i;
760 30 andreas
 
761
        Do_ACC_Wr <= '1' when (ACC_Wr or RAM_Rd_i)='1' or
762
                              (SFR_Wr_i = '1' and Int_AddrA_r = "11100000") else
763
                     '0';
764
 
765
-- Gefählich sind:
766
-- mov @Ri,direct
767
-- mov Ri,data
768
-- da diese Befehle die Quelldaten einen Takt früher lesen als alle anderen Befehle
769 35 andreas
 
770 30 andreas
--      xxx_flag <= '1' when ((SFR_Wr_i and rd_flag)= '1' and Int_AddrA_r=Int_AddrA) or
771
--                            ((Do_ACC_Wr and rd_flag)='1' and Int_AddrA = "11010000") or
772
--                            (Status_Wr/="000" and rd_flag='1' and Int_AddrA="11010000") or
773 35 andreas
--                            (fast_cpu_c=0 and (rd_sfr_flag and SFR_Wr_i) = '1' and Int_AddrA_r = "11010000") else
774 30 andreas
--                  '0';
775 35 andreas
  fast: if fast_cpu_c/=0 generate
776 30 andreas
        xxx_flag <= '1' when ((SFR_Wr_i and rd_flag)= '1' and Int_AddrA_r=Int_AddrA) or
777 32 andreas
                              ((Do_ACC_Wr and rd_flag)='1' and Int_AddrA = "11010000") or  -- WR to ACC in Progress and read from PSW
778 30 andreas
                              ((B_Wr and rd_flag)= '1' and Int_AddrA = "11110000") or
779 32 andreas
                              (Status_Wr/="000" and rd_flag='1' and Int_AddrA="11010000") or
780
--                            (ramc='1' and ramc_r='0')
781 39 andreas
                          (t8032=0 and Inst(7 downto 2) = "111000" and Inst(1 downto 0) /= "01" and ramc_r='0') --MOVX A,??
782 32 andreas
--                          (((RAM_Rd_i and ramc)='1' or RAM_Wr_i='1') and ramrw_r='0' and DualBus=0) 
783
                              else
784 30 andreas
                    '0';
785
        end generate;
786 35 andreas
        slow: if fast_cpu_c=0 generate
787 30 andreas
          -- Inserts an Waitstate on every mov @Ri,direct or mov Ri,data Instruction
788 32 andreas
        xxx_flag <= '1' when (rd_flag and not rd_flag_r) = '1' or                                        -- mov @ri,direct or mov ri,direct
789
                             ((rd_sfr_flag and SFR_Wr_i) = '1' and Int_AddrA_r = "11010000")  or         -- Wr to PSW and @Ri Adressing at next instruction
790
--                           (ramc='1' and ramc_r='0')
791 39 andreas
                         (t8032=0 and Inst(7 downto 2) = "111000" and Inst(1 downto 0) /= "01" and ramc_r='0') or  --MOVX A,??
792 32 andreas
--                         (((RAM_Rd_i and ramc)='1' or RAM_Wr_i='1') and ramrw_r='0' and DualBus=0) 
793 39 andreas
                         (t8032=0 and (RAM_Wr_i='1') and ramrw_r='0' and DualBus=0)
794 32 andreas
                             else
795 30 andreas
                    '0';
796 32 andreas
 
797 30 andreas
    process(Rst_n, Clk)
798
    begin
799
      if Rst_n = '0' then
800
        rd_flag_r <= '0';
801
      elsif Clk'event and Clk = '1' then
802
        rd_flag_r <= rd_flag;
803
      end if;
804
    end process;
805
 
806
        end generate;
807
 
808 2 jesus
        process (Rst_n, Clk)
809
                variable tmp : unsigned(15 downto 0);
810
        begin
811
                if Rst_n = '0' then
812
                        P2R <= "11111111";
813 30 andreas
                        DPL0 <= "00000000";
814
                        DPH0 <= "00000000";
815 2 jesus
                        INC_DPTR <= '0';
816 19 jesus
                        RAM_Rd_i <= '0';
817 32 andreas
                        RAM_Wr_i <= '0';
818 30 andreas
                        if SecondDPTR/=0 then
819
                          DPL1   <= "00000000";
820
                          DPH1   <= "00000000";
821
                          DPS_r  <= '0';
822
                        end if;
823 32 andreas
                        ramc_r <= '0';
824
                        ramrw_r <= '0';
825 2 jesus
                elsif Clk'event and Clk = '1' then
826 32 andreas
                  if Ready='1' then
827
                    ramc_r  <= ramc;
828
                    ramrw_r <= (RAM_Rd_i and ramc) or RAM_Wr_i;
829
                  end if;
830 19 jesus
                        if SFR_Wr_i = '1' and Int_AddrA_r = "10100000" then
831
                                P2R <= Res_Bus;
832
                        end if;
833
                        if SFR_Wr_i = '1' and Int_AddrA_r = "10000010" then
834 30 andreas
                                DPL0 <= Res_Bus;
835 19 jesus
                        end if;
836
                        if SFR_Wr_i = '1' and Int_AddrA_r = "10000011" then
837 30 andreas
                                DPH0 <= Res_Bus;
838 19 jesus
                        end if;
839 30 andreas
                        if SecondDPTR/=0 then
840
                        if SFR_Wr_i = '1' and Int_AddrA_r = "10000100" then
841
                                DPL1 <= Res_Bus;
842
                        end if;
843
                        if SFR_Wr_i = '1' and Int_AddrA_r = "10000101" then
844
                                DPH1 <= Res_Bus;
845
                        end if;
846
                        if SFR_Wr_i = '1' and Int_AddrA_r = "10000110" then
847
                                DPS_r <= Res_Bus(0);
848
                        end if;
849
                        end if;
850
                        if iReady = '1' then
851
                                if SecondDPTR=0 or
852
                                   (SecondDPTR/=0 and DPS='0') then
853
                                  -- 10010000 3 MOV   DPTR,#data
854
                                if Inst = "10010000" and FCycle = "10" then
855
                                        DPH0 <= Inst1;
856
                                end if;
857
                                if Inst = "10010000" and FCycle = "11" then
858
                                        DPL0 <= Inst2;
859
                                end if;
860
                                -- 10100011 1 INC   DPTR
861
                                if INC_DPTR = '1' then
862 35 andreas
--                                      tmp := unsigned(DPH) & unsigned(DPL) + 1;
863
--                                      DPH0 <= std_logic_vector(tmp(15 downto 8));
864
--                                      DPL0 <= std_logic_vector(tmp(7 downto 0));
865
            DPH0 <= dptr_inc(15 downto 8);
866
            DPL0 <= dptr_inc(7 downto 0);
867 30 andreas
                                end if;
868
                  elsif SecondDPTR/=0 and DPS='1' then
869
                    -- 10010000 3 MOV   DPTR,#data
870
                    if Inst = "10010000" and FCycle = "10" then
871
                                        DPH1 <= Inst1;
872
                                end if;
873
                                if Inst = "10010000" and FCycle = "11" then
874
                                        DPL1 <= Inst2;
875
                                end if;
876
                                -- 10100011 1 INC   DPTR
877
                                if INC_DPTR = '1' then
878 35 andreas
--                                      tmp := unsigned(DPH) & unsigned(DPL) + 1;
879
--                                      DPH1 <= std_logic_vector(tmp(15 downto 8));
880
--                                      DPL1 <= std_logic_vector(tmp(7 downto 0));
881
            DPH1 <= dptr_inc(15 downto 8);
882
            DPL1 <= dptr_inc(7 downto 0);
883 30 andreas
                                end if;
884
                  end if;
885 4 jesus
                                INC_DPTR <= '0';
886
                                if Inst = "10100011" then
887
                                        INC_DPTR <= '1';
888
                                end if;
889 2 jesus
                        end if;
890 39 andreas
                        if Ready='1' or t8032/=0 then
891 32 andreas
                        RAM_Wr_i <= '0';
892
                        -- movx instruction
893 39 andreas
                        if t8032=0 then
894
                          if (Inst(7 downto 2) = "111100" and Inst(1 downto 0) /= "01") then
895
                                  RAM_Wr_i <= '1';
896
                          end if;
897
                        elsif (Inst(7 downto 2) = "111100" and Inst(1 downto 0) /= "01" and DualBus/=0) or
898
                                      (Inst(7 downto 2) = "111100" and Inst(1 downto 0) /= "01" and iReady = '0' and DualBus=0) then
899
                                  RAM_Wr_i <= '1';
900 32 andreas
                        end if;
901
                        RAM_Rd_i <= '0';
902
  --                    if Inst(7 downto 2) = "111000" and Inst(1 downto 0) /= "01" and iReady = '1' then
903
        if Inst(7 downto 2) = "111000" and Inst(1 downto 0) /= "01" then
904
                                RAM_Rd_i <= '1';
905
                        end if;
906 19 jesus
                        end if;
907 2 jesus
                end if;
908
        end process;
909 30 andreas
 
910 35 andreas
  dptr_inc <= std_logic_vector(unsigned(DPH) & unsigned(DPL) + 1);
911
 
912 30 andreas
  process(DPS_r)
913
  begin
914
    if SecondDPTR/=0 then
915
      DPS <= DPS_r;
916
    else
917
      DPS <= '0';
918
    end if;
919
  end process;
920 2 jesus
 
921
        -- Interrupts
922 4 jesus
        IStart <= Last and IPending and not Inst_Skip;
923 30 andreas
 
924 2 jesus
        process (Rst_n, Clk)
925
        begin
926
                if Rst_n = '0' then
927
                        LPInt <= '0';
928
                        HPInt <= '0';
929
                        Int_Acc <= (others => '0');
930
                        Int_Trig_r <= (others => '0');
931
                        IPending <= '0';
932
                        IP <= "00000000";
933
                        ICall <= '0';
934
                elsif Clk'event and Clk = '1' then
935 19 jesus
                        if SFR_Wr_i = '1' and Int_AddrA_r = "10111000" then
936
                                IP <= Res_Bus;
937
                        end if;
938 30 andreas
                        if iReady = '1' then
939 4 jesus
                                if (Int_Trig and IP(6 downto 0)) /= "0000000" and HPInt = '0' and IPending = '0' and ICall = '0' then
940
                                        Int_Trig_r <= Int_Trig and IP(6 downto 0);
941
                                        IPending <= '1';
942
                                        HPInt <= '1';
943
                                elsif Int_Trig /= "0000000" and LPInt = '0' and HPInt = '0'  and IPending = '0' and ICall = '0' then
944
                                        IPending <= '1';
945
                                        Int_Trig_r <= Int_Trig;
946
                                        LPInt <= '1';
947 2 jesus
                                end if;
948 4 jesus
                                if ICall = '1' then
949
                                        IPending <= '0';
950 2 jesus
                                end if;
951 30 andreas
                                if IStart = '1' and SP_Stall='0' then
952 4 jesus
                                        ICall <= '1';
953
                                end if;
954
                                if ICall = '1' and Last = '1' then
955
                                        ICall <= '0';
956
                                        Int_Trig_r <= (others => '0');
957
                                end if;
958
                                Int_Acc <= (others => '0');
959
                                if IPending = '1' and ICall = '1' then
960
                                        if Int_Trig_r(0) = '1' then Int_Acc(0) <= '1';
961
                                        elsif Int_Trig_r(1) = '1' then Int_Acc(1) <= '1';
962
                                        elsif Int_Trig_r(2) = '1' then Int_Acc(2) <= '1';
963
                                        elsif Int_Trig_r(3) = '1' then Int_Acc(3) <= '1';
964
                                        elsif Int_Trig_r(4) = '1' then Int_Acc(4) <= '1';
965
                                        elsif Int_Trig_r(5) = '1' then Int_Acc(5) <= '1';
966
                                        elsif Int_Trig_r(6) = '1' then Int_Acc(6) <= '1';
967
                                        end if;
968
                                end if;
969 30 andreas
                                if Inst = "00110010" then   -- reti
970 4 jesus
                                        if HPInt = '0' then
971
                                                LPInt <= '0';
972
                                        else
973
                                                HPInt <= '0';
974
                                        end if;
975
                                end if;
976 2 jesus
                        end if;
977
                end if;
978
        end process;
979
 
980
        -- Program counter
981
        ROM_Addr <= std_logic_vector(NPC);
982
        process (Rst_n, Clk)
983
        begin
984
                if Rst_n = '0' then
985 4 jesus
                        PC <= (others => '0');
986 2 jesus
                        OPC <= (others => '0');
987
                        FCycle <= "01";
988
                        RET_r <= '0';
989
                        PCPaused <= (others => '0');
990
                elsif Clk'event and Clk = '1' then
991 30 andreas
                        if iReady = '1' then
992 4 jesus
                                PC <= NPC;
993
                                RET_r <= RET;
994 2 jesus
 
995 4 jesus
                                if PCPause = '1' then
996
                                        PCPaused <= std_logic_vector(unsigned(PCPaused) + 1);
997
                                else
998
                                        PCPaused <= (others => '0');
999
                                end if;
1000 2 jesus
 
1001 4 jesus
                                if PCPause = '0' then
1002
                                        FCycle <= std_logic_vector(unsigned(FCycle) + 1);
1003
                                        if Last = '1' then
1004
                                                FCycle <= "01";
1005
                                        end if;
1006 2 jesus
                                end if;
1007
 
1008 4 jesus
                                if Inst(7 downto 5) = "100" and Inst(3 downto 0) = "0011" then -- MOVC
1009
                                        if FCycle = "01" then
1010
                                                OPC <= PC;
1011
                                        end if;
1012 2 jesus
                                end if;
1013
                        end if;
1014
                end if;
1015
        end process;
1016 30 andreas
 
1017
--            (FCycle, Inst, Inst2, CJNE, DJNZ, PC, OPC, Inst1, ROM_Data,
1018
--                      Next_PSW7, Next_ACC_Z, DPL, DPH, ACC, PCPaused, Op_A, Mem_A, Mem_B,
1019
--                      Bit_Pattern, Ri_Stall, PSW_Stall, ACC_Stall, RET_r, Div_Rdy, ICall,
1020
--                      Int_Trig_r, Ready, Rst_r_n)
1021
 
1022
        process (ACC, Bit_Pattern, CJNE, DJNZ, DPH, DPL, Div_Rdy, FCycle, ICall,
1023
             Inst, Inst1, Inst2, Int_Trig_r, Mem_A, Mem_B, Next_ACC_Z, Next_PSW7, OPC,
1024 32 andreas
             Op_A, PC, PCPaused, RET_r, ROM_Data, iReady, Rst_r_n, Stall_pipe,RAM_Rd_i,RAM_Wr_i,ramc)
1025 2 jesus
        begin
1026
                NPC <= PC;
1027
                J_Skip <= '0';
1028
                RET <= '0';
1029
                PCPause <= '0';
1030 30 andreas
                -- push,pop
1031 2 jesus
                if (Inst(7 downto 5) = "110" and Inst(3 downto 0) = "0000" and FCycle = "01" and PCPaused(0) = '0') or -- PUSH, POP
1032 39 andreas
      (t8032=0 and Inst(7 downto 2) = "111000" and Inst(1 downto 0) /= "01" and DualBus=0 and PCPaused(0) = '0') or
1033
      (t8032/=0 and Inst(7 downto 5) = "111" and Inst(3 downto 2) = "00" and Inst(1 downto 0) /= "01" and DualBus=0 and PCPaused(0) = '0') or -- Single bus MOVX
1034 2 jesus
                        (Inst = "10000100" and (PCPaused(3 downto 1) = "000" or Div_Rdy = '0')) then -- DIV
1035
                        PCPause <= '1';
1036
                else
1037 30 andreas
--                      if Ri_Stall = '0' and PSW_Stall = '0' and ACC_Stall='0' then
1038
      if Stall_pipe = '0' then
1039 2 jesus
                                NPC <= PC + 1;
1040
                        end if;
1041
                end if;
1042 19 jesus
                -- Single bus MOVX
1043 39 andreas
    if (t8032=0 and Inst(7 downto 2) = "111000" and Inst(1 downto 0) /= "01"  and DualBus=0) or
1044
       (t8032/=0 and Inst(7 downto 5) = "111" and Inst(3 downto 2) = "00" and Inst(1 downto 0) /= "01" and DualBus=0) then
1045 19 jesus
                        J_Skip <= '1';
1046
                end if;
1047 2 jesus
                -- Return
1048
                if Inst(7 downto 5) = "001" and Inst(3 downto 0) = "0010" then -- RET, RETI
1049
                        RET <= '1';
1050
                        J_Skip <= '1';
1051
                end if;
1052
                -- MOVC
1053
                if Inst(7 downto 5) = "100" and Inst(3 downto 0) = "0011" and FCycle = "11" then
1054
                        NPC <= OPC;
1055
                        J_Skip <= '1';
1056
                end if;
1057
                -- 2 byte 8 bit relative jump
1058
                if FCycle = "10" then
1059
                        if (Inst = "01000000" and Next_PSW7 = '1') or -- JC
1060
                                (Inst = "01010000" and Next_PSW7 = '0') or -- JNC
1061
                                (Inst = "01100000" and Next_ACC_Z = '1') or -- JZ
1062
                                (Inst = "01110000" and Next_ACC_Z = '0') or -- JNZ
1063 4 jesus
                                (Inst(7 downto 3) = "11011" and DJNZ = '1') or -- DJNZ
1064 2 jesus
                                Inst = "10000000" then -- SJMP
1065
                                NPC <= PC + unsigned(resize(signed(Inst1),16));
1066
                                J_Skip <= '1';
1067
                        end if;
1068
                end if;
1069 30 andreas
 
1070 2 jesus
                -- 3 byte 8 bit relative jump
1071
                if FCycle = "11" then
1072
                        if (Inst = "00100000" or Inst = "00010000") and (Bit_Pattern and Op_A) /= "00000000" then -- JB, JBC
1073
                                NPC <= PC + unsigned(resize(signed(Inst2),16));
1074
                                J_Skip <= '1';
1075
                        end if;
1076
                        if Inst = "00110000" and (Bit_Pattern and Op_A) = "00000000" then -- JNB
1077
                                NPC <= PC + unsigned(resize(signed(Inst2),16));
1078
                                J_Skip <= '1';
1079
                        end if;
1080 4 jesus
                        if Inst(7 downto 4) = "1011" and Inst(3 downto 2) /= "00" and CJNE = '1' then -- CJNE
1081 2 jesus
                                NPC <= PC + unsigned(resize(signed(Inst2),16));
1082
                                J_Skip <= '1';
1083
                        end if;
1084 4 jesus
                        if Inst = "11010101" and DJNZ = '1' then -- DJNZ
1085 2 jesus
                                NPC <= PC + unsigned(resize(signed(Inst2),16));
1086
                                J_Skip <= '1';
1087
                        end if;
1088
                end if;
1089
                -- 11 bit absolute
1090
                if FCycle = "10" then
1091
                        if Inst(4 downto 0) = "00001" or Inst(4 downto 0) = "10001" then
1092
                                -- AJMP, ACALL
1093
                                NPC(15 downto 11) <= PC(15 downto 11);
1094
                                NPC(10 downto 8) <= unsigned(Inst(7 downto 5));
1095
                                NPC(7 downto 0) <= unsigned(Inst1);
1096
                                J_Skip <= '1';
1097
                        end if;
1098
                end if;
1099
                -- 16 bit absolute
1100
                if FCycle = "10" then
1101
                        if Inst = "00000010" or Inst = "00010010" then
1102
                                -- LJMP, LCALL
1103
                                NPC(15 downto 8) <= unsigned(Inst1);
1104
                                NPC(7 downto 0) <= unsigned(ROM_Data);
1105
                        end if;
1106
                        if ICall = '1' then
1107
                                NPC <= (1 => '1', 0 => '1', others => '0');
1108
                                if Int_Trig_r(1) = '1' then NPC(5 downto 3) <= "001";
1109
                                elsif Int_Trig_r(2) = '1' then NPC(5 downto 3) <= "010";
1110
                                elsif Int_Trig_r(3) = '1' then NPC(5 downto 3) <= "011";
1111
                                elsif Int_Trig_r(4) = '1' then NPC(5 downto 3) <= "100";
1112
                                elsif Int_Trig_r(5) = '1' then NPC(5 downto 3) <= "101";
1113
                                elsif Int_Trig_r(6) = '1' then NPC(5 downto 3) <= "110";
1114
                                end if;
1115
                        end if;
1116
                end if;
1117
                -- A+DPTR Absolute
1118
                if Inst = "01110011" then
1119
                        -- JMP @A+DPTR
1120
                        NPC <= (unsigned(DPH) & unsigned(DPL)) + unsigned(resize(signed(ACC),16));
1121
                        J_Skip <= '1';
1122
                end if;
1123
 
1124
                if Inst(7 downto 5) = "100" and Inst(3 downto 0) = "0011" then -- MOVC
1125
                        if FCycle = "10" then
1126
                                if Inst(4) = '0' then
1127
                                        NPC <= unsigned(ACC) + OPC;
1128
                                else
1129
                                        NPC <= unsigned(ACC) + (unsigned(DPH) & unsigned(DPL));
1130
                                end if;
1131
                        end if;
1132
                end if;
1133
 
1134
                if RET_r = '1' then -- and unsigned(Mem_A) /= PC(15 downto 8) then ???????????????????????????
1135
                        NPC <= unsigned(Mem_A) & unsigned(Mem_B);
1136
                end if;
1137 4 jesus
 
1138 30 andreas
                if iReady = '0' then
1139 4 jesus
                        NPC <= PC;
1140
                end if;
1141
                if Rst_r_n = '0' then
1142
                        NPC <= (others => '0');
1143
                end if;
1144 2 jesus
        end process;
1145
 
1146
        -- ALU
1147
        alu : T51_ALU
1148 30 andreas
          generic map(
1149
            tristate => tristate
1150
          )
1151 2 jesus
                port map(
1152
                        Clk => Clk,
1153
                        Last => Last,
1154
                        OpCode => Inst,
1155
                        ACC => ACC,
1156
                        B => B,
1157
                        IA => Op_A,
1158
                        IB => Op_B,
1159
                        Bit_Pattern     => Bit_Pattern,
1160
                        CY_In => PSW(7),
1161
                        AC_In => PSW(6),
1162
                        ACC_Q => ACC_Q,
1163
                        B_Q => B_Q,
1164
                        IDCPBL_Q =>     Res_Bus,
1165 4 jesus
                        Div_Rdy => Div_Rdy,
1166
                        CJNE => CJNE,
1167
                        DJNZ => DJNZ,
1168 2 jesus
                        CY_Out => Status_D(7),
1169
                        AC_Out => Status_D(6),
1170
                        OV_Out => Status_D(5),
1171
                        CY_Wr => Status_Wr(7),
1172
                        AC_Wr => Status_Wr(6),
1173 4 jesus
                        OV_Wr => Status_Wr(5));
1174 2 jesus
 
1175
        process (Clk)
1176
        begin
1177
                if Clk'event and Clk = '1' then
1178
                        Old_Mem_B <= Mem_B;
1179
                        if FCycle = "01" then
1180
                                if Inst(1) = '1' then
1181
                                        PCC <= std_logic_vector(PC + 2);
1182
                                else
1183
                                        PCC <= std_logic_vector(PC + 1);
1184
                                end if;
1185 4 jesus
                                if ICall = '1' then
1186
                                        PCC <= std_logic_vector(PC - 1);
1187
                                end if;
1188 2 jesus
                        end if;
1189
                        SFR_RData_r <= SFR_RData;
1190
                end if;
1191
        end process;
1192
 
1193 30 andreas
        Generic_MODEL: if not Altera_IRAM_c generate
1194
        ram : T51_RAM
1195
                generic map(
1196
                        RAMAddressWidth => RAMAddressWidth)
1197
                port map(
1198
                        Clk => Clk,
1199
                        Rst_n => Rst_n,
1200
                        ARE => Ready,
1201
                        Wr => Mem_Wr,
1202
                        DIn => Mem_Din,
1203
                        Int_AddrA => Int_AddrA,
1204
                        Int_AddrA_r => Int_AddrA_r,
1205
                        Int_AddrB => Int_AddrB,
1206
                        Mem_A => Mem_A,
1207
                        Mem_B => Mem_B);
1208
  end generate;
1209
  Altera_MODEL: if Altera_IRAM_c generate
1210
        ram : T51_RAM_Altera
1211
                generic map(
1212
                        RAMAddressWidth => RAMAddressWidth)
1213
                port map(
1214
                        Clk => Clk,
1215
                        Rst_n => Rst_n,
1216
                        ARE => Ready,
1217
                        Wr => Mem_Wr,
1218
                        DIn => Mem_Din,
1219
                        Int_AddrA => Int_AddrA,
1220
                        Int_AddrA_r => Int_AddrA_r,
1221
                        Int_AddrB => Int_AddrB,
1222
                        Mem_A => Mem_A,
1223
                        Mem_B => Mem_B);
1224
  end generate;
1225
 
1226
  IRAM_Wr    <= Mem_Wr;
1227
  IRAM_Addr  <= Int_AddrA_r;
1228
  IRAM_WData <= Mem_Din;
1229
 
1230 2 jesus
        process (Inst)
1231
        begin
1232
                case Inst is
1233
                -- 1 downto 0 instruction length
1234
                -- 2 write ACC
1235
                -- 3 write register file
1236
                when "00000000" => MCode <= "0001";     -- 00000000 1 NOP
1237
                when "00000001" => MCode <= "0010";     -- aaa00001 2 AJMP  code addr
1238
                when "00000010" => MCode <= "0011";     -- 00000010 3 LJMP  code addr
1239
                when "00000011" => MCode <= "0101";     -- 00000011 1 RR    A
1240
                when "00000100" => MCode <= "0101";     -- 00000100 1 INC   A
1241
                when "00000101" => MCode <= "1010";     -- 00000101 2 INC   data addr
1242
                when "00000110" => MCode <= "1001";     -- 0000011i 1 INC   @Ri
1243
                when "00000111" => MCode <= "1001";     -- 0000011i 1 INC   @Ri
1244
                when "00001000" => MCode <= "1001";     -- 00001rrr 1 INC   Rn
1245
                when "00001001" => MCode <= "1001";     -- 00001rrr 1 INC   Rn
1246
                when "00001010" => MCode <= "1001";     -- 00001rrr 1 INC   Rn
1247
                when "00001011" => MCode <= "1001";     -- 00001rrr 1 INC   Rn
1248
                when "00001100" => MCode <= "1001";     -- 00001rrr 1 INC   Rn
1249
                when "00001101" => MCode <= "1001";     -- 00001rrr 1 INC   Rn
1250
                when "00001110" => MCode <= "1001";     -- 00001rrr 1 INC   Rn
1251
                when "00001111" => MCode <= "1001";     -- 00001rrr 1 INC   Rn
1252
                when "00010000" => MCode <= "1011";     -- 00010000 3 JBC   bit addr, code addr
1253
                when "00010001" => MCode <= "0010";     -- aaa10001 2 ACALL code addr
1254
                when "00010010" => MCode <= "0011";     -- 00010010 3 LCALL code addr
1255
                when "00010011" => MCode <= "0101";     -- 00010011 1 RRC   A
1256
                when "00010100" => MCode <= "0101";     -- 00010100 1 DEC   A
1257
                when "00010101" => MCode <= "1010";     -- 00010101 2 DEC   data addr
1258
                when "00010110" => MCode <= "1001";     -- 0001011i 1 DEC   @Ri
1259
                when "00010111" => MCode <= "1001";     -- 0001011i 1 DEC   @Ri
1260
                when "00011000" => MCode <= "1001";     -- 00011rrr 1 DEC   Rn
1261
                when "00011001" => MCode <= "1001";     -- 00011rrr 1 DEC   Rn
1262
                when "00011010" => MCode <= "1001";     -- 00011rrr 1 DEC   Rn
1263
                when "00011011" => MCode <= "1001";     -- 00011rrr 1 DEC   Rn
1264
                when "00011100" => MCode <= "1001";     -- 00011rrr 1 DEC   Rn
1265
                when "00011101" => MCode <= "1001";     -- 00011rrr 1 DEC   Rn
1266
                when "00011110" => MCode <= "1001";     -- 00011rrr 1 DEC   Rn
1267
                when "00011111" => MCode <= "1001";     -- 00011rrr 1 DEC   Rn
1268
                when "00100000" => MCode <= "0011";     -- 00100000 3 JB    bit addr, code addr
1269
                when "00100001" => MCode <= "0010";     -- aaa00001 2 AJMP  code addr
1270
                when "00100010" => MCode <= "0001";     -- 00100010 1 RET
1271
                when "00100011" => MCode <= "0101";     -- 00100011 1 RL    A
1272
                when "00100100" => MCode <= "0110";     -- 00100100 2 ADD   A,#data
1273
                when "00100101" => MCode <= "0110";     -- 00100101 2 ADD   A,data addr
1274
                when "00100110" => MCode <= "0101";     -- 0010011i 1 ADD   A,@Ri
1275
                when "00100111" => MCode <= "0101";     -- 0010011i 1 ADD   A,@Ri
1276
                when "00101000" => MCode <= "0101";     -- 00101rrr 1 ADD   A,Rn
1277
                when "00101001" => MCode <= "0101";     -- 00101rrr 1 ADD   A,Rn
1278
                when "00101010" => MCode <= "0101";     -- 00101rrr 1 ADD   A,Rn
1279
                when "00101011" => MCode <= "0101";     -- 00101rrr 1 ADD   A,Rn
1280
                when "00101100" => MCode <= "0101";     -- 00101rrr 1 ADD   A,Rn
1281
                when "00101101" => MCode <= "0101";     -- 00101rrr 1 ADD   A,Rn
1282
                when "00101110" => MCode <= "0101";     -- 00101rrr 1 ADD   A,Rn
1283
                when "00101111" => MCode <= "0101";     -- 00101rrr 1 ADD   A,Rn
1284
                when "00110000" => MCode <= "0011";     -- 00110000 3 JNB   bit addr, code addr
1285
                when "00110001" => MCode <= "0010";     -- aaa10001 2 ACALL code addr
1286
                when "00110010" => MCode <= "0001";     -- 00110010 1 RETI
1287
                when "00110011" => MCode <= "0101";     -- 00110011 1 RLC   A
1288
                when "00110100" => MCode <= "0110";     -- 00110100 2 ADDC  A,#data
1289
                when "00110101" => MCode <= "0110";     -- 00110101 2 ADDC  A,data addr
1290
                when "00110110" => MCode <= "0101";     -- 0011011i 1 ADDC  A,@Ri
1291
                when "00110111" => MCode <= "0101";     -- 0011011i 1 ADDC  A,@Ri
1292
                when "00111000" => MCode <= "0101";     -- 00111rrr 1 ADDC  A,Rn
1293
                when "00111001" => MCode <= "0101";     -- 00111rrr 1 ADDC  A,Rn
1294
                when "00111010" => MCode <= "0101";     -- 00111rrr 1 ADDC  A,Rn
1295
                when "00111011" => MCode <= "0101";     -- 00111rrr 1 ADDC  A,Rn
1296
                when "00111100" => MCode <= "0101";     -- 00111rrr 1 ADDC  A,Rn
1297
                when "00111101" => MCode <= "0101";     -- 00111rrr 1 ADDC  A,Rn
1298
                when "00111110" => MCode <= "0101";     -- 00111rrr 1 ADDC  A,Rn
1299
                when "00111111" => MCode <= "0101";     -- 00111rrr 1 ADDC  A,Rn
1300
                when "01000000" => MCode <= "0010";     -- 01000000 2 JC    code addr
1301
                when "01000001" => MCode <= "0010";     -- aaa00001 2 AJMP  code addr
1302
                when "01000010" => MCode <= "1010";     -- 01000010 2 ORL   data addr,A
1303
                when "01000011" => MCode <= "1011";     -- 01000011 3 ORL   data addr,#data
1304
                when "01000100" => MCode <= "0110";     -- 01000100 2 ORL   A,#data
1305
                when "01000101" => MCode <= "0110";     -- 01000101 2 ORL   A,data addr
1306
                when "01000110" => MCode <= "0101";     -- 0100011i 1 ORL   A,@Ri
1307
                when "01000111" => MCode <= "0101";     -- 0100011i 1 ORL   A,@Ri
1308
                when "01001000" => MCode <= "0101";     -- 01001rrr 1 ORL   A,Rn
1309
                when "01001001" => MCode <= "0101";     -- 01001rrr 1 ORL   A,Rn
1310
                when "01001010" => MCode <= "0101";     -- 01001rrr 1 ORL   A,Rn
1311
                when "01001011" => MCode <= "0101";     -- 01001rrr 1 ORL   A,Rn
1312
                when "01001100" => MCode <= "0101";     -- 01001rrr 1 ORL   A,Rn
1313
                when "01001101" => MCode <= "0101";     -- 01001rrr 1 ORL   A,Rn
1314
                when "01001110" => MCode <= "0101";     -- 01001rrr 1 ORL   A,Rn
1315
                when "01001111" => MCode <= "0101";     -- 01001rrr 1 ORL   A,Rn
1316
                when "01010000" => MCode <= "0010";     -- 01010000 2 JNC   code addr
1317
                when "01010001" => MCode <= "0010";     -- aaa10001 2 ACALL code addr
1318
                when "01010010" => MCode <= "1010";     -- 01010010 2 ANL   data addr,A
1319
                when "01010011" => MCode <= "1011";     -- 01010011 3 ANL   data addr,#data
1320
                when "01010100" => MCode <= "0110";     -- 01010100 2 ANL   A,#data
1321
                when "01010101" => MCode <= "0110";     -- 01010101 2 ANL   A,data addr
1322
                when "01010110" => MCode <= "0101";     -- 0101011i 1 ANL   A,@Ri
1323
                when "01010111" => MCode <= "0101";     -- 0101011i 1 ANL   A,@Ri
1324
                when "01011000" => MCode <= "0101";     -- 01011rrr 1 ANL   A,Rn
1325
                when "01011001" => MCode <= "0101";     -- 01011rrr 1 ANL   A,Rn
1326
                when "01011010" => MCode <= "0101";     -- 01011rrr 1 ANL   A,Rn
1327
                when "01011011" => MCode <= "0101";     -- 01011rrr 1 ANL   A,Rn
1328
                when "01011100" => MCode <= "0101";     -- 01011rrr 1 ANL   A,Rn
1329
                when "01011101" => MCode <= "0101";     -- 01011rrr 1 ANL   A,Rn
1330
                when "01011110" => MCode <= "0101";     -- 01011rrr 1 ANL   A,Rn
1331
                when "01011111" => MCode <= "0101";     -- 01011rrr 1 ANL   A,Rn
1332
                when "01100000" => MCode <= "0010";     -- 01100000 2 JZ    code addr
1333
                when "01100001" => MCode <= "0010";     -- aaa00001 2 AJMP  code addr
1334
                when "01100010" => MCode <= "1010";     -- 01100010 2 XRL   data addr,A
1335
                when "01100011" => MCode <= "1011";     -- 01100011 3 XRL   data addr,#data
1336
                when "01100100" => MCode <= "0110";     -- 01100100 2 XRL   A,#data
1337
                when "01100101" => MCode <= "0110";     -- 01100101 2 XRL   A,data addr
1338
                when "01100110" => MCode <= "0101";     -- 0110011i 1 XRL   A,@Ri
1339
                when "01100111" => MCode <= "0101";     -- 0110011i 1 XRL   A,@Ri
1340
                when "01101000" => MCode <= "0101";     -- 01101rrr 1 XRL   A,Rn
1341
                when "01101001" => MCode <= "0101";     -- 01101rrr 1 XRL   A,Rn
1342
                when "01101010" => MCode <= "0101";     -- 01101rrr 1 XRL   A,Rn
1343
                when "01101011" => MCode <= "0101";     -- 01101rrr 1 XRL   A,Rn
1344
                when "01101100" => MCode <= "0101";     -- 01101rrr 1 XRL   A,Rn
1345
                when "01101101" => MCode <= "0101";     -- 01101rrr 1 XRL   A,Rn
1346
                when "01101110" => MCode <= "0101";     -- 01101rrr 1 XRL   A,Rn
1347
                when "01101111" => MCode <= "0101";     -- 01101rrr 1 XRL   A,Rn
1348
                when "01110000" => MCode <= "0010";     -- 01110000 2 JNZ   code addr
1349
                when "01110001" => MCode <= "0010";     -- aaa10001 2 ACALL code addr
1350
                when "01110010" => MCode <= "0010";     -- 01110010 2 ORL   C, bit addr
1351
                when "01110011" => MCode <= "0001";     -- 01110011 1 JMP   @A+DPTR
1352
                when "01110100" => MCode <= "0110";     -- 01110100 2 MOV   A,#data
1353
                when "01110101" => MCode <= "1011";     -- 01110101 3 MOV   data addr,#data
1354
                when "01110110" => MCode <= "1010";     -- 0111011i 2 MOV   @Ri,#data
1355
                when "01110111" => MCode <= "1010";     -- 0111011i 2 MOV   @Ri,#data
1356
                when "01111000" => MCode <= "1010";     -- 01111rrr 2 MOV   Rn,#data
1357
                when "01111001" => MCode <= "1010";     -- 01111rrr 2 MOV   Rn,#data
1358
                when "01111010" => MCode <= "1010";     -- 01111rrr 2 MOV   Rn,#data
1359
                when "01111011" => MCode <= "1010";     -- 01111rrr 2 MOV   Rn,#data
1360
                when "01111100" => MCode <= "1010";     -- 01111rrr 2 MOV   Rn,#data
1361
                when "01111101" => MCode <= "1010";     -- 01111rrr 2 MOV   Rn,#data
1362
                when "01111110" => MCode <= "1010";     -- 01111rrr 2 MOV   Rn,#data
1363
                when "01111111" => MCode <= "1010";     -- 01111rrr 2 MOV   Rn,#data
1364
                when "10000000" => MCode <= "0010";     -- 10000000 2 SJMP  code addr
1365
                when "10000001" => MCode <= "0010";     -- aaa00001 2 AJMP  code addr
1366
                when "10000010" => MCode <= "0010";     -- 10000010 2 ANL   C,bit addr
1367
                when "10000011" => MCode <= "0011";     -- 10000011 1 MOVC  A,@A+PC
1368
                when "10000100" => MCode <= "0001";     -- 10000100 1 DIV   AB
1369
                when "10000101" => MCode <= "1011";     -- 10000101 3 MOV   data addr,data addr
1370
                when "10000110" => MCode <= "1010";     -- 1000011i 2 MOV   data addr,@Ri
1371
                when "10000111" => MCode <= "1010";     -- 1000011i 2 MOV   data addr,@Ri
1372
                when "10001000" => MCode <= "1010";     -- 10001rrr 2 MOV   data addr,Rn
1373
                when "10001001" => MCode <= "1010";     -- 10001rrr 2 MOV   data addr,Rn
1374
                when "10001010" => MCode <= "1010";     -- 10001rrr 2 MOV   data addr,Rn
1375
                when "10001011" => MCode <= "1010";     -- 10001rrr 2 MOV   data addr,Rn
1376
                when "10001100" => MCode <= "1010";     -- 10001rrr 2 MOV   data addr,Rn
1377
                when "10001101" => MCode <= "1010";     -- 10001rrr 2 MOV   data addr,Rn
1378
                when "10001110" => MCode <= "1010";     -- 10001rrr 2 MOV   data addr,Rn
1379
                when "10001111" => MCode <= "1010";     -- 10001rrr 2 MOV   data addr,Rn
1380
                when "10010000" => MCode <= "0011";     -- 10010000 3 MOV   DPTR,#data
1381
                when "10010001" => MCode <= "0010";     -- aaa10001 2 ACALL code addr
1382
                when "10010010" => MCode <= "1010";     -- 10010010 2 MOV   bit addr,C
1383
                when "10010011" => MCode <= "0011";     -- 10010011 1 MOVC  A,@A+DPTR
1384
                when "10010100" => MCode <= "0110";     -- 10010100 2 SUBB  A,#data
1385
                when "10010101" => MCode <= "0110";     -- 10010101 2 SUBB  A,data addr
1386
                when "10010110" => MCode <= "0101";     -- 1001011i 1 SUBB  A,@Ri
1387
                when "10010111" => MCode <= "0101";     -- 1001011i 1 SUBB  A,@Ri
1388
                when "10011000" => MCode <= "0101";     -- 10011rrr 1 SUBB  A,Rn
1389
                when "10011001" => MCode <= "0101";     -- 10011rrr 1 SUBB  A,Rn
1390
                when "10011010" => MCode <= "0101";     -- 10011rrr 1 SUBB  A,Rn
1391
                when "10011011" => MCode <= "0101";     -- 10011rrr 1 SUBB  A,Rn
1392
                when "10011100" => MCode <= "0101";     -- 10011rrr 1 SUBB  A,Rn
1393
                when "10011101" => MCode <= "0101";     -- 10011rrr 1 SUBB  A,Rn
1394
                when "10011110" => MCode <= "0101";     -- 10011rrr 1 SUBB  A,Rn
1395
                when "10011111" => MCode <= "0101";     -- 10011rrr 1 SUBB  A,Rn
1396
                when "10100000" => MCode <= "0010";     -- 10100000 2 ORL   C,/bit addr
1397
                when "10100001" => MCode <= "0010";     -- aaa00001 2 AJMP  code addr
1398
                when "10100010" => MCode <= "0010";     -- 10100010 2 MOV   C,bit addr
1399
                when "10100011" => MCode <= "0001";     -- 10100011 1 INC   DPTR
1400
                when "10100100" => MCode <= "0101";     -- 10100100 1 MUL   AB
1401
                when "10100101" => MCode <= "0001";     -- 10100101   reserved
1402
                when "10100110" => MCode <= "1010";     -- 1010011i 2 MOV   @Ri,data addr
1403
                when "10100111" => MCode <= "1010";     -- 1010011i 2 MOV   @Ri,data addr
1404
                when "10101000" => MCode <= "1010";     -- 10101rrr 2 MOV   Rn,data addr
1405
                when "10101001" => MCode <= "1010";     -- 10101rrr 2 MOV   Rn,data addr
1406
                when "10101010" => MCode <= "1010";     -- 10101rrr 2 MOV   Rn,data addr
1407
                when "10101011" => MCode <= "1010";     -- 10101rrr 2 MOV   Rn,data addr
1408
                when "10101100" => MCode <= "1010";     -- 10101rrr 2 MOV   Rn,data addr
1409
                when "10101101" => MCode <= "1010";     -- 10101rrr 2 MOV   Rn,data addr
1410
                when "10101110" => MCode <= "1010";     -- 10101rrr 2 MOV   Rn,data addr
1411
                when "10101111" => MCode <= "1010";     -- 10101rrr 2 MOV   Rn,data addr
1412
                when "10110000" => MCode <= "0010";     -- 10110000 2 ANL   C,/bit addr
1413
                when "10110001" => MCode <= "0010";     -- aaa10001 2 ACALL code addr
1414
                when "10110010" => MCode <= "1010";     -- 10110010 2 CPL   bit addr
1415
                when "10110011" => MCode <= "0001";     -- 10110011 1 CPL   C
1416
                when "10110100" => MCode <= "0011";     -- 10110100 3 CJNE  A,#data,code addr
1417
                when "10110101" => MCode <= "0011";     -- 10110101 3 CJNE  A,data addr,code addr
1418
                when "10110110" => MCode <= "0011";     -- 1011011i 3 CJNE  @Ri,#data,code addr
1419
                when "10110111" => MCode <= "0011";     -- 1011011i 3 CJNE  @Ri,#data,code addr
1420
                when "10111000" => MCode <= "0011";     -- 10111rrr 3 CJNE  Rn,#data,code addr
1421
                when "10111001" => MCode <= "0011";     -- 10111rrr 3 CJNE  Rn,#data,code addr
1422
                when "10111010" => MCode <= "0011";     -- 10111rrr 3 CJNE  Rn,#data,code addr
1423
                when "10111011" => MCode <= "0011";     -- 10111rrr 3 CJNE  Rn,#data,code addr
1424
                when "10111100" => MCode <= "0011";     -- 10111rrr 3 CJNE  Rn,#data,code addr
1425
                when "10111101" => MCode <= "0011";     -- 10111rrr 3 CJNE  Rn,#data,code addr
1426
                when "10111110" => MCode <= "0011";     -- 10111rrr 3 CJNE  Rn,#data,code addr
1427
                when "10111111" => MCode <= "0011";     -- 10111rrr 3 CJNE  Rn,#data,code addr
1428
                when "11000000" => MCode <= "1010";     -- 11000000 2 PUSH  data addr
1429
                when "11000001" => MCode <= "0010";     -- aaa00001 2 AJMP  code addr
1430
                when "11000010" => MCode <= "1010";     -- 11000010 2 CLR   bit addr
1431
                when "11000011" => MCode <= "0001";     -- 11000011 1 CLR   C
1432
                when "11000100" => MCode <= "0101";     -- 11000100 1 SWAP  A
1433
                when "11000101" => MCode <= "1110";     -- 11000101 2 XCH   A,data addr
1434
                when "11000110" => MCode <= "1101";     -- 1100011i 1 XCH   A,@Ri
1435
                when "11000111" => MCode <= "1101";     -- 1100011i 1 XCH   A,@Ri
1436
                when "11001000" => MCode <= "1101";     -- 11001rrr 1 XCH   A,Rn
1437
                when "11001001" => MCode <= "1101";     -- 11001rrr 1 XCH   A,Rn
1438
                when "11001010" => MCode <= "1101";     -- 11001rrr 1 XCH   A,Rn
1439
                when "11001011" => MCode <= "1101";     -- 11001rrr 1 XCH   A,Rn
1440
                when "11001100" => MCode <= "1101";     -- 11001rrr 1 XCH   A,Rn
1441
                when "11001101" => MCode <= "1101";     -- 11001rrr 1 XCH   A,Rn
1442
                when "11001110" => MCode <= "1101";     -- 11001rrr 1 XCH   A,Rn
1443
                when "11001111" => MCode <= "1101";     -- 11001rrr 1 XCH   A,Rn
1444
                when "11010000" => MCode <= "1010";     -- 11010000 2 POP   data addr
1445
                when "11010001" => MCode <= "0010";     -- aaa10001 2 ACALL code addr
1446
                when "11010010" => MCode <= "1010";     -- 11010010 2 SETB  bit addr
1447
                when "11010011" => MCode <= "0001";     -- 11010011 1 SETB  C
1448
                when "11010100" => MCode <= "0101";     -- 11010100 1 DA    A
1449
                when "11010101" => MCode <= "1011";     -- 11010101 3 DJNZ  data addr, code addr
1450
                when "11010110" => MCode <= "1101";     -- 1101011i 1 XCHD  A,@Ri
1451
                when "11010111" => MCode <= "1101";     -- 1101011i 1 XCHD  A,@Ri
1452
                when "11011000" => MCode <= "1010";     -- 11011rrr 2 DJNZ  Rn,code addr
1453
                when "11011001" => MCode <= "1010";     -- 11011rrr 2 DJNZ  Rn,code addr
1454
                when "11011010" => MCode <= "1010";     -- 11011rrr 2 DJNZ  Rn,code addr
1455
                when "11011011" => MCode <= "1010";     -- 11011rrr 2 DJNZ  Rn,code addr
1456
                when "11011100" => MCode <= "1010";     -- 11011rrr 2 DJNZ  Rn,code addr
1457
                when "11011101" => MCode <= "1010";     -- 11011rrr 2 DJNZ  Rn,code addr
1458
                when "11011110" => MCode <= "1010";     -- 11011rrr 2 DJNZ  Rn,code addr
1459
                when "11011111" => MCode <= "1010";     -- 11011rrr 2 DJNZ  Rn,code addr
1460
                when "11100000" => MCode <= "0101";     -- 11100000 1 MOVX  A,@DPTR
1461
                when "11100001" => MCode <= "0010";     -- aaa00001 2 AJMP  code addr
1462
                when "11100010" => MCode <= "0101";     -- 1110001i 1 MOVX  A,@Ri
1463
                when "11100011" => MCode <= "0101";     -- 1110001i 1 MOVX  A,@Ri
1464
                when "11100100" => MCode <= "0101";     -- 11100100 1 CLR   A
1465
                when "11100101" => MCode <= "0110";     -- 11100101 2 MOV   A,data addr
1466
                when "11100110" => MCode <= "0101";     -- 1110011i 1 MOV   A,@Ri
1467
                when "11100111" => MCode <= "0101";     -- 1110011i 1 MOV   A,@Ri
1468
                when "11101000" => MCode <= "0101";     -- 11101rrr 1 MOV   A,Rn
1469
                when "11101001" => MCode <= "0101";     -- 11101rrr 1 MOV   A,Rn
1470
                when "11101010" => MCode <= "0101";     -- 11101rrr 1 MOV   A,Rn
1471
                when "11101011" => MCode <= "0101";     -- 11101rrr 1 MOV   A,Rn
1472
                when "11101100" => MCode <= "0101";     -- 11101rrr 1 MOV   A,Rn
1473
                when "11101101" => MCode <= "0101";     -- 11101rrr 1 MOV   A,Rn
1474
                when "11101110" => MCode <= "0101";     -- 11101rrr 1 MOV   A,Rn
1475
                when "11101111" => MCode <= "0101";     -- 11101rrr 1 MOV   A,Rn
1476
                when "11110000" => MCode <= "0001";     -- 11110000 1 MOVX  @DPTR,A
1477
                when "11110001" => MCode <= "0010";     -- aaa10001 2 ACALL code addr
1478
                when "11110010" => MCode <= "0001";     -- 1111001i 1 MOVX  @Ri,A
1479
                when "11110011" => MCode <= "0001";     -- 1111001i 1 MOVX  @Ri,A
1480
                when "11110100" => MCode <= "0101";     -- 11110100 1 CPL   A
1481
                when "11110101" => MCode <= "1010";     -- 11110101 2 MOV   data addr,A
1482
                when "11110110" => MCode <= "1001";     -- 1111011i 1 MOV   @Ri,A
1483
                when "11110111" => MCode <= "1001";     -- 1111011i 1 MOV   @Ri,A
1484
                when "11111000" => MCode <= "1001";     -- 11111rrr 1 MOV   Rn,A
1485
                when "11111001" => MCode <= "1001";     -- 11111rrr 1 MOV   Rn,A
1486
                when "11111010" => MCode <= "1001";     -- 11111rrr 1 MOV   Rn,A
1487
                when "11111011" => MCode <= "1001";     -- 11111rrr 1 MOV   Rn,A
1488
                when "11111100" => MCode <= "1001";     -- 11111rrr 1 MOV   Rn,A
1489
                when "11111101" => MCode <= "1001";     -- 11111rrr 1 MOV   Rn,A
1490
                when "11111110" => MCode <= "1001";     -- 11111rrr 1 MOV   Rn,A
1491
                when "11111111" => MCode <= "1001";     -- 11111rrr 1 MOV   Rn,A
1492
                when others => MCode <= "----";
1493
                end case;
1494
        end process;
1495
 
1496
end;

powered by: WebSVN 2.1.0

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