|
|
1.1 ! root 1: // ! 2: // nono ! 3: // Copyright (C) 2017 [email protected] ! 4: // ! 5: // EA ! 6: // ! 7: ! 8: #pragma once ! 9: ! 10: // EA は大別して5種類。 ! 11: // ! 12: // |d m rxwp | 制御 CalcCtrl サイズ不問 ! 13: // |dam+-rxw | 可変 CalcData B/W/L ! 14: // | m rxwp | MMU CalcMMU サイズ不問 ! 15: // |dam+-rxwpi| FPU CalcFPU B/W/L/S/D/X/P ! 16: // |d m+-rxwpi| データ FetchData B/W/L ! 17: // |dam+-rxwpi| All FetchAll B/W/L ! 18: // ! 19: // CalcCtrl はユーザーズマニュアルで「制御(Control)」と呼ばれている ! 20: // グループで、デスティネーション側のため EA の計算のみ。 ! 21: // また (An)+/-(An) を含まないため、サイズに関係なく1種類だけでよい。 ! 22: // ! 23: // CalcData はユーザーズマニュアルで「可変」と呼ばれているグループで、 ! 24: // デスティネーション側のため EA の計算のみ。B/W/L ! 25: // ! 26: // CalcMMU は対 MMU 用に勝手に用意したもの。 ! 27: // ! 28: // CalcFPU は対 FPU 用。ソースであっても CalcFPU を使用する。 ! 29: // サイズは B/W/L/S/D/X/P。 ! 30: // フェッチサイクルは別途存在するはずだが不詳。 ! 31: // ! 32: // FetchData はユーザーズマニュアルで「データ(Data)」と呼ばれている ! 33: // グループで、ソース側のため EA 計算および値の取得。B/W/L ! 34: // ! 35: // FetchAll はユーザーズマニュアルのここには記載がないグループで、 ! 36: // ソース側のため EA 計算および値の取得。B/W/L ! 37: // ! 38: // CalcCtrl、CalcData でアドレッシングモードに D や A が含まれている場合は ! 39: // その命令のデスティネーションに Dn、An が指定できるという意味であり、 ! 40: // EA 処理であるここには関係ない。 ! 41: // EA 計算より前に呼出側で条件分けして処理すること。 ! 42: // ! 43: // CalcCtrl、CalcData と FetchData には (*) 印の例外があるので留意。 ! 44: // ! 45: // (CalcCtrl) ! 46: // | m rxwp | CMP2/CHK2 ! 47: // | m rxwp | JMP/JSR ! 48: // | m rxwp | LEA/PEA ! 49: // |d m rxwp | BFEXT*/BFFFO/BFTST ! 50: // |d m rxw | (*) BFCHG/BFCLR/BFINS/BFSET <ea>{#o:#w} ! 51: // ! 52: // (CalcData) ! 53: // | m+-rxw | ADD/SUB/CMP Dx,<ea> ! 54: // | m+-rxw | CAS/TAS <ea> ! 55: // | m+-rxw | MOVES <ea>,Rn ! 56: // | m+-rxw | shift/rotate.W <ea> ! 57: // | m+-rxw | BCHG/BCLR/BSET src,<ea> ! 58: // |d m+-rxw | ADDI/SUBI Dx,<ea> ! 59: // |d m+-rwx | NBCD <ea> ! 60: // |d m+-rxw | AND/OR/EOR Dx,<ea> ! 61: // |d m+-rxw | CLR/NEG/NEGX/NOT/TST/Scc <ea> ! 62: // |d m+-rxw | MOVE CCR/SR,<ea> ! 63: // |dam+-rxw | ADDQ/SUBQ #qqq,<ea> ! 64: // |dam+-rxw | (*) MOVE の dst 側。EA の分類的には CalcData だが、 ! 65: // 下位6ビットの IR ではないので、cea_data_NN() ではなく ! 66: // 各々 cea_XXXX() のほうを個別に呼ぶこと。 ! 67: // ! 68: // (CalcMMU) ! 69: // | m rxw | MMU ! 70: // ! 71: // (CalcFPU) ! 72: // |d m+-rxw | FScc.B <ea> ! 73: // |dam+-rxw | FMOVE.f FPn,<ea> ! 74: // |dam+-rxw | FMOVE.L ctl,<ea> ! 75: // |dam+-rxw | FMOVEM.L ctl,<ea> ! 76: // |d m+-rxwpi| Fgen <ea>,FPn ! 77: // |d m+-rxwpi| FMOVE.f <ea>,FPn ! 78: // |dam+-rwxpi| FMOVE.L <ea>,ctl ! 79: // |dam+-rxwpi| FMOVEM.L <ea>,ctl ! 80: // 実際にどのアドレッシングモードが有効かどうかは極力個別の命令内で判断する? ! 81: // ここは実行サイクル数的な分類。 ! 82: // ! 83: // (FetchData) ! 84: // |d m+-rxwpi| AND/OR/CHK <ea>,Dn ! 85: // |d m+-rxwpi| MOVE.B <ea>,dst ! 86: // |d m+-rxwpi| MOVE <ea>,CCR/SR ! 87: // |d m+-rxwpi| MUL*/DIV* <ea>,Dn ! 88: // |d m+-rxwp | (*) TST.B <ea> ! 89: // |d m+-rxwp | (*) CMPI #<data>,<ea> ! 90: // | m+-rxwp | (*) BTST.B #<data>,<ea> ! 91: // | m+-rxwpi| (*) BTST.B Dx,<ea> ! 92: // ! 93: // (FetchAll) ! 94: // |dam+-rxwpi| ADD/SUB/CMP <ea>,Dn ! 95: // |dam+-rxwpi| MOVEA/ADDA/SUBA/CMPA <ea>,An ! 96: // |dam+-rxwpi| TST.WL <ea> ! 97: // |dam+-rxwpi| MOVE.WL <ea>,dst ! 98: // ! 99: // (たぶん別対応) ! 100: // | m -rxw | MOVEM list,<ea> ! 101: // | m -rxw | FMOVEM.X reg,<ea> ! 102: // | m -rxw | FSAVE <ea> ! 103: // | m+ rxwp | MOVEM <ea>,list ! 104: // | m+ rxwp | FMOVEM.X <ea>,reg ! 105: // | m+ rxwp | FRESTORE <ea> ! 106: ! 107: extern uint32 internal_ea_ix(m68kcpu *cpu, uint32 anpc); ! 108: ! 109: extern uint32 cea_ctrl(m68kcpu *); ! 110: extern uint32 cea_data_8(m68kcpu *); ! 111: extern uint32 cea_data_16(m68kcpu *); ! 112: extern uint32 cea_data_32(m68kcpu *); ! 113: extern uint32 cea_copro(m68kcpu *); ! 114: extern uint32 fea_data_8(m68kcpu *); ! 115: extern uint32 fea_data_16(m68kcpu *); ! 116: extern uint32 fea_data_32(m68kcpu *); ! 117: extern uint32 fea_all_8(m68kcpu *); ! 118: extern uint32 fea_all_16(m68kcpu *); ! 119: extern uint32 fea_all_32(m68kcpu *); ! 120: ! 121: // mmmrrr のうち mmm の部分を取り出す ! 122: #define eamode(x) (((x) >> 3) & 7) ! 123: ! 124: // mmmrrr のうち rrr の部分を取り出す ! 125: #define eanum(x) ((x) & 7) ! 126: ! 127: // ! 128: // EA を計算だけするマクロ ! 129: // MOVE の DST 側からも呼ばれる ! 130: // ! 131: ! 132: // (An) ! 133: static inline uint32 internal_ea_anin(m68kcpu *cpu, int n) ! 134: { ! 135: return RegA(n); ! 136: } ! 137: ! 138: // (An)+ .B ! 139: static inline uint32 internal_ea_anpi_8(m68kcpu *cpu, int n) ! 140: { ! 141: m68030_save_reg_pi(cpu, n); ! 142: if (n == 7) { ! 143: RegA(n) += 2; ! 144: return RegA(n) - 2; ! 145: } else { ! 146: RegA(n) += 1; ! 147: return RegA(n) - 1; ! 148: } ! 149: } ! 150: ! 151: // (An)+ .W ! 152: static inline uint32 internal_ea_anpi_16(m68kcpu *cpu, int n) ! 153: { ! 154: m68030_save_reg_pi(cpu, n); ! 155: RegA(n) += 2; ! 156: return RegA(n) - 2; ! 157: } ! 158: ! 159: // (An)+ .L ! 160: static inline uint32 internal_ea_anpi_32(m68kcpu *cpu, int n) ! 161: { ! 162: m68030_save_reg_pi(cpu, n); ! 163: RegA(n) += 4; ! 164: return RegA(n) - 4; ! 165: } ! 166: ! 167: // -(An) .B ! 168: static inline uint32 internal_ea_anpd_8(m68kcpu *cpu, int n) ! 169: { ! 170: m68030_save_reg_pd(cpu, n); ! 171: if (n == 7) { ! 172: RegA(n) -= 2; ! 173: } else { ! 174: RegA(n) -= 1; ! 175: } ! 176: return RegA(n); ! 177: } ! 178: ! 179: // -(An) .W ! 180: static inline uint32 internal_ea_anpd_16(m68kcpu *cpu, int n) ! 181: { ! 182: m68030_save_reg_pd(cpu, n); ! 183: RegA(n) -= 2; ! 184: return RegA(n); ! 185: } ! 186: ! 187: // -(An) .L ! 188: static inline uint32 internal_ea_anpd_32(m68kcpu *cpu, int n) ! 189: { ! 190: m68030_save_reg_pd(cpu, n); ! 191: RegA(n) -= 4; ! 192: return RegA(n); ! 193: } ! 194: ! 195: // d16(An) ! 196: static inline uint32 internal_ea_andi(m68kcpu *cpu, int n) ! 197: { ! 198: int32 disp = (int32)(int16)m68030_fetch_16(cpu); ! 199: return RegA(n) + disp; ! 200: } ! 201: ! 202: // (An,IX) ! 203: static inline uint32 internal_ea_anix(m68kcpu *cpu, int n) ! 204: { ! 205: return internal_ea_ix(cpu, RegA(n)); ! 206: } ! 207: ! 208: // Abs.W ! 209: static inline uint32 internal_ea_absw(m68kcpu *cpu) ! 210: { ! 211: return (int32)(int16)m68030_fetch_16(cpu); ! 212: } ! 213: ! 214: // Abs.L ! 215: static inline uint32 internal_ea_absl(m68kcpu *cpu) ! 216: { ! 217: return m68030_fetch_32(cpu); ! 218: } ! 219: ! 220: // d16(PC) ! 221: static inline uint32 internal_ea_pcdi(m68kcpu *cpu) ! 222: { ! 223: int32 pc = RegPC; ! 224: int32 disp = (int32)(int16)m68030_fetch_16(cpu); ! 225: return pc + disp; ! 226: } ! 227: ! 228: // (PC,IX) ! 229: static inline uint32 internal_ea_pcix(m68kcpu *cpu) ! 230: { ! 231: return internal_ea_ix(cpu, RegPC); ! 232: } ! 233: ! 234: // ! 235: // Calc EA ! 236: // ! 237: ! 238: static inline uint32 ! 239: cea_anin(m68kcpu *cpu, int n) ! 240: { ! 241: CYCLE(2); ! 242: return internal_ea_anin(cpu, n); ! 243: } ! 244: ! 245: static inline uint32 ! 246: cea_anpi_8(m68kcpu *cpu, int n) ! 247: { ! 248: CYCLE(2); ! 249: return internal_ea_anpi_8(cpu, n); ! 250: } ! 251: ! 252: static inline uint32 ! 253: cea_anpi_16(m68kcpu *cpu, int n) ! 254: { ! 255: CYCLE(2); ! 256: return internal_ea_anpi_16(cpu, n); ! 257: } ! 258: ! 259: static inline uint32 ! 260: cea_anpi_32(m68kcpu *cpu, int n) ! 261: { ! 262: CYCLE(2); ! 263: return internal_ea_anpi_32(cpu, n); ! 264: } ! 265: ! 266: static inline uint32 ! 267: cea_anpd_8(m68kcpu *cpu, int n) ! 268: { ! 269: CYCLE(2); ! 270: return internal_ea_anpd_8(cpu, n); ! 271: } ! 272: ! 273: static inline uint32 ! 274: cea_anpd_16(m68kcpu *cpu, int n) ! 275: { ! 276: CYCLE(2); ! 277: return internal_ea_anpd_16(cpu, n); ! 278: } ! 279: ! 280: static inline uint32 ! 281: cea_anpd_32(m68kcpu *cpu, int n) ! 282: { ! 283: CYCLE(2); ! 284: return internal_ea_anpd_32(cpu, n); ! 285: } ! 286: ! 287: static inline uint32 ! 288: cea_andi(m68kcpu *cpu, int n) ! 289: { ! 290: CYCLE(2); ! 291: return internal_ea_andi(cpu, n); ! 292: } ! 293: ! 294: static inline uint32 ! 295: cea_anix(m68kcpu *cpu, int n) ! 296: { ! 297: CYCLE(10); // XXX 4,4-18,20 ! 298: return internal_ea_anix(cpu, n); ! 299: } ! 300: ! 301: static inline uint32 ! 302: cea_absw(m68kcpu *cpu) ! 303: { ! 304: CYCLE(2); ! 305: return internal_ea_absw(cpu); ! 306: } ! 307: ! 308: static inline uint32 ! 309: cea_absl(m68kcpu *cpu) ! 310: { ! 311: CYCLE(4); ! 312: return internal_ea_absl(cpu); ! 313: } ! 314: ! 315: static inline uint32 ! 316: cea_pcdi(m68kcpu *cpu) ! 317: { ! 318: CYCLE(2); ! 319: return internal_ea_pcdi(cpu); ! 320: } ! 321: ! 322: static inline uint32 ! 323: cea_pcix(m68kcpu *cpu) ! 324: { ! 325: CYCLE(10); // XXX 4,4-18,20 ! 326: return internal_ea_pcix(cpu); ! 327: } ! 328: ! 329: // ! 330: // Fetch EA ! 331: // ! 332: ! 333: static inline uint32 ! 334: fea_anin(m68kcpu *cpu) ! 335: { ! 336: CYCLE(3); ! 337: return internal_ea_anin(cpu, eanum(RegIR)); ! 338: } ! 339: ! 340: static inline uint32 ! 341: fea_anpi_8(m68kcpu *cpu) ! 342: { ! 343: CYCLE(3); ! 344: return internal_ea_anpi_8(cpu, eanum(RegIR)); ! 345: } ! 346: ! 347: static inline uint32 ! 348: fea_anpi_16(m68kcpu *cpu) ! 349: { ! 350: CYCLE(3); ! 351: return internal_ea_anpi_16(cpu, eanum(RegIR)); ! 352: } ! 353: ! 354: static inline uint32 ! 355: fea_anpi_32(m68kcpu *cpu) ! 356: { ! 357: CYCLE(3); ! 358: return internal_ea_anpi_32(cpu, eanum(RegIR)); ! 359: } ! 360: ! 361: static inline uint32 ! 362: fea_anpd_8(m68kcpu *cpu) ! 363: { ! 364: CYCLE(4); ! 365: return internal_ea_anpd_8(cpu, eanum(RegIR)); ! 366: } ! 367: ! 368: static inline uint32 ! 369: fea_anpd_16(m68kcpu *cpu) ! 370: { ! 371: CYCLE(4); ! 372: return internal_ea_anpd_16(cpu, eanum(RegIR)); ! 373: } ! 374: ! 375: static inline uint32 ! 376: fea_anpd_32(m68kcpu *cpu) ! 377: { ! 378: CYCLE(4); ! 379: return internal_ea_anpd_32(cpu, eanum(RegIR)); ! 380: } ! 381: ! 382: static inline uint32 ! 383: fea_andi(m68kcpu *cpu) ! 384: { ! 385: CYCLE(4); ! 386: return internal_ea_andi(cpu, eanum(RegIR)); ! 387: } ! 388: ! 389: static inline uint32 ! 390: fea_anix(m68kcpu *cpu) ! 391: { ! 392: CYCLE2(12, 14); // XXX 6,6-18,21 ! 393: return internal_ea_anix(cpu, eanum(RegIR)); ! 394: } ! 395: ! 396: static inline uint32 ! 397: fea_absw(m68kcpu *cpu) ! 398: { ! 399: CYCLE(4); ! 400: return internal_ea_absw(cpu); ! 401: } ! 402: ! 403: static inline uint32 ! 404: fea_absl(m68kcpu *cpu) ! 405: { ! 406: CYCLE2(4, 5); ! 407: return internal_ea_absl(cpu); ! 408: } ! 409: ! 410: static inline uint32 ! 411: fea_pcdi(m68kcpu *cpu) ! 412: { ! 413: CYCLE(4); ! 414: return internal_ea_pcdi(cpu); ! 415: } ! 416: ! 417: static inline uint32 ! 418: fea_pcix(m68kcpu *cpu) ! 419: { ! 420: CYCLE2(12, 14); // XXX 6,6-18,21 ! 421: return internal_ea_pcix(cpu); ! 422: } ! 423: ! 424: static inline void ! 425: fea_imm_16(m68kcpu *cpu) ! 426: { ! 427: CYCLE(2); ! 428: } ! 429: ! 430: static inline void ! 431: fea_imm_32(m68kcpu *cpu) ! 432: { ! 433: CYCLE(4); ! 434: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.