diff --git a/sim/mips/.Sanitize b/sim/mips/.Sanitize index 3c7136280f..b0f4205838 100644 --- a/sim/mips/.Sanitize +++ b/sim/mips/.Sanitize @@ -35,9 +35,9 @@ sky_files="ChangeLog.sky sky-device.c sky-device.h sky-dma.c sky-dma.h sky-bits. sky_files="$sky_files sky-engine.c sky-gpuif.c sky-gpuif.h" sky_files="$sky_files sky-gs.c sky-gs.h" sky_files="$sky_files sky-hardware.c sky-hardware.h sky-gdb.c sky-gdb.h" -sky_files="$sky_files sky-libvpe.c sky-libvpe.h sky-pke.c sky-pke.h" +sky_files="$sky_files sky-libvpe.c sky-libvpe.h sky-vif.c sky-vif.h" sky_files="$sky_files sky-vpe.h sky-vu.h sky-vu.c sky-vudis.h sky-vudis.c" -sky_files="$sky_files sky-console.h sky-console.c" +sky_files="$sky_files sky-console.h sky-console.c sky-psio.h sky-psio.c" sky_files="$sky_files sky-interact.h sky-interact.c" sky_files="$sky_files sky-indebug.h sky-indebug.c" if ( echo $* | grep keep\-sky > /dev/null ) ; then diff --git a/sim/mips/ChangeLog b/sim/mips/ChangeLog index c93221dd76..873c6e8026 100644 --- a/sim/mips/ChangeLog +++ b/sim/mips/ChangeLog @@ -3,7 +3,22 @@ Fri Oct 9 18:02:25 1998 Doug Evans * interp.c: #include "itable.h" if WITH_IGEN. (get_insn_name): New function. (sim_open): Initialize CPU_INSN_NAME,CPU_MAX_INSNS. + * sim-main.h (MAX_INSNS,INSN_NAME): Delete. +start-sanitize-sky +Tue Sep 22 10:35:37 1998 Frank Ch. Eigler + + * sim-main.c (tlb_try_match): Specially match virtual + pages mapped to scratchpad RAM, an unimplemented feature. + +end-sanitize-sky +start-sanitize-r5900 +Fri Sep 18 11:31:16 1998 Frank Ch. Eigler + + * r5900.igen (prot3w): Correct rotation sequence; patch + from customer. + +end-sanitize-r5900 Mon Sep 14 12:36:44 1998 Frank Ch. Eigler * configure: Rebuilt to inhale new common/aclocal.m4. @@ -13,6 +28,13 @@ Thu Sep 10 11:50:54 1998 Doug Evans * r5900.igen (plzcw): Make `i' signed. +Wed Sep 9 15:02:10 1998 Doug Evans + + * sim-main.h (COP0_COUNT,COP0_COMPARE,status_IM7): New macros. + * sky-engine.c (cpu_issue): Increment COP0_COUNT and signal an + interrupt if == COP0_COMPARE and interrupt masks/enables allow it. + * interp.c (signal_exception, sky version): Handle INT 2. + Wed Sep 9 11:28:20 1998 Ron Unrau * sim-main.h: track COP0 registers @@ -49,6 +71,13 @@ Tue Aug 25 12:49:46 1998 Frank Ch. Eigler frequent hw-trace messages. end-sanitize-tx3904 +start-sanitize-sky +Tue Aug 11 13:52:16 1998 Frank Ch. Eigler + + * interp.c (signal_exception): Set IP3 bit in CAUSE on + sky interrupt. + +end-sanitize-sky Fri Jul 31 18:14:16 1998 Andrew Cagney * vr.igen (MulAcc): Identify as a vr4100 specific function. @@ -67,8 +96,48 @@ end-sanitize-cygnus start-sanitize-vr4320 * vr4320.igen: Move instructions to vr.igen. * Makefile.in (IGEN_INCLUDE): Remove vr5320.igen. -end-sanitize-vr4320 +end-sanitize-vr4320 +start-sanitize-sky +Fri Jul 24 16:01:03 1998 Ian Carmichael + + * interp.c (MONITOR_SIZE): Make 1MB monitor for SKY. + * mips.igen (BREAK): Fix 0xffff2 monitor call. Slightly less + confusing message if not enough --load-next options appear. + + * sky-pke.h (VUx_MEMx_SRCADDR_START): Move to 0x19800000 range. + * sim-main.c (GDB_COMM_AREA): Move to 0x19810000. + * sky-gdb.c (init_fifo_bp_cache): Use VIO_BASE when reading GDB area. + (resume_handler): Same. + (suspend_handler): Same. + +Wed Jul 22 13:04:13 1998 Frank Ch. Eigler + + * mips.igen (break): Implement LOAD_INSTRUCTION ("break 0xffff1") + to trigger multi-phase load. + + * sim-main.c: Include sim-assert.h for ASSERT macro. + * sim-main.h (PRINTF_INSTRUCTION): Correct bit pattern for + "break 0xffff2". + +Tue Jul 21 18:37:36 1998 Ian Carmichael + + MMU support. + * interp.c (sim_open): Initialize TLB. + * interp.c (signal_exceptions): New 5900 handling. + * r5900.igen (TLBWR, TLBWI, TLBR, TLBP): Make these work. + * sim-main.c (tlb_try_match, tlb_lookup): New functions. + (address_translation): Use the TLB. + * sim-main.h (r4000_tlb_entry_t): New type. + (TLB_*): New constants. + (COP0_*): New register names. + + Sky character I/O device. + * sky-psio.c: New file. + * sky-psio.h: New file. + * Makefile.in: Add sky-psio.o. + +end-sanitize-sky start-sanitize-r5900 Tue Jul 14 16:10:45 1998 Andrew Cagney diff --git a/sim/mips/Makefile.in b/sim/mips/Makefile.in index 4f3bb2f9f2..70ba724c49 100644 --- a/sim/mips/Makefile.in +++ b/sim/mips/Makefile.in @@ -10,13 +10,17 @@ SIM_NO_OBJ = # start-sanitize-sky SIM_SKY_OBJS = \ + sky-console.o \ sky-device.o \ sky-dma.o \ sky-engine.o \ + sky-interact.o \ sky-gpuif.o \ sky-hardware.o \ + sky-indebug.o \ sky-libvpe.o \ - sky-pke.o \ + sky-vif.o \ + sky-psio.o \ sky-vu.o \ sky-vudis.o \ sky-gs.o \ @@ -29,7 +33,7 @@ SIM_IGEN_OBJ = \ semantics.o \ idecode.o \ icache.o \ - engine.o \ + @mips_igen_engine@ \ irun.o \ SIM_M16_OBJ = \ @@ -128,15 +132,12 @@ IGEN_INCLUDE=\ $(start-sanitize-r5900) \ $(srcdir)/r5900.igen \ $(end-sanitize-r5900) \ - $(start-sanitize-vr5400) \ - $(srcdir)/vr5400.igen \ + $(start-sanitize-cygnus) \ $(srcdir)/mdmx.igen \ - $(end-sanitize-vr5400) \ - $(start-sanitize-vr4320) \ - $(srcdir)/vr4320.igen \ - $(end-sanitize-vr4320) \ + $(end-sanitize-cygnus) \ $(srcdir)/m16.igen \ - $(srcdir)/tx.igen + $(srcdir)/tx.igen \ + $(srcdir)/vr.igen \ SIM_IGEN_ALL = tmp-igen diff --git a/sim/mips/configure b/sim/mips/configure index fde6b62607..19f1a11cfc 100755 --- a/sim/mips/configure +++ b/sim/mips/configure @@ -133,7 +133,7 @@ sim_inline="-DDEFAULT_INLINE=0" # Guess values for system-dependent variables and create Makefiles. -# Generated automatically using autoconf version 2.12.1 +# Generated automatically using autoconf version 2.12.2 # Copyright (C) 1992, 93, 94, 95, 96 Free Software Foundation, Inc. # # This configure script is free software; the Free Software Foundation @@ -185,6 +185,8 @@ ac_help="$ac_help --with-x use the X Window System" ac_help="$ac_help --with-sim-gpu2=path Use GPU2 library under given directory" +ac_help="$ac_help + --with-x use the X Window System" ac_help="$ac_help --with-sim-funit=path Use target FP library under given directory" @@ -509,7 +511,7 @@ EOF verbose=yes ;; -version | --version | --versio | --versi | --vers) - echo "configure generated by autoconf version 2.12.1" + echo "configure generated by autoconf version 2.12.2" exit 0 ;; -with-* | --with-*) @@ -679,9 +681,11 @@ ac_ext=c # CFLAGS is not in ac_cpp because -g, -O, etc. are not valid cpp options. ac_cpp='$CPP $CPPFLAGS' ac_compile='${CC-cc} -c $CFLAGS $CPPFLAGS conftest.$ac_ext 1>&5' -ac_link='${CC-cc} -o conftest $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' +ac_link='${CC-cc} -o conftest${ac_exeext} $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' cross_compiling=$ac_cv_prog_cc_cross +ac_exeext= +ac_objext=o if (echo "testing\c"; echo 1,2,3) | grep c >/dev/null; then # Stardent Vistra SVR4 grep lacks -e, says ghazi@caip.rutgers.edu. if (echo -n testing; echo 1,2,3) | sed s/-n/xn/ | grep xn >/dev/null; then @@ -697,7 +701,7 @@ fi echo $ac_n "checking how to run the C preprocessor""... $ac_c" 1>&6 -echo "configure:701: checking how to run the C preprocessor" >&5 +echo "configure:705: checking how to run the C preprocessor" >&5 # On Suns, sometimes $CPP names a directory. if test -n "$CPP" && test -d "$CPP"; then CPP= @@ -712,14 +716,14 @@ else # On the NeXT, cc -E runs the code through the compiler's parser, # not just through cpp. cat > conftest.$ac_ext < Syntax Error EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:722: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` +{ (eval echo configure:726: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then : else @@ -729,14 +733,31 @@ else rm -rf conftest* CPP="${CC-cc} -E -traditional-cpp" cat > conftest.$ac_ext < Syntax Error EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:739: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` +{ (eval echo configure:743: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` +if test -z "$ac_err"; then + : +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + CPP="${CC-cc} -nologo -E" + cat > conftest.$ac_ext < +Syntax Error +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:760: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then : else @@ -748,6 +769,8 @@ else fi rm -f conftest* fi +rm -f conftest* +fi rm -f conftest* ac_cv_prog_CPP="$CPP" fi @@ -758,7 +781,7 @@ fi echo "$ac_t""$CPP" 1>&6 echo $ac_n "checking whether ${MAKE-make} sets \${MAKE}""... $ac_c" 1>&6 -echo "configure:762: checking whether ${MAKE-make} sets \${MAKE}" >&5 +echo "configure:785: checking whether ${MAKE-make} sets \${MAKE}" >&5 set dummy ${MAKE-make}; ac_make=`echo "$2" | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_prog_make_${ac_make}_set'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -785,7 +808,7 @@ else fi echo $ac_n "checking for POSIXized ISC""... $ac_c" 1>&6 -echo "configure:789: checking for POSIXized ISC" >&5 +echo "configure:812: checking for POSIXized ISC" >&5 if test -d /etc/conf/kconfig.d && grep _POSIX_VERSION /usr/include/sys/unistd.h >/dev/null 2>&1 then @@ -806,12 +829,12 @@ else fi echo $ac_n "checking for ANSI C header files""... $ac_c" 1>&6 -echo "configure:810: checking for ANSI C header files" >&5 +echo "configure:833: checking for ANSI C header files" >&5 if eval "test \"`echo '$''{'ac_cv_header_stdc'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < #include @@ -819,8 +842,8 @@ else #include EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:823: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` +{ (eval echo configure:846: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* ac_cv_header_stdc=yes @@ -836,7 +859,7 @@ rm -f conftest* if test $ac_cv_header_stdc = yes; then # SunOS 4.x string.h does not declare mem*, contrary to ANSI. cat > conftest.$ac_ext < EOF @@ -854,7 +877,7 @@ fi if test $ac_cv_header_stdc = yes; then # ISC 2.0.2 stdlib.h does not declare free, contrary to ANSI. cat > conftest.$ac_ext < EOF @@ -875,7 +898,7 @@ if test "$cross_compiling" = yes; then : else cat > conftest.$ac_ext < #define ISLOWER(c) ('a' <= (c) && (c) <= 'z') @@ -886,7 +909,7 @@ if (XOR (islower (i), ISLOWER (i)) || toupper (i) != TOUPPER (i)) exit(2); exit (0); } EOF -if { (eval echo configure:890: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +if { (eval echo configure:913: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then : else @@ -910,12 +933,12 @@ EOF fi echo $ac_n "checking for working const""... $ac_c" 1>&6 -echo "configure:914: checking for working const" >&5 +echo "configure:937: checking for working const" >&5 if eval "test \"`echo '$''{'ac_cv_c_const'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:991: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_const=yes else @@ -985,21 +1008,21 @@ EOF fi echo $ac_n "checking for inline""... $ac_c" 1>&6 -echo "configure:989: checking for inline" >&5 +echo "configure:1012: checking for inline" >&5 if eval "test \"`echo '$''{'ac_cv_c_inline'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else ac_cv_c_inline=no for ac_kw in inline __inline__ __inline; do cat > conftest.$ac_ext <&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:1026: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_inline=$ac_kw; break else @@ -1025,12 +1048,12 @@ EOF esac echo $ac_n "checking for off_t""... $ac_c" 1>&6 -echo "configure:1029: checking for off_t" >&5 +echo "configure:1052: checking for off_t" >&5 if eval "test \"`echo '$''{'ac_cv_type_off_t'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < #if STDC_HEADERS @@ -1058,12 +1081,12 @@ EOF fi echo $ac_n "checking for size_t""... $ac_c" 1>&6 -echo "configure:1062: checking for size_t" >&5 +echo "configure:1085: checking for size_t" >&5 if eval "test \"`echo '$''{'ac_cv_type_size_t'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < #if STDC_HEADERS @@ -1093,19 +1116,19 @@ fi # The Ultrix 4.2 mips builtin alloca declared by alloca.h only works # for constant arguments. Useless! echo $ac_n "checking for working alloca.h""... $ac_c" 1>&6 -echo "configure:1097: checking for working alloca.h" >&5 +echo "configure:1120: checking for working alloca.h" >&5 if eval "test \"`echo '$''{'ac_cv_header_alloca_h'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < int main() { char *p = alloca(2 * sizeof(int)); ; return 0; } EOF -if { (eval echo configure:1109: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:1132: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_header_alloca_h=yes else @@ -1126,25 +1149,30 @@ EOF fi echo $ac_n "checking for alloca""... $ac_c" 1>&6 -echo "configure:1130: checking for alloca" >&5 +echo "configure:1153: checking for alloca" >&5 if eval "test \"`echo '$''{'ac_cv_func_alloca_works'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < +# ifdef _MSC_VER +# include +# define alloca _alloca # else -# ifdef _AIX - #pragma alloca +# if HAVE_ALLOCA_H +# include # else -# ifndef alloca /* predefined by HP cc +Olibcalls */ +# ifdef _AIX + #pragma alloca +# else +# ifndef alloca /* predefined by HP cc +Olibcalls */ char *alloca (); +# endif # endif # endif # endif @@ -1154,7 +1182,7 @@ int main() { char *p = (char *) alloca(1); ; return 0; } EOF -if { (eval echo configure:1158: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:1186: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_func_alloca_works=yes else @@ -1179,19 +1207,19 @@ if test $ac_cv_func_alloca_works = no; then # that cause trouble. Some versions do not even contain alloca or # contain a buggy version. If you still want to use their alloca, # use ar to extract alloca.o from them instead of compiling alloca.c. - ALLOCA=alloca.o + ALLOCA=alloca.${ac_objext} cat >> confdefs.h <<\EOF #define C_ALLOCA 1 EOF echo $ac_n "checking whether alloca needs Cray hooks""... $ac_c" 1>&6 -echo "configure:1190: checking whether alloca needs Cray hooks" >&5 +echo "configure:1218: checking whether alloca needs Cray hooks" >&5 if eval "test \"`echo '$''{'ac_cv_os_cray'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&6 if test $ac_cv_os_cray = yes; then for ac_func in _getb67 GETB67 getb67; do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:1220: checking for $ac_func" >&5 +echo "configure:1248: checking for $ac_func" >&5 if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:1276: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -1271,7 +1299,7 @@ done fi echo $ac_n "checking stack direction for C alloca""... $ac_c" 1>&6 -echo "configure:1275: checking stack direction for C alloca" >&5 +echo "configure:1303: checking stack direction for C alloca" >&5 if eval "test \"`echo '$''{'ac_cv_c_stack_direction'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -1279,7 +1307,7 @@ else ac_cv_c_stack_direction=0 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +if { (eval echo configure:1330: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then ac_cv_c_stack_direction=1 else @@ -1323,18 +1351,18 @@ for ac_hdr in unistd.h do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:1327: checking for $ac_hdr" >&5 +echo "configure:1355: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:1337: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` +{ (eval echo configure:1365: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* eval "ac_cv_header_$ac_safe=yes" @@ -1362,12 +1390,12 @@ done for ac_func in getpagesize do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:1366: checking for $ac_func" >&5 +echo "configure:1394: checking for $ac_func" >&5 if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:1422: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -1415,7 +1443,7 @@ fi done echo $ac_n "checking for working mmap""... $ac_c" 1>&6 -echo "configure:1419: checking for working mmap" >&5 +echo "configure:1447: checking for working mmap" >&5 if eval "test \"`echo '$''{'ac_cv_func_mmap_fixed_mapped'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -1423,7 +1451,7 @@ else ac_cv_func_mmap_fixed_mapped=no else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +if { (eval echo configure:1595: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then ac_cv_func_mmap_fixed_mapped=yes else @@ -1636,7 +1664,7 @@ else { echo "configure: error: can not run $ac_config_sub" 1>&2; exit 1; } fi echo $ac_n "checking host system type""... $ac_c" 1>&6 -echo "configure:1640: checking host system type" >&5 +echo "configure:1668: checking host system type" >&5 host_alias=$host case "$host_alias" in @@ -1657,7 +1685,7 @@ host_os=`echo $host | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\3/'` echo "$ac_t""$host" 1>&6 echo $ac_n "checking target system type""... $ac_c" 1>&6 -echo "configure:1661: checking target system type" >&5 +echo "configure:1689: checking target system type" >&5 target_alias=$target case "$target_alias" in @@ -1675,7 +1703,7 @@ target_os=`echo $target | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\3/'` echo "$ac_t""$target" 1>&6 echo $ac_n "checking build system type""... $ac_c" 1>&6 -echo "configure:1679: checking build system type" >&5 +echo "configure:1707: checking build system type" >&5 build_alias=$build case "$build_alias" in @@ -1719,14 +1747,14 @@ test "$program_transform_name" = "" && program_transform_name="s,x,x," # Extract the first word of "gcc", so it can be a program name with args. set dummy gcc; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:1723: checking for $ac_word" >&5 +echo "configure:1751: checking for $ac_word" >&5 if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. else - IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS=":" for ac_dir in $PATH; do test -z "$ac_dir" && ac_dir=. if test -f $ac_dir/$ac_word; then @@ -1748,14 +1776,14 @@ if test -z "$CC"; then # Extract the first word of "cc", so it can be a program name with args. set dummy cc; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:1752: checking for $ac_word" >&5 +echo "configure:1780: checking for $ac_word" >&5 if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. else - IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS=":" ac_prog_rejected=no for ac_dir in $PATH; do test -z "$ac_dir" && ac_dir=. @@ -1792,25 +1820,58 @@ else echo "$ac_t""no" 1>&6 fi + if test -z "$CC"; then + case "`uname -s`" in + *win32* | *WIN32*) + # Extract the first word of "cl", so it can be a program name with args. +set dummy cl; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:1830: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS=":" + for ac_dir in $PATH; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_prog_CC="cl" + break + fi + done + IFS="$ac_save_ifs" +fi +fi +CC="$ac_cv_prog_CC" +if test -n "$CC"; then + echo "$ac_t""$CC" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + ;; + esac + fi test -z "$CC" && { echo "configure: error: no acceptable cc found in \$PATH" 1>&2; exit 1; } fi echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works""... $ac_c" 1>&6 -echo "configure:1800: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5 +echo "configure:1861: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5 ac_ext=c # CFLAGS is not in ac_cpp because -g, -O, etc. are not valid cpp options. ac_cpp='$CPP $CPPFLAGS' ac_compile='${CC-cc} -c $CFLAGS $CPPFLAGS conftest.$ac_ext 1>&5' -ac_link='${CC-cc} -o conftest $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' +ac_link='${CC-cc} -o conftest${ac_exeext} $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' cross_compiling=$ac_cv_prog_cc_cross cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:1875: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then ac_cv_prog_cc_works=yes # If we can't run a trivial program, we are probably using a cross compiler. if (./conftest; exit) 2>/dev/null; then @@ -1830,12 +1891,12 @@ if test $ac_cv_prog_cc_works = no; then { echo "configure: error: installation or configuration problem: C compiler cannot create executables." 1>&2; exit 1; } fi echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler""... $ac_c" 1>&6 -echo "configure:1834: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5 +echo "configure:1895: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5 echo "$ac_t""$ac_cv_prog_cc_cross" 1>&6 cross_compiling=$ac_cv_prog_cc_cross echo $ac_n "checking whether we are using GNU C""... $ac_c" 1>&6 -echo "configure:1839: checking whether we are using GNU C" >&5 +echo "configure:1900: checking whether we are using GNU C" >&5 if eval "test \"`echo '$''{'ac_cv_prog_gcc'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -1844,7 +1905,7 @@ else yes; #endif EOF -if { ac_try='${CC-cc} -E conftest.c'; { (eval echo configure:1848: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then +if { ac_try='${CC-cc} -E conftest.c'; { (eval echo configure:1909: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then ac_cv_prog_gcc=yes else ac_cv_prog_gcc=no @@ -1855,11 +1916,15 @@ echo "$ac_t""$ac_cv_prog_gcc" 1>&6 if test $ac_cv_prog_gcc = yes; then GCC=yes - ac_test_CFLAGS="${CFLAGS+set}" - ac_save_CFLAGS="$CFLAGS" - CFLAGS= - echo $ac_n "checking whether ${CC-cc} accepts -g""... $ac_c" 1>&6 -echo "configure:1863: checking whether ${CC-cc} accepts -g" >&5 +else + GCC= +fi + +ac_test_CFLAGS="${CFLAGS+set}" +ac_save_CFLAGS="$CFLAGS" +CFLAGS= +echo $ac_n "checking whether ${CC-cc} accepts -g""... $ac_c" 1>&6 +echo "configure:1928: checking whether ${CC-cc} accepts -g" >&5 if eval "test \"`echo '$''{'ac_cv_prog_cc_g'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -1874,16 +1939,20 @@ rm -f conftest* fi echo "$ac_t""$ac_cv_prog_cc_g" 1>&6 - if test "$ac_test_CFLAGS" = set; then - CFLAGS="$ac_save_CFLAGS" - elif test $ac_cv_prog_cc_g = yes; then +if test "$ac_test_CFLAGS" = set; then + CFLAGS="$ac_save_CFLAGS" +elif test $ac_cv_prog_cc_g = yes; then + if test "$GCC" = yes; then CFLAGS="-g -O2" else - CFLAGS="-O2" + CFLAGS="-g" fi else - GCC= - test "${CFLAGS+set}" = set || CFLAGS="-g" + if test "$GCC" = yes; then + CFLAGS="-O2" + else + CFLAGS= + fi fi # Find a good install program. We prefer a C program (faster), @@ -1898,12 +1967,12 @@ fi # SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff" # ./install, which can be erroneously created by make from ./install.sh. echo $ac_n "checking for a BSD compatible install""... $ac_c" 1>&6 -echo "configure:1902: checking for a BSD compatible install" >&5 +echo "configure:1971: checking for a BSD compatible install" >&5 if test -z "$INSTALL"; then if eval "test \"`echo '$''{'ac_cv_path_install'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else - IFS="${IFS= }"; ac_save_IFS="$IFS"; IFS="${IFS}:" + IFS="${IFS= }"; ac_save_IFS="$IFS"; IFS=":" for ac_dir in $PATH; do # Account for people who put trailing slashes in PATH elements. case "$ac_dir/" in @@ -1964,14 +2033,14 @@ AR=${AR-ar} # Extract the first word of "ranlib", so it can be a program name with args. set dummy ranlib; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:1968: checking for $ac_word" >&5 +echo "configure:2037: checking for $ac_word" >&5 if eval "test \"`echo '$''{'ac_cv_prog_RANLIB'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else if test -n "$RANLIB"; then ac_cv_prog_RANLIB="$RANLIB" # Let the user override the test. else - IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS=":" for ac_dir in $PATH; do test -z "$ac_dir" && ac_dir=. if test -f $ac_dir/$ac_word; then @@ -1998,18 +2067,18 @@ unistd.h values.h sys/param.h do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:2002: checking for $ac_hdr" >&5 +echo "configure:2071: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:2012: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` +{ (eval echo configure:2081: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* eval "ac_cv_header_$ac_safe=yes" @@ -2038,12 +2107,12 @@ done __argz_count __argz_stringify __argz_next do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:2042: checking for $ac_func" >&5 +echo "configure:2111: checking for $ac_func" >&5 if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:2139: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -2095,12 +2164,12 @@ done for ac_func in stpcpy do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:2099: checking for $ac_func" >&5 +echo "configure:2168: checking for $ac_func" >&5 if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:2196: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -2157,19 +2226,19 @@ EOF if test $ac_cv_header_locale_h = yes; then echo $ac_n "checking for LC_MESSAGES""... $ac_c" 1>&6 -echo "configure:2161: checking for LC_MESSAGES" >&5 +echo "configure:2230: checking for LC_MESSAGES" >&5 if eval "test \"`echo '$''{'am_cv_val_LC_MESSAGES'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < int main() { return LC_MESSAGES ; return 0; } EOF -if { (eval echo configure:2173: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:2242: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* am_cv_val_LC_MESSAGES=yes else @@ -2190,7 +2259,7 @@ EOF fi fi echo $ac_n "checking whether NLS is requested""... $ac_c" 1>&6 -echo "configure:2194: checking whether NLS is requested" >&5 +echo "configure:2263: checking whether NLS is requested" >&5 # Check whether --enable-nls or --disable-nls was given. if test "${enable_nls+set}" = set; then enableval="$enable_nls" @@ -2210,7 +2279,7 @@ fi EOF echo $ac_n "checking whether included gettext is requested""... $ac_c" 1>&6 -echo "configure:2214: checking whether included gettext is requested" >&5 +echo "configure:2283: checking whether included gettext is requested" >&5 # Check whether --with-included-gettext or --without-included-gettext was given. if test "${with_included_gettext+set}" = set; then withval="$with_included_gettext" @@ -2229,18 +2298,18 @@ fi ac_safe=`echo "libintl.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for libintl.h""... $ac_c" 1>&6 -echo "configure:2233: checking for libintl.h" >&5 +echo "configure:2302: checking for libintl.h" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:2243: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` +{ (eval echo configure:2312: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* eval "ac_cv_header_$ac_safe=yes" @@ -2256,19 +2325,19 @@ fi if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then echo "$ac_t""yes" 1>&6 echo $ac_n "checking for gettext in libc""... $ac_c" 1>&6 -echo "configure:2260: checking for gettext in libc" >&5 +echo "configure:2329: checking for gettext in libc" >&5 if eval "test \"`echo '$''{'gt_cv_func_gettext_libc'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < int main() { return (int) gettext ("") ; return 0; } EOF -if { (eval echo configure:2272: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:2341: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* gt_cv_func_gettext_libc=yes else @@ -2284,7 +2353,7 @@ echo "$ac_t""$gt_cv_func_gettext_libc" 1>&6 if test "$gt_cv_func_gettext_libc" != "yes"; then echo $ac_n "checking for bindtextdomain in -lintl""... $ac_c" 1>&6 -echo "configure:2288: checking for bindtextdomain in -lintl" >&5 +echo "configure:2357: checking for bindtextdomain in -lintl" >&5 ac_lib_var=`echo intl'_'bindtextdomain | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -2292,7 +2361,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lintl $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:2376: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -2319,19 +2388,19 @@ fi if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then echo "$ac_t""yes" 1>&6 echo $ac_n "checking for gettext in libintl""... $ac_c" 1>&6 -echo "configure:2323: checking for gettext in libintl" >&5 +echo "configure:2392: checking for gettext in libintl" >&5 if eval "test \"`echo '$''{'gt_cv_func_gettext_libintl'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:2404: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* gt_cv_func_gettext_libintl=yes else @@ -2359,7 +2428,7 @@ EOF # Extract the first word of "msgfmt", so it can be a program name with args. set dummy msgfmt; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:2363: checking for $ac_word" >&5 +echo "configure:2432: checking for $ac_word" >&5 if eval "test \"`echo '$''{'ac_cv_path_MSGFMT'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -2393,12 +2462,12 @@ fi for ac_func in dcgettext do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:2397: checking for $ac_func" >&5 +echo "configure:2466: checking for $ac_func" >&5 if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:2494: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -2448,7 +2517,7 @@ done # Extract the first word of "gmsgfmt", so it can be a program name with args. set dummy gmsgfmt; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:2452: checking for $ac_word" >&5 +echo "configure:2521: checking for $ac_word" >&5 if eval "test \"`echo '$''{'ac_cv_path_GMSGFMT'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -2460,7 +2529,7 @@ else ac_cv_path_GMSGFMT="$GMSGFMT" # Let the user override the test with a dos path. ;; *) - IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS=":" for ac_dir in $PATH; do test -z "$ac_dir" && ac_dir=. if test -f $ac_dir/$ac_word; then @@ -2483,7 +2552,7 @@ fi # Extract the first word of "xgettext", so it can be a program name with args. set dummy xgettext; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:2487: checking for $ac_word" >&5 +echo "configure:2556: checking for $ac_word" >&5 if eval "test \"`echo '$''{'ac_cv_path_XGETTEXT'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -2515,7 +2584,7 @@ else fi cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:2596: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* CATOBJEXT=.gmo DATADIRNAME=share @@ -2555,7 +2624,7 @@ fi # Extract the first word of "msgfmt", so it can be a program name with args. set dummy msgfmt; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:2559: checking for $ac_word" >&5 +echo "configure:2628: checking for $ac_word" >&5 if eval "test \"`echo '$''{'ac_cv_path_MSGFMT'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -2589,7 +2658,7 @@ fi # Extract the first word of "gmsgfmt", so it can be a program name with args. set dummy gmsgfmt; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:2593: checking for $ac_word" >&5 +echo "configure:2662: checking for $ac_word" >&5 if eval "test \"`echo '$''{'ac_cv_path_GMSGFMT'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -2601,7 +2670,7 @@ else ac_cv_path_GMSGFMT="$GMSGFMT" # Let the user override the test with a dos path. ;; *) - IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS=":" for ac_dir in $PATH; do test -z "$ac_dir" && ac_dir=. if test -f $ac_dir/$ac_word; then @@ -2624,7 +2693,7 @@ fi # Extract the first word of "xgettext", so it can be a program name with args. set dummy xgettext; ac_word=$2 echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 -echo "configure:2628: checking for $ac_word" >&5 +echo "configure:2697: checking for $ac_word" >&5 if eval "test \"`echo '$''{'ac_cv_path_XGETTEXT'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -2714,7 +2783,7 @@ fi LINGUAS= else echo $ac_n "checking for catalogs to be installed""... $ac_c" 1>&6 -echo "configure:2718: checking for catalogs to be installed" >&5 +echo "configure:2787: checking for catalogs to be installed" >&5 NEW_LINGUAS= for lang in ${LINGUAS=$ALL_LINGUAS}; do case "$ALL_LINGUAS" in @@ -2742,18 +2811,18 @@ echo "configure:2718: checking for catalogs to be installed" >&5 if test "$CATOBJEXT" = ".cat"; then ac_safe=`echo "linux/version.h" | sed 'y%./+-%__p_%'` echo $ac_n "checking for linux/version.h""... $ac_c" 1>&6 -echo "configure:2746: checking for linux/version.h" >&5 +echo "configure:2815: checking for linux/version.h" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:2756: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` +{ (eval echo configure:2825: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* eval "ac_cv_header_$ac_safe=yes" @@ -2821,18 +2890,18 @@ for ac_hdr in stdlib.h string.h strings.h unistd.h time.h do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:2825: checking for $ac_hdr" >&5 +echo "configure:2894: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:2835: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` +{ (eval echo configure:2904: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* eval "ac_cv_header_$ac_safe=yes" @@ -2861,18 +2930,18 @@ for ac_hdr in sys/time.h sys/resource.h do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:2865: checking for $ac_hdr" >&5 +echo "configure:2934: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:2875: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` +{ (eval echo configure:2944: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* eval "ac_cv_header_$ac_safe=yes" @@ -2901,18 +2970,18 @@ for ac_hdr in fcntl.h fpu_control.h do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:2905: checking for $ac_hdr" >&5 +echo "configure:2974: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:2915: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` +{ (eval echo configure:2984: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* eval "ac_cv_header_$ac_safe=yes" @@ -2940,12 +3009,12 @@ done for ac_func in getrusage time sigaction __setfpucw do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:2944: checking for $ac_func" >&5 +echo "configure:3013: checking for $ac_func" >&5 if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:3041: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -2993,6 +3062,102 @@ fi done +# Check for socket libraries +echo $ac_n "checking for bind in -lsocket""... $ac_c" 1>&6 +echo "configure:3068: checking for bind in -lsocket" >&5 +ac_lib_var=`echo socket'_'bind | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_save_LIBS="$LIBS" +LIBS="-lsocket $LIBS" +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=no" +fi +rm -f conftest* +LIBS="$ac_save_LIBS" + +fi +if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_lib=HAVE_LIB`echo socket | sed -e 's/[^a-zA-Z0-9_]/_/g' \ + -e 'y/abcdefghijklmnopqrstuvwxyz/ABCDEFGHIJKLMNOPQRSTUVWXYZ/'` + cat >> confdefs.h <&6 +fi + +echo $ac_n "checking for gethostbyname in -lnsl""... $ac_c" 1>&6 +echo "configure:3115: checking for gethostbyname in -lnsl" >&5 +ac_lib_var=`echo nsl'_'gethostbyname | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_save_LIBS="$LIBS" +LIBS="-lnsl $LIBS" +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=no" +fi +rm -f conftest* +LIBS="$ac_save_LIBS" + +fi +if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_lib=HAVE_LIB`echo nsl | sed -e 's/[^a-zA-Z0-9_]/_/g' \ + -e 'y/abcdefghijklmnopqrstuvwxyz/ABCDEFGHIJKLMNOPQRSTUVWXYZ/'` + cat >> confdefs.h <&6 +fi + + . ${srcdir}/../../bfd/configure.host @@ -3141,12 +3306,12 @@ fi echo $ac_n "checking return type of signal handlers""... $ac_c" 1>&6 -echo "configure:3145: checking return type of signal handlers" >&5 +echo "configure:3310: checking return type of signal handlers" >&5 if eval "test \"`echo '$''{'ac_cv_type_signal'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < #include @@ -3163,7 +3328,7 @@ int main() { int i; ; return 0; } EOF -if { (eval echo configure:3167: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:3332: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_type_signal=void else @@ -3183,7 +3348,7 @@ EOF echo $ac_n "checking for executable suffix""... $ac_c" 1>&6 -echo "configure:3187: checking for executable suffix" >&5 +echo "configure:3352: checking for executable suffix" >&5 if eval "test \"`echo '$''{'am_cv_exeext'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -3336,14 +3501,14 @@ else if test "x$cross_compiling" = "xno"; then echo $ac_n "checking whether byte ordering is bigendian""... $ac_c" 1>&6 -echo "configure:3340: checking whether byte ordering is bigendian" >&5 +echo "configure:3505: checking whether byte ordering is bigendian" >&5 if eval "test \"`echo '$''{'ac_cv_c_bigendian'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else ac_cv_c_bigendian=unknown # See if sys/param.h defines the BYTE_ORDER macro. cat > conftest.$ac_ext < #include @@ -3354,11 +3519,11 @@ int main() { #endif ; return 0; } EOF -if { (eval echo configure:3358: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:3523: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* # It does; now see whether it defined to BIG_ENDIAN or not. cat > conftest.$ac_ext < #include @@ -3369,7 +3534,7 @@ int main() { #endif ; return 0; } EOF -if { (eval echo configure:3373: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:3538: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_bigendian=yes else @@ -3389,7 +3554,7 @@ if test "$cross_compiling" = yes; then { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +if { (eval echo configure:3571: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then ac_cv_c_bigendian=no else @@ -3500,6 +3665,7 @@ case "${target}" in # start-sanitize-r5900 mips64r59*-*-*) mips_endian=LITTLE_ENDIAN ;; # end-sanitize-r5900 + mips64el*-*-*) mips_endian=LITTLE_ENDIAN ;; mips64*-*-*) default_endian=BIG_ENDIAN ;; mips16*-*-*) default_endian=BIG_ENDIAN ;; mips*-*-*) default_endian=BIG_ENDIAN ;; @@ -3565,6 +3731,9 @@ case "${target}" in # start-sanitize-r5900 mips64r59*-*-*) mips_bitsize=64 ; mips_msb=63 ; mips_addr_bitsize=32;; # end-sanitize-r5900 +# start-sanitize-sky + mips64*-sky*-*) mips_bitsize=64 ; mips_msb=63 ; mips_addr_bitsize=32;; +# end-sanitize-sky mips64*-*-*) mips_bitsize=64 ; mips_msb=63 ;; mips16*-*-*) mips_bitsize=64 ; mips_msb=63 ;; mips*-*-*) mips_bitsize=32 ; mips_msb=31 ;; @@ -3648,9 +3817,12 @@ case "${target}" in # start-sanitize-r5900 mips64r59*-*-*) mips_fpu=HARD_FLOATING_POINT ; mips_fpu_bitsize=32 ;; # end-sanitize-r5900 +# start-sanitize-sky + mips64*-sky*-*) mips_fpu=HARD_FLOATING_POINT ; mips_fpu_bitsize=32 ;; +# end-sanitize-sky mips64*-*-*) mips_fpu=HARD_FLOATING_POINT ;; mips16*-*-*) mips_fpu=HARD_FLOATING_POINT ;; - mips*-*-*) mips_fpu=HARD_FLOATING_POINT ;; + mips*-*-*) mips_fpu=HARD_FLOATING_POINT ; mips_fpu_bitsize=32 ;; *) mips_fpu=HARD_FLOATING_POINT ;; esac @@ -3758,18 +3930,18 @@ case "${target}" in sim_igen_machine="-M mipsIV,vr4320 -G gen-multi-sim=mipsIV" # end-sanitize-vr4320 ;; -# start-sanitize-vr5400 +# start-sanitize-cygnus mips64vr54*-*-*) sim_default_gen=IGEN sim_use_gen=IGEN sim_igen_machine="-M vr5000,vr5400 -G gen-multi-sim=vr5400" ;; -# end-sanitize-vr5400 +# end-sanitize-cygnus mips64vr5*-*-*) sim_default_gen=IGEN sim_use_gen=IGEN sim_igen_machine="-M vr5000" -# start-sanitize-vr5400 +# start-sanitize-cygnus sim_igen_machine="-M vr5000,vr5400 -G gen-multi-sim=vr5000" -# end-sanitize-vr5400 +# end-sanitize-cygnus ;; mips64vr4100-*-*) echo "NOTE: mips64vr4100 still uses gencode" sim_default_gen=M16 @@ -3822,26 +3994,32 @@ fi -case "${target}" in -# start-sanitize-sky - mips64r59*-sky-*) mips_extra_objs='$(SIM_SKY_OBJS)' ; - SIM_SUBTARGET="-DTARGET_SKY -DWITH_DEVICES=1 -DDEVICE_INIT=1";; - -# end-sanitize-sky - *) mips_extra_objs="" ;; -esac - - - - -# start-sanitize-tx3904 # # Add simulated hardware devices # hw_enabled=no case "${target}" in - mips*tx39*) hw_enabled=yes ; hw_extra_devices="tx3904cpu tx3904irc tx3904tmr" ;; - *) ;; +# start-sanitize-tx3904 + mips*tx39*) + hw_enabled=yes + hw_extra_devices="tx3904cpu tx3904irc tx3904tmr tx3904sio" + mips_extra_objs="dv-sockser.o" + SIM_SUBTARGET="$SIM_SUBTARGET -DTARGET_TX3904=1" + ;; +# end-sanitize-tx3904 +# start-sanitize-sky + mips64r59*-sky-*) + mips_extra_objs='$(SIM_SKY_OBJS)' + SIM_SUBTARGET="-DTARGET_SKY -DWITH_DEVICES=1 -DDEVICE_INIT=1" + ;; + mips64*-skyb-*) + mips_extra_objs='$(SIM_SKY_OBJS)' + SIM_SUBTARGET="-DTARGET_SKY -DTARGET_SKY_B -DWITH_DEVICES=1 -DDEVICE_INIT=1" + ;; +# end-sanitize-sky + *) + mips_extra_objs="" + ;; esac if test x"$hw_enabled" = x"yes"; then @@ -3900,7 +4078,23 @@ if test x"$silent" != x"yes"; then fi fi -# end-sanitize-tx3904 + + + +# Choose simulator engine +case "${target}" in +# start-sanitize-sky + mips64r59*-sky-*) + mips_igen_engine="" + ;; + mips64*-skyb-*) + mips_igen_engine="" + ;; +# end-sanitize-sky + *) mips_igen_engine="engine.o" + ;; +esac + # If we find X, set shell vars x_includes and x_libraries to the @@ -3908,7 +4102,7 @@ fi # Uses ac_ vars as temps to allow command line to override cache and checks. # --without-x overrides everything else, but does not touch the cache. echo $ac_n "checking for X""... $ac_c" 1>&6 -echo "configure:3912: checking for X" >&5 +echo "configure:4106: checking for X" >&5 # Check whether --with-x or --without-x was given. if test "${with_x+set}" = set; then @@ -3970,13 +4164,13 @@ if test "$ac_x_includes" = NO; then # First, try using that file with no special directory specified. cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3979: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` +{ (eval echo configure:4173: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* # We can compile using X headers with no special include directory. @@ -4044,14 +4238,14 @@ if test "$ac_x_libraries" = NO; then ac_save_LIBS="$LIBS" LIBS="-l$x_direct_test_library $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:4249: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* LIBS="$ac_save_LIBS" # We can link X programs with no special library path. @@ -4146,11 +4340,779 @@ if test "${with_sim_gpu2+set}" = set; then if test -d "${withval}" then SIM_SUBTARGET="${SIM_SUBTARGET} -DSKY_GPU2 -I${withval}/include" - mips_extra_libs="-L${withval}/lib -lgpu2 -L${x_libraries} -lX11" + mips_extra_libs="-L${withval}/lib -lgpu2 -L${x_libraries} -lX11 -lXext" + WITH_GPU2="yes" ; export WITH_GPU2 + + # complex X/etc. detection; stolen shamelessly from tcl/tk/gdb configury. --angela + + #-------------------------------------------------------------------- + # Locate the X11 header files and the X11 library archive. Try + # the ac_path_x macro first, but if it doesn't find the X stuff + # (e.g. because there's no xmkmf program) then check through + # a list of possible directories. Under some conditions the + # autoconf macro will return an include directory that contains + # no include files, so double-check its result just to be safe. + #-------------------------------------------------------------------- + + # If we find X, set shell vars x_includes and x_libraries to the +# paths, otherwise set no_x=yes. +# Uses ac_ vars as temps to allow command line to override cache and checks. +# --without-x overrides everything else, but does not touch the cache. +echo $ac_n "checking for X""... $ac_c" 1>&6 +echo "configure:4363: checking for X" >&5 + +# Check whether --with-x or --without-x was given. +if test "${with_x+set}" = set; then + withval="$with_x" + : +fi + +# $have_x is `yes', `no', `disabled', or empty when we do not yet know. +if test "x$with_x" = xno; then + # The user explicitly disabled X. + have_x=disabled +else + if test "x$x_includes" != xNONE && test "x$x_libraries" != xNONE; then + # Both variables are already set. + have_x=yes + else +if eval "test \"`echo '$''{'ac_cv_have_x'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + # One or both of the vars are not set, and there is no cached value. +ac_x_includes=NO ac_x_libraries=NO +rm -fr conftestdir +if mkdir conftestdir; then + cd conftestdir + # Make sure to not put "make" in the Imakefile rules, since we grep it out. + cat > Imakefile <<'EOF' +acfindx: + @echo 'ac_im_incroot="${INCROOT}"; ac_im_usrlibdir="${USRLIBDIR}"; ac_im_libdir="${LIBDIR}"' +EOF + if (xmkmf) >/dev/null 2>/dev/null && test -f Makefile; then + # GNU make sometimes prints "make[1]: Entering...", which would confuse us. + eval `${MAKE-make} acfindx 2>/dev/null | grep -v make` + # Open Windows xmkmf reportedly sets LIBDIR instead of USRLIBDIR. + for ac_extension in a so sl; do + if test ! -f $ac_im_usrlibdir/libX11.$ac_extension && + test -f $ac_im_libdir/libX11.$ac_extension; then + ac_im_usrlibdir=$ac_im_libdir; break + fi + done + # Screen out bogus values from the imake configuration. They are + # bogus both because they are the default anyway, and because + # using them would break gcc on systems where it needs fixed includes. + case "$ac_im_incroot" in + /usr/include) ;; + *) test -f "$ac_im_incroot/X11/Xos.h" && ac_x_includes="$ac_im_incroot" ;; + esac + case "$ac_im_usrlibdir" in + /usr/lib | /lib) ;; + *) test -d "$ac_im_usrlibdir" && ac_x_libraries="$ac_im_usrlibdir" ;; + esac + fi + cd .. + rm -fr conftestdir +fi + +if test "$ac_x_includes" = NO; then + # Guess where to find include files, by looking for this one X11 .h file. + test -z "$x_direct_test_include" && x_direct_test_include=X11/Intrinsic.h + + # First, try using that file with no special directory specified. +cat > conftest.$ac_ext < +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:4430: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` +if test -z "$ac_err"; then + rm -rf conftest* + # We can compile using X headers with no special include directory. +ac_x_includes= +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + # Look for the header file in a standard set of common directories. +# Check X11 before X11Rn because it is often a symlink to the current release. + for ac_dir in \ + /usr/X11/include \ + /usr/X11R6/include \ + /usr/X11R5/include \ + /usr/X11R4/include \ + \ + /usr/include/X11 \ + /usr/include/X11R6 \ + /usr/include/X11R5 \ + /usr/include/X11R4 \ + \ + /usr/local/X11/include \ + /usr/local/X11R6/include \ + /usr/local/X11R5/include \ + /usr/local/X11R4/include \ + \ + /usr/local/include/X11 \ + /usr/local/include/X11R6 \ + /usr/local/include/X11R5 \ + /usr/local/include/X11R4 \ + \ + /usr/X386/include \ + /usr/x386/include \ + /usr/XFree86/include/X11 \ + \ + /usr/include \ + /usr/local/include \ + /usr/unsupported/include \ + /usr/athena/include \ + /usr/local/x11r5/include \ + /usr/lpp/Xamples/include \ + \ + /usr/openwin/include \ + /usr/openwin/share/include \ + ; \ + do + if test -r "$ac_dir/$x_direct_test_include"; then + ac_x_includes=$ac_dir + break + fi + done +fi +rm -f conftest* +fi # $ac_x_includes = NO + +if test "$ac_x_libraries" = NO; then + # Check for the libraries. + + test -z "$x_direct_test_library" && x_direct_test_library=Xt + test -z "$x_direct_test_function" && x_direct_test_function=XtMalloc + + # See if we find them without any special options. + # Don't add to $LIBS permanently. + ac_save_LIBS="$LIBS" + LIBS="-l$x_direct_test_library $LIBS" +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + LIBS="$ac_save_LIBS" +# We can link X programs with no special library path. +ac_x_libraries= +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + LIBS="$ac_save_LIBS" +# First see if replacing the include by lib works. +# Check X11 before X11Rn because it is often a symlink to the current release. +for ac_dir in `echo "$ac_x_includes" | sed s/include/lib/` \ + /usr/X11/lib \ + /usr/X11R6/lib \ + /usr/X11R5/lib \ + /usr/X11R4/lib \ + \ + /usr/lib/X11 \ + /usr/lib/X11R6 \ + /usr/lib/X11R5 \ + /usr/lib/X11R4 \ + \ + /usr/local/X11/lib \ + /usr/local/X11R6/lib \ + /usr/local/X11R5/lib \ + /usr/local/X11R4/lib \ + \ + /usr/local/lib/X11 \ + /usr/local/lib/X11R6 \ + /usr/local/lib/X11R5 \ + /usr/local/lib/X11R4 \ + \ + /usr/X386/lib \ + /usr/x386/lib \ + /usr/XFree86/lib/X11 \ + \ + /usr/lib \ + /usr/local/lib \ + /usr/unsupported/lib \ + /usr/athena/lib \ + /usr/local/x11r5/lib \ + /usr/lpp/Xamples/lib \ + /lib/usr/lib/X11 \ + \ + /usr/openwin/lib \ + /usr/openwin/share/lib \ + ; \ +do + for ac_extension in a so sl; do + if test -r $ac_dir/lib${x_direct_test_library}.$ac_extension; then + ac_x_libraries=$ac_dir + break 2 + fi + done +done +fi +rm -f conftest* +fi # $ac_x_libraries = NO + +if test "$ac_x_includes" = NO || test "$ac_x_libraries" = NO; then + # Didn't find X anywhere. Cache the known absence of X. + ac_cv_have_x="have_x=no" +else + # Record where we found X for the cache. + ac_cv_have_x="have_x=yes \ + ac_x_includes=$ac_x_includes ac_x_libraries=$ac_x_libraries" +fi +fi + fi + eval "$ac_cv_have_x" +fi # $with_x != no + +if test "$have_x" != yes; then + echo "$ac_t""$have_x" 1>&6 + no_x=yes +else + # If each of the values was on the command line, it overrides each guess. + test "x$x_includes" = xNONE && x_includes=$ac_x_includes + test "x$x_libraries" = xNONE && x_libraries=$ac_x_libraries + # Update the cache value to reflect the command line values. + ac_cv_have_x="have_x=yes \ + ac_x_includes=$x_includes ac_x_libraries=$x_libraries" + echo "$ac_t""libraries $x_libraries, headers $x_includes" 1>&6 +fi + + not_really_there="" + if test "$no_x" = ""; then + if test "$x_includes" = ""; then + cat > conftest.$ac_ext < +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:4601: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` +if test -z "$ac_err"; then + : +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + not_really_there="yes" +fi +rm -f conftest* + else + if test ! -r $x_includes/X11/Intrinsic.h; then + not_really_there="yes" + fi + fi + fi + if test "$no_x" = "yes" -o "$not_really_there" = "yes"; then + echo $ac_n "checking for X11 header files""... $ac_c" 1>&6 +echo "configure:4621: checking for X11 header files" >&5 + XINCLUDES="# no special path needed" + cat > conftest.$ac_ext < +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:4629: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` +if test -z "$ac_err"; then + : +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + XINCLUDES="nope" +fi +rm -f conftest* + if test "$XINCLUDES" = nope; then + dirs="/usr/unsupported/include /usr/local/include /usr/X386/include /usr/X11R6/include /usr/X11R5/include /usr/include/X11R5 /usr/include/X11R4 /usr/openwin/include /usr/X11/include /usr/sww/include" + for i in $dirs ; do + if test -r $i/X11/Intrinsic.h; then + echo "$ac_t""$i" 1>&6 + XINCLUDES=" -I$i" + break + fi + done + fi + else + if test "$x_includes" != ""; then + XINCLUDES=-I$x_includes + else + XINCLUDES="# no special path needed" + fi + fi + if test "$XINCLUDES" = nope; then + echo "$ac_t""couldn't find any!" 1>&6 + XINCLUDES="# no include files found" + fi + + if test "$no_x" = yes; then + echo $ac_n "checking for X11 libraries""... $ac_c" 1>&6 +echo "configure:4665: checking for X11 libraries" >&5 + XLIBSW=nope + dirs="/usr/unsupported/lib /usr/local/lib /usr/X386/lib /usr/X11R6/lib /usr/X11R5/lib /usr/lib/X11R5 /usr/lib/X11R4 /usr/lib/X11 /usr/openwin/lib /usr/X11/lib /usr/sww/X11/lib" + for i in $dirs ; do + if test -r $i/libX11.a -o -r $i/libX11.so -o -r $i/libX11.sl; then + echo "$ac_t""$i" 1>&6 + XLIBSW="-L$i -lX11" + x_libraries="$i" + break + fi + done + else + if test "$x_libraries" = ""; then + XLIBSW=-lX11 + else + XLIBSW="-L$x_libraries -lX11" + fi + fi + if test "$XLIBSW" = nope ; then + echo $ac_n "checking for XCreateWindow in -lXwindow""... $ac_c" 1>&6 +echo "configure:4685: checking for XCreateWindow in -lXwindow" >&5 +ac_lib_var=`echo Xwindow'_'XCreateWindow | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_save_LIBS="$LIBS" +LIBS="-lXwindow $LIBS" +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=no" +fi +rm -f conftest* +LIBS="$ac_save_LIBS" + +fi +if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then + echo "$ac_t""yes" 1>&6 + XLIBSW=-lXwindow +else + echo "$ac_t""no" 1>&6 +fi + + fi + if test "$XLIBSW" = nope ; then + echo "$ac_t""couldn't find any! Using -lX11." 1>&6 + XLIBSW=-lX11 + fi + + #-------------------------------------------------------------------- + # Various manipulations on the search path used at runtime to + # find shared libraries: + # 1. If the X library binaries are in a non-standard directory, + # add the X library location into that search path. + # 2. On systems such as AIX and Ultrix that use "-L" as the + # search path option, colons cannot be used to separate + # directories from each other. Change colons to " -L". + # 3. Create two sets of search flags, one for use in cc lines + # and the other for when the linker is invoked directly. In + # the second case, '-Wl,' must be stripped off and commas must + # be replaced by spaces. + #-------------------------------------------------------------------- + + # + # CYGNUS LOCAL: statically link on Solaris, HPUX & SunOS so that + # we don't have problems with people not having libraries + # installed or not having LD_LIBRARY_PATH set. + # + + case "$host" in + # + # gdb linked statically w/ Solaris iff GCC and GNU ld are used, + # otherwise dynamic + # + sparc-sun-solaris2*) + sol_xlibsw= + if test "x$GCC" = "xyes" ; then + # This is probably the simplest way to test for GNU ld. + # It only works with relatively recent versions of GNU + # ld. + gld_text=`$CC -Wl,--version 2>&1 | sed 1q` + case "$gld_text" in + GNU* | *BFD*) + # Why do we link against libX11 twice? Because the + # Openwin X11 and Xext libraries are seriously broken. + sol_xlibsw="-Wl,-Bstatic $XLIBSW -lXext -lX11 -Wl,-Bdynamic" + ;; + esac + fi + if test -z "$sol_xlibsw"; then + if test "x$x_libraries" != "x"; then + XLIBSW="$XLIBSW -R$x_libraries" + fi + else + XLIBSW=$sol_xlibsw + suppress_enable_shared=yes + fi + ;; + # + # gdb linked statically w/ SunOS or HPUX + # + m68k-hp-hpux*|hppa*-hp-hpux*|sparc-sun-sunos*) + if test "x$x_libraries" != "x" ; + then + XLIBSW="$x_libraries/libX11.a" + else + XLIBSW="/usr/lib/libX11.a" + fi + suppress_enable_shared=yes + ;; + # + # default is to link dynamically + # + *) + ;; + esac + # + # END CYGNUS LOCAL + + + #-------------------------------------------------------------------- + # Check for the existence of various libraries. The order here + # is important, so that then end up in the right order in the + # command line generated by make. The -lsocket and -lnsl libraries + # require a couple of special tricks: + # 1. Use "connect" and "accept" to check for -lsocket, and + # "gethostbyname" to check for -lnsl. + # 2. Use each function name only once: can't redo a check because + # autoconf caches the results of the last check and won't redo it. + # 3. Use -lnsl and -lsocket only if they supply procedures that + # aren't already present in the normal libraries. This is because + # IRIX 5.2 has libraries, but they aren't needed and they're + # bogus: they goof up name resolution if used. + # 4. On some SVR4 systems, can't use -lsocket without -lnsl too. + # To get around this problem, check for both libraries together + # if -lsocket doesn't work by itself. + #-------------------------------------------------------------------- + + echo $ac_n "checking for main in -lXbsd""... $ac_c" 1>&6 +echo "configure:4820: checking for main in -lXbsd" >&5 +ac_lib_var=`echo Xbsd'_'main | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_save_LIBS="$LIBS" +LIBS="-lXbsd $LIBS" +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=no" +fi +rm -f conftest* +LIBS="$ac_save_LIBS" + +fi +if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then + echo "$ac_t""yes" 1>&6 + SOCKLIBSW="$SOCKLIBSW -lXbsd" +else + echo "$ac_t""no" 1>&6 +fi + + + # CYGNUS LOCAL: Store any socket library(ies) in the cache, and don't + # mess up the cache values of the functions we check for. + echo $ac_n "checking for socket libraries""... $ac_c" 1>&6 +echo "configure:4859: checking for socket libraries" >&5 +if eval "test \"`echo '$''{'sim_cv_lib_sockets'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + sim_cv_lib_sockets= + sim_checkBoth=0 + unset ac_cv_func_connect + echo $ac_n "checking for connect""... $ac_c" 1>&6 +echo "configure:4867: checking for connect" >&5 +if eval "test \"`echo '$''{'ac_cv_func_connect'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +/* Override any gcc2 internal prototype to avoid an error. */ +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char connect(); + +int main() { + +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_connect) || defined (__stub___connect) +choke me +#else +connect(); +#endif + +; return 0; } +EOF +if { (eval echo configure:4895: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_func_connect=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_func_connect=no" +fi +rm -f conftest* +fi + +if eval "test \"`echo '$ac_cv_func_'connect`\" = yes"; then + echo "$ac_t""yes" 1>&6 + sim_checkSocket=0 +else + echo "$ac_t""no" 1>&6 +sim_checkSocket=1 +fi + + if test "$sim_checkSocket" = 1; then + unset ac_cv_func_connect + echo $ac_n "checking for main in -lsocket""... $ac_c" 1>&6 +echo "configure:4918: checking for main in -lsocket" >&5 +ac_lib_var=`echo socket'_'main | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_save_LIBS="$LIBS" +LIBS="-lsocket $LIBS" +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=no" +fi +rm -f conftest* +LIBS="$ac_save_LIBS" + +fi +if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then + echo "$ac_t""yes" 1>&6 + sim_cv_lib_sockets="-lsocket" +else + echo "$ac_t""no" 1>&6 +sim_checkBoth=1 +fi + + fi + if test "$sim_checkBoth" = 1; then + sim_oldLibs=$SOCKLIBSW + SOCKLIBSW="$SOCKLIBSW -lsocket -lnsl" + unset ac_cv_func_accept + echo $ac_n "checking for accept""... $ac_c" 1>&6 +echo "configure:4960: checking for accept" >&5 +if eval "test \"`echo '$''{'ac_cv_func_accept'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +/* Override any gcc2 internal prototype to avoid an error. */ +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char accept(); + +int main() { + +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_accept) || defined (__stub___accept) +choke me +#else +accept(); +#endif + +; return 0; } +EOF +if { (eval echo configure:4988: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_func_accept=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_func_accept=no" +fi +rm -f conftest* +fi + +if eval "test \"`echo '$ac_cv_func_'accept`\" = yes"; then + echo "$ac_t""yes" 1>&6 + sim_checkNsl=0 + sim_cv_lib_sockets="-lsocket -lnsl" +else + echo "$ac_t""no" 1>&6 +fi + + unset ac_cv_func_accept + SOCKLIBSW=$sim_oldLibs + fi + unset ac_cv_func_gethostbyname + sim_oldLibs=$SOCKLIBSW + SOCKLIBSW="$SOCKLIBSW $sim_cv_lib_sockets" + echo $ac_n "checking for gethostbyname""... $ac_c" 1>&6 +echo "configure:5015: checking for gethostbyname" >&5 +if eval "test \"`echo '$''{'ac_cv_func_gethostbyname'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +/* Override any gcc2 internal prototype to avoid an error. */ +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char gethostbyname(); + +int main() { + +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_gethostbyname) || defined (__stub___gethostbyname) +choke me +#else +gethostbyname(); +#endif + +; return 0; } +EOF +if { (eval echo configure:5043: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_func_gethostbyname=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_func_gethostbyname=no" +fi +rm -f conftest* +fi + +if eval "test \"`echo '$ac_cv_func_'gethostbyname`\" = yes"; then + echo "$ac_t""yes" 1>&6 + : +else + echo "$ac_t""no" 1>&6 +echo $ac_n "checking for main in -lnsl""... $ac_c" 1>&6 +echo "configure:5061: checking for main in -lnsl" >&5 +ac_lib_var=`echo nsl'_'main | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_save_LIBS="$LIBS" +LIBS="-lnsl $LIBS" +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=no" +fi +rm -f conftest* +LIBS="$ac_save_LIBS" + +fi +if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then + echo "$ac_t""yes" 1>&6 + sim_cv_lib_sockets="$sim_cv_lib_sockets -lnsl" +else + echo "$ac_t""no" 1>&6 +fi + +fi + + unset ac_cv_func_gethostbyname + SOCKLIBSW=$sim_oldSOCKLIBSW + +fi + +echo "$ac_t""$sim_cv_lib_sockets" 1>&6 + test -z "$sim_cv_lib_sockets" || SOCKLIBSW="$SOCKLIBSW $sim_cv_lib_sockets" + + mips_extra_libs="-L${withval}/lib -lgpu2 -lm $XLIBSW $SOCKLIBSW" + cat > simConfig.sh << --EOF-- +mips_extra_libs="$mips_extra_libs" +--EOF-- + else { echo "configure: error: "Directory ${withval} does not exist."" 1>&2; exit 1; }; fi fi + + # Enable target accurate FP library # Check whether --with-sim-funit or --without-sim-funit was given. if test "${with_sim_funit+set}" = set; then @@ -4170,18 +5132,18 @@ for ac_hdr in string.h strings.h stdlib.h stdlib.h do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:4174: checking for $ac_hdr" >&5 +echo "configure:5136: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:4184: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } -ac_err=`grep -v '^ *+' conftest.out` +{ (eval echo configure:5146: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* eval "ac_cv_header_$ac_safe=yes" @@ -4207,7 +5169,7 @@ fi done echo $ac_n "checking for fabs in -lm""... $ac_c" 1>&6 -echo "configure:4211: checking for fabs in -lm" >&5 +echo "configure:5173: checking for fabs in -lm" >&5 ac_lib_var=`echo m'_'fabs | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -4215,7 +5177,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lm $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:5192: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -4256,12 +5218,12 @@ fi for ac_func in aint anint sqrt do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:4260: checking for $ac_func" >&5 +echo "configure:5222: checking for $ac_func" >&5 if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then +if { (eval echo configure:5250: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -4401,7 +5363,7 @@ do echo "running \${CONFIG_SHELL-/bin/sh} $0 $ac_configure_args --no-create --no-recursion" exec \${CONFIG_SHELL-/bin/sh} $0 $ac_configure_args --no-create --no-recursion ;; -version | --version | --versio | --versi | --vers | --ver | --ve | --v) - echo "$CONFIG_STATUS generated by autoconf version 2.12.1" + echo "$CONFIG_STATUS generated by autoconf version 2.12.2" exit 0 ;; -help | --help | --hel | --he | --h) echo "\$ac_cs_usage"; exit 0 ;; @@ -4522,6 +5484,7 @@ s%@sim_igen_flags@%$sim_igen_flags%g s%@sim_m16_flags@%$sim_m16_flags%g s%@sim_gen@%$sim_gen%g s%@mips_extra_objs@%$mips_extra_objs%g +s%@mips_igen_engine@%$mips_igen_engine%g s%@mips_extra_libs@%$mips_extra_libs%g CEOF diff --git a/sim/mips/configure.in b/sim/mips/configure.in index 6ceb6ef151..68d68739af 100644 --- a/sim/mips/configure.in +++ b/sim/mips/configure.in @@ -59,6 +59,7 @@ case "${target}" in # start-sanitize-r5900 mips64r59*-*-*) mips_endian=LITTLE_ENDIAN ;; # end-sanitize-r5900 + mips64el*-*-*) mips_endian=LITTLE_ENDIAN ;; mips64*-*-*) default_endian=BIG_ENDIAN ;; mips16*-*-*) default_endian=BIG_ENDIAN ;; mips*-*-*) default_endian=BIG_ENDIAN ;; @@ -79,6 +80,9 @@ case "${target}" in # start-sanitize-r5900 mips64r59*-*-*) mips_bitsize=64 ; mips_msb=63 ; mips_addr_bitsize=32;; # end-sanitize-r5900 +# start-sanitize-sky + mips64*-sky*-*) mips_bitsize=64 ; mips_msb=63 ; mips_addr_bitsize=32;; +# end-sanitize-sky mips64*-*-*) mips_bitsize=64 ; mips_msb=63 ;; mips16*-*-*) mips_bitsize=64 ; mips_msb=63 ;; mips*-*-*) mips_bitsize=32 ; mips_msb=31 ;; @@ -103,6 +107,9 @@ case "${target}" in # start-sanitize-r5900 mips64r59*-*-*) mips_fpu=HARD_FLOATING_POINT ; mips_fpu_bitsize=32 ;; # end-sanitize-r5900 +# start-sanitize-sky + mips64*-sky*-*) mips_fpu=HARD_FLOATING_POINT ; mips_fpu_bitsize=32 ;; +# end-sanitize-sky mips64*-*-*) mips_fpu=HARD_FLOATING_POINT ;; mips16*-*-*) mips_fpu=HARD_FLOATING_POINT ;; mips*-*-*) mips_fpu=HARD_FLOATING_POINT ; mips_fpu_bitsize=32 ;; @@ -242,9 +249,13 @@ case "${target}" in # end-sanitize-tx3904 # start-sanitize-sky mips64r59*-sky-*) - mips_extra_objs="$mips_extra_objs "'$(SIM_SKY_OBJS)' + mips_extra_objs='$(SIM_SKY_OBJS)' SIM_SUBTARGET="-DTARGET_SKY -DWITH_DEVICES=1 -DDEVICE_INIT=1" ;; + mips64*-skyb-*) + mips_extra_objs='$(SIM_SKY_OBJS)' + SIM_SUBTARGET="-DTARGET_SKY -DTARGET_SKY_B -DWITH_DEVICES=1 -DDEVICE_INIT=1" + ;; # end-sanitize-sky *) mips_extra_objs="" @@ -254,6 +265,22 @@ SIM_AC_OPTION_HARDWARE($hw_enabled,$hw_devices,$hw_extra_devices) AC_SUBST(mips_extra_objs) +# Choose simulator engine +case "${target}" in +# start-sanitize-sky + mips64r59*-sky-*) + mips_igen_engine="" + ;; + mips64*-skyb-*) + mips_igen_engine="" + ;; +# end-sanitize-sky + *) mips_igen_engine="engine.o" + ;; +esac +AC_SUBST(mips_igen_engine) + + AC_PATH_X mips_extra_libs="" # start-sanitize-sky @@ -264,9 +291,217 @@ AC_ARG_WITH(sim-gpu2, then SIM_SUBTARGET="${SIM_SUBTARGET} -DSKY_GPU2 -I${withval}/include" mips_extra_libs="-L${withval}/lib -lgpu2 -L${x_libraries} -lX11 -lXext" + WITH_GPU2="yes" ; export WITH_GPU2 + + # complex X/etc. detection; stolen shamelessly from tcl/tk/gdb configury. --angela + + #-------------------------------------------------------------------- + # Locate the X11 header files and the X11 library archive. Try + # the ac_path_x macro first, but if it doesn't find the X stuff + # (e.g. because there's no xmkmf program) then check through + # a list of possible directories. Under some conditions the + # autoconf macro will return an include directory that contains + # no include files, so double-check its result just to be safe. + #-------------------------------------------------------------------- + + AC_PATH_X + not_really_there="" + if test "$no_x" = ""; then + if test "$x_includes" = ""; then + AC_TRY_CPP([#include ], , not_really_there="yes") + else + if test ! -r $x_includes/X11/Intrinsic.h; then + not_really_there="yes" + fi + fi + fi + if test "$no_x" = "yes" -o "$not_really_there" = "yes"; then + AC_MSG_CHECKING(for X11 header files) + XINCLUDES="# no special path needed" + AC_TRY_CPP([#include ], , XINCLUDES="nope") + if test "$XINCLUDES" = nope; then + dirs="/usr/unsupported/include /usr/local/include /usr/X386/include /usr/X11R6/include /usr/X11R5/include /usr/include/X11R5 /usr/include/X11R4 /usr/openwin/include /usr/X11/include /usr/sww/include" + for i in $dirs ; do + if test -r $i/X11/Intrinsic.h; then + AC_MSG_RESULT($i) + XINCLUDES=" -I$i" + break + fi + done + fi + else + if test "$x_includes" != ""; then + XINCLUDES=-I$x_includes + else + XINCLUDES="# no special path needed" + fi + fi + if test "$XINCLUDES" = nope; then + AC_MSG_RESULT(couldn't find any!) + XINCLUDES="# no include files found" + fi + + if test "$no_x" = yes; then + AC_MSG_CHECKING(for X11 libraries) + XLIBSW=nope + dirs="/usr/unsupported/lib /usr/local/lib /usr/X386/lib /usr/X11R6/lib /usr/X11R5/lib /usr/lib/X11R5 /usr/lib/X11R4 /usr/lib/X11 /usr/openwin/lib /usr/X11/lib /usr/sww/X11/lib" + for i in $dirs ; do + if test -r $i/libX11.a -o -r $i/libX11.so -o -r $i/libX11.sl; then + AC_MSG_RESULT($i) + XLIBSW="-L$i -lX11" + x_libraries="$i" + break + fi + done + else + if test "$x_libraries" = ""; then + XLIBSW=-lX11 + else + XLIBSW="-L$x_libraries -lX11" + fi + fi + if test "$XLIBSW" = nope ; then + AC_CHECK_LIB(Xwindow, XCreateWindow, XLIBSW=-lXwindow) + fi + if test "$XLIBSW" = nope ; then + AC_MSG_RESULT(couldn't find any! Using -lX11.) + XLIBSW=-lX11 + fi + + #-------------------------------------------------------------------- + # Various manipulations on the search path used at runtime to + # find shared libraries: + # 1. If the X library binaries are in a non-standard directory, + # add the X library location into that search path. + # 2. On systems such as AIX and Ultrix that use "-L" as the + # search path option, colons cannot be used to separate + # directories from each other. Change colons to " -L". + # 3. Create two sets of search flags, one for use in cc lines + # and the other for when the linker is invoked directly. In + # the second case, '-Wl,' must be stripped off and commas must + # be replaced by spaces. + #-------------------------------------------------------------------- + + # + # CYGNUS LOCAL: statically link on Solaris, HPUX & SunOS so that + # we don't have problems with people not having libraries + # installed or not having LD_LIBRARY_PATH set. + # + + case "$host" in + # + # gdb linked statically w/ Solaris iff GCC and GNU ld are used, + # otherwise dynamic + # + sparc-sun-solaris2*) + sol_xlibsw= + if test "x$GCC" = "xyes" ; then + # This is probably the simplest way to test for GNU ld. + # It only works with relatively recent versions of GNU + # ld. + gld_text=`$CC -Wl,--version 2>&1 | sed 1q` + case "$gld_text" in + GNU* | *BFD*) + # Why do we link against libX11 twice? Because the + # Openwin X11 and Xext libraries are seriously broken. + sol_xlibsw="-Wl,-Bstatic $XLIBSW -lXext -lX11 -Wl,-Bdynamic" + ;; + esac + fi + if test -z "$sol_xlibsw"; then + if test "x$x_libraries" != "x"; then + XLIBSW="$XLIBSW -R$x_libraries" + fi + else + XLIBSW=$sol_xlibsw + suppress_enable_shared=yes + fi + ;; + # + # gdb linked statically w/ SunOS or HPUX + # + m68k-hp-hpux*|hppa*-hp-hpux*|sparc-sun-sunos*) + if test "x$x_libraries" != "x" ; + then + XLIBSW="$x_libraries/libX11.a" + else + XLIBSW="/usr/lib/libX11.a" + fi + suppress_enable_shared=yes + ;; + # + # default is to link dynamically + # + *) + ;; + esac + # + # END CYGNUS LOCAL + + + #-------------------------------------------------------------------- + # Check for the existence of various libraries. The order here + # is important, so that then end up in the right order in the + # command line generated by make. The -lsocket and -lnsl libraries + # require a couple of special tricks: + # 1. Use "connect" and "accept" to check for -lsocket, and + # "gethostbyname" to check for -lnsl. + # 2. Use each function name only once: can't redo a check because + # autoconf caches the results of the last check and won't redo it. + # 3. Use -lnsl and -lsocket only if they supply procedures that + # aren't already present in the normal libraries. This is because + # IRIX 5.2 has libraries, but they aren't needed and they're + # bogus: they goof up name resolution if used. + # 4. On some SVR4 systems, can't use -lsocket without -lnsl too. + # To get around this problem, check for both libraries together + # if -lsocket doesn't work by itself. + #-------------------------------------------------------------------- + + AC_CHECK_LIB(Xbsd, main, [SOCKLIBSW="$SOCKLIBSW -lXbsd"]) + + # CYGNUS LOCAL: Store any socket library(ies) in the cache, and don't + # mess up the cache values of the functions we check for. + AC_CACHE_CHECK([for socket libraries], sim_cv_lib_sockets, + [sim_cv_lib_sockets= + sim_checkBoth=0 + unset ac_cv_func_connect + AC_CHECK_FUNC(connect, sim_checkSocket=0, sim_checkSocket=1) + if test "$sim_checkSocket" = 1; then + unset ac_cv_func_connect + AC_CHECK_LIB(socket, main, sim_cv_lib_sockets="-lsocket", + sim_checkBoth=1) + fi + if test "$sim_checkBoth" = 1; then + sim_oldLibs=$SOCKLIBSW + SOCKLIBSW="$SOCKLIBSW -lsocket -lnsl" + unset ac_cv_func_accept + AC_CHECK_FUNC(accept, + [sim_checkNsl=0 + sim_cv_lib_sockets="-lsocket -lnsl"]) + unset ac_cv_func_accept + SOCKLIBSW=$sim_oldLibs + fi + unset ac_cv_func_gethostbyname + sim_oldLibs=$SOCKLIBSW + SOCKLIBSW="$SOCKLIBSW $sim_cv_lib_sockets" + AC_CHECK_FUNC(gethostbyname, , + [AC_CHECK_LIB(nsl, main, + [sim_cv_lib_sockets="$sim_cv_lib_sockets -lnsl"])]) + unset ac_cv_func_gethostbyname + SOCKLIBSW=$sim_oldSOCKLIBSW + ]) + test -z "$sim_cv_lib_sockets" || SOCKLIBSW="$SOCKLIBSW $sim_cv_lib_sockets" + + mips_extra_libs="-L${withval}/lib -lgpu2 -lm $XLIBSW $SOCKLIBSW" + cat > simConfig.sh << --EOF-- +mips_extra_libs="$mips_extra_libs" +--EOF-- + else AC_MSG_ERROR("Directory ${withval} does not exist."); fi])dnl + + # Enable target accurate FP library AC_ARG_WITH(sim-funit, [ --with-sim-funit=path Use target FP library under given directory], diff --git a/sim/mips/interp.c b/sim/mips/interp.c index 4c9747dc3e..ba3d6e51f2 100644 --- a/sim/mips/interp.c +++ b/sim/mips/interp.c @@ -39,12 +39,16 @@ code on the hardware. #include "sim-assert.h" #include "sim-hw.h" +#if WITH_IGEN +#include "itable.h" +#endif + /* start-sanitize-sky */ #ifdef TARGET_SKY #include "sky-vu.h" #include "sky-vpe.h" #include "sky-libvpe.h" -#include "sky-pke.h" +#include "sky-vif.h" #include "idecode.h" #include "sky-gdb.h" #endif @@ -159,6 +163,8 @@ static void ColdReset PARAMS((SIM_DESC sd)); #ifdef TARGET_SKY #undef MEM_SIZE #define MEM_SIZE (16 << 20) /* 16 MB */ +#undef MONITOR_SIZE +#define MONITOR_SIZE 0x100000 /* 1MB */ #endif /* end-sanitize-sky */ @@ -168,6 +174,10 @@ FILE *tracefh = NULL; static void open_trace PARAMS((SIM_DESC sd)); #endif /* TRACE */ +#if WITH_IGEN +static const char * get_insn_name (sim_cpu *, int); +#endif + /* simulation target board. NULL=canonical */ static char* board = NULL; @@ -329,7 +339,7 @@ interrupt_event (SIM_DESC sd, void *data) if (SR & status_IE) { interrupt_pending = 0; - SignalExceptionInterrupt (); + SignalExceptionInterrupt (1); /* interrupt "1" */ } else if (!interrupt_pending) sim_events_schedule (sd, 1, interrupt_event, data); @@ -367,6 +377,12 @@ sim_open (kind, cb, abfd, argv) STATE_WATCHPOINTS (sd)->sizeof_pc = sizeof (PC); STATE_WATCHPOINTS (sd)->interrupt_handler = interrupt_event; +#if WITH_IGEN + /* Initialize the mechanism for doing insn profiling. */ + CPU_INSN_NAME (cpu) = get_insn_name; + CPU_MAX_INSNS (cpu) = nr_itable_entries; +#endif + STATE = 0; if (sim_pre_argv_init (sd, argv[0]) != SIM_RC_OK) @@ -431,6 +447,10 @@ sim_open (kind, cb, abfd, argv) { /* match VIRTUAL memory layout of JMR-TX3904 board */ + /* --- environment --- */ + + STATE_ENVIRONMENT (sd) = OPERATING_ENVIRONMENT; + /* --- memory --- */ /* ROM: 0x9FC0_0000 - 0x9FFF_FFFF and 0xBFC0_0000 - 0xBFFF_FFFF */ @@ -451,18 +471,38 @@ sim_open (kind, cb, abfd, argv) 32 * 1024 * 1024, /* 32 MB */ 0xA8000000); + /* Dummy memory regions for unsimulated devices */ + + sim_do_commandf (sd, "memory alias 0x%lx@1,0x%lx", 0xFFFFE010, 0x00c); /* EBIF */ + sim_do_commandf (sd, "memory alias 0x%lx@1,0x%lx", 0xFFFF9000, 0x200); /* EBIF */ + sim_do_commandf (sd, "memory alias 0x%lx@1,0x%lx", 0xFFFFF500, 0x300); /* PIO */ + /* --- simulated devices --- */ sim_hw_parse (sd, "/tx3904irc@0xffffc000/reg 0xffffc000 0x20"); sim_hw_parse (sd, "/tx3904cpu"); sim_hw_parse (sd, "/tx3904tmr@0xfffff000/reg 0xfffff000 0x100"); sim_hw_parse (sd, "/tx3904tmr@0xfffff100/reg 0xfffff100 0x100"); sim_hw_parse (sd, "/tx3904tmr@0xfffff200/reg 0xfffff200 0x100"); - + sim_hw_parse (sd, "/tx3904sio@0xfffff300/reg 0xfffff300 0x100"); + { + /* FIXME: poking at dv-sockser internals, use tcp backend if + --sockser_addr option was given.*/ + extern char* sockser_addr; + if(sockser_addr == NULL) + sim_hw_parse (sd, "/tx3904sio@0xfffff300/backend stdio"); + else + sim_hw_parse (sd, "/tx3904sio@0xfffff300/backend tcp"); + } + sim_hw_parse (sd, "/tx3904sio@0xfffff400/reg 0xfffff400 0x100"); + sim_hw_parse (sd, "/tx3904sio@0xfffff400/backend stdio"); + /* -- device connections --- */ sim_hw_parse (sd, "/tx3904irc > ip level /tx3904cpu"); sim_hw_parse (sd, "/tx3904tmr@0xfffff000 > int tmr0 /tx3904irc"); sim_hw_parse (sd, "/tx3904tmr@0xfffff100 > int tmr1 /tx3904irc"); sim_hw_parse (sd, "/tx3904tmr@0xfffff200 > int tmr2 /tx3904irc"); + sim_hw_parse (sd, "/tx3904sio@0xfffff300 > int sio0 /tx3904irc"); + sim_hw_parse (sd, "/tx3904sio@0xfffff400 > int sio1 /tx3904irc"); /* add PAL timer & I/O module */ if(! strcmp(board, BOARD_JMR3904_PAL)) @@ -559,11 +599,14 @@ sim_open (kind, cb, abfd, argv) else cpu->register_widths[rn] = 0; } - /* start-sanitize-r5900 */ + /* start-sanitize-r5900 */ /* set the 5900 "upper" registers to 64 bits */ - for( rn = LAST_EMBED_REGNUM+1; rn < NUM_REGS; rn++) + for( rn = LAST_EMBED_REGNUM+1; rn < FIRST_COP0_REG; rn++) cpu->register_widths[rn] = 64; + + for( rn = FIRST_COP0_REG; rn < NUM_REGS; rn++) + cpu->register_widths[rn] = 32; /* end-sanitize-r5900 */ /* start-sanitize-sky */ @@ -601,8 +644,12 @@ sim_open (kind, cb, abfd, argv) HALT_INSTRUCTION /* BREAK */ }; H2T (halt[0]); H2T (halt[1]); + sim_write (sd, 0x80000000, (char *) halt, sizeof (halt)); sim_write (sd, 0x80000180, (char *) halt, sizeof (halt)); + sim_write (sd, 0x80000200, (char *) halt, sizeof (halt)); + sim_write (sd, 0xBFC00200, (char *) halt, sizeof (halt)); sim_write (sd, 0xBFC00380, (char *) halt, sizeof (halt)); + sim_write (sd, 0xBFC00400, (char *) halt, sizeof (halt)); } @@ -667,6 +714,31 @@ sim_open (kind, cb, abfd, argv) } } + + /* start-sanitize-sky */ +#ifdef TARGET_SKY + /* Default TLB initialization... */ + +#define KPAGEMASK 0x001fe000 +#define PAGE_MASK_4K 0x00000000 +#define PAGE_MASK_16K 0x00006000 +#define PAGE_MASK_64K 0x0001e000 +#define PAGE_MASK_256K 0x0007e000 +#define PAGE_MASK_1M 0x001fe000 +#define PAGE_MASK_4M 0x007fe000 +#define PAGE_MASK_16M 0x01ffe000 + +#define SET_TLB(index, page_mask, entry_hi, entry_lo0, entry_lo1) \ + TLB[index].mask = page_mask; \ + TLB[index].hi = entry_hi; \ + TLB[index].lo0 = entry_lo0; \ + TLB[index].lo1 = entry_lo1 + + SET_TLB(0, PAGE_MASK_16M, 0x00000000, 0x0000001e, 0x0004001e);/*0-32M*/ + +#endif /* TARGET_SKY */ + /* end-sanitize-sky */ + return sd; } @@ -684,6 +756,15 @@ open_trace(sd) } #endif /* TRACE */ +#if WITH_IGEN +/* Return name of an insn, used by insn profiling. */ +static const char * +get_insn_name (sim_cpu *cpu, int i) +{ + return itable[i].name; +} +#endif + void sim_close (sd, quitting) SIM_DESC sd; @@ -821,6 +902,38 @@ sim_store_register (sd,rn,memory,length) HI1 = T2H_8(*(unsigned64*)memory); return 8; } + + if (rn >= FIRST_COP0_REG && rn < (FIRST_COP0_REG+NUM_COP0_REGS)) + { + switch (rn - FIRST_COP0_REG) + { + case 12: /* Status */ + case 13: /* Cause */ + return -1; /* Already done in regular register set */ + case 14: + EPC = T2H_4(*((unsigned32*) memory)); + break; + case 16: + C0_CONFIG = T2H_4(*((unsigned32*) memory)); + break; + case 17: /* Debug */ + Debug = T2H_4(*((unsigned32*) memory)); + break; + case 18: /* Perf */ + COP0_GPR[rn - FIRST_COP0_REG + 7] = T2H_4(*((unsigned32*) memory)); + break; + case 19: /* TagLo */ + case 20: /* TagHi */ + case 21: /* ErrorEPC */ + COP0_GPR[rn - FIRST_COP0_REG + 9] = T2H_4(*((unsigned32*) memory)); + break; + default: + COP0_GPR[rn - FIRST_COP0_REG] = T2H_4(*((unsigned32*) memory)); + break; + } + + return 4; + } /* end-sanitize-r5900 */ /* start-sanitize-sky */ @@ -831,6 +944,10 @@ sim_store_register (sd,rn,memory,length) if( rn < NUM_VU_REGS ) { +#ifdef TARGET_SKY_B + sim_io_eprintf( sd, "Invalid VU register (register store ignored)\n" ); + return 0; +#else if (rn < NUM_VU_INTEGER_REGS) return write_vu_int_reg (&(vu0_device.regs), rn, memory); else if (rn >= FIRST_VEC_REG) @@ -842,24 +959,34 @@ sim_store_register (sd,rn,memory,length) else switch (rn - NUM_VU_INTEGER_REGS) { case 0: - return write_vu_special_reg (&vu0_device, VU_REG_CIA, - memory); - case 1: - return write_vu_misc_reg (&(vu0_device.regs), VU_REG_MR, - memory); - case 2: /* VU0 has no P register */ + return write_vu_special_reg (&vu0_device, VU_REG_CIA, memory); + + case 1: /* Can't write TPC register */ + case 2: /* or VPU_STAT */ + case 4: /* or MAC */ + case 9: /* VU0 has no P register */ return 4; + case 3: - return write_vu_misc_reg (&(vu0_device.regs), VU_REG_MI, - memory); - case 4: - return write_vu_misc_reg (&(vu0_device.regs), VU_REG_MQ, - memory); + return write_vu_misc_reg(&(vu0_device.regs), VU_REG_MST, memory); + case 5: + return write_vu_misc_reg(&(vu0_device.regs), VU_REG_MCP, memory); + case 6: + return write_vu_special_reg (&vu0_device, VU_REG_CMSAR0, memory); + case 7: + return write_vu_special_reg (&vu0_device, VU_REG_FBRST, memory); + case 8: + return write_vu_misc_reg (&(vu0_device.regs), VU_REG_MR, memory); + case 10: + return write_vu_misc_reg (&(vu0_device.regs), VU_REG_MI, memory); + case 11: + return write_vu_misc_reg (&(vu0_device.regs), VU_REG_MQ, memory); default: return write_vu_acc_reg (&(vu0_device.regs), - rn - (NUM_VU_INTEGER_REGS + 5), + rn - (NUM_VU_INTEGER_REGS + 12), memory); } +#endif /* ! TARGET_SKY_B */ } rn = rn - NUM_VU_REGS; @@ -877,23 +1004,35 @@ sim_store_register (sd,rn,memory,length) else switch (rn - NUM_VU_INTEGER_REGS) { case 0: - return write_vu_special_reg (&vu1_device, VU_REG_CIA, - memory); - case 1: - return write_vu_misc_reg (&(vu1_device.regs), VU_REG_MR, - memory); - case 2: - return write_vu_misc_reg (&(vu1_device.regs), VU_REG_MP, - memory); + return write_vu_special_reg (&vu1_device, VU_REG_CIA, memory); + + case 1: /* Can't write TPC register */ + case 2: /* or VPU_STAT */ + case 4: /* or MAC */ + case 7: /* VU1 has no FBRST register */ + return 4; + case 3: - return write_vu_misc_reg (&(vu1_device.regs), VU_REG_MI, - memory); - case 4: - return write_vu_misc_reg (&(vu1_device.regs), VU_REG_MQ, - memory); + return write_vu_misc_reg(&(vu1_device.regs), VU_REG_MST, memory); + case 5: + return write_vu_misc_reg(&(vu1_device.regs), VU_REG_MCP, memory); + case 6: /* CMSAR1 is actually part of VU0 */ +#ifdef TARGET_SKY_B + return 0; +#else + return write_vu_special_reg (&vu0_device, VU_REG_CMSAR1, memory); +#endif /* ! TARGET_SKY_B */ + case 8: + return write_vu_misc_reg (&(vu1_device.regs), VU_REG_MR, memory); + case 9: + return write_vu_misc_reg (&(vu1_device.regs), VU_REG_MP, memory); + case 10: + return write_vu_misc_reg (&(vu1_device.regs), VU_REG_MI, memory); + case 11: + return write_vu_misc_reg (&(vu1_device.regs), VU_REG_MQ, memory); default: return write_vu_acc_reg (&(vu1_device.regs), - rn - (NUM_VU_INTEGER_REGS + 5), + rn - (NUM_VU_INTEGER_REGS + 12), memory); } } @@ -902,13 +1041,18 @@ sim_store_register (sd,rn,memory,length) if (rn < NUM_VIF_REGS) { +#ifdef TARGET_SKY_B + sim_io_eprintf( sd, "Invalid VIF register (register store ignored)\n" ); + return 0; +#else if (rn < NUM_VIF_REGS-1) - return write_pke_reg (&pke0_device, rn, memory); + return write_vif_reg (&vif0_device, rn, memory); else { sim_io_eprintf( sd, "Can't write vif0_pc (store ignored)\n" ); return 0; } +#endif /* ! TARGET_SKY_B */ } rn -= NUM_VIF_REGS; /* VIF1 registers are last */ @@ -916,7 +1060,7 @@ sim_store_register (sd,rn,memory,length) if (rn < NUM_VIF_REGS) { if (rn < NUM_VIF_REGS-1) - return write_pke_reg (&pke1_device, rn, memory); + return write_vif_reg (&vif1_device, rn, memory); else { sim_io_eprintf( sd, "Can't write vif1_pc (store ignored)\n" ); @@ -996,6 +1140,38 @@ sim_fetch_register (sd,rn,memory,length) *((unsigned64*)memory) = H2T_8(HI1); return 8; } + + if (rn >= FIRST_COP0_REG && rn < (FIRST_COP0_REG+NUM_COP0_REGS)) + { + switch (rn - FIRST_COP0_REG) + { + case 12: /* Status */ + case 13: /* Cause */ + return -1; /* Already done in regular register set */ + case 14: + *((unsigned32*) memory) = H2T_4(EPC); + break; + case 16: + *((unsigned32*) memory) = H2T_4(C0_CONFIG); + break; + case 17: /* Debug */ + *((unsigned32*) memory) = H2T_4(Debug); + break; + case 18: /* Perf */ + *((unsigned32*) memory) = H2T_4(COP0_GPR[rn - FIRST_COP0_REG + 7]); + break; + case 19: /* TagLo */ + case 20: /* TagHi */ + case 21: /* ErrorEPC */ + *((unsigned32*) memory) = H2T_4(COP0_GPR[rn - FIRST_COP0_REG + 9]); + break; + default: + *((unsigned32*) memory) = H2T_4(COP0_GPR[rn - FIRST_COP0_REG]); + break; + } + + return 4; + } /* end-sanitize-r5900 */ /* start-sanitize-sky */ @@ -1006,6 +1182,10 @@ sim_fetch_register (sd,rn,memory,length) if (rn < NUM_VU_REGS) { +#ifdef TARGET_SKY_B + sim_io_eprintf( sd, "Invalid VU register (register fetch ignored)\n" ); + return 0; +#else if (rn < NUM_VU_INTEGER_REGS) return read_vu_int_reg (&(vu0_device.regs), rn, memory); else if (rn >= FIRST_VEC_REG) @@ -1017,24 +1197,36 @@ sim_fetch_register (sd,rn,memory,length) else switch (rn - NUM_VU_INTEGER_REGS) { case 0: - return read_vu_special_reg(&vu0_device, VU_REG_CIA, memory); + return read_vu_special_reg (&vu0_device, VU_REG_CIA, memory); case 1: - return read_vu_misc_reg (&(vu0_device.regs), VU_REG_MR, - memory); - case 2: /* VU0 has no P register */ + return read_vu_misc_reg(&(vu0_device.regs), VU_REG_MTPC, memory); + case 2: + return read_vu_special_reg (&vu0_device, VU_REG_STAT, memory); + case 3: + return read_vu_misc_reg (&(vu0_device.regs), VU_REG_MST, memory); + case 4: + return read_vu_misc_reg (&(vu0_device.regs), VU_REG_MMC, memory); + case 5: + return read_vu_misc_reg (&(vu0_device.regs), VU_REG_MCP, memory); + case 6: + return read_vu_special_reg (&vu0_device, VU_REG_CMSAR0, memory); + case 7: + return read_vu_special_reg (&vu0_device, VU_REG_FBRST, memory); + case 8: + return read_vu_misc_reg (&(vu0_device.regs), VU_REG_MR, memory); + case 9: /* VU0 has no P register */ *((int *) memory) = 0; return 4; - case 3: - return read_vu_misc_reg (&(vu0_device.regs), VU_REG_MI, - memory); - case 4: - return read_vu_misc_reg (&(vu0_device.regs), VU_REG_MQ, - memory); + case 10: + return read_vu_misc_reg (&(vu0_device.regs), VU_REG_MI, memory); + case 11: + return read_vu_misc_reg (&(vu0_device.regs), VU_REG_MQ, memory); default: return read_vu_acc_reg (&(vu0_device.regs), - rn - (NUM_VU_INTEGER_REGS + 5), + rn - (NUM_VU_INTEGER_REGS + 12), memory); } +#endif /* ! TARGET_SKY_B */ } rn -= NUM_VU_REGS; /* VU1 registers are next */ @@ -1052,22 +1244,37 @@ sim_fetch_register (sd,rn,memory,length) else switch (rn - NUM_VU_INTEGER_REGS) { case 0: - return read_vu_special_reg(&vu1_device, VU_REG_CIA, memory); + return read_vu_special_reg (&vu1_device, VU_REG_CIA, memory); case 1: - return read_vu_misc_reg (&(vu1_device.regs), - VU_REG_MR, memory); + return read_vu_misc_reg(&(vu1_device.regs), VU_REG_MTPC, memory); case 2: - return read_vu_misc_reg (&(vu1_device.regs), - VU_REG_MP, memory); + return read_vu_special_reg (&vu1_device, VU_REG_STAT, memory); case 3: - return read_vu_misc_reg (&(vu1_device.regs), - VU_REG_MI, memory); + return read_vu_misc_reg (&(vu1_device.regs), VU_REG_MST, memory); case 4: - return read_vu_misc_reg (&(vu1_device.regs), - VU_REG_MQ, memory); + return read_vu_misc_reg (&(vu1_device.regs), VU_REG_MMC, memory); + case 5: + return read_vu_misc_reg (&(vu1_device.regs), VU_REG_MCP, memory); + case 6: /* CMSAR1 is actually from VU0 */ +#ifdef TARGET_SKY_B + return 0; +#else + return read_vu_special_reg (&vu0_device, VU_REG_CMSAR1, memory); +#endif /* ! TARGET_SKY_B */ + case 7: /* VU1 has no FBRST register */ + *((int *) memory) = 0; + return 4; + case 8: + return read_vu_misc_reg (&(vu1_device.regs), VU_REG_MR, memory); + case 9: + return read_vu_misc_reg (&(vu1_device.regs), VU_REG_MP, memory); + case 10: + return read_vu_misc_reg (&(vu1_device.regs), VU_REG_MI, memory); + case 11: + return read_vu_misc_reg (&(vu1_device.regs), VU_REG_MQ, memory); default: return read_vu_acc_reg (&(vu1_device.regs), - rn - (NUM_VU_INTEGER_REGS + 5), + rn - (NUM_VU_INTEGER_REGS + 12), memory); } } @@ -1076,12 +1283,17 @@ sim_fetch_register (sd,rn,memory,length) if (rn < NUM_VIF_REGS) { +#ifdef TARGET_SKY_B + sim_io_eprintf( sd, "Invalid VIF register (register fetch ignored)\n" ); + return 0; +#else if (rn < NUM_VIF_REGS-2) - return read_pke_reg (&pke0_device, rn, memory); + return read_vif_reg (&vif0_device, rn, memory); else if (rn == NUM_VIF_REGS-2) - return read_pke_pc (&pke0_device, memory); + return read_vif_pc (&vif0_device, memory); else - return read_pke_pcx (&pke0_device, memory); + return read_vif_pcx (&vif0_device, memory); +#endif /* ! TARGET_SKY_B */ } rn -= NUM_VIF_REGS; /* VIF1 registers are last */ @@ -1089,11 +1301,11 @@ sim_fetch_register (sd,rn,memory,length) if (rn < NUM_VIF_REGS) { if (rn < NUM_VIF_REGS-2) - return read_pke_reg (&pke1_device, rn, memory); + return read_vif_reg (&vif1_device, rn, memory); else if (rn == NUM_VIF_REGS-2) - return read_pke_pc (&pke1_device, memory); + return read_vif_pc (&vif1_device, memory); else - return read_pke_pcx (&pke1_device, memory); + return read_vif_pcx (&vif1_device, memory); } sim_io_eprintf( sd, "Invalid VU register (register fetch ignored)\n" ); @@ -1205,7 +1417,7 @@ fetch_str (sd, addr) } /* Simple monitor interface (currently setup for the IDT and PMON monitors) */ -static void +void sim_monitor (SIM_DESC sd, sim_cpu *cpu, address_word cia, @@ -1715,6 +1927,259 @@ ColdReset (SIM_DESC sd) } } + + +/* start-sanitize-sky */ +#ifdef TARGET_SKY + +/* See ch. 5 of the 5900 Users' Guide. */ +void +signal_exception (SIM_DESC sd, + sim_cpu *cpu, + address_word cia, + int cause, ...) +{ + /* int vector; */ + +#ifdef DEBUG + sim_io_printf(sd,"DBG: SignalException(%d) PC = 0x%s\n",cause,pr_addr(cia)); +#endif /* DEBUG */ + + /* Ensure that any active atomic read/modify/write operation will fail: */ + LLBIT = 0; + + /* First, handle any simulator specific magic exceptions. These are not "real" exceptions, but + are exceptions which the simulator uses to implement different features. */ + + switch (cause) { + + case SimulatorFault: + { + va_list ap; + char *msg; + va_start(ap,cause); + msg = va_arg(ap,char *); + va_end(ap); + sim_engine_abort (SD, CPU, NULL_CIA, + "FATAL: Simulator error \"%s\"\n",msg); + } + + case DebugBreakPoint : + if (! (Debug & Debug_DM)) + { + if (INDELAYSLOT()) + { + CANCELDELAYSLOT(); + + Debug |= Debug_DBD; /* signaled from within in delay slot */ + DEPC = cia - 4; /* reference the branch instruction */ + } + else + { + Debug &= ~Debug_DBD; /* not signaled from within a delay slot */ + DEPC = cia; + } + + Debug |= Debug_DM; /* in debugging mode */ + Debug |= Debug_DBp; /* raising a DBp exception */ + PC = 0xBFC00200; + sim_engine_restart (SD, CPU, NULL, NULL_CIA); + } + break; + + case ReservedInstruction : + { + va_list ap; + unsigned int instruction; + va_start(ap,cause); + instruction = va_arg(ap,unsigned int); + va_end(ap); + /* Provide simple monitor support using ReservedInstruction + exceptions. The following code simulates the fixed vector + entry points into the IDT monitor by causing a simulator + trap, performing the monitor operation, and returning to + the address held in the $ra register (standard PCS return + address). This means we only need to pre-load the vector + space with suitable instruction values. For systems were + actual trap instructions are used, we would not need to + perform this magic. */ + if ((instruction & RSVD_INSTRUCTION_MASK) == RSVD_INSTRUCTION) + { + sim_monitor (SD, CPU, cia, ((instruction >> RSVD_INSTRUCTION_ARG_SHIFT) & RSVD_INSTRUCTION_ARG_MASK) ); + /* NOTE: This assumes that a branch-and-link style + instruction was used to enter the vector (which is the + case with the current IDT monitor). */ + sim_engine_restart (SD, CPU, NULL, RA); + } + /* Look for the mips16 entry and exit instructions, and + simulate a handler for them. */ + else if ((cia & 1) != 0 + && (instruction & 0xf81f) == 0xe809 + && (instruction & 0x0c0) != 0x0c0) + { + mips16_entry (SD, CPU, cia, instruction); + sim_engine_restart (sd, NULL, NULL, NULL_CIA); + } + /* else fall through to normal exception processing */ + sim_io_eprintf(sd,"ReservedInstruction at PC = 0x%s\n", pr_addr (cia)); + } + } + + /* Now we have the code for processing "real" exceptions. */ + + if (is5900Level2Exception(cause)) { + switch(cause) { + case NMIReset: + cause_set_EXC2(1); + break; + default: + sim_engine_abort (SD, CPU, NULL_CIA, + "FATAL: Unexpected level 2 exception %d\n", cause); + } + if (STATE & simDELAYSLOT) + { + STATE &= ~simDELAYSLOT; + COP0_ERROREPC = (cia - 4); /* reference the branch instruction */ + CAUSE |= cause_BD2; + } + else + { + COP0_ERROREPC = cia; + CAUSE &= ~cause_BD2; + } + + SR |= status_ERL; + + if (cause == NMIReset) + PC = 0xBFC0000; + else + { + ASSERT(0); /* At the moment, COUNTER, DEBUG never generated. */ + } + sim_engine_restart (SD, CPU, NULL, PC); + } else { + /* A level 1 exception. */ + int refill, vector_offset; + + cause_set_EXC(cause); + if (SR & status_EXL) + vector_offset = 0x180; + else + { + if (cause == TLBLoad || cause == TLBStore) { + va_list ap; + va_start(ap, cause); + refill = va_arg(ap,int); + va_end(ap); + } + + if (STATE & simDELAYSLOT) + { + STATE &= ~simDELAYSLOT; + CAUSE |= cause_BD; + COP0_EPC = (cia - 4); /* reference the branch instruction */ + } + else + { + COP0_EPC = cia; + CAUSE &= ~cause_BD; + } + + SR |= status_EXL; + + if ((cause == TLBLoad || cause == TLBStore) && refill == TLB_REFILL) + vector_offset = 0x000; + else if (cause == Interrupt) + vector_offset = 0x200; + else + vector_offset = 0x180; + + if (SR & status_BEV) + PC = (signed)0xBFC00200 + vector_offset; + else + PC = (signed)0x80000000 + vector_offset; + } + + /* Now, handle the exception. */ + switch (cause) + { + case Interrupt: + { + va_list ap; + unsigned int level; + va_start(ap, cause); + level = va_arg(ap,unsigned int); + va_end(ap); + /* Interrupts arrive during event processing, no need to restart. + Hardware interrupts on sky target are INT1 and INT2. */ + if ( level == 1 ) + CAUSE |= cause_IP3; /* bit 11 */ + else if ( level == 2 ) + CAUSE |= cause_IP7; /* bit 15 */ + else + sim_engine_abort (SD, CPU, NULL_CIA, + "FATAL: Unexpected interrupt level %d\n", level); + return; + } + + case NMIReset: + ASSERT(0); /* NMIReset is a level 0 exception. */ + return; + + case AddressLoad: + case AddressStore: + case InstructionFetch: + case DataReference: + /* The following is so that the simulator will continue from the + exception address on breakpoint operations. */ + PC = COP0_EPC; + sim_engine_halt (SD, CPU, NULL, NULL_CIA, + sim_stopped, SIM_SIGBUS); + break; + + case ReservedInstruction: + case CoProcessorUnusable: + PC = COP0_EPC; + sim_engine_halt (SD, CPU, NULL, NULL_CIA, + sim_stopped, SIM_SIGILL); + break; + + case IntegerOverflow: + case FPE: + PC = COP0_EPC; + sim_engine_halt (SD, CPU, NULL, NULL_CIA, + sim_stopped, SIM_SIGFPE); + break; + + case TLBModification: + case TLBLoad: + case TLBStore: + case BreakPoint: + case SystemCall: + case Trap: + sim_engine_restart (SD, CPU, NULL, PC); + break; + + case Watch: + PC = COP0_EPC; + sim_engine_halt (SD, CPU, NULL, NULL_CIA, + sim_stopped, SIM_SIGTRAP); + break; + + default : /* Unknown internal exception */ + PC = COP0_EPC; + sim_engine_halt (SD, CPU, NULL, NULL_CIA, + sim_stopped, SIM_SIGABRT); + break; + + } + } + return; +} + +#else /* TARGET_SKY */ +/* end-sanitize-sky */ + /* Description from page A-26 of the "MIPS IV Instruction Set" manual (revision 3.1) */ /* Signal an exception condition. This will result in an exception that aborts the instruction. The instruction operation pseudocode @@ -1928,6 +2393,11 @@ signal_exception (SIM_DESC sd, return; } +/* start-sanitize-sky */ +#endif /* ! TARGET_SKY */ +/* end-sanitize-sky */ + + #if defined(WARN_RESULT) /* Description from page A-26 of the "MIPS IV Instruction Set" manual (revision 3.1) */ /* This function indicates that the result of the operation is @@ -3082,7 +3552,7 @@ cop_ld (SIM_DESC sd, /* start-sanitize-sky */ -#ifdef TARGET_SKY +#if defined(TARGET_SKY) && !defined(TARGET_SKY_B) void cop_lq (SIM_DESC sd, sim_cpu *cpu, @@ -3183,7 +3653,7 @@ cop_sd (SIM_DESC sd, /* start-sanitize-sky */ -#ifdef TARGET_SKY +#if defined(TARGET_SKY) && !defined(TARGET_SKY_B) unsigned128 cop_sq (SIM_DESC sd, sim_cpu *cpu, @@ -3423,7 +3893,7 @@ decode_coproc (SIM_DESC sd, int handle = 0; /* start-sanitize-sky */ -#ifdef TARGET_SKY +#if defined(TARGET_SKY) && !defined(TARGET_SKY_B) /* On the R5900, this refers to a "VU" vector co-processor. */ int i_25_21 = (instruction >> 21) & 0x1f; @@ -3595,10 +4065,6 @@ decode_coproc (SIM_DESC sd, /* NOTREACHED */ } -#undef MY_INDEX -#undef MY_PREFIX -#undef MY_NAME - #endif /* TARGET_SKY */ /* end-sanitize-sky */ diff --git a/sim/mips/sim-main.h b/sim/mips/sim-main.h index f577ed7f27..95b04fd5de 100644 --- a/sim/mips/sim-main.h +++ b/sim/mips/sim-main.h @@ -36,14 +36,6 @@ with this program; if not, write to the Free Software Foundation, Inc., typedef address_word sim_cia; -#if (WITH_IGEN) -/* Get the number of instructions. FIXME: must be a more elegant way - of doing this. */ -#include "itable.h" -#define MAX_INSNS (nr_itable_entries) -#define INSN_NAME(cpu,i) itable[(i)].name -#endif - #include "sim-base.h" @@ -254,7 +246,25 @@ enum { R5900_FPMIN = LSMASK32 (31, 0), }; +typedef struct _r4000_tlb_entry { + unsigned32 mask; + unsigned32 hi; + unsigned32 lo0; + unsigned32 lo1; +} r4000_tlb_entry_t; +#define TLB_MASK_MASK_MASK 0x01ffe000 +#define TLB_HI_VPN2_MASK 0xffffe000 +#define TLB_HI_G_MASK 0x00001000 +#define TLB_HI_ASID_MASK 0x000000ff + +#define TLB_LO_S_MASK 0x80000000 +#define TLB_LO_PFN_MASK 0x03ffffc0 +#define TLB_LO_C_MASK 0x00000038 +#define TLB_LO_D_MASK 0x00000004 +#define TLB_LO_V_MASK 0x00000002 + +#define TLB_SIZE 48 typedef struct _sim_r5900_cpu { @@ -270,6 +280,7 @@ typedef struct _sim_r5900_cpu { same register. */ signed_word gpr1[32]; #define GPR1 ((CPU)->r5900.gpr1) +#define GPR1_SET(N,VAL) (GPR1[(N]) = (VAL)) signed_word lo1; signed_word hi1; #define LO1 ((CPU)->r5900.lo1) @@ -294,6 +305,9 @@ typedef struct _sim_r5900_cpu { hilo_history lo1_history; #define LO1HISTORY (&(CPU)->r5900.lo1_history) + r4000_tlb_entry_t tlb[TLB_SIZE]; +#define TLB ((CPU)->r5900.tlb) + } sim_r5900_cpu; #define BYTES_IN_MMI_REGS (sizeof(signed_word) + sizeof(signed_word)) @@ -565,10 +579,14 @@ struct _sim_cpu { #ifndef TM_MIPS_H #define LAST_EMBED_REGNUM (89) #define NUM_REGS (LAST_EMBED_REGNUM + 1) + /* start-sanitize-r5900 */ +#define FIRST_COP0_REG 128 +#define NUM_COP0_REGS 22 #undef NUM_REGS -#define NUM_REGS (128) +#define NUM_REGS (150) /* end-sanitize-r5900 */ + #endif /* start-sanitize-sky */ @@ -582,7 +600,7 @@ struct _sim_cpu { #define NUM_VIF_REGS 26 -#define NUM_CORE_REGS 128 +#define NUM_CORE_REGS 150 #undef NUM_REGS #define NUM_REGS (NUM_CORE_REGS + 2*(NUM_VU_REGS) + 2*(NUM_VIF_REGS)) @@ -667,9 +685,31 @@ enum float_operation #define COP0_BP ((CPU)->cop0_bp) #define NR_COP0_P 64 unsigned_word cop0_p[NR_COP0_P]; -#define COP0_P ((CPU)->cop0_p) - /* end-sanitize-r5900 */ +#define COP0_P ((CPU)->cop0_p) +#define COP0_INDEX ((unsigned32)(COP0_GPR[0])) +#define COP0_RANDOM ((unsigned32)(COP0_GPR[1])) +#define COP0_ENTRYLO0 ((unsigned32)(COP0_GPR[2])) +#define COP0_ENTRYLO1 ((unsigned32)(COP0_GPR[3])) +#define COP0_CONTEXT ((unsigned32)(COP0_GPR[4])) +#define COP0_PAGEMASK ((unsigned32)(COP0_GPR[5])) +#define COP0_WIRED ((unsigned32)(COP0_GPR[6])) +#define COP0_BADVADDR ((unsigned32)(COP0_GPR[8])) +#define COP0_COUNT ((unsigned32)(COP0_GPR[9])) +#define COP0_ENTRYHI ((unsigned32)(COP0_GPR[10])) +#define COP0_COMPARE ((unsigned32)(COP0_GPR[11])) +#define COP0_EPC ((unsigned32)(EPC)) /* 14 */ +#define COP0_PRID ((unsigned32)(COP0_GPR[15])) +#define COP0_CONFIG ((unsigned32)(C0_CONFIG)) /* 16 */ +#define COP0_TAGLO ((unsigned32)(COP0_GPR[28])) +#define COP0_TAGHI ((unsigned32)(COP0_GPR[29])) +#define COP0_ERROREPC ((unsigned32)(COP0_GPR[30])) + +#define COP0_CONTEXT_BADVPN2_MASK 0x007ffff0 + +#define COP0_CONTEXT_set_BADVPN2(x) \ + (COP0_CONTEXT = ((COP0_CONTEXT & 0xff100000) | ((x << 4) & 0x007ffff0))) + /* end-sanitize-r5900 */ /* Keep the current format state for each register: */ FP_formats fpr_state[32]; @@ -716,20 +756,20 @@ enum float_operation /* end-sanitize-branchbug4011 */ /* start-sanitize-r5900 */ sim_r5900_cpu r5900; - /* end-sanitize-r5900 */ - /* start-sanitize-cygnus */ + /* start-sanitize-cygnus */ /* The MDMX ISA has a very very large accumulator */ unsigned8 acc[3 * 8]; /* end-sanitize-cygnus */ - /* start-sanitize-sky */ + /* start-sanitize-sky */ #ifdef TARGET_SKY /* Device on which instruction issue last occured. */ char cur_device; #endif /* end-sanitize-sky */ + sim_cpu_base base; }; @@ -778,13 +818,15 @@ struct sim_state { /* TODO : these should be the bitmasks for these bits within the status register. At the moment the following are VR4300 bit-positions: */ -#define status_KSU_mask (0x3) /* mask for KSU bits */ +#define status_KSU_mask (0x18) /* mask for KSU bits */ #define status_KSU_shift (3) /* shift for field */ #define ksu_kernel (0x0) #define ksu_supervisor (0x1) #define ksu_user (0x2) #define ksu_unknown (0x3) +#define SR_KSU ((SR & status_KSU_mask) >> status_KSU_shift) + #define status_IE (1 << 0) /* Interrupt enable */ #define status_EIE (1 << 16) /* Enable Interrupt Enable */ #define status_EXL (1 << 1) /* Exception level */ @@ -794,6 +836,7 @@ struct sim_state { #define status_BEV (1 << 22) /* Location of general exception vectors */ #define status_TS (1 << 21) /* TLB shutdown has occurred */ #define status_ERL (1 << 2) /* Error level */ +#define status_IM7 (1 << 15) /* Timer Interrupt Mask */ #define status_RP (1 << 27) /* Reduced Power mode */ /* start-sanitize-r5900 */ #define status_CU0 (1 << 28) /* COP0 usable */ @@ -813,16 +856,35 @@ struct sim_state { #define status_NMI (1 << 20) /* NMI */ #define status_NMI (1 << 20) /* NMI */ -#define cause_EXC_mask (0x1f) /* Exception code */ +#define cause_BD ((unsigned)1 << 31) /* L1 Exception in branch delay slot */ +#define cause_BD2 (1 << 30) /* L2 Exception in branch delay slot */ +#define cause_CE_mask 0x30000000 /* Coprocessor exception */ +#define cause_CE_shift 28 +#define cause_EXC2_mask 0x00070000 +#define cause_EXC2_shift 16 +#define cause_IP7 (1 << 15) /* Interrupt pending */ +#define cause_SIOP (1 << 12) /* SIO pending */ +#define cause_IP3 (1 << 11) /* Int 0 pending */ +#define cause_IP2 (1 << 10) /* Int 1 pending */ + +/* start-sanitize-sky */ +#ifdef TARGET_SKY +#define cause_EXC_mask (0x7c) /* Exception code */ +#else +/* end-sanitize-sky */ +#define cause_EXC_mask (0x1c) /* Exception code */ +/* start-sanitize-sky */ +#endif +/* end-sanitize-sky */ #define cause_EXC_shift (2) + #define cause_SW0 (1 << 8) /* Software interrupt 0 */ #define cause_SW1 (1 << 9) /* Software interrupt 1 */ #define cause_IP_mask (0x3f) /* Interrupt pending field */ #define cause_IP_shift (10) -#define cause_CE_mask (0x3) /* Coprocessor error */ -#define cause_CE_shift (28) -#define cause_BD ((unsigned)1 << 31) /* Exception in branch delay slot */ +#define cause_set_EXC(x) CAUSE = (CAUSE & ~cause_EXC_mask) | ((x << cause_EXC_shift) & cause_EXC_mask) +#define cause_set_EXC2(x) CAUSE = (CAUSE & ~cause_EXC2_mask) | ((x << cause_EXC2_shift) & cause_EXC2_mask) /* NOTE: We keep the following status flags as bit values (1 for true, @@ -834,7 +896,7 @@ struct sim_state { #ifdef SUBTARGET_R3900 #define UserMode ((SR & status_KUc) ? 1 : 0) #else -#define UserMode ((((SR & status_KSU_mask) >> status_KSU_shift) == ksu_user) ? 1 : 0) +#define UserMode ((((SR & status_KSU_mask) >> status_KSU_shift) == ksu_user) ? 1 : 0) #endif /* SUBTARGET_R3900 */ /* BigEndianMem */ @@ -863,54 +925,72 @@ struct sim_state { /* NOTE: These numbers depend on the processor architecture being simulated: */ -#define Interrupt (0) -#define TLBModification (1) -#define TLBLoad (2) -#define TLBStore (3) -#define AddressLoad (4) -#define AddressStore (5) -#define InstructionFetch (6) -#define DataReference (7) -#define SystemCall (8) -#define BreakPoint (9) -#define ReservedInstruction (10) -#define CoProcessorUnusable (11) -#define IntegerOverflow (12) /* Arithmetic overflow (IDT monitor raises SIGFPE) */ -#define Trap (13) -#define FPE (15) -#define DebugBreakPoint (16) -#define Watch (23) -#define NMIReset (31) +enum ExceptionCause { + Interrupt = 0, + TLBModification = 1, + TLBLoad = 2, + TLBStore = 3, + AddressLoad = 4, + AddressStore = 5, + InstructionFetch = 6, + DataReference = 7, + SystemCall = 8, + BreakPoint = 9, + ReservedInstruction = 10, + CoProcessorUnusable = 11, + IntegerOverflow = 12, /* Arithmetic overflow (IDT monitor raises SIGFPE) */ + Trap = 13, + FPE = 15, + DebugBreakPoint = 16, + Watch = 23, + NMIReset = 31, /* The following exception code is actually private to the simulator world. It is *NOT* a processor feature, and is used to signal run-time errors in the simulator. */ -#define SimulatorFault (0xFFFFFFFF) + SimulatorFault = 0xFFFFFFFF +}; + +#define TLB_REFILL (0) +#define TLB_INVALID (1) + +/* start-sanitize-r5900 */ +/* For the 5900, we have level 1 and level 2 exceptions. The level 2 exceptions + are ColdReset, NMI, Counter, and Debug/SIO. Of these, we support only + the NMIReset exception. */ + +#define is5900Level2Exception(x) (x == NMIReset) +/* end-sanitize-r5900 */ /* The following break instructions are reserved for use by the simulator. The first is used to halt the simulation. The second is used by gdb for break-points. NOTE: Care must be taken, since this value may be used in later revisions of the MIPS ISA. */ -#define HALT_INSTRUCTION_MASK (0x03FFFFC0) +#define HALT_INSTRUCTION_MASK (0x03FFFFC0) -#define HALT_INSTRUCTION (0x03ff000d) -#define HALT_INSTRUCTION2 (0x0000ffcd) +#define HALT_INSTRUCTION (0x03ff000d) +#define HALT_INSTRUCTION2 (0x0000ffcd) /* start-sanitize-sky */ -#define HALT_INSTRUCTION_PASS (0x03fffc0d) -#define HALT_INSTRUCTION_FAIL (0x03ffffcd) +#define HALT_INSTRUCTION_PASS (0x03fffc0d) /* break 0xffff0 */ +#define HALT_INSTRUCTION_FAIL (0x03ffffcd) /* break 0xfffff */ /* end-sanitize-sky */ #define BREAKPOINT_INSTRUCTION (0x0005000d) #define BREAKPOINT_INSTRUCTION2 (0x0000014d) +/* start-sanitize-sky */ +#define LOAD_INSTRUCTION (0x03fffc4d) /* break 0xffff1 */ +#define PRINTF_INSTRUCTION (0x03fffc8d) /* break 0xffff2 */ +/* end-sanitize-sky */ + void interrupt_event (SIM_DESC sd, void *data); void signal_exception (SIM_DESC sd, sim_cpu *cpu, address_word cia, int exception, ...); #define SignalException(exc,instruction) signal_exception (SD, CPU, cia, (exc), (instruction)) -#define SignalExceptionInterrupt() signal_exception (SD, CPU, cia, Interrupt) +#define SignalExceptionInterrupt(level) signal_exception (SD, CPU, cia, Interrupt, level) #define SignalExceptionInstructionFetch() signal_exception (SD, CPU, cia, InstructionFetch) #define SignalExceptionAddressStore() signal_exception (SD, CPU, cia, AddressStore) #define SignalExceptionAddressLoad() signal_exception (SD, CPU, cia, AddressLoad) @@ -919,6 +999,11 @@ void signal_exception (SIM_DESC sd, sim_cpu *cpu, address_word cia, int exceptio #define SignalExceptionIntegerOverflow() signal_exception (SD, CPU, cia, IntegerOverflow) #define SignalExceptionCoProcessorUnusable() signal_exception (SD, CPU, cia, CoProcessorUnusable) #define SignalExceptionNMIReset() signal_exception (SD, CPU, cia, NMIReset) +#define SignalExceptionTLBRefillStore() signal_exception (SD, CPU, cia, TLBStore, TLB_REFILL) +#define SignalExceptionTLBRefillLoad() signal_exception (SD, CPU, cia, TLBLoad, TLB_REFILL) +#define SignalExceptionTLBInvalidStore() signal_exception (SD, CPU, cia, TLBStore, TLB_INVALID) +#define SignalExceptionTLBInvalidLoad() signal_exception (SD, CPU, cia, TLBLoad, TLB_INVALID) +#define SignalExceptionTLBModification() signal_exception (SD, CPU, cia, TLBModification) /* Co-processor accesses */ @@ -1036,6 +1121,7 @@ char* pr_uword64 PARAMS ((uword64 addr)); /* start-sanitize-sky */ #ifdef TARGET_SKY + #ifdef SIM_ENGINE_HALT_HOOK #undef SIM_ENGINE_HALT_HOOK #endif @@ -1055,6 +1141,8 @@ SIM_RC sky_sim_module_install PARAMS ((SIM_DESC sd)); #define MODULE_LIST sky_sim_module_install, +void sim_monitor (SIM_DESC sd, sim_cpu *cpu, address_word cia, unsigned int arg); + #ifndef TM_TXVU_H /* In case GDB hasn't been configured yet */ enum txvu_cpu_context { @@ -1062,7 +1150,7 @@ enum txvu_cpu_context TXVU_CPU_MASTER = 0, /* R5900 core */ TXVU_CPU_VU0 = 1, /* Vector units */ TXVU_CPU_VU1 = 2, - TXVU_CPU_VIF0 = 3, /* FIFO's */ + TXVU_CPU_VIF0 = 3, /* Vector interface units */ TXVU_CPU_VIF1 = 4, TXVU_CPU_LAST /* Count of context types */ }; diff --git a/sim/mips/sky-pke.c b/sim/mips/sky-pke.c deleted file mode 100644 index 9a2c1518e0..0000000000 --- a/sim/mips/sky-pke.c +++ /dev/null @@ -1,2580 +0,0 @@ -/* Copyright (C) 1998, Cygnus Solutions */ - - -#include "config.h" - -#include -#include "sim-main.h" -#include "sim-bits.h" -#include "sim-assert.h" -#include "sky-pke.h" -#include "sky-dma.h" -#include "sky-vu.h" -#include "sky-gpuif.h" -#include "sky-gdb.h" -#include "sky-device.h" - - -#ifdef HAVE_STRING_H -#include -#else -#ifdef HAVE_STRINGS_H -#include -#endif -#endif - - -/* Internal function declarations */ - -static int pke_io_read_buffer(device*, void*, int, address_word, - unsigned, sim_cpu*, sim_cia); -static int pke_io_write_buffer(device*, const void*, int, address_word, - unsigned, sim_cpu*, sim_cia); -static void pke_reset(struct pke_device*); -static void pke_issue(SIM_DESC, struct pke_device*); -static void pke_pc_advance(struct pke_device*, int num_words); -static struct fifo_quadword* pke_pcrel_fifo(struct pke_device*, int operand_num, - unsigned_4** operand); -static unsigned_4* pke_pcrel_operand(struct pke_device*, int operand_num); -static unsigned_4 pke_pcrel_operand_bits(struct pke_device*, int bit_offset, - int bit_width, unsigned_4* sourceaddr); -static void pke_attach(SIM_DESC sd, struct pke_device* me); -enum pke_check_target { chk_vu, chk_path1, chk_path2, chk_path3 }; -static int pke_check_stall(struct pke_device* me, enum pke_check_target what); -static void pke_flip_dbf(struct pke_device* me); -static void pke_begin_interrupt_stall(struct pke_device* me); -/* PKEcode handlers */ -static void pke_code_nop(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_stcycl(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_offset(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_base(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_itop(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_stmod(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_mskpath3(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_pkemark(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_flushe(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_flush(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_flusha(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_pkemscal(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_pkemscnt(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_pkemscalf(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_stmask(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_strow(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_stcol(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_mpg(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_direct(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_directhl(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_unpack(struct pke_device* me, unsigned_4 pkecode); -static void pke_code_error(struct pke_device* me, unsigned_4 pkecode); -unsigned_4 pke_fifo_flush(struct pke_fifo*); -void pke_fifo_reset(struct pke_fifo*); -struct fifo_quadword* pke_fifo_fit(struct pke_fifo*); -struct fifo_quadword* pke_fifo_access(struct pke_fifo*, unsigned_4 qwnum); -void pke_fifo_old(struct pke_fifo*, unsigned_4 qwnum); - -/* Default --log-file names */ -const char *pke0_default_trace = "vif0.s"; -const char *pke1_default_trace = "vif1.s"; - - -/* Static data */ - -struct pke_device pke0_device = -{ - { "vif0", &pke_io_read_buffer, &pke_io_write_buffer }, /* device */ - 0, 0, /* ID, flags */ - {}, /* regs */ - {}, 0, /* FIFO write buffer */ - { NULL, 0, 0, 0 }, /* FIFO */ - NULL, NULL, /* FIFO trace file descriptor and name */ - -1, -1, 0, 0, 0, /* invalid FIFO cache */ - 0, 0, /* pc */ - NULL, NULL /* disassembly trace file descriptor and name */ -}; - - -struct pke_device pke1_device = -{ - { "vif1", &pke_io_read_buffer, &pke_io_write_buffer }, /* device */ - 1, 0, /* ID, flags */ - {}, /* regs */ - {}, 0, /* FIFO write buffer */ - { NULL, 0, 0, 0 }, /* FIFO */ - NULL, NULL, /* FIFO trace file descriptor and name */ - -1, -1, 0, 0, 0, /* invalid FIFO cache */ - 0, 0, /* pc */ - NULL, NULL /* disassembly trace file descriptor and name */ -}; - - - -/* External functions */ - - -/* Attach PKE addresses to main memory */ - -void -pke0_attach(SIM_DESC sd) -{ - pke_attach(sd, & pke0_device); - pke_reset(& pke0_device); -} - -void -pke1_attach(SIM_DESC sd) -{ - pke_attach(sd, & pke1_device); - pke_reset(& pke1_device); -} - - - -/* Issue a PKE instruction if possible */ - -void -pke0_issue(SIM_DESC sd) -{ - pke_issue(sd, & pke0_device); -} - -void -pke1_issue(SIM_DESC sd) -{ - pke_issue(sd, & pke1_device); -} - - - -/* Internal functions */ - - -/* Attach PKE memory regions to simulator */ - -void -pke_attach(SIM_DESC sd, struct pke_device* me) -{ - /* register file */ - sim_core_attach (sd, NULL, 0, access_read_write, 0, - (me->pke_number == 0) ? PKE0_REGISTER_WINDOW_START : PKE1_REGISTER_WINDOW_START, - PKE_REGISTER_WINDOW_SIZE /*nr_bytes*/, - 0 /*modulo*/, - (device*) me, - NULL /*buffer*/); - - /* FIFO port */ - sim_core_attach (sd, NULL, 0, access_read_write, 0, - (me->pke_number == 0) ? PKE0_FIFO_ADDR : PKE1_FIFO_ADDR, - sizeof(quadword) /*nr_bytes*/, - 0 /*modulo*/, - (device*) me, - NULL /*buffer*/); - - /* VU MEM0 tracking table */ - sim_core_attach (sd, NULL, 0, access_read_write, 0, - ((me->pke_number == 0) ? VU0_MEM0_SRCADDR_START : VU1_MEM0_SRCADDR_START), - ((me->pke_number == 0) ? VU0_MEM0_SIZE : VU1_MEM0_SIZE) / 2, - 0 /*modulo*/, - NULL, - NULL /*buffer*/); - - /* VU MEM1 tracking table */ - sim_core_attach (sd, NULL, 0, access_read_write, 0, - ((me->pke_number == 0) ? VU0_MEM1_SRCADDR_START : VU1_MEM1_SRCADDR_START), - ((me->pke_number == 0) ? VU0_MEM1_SIZE : VU1_MEM1_SIZE) / 4, - 0 /*modulo*/, - NULL, - NULL /*buffer*/); -} - - -/* Read PKE Pseudo-PC index into buf in target order */ -int -read_pke_pcx (struct pke_device *me, void *buf) -{ - *((int *) buf) = H2T_4( (me->fifo_pc << 2) | me->qw_pc ); - return 4; -} - - -/* Read PKE Pseudo-PC source address into buf in target order */ -int -read_pke_pc (struct pke_device *me, void *buf) -{ - struct fifo_quadword* fqw = pke_fifo_access(& me->fifo, me->fifo_pc); - unsigned_4 addr; - - if (fqw == NULL) - *((int *) buf) = 0; - else - { - addr = (fqw->source_address & ~15) | (me->qw_pc << 2); - *((unsigned_4 *) buf) = H2T_4( addr ); - } - - return 4; -} - - -/* Read PKE reg into buf in target order */ -int -read_pke_reg (struct pke_device *me, int reg_num, void *buf) -{ - /* handle reads to individual registers; clear `readable' on error */ - switch (reg_num) - { - /* handle common case of register reading, side-effect free */ - /* PKE1-only registers*/ - case PKE_REG_BASE: - case PKE_REG_OFST: - case PKE_REG_TOPS: - case PKE_REG_TOP: - case PKE_REG_DBF: - if (me->pke_number == 0) - { - *((int *) buf) = 0; - break; - } - /* fall through */ - - /* PKE0 & PKE1 common registers*/ - case PKE_REG_STAT: - case PKE_REG_ERR: - case PKE_REG_MARK: - case PKE_REG_CYCLE: - case PKE_REG_MODE: - case PKE_REG_NUM: - case PKE_REG_MASK: - case PKE_REG_CODE: - case PKE_REG_ITOPS: - case PKE_REG_ITOP: - case PKE_REG_R0: - case PKE_REG_R1: - case PKE_REG_R2: - case PKE_REG_R3: - case PKE_REG_C0: - case PKE_REG_C1: - case PKE_REG_C2: - case PKE_REG_C3: - *((int *) buf) = H2T_4(me->regs[reg_num][0]); - break; - - /* handle common case of write-only registers */ - case PKE_REG_FBRST: - *((int *) buf) = 0; - break; - - default: - ASSERT(0); /* tests above should prevent this possibility */ - } - - return 4; -} - - -/* Handle a PKE read; return no. of bytes read */ - -int -pke_io_read_buffer(device *me_, - void *dest, - int space, - address_word addr, - unsigned nr_bytes, - sim_cpu *cpu, - sim_cia cia) -{ - /* downcast to gather embedding pke_device struct */ - struct pke_device* me = (struct pke_device*) me_; - - /* find my address ranges */ - address_word my_reg_start = - (me->pke_number == 0) ? PKE0_REGISTER_WINDOW_START : PKE1_REGISTER_WINDOW_START; - address_word my_fifo_addr = - (me->pke_number == 0) ? PKE0_FIFO_ADDR : PKE1_FIFO_ADDR; - - /* enforce that an access does not span more than one quadword */ - address_word low = ADDR_TRUNC_QW(addr); - address_word high = ADDR_TRUNC_QW(addr + nr_bytes - 1); - if(low != high) - return 0; - - /* classify address & handle */ - if((addr >= my_reg_start) && (addr < my_reg_start + PKE_REGISTER_WINDOW_SIZE)) - { - /* register bank */ - int reg_num = ADDR_TRUNC_QW(addr - my_reg_start) >> 4; - int reg_byte = ADDR_OFFSET_QW(addr); /* find byte-offset inside register bank */ - quadword result; - - /* clear result */ - result[0] = result[1] = result[2] = result[3] = 0; - - read_pke_reg (me, reg_num, result); - - /* perform transfer & return */ - memcpy(dest, ((unsigned_1*) &result) + reg_byte, nr_bytes); - - return nr_bytes; - /* NOTREACHED */ - } - else if(addr >= my_fifo_addr && - addr < my_fifo_addr + sizeof(quadword)) - { - /* FIFO */ - - /* FIFO is not readable: return a word of zeroes */ - memset(dest, 0, nr_bytes); - return nr_bytes; - } - - /* NOTREACHED */ - return 0; -} - -/* Write PKE reg from buf, which is in target order */ -int -write_pke_reg (struct pke_device *me, int reg_num, const void *buf) -{ - int writeable = 1; - /* make words host-endian */ - unsigned_4 input = T2H_4( *((unsigned_4 *) buf) ); - - /* handle writes to individual registers; clear `writeable' on error */ - switch (reg_num) - { - case PKE_REG_FBRST: - /* Order these tests from least to most overriding, in case - multiple bits are set. */ - if(BIT_MASK_GET(input, PKE_REG_FBRST_STC_B, PKE_REG_FBRST_STC_E)) - { - /* clear a bunch of status bits */ - PKE_REG_MASK_SET(me, STAT, PSS, 0); - PKE_REG_MASK_SET(me, STAT, PFS, 0); - PKE_REG_MASK_SET(me, STAT, PIS, 0); - PKE_REG_MASK_SET(me, STAT, INT, 0); - PKE_REG_MASK_SET(me, STAT, ER0, 0); - PKE_REG_MASK_SET(me, STAT, ER1, 0); - me->flags &= ~PKE_FLAG_PENDING_PSS; - /* will allow resumption of possible stalled instruction */ - } - if(BIT_MASK_GET(input, PKE_REG_FBRST_STP_B, PKE_REG_FBRST_STP_E)) - { - me->flags |= PKE_FLAG_PENDING_PSS; - } - if(BIT_MASK_GET(input, PKE_REG_FBRST_FBK_B, PKE_REG_FBRST_FBK_E)) - { - PKE_REG_MASK_SET(me, STAT, PFS, 1); - } - if(BIT_MASK_GET(input, PKE_REG_FBRST_RST_B, PKE_REG_FBRST_RST_E)) - { - pke_reset(me); - } - break; - - case PKE_REG_ERR: - /* copy bottom three bits */ - BIT_MASK_SET(me->regs[PKE_REG_ERR][0], 0, 2, BIT_MASK_GET(input, 0, 2)); - break; - - case PKE_REG_MARK: - /* copy bottom sixteen bits */ - PKE_REG_MASK_SET(me, MARK, MARK, BIT_MASK_GET(input, 0, 15)); - /* reset MRK bit in STAT */ - PKE_REG_MASK_SET(me, STAT, MRK, 0); - break; - - /* handle common case of read-only registers */ - /* PKE1-only registers - not really necessary to handle separately */ - case PKE_REG_BASE: - case PKE_REG_OFST: - case PKE_REG_TOPS: - case PKE_REG_TOP: - case PKE_REG_DBF: - if(me->pke_number == 0) - writeable = 0; - /* fall through */ - /* PKE0 & PKE1 common registers*/ - case PKE_REG_STAT: - /* ignore FDR bit for PKE1_STAT -- simulator does not implement PKE->RAM transfers */ - case PKE_REG_CYCLE: - case PKE_REG_MODE: - case PKE_REG_NUM: - case PKE_REG_MASK: - case PKE_REG_CODE: - case PKE_REG_ITOPS: - case PKE_REG_ITOP: - case PKE_REG_R0: - case PKE_REG_R1: - case PKE_REG_R2: - case PKE_REG_R3: - case PKE_REG_C0: - case PKE_REG_C1: - case PKE_REG_C2: - case PKE_REG_C3: - writeable = 0; - break; - - default: - ASSERT(0); /* test above should prevent this possibility */ - } - - /* perform return */ - if(! writeable) - { - return 0; /* error */ - } - - return 4; -} - - -/* Handle a PKE write; return no. of bytes written */ - -int -pke_io_write_buffer(device *me_, - const void *src, - int space, - address_word addr, - unsigned nr_bytes, - sim_cpu *cpu, - sim_cia cia) -{ - /* downcast to gather embedding pke_device struct */ - struct pke_device* me = (struct pke_device*) me_; - - /* find my address ranges */ - address_word my_reg_start = - (me->pke_number == 0) ? PKE0_REGISTER_WINDOW_START : PKE1_REGISTER_WINDOW_START; - address_word my_fifo_addr = - (me->pke_number == 0) ? PKE0_FIFO_ADDR : PKE1_FIFO_ADDR; - - /* enforce that an access does not span more than one quadword */ - address_word low = ADDR_TRUNC_QW(addr); - address_word high = ADDR_TRUNC_QW(addr + nr_bytes - 1); - if(low != high) - return 0; - - /* classify address & handle */ - if((addr >= my_reg_start) && (addr < my_reg_start + PKE_REGISTER_WINDOW_SIZE)) - { - /* register bank */ - int reg_num = ADDR_TRUNC_QW(addr - my_reg_start) >> 4; - int reg_byte = ADDR_OFFSET_QW(addr); /* find byte-offset inside register bank */ - quadword input; - - /* clear input */ - input[0] = input[1] = input[2] = input[3] = 0; - - /* write user-given bytes into input */ - memcpy(((unsigned_1*) &input) + reg_byte, src, nr_bytes); - - write_pke_reg (me, reg_num, input); - return nr_bytes; - - /* NOTREACHED */ - } - else if(addr >= my_fifo_addr && - addr < my_fifo_addr + sizeof(quadword)) - { - /* FIFO */ - struct fifo_quadword* fqw; - int fifo_byte = ADDR_OFFSET_QW(addr); /* find byte-offset inside fifo quadword */ - unsigned_4 dma_tag_present = 0; - int i; - - /* collect potentially-partial quadword in write buffer; LE byte order */ - memcpy(((unsigned_1*)& me->fifo_qw_in_progress) + fifo_byte, src, nr_bytes); - /* mark bytes written */ - for(i = fifo_byte; i < fifo_byte + nr_bytes; i++) - BIT_MASK_SET(me->fifo_qw_done, i, i, 1); - - /* return if quadword not quite written yet */ - if(BIT_MASK_GET(me->fifo_qw_done, 0, sizeof(quadword)-1) != - BIT_MASK_BTW(0, sizeof(quadword)-1)) - return nr_bytes; - - /* all done - process quadword after clearing flag */ - BIT_MASK_SET(me->fifo_qw_done, 0, sizeof(quadword)-1, 0); - - /* allocate required address in FIFO */ - fqw = pke_fifo_fit(& me->fifo); - ASSERT(fqw != NULL); - - /* fill in unclassified FIFO quadword data in host byte order */ - fqw->word_class[0] = fqw->word_class[1] = - fqw->word_class[2] = fqw->word_class[3] = wc_unknown; - fqw->data[0] = T2H_4(me->fifo_qw_in_progress[0]); - fqw->data[1] = T2H_4(me->fifo_qw_in_progress[1]); - fqw->data[2] = T2H_4(me->fifo_qw_in_progress[2]); - fqw->data[3] = T2H_4(me->fifo_qw_in_progress[3]); - - /* read DMAC-supplied indicators */ - ASSERT(sizeof(unsigned_4) == 4); - PKE_MEM_READ(me, (me->pke_number == 0 ? DMA_D0_MADR : DMA_D1_MADR), - & fqw->source_address, /* converted to host-endian */ - 4); - PKE_MEM_READ(me, (me->pke_number == 0 ? DMA_D0_PKTFLAG : DMA_D1_PKTFLAG), - & dma_tag_present, - 4); - - if(dma_tag_present) - { - /* lower two words are DMA tags */ - fqw->word_class[0] = fqw->word_class[1] = wc_dma; - } - - /* set FQC to "1" as FIFO is now not empty */ - PKE_REG_MASK_SET(me, STAT, FQC, 1); - - /* okay */ - return nr_bytes; - } - - /* NOTREACHED */ - return 0; -} - - - -/* Reset the simulated PKE hardware state. Preserve other internal - state. */ -void -pke_reset(struct pke_device* me) -{ - /* advance PC over last quadword in FIFO; keep previous FIFO history */ - me->fifo_pc = pke_fifo_flush(& me->fifo); - me->qw_pc = 0; - /* clear registers, flag, other state */ - memset(me->regs, 0, sizeof(me->regs)); - me->fifo_qw_done = 0; - /* Command options will remain alive over the reset. */ - me->flags &= PKE_FLAG_TRACE_ON; - - /* NOTE: Since disassembly / trace logs remain open across ordinary - simulated hardware resets, there may be a problem of producing a - trace file that has only partial results from the prior - operation. For the current PKE model, however, this cannot - happen as stalls & interrupts only occur *between* simulated - PKEcode executions. This means that our trace files ought remain - syntactically valid, despite resets. */ - - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n;%s RESET\n", - me->dev.name); - } - } - - - -/* Issue & swallow next PKE opcode if possible/available */ - -void -pke_issue(SIM_DESC sd, struct pke_device* me) -{ - struct fifo_quadword* fqw; - unsigned_4 fw; - unsigned_4 cmd, intr; - - /* 1 -- fetch PKE instruction */ - - /* confirm availability of new quadword of PKE instructions */ - fqw = pke_fifo_access(& me->fifo, me->fifo_pc); - if(fqw == NULL) - return; - - /* skip over DMA tag, if present */ - pke_pc_advance(me, 0); - /* note: this can only change qw_pc from 0 to 2 and will not - invalidate fqw */ - - /* "fetch" instruction quadword and word */ - fw = fqw->data[me->qw_pc]; - - /* store word in PKECODE register */ - me->regs[PKE_REG_CODE][0] = fw; - - /* 2 -- test go / no-go for PKE execution */ - - /* switch on STAT:PSS if PSS-pending and in idle state */ - if((PKE_REG_MASK_GET(me, STAT, PPS) == PKE_REG_STAT_PPS_IDLE) && - (me->flags & PKE_FLAG_PENDING_PSS) != 0) - { - me->flags &= ~PKE_FLAG_PENDING_PSS; - PKE_REG_MASK_SET(me, STAT, PSS, 1); - } - - /* check for stall/halt control bits */ - if(PKE_REG_MASK_GET(me, STAT, PFS) || - PKE_REG_MASK_GET(me, STAT, PSS) || /* note special treatment below */ - /* PEW bit not a reason to keep stalling - it's just an indication, re-computed below */ - /* PGW bit not a reason to keep stalling - it's just an indication, re-computed below */ - /* ER0/ER1 not a reason to keep stalling - it's just an indication */ - PKE_REG_MASK_GET(me, STAT, PIS)) - { - /* (still) stalled */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_STALL); - /* try again next cycle */ - return; - } - - - /* 3 -- decode PKE instruction */ - - /* decoding */ - if(PKE_REG_MASK_GET(me, STAT, PPS) == PKE_REG_STAT_PPS_IDLE) - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_DECODE); - - /* Extract relevant bits from PKEcode */ - intr = BIT_MASK_GET(fw, PKE_OPCODE_I_B, PKE_OPCODE_I_E); - cmd = BIT_MASK_GET(fw, PKE_OPCODE_CMD_B, PKE_OPCODE_CMD_E); - - /* handle interrupts */ - if(intr) - { - /* check to see if the interrupt bit is being used for a breakpoint */ - if (is_vif_breakpoint ((fqw->source_address & ~15) | (me->qw_pc << 2))) - { - sim_cpu *cpu = STATE_CPU (sd, 0); - unsigned_4 pc_addr = (fqw->source_address & ~15) | (me->qw_pc << 2); - - sim_engine_halt (sd, cpu, NULL, pc_addr, sim_stopped, SIM_SIGTRAP); - } - - /* are we resuming an interrupt-stalled instruction? */ - if(me->flags & PKE_FLAG_INT_NOLOOP) - { - /* clear loop-prevention flag */ - me->flags &= ~PKE_FLAG_INT_NOLOOP; - - /* fall through to decode & execute */ - /* The pke_code_* functions should not check the MSB in the - pkecode. */ - } - else /* new interrupt-flagged instruction */ - { - /* set INT flag in STAT register */ - PKE_REG_MASK_SET(me, STAT, INT, 1); - /* set loop-prevention flag */ - me->flags |= PKE_FLAG_INT_NOLOOP; - - /* set PIS if stall not masked */ - if(!PKE_REG_MASK_GET(me, ERR, MII)) - pke_begin_interrupt_stall(me); - - /* suspend this instruction unless it's PKEMARK */ - if(!IS_PKE_CMD(cmd, PKEMARK)) - { - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_STALL); - return; - } - else - { - ; /* fall through to decode & execute */ - } - } - } - - /* open trace file if necessary */ - if((me->flags & PKE_FLAG_TRACE_ON) && - (me->trace_file == NULL)) - { - /* use default names */ - if(me->trace_file_name == NULL) - { - if(me->pke_number == 0) - me->trace_file_name = (char *) pke0_default_trace; - else - me->trace_file_name = (char *) pke1_default_trace; - } - - sky_open_file(& (me->trace_file), - me->trace_file_name, - (char *) NULL, _IOFBF ); - - /* print disassembly header */ - fprintf(me->trace_file, - "\t.global %s_disassembly_tag\n" - "%s_disassembly_tag:\n", - me->dev.name, me->dev.name); - } - - /* decode & execute */ - /* order tests in decreasing order of frequency */ - if(IS_PKE_CMD(cmd, PKENOP)) - pke_code_nop(me, fw); - else if(IS_PKE_CMD(cmd, PKEMSCAL)) - pke_code_pkemscal(me, fw); - else if(IS_PKE_CMD(cmd, PKEMSCNT)) - pke_code_pkemscnt(me, fw); - else if(me->pke_number == 1 && IS_PKE_CMD(cmd, PKEMSCALF)) - pke_code_pkemscalf(me, fw); - else if(IS_PKE_CMD(cmd, UNPACK)) - pke_code_unpack(me, fw); - else if(IS_PKE_CMD(cmd, STCYCL)) - pke_code_stcycl(me, fw); - else if(IS_PKE_CMD(cmd, FLUSHE)) - pke_code_flushe(me, fw); - else if(me->pke_number == 1 && IS_PKE_CMD(cmd, FLUSH)) - pke_code_flush(me, fw); - else if(me->pke_number == 1 && IS_PKE_CMD(cmd, FLUSHA)) - pke_code_flusha(me, fw); - else if(IS_PKE_CMD(cmd, DIRECT)) - pke_code_direct(me, fw); - else if(IS_PKE_CMD(cmd, DIRECTHL)) - pke_code_directhl(me, fw); - else if(me->pke_number == 1 && IS_PKE_CMD(cmd, OFFSET)) - pke_code_offset(me, fw); - else if(me->pke_number == 1 && IS_PKE_CMD(cmd, BASE)) - pke_code_base(me, fw); - else if(IS_PKE_CMD(cmd, ITOP)) - pke_code_itop(me, fw); - else if(IS_PKE_CMD(cmd, STMOD)) - pke_code_stmod(me, fw); - else if(IS_PKE_CMD(cmd, PKEMARK)) - pke_code_pkemark(me, fw); - else if(IS_PKE_CMD(cmd, STMASK)) - pke_code_stmask(me, fw); - else if(IS_PKE_CMD(cmd, STROW)) - pke_code_strow(me, fw); - else if(IS_PKE_CMD(cmd, STCOL)) - pke_code_stcol(me, fw); - else if(IS_PKE_CMD(cmd, MPG)) - pke_code_mpg(me, fw); - else if(me->pke_number == 1 && IS_PKE_CMD(cmd, MSKPATH3)) - pke_code_mskpath3(me, fw); - /* ... no other commands ... */ - else - pke_code_error(me, fw); -} - - - -/* Clear out contents of FIFO; act as if it was empty. Return PC - pointing to one-past-last word. */ - -unsigned_4 -pke_fifo_flush(struct pke_fifo* fifo) -{ - /* don't modify any state! */ - return fifo->origin + fifo->next; -} - - - -/* Clear out contents of FIFO; make it really empty. */ - -void -pke_fifo_reset(struct pke_fifo* fifo) -{ - int i; - - /* clear fifo quadwords */ - for(i=0; inext; i++) - { - zfree(fifo->quadwords[i]); - fifo->quadwords[i] = NULL; - } - - /* reset pointers */ - fifo->origin = 0; - fifo->next = 0; -} - - - -/* Make space for the next quadword in the FIFO. Allocate/enlarge - FIFO pointer block if necessary. Return a pointer to it. */ - -struct fifo_quadword* -pke_fifo_fit(struct pke_fifo* fifo) -{ - struct fifo_quadword* fqw; - - /* out of space on quadword pointer array? */ - if(fifo->next == fifo->length) /* also triggered before fifo->quadwords allocated */ - { - struct fifo_quadword** new_qw; - unsigned_4 new_length = fifo->length + PKE_FIFO_GROW_SIZE; - - /* allocate new pointer block */ - new_qw = zalloc(new_length * sizeof(struct fifo_quadword*)); - ASSERT(new_qw != NULL); - - /* copy over old contents, if any */ - if(fifo->quadwords != NULL) - { - /* copy over old pointers to beginning of new block */ - memcpy(new_qw, fifo->quadwords, - fifo->length * sizeof(struct fifo_quadword*)); - - /* free old block */ - zfree(fifo->quadwords); - } - - /* replace pointers & counts */ - fifo->quadwords = new_qw; - fifo->length = new_length; - } - - /* sanity check */ - ASSERT(fifo->quadwords != NULL); - - /* allocate new quadword from heap */ - fqw = zalloc(sizeof(struct fifo_quadword)); - ASSERT(fqw != NULL); - - /* push quadword onto fifo */ - fifo->quadwords[fifo->next] = fqw; - fifo->next++; - return fqw; -} - - - -/* Return a pointer to the FIFO quadword with given absolute index, or - NULL if it is out of range */ - -struct fifo_quadword* -pke_fifo_access(struct pke_fifo* fifo, unsigned_4 qwnum) -{ - struct fifo_quadword* fqw; - - if((qwnum < fifo->origin) || /* before history */ - (qwnum >= fifo->origin + fifo->next)) /* after last available quadword */ - fqw = NULL; - else - { - ASSERT(fifo->quadwords != NULL); /* must be allocated already */ - fqw = fifo->quadwords[qwnum - fifo->origin]; /* pull out pointer from array */ - ASSERT(fqw != NULL); /* must be allocated already */ - } - - return fqw; -} - - -/* Authorize release of any FIFO entries older than given absolute quadword. */ -void -pke_fifo_old(struct pke_fifo* fifo, unsigned_4 qwnum) -{ - /* do we have any too-old FIFO elements? */ - if(fifo->origin + PKE_FIFO_ARCHEOLOGY < qwnum) - { - /* count quadwords to forget */ - int horizon = qwnum - (fifo->origin + PKE_FIFO_ARCHEOLOGY); - int i; - - /* free quadwords at indices below horizon */ - for(i=0; i < horizon; i++) - zfree(fifo->quadwords[i]); - - /* move surviving quadword pointers down to beginning of array */ - for(i=horizon; i < fifo->next; i++) - fifo->quadwords[i-horizon] = fifo->quadwords[i]; - - /* clear duplicate pointers */ - for(i=fifo->next - horizon; i < fifo->next; i++) - fifo->quadwords[i] = NULL; - - /* adjust FIFO pointers */ - fifo->origin = fifo->origin + horizon; - fifo->next = fifo->next - horizon; - } -} - - - - -/* advance the PC by given number of data words; update STAT/FQC - field; assume FIFO is filled enough; classify passed-over words; - write FIFO trace line */ - -void -pke_pc_advance(struct pke_device* me, int num_words) -{ - int num = num_words; - struct fifo_quadword* fq = NULL; - unsigned_4 old_fifo_pc = me->fifo_pc; - - ASSERT(num_words >= 0); - - /* printf("pke %d pc_advance num_words %d\n", me->pke_number, num_words); */ - - while(1) - { - /* find next quadword, if any */ - fq = pke_fifo_access(& me->fifo, me->fifo_pc); - - /* skip over DMA tag words if present in word 0 or 1 */ - if(fq != NULL && fq->word_class[me->qw_pc] == wc_dma) - { - /* skip by going around loop an extra time */ - num ++; - } - - /* nothing left to skip / no DMA tag here */ - if(num == 0) - break; - - /* we are supposed to skip existing words */ - ASSERT(fq != NULL); - - /* one word skipped */ - num --; - - /* point to next word */ - me->qw_pc ++; - if(me->qw_pc == 4) - { - me->qw_pc = 0; - me->fifo_pc ++; - - /* trace the consumption of the FIFO quadword we just skipped over */ - /* fq still points to it */ - if ( indebug (me->dev.name)) - { - if (( me->fifo_trace_file == NULL) && - ( me->fifo_trace_file_name != NULL )) - sky_open_file (&me->fifo_trace_file, me->fifo_trace_file_name, - (char *) NULL, _IOLBF ); - - /* assert complete classification */ - ASSERT(fq->word_class[3] != wc_unknown); - ASSERT(fq->word_class[2] != wc_unknown); - ASSERT(fq->word_class[1] != wc_unknown); - ASSERT(fq->word_class[0] != wc_unknown); - - /* print trace record */ - fprintf((me->fifo_trace_file != NULL) ? me->fifo_trace_file : stdout, - "%d 0x%08x_%08x_%08x_%08x 0x%08x %c%c%c%c\n", - (me->pke_number == 0 ? 0 : 1), - (unsigned) fq->data[3], (unsigned) fq->data[2], - (unsigned) fq->data[1], (unsigned) fq->data[0], - (unsigned) fq->source_address, - fq->word_class[3], fq->word_class[2], - fq->word_class[1], fq->word_class[0]); - } - } /* next quadword */ - } - - /* age old entries before PC */ - if(me->fifo_pc != old_fifo_pc) - { - /* we advanced the fifo-pc; authorize disposal of anything - before previous PKEcode */ - pke_fifo_old(& me->fifo, old_fifo_pc); - } - - /* clear FQC if FIFO is now empty */ - fq = pke_fifo_access(& me->fifo, me->fifo_pc); - if(fq == NULL) - { - PKE_REG_MASK_SET(me, STAT, FQC, 0); - } - else /* annote the word where the PC lands as an PKEcode */ - { - ASSERT(fq->word_class[me->qw_pc] == wc_pkecode || fq->word_class[me->qw_pc] == wc_unknown); - fq->word_class[me->qw_pc] = wc_pkecode; - } -} - - - - - -/* Return pointer to FIFO quadword containing given operand# in FIFO. - `operand_num' starts at 1. Return pointer to operand word in last - argument, if non-NULL. If FIFO is not full enough, return 0. - Signal an ER0 indication upon skipping a DMA tag. */ - -struct fifo_quadword* -pke_pcrel_fifo(struct pke_device* me, int operand_num, unsigned_4** operand) -{ - int num; - int new_qw_pc, new_fifo_pc; - struct fifo_quadword* fq = NULL; - - /* check for validity of last search results in cache */ - if(me->last_fifo_pc == me->fifo_pc && - me->last_qw_pc == me->qw_pc && - operand_num > me->last_num) - { - /* continue search from last stop */ - new_fifo_pc = me->last_new_fifo_pc; - new_qw_pc = me->last_new_qw_pc; - num = operand_num - me->last_num; - } - else - { - /* start search from scratch */ - new_fifo_pc = me->fifo_pc; - new_qw_pc = me->qw_pc; - num = operand_num; - } - - ASSERT(num > 0); - - /* printf("pke %d pcrel_fifo operand_num %d\n", me->pke_number, operand_num); */ - - do - { - /* one word skipped */ - num --; - - /* point to next word */ - new_qw_pc ++; - if(new_qw_pc == 4) - { - new_qw_pc = 0; - new_fifo_pc ++; - } - - fq = pke_fifo_access(& me->fifo, new_fifo_pc); - - /* check for FIFO underflow */ - if(fq == NULL) - break; - - /* skip over DMA tag words if present in word 0 or 1 */ - if(fq->word_class[new_qw_pc] == wc_dma) - { - /* set ER0 */ - PKE_REG_MASK_SET(me, STAT, ER0, 1); - - /* mismatch error! */ - if(! PKE_REG_MASK_GET(me, ERR, ME0)) - { - pke_begin_interrupt_stall(me); - /* don't stall just yet -- finish this instruction */ - /* the PPS_STALL state will be entered by pke_issue() next time */ - } - /* skip by going around loop an extra time */ - num ++; - } - } - while(num > 0); - - /* return pointer to operand word itself */ - if(fq != NULL) - { - *operand = & fq->data[new_qw_pc]; - - /* annote the word where the pseudo-PC lands as an PKE operand */ - ASSERT(fq->word_class[new_qw_pc] == wc_pkedata || fq->word_class[new_qw_pc] == wc_unknown); - fq->word_class[new_qw_pc] = wc_pkedata; - - /* store search results in cache */ - /* keys */ - me->last_fifo_pc = me->fifo_pc; - me->last_qw_pc = me->qw_pc; - /* values */ - me->last_num = operand_num; - me->last_new_fifo_pc = new_fifo_pc; - me->last_new_qw_pc = new_qw_pc; - } - - return fq; -} - - -/* Return pointer to given operand# in FIFO. `operand_num' starts at 1. - If FIFO is not full enough, return 0. Skip over DMA tags, but mark - them as an error (ER0). */ - -unsigned_4* -pke_pcrel_operand(struct pke_device* me, int operand_num) -{ - unsigned_4* operand = NULL; - struct fifo_quadword* fifo_operand; - - fifo_operand = pke_pcrel_fifo(me, operand_num, & operand); - - if(fifo_operand == NULL) - ASSERT(operand == NULL); /* pke_pcrel_fifo() ought leave it untouched */ - - return operand; -} - - -/* Return a bit-field extract of given operand# in FIFO, and its - word-accurate source-addr. `bit_offset' starts at 0, referring to - LSB after PKE instruction word. Width must be >0, <=32. Assume - FIFO is full enough. Skip over DMA tags, but mark them as an error - (ER0). */ - -unsigned_4 -pke_pcrel_operand_bits(struct pke_device* me, int bit_offset, int bit_width, unsigned_4* source_addr) -{ - unsigned_4* word = NULL; - unsigned_4 value; - struct fifo_quadword* fifo_operand; - int wordnumber, bitnumber; - int i; - - wordnumber = bit_offset/32; - bitnumber = bit_offset%32; - - /* find operand word with bitfield */ - fifo_operand = pke_pcrel_fifo(me, wordnumber + 1, &word); - ASSERT(word != NULL); - - /* extract bitfield from word */ - value = BIT_MASK_GET(*word, bitnumber, bitnumber + bit_width - 1); - - /* extract source addr from fifo word */ - *source_addr = fifo_operand->source_address; - - /* add word offset */ - for(i=0; i<3; i++) - if(word == & fifo_operand->data[i]) - *source_addr += sizeof(unsigned_4) * i; - - return value; -} - - - -/* check for stall conditions on indicated devices (path* only on - PKE1), do not change status; return 0 iff no stall */ -int -pke_check_stall(struct pke_device* me, enum pke_check_target what) -{ - int any_stall = 0; - unsigned_4 cop2_stat, gpuif_stat; - - /* read status words */ - ASSERT(sizeof(unsigned_4) == 4); - PKE_MEM_READ(me, (GIF_REG_STAT), - & gpuif_stat, - 4); - PKE_MEM_READ(me, (COP2_REG_STAT_ADDR), - & cop2_stat, - 4); - - /* perform checks */ - if(what == chk_vu) - { - if(me->pke_number == 0) - any_stall = BIT_MASK_GET(cop2_stat, COP2_REG_STAT_VBS0_B, COP2_REG_STAT_VBS0_E); - else /* if(me->pke_number == 1) */ - any_stall = BIT_MASK_GET(cop2_stat, COP2_REG_STAT_VBS1_B, COP2_REG_STAT_VBS1_E); - } - else if(what == chk_path1) /* VU -> GPUIF */ - { - ASSERT(me->pke_number == 1); - if(BIT_MASK_GET(gpuif_stat, GPUIF_REG_STAT_APATH_B, GPUIF_REG_STAT_APATH_E) == 1) - any_stall = 1; - } - else if(what == chk_path2) /* PKE -> GPUIF */ - { - ASSERT(me->pke_number == 1); - if(BIT_MASK_GET(gpuif_stat, GPUIF_REG_STAT_APATH_B, GPUIF_REG_STAT_APATH_E) == 2) - any_stall = 1; - } - else if(what == chk_path3) /* DMA -> GPUIF */ - { - ASSERT(me->pke_number == 1); - if(BIT_MASK_GET(gpuif_stat, GPUIF_REG_STAT_APATH_B, GPUIF_REG_STAT_APATH_E) == 3) - any_stall = 1; - } - else - { - /* invalid what */ - ASSERT(0); - } - - /* any stall reasons? */ - return any_stall; -} - - -/* PKE1 only: flip the DBF bit; recompute TOPS, TOP */ -void -pke_flip_dbf(struct pke_device* me) -{ - int newdf; - /* compute new TOP */ - PKE_REG_MASK_SET(me, TOP, TOP, - PKE_REG_MASK_GET(me, TOPS, TOPS)); - /* flip DBF */ - newdf = PKE_REG_MASK_GET(me, DBF, DF) ? 0 : 1; - PKE_REG_MASK_SET(me, DBF, DF, newdf); - PKE_REG_MASK_SET(me, STAT, DBF, newdf); - /* compute new TOPS */ - PKE_REG_MASK_SET(me, TOPS, TOPS, - (PKE_REG_MASK_GET(me, BASE, BASE) + - newdf * PKE_REG_MASK_GET(me, OFST, OFFSET))); - - /* this is equivalent to last word from okadaa (98-02-25): - 1) TOP=TOPS; - 2) TOPS=BASE + !DBF*OFFSET - 3) DBF=!DBF */ -} - - -/* set the STAT:PIS bit and send an interrupt to the 5900 */ -void -pke_begin_interrupt_stall(struct pke_device* me) -{ - /* set PIS */ - PKE_REG_MASK_SET(me, STAT, PIS, 1); - sky_signal_interrupt(); -} - - - - -/* PKEcode handler functions -- responsible for checking and - confirming old stall conditions, executing pkecode, updating PC and - status registers -- may assume being run on correct PKE unit */ - -void -pke_code_nop(struct pke_device* me, unsigned_4 pkecode) -{ - /* done */ - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tVIFNOP%s\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "[i]" : "")); - } - pke_pc_advance(me, 1); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); -} - - -void -pke_code_stcycl(struct pke_device* me, unsigned_4 pkecode) -{ - int imm = BIT_MASK_GET(pkecode, PKE_OPCODE_IMM_B, PKE_OPCODE_IMM_E); - - /* copy immediate value into CYCLE reg */ - PKE_REG_MASK_SET(me, CYCLE, WL, BIT_MASK_GET(imm, 8, 15)); - PKE_REG_MASK_SET(me, CYCLE, CL, BIT_MASK_GET(imm, 0, 7)); - /* done */ - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tSTCYCL%s %d,%d\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "[i]" : ""), - BIT_MASK_GET(imm, 8, 15), BIT_MASK_GET(imm, 0, 7)); - } - pke_pc_advance(me, 1); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); -} - - -void -pke_code_offset(struct pke_device* me, unsigned_4 pkecode) -{ - int imm = BIT_MASK_GET(pkecode, PKE_OPCODE_IMM_B, PKE_OPCODE_IMM_E); - - /* copy 10 bits to OFFSET field */ - PKE_REG_MASK_SET(me, OFST, OFFSET, BIT_MASK_GET(imm, 0, 9)); - /* clear DBF bit */ - PKE_REG_MASK_SET(me, DBF, DF, 0); - /* clear other DBF bit */ - PKE_REG_MASK_SET(me, STAT, DBF, 0); - /* set TOPS = BASE */ - PKE_REG_MASK_SET(me, TOPS, TOPS, PKE_REG_MASK_GET(me, BASE, BASE)); - /* done */ - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tOFFSET%s 0x%x\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "[i]" : ""), - imm); - } - pke_pc_advance(me, 1); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); -} - - -void -pke_code_base(struct pke_device* me, unsigned_4 pkecode) -{ - int imm = BIT_MASK_GET(pkecode, PKE_OPCODE_IMM_B, PKE_OPCODE_IMM_E); - - /* copy 10 bits to BASE field */ - PKE_REG_MASK_SET(me, BASE, BASE, BIT_MASK_GET(imm, 0, 9)); - /* done */ - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tBASE%s 0x%x\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "[i]" : ""), - imm); - } - pke_pc_advance(me, 1); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); -} - - -void -pke_code_itop(struct pke_device* me, unsigned_4 pkecode) -{ - int imm = BIT_MASK_GET(pkecode, PKE_OPCODE_IMM_B, PKE_OPCODE_IMM_E); - - /* copy 10 bits to ITOPS field */ - PKE_REG_MASK_SET(me, ITOPS, ITOPS, BIT_MASK_GET(imm, 0, 9)); - /* done */ - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tITOP%s 0x%x\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "[i]" : ""), - imm); - } - pke_pc_advance(me, 1); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); -} - - -void -pke_code_stmod(struct pke_device* me, unsigned_4 pkecode) -{ - int imm = BIT_MASK_GET(pkecode, PKE_OPCODE_IMM_B, PKE_OPCODE_IMM_E); - - /* copy 2 bits to MODE register */ - PKE_REG_MASK_SET(me, MODE, MDE, BIT_MASK_GET(imm, 0, 1)); - /* done */ - if(me->trace_file != NULL) - { - char* mode; - if(BIT_MASK_GET(imm, 0, 1) == 0) mode = "direct"; - else if(BIT_MASK_GET(imm, 0, 1) == 1) mode = "add"; - else if(BIT_MASK_GET(imm, 0, 1) == 2) mode = "addrow"; - else mode = "3"; /* invalid mode */ - - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tSTMOD%s %s\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "[i]" : ""), - mode); - } - pke_pc_advance(me, 1); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); -} - - -void -pke_code_mskpath3(struct pke_device* me, unsigned_4 pkecode) -{ - int imm = BIT_MASK_GET(pkecode, PKE_OPCODE_IMM_B, PKE_OPCODE_IMM_E); - unsigned_4 gif_mode; - - /* set appropriate bit */ - if(BIT_MASK_GET(imm, PKE_REG_MSKPATH3_B, PKE_REG_MSKPATH3_E) != 0) - gif_mode = GIF_REG_STAT_M3P; - else - gif_mode = 0; - - /* write register to "read-only" register; gpuif code will look at M3P bit only */ - PKE_MEM_WRITE(me, GIF_REG_VIF_M3P, & gif_mode, 4); - - /* done */ - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tMSKPATH3%s %s\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "[i]" : ""), - (gif_mode ? "disable" : "enable")); - } - pke_pc_advance(me, 1); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); -} - - -void -pke_code_pkemark(struct pke_device* me, unsigned_4 pkecode) -{ - int imm = BIT_MASK_GET(pkecode, PKE_OPCODE_IMM_B, PKE_OPCODE_IMM_E); - /* copy 16 bits to MARK register */ - PKE_REG_MASK_SET(me, MARK, MARK, BIT_MASK_GET(imm, 0, 15)); - /* set MRK bit in STAT register - CPU2 v2.1 docs incorrect */ - PKE_REG_MASK_SET(me, STAT, MRK, 1); - /* done */ - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tMARK%s 0x%x\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "[i]" : ""), - imm); - } - pke_pc_advance(me, 1); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); -} - - -void -pke_code_flushe(struct pke_device* me, unsigned_4 pkecode) -{ - /* compute next PEW bit */ - if(pke_check_stall(me, chk_vu)) - { - /* VU busy */ - PKE_REG_MASK_SET(me, STAT, PEW, 1); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_STALL); - /* try again next cycle */ - } - else - { - /* VU idle */ - PKE_REG_MASK_SET(me, STAT, PEW, 0); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tFLUSHE%s\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "[i]" : "")); - } - pke_pc_advance(me, 1); - } -} - - -void -pke_code_flush(struct pke_device* me, unsigned_4 pkecode) -{ - int something_busy = 0; - - /* compute next PEW, PGW bits */ - if(pke_check_stall(me, chk_vu)) - { - something_busy = 1; - PKE_REG_MASK_SET(me, STAT, PEW, 1); - } - else - PKE_REG_MASK_SET(me, STAT, PEW, 0); - - - if(pke_check_stall(me, chk_path1) || - pke_check_stall(me, chk_path2)) - { - something_busy = 1; - PKE_REG_MASK_SET(me, STAT, PGW, 1); - } - else - PKE_REG_MASK_SET(me, STAT, PGW, 0); - - /* go or no go */ - if(something_busy) - { - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_WAIT); - /* try again next cycle */ - } - else - { - /* all idle */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tFLUSH%s\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "[i]" : "")); - } - pke_pc_advance(me, 1); - } -} - - -void -pke_code_flusha(struct pke_device* me, unsigned_4 pkecode) -{ - int something_busy = 0; - - /* compute next PEW, PGW bits */ - if(pke_check_stall(me, chk_vu)) - { - something_busy = 1; - PKE_REG_MASK_SET(me, STAT, PEW, 1); - } - else - PKE_REG_MASK_SET(me, STAT, PEW, 0); - - - if(pke_check_stall(me, chk_path1) || - pke_check_stall(me, chk_path2) || - pke_check_stall(me, chk_path3)) - { - something_busy = 1; - PKE_REG_MASK_SET(me, STAT, PGW, 1); - } - else - PKE_REG_MASK_SET(me, STAT, PGW, 0); - - if(something_busy) - { - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_WAIT); - /* try again next cycle */ - } - else - { - /* all idle */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tFLUSHA%s\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "[i]" : "")); - } - pke_pc_advance(me, 1); - } -} - - -void -pke_code_pkemscal(struct pke_device* me, unsigned_4 pkecode) -{ - /* compute next PEW bit */ - if(pke_check_stall(me, chk_vu)) - { - /* VU busy */ - PKE_REG_MASK_SET(me, STAT, PEW, 1); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_STALL); - /* try again next cycle */ - } - else - { - unsigned_4 vu_pc; - int imm = BIT_MASK_GET(pkecode, PKE_OPCODE_IMM_B, PKE_OPCODE_IMM_E); - - /* VU idle */ - PKE_REG_MASK_SET(me, STAT, PEW, 0); - - /* flip DBF on PKE1 */ - if(me->pke_number == 1) - pke_flip_dbf(me); - - /* compute new PC for VU (host byte-order) */ - vu_pc = BIT_MASK_GET(imm, 0, 15); - vu_pc = T2H_4(vu_pc); - - /* write new PC; callback function gets VU running */ - ASSERT(sizeof(unsigned_4) == 4); - PKE_MEM_WRITE(me, (me->pke_number == 0 ? VU0_CIA : VU1_CIA), - & vu_pc, - 4); - - /* copy ITOPS field to ITOP */ - PKE_REG_MASK_SET(me, ITOP, ITOP, PKE_REG_MASK_GET(me, ITOPS, ITOPS)); - - /* done */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tMSCAL%s 0x%x\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "[i]" : ""), - imm); - } - pke_pc_advance(me, 1); - } -} - - - -void -pke_code_pkemscnt(struct pke_device* me, unsigned_4 pkecode) -{ - /* compute next PEW bit */ - if(pke_check_stall(me, chk_vu)) - { - /* VU busy */ - PKE_REG_MASK_SET(me, STAT, PEW, 1); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_STALL); - /* try again next cycle */ - } - else - { - unsigned_4 vu_pc; - - /* VU idle */ - PKE_REG_MASK_SET(me, STAT, PEW, 0); - - /* flip DBF on PKE1 */ - if(me->pke_number == 1) - pke_flip_dbf(me); - - /* read old PC */ - ASSERT(sizeof(unsigned_4) == 4); - PKE_MEM_READ(me, (me->pke_number == 0 ? VU0_CIA : VU1_CIA), - & vu_pc, - 4); - - /* rewrite new PC; callback function gets VU running */ - ASSERT(sizeof(unsigned_4) == 4); - PKE_MEM_WRITE(me, (me->pke_number == 0 ? VU0_CIA : VU1_CIA), - & vu_pc, - 4); - - /* copy ITOPS field to ITOP */ - PKE_REG_MASK_SET(me, ITOP, ITOP, PKE_REG_MASK_GET(me, ITOPS, ITOPS)); - - /* done */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tMSCNT\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc); - } - pke_pc_advance(me, 1); - } -} - - -void -pke_code_pkemscalf(struct pke_device* me, unsigned_4 pkecode) -{ - int something_busy = 0; - - /* compute next PEW, PGW bits */ - if(pke_check_stall(me, chk_vu)) - { - something_busy = 1; - PKE_REG_MASK_SET(me, STAT, PEW, 1); - } - else - PKE_REG_MASK_SET(me, STAT, PEW, 0); - - - if(pke_check_stall(me, chk_path1) || - pke_check_stall(me, chk_path2) || - pke_check_stall(me, chk_path3)) - { - something_busy = 1; - PKE_REG_MASK_SET(me, STAT, PGW, 1); - } - else - PKE_REG_MASK_SET(me, STAT, PGW, 0); - - /* go or no go */ - if(something_busy) - { - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_WAIT); - /* try again next cycle */ - } - else - { - unsigned_4 vu_pc; - int imm = BIT_MASK_GET(pkecode, PKE_OPCODE_IMM_B, PKE_OPCODE_IMM_E); - - /* flip DBF on PKE1 */ - if(me->pke_number == 1) - pke_flip_dbf(me); - - /* compute new PC for VU (host byte-order) */ - vu_pc = BIT_MASK_GET(imm, 0, 15); - vu_pc = T2H_4(vu_pc); - - /* rewrite new PC; callback function gets VU running */ - ASSERT(sizeof(unsigned_4) == 4); - PKE_MEM_WRITE(me, (me->pke_number == 0 ? VU0_CIA : VU1_CIA), - & vu_pc, - 4); - - /* copy ITOPS field to ITOP */ - PKE_REG_MASK_SET(me, ITOP, ITOP, PKE_REG_MASK_GET(me, ITOPS, ITOPS)); - - /* done */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tMSCALF 0x%x\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - imm); - } - pke_pc_advance(me, 1); - } -} - - -void -pke_code_stmask(struct pke_device* me, unsigned_4 pkecode) -{ - unsigned_4* mask; - - /* check that FIFO has one more word for STMASK operand */ - mask = pke_pcrel_operand(me, 1); - if(mask != NULL) - { - /* "transferring" operand */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_XFER); - - /* set NUM */ - PKE_REG_MASK_SET(me, NUM, NUM, 1); - - /* fill the register */ - PKE_REG_MASK_SET(me, MASK, MASK, *mask); - - /* set NUM */ - PKE_REG_MASK_SET(me, NUM, NUM, 0); - - /* done */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tSTMASK 0x%x\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - *mask); - } - pke_pc_advance(me, 2); - } - else - { - /* need to wait for another word */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_WAIT); - /* try again next cycle */ - } -} - - -void -pke_code_strow(struct pke_device* me, unsigned_4 pkecode) -{ - /* check that FIFO has four more words for STROW operand */ - unsigned_4* last_op; - - last_op = pke_pcrel_operand(me, 4); - if(last_op != NULL) - { - /* "transferring" operand */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_XFER); - - /* set NUM */ - PKE_REG_MASK_SET(me, NUM, NUM, 1); - - /* copy ROW registers: must all exist if 4th operand exists */ - me->regs[PKE_REG_R0][0] = * pke_pcrel_operand(me, 1); - me->regs[PKE_REG_R1][0] = * pke_pcrel_operand(me, 2); - me->regs[PKE_REG_R2][0] = * pke_pcrel_operand(me, 3); - me->regs[PKE_REG_R3][0] = * pke_pcrel_operand(me, 4); - - /* set NUM */ - PKE_REG_MASK_SET(me, NUM, NUM, 0); - - /* done */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tSTROW 0x%x,0x%x,0x%x,0x%x\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - * pke_pcrel_operand(me, 1), - * pke_pcrel_operand(me, 2), - * pke_pcrel_operand(me, 3), - * pke_pcrel_operand(me, 4)); - } - pke_pc_advance(me, 5); - } - else - { - /* need to wait for another word */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_WAIT); - /* try again next cycle */ - } -} - - -void -pke_code_stcol(struct pke_device* me, unsigned_4 pkecode) -{ - /* check that FIFO has four more words for STCOL operand */ - unsigned_4* last_op; - - last_op = pke_pcrel_operand(me, 4); - if(last_op != NULL) - { - /* "transferring" operand */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_XFER); - - /* set NUM */ - PKE_REG_MASK_SET(me, NUM, NUM, 1); - - /* copy COL registers: must all exist if 4th operand exists */ - me->regs[PKE_REG_C0][0] = * pke_pcrel_operand(me, 1); - me->regs[PKE_REG_C1][0] = * pke_pcrel_operand(me, 2); - me->regs[PKE_REG_C2][0] = * pke_pcrel_operand(me, 3); - me->regs[PKE_REG_C3][0] = * pke_pcrel_operand(me, 4); - - /* set NUM */ - PKE_REG_MASK_SET(me, NUM, NUM, 0); - - /* done */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tSTCOL 0x%x,0x%x,0x%x,0x%x\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - * pke_pcrel_operand(me, 1), - * pke_pcrel_operand(me, 2), - * pke_pcrel_operand(me, 3), - * pke_pcrel_operand(me, 4)); - } - pke_pc_advance(me, 5); - } - else - { - /* need to wait for another word */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_WAIT); - /* try again next cycle */ - } -} - - -void -pke_code_mpg(struct pke_device* me, unsigned_4 pkecode) -{ - unsigned_4* last_mpg_word; - int num = BIT_MASK_GET(pkecode, PKE_OPCODE_NUM_B, PKE_OPCODE_NUM_E); - int imm = BIT_MASK_GET(pkecode, PKE_OPCODE_IMM_B, PKE_OPCODE_IMM_E); - - /* assert 64-bit alignment of MPG operand */ - if(me->qw_pc != 3 && me->qw_pc != 1) - return pke_code_error(me, pkecode); - - /* map zero to max+1 */ - if(num==0) num=0x100; - - /* check that FIFO has a few more words for MPG operand */ - last_mpg_word = pke_pcrel_operand(me, num*2); /* num: number of 64-bit words */ - if(last_mpg_word != NULL) - { - /* perform implied FLUSHE */ - if(pke_check_stall(me, chk_vu)) - { - /* VU busy */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_STALL); - /* retry this instruction next clock */ - } - else - { - /* VU idle */ - int i; - - /* "transferring" operand */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_XFER); - - /* set NUM */ - PKE_REG_MASK_SET(me, NUM, NUM, num); - - /* disassembly */ - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tMPG 0x%x,0x%x\n", - me->dev.name, me->fifo_pc, me->qw_pc, - imm, num); - } - - /* transfer VU instructions, one word-pair per iteration */ - for(i=0; ipke_number == 0) ? - VU0_MEM0_WINDOW_START : VU1_MEM0_WINDOW_START; - vu_addr_max_size = (me->pke_number == 0) ? - VU0_MEM0_SIZE : VU1_MEM0_SIZE; - vutrack_addr_base = (me->pke_number == 0) ? - VU0_MEM0_SRCADDR_START : VU1_MEM0_SRCADDR_START; - - /* compute VU address for this word-pair */ - vu_addr = vu_addr_base + (imm + i) * 8; - /* check for vu_addr overflow */ - while(vu_addr >= vu_addr_base + vu_addr_max_size) - vu_addr -= vu_addr_max_size; - - /* compute VU tracking address */ - vutrack_addr = vutrack_addr_base + ((signed_8)vu_addr - (signed_8)vu_addr_base) / 2; - - /* Fetch operand words; assume they are already little-endian for VU imem */ - fq = pke_pcrel_fifo(me, i*2 + 1, & operand); - vu_lower_opcode = *operand; - - source_addr = fq->source_address; - /* add word offset */ - for(j=0; j<3; j++) - if(operand == & fq->data[j]) - source_addr += sizeof(unsigned_4) * j; - - fq = pke_pcrel_fifo(me, i*2 + 2, & operand); - vu_upper_opcode = *operand; - - /* write data into VU memory */ - /* lower (scalar) opcode comes in first word ; macro performs H2T! */ - PKE_MEM_WRITE(me, vu_addr, - & vu_lower_opcode, - 4); - /* upper (vector) opcode comes in second word ; H2T */ - ASSERT(sizeof(unsigned_4) == 4); - PKE_MEM_WRITE(me, vu_addr + 4, - & vu_upper_opcode, - 4); - - /* write tracking address in target byte-order */ - ASSERT(sizeof(unsigned_4) == 4); - PKE_MEM_WRITE(me, vutrack_addr, - & source_addr, - 4); - - /* disassembly */ - if(me->trace_file != NULL) - { - unsigned long opcodes[2] = { vu_upper_opcode, vu_lower_opcode }; - fprintf(me->trace_file, "\t"); - opcode_analyze(me->trace_file, opcodes); - fprintf(me->trace_file, "\n"); - } - } /* VU xfer loop */ - - /* check NUM */ - ASSERT(PKE_REG_MASK_GET(me, NUM, NUM) == 0); - - /* done */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\t.EndMpg\n" - "\t.EndDmaData\n"); - } - pke_pc_advance(me, 1 + num*2); - } - } /* if FIFO full enough */ - else - { - /* need to wait for another word */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_WAIT); - /* retry this instruction next clock */ - } -} - - -void -pke_code_direct(struct pke_device* me, unsigned_4 pkecode) -{ - /* check that FIFO has a few more words for DIRECT operand */ - unsigned_4* last_direct_word; - int imm = BIT_MASK_GET(pkecode, PKE_OPCODE_IMM_B, PKE_OPCODE_IMM_E); - - /* assert 128-bit alignment of DIRECT operand */ - if(me->qw_pc != 3) - return pke_code_error(me, pkecode); - - /* map zero to max+1 */ - if(imm==0) imm=0x10000; - - last_direct_word = pke_pcrel_operand(me, imm*4); /* imm: number of 128-bit words */ - if(last_direct_word != NULL) - { - /* VU idle */ - int i; - unsigned_16 fifo_data; - - /* "transferring" operand */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_XFER); - - /* disassembly */ - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\t%s 0x%x\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (IS_PKE_CMD(pkecode, DIRECT) ? "DIRECT" : "DIRECTHL"), - imm); - } - - /* transfer GPUIF quadwords, one word per iteration */ - for(i=0; itrace_file != NULL) - { - char buffer[200]; /* one line of disassembly */ - gif_disassemble_pke_data(buffer, (quadword*) &fifo_data); - fprintf(me->trace_file, "\t%s\n", buffer); - } - } /* write collected quadword */ - } /* GPUIF xfer loop */ - - /* done */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\t.EndDirect\n" - "\t.EndDmaData\n"); - } - pke_pc_advance(me, 1 + imm*4); - } /* if FIFO full enough */ - else - { - /* need to wait for another word */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_WAIT); - /* retry this instruction next clock */ - } -} - - -void -pke_code_directhl(struct pke_device* me, unsigned_4 pkecode) -{ - /* treat the same as DIRECT */ - pke_code_direct(me, pkecode); - /* dissassembly code handles DIRECT/DIRECTHL overloading */ -} - - -void -pke_code_unpack(struct pke_device* me, unsigned_4 pkecode) -{ - int imm = BIT_MASK_GET(pkecode, PKE_OPCODE_IMM_B, PKE_OPCODE_IMM_E); - int cmd = BIT_MASK_GET(pkecode, PKE_OPCODE_CMD_B, PKE_OPCODE_CMD_E); - int num = BIT_MASK_GET(pkecode, PKE_OPCODE_NUM_B, PKE_OPCODE_NUM_E); - int nummx = (num == 0) ? 0x0100 : num; - short vn = BIT_MASK_GET(cmd, 2, 3); /* unpack shape controls */ - short vl = BIT_MASK_GET(cmd, 0, 1); - int m = BIT_MASK_GET(cmd, 4, 4); - short cl = PKE_REG_MASK_GET(me, CYCLE, CL); /* cycle controls */ - short wl = PKE_REG_MASK_GET(me, CYCLE, WL); - short addrwl = (wl == 0) ? 0x0100 : wl; - int r = BIT_MASK_GET(imm, 15, 15); /* indicator bits in imm value */ - int usn = BIT_MASK_GET(imm, 14, 14); - - int n, num_operands; - unsigned_4* last_operand_word = NULL; - - /* catch all illegal UNPACK variants */ - if(vl == 3 && vn < 3) - { - pke_code_error(me, pkecode); - return; - } - - /* compute PKEcode length, as given in CPU2 spec, v2.1 pg. 11 */ - if(cl >= addrwl) - n = num; - else - n = cl * (nummx / addrwl) + PKE_LIMIT(nummx % addrwl, cl); - num_operands = (31 + (32 >> vl) * (vn+1) * n)/32; /* round up to next word */ - - /* confirm that FIFO has enough words in it */ - if(num_operands > 0) - last_operand_word = pke_pcrel_operand(me, num_operands); - if(last_operand_word != NULL || num_operands == 0) - { - address_word vu_addr_base, vutrack_addr_base; - address_word vu_addr_max_size; - int vector_num_out, vector_num_in; - - /* "transferring" operand */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_XFER); - - /* disassembly */ - if(me->trace_file != NULL) - { - char unpack_type[8]; - char flags[8]; - sprintf(flags,"[%s%s%s%s]", - (m ? "m" : ""), - (usn ? "u" : ""), - (r ? "r" : ""), - (BIT_MASK_GET(pkecode, PKE_OPCODE_I_B, PKE_OPCODE_I_E) ? "i" : "")); - if(vn > 0) - sprintf(unpack_type, "V%d_%d", - (vn + 1), - (vl == 3 ? 5 : (32 >> vl))); - else - sprintf(unpack_type, "S_%d", - (vl == 3 ? 5 : (32 >> vl))); - - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\tUNPACK%s %s,0x%x,0x%x\n", - me->dev.name, me->fifo_pc, me->qw_pc, - flags, unpack_type, imm, num); - } - - /* don't check whether VU is idle */ - - /* compute VU address base */ - if(me->pke_number == 0) - { - vu_addr_base = VU0_MEM1_WINDOW_START; - vu_addr_max_size = VU0_MEM1_SIZE; - vutrack_addr_base = VU0_MEM1_SRCADDR_START; - r = 0; - } - else - { - vu_addr_base = VU1_MEM1_WINDOW_START; - vu_addr_max_size = VU1_MEM1_SIZE; - vutrack_addr_base = VU1_MEM1_SRCADDR_START; - } - - /* set NUM */ - PKE_REG_MASK_SET(me, NUM, NUM, nummx); - - /* transfer given number of vectors */ - vector_num_out = 0; /* output vector number being processed */ - vector_num_in = 0; /* argument vector number being processed */ - do - { - quadword vu_old_data; - quadword vu_new_data; - quadword unpacked_data; - address_word vu_addr; - address_word vutrack_addr; - unsigned_4 source_addr = 0; - int i; - int next_num; - - /* decrement NUM */ - next_num = PKE_REG_MASK_GET(me, NUM, NUM) - 1; - PKE_REG_MASK_SET(me, NUM, NUM, next_num); - - /* compute VU destination address, as bytes in R5900 memory */ - if(cl >= wl) - { - /* map zero to max+1 */ - vu_addr = vu_addr_base + 16 * (BIT_MASK_GET(imm, 0, 9) + - (vector_num_out / addrwl) * cl + - (vector_num_out % addrwl)); - } - else - vu_addr = vu_addr_base + 16 * (BIT_MASK_GET(imm, 0, 9) + - vector_num_out); - - /* handle "R" double-buffering bit */ - if(r) - vu_addr += 16 * PKE_REG_MASK_GET(me, TOPS, TOPS); - - /* check for vu_addr overflow */ - while(vu_addr >= vu_addr_base + vu_addr_max_size) - vu_addr -= vu_addr_max_size; - - /* compute address of tracking table entry */ - vutrack_addr = vutrack_addr_base + ((signed_8)vu_addr - (signed_8)vu_addr_base) / 4; - - /* read old VU data word at address; reverse words if needed */ - { - unsigned_16 vu_old_badwords; - ASSERT(sizeof(vu_old_badwords) == 16); - PKE_MEM_READ(me, vu_addr, - &vu_old_badwords, 16); - vu_old_data[0] = * A4_16(& vu_old_badwords, 3); - vu_old_data[1] = * A4_16(& vu_old_badwords, 2); - vu_old_data[2] = * A4_16(& vu_old_badwords, 1); - vu_old_data[3] = * A4_16(& vu_old_badwords, 0); - } - - /* For cyclic unpack, next operand quadword may come from instruction stream - or be zero. */ - if((cl < addrwl) && - (vector_num_out % addrwl) >= cl) - { - /* clear operand - used only in a "indeterminate" state */ - for(i = 0; i < 4; i++) - unpacked_data[i] = 0; - } - else - { - /* compute packed vector dimensions */ - int vectorbits = 0, unitbits = 0; - - /* disassembly */ - if(me->trace_file != NULL) - { - fprintf(me->trace_file, "\t; unpack input row %d\n", vector_num_in); - } - - if(vl < 3) /* PKE_UNPACK_*_{32,16,8} */ - { - unitbits = (32 >> vl); - vectorbits = unitbits * (vn+1); - } - else if(vl == 3 && vn == 3) /* PKE_UNPACK_V4_5 */ - { - unitbits = 5; - vectorbits = 16; - } - else /* illegal unpack variant */ - { - /* should have been caught at top of function */ - ASSERT(0); - } - - /* loop over columns */ - for(i=0; i<=vn; i++) - { - unsigned_4 operand; - - /* offset in bits in current operand word */ - int bitoffset = - (vector_num_in * vectorbits) + (i * unitbits); /* # of bits from PKEcode */ - - /* last unit of V4_5 is only one bit wide */ - if(vl == 3 && vn == 3 && i == 3) /* PKE_UNPACK_V4_5 */ - unitbits = 1; - - /* confirm we're not reading more than we said we needed */ - if(vector_num_in * vectorbits >= num_operands * 32) - { - /* this condition may be triggered by illegal - PKEcode / CYCLE combinations. */ - pke_code_error(me, pkecode); - /* XXX: this case needs to be better understood, - and detected at a better time. */ - return; - } - - /* fetch bitfield operand */ - operand = pke_pcrel_operand_bits(me, bitoffset, unitbits, & source_addr); - - /* disassemble */ - if(me->trace_file != NULL && vl < 3) /* not for V4_5 */ - { - char* data_size; - if(vl == 0) data_size=".word"; - else if(vl == 1) data_size=".short"; - else if(vl == 2) data_size=".byte"; - else data_size = ""; - - fprintf(me->trace_file, "\t%s 0x%x\n", data_size, operand); - } - - /* selectively sign-extend; not for V4_5 1-bit value */ - if(usn || unitbits == 1) - unpacked_data[i] = operand; - else - unpacked_data[i] = SEXT32(operand, unitbits-1); - } - - /* disassemble */ - if(me->trace_file != NULL && vl == 3) /* only for V4_5 */ - { - unsigned short operand = - ((unpacked_data[0] & 0x1f) << 0) | - ((unpacked_data[1] & 0x1f) << 5) | - ((unpacked_data[2] & 0x1f) << 10) | - ((unpacked_data[3] & 0x1) << 15); - - fprintf(me->trace_file, "\t.short 0x%x\n", operand); - } - - /* set remaining top words in vector */ - for(i=vn+1; i<4; i++) - { - if(vn == 0) /* S_{32,16,8}: copy lowest element */ - unpacked_data[i] = unpacked_data[0]; - else - unpacked_data[i] = 0; - } - - /* consumed a vector from the PKE instruction stream */ - vector_num_in ++; - } /* unpack word from instruction operand */ - - /* process STMOD register for accumulation operations */ - switch(PKE_REG_MASK_GET(me, MODE, MDE)) - { - case PKE_MODE_ADDROW: /* add row registers to output data */ - case PKE_MODE_ACCROW: /* same .. later conditionally accumulate */ - for(i=0; i<4; i++) - /* exploit R0..R3 contiguity */ - unpacked_data[i] += me->regs[PKE_REG_R0 + i][0]; - break; - - case PKE_MODE_INPUT: /* pass data through */ - default: /* specified as undefined */ - ; - } - - /* compute replacement word */ - if(m) /* use mask register? */ - { - /* compute index into mask register for this word */ - int mask_index = PKE_LIMIT(vector_num_out % addrwl, 3); - - for(i=0; i<4; i++) /* loop over columns */ - { - int mask_op = PKE_MASKREG_GET(me, mask_index, i); - unsigned_4* masked_value = NULL; - - switch(mask_op) - { - case PKE_MASKREG_INPUT: - masked_value = & unpacked_data[i]; - - /* conditionally accumulate */ - if(PKE_REG_MASK_GET(me, MODE, MDE) == PKE_MODE_ACCROW) - me->regs[PKE_REG_R0 + i][0] = unpacked_data[i]; - - break; - - case PKE_MASKREG_ROW: /* exploit R0..R3 contiguity */ - masked_value = & me->regs[PKE_REG_R0 + i][0]; - break; - - case PKE_MASKREG_COLUMN: /* exploit C0..C3 contiguity */ - masked_value = & me->regs[PKE_REG_C0 + mask_index][0]; - break; - - case PKE_MASKREG_NOTHING: - /* "write inhibit" by re-copying old data */ - masked_value = & vu_old_data[i]; - break; - - default: - ASSERT(0); - /* no other cases possible */ - } - - /* copy masked value for column */ - vu_new_data[i] = *masked_value; - } /* loop over columns */ - } /* mask */ - else - { - /* no mask - just copy over entire unpacked quadword */ - memcpy(vu_new_data, unpacked_data, sizeof(unpacked_data)); - - /* conditionally store accumulated row results */ - if(PKE_REG_MASK_GET(me, MODE, MDE) == PKE_MODE_ACCROW) - for(i=0; i<4; i++) - me->regs[PKE_REG_R0 + i][0] = unpacked_data[i]; - } - - /* write new VU data word at address; reverse words if needed */ - { - unsigned_16 vu_new_badwords; - * A4_16(& vu_new_badwords, 3) = vu_new_data[0]; - * A4_16(& vu_new_badwords, 2) = vu_new_data[1]; - * A4_16(& vu_new_badwords, 1) = vu_new_data[2]; - * A4_16(& vu_new_badwords, 0) = vu_new_data[3]; - ASSERT(sizeof(vu_new_badwords) == 16); - PKE_MEM_WRITE(me, vu_addr, - &vu_new_badwords, 16); - } - - /* write tracking address */ - ASSERT(sizeof(unsigned_4) == 4); - PKE_MEM_WRITE(me, vutrack_addr, - & source_addr, - 4); - - /* next vector please */ - vector_num_out ++; - } /* vector transfer loop */ - while(PKE_REG_MASK_GET(me, NUM, NUM) > 0); - - /* confirm we've written as many vectors as told */ - ASSERT(nummx == vector_num_out); - - /* done */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\t.EndUnpack\n" - "\t.EndDmaData\n"); - } - pke_pc_advance(me, 1 + num_operands); - } /* PKE FIFO full enough */ - else - { - /* need to wait for another word */ - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_WAIT); - /* retry this instruction next clock */ - } -} - - -void -pke_code_error(struct pke_device* me, unsigned_4 pkecode) -{ - /* set ER1 flag in STAT register */ - PKE_REG_MASK_SET(me, STAT, ER1, 1); - - if(! PKE_REG_MASK_GET(me, ERR, ME1)) - { - pke_begin_interrupt_stall(me); - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_STALL); - } - else - { - PKE_REG_MASK_SET(me, STAT, PPS, PKE_REG_STAT_PPS_IDLE); - } - - if(me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n; %s PC %d/%d\n" - "\tDmaCnt *\n" - "\t.word 0x%x\n" - "\t.EndDmaData\n", - me->dev.name, me->fifo_pc, me->qw_pc, - (long) pkecode); - } - - /* advance over faulty word */ - pke_pc_advance(me, 1); -} - -void -pke_options(struct pke_device *me, unsigned_4 option, char *option_string) -{ - switch (option) - { - case SKY_OPT_DEBUG_NAME: - if ( me->fifo_trace_file != NULL ) - { - fclose (me->fifo_trace_file); - me->fifo_trace_file = NULL; - } - sky_store_file_name (&me->fifo_trace_file_name, option_string); - break; - - case SKY_OPT_TRACE_ON: - me->flags |= PKE_FLAG_TRACE_ON; - break; - - case SKY_OPT_TRACE_OFF: - case SKY_OPT_TRACE_NAME: - if ( me->trace_file != NULL ) - { - fprintf(me->trace_file, - "\n\n\tDmaEnd 0\n" - "\t.EndDmaData\n"); - fclose (me->trace_file); - me->trace_file = NULL; - } - - if ( option == SKY_OPT_TRACE_OFF ) - me->flags &= ~PKE_FLAG_TRACE_ON; - else - sky_store_file_name (&me->trace_file_name, option_string); - - break; - - case SKY_OPT_CLOSE: - if (me->trace_file != NULL) - { - fprintf(me->trace_file, - "\n\n\tDmaEnd 0\n" - "\t.EndDmaData\n"); - fclose(me->trace_file); - me->trace_file = NULL; - } - if (me->fifo_trace_file != NULL ) - fclose (me->fifo_trace_file); - me->fifo_trace_file = NULL; - break; - - default: - ASSERT (0); - break; - } - - return; -} diff --git a/sim/mips/sky-pke.h b/sim/mips/sky-pke.h deleted file mode 100644 index 48561c4807..0000000000 --- a/sim/mips/sky-pke.h +++ /dev/null @@ -1,495 +0,0 @@ -/* Copyright (C) 1998, Cygnus Solutions */ - -#ifndef H_PKE_H -#define H_PKE_H - -#include "sim-main.h" -#include "sky-device.h" - - -/* External functions */ - -struct pke_fifo; -struct fifo_quadword; -struct pke_device; - -void pke0_attach(SIM_DESC sd); -void pke0_issue(SIM_DESC sd); -void pke1_attach(SIM_DESC sd); -void pke1_issue(SIM_DESC sd); - -void pke_options(struct pke_device *device, unsigned_4 option, char *option_string); -int read_pke_reg (struct pke_device *device, int regno, void *buf); -int write_pke_reg (struct pke_device *device, int regno, const void *buf); -int read_pke_pc (struct pke_device *device, void *buf); -int read_pke_pcx (struct pke_device *device, void *buf); -struct fifo_quadword* pke_fifo_access(struct pke_fifo*, unsigned_4 qwnum); - - -/* Quadword data type */ - -typedef unsigned_4 quadword[4]; - -/* truncate address to quadword */ -#define ADDR_TRUNC_QW(addr) ((addr) & ~0x0f) -/* extract offset in quadword */ -#define ADDR_OFFSET_QW(addr) ((addr) & 0x0f) - - -/* SCEI memory mapping information */ - -#define PKE0_REGISTER_WINDOW_START 0x10003800 -#define PKE1_REGISTER_WINDOW_START 0x10003C00 -#define PKE0_FIFO_ADDR 0x10004000 -#define PKE1_FIFO_ADDR 0x10005000 - - -/* VU source-addr tracking tables */ /* changed from 1998-01-22 e-mail plans */ -#define VU0_MEM0_SRCADDR_START 0x19800000 -#define VU0_MEM1_SRCADDR_START 0x19804000 -#define VU1_MEM0_SRCADDR_START 0x19808000 -#define VU1_MEM1_SRCADDR_START 0x1980C000 - -#define VU0_CIA (VU0_REGISTER_WINDOW_START + VU_REG_CIA) -#define VU1_CIA (VU1_REGISTER_WINDOW_START + VU_REG_CIA) - -/* GPUIF STAT register */ -#define GPUIF_REG_STAT_APATH_E 11 -#define GPUIF_REG_STAT_APATH_B 10 - -/* COP2 STAT register */ -#define COP2_REG_STAT_ADDR VPU_STAT_ADDR -#define COP2_REG_STAT_VBS1_E 8 -#define COP2_REG_STAT_VBS1_B 8 -#define COP2_REG_STAT_VBS0_E 0 -#define COP2_REG_STAT_VBS0_B 0 - - -/* Quadword indices of PKE registers. Actual registers sit at bottom - 32 bits of each quadword. */ -#define PKE_REG_STAT 0x00 -#define PKE_REG_FBRST 0x01 -#define PKE_REG_ERR 0x02 -#define PKE_REG_MARK 0x03 -#define PKE_REG_CYCLE 0x04 -#define PKE_REG_MODE 0x05 -#define PKE_REG_NUM 0x06 -#define PKE_REG_MASK 0x07 -#define PKE_REG_CODE 0x08 -#define PKE_REG_ITOPS 0x09 -#define PKE_REG_BASE 0x0a /* pke1 only */ -#define PKE_REG_OFST 0x0b /* pke1 only */ -#define PKE_REG_TOPS 0x0c /* pke1 only */ -#define PKE_REG_ITOP 0x0d -#define PKE_REG_TOP 0x0e /* pke1 only */ -#define PKE_REG_DBF 0x0f /* pke1 only */ -#define PKE_REG_R0 0x10 /* R0 .. R3 must be contiguous */ -#define PKE_REG_R1 0x11 -#define PKE_REG_R2 0x12 -#define PKE_REG_R3 0x13 -#define PKE_REG_C0 0x14 /* C0 .. C3 must be contiguous */ -#define PKE_REG_C1 0x15 -#define PKE_REG_C2 0x16 -#define PKE_REG_C3 0x17 -/* one plus last index */ -#define PKE_NUM_REGS 0x18 - -#define PKE_REGISTER_WINDOW_SIZE (sizeof(quadword) * PKE_NUM_REGS) - - - -/* PKE commands */ - -#define PKE_CMD_PKENOP_MASK 0x7F -#define PKE_CMD_PKENOP_BITS 0x00 -#define PKE_CMD_STCYCL_MASK 0x7F -#define PKE_CMD_STCYCL_BITS 0x01 -#define PKE_CMD_OFFSET_MASK 0x7F -#define PKE_CMD_OFFSET_BITS 0x02 -#define PKE_CMD_BASE_MASK 0x7F -#define PKE_CMD_BASE_BITS 0x03 -#define PKE_CMD_ITOP_MASK 0x7F -#define PKE_CMD_ITOP_BITS 0x04 -#define PKE_CMD_STMOD_MASK 0x7F -#define PKE_CMD_STMOD_BITS 0x05 -#define PKE_CMD_MSKPATH3_MASK 0x7F -#define PKE_CMD_MSKPATH3_BITS 0x06 -#define PKE_CMD_PKEMARK_MASK 0x7F -#define PKE_CMD_PKEMARK_BITS 0x07 -#define PKE_CMD_FLUSHE_MASK 0x7F -#define PKE_CMD_FLUSHE_BITS 0x10 -#define PKE_CMD_FLUSH_MASK 0x7F -#define PKE_CMD_FLUSH_BITS 0x11 -#define PKE_CMD_FLUSHA_MASK 0x7F -#define PKE_CMD_FLUSHA_BITS 0x13 -#define PKE_CMD_PKEMSCAL_MASK 0x7F /* CAL == "call" */ -#define PKE_CMD_PKEMSCAL_BITS 0x14 -#define PKE_CMD_PKEMSCNT_MASK 0x7F /* CNT == "continue" */ -#define PKE_CMD_PKEMSCNT_BITS 0x17 -#define PKE_CMD_PKEMSCALF_MASK 0x7F /* CALF == "call after flush" */ -#define PKE_CMD_PKEMSCALF_BITS 0x15 -#define PKE_CMD_STMASK_MASK 0x7F -#define PKE_CMD_STMASK_BITS 0x20 -#define PKE_CMD_STROW_MASK 0x7F -#define PKE_CMD_STROW_BITS 0x30 -#define PKE_CMD_STCOL_MASK 0x7F -#define PKE_CMD_STCOL_BITS 0x31 -#define PKE_CMD_MPG_MASK 0x7F -#define PKE_CMD_MPG_BITS 0x4A -#define PKE_CMD_DIRECT_MASK 0x7F -#define PKE_CMD_DIRECT_BITS 0x50 -#define PKE_CMD_DIRECTHL_MASK 0x7F -#define PKE_CMD_DIRECTHL_BITS 0x51 -#define PKE_CMD_UNPACK_MASK 0x60 -#define PKE_CMD_UNPACK_BITS 0x60 - -/* test given word for particular PKE command bit pattern */ -#define IS_PKE_CMD(word,cmd) (((word) & PKE_CMD_##cmd##_MASK) == PKE_CMD_##cmd##_BITS) - - -/* register bitmasks: bit numbers for end and beginning of fields */ - -/* PKE opcode */ -#define PKE_OPCODE_I_E 31 -#define PKE_OPCODE_I_B 31 -#define PKE_OPCODE_CMD_E 30 -#define PKE_OPCODE_CMD_B 24 -#define PKE_OPCODE_NUM_E 23 -#define PKE_OPCODE_NUM_B 16 -#define PKE_OPCODE_IMM_E 15 -#define PKE_OPCODE_IMM_B 0 - -/* STAT register */ -#define PKE_REG_STAT_FQC_E 28 -#define PKE_REG_STAT_FQC_B 24 -#define PKE_REG_STAT_FDR_E 23 -#define PKE_REG_STAT_FDR_B 23 -#define PKE_REG_STAT_ER1_E 13 -#define PKE_REG_STAT_ER1_B 13 -#define PKE_REG_STAT_ER0_E 12 -#define PKE_REG_STAT_ER0_B 12 -#define PKE_REG_STAT_INT_E 11 -#define PKE_REG_STAT_INT_B 11 -#define PKE_REG_STAT_PIS_E 10 -#define PKE_REG_STAT_PIS_B 10 -#define PKE_REG_STAT_PFS_E 9 -#define PKE_REG_STAT_PFS_B 9 -#define PKE_REG_STAT_PSS_E 8 -#define PKE_REG_STAT_PSS_B 8 -#define PKE_REG_STAT_DBF_E 7 -#define PKE_REG_STAT_DBF_B 7 -#define PKE_REG_STAT_MRK_E 6 -#define PKE_REG_STAT_MRK_B 6 -#define PKE_REG_STAT_PGW_E 3 -#define PKE_REG_STAT_PGW_B 3 -#define PKE_REG_STAT_PEW_E 2 -#define PKE_REG_STAT_PEW_B 2 -#define PKE_REG_STAT_PPS_E 1 -#define PKE_REG_STAT_PPS_B 0 - -#define PKE_REG_STAT_PPS_IDLE 0x00 /* ready to execute next instruction */ -#define PKE_REG_STAT_PPS_WAIT 0x01 /* not enough words in FIFO */ -#define PKE_REG_STAT_PPS_DECODE 0x02 /* decoding instruction */ -#define PKE_REG_STAT_PPS_STALL 0x02 /* alias state for stall (e.g., FLUSHE) */ -#define PKE_REG_STAT_PPS_XFER 0x03 /* transferring instruction operands */ - -/* DBF register */ -#define PKE_REG_DBF_DF_E 0 -#define PKE_REG_DBF_DF_B 0 - -/* OFST register */ -#define PKE_REG_OFST_OFFSET_E 9 -#define PKE_REG_OFST_OFFSET_B 0 - -/* OFST register */ -#define PKE_REG_TOPS_TOPS_E 9 -#define PKE_REG_TOPS_TOPS_B 0 - -/* BASE register */ -#define PKE_REG_BASE_BASE_E 9 -#define PKE_REG_BASE_BASE_B 0 - -/* ITOPS register */ -#define PKE_REG_ITOPS_ITOPS_E 9 -#define PKE_REG_ITOPS_ITOPS_B 0 - -/* MODE register */ -#define PKE_REG_MODE_MDE_E 1 -#define PKE_REG_MODE_MDE_B 0 - -/* NUM register */ -#define PKE_REG_NUM_NUM_E 9 -#define PKE_REG_NUM_NUM_B 0 - -/* MARK register */ -#define PKE_REG_MARK_MARK_E 15 -#define PKE_REG_MARK_MARK_B 0 - -/* ITOP register */ -#define PKE_REG_ITOP_ITOP_E 9 -#define PKE_REG_ITOP_ITOP_B 0 - -/* TOP register */ -#define PKE_REG_TOP_TOP_E 9 -#define PKE_REG_TOP_TOP_B 0 - -/* MASK register */ -#define PKE_REG_MASK_MASK_E 31 -#define PKE_REG_MASK_MASK_B 0 - -/* CYCLE register */ -#define PKE_REG_CYCLE_WL_E 15 -#define PKE_REG_CYCLE_WL_B 8 -#define PKE_REG_CYCLE_CL_E 7 -#define PKE_REG_CYCLE_CL_B 0 - -/* ERR register */ -#define PKE_REG_ERR_ME1_E 2 -#define PKE_REG_ERR_ME1_B 2 -#define PKE_REG_ERR_ME0_E 1 -#define PKE_REG_ERR_ME0_B 1 -#define PKE_REG_ERR_MII_E 0 -#define PKE_REG_ERR_MII_B 0 - -/* FBRST command bitfields */ -#define PKE_REG_FBRST_STC_E 3 -#define PKE_REG_FBRST_STC_B 3 -#define PKE_REG_FBRST_STP_E 2 -#define PKE_REG_FBRST_STP_B 2 -#define PKE_REG_FBRST_FBK_E 1 -#define PKE_REG_FBRST_FBK_B 1 -#define PKE_REG_FBRST_RST_E 0 -#define PKE_REG_FBRST_RST_B 0 - -/* MSKPATH3 command bitfields */ -#define PKE_REG_MSKPATH3_E 15 -#define PKE_REG_MSKPATH3_B 15 - - -/* UNPACK opcodes */ -#define PKE_UNPACK(vn,vl) ((vn) << 2 | (vl)) -#define PKE_UNPACK_S_32 PKE_UNPACK(0, 0) -#define PKE_UNPACK_S_16 PKE_UNPACK(0, 1) -#define PKE_UNPACK_S_8 PKE_UNPACK(0, 2) -#define PKE_UNPACK_V2_32 PKE_UNPACK(1, 0) -#define PKE_UNPACK_V2_16 PKE_UNPACK(1, 1) -#define PKE_UNPACK_V2_8 PKE_UNPACK(1, 2) -#define PKE_UNPACK_V3_32 PKE_UNPACK(2, 0) -#define PKE_UNPACK_V3_16 PKE_UNPACK(2, 1) -#define PKE_UNPACK_V3_8 PKE_UNPACK(2, 2) -#define PKE_UNPACK_V4_32 PKE_UNPACK(3, 0) -#define PKE_UNPACK_V4_16 PKE_UNPACK(3, 1) -#define PKE_UNPACK_V4_8 PKE_UNPACK(3, 2) -#define PKE_UNPACK_V4_5 PKE_UNPACK(3, 3) - - -/* MASK register sub-field definitions */ -#define PKE_MASKREG_INPUT 0 -#define PKE_MASKREG_ROW 1 -#define PKE_MASKREG_COLUMN 2 -#define PKE_MASKREG_NOTHING 3 - - -/* STMOD register field definitions */ -#define PKE_MODE_INPUT 0 -#define PKE_MODE_ADDROW 1 -#define PKE_MODE_ACCROW 2 - - -/* extract a MASK register sub-field for row [0..3] and column [0..3] */ -/* MASK register is laid out of 2-bit values in this r-c order */ -/* m33 m32 m31 m30 m23 m22 m21 m20 m13 m12 m11 m10 m03 m02 m01 m00 */ -#define PKE_MASKREG_GET(me,row,col) \ -((((me)->regs[PKE_REG_MASK][0]) >> (8*(row) + 2*(col))) & 0x03) - - -/* operations - replace with those in sim-bits.h when convenient */ - -/* unsigned 32-bit mask of given width */ -#define BIT_MASK(width) ((width) == 31 ? 0xffffffff : (((unsigned_4)1) << (width+1)) - 1) -/* e.g.: BIT_MASK(4) = 00011111 */ - -/* mask between given given bits numbers (MSB) */ -#define BIT_MASK_BTW(begin,end) ((BIT_MASK(end) & ~((begin) == 0 ? 0 : BIT_MASK((begin)-1)))) -/* e.g.: BIT_MASK_BTW(4,11) = 0000111111110000 */ - -/* set bitfield value */ -#define BIT_MASK_SET(lvalue,begin,end,value) \ -do { \ - ASSERT((begin) <= (end)); \ - (lvalue) &= ~BIT_MASK_BTW((begin),(end)); \ - (lvalue) |= ((value) << (begin)) & BIT_MASK_BTW((begin),(end)); \ -} while(0) - -/* get bitfield value */ -#define BIT_MASK_GET(rvalue,begin,end) \ - (((rvalue) & BIT_MASK_BTW(begin,end)) >> (begin)) -/* e.g., BIT_MASK_GET(0000111100001111, 2, 8) = 0000000100001100 */ - -/* These ugly macro hacks allow succinct bitfield accesses */ -/* set a bitfield in a register by "name" */ -#define PKE_REG_MASK_SET(me,reg,flag,value) \ - do { \ - unsigned_4 old = BIT_MASK_GET(((me)->regs[PKE_REG_##reg][0]), \ - PKE_REG_##reg##_##flag##_B, PKE_REG_##reg##_##flag##_E); \ - BIT_MASK_SET(((me)->regs[PKE_REG_##reg][0]), \ - PKE_REG_##reg##_##flag##_B, PKE_REG_##reg##_##flag##_E, \ - (value)); \ - if( indebug ((me)->dev.name)) \ - { \ - if (old != (value)) \ - { \ - if (((me)->fifo_trace_file == NULL ) && \ - ((me)->fifo_trace_file_name != NULL )) \ - sky_open_file (&((me)->fifo_trace_file), \ - (me)->fifo_trace_file_name, \ - (char *) NULL, _IOLBF ); \ - fprintf (((me)->fifo_trace_file != NULL) ? \ - (me)->fifo_trace_file : stdout, \ - "# Reg %s:%s = 0x%x\n", #reg, #flag, (unsigned)(value)); \ - } \ - } \ - } while(0) - -/* get a bitfield from a register by "name" */ -#define PKE_REG_MASK_GET(me,reg,flag) \ - BIT_MASK_GET(((me)->regs[PKE_REG_##reg][0]), \ - PKE_REG_##reg##_##flag##_B, PKE_REG_##reg##_##flag##_E) - - -#define PKE_LIMIT(value,max) ((value) > (max) ? (max) : (value)) - - -/* Classify words in a FIFO quadword */ -enum wordclass -{ - wc_dma = 'D', - wc_pkecode = 'P', - wc_unknown = '?', - wc_pkedata = '.', - wc_gpuiftag = 'g' -}; - - -/* One row in the FIFO */ -struct fifo_quadword -{ - /* 128 bits of data */ - quadword data; - /* source main memory address (or 0: unknown) */ - unsigned_4 source_address; - /* classification of words in quadword; wc_dma set on DMA tags at FIFO write */ - enum wordclass word_class[4]; -}; - - -/* quadword FIFO structure for PKE */ -typedef struct pke_fifo -{ - struct fifo_quadword** quadwords; /* pointer to fifo quadwords */ - unsigned_4 origin; /* quadword serial number of quadwords[0] */ - unsigned_4 length; /* length of quadword pointer array: 0..N */ - unsigned_4 next; /* relative index of first unfilled quadword: 0..length-1 */ -} pke_fifo; - -#define PKE_FIFO_GROW_SIZE 1000 /* number of quadword pointers to allocate */ -#define PKE_FIFO_ARCHEOLOGY 1000 /* number of old quadwords to keep as history */ - - - -/* PKE internal state: FIFOs, registers, handle to VU friend */ -struct pke_device -{ - /* common device info */ - device dev; - - /* identity: 0=PKE0, 1=PKE1 */ - int pke_number; - int flags; - - /* quadword registers: data in [0] word only */ - quadword regs[PKE_NUM_REGS]; - - /* write buffer for FIFO address */ - quadword fifo_qw_in_progress; - int fifo_qw_done; /* bitfield */ - - /* FIFO - private: use only pke_fifo_* routines to access */ - struct pke_fifo fifo; /* array of FIFO quadword pointers */ - FILE* fifo_trace_file; /* stdio stream open in append mode, or 0 for no trace */ - char* fifo_trace_file_name; /* user defined debug trace file name */ - - /* FIFO cache -- curry last search pke_pcrel_fifo results */ - unsigned_4 last_fifo_pc; - unsigned_4 last_qw_pc; - unsigned_4 last_num; - unsigned_4 last_new_fifo_pc; - unsigned_4 last_new_qw_pc; - - /* PC */ - int fifo_pc; /* 0 .. (fifo_num_elements-1): quadword index of next instruction */ - int qw_pc; /* 0 .. 3: word index of next instruction */ - - /* Disassembly state */ - FILE *trace_file; - char *trace_file_name; -}; - - -extern struct pke_device pke0_device; -extern struct pke_device pke1_device; - - - -/* Flags for PKE.flags */ - -#define PKE_FLAG_NONE 0x00 -#define PKE_FLAG_PENDING_PSS 0x01 /* PSS bit written-to; set STAT:PSS after current instruction */ -#define PKE_FLAG_INT_NOLOOP 0x02 /* INT PKEcode received; INT/PIS set; suppress loop after resumption */ -#define PKE_FLAG_TRACE_ON 0x04 /* Trace file request from command line */ - -/* Kludge alert */ - -#define PKE_MEM_READ(me,addr,data,size) \ - do { \ - sim_cpu* cpu = STATE_CPU(CURRENT_STATE, 0); \ - unsigned_##size value = \ - sim_core_read_aligned_##size(cpu, CIA_GET(cpu), read_map, \ - (SIM_ADDR)(addr)); \ - memcpy((unsigned_##size*) (data), (void*) & value, size); \ - } while(0) - -#define PKE_MEM_WRITE(me,addr,data,size) \ - do { sim_cpu* cpu = STATE_CPU(CURRENT_STATE, 0); \ - unsigned_##size value; \ - memcpy((void*) & value, (unsigned_##size*)(data), size); \ - sim_core_write_aligned_##size(cpu, CIA_GET(cpu), write_map, \ - (SIM_ADDR)(addr), value); \ - if (indebug ((me)->dev.name)) \ - { \ - int i; \ - unsigned_##size value_te; \ - value_te = H2T_##size(value); \ - if (((me)->fifo_trace_file == NULL ) && \ - ((me)->fifo_trace_file_name != NULL )) \ - sky_open_file (&((me)->fifo_trace_file), \ - (me)->fifo_trace_file_name, \ - (char *) NULL, _IOLBF ); \ - fprintf (((me)->fifo_trace_file != NULL) ? \ - (me)->fifo_trace_file : stdout, \ - "# Write %2d bytes to ", size); \ - fprintf (((me)->fifo_trace_file != NULL) ? \ - (me)->fifo_trace_file : stdout, \ - "0x%08lx: ", (unsigned long)(addr)); \ - for(i=0; ififo_trace_file != NULL) ? \ - (me)->fifo_trace_file : stdout, \ - " %02x", ((unsigned_1*)(& value_te))[i]); \ - fprintf (((me)->fifo_trace_file != NULL) ? \ - (me)->fifo_trace_file : stdout, \ - "\n"); \ - } \ - } while(0) - - -#endif /* H_PKE_H */