//
// Top level module for the FPGA on the MAX80 board by
// Per MÃ¥rtensson and H. Peter Anvin
//
// MAX80 v1
//

module v1
   (
    // Clock oscillator
    input	  clock_48, // 48 MHz
    input	  board_id, // This better match the firmware

    // ABC-bus
    input	  abc_clk, // ABC-bus 3 MHz clock
    input [15:0]  abc_a, // ABC address bus
    inout [7:0]   abc_d, // ABC data bus
    output	  abc_d_oe, // Data bus output enable
    input	  abc_rst_n, // ABC bus reset strobe
    input	  abc_cs_n, // ABC card select strobe
    input [4:0]   abc_out_n, // OUT, C1-C4 strobe
    input [1:0]   abc_inp_n, // INP, STATUS strobe
    input	  abc_xmemfl_n, // Memory read strobe
    input	  abc_xmemw800_n, // Memory write strobe (ABC800)
    input	  abc_xmemw80_n, // Memory write strobe (ABC80)
    input	  abc_xinpstb_n, // I/O read strobe (ABC800)
    input	  abc_xoutpstb_n, // I/O write strobe (ABC80)
    // The following are inverted versus the bus IF
    // the corresponding MOSFETs are installed
    output	  abc_rdy_x, // RDY = WAIT#
    output	  abc_resin_x, // System reset request
    output	  abc_int80_x, // System INT request (ABC80)
    output	  abc_int800_x, // System INT request (ABC800)
    output	  abc_nmi_x, // System NMI request (ABC800)
    output	  abc_xm_x, // System memory override (ABC800)
    // Host/device control
    output	  abc_host, // 1 = host, 0 = target
    output	  abc_a_oe,
    // Bus isolation
    output	  abc_d_ce_n,

    // ABC-bus extension header
    // (Note: cannot use an array here because HC and HH are
    // input only.)
    inout	  exth_ha,
    inout	  exth_hb,
    input	  exth_hc,
    inout	  exth_hd,
    inout	  exth_he,
    inout	  exth_hf,
    inout	  exth_hg,
    input	  exth_hh,

    // SDRAM bus
    output	  sr_clk,
    output	  sr_cke,
    output [1:0]  sr_ba, // Bank address
    output [12:0] sr_a, // Address within bank
    inout [15:0]  sr_dq, // Also known as D or IO
    output [1:0]  sr_dqm, // DQML and DQMH
    output	  sr_cs_n,
    output	  sr_we_n,
    output	  sr_cas_n,
    output	  sr_ras_n,

    // SD card
    output	  sd_clk,
    output	  sd_cmd,
    inout [3:0]   sd_dat,

    // Serial console (naming is FPGA as DCE)
    input	  tty_txd,
    output	  tty_rxd,
    input	  tty_rts,
    output	  tty_cts,
    input	  tty_dtr,

    // SPI flash memory (also configuration)
    output	  flash_cs_n,
    output	  flash_sck,
    inout [1:0]   flash_io,

    // SPI bus (connected to ESP32 so can be bidirectional)
    inout	  spi_clk,	  // ESP32 IO12
    inout [1:0]   spi_io,	  // ESP32 IO13,IO11
    inout	  spi_cs_esp_n,   // ESP32 IO10
    inout	  spi_cs_flash_n, // ESP32 IO01

    // Other ESP32 connections
    inout	  esp_io0,        // ESP32 IO00
    inout	  esp_int,        // ESP32 IO09

    // I2C bus (RTC and external)
    inout	  i2c_scl,
    inout	  i2c_sda,
    input	  rtc_32khz,
    input	  rtc_int_n,

    // LED (2 = D23/G, 1 = D22/R, 0 = D17/B)
    output [2:0]  led,

    // GPIO
    inout [5:0]   gpio,

    // HDMI
    output [2:0]  hdmi_d,
    output	  hdmi_clk,
    inout	  hdmi_scl,
    inout	  hdmi_sda,
    inout	  hdmi_hpd,

    // Unconnected pins with pullups, used for randomness
    inout [2:0]   rngio
    );

   // ABC data bus isolation not supported or needed
   assign abc_d_ce_n  = 1'b0;

   // This signal duplicates abc_host
   assign abc_a_oe    = abc_host;

   // Permanently unused
   assign sd_dat[2:1] = 2'bzz;
   assign gpio[0] = 1'bz;
   assign gpio[2] = 1'bz;
   assign gpio[4] = 1'bz;

   // Always active
   assign sr_cke      = 1'b1;

   // Master PLL: 48 -> 336 MHz
   wire		  reset_plls;
   wire		  master_pll_locked;
   wire		  master_clk;	// 336 MHz
   wire		  slow_clk;	//  12 MHz

   pll2_48 pll2 (
		 .areset ( reset_plls ),
		 .locked ( master_pll_locked ),
		 .inclk0 ( clock_48 ),
		 .c0 ( master_clk ),
		 .c1 ( slow_clk )
		 );

   max80 #(.x_mosfet(6'b111111),
	   .fpga_ver(8'd1))
   max80 (
	  .master_clk             ( master_clk ),
	  .slow_clk               ( slow_clk ),
	  .master_pll_locked	  ( master_pll_locked ),
	  .reset_plls             ( reset_plls ),
	  .board_id               ( board_id ),
	  .abc_clk                ( abc_clk ),
	  .abc_a                  ( abc_a ),
	  .abc_d                  ( abc_d ),
	  .abc_d_oe               ( abc_d_oe ),
	  .abc_rst_n              ( abc_rst_n ),
	  .abc_cs_n               ( abc_cs_n ),
	  .abc_out_n              ( abc_out_n ),
	  .abc_inp_n              ( abc_inp_n ),
	  .abc_xmemfl_n           ( abc_xmemfl_n ),
	  .abc_xmemw800_n         ( abc_xmemw800_n ),
	  .abc_xmemw80_n          ( abc_xmemw80_n ),
	  .abc_xinpstb_n          ( abc_xinpstb_n ),
	  .abc_xoutpstb_n         ( abc_xoutpstb_n ),
	  .abc_rdy_x              ( abc_rdy_x ),
	  .abc_resin_x            ( abc_resin_x ),
	  .abc_int80_x            ( abc_int80_x ),
	  .abc_int800_x           ( abc_int800_x ),
	  .abc_nmi_x              ( abc_nmi_x ),
	  .abc_xm_x               ( abc_xm_x ),
	  .abc_host               ( abc_host ),
	  .exth_ha                ( exth_ha ),
	  .exth_hb                ( exth_hb ),
	  .exth_hc                ( exth_hc ),
	  .exth_hd                ( exth_hd ),
	  .exth_he                ( exth_he ),
	  .exth_hf                ( exth_hf ),
	  .exth_hg                ( exth_hg ),
	  .exth_hh                ( exth_hh ),
	  .sr_clk                 ( sr_clk ),
	  .sr_ba                  ( sr_ba ),
	  .sr_a                   ( sr_a ),
	  .sr_dq                  ( sr_dq ),
	  .sr_dqm                 ( sr_dqm ),
	  .sr_cs_n                ( sr_cs_n ),
	  .sr_we_n                ( sr_we_n ),
	  .sr_cas_n               ( sr_cas_n ),
	  .sr_ras_n               ( sr_ras_n ),
	  .sd_cd_n		  ( 1'b0 ), // Card detect
	  .sd_cs_n                ( sd_dat[3] ),
	  .sd_clk                 ( sd_clk ),
	  .sd_di                  ( sd_cmd ),
	  .sd_do		  ( sd_dat[0] ),
	  .tty_txd                ( tty_txd ),
	  .tty_rxd                ( tty_rxd ),
	  .tty_rts                ( tty_rts ),
	  .tty_cts                ( tty_cts ),
	  .tty_dtr                ( tty_dtr ),
	  .flash_cs_n             ( flash_cs_n ),
	  .flash_sck              ( flash_sck ),
	  .flash_io               ( flash_io ),
	  .spi_clk                ( spi_clk ),
	  .spi_io                 ( spi_io ),
	  .spi_cs_esp_n           ( spi_cs_esp_n ),
	  .spi_cs_flash_n         ( spi_cs_flash_n ),
	  .esp_io0                ( esp_io0 ),
	  .esp_int                ( esp_int ),
	  .i2c_scl                ( i2c_scl ),
	  .i2c_sda                ( i2c_sda ),
	  .rtc_32khz              ( rtc_32khz ),
	  .rtc_int_n              ( rtc_int_n ),
	  .led                    ( led ),
	  .usb_dp                 ( gpio[3] ),
	  .usb_dn                 ( gpio[5] ),
	  .usb_rx                 ( 1'bx ),
	  .usb_rx_ok		  ( 1'b0 ),
	  .usb_pu		  ( gpio[1] ),
	  .hdmi_d                 ( hdmi_d ),
	  .hdmi_clk               ( hdmi_clk ),
	  .hdmi_scl               ( hdmi_scl ),
	  .hdmi_sda               ( hdmi_sda ),
	  .hdmi_hpd               ( hdmi_hpd ),
	  .rngio                  ( rngio )
	  );

endmodule // v1