/*  This file is part of the program GDB, the GNU debugger.
    
    Copyright (C) 1998-2021 Free Software Foundation, Inc.
    Contributed by Cygnus Solutions.
    
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation; either version 3 of the License, or
    (at your option) any later version.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program.  If not, see <http://www.gnu.org/licenses/>.
    
    */

/* This must come before any other includes.  */
#include "defs.h"

#include "sim-main.h"
#include "hw-main.h"

/* DEVICE

   
   mn103cpu - mn10300 cpu virtual device

   
   DESCRIPTION

   
   Implements the external mn10300 functionality.  This includes the
   delivery of interrupts generated from other devices and the
   handling of device specific registers.


   PROPERTIES
   

   reg = <address> <size>

   Specify the address of the mn10300's control register block.  This
   block contains the Interrupt Vector Registers.

   The reg property value `0x20000000 0x42' locates the register block
   at the address specified in the mn10300 user guide.


   PORTS


   reset (input)

   Currently ignored.


   nmi (input)

   Deliver a non-maskable interrupt to the processor.


   level (input)

   Maskable interrupt level port port.  The interrupt controller
   notifies the processor of any change in the level of pending
   requested interrupts via this port.


   ack (output)

   Output signal indicating that the processor is delivering a level
   interrupt.  The value passed with the event specifies the level of
   the interrupt being delivered.


   BUGS


   When delivering an interrupt, this code assumes that there is only
   one processor (number 0).

   This code does not attempt to be efficient at handling pending
   interrupts.  It simply schedules the interrupt delivery handler
   every instruction cycle until all pending interrupts go away.  An
   alternative implementation might modify instructions that change
   the PSW and have them check to see if the change makes an interrupt
   delivery possible.

   */


/* The interrupt vectors */

enum { NR_VECTORS = 7, };


/* The interrupt controller register address blocks */

struct mn103cpu_block {
  unsigned_word base;
  unsigned_word bound;
};


struct mn103cpu {
  struct mn103cpu_block block;
  struct hw_event *pending_handler;
  int pending_level;
  int pending_nmi;
  int pending_reset;
  /* the visible registers */
  unsigned16 interrupt_vector[NR_VECTORS];
  unsigned16 internal_memory_control;
  unsigned16 cpu_mode;
};



/* input port ID's */ 

enum {
  RESET_PORT,
  NMI_PORT,
  LEVEL_PORT,
};


/* output port ID's */

enum {
  ACK_PORT,
};

static const struct hw_port_descriptor mn103cpu_ports[] = {

  /* interrupt inputs */
  { "reset", RESET_PORT, 0, input_port, },
  { "nmi", NMI_PORT, 0, input_port, },
  { "level", LEVEL_PORT, 0, input_port, },

  /* interrupt ack (latch) output from cpu */
  { "ack", ACK_PORT, 0, output_port, },

  { NULL, },
};


/* Finish off the partially created hw device.  Attach our local
   callbacks.  Wire up our port names etc */

static hw_io_read_buffer_method mn103cpu_io_read_buffer;
static hw_io_write_buffer_method mn103cpu_io_write_buffer;
static hw_port_event_method mn103cpu_port_event;

static void
attach_mn103cpu_regs (struct hw *me,
		      struct mn103cpu *controller)
{
  unsigned_word attach_address;
  int attach_space;
  unsigned attach_size;
  reg_property_spec reg;
  if (hw_find_property (me, "reg") == NULL)
    hw_abort (me, "Missing \"reg\" property");
  if (!hw_find_reg_array_property (me, "reg", 0, &reg))
    hw_abort (me, "\"reg\" property must contain three addr/size entries");
  hw_unit_address_to_attach_address (hw_parent (me),
				     &reg.address,
				     &attach_space,
				     &attach_address,
				     me);
  controller->block.base = attach_address;
  hw_unit_size_to_attach_size (hw_parent (me),
			       &reg.size,
			       &attach_size, me);
  controller->block.bound = attach_address + (attach_size - 1);
  if ((controller->block.base & 3) != 0)
    hw_abort (me, "cpu register block must be 4 byte aligned");
  hw_attach_address (hw_parent (me),
		     0,
		     attach_space, attach_address, attach_size,
		     me);
}


static void
mn103cpu_finish (struct hw *me)
{
  struct mn103cpu *controller;

  controller = HW_ZALLOC (me, struct mn103cpu);
  set_hw_data (me, controller);
  set_hw_io_read_buffer (me, mn103cpu_io_read_buffer);
  set_hw_io_write_buffer (me, mn103cpu_io_write_buffer);
  set_hw_ports (me, mn103cpu_ports);
  set_hw_port_event (me, mn103cpu_port_event);

  /* Attach ourself to our parent bus */
  attach_mn103cpu_regs (me, controller);

  /* Initialize the read-only registers */
  controller->pending_level = 7; /* FIXME */
  /* ... */
}



/* An event arrives on an interrupt port */

