# Simulator main loop for m32r2. -*- C -*-
#
# Copyright 1996-2024 Free Software Foundation, Inc.
#
# This file is part of GDB, the GNU debugger.
#
# 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/>.

# Syntax:
# /bin/sh mainloop.in command
#
# Command is one of:
#
# init
# support
# extract-{simple,scache,pbb}
# {full,fast}-exec-{simple,scache,pbb}
#
# A target need only provide a "full" version of one of simple,scache,pbb.
# If the target wants it can also provide a fast version of same, or if
# the slow (full featured) version is `simple', then the fast version can be
# one of scache/pbb.
# A target can't provide more than this.

# ??? After a few more ports are done, revisit.
# Will eventually need to machine generate a lot of this.

case "x$1" in

xsupport)

cat <<EOF
#line $LINENO "$0"

/* Emit insns to write back the results of insns executed in parallel.
   SC points to a sufficient number of scache entries for the writeback
   handlers.
   SC1/ID1 is the first insn (left slot, lower address).
   SC2/ID2 is the second insn (right slot, higher address).  */

static INLINE void
emit_par_finish (SIM_CPU *current_cpu, PCADDR pc, SCACHE *sc,
		 SCACHE *sc1, const IDESC *id1, SCACHE *sc2, const IDESC *id2)
{
  ARGBUF *abuf;

  abuf = &sc->argbuf;
  id1 = id1->par_idesc;
  abuf->fields.write.abuf = &sc1->argbuf;
  @cpu@_fill_argbuf (current_cpu, abuf, id1, pc, 0);
  /* no need to set trace_p,profile_p */
#if 0 /* not currently needed for id2 since results written directly */
  abuf = &sc[1].argbuf;
  id2 = id2->par_idesc;
  abuf->fields.write.abuf = &sc2->argbuf;
  @cpu@_fill_argbuf (current_cpu, abuf, id2, pc + 2, 0);
  /* no need to set trace_p,profile_p */
#endif
}

static INLINE const IDESC *
emit_16 (SIM_CPU *current_cpu, PCADDR pc, CGEN_INSN_INT insn,
	 SCACHE *sc, int fast_p, int parallel_p)
{
  ARGBUF *abuf = &sc->argbuf;
  const IDESC *id = @cpu@_decode (current_cpu, pc, insn, insn, abuf);

  if (parallel_p)
    id = id->par_idesc;
  @cpu@_fill_argbuf (current_cpu, abuf, id, pc, fast_p);
  return id;
}

static INLINE const IDESC *
emit_full16 (SIM_CPU *current_cpu, PCADDR pc, CGEN_INSN_INT insn, SCACHE *sc,
	     int trace_p, int profile_p)
{
  const IDESC *id;

  @cpu@_emit_before (current_cpu, sc, pc, 1);
  id = emit_16 (current_cpu, pc, insn, sc + 1, 0, 0);
  @cpu@_emit_after (current_cpu, sc + 2, pc);
  @cpu@_fill_argbuf_tp (current_cpu, &sc[1].argbuf, trace_p, profile_p);
  return id;
}

static INLINE const IDESC *
emit_parallel (SIM_CPU *current_cpu, PCADDR pc, CGEN_INSN_INT insn,
	       SCACHE *sc, int fast_p)
{
  const IDESC *id,*id2;

  /* Emit both insns, then emit a finisher-upper.
     We speed things up by handling the second insn serially
     [not parallelly].  Then the writeback only has to deal
     with the first insn.  */
  /* ??? Revisit to handle exceptions right.  */

  /* FIXME: No need to handle this parallelly if second is nop.  */
  id = emit_16 (current_cpu, pc, insn >> 16, sc, fast_p, 1);

  /* Note that this can never be a cti.  No cti's go in the S pipeline.  */
  id2 = emit_16 (current_cpu, pc + 2, insn & 0x7fff, sc + 1, fast_p, 0);

  /* Set sc/snc insns notion of where to skip to.  */
  if (IDESC_SKIP_P (id))
    SEM_SKIP_COMPILE (current_cpu, sc, 1);

  /* Emit code to finish executing the semantics
     (write back the results).  */
  emit_par_finish (current_cpu, pc, sc + 2, sc, id, sc + 1, id2);

  return id;
}

static INLINE const IDESC *
emit_full_parallel (SIM_CPU *current_cpu, PCADDR pc, CGEN_INSN_INT insn,
		    SCACHE *sc, int trace_p, int profile_p)
{
  const IDESC *id,*id2;

  /* Emit both insns, then emit a finisher-upper.
     We speed things up by handling the second insn serially
     [not parallelly].  Then the writeback only has to deal
     with the first insn.  */
  /* ??? Revisit to handle exceptions right.  */

  @cpu@_emit_before (current_cpu, sc, pc, 1);

  /* FIXME: No need to handle this parallelly if second is nop.  */
  id = emit_16 (current_cpu, pc, insn >> 16, sc + 1, 0, 1);
  @cpu@_fill_argbuf_tp (current_cpu, &sc[1].argbuf, trace_p, profile_p);

  @cpu@_emit_before (current_cpu, sc + 2, pc, 0);

  /* Note that this can never be a cti.  No cti's go in the S pipeline.  */
  id2 = emit_16 (current_cpu, pc + 2, insn & 0x7fff, sc + 3, 0, 0);
  @cpu@_fill_argbuf_tp (current_cpu, &sc[3].argbuf, trace_p, profile_p);

  /* Set sc/snc insns notion of where to skip to.  */
  if (IDESC_SKIP_P (id))
    SEM_SKIP_COMPILE (current_cpu, sc, 4);

  /* Emit code to finish executing the semantics
     (write back the results).  */
  emit_par_finish (current_cpu, pc, sc + 4, sc + 1, id, sc + 3, id2);

  @cpu@_emit_after (current_cpu, sc + 5, pc);

  return id;
}

static INLINE const IDESC *
emit_32 (SIM_CPU *current_cpu, PCADDR pc, CGEN_INSN_INT insn,
	 SCACHE *sc, int fast_p)
{
  ARGBUF *abuf = &sc->argbuf;
  const IDESC *id = @cpu@_decode (current_cpu, pc,
				  (USI) insn >> 16, insn, abuf);

  @cpu@_fill_argbuf (current_cpu, abuf, id, pc, fast_p);
  return id;
}

static INLINE const IDESC *
emit_full32 (SIM_CPU *current_cpu, PCADDR pc, CGEN_INSN_INT insn, SCACHE *sc,
	     int trace_p, int profile_p)
{
  const IDESC *id;

  @cpu@_emit_before (current_cpu, sc, pc, 1);
  id = emit_32 (current_cpu, pc, insn, sc + 1, 0);
  @cpu@_emit_after (current_cpu, sc + 2, pc);
  @cpu@_fill_argbuf_tp (current_cpu, &sc[1].argbuf, trace_p, profile_p);
  return id;
}

EOF

;;

xinit)

# Nothing needed.

;;

xextract-pbb)

# Inputs:  current_cpu, pc, sc, max_insns, FAST_P
# Outputs: sc, pc
# sc must be left pointing past the last created entry.
# pc must be left pointing past the last created entry.
# If the pbb is terminated by a cti insn, SET_CTI_VPC(sc) must be called
# to record the vpc of the cti insn.
# SET_INSN_COUNT(n) must be called to record number of real insns.

cat <<EOF
#line $LINENO "$0"
{
  const IDESC *idesc;
  int icount = 0;

  if ((pc & 3) != 0)
    {
      /* This occurs when single stepping and when compiling the not-taken
	 part of conditional branches.  */
      UHI insn = GETIMEMUHI (current_cpu, pc);
      int trace_p = PC_IN_TRACE_RANGE_P (current_cpu, pc);
      int profile_p = PC_IN_PROFILE_RANGE_P (current_cpu, pc);
      SCACHE *cti_sc; /* ??? tmp hack */

      /* A parallel insn isn't allowed here, but we don't mind nops.
	 ??? We need to wait until the insn is executed before signalling
	 the error, for situations where such signalling is wanted.  */
#if 0
      if ((insn & 0x8000) != 0
	  && (insn & 0x7fff) != 0x7000) /* parallel nops are ok */
	sim_engine_invalid_insn (current_cpu, pc, 0);
#endif

      /* Only emit before/after handlers if necessary.  */
      if (FAST_P || (! trace_p && ! profile_p))
	{
	  idesc = emit_16 (current_cpu, pc, insn & 0x7fff, sc, FAST_P, 0);
	  cti_sc = sc;
	  ++sc;
	  --max_insns;
	}
      else
	{
	  idesc = emit_full16 (current_cpu, pc, insn & 0x7fff, sc,
			       trace_p, profile_p);
	  cti_sc = sc + 1;
	  sc += 3;
	  max_insns -= 3;
	}
      ++icount;
      pc += 2;
      if (IDESC_CTI_P (idesc))
	{
	  SET_CTI_VPC (cti_sc);
	  goto Finish;
	}
    }

  /* There are two copies of the compiler: full(!fast) and fast.
     The "full" case emits before/after handlers for each insn.
     Having two copies of this code is a tradeoff, having one copy
     seemed a bit more difficult to read (due to constantly testing
     FAST_P).  ??? On the other hand, with address ranges we'll want to
     omit before/after handlers for unwanted insns.  Having separate loops
     for FAST/!FAST avoids constantly doing the test in the loop, but
     typically FAST_P is a constant and such tests will get optimized out.  */

  if (FAST_P)
    {
      while (max_insns > 0)
	{
	  USI insn = GETIMEMUSI (current_cpu, pc);
	  if ((SI) insn < 0)
	    {
	      /* 32 bit insn */
	      idesc = emit_32 (current_cpu, pc, insn, sc, 1);
	      ++sc;
	      --max_insns;
	      ++icount;
	      pc += 4;
	      if (IDESC_CTI_P (idesc))
		{
		  SET_CTI_VPC (sc - 1);
		  break;
		}
	    }
	  else
	    {
	      if ((insn & 0x8000) != 0) /* parallel? */
		{
                  int up_count;

		  if (((insn >> 16) & 0xfff0) == 0x10f0)
		    {
		      /* FIXME: No need to handle this sequentially if system
		         calls will be able to execute after second insn in
		         parallel. ( trap #num || insn ) */
		      /* insn */
		      idesc = emit_16 (current_cpu, pc + 2, insn & 0x7fff,
				       sc, 1, 0);
		      /* trap */
		      emit_16 (current_cpu, pc, insn >> 16, sc + 1, 1, 0);
                      up_count = 2;
		    }
		  else
		    {
		      /* Yep.  Here's the "interesting" [sic] part.  */
		      idesc = emit_parallel (current_cpu, pc, insn, sc, 1);
                      up_count = 3;
		    }
		  sc += up_count;
		  max_insns -= up_count;
		  icount += 2;
		  pc += 4;
		  if (IDESC_CTI_P (idesc))
		    {
		      SET_CTI_VPC (sc - up_count);
		      break;
		    }
		}
	      else /* 2 serial 16 bit insns */
		{
		  idesc = emit_16 (current_cpu, pc, insn >> 16, sc, 1, 0);
		  ++sc;
		  --max_insns;
		  ++icount;
		  pc += 2;
		  if (IDESC_CTI_P (idesc))
		    {
		      SET_CTI_VPC (sc - 1);
		      break;
		    }
		  /* While we're guaranteed that there's room to extract the
		     insn, when single stepping we can't; the pbb must stop
		     after the first insn.  */
		  if (max_insns == 0)
		    break;
		  idesc = emit_16 (current_cpu, pc, insn & 0x7fff, sc, 1, 0);
		  ++sc;
		  --max_insns;
		  ++icount;
		  pc += 2;
		  if (IDESC_CTI_P (idesc))
		    {
		      SET_CTI_VPC (sc - 1);
		      break;
		    }
		}
	    }
	}
    }
  else /* ! FAST_P */
    {
      while (max_insns > 0)
	{
	  USI insn = GETIMEMUSI (current_cpu, pc);
	  int trace_p = PC_IN_TRACE_RANGE_P (current_cpu, pc);
	  int profile_p = PC_IN_PROFILE_RANGE_P (current_cpu, pc);
	  SCACHE *cti_sc; /* ??? tmp hack */
	  if ((SI) insn < 0)
	    {
	      /* 32 bit insn
		 Only emit before/after handlers if necessary.  */
	      if (trace_p || profile_p)
		{
		  idesc = emit_full32 (current_cpu, pc, insn, sc,
				       trace_p, profile_p);
		  cti_sc = sc + 1;
		  sc += 3;
		  max_insns -= 3;
		}
	      else
		{
		  idesc = emit_32 (current_cpu, pc, insn, sc, 0);
		  cti_sc = sc;
		  ++sc;
		  --max_insns;
		}
	      ++icount;
	      pc += 4;
	      if (IDESC_CTI_P (idesc))
		{
		  SET_CTI_VPC (cti_sc);
		  break;
		}
	    }
	  else
	    {
	      if ((insn & 0x8000) != 0) /* parallel? */
		{
		  /* Yep.  Here's the "interesting" [sic] part.
		     Only emit before/after handlers if necessary.  */
		  if (trace_p || profile_p)
		    {
		      if (((insn >> 16) & 0xfff0) == 0x10f0)
		        {
		          /* FIXME: No need to handle this sequentially if
			     system calls will be able to execute after second
			     insn in parallel. ( trap #num || insn ) */
		          /* insn */
			  idesc = emit_full16 (current_cpu, pc + 2,
					       insn & 0x7fff, sc, 0, 0);
		          /* trap */
			  emit_full16 (current_cpu, pc, insn >> 16, sc + 3,
				       0, 0);
		        }
		      else
		        {
		          idesc = emit_full_parallel (current_cpu, pc, insn,
						      sc, trace_p, profile_p);
		        }
		      cti_sc = sc + 1;
		      sc += 6;
		      max_insns -= 6;
		    }
		  else
		    {
                      int up_count;

		      if (((insn >> 16) & 0xfff0) == 0x10f0)
		        {
		          /* FIXME: No need to handle this sequentially if
			     system calls will be able to execute after second
			     insn in parallel. ( trap #num || insn ) */
		          /* insn */
		          idesc = emit_16 (current_cpu, pc + 2, insn & 0x7fff,
				           sc, 0, 0);
		          /* trap */
		          emit_16 (current_cpu, pc, insn >> 16, sc + 1, 0, 0);
                          up_count = 2;
		        }
		      else
		        {
		          idesc = emit_parallel (current_cpu, pc, insn, sc, 0);
                          up_count = 3;
		        }
		      cti_sc = sc;
		      sc += up_count;
		      max_insns -= up_count;
		    }
		  icount += 2;
		  pc += 4;
		  if (IDESC_CTI_P (idesc))
		    {
		      SET_CTI_VPC (cti_sc);
		      break;
		    }
		}
	      else /* 2 serial 16 bit insns */
		{
		  /* Only emit before/after handlers if necessary.  */
		  if (trace_p || profile_p)
		    {
		      idesc = emit_full16 (current_cpu, pc, insn >> 16, sc,
					   trace_p, profile_p);
		      cti_sc = sc + 1;
		      sc += 3;
		      max_insns -= 3;
		    }
		  else
		    {
		      idesc = emit_16 (current_cpu, pc, insn >> 16, sc, 0, 0);
		      cti_sc = sc;
		      ++sc;
		      --max_insns;
		    }
		  ++icount;
		  pc += 2;
		  if (IDESC_CTI_P (idesc))
		    {
		      SET_CTI_VPC (cti_sc);
		      break;
		    }
		  /* While we're guaranteed that there's room to extract the
		     insn, when single stepping we can't; the pbb must stop
		     after the first insn.  */
		  if (max_insns <= 0)
		    break;
		  /* Use the same trace/profile address for the 2nd insn.
		     Saves us having to compute it and they come in pairs
		     anyway (e.g. can never branch to the 2nd insn).  */
		  if (trace_p || profile_p)
		    {
		      idesc = emit_full16 (current_cpu, pc, insn & 0x7fff, sc,
					   trace_p, profile_p);
		      cti_sc = sc + 1;
		      sc += 3;
		      max_insns -= 3;
		    }
		  else
		    {
		      idesc = emit_16 (current_cpu, pc, insn & 0x7fff, sc, 0, 0);
		      cti_sc = sc;
		      ++sc;
		      --max_insns;
		    }
		  ++icount;
		  pc += 2;
		  if (IDESC_CTI_P (idesc))
		    {
		      SET_CTI_VPC (cti_sc);
		      break;
		    }
		}
	    }
	}
    }

 Finish:
  SET_INSN_COUNT (icount);
}
EOF

;;

xfull-exec-pbb)

# Inputs: current_cpu, vpc, FAST_P
# Outputs: vpc
# vpc is the virtual program counter.

cat <<EOF
#line $LINENO "$0"
#define DEFINE_SWITCH
#include "sem2-switch.c"
EOF

;;

*)
  echo "Invalid argument to mainloop.in: $1" >&2
  exit 1
  ;;

esac
