|
|
1.1.1.2 ! root 1: /* $Id: sparc-impl.h,v 1.11 2010/06/05 16:13:15 fredette Exp $ */ 1.1 root 2: 3: /* ic/sparc/sparc-impl.h - implementation header file for SPARC emulation: */ 4: 5: /* 1.1.1.2 ! root 6: * Copyright (c) 2005, 2007, 2009 Matt Fredette 1.1 root 7: * All rights reserved. 8: * 9: * Redistribution and use in source and binary forms, with or without 10: * modification, are permitted provided that the following conditions 11: * are met: 12: * 1. Redistributions of source code must retain the above copyright 13: * notice, this list of conditions and the following disclaimer. 14: * 2. Redistributions in binary form must reproduce the above copyright 15: * notice, this list of conditions and the following disclaimer in the 16: * documentation and/or other materials provided with the distribution. 17: * 3. All advertising materials mentioning features or use of this software 18: * must display the following acknowledgement: 19: * This product includes software developed by Matt Fredette. 20: * 4. The name of the author may not be used to endorse or promote products 21: * derived from this software without specific prior written permission. 22: * 23: * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 24: * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 25: * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 26: * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, 27: * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 28: * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 29: * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 30: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 31: * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN 32: * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 33: * POSSIBILITY OF SUCH DAMAGE. 34: */ 35: 36: #ifndef _IC_SPARC_IMPL_H 37: #define _IC_SPARC_IMPL_H 38: 39: #include <tme/common.h> 1.1.1.2 ! root 40: _TME_RCSID("$Id: sparc-impl.h,v 1.11 2010/06/05 16:13:15 fredette Exp $"); 1.1 root 41: 42: /* includes: */ 43: #include <tme/ic/sparc.h> 44: #include <tme/ic/ieee754.h> 45: #include <tme/generic/ic.h> 1.1.1.2 ! root 46: #include <tme/bus/upa.h> ! 47: #if TME_HAVE_RECODE ! 48: #include <tme/recode.h> ! 49: #endif /* TME_HAVE_RECODE */ ! 50: #include <tme/runlength.h> ! 51: #include <tme/misc.h> 1.1 root 52: #include <setjmp.h> 53: 54: /* macros: */ 55: 56: /* generic registers: */ 57: #define tme_sparc_ireg_uint64(x) tme_sparc_ic.tme_ic_ireg_uint64(x) 58: #define tme_sparc_ireg_int64(x) tme_sparc_ic.tme_ic_ireg_int64(x) 59: #define tme_sparc_ireg_uint32(x) tme_sparc_ic.tme_ic_ireg_uint32(x) 60: #define tme_sparc_ireg_int32(x) tme_sparc_ic.tme_ic_ireg_int32(x) 61: #define tme_sparc_ireg_uint8(x) tme_sparc_ic.tme_ic_ireg_uint8(x) 62: 63: /* format 3 instruction fields: */ 64: #define TME_SPARC_FORMAT3_MASK_RS2 (0x1f << 0) 65: #define TME_SPARC_FORMAT3_MASK_RS1 (0x1f << 14) 66: #define TME_SPARC_FORMAT3_MASK_RD (0x1f << 25) 67: 68: /* traps: */ 1.1.1.2 ! root 69: #define TME_SPARC_TRAP_IMPDEP_RESET (0x80000000) ! 70: #define _TME_SPARC_TRAP_IMPDEP(x) TME_BIT(30 - (x)) ! 71: #define _TME_SPARC_TRAP(priority, tt) (((priority) * 0x1000) + (tt)) ! 72: #define TME_SPARC_TRAP_PRIORITY(trap) \ ! 73: (((trap) / _TME_SPARC_TRAP(1, 0)) % (TME_SPARC_TRAP_IMPDEP_RESET / _TME_SPARC_TRAP(1, 0))) ! 74: #define TME_SPARC_TRAP_TT(trap) ((trap) % _TME_SPARC_TRAP(1, 0)) ! 75: #define TME_SPARC_TRAP_none _TME_SPARC_TRAP(0xfff, 0) ! 76: ! 77: /* sparc32 traps: */ ! 78: #define TME_SPARC32_TRAP_reset _TME_SPARC_TRAP( 1, 0x100) ! 79: #define TME_SPARC32_TRAP_instruction_access_MMU_miss _TME_SPARC_TRAP( 2, 0x3C) ! 80: #define TME_SPARC32_TRAP_instruction_access_error _TME_SPARC_TRAP( 3, 0x21) ! 81: #define TME_SPARC32_TRAP_r_register_access_error _TME_SPARC_TRAP( 4, 0x20) ! 82: #define TME_SPARC32_TRAP_instruction_access_exception _TME_SPARC_TRAP( 5, 0x01) ! 83: #define TME_SPARC32_TRAP_privileged_instruction _TME_SPARC_TRAP( 6, 0x03) ! 84: #define TME_SPARC32_TRAP_illegal_instruction _TME_SPARC_TRAP( 7, 0x02) ! 85: #define TME_SPARC32_TRAP_fp_disabled _TME_SPARC_TRAP( 8, 0x04) ! 86: #define TME_SPARC32_TRAP_cp_disabled _TME_SPARC_TRAP( 8, 0x24) ! 87: #define TME_SPARC32_TRAP_unimplemented_FLUSH _TME_SPARC_TRAP( 8, 0x25) ! 88: #define TME_SPARC32_TRAP_watchpoint_detected _TME_SPARC_TRAP( 8, 0x0B) ! 89: #define TME_SPARC32_TRAP_window_overflow _TME_SPARC_TRAP( 9, 0x05) ! 90: #define TME_SPARC32_TRAP_window_underflow _TME_SPARC_TRAP( 9, 0x06) ! 91: #define TME_SPARC32_TRAP_mem_address_not_aligned _TME_SPARC_TRAP(10, 0x07) ! 92: #define TME_SPARC32_TRAP_fp_exception _TME_SPARC_TRAP(11, 0x08) ! 93: #define TME_SPARC32_TRAP_cp_exception _TME_SPARC_TRAP(11, 0x28) ! 94: #define TME_SPARC32_TRAP_data_access_error _TME_SPARC_TRAP(12, 0x29) ! 95: #define TME_SPARC32_TRAP_data_access_MMU_miss _TME_SPARC_TRAP(12, 0x2C) ! 96: #define TME_SPARC32_TRAP_data_access_exception _TME_SPARC_TRAP(13, 0x09) ! 97: #define TME_SPARC32_TRAP_tag_overflow _TME_SPARC_TRAP(14, 0x0A) ! 98: #define TME_SPARC32_TRAP_division_by_zero _TME_SPARC_TRAP(15, 0x2A) ! 99: #define TME_SPARC32_TRAP_trap_instruction(x) _TME_SPARC_TRAP(16, 0x80 + (x)) ! 100: #define TME_SPARC32_TRAP_interrupt_level(il) _TME_SPARC_TRAP(32 - (il), 0x10 + (il)) ! 101: ! 102: /* sparc64 traps: */ ! 103: #define TME_SPARC64_TRAP_power_on_reset _TME_SPARC_TRAP( 0, 0x001) ! 104: #define TME_SPARC64_TRAP_watchdog_reset _TME_SPARC_TRAP( 1, 0x002) ! 105: #define TME_SPARC64_TRAP_externally_initiated_reset _TME_SPARC_TRAP( 1, 0x003) ! 106: #define TME_SPARC64_TRAP_software_initiated_reset _TME_SPARC_TRAP( 1, 0x004) ! 107: #define TME_SPARC64_TRAP_RED_state_exception _TME_SPARC_TRAP( 1, 0x005) ! 108: #define TME_SPARC64_TRAP_instruction_access_exception _TME_SPARC_TRAP( 5, 0x008) ! 109: #define TME_SPARC64_TRAP_instruction_access_MMU_miss _TME_SPARC_TRAP( 2, 0x009) ! 110: #define TME_SPARC64_TRAP_instruction_access_error _TME_SPARC_TRAP( 3, 0x00a) ! 111: #define TME_SPARC64_TRAP_illegal_instruction _TME_SPARC_TRAP( 7, 0x010) ! 112: #define TME_SPARC64_TRAP_privileged_opcode _TME_SPARC_TRAP( 6, 0x011) ! 113: #define TME_SPARC64_TRAP_unimplemented_LDD _TME_SPARC_TRAP( 6, 0x012) ! 114: #define TME_SPARC64_TRAP_unimplemented_STD _TME_SPARC_TRAP( 6, 0x013) ! 115: #define TME_SPARC64_TRAP_fp_disabled _TME_SPARC_TRAP( 8, 0x020) ! 116: #define TME_SPARC64_TRAP_fp_exception_ieee_754 _TME_SPARC_TRAP(11, 0x021) ! 117: #define TME_SPARC64_TRAP_fp_exception_other _TME_SPARC_TRAP(11, 0x022) ! 118: #define TME_SPARC64_TRAP_tag_overflow _TME_SPARC_TRAP(14, 0x023) ! 119: #define TME_SPARC64_TRAP_clean_window _TME_SPARC_TRAP(10, 0x024) ! 120: #define TME_SPARC64_TRAP_division_by_zero _TME_SPARC_TRAP(15, 0x028) ! 121: #define TME_SPARC64_TRAP_internal_processor_error _TME_SPARC_TRAP( 4, 0x029) ! 122: #define TME_SPARC64_TRAP_data_access_exception _TME_SPARC_TRAP(12, 0x030) ! 123: #define TME_SPARC64_TRAP_data_access_MMU_miss _TME_SPARC_TRAP(12, 0x031) ! 124: #define TME_SPARC64_TRAP_data_access_error _TME_SPARC_TRAP(12, 0x032) ! 125: #define TME_SPARC64_TRAP_data_access_protection _TME_SPARC_TRAP(12, 0x033) ! 126: #define TME_SPARC64_TRAP_mem_address_not_aligned _TME_SPARC_TRAP(10, 0x034) ! 127: #define TME_SPARC64_TRAP_LDDF_mem_address_not_aligned _TME_SPARC_TRAP(10, 0x035) ! 128: #define TME_SPARC64_TRAP_STDF_mem_address_not_aligned _TME_SPARC_TRAP(10, 0x036) ! 129: #define TME_SPARC64_TRAP_privileged_action _TME_SPARC_TRAP(11, 0x037) ! 130: #define TME_SPARC64_TRAP_LDQF_mem_address_not_aligned _TME_SPARC_TRAP(10, 0x038) ! 131: #define TME_SPARC64_TRAP_STQF_mem_address_not_aligned _TME_SPARC_TRAP(10, 0x039) ! 132: #define TME_SPARC64_TRAP_async_data_error _TME_SPARC_TRAP( 2, 0x040) ! 133: #define TME_SPARC64_TRAP_interrupt_level(n) _TME_SPARC_TRAP(32 - (n), 0x40 + (n)) ! 134: #define TME_SPARC64_TRAP_spill_normal(n) _TME_SPARC_TRAP( 9, 0x080 + (4 * (n))) ! 135: #define TME_SPARC64_TRAP_spill_other(n) _TME_SPARC_TRAP( 9, 0x0a0 + (4 * (n))) ! 136: #define TME_SPARC64_TRAP_fill_normal(n) _TME_SPARC_TRAP( 9, 0x0c0 + (4 * (n))) ! 137: #define TME_SPARC64_TRAP_fill_other(n) _TME_SPARC_TRAP( 9, 0x0e0 + (4 * (n))) ! 138: #define TME_SPARC64_TRAP_trap_instruction(x) _TME_SPARC_TRAP(16, 0x100 + (x)) ! 139: ! 140: /* generic traps: */ ! 141: #define TME_SPARC_TRAP(ic, trap) \ ! 142: (TME_SPARC_VERSION(ic) < 9 \ ! 143: ? _TME_CONCAT(TME_SPARC32_TRAP_,trap) \ ! 144: : _TME_CONCAT(TME_SPARC64_TRAP_,trap)) 1.1 root 145: 146: /* SPARC FPU FSR fields: */ 147: #define TME_SPARC_FSR_RND (0xc0000000) 148: #define TME_SPARC_FSR_RND_RN (0x00000000) 149: #define TME_SPARC_FSR_RND_RZ (0x40000000) 150: #define TME_SPARC_FSR_RND_RP (0x80000000) 151: #define TME_SPARC_FSR_RND_RM (0xc0000000) 152: #define TME_SPARC_FSR_TEM (0x0f800000) 153: #define TME_SPARC_FSR_NS TME_BIT(22) 154: #define TME_SPARC_FSR_VER (0x000e0000) 155: #define TME_SPARC_FSR_VER_missing (0x000e0000) 156: #define TME_SPARC_FSR_FTT (0x0001c000) 157: #define TME_SPARC_FSR_FTT_none (0x00000000) 158: #define TME_SPARC_FSR_FTT_IEEE754_exception (0x00004000) 159: #define TME_SPARC_FSR_FTT_unfinished_FPop (0x00008000) 160: #define TME_SPARC_FSR_FTT_unimplemented_FPop (0x0000c000) 161: #define TME_SPARC_FSR_FTT_sequence_error (0x00010000) 162: #define TME_SPARC_FSR_FTT_hardware_error (0x00014000) 163: #define TME_SPARC_FSR_FTT_invalid_fp_register (0x00018000) 164: #define TME_SPARC_FSR_QNE TME_BIT(13) 165: #define TME_SPARC_FSR_FCC (0x00000c00) 166: #define TME_SPARC_FSR_FCC_EQ (0x00000000) 167: #define TME_SPARC_FSR_FCC_LT (0x00000400) 168: #define TME_SPARC_FSR_FCC_GT (0x00000800) 169: #define TME_SPARC_FSR_FCC_UN (0x00000c00) 170: #define TME_SPARC_FSR_AEXC (0x000003e0) 171: #define TME_SPARC_FSR_CEXC (0x0000001f) 172: #define TME_SPARC_FSR_CEXC_NVC TME_BIT(4) 173: #define TME_SPARC_FSR_CEXC_OFC TME_BIT(3) 174: #define TME_SPARC_FSR_CEXC_UFC TME_BIT(2) 175: #define TME_SPARC_FSR_CEXC_DZC TME_BIT(1) 176: #define TME_SPARC_FSR_CEXC_NXC TME_BIT(0) 177: 178: /* sparc32 PSR fields: */ 179: #define TME_SPARC32_PSR_IMPL (0xf0000000) 180: #define TME_SPARC32_PSR_VER (0x0f000000) 181: #define TME_SPARC32_PSR_ICC_N TME_BIT(23) 182: #define TME_SPARC32_PSR_ICC_Z TME_BIT(22) 183: #define TME_SPARC32_PSR_ICC_V TME_BIT(21) 184: #define TME_SPARC32_PSR_ICC_C TME_BIT(20) 185: #define TME_SPARC32_PSR_ICC (TME_SPARC32_PSR_ICC_N | TME_SPARC32_PSR_ICC_Z | TME_SPARC32_PSR_ICC_V | TME_SPARC32_PSR_ICC_C) 186: #define TME_SPARC32_PSR_EC TME_BIT(13) 187: #define TME_SPARC32_PSR_EF TME_BIT(12) 188: #define TME_SPARC32_PSR_PIL (0x00000f00) 189: #define TME_SPARC32_PSR_S TME_BIT(7) 190: #define TME_SPARC32_PSR_PS TME_BIT(6) 191: #define TME_SPARC32_PSR_ET TME_BIT(5) 192: #define TME_SPARC32_PSR_CWP (0x0000001f) 193: 194: /* sparc64 PSTATE flags: */ 195: #define TME_SPARC64_PSTATE_CLE TME_BIT(9) 1.1.1.2 ! root 196: #define TME_SPARC64_PSTATE_TLE TME_BIT(8) ! 197: #define TME_SPARC64_PSTATE_MM ((2 << 7) - (1 << 6)) ! 198: #define TME_SPARC64_PSTATE_RED TME_BIT(5) 1.1 root 199: #define TME_SPARC64_PSTATE_PEF TME_BIT(4) 1.1.1.2 ! root 200: #define TME_SPARC64_PSTATE_AM TME_BIT(3) ! 201: #define TME_SPARC64_PSTATE_PRIV TME_BIT(2) ! 202: #define TME_SPARC64_PSTATE_IE TME_BIT(1) ! 203: #define TME_SPARC64_PSTATE_AG TME_BIT(0) 1.1 root 204: 205: /* sparc64 CCR flags: */ 206: #define TME_SPARC64_CCR_XCC_N TME_BIT(7) 207: #define TME_SPARC64_CCR_XCC_Z TME_BIT(6) 208: #define TME_SPARC64_CCR_XCC_V TME_BIT(5) 209: #define TME_SPARC64_CCR_XCC_C TME_BIT(4) 210: #define TME_SPARC64_CCR_ICC_N TME_BIT(3) 211: #define TME_SPARC64_CCR_ICC_Z TME_BIT(2) 212: #define TME_SPARC64_CCR_ICC_V TME_BIT(1) 213: #define TME_SPARC64_CCR_ICC_C TME_BIT(0) 214: #define TME_SPARC64_CCR_ICC (TME_SPARC64_CCR_ICC_N | TME_SPARC64_CCR_ICC_Z | TME_SPARC64_CCR_ICC_V | TME_SPARC64_CCR_ICC_C) 1.1.1.2 ! root 215: #define TME_SPARC64_CCR_XCC (TME_SPARC64_CCR_XCC_N | TME_SPARC64_CCR_XCC_Z | TME_SPARC64_CCR_XCC_V | TME_SPARC64_CCR_XCC_C) ! 216: ! 217: /* sparc64 FPRS flags: */ ! 218: #define TME_SPARC64_FPRS_DL TME_BIT(0) ! 219: #define TME_SPARC64_FPRS_DU TME_BIT(1) ! 220: #define TME_SPARC64_FPRS_FEF TME_BIT(2) ! 221: ! 222: /* sparc64 TSTATE flags: */ ! 223: #define TME_SPARC64_TSTATE_MASK_CWP (0x1f << 0) ! 224: #define TME_SPARC64_TSTATE_MASK_PSTATE (0xfff << 8) ! 225: #define TME_SPARC64_TSTATE_MASK_ASI (0xff << 24) ! 226: #define TME_SPARC64_TSTATE_MASK_CCR (((tme_uint64_t) 0xff) << 32) ! 227: ! 228: /* sparc64 WSTATE fields: */ ! 229: #define TME_SPARC64_WSTATE_NORMAL (0x07) ! 230: #define TME_SPARC64_WSTATE_OTHER (0x38) ! 231: ! 232: /* sparc64 VER fields: */ ! 233: #define TME_SPARC64_VER_MANUF (((tme_uint64_t) 0xffff) << 48) ! 234: #define TME_SPARC64_VER_IMPL (((tme_uint64_t) 0xffff) << 32) ! 235: #define TME_SPARC64_VER_MASK (((tme_uint32_t) 0xff) << 24) ! 236: #define TME_SPARC64_VER_MAXTL (((tme_uint32_t) 0xff) << 8) ! 237: #define TME_SPARC64_VER_MAXWIN (((tme_uint32_t) 0x1f) << 0) ! 238: ! 239: /* sparc64 TICK fields: */ ! 240: #define TME_SPARC64_TICK_NPT (((tme_uint64_t) 1) << 63) ! 241: #define TME_SPARC64_TICK_COUNTER (TME_SPARC64_TICK_NPT - 1) ! 242: ! 243: /* sparc VIS ASIs: */ ! 244: #define TME_SPARC_VIS_ASI_PST8 (0xc0) ! 245: #define TME_SPARC_VIS_ASI_PST16 (0xc2) ! 246: #define TME_SPARC_VIS_ASI_PST32 (0xc4) ! 247: #define TME_SPARC_VIS_ASI_FL8 (0xd0) ! 248: #define TME_SPARC_VIS_ASI_FL16 (0xd2) ! 249: ! 250: /* sparc VIS GSR fields: */ ! 251: #define TME_SPARC_VIS_GSR_ALIGNADDR_OFF ((2 << 2) - (1 << 0)) ! 252: #define TME_SPARC_VIS_GSR_SCALE_FACTOR ((2 << 6) - (1 << 3)) ! 253: ! 254: /* sparc conditions: */ ! 255: #define TME_SPARC_COND_N (0) ! 256: #define TME_SPARC_COND_E (1) ! 257: #define TME_SPARC_COND_LE (2) ! 258: #define TME_SPARC_COND_L (3) ! 259: #define TME_SPARC_COND_LEU (4) ! 260: #define TME_SPARC_COND_CS (5) ! 261: #define TME_SPARC_COND_NEG (6) ! 262: #define TME_SPARC_COND_VS (7) ! 263: #define TME_SPARC_COND_NOT (8) ! 264: #define TME_SPARC_COND_IS_CONDITIONAL(cond) (((cond) % TME_SPARC_COND_NOT) != TME_SPARC_COND_N) 1.1 root 265: 266: /* idle types and idle type state: */ 267: #define TME_SPARC_IDLE_TYPE_NULL (0) 268: #define TME_SPARC_IDLE_TYPE_NETBSD32_TYPE_0 TME_BIT(0) 269: #define TME_SPARC_IDLE_TYPE_SUNOS32_TYPE_0 TME_BIT(1) 1.1.1.2 ! root 270: #define TME_SPARC_IDLE_TYPE_NETBSD32_TYPE_1 TME_BIT(2) ! 271: #define TME_SPARC_IDLE_TYPE_NETBSD64_TYPE_0 TME_BIT(3) ! 272: #define TME_SPARC_IDLE_TYPE_NETBSD64_TYPE_1 TME_BIT(4) ! 273: #define TME_SPARC_IDLE_TYPE_SUNOS64_TYPE_0 TME_BIT(5) ! 274: #define TME_SPARC_IDLE_TYPES_32 \ ! 275: (TME_SPARC_IDLE_TYPE_NETBSD32_TYPE_0 \ ! 276: + TME_SPARC_IDLE_TYPE_SUNOS32_TYPE_0 \ ! 277: + TME_SPARC_IDLE_TYPE_NETBSD32_TYPE_1 \ ! 278: ) ! 279: #define TME_SPARC_IDLE_TYPES_64 \ ! 280: (TME_SPARC_IDLE_TYPE_NETBSD64_TYPE_0 \ ! 281: + TME_SPARC_IDLE_TYPE_NETBSD64_TYPE_1 \ ! 282: + TME_SPARC_IDLE_TYPE_SUNOS64_TYPE_0 \ ! 283: ) ! 284: #define TME_SPARC_IDLE_TYPES_TARGET_CALL \ ! 285: (TME_SPARC_IDLE_TYPE_NETBSD32_TYPE_1 \ ! 286: + TME_SPARC_IDLE_TYPE_NETBSD64_TYPE_1 \ ! 287: ) ! 288: #define TME_SPARC_IDLE_TYPES_TARGET_BRANCH \ ! 289: (TME_SPARC_IDLE_TYPE_SUNOS32_TYPE_0 \ ! 290: ) ! 291: #define TME_SPARC_IDLE_TYPES_PC_RANGE \ ! 292: (TME_SPARC_IDLE_TYPE_NETBSD32_TYPE_0 \ ! 293: + TME_SPARC_IDLE_TYPE_SUNOS64_TYPE_0 \ ! 294: ) ! 295: #define TME_SPARC_IDLE_TYPE_IS_SUPPORTED(ic, x) \ ! 296: (((x) \ ! 297: & (0 - (unsigned int) 1)) \ ! 298: & (TME_SPARC_VERSION(ic) < 9 \ ! 299: ? TME_SPARC_IDLE_TYPES_32 \ ! 300: : TME_SPARC_IDLE_TYPES_64)) 1.1 root 301: #define TME_SPARC_IDLE_TYPE_IS(ic, x) \ 1.1.1.2 ! root 302: (TME_SPARC_IDLE_TYPE_IS_SUPPORTED(ic, x) \ ! 303: & (ic)->tme_sparc_idle_type) ! 304: #define TME_SPARC_IDLE_TYPE_PC_STATE(x) (((tme_uint32_t) (x)) % sizeof(tme_uint32_t)) ! 305: ! 306: /* this makes an idle mark: */ ! 307: #define TME_SPARC_IDLE_MARK(ic) \ ! 308: do { \ ! 309: \ ! 310: /* increment the idle marks, up to two: */ \ ! 311: ic->tme_sparc_idle_marks += (ic->tme_sparc_idle_marks < 2); \ ! 312: \ ! 313: /* limit the remaining instruction burst to no more than \ ! 314: an idle instruction burst: */ \ ! 315: ic->_tme_sparc_instruction_burst_remaining \ ! 316: = TME_MIN(ic->_tme_sparc_instruction_burst_remaining, \ ! 317: ic->_tme_sparc_instruction_burst_idle); \ ! 318: ic->_tme_sparc_instruction_burst_other = TRUE; \ ! 319: } while (/* CONSTCOND */ 0) ! 320: ! 321: /* this stops idling: */ ! 322: #define TME_SPARC_IDLE_STOP(ic) \ ! 323: do { \ ! 324: \ ! 325: /* clear the idle marks: */ \ ! 326: ic->tme_sparc_idle_marks = 0; \ ! 327: } while (/* CONSTCOND */ 0) 1.1 root 328: 329: /* major modes of the emulator: */ 330: #define TME_SPARC_MODE_EXECUTION (0) 331: #define TME_SPARC_MODE_STOP (1) 332: #define TME_SPARC_MODE_HALT (2) 1.1.1.2 ! root 333: #define TME_SPARC_MODE_OFF (3) ! 334: #define TME_SPARC_MODE_TIMING_LOOP (4) 1.1 root 335: 336: /* the maximum number of windows: */ 337: #define TME_SPARC_WINDOWS_MAX (16) 338: 1.1.1.2 ! root 339: /* the maximum number of trap levels: */ ! 340: #define TME_SPARC_TL_MAX (8) ! 341: ! 342: /* this updates the recode CWP register offsets: */ ! 343: #if TME_HAVE_RECODE ! 344: #define _TME_SPARC_RECODE_CWP_UPDATE(ic, reg_type) \ ! 345: do { \ ! 346: (ic)->tme_sparc_recode_window_base_offsets[0] \ ! 347: = (ic)->tme_sparc_reg8_offset[1] * 8 * sizeof(reg_type); \ ! 348: (ic)->tme_sparc_recode_window_base_offsets[1] \ ! 349: = (ic)->tme_sparc_reg8_offset[3] * 8 * sizeof(reg_type); \ ! 350: if (sizeof(reg_type) > sizeof(tme_uint32_t)) { \ ! 351: (ic)->tme_sparc_recode_window_base_offsets[2] \ ! 352: = (ic)->tme_sparc_reg8_offset[0] * 8 * sizeof(reg_type);\ ! 353: } \ ! 354: } while (/* CONSTCOND */ 0) ! 355: #else /* !TME_HAVE_RECODE */ ! 356: #define _TME_SPARC_RECODE_CWP_UPDATE(ic, reg_type) \ ! 357: do { \ ! 358: } while (/* CONSTCOND */ 0 && (ic) && (reg_type) 0) ! 359: #endif /* !TME_HAVE_RECODE */ ! 360: ! 361: /* this updates the CWP register offset: */ ! 362: #define _TME_SPARC_CWP_UPDATE(ic, cwp, reg8_offset_r8_r23, cwp_wraps, reg_type) \ ! 363: do { \ ! 364: (ic)->tme_sparc_reg8_offset[1] = (reg8_offset_r8_r23); \ ! 365: (ic)->tme_sparc_reg8_offset[2] = (reg8_offset_r8_r23); \ ! 366: (ic)->tme_sparc_reg8_offset[3] \ ! 367: = ((cwp) == (cwp_wraps) \ ! 368: ? ((8 - 24) / 8) \ ! 369: : (reg8_offset_r8_r23)); \ ! 370: _TME_SPARC_RECODE_CWP_UPDATE(ic, reg_type); \ ! 371: } while (/* CONSTCOND */ 0) ! 372: ! 373: /* this updates the sparc32 CWP register offsets: */ ! 374: #define TME_SPARC32_CWP_UPDATE(ic, cwp, reg8_offset_r8_r23) \ ! 375: do { \ ! 376: (reg8_offset_r8_r23) = (cwp) * 2; \ ! 377: _TME_SPARC_CWP_UPDATE(ic, cwp, reg8_offset_r8_r23, TME_SPARC_NWINDOWS(ic) - 1, tme_uint32_t); \ ! 378: } while (/* CONSTCOND */ 0) ! 379: ! 380: /* this updates the sparc64 CWP register offsets: */ ! 381: #define TME_SPARC64_CWP_UPDATE(ic, cwp, reg8_offset_r8_r23) \ ! 382: do { \ ! 383: assert (cwp < TME_SPARC_NWINDOWS(ic)); \ ! 384: (reg8_offset_r8_r23) \ ! 385: = (((TME_SPARC_NWINDOWS(ic) - 1) - cwp) \ ! 386: * 2); \ ! 387: _TME_SPARC_CWP_UPDATE(ic, cwp, reg8_offset_r8_r23, 0, tme_uint64_t); \ ! 388: } while (/* CONSTCOND */ 0) ! 389: ! 390: /* this gives the current %g0 register set index: */ ! 391: #define TME_SPARC_G0_OFFSET(ic) \ ! 392: (TME_SPARC_VERSION(ic) < 9 ? 0 : ((ic)->tme_sparc_reg8_offset[0] * 8)) 1.1 root 393: 394: /* this converts the given lvalue from a register number into a 395: register set index: */ 396: #define TME_SPARC_REG_INDEX(ic, reg) \ 397: do { \ 1.1.1.2 ! root 398: (reg) += ((ic)->tme_sparc_reg8_offset[(reg) / 8] * 8); \ 1.1 root 399: } while (/* CONSTCOND */ 0) 400: 1.1.1.2 ! root 401: /* this gives the hash for an address: */ ! 402: #define TME_SPARC_TLB_HASH(ic, context, address) \ ! 403: ((((tme_uint32_t) (address)) \ ! 404: >> (ic)->tme_sparc_tlb_page_size_log2) \ ! 405: + (0 && (context))) ! 406: ! 407: /* the size of the DTLB hash: */ 1.1 root 408: #define _TME_SPARC_DTLB_HASH_SIZE (1024) 1.1.1.2 ! root 409: ! 410: /* this gives the DTLB entry for a hash key: */ ! 411: #define TME_SPARC_DTLB_ENTRY(ic, tlb_hash) \ ! 412: (((tlb_hash) % _TME_SPARC_DTLB_HASH_SIZE) \ ! 413: + (0 && (ic))) 1.1 root 414: 415: /* the size of the ITLB hash: */ 416: #define _TME_SPARC_ITLB_HASH_SIZE (32) 417: 1.1.1.2 ! root 418: /* this gives the ITLB entry for a hash key: */ ! 419: #define TME_SPARC_ITLB_ENTRY(ic, tlb_hash) \ ! 420: (_TME_SPARC_DTLB_HASH_SIZE \ ! 421: + ((tlb_hash) % _TME_SPARC_ITLB_HASH_SIZE) \ ! 422: + (0 && (ic))) ! 423: ! 424: /* the count of all TLB entries: */ ! 425: #define _TME_SPARC_TLB_COUNT \ ! 426: (_TME_SPARC_DTLB_HASH_SIZE \ ! 427: + _TME_SPARC_ITLB_HASH_SIZE) ! 428: ! 429: /* load/store information: */ ! 430: #define TME_SPARC_LSINFO_SIZE(x) (x) ! 431: #define TME_SPARC_LSINFO_WHICH_SIZE(x) (((x) / TME_SPARC_LSINFO_SIZE(1)) & 0xff) ! 432: #define TME_SPARC_LSINFO_ASI(x) ((x) << 8) ! 433: #define TME_SPARC_LSINFO_WHICH_ASI(x) (((x) / TME_SPARC_LSINFO_ASI(1)) & 0xff) ! 434: #define TME_SPARC_LSINFO_ASI_FLAGS(x) TME_SPARC_LSINFO_ASI(x) ! 435: #define TME_SPARC_LSINFO_WHICH_ASI_FLAGS(x) TME_SPARC_LSINFO_WHICH_ASI(x) ! 436: #define TME_SPARC_LSINFO_A (1 << 16) ! 437: #define TME_SPARC_LSINFO_OP_LD (1 << 17) ! 438: #define TME_SPARC_LSINFO_OP_ST (1 << 18) ! 439: #define TME_SPARC_LSINFO_OP_ATOMIC (1 << 19) ! 440: #define TME_SPARC_LSINFO_OP_FETCH (1 << 20) ! 441: #define TME_SPARC_LSINFO_LDD_STD (1 << 21) ! 442: #define TME_SPARC_LSINFO_NO_FAULT (1 << 22) ! 443: #define TME_SPARC_LSINFO_NO_CHECK_TLB (1 << 23) ! 444: #define TME_SPARC_LSINFO_SLOW_CYCLES (1 << 24) ! 445: #define TME_SPARC_LSINFO_LD_COMPLETED (1 << 25) ! 446: #define TME_SPARC_LSINFO_ENDIAN_LITTLE (1 << 26) ! 447: #define _TME_SPARC_LSINFO_X(x) (1 << (27 + (x))) ! 448: ! 449: /* load/store faults: */ ! 450: #define TME_SPARC_LS_FAULT_NONE (0) ! 451: #define TME_SPARC_LS_FAULT_ADDRESS_NOT_ALIGNED TME_BIT(0) ! 452: #define TME_SPARC_LS_FAULT_LDD_STD_RD_ODD TME_BIT(1) ! 453: #define TME_SPARC_LS_FAULT_BUS_FAULT TME_BIT(2) ! 454: #define TME_SPARC_LS_FAULT_BUS_ERROR TME_BIT(3) ! 455: #define _TME_SPARC_LS_FAULT_X(x) TME_BIT(4 + (x)) ! 456: #define TME_SPARC64_LS_FAULT_PRIVILEGED_ASI _TME_SPARC_LS_FAULT_X(0) ! 457: #define TME_SPARC64_LS_FAULT_NO_FAULT_NON_LOAD _TME_SPARC_LS_FAULT_X(1) ! 458: #define TME_SPARC64_LS_FAULT_NO_FAULT_FAULT _TME_SPARC_LS_FAULT_X(2) ! 459: #define TME_SPARC64_LS_FAULT_SIDE_EFFECTS _TME_SPARC_LS_FAULT_X(3) ! 460: #define TME_SPARC64_LS_FAULT_VA_RANGE _TME_SPARC_LS_FAULT_X(4) ! 461: #define TME_SPARC64_LS_FAULT_VA_RANGE_NNPC _TME_SPARC_LS_FAULT_X(5) ! 462: #define TME_SPARC64_LS_FAULT_UNCACHEABLE _TME_SPARC_LS_FAULT_X(6) ! 463: #define _TME_SPARC64_LS_FAULT_X(x) _TME_SPARC_LS_FAULT_X(7 + (x)) ! 464: ! 465: /* flags for memory features: */ ! 466: #define TME_SPARC_MEMORY_FLAG_HAS_NUCLEUS (1 << 0) ! 467: #define TME_SPARC_MEMORY_FLAG_HAS_INVERT_ENDIAN (1 << 1) ! 468: #define TME_SPARC_MEMORY_FLAG_HAS_LDDF_STDF_32 (1 << 2) ! 469: #define TME_SPARC_MEMORY_FLAG_HAS_LDQF_STQF_32 (1 << 3) ! 470: ! 471: /* the undefined FPU register number: */ ! 472: #define TME_SPARC_FPU_FPREG_NUMBER_UNDEF (64) 1.1 root 473: 474: /* flags for FPU features: */ 475: #define TME_SPARC_FPU_FLAG_NO_QUAD TME_BIT(0) 476: #define TME_SPARC_FPU_FLAG_NO_FSQRT TME_BIT(1) 477: #define TME_SPARC_FPU_FLAG_NO_FMUL_WIDER TME_BIT(2) 478: #define TME_SPARC_FPU_FLAG_OK_REG_MISALIGNED TME_BIT(3) 479: 480: /* FPU modes: */ 481: #define TME_SPARC_FPU_MODE_EXECUTE (0) 482: #define TME_SPARC_FPU_MODE_EXCEPTION_PENDING (1) 483: #define TME_SPARC_FPU_MODE_EXCEPTION (2) 484: 1.1.1.2 ! root 485: /* this marks an FPU register as dirty: */ ! 486: #define TME_SPARC_FPU_DIRTY(ic, fpreg_number) \ ! 487: do { \ ! 488: if (TME_SPARC_VERSION(ic) >= 9) { \ ! 489: assert ((TME_SPARC64_FPRS_DU - 1) \ ! 490: == TME_SPARC64_FPRS_DL); \ ! 491: (ic)->tme_sparc64_ireg_fprs \ ! 492: |= (TME_SPARC64_FPRS_DU \ ! 493: - ((fpreg_number) < 32)); \ ! 494: } \ ! 495: } while (/* CONSTCOND */ 0) ! 496: ! 497: /* this returns nonzero if the FPU is disabled: */ ! 498: #define TME_SPARC_FPU_IS_DISABLED(ic) \ ! 499: ((TME_SPARC_VERSION(ic) < 9) \ ! 500: ? ((ic)->tme_sparc32_ireg_psr & TME_SPARC32_PSR_EF) == 0 \ ! 501: : (((ic)->tme_sparc64_ireg_pstate & TME_SPARC64_PSTATE_PEF) == 0 \ ! 502: || ((ic)->tme_sparc64_ireg_fprs & TME_SPARC64_FPRS_FEF) == 0)) ! 503: ! 504: /* this returns nonzero if recode supports this sparc: */ ! 505: #if TME_HAVE_RECODE ! 506: #ifndef TME_HAVE_INT64_T ! 507: #define TME_SPARC_HAVE_RECODE(ic) (1) ! 508: #else /* TME_HAVE_INT64_T */ ! 509: #define TME_SPARC_HAVE_RECODE(ic) \ ! 510: (TME_RECODE_SIZE_GUEST_MAX > TME_RECODE_SIZE_32 \ ! 511: || TME_SPARC_VERSION(ic) < 9) ! 512: #endif /* TME_HAVE_INT64_T */ ! 513: #else /* !TME_HAVE_RECODE */ ! 514: #define TME_SPARC_HAVE_RECODE(ic) (0) ! 515: #endif /* !TME_HAVE_RECODE */ ! 516: ! 517: #if TME_HAVE_RECODE ! 518: ! 519: /* this is the maximum number of cacheable address regions that we ! 520: will recode from: */ ! 521: #define TME_SPARC_RECODE_CACHEABLES_MAX (4) ! 522: ! 523: /* this is the modulus used in the recode source address hash: */ ! 524: #define TME_SPARC_RECODE_SRC_HASH_MODULUS (16381) ! 525: ! 526: /* the recode source address hash is set associative. this is the ! 527: number of ways in each set: */ ! 528: #define TME_SPARC_RECODE_SRC_HASH_SIZE_SET (4) ! 529: ! 530: /* the sparc recode TLB flags for loads and stores: */ ! 531: #define TME_SPARC_RECODE_TLB_FLAG_LD_USER(ic) TME_RECODE_TLB_FLAG(ic->tme_sparc_recode_ic, 0) ! 532: #define TME_SPARC_RECODE_TLB_FLAG_LD_PRIV(ic) TME_RECODE_TLB_FLAG(ic->tme_sparc_recode_ic, 1) ! 533: #define TME_SPARC_RECODE_TLB_FLAG_LD_NF(ic) TME_RECODE_TLB_FLAG(ic->tme_sparc_recode_ic, 2) ! 534: #define TME_SPARC_RECODE_TLB_FLAG_LD_F(ic) TME_RECODE_TLB_FLAG(ic->tme_sparc_recode_ic, 3) ! 535: #define TME_SPARC_RECODE_TLB_FLAG_ST_USER(ic) TME_RECODE_TLB_FLAG(ic->tme_sparc_recode_ic, 4) ! 536: #define TME_SPARC_RECODE_TLB_FLAG_ST_PRIV(ic) TME_RECODE_TLB_FLAG(ic->tme_sparc_recode_ic, 5) ! 537: #define TME_SPARC_RECODE_TLB_FLAG_LS_ENDIAN_LITTLE(ic) TME_RECODE_TLB_FLAG(ic->tme_sparc_recode_ic, 6) ! 538: #define TME_SPARC_RECODE_TLB_FLAG_LS_ENDIAN_BIG(ic) TME_RECODE_TLB_FLAG(ic->tme_sparc_recode_ic, 7) ! 539: #define TME_SPARC_RECODE_TLB_FLAG_LS_ENDIAN_INVERT(ic) TME_RECODE_TLB_FLAG(ic->tme_sparc_recode_ic, 8) ! 540: ! 541: /* the sparc recode TLB flags for chaining: */ ! 542: #define TME_SPARC_RECODE_TLB_FLAG_CHAIN_USER(ic) TME_RECODE_TLB_FLAG(ic->tme_sparc_recode_ic, 0) ! 543: #define TME_SPARC_RECODE_TLB_FLAG_CHAIN_PRIV(ic) TME_RECODE_TLB_FLAG(ic->tme_sparc_recode_ic, 1) ! 544: ! 545: #endif /* TME_HAVE_RECODE */ ! 546: 1.1 root 547: /* instruction handler macros: */ 548: #define TME_SPARC_FORMAT3_DECL(name, type) void name _TME_P((struct tme_sparc *, const type *, const type *, type *)) 549: #ifdef __STDC__ 550: #define TME_SPARC_FORMAT3(name, type) void name(struct tme_sparc *ic, const type *_rs1, const type *_rs2, type *_rd) 551: #else /* !__STDC__ */ 552: #define TME_SPARC_FORMAT3(name, type) void name(ic, _rs1, _rs2, _rd) struct tme_sparc *ic; const type *_rs1, *_rs2; type *_rd; 553: #endif /* !__STDC__ */ 554: #define TME_SPARC_FORMAT3_RS1 (*_rs1) 555: #define TME_SPARC_FORMAT3_RS2 (*_rs2) 556: #define TME_SPARC_FORMAT3_RD (*_rd) 1.1.1.2 ! root 557: #define TME_SPARC_FORMAT3_RD_ODD(iregs) (*(_rd + (&(((struct tme_ic *) NULL)->iregs(1)) - &(((struct tme_ic *) NULL)->iregs(0))))) 1.1 root 558: #define TME_SPARC_INSN ic->_tme_sparc_insn 559: #define TME_SPARC_INSN_OK return 560: #define TME_SPARC_INSN_TRAP(trap) \ 561: do { \ 562: if (TME_SPARC_VERSION(ic) < 9) { \ 563: tme_sparc32_trap(ic, trap); \ 564: } \ 565: else { \ 566: tme_sparc64_trap(ic, trap); \ 567: } \ 568: } while (/* CONSTCOND */ 0) 569: #define TME_SPARC_INSN_PRIV \ 570: do { \ 571: if (__tme_predict_false(!TME_SPARC_PRIV(ic))) { \ 1.1.1.2 ! root 572: TME_SPARC_INSN_TRAP(TME_SPARC_VERSION(ic) < 9 \ ! 573: ? TME_SPARC32_TRAP_privileged_instruction \ ! 574: : TME_SPARC64_TRAP_privileged_opcode); \ 1.1 root 575: } \ 576: } while (/* CONSTCOND */ 0) 1.1.1.2 ! root 577: #define TME_SPARC_INSN_FPU_ENABLED \ 1.1 root 578: do { \ 1.1.1.2 ! root 579: if (__tme_predict_false(TME_SPARC_FPU_IS_DISABLED(ic))) { \ ! 580: TME_SPARC_INSN_TRAP(TME_SPARC_TRAP(ic,fp_disabled));\ ! 581: } \ 1.1 root 582: } while (/* CONSTCOND */ 0) 1.1.1.2 ! root 583: #define TME_SPARC_INSN_FPU \ 1.1 root 584: do { \ 1.1.1.2 ! root 585: TME_SPARC_INSN_FPU_ENABLED; \ 1.1 root 586: if (__tme_predict_false((ic)->tme_sparc_fpu_mode \ 1.1.1.2 ! root 587: != TME_SPARC_FPU_MODE_EXECUTE)) { \ 1.1 root 588: tme_sparc_fpu_exception_check(ic); \ 589: } \ 590: } while (/* CONSTCOND */ 0) 591: 1.1.1.2 ! root 592: #define TME_SPARC_INSN_ILL(ic) \ ! 593: TME_SPARC_INSN_TRAP(TME_SPARC_TRAP(ic,illegal_instruction)) 1.1 root 594: 595: /* logging: */ 596: #define TME_SPARC_LOG_HANDLE(ic) \ 597: (&(ic)->tme_sparc_element->tme_element_log_handle) 598: #define tme_sparc_log_start(ic, level, rc) \ 599: do { \ 600: tme_log_start(TME_SPARC_LOG_HANDLE(ic), level, rc) { \ 601: if ((ic)->_tme_sparc_mode != TME_SPARC_MODE_EXECUTION) { \ 602: tme_log_part(TME_SPARC_LOG_HANDLE(ic), \ 603: "mode=%d ", \ 604: (ic)->_tme_sparc_mode); \ 605: } \ 1.1.1.2 ! root 606: else if (TME_SPARC_VERSION(ic) < 9) { \ ! 607: tme_log_part(TME_SPARC_LOG_HANDLE(ic), \ ! 608: "pc=%c/0x%08" TME_PRIx32 " ", \ ! 609: (TME_SPARC_PRIV(ic) \ ! 610: ? 'S' \ ! 611: : 'U'), \ ! 612: ic->tme_sparc_ireg_uint32(TME_SPARC_IREG_PC)); \ ! 613: } \ 1.1 root 614: else { \ 615: tme_log_part(TME_SPARC_LOG_HANDLE(ic), \ 1.1.1.2 ! root 616: "pc=%c/0x%08" TME_PRIx64 " ", \ 1.1 root 617: (TME_SPARC_PRIV(ic) \ 618: ? 'S' \ 619: : 'U'), \ 1.1.1.2 ! root 620: ic->tme_sparc_ireg_uint64(TME_SPARC_IREG_PC)); \ 1.1 root 621: } \ 622: do 623: #define tme_sparc_log_finish(ic) \ 624: while (/* CONSTCOND */ 0); \ 625: } tme_log_finish(TME_SPARC_LOG_HANDLE(ic)); \ 626: } while (/* CONSTCOND */ 0) 627: #define tme_sparc_log(ic, level, rc, x) \ 628: do { \ 629: tme_sparc_log_start(ic, level, rc) { \ 630: tme_log_part x; \ 631: } tme_sparc_log_finish(ic); \ 632: } while (/* CONSTCOND */ 0) 633: 1.1.1.2 ! root 634: /* PROM delay factors: */ ! 635: #define TME_SPARC_PROM_DELAY_FACTOR_UNCORRECTED ((tme_uint32_t) (0 - (tme_uint32_t) 1)) ! 636: #define TME_SPARC_PROM_DELAY_FACTOR_BEST ((tme_uint32_t) (0 - (tme_uint32_t) 2)) ! 637: #define TME_SPARC_PROM_DELAY_FACTOR_MIN ((tme_uint32_t) (0 - (tme_uint32_t) 3)) ! 638: ! 639: /* flags for _tme_sparc_external_check(): */ ! 640: #define TME_SPARC_EXTERNAL_CHECK_NULL (0) ! 641: #define TME_SPARC_EXTERNAL_CHECK_MUTEX_LOCKED (1 << 0) ! 642: #define TME_SPARC_EXTERNAL_CHECK_PCS_UPDATED (1 << 1) ! 643: 1.1 root 644: /* miscellaneous: */ 645: #define _TME_SPARC_VERSION(ic) ((ic)->tme_sparc_version) 646: #define _TME_SPARC_NWINDOWS(ic) ((ic)->tme_sparc_nwindows) 1.1.1.2 ! root 647: #define _TME_SPARC_MEMORY_FLAGS(ic) ((ic)->tme_sparc_memory_flags) 1.1 root 648: #define _TME_SPARC32_PRIV(ic) (((ic)->tme_sparc32_ireg_psr & TME_SPARC32_PSR_S) != 0) 649: #define _TME_SPARC64_PRIV(ic) (((ic)->tme_sparc64_ireg_pstate & TME_SPARC64_PSTATE_PRIV) != 0) 650: #define TME_SPARC_VERSION(ic) _TME_SPARC_VERSION(ic) 651: #define TME_SPARC_NWINDOWS(ic) _TME_SPARC_NWINDOWS(ic) 1.1.1.2 ! root 652: #define TME_SPARC_MEMORY_FLAGS(ic) _TME_SPARC_MEMORY_FLAGS(ic) 1.1 root 653: #define TME_SPARC_PRIV(ic) \ 654: ((TME_SPARC_VERSION(ic) < 9) \ 655: ? _TME_SPARC32_PRIV(ic) \ 656: : _TME_SPARC64_PRIV(ic)) 657: 658: /* structures: */ 659: struct tme_sparc; 660: 1.1.1.2 ! root 661: /* the widest supported sparc register: */ ! 662: #ifdef TME_HAVE_INT64_T ! 663: typedef tme_uint64_t tme_sparc_ireg_umax_t; ! 664: #else /* !TME_HAVE_INT64_T */ ! 665: typedef tme_uint32_t tme_sparc_ireg_umax_t; ! 666: #endif /* !TME_HAVE_INT64_T */ ! 667: 1.1 root 668: /* format 3 instruction functions: */ 669: typedef TME_SPARC_FORMAT3_DECL((*_tme_sparc32_format3), tme_uint32_t); 1.1.1.2 ! root 670: #ifdef TME_HAVE_INT64_T ! 671: typedef TME_SPARC_FORMAT3_DECL((*_tme_sparc64_format3), tme_uint64_t); ! 672: #endif /* TME_HAVE_INT64_T */ 1.1 root 673: 674: /* a sparc deferred-trap queue: */ 675: struct tme_sparc_trapqueue { 676: #ifdef TME_HAVE_INT64_T 677: tme_uint64_t tme_sparc_trapqueue_address; 678: #else /* !TME_HAVE_INT64_T */ 679: tme_uint32_t tme_sparc_trapqueue_address; 680: #endif /* !TME_HAVE_INT64_T */ 681: tme_uint32_t tme_sparc_trapqueue_insn; 682: }; 683: 1.1.1.2 ! root 684: /* a sparc load/store: */ ! 685: struct tme_sparc_ls { ! 686: ! 687: /* this maps an address for the bus: */ ! 688: void (*tme_sparc_ls_address_map) _TME_P((struct tme_sparc *, struct tme_sparc_ls *)); ! 689: ! 690: /* the current slow cycle function: */ ! 691: void (*tme_sparc_ls_cycle) _TME_P((struct tme_sparc *, struct tme_sparc_ls *)); ! 692: ! 693: /* a pointer to the rd register: */ ! 694: union { ! 695: tme_uint32_t *_tme_sparc_ls_rd_u_32; ! 696: #define tme_sparc_ls_rd32 _tme_sparc_ls_rd_u._tme_sparc_ls_rd_u_32 ! 697: #ifdef TME_HAVE_INT64_T ! 698: tme_uint64_t *_tme_sparc_ls_rd_u_64; ! 699: #define tme_sparc_ls_rd64 _tme_sparc_ls_rd_u._tme_sparc_ls_rd_u_64 ! 700: #endif /* TME_HAVE_INT64_T */ ! 701: } _tme_sparc_ls_rd_u; ! 702: ! 703: /* a pointer to the TLB entry: */ ! 704: struct tme_sparc_tlb *tme_sparc_ls_tlb; ! 705: ! 706: /* the current address: */ ! 707: union { ! 708: tme_uint32_t _tme_sparc_ls_address_u_32; ! 709: #define tme_sparc_ls_address32 _tme_sparc_ls_address_u._tme_sparc_ls_address_u_32 ! 710: #ifdef TME_HAVE_INT64_T ! 711: tme_uint64_t _tme_sparc_ls_address_u_64; ! 712: #define tme_sparc_ls_address64 _tme_sparc_ls_address_u._tme_sparc_ls_address_u_64 ! 713: #endif /* TME_HAVE_INT64_T */ ! 714: } _tme_sparc_ls_address_u; ! 715: ! 716: /* the context and ASI mask: */ ! 717: tme_bus_context_t tme_sparc_ls_context; ! 718: tme_uint32_t tme_sparc_ls_asi_mask; ! 719: ! 720: /* the index of the TLB entry: */ ! 721: tme_uint32_t tme_sparc_ls_tlb_i; ! 722: ! 723: /* the lsinfo: */ ! 724: tme_uint32_t tme_sparc_ls_lsinfo; ! 725: ! 726: /* any fault information: */ ! 727: tme_uint32_t tme_sparc_ls_faults; ! 728: ! 729: /* the current size: */ ! 730: tme_uint8_t tme_sparc_ls_size; ! 731: ! 732: /* the current offset in the memory buffer: */ ! 733: tme_uint8_t tme_sparc_ls_buffer_offset; ! 734: ! 735: /* some current state of the operation: */ ! 736: tme_uint8_t tme_sparc_ls_state; ! 737: ! 738: /* a mapping TLB entry: */ ! 739: struct tme_bus_tlb tme_sparc_ls_tlb_map; ! 740: ! 741: /* a bus cycle structure: */ ! 742: struct tme_bus_cycle tme_sparc_ls_bus_cycle; ! 743: }; ! 744: ! 745: /* ASI handlers: */ ! 746: typedef void (*_tme_sparc_ls_asi_handler) _TME_P((struct tme_sparc *, struct tme_sparc_ls *)); ! 747: ! 748: #if TME_HAVE_RECODE ! 749: ! 750: /* this is the type used for keys in the recode source address hash. ! 751: if the widest recode guest is only 32 bits, we only need a ! 752: tme_uint32_t, because a sparc32 recode guest can only make 32-bit ! 753: guest addresses. ! 754: ! 755: otherwise, we use an unsigned long, which we assume is at least as ! 756: wide as the address size of the *host*. NB that this may be ! 757: narrower than the address size of a sparc guest, but since source ! 758: address hash keys are for guest addresses that are cacheable, which ! 759: correspond to host addresses, this is fine (the source address hash ! 760: key is essentially the guest address mapped into the host address ! 761: space): */ ! 762: #if TME_RECODE_SIZE_GUEST_MAX <= TME_RECODE_SIZE_32 ! 763: typedef tme_uint32_t tme_sparc_recode_src_key_t; ! 764: #else /* TME_RECODE_SIZE_GUEST_MAX > TME_RECODE_SIZE_32 */ ! 765: typedef unsigned long tme_sparc_recode_src_key_t; ! 766: #endif /* TME_RECODE_SIZE_GUEST_MAX > TME_RECODE_SIZE_32 */ ! 767: ! 768: /* a recode cacheable source memory: */ ! 769: struct tme_sparc_recode_cacheable { ! 770: ! 771: /* the cacheable contents and size: */ ! 772: const tme_shared tme_uint8_t *tme_sparc_recode_cacheable_contents; ! 773: unsigned long tme_sparc_recode_cacheable_size; ! 774: ! 775: /* the source address hash key for the first instruction word in the ! 776: cacheable contents: */ ! 777: tme_sparc_recode_src_key_t tme_sparc_recode_cacheable_src_key_first; ! 778: ! 779: /* the valids bitmap for this cacheable: */ ! 780: tme_shared tme_uint8_t *tme_sparc_recode_cacheable_valids; ! 781: }; ! 782: ! 783: #endif /* TME_HAVE_RECODE */ ! 784: 1.1 root 785: /* the sparc state: */ 786: struct tme_sparc { 787: 788: /* the IC data structure. it is beneficial to have this structure 789: first, since register numbers can often simply be scaled and 790: added without an offset to the struct tme_sparc pointer to get 791: to their contents: */ 792: struct tme_ic tme_sparc_ic; 793: 1.1.1.2 ! root 794: /* the cycles scaling: */ ! 795: tme_misc_cycles_scaling_t tme_sparc_cycles_scaling; ! 796: tme_misc_cycles_scaling_t tme_sparc_cycles_unscaling; ! 797: ! 798: /* the number of scaled cycles per microsecond: */ ! 799: tme_uint32_t tme_sparc_cycles_scaled_per_usec; ! 800: ! 801: /* the register offsets for the four groups of eight registers: */ ! 802: tme_int8_t tme_sparc_reg8_offset[4]; 1.1 root 803: 804: /* the architecture version, and number of windows: */ 805: unsigned int tme_sparc_version; 806: unsigned int tme_sparc_nwindows; 807: 1.1.1.2 ! root 808: /* v9 constants: */ ! 809: unsigned int tme_sparc64_maxtl; ! 810: 1.1 root 811: /* the backpointer to our element: */ 812: struct tme_element *tme_sparc_element; 813: 1.1.1.2 ! root 814: /* our bus connection. the sparc bus connection may be an ! 815: adaptation layer for another bus connection type: */ ! 816: struct tme_upa_bus_connection *_tme_upa_bus_connection; 1.1 root 817: struct tme_sparc_bus_connection *_tme_sparc_bus_connection; 818: struct tme_bus_connection *_tme_sparc_bus_generic; 819: 820: /* a jmp_buf back to the dispatcher: */ 821: jmp_buf _tme_sparc_dispatcher; 822: 823: /* the current mode of the CPU: */ 824: int _tme_sparc_mode; 825: 826: /* address space identifiers and masks: */ 827: tme_uint32_t tme_sparc_asi_mask_insn; 828: tme_uint32_t tme_sparc_asi_mask_data; 829: 1.1.1.2 ! root 830: /* the implementation-dependent data: */ ! 831: union { ! 832: const _tme_sparc32_format3 *_tme_sparc_execute_opmap_u_32; ! 833: #define _tme_sparc32_execute_opmap _tme_sparc_execute_opmap_u._tme_sparc_execute_opmap_u_32 ! 834: #ifdef TME_HAVE_INT64_T ! 835: const _tme_sparc64_format3 *_tme_sparc_execute_opmap_u_64; ! 836: #define _tme_sparc64_execute_opmap _tme_sparc_execute_opmap_u._tme_sparc_execute_opmap_u_64 ! 837: #endif /* TME_HAVE_INT64_T */ ! 838: } _tme_sparc_execute_opmap_u; ! 839: tme_uint32_t (*_tme_sparc_ls_asi_misaligned) _TME_P((struct tme_sparc *, tme_uint32_t)); ! 840: const _tme_sparc_ls_asi_handler *_tme_sparc_ls_asi_handlers; ! 841: #ifdef TME_HAVE_INT64_T ! 842: tme_uint64_t tme_sparc64_rstvaddr; ! 843: #endif /* TME_HAVE_INT64_T */ ! 844: 1.1 root 845: /* the implementation-dependent functions: */ 846: void (*_tme_sparc_execute) _TME_P((struct tme_sparc *)); 847: tme_uint32_t (*_tme_sparc_fpu_ver) _TME_P((struct tme_sparc *, const char *, char **)); 1.1.1.2 ! root 848: void (*_tme_sparc_external_check) _TME_P((struct tme_sparc *, int)); ! 849: void (*_tme_sparc_ls_address_map) _TME_P((struct tme_sparc *, struct tme_sparc_ls *)); ! 850: void (*_tme_sparc_ls_bus_cycle) _TME_P((const struct tme_sparc *, struct tme_sparc_ls *)); ! 851: void (*_tme_sparc_ls_bus_fault) _TME_P((struct tme_sparc *, struct tme_sparc_ls *, int)); ! 852: void (*_tme_sparc_ls_trap) _TME_P((struct tme_sparc *, struct tme_sparc_ls *)); ! 853: int (*_tme_sparc_tlb_fill) _TME_P((struct tme_bus_connection *, ! 854: struct tme_bus_tlb *, ! 855: tme_bus_addr_t, ! 856: unsigned int)); ! 857: #ifdef TME_HAVE_INT64_T ! 858: void (*_tme_sparc_upa_interrupt) _TME_P((struct tme_upa_bus_connection *, ! 859: tme_uint32_t, ! 860: const tme_uint64_t *, ! 861: struct tme_completion *)); ! 862: #endif /* TME_HAVE_INT64_T */ ! 863: void (*_tme_sparc64_update_pstate) _TME_P((struct tme_sparc *, tme_uint32_t, tme_uint32_t)); ! 864: ! 865: /* the runlength state: */ ! 866: struct tme_runlength tme_sparc_runlength; ! 867: tme_uint32_t tme_sparc_runlength_update_period; ! 868: tme_uint32_t tme_sparc_runlength_update_next; ! 869: ! 870: /* the instruction burst counts, and the remaining burst: */ ! 871: #define _tme_sparc_instruction_burst tme_sparc_runlength.tme_runlength_value ! 872: tme_uint32_t _tme_sparc_instruction_burst_idle; ! 873: tme_uint32_t _tme_sparc_instruction_burst_remaining; ! 874: unsigned int _tme_sparc_instruction_burst_other; 1.1 root 875: 1.1.1.2 ! root 876: /* the token for any currently busy instruction TLB entry: */ ! 877: struct tme_token *_tme_sparc_itlb_current_token; 1.1 root 878: 879: /* instruction information: */ 880: tme_uint32_t _tme_sparc_insn; 881: 1.1.1.2 ! root 882: /* memory flags: */ ! 883: tme_uint32_t tme_sparc_memory_flags; ! 884: ! 885: /* ASIs: */ ! 886: struct { ! 887: tme_uint8_t tme_sparc_asi_mask_flags; ! 888: tme_uint8_t tme_sparc_asi_handler; ! 889: } tme_sparc_asis[0x100]; ! 890: ! 891: /* contexts: */ ! 892: tme_bus_context_t tme_sparc_memory_context_max; ! 893: tme_bus_context_t tme_sparc_memory_context_default; ! 894: tme_uint32_t tme_sparc_memory_context_primary; ! 895: tme_uint32_t tme_sparc_memory_context_secondary; 1.1 root 896: 1.1.1.2 ! root 897: /* the external interface: */ 1.1 root 898: tme_mutex_t tme_sparc_external_mutex; 899: tme_cond_t tme_sparc_external_cond; 1.1.1.2 ! root 900: tme_memory_atomic_flag_t tme_sparc_external_flag; ! 901: tme_memory_atomic_flag_t tme_sparc_external_reset_asserted; ! 902: tme_memory_atomic_flag_t tme_sparc_external_reset_negated; ! 903: tme_memory_atomic_flag_t tme_sparc_external_halt_asserted; ! 904: tme_memory_atomic_flag_t tme_sparc_external_halt_negated; ! 905: tme_memory_atomic_flag_t tme_sparc_external_bg_asserted; ! 906: tme_shared tme_uint8_t tme_sparc_external_ipl; ! 907: tme_rwlock_t tme_sparc_external_ipl_rwlock; 1.1 root 908: 909: /* the slow load/store buffer: */ 1.1.1.2 ! root 910: union { ! 911: tme_uint8_t tme_sparc_memory_buffer8s[64]; ! 912: tme_uint16_t tme_sparc_memory_buffer16s[32]; ! 913: tme_uint32_t tme_sparc_memory_buffer32s[16]; ! 914: #ifdef TME_HAVE_INT64_T ! 915: tme_uint64_t tme_sparc_memory_buffer64s[8]; ! 916: #endif /* TME_HAVE_INT64_T */ ! 917: } tme_sparc_memory_buffer; 1.1 root 918: 919: /* any FPU state: */ 920: struct tme_ieee754_ctl tme_sparc_fpu_ieee754_ctl; 921: _tme_const struct tme_ieee754_ops *tme_sparc_fpu_ieee754_ops; 922: _tme_const struct tme_ieee754_ops *tme_sparc_fpu_ieee754_ops_user; 923: _tme_const struct tme_ieee754_ops *tme_sparc_fpu_ieee754_ops_strict; 1.1.1.2 ! root 924: struct tme_float tme_sparc_fpu_fpregs[TME_SPARC_FPU_FPREG_NUMBER_UNDEF]; ! 925: unsigned int tme_sparc_fpu_fpreg_sizes[TME_SPARC_FPU_FPREG_NUMBER_UNDEF]; 1.1 root 926: tme_uint32_t tme_sparc_fpu_fsr; 1.1.1.2 ! root 927: tme_uint32_t tme_sparc_fpu_xfsr; 1.1 root 928: struct tme_sparc_trapqueue tme_sparc_fpu_fq[1]; 929: unsigned int tme_sparc_fpu_mode; 930: unsigned int tme_sparc_fpu_flags; 931: int tme_sparc_fpu_incomplete_abort; 932: 1.1.1.2 ! root 933: /* any VIS state: */ ! 934: tme_uint32_t tme_sparc_vis_ls_fault_illegal; ! 935: tme_uint8_t tme_sparc_vis_gsr; ! 936: ! 937: /* the idle state: */ ! 938: tme_uint8_t tme_sparc_idle_marks; 1.1 root 939: unsigned int tme_sparc_idle_type; 1.1.1.2 ! root 940: union { ! 941: tme_uint32_t tme_sparc_idle_pcs_32[4]; ! 942: #ifdef TME_HAVE_INT64_T ! 943: tme_uint64_t tme_sparc_idle_pcs_64[4]; ! 944: #endif /* TME_HAVE_INT64_T */ ! 945: } tme_sparc_idle_pcs; ! 946: #define tme_sparc_idle_pcs_32 tme_sparc_idle_pcs.tme_sparc_idle_pcs_32 ! 947: #define tme_sparc_idle_pcs_64 tme_sparc_idle_pcs.tme_sparc_idle_pcs_64 ! 948: ! 949: /* the address mask: */ ! 950: tme_sparc_ireg_umax_t tme_sparc_address_mask; ! 951: ! 952: /* the PROM delay factor: */ ! 953: tme_uint32_t tme_sparc_prom_delay_factor; ! 954: ! 955: /* the log2 of the TLB page size: */ ! 956: unsigned int tme_sparc_tlb_page_size_log2; ! 957: ! 958: /* the data and instruction TLB entry sets: */ ! 959: struct tme_sparc_tlb tme_sparc_tlbs[_TME_SPARC_TLB_COUNT]; ! 960: ! 961: /* either tokens or recode TLB entries for the sparc TLB entries: */ ! 962: union { ! 963: struct tme_token _tme_sparc_tlb_tokens_u_tokens[_TME_SPARC_TLB_COUNT]; ! 964: #define tme_sparc_tlb_tokens _tme_sparc_tlb_tokens_u._tme_sparc_tlb_tokens_u_tokens ! 965: #if TME_HAVE_RECODE ! 966: struct tme_recode_tlb_c16_a32 _tme_sparc_tlb_tokens_u_tlb32s[_TME_SPARC_TLB_COUNT]; ! 967: #define tme_sparc_recode_tlb32s _tme_sparc_tlb_tokens_u._tme_sparc_tlb_tokens_u_tlb32s ! 968: #if TME_RECODE_SIZE_GUEST_MAX > TME_RECODE_SIZE_32 ! 969: struct tme_recode_tlb_c16_a64 _tme_sparc_tlb_tokens_u_tlb64s[_TME_SPARC_TLB_COUNT]; ! 970: #define tme_sparc_recode_tlb64s _tme_sparc_tlb_tokens_u._tme_sparc_tlb_tokens_u_tlb64s ! 971: #endif /* TME_RECODE_SIZE_GUEST_MAX > TME_RECODE_SIZE_32 */ ! 972: #endif /* TME_HAVE_RECODE */ ! 973: } _tme_sparc_tlb_tokens_u; ! 974: ! 975: /* timing information: */ ! 976: tme_uint8_t tme_sparc_timing_loop_cycles_each; ! 977: tme_int8_t tme_sparc_timing_loop_addend; ! 978: tme_uint8_t tme_sparc_timing_loop_branch_taken_max; ! 979: tme_sparc_ireg_umax_t tme_sparc_timing_loop_branch_taken_count_max_m1; ! 980: union tme_value64 tme_sparc_timing_loop_start; ! 981: union tme_value64 tme_sparc_timing_loop_finish; ! 982: ! 983: #if TME_HAVE_RECODE ! 984: ! 985: /* the recode IC: */ ! 986: struct tme_recode_ic *tme_sparc_recode_ic; ! 987: ! 988: /* the register window base offsets. %r8 through %r23 use window ! 989: zero, %r24 through %r31 use window one, and %r0 through %r7 use ! 990: window two: */ ! 991: tme_int32_t tme_sparc_recode_window_base_offsets[3]; ! 992: ! 993: /* the flags thunks: */ ! 994: const struct tme_recode_flags_thunk *tme_sparc_recode_flags_thunk_add; ! 995: const struct tme_recode_flags_thunk *tme_sparc_recode_flags_thunk_sub; ! 996: const struct tme_recode_flags_thunk *tme_sparc_recode_flags_thunk_logical; ! 997: const struct tme_recode_flags_thunk *tme_sparc_recode_flags_thunk_rcc; ! 998: ! 999: /* the conditions thunks: */ ! 1000: const struct tme_recode_conds_thunk *tme_sparc_recode_conds_thunk_icc; ! 1001: const struct tme_recode_conds_thunk *tme_sparc_recode_conds_thunk_xcc; ! 1002: const struct tme_recode_conds_thunk *tme_sparc_recode_conds_thunk_rcc; ! 1003: ! 1004: /* the read/write thunks: */ ! 1005: const struct tme_recode_rw_thunk *tme_sparc_recode_rw_thunks[128]; ! 1006: ! 1007: /* the current read/write TLB flags: */ ! 1008: tme_uint32_t tme_sparc_recode_rw_tlb_flags; ! 1009: ! 1010: /* the current chain TLB flags: */ ! 1011: tme_uint32_t tme_sparc_recode_chain_tlb_flags; ! 1012: ! 1013: /* the chain return address stack: */ ! 1014: tme_recode_ras_entry_t _tme_sparc_recode_chain_ras[16]; ! 1015: tme_uint32_t _tme_sparc_recode_chain_ras_pointer; ! 1016: ! 1017: /* the recode cacheable source memories: */ ! 1018: struct tme_sparc_recode_cacheable tme_sparc_recode_cacheables[TME_SPARC_RECODE_CACHEABLES_MAX]; ! 1019: ! 1020: /* the most recently added cacheable: */ ! 1021: struct tme_sparc_recode_cacheable *tme_sparc_recode_cacheable_first; ! 1022: ! 1023: /* the bitmap of active cacheable recode pages: */ ! 1024: tme_uint8_t *tme_sparc_recode_cacheable_actives; ! 1025: ! 1026: /* the recode source hash: */ ! 1027: /* NB: conceptually, each entry in the recode source address hash is ! 1028: one tme_sparc_recode_src_key_t and one tme_recode_thunk_off_t. ! 1029: since these types may be different sizes, to guarantee that the ! 1030: recode source address hash is packed, each element of this recode ! 1031: source address hash array covers this many entries: */ ! 1032: #define TME_SPARC_RECODE_SRC_HASH_SIZE_ELEMENT \ ! 1033: ((sizeof(tme_sparc_recode_src_key_t) \ ! 1034: + (sizeof(tme_recode_thunk_off_t) - 1)) \ ! 1035: / sizeof(tme_recode_thunk_off_t)) ! 1036: struct { ! 1037: ! 1038: /* the source address hash keys: */ ! 1039: tme_sparc_recode_src_key_t tme_sparc_recode_src_hash_keys[TME_SPARC_RECODE_SRC_HASH_SIZE_ELEMENT]; ! 1040: ! 1041: /* if bit zero is set, the remaining bits of the hash value are ! 1042: the hit count for the program counter, otherwise, the entire ! 1043: hash value is the offset of the instructions thunk for the ! 1044: program counter: */ ! 1045: tme_recode_thunk_off_t tme_sparc_recode_src_hash_values[TME_SPARC_RECODE_SRC_HASH_SIZE_ELEMENT]; ! 1046: ! 1047: } tme_sparc_recode_src_hash[(TME_SPARC_RECODE_SRC_HASH_MODULUS ! 1048: * TME_SPARC_RECODE_SRC_HASH_SIZE_SET) ! 1049: / TME_SPARC_RECODE_SRC_HASH_SIZE_ELEMENT]; ! 1050: ! 1051: /* an instructions group: */ ! 1052: struct tme_recode_insns_group tme_sparc_recode_insns_group; ! 1053: ! 1054: /* the recode insns buffer: */ ! 1055: struct tme_recode_insn tme_sparc_recode_insns[TME_RECODE_INSNS_THUNK_INSNS_MAX]; ! 1056: ! 1057: #ifdef _TME_SPARC_RECODE_VERIFY ! 1058: ! 1059: /* the last PC to replay, or zero if instructions are not being ! 1060: replayed: */ ! 1061: tme_recode_uguest_t tme_sparc_recode_verify_replay_last_pc; ! 1062: ! 1063: /* the size of the sparc state to verify, and the sparc state total ! 1064: size: */ ! 1065: unsigned long tme_sparc_recode_verify_ic_size; ! 1066: unsigned long tme_sparc_recode_verify_ic_size_total; ! 1067: ! 1068: #endif /* _TME_SPARC_RECODE_VERIFY */ ! 1069: ! 1070: #endif /* TME_HAVE_RECODE */ 1.1 root 1071: 1072: #ifdef _TME_SPARC_STATS 1073: /* statistics: */ 1074: struct { 1075: 1076: /* the total number of instructions executed: */ 1077: tme_uint64_t tme_sparc_stats_insns_total; 1078: 1079: /* the total number of instructions fetched slowly: */ 1.1.1.2 ! root 1080: tme_uint64_t tme_sparc_stats_insns_slow; 1.1 root 1081: 1082: /* the total number of redispatches: */ 1083: tme_uint64_t tme_sparc_stats_redispatches; 1084: 1085: /* the total number of data memory operations: */ 1086: tme_uint64_t tme_sparc_stats_memory_total; 1087: 1.1.1.2 ! root 1088: /* the total number of ITLB maps: */ ! 1089: tme_uint64_t tme_sparc_stats_itlb_map; ! 1090: ! 1091: /* the total number of DTLB map: */ ! 1092: tme_uint64_t tme_sparc_stats_dtlb_map; ! 1093: 1.1 root 1094: /* the total number of ITLB fills: */ 1095: tme_uint64_t tme_sparc_stats_itlb_fill; 1096: 1097: /* the total number of DTLB fills: */ 1098: tme_uint64_t tme_sparc_stats_dtlb_fill; 1099: 1.1.1.2 ! root 1100: #if TME_HAVE_RECODE ! 1101: ! 1102: /* the total number of calls to tme_sparc_recode(): */ ! 1103: tme_uint64_t tme_sparc_stats_recode_calls; ! 1104: ! 1105: /* the total number of active recode page invalidations: */ ! 1106: tme_uint64_t tme_sparc_stats_recode_page_invalids; ! 1107: ! 1108: /* the total number of recode source hash probes: */ ! 1109: tme_uint64_t tme_sparc_stats_recode_source_hash_probes; ! 1110: ! 1111: /* the total number of recode source hash misses: */ ! 1112: tme_uint64_t tme_sparc_stats_recode_source_hash_misses; ! 1113: ! 1114: /* the total number of instructions executed in thunks: */ ! 1115: tme_uint64_t tme_sparc_stats_recode_insns_total; ! 1116: ! 1117: /* the total number of various assists: */ ! 1118: tme_uint64_t tme_sparc_stats_recode_assist; ! 1119: tme_uint64_t tme_sparc_stats_recode_assist_full; ! 1120: tme_uint64_t tme_sparc_stats_recode_assist_ld; ! 1121: tme_uint64_t tme_sparc_stats_recode_assist_st; ! 1122: ! 1123: /* the total number of assists by opcode: */ ! 1124: tme_uint64_t tme_sparc_stats_recode_assist_opcode[128]; ! 1125: ! 1126: #endif /* TME_HAVE_RECODE */ ! 1127: 1.1 root 1128: } tme_sparc_stats; 1.1.1.2 ! root 1129: #define TME_SPARC_STAT_N(ic, x, n) do { (ic)->tme_sparc_stats.x += (n); } while (/* CONSTCOND */ 0) ! 1130: #else /* !_TME_SPARC_STATS */ ! 1131: #define TME_SPARC_STAT_N(ic, x, n) do { } while (/* CONSTCOND */ 0 && (ic) && (n)) ! 1132: #endif /* !_TME_SPARC_STATS */ ! 1133: #define TME_SPARC_STAT(ic, x) TME_SPARC_STAT_N(ic, x, 1) 1.1 root 1134: }; 1135: 1136: /* globals: */ 1137: extern const tme_uint8_t _tme_sparc_conds_icc[16]; 1138: extern const tme_uint8_t _tme_sparc_conds_fcc[4]; 1139: 1140: /* prototypes: */ 1.1.1.2 ! root 1141: void tme_sparc_sync_init _TME_P((struct tme_sparc *)); 1.1 root 1142: int tme_sparc_new _TME_P((struct tme_sparc *, const char * const *, const void *, char **)); 1143: void tme_sparc_redispatch _TME_P((struct tme_sparc *)); 1144: void tme_sparc_do_reset _TME_P((struct tme_sparc *)); 1145: void tme_sparc_do_idle _TME_P((struct tme_sparc *)); 1.1.1.2 ! root 1146: void tme_sparc32_external_check _TME_P((struct tme_sparc *, int)); ! 1147: struct tme_sparc_tlb *tme_sparc_itlb_current _TME_P((struct tme_sparc *)); ! 1148: tme_uint32_t tme_sparc_insn_peek _TME_P((struct tme_sparc *, tme_sparc_ireg_umax_t)); 1.1 root 1149: tme_uint32_t tme_sparc_fetch_nearby _TME_P((struct tme_sparc *, long)); 1150: void tme_sparc_callout_unlock _TME_P((struct tme_sparc *)); 1151: void tme_sparc_callout_relock _TME_P((struct tme_sparc *)); 1152: 1.1.1.2 ! root 1153: /* load/store support: */ ! 1154: void tme_sparc_ls_bus_fault _TME_P((struct tme_sparc *, struct tme_sparc_ls *, int)); ! 1155: void tme_sparc32_ls_address_map _TME_P((struct tme_sparc *, struct tme_sparc_ls *)); ! 1156: void tme_sparc32_ls_bus_cycle _TME_P((const struct tme_sparc *, struct tme_sparc_ls *)); ! 1157: void tme_sparc32_ls_trap _TME_P((struct tme_sparc *, struct tme_sparc_ls *)); ! 1158: 1.1 root 1159: /* trap support: */ 1.1.1.2 ! root 1160: void tme_sparc32_trap_preinstruction _TME_P((struct tme_sparc *, tme_uint32_t)); 1.1 root 1161: void tme_sparc32_trap _TME_P((struct tme_sparc *, tme_uint32_t)); 1.1.1.2 ! root 1162: void tme_sparc64_trap_preinstruction _TME_P((struct tme_sparc *, tme_uint32_t)); 1.1 root 1163: void tme_sparc64_trap _TME_P((struct tme_sparc *, tme_uint32_t)); 1.1.1.2 ! root 1164: void tme_sparc64_trap_error_state _TME_P((struct tme_sparc *)); ! 1165: void tme_sparc_nnpc_trap _TME_P((struct tme_sparc *, tme_uint32_t)); 1.1 root 1166: 1167: /* FPU support: */ 1168: int tme_sparc_fpu_new _TME_P((struct tme_sparc *, const char * const *, int *, int *, char **)); 1169: void tme_sparc_fpu_reset _TME_P((struct tme_sparc *)); 1170: void tme_sparc_fpu_usage _TME_P((struct tme_sparc *, char **)); 1171: void tme_sparc_fpu_strict _TME_P((struct tme_sparc_bus_connection *, unsigned int)); 1172: void tme_sparc_fpu_exception_check _TME_P((struct tme_sparc *)); 1.1.1.2 ! root 1173: unsigned int tme_sparc_fpu_fpreg_decode _TME_P((struct tme_sparc *, unsigned int, unsigned int)); 1.1 root 1174: void tme_sparc_fpu_fpreg_format _TME_P((struct tme_sparc *, unsigned int, unsigned int)); 1175: void tme_sparc_fpu_fpop1 _TME_P((struct tme_sparc *)); 1176: void tme_sparc_fpu_fpop2 _TME_P((struct tme_sparc *)); 1.1.1.2 ! root 1177: #ifdef TME_HAVE_INT64_T ! 1178: void tme_sparc_vis _TME_P((struct tme_sparc *)); ! 1179: void tme_sparc64_vis_ls_asi_pst _TME_P((struct tme_sparc *, struct tme_sparc_ls *)); ! 1180: void tme_sparc64_vis_ls_asi_fl _TME_P((struct tme_sparc *, struct tme_sparc_ls *)); ! 1181: tme_uint32_t tme_sparc64_vis_ls_asi_misaligned _TME_P((struct tme_sparc *, tme_uint32_t)); ! 1182: #endif /* TME_HAVE_INT64_T */ ! 1183: ! 1184: /* timing support: */ ! 1185: int tme_sparc_timing_loop_ok _TME_P((tme_uint32_t, tme_uint32_t)); ! 1186: void tme_sparc_timing_loop_start _TME_P((struct tme_sparc *)); ! 1187: void tme_sparc_timing_loop_finish _TME_P((struct tme_sparc *)); ! 1188: #if TME_HAVE_RECODE ! 1189: tme_recode_uguest_t tme_sparc_timing_loop_assist _TME_P((struct tme_ic *, tme_recode_uguest_t, tme_recode_uguest_t)); ! 1190: #endif /* TME_HAVE_RECODE */ ! 1191: ! 1192: /* recode support: */ ! 1193: void tme_sparc_recode_init _TME_P((struct tme_sparc *)); ! 1194: #if TME_HAVE_RECODE ! 1195: tme_recode_thunk_off_t tme_sparc_recode _TME_P((struct tme_sparc *, const struct tme_sparc_tlb *, const tme_shared tme_uint32_t *)); ! 1196: void tme_sparc_recode_invalidate_all _TME_P((struct tme_sparc *)); ! 1197: tme_recode_uguest_t tme_sparc32_recode_insn_assist_redispatch _TME_P((struct tme_sparc *)); ! 1198: tme_uint32_t tme_sparc32_recode_insn_current _TME_P((const struct tme_sparc *)); ! 1199: void tme_sparc32_recode_chain_tlb_update _TME_P((struct tme_sparc *, const struct tme_sparc_ls *)); ! 1200: void tme_sparc32_recode_ls_tlb_update _TME_P((struct tme_sparc *, const struct tme_sparc_ls *)); ! 1201: #if TME_RECODE_SIZE_GUEST_MAX > TME_RECODE_SIZE_32 ! 1202: tme_recode_uguest_t tme_sparc64_recode_insn_assist_redispatch _TME_P((struct tme_sparc *)); ! 1203: tme_uint32_t tme_sparc64_recode_insn_current _TME_P((const struct tme_sparc *)); ! 1204: void tme_sparc64_recode_chain_tlb_update _TME_P((struct tme_sparc *, const struct tme_sparc_ls *)); ! 1205: void tme_sparc64_recode_ls_tlb_update _TME_P((struct tme_sparc *, const struct tme_sparc_ls *)); ! 1206: #endif /* TME_RECODE_SIZE_GUEST_MAX > TME_RECODE_SIZE_32 */ ! 1207: #define TME_SPARC_RECODE_VERIFY_MEM_SIZE_MASK (0x7) ! 1208: #define TME_SPARC_RECODE_VERIFY_MEM_LOAD TME_BIT(3) ! 1209: #define TME_SPARC_RECODE_VERIFY_MEM_STORE TME_BIT(4) ! 1210: #define TME_SPARC_RECODE_VERIFY_MEM_CAS TME_BIT(5) ! 1211: #ifdef _TME_SPARC_RECODE_VERIFY ! 1212: void tme_sparc_recode_verify_begin _TME_P((struct tme_sparc *)); ! 1213: void tme_sparc_recode_verify_mem _TME_P((struct tme_sparc *, void *, unsigned int, tme_recode_uguest_t, unsigned int)); ! 1214: void tme_sparc_recode_verify_mem_load _TME_P((struct tme_sparc *, const void *)); ! 1215: void tme_sparc_recode_verify_mem_block _TME_P((struct tme_sparc *, unsigned int)); ! 1216: void tme_sparc_recode_verify_reg_tick _TME_P((struct tme_sparc *, void *)); ! 1217: void tme_sparc_recode_verify_reg_tick_now _TME_P((struct tme_sparc *, const void *)); ! 1218: void tme_sparc_recode_verify_end _TME_P((struct tme_sparc *, tme_uint32_t)); ! 1219: void tme_sparc_recode_verify_end_preinstruction _TME_P((struct tme_sparc *)); ! 1220: #define tme_sparc_recode_verify_replay_last_pc(ic) ((ic)->tme_sparc_recode_verify_replay_last_pc) ! 1221: #define TME_SPARC_RECODE_VERIFY_PC_NONE (1) ! 1222: #endif /* _TME_SPARC_RECODE_VERIFY */ ! 1223: #else /* !TME_HAVE_RECODE */ ! 1224: #define tme_sparc_recode_invalidate_all(ic) do { } while (/* CONSTCOND */ 0 && (ic)) ! 1225: #endif /* !TME_HAVE_RECODE */ ! 1226: #ifndef _TME_SPARC_RECODE_VERIFY ! 1227: #define tme_sparc_recode_verify_begin(ic) \ ! 1228: do { } while (/* CONSTCOND */ 0 && (ic)) ! 1229: #define tme_sparc_recode_verify_mem(ic, rd, asi, addr, flags) \ ! 1230: do { } while (/* CONSTCOND */ 0 && (ic) && (rd) && (asi) && (addr)) ! 1231: #define tme_sparc_recode_verify_mem_load(ic, rd) \ ! 1232: do { } while (/* CONSTCOND */ 0 && (ic) && (rd)) ! 1233: #define tme_sparc_recode_verify_mem_block(ic, flags) \ ! 1234: do { } while (/* CONSTCOND */ 0 && (ic)) ! 1235: #define tme_sparc_recode_verify_reg_tick(ic, rd) \ ! 1236: do { } while (/* CONSTCOND */ 0 && (ic) && (rd)) ! 1237: #define tme_sparc_recode_verify_reg_tick_now(ic, rd) \ ! 1238: do { } while (/* CONSTCOND */ 0 && (ic) && *(rd)) ! 1239: #define tme_sparc_recode_verify_end(ic, trap) \ ! 1240: do { } while (/* CONSTCOND */ 0 && (ic) && (trap)) ! 1241: #define tme_sparc_recode_verify_end_preinstruction(ic) \ ! 1242: do { } while (/* CONSTCOND */ 0 && (ic)) ! 1243: #define tme_sparc_recode_verify_replay_last_pc(ic) (0) ! 1244: #endif /* !_TME_SPARC_RECODE_VERIFY */ 1.1 root 1245: 1246: /* instruction functions: */ 1247: TME_SPARC_FORMAT3_DECL(tme_sparc32_illegal, tme_uint32_t); 1248: TME_SPARC_FORMAT3_DECL(tme_sparc32_cpop1, tme_uint32_t); 1249: TME_SPARC_FORMAT3_DECL(tme_sparc32_cpop2, tme_uint32_t); 1250: TME_SPARC_FORMAT3_DECL(tme_sparc32_ldc, tme_uint32_t); 1251: TME_SPARC_FORMAT3_DECL(tme_sparc32_ldcsr, tme_uint32_t); 1252: TME_SPARC_FORMAT3_DECL(tme_sparc32_lddc, tme_uint32_t); 1253: TME_SPARC_FORMAT3_DECL(tme_sparc32_stc, tme_uint32_t); 1254: TME_SPARC_FORMAT3_DECL(tme_sparc32_stcsr, tme_uint32_t); 1255: TME_SPARC_FORMAT3_DECL(tme_sparc32_stdc, tme_uint32_t); 1256: TME_SPARC_FORMAT3_DECL(tme_sparc32_stdcq, tme_uint32_t); 1257: TME_SPARC_FORMAT3_DECL(tme_sparc32_rdasr, tme_uint32_t); 1258: TME_SPARC_FORMAT3_DECL(tme_sparc32_rdpsr, tme_uint32_t); 1259: TME_SPARC_FORMAT3_DECL(tme_sparc32_rdwim, tme_uint32_t); 1260: TME_SPARC_FORMAT3_DECL(tme_sparc32_rdtbr, tme_uint32_t); 1261: TME_SPARC_FORMAT3_DECL(tme_sparc32_wrasr, tme_uint32_t); 1262: TME_SPARC_FORMAT3_DECL(tme_sparc32_wrpsr, tme_uint32_t); 1263: TME_SPARC_FORMAT3_DECL(tme_sparc32_wrwim, tme_uint32_t); 1264: TME_SPARC_FORMAT3_DECL(tme_sparc32_wrtbr, tme_uint32_t); 1265: TME_SPARC_FORMAT3_DECL(tme_sparc32_flush, tme_uint32_t); 1266: TME_SPARC_FORMAT3_DECL(tme_sparc32_rett, tme_uint32_t); 1267: TME_SPARC_FORMAT3_DECL(tme_sparc32_save_restore, tme_uint32_t); 1268: TME_SPARC_FORMAT3_DECL(tme_sparc32_ticc, tme_uint32_t); 1269: TME_SPARC_FORMAT3_DECL(tme_sparc32_stdfq, tme_uint32_t); 1270: TME_SPARC_FORMAT3_DECL(tme_sparc32_fpop1, tme_uint32_t); 1271: TME_SPARC_FORMAT3_DECL(tme_sparc32_fpop2, tme_uint32_t); 1.1.1.2 ! root 1272: #ifdef TME_HAVE_INT64_T ! 1273: TME_SPARC_FORMAT3_DECL(tme_sparc64_movcc, tme_uint64_t); ! 1274: TME_SPARC_FORMAT3_DECL(tme_sparc64_movr, tme_uint64_t); ! 1275: TME_SPARC_FORMAT3_DECL(tme_sparc64_tcc, tme_uint64_t); ! 1276: TME_SPARC_FORMAT3_DECL(tme_sparc64_save_restore, tme_uint64_t); ! 1277: TME_SPARC_FORMAT3_DECL(tme_sparc64_return, tme_uint64_t); ! 1278: TME_SPARC_FORMAT3_DECL(tme_sparc64_saved_restored, tme_uint64_t); ! 1279: TME_SPARC_FORMAT3_DECL(tme_sparc64_flushw, tme_uint64_t); ! 1280: TME_SPARC_FORMAT3_DECL(tme_sparc64_prefetch, tme_uint64_t); ! 1281: TME_SPARC_FORMAT3_DECL(tme_sparc64_rdpr, tme_uint64_t); ! 1282: TME_SPARC_FORMAT3_DECL(tme_sparc64_wrpr, tme_uint64_t); ! 1283: TME_SPARC_FORMAT3_DECL(tme_sparc64_rdasr, tme_uint64_t); ! 1284: TME_SPARC_FORMAT3_DECL(tme_sparc64_wrasr, tme_uint64_t); ! 1285: TME_SPARC_FORMAT3_DECL(tme_sparc64_done_retry, tme_uint64_t); ! 1286: TME_SPARC_FORMAT3_DECL(tme_sparc64_fpop1, tme_uint64_t); ! 1287: TME_SPARC_FORMAT3_DECL(tme_sparc64_fpop2, tme_uint64_t); ! 1288: TME_SPARC_FORMAT3_DECL(tme_sparc64_illegal_instruction, tme_uint64_t); ! 1289: #endif /* TME_HAVE_INT64_T */ 1.1 root 1290: 1291: /* the automatically-generated header information: */ 1292: #include <sparc-auto.h> 1293: 1294: #endif /* !_IC_SPARC_IMPL_H */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.