| 1 | /* |
| 2 | * m68k virtual CPU header |
| 3 | * |
| 4 | * Copyright (c) 2005-2007 CodeSourcery |
| 5 | * Written by Paul Brook |
| 6 | * |
| 7 | * This library is free software; you can redistribute it and/or |
| 8 | * modify it under the terms of the GNU Lesser General Public |
| 9 | * License as published by the Free Software Foundation; either |
| 10 | * version 2.1 of the License, or (at your option) any later version. |
| 11 | * |
| 12 | * This library is distributed in the hope that it will be useful, |
| 13 | * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 14 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
| 15 | * Lesser General Public License for more details. |
| 16 | * |
| 17 | * You should have received a copy of the GNU Lesser General Public |
| 18 | * License along with this library; if not, see <http://www.gnu.org/licenses/>. |
| 19 | */ |
| 20 | |
| 21 | #ifndef M68K_CPU_H |
| 22 | #define M68K_CPU_H |
| 23 | |
| 24 | #include "exec/cpu-common.h" |
| 25 | #include "exec/cpu-interrupt.h" |
| 26 | #include "qemu/cpu-float.h" |
| 27 | #include "cpu-qom.h" |
| 28 | |
| 29 | #define OS_BYTE 0 |
| 30 | #define OS_WORD 1 |
| 31 | #define OS_LONG 2 |
| 32 | #define OS_SINGLE 3 |
| 33 | #define OS_DOUBLE 4 |
| 34 | #define OS_EXTENDED 5 |
| 35 | #define OS_PACKED 6 |
| 36 | #define OS_UNSIZED 7 |
| 37 | |
| 38 | #define EXCP_ACCESS 2 /* Access (MMU) error. */ |
| 39 | #define EXCP_ADDRESS 3 /* Address error. */ |
| 40 | #define EXCP_ILLEGAL 4 /* Illegal instruction. */ |
| 41 | #define EXCP_DIV0 5 /* Divide by zero */ |
| 42 | #define EXCP_CHK 6 /* CHK, CHK2 Instructions */ |
| 43 | #define EXCP_TRAPCC 7 /* FTRAPcc, TRAPcc, TRAPV Instructions */ |
| 44 | #define EXCP_PRIVILEGE 8 /* Privilege violation. */ |
| 45 | #define EXCP_TRACE 9 |
| 46 | #define EXCP_LINEA 10 /* Unimplemented line-A (MAC) opcode. */ |
| 47 | #define EXCP_LINEF 11 /* Unimplemented line-F (FPU) opcode. */ |
| 48 | #define EXCP_DEBUGNBP 12 /* Non-breakpoint debug interrupt. */ |
| 49 | #define EXCP_DEBEGBP 13 /* Breakpoint debug interrupt. */ |
| 50 | #define EXCP_FORMAT 14 /* RTE format error. */ |
| 51 | #define EXCP_UNINITIALIZED 15 |
| 52 | #define EXCP_SPURIOUS 24 /* Spurious interrupt */ |
| 53 | #define EXCP_INT_LEVEL_1 25 /* Level 1 Interrupt autovector */ |
| 54 | #define EXCP_INT_LEVEL_7 31 /* Level 7 Interrupt autovector */ |
| 55 | #define EXCP_TRAP0 32 /* User trap #0. */ |
| 56 | #define EXCP_TRAP15 47 /* User trap #15. */ |
| 57 | #define EXCP_FP_BSUN 48 /* Branch Set on Unordered */ |
| 58 | #define EXCP_FP_INEX 49 /* Inexact result */ |
| 59 | #define EXCP_FP_DZ 50 /* Divide by Zero */ |
| 60 | #define EXCP_FP_UNFL 51 /* Underflow */ |
| 61 | #define EXCP_FP_OPERR 52 /* Operand Error */ |
| 62 | #define EXCP_FP_OVFL 53 /* Overflow */ |
| 63 | #define EXCP_FP_SNAN 54 /* Signaling Not-A-Number */ |
| 64 | #define EXCP_FP_UNIMP 55 /* Unimplemented Data type */ |
| 65 | #define EXCP_MMU_CONF 56 /* MMU Configuration Error */ |
| 66 | #define EXCP_MMU_ILLEGAL 57 /* MMU Illegal Operation Error */ |
| 67 | #define EXCP_MMU_ACCESS 58 /* MMU Access Level Violation Error */ |
| 68 | |
| 69 | #define EXCP_RTE 0x100 |
| 70 | #define EXCP_SEMIHOSTING 0x101 |
| 71 | |
| 72 | #define M68K_DTTR0 0 |
| 73 | #define M68K_DTTR1 1 |
| 74 | #define M68K_ITTR0 2 |
| 75 | #define M68K_ITTR1 3 |
| 76 | |
| 77 | #define M68K_MAX_TTR 2 |
| 78 | #define TTR(type, index) ttr[((type & ACCESS_CODE) == ACCESS_CODE) * 2 + index] |
| 79 | |
| 80 | typedef CPU_LDoubleU FPReg; |
| 81 | |
| 82 | typedef struct CPUArchState { |
| 83 | uint32_t dregs[8]; |
| 84 | uint32_t aregs[8]; |
| 85 | uint32_t pc; |
| 86 | uint32_t sr; |
| 87 | |
| 88 | /* |
| 89 | * The 68020/30/40 support two supervisor stacks, ISP and MSP. |
| 90 | * The 68000/10, Coldfire, and CPU32 only have USP/SSP. |
| 91 | * |
| 92 | * The current_sp is stored in aregs[7], the other here. |
| 93 | * The USP, SSP, and if used the additional ISP for 68020/30/40. |
| 94 | */ |
| 95 | int current_sp; |
| 96 | uint32_t sp[3]; |
| 97 | |
| 98 | /* Condition flags. */ |
| 99 | uint32_t cc_op; |
| 100 | uint32_t cc_x; /* always 0/1 */ |
| 101 | uint32_t cc_n; /* in bit 31 (i.e. negative) */ |
| 102 | uint32_t cc_v; /* in bit 31, unused, or computed from cc_n and cc_v */ |
| 103 | uint32_t cc_c; /* either 0/1, unused, or computed from cc_n and cc_v */ |
| 104 | uint32_t cc_z; /* == 0 or unused */ |
| 105 | |
| 106 | FPReg fregs[8]; |
| 107 | FPReg fp_result; |
| 108 | uint32_t fpcr; |
| 109 | uint32_t fpsr; |
| 110 | float_status fp_status; |
| 111 | |
| 112 | uint64_t mactmp; |
| 113 | /* |
| 114 | * EMAC Hardware deals with 48-bit values composed of one 32-bit and |
| 115 | * two 8-bit parts. We store a single 64-bit value and |
| 116 | * rearrange/extend this when changing modes. |
| 117 | */ |
| 118 | uint64_t macc[4]; |
| 119 | uint32_t macsr; |
| 120 | uint32_t mac_mask; |
| 121 | |
| 122 | /* MMU status. */ |
| 123 | struct { |
| 124 | /* |
| 125 | * Holds the "address" value in between raising an exception |
| 126 | * and creation of the exception stack frame. |
| 127 | * Used for both Format 7 exceptions (Access, i.e. mmu) |
| 128 | * and Format 2 exceptions (chk, div0, trapcc, etc). |
| 129 | */ |
| 130 | uint32_t ar; |
| 131 | uint32_t ssw; |
| 132 | /* 68040 */ |
| 133 | uint16_t tcr; |
| 134 | uint32_t urp; |
| 135 | uint32_t srp; |
| 136 | bool fault; |
| 137 | uint32_t ttr[4]; |
| 138 | uint32_t mmusr; |
| 139 | } mmu; |
| 140 | |
| 141 | /* Control registers. */ |
| 142 | uint32_t vbr; |
| 143 | uint32_t mbar; |
| 144 | uint32_t rambar0; |
| 145 | uint32_t cacr; |
| 146 | uint32_t sfc; |
| 147 | uint32_t dfc; |
| 148 | |
| 149 | int pending_vector; |
| 150 | int pending_level; |
| 151 | |
| 152 | /* Fields up to this point are cleared by a CPU reset */ |
| 153 | struct {} end_reset_fields; |
| 154 | |
| 155 | /* Fields from here on are preserved across CPU reset. */ |
| 156 | uint64_t features; |
| 157 | } CPUM68KState; |
| 158 | |
| 159 | /* |
| 160 | * M68kCPU: |
| 161 | * @env: #CPUM68KState |
| 162 | * |
| 163 | * A Motorola 68k CPU. |
| 164 | */ |
| 165 | struct ArchCPU { |
| 166 | CPUState parent_obj; |
| 167 | |
| 168 | CPUM68KState env; |
| 169 | }; |
| 170 | |
| 171 | /* |
| 172 | * M68kCPUClass: |
| 173 | * @parent_realize: The parent class' realize handler. |
| 174 | * @parent_phases: The parent class' reset phase handlers. |
| 175 | * |
| 176 | * A Motorola 68k CPU model. |
| 177 | */ |
| 178 | struct M68kCPUClass { |
| 179 | CPUClass parent_class; |
| 180 | |
| 181 | DeviceRealize parent_realize; |
| 182 | ResettablePhases parent_phases; |
| 183 | }; |
| 184 | |
| 185 | #ifndef CONFIG_USER_ONLY |
| 186 | void m68k_cpu_do_interrupt(CPUState *cpu); |
| 187 | bool m68k_cpu_exec_interrupt(CPUState *cpu, int int_req); |
| 188 | hwaddr m68k_cpu_get_phys_addr_debug(CPUState *cpu, vaddr addr); |
| 189 | #endif /* !CONFIG_USER_ONLY */ |
| 190 | void m68k_cpu_dump_state(CPUState *cpu, FILE *f, int flags); |
| 191 | int m68k_cpu_gdb_read_register(CPUState *cpu, GByteArray *buf, int reg); |
| 192 | int m68k_cpu_gdb_write_register(CPUState *cpu, uint8_t *buf, int reg); |
| 193 | |
| 194 | void m68k_tcg_init(void); |
| 195 | void m68k_translate_code(CPUState *cs, TranslationBlock *tb, |
| 196 | int *max_insns, vaddr pc, void *host_pc); |
| 197 | void m68k_cpu_init_gdb(M68kCPU *cpu); |
| 198 | uint32_t cpu_m68k_get_ccr(CPUM68KState *env); |
| 199 | void cpu_m68k_set_ccr(CPUM68KState *env, uint32_t); |
| 200 | void cpu_m68k_set_sr(CPUM68KState *env, uint32_t); |
| 201 | void cpu_m68k_restore_fp_status(CPUM68KState *env); |
| 202 | void cpu_m68k_set_fpcr(CPUM68KState *env, uint32_t val); |
| 203 | uint32_t cpu_m68k_get_fpsr(CPUM68KState *env); |
| 204 | void cpu_m68k_set_fpsr(CPUM68KState *env, uint32_t val); |
| 205 | |
| 206 | /* |
| 207 | * Instead of computing the condition codes after each m68k instruction, |
| 208 | * QEMU just stores one operand (called CC_SRC), the result |
| 209 | * (called CC_DEST) and the type of operation (called CC_OP). When the |
| 210 | * condition codes are needed, the condition codes can be calculated |
| 211 | * using this information. Condition codes are not generated if they |
| 212 | * are only needed for conditional branches. |
| 213 | */ |
| 214 | typedef enum { |
| 215 | /* Translator only -- use env->cc_op. */ |
| 216 | CC_OP_DYNAMIC, |
| 217 | |
| 218 | /* Each flag bit computed into cc_[xcnvz]. */ |
| 219 | CC_OP_FLAGS, |
| 220 | |
| 221 | /* X in cc_x, C = X, N in cc_n, Z in cc_n, V via cc_n/cc_v. */ |
| 222 | CC_OP_ADDB, CC_OP_ADDW, CC_OP_ADDL, |
| 223 | CC_OP_SUBB, CC_OP_SUBW, CC_OP_SUBL, |
| 224 | |
| 225 | /* X in cc_x, {N,Z,C,V} via cc_n/cc_v. */ |
| 226 | CC_OP_CMPB, CC_OP_CMPW, CC_OP_CMPL, |
| 227 | |
| 228 | /* X in cc_x, C = 0, V = 0, N in cc_n, Z in cc_n. */ |
| 229 | CC_OP_LOGIC, |
| 230 | |
| 231 | CC_OP_NB |
| 232 | } CCOp; |
| 233 | |
| 234 | #define CCF_C 0x01 |
| 235 | #define CCF_V 0x02 |
| 236 | #define CCF_Z 0x04 |
| 237 | #define CCF_N 0x08 |
| 238 | #define CCF_X 0x10 |
| 239 | |
| 240 | #define SR_I_SHIFT 8 |
| 241 | #define SR_I 0x0700 |
| 242 | #define SR_M 0x1000 |
| 243 | #define SR_S 0x2000 |
| 244 | #define SR_T_SHIFT 14 |
| 245 | #define SR_T 0xc000 |
| 246 | |
| 247 | #define M68K_SR_TRACE(sr) ((sr & SR_T) >> SR_T_SHIFT) |
| 248 | #define M68K_SR_TRACE_ANY_INS 0x2 |
| 249 | |
| 250 | #define M68K_SSP 0 |
| 251 | #define M68K_USP 1 |
| 252 | #define M68K_ISP 2 |
| 253 | |
| 254 | /* bits for 68040 special status word */ |
| 255 | #define M68K_CP_040 0x8000 |
| 256 | #define M68K_CU_040 0x4000 |
| 257 | #define M68K_CT_040 0x2000 |
| 258 | #define M68K_CM_040 0x1000 |
| 259 | #define M68K_MA_040 0x0800 |
| 260 | #define M68K_ATC_040 0x0400 |
| 261 | #define M68K_LK_040 0x0200 |
| 262 | #define M68K_RW_040 0x0100 |
| 263 | #define M68K_SIZ_040 0x0060 |
| 264 | #define M68K_TT_040 0x0018 |
| 265 | #define M68K_TM_040 0x0007 |
| 266 | |
| 267 | #define M68K_TM_040_DATA 0x0001 |
| 268 | #define M68K_TM_040_CODE 0x0002 |
| 269 | #define M68K_TM_040_SUPER 0x0004 |
| 270 | |
| 271 | /* bits for 68040 write back status word */ |
| 272 | #define M68K_WBV_040 0x80 |
| 273 | #define M68K_WBSIZ_040 0x60 |
| 274 | #define M68K_WBBYT_040 0x20 |
| 275 | #define M68K_WBWRD_040 0x40 |
| 276 | #define M68K_WBLNG_040 0x00 |
| 277 | #define M68K_WBTT_040 0x18 |
| 278 | #define M68K_WBTM_040 0x07 |
| 279 | |
| 280 | /* bus access size codes */ |
| 281 | #define M68K_BA_SIZE_MASK 0x60 |
| 282 | #define M68K_BA_SIZE_BYTE 0x20 |
| 283 | #define M68K_BA_SIZE_WORD 0x40 |
| 284 | #define M68K_BA_SIZE_LONG 0x00 |
| 285 | #define M68K_BA_SIZE_LINE 0x60 |
| 286 | |
| 287 | /* bus access transfer type codes */ |
| 288 | #define M68K_BA_TT_MOVE16 0x08 |
| 289 | |
| 290 | /* bits for 68040 MMU status register (mmusr) */ |
| 291 | #define M68K_MMU_B_040 0x0800 |
| 292 | #define M68K_MMU_G_040 0x0400 |
| 293 | #define M68K_MMU_U1_040 0x0200 |
| 294 | #define M68K_MMU_U0_040 0x0100 |
| 295 | #define M68K_MMU_S_040 0x0080 |
| 296 | #define M68K_MMU_CM_040 0x0060 |
| 297 | #define M68K_MMU_M_040 0x0010 |
| 298 | #define M68K_MMU_WP_040 0x0004 |
| 299 | #define M68K_MMU_T_040 0x0002 |
| 300 | #define M68K_MMU_R_040 0x0001 |
| 301 | |
| 302 | #define M68K_MMU_SR_MASK_040 (M68K_MMU_G_040 | M68K_MMU_U1_040 | \ |
| 303 | M68K_MMU_U0_040 | M68K_MMU_S_040 | \ |
| 304 | M68K_MMU_CM_040 | M68K_MMU_M_040 | \ |
| 305 | M68K_MMU_WP_040) |
| 306 | |
| 307 | /* bits for 68040 MMU Translation Control Register */ |
| 308 | #define M68K_TCR_ENABLED 0x8000 |
| 309 | #define M68K_TCR_PAGE_8K 0x4000 |
| 310 | |
| 311 | /* bits for 68040 MMU Table Descriptor / Page Descriptor / TTR */ |
| 312 | #define M68K_DESC_WRITEPROT 0x00000004 |
| 313 | #define M68K_DESC_USED 0x00000008 |
| 314 | #define M68K_DESC_MODIFIED 0x00000010 |
| 315 | #define M68K_DESC_CACHEMODE 0x00000060 |
| 316 | #define M68K_DESC_CM_WRTHRU 0x00000000 |
| 317 | #define M68K_DESC_CM_COPYBK 0x00000020 |
| 318 | #define M68K_DESC_CM_SERIAL 0x00000040 |
| 319 | #define M68K_DESC_CM_NCACHE 0x00000060 |
| 320 | #define M68K_DESC_SUPERONLY 0x00000080 |
| 321 | #define M68K_DESC_USERATTR 0x00000300 |
| 322 | #define M68K_DESC_USERATTR_SHIFT 8 |
| 323 | #define M68K_DESC_GLOBAL 0x00000400 |
| 324 | #define M68K_DESC_URESERVED 0x00000800 |
| 325 | |
| 326 | #define M68K_ROOT_POINTER_ENTRIES 128 |
| 327 | #define M68K_4K_PAGE_MASK (~0xff) |
| 328 | #define M68K_POINTER_BASE(entry) (entry & ~0x1ff) |
| 329 | #define M68K_ROOT_INDEX(addr) ((address >> 23) & 0x1fc) |
| 330 | #define M68K_POINTER_INDEX(addr) ((address >> 16) & 0x1fc) |
| 331 | #define M68K_4K_PAGE_BASE(entry) (next & M68K_4K_PAGE_MASK) |
| 332 | #define M68K_4K_PAGE_INDEX(addr) ((address >> 10) & 0xfc) |
| 333 | #define M68K_8K_PAGE_MASK (~0x7f) |
| 334 | #define M68K_8K_PAGE_BASE(entry) (next & M68K_8K_PAGE_MASK) |
| 335 | #define M68K_8K_PAGE_INDEX(addr) ((address >> 11) & 0x7c) |
| 336 | #define M68K_UDT_VALID(entry) (entry & 2) |
| 337 | #define M68K_PDT_VALID(entry) (entry & 3) |
| 338 | #define M68K_PDT_INDIRECT(entry) ((entry & 3) == 2) |
| 339 | #define M68K_INDIRECT_POINTER(addr) (addr & ~3) |
| 340 | #define M68K_TTS_POINTER_SHIFT 18 |
| 341 | #define M68K_TTS_ROOT_SHIFT 25 |
| 342 | |
| 343 | /* bits for 68040 MMU Transparent Translation Registers */ |
| 344 | #define M68K_TTR_ADDR_BASE 0xff000000 |
| 345 | #define M68K_TTR_ADDR_MASK 0x00ff0000 |
| 346 | #define M68K_TTR_ADDR_MASK_SHIFT 8 |
| 347 | #define M68K_TTR_ENABLED 0x00008000 |
| 348 | #define M68K_TTR_SFIELD 0x00006000 |
| 349 | #define M68K_TTR_SFIELD_USER 0x0000 |
| 350 | #define M68K_TTR_SFIELD_SUPER 0x2000 |
| 351 | |
| 352 | /* m68k Control Registers */ |
| 353 | |
| 354 | /* ColdFire */ |
| 355 | /* Memory Management Control Registers */ |
| 356 | #define M68K_CR_ASID 0x003 |
| 357 | #define M68K_CR_ACR0 0x004 |
| 358 | #define M68K_CR_ACR1 0x005 |
| 359 | #define M68K_CR_ACR2 0x006 |
| 360 | #define M68K_CR_ACR3 0x007 |
| 361 | #define M68K_CR_MMUBAR 0x008 |
| 362 | |
| 363 | /* Processor Miscellaneous Registers */ |
| 364 | #define M68K_CR_PC 0x80F |
| 365 | |
| 366 | /* Local Memory and Module Control Registers */ |
| 367 | #define M68K_CR_ROMBAR0 0xC00 |
| 368 | #define M68K_CR_ROMBAR1 0xC01 |
| 369 | #define M68K_CR_RAMBAR0 0xC04 |
| 370 | #define M68K_CR_RAMBAR1 0xC05 |
| 371 | #define M68K_CR_MPCR 0xC0C |
| 372 | #define M68K_CR_EDRAMBAR 0xC0D |
| 373 | #define M68K_CR_SECMBAR 0xC0E |
| 374 | #define M68K_CR_MBAR 0xC0F |
| 375 | |
| 376 | /* Local Memory Address Permutation Control Registers */ |
| 377 | #define M68K_CR_PCR1U0 0xD02 |
| 378 | #define M68K_CR_PCR1L0 0xD03 |
| 379 | #define M68K_CR_PCR2U0 0xD04 |
| 380 | #define M68K_CR_PCR2L0 0xD05 |
| 381 | #define M68K_CR_PCR3U0 0xD06 |
| 382 | #define M68K_CR_PCR3L0 0xD07 |
| 383 | #define M68K_CR_PCR1U1 0xD0A |
| 384 | #define M68K_CR_PCR1L1 0xD0B |
| 385 | #define M68K_CR_PCR2U1 0xD0C |
| 386 | #define M68K_CR_PCR2L1 0xD0D |
| 387 | #define M68K_CR_PCR3U1 0xD0E |
| 388 | #define M68K_CR_PCR3L1 0xD0F |
| 389 | |
| 390 | /* MC680x0 */ |
| 391 | /* MC680[1234]0/CPU32 */ |
| 392 | #define M68K_CR_SFC 0x000 |
| 393 | #define M68K_CR_DFC 0x001 |
| 394 | #define M68K_CR_USP 0x800 |
| 395 | #define M68K_CR_VBR 0x801 /* + Coldfire */ |
| 396 | |
| 397 | /* MC680[234]0 */ |
| 398 | #define M68K_CR_CACR 0x002 /* + Coldfire */ |
| 399 | #define M68K_CR_CAAR 0x802 /* MC68020 and MC68030 only */ |
| 400 | #define M68K_CR_MSP 0x803 |
| 401 | #define M68K_CR_ISP 0x804 |
| 402 | |
| 403 | /* MC68040/MC68LC040 */ |
| 404 | #define M68K_CR_TC 0x003 |
| 405 | #define M68K_CR_ITT0 0x004 |
| 406 | #define M68K_CR_ITT1 0x005 |
| 407 | #define M68K_CR_DTT0 0x006 |
| 408 | #define M68K_CR_DTT1 0x007 |
| 409 | #define M68K_CR_MMUSR 0x805 |
| 410 | #define M68K_CR_URP 0x806 |
| 411 | #define M68K_CR_SRP 0x807 |
| 412 | |
| 413 | /* MC68EC040 */ |
| 414 | #define M68K_CR_IACR0 0x004 |
| 415 | #define M68K_CR_IACR1 0x005 |
| 416 | #define M68K_CR_DACR0 0x006 |
| 417 | #define M68K_CR_DACR1 0x007 |
| 418 | |
| 419 | /* MC68060 */ |
| 420 | #define M68K_CR_BUSCR 0x008 |
| 421 | #define M68K_CR_PCR 0x808 |
| 422 | |
| 423 | #define M68K_FPIAR_SHIFT 0 |
| 424 | #define M68K_FPIAR (1 << M68K_FPIAR_SHIFT) |
| 425 | #define M68K_FPSR_SHIFT 1 |
| 426 | #define M68K_FPSR (1 << M68K_FPSR_SHIFT) |
| 427 | #define M68K_FPCR_SHIFT 2 |
| 428 | #define M68K_FPCR (1 << M68K_FPCR_SHIFT) |
| 429 | |
| 430 | /* Floating-Point Status Register */ |
| 431 | |
| 432 | /* Condition Code */ |
| 433 | #define FPSR_CC_MASK 0x0f000000 |
| 434 | #define FPSR_CC_A 0x01000000 /* Not-A-Number */ |
| 435 | #define FPSR_CC_I 0x02000000 /* Infinity */ |
| 436 | #define FPSR_CC_Z 0x04000000 /* Zero */ |
| 437 | #define FPSR_CC_N 0x08000000 /* Negative */ |
| 438 | |
| 439 | /* Quotient */ |
| 440 | |
| 441 | #define FPSR_QT_MASK 0x00ff0000 |
| 442 | #define FPSR_QT_SHIFT 16 |
| 443 | |
| 444 | /* Floating-Point Control Register */ |
| 445 | /* Rounding mode */ |
| 446 | #define FPCR_RND_MASK 0x0030 |
| 447 | #define FPCR_RND_N 0x0000 |
| 448 | #define FPCR_RND_Z 0x0010 |
| 449 | #define FPCR_RND_M 0x0020 |
| 450 | #define FPCR_RND_P 0x0030 |
| 451 | |
| 452 | /* Rounding precision */ |
| 453 | #define FPCR_PREC_MASK 0x00c0 |
| 454 | #define FPCR_PREC_X 0x0000 |
| 455 | #define FPCR_PREC_S 0x0040 |
| 456 | #define FPCR_PREC_D 0x0080 |
| 457 | #define FPCR_PREC_U 0x00c0 |
| 458 | |
| 459 | #define FPCR_EXCP_MASK 0xff00 |
| 460 | |
| 461 | /* CACR fields are implementation defined, but some bits are common. */ |
| 462 | #define M68K_CACR_EUSP 0x10 |
| 463 | |
| 464 | #define MACSR_PAV0 0x100 |
| 465 | #define MACSR_OMC 0x080 |
| 466 | #define MACSR_SU 0x040 |
| 467 | #define MACSR_FI 0x020 |
| 468 | #define MACSR_RT 0x010 |
| 469 | #define MACSR_N 0x008 |
| 470 | #define MACSR_Z 0x004 |
| 471 | #define MACSR_V 0x002 |
| 472 | #define MACSR_EV 0x001 |
| 473 | |
| 474 | void m68k_set_irq_level(M68kCPU *cpu, int level, uint8_t vector); |
| 475 | void m68k_switch_sp(CPUM68KState *env); |
| 476 | |
| 477 | void do_m68k_semihosting(CPUM68KState *env, int nr); |
| 478 | |
| 479 | /* |
| 480 | * The 68000 family is defined in six main CPU classes, the 680[012346]0. |
| 481 | * Generally each successive CPU adds enhanced data/stack/instructions. |
| 482 | * However, some features are only common to one, or a few classes. |
| 483 | * The features cover those subsets of instructions. |
| 484 | * |
| 485 | * CPU32/32+ are basically 680010 compatible with some 68020 class |
| 486 | * instructions, and some additional CPU32 instructions. Mostly Supervisor |
| 487 | * state differences. |
| 488 | * |
| 489 | * The ColdFire core ISA is a RISC-style reduction of the 68000 series cpu. |
| 490 | * There are 4 ColdFire core ISA revisions: A, A+, B and C. |
| 491 | * Each feature covers the subset of instructions common to the |
| 492 | * ISA revisions mentioned. |
| 493 | */ |
| 494 | |
| 495 | enum m68k_features { |
| 496 | /* Base Motorola CPU set (not set for Coldfire CPUs) */ |
| 497 | M68K_FEATURE_M68K, |
| 498 | /* Motorola CPU feature sets */ |
| 499 | M68K_FEATURE_M68010, |
| 500 | M68K_FEATURE_M68020, |
| 501 | M68K_FEATURE_M68030, |
| 502 | M68K_FEATURE_M68040, |
| 503 | M68K_FEATURE_M68060, |
| 504 | /* Base Coldfire set Rev A. */ |
| 505 | M68K_FEATURE_CF_ISA_A, |
| 506 | /* (ISA B or C). */ |
| 507 | M68K_FEATURE_CF_ISA_B, |
| 508 | /* BIT/BITREV, FF1, STRLDSR (ISA A+ or C). */ |
| 509 | M68K_FEATURE_CF_ISA_APLUSC, |
| 510 | /* BRA with Long branch. (680[2346]0, ISA A+ or B). */ |
| 511 | M68K_FEATURE_BRAL, |
| 512 | M68K_FEATURE_CF_FPU, |
| 513 | M68K_FEATURE_CF_MAC, |
| 514 | M68K_FEATURE_CF_EMAC, |
| 515 | /* Revision B EMAC (dual accumulate). */ |
| 516 | M68K_FEATURE_CF_EMAC_B, |
| 517 | /* User Stack Pointer. (680[012346]0, ISA A+, B or C). */ |
| 518 | M68K_FEATURE_USP, |
| 519 | /* Master Stack Pointer. (680[234]0) */ |
| 520 | M68K_FEATURE_MSP, |
| 521 | /* 68020+ full extension word. */ |
| 522 | M68K_FEATURE_EXT_FULL, |
| 523 | /* word sized address index registers. */ |
| 524 | M68K_FEATURE_WORD_INDEX, |
| 525 | /* scaled address index registers. */ |
| 526 | M68K_FEATURE_SCALED_INDEX, |
| 527 | /* 32 bit mul/div. (680[2346]0, and CPU32) */ |
| 528 | M68K_FEATURE_LONG_MULDIV, |
| 529 | /* 64 bit mul/div. (680[2346]0, and CPU32) */ |
| 530 | M68K_FEATURE_QUAD_MULDIV, |
| 531 | /* Bcc with Long branches. (680[2346]0, and CPU32) */ |
| 532 | M68K_FEATURE_BCCL, |
| 533 | /* BFxxx Bit field insns. (680[2346]0) */ |
| 534 | M68K_FEATURE_BITFIELD, |
| 535 | /* fpu insn. (680[46]0) */ |
| 536 | M68K_FEATURE_FPU, |
| 537 | /* CAS/CAS2[WL] insns. (680[2346]0) */ |
| 538 | M68K_FEATURE_CAS, |
| 539 | /* BKPT insn. (680[12346]0, and CPU32) */ |
| 540 | M68K_FEATURE_BKPT, |
| 541 | /* RTD insn. (680[12346]0, and CPU32) */ |
| 542 | M68K_FEATURE_RTD, |
| 543 | /* CHK2 insn. (680[2346]0, and CPU32) */ |
| 544 | M68K_FEATURE_CHK2, |
| 545 | /* MOVEP insn. (680[01234]0, and CPU32) */ |
| 546 | M68K_FEATURE_MOVEP, |
| 547 | /* MOVEC insn. (from 68010) */ |
| 548 | M68K_FEATURE_MOVEC, |
| 549 | /* Unaligned data accesses (680[2346]0) */ |
| 550 | M68K_FEATURE_UNALIGNED_DATA, |
| 551 | /* TRAPcc insn. (680[2346]0, and CPU32) */ |
| 552 | M68K_FEATURE_TRAPCC, |
| 553 | /* MOVE from SR privileged (from 68010) */ |
| 554 | M68K_FEATURE_MOVEFROMSR_PRIV, |
| 555 | /* Exception frame with format+vector (from 68010) */ |
| 556 | M68K_FEATURE_EXCEPTION_FORMAT_VEC, |
| 557 | /* LINK.L (680[2346]0, and CPU32) */ |
| 558 | M68K_FEATURE_LINKL, |
| 559 | }; |
| 560 | |
| 561 | static inline bool m68k_feature(CPUM68KState *env, int feature) |
| 562 | { |
| 563 | return (env->features & BIT_ULL(feature)) != 0; |
| 564 | } |
| 565 | |
| 566 | void register_m68k_insns (CPUM68KState *env); |
| 567 | |
| 568 | enum { |
| 569 | /* 1 bit to define user level / supervisor access */ |
| 570 | ACCESS_SUPER = 0x01, |
| 571 | /* 1 bit to indicate direction */ |
| 572 | ACCESS_STORE = 0x02, |
| 573 | /* 1 bit to indicate debug access */ |
| 574 | ACCESS_DEBUG = 0x04, |
| 575 | /* PTEST instruction */ |
| 576 | ACCESS_PTEST = 0x08, |
| 577 | /* Type of instruction that generated the access */ |
| 578 | ACCESS_CODE = 0x10, /* Code fetch access */ |
| 579 | ACCESS_DATA = 0x20, /* Data load/store access */ |
| 580 | }; |
| 581 | |
| 582 | #define CPU_RESOLVING_TYPE TYPE_M68K_CPU |
| 583 | |
| 584 | /* MMU modes definitions */ |
| 585 | #define MMU_KERNEL_IDX 0 |
| 586 | #define MMU_USER_IDX 1 |
| 587 | |
| 588 | bool m68k_cpu_tlb_fill(CPUState *cs, vaddr address, int size, |
| 589 | MMUAccessType access_type, int mmu_idx, |
| 590 | bool probe, uintptr_t retaddr); |
| 591 | #ifndef CONFIG_USER_ONLY |
| 592 | void m68k_cpu_transaction_failed(CPUState *cs, hwaddr physaddr, vaddr addr, |
| 593 | unsigned size, MMUAccessType access_type, |
| 594 | int mmu_idx, MemTxAttrs attrs, |
| 595 | MemTxResult response, uintptr_t retaddr); |
| 596 | #endif |
| 597 | |
| 598 | /* TB flags */ |
| 599 | #define TB_FLAGS_MACSR 0x0f |
| 600 | #define TB_FLAGS_MSR_S_BIT 13 |
| 601 | #define TB_FLAGS_MSR_S (1 << TB_FLAGS_MSR_S_BIT) |
| 602 | #define TB_FLAGS_SFC_S_BIT 14 |
| 603 | #define TB_FLAGS_SFC_S (1 << TB_FLAGS_SFC_S_BIT) |
| 604 | #define TB_FLAGS_DFC_S_BIT 15 |
| 605 | #define TB_FLAGS_DFC_S (1 << TB_FLAGS_DFC_S_BIT) |
| 606 | #define TB_FLAGS_TRACE 16 |
| 607 | #define TB_FLAGS_TRACE_BIT (1 << TB_FLAGS_TRACE) |
| 608 | |
| 609 | void dump_mmu(CPUM68KState *env); |
| 610 | |
| 611 | #endif |