Subversion Repositories ngs

Rev

Rev 2 | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed | ?url?

  1. -- ****
  2. -- T80(b) core. In an effort to merge and maintain bug fixes ....
  3. --
  4. --
  5. -- Ver 300 started tidyup
  6. -- MikeJ March 2005
  7. -- Latest version from www.fpgaarcade.com (original www.opencores.org)
  8. --
  9. -- ****
  10. --
  11. -- Z80 compatible microprocessor core, asynchronous top level
  12. --
  13. -- Version : 0247
  14. --
  15. -- Copyright (c) 2001-2002 Daniel Wallner (jesus@opencores.org)
  16. --
  17. -- All rights reserved
  18. --
  19. -- Redistribution and use in source and synthezised forms, with or without
  20. -- modification, are permitted provided that the following conditions are met:
  21. --
  22. -- Redistributions of source code must retain the above copyright notice,
  23. -- this list of conditions and the following disclaimer.
  24. --
  25. -- Redistributions in synthesized form must reproduce the above copyright
  26. -- notice, this list of conditions and the following disclaimer in the
  27. -- documentation and/or other materials provided with the distribution.
  28. --
  29. -- Neither the name of the author nor the names of other contributors may
  30. -- be used to endorse or promote products derived from this software without
  31. -- specific prior written permission.
  32. --
  33. -- THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
  34. -- AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
  35. -- THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
  36. -- PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE
  37. -- LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
  38. -- CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
  39. -- SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
  40. -- INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
  41. -- CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
  42. -- ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
  43. -- POSSIBILITY OF SUCH DAMAGE.
  44. --
  45. -- Please report bugs to the author, but before you do so, please
  46. -- make sure that this is not a derivative work and that
  47. -- you have the latest version of this file.
  48. --
  49. -- The latest version of this file can be found at:
  50. --      http://www.opencores.org/cvsweb.shtml/t80/
  51. --
  52. -- Limitations :
  53. --
  54. -- File history :
  55. --
  56. --      0208 : First complete release
  57. --
  58. --      0211 : Fixed interrupt cycle
  59. --
  60. --      0235 : Updated for T80 interface change
  61. --
  62. --      0238 : Updated for T80 interface change
  63. --
  64. --      0240 : Updated for T80 interface change
  65. --
  66. --      0242 : Updated for T80 interface change
  67. --
  68. --      0247 : Fixed bus req/ack cycle
  69. --
  70.  
  71. library IEEE;
  72. use IEEE.std_logic_1164.all;
  73. use IEEE.numeric_std.all;
  74. use work.T80_Pack.all;
  75.  
  76. entity T80a is
  77.         generic(
  78.                 Mode : integer := 0     -- 0 => Z80, 1 => Fast Z80, 2 => 8080, 3 => GB
  79.         );
  80.         port(
  81.                 RESET_n         : in std_logic;
  82.                 CLK_n           : in std_logic;
  83.                 WAIT_n          : in std_logic;
  84.                 INT_n           : in std_logic;
  85.                 NMI_n           : in std_logic;
  86.                 BUSRQ_n         : in std_logic;
  87.                 M1_n            : out std_logic;
  88.                 MREQ_n          : out std_logic;
  89.                 IORQ_n          : out std_logic;
  90.                 RD_n            : out std_logic;
  91.                 WR_n            : out std_logic;
  92.                 RFSH_n          : out std_logic;
  93.                 HALT_n          : out std_logic;
  94.                 BUSAK_n         : out std_logic;
  95.                 A                       : out std_logic_vector(15 downto 0);
  96.                 D                       : inout std_logic_vector(7 downto 0)
  97.         );
  98. end T80a;
  99.  
  100. architecture rtl of T80a is
  101.  
  102.         signal CEN                  : std_logic;
  103.         signal Reset_s              : std_logic;
  104.         signal IntCycle_n   : std_logic;
  105.         signal IORQ                 : std_logic;
  106.         signal NoRead               : std_logic;
  107.         signal Write                : std_logic;
  108.         signal MREQ                 : std_logic;
  109.         signal MReq_Inhibit : std_logic;
  110.         signal Req_Inhibit  : std_logic;
  111.         signal RD                   : std_logic;
  112.         signal MREQ_n_i             : std_logic;
  113.         signal IORQ_n_i             : std_logic;
  114.         signal RD_n_i               : std_logic;
  115.         signal WR_n_i               : std_logic;
  116.         signal RFSH_n_i             : std_logic;
  117.         signal BUSAK_n_i    : std_logic;
  118.         signal A_i                  : std_logic_vector(15 downto 0);
  119.         signal DO                   : std_logic_vector(7 downto 0);
  120.         signal DI_Reg               : std_logic_vector (7 downto 0);        -- Input synchroniser
  121.         signal Wait_s               : std_logic;
  122.         signal MCycle               : std_logic_vector(2 downto 0);
  123.         signal TState               : std_logic_vector(2 downto 0);
  124.  
  125. begin
  126.  
  127.         CEN <= '1';
  128.  
  129.         BUSAK_n <= BUSAK_n_i;
  130.         MREQ_n_i <= not MREQ or (Req_Inhibit and MReq_Inhibit);
  131.         RD_n_i <= not RD or Req_Inhibit;
  132.  
  133.         MREQ_n <= MREQ_n_i when BUSAK_n_i = '1' else 'Z';
  134.         IORQ_n <= IORQ_n_i when BUSAK_n_i = '1' else 'Z';
  135.         RD_n <= RD_n_i when BUSAK_n_i = '1' else 'Z';
  136.         WR_n <= WR_n_i when BUSAK_n_i = '1' else 'Z';
  137.         RFSH_n <= RFSH_n_i when BUSAK_n_i = '1' else 'Z';
  138.         A <= A_i when BUSAK_n_i = '1' else (others => 'Z');
  139.         D <= DO when Write = '1' and BUSAK_n_i = '1' else (others => 'Z');
  140.  
  141.         process (RESET_n, CLK_n)
  142.         begin
  143.                 if RESET_n = '0' then
  144.                         Reset_s <= '0';
  145.                 elsif CLK_n'event and CLK_n = '1' then
  146.                         Reset_s <= '1';
  147.                 end if;
  148.         end process;
  149.  
  150.         u0 : T80
  151.                 generic map(
  152.                         Mode => Mode,
  153.                         IOWait => 1)
  154.                 port map(
  155.                         CEN => CEN,
  156.                         M1_n => M1_n,
  157.                         IORQ => IORQ,
  158.                         NoRead => NoRead,
  159.                         Write => Write,
  160.                         RFSH_n => RFSH_n_i,
  161.                         HALT_n => HALT_n,
  162.                         WAIT_n => Wait_s,
  163.                         INT_n => INT_n,
  164.                         NMI_n => NMI_n,
  165.                         RESET_n => Reset_s,
  166.                         BUSRQ_n => BUSRQ_n,
  167.                         BUSAK_n => BUSAK_n_i,
  168.                         CLK_n => CLK_n,
  169.                         A => A_i,
  170.                         DInst => D,
  171.                         DI => DI_Reg,
  172.                         DO => DO,
  173.                         MC => MCycle,
  174.                         TS => TState,
  175.                         IntCycle_n => IntCycle_n);
  176.  
  177.         process (CLK_n)
  178.         begin
  179.                 if CLK_n'event and CLK_n = '0' then
  180.                         Wait_s <= WAIT_n;
  181.                         if TState = "011" and BUSAK_n_i = '1' then
  182.                                 DI_Reg <= to_x01(D);
  183.                         end if;
  184.                 end if;
  185.         end process;
  186.  
  187.         process (Reset_s,CLK_n)
  188.         begin
  189.                 if Reset_s = '0' then
  190.                         WR_n_i <= '1';
  191.                 elsif CLK_n'event and CLK_n = '1' then
  192.                         WR_n_i <= '1';
  193.                         if TState = "001" then      -- To short for IO writes !!!!!!!!!!!!!!!!!!!
  194.                                 WR_n_i <= not Write;
  195.                         end if;
  196.                 end if;
  197.         end process;
  198.  
  199.         process (Reset_s,CLK_n)
  200.         begin
  201.                 if Reset_s = '0' then
  202.                         Req_Inhibit <= '0';
  203.                 elsif CLK_n'event and CLK_n = '1' then
  204.                         if MCycle = "001" and TState = "010" then
  205.                                 Req_Inhibit <= '1';
  206.                         else
  207.                                 Req_Inhibit <= '0';
  208.                         end if;
  209.                 end if;
  210.         end process;
  211.  
  212.         process (Reset_s,CLK_n)
  213.         begin
  214.                 if Reset_s = '0' then
  215.                         MReq_Inhibit <= '0';
  216.                 elsif CLK_n'event and CLK_n = '0' then
  217.                         if MCycle = "001" and TState = "010" then
  218.                                 MReq_Inhibit <= '1';
  219.                         else
  220.                                 MReq_Inhibit <= '0';
  221.                         end if;
  222.                 end if;
  223.         end process;
  224.  
  225.         process(Reset_s,CLK_n)
  226.         begin
  227.                 if Reset_s = '0' then
  228.                         RD <= '0';
  229.                         IORQ_n_i <= '1';
  230.                         MREQ <= '0';
  231.                 elsif CLK_n'event and CLK_n = '0' then
  232.  
  233.                         if MCycle = "001" then
  234.                                 if TState = "001" then
  235.                                         RD <= IntCycle_n;
  236.                                         MREQ <= IntCycle_n;
  237.                                         IORQ_n_i <= IntCycle_n;
  238.                                 end if;
  239.                                 if TState = "011" then
  240.                                         RD <= '0';
  241.                                         IORQ_n_i <= '1';
  242.                                         MREQ <= '1';
  243.                                 end if;
  244.                                 if TState = "100" then
  245.                                         MREQ <= '0';
  246.                                 end if;
  247.                         else
  248.                                 if TState = "001" and NoRead = '0' then
  249.                                         RD <= not Write;
  250.                                         IORQ_n_i <= not IORQ;
  251.                                         MREQ <= not IORQ;
  252.                                 end if;
  253.                                 if TState = "011" then
  254.                                         RD <= '0';
  255.                                         IORQ_n_i <= '1';
  256.                                         MREQ <= '0';
  257.                                 end if;
  258.                         end if;
  259.                 end if;
  260.         end process;
  261.  
  262. end;
  263.