Revision a750fc0b target-ppc/helper.c
b/target-ppc/helper.c | ||
---|---|---|
586 | 586 |
static inline int find_pte (CPUState *env, mmu_ctx_t *ctx, int h, int rw) |
587 | 587 |
{ |
588 | 588 |
#if defined(TARGET_PPC64) |
589 |
if (PPC_MMU(env) == PPC_FLAGS_MMU_64B ||
|
|
590 |
PPC_MMU(env) == PPC_FLAGS_MMU_64BRIDGE)
|
|
589 |
if (env->mmu_model == POWERPC_MMU_64B ||
|
|
590 |
env->mmu_model == POWERPC_MMU_64BRIDGE)
|
|
591 | 591 |
return find_pte64(ctx, h, rw); |
592 | 592 |
#endif |
593 | 593 |
|
... | ... | |
669 | 669 |
int ret, ret2; |
670 | 670 |
|
671 | 671 |
#if defined(TARGET_PPC64) |
672 |
if (PPC_MMU(env) == PPC_FLAGS_MMU_64B) {
|
|
672 |
if (env->mmu_model == POWERPC_MMU_64B) {
|
|
673 | 673 |
ret = slb_lookup(env, eaddr, &vsid, &page_mask, &attr); |
674 | 674 |
if (ret < 0) |
675 | 675 |
return ret; |
... | ... | |
724 | 724 |
hash = (~hash) & vsid_mask; |
725 | 725 |
ctx->pg_addr[1] = get_pgaddr(sdr, sdr_sh, hash, mask); |
726 | 726 |
#if defined(TARGET_PPC64) |
727 |
if (PPC_MMU(env) == PPC_FLAGS_MMU_64B ||
|
|
728 |
PPC_MMU(env) == PPC_FLAGS_MMU_64BRIDGE) {
|
|
727 |
if (env->mmu_model == POWERPC_MMU_64B ||
|
|
728 |
env->mmu_model == POWERPC_MMU_64BRIDGE) {
|
|
729 | 729 |
/* Only 5 bits of the page index are used in the AVPN */ |
730 | 730 |
ctx->ptem = (vsid << 12) | ((pgidx >> 4) & 0x0F80); |
731 | 731 |
} else |
... | ... | |
735 | 735 |
} |
736 | 736 |
/* Initialize real address with an invalid value */ |
737 | 737 |
ctx->raddr = (target_ulong)-1; |
738 |
if (unlikely(PPC_MMU(env) == PPC_FLAGS_MMU_SOFT_6xx)) {
|
|
738 |
if (unlikely(env->mmu_model == POWERPC_MMU_SOFT_6xx)) {
|
|
739 | 739 |
/* Software TLB search */ |
740 | 740 |
ret = ppc6xx_tlb_check(env, ctx, eaddr, rw, type); |
741 | 741 |
} else { |
... | ... | |
865 | 865 |
|
866 | 866 |
/* Default return value is no match */ |
867 | 867 |
ret = -1; |
868 |
for (i = 0; i < 64; i++) {
|
|
868 |
for (i = 0; i < env->nb_tlb; i++) {
|
|
869 | 869 |
tlb = &env->tlb[i].tlbe; |
870 | 870 |
if (ppcemb_tlb_check(env, tlb, &raddr, address, pid, 0, i) == 0) { |
871 | 871 |
ret = i; |
... | ... | |
876 | 876 |
return ret; |
877 | 877 |
} |
878 | 878 |
|
879 |
void ppc4xx_tlb_invalidate_virt (CPUState *env, target_ulong eaddr, |
|
880 |
uint32_t pid) |
|
881 |
{ |
|
882 |
ppcemb_tlb_t *tlb; |
|
883 |
target_phys_addr_t raddr; |
|
884 |
target_ulong page, end; |
|
885 |
int i; |
|
886 |
|
|
887 |
for (i = 0; i < env->nb_tlb; i++) { |
|
888 |
tlb = &env->tlb[i].tlbe; |
|
889 |
if (ppcemb_tlb_check(env, tlb, &raddr, eaddr, pid, 0, i) == 0) { |
|
890 |
end = tlb->EPN + tlb->size; |
|
891 |
for (page = tlb->EPN; page < end; page += TARGET_PAGE_SIZE) |
|
892 |
tlb_flush_page(env, page); |
|
893 |
tlb->prot &= ~PAGE_VALID; |
|
894 |
break; |
|
895 |
} |
|
896 |
} |
|
897 |
} |
|
898 |
|
|
879 | 899 |
/* Helpers specific to PowerPC 40x implementations */ |
880 | 900 |
void ppc4xx_tlb_invalidate_all (CPUState *env) |
881 | 901 |
{ |
... | ... | |
1069 | 1089 |
ctx->raddr = eaddr; |
1070 | 1090 |
ctx->prot = PAGE_READ; |
1071 | 1091 |
ret = 0; |
1072 |
switch (PPC_MMU(env)) {
|
|
1073 |
case PPC_FLAGS_MMU_32B:
|
|
1074 |
case PPC_FLAGS_MMU_SOFT_6xx:
|
|
1075 |
case PPC_FLAGS_MMU_601:
|
|
1076 |
case PPC_FLAGS_MMU_SOFT_4xx:
|
|
1077 |
case PPC_FLAGS_MMU_401:
|
|
1092 |
switch (env->mmu_model) {
|
|
1093 |
case POWERPC_MMU_32B:
|
|
1094 |
case POWERPC_MMU_SOFT_6xx:
|
|
1095 |
case POWERPC_MMU_601:
|
|
1096 |
case POWERPC_MMU_SOFT_4xx:
|
|
1097 |
case POWERPC_MMU_REAL_4xx:
|
|
1078 | 1098 |
ctx->prot |= PAGE_WRITE; |
1079 | 1099 |
break; |
1080 | 1100 |
#if defined(TARGET_PPC64) |
1081 |
case PPC_FLAGS_MMU_64B:
|
|
1082 |
case PPC_FLAGS_MMU_64BRIDGE:
|
|
1101 |
case POWERPC_MMU_64B:
|
|
1102 |
case POWERPC_MMU_64BRIDGE:
|
|
1083 | 1103 |
/* Real address are 60 bits long */ |
1084 |
ctx->raddr &= 0x0FFFFFFFFFFFFFFFUL; |
|
1104 |
ctx->raddr &= 0x0FFFFFFFFFFFFFFFULL;
|
|
1085 | 1105 |
ctx->prot |= PAGE_WRITE; |
1086 | 1106 |
break; |
1087 | 1107 |
#endif |
1088 |
case PPC_FLAGS_MMU_403:
|
|
1108 |
case POWERPC_MMU_SOFT_4xx_Z:
|
|
1089 | 1109 |
if (unlikely(msr_pe != 0)) { |
1090 | 1110 |
/* 403 family add some particular protections, |
1091 | 1111 |
* using PBL/PBU registers for accesses with no translation. |
... | ... | |
1108 | 1128 |
ctx->prot |= PAGE_WRITE; |
1109 | 1129 |
} |
1110 | 1130 |
} |
1111 |
case PPC_FLAGS_MMU_BOOKE:
|
|
1131 |
case POWERPC_MMU_BOOKE:
|
|
1112 | 1132 |
ctx->prot |= PAGE_WRITE; |
1113 | 1133 |
break; |
1114 |
case PPC_FLAGS_MMU_BOOKE_FSL:
|
|
1134 |
case POWERPC_MMU_BOOKE_FSL:
|
|
1115 | 1135 |
/* XXX: TODO */ |
1116 | 1136 |
cpu_abort(env, "BookE FSL MMU model not implemented\n"); |
1117 | 1137 |
break; |
... | ... | |
1138 | 1158 |
ret = check_physical(env, ctx, eaddr, rw); |
1139 | 1159 |
} else { |
1140 | 1160 |
ret = -1; |
1141 |
switch (PPC_MMU(env)) {
|
|
1142 |
case PPC_FLAGS_MMU_32B:
|
|
1143 |
case PPC_FLAGS_MMU_SOFT_6xx:
|
|
1161 |
switch (env->mmu_model) {
|
|
1162 |
case POWERPC_MMU_32B:
|
|
1163 |
case POWERPC_MMU_SOFT_6xx:
|
|
1144 | 1164 |
/* Try to find a BAT */ |
1145 | 1165 |
if (check_BATs) |
1146 | 1166 |
ret = get_bat(env, ctx, eaddr, rw, access_type); |
1147 | 1167 |
/* No break here */ |
1148 | 1168 |
#if defined(TARGET_PPC64) |
1149 |
case PPC_FLAGS_MMU_64B:
|
|
1150 |
case PPC_FLAGS_MMU_64BRIDGE:
|
|
1169 |
case POWERPC_MMU_64B:
|
|
1170 |
case POWERPC_MMU_64BRIDGE:
|
|
1151 | 1171 |
#endif |
1152 | 1172 |
if (ret < 0) { |
1153 | 1173 |
/* We didn't match any BAT entry or don't have BATs */ |
1154 | 1174 |
ret = get_segment(env, ctx, eaddr, rw, access_type); |
1155 | 1175 |
} |
1156 | 1176 |
break; |
1157 |
case PPC_FLAGS_MMU_SOFT_4xx:
|
|
1158 |
case PPC_FLAGS_MMU_403:
|
|
1177 |
case POWERPC_MMU_SOFT_4xx:
|
|
1178 |
case POWERPC_MMU_SOFT_4xx_Z:
|
|
1159 | 1179 |
ret = mmu40x_get_physical_address(env, ctx, eaddr, |
1160 | 1180 |
rw, access_type); |
1161 | 1181 |
break; |
1162 |
case PPC_FLAGS_MMU_601:
|
|
1182 |
case POWERPC_MMU_601:
|
|
1163 | 1183 |
/* XXX: TODO */ |
1164 | 1184 |
cpu_abort(env, "601 MMU model not implemented\n"); |
1165 | 1185 |
return -1; |
1166 |
case PPC_FLAGS_MMU_BOOKE:
|
|
1186 |
case POWERPC_MMU_BOOKE:
|
|
1167 | 1187 |
ret = mmubooke_get_physical_address(env, ctx, eaddr, |
1168 | 1188 |
rw, access_type); |
1169 | 1189 |
break; |
1170 |
case PPC_FLAGS_MMU_BOOKE_FSL:
|
|
1190 |
case POWERPC_MMU_BOOKE_FSL:
|
|
1171 | 1191 |
/* XXX: TODO */ |
1172 | 1192 |
cpu_abort(env, "BookE FSL MMU model not implemented\n"); |
1173 | 1193 |
return -1; |
1174 |
case PPC_FLAGS_MMU_401:
|
|
1194 |
case POWERPC_MMU_REAL_4xx:
|
|
1175 | 1195 |
cpu_abort(env, "PowerPC 401 does not do any translation\n"); |
1176 | 1196 |
return -1; |
1177 | 1197 |
default: |
... | ... | |
1234 | 1254 |
switch (ret) { |
1235 | 1255 |
case -1: |
1236 | 1256 |
/* No matches in page tables or TLB */ |
1237 |
switch (PPC_MMU(env)) {
|
|
1238 |
case PPC_FLAGS_MMU_SOFT_6xx:
|
|
1257 |
switch (env->mmu_model) {
|
|
1258 |
case POWERPC_MMU_SOFT_6xx:
|
|
1239 | 1259 |
exception = EXCP_I_TLBMISS; |
1240 | 1260 |
env->spr[SPR_IMISS] = address; |
1241 | 1261 |
env->spr[SPR_ICMP] = 0x80000000 | ctx.ptem; |
1242 | 1262 |
error_code = 1 << 18; |
1243 | 1263 |
goto tlb_miss; |
1244 |
case PPC_FLAGS_MMU_SOFT_4xx:
|
|
1245 |
case PPC_FLAGS_MMU_403:
|
|
1264 |
case POWERPC_MMU_SOFT_4xx:
|
|
1265 |
case POWERPC_MMU_SOFT_4xx_Z:
|
|
1246 | 1266 |
exception = EXCP_40x_ITLBMISS; |
1247 | 1267 |
error_code = 0; |
1248 | 1268 |
env->spr[SPR_40x_DEAR] = address; |
1249 | 1269 |
env->spr[SPR_40x_ESR] = 0x00000000; |
1250 | 1270 |
break; |
1251 |
case PPC_FLAGS_MMU_32B:
|
|
1271 |
case POWERPC_MMU_32B:
|
|
1252 | 1272 |
error_code = 0x40000000; |
1253 | 1273 |
break; |
1254 | 1274 |
#if defined(TARGET_PPC64) |
1255 |
case PPC_FLAGS_MMU_64B:
|
|
1275 |
case POWERPC_MMU_64B:
|
|
1256 | 1276 |
/* XXX: TODO */ |
1257 | 1277 |
cpu_abort(env, "MMU model not implemented\n"); |
1258 | 1278 |
return -1; |
1259 |
case PPC_FLAGS_MMU_64BRIDGE:
|
|
1279 |
case POWERPC_MMU_64BRIDGE:
|
|
1260 | 1280 |
/* XXX: TODO */ |
1261 | 1281 |
cpu_abort(env, "MMU model not implemented\n"); |
1262 | 1282 |
return -1; |
1263 | 1283 |
#endif |
1264 |
case PPC_FLAGS_MMU_601:
|
|
1284 |
case POWERPC_MMU_601:
|
|
1265 | 1285 |
/* XXX: TODO */ |
1266 | 1286 |
cpu_abort(env, "MMU model not implemented\n"); |
1267 | 1287 |
return -1; |
1268 |
case PPC_FLAGS_MMU_BOOKE:
|
|
1288 |
case POWERPC_MMU_BOOKE:
|
|
1269 | 1289 |
/* XXX: TODO */ |
1270 | 1290 |
cpu_abort(env, "MMU model not implemented\n"); |
1271 | 1291 |
return -1; |
1272 |
case PPC_FLAGS_MMU_BOOKE_FSL:
|
|
1292 |
case POWERPC_MMU_BOOKE_FSL:
|
|
1273 | 1293 |
/* XXX: TODO */ |
1274 | 1294 |
cpu_abort(env, "MMU model not implemented\n"); |
1275 | 1295 |
return -1; |
1276 |
case PPC_FLAGS_MMU_401:
|
|
1296 |
case POWERPC_MMU_REAL_4xx:
|
|
1277 | 1297 |
cpu_abort(env, "PowerPC 401 should never raise any MMU " |
1278 | 1298 |
"exceptions\n"); |
1279 | 1299 |
return -1; |
... | ... | |
1306 | 1326 |
switch (ret) { |
1307 | 1327 |
case -1: |
1308 | 1328 |
/* No matches in page tables or TLB */ |
1309 |
switch (PPC_MMU(env)) {
|
|
1310 |
case PPC_FLAGS_MMU_SOFT_6xx:
|
|
1329 |
switch (env->mmu_model) {
|
|
1330 |
case POWERPC_MMU_SOFT_6xx:
|
|
1311 | 1331 |
if (rw == 1) { |
1312 | 1332 |
exception = EXCP_DS_TLBMISS; |
1313 | 1333 |
error_code = 1 << 16; |
... | ... | |
1323 | 1343 |
env->spr[SPR_HASH2] = ctx.pg_addr[1]; |
1324 | 1344 |
/* Do not alter DAR nor DSISR */ |
1325 | 1345 |
goto out; |
1326 |
case PPC_FLAGS_MMU_SOFT_4xx:
|
|
1327 |
case PPC_FLAGS_MMU_403:
|
|
1346 |
case POWERPC_MMU_SOFT_4xx:
|
|
1347 |
case POWERPC_MMU_SOFT_4xx_Z:
|
|
1328 | 1348 |
exception = EXCP_40x_DTLBMISS; |
1329 | 1349 |
error_code = 0; |
1330 | 1350 |
env->spr[SPR_40x_DEAR] = address; |
... | ... | |
1333 | 1353 |
else |
1334 | 1354 |
env->spr[SPR_40x_ESR] = 0x00000000; |
1335 | 1355 |
break; |
1336 |
case PPC_FLAGS_MMU_32B:
|
|
1356 |
case POWERPC_MMU_32B:
|
|
1337 | 1357 |
error_code = 0x40000000; |
1338 | 1358 |
break; |
1339 | 1359 |
#if defined(TARGET_PPC64) |
1340 |
case PPC_FLAGS_MMU_64B:
|
|
1360 |
case POWERPC_MMU_64B:
|
|
1341 | 1361 |
/* XXX: TODO */ |
1342 | 1362 |
cpu_abort(env, "MMU model not implemented\n"); |
1343 | 1363 |
return -1; |
1344 |
case PPC_FLAGS_MMU_64BRIDGE:
|
|
1364 |
case POWERPC_MMU_64BRIDGE:
|
|
1345 | 1365 |
/* XXX: TODO */ |
1346 | 1366 |
cpu_abort(env, "MMU model not implemented\n"); |
1347 | 1367 |
return -1; |
1348 | 1368 |
#endif |
1349 |
case PPC_FLAGS_MMU_601:
|
|
1369 |
case POWERPC_MMU_601:
|
|
1350 | 1370 |
/* XXX: TODO */ |
1351 | 1371 |
cpu_abort(env, "MMU model not implemented\n"); |
1352 | 1372 |
return -1; |
1353 |
case PPC_FLAGS_MMU_BOOKE:
|
|
1373 |
case POWERPC_MMU_BOOKE:
|
|
1354 | 1374 |
/* XXX: TODO */ |
1355 | 1375 |
cpu_abort(env, "MMU model not implemented\n"); |
1356 | 1376 |
return -1; |
1357 |
case PPC_FLAGS_MMU_BOOKE_FSL:
|
|
1377 |
case POWERPC_MMU_BOOKE_FSL:
|
|
1358 | 1378 |
/* XXX: TODO */ |
1359 | 1379 |
cpu_abort(env, "MMU model not implemented\n"); |
1360 | 1380 |
return -1; |
1361 |
case PPC_FLAGS_MMU_401:
|
|
1381 |
case POWERPC_MMU_REAL_4xx:
|
|
1362 | 1382 |
cpu_abort(env, "PowerPC 401 should never raise any MMU " |
1363 | 1383 |
"exceptions\n"); |
1364 | 1384 |
return -1; |
... | ... | |
1544 | 1564 |
/* TLB management */ |
1545 | 1565 |
void ppc_tlb_invalidate_all (CPUPPCState *env) |
1546 | 1566 |
{ |
1547 |
if (unlikely(PPC_MMU(env) == PPC_FLAGS_MMU_SOFT_6xx)) {
|
|
1567 |
if (unlikely(env->mmu_model == POWERPC_MMU_SOFT_6xx)) {
|
|
1548 | 1568 |
ppc6xx_tlb_invalidate_all(env); |
1549 |
} else if (unlikely(PPC_MMU(env) == PPC_FLAGS_MMU_SOFT_4xx)) {
|
|
1569 |
} else if (unlikely(env->mmu_model == POWERPC_MMU_SOFT_4xx)) {
|
|
1550 | 1570 |
ppc4xx_tlb_invalidate_all(env); |
1551 | 1571 |
} else { |
1552 | 1572 |
tlb_flush(env, 1); |
... | ... | |
1707 | 1727 |
fprintf(logfile, "%s: T0 %08lx\n", __func__, value); |
1708 | 1728 |
} |
1709 | 1729 |
#endif |
1710 |
switch (PPC_EXCP(env)) { |
|
1711 |
case PPC_FLAGS_EXCP_602: |
|
1712 |
case PPC_FLAGS_EXCP_603: |
|
1730 |
switch (env->excp_model) { |
|
1731 |
case POWERPC_EXCP_602: |
|
1732 |
case POWERPC_EXCP_603: |
|
1733 |
case POWERPC_EXCP_603E: |
|
1734 |
case POWERPC_EXCP_G2: |
|
1713 | 1735 |
if (((value >> MSR_TGPR) & 1) != msr_tgpr) { |
1714 | 1736 |
/* Swap temporary saved registers with GPRs */ |
1715 | 1737 |
swap_gpr_tgpr(env); |
... | ... | |
1750 | 1772 |
do_compute_hflags(env); |
1751 | 1773 |
|
1752 | 1774 |
enter_pm = 0; |
1753 |
switch (PPC_EXCP(env)) { |
|
1754 |
case PPC_FLAGS_EXCP_603: |
|
1775 |
switch (env->excp_model) { |
|
1776 |
case POWERPC_EXCP_603: |
|
1777 |
case POWERPC_EXCP_603E: |
|
1778 |
case POWERPC_EXCP_G2: |
|
1755 | 1779 |
/* Don't handle SLEEP mode: we should disable all clocks... |
1756 | 1780 |
* No dynamic power-management. |
1757 | 1781 |
*/ |
1758 | 1782 |
if (msr_pow == 1 && (env->spr[SPR_HID0] & 0x00C00000) != 0) |
1759 | 1783 |
enter_pm = 1; |
1760 | 1784 |
break; |
1761 |
case PPC_FLAGS_EXCP_604:
|
|
1785 |
case POWERPC_EXCP_604:
|
|
1762 | 1786 |
if (msr_pow == 1) |
1763 | 1787 |
enter_pm = 1; |
1764 | 1788 |
break; |
1765 |
case PPC_FLAGS_EXCP_7x0:
|
|
1789 |
case POWERPC_EXCP_7x0:
|
|
1766 | 1790 |
if (msr_pow == 1 && (env->spr[SPR_HID0] & 0x00E00000) != 0) |
1767 | 1791 |
enter_pm = 1; |
1768 | 1792 |
break; |
... | ... | |
1854 | 1878 |
switch (excp) { |
1855 | 1879 |
/* Generic PowerPC exceptions */ |
1856 | 1880 |
case EXCP_RESET: /* 0x0100 */ |
1857 |
switch (PPC_EXCP(env)) {
|
|
1858 |
case PPC_FLAGS_EXCP_40x:
|
|
1881 |
switch (env->excp_model) {
|
|
1882 |
case POWERPC_EXCP_40x:
|
|
1859 | 1883 |
srr_0 = &env->spr[SPR_40x_SRR2]; |
1860 | 1884 |
srr_1 = &env->spr[SPR_40x_SRR3]; |
1861 | 1885 |
break; |
1862 |
case PPC_FLAGS_EXCP_BOOKE:
|
|
1886 |
case POWERPC_EXCP_BOOKE:
|
|
1863 | 1887 |
idx = 0; |
1864 | 1888 |
srr_0 = &env->spr[SPR_BOOKE_CSRR0]; |
1865 | 1889 |
srr_1 = &env->spr[SPR_BOOKE_CSRR1]; |
... | ... | |
1872 | 1896 |
} |
1873 | 1897 |
goto store_next; |
1874 | 1898 |
case EXCP_MACHINE_CHECK: /* 0x0200 */ |
1875 |
switch (PPC_EXCP(env)) {
|
|
1876 |
case PPC_FLAGS_EXCP_40x:
|
|
1899 |
switch (env->excp_model) {
|
|
1900 |
case POWERPC_EXCP_40x:
|
|
1877 | 1901 |
srr_0 = &env->spr[SPR_40x_SRR2]; |
1878 | 1902 |
srr_1 = &env->spr[SPR_40x_SRR3]; |
1879 | 1903 |
break; |
1880 |
case PPC_FLAGS_EXCP_BOOKE:
|
|
1904 |
case POWERPC_EXCP_BOOKE:
|
|
1881 | 1905 |
idx = 1; |
1882 | 1906 |
srr_0 = &env->spr[SPR_BOOKE_MCSRR0]; |
1883 | 1907 |
srr_1 = &env->spr[SPR_BOOKE_MCSRR1]; |
... | ... | |
1920 | 1944 |
idx = 4; |
1921 | 1945 |
goto store_next; |
1922 | 1946 |
case EXCP_ALIGN: /* 0x0600 */ |
1923 |
if (likely(PPC_EXCP(env) != PPC_FLAGS_EXCP_601)) {
|
|
1947 |
if (likely(env->excp_model != POWERPC_EXCP_601)) {
|
|
1924 | 1948 |
/* Store exception cause */ |
1925 | 1949 |
idx = 5; |
1926 | 1950 |
/* Get rS/rD and rA from faulting opcode */ |
... | ... | |
2028 | 2052 |
goto store_next; |
2029 | 2053 |
/* Implementation specific exceptions */ |
2030 | 2054 |
case 0x0A00: |
2031 |
if (likely(env->spr[SPR_PVR] == CPU_PPC_G2 ||
|
|
2032 |
env->spr[SPR_PVR] == CPU_PPC_G2LE)) {
|
|
2055 |
switch (env->excp_model) {
|
|
2056 |
case POWERPC_EXCP_G2:
|
|
2033 | 2057 |
/* Critical interrupt on G2 */ |
2034 | 2058 |
/* XXX: TODO */ |
2035 | 2059 |
cpu_abort(env, "G2 critical interrupt is not implemented yet !\n"); |
2036 | 2060 |
goto store_next; |
2037 |
} else {
|
|
2061 |
default:
|
|
2038 | 2062 |
cpu_abort(env, "Invalid exception 0x0A00 !\n"); |
2063 |
break; |
|
2039 | 2064 |
} |
2040 | 2065 |
return; |
2041 | 2066 |
case 0x0F20: |
2042 | 2067 |
idx = 9; |
2043 |
switch (PPC_EXCP(env)) {
|
|
2044 |
case PPC_FLAGS_EXCP_40x:
|
|
2068 |
switch (env->excp_model) {
|
|
2069 |
case POWERPC_EXCP_40x:
|
|
2045 | 2070 |
/* APU unavailable on 405 */ |
2046 | 2071 |
/* XXX: TODO */ |
2047 | 2072 |
cpu_abort(env, |
2048 | 2073 |
"APU unavailable exception is not implemented yet !\n"); |
2049 | 2074 |
goto store_next; |
2050 |
case PPC_FLAGS_EXCP_74xx:
|
|
2075 |
case POWERPC_EXCP_74xx:
|
|
2051 | 2076 |
/* Altivec unavailable */ |
2052 | 2077 |
/* XXX: TODO */ |
2053 | 2078 |
cpu_abort(env, "Altivec unavailable exception " |
... | ... | |
2060 | 2085 |
return; |
2061 | 2086 |
case 0x1000: |
2062 | 2087 |
idx = 10; |
2063 |
switch (PPC_EXCP(env)) {
|
|
2064 |
case PPC_FLAGS_EXCP_40x:
|
|
2088 |
switch (env->excp_model) {
|
|
2089 |
case POWERPC_EXCP_40x:
|
|
2065 | 2090 |
/* PIT on 4xx */ |
2066 | 2091 |
msr &= ~0xFFFF0000; |
2067 | 2092 |
#if defined (DEBUG_EXCEPTIONS) |
... | ... | |
2069 | 2094 |
fprintf(logfile, "PIT exception\n"); |
2070 | 2095 |
#endif |
2071 | 2096 |
goto store_next; |
2072 |
case PPC_FLAGS_EXCP_602: |
|
2073 |
case PPC_FLAGS_EXCP_603: |
|
2097 |
case POWERPC_EXCP_602: |
|
2098 |
case POWERPC_EXCP_603: |
|
2099 |
case POWERPC_EXCP_603E: |
|
2100 |
case POWERPC_EXCP_G2: |
|
2074 | 2101 |
/* ITLBMISS on 602/603 */ |
2075 | 2102 |
goto store_gprs; |
2076 |
case PPC_FLAGS_EXCP_7x5:
|
|
2103 |
case POWERPC_EXCP_7x5:
|
|
2077 | 2104 |
/* ITLBMISS on 745/755 */ |
2078 | 2105 |
goto tlb_miss; |
2079 | 2106 |
default: |
... | ... | |
2083 | 2110 |
return; |
2084 | 2111 |
case 0x1010: |
2085 | 2112 |
idx = 11; |
2086 |
switch (PPC_EXCP(env)) {
|
|
2087 |
case PPC_FLAGS_EXCP_40x:
|
|
2113 |
switch (env->excp_model) {
|
|
2114 |
case POWERPC_EXCP_40x:
|
|
2088 | 2115 |
/* FIT on 4xx */ |
2089 | 2116 |
msr &= ~0xFFFF0000; |
2090 | 2117 |
#if defined (DEBUG_EXCEPTIONS) |
... | ... | |
2099 | 2126 |
return; |
2100 | 2127 |
case 0x1020: |
2101 | 2128 |
idx = 12; |
2102 |
switch (PPC_EXCP(env)) {
|
|
2103 |
case PPC_FLAGS_EXCP_40x:
|
|
2129 |
switch (env->excp_model) {
|
|
2130 |
case POWERPC_EXCP_40x:
|
|
2104 | 2131 |
/* Watchdog on 4xx */ |
2105 | 2132 |
msr &= ~0xFFFF0000; |
2106 | 2133 |
#if defined (DEBUG_EXCEPTIONS) |
... | ... | |
2108 | 2135 |
fprintf(logfile, "WDT exception\n"); |
2109 | 2136 |
#endif |
2110 | 2137 |
goto store_next; |
2111 |
case PPC_FLAGS_EXCP_BOOKE:
|
|
2138 |
case POWERPC_EXCP_BOOKE:
|
|
2112 | 2139 |
srr_0 = &env->spr[SPR_BOOKE_CSRR0]; |
2113 | 2140 |
srr_1 = &env->spr[SPR_BOOKE_CSRR1]; |
2114 | 2141 |
break; |
... | ... | |
2119 | 2146 |
return; |
2120 | 2147 |
case 0x1100: |
2121 | 2148 |
idx = 13; |
2122 |
switch (PPC_EXCP(env)) {
|
|
2123 |
case PPC_FLAGS_EXCP_40x:
|
|
2149 |
switch (env->excp_model) {
|
|
2150 |
case POWERPC_EXCP_40x:
|
|
2124 | 2151 |
/* DTLBMISS on 4xx */ |
2125 | 2152 |
msr &= ~0xFFFF0000; |
2126 | 2153 |
goto store_next; |
2127 |
case PPC_FLAGS_EXCP_602: |
|
2128 |
case PPC_FLAGS_EXCP_603: |
|
2154 |
case POWERPC_EXCP_602: |
|
2155 |
case POWERPC_EXCP_603: |
|
2156 |
case POWERPC_EXCP_603E: |
|
2157 |
case POWERPC_EXCP_G2: |
|
2129 | 2158 |
/* DLTLBMISS on 602/603 */ |
2130 | 2159 |
goto store_gprs; |
2131 |
case PPC_FLAGS_EXCP_7x5:
|
|
2160 |
case POWERPC_EXCP_7x5:
|
|
2132 | 2161 |
/* DLTLBMISS on 745/755 */ |
2133 | 2162 |
goto tlb_miss; |
2134 | 2163 |
default: |
... | ... | |
2138 | 2167 |
return; |
2139 | 2168 |
case 0x1200: |
2140 | 2169 |
idx = 14; |
2141 |
switch (PPC_EXCP(env)) {
|
|
2142 |
case PPC_FLAGS_EXCP_40x:
|
|
2170 |
switch (env->excp_model) {
|
|
2171 |
case POWERPC_EXCP_40x:
|
|
2143 | 2172 |
/* ITLBMISS on 4xx */ |
2144 | 2173 |
msr &= ~0xFFFF0000; |
2145 | 2174 |
goto store_next; |
2146 |
case PPC_FLAGS_EXCP_602: |
|
2147 |
case PPC_FLAGS_EXCP_603: |
|
2175 |
case POWERPC_EXCP_602: |
|
2176 |
case POWERPC_EXCP_603: |
|
2177 |
case POWERPC_EXCP_603E: |
|
2178 |
case POWERPC_EXCP_G2: |
|
2148 | 2179 |
/* DSTLBMISS on 602/603 */ |
2149 | 2180 |
store_gprs: |
2150 | 2181 |
/* Swap temporary saved registers with GPRs */ |
... | ... | |
2177 | 2208 |
} |
2178 | 2209 |
#endif |
2179 | 2210 |
goto tlb_miss; |
2180 |
case PPC_FLAGS_EXCP_7x5:
|
|
2211 |
case POWERPC_EXCP_7x5:
|
|
2181 | 2212 |
/* DSTLBMISS on 745/755 */ |
2182 | 2213 |
tlb_miss: |
2183 | 2214 |
msr &= ~0xF83F0000; |
... | ... | |
2192 | 2223 |
} |
2193 | 2224 |
return; |
2194 | 2225 |
case 0x1300: |
2195 |
switch (PPC_EXCP(env)) { |
|
2196 |
case PPC_FLAGS_EXCP_601: |
|
2197 |
case PPC_FLAGS_EXCP_602: |
|
2198 |
case PPC_FLAGS_EXCP_603: |
|
2199 |
case PPC_FLAGS_EXCP_604: |
|
2200 |
case PPC_FLAGS_EXCP_7x0: |
|
2201 |
case PPC_FLAGS_EXCP_7x5: |
|
2226 |
switch (env->excp_model) { |
|
2227 |
case POWERPC_EXCP_601: |
|
2228 |
case POWERPC_EXCP_602: |
|
2229 |
case POWERPC_EXCP_603: |
|
2230 |
case POWERPC_EXCP_603E: |
|
2231 |
case POWERPC_EXCP_G2: |
|
2232 |
case POWERPC_EXCP_604: |
|
2233 |
case POWERPC_EXCP_7x0: |
|
2234 |
case POWERPC_EXCP_7x5: |
|
2202 | 2235 |
/* IABR on 6xx/7xx */ |
2203 | 2236 |
/* XXX: TODO */ |
2204 | 2237 |
cpu_abort(env, "IABR exception is not implemented yet !\n"); |
... | ... | |
2209 | 2242 |
} |
2210 | 2243 |
return; |
2211 | 2244 |
case 0x1400: |
2212 |
switch (PPC_EXCP(env)) { |
|
2213 |
case PPC_FLAGS_EXCP_601: |
|
2214 |
case PPC_FLAGS_EXCP_602: |
|
2215 |
case PPC_FLAGS_EXCP_603: |
|
2216 |
case PPC_FLAGS_EXCP_604: |
|
2217 |
case PPC_FLAGS_EXCP_7x0: |
|
2218 |
case PPC_FLAGS_EXCP_7x5: |
|
2245 |
switch (env->excp_model) { |
|
2246 |
case POWERPC_EXCP_601: |
|
2247 |
case POWERPC_EXCP_602: |
|
2248 |
case POWERPC_EXCP_603: |
|
2249 |
case POWERPC_EXCP_603E: |
|
2250 |
case POWERPC_EXCP_G2: |
|
2251 |
case POWERPC_EXCP_604: |
|
2252 |
case POWERPC_EXCP_7x0: |
|
2253 |
case POWERPC_EXCP_7x5: |
|
2219 | 2254 |
/* SMI on 6xx/7xx */ |
2220 | 2255 |
/* XXX: TODO */ |
2221 | 2256 |
cpu_abort(env, "SMI exception is not implemented yet !\n"); |
... | ... | |
2226 | 2261 |
} |
2227 | 2262 |
return; |
2228 | 2263 |
case 0x1500: |
2229 |
switch (PPC_EXCP(env)) {
|
|
2230 |
case PPC_FLAGS_EXCP_602:
|
|
2264 |
switch (env->excp_model) {
|
|
2265 |
case POWERPC_EXCP_602:
|
|
2231 | 2266 |
/* Watchdog on 602 */ |
2232 | 2267 |
/* XXX: TODO */ |
2233 | 2268 |
cpu_abort(env, |
2234 | 2269 |
"602 watchdog exception is not implemented yet !\n"); |
2235 | 2270 |
goto store_next; |
2236 |
case PPC_FLAGS_EXCP_970:
|
|
2271 |
case POWERPC_EXCP_970:
|
|
2237 | 2272 |
/* Soft patch exception on 970 */ |
2238 | 2273 |
/* XXX: TODO */ |
2239 | 2274 |
cpu_abort(env, |
2240 | 2275 |
"970 soft-patch exception is not implemented yet !\n"); |
2241 | 2276 |
goto store_next; |
2242 |
case PPC_FLAGS_EXCP_74xx:
|
|
2277 |
case POWERPC_EXCP_74xx:
|
|
2243 | 2278 |
/* VPU assist on 74xx */ |
2244 | 2279 |
/* XXX: TODO */ |
2245 | 2280 |
cpu_abort(env, "VPU assist exception is not implemented yet !\n"); |
... | ... | |
2250 | 2285 |
} |
2251 | 2286 |
return; |
2252 | 2287 |
case 0x1600: |
2253 |
switch (PPC_EXCP(env)) {
|
|
2254 |
case PPC_FLAGS_EXCP_602:
|
|
2288 |
switch (env->excp_model) {
|
|
2289 |
case POWERPC_EXCP_602:
|
|
2255 | 2290 |
/* Emulation trap on 602 */ |
2256 | 2291 |
/* XXX: TODO */ |
2257 | 2292 |
cpu_abort(env, "602 emulation trap exception " |
2258 | 2293 |
"is not implemented yet !\n"); |
2259 | 2294 |
goto store_next; |
2260 |
case PPC_FLAGS_EXCP_970:
|
|
2295 |
case POWERPC_EXCP_970:
|
|
2261 | 2296 |
/* Maintenance exception on 970 */ |
2262 | 2297 |
/* XXX: TODO */ |
2263 | 2298 |
cpu_abort(env, |
... | ... | |
2269 | 2304 |
} |
2270 | 2305 |
return; |
2271 | 2306 |
case 0x1700: |
2272 |
switch (PPC_EXCP(env)) {
|
|
2273 |
case PPC_FLAGS_EXCP_7x0:
|
|
2274 |
case PPC_FLAGS_EXCP_7x5:
|
|
2307 |
switch (env->excp_model) {
|
|
2308 |
case POWERPC_EXCP_7x0:
|
|
2309 |
case POWERPC_EXCP_7x5:
|
|
2275 | 2310 |
/* Thermal management interrupt on G3 */ |
2276 | 2311 |
/* XXX: TODO */ |
2277 | 2312 |
cpu_abort(env, "G3 thermal management exception " |
2278 | 2313 |
"is not implemented yet !\n"); |
2279 | 2314 |
goto store_next; |
2280 |
case PPC_FLAGS_EXCP_970:
|
|
2315 |
case POWERPC_EXCP_970:
|
|
2281 | 2316 |
/* VPU assist on 970 */ |
2282 | 2317 |
/* XXX: TODO */ |
2283 | 2318 |
cpu_abort(env, |
... | ... | |
2289 | 2324 |
} |
2290 | 2325 |
return; |
2291 | 2326 |
case 0x1800: |
2292 |
switch (PPC_EXCP(env)) {
|
|
2293 |
case PPC_FLAGS_EXCP_970:
|
|
2327 |
switch (env->excp_model) {
|
|
2328 |
case POWERPC_EXCP_970:
|
|
2294 | 2329 |
/* Thermal exception on 970 */ |
2295 | 2330 |
/* XXX: TODO */ |
2296 | 2331 |
cpu_abort(env, "970 thermal management exception " |
... | ... | |
2302 | 2337 |
} |
2303 | 2338 |
return; |
2304 | 2339 |
case 0x2000: |
2305 |
switch (PPC_EXCP(env)) {
|
|
2306 |
case PPC_FLAGS_EXCP_40x:
|
|
2340 |
switch (env->excp_model) {
|
|
2341 |
case POWERPC_EXCP_40x:
|
|
2307 | 2342 |
/* DEBUG on 4xx */ |
2308 | 2343 |
/* XXX: TODO */ |
2309 | 2344 |
cpu_abort(env, "40x debug exception is not implemented yet !\n"); |
2310 | 2345 |
goto store_next; |
2311 |
case PPC_FLAGS_EXCP_601:
|
|
2346 |
case POWERPC_EXCP_601:
|
|
2312 | 2347 |
/* Run mode exception on 601 */ |
2313 | 2348 |
/* XXX: TODO */ |
2314 | 2349 |
cpu_abort(env, |
2315 | 2350 |
"601 run mode exception is not implemented yet !\n"); |
2316 | 2351 |
goto store_next; |
2317 |
case PPC_FLAGS_EXCP_BOOKE:
|
|
2352 |
case POWERPC_EXCP_BOOKE:
|
|
2318 | 2353 |
srr_0 = &env->spr[SPR_BOOKE_CSRR0]; |
2319 | 2354 |
srr_1 = &env->spr[SPR_BOOKE_CSRR1]; |
2320 | 2355 |
break; |
... | ... | |
2361 | 2396 |
msr_dr = 0; |
2362 | 2397 |
msr_ri = 0; |
2363 | 2398 |
msr_le = msr_ile; |
2364 |
if (PPC_EXCP(env) == PPC_FLAGS_EXCP_BOOKE) {
|
|
2399 |
if (env->excp_model == POWERPC_EXCP_BOOKE) {
|
|
2365 | 2400 |
msr_cm = msr_icm; |
2366 | 2401 |
if (idx == -1 || (idx >= 16 && idx < 32)) { |
2367 | 2402 |
cpu_abort(env, "Invalid exception index for excp %d %08x idx %d\n", |
Also available in: Unified diff