static void
deliver_mn103cpu_interrupt (struct hw *me,
			    void *data)
{
  struct mn103cpu *controller = hw_data (me);
  SIM_DESC simulator = hw_system (me);
  sim_cpu *cpu = STATE_CPU (simulator, 0);

  if (controller->pending_reset)
    {
      controller->pending_reset = 0;
      /* need to clear all registers et.al! */
      HW_TRACE ((me, "Reset!"));
      hw_abort (me, "Reset!");
    }
  else if (controller->pending_nmi)
    {
      controller->pending_nmi = 0;
      store_word (SP - 4, CPU_PC_GET (cpu));
      store_half (SP - 8, PSW);
      PSW &= ~PSW_IE;
      SP = SP - 8;
      CPU_PC_SET (cpu, 0x40000008);
      HW_TRACE ((me, "nmi pc=0x%08lx psw=0x%04x sp=0x%08lx",
		 (long) CPU_PC_GET (cpu), (unsigned) PSW, (long) SP));
    }
  else if ((controller->pending_level < EXTRACT_PSW_LM)
	   && (PSW & PSW_IE))
    {
      /* Don't clear pending level.  Request continues to be pending
         until the interrupt controller clears/changes it */
      store_word (SP - 4, CPU_PC_GET (cpu));
      store_half (SP - 8, PSW);
      PSW &= ~PSW_IE;
      PSW &= ~PSW_LM;
      PSW |= INSERT_PSW_LM (controller->pending_level);
      SP = SP - 8;
      CPU_PC_SET (cpu, 0x40000000 + controller->interrupt_vector[controller->pending_level]);
      HW_TRACE ((me, "port-out ack %d", controller->pending_level));
      hw_port_event (me, ACK_PORT, controller->pending_level);
      HW_TRACE ((me, "int level=%d pc=0x%08lx psw=0x%04x sp=0x%08lx",
		 controller->pending_level,
		 (long) CPU_PC_GET (cpu), (unsigned) PSW, (long) SP));
    }

  if (controller->pending_level < 7) /* FIXME */
    {
      /* As long as there is the potential need to deliver an
	 interrupt we keep rescheduling this routine. */
      if (controller->pending_handler != NULL)
	controller->pending_handler =
	  hw_event_queue_schedule (me, 1, deliver_mn103cpu_interrupt, NULL);
    }
  else
    {
      /* Don't bother re-scheduling the interrupt handler as there is
         nothing to deliver */
      controller->pending_handler = NULL;
    }

}


static void
mn103cpu_port_event (struct hw *me,
		     int my_port,
		     struct hw *source,
		     int source_port,
		     int level)
{
  struct mn103cpu *controller = hw_data (me);

  /* Schedule our event handler *now* */
  if (controller->pending_handler == NULL)
    controller->pending_handler =
      hw_event_queue_schedule (me, 0, deliver_mn103cpu_interrupt, NULL);

  switch (my_port)
    {
      
    case RESET_PORT:
      controller->pending_reset = 1;
      HW_TRACE ((me, "port-in reset"));
      break;
      
    case NMI_PORT:
      controller->pending_nmi = 1;
      HW_TRACE ((me, "port-in nmi"));
      break;
      
    case LEVEL_PORT:
      controller->pending_level = level;
      HW_TRACE ((me, "port-in level=%d", level));
      break;
      
    default:
      hw_abort (me, "bad switch");
      break;

    }
}


/* Read/write to a CPU register */

enum mn103cpu_regs {
  INVALID_REG,
  IVR0_REG,
  IVR1_REG,
  IVR2_REG,
  IVR3_REG,
  IVR4_REG,
  IVR5_REG,
  IVR6_REG,
  IMCR_REG,
  CPUM_REG,
};

static enum mn103cpu_regs
decode_mn103cpu_addr (struct hw *me,
		      struct mn103cpu *controller,
		      unsigned_word base)
{
  switch (base - controller->block.base)
    {
    case 0x000: return IVR0_REG;
    case 0x004: return IVR1_REG;
    case 0x008: return IVR2_REG;
    case 0x00c: return IVR3_REG;
    case 0x010: return IVR4_REG;
    case 0x014: return IVR5_REG;
    case 0x018: return IVR6_REG;
    case 0x020: return IMCR_REG;
    case 0x040: return CPUM_REG;
    default: return INVALID_REG;
    }
}

static unsigned
mn103cpu_io_read_buffer (struct hw *me,
			 void *dest,
			 int space,
			 unsigned_word base,
			 unsigned nr_bytes)
{
  struct mn103cpu *controller = hw_data (me);
  unsigned16 val = 0;
  enum mn103cpu_regs reg = decode_mn103cpu_addr (me, controller, base);

  switch (reg)
    {
    case IVR0_REG:
    case IVR1_REG:
    case IVR2_REG:
    case IVR3_REG:
    case IVR4_REG:
    case IVR5_REG:
    case IVR6_REG:
      val = controller->interrupt_vector[reg - IVR0_REG];
      break;
    case IMCR_REG:
      val = controller->internal_memory_control;
      break;
    case CPUM_REG:
      val = controller->cpu_mode;
      break;
    default:
      /* just ignore the read */
      break;
    }

  if (nr_bytes == 2)
    *(unsigned16*) dest = H2LE_2 (val);

  return nr_bytes;
}     

static unsigned
mn103cpu_io_write_buffer (struct hw *me,
			  const void *source,
			  int space,
			  unsigned_word base,
			  unsigned nr_bytes)
{
  struct mn103cpu *controller = hw_data (me);
  unsigned16 val;
  enum mn103cpu_regs reg;

  if (nr_bytes != 2)
    hw_abort (me, "must be two byte write");

  reg = decode_mn103cpu_addr (me, controller, base);
  val = LE2H_2 (* (unsigned16 *) source);

  switch (reg)
    {
    case IVR0_REG:
    case IVR1_REG:
    case IVR2_REG:
    case IVR3_REG:
    case IVR4_REG:
    case IVR5_REG:
    case IVR6_REG:
      controller->interrupt_vector[reg - IVR0_REG] = val;
      HW_TRACE ((me, "ivr%d = 0x%04lx", reg - IVR0_REG, (long) val));
      break;
    default:
      /* just ignore the write */
      break;
    }

  return nr_bytes;
}     


const struct hw_descriptor dv_mn103cpu_descriptor[] = {
  { "mn103cpu", mn103cpu_finish, },
  { NULL },
};
