|
|
1.1 ! root 1: /* $Id: cy7c601.c,v 1.2 2006/11/15 22:29:09 fredette Exp $ */ ! 2: ! 3: /* ic/m68k/cy7c601.c - implementation of Cypress SPARC CY7C601 emulation: */ ! 4: ! 5: /* ! 6: * Copyright (c) 2005 Matt Fredette ! 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: #include <tme/common.h> ! 37: _TME_RCSID("$Id: cy7c601.c,v 1.2 2006/11/15 22:29:09 fredette Exp $"); ! 38: ! 39: /* includes: */ ! 40: #include "sparc-impl.h" ! 41: ! 42: /* the format three opcode map: */ ! 43: #define _TME_SPARC_EXECUTE_OPMAP tme_sparc_opcodes_cy7c601 ! 44: const _tme_sparc32_format3 _TME_SPARC_EXECUTE_OPMAP[] = { ! 45: ! 46: /* op=2: arithmetic, logical, shift, and remaining: */ ! 47: ! 48: /* 000000 */ tme_sparc32_add, ! 49: /* 000001 */ tme_sparc32_and, ! 50: /* 000010 */ tme_sparc32_or, ! 51: /* 000011 */ tme_sparc32_xor, ! 52: /* 000100 */ tme_sparc32_sub, ! 53: /* 000101 */ tme_sparc32_andn, ! 54: /* 000110 */ tme_sparc32_orn, ! 55: /* 000111 */ tme_sparc32_xnor, ! 56: /* 001000 */ tme_sparc32_addx, ! 57: /* 001001 */ NULL, ! 58: /* 001010 */ tme_sparc32_illegal, /* the CY7C601 does not implement umul */ ! 59: /* 001011 */ tme_sparc32_illegal, /* the CY7C601 does not implement smul */ ! 60: /* 001100 */ tme_sparc32_subx, ! 61: /* 001101 */ NULL, ! 62: /* 001110 */ tme_sparc32_illegal, /* the CY7C601 does not implement udiv */ ! 63: /* 001111 */ tme_sparc32_illegal, /* the CY7C601 does not implement sdiv */ ! 64: /* 010000 */ tme_sparc32_addcc, ! 65: /* 010001 */ tme_sparc32_andcc, ! 66: /* 010010 */ tme_sparc32_orcc, ! 67: /* 010011 */ tme_sparc32_xorcc, ! 68: /* 010100 */ tme_sparc32_subcc, ! 69: /* 010101 */ tme_sparc32_andncc, ! 70: /* 010110 */ tme_sparc32_orncc, ! 71: /* 010111 */ tme_sparc32_xnorcc, ! 72: /* 011000 */ tme_sparc32_addxcc, ! 73: /* 011001 */ NULL, ! 74: /* 011010 */ tme_sparc32_illegal, /* the CY7C601 does not implement umulcc */ ! 75: /* 011011 */ tme_sparc32_illegal, /* the CY7C601 does not implement smulcc */ ! 76: /* 011100 */ tme_sparc32_subxcc, ! 77: /* 011101 */ NULL, ! 78: /* 011110 */ tme_sparc32_illegal, /* the CY7C601 does not implement udivcc */ ! 79: /* 011111 */ tme_sparc32_illegal, /* the CY7C601 does not implement sdivcc */ ! 80: /* 100000 */ tme_sparc32_taddcc, ! 81: /* 100001 */ tme_sparc32_tsubcc, ! 82: /* 100010 */ tme_sparc32_taddcctv, ! 83: /* 100011 */ tme_sparc32_tsubcctv, ! 84: /* 100100 */ tme_sparc32_mulscc, ! 85: /* 100101 */ tme_sparc32_sll, ! 86: /* 100110 */ tme_sparc32_srl, ! 87: /* 100111 */ tme_sparc32_sra, ! 88: /* 101000 */ tme_sparc32_rdasr, ! 89: /* 101001 */ tme_sparc32_rdpsr, ! 90: /* 101010 */ tme_sparc32_rdwim, ! 91: /* 101011 */ tme_sparc32_rdtbr, ! 92: /* 101100 */ NULL, ! 93: /* 101101 */ NULL, ! 94: /* 101110 */ NULL, ! 95: /* 101111 */ NULL, ! 96: /* 110000 */ tme_sparc32_wrasr, ! 97: /* 110001 */ tme_sparc32_wrpsr, ! 98: /* 110010 */ tme_sparc32_wrwim, ! 99: /* 110011 */ tme_sparc32_wrtbr, ! 100: /* 110100 */ tme_sparc32_fpop1, ! 101: /* 110101 */ tme_sparc32_fpop2, ! 102: /* 110110 */ tme_sparc32_cpop1, ! 103: /* 110111 */ tme_sparc32_cpop2, ! 104: /* 111000 */ tme_sparc32_jmpl, ! 105: /* 111001 */ tme_sparc32_rett, ! 106: /* 111010 */ tme_sparc32_ticc, ! 107: /* 111011 */ tme_sparc32_flush, ! 108: /* 111100 */ tme_sparc32_save_restore, ! 109: /* 111101 */ tme_sparc32_save_restore, ! 110: /* 111110 */ NULL, ! 111: /* 111111 */ NULL, ! 112: ! 113: /* op=3: memory instructions: */ ! 114: ! 115: /* 000000 */ tme_sparc32_ld, ! 116: /* 000001 */ tme_sparc32_ldb, ! 117: /* 000010 */ tme_sparc32_ldh, ! 118: /* 000011 */ tme_sparc32_ldd, ! 119: /* 000100 */ tme_sparc32_st, ! 120: /* 000101 */ tme_sparc32_stb, ! 121: /* 000110 */ tme_sparc32_sth, ! 122: /* 000111 */ tme_sparc32_std, ! 123: /* 001000 */ NULL, ! 124: /* 001001 */ tme_sparc32_ldb, ! 125: /* 001010 */ tme_sparc32_ldh, ! 126: /* 001011 */ NULL, ! 127: /* 001100 */ NULL, ! 128: /* 001101 */ tme_sparc32_ldstub, ! 129: /* 001110 */ NULL, ! 130: /* 001111 */ tme_sparc32_swap, ! 131: /* 010000 */ tme_sparc32_lda, ! 132: /* 010001 */ tme_sparc32_ldba, ! 133: /* 010010 */ tme_sparc32_ldha, ! 134: /* 010011 */ tme_sparc32_ldda, ! 135: /* 010100 */ tme_sparc32_sta, ! 136: /* 010101 */ tme_sparc32_stba, ! 137: /* 010110 */ tme_sparc32_stha, ! 138: /* 010111 */ tme_sparc32_stda, ! 139: /* 011000 */ NULL, ! 140: /* 011001 */ tme_sparc32_ldba, ! 141: /* 011010 */ tme_sparc32_ldha, ! 142: /* 011011 */ NULL, ! 143: /* 011100 */ NULL, ! 144: /* 011101 */ tme_sparc32_ldstuba, ! 145: /* 011110 */ NULL, ! 146: /* 011111 */ tme_sparc32_swapa, ! 147: /* 100000 */ tme_sparc32_ldf, ! 148: /* 100001 */ tme_sparc32_ldfsr, ! 149: /* 100010 */ NULL, ! 150: /* 100011 */ tme_sparc32_lddf, ! 151: /* 100100 */ tme_sparc32_stf, ! 152: /* 100101 */ tme_sparc32_stfsr, ! 153: /* 100110 */ tme_sparc32_stdfq, ! 154: /* 100111 */ tme_sparc32_stdf, ! 155: /* 101000 */ NULL, ! 156: /* 101001 */ NULL, ! 157: /* 101010 */ NULL, ! 158: /* 101011 */ NULL, ! 159: /* 101100 */ NULL, ! 160: /* 101101 */ NULL, ! 161: /* 101110 */ NULL, ! 162: /* 101111 */ NULL, ! 163: /* 110000 */ tme_sparc32_ldc, ! 164: /* 110001 */ tme_sparc32_ldcsr, ! 165: /* 110010 */ NULL, ! 166: /* 110011 */ tme_sparc32_lddc, ! 167: /* 110100 */ tme_sparc32_stc, ! 168: /* 110101 */ tme_sparc32_stcsr, ! 169: /* 110110 */ tme_sparc32_stdcq, ! 170: /* 110111 */ tme_sparc32_stdc, ! 171: /* 111000 */ NULL, ! 172: /* 111001 */ NULL, ! 173: /* 111010 */ NULL, ! 174: /* 111011 */ NULL, ! 175: /* 111100 */ NULL, ! 176: /* 111101 */ NULL, ! 177: /* 111110 */ NULL, ! 178: /* 111111 */ NULL, ! 179: }; ! 180: ! 181: /* make the executor for the CY7C601: */ ! 182: #undef TME_SPARC_VERSION ! 183: #define TME_SPARC_VERSION(ic) (7) ! 184: #undef TME_SPARC_NWINDOWS ! 185: #define TME_SPARC_NWINDOWS(ic) (8) ! 186: #define _TME_SPARC_EXECUTE_NAME _tme_sparc_execute_cy7c601 ! 187: #include "sparc-execute.c" ! 188: ! 189: /* this returns the version of an FPU for an cy7c601: */ ! 190: static tme_uint32_t ! 191: _tme_sparc_fpu_ver_cy7c601(struct tme_sparc *ic, const char *fpu_name, char **_output) ! 192: { ! 193: tme_uint32_t ver; ! 194: ! 195: /* if we're returning a usage: */ ! 196: if (_output != NULL) { ! 197: tme_output_append_error(_output, ! 198: "{ l64812/act8847 | l64814 | tms390-c602A | wtl3171/cy7c602 }"); ! 199: return (TME_SPARC_FSR_VER_missing); ! 200: } ! 201: ! 202: if (TME_ARG_IS(fpu_name, "l64812/act8847")) { ! 203: ver = 0; ! 204: } ! 205: else if (TME_ARG_IS(fpu_name, "l64814")) { ! 206: ver = 1; ! 207: } ! 208: else if (TME_ARG_IS(fpu_name, "tms390-c602A")) { ! 209: ver = 2; ! 210: } ! 211: else if (TME_ARG_IS(fpu_name, "wtl3171/cy7c602")) { ! 212: ver = 3; ! 213: } ! 214: else { ! 215: return (TME_SPARC_FSR_VER_missing); ! 216: } ! 217: ! 218: ic->tme_sparc_fpu_flags ! 219: = (TME_SPARC_FPU_FLAG_NO_QUAD ! 220: | TME_SPARC_FPU_FLAG_NO_FMUL_WIDER ! 221: | TME_SPARC_FPU_FLAG_OK_REG_MISALIGNED); ! 222: return (ver * _TME_FIELD_MASK_FACTOR(TME_SPARC_FSR_VER)); ! 223: } ! 224: ! 225: /* this creates and returns a new cy7c601: */ ! 226: TME_ELEMENT_X_NEW_DECL(tme_ic_,sparc,cy7c601) { ! 227: struct tme_sparc *ic; ! 228: tme_uint32_t psr; ! 229: ! 230: /* allocate the sparc structure: */ ! 231: ic = tme_new0(struct tme_sparc, 1); ! 232: ic->tme_sparc_element = element; ! 233: ! 234: /* fill in the cy7c601-specific parts of the structure: */ ! 235: psr = 0; ! 236: TME_FIELD_MASK_DEPOSITU(psr, TME_SPARC32_PSR_IMPL, 1); ! 237: TME_FIELD_MASK_DEPOSITU(psr, TME_SPARC32_PSR_VER, 1); ! 238: ic->tme_sparc32_ireg_psr = psr; ! 239: ic->tme_sparc_version = TME_SPARC_VERSION(ic); ! 240: ic->tme_sparc_nwindows = TME_SPARC_NWINDOWS(ic); ! 241: ic->_tme_sparc_execute = _tme_sparc_execute_cy7c601; ! 242: ic->_tme_sparc_fpu_ver = _tme_sparc_fpu_ver_cy7c601; ! 243: ic->_tme_sparc_bus_fault = tme_sparc32_bus_fault; ! 244: ic->_tme_sparc_fetch_slow = tme_sparc32_fetch_slow; ! 245: ! 246: /* call the common sparc new function: */ ! 247: return (tme_sparc_new(ic, args, extra, _output)); ! 248: } ! 249: ! 250: #undef TME_SPARC_VERSION ! 251: #define TME_SPARC_VERSION(ic) _TME_SPARC_VERSION(ic) ! 252: #undef TME_SPARC_NWINDOWS ! 253: #define TME_SPARC_NWINDOWS(ic) _TME_SPARC_NWINDOWS(ic) ! 254: #undef _TME_SPARC_EXECUTE_NAME ! 255: #undef _TME_SPARC_EXECUTE_OPMAP
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.