Initial creation of sourceware repository

This commit is contained in:
Stan Shebs 1999-04-16 01:35:26 +00:00
parent cd946cff9e
commit c906108c21
2470 changed files with 976797 additions and 0 deletions

1046
sim/m32r/ChangeLog Normal file

File diff suppressed because it is too large Load diff

95
sim/m32r/Makefile.in Normal file
View file

@ -0,0 +1,95 @@
# Makefile template for Configure for the m32r simulator
# Copyright (C) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
# Contributed by Cygnus Support.
#
# 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 2 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, write to the Free Software Foundation, Inc.,
# 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
## COMMON_PRE_CONFIG_FRAG
M32R_OBJS = m32r.o cpu.o decode.o sem.o model.o mloop.o
CONFIG_DEVICES = dv-sockser.o
CONFIG_DEVICES =
SIM_OBJS = \
$(SIM_NEW_COMMON_OBJS) \
sim-cpu.o \
sim-hload.o \
sim-hrw.o \
sim-model.o \
sim-reg.o \
cgen-utils.o cgen-trace.o cgen-scache.o \
cgen-run.o sim-reason.o sim-engine.o sim-stop.o \
sim-if.o arch.o \
$(M32R_OBJS) \
traps.o devices.o \
$(CONFIG_DEVICES)
# Extra headers included by sim-main.h.
SIM_EXTRA_DEPS = \
$(CGEN_INCLUDE_DEPS) \
arch.h cpuall.h m32r-sim.h $(srcdir)/../../opcodes/m32r-desc.h
SIM_EXTRA_CFLAGS =
SIM_RUN_OBJS = nrun.o
SIM_EXTRA_CLEAN = m32r-clean
# This selects the m32r newlib/libgloss syscall definitions.
NL_TARGET = -DNL_TARGET_m32r
## COMMON_POST_CONFIG_FRAG
arch = m32r
sim-if.o: sim-if.c $(SIM_MAIN_DEPS) $(srcdir)/../common/sim-core.h
arch.o: arch.c $(SIM_MAIN_DEPS)
traps.o: traps.c targ-vals.h $(SIM_MAIN_DEPS)
devices.o: devices.c $(SIM_MAIN_DEPS)
# M32R objs
M32RBF_INCLUDE_DEPS = \
$(CGEN_MAIN_CPU_DEPS) \
cpu.h decode.h eng.h
m32r.o: m32r.c $(M32RBF_INCLUDE_DEPS)
# FIXME: Use of `mono' is wip.
mloop.c eng.h: stamp-mloop
stamp-mloop: $(srcdir)/../common/genmloop.sh mloop.in Makefile
$(SHELL) $(srccom)/genmloop.sh \
-mono -fast -pbb -switch sem-switch.c \
-cpu m32rbf -infile $(srcdir)/mloop.in
$(SHELL) $(srcroot)/move-if-change eng.hin eng.h
$(SHELL) $(srcroot)/move-if-change mloop.cin mloop.c
touch stamp-mloop
mloop.o: mloop.c sem-switch.c $(M32RBF_INCLUDE_DEPS)
cpu.o: cpu.c $(M32RBF_INCLUDE_DEPS)
decode.o: decode.c $(M32RBF_INCLUDE_DEPS)
sem.o: sem.c $(M32RBF_INCLUDE_DEPS)
model.o: model.c $(M32RBF_INCLUDE_DEPS)
m32r-clean:
rm -f mloop.c eng.h stamp-mloop
rm -f tmp-*

14
sim/m32r/README Normal file
View file

@ -0,0 +1,14 @@
This is the m32r simulator directory.
It is still work-in-progress. The current sources are reasonably
well tested and lots of features are in. However, there's lots
more yet to come.
There are lots of machine generated files in the source directory!
They are only generated if you configure with --enable-cgen-maint,
similar in behaviour to Makefile.in, configure under automake/autoconf.
For details on the generator, see ../../cgen.
devo/cgen isn't part of the comp-tools module yet.
You'll need to check it out manually (also akin to automake/autoconf).

9
sim/m32r/TODO Normal file
View file

@ -0,0 +1,9 @@
- header file dependencies revisit
- hooks cleanup
- testsuites
- FIXME's
- memory accesses still test if profiling is on even in fast mode
- fill nop counting done even in fast mode
- have semantic code use G/SET_H_FOO if not default [incl fun-access]
- have G/SET_H_FOO macros call function if fun-access
- --> can always use G/S_H_FOO macros

15
sim/m32r/acconfig.h Normal file
View file

@ -0,0 +1,15 @@
/* Define to 1 if NLS is requested. */
#undef ENABLE_NLS
/* Define as 1 if you have catgets and don't want to use GNU gettext. */
#undef HAVE_CATGETS
/* Define as 1 if you have gettext and don't want to use GNU gettext. */
#undef HAVE_GETTEXT
/* Define as 1 if you have the stpcpy function. */
#undef HAVE_STPCPY
/* Define if your locale.h file contains LC_MESSAGES. */
#undef HAVE_LC_MESSAGES

356
sim/m32r/arch.c Normal file
View file

@ -0,0 +1,356 @@
/* Simulator support for m32r.
THIS FILE IS MACHINE GENERATED WITH CGEN.
Copyright (C) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
This file is part of the GNU Simulators.
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 2, 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, write to the Free Software Foundation, Inc.,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#include "sim-main.h"
#include "bfd.h"
const MACH *sim_machs[] =
{
#ifdef HAVE_CPU_M32RBF
& m32r_mach,
#endif
0
};
/* Get the value of h-pc. */
USI
a_m32r_h_pc_get (SIM_CPU *current_cpu)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
return m32rbf_h_pc_get (current_cpu);
#endif
default :
abort ();
}
}
/* Set a value for h-pc. */
void
a_m32r_h_pc_set (SIM_CPU *current_cpu, USI newval)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
m32rbf_h_pc_set (current_cpu, newval);
break;
#endif
default :
abort ();
}
}
/* Get the value of h-gr. */
SI
a_m32r_h_gr_get (SIM_CPU *current_cpu, UINT regno)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
return m32rbf_h_gr_get (current_cpu, regno);
#endif
default :
abort ();
}
}
/* Set a value for h-gr. */
void
a_m32r_h_gr_set (SIM_CPU *current_cpu, UINT regno, SI newval)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
m32rbf_h_gr_set (current_cpu, regno, newval);
break;
#endif
default :
abort ();
}
}
/* Get the value of h-cr. */
USI
a_m32r_h_cr_get (SIM_CPU *current_cpu, UINT regno)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
return m32rbf_h_cr_get (current_cpu, regno);
#endif
default :
abort ();
}
}
/* Set a value for h-cr. */
void
a_m32r_h_cr_set (SIM_CPU *current_cpu, UINT regno, USI newval)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
m32rbf_h_cr_set (current_cpu, regno, newval);
break;
#endif
default :
abort ();
}
}
/* Get the value of h-accum. */
DI
a_m32r_h_accum_get (SIM_CPU *current_cpu)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
return m32rbf_h_accum_get (current_cpu);
#endif
default :
abort ();
}
}
/* Set a value for h-accum. */
void
a_m32r_h_accum_set (SIM_CPU *current_cpu, DI newval)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
m32rbf_h_accum_set (current_cpu, newval);
break;
#endif
default :
abort ();
}
}
/* Get the value of h-accums. */
DI
a_m32r_h_accums_get (SIM_CPU *current_cpu, UINT regno)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
default :
abort ();
}
}
/* Set a value for h-accums. */
void
a_m32r_h_accums_set (SIM_CPU *current_cpu, UINT regno, DI newval)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
default :
abort ();
}
}
/* Get the value of h-cond. */
BI
a_m32r_h_cond_get (SIM_CPU *current_cpu)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
return m32rbf_h_cond_get (current_cpu);
#endif
default :
abort ();
}
}
/* Set a value for h-cond. */
void
a_m32r_h_cond_set (SIM_CPU *current_cpu, BI newval)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
m32rbf_h_cond_set (current_cpu, newval);
break;
#endif
default :
abort ();
}
}
/* Get the value of h-psw. */
UQI
a_m32r_h_psw_get (SIM_CPU *current_cpu)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
return m32rbf_h_psw_get (current_cpu);
#endif
default :
abort ();
}
}
/* Set a value for h-psw. */
void
a_m32r_h_psw_set (SIM_CPU *current_cpu, UQI newval)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
m32rbf_h_psw_set (current_cpu, newval);
break;
#endif
default :
abort ();
}
}
/* Get the value of h-bpsw. */
UQI
a_m32r_h_bpsw_get (SIM_CPU *current_cpu)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
return m32rbf_h_bpsw_get (current_cpu);
#endif
default :
abort ();
}
}
/* Set a value for h-bpsw. */
void
a_m32r_h_bpsw_set (SIM_CPU *current_cpu, UQI newval)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
m32rbf_h_bpsw_set (current_cpu, newval);
break;
#endif
default :
abort ();
}
}
/* Get the value of h-bbpsw. */
UQI
a_m32r_h_bbpsw_get (SIM_CPU *current_cpu)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
return m32rbf_h_bbpsw_get (current_cpu);
#endif
default :
abort ();
}
}
/* Set a value for h-bbpsw. */
void
a_m32r_h_bbpsw_set (SIM_CPU *current_cpu, UQI newval)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
m32rbf_h_bbpsw_set (current_cpu, newval);
break;
#endif
default :
abort ();
}
}
/* Get the value of h-lock. */
BI
a_m32r_h_lock_get (SIM_CPU *current_cpu)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
return m32rbf_h_lock_get (current_cpu);
#endif
default :
abort ();
}
}
/* Set a value for h-lock. */
void
a_m32r_h_lock_set (SIM_CPU *current_cpu, BI newval)
{
switch (STATE_ARCHITECTURE (CPU_STATE (current_cpu))->mach)
{
#ifdef HAVE_CPU_M32RBF
case bfd_mach_m32r :
m32rbf_h_lock_set (current_cpu, newval);
break;
#endif
default :
abort ();
}
}

69
sim/m32r/arch.h Normal file
View file

@ -0,0 +1,69 @@
/* Simulator header for m32r.
THIS FILE IS MACHINE GENERATED WITH CGEN.
Copyright (C) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
This file is part of the GNU Simulators.
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 2, 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, write to the Free Software Foundation, Inc.,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef M32R_ARCH_H
#define M32R_ARCH_H
#define TARGET_BIG_ENDIAN 1
/* Cover fns for register access. */
USI a_m32r_h_pc_get (SIM_CPU *);
void a_m32r_h_pc_set (SIM_CPU *, USI);
SI a_m32r_h_gr_get (SIM_CPU *, UINT);
void a_m32r_h_gr_set (SIM_CPU *, UINT, SI);
USI a_m32r_h_cr_get (SIM_CPU *, UINT);
void a_m32r_h_cr_set (SIM_CPU *, UINT, USI);
DI a_m32r_h_accum_get (SIM_CPU *);
void a_m32r_h_accum_set (SIM_CPU *, DI);
DI a_m32r_h_accums_get (SIM_CPU *, UINT);
void a_m32r_h_accums_set (SIM_CPU *, UINT, DI);
BI a_m32r_h_cond_get (SIM_CPU *);
void a_m32r_h_cond_set (SIM_CPU *, BI);
UQI a_m32r_h_psw_get (SIM_CPU *);
void a_m32r_h_psw_set (SIM_CPU *, UQI);
UQI a_m32r_h_bpsw_get (SIM_CPU *);
void a_m32r_h_bpsw_set (SIM_CPU *, UQI);
UQI a_m32r_h_bbpsw_get (SIM_CPU *);
void a_m32r_h_bbpsw_set (SIM_CPU *, UQI);
BI a_m32r_h_lock_get (SIM_CPU *);
void a_m32r_h_lock_set (SIM_CPU *, BI);
/* Enum declaration for model types. */
typedef enum model_type {
MODEL_M32R_D, MODEL_TEST
, MODEL_MAX
} MODEL_TYPE;
#define MAX_MODELS ((int) MODEL_MAX)
/* Enum declaration for unit types. */
typedef enum unit_type {
UNIT_NONE, UNIT_M32R_D_U_STORE, UNIT_M32R_D_U_LOAD, UNIT_M32R_D_U_CTI
, UNIT_M32R_D_U_MAC, UNIT_M32R_D_U_CMP, UNIT_M32R_D_U_EXEC, UNIT_TEST_U_EXEC
, UNIT_MAX
} UNIT_TYPE;
#define MAX_UNITS (2)
#endif /* M32R_ARCH_H */

162
sim/m32r/config.in Normal file
View file

@ -0,0 +1,162 @@
/* config.in. Generated automatically from configure.in by autoheader. */
/* Define if using alloca.c. */
#undef C_ALLOCA
/* Define to empty if the keyword does not work. */
#undef const
/* Define to one of _getb67, GETB67, getb67 for Cray-2 and Cray-YMP systems.
This function is required for alloca.c support on those systems. */
#undef CRAY_STACKSEG_END
/* Define if you have alloca, as a function or macro. */
#undef HAVE_ALLOCA
/* Define if you have <alloca.h> and it should be used (not on Ultrix). */
#undef HAVE_ALLOCA_H
/* Define if you have a working `mmap' system call. */
#undef HAVE_MMAP
/* Define as __inline if that's what the C compiler calls it. */
#undef inline
/* Define to `long' if <sys/types.h> doesn't define. */
#undef off_t
/* Define if you need to in order for stat and other things to work. */
#undef _POSIX_SOURCE
/* Define as the return type of signal handlers (int or void). */
#undef RETSIGTYPE
/* Define to `unsigned' if <sys/types.h> doesn't define. */
#undef size_t
/* If using the C implementation of alloca, define if you know the
direction of stack growth for your system; otherwise it will be
automatically deduced at run-time.
STACK_DIRECTION > 0 => grows toward higher addresses
STACK_DIRECTION < 0 => grows toward lower addresses
STACK_DIRECTION = 0 => direction of growth unknown
*/
#undef STACK_DIRECTION
/* Define if you have the ANSI C header files. */
#undef STDC_HEADERS
/* Define if your processor stores words with the most significant
byte first (like Motorola and SPARC, unlike Intel and VAX). */
#undef WORDS_BIGENDIAN
/* Define to 1 if NLS is requested. */
#undef ENABLE_NLS
/* Define as 1 if you have gettext and don't want to use GNU gettext. */
#undef HAVE_GETTEXT
/* Define as 1 if you have the stpcpy function. */
#undef HAVE_STPCPY
/* Define if your locale.h file contains LC_MESSAGES. */
#undef HAVE_LC_MESSAGES
/* Define if you have the __argz_count function. */
#undef HAVE___ARGZ_COUNT
/* Define if you have the __argz_next function. */
#undef HAVE___ARGZ_NEXT
/* Define if you have the __argz_stringify function. */
#undef HAVE___ARGZ_STRINGIFY
/* Define if you have the __setfpucw function. */
#undef HAVE___SETFPUCW
/* Define if you have the dcgettext function. */
#undef HAVE_DCGETTEXT
/* Define if you have the getcwd function. */
#undef HAVE_GETCWD
/* Define if you have the getpagesize function. */
#undef HAVE_GETPAGESIZE
/* Define if you have the getrusage function. */
#undef HAVE_GETRUSAGE
/* Define if you have the munmap function. */
#undef HAVE_MUNMAP
/* Define if you have the putenv function. */
#undef HAVE_PUTENV
/* Define if you have the setenv function. */
#undef HAVE_SETENV
/* Define if you have the setlocale function. */
#undef HAVE_SETLOCALE
/* Define if you have the sigaction function. */
#undef HAVE_SIGACTION
/* Define if you have the stpcpy function. */
#undef HAVE_STPCPY
/* Define if you have the strcasecmp function. */
#undef HAVE_STRCASECMP
/* Define if you have the strchr function. */
#undef HAVE_STRCHR
/* Define if you have the time function. */
#undef HAVE_TIME
/* Define if you have the <argz.h> header file. */
#undef HAVE_ARGZ_H
/* Define if you have the <fcntl.h> header file. */
#undef HAVE_FCNTL_H
/* Define if you have the <fpu_control.h> header file. */
#undef HAVE_FPU_CONTROL_H
/* Define if you have the <limits.h> header file. */
#undef HAVE_LIMITS_H
/* Define if you have the <locale.h> header file. */
#undef HAVE_LOCALE_H
/* Define if you have the <malloc.h> header file. */
#undef HAVE_MALLOC_H
/* Define if you have the <nl_types.h> header file. */
#undef HAVE_NL_TYPES_H
/* Define if you have the <stdlib.h> header file. */
#undef HAVE_STDLIB_H
/* Define if you have the <string.h> header file. */
#undef HAVE_STRING_H
/* Define if you have the <strings.h> header file. */
#undef HAVE_STRINGS_H
/* Define if you have the <sys/param.h> header file. */
#undef HAVE_SYS_PARAM_H
/* Define if you have the <sys/resource.h> header file. */
#undef HAVE_SYS_RESOURCE_H
/* Define if you have the <sys/time.h> header file. */
#undef HAVE_SYS_TIME_H
/* Define if you have the <time.h> header file. */
#undef HAVE_TIME_H
/* Define if you have the <unistd.h> header file. */
#undef HAVE_UNISTD_H
/* Define if you have the <values.h> header file. */
#undef HAVE_VALUES_H

4251
sim/m32r/configure vendored Executable file

File diff suppressed because it is too large Load diff

17
sim/m32r/configure.in Normal file
View file

@ -0,0 +1,17 @@
dnl Process this file with autoconf to produce a configure script.
sinclude(../common/aclocal.m4)
AC_PREREQ(2.5)dnl
AC_INIT(Makefile.in)
SIM_AC_COMMON
SIM_AC_OPTION_ENDIAN(BIG_ENDIAN)
SIM_AC_OPTION_ALIGNMENT(STRICT_ALIGNMENT)
SIM_AC_OPTION_HOSTENDIAN
SIM_AC_OPTION_SCACHE(16384)
SIM_AC_OPTION_DEFAULT_MODEL(m32r/d)
SIM_AC_OPTION_ENVIRONMENT
SIM_AC_OPTION_INLINE()
SIM_AC_OPTION_CGEN_MAINT
SIM_AC_OUTPUT

196
sim/m32r/cpu.c Normal file
View file

@ -0,0 +1,196 @@
/* Misc. support for CPU family m32rbf.
THIS FILE IS MACHINE GENERATED WITH CGEN.
Copyright (C) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
This file is part of the GNU Simulators.
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 2, 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, write to the Free Software Foundation, Inc.,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#define WANT_CPU m32rbf
#define WANT_CPU_M32RBF
#include "sim-main.h"
/* Get the value of h-pc. */
USI
m32rbf_h_pc_get (SIM_CPU *current_cpu)
{
return CPU (h_pc);
}
/* Set a value for h-pc. */
void
m32rbf_h_pc_set (SIM_CPU *current_cpu, USI newval)
{
CPU (h_pc) = newval;
}
/* Get the value of h-gr. */
SI
m32rbf_h_gr_get (SIM_CPU *current_cpu, UINT regno)
{
return CPU (h_gr[regno]);
}
/* Set a value for h-gr. */
void
m32rbf_h_gr_set (SIM_CPU *current_cpu, UINT regno, SI newval)
{
CPU (h_gr[regno]) = newval;
}
/* Get the value of h-cr. */
USI
m32rbf_h_cr_get (SIM_CPU *current_cpu, UINT regno)
{
return GET_H_CR (regno);
}
/* Set a value for h-cr. */
void
m32rbf_h_cr_set (SIM_CPU *current_cpu, UINT regno, USI newval)
{
SET_H_CR (regno, newval);
}
/* Get the value of h-accum. */
DI
m32rbf_h_accum_get (SIM_CPU *current_cpu)
{
return GET_H_ACCUM ();
}
/* Set a value for h-accum. */
void
m32rbf_h_accum_set (SIM_CPU *current_cpu, DI newval)
{
SET_H_ACCUM (newval);
}
/* Get the value of h-accums. */
DI
m32rbf_h_accums_get (SIM_CPU *current_cpu, UINT regno)
{
return GET_H_ACCUMS (regno);
}
/* Set a value for h-accums. */
void
m32rbf_h_accums_set (SIM_CPU *current_cpu, UINT regno, DI newval)
{
SET_H_ACCUMS (regno, newval);
}
/* Get the value of h-cond. */
BI
m32rbf_h_cond_get (SIM_CPU *current_cpu)
{
return CPU (h_cond);
}
/* Set a value for h-cond. */
void
m32rbf_h_cond_set (SIM_CPU *current_cpu, BI newval)
{
CPU (h_cond) = newval;
}
/* Get the value of h-psw. */
UQI
m32rbf_h_psw_get (SIM_CPU *current_cpu)
{
return GET_H_PSW ();
}
/* Set a value for h-psw. */
void
m32rbf_h_psw_set (SIM_CPU *current_cpu, UQI newval)
{
SET_H_PSW (newval);
}
/* Get the value of h-bpsw. */
UQI
m32rbf_h_bpsw_get (SIM_CPU *current_cpu)
{
return CPU (h_bpsw);
}
/* Set a value for h-bpsw. */
void
m32rbf_h_bpsw_set (SIM_CPU *current_cpu, UQI newval)
{
CPU (h_bpsw) = newval;
}
/* Get the value of h-bbpsw. */
UQI
m32rbf_h_bbpsw_get (SIM_CPU *current_cpu)
{
return CPU (h_bbpsw);
}
/* Set a value for h-bbpsw. */
void
m32rbf_h_bbpsw_set (SIM_CPU *current_cpu, UQI newval)
{
CPU (h_bbpsw) = newval;
}
/* Get the value of h-lock. */
BI
m32rbf_h_lock_get (SIM_CPU *current_cpu)
{
return CPU (h_lock);
}
/* Set a value for h-lock. */
void
m32rbf_h_lock_set (SIM_CPU *current_cpu, BI newval)
{
CPU (h_lock) = newval;
}
/* Record trace results for INSN. */
void
m32rbf_record_trace_results (SIM_CPU *current_cpu, CGEN_INSN *insn,
int *indices, TRACE_RECORD *tr)
{
}

852
sim/m32r/cpu.h Normal file
View file

@ -0,0 +1,852 @@
/* CPU family header for m32rbf.
THIS FILE IS MACHINE GENERATED WITH CGEN.
Copyright (C) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
This file is part of the GNU Simulators.
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 2, 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, write to the Free Software Foundation, Inc.,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef CPU_M32RBF_H
#define CPU_M32RBF_H
/* Maximum number of instructions that are fetched at a time.
This is for LIW type instructions sets (e.g. m32r). */
#define MAX_LIW_INSNS 2
/* Maximum number of instructions that can be executed in parallel. */
#define MAX_PARALLEL_INSNS 1
/* CPU state information. */
typedef struct {
/* Hardware elements. */
struct {
/* program counter */
USI h_pc;
#define GET_H_PC() CPU (h_pc)
#define SET_H_PC(x) (CPU (h_pc) = (x))
/* general registers */
SI h_gr[16];
#define GET_H_GR(a1) CPU (h_gr)[a1]
#define SET_H_GR(a1, x) (CPU (h_gr)[a1] = (x))
/* control registers */
USI h_cr[16];
/* GET_H_CR macro user-written */
/* SET_H_CR macro user-written */
/* accumulator */
DI h_accum;
/* GET_H_ACCUM macro user-written */
/* SET_H_ACCUM macro user-written */
/* condition bit */
BI h_cond;
#define GET_H_COND() CPU (h_cond)
#define SET_H_COND(x) (CPU (h_cond) = (x))
/* psw part of psw */
UQI h_psw;
/* GET_H_PSW macro user-written */
/* SET_H_PSW macro user-written */
/* backup psw */
UQI h_bpsw;
#define GET_H_BPSW() CPU (h_bpsw)
#define SET_H_BPSW(x) (CPU (h_bpsw) = (x))
/* backup bpsw */
UQI h_bbpsw;
#define GET_H_BBPSW() CPU (h_bbpsw)
#define SET_H_BBPSW(x) (CPU (h_bbpsw) = (x))
/* lock */
BI h_lock;
#define GET_H_LOCK() CPU (h_lock)
#define SET_H_LOCK(x) (CPU (h_lock) = (x))
} hardware;
#define CPU_CGEN_HW(cpu) (& (cpu)->cpu_data.hardware)
} M32RBF_CPU_DATA;
/* Cover fns for register access. */
USI m32rbf_h_pc_get (SIM_CPU *);
void m32rbf_h_pc_set (SIM_CPU *, USI);
SI m32rbf_h_gr_get (SIM_CPU *, UINT);
void m32rbf_h_gr_set (SIM_CPU *, UINT, SI);
USI m32rbf_h_cr_get (SIM_CPU *, UINT);
void m32rbf_h_cr_set (SIM_CPU *, UINT, USI);
DI m32rbf_h_accum_get (SIM_CPU *);
void m32rbf_h_accum_set (SIM_CPU *, DI);
DI m32rbf_h_accums_get (SIM_CPU *, UINT);
void m32rbf_h_accums_set (SIM_CPU *, UINT, DI);
BI m32rbf_h_cond_get (SIM_CPU *);
void m32rbf_h_cond_set (SIM_CPU *, BI);
UQI m32rbf_h_psw_get (SIM_CPU *);
void m32rbf_h_psw_set (SIM_CPU *, UQI);
UQI m32rbf_h_bpsw_get (SIM_CPU *);
void m32rbf_h_bpsw_set (SIM_CPU *, UQI);
UQI m32rbf_h_bbpsw_get (SIM_CPU *);
void m32rbf_h_bbpsw_set (SIM_CPU *, UQI);
BI m32rbf_h_lock_get (SIM_CPU *);
void m32rbf_h_lock_set (SIM_CPU *, BI);
/* These must be hand-written. */
extern CPUREG_FETCH_FN m32rbf_fetch_register;
extern CPUREG_STORE_FN m32rbf_store_register;
typedef struct {
UINT h_gr;
} MODEL_M32R_D_DATA;
typedef struct {
int empty;
} MODEL_TEST_DATA;
union sem_fields {
struct { /* empty sformat for unspecified field list */
int empty;
} fmt_empty;
struct { /* e.g. add $dr,$sr */
SI * i_dr;
SI * i_sr;
unsigned char in_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_add;
struct { /* e.g. add3 $dr,$sr,$hash$slo16 */
INT f_simm16;
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_add3;
struct { /* e.g. and3 $dr,$sr,$uimm16 */
UINT f_uimm16;
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_and3;
struct { /* e.g. or3 $dr,$sr,$hash$ulo16 */
UINT f_uimm16;
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_or3;
struct { /* e.g. addi $dr,$simm8 */
INT f_simm8;
SI * i_dr;
unsigned char in_dr;
unsigned char out_dr;
} fmt_addi;
struct { /* e.g. addv $dr,$sr */
SI * i_dr;
SI * i_sr;
unsigned char in_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_addv;
struct { /* e.g. addv3 $dr,$sr,$simm16 */
INT f_simm16;
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_addv3;
struct { /* e.g. addx $dr,$sr */
SI * i_dr;
SI * i_sr;
unsigned char in_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_addx;
struct { /* e.g. cmp $src1,$src2 */
SI * i_src1;
SI * i_src2;
unsigned char in_src1;
unsigned char in_src2;
} fmt_cmp;
struct { /* e.g. cmpi $src2,$simm16 */
INT f_simm16;
SI * i_src2;
unsigned char in_src2;
} fmt_cmpi;
struct { /* e.g. div $dr,$sr */
SI * i_dr;
SI * i_sr;
unsigned char in_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_div;
struct { /* e.g. ld $dr,@$sr */
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_ld;
struct { /* e.g. ld $dr,@($slo16,$sr) */
INT f_simm16;
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_ld_d;
struct { /* e.g. ldb $dr,@$sr */
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_ldb;
struct { /* e.g. ldb $dr,@($slo16,$sr) */
INT f_simm16;
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_ldb_d;
struct { /* e.g. ldh $dr,@$sr */
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_ldh;
struct { /* e.g. ldh $dr,@($slo16,$sr) */
INT f_simm16;
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_ldh_d;
struct { /* e.g. ld $dr,@$sr+ */
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
unsigned char out_sr;
} fmt_ld_plus;
struct { /* e.g. ld24 $dr,$uimm24 */
ADDR i_uimm24;
SI * i_dr;
unsigned char out_dr;
} fmt_ld24;
struct { /* e.g. ldi8 $dr,$simm8 */
INT f_simm8;
SI * i_dr;
unsigned char out_dr;
} fmt_ldi8;
struct { /* e.g. ldi16 $dr,$hash$slo16 */
INT f_simm16;
SI * i_dr;
unsigned char out_dr;
} fmt_ldi16;
struct { /* e.g. lock $dr,@$sr */
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_lock;
struct { /* e.g. machi $src1,$src2 */
SI * i_src1;
SI * i_src2;
unsigned char in_src1;
unsigned char in_src2;
} fmt_machi;
struct { /* e.g. mulhi $src1,$src2 */
SI * i_src1;
SI * i_src2;
unsigned char in_src1;
unsigned char in_src2;
} fmt_mulhi;
struct { /* e.g. mv $dr,$sr */
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_mv;
struct { /* e.g. mvfachi $dr */
SI * i_dr;
unsigned char out_dr;
} fmt_mvfachi;
struct { /* e.g. mvfc $dr,$scr */
UINT f_r2;
SI * i_dr;
unsigned char out_dr;
} fmt_mvfc;
struct { /* e.g. mvtachi $src1 */
SI * i_src1;
unsigned char in_src1;
} fmt_mvtachi;
struct { /* e.g. mvtc $sr,$dcr */
UINT f_r1;
SI * i_sr;
unsigned char in_sr;
} fmt_mvtc;
struct { /* e.g. nop */
int empty;
} fmt_nop;
struct { /* e.g. rac */
int empty;
} fmt_rac;
struct { /* e.g. seth $dr,$hash$hi16 */
UINT f_hi16;
SI * i_dr;
unsigned char out_dr;
} fmt_seth;
struct { /* e.g. sll3 $dr,$sr,$simm16 */
INT f_simm16;
SI * i_sr;
SI * i_dr;
unsigned char in_sr;
unsigned char out_dr;
} fmt_sll3;
struct { /* e.g. slli $dr,$uimm5 */
UINT f_uimm5;
SI * i_dr;
unsigned char in_dr;
unsigned char out_dr;
} fmt_slli;
struct { /* e.g. st $src1,@$src2 */
SI * i_src1;
SI * i_src2;
unsigned char in_src1;
unsigned char in_src2;
} fmt_st;
struct { /* e.g. st $src1,@($slo16,$src2) */
INT f_simm16;
SI * i_src1;
SI * i_src2;
unsigned char in_src1;
unsigned char in_src2;
} fmt_st_d;
struct { /* e.g. stb $src1,@$src2 */
SI * i_src1;
SI * i_src2;
unsigned char in_src1;
unsigned char in_src2;
} fmt_stb;
struct { /* e.g. stb $src1,@($slo16,$src2) */
INT f_simm16;
SI * i_src1;
SI * i_src2;
unsigned char in_src1;
unsigned char in_src2;
} fmt_stb_d;
struct { /* e.g. sth $src1,@$src2 */
SI * i_src1;
SI * i_src2;
unsigned char in_src1;
unsigned char in_src2;
} fmt_sth;
struct { /* e.g. sth $src1,@($slo16,$src2) */
INT f_simm16;
SI * i_src1;
SI * i_src2;
unsigned char in_src1;
unsigned char in_src2;
} fmt_sth_d;
struct { /* e.g. st $src1,@+$src2 */
SI * i_src1;
SI * i_src2;
unsigned char in_src1;
unsigned char in_src2;
unsigned char out_src2;
} fmt_st_plus;
struct { /* e.g. unlock $src1,@$src2 */
SI * i_src1;
SI * i_src2;
unsigned char in_src1;
unsigned char in_src2;
} fmt_unlock;
/* cti insns, kept separately so addr_cache is in fixed place */
struct {
union {
struct { /* e.g. bc.s $disp8 */
IADDR i_disp8;
} fmt_bc8;
struct { /* e.g. bc.l $disp24 */
IADDR i_disp24;
} fmt_bc24;
struct { /* e.g. beq $src1,$src2,$disp16 */
IADDR i_disp16;
SI * i_src1;
SI * i_src2;
unsigned char in_src1;
unsigned char in_src2;
} fmt_beq;
struct { /* e.g. beqz $src2,$disp16 */
IADDR i_disp16;
SI * i_src2;
unsigned char in_src2;
} fmt_beqz;
struct { /* e.g. bl.s $disp8 */
IADDR i_disp8;
unsigned char out_h_gr_14;
} fmt_bl8;
struct { /* e.g. bl.l $disp24 */
IADDR i_disp24;
unsigned char out_h_gr_14;
} fmt_bl24;
struct { /* e.g. bra.s $disp8 */
IADDR i_disp8;
} fmt_bra8;
struct { /* e.g. bra.l $disp24 */
IADDR i_disp24;
} fmt_bra24;
struct { /* e.g. jl $sr */
SI * i_sr;
unsigned char in_sr;
unsigned char out_h_gr_14;
} fmt_jl;
struct { /* e.g. jmp $sr */
SI * i_sr;
unsigned char in_sr;
} fmt_jmp;
struct { /* e.g. rte */
int empty;
} fmt_rte;
struct { /* e.g. trap $uimm4 */
UINT f_uimm4;
} fmt_trap;
} fields;
#if WITH_SCACHE_PBB
SEM_PC addr_cache;
#endif
} cti;
#if WITH_SCACHE_PBB
/* Writeback handler. */
struct {
/* Pointer to argbuf entry for insn whose results need writing back. */
const struct argbuf *abuf;
} write;
/* x-before handler */
struct {
/*const SCACHE *insns[MAX_PARALLEL_INSNS];*/
int first_p;
} before;
/* x-after handler */
struct {
int empty;
} after;
/* This entry is used to terminate each pbb. */
struct {
/* Number of insns in pbb. */
int insn_count;
/* Next pbb to execute. */
SCACHE *next;
} chain;
#endif
};
/* The ARGBUF struct. */
struct argbuf {
/* These are the baseclass definitions. */
IADDR addr;
const IDESC *idesc;
char trace_p;
char profile_p;
/* cpu specific data follows */
union sem semantic;
int written;
union sem_fields fields;
};
/* A cached insn.
??? SCACHE used to contain more than just argbuf. We could delete the
type entirely and always just use ARGBUF, but for future concerns and as
a level of abstraction it is left in. */
struct scache {
struct argbuf argbuf;
};
/* Macros to simplify extraction, reading and semantic code.
These define and assign the local vars that contain the insn's fields. */
#define EXTRACT_IFMT_EMPTY_VARS \
/* Instruction fields. */ \
unsigned int length;
#define EXTRACT_IFMT_EMPTY_CODE \
length = 0; \
#define EXTRACT_IFMT_ADD_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
unsigned int length;
#define EXTRACT_IFMT_ADD_CODE \
length = 2; \
f_op1 = EXTRACT_UINT (insn, 16, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 16, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 16, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 16, 12, 4); \
#define EXTRACT_IFMT_ADD3_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
INT f_simm16; \
unsigned int length;
#define EXTRACT_IFMT_ADD3_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 32, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 32, 12, 4); \
f_simm16 = EXTRACT_INT (insn, 32, 16, 16); \
#define EXTRACT_IFMT_AND3_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
UINT f_uimm16; \
unsigned int length;
#define EXTRACT_IFMT_AND3_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 32, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 32, 12, 4); \
f_uimm16 = EXTRACT_UINT (insn, 32, 16, 16); \
#define EXTRACT_IFMT_OR3_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
UINT f_uimm16; \
unsigned int length;
#define EXTRACT_IFMT_OR3_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 32, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 32, 12, 4); \
f_uimm16 = EXTRACT_UINT (insn, 32, 16, 16); \
#define EXTRACT_IFMT_ADDI_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
INT f_simm8; \
unsigned int length;
#define EXTRACT_IFMT_ADDI_CODE \
length = 2; \
f_op1 = EXTRACT_UINT (insn, 16, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 16, 4, 4); \
f_simm8 = EXTRACT_INT (insn, 16, 8, 8); \
#define EXTRACT_IFMT_ADDV3_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
INT f_simm16; \
unsigned int length;
#define EXTRACT_IFMT_ADDV3_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 32, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 32, 12, 4); \
f_simm16 = EXTRACT_INT (insn, 32, 16, 16); \
#define EXTRACT_IFMT_BC8_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
SI f_disp8; \
unsigned int length;
#define EXTRACT_IFMT_BC8_CODE \
length = 2; \
f_op1 = EXTRACT_UINT (insn, 16, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 16, 4, 4); \
f_disp8 = ((((EXTRACT_INT (insn, 16, 8, 8)) << (2))) + (((pc) & (-4)))); \
#define EXTRACT_IFMT_BC24_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
SI f_disp24; \
unsigned int length;
#define EXTRACT_IFMT_BC24_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_disp24 = ((((EXTRACT_INT (insn, 32, 8, 24)) << (2))) + (pc)); \
#define EXTRACT_IFMT_BEQ_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
SI f_disp16; \
unsigned int length;
#define EXTRACT_IFMT_BEQ_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 32, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 32, 12, 4); \
f_disp16 = ((((EXTRACT_INT (insn, 32, 16, 16)) << (2))) + (pc)); \
#define EXTRACT_IFMT_BEQZ_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
SI f_disp16; \
unsigned int length;
#define EXTRACT_IFMT_BEQZ_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 32, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 32, 12, 4); \
f_disp16 = ((((EXTRACT_INT (insn, 32, 16, 16)) << (2))) + (pc)); \
#define EXTRACT_IFMT_CMP_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
unsigned int length;
#define EXTRACT_IFMT_CMP_CODE \
length = 2; \
f_op1 = EXTRACT_UINT (insn, 16, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 16, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 16, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 16, 12, 4); \
#define EXTRACT_IFMT_CMPI_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
INT f_simm16; \
unsigned int length;
#define EXTRACT_IFMT_CMPI_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 32, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 32, 12, 4); \
f_simm16 = EXTRACT_INT (insn, 32, 16, 16); \
#define EXTRACT_IFMT_DIV_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
INT f_simm16; \
unsigned int length;
#define EXTRACT_IFMT_DIV_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 32, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 32, 12, 4); \
f_simm16 = EXTRACT_INT (insn, 32, 16, 16); \
#define EXTRACT_IFMT_JL_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
unsigned int length;
#define EXTRACT_IFMT_JL_CODE \
length = 2; \
f_op1 = EXTRACT_UINT (insn, 16, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 16, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 16, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 16, 12, 4); \
#define EXTRACT_IFMT_LD24_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_uimm24; \
unsigned int length;
#define EXTRACT_IFMT_LD24_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_uimm24 = EXTRACT_UINT (insn, 32, 8, 24); \
#define EXTRACT_IFMT_LDI16_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
INT f_simm16; \
unsigned int length;
#define EXTRACT_IFMT_LDI16_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 32, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 32, 12, 4); \
f_simm16 = EXTRACT_INT (insn, 32, 16, 16); \
#define EXTRACT_IFMT_MVFACHI_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
unsigned int length;
#define EXTRACT_IFMT_MVFACHI_CODE \
length = 2; \
f_op1 = EXTRACT_UINT (insn, 16, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 16, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 16, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 16, 12, 4); \
#define EXTRACT_IFMT_MVFC_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
unsigned int length;
#define EXTRACT_IFMT_MVFC_CODE \
length = 2; \
f_op1 = EXTRACT_UINT (insn, 16, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 16, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 16, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 16, 12, 4); \
#define EXTRACT_IFMT_MVTACHI_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
unsigned int length;
#define EXTRACT_IFMT_MVTACHI_CODE \
length = 2; \
f_op1 = EXTRACT_UINT (insn, 16, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 16, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 16, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 16, 12, 4); \
#define EXTRACT_IFMT_MVTC_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
unsigned int length;
#define EXTRACT_IFMT_MVTC_CODE \
length = 2; \
f_op1 = EXTRACT_UINT (insn, 16, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 16, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 16, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 16, 12, 4); \
#define EXTRACT_IFMT_NOP_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
unsigned int length;
#define EXTRACT_IFMT_NOP_CODE \
length = 2; \
f_op1 = EXTRACT_UINT (insn, 16, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 16, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 16, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 16, 12, 4); \
#define EXTRACT_IFMT_SETH_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
UINT f_hi16; \
unsigned int length;
#define EXTRACT_IFMT_SETH_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 32, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 32, 12, 4); \
f_hi16 = EXTRACT_UINT (insn, 32, 16, 16); \
#define EXTRACT_IFMT_SLLI_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_shift_op2; \
UINT f_uimm5; \
unsigned int length;
#define EXTRACT_IFMT_SLLI_CODE \
length = 2; \
f_op1 = EXTRACT_UINT (insn, 16, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 16, 4, 4); \
f_shift_op2 = EXTRACT_UINT (insn, 16, 8, 3); \
f_uimm5 = EXTRACT_UINT (insn, 16, 11, 5); \
#define EXTRACT_IFMT_ST_D_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_r2; \
INT f_simm16; \
unsigned int length;
#define EXTRACT_IFMT_ST_D_CODE \
length = 4; \
f_op1 = EXTRACT_UINT (insn, 32, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 32, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 32, 8, 4); \
f_r2 = EXTRACT_UINT (insn, 32, 12, 4); \
f_simm16 = EXTRACT_INT (insn, 32, 16, 16); \
#define EXTRACT_IFMT_TRAP_VARS \
/* Instruction fields. */ \
UINT f_op1; \
UINT f_r1; \
UINT f_op2; \
UINT f_uimm4; \
unsigned int length;
#define EXTRACT_IFMT_TRAP_CODE \
length = 2; \
f_op1 = EXTRACT_UINT (insn, 16, 0, 4); \
f_r1 = EXTRACT_UINT (insn, 16, 4, 4); \
f_op2 = EXTRACT_UINT (insn, 16, 8, 4); \
f_uimm4 = EXTRACT_UINT (insn, 16, 12, 4); \
/* Collection of various things for the trace handler to use. */
typedef struct trace_record {
IADDR pc;
/* FIXME:wip */
} TRACE_RECORD;
#endif /* CPU_M32RBF_H */

70
sim/m32r/cpuall.h Normal file
View file

@ -0,0 +1,70 @@
/* Simulator CPU header for m32r.
THIS FILE IS MACHINE GENERATED WITH CGEN.
Copyright (C) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
This file is part of the GNU Simulators.
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 2, 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, write to the Free Software Foundation, Inc.,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef M32R_CPUALL_H
#define M32R_CPUALL_H
/* Include files for each cpu family. */
#ifdef WANT_CPU_M32RBF
#include "eng.h"
#include "cgen-engine.h"
#include "cpu.h"
#include "decode.h"
#endif
#ifdef WANT_CPU_M32RXF
#include "engx.h"
#include "cgen-engine.h"
#include "cpux.h"
#include "decodex.h"
#endif
extern const MACH m32r_mach;
#ifndef WANT_CPU
/* The ARGBUF struct. */
struct argbuf {
/* These are the baseclass definitions. */
IADDR addr;
const IDESC *idesc;
char trace_p;
char profile_p;
/* cpu specific data follows */
};
#endif
#ifndef WANT_CPU
/* A cached insn.
??? SCACHE used to contain more than just argbuf. We could delete the
type entirely and always just use ARGBUF, but for future concerns and as
a level of abstraction it is left in. */
struct scache {
struct argbuf argbuf;
};
#endif
#endif /* M32R_CPUALL_H */

1996
sim/m32r/decode.c Normal file

File diff suppressed because it is too large Load diff

208
sim/m32r/decode.h Normal file
View file

@ -0,0 +1,208 @@
/* Decode header for m32rbf.
THIS FILE IS MACHINE GENERATED WITH CGEN.
Copyright (C) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
This file is part of the GNU Simulators.
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 2, 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, write to the Free Software Foundation, Inc.,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef M32RBF_DECODE_H
#define M32RBF_DECODE_H
extern const IDESC *m32rbf_decode (SIM_CPU *, IADDR,
CGEN_INSN_INT, CGEN_INSN_INT,
ARGBUF *);
extern void m32rbf_init_idesc_table (SIM_CPU *);
/* Enum declaration for instructions in cpu family m32rbf. */
typedef enum m32rbf_insn_type {
M32RBF_INSN_X_INVALID, M32RBF_INSN_X_AFTER, M32RBF_INSN_X_BEFORE, M32RBF_INSN_X_CTI_CHAIN
, M32RBF_INSN_X_CHAIN, M32RBF_INSN_X_BEGIN, M32RBF_INSN_ADD, M32RBF_INSN_ADD3
, M32RBF_INSN_AND, M32RBF_INSN_AND3, M32RBF_INSN_OR, M32RBF_INSN_OR3
, M32RBF_INSN_XOR, M32RBF_INSN_XOR3, M32RBF_INSN_ADDI, M32RBF_INSN_ADDV
, M32RBF_INSN_ADDV3, M32RBF_INSN_ADDX, M32RBF_INSN_BC8, M32RBF_INSN_BC24
, M32RBF_INSN_BEQ, M32RBF_INSN_BEQZ, M32RBF_INSN_BGEZ, M32RBF_INSN_BGTZ
, M32RBF_INSN_BLEZ, M32RBF_INSN_BLTZ, M32RBF_INSN_BNEZ, M32RBF_INSN_BL8
, M32RBF_INSN_BL24, M32RBF_INSN_BNC8, M32RBF_INSN_BNC24, M32RBF_INSN_BNE
, M32RBF_INSN_BRA8, M32RBF_INSN_BRA24, M32RBF_INSN_CMP, M32RBF_INSN_CMPI
, M32RBF_INSN_CMPU, M32RBF_INSN_CMPUI, M32RBF_INSN_DIV, M32RBF_INSN_DIVU
, M32RBF_INSN_REM, M32RBF_INSN_REMU, M32RBF_INSN_JL, M32RBF_INSN_JMP
, M32RBF_INSN_LD, M32RBF_INSN_LD_D, M32RBF_INSN_LDB, M32RBF_INSN_LDB_D
, M32RBF_INSN_LDH, M32RBF_INSN_LDH_D, M32RBF_INSN_LDUB, M32RBF_INSN_LDUB_D
, M32RBF_INSN_LDUH, M32RBF_INSN_LDUH_D, M32RBF_INSN_LD_PLUS, M32RBF_INSN_LD24
, M32RBF_INSN_LDI8, M32RBF_INSN_LDI16, M32RBF_INSN_LOCK, M32RBF_INSN_MACHI
, M32RBF_INSN_MACLO, M32RBF_INSN_MACWHI, M32RBF_INSN_MACWLO, M32RBF_INSN_MUL
, M32RBF_INSN_MULHI, M32RBF_INSN_MULLO, M32RBF_INSN_MULWHI, M32RBF_INSN_MULWLO
, M32RBF_INSN_MV, M32RBF_INSN_MVFACHI, M32RBF_INSN_MVFACLO, M32RBF_INSN_MVFACMI
, M32RBF_INSN_MVFC, M32RBF_INSN_MVTACHI, M32RBF_INSN_MVTACLO, M32RBF_INSN_MVTC
, M32RBF_INSN_NEG, M32RBF_INSN_NOP, M32RBF_INSN_NOT, M32RBF_INSN_RAC
, M32RBF_INSN_RACH, M32RBF_INSN_RTE, M32RBF_INSN_SETH, M32RBF_INSN_SLL
, M32RBF_INSN_SLL3, M32RBF_INSN_SLLI, M32RBF_INSN_SRA, M32RBF_INSN_SRA3
, M32RBF_INSN_SRAI, M32RBF_INSN_SRL, M32RBF_INSN_SRL3, M32RBF_INSN_SRLI
, M32RBF_INSN_ST, M32RBF_INSN_ST_D, M32RBF_INSN_STB, M32RBF_INSN_STB_D
, M32RBF_INSN_STH, M32RBF_INSN_STH_D, M32RBF_INSN_ST_PLUS, M32RBF_INSN_ST_MINUS
, M32RBF_INSN_SUB, M32RBF_INSN_SUBV, M32RBF_INSN_SUBX, M32RBF_INSN_TRAP
, M32RBF_INSN_UNLOCK, M32RBF_INSN_MAX
} M32RBF_INSN_TYPE;
#if ! WITH_SEM_SWITCH_FULL
#define SEMFULL(fn) extern SEMANTIC_FN CONCAT3 (m32rbf,_sem_,fn);
#else
#define SEMFULL(fn)
#endif
#if ! WITH_SEM_SWITCH_FAST
#define SEMFAST(fn) extern SEMANTIC_FN CONCAT3 (m32rbf,_semf_,fn);
#else
#define SEMFAST(fn)
#endif
#define SEM(fn) SEMFULL (fn) SEMFAST (fn)
/* The function version of the before/after handlers is always needed,
so we always want the SEMFULL declaration of them. */
extern SEMANTIC_FN CONCAT3 (m32rbf,_sem_,x_before);
extern SEMANTIC_FN CONCAT3 (m32rbf,_sem_,x_after);
SEM (x_invalid)
SEM (x_after)
SEM (x_before)
SEM (x_cti_chain)
SEM (x_chain)
SEM (x_begin)
SEM (add)
SEM (add3)
SEM (and)
SEM (and3)
SEM (or)
SEM (or3)
SEM (xor)
SEM (xor3)
SEM (addi)
SEM (addv)
SEM (addv3)
SEM (addx)
SEM (bc8)
SEM (bc24)
SEM (beq)
SEM (beqz)
SEM (bgez)
SEM (bgtz)
SEM (blez)
SEM (bltz)
SEM (bnez)
SEM (bl8)
SEM (bl24)
SEM (bnc8)
SEM (bnc24)
SEM (bne)
SEM (bra8)
SEM (bra24)
SEM (cmp)
SEM (cmpi)
SEM (cmpu)
SEM (cmpui)
SEM (div)
SEM (divu)
SEM (rem)
SEM (remu)
SEM (jl)
SEM (jmp)
SEM (ld)
SEM (ld_d)
SEM (ldb)
SEM (ldb_d)
SEM (ldh)
SEM (ldh_d)
SEM (ldub)
SEM (ldub_d)
SEM (lduh)
SEM (lduh_d)
SEM (ld_plus)
SEM (ld24)
SEM (ldi8)
SEM (ldi16)
SEM (lock)
SEM (machi)
SEM (maclo)
SEM (macwhi)
SEM (macwlo)
SEM (mul)
SEM (mulhi)
SEM (mullo)
SEM (mulwhi)
SEM (mulwlo)
SEM (mv)
SEM (mvfachi)
SEM (mvfaclo)
SEM (mvfacmi)
SEM (mvfc)
SEM (mvtachi)
SEM (mvtaclo)
SEM (mvtc)
SEM (neg)
SEM (nop)
SEM (not)
SEM (rac)
SEM (rach)
SEM (rte)
SEM (seth)
SEM (sll)
SEM (sll3)
SEM (slli)
SEM (sra)
SEM (sra3)
SEM (srai)
SEM (srl)
SEM (srl3)
SEM (srli)
SEM (st)
SEM (st_d)
SEM (stb)
SEM (stb_d)
SEM (sth)
SEM (sth_d)
SEM (st_plus)
SEM (st_minus)
SEM (sub)
SEM (subv)
SEM (subx)
SEM (trap)
SEM (unlock)
#undef SEMFULL
#undef SEMFAST
#undef SEM
/* Function unit handlers (user written). */
extern int m32rbf_model_m32r_d_u_store (SIM_CPU *, const IDESC *, int /*unit_num*/, int /*referenced*/, INT /*src1*/, INT /*src2*/);
extern int m32rbf_model_m32r_d_u_load (SIM_CPU *, const IDESC *, int /*unit_num*/, int /*referenced*/, INT /*sr*/, INT /*dr*/);
extern int m32rbf_model_m32r_d_u_cti (SIM_CPU *, const IDESC *, int /*unit_num*/, int /*referenced*/, INT /*sr*/);
extern int m32rbf_model_m32r_d_u_mac (SIM_CPU *, const IDESC *, int /*unit_num*/, int /*referenced*/, INT /*src1*/, INT /*src2*/);
extern int m32rbf_model_m32r_d_u_cmp (SIM_CPU *, const IDESC *, int /*unit_num*/, int /*referenced*/, INT /*src1*/, INT /*src2*/);
extern int m32rbf_model_m32r_d_u_exec (SIM_CPU *, const IDESC *, int /*unit_num*/, int /*referenced*/, INT /*sr*/, INT /*dr*/, INT /*dr*/);
extern int m32rbf_model_test_u_exec (SIM_CPU *, const IDESC *, int /*unit_num*/, int /*referenced*/);
/* Profiling before/after handlers (user written) */
extern void m32rbf_model_insn_before (SIM_CPU *, int /*first_p*/);
extern void m32rbf_model_insn_after (SIM_CPU *, int /*last_p*/, int /*cycles*/);
#endif /* M32RBF_DECODE_H */

108
sim/m32r/devices.c Normal file
View file

@ -0,0 +1,108 @@
/* m32r device support
Copyright (C) 1997, 1998 Free Software Foundation, Inc.
Contributed by Cygnus Solutions.
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 2, 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, write to the Free Software Foundation, Inc.,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#include "sim-main.h"
#ifdef HAVE_DV_SOCKSER
#include "dv-sockser.h"
#endif
/* Handling the MSPR register is done by creating a device in the core
mapping that winds up here. */
device m32r_devices;
int
device_io_read_buffer (device *me, void *source, int space,
address_word addr, unsigned nr_bytes,
SIM_CPU *cpu, sim_cia cia)
{
SIM_DESC sd = CPU_STATE (cpu);
if (STATE_ENVIRONMENT (sd) != OPERATING_ENVIRONMENT)
return nr_bytes;
#ifdef HAVE_DV_SOCKSER
if (addr == UART_INCHAR_ADDR)
{
int c = dv_sockser_read (sd);
if (c == -1)
return 0;
*(char *) source = c;
return 1;
}
if (addr == UART_STATUS_ADDR)
{
int status = dv_sockser_status (sd);
unsigned char *p = source;
p[0] = 0;
p[1] = (((status & DV_SOCKSER_INPUT_EMPTY)
#ifdef UART_INPUT_READY0
? UART_INPUT_READY : 0)
#else
? 0 : UART_INPUT_READY)
#endif
+ ((status & DV_SOCKSER_OUTPUT_EMPTY) ? UART_OUTPUT_READY : 0));
return 2;
}
#endif
return nr_bytes;
}
int
device_io_write_buffer (device *me, const void *source, int space,
address_word addr, unsigned nr_bytes,
SIM_CPU *cpu, sim_cia cia)
{
SIM_DESC sd = CPU_STATE (cpu);
#if WITH_SCACHE
/* MSPR support is deprecated but is kept in for upward compatibility
with existing overlay support. */
if (addr == MSPR_ADDR)
{
if ((*(const char *) source & MSPR_PURGE) != 0)
scache_flush (sd);
return nr_bytes;
}
if (addr == MCCR_ADDR)
{
if ((*(const char *) source & MCCR_CP) != 0)
scache_flush (sd);
return nr_bytes;
}
#endif
if (STATE_ENVIRONMENT (sd) != OPERATING_ENVIRONMENT)
return nr_bytes;
#ifdef HAVE_DV_SOCKSER
if (addr == UART_OUTCHAR_ADDR)
{
int rc = dv_sockser_write (sd, *(char *) source);
return rc == 1;
}
#endif
return nr_bytes;
}
void device_error () {}

203
sim/m32r/m32r-sim.h Normal file
View file

@ -0,0 +1,203 @@
/* collection of junk waiting time to sort out
Copyright (C) 1996, 1997, 1998 Free Software Foundation, Inc.
Contributed by Cygnus Support.
This file is part of the GNU Simulators.
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 2, 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, write to the Free Software Foundation, Inc.,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#ifndef M32R_SIM_H
#define M32R_SIM_H
/* gdb register numbers */
#define PSW_REGNUM 16
#define CBR_REGNUM 17
#define SPI_REGNUM 18
#define SPU_REGNUM 19
#define BPC_REGNUM 20
#define PC_REGNUM 21
#define ACCL_REGNUM 22
#define ACCH_REGNUM 23
#define ACC1L_REGNUM 24
#define ACC1H_REGNUM 25
#define BBPSW_REGNUM 26
#define BBPC_REGNUM 27
extern int m32r_decode_gdb_ctrl_regnum (int);
/* Cover macros for hardware accesses.
FIXME: Eventually move to cgen. */
#define GET_H_SM() ((CPU (h_psw) & 0x80) != 0)
extern USI m32rbf_h_cr_get_handler (SIM_CPU *, UINT);
extern void m32rbf_h_cr_set_handler (SIM_CPU *, UINT, USI);
#define GET_H_CR(regno) \
XCONCAT2 (WANT_CPU,_h_cr_get_handler) (current_cpu, (regno))
#define SET_H_CR(regno, val) \
XCONCAT2 (WANT_CPU,_h_cr_set_handler) (current_cpu, (regno), (val))
extern UQI m32rbf_h_psw_get_handler (SIM_CPU *);
extern void m32rbf_h_psw_set_handler (SIM_CPU *, UQI);
#define GET_H_PSW() \
XCONCAT2 (WANT_CPU,_h_psw_get_handler) (current_cpu)
#define SET_H_PSW(val) \
XCONCAT2 (WANT_CPU,_h_psw_set_handler) (current_cpu, (val))
extern DI m32rbf_h_accum_get_handler (SIM_CPU *);
extern void m32rbf_h_accum_set_handler (SIM_CPU *, DI);
#define GET_H_ACCUM() \
XCONCAT2 (WANT_CPU,_h_accum_get_handler) (current_cpu)
#define SET_H_ACCUM(val) \
XCONCAT2 (WANT_CPU,_h_accum_set_handler) (current_cpu, (val))
/* Misc. profile data. */
typedef struct {
/* nop insn slot filler count */
unsigned int fillnop_count;
/* number of parallel insns */
unsigned int parallel_count;
/* FIXME: generalize this to handle all insn lengths, move to common. */
/* number of short insns, not including parallel ones */
unsigned int short_count;
/* number of long insns */
unsigned int long_count;
/* Working area for computing cycle counts. */
unsigned long insn_cycles; /* FIXME: delete */
unsigned long cti_stall;
unsigned long load_stall;
unsigned long biggest_cycles;
/* Bitmask of registers loaded by previous insn. */
unsigned int load_regs;
/* Bitmask of registers loaded by current insn. */
unsigned int load_regs_pending;
} M32R_MISC_PROFILE;
/* Initialize the working area. */
void m32r_init_insn_cycles (SIM_CPU *, int);
/* Update the totals for the insn. */
void m32r_record_insn_cycles (SIM_CPU *, int);
/* This is invoked by the nop pattern in the .cpu file. */
#define PROFILE_COUNT_FILLNOPS(cpu, addr) \
do { \
if (PROFILE_INSN_P (cpu) \
&& (addr & 3) != 0) \
++ CPU_M32R_MISC_PROFILE (cpu)->fillnop_count; \
} while (0)
/* This is invoked by the execute section of mloop{,x}.in. */
#define PROFILE_COUNT_PARINSNS(cpu) \
do { \
if (PROFILE_INSN_P (cpu)) \
++ CPU_M32R_MISC_PROFILE (cpu)->parallel_count; \
} while (0)
/* This is invoked by the execute section of mloop{,x}.in. */
#define PROFILE_COUNT_SHORTINSNS(cpu) \
do { \
if (PROFILE_INSN_P (cpu)) \
++ CPU_M32R_MISC_PROFILE (cpu)->short_count; \
} while (0)
/* This is invoked by the execute section of mloop{,x}.in. */
#define PROFILE_COUNT_LONGINSNS(cpu) \
do { \
if (PROFILE_INSN_P (cpu)) \
++ CPU_M32R_MISC_PROFILE (cpu)->long_count; \
} while (0)
#define GETTWI GETTSI
#define SETTWI SETTSI
/* Additional execution support. */
/* Hardware/device support.
??? Will eventually want to move device stuff to config files. */
/* Exception, Interrupt, and Trap addresses */
#define EIT_SYSBREAK_ADDR 0x10
#define EIT_RSVD_INSN_ADDR 0x20
#define EIT_ADDR_EXCP_ADDR 0x30
#define EIT_TRAP_BASE_ADDR 0x40
#define EIT_EXTERN_ADDR 0x80
#define EIT_RESET_ADDR 0x7ffffff0
#define EIT_WAKEUP_ADDR 0x7ffffff0
/* Special purpose traps. */
#define TRAP_SYSCALL 0
#define TRAP_BREAKPOINT 1
/* Support for the MSPR register (Cache Purge Control Register)
and the MCCR register (Cache Control Register) are needed in order for
overlays to work correctly with the scache.
MSPR no longer exists but is supported for upward compatibility with
early overlay support. */
/* Cache Purge Control (only exists on early versions of chips) */
#define MSPR_ADDR 0xfffffff7
#define MSPR_PURGE 1
/* Lock Control Register (not supported) */
#define MLCR_ADDR 0xfffffff7
#define MLCR_LM 1
/* Power Management Control Register (not supported) */
#define MPMR_ADDR 0xfffffffb
/* Cache Control Register */
#define MCCR_ADDR 0xffffffff
#define MCCR_CP 0x80
/* not supported */
#define MCCR_CM0 2
#define MCCR_CM1 1
/* Serial device addresses. */
#ifdef M32R_EVA /* orig eva board, no longer supported */
#define UART_INCHAR_ADDR 0xff102013
#define UART_OUTCHAR_ADDR 0xff10200f
#define UART_STATUS_ADDR 0xff102006
/* Indicate ready bit is inverted. */
#define UART_INPUT_READY0
#else
/* These are the values for the MSA2000 board.
??? Will eventually need to move this to a config file. */
#define UART_INCHAR_ADDR 0xff004009
#define UART_OUTCHAR_ADDR 0xff004007
#define UART_STATUS_ADDR 0xff004002
#endif
#define UART_INPUT_READY 0x4
#define UART_OUTPUT_READY 0x1
/* Start address and length of all device support. */
#define M32R_DEVICE_ADDR 0xff000000
#define M32R_DEVICE_LEN 0x00ffffff
/* sim_core_attach device argument. */
extern device m32r_devices;
/* FIXME: Temporary, until device support ready. */
struct _device { int foo; };
/* Handle the trap insn. */
USI m32r_trap (SIM_CPU *, PCADDR, int);
#endif /* M32R_SIM_H */

413
sim/m32r/m32r.c Normal file
View file

@ -0,0 +1,413 @@
/* m32r simulator support code
Copyright (C) 1996, 1997, 1998 Free Software Foundation, Inc.
Contributed by Cygnus Support.
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 2, 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, write to the Free Software Foundation, Inc.,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#define WANT_CPU m32rbf
#define WANT_CPU_M32RBF
#include "sim-main.h"
#include "cgen-mem.h"
#include "cgen-ops.h"
/* Decode gdb ctrl register number. */
int
m32r_decode_gdb_ctrl_regnum (int gdb_regnum)
{
switch (gdb_regnum)
{
case PSW_REGNUM : return H_CR_PSW;
case CBR_REGNUM : return H_CR_CBR;
case SPI_REGNUM : return H_CR_SPI;
case SPU_REGNUM : return H_CR_SPU;
case BPC_REGNUM : return H_CR_BPC;
case BBPSW_REGNUM : return H_CR_BBPSW;
case BBPC_REGNUM : return H_CR_BBPC;
}
abort ();
}
/* The contents of BUF are in target byte order. */
int
m32rbf_fetch_register (SIM_CPU *current_cpu, int rn, unsigned char *buf, int len)
{
if (rn < 16)
SETTWI (buf, a_m32r_h_gr_get (current_cpu, rn));
else
switch (rn)
{
case PSW_REGNUM :
case CBR_REGNUM :
case SPI_REGNUM :
case SPU_REGNUM :
case BPC_REGNUM :
case BBPSW_REGNUM :
case BBPC_REGNUM :
SETTWI (buf, a_m32r_h_cr_get (current_cpu,
m32r_decode_gdb_ctrl_regnum (rn)));
break;
case PC_REGNUM :
SETTWI (buf, a_m32r_h_pc_get (current_cpu));
break;
case ACCL_REGNUM :
SETTWI (buf, GETLODI (a_m32r_h_accum_get (current_cpu)));
break;
case ACCH_REGNUM :
SETTWI (buf, GETHIDI (a_m32r_h_accum_get (current_cpu)));
break;
default :
return 0;
}
return -1; /*FIXME*/
}
/* The contents of BUF are in target byte order. */
int
m32rbf_store_register (SIM_CPU *current_cpu, int rn, unsigned char *buf, int len)
{
if (rn < 16)
a_m32r_h_gr_set (current_cpu, rn, GETTWI (buf));
else
switch (rn)
{
case PSW_REGNUM :
case CBR_REGNUM :
case SPI_REGNUM :
case SPU_REGNUM :
case BPC_REGNUM :
case BBPSW_REGNUM :
case BBPC_REGNUM :
a_m32r_h_cr_set (current_cpu,
m32r_decode_gdb_ctrl_regnum (rn),
GETTWI (buf));
break;
case PC_REGNUM :
a_m32r_h_pc_set (current_cpu, GETTWI (buf));
break;
case ACCL_REGNUM :
{
DI val = a_m32r_h_accum_get (current_cpu);
SETLODI (val, GETTWI (buf));
a_m32r_h_accum_set (current_cpu, val);
break;
}
case ACCH_REGNUM :
{
DI val = a_m32r_h_accum_get (current_cpu);
SETHIDI (val, GETTWI (buf));
a_m32r_h_accum_set (current_cpu, val);
break;
}
default :
return 0;
}
return -1; /*FIXME*/
}
USI
m32rbf_h_cr_get_handler (SIM_CPU *current_cpu, UINT cr)
{
switch (cr)
{
case H_CR_PSW : /* psw */
return (((CPU (h_bpsw) & 0xc1) << 8)
| ((CPU (h_psw) & 0xc0) << 0)
| GET_H_COND ());
case H_CR_BBPSW : /* backup backup psw */
return CPU (h_bbpsw) & 0xc1;
case H_CR_CBR : /* condition bit */
return GET_H_COND ();
case H_CR_SPI : /* interrupt stack pointer */
if (! GET_H_SM ())
return CPU (h_gr[H_GR_SP]);
else
return CPU (h_cr[H_CR_SPI]);
case H_CR_SPU : /* user stack pointer */
if (GET_H_SM ())
return CPU (h_gr[H_GR_SP]);
else
return CPU (h_cr[H_CR_SPU]);
case H_CR_BPC : /* backup pc */
return CPU (h_cr[H_CR_BPC]) & 0xfffffffe;
case H_CR_BBPC : /* backup backup pc */
return CPU (h_cr[H_CR_BBPC]) & 0xfffffffe;
case 4 : /* ??? unspecified, but apparently available */
case 5 : /* ??? unspecified, but apparently available */
return CPU (h_cr[cr]);
default :
return 0;
}
}
void
m32rbf_h_cr_set_handler (SIM_CPU *current_cpu, UINT cr, USI newval)
{
switch (cr)
{
case H_CR_PSW : /* psw */
{
int old_sm = (CPU (h_psw) & 0x80) != 0;
int new_sm = (newval & 0x80) != 0;
CPU (h_bpsw) = (newval >> 8) & 0xff;
CPU (h_psw) = newval & 0xff;
SET_H_COND (newval & 1);
/* When switching stack modes, update the registers. */
if (old_sm != new_sm)
{
if (old_sm)
{
/* Switching user -> system. */
CPU (h_cr[H_CR_SPU]) = CPU (h_gr[H_GR_SP]);
CPU (h_gr[H_GR_SP]) = CPU (h_cr[H_CR_SPI]);
}
else
{
/* Switching system -> user. */
CPU (h_cr[H_CR_SPI]) = CPU (h_gr[H_GR_SP]);
CPU (h_gr[H_GR_SP]) = CPU (h_cr[H_CR_SPU]);
}
}
break;
}
case H_CR_BBPSW : /* backup backup psw */
CPU (h_bbpsw) = newval & 0xff;
break;
case H_CR_CBR : /* condition bit */
SET_H_COND (newval & 1);
break;
case H_CR_SPI : /* interrupt stack pointer */
if (! GET_H_SM ())
CPU (h_gr[H_GR_SP]) = newval;
else
CPU (h_cr[H_CR_SPI]) = newval;
break;
case H_CR_SPU : /* user stack pointer */
if (GET_H_SM ())
CPU (h_gr[H_GR_SP]) = newval;
else
CPU (h_cr[H_CR_SPU]) = newval;
break;
case H_CR_BPC : /* backup pc */
CPU (h_cr[H_CR_BPC]) = newval;
break;
case H_CR_BBPC : /* backup backup pc */
CPU (h_cr[H_CR_BBPC]) = newval;
break;
case 4 : /* ??? unspecified, but apparently available */
case 5 : /* ??? unspecified, but apparently available */
CPU (h_cr[cr]) = newval;
break;
default :
/* ignore */
break;
}
}
/* Cover fns to access h-psw. */
UQI
m32rbf_h_psw_get_handler (SIM_CPU *current_cpu)
{
return (CPU (h_psw) & 0xfe) | (CPU (h_cond) & 1);
}
void
m32rbf_h_psw_set_handler (SIM_CPU *current_cpu, UQI newval)
{
CPU (h_psw) = newval;
CPU (h_cond) = newval & 1;
}
/* Cover fns to access h-accum. */
DI
m32rbf_h_accum_get_handler (SIM_CPU *current_cpu)
{
/* Sign extend the top 8 bits. */
DI r;
#if 1
r = ANDDI (CPU (h_accum), MAKEDI (0xffffff, 0xffffffff));
r = XORDI (r, MAKEDI (0x800000, 0));
r = SUBDI (r, MAKEDI (0x800000, 0));
#else
SI hi,lo;
r = CPU (h_accum);
hi = GETHIDI (r);
lo = GETLODI (r);
hi = ((hi & 0xffffff) ^ 0x800000) - 0x800000;
r = MAKEDI (hi, lo);
#endif
return r;
}
void
m32rbf_h_accum_set_handler (SIM_CPU *current_cpu, DI newval)
{
CPU (h_accum) = newval;
}
#if WITH_PROFILE_MODEL_P
/* FIXME: Some of these should be inline or macros. Later. */
/* Initialize cycle counting for an insn.
FIRST_P is non-zero if this is the first insn in a set of parallel
insns. */
void
m32rbf_model_insn_before (SIM_CPU *cpu, int first_p)
{
M32R_MISC_PROFILE *mp = CPU_M32R_MISC_PROFILE (cpu);
mp->cti_stall = 0;
mp->load_stall = 0;
if (first_p)
{
mp->load_regs_pending = 0;
mp->biggest_cycles = 0;
}
}
/* Record the cycles computed for an insn.
LAST_P is non-zero if this is the last insn in a set of parallel insns,
and we update the total cycle count.
CYCLES is the cycle count of the insn. */
void
m32rbf_model_insn_after (SIM_CPU *cpu, int last_p, int cycles)
{
PROFILE_DATA *p = CPU_PROFILE_DATA (cpu);
M32R_MISC_PROFILE *mp = CPU_M32R_MISC_PROFILE (cpu);
unsigned long total = cycles + mp->cti_stall + mp->load_stall;
if (last_p)
{
unsigned long biggest = total > mp->biggest_cycles ? total : mp->biggest_cycles;
PROFILE_MODEL_TOTAL_CYCLES (p) += biggest;
PROFILE_MODEL_CUR_INSN_CYCLES (p) = total;
}
else
{
/* Here we take advantage of the fact that !last_p -> first_p. */
mp->biggest_cycles = total;
PROFILE_MODEL_CUR_INSN_CYCLES (p) = total;
}
/* Branch and load stall counts are recorded independently of the
total cycle count. */
PROFILE_MODEL_CTI_STALL_CYCLES (p) += mp->cti_stall;
PROFILE_MODEL_LOAD_STALL_CYCLES (p) += mp->load_stall;
mp->load_regs = mp->load_regs_pending;
}
static INLINE void
check_load_stall (SIM_CPU *cpu, int regno)
{
UINT h_gr = CPU_M32R_MISC_PROFILE (cpu)->load_regs;
if (regno != -1
&& (h_gr & (1 << regno)) != 0)
{
CPU_M32R_MISC_PROFILE (cpu)->load_stall += 2;
if (TRACE_INSN_P (cpu))
cgen_trace_printf (cpu, " ; Load stall of 2 cycles.");
}
}
int
m32rbf_model_m32r_d_u_exec (SIM_CPU *cpu, const IDESC *idesc,
int unit_num, int referenced,
INT sr, INT sr2, INT dr)
{
check_load_stall (cpu, sr);
check_load_stall (cpu, sr2);
return idesc->timing->units[unit_num].done;
}
int
m32rbf_model_m32r_d_u_cmp (SIM_CPU *cpu, const IDESC *idesc,
int unit_num, int referenced,
INT src1, INT src2)
{
check_load_stall (cpu, src1);
check_load_stall (cpu, src2);
return idesc->timing->units[unit_num].done;
}
int
m32rbf_model_m32r_d_u_mac (SIM_CPU *cpu, const IDESC *idesc,
int unit_num, int referenced,
INT src1, INT src2)
{
check_load_stall (cpu, src1);
check_load_stall (cpu, src2);
return idesc->timing->units[unit_num].done;
}
int
m32rbf_model_m32r_d_u_cti (SIM_CPU *cpu, const IDESC *idesc,
int unit_num, int referenced,
INT sr)
{
PROFILE_DATA *profile = CPU_PROFILE_DATA (cpu);
int taken_p = (referenced & (1 << 1)) != 0;
check_load_stall (cpu, sr);
if (taken_p)
{
CPU_M32R_MISC_PROFILE (cpu)->cti_stall += 2;
PROFILE_MODEL_TAKEN_COUNT (profile) += 1;
}
else
PROFILE_MODEL_UNTAKEN_COUNT (profile) += 1;
return idesc->timing->units[unit_num].done;
}
int
m32rbf_model_m32r_d_u_load (SIM_CPU *cpu, const IDESC *idesc,
int unit_num, int referenced,
INT sr, INT dr)
{
CPU_M32R_MISC_PROFILE (cpu)->load_regs_pending |= (1 << dr);
check_load_stall (cpu, sr);
return idesc->timing->units[unit_num].done;
}
int
m32rbf_model_m32r_d_u_store (SIM_CPU *cpu, const IDESC *idesc,
int unit_num, int referenced,
INT src1, INT src2)
{
check_load_stall (cpu, src1);
check_load_stall (cpu, src2);
return idesc->timing->units[unit_num].done;
}
int
m32rbf_model_test_u_exec (SIM_CPU *cpu, const IDESC *idesc,
int unit_num, int referenced)
{
return idesc->timing->units[unit_num].done;
}
#endif /* WITH_PROFILE_MODEL_P */

319
sim/m32r/mloop.in Normal file
View file

@ -0,0 +1,319 @@
# Simulator main loop for m32r. -*- C -*-
# Copyright (C) 1996, 1997, 1998 Free Software Foundation, Inc.
#
# This file is part of the GNU Simulators.
#
# 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 2, 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, write to the Free Software Foundation, Inc.,
# 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
# 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.
# However for illustration's sake this file provides examples of all.
# ??? 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
static INLINE const IDESC *
extract16 (SIM_CPU *current_cpu, PCADDR pc, CGEN_INSN_INT insn,
ARGBUF *abuf, int fast_p)
{
const IDESC *id = @cpu@_decode (current_cpu, pc, insn, insn, abuf);
@cpu@_fill_argbuf (current_cpu, abuf, id, pc, fast_p);
if (! fast_p)
{
int trace_p = PC_IN_TRACE_RANGE_P (current_cpu, pc);
int profile_p = PC_IN_PROFILE_RANGE_P (current_cpu, pc);
@cpu@_fill_argbuf_tp (current_cpu, abuf, trace_p, profile_p);
}
return id;
}
static INLINE const IDESC *
extract32 (SIM_CPU *current_cpu, PCADDR pc, CGEN_INSN_INT insn,
ARGBUF *abuf, int fast_p)
{
const IDESC *id = @cpu@_decode (current_cpu, pc, (USI) insn >> 16, insn, abuf);
@cpu@_fill_argbuf (current_cpu, abuf, id, pc, fast_p);
if (! fast_p)
{
int trace_p = PC_IN_TRACE_RANGE_P (current_cpu, pc);
int profile_p = PC_IN_PROFILE_RANGE_P (current_cpu, pc);
@cpu@_fill_argbuf_tp (current_cpu, abuf, trace_p, profile_p);
}
return id;
}
static INLINE SEM_PC
execute (SIM_CPU *current_cpu, SCACHE *sc, int fast_p)
{
SEM_PC vpc;
if (fast_p)
{
#if ! WITH_SEM_SWITCH_FAST
#if WITH_SCACHE
vpc = (*sc->argbuf.semantic.sem_fast) (current_cpu, sc);
#else
vpc = (*sc->argbuf.semantic.sem_fast) (current_cpu, &sc->argbuf);
#endif
#else
abort ();
#endif /* WITH_SEM_SWITCH_FAST */
}
else
{
#if ! WITH_SEM_SWITCH_FULL
ARGBUF *abuf = &sc->argbuf;
const IDESC *idesc = abuf->idesc;
const CGEN_INSN *idata = idesc->idata;
#if WITH_SCACHE_PBB
int virtual_p = CGEN_INSN_ATTR_VALUE (idata, CGEN_INSN_VIRTUAL);
#else
int virtual_p = 0;
#endif
if (! virtual_p)
{
/* FIXME: call x-before */
if (ARGBUF_PROFILE_P (abuf))
PROFILE_COUNT_INSN (current_cpu, abuf->addr, idesc->num);
/* FIXME: Later make cover macros: PROFILE_INSN_{INIT,FINI}. */
if (PROFILE_MODEL_P (current_cpu)
&& ARGBUF_PROFILE_P (abuf))
@cpu@_model_insn_before (current_cpu, 1 /*first_p*/);
TRACE_INSN_INIT (current_cpu, abuf, 1);
TRACE_INSN (current_cpu, idata,
(const struct argbuf *) abuf, abuf->addr);
}
#if WITH_SCACHE
vpc = (*sc->argbuf.semantic.sem_full) (current_cpu, sc);
#else
vpc = (*sc->argbuf.semantic.sem_full) (current_cpu, abuf);
#endif
if (! virtual_p)
{
/* FIXME: call x-after */
if (PROFILE_MODEL_P (current_cpu)
&& ARGBUF_PROFILE_P (abuf))
{
int cycles;
cycles = (*idesc->timing->model_fn) (current_cpu, sc);
@cpu@_model_insn_after (current_cpu, 1 /*last_p*/, cycles);
}
TRACE_INSN_FINI (current_cpu, abuf, 1);
}
#else
abort ();
#endif /* WITH_SEM_SWITCH_FULL */
}
return vpc;
}
EOF
;;
xinit)
# Nothing needed.
;;
xextract-simple | xextract-scache)
cat <<EOF
{
if ((pc & 3) != 0)
{
/* This only occurs when single stepping.
The test is unnecessary otherwise, but the cost is teensy,
compared with decoding/extraction. */
UHI insn = GETIMEMUHI (current_cpu, pc);
extract16 (current_cpu, pc, insn & 0x7fff, sc, FAST_P);
}
else
{
USI insn = GETIMEMUSI (current_cpu, pc);
if ((SI) insn < 0)
{
extract32 (current_cpu, pc, insn, sc, FAST_P);
}
else
{
extract16 (current_cpu, pc, insn >> 16, sc, FAST_P);
extract16 (current_cpu, pc + 2, insn & 0x7fff, sc + 1, FAST_P);
/* The m32r doesn't support parallel execution. */
if ((insn & 0x8000) != 0
&& (insn & 0x7fff) != 0x7000) /* parallel nops are ok */
sim_engine_illegal_insn (current_cpu, pc);
}
}
}
EOF
;;
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
{
const IDESC *idesc;
int icount = 0;
if ((pc & 3) != 0)
{
/* This only occurs when single stepping.
The test is unnecessary otherwise, but the cost is teensy,
compared with decoding/extraction. */
UHI insn = GETIMEMUHI (current_cpu, pc);
idesc = extract16 (current_cpu, pc, insn & 0x7fff, &sc->argbuf, FAST_P);
++sc;
--max_insns;
++icount;
pc += 2;
if (IDESC_CTI_P (idesc))
{
SET_CTI_VPC (sc - 1);
goto Finish;
}
}
while (max_insns > 0)
{
USI insn = GETIMEMUSI (current_cpu, pc);
if ((SI) insn < 0)
{
idesc = extract32 (current_cpu, pc, insn, &sc->argbuf, FAST_P);
++sc;
--max_insns;
++icount;
pc += 4;
if (IDESC_CTI_P (idesc))
{
SET_CTI_VPC (sc - 1);
break;
}
}
else
{
idesc = extract16 (current_cpu, pc, insn >> 16, &sc->argbuf, FAST_P);
++sc;
--max_insns;
++icount;
pc += 2;
if (IDESC_CTI_P (idesc))
{
SET_CTI_VPC (sc - 1);
break;
}
/* The m32r doesn't support parallel execution. */
if ((insn & 0x8000) != 0)
{
/* ??? Defer signalling to execution. */
if ((insn & 0x7fff) != 0x7000) /* parallel nops are ok */
sim_engine_invalid_insn (current_cpu, pc - 2);
/* There's no point in processing parallel nops in fast mode.
We might as well do this test since we've already tested
that we have a parallel nop. */
if (0 && FAST_P)
{
pc += 2;
continue;
}
}
else
{
/* Non-parallel case.
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;
}
/* We're guaranteed that we can always process 16 bit insns in
pairs. */
idesc = extract16 (current_cpu, pc, insn & 0x7fff, &sc->argbuf, FAST_P);
++sc;
--max_insns;
++icount;
pc += 2;
if (IDESC_CTI_P (idesc))
{
SET_CTI_VPC (sc - 1);
break;
}
}
}
Finish:
SET_INSN_COUNT (icount);
}
EOF
;;
xfull-exec-* | xfast-exec-*)
# Inputs: current_cpu, vpc, FAST_P
# Outputs: vpc
# vpc is the virtual program counter.
cat <<EOF
#if (! FAST_P && WITH_SEM_SWITCH_FULL) || (FAST_P && WITH_SEM_SWITCH_FAST)
#define DEFINE_SWITCH
#include "sem-switch.c"
#else
vpc = execute (current_cpu, vpc, FAST_P);
#endif
EOF
;;
*)
echo "Invalid argument to mainloop.in: $1" >&2
exit 1
;;
esac

4168
sim/m32r/model.c Normal file

File diff suppressed because it is too large Load diff

2503
sim/m32r/sem-switch.c Normal file

File diff suppressed because it is too large Load diff

2544
sim/m32r/sem.c Normal file

File diff suppressed because it is too large Load diff

287
sim/m32r/sim-if.c Normal file
View file

@ -0,0 +1,287 @@
/* Main simulator entry points specific to the M32R.
Copyright (C) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
Contributed by Cygnus Support.
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 2, 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, write to the Free Software Foundation, Inc.,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#include "sim-main.h"
#include "sim-options.h"
#include "libiberty.h"
#include "bfd.h"
#ifdef HAVE_STRING_H
#include <string.h>
#else
#ifdef HAVE_STRINGS_H
#include <strings.h>
#endif
#endif
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
static void free_state (SIM_DESC);
static void print_m32r_misc_cpu (SIM_CPU *cpu, int verbose);
/* Records simulator descriptor so utilities like m32r_dump_regs can be
called from gdb. */
SIM_DESC current_state;
/* Cover function of sim_state_free to free the cpu buffers as well. */
static void
free_state (SIM_DESC sd)
{
if (STATE_MODULES (sd) != NULL)
sim_module_uninstall (sd);
sim_cpu_free_all (sd);
sim_state_free (sd);
}
/* Create an instance of the simulator. */
SIM_DESC
sim_open (kind, callback, abfd, argv)
SIM_OPEN_KIND kind;
host_callback *callback;
struct _bfd *abfd;
char **argv;
{
SIM_DESC sd = sim_state_alloc (kind, callback);
char c;
int i;
/* The cpu data is kept in a separately allocated chunk of memory. */
if (sim_cpu_alloc_all (sd, 1, cgen_cpu_max_extra_bytes ()) != SIM_RC_OK)
{
free_state (sd);
return 0;
}
#if 0 /* FIXME: pc is in mach-specific struct */
/* FIXME: watchpoints code shouldn't need this */
{
SIM_CPU *current_cpu = STATE_CPU (sd, 0);
STATE_WATCHPOINTS (sd)->pc = &(PC);
STATE_WATCHPOINTS (sd)->sizeof_pc = sizeof (PC);
}
#endif
if (sim_pre_argv_init (sd, argv[0]) != SIM_RC_OK)
{
free_state (sd);
return 0;
}
#ifdef HAVE_DV_SOCKSER /* FIXME: was done differently before */
if (dv_sockser_install (sd) != SIM_RC_OK)
{
free_state (sd);
return 0;
}
#endif
#if 0 /* FIXME: 'twould be nice if we could do this */
/* These options override any module options.
Obviously ambiguity should be avoided, however the caller may wish to
augment the meaning of an option. */
if (extra_options != NULL)
sim_add_option_table (sd, extra_options);
#endif
/* getopt will print the error message so we just have to exit if this fails.
FIXME: Hmmm... in the case of gdb we need getopt to call
print_filtered. */
if (sim_parse_args (sd, argv) != SIM_RC_OK)
{
free_state (sd);
return 0;
}
/* Allocate a handler for the control registers and other devices
if no memory for that range has been allocated by the user.
All are allocated in one chunk to keep things from being
unnecessarily complicated. */
if (sim_core_read_buffer (sd, NULL, read_map, &c, M32R_DEVICE_ADDR, 1) == 0)
sim_core_attach (sd, NULL,
0 /*level*/,
access_read_write,
0 /*space ???*/,
M32R_DEVICE_ADDR, M32R_DEVICE_LEN /*nr_bytes*/,
0 /*modulo*/,
&m32r_devices,
NULL /*buffer*/);
/* Allocate core managed memory if none specified by user.
Use address 4 here in case the user wanted address 0 unmapped. */
if (sim_core_read_buffer (sd, NULL, read_map, &c, 4, 1) == 0)
sim_do_commandf (sd, "memory region 0,0x%x", M32R_DEFAULT_MEM_SIZE);
/* check for/establish the reference program image */
if (sim_analyze_program (sd,
(STATE_PROG_ARGV (sd) != NULL
? *STATE_PROG_ARGV (sd)
: NULL),
abfd) != SIM_RC_OK)
{
free_state (sd);
return 0;
}
/* Establish any remaining configuration options. */
if (sim_config (sd) != SIM_RC_OK)
{
free_state (sd);
return 0;
}
if (sim_post_argv_init (sd) != SIM_RC_OK)
{
free_state (sd);
return 0;
}
/* Open a copy of the cpu descriptor table. */
{
CGEN_CPU_DESC cd = m32r_cgen_cpu_open (STATE_ARCHITECTURE (sd)->mach,
CGEN_ENDIAN_BIG);
for (i = 0; i < MAX_NR_PROCESSORS; ++i)
{
SIM_CPU *cpu = STATE_CPU (sd, i);
CPU_CPU_DESC (cpu) = cd;
CPU_DISASSEMBLER (cpu) = sim_cgen_disassemble_insn;
}
m32r_cgen_init_dis (cd);
}
/* Initialize various cgen things not done by common framework.
Must be done after m32r_cgen_cpu_open. */
cgen_init (sd);
for (c = 0; c < MAX_NR_PROCESSORS; ++c)
{
/* Only needed for profiling, but the structure member is small. */
memset (CPU_M32R_MISC_PROFILE (STATE_CPU (sd, i)), 0,
sizeof (* CPU_M32R_MISC_PROFILE (STATE_CPU (sd, i))));
/* Hook in callback for reporting these stats */
PROFILE_INFO_CPU_CALLBACK (CPU_PROFILE_DATA (STATE_CPU (sd, i)))
= print_m32r_misc_cpu;
}
/* Store in a global so things like sparc32_dump_regs can be invoked
from the gdb command line. */
current_state = sd;
return sd;
}
void
sim_close (sd, quitting)
SIM_DESC sd;
int quitting;
{
m32r_cgen_cpu_close (CPU_CPU_DESC (STATE_CPU (sd, 0)));
sim_module_uninstall (sd);
}
SIM_RC
sim_create_inferior (sd, abfd, argv, envp)
SIM_DESC sd;
struct _bfd *abfd;
char **argv;
char **envp;
{
SIM_CPU *current_cpu = STATE_CPU (sd, 0);
SIM_ADDR addr;
if (abfd != NULL)
addr = bfd_get_start_address (abfd);
else
addr = 0;
sim_pc_set (current_cpu, addr);
#if 0
STATE_ARGV (sd) = sim_copy_argv (argv);
STATE_ENVP (sd) = sim_copy_argv (envp);
#endif
return SIM_RC_OK;
}
/* PROFILE_CPU_CALLBACK */
static void
print_m32r_misc_cpu (SIM_CPU *cpu, int verbose)
{
SIM_DESC sd = CPU_STATE (cpu);
char buf[20];
if (CPU_PROFILE_FLAGS (cpu) [PROFILE_INSN_IDX])
{
sim_io_printf (sd, "Miscellaneous Statistics\n\n");
sim_io_printf (sd, " %-*s %s\n\n",
PROFILE_LABEL_WIDTH, "Fill nops:",
sim_add_commas (buf, sizeof (buf),
CPU_M32R_MISC_PROFILE (cpu)->fillnop_count));
}
}
void
sim_do_command (sd, cmd)
SIM_DESC sd;
char *cmd;
{
char **argv;
if (cmd == NULL)
return;
argv = buildargv (cmd);
if (argv[0] != NULL
&& strcasecmp (argv[0], "info") == 0
&& argv[1] != NULL
&& strncasecmp (argv[1], "reg", 3) == 0)
{
SI val;
/* We only support printing bbpsw,bbpc here as there is no equivalent
functionality in gdb. */
if (argv[2] == NULL)
sim_io_eprintf (sd, "Missing register in `%s'\n", cmd);
else if (argv[3] != NULL)
sim_io_eprintf (sd, "Too many arguments in `%s'\n", cmd);
else if (strcasecmp (argv[2], "bbpsw") == 0)
{
val = a_m32r_h_cr_get (STATE_CPU (sd, 0), H_CR_BBPSW);
sim_io_printf (sd, "bbpsw 0x%x %d\n", val, val);
}
else if (strcasecmp (argv[2], "bbpc") == 0)
{
val = a_m32r_h_cr_get (STATE_CPU (sd, 0), H_CR_BBPC);
sim_io_printf (sd, "bbpc 0x%x %d\n", val, val);
}
else
sim_io_eprintf (sd, "Printing of register `%s' not supported with `sim info'\n",
argv[2]);
}
else
{
if (sim_args_command (sd, cmd) != SIM_RC_OK)
sim_io_eprintf (sd, "Unknown sim command `%s'\n", cmd);
}
freeargv (argv);
}

85
sim/m32r/sim-main.h Normal file
View file

@ -0,0 +1,85 @@
/* Main header for the m32r. */
#ifndef SIM_MAIN_H
#define SIM_MAIN_H
#define USING_SIM_BASE_H /* FIXME: quick hack */
struct _sim_cpu; /* FIXME: should be in sim-basics.h */
typedef struct _sim_cpu SIM_CPU;
#include "symcat.h"
#include "sim-basics.h"
#include "cgen-types.h"
#include "m32r-desc.h"
#include "m32r-opc.h"
#include "arch.h"
/* These must be defined before sim-base.h. */
typedef USI sim_cia;
#define CIA_GET(cpu) CPU_PC_GET (cpu)
#define CIA_SET(cpu,val) CPU_PC_SET ((cpu), (val))
#define SIM_ENGINE_HALT_HOOK(sd, cpu, cia) \
do { \
if (cpu) /* null if ctrl-c */ \
sim_pc_set ((cpu), (cia)); \
} while (0)
#define SIM_ENGINE_RESTART_HOOK(sd, cpu, cia) \
do { \
sim_pc_set ((cpu), (cia)); \
} while (0)
#include "sim-base.h"
#include "cgen-sim.h"
#include "m32r-sim.h"
#include "opcode/cgen.h"
/* The _sim_cpu struct. */
struct _sim_cpu {
/* sim/common cpu base. */
sim_cpu_base base;
/* Static parts of cgen. */
CGEN_CPU cgen_cpu;
M32R_MISC_PROFILE m32r_misc_profile;
#define CPU_M32R_MISC_PROFILE(cpu) (& (cpu)->m32r_misc_profile)
/* CPU specific parts go here.
Note that in files that don't need to access these pieces WANT_CPU_FOO
won't be defined and thus these parts won't appear. This is ok in the
sense that things work. It is a source of bugs though.
One has to of course be careful to not take the size of this
struct and no structure members accessed in non-cpu specific files can
go after here. Oh for a better language. */
#if defined (WANT_CPU_M32RBF)
M32RBF_CPU_DATA cpu_data;
#endif
};
/* The sim_state struct. */
struct sim_state {
sim_cpu *cpu;
#define STATE_CPU(sd, n) (/*&*/ (sd)->cpu)
CGEN_STATE cgen_state;
sim_state_base base;
};
/* Misc. */
/* Catch address exceptions. */
extern SIM_CORE_SIGNAL_FN m32r_core_signal;
#define SIM_CORE_SIGNAL(SD,CPU,CIA,MAP,NR_BYTES,ADDR,TRANSFER,ERROR) \
m32r_core_signal ((SD), (CPU), (CIA), (MAP), (NR_BYTES), (ADDR), \
(TRANSFER), (ERROR))
/* Default memory size. */
#define M32R_DEFAULT_MEM_SIZE 0x800000 /* 8M */
#endif /* SIM_MAIN_H */

47
sim/m32r/tconfig.in Normal file
View file

@ -0,0 +1,47 @@
/* M32R target configuration file. -*- C -*- */
#ifndef M32R_TCONFIG_H
#define M32R_TCONFIG_H
/* Define this if the simulator can vary the size of memory.
See the xxx simulator for an example.
This enables the `-m size' option.
The memory size is stored in STATE_MEM_SIZE. */
/* Not used for M32R since we use the memory module. */
/* #define SIM_HAVE_MEM_SIZE */
/* See sim-hload.c. We properly handle LMA. */
#define SIM_HANDLES_LMA 1
/* For MSPR support. FIXME: revisit. */
#define WITH_DEVICES 1
/* FIXME: Revisit. */
#ifdef HAVE_DV_SOCKSER
MODULE_INSTALL_FN dv_sockser_install;
#define MODULE_LIST dv_sockser_install,
#endif
#if 0
/* Enable watchpoints. */
#define WITH_WATCHPOINTS 1
#endif
/* Define this to enable the intrinsic breakpoint mechanism. */
/* FIXME: may be able to remove SIM_HAVE_BREAKPOINT since it essentially
duplicates ifdef SIM_BREAKPOINT (right?) */
#if 0
#define SIM_HAVE_BREAKPOINTS
#define SIM_BREAKPOINT { 0x10, 0xf1 }
#define SIM_BREAKPOINT_SIZE 2
#endif
#if 0
#define HAVE_DV_SOCKSER
#endif
/* This is a global setting. Different cpu families can't mix-n-match -scache
and -pbb. However some cpu families may use -simple while others use
one of -scache/-pbb. */
#define WITH_SCACHE_PBB 1
#endif /* M32R_TCONFIG_H */

170
sim/m32r/traps.c Normal file
View file

@ -0,0 +1,170 @@
/* m32r exception, interrupt, and trap (EIT) support
Copyright (C) 1998 Free Software Foundation, Inc.
Contributed by Cygnus Solutions.
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 2, 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, write to the Free Software Foundation, Inc.,
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#include "sim-main.h"
#include "targ-vals.h"
/* The semantic code invokes this for invalid (unrecognized) instructions. */
void
sim_engine_invalid_insn (SIM_CPU *current_cpu, IADDR cia)
{
SIM_DESC sd = CPU_STATE (current_cpu);
#if 0
if (STATE_ENVIRONMENT (sd) == OPERATING_ENVIRONMENT)
{
h_bsm_set (current_cpu, h_sm_get (current_cpu));
h_bie_set (current_cpu, h_ie_get (current_cpu));
h_bcond_set (current_cpu, h_cond_get (current_cpu));
/* sm not changed */
h_ie_set (current_cpu, 0);
h_cond_set (current_cpu, 0);
h_bpc_set (current_cpu, cia);
sim_engine_restart (CPU_STATE (current_cpu), current_cpu, NULL,
EIT_RSVD_INSN_ADDR);
}
else
#endif
sim_engine_halt (sd, current_cpu, NULL, cia, sim_stopped, SIM_SIGILL);
}
/* Process an address exception. */
void
m32r_core_signal (SIM_DESC sd, SIM_CPU *current_cpu, sim_cia cia,
unsigned int map, int nr_bytes, address_word addr,
transfer_type transfer, sim_core_signals sig)
{
if (STATE_ENVIRONMENT (sd) == OPERATING_ENVIRONMENT)
{
a_m32r_h_cr_set (current_cpu, H_CR_BBPC,
a_m32r_h_cr_get (current_cpu, H_CR_BPC));
a_m32r_h_bpsw_set (current_cpu, a_m32r_h_psw_get (current_cpu));
/* sm not changed */
a_m32r_h_psw_set (current_cpu, a_m32r_h_psw_get (current_cpu) & 0x80);
a_m32r_h_cr_set (current_cpu, H_CR_BPC, cia);
sim_engine_restart (CPU_STATE (current_cpu), current_cpu, NULL,
EIT_ADDR_EXCP_ADDR);
}
else
sim_core_signal (sd, current_cpu, cia, map, nr_bytes, addr,
transfer, sig);
}
/* Read/write functions for system call interface. */
static int
syscall_read_mem (host_callback *cb, struct cb_syscall *sc,
unsigned long taddr, char *buf, int bytes)
{
SIM_DESC sd = (SIM_DESC) sc->p1;
SIM_CPU *cpu = (SIM_CPU *) sc->p2;
return sim_core_read_buffer (sd, cpu, read_map, buf, taddr, bytes);
}
static int
syscall_write_mem (host_callback *cb, struct cb_syscall *sc,
unsigned long taddr, const char *buf, int bytes)
{
SIM_DESC sd = (SIM_DESC) sc->p1;
SIM_CPU *cpu = (SIM_CPU *) sc->p2;
return sim_core_write_buffer (sd, cpu, write_map, buf, taddr, bytes);
}
/* Trap support.
The result is the pc address to continue at.
Preprocessing like saving the various registers has already been done. */
USI
m32r_trap (SIM_CPU *current_cpu, PCADDR pc, int num)
{
SIM_DESC sd = CPU_STATE (current_cpu);
host_callback *cb = STATE_CALLBACK (sd);
#ifdef SIM_HAVE_BREAKPOINTS
/* Check for breakpoints "owned" by the simulator first, regardless
of --environment. */
if (num == TRAP_BREAKPOINT)
{
/* First try sim-break.c. If it's a breakpoint the simulator "owns"
it doesn't return. Otherwise it returns and let's us try. */
sim_handle_breakpoint (sd, current_cpu, pc);
/* Fall through. */
}
#endif
if (STATE_ENVIRONMENT (sd) == OPERATING_ENVIRONMENT)
{
/* The new pc is the trap vector entry.
We assume there's a branch there to some handler. */
USI new_pc = EIT_TRAP_BASE_ADDR + num * 4;
return new_pc;
}
switch (num)
{
case TRAP_SYSCALL :
{
CB_SYSCALL s;
CB_SYSCALL_INIT (&s);
s.func = a_m32r_h_gr_get (current_cpu, 0);
s.arg1 = a_m32r_h_gr_get (current_cpu, 1);
s.arg2 = a_m32r_h_gr_get (current_cpu, 2);
s.arg3 = a_m32r_h_gr_get (current_cpu, 3);
if (s.func == TARGET_SYS_exit)
{
sim_engine_halt (sd, current_cpu, NULL, pc, sim_exited, s.arg1);
}
s.p1 = (PTR) sd;
s.p2 = (PTR) current_cpu;
s.read_mem = syscall_read_mem;
s.write_mem = syscall_write_mem;
cb_syscall (cb, &s);
a_m32r_h_gr_set (current_cpu, 2, s.errcode);
a_m32r_h_gr_set (current_cpu, 0, s.result);
a_m32r_h_gr_set (current_cpu, 1, s.result2);
break;
}
case TRAP_BREAKPOINT:
sim_engine_halt (sd, current_cpu, NULL, pc,
sim_stopped, SIM_SIGTRAP);
break;
default :
{
USI new_pc = EIT_TRAP_BASE_ADDR + num * 4;
return new_pc;
}
}
/* Fake an "rte" insn. */
/* FIXME: Should duplicate all of rte processing. */
return (pc & -4) + 4;
}