1 /* 2 * PowerPC MMU, TLB, SLB and BAT emulation helpers for QEMU. 3 * 4 * Copyright (c) 2003-2007 Jocelyn Mayer 5 * 6 * This library is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU Lesser General Public 8 * License as published by the Free Software Foundation; either 9 * version 2.1 of the License, or (at your option) any later version. 10 * 11 * This library is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14 * Lesser General Public License for more details. 15 * 16 * You should have received a copy of the GNU Lesser General Public 17 * License along with this library; if not, see <http://www.gnu.org/licenses/>. 18 */ 19 20 #include "qemu/osdep.h" 21 #include "qemu/units.h" 22 #include "cpu.h" 23 #include "sysemu/kvm.h" 24 #include "kvm_ppc.h" 25 #include "mmu-hash64.h" 26 #include "mmu-hash32.h" 27 #include "exec/exec-all.h" 28 #include "exec/page-protection.h" 29 #include "exec/log.h" 30 #include "helper_regs.h" 31 #include "qemu/error-report.h" 32 #include "qemu/qemu-print.h" 33 #include "internal.h" 34 #include "mmu-book3s-v3.h" 35 #include "mmu-radix64.h" 36 37 /* #define DUMP_PAGE_TABLES */ 38 39 /* Context used internally during MMU translations */ 40 typedef struct { 41 hwaddr raddr; /* Real address */ 42 hwaddr eaddr; /* Effective address */ 43 int prot; /* Protection bits */ 44 hwaddr hash[2]; /* Pagetable hash values */ 45 target_ulong ptem; /* Virtual segment ID | API */ 46 int key; /* Access key */ 47 int nx; /* Non-execute area */ 48 } mmu_ctx_t; 49 50 void ppc_store_sdr1(CPUPPCState *env, target_ulong value) 51 { 52 PowerPCCPU *cpu = env_archcpu(env); 53 qemu_log_mask(CPU_LOG_MMU, "%s: " TARGET_FMT_lx "\n", __func__, value); 54 assert(!cpu->env.has_hv_mode || !cpu->vhyp); 55 #if defined(TARGET_PPC64) 56 if (mmu_is_64bit(env->mmu_model)) { 57 target_ulong sdr_mask = SDR_64_HTABORG | SDR_64_HTABSIZE; 58 target_ulong htabsize = value & SDR_64_HTABSIZE; 59 60 if (value & ~sdr_mask) { 61 qemu_log_mask(LOG_GUEST_ERROR, "Invalid bits 0x"TARGET_FMT_lx 62 " set in SDR1", value & ~sdr_mask); 63 value &= sdr_mask; 64 } 65 if (htabsize > 28) { 66 qemu_log_mask(LOG_GUEST_ERROR, "Invalid HTABSIZE 0x" TARGET_FMT_lx 67 " stored in SDR1", htabsize); 68 return; 69 } 70 } 71 #endif /* defined(TARGET_PPC64) */ 72 /* FIXME: Should check for valid HTABMASK values in 32-bit case */ 73 env->spr[SPR_SDR1] = value; 74 } 75 76 /*****************************************************************************/ 77 /* PowerPC MMU emulation */ 78 79 static int pp_check(int key, int pp, int nx) 80 { 81 int access; 82 83 /* Compute access rights */ 84 access = 0; 85 if (key == 0) { 86 switch (pp) { 87 case 0x0: 88 case 0x1: 89 case 0x2: 90 access |= PAGE_WRITE; 91 /* fall through */ 92 case 0x3: 93 access |= PAGE_READ; 94 break; 95 } 96 } else { 97 switch (pp) { 98 case 0x0: 99 access = 0; 100 break; 101 case 0x1: 102 case 0x3: 103 access = PAGE_READ; 104 break; 105 case 0x2: 106 access = PAGE_READ | PAGE_WRITE; 107 break; 108 } 109 } 110 if (nx == 0) { 111 access |= PAGE_EXEC; 112 } 113 114 return access; 115 } 116 117 int ppc6xx_tlb_getnum(CPUPPCState *env, target_ulong eaddr, 118 int way, int is_code) 119 { 120 int nr; 121 122 /* Select TLB num in a way from address */ 123 nr = (eaddr >> TARGET_PAGE_BITS) & (env->tlb_per_way - 1); 124 /* Select TLB way */ 125 nr += env->tlb_per_way * way; 126 /* 6xx has separate TLBs for instructions and data */ 127 if (is_code) { 128 nr += env->nb_tlb; 129 } 130 131 return nr; 132 } 133 134 static int ppc6xx_tlb_pte_check(mmu_ctx_t *ctx, target_ulong pte0, 135 target_ulong pte1, int h, 136 MMUAccessType access_type) 137 { 138 target_ulong ptem, mmask; 139 int access, ret, pteh, ptev, pp; 140 141 ret = -1; 142 /* Check validity and table match */ 143 ptev = pte_is_valid(pte0); 144 pteh = (pte0 >> 6) & 1; 145 if (ptev && h == pteh) { 146 /* Check vsid & api */ 147 ptem = pte0 & PTE_PTEM_MASK; 148 mmask = PTE_CHECK_MASK; 149 pp = pte1 & 0x00000003; 150 if (ptem == ctx->ptem) { 151 if (ctx->raddr != (hwaddr)-1ULL) { 152 /* all matches should have equal RPN, WIMG & PP */ 153 if ((ctx->raddr & mmask) != (pte1 & mmask)) { 154 qemu_log_mask(CPU_LOG_MMU, "Bad RPN/WIMG/PP\n"); 155 return -3; 156 } 157 } 158 /* Compute access rights */ 159 access = pp_check(ctx->key, pp, ctx->nx); 160 /* Keep the matching PTE information */ 161 ctx->raddr = pte1; 162 ctx->prot = access; 163 if (check_prot_access_type(ctx->prot, access_type)) { 164 /* Access granted */ 165 qemu_log_mask(CPU_LOG_MMU, "PTE access granted !\n"); 166 ret = 0; 167 } else { 168 /* Access right violation */ 169 qemu_log_mask(CPU_LOG_MMU, "PTE access rejected\n"); 170 ret = -2; 171 } 172 } 173 } 174 175 return ret; 176 } 177 178 static int pte_update_flags(mmu_ctx_t *ctx, target_ulong *pte1p, 179 int ret, MMUAccessType access_type) 180 { 181 int store = 0; 182 183 /* Update page flags */ 184 if (!(*pte1p & 0x00000100)) { 185 /* Update accessed flag */ 186 *pte1p |= 0x00000100; 187 store = 1; 188 } 189 if (!(*pte1p & 0x00000080)) { 190 if (access_type == MMU_DATA_STORE && ret == 0) { 191 /* Update changed flag */ 192 *pte1p |= 0x00000080; 193 store = 1; 194 } else { 195 /* Force page fault for first write access */ 196 ctx->prot &= ~PAGE_WRITE; 197 } 198 } 199 200 return store; 201 } 202 203 /* Software driven TLB helpers */ 204 205 static int ppc6xx_tlb_check(CPUPPCState *env, mmu_ctx_t *ctx, 206 target_ulong eaddr, MMUAccessType access_type) 207 { 208 ppc6xx_tlb_t *tlb; 209 int nr, best, way; 210 int ret; 211 212 best = -1; 213 ret = -1; /* No TLB found */ 214 for (way = 0; way < env->nb_ways; way++) { 215 nr = ppc6xx_tlb_getnum(env, eaddr, way, access_type == MMU_INST_FETCH); 216 tlb = &env->tlb.tlb6[nr]; 217 /* This test "emulates" the PTE index match for hardware TLBs */ 218 if ((eaddr & TARGET_PAGE_MASK) != tlb->EPN) { 219 qemu_log_mask(CPU_LOG_MMU, "TLB %d/%d %s [" TARGET_FMT_lx 220 " " TARGET_FMT_lx "] <> " TARGET_FMT_lx "\n", 221 nr, env->nb_tlb, 222 pte_is_valid(tlb->pte0) ? "valid" : "inval", 223 tlb->EPN, tlb->EPN + TARGET_PAGE_SIZE, eaddr); 224 continue; 225 } 226 qemu_log_mask(CPU_LOG_MMU, "TLB %d/%d %s " TARGET_FMT_lx " <> " 227 TARGET_FMT_lx " " TARGET_FMT_lx " %c %c\n", 228 nr, env->nb_tlb, 229 pte_is_valid(tlb->pte0) ? "valid" : "inval", 230 tlb->EPN, eaddr, tlb->pte1, 231 access_type == MMU_DATA_STORE ? 'S' : 'L', 232 access_type == MMU_INST_FETCH ? 'I' : 'D'); 233 switch (ppc6xx_tlb_pte_check(ctx, tlb->pte0, tlb->pte1, 234 0, access_type)) { 235 case -2: 236 /* Access violation */ 237 ret = -2; 238 best = nr; 239 break; 240 case -1: /* No match */ 241 case -3: /* TLB inconsistency */ 242 default: 243 break; 244 case 0: 245 /* access granted */ 246 /* 247 * XXX: we should go on looping to check all TLBs 248 * consistency but we can speed-up the whole thing as 249 * the result would be undefined if TLBs are not 250 * consistent. 251 */ 252 ret = 0; 253 best = nr; 254 goto done; 255 } 256 } 257 if (best != -1) { 258 done: 259 qemu_log_mask(CPU_LOG_MMU, "found TLB at addr " HWADDR_FMT_plx 260 " prot=%01x ret=%d\n", 261 ctx->raddr & TARGET_PAGE_MASK, ctx->prot, ret); 262 /* Update page flags */ 263 pte_update_flags(ctx, &env->tlb.tlb6[best].pte1, ret, access_type); 264 } 265 #if defined(DUMP_PAGE_TABLES) 266 if (qemu_loglevel_mask(CPU_LOG_MMU)) { 267 CPUState *cs = env_cpu(env); 268 hwaddr base = ppc_hash32_hpt_base(env_archcpu(env)); 269 hwaddr len = ppc_hash32_hpt_mask(env_archcpu(env)) + 0x80; 270 uint32_t a0, a1, a2, a3; 271 272 qemu_log("Page table: " HWADDR_FMT_plx " len " HWADDR_FMT_plx "\n", 273 base, len); 274 for (hwaddr curaddr = base; curaddr < base + len; curaddr += 16) { 275 a0 = ldl_phys(cs->as, curaddr); 276 a1 = ldl_phys(cs->as, curaddr + 4); 277 a2 = ldl_phys(cs->as, curaddr + 8); 278 a3 = ldl_phys(cs->as, curaddr + 12); 279 if (a0 != 0 || a1 != 0 || a2 != 0 || a3 != 0) { 280 qemu_log(HWADDR_FMT_plx ": %08x %08x %08x %08x\n", 281 curaddr, a0, a1, a2, a3); 282 } 283 } 284 } 285 #endif 286 return ret; 287 } 288 289 /* Perform BAT hit & translation */ 290 static inline void bat_size_prot(CPUPPCState *env, target_ulong *blp, 291 int *validp, int *protp, target_ulong *BATu, 292 target_ulong *BATl) 293 { 294 target_ulong bl; 295 int pp, valid, prot; 296 297 bl = (*BATu & 0x00001FFC) << 15; 298 valid = 0; 299 prot = 0; 300 if ((!FIELD_EX64(env->msr, MSR, PR) && (*BATu & 0x00000002)) || 301 (FIELD_EX64(env->msr, MSR, PR) && (*BATu & 0x00000001))) { 302 valid = 1; 303 pp = *BATl & 0x00000003; 304 if (pp != 0) { 305 prot = PAGE_READ | PAGE_EXEC; 306 if (pp == 0x2) { 307 prot |= PAGE_WRITE; 308 } 309 } 310 } 311 *blp = bl; 312 *validp = valid; 313 *protp = prot; 314 } 315 316 static int get_bat_6xx_tlb(CPUPPCState *env, mmu_ctx_t *ctx, 317 target_ulong virtual, MMUAccessType access_type) 318 { 319 target_ulong *BATlt, *BATut, *BATu, *BATl; 320 target_ulong BEPIl, BEPIu, bl; 321 int i, valid, prot; 322 int ret = -1; 323 bool ifetch = access_type == MMU_INST_FETCH; 324 325 qemu_log_mask(CPU_LOG_MMU, "%s: %cBAT v " TARGET_FMT_lx "\n", __func__, 326 ifetch ? 'I' : 'D', virtual); 327 if (ifetch) { 328 BATlt = env->IBAT[1]; 329 BATut = env->IBAT[0]; 330 } else { 331 BATlt = env->DBAT[1]; 332 BATut = env->DBAT[0]; 333 } 334 for (i = 0; i < env->nb_BATs; i++) { 335 BATu = &BATut[i]; 336 BATl = &BATlt[i]; 337 BEPIu = *BATu & 0xF0000000; 338 BEPIl = *BATu & 0x0FFE0000; 339 bat_size_prot(env, &bl, &valid, &prot, BATu, BATl); 340 qemu_log_mask(CPU_LOG_MMU, "%s: %cBAT%d v " TARGET_FMT_lx " BATu " 341 TARGET_FMT_lx " BATl " TARGET_FMT_lx "\n", __func__, 342 ifetch ? 'I' : 'D', i, virtual, *BATu, *BATl); 343 if ((virtual & 0xF0000000) == BEPIu && 344 ((virtual & 0x0FFE0000) & ~bl) == BEPIl) { 345 /* BAT matches */ 346 if (valid != 0) { 347 /* Get physical address */ 348 ctx->raddr = (*BATl & 0xF0000000) | 349 ((virtual & 0x0FFE0000 & bl) | (*BATl & 0x0FFE0000)) | 350 (virtual & 0x0001F000); 351 /* Compute access rights */ 352 ctx->prot = prot; 353 if (check_prot_access_type(ctx->prot, access_type)) { 354 qemu_log_mask(CPU_LOG_MMU, "BAT %d match: r " HWADDR_FMT_plx 355 " prot=%c%c\n", i, ctx->raddr, 356 ctx->prot & PAGE_READ ? 'R' : '-', 357 ctx->prot & PAGE_WRITE ? 'W' : '-'); 358 ret = 0; 359 } else { 360 ret = -2; 361 } 362 break; 363 } 364 } 365 } 366 if (ret < 0) { 367 if (qemu_log_enabled()) { 368 qemu_log_mask(CPU_LOG_MMU, "no BAT match for " 369 TARGET_FMT_lx ":\n", virtual); 370 for (i = 0; i < 4; i++) { 371 BATu = &BATut[i]; 372 BATl = &BATlt[i]; 373 BEPIu = *BATu & 0xF0000000; 374 BEPIl = *BATu & 0x0FFE0000; 375 bl = (*BATu & 0x00001FFC) << 15; 376 qemu_log_mask(CPU_LOG_MMU, "%s: %cBAT%d v " TARGET_FMT_lx 377 " BATu " TARGET_FMT_lx " BATl " TARGET_FMT_lx 378 "\n\t" TARGET_FMT_lx " " TARGET_FMT_lx " " 379 TARGET_FMT_lx "\n", __func__, ifetch ? 'I' : 'D', 380 i, virtual, *BATu, *BATl, BEPIu, BEPIl, bl); 381 } 382 } 383 } 384 /* No hit */ 385 return ret; 386 } 387 388 static int mmu6xx_get_physical_address(CPUPPCState *env, mmu_ctx_t *ctx, 389 target_ulong eaddr, 390 MMUAccessType access_type, int type) 391 { 392 PowerPCCPU *cpu = env_archcpu(env); 393 hwaddr hash; 394 target_ulong vsid, sr, pgidx; 395 int ds, target_page_bits; 396 bool pr; 397 398 /* First try to find a BAT entry if there are any */ 399 if (env->nb_BATs && get_bat_6xx_tlb(env, ctx, eaddr, access_type) == 0) { 400 return 0; 401 } 402 403 /* Perform segment based translation when no BATs matched */ 404 pr = FIELD_EX64(env->msr, MSR, PR); 405 ctx->eaddr = eaddr; 406 407 sr = env->sr[eaddr >> 28]; 408 ctx->key = (((sr & 0x20000000) && pr) || 409 ((sr & 0x40000000) && !pr)) ? 1 : 0; 410 ds = sr & 0x80000000 ? 1 : 0; 411 ctx->nx = sr & 0x10000000 ? 1 : 0; 412 vsid = sr & 0x00FFFFFF; 413 target_page_bits = TARGET_PAGE_BITS; 414 qemu_log_mask(CPU_LOG_MMU, 415 "Check segment v=" TARGET_FMT_lx " %d " TARGET_FMT_lx 416 " nip=" TARGET_FMT_lx " lr=" TARGET_FMT_lx 417 " ir=%d dr=%d pr=%d %d t=%d\n", 418 eaddr, (int)(eaddr >> 28), sr, env->nip, env->lr, 419 (int)FIELD_EX64(env->msr, MSR, IR), 420 (int)FIELD_EX64(env->msr, MSR, DR), pr ? 1 : 0, 421 access_type == MMU_DATA_STORE, type); 422 pgidx = (eaddr & ~SEGMENT_MASK_256M) >> target_page_bits; 423 hash = vsid ^ pgidx; 424 ctx->ptem = (vsid << 7) | (pgidx >> 10); 425 426 qemu_log_mask(CPU_LOG_MMU, "pte segment: key=%d ds %d nx %d vsid " 427 TARGET_FMT_lx "\n", ctx->key, ds, ctx->nx, vsid); 428 if (!ds) { 429 /* Check if instruction fetch is allowed, if needed */ 430 if (type == ACCESS_CODE && ctx->nx) { 431 qemu_log_mask(CPU_LOG_MMU, "No access allowed\n"); 432 return -3; 433 } 434 /* Page address translation */ 435 qemu_log_mask(CPU_LOG_MMU, "htab_base " HWADDR_FMT_plx " htab_mask " 436 HWADDR_FMT_plx " hash " HWADDR_FMT_plx "\n", 437 ppc_hash32_hpt_base(cpu), ppc_hash32_hpt_mask(cpu), hash); 438 ctx->hash[0] = hash; 439 ctx->hash[1] = ~hash; 440 441 /* Initialize real address with an invalid value */ 442 ctx->raddr = (hwaddr)-1ULL; 443 /* Software TLB search */ 444 return ppc6xx_tlb_check(env, ctx, eaddr, access_type); 445 } 446 447 /* Direct-store segment : absolutely *BUGGY* for now */ 448 qemu_log_mask(CPU_LOG_MMU, "direct store...\n"); 449 switch (type) { 450 case ACCESS_INT: 451 /* Integer load/store : only access allowed */ 452 break; 453 case ACCESS_CODE: 454 /* No code fetch is allowed in direct-store areas */ 455 return -4; 456 case ACCESS_FLOAT: 457 /* Floating point load/store */ 458 return -4; 459 case ACCESS_RES: 460 /* lwarx, ldarx or srwcx. */ 461 return -4; 462 case ACCESS_CACHE: 463 /* 464 * dcba, dcbt, dcbtst, dcbf, dcbi, dcbst, dcbz, or icbi 465 * 466 * Should make the instruction do no-op. As it already do 467 * no-op, it's quite easy :-) 468 */ 469 ctx->raddr = eaddr; 470 return 0; 471 case ACCESS_EXT: 472 /* eciwx or ecowx */ 473 return -4; 474 default: 475 qemu_log_mask(CPU_LOG_MMU, "ERROR: instruction should not need address" 476 " translation\n"); 477 return -4; 478 } 479 if ((access_type == MMU_DATA_STORE || ctx->key != 1) && 480 (access_type == MMU_DATA_LOAD || ctx->key != 0)) { 481 ctx->raddr = eaddr; 482 return 2; 483 } 484 return -2; 485 } 486 487 /* Generic TLB check function for embedded PowerPC implementations */ 488 static bool ppcemb_tlb_check(CPUPPCState *env, ppcemb_tlb_t *tlb, 489 hwaddr *raddrp, 490 target_ulong address, uint32_t pid, int i) 491 { 492 target_ulong mask; 493 494 /* Check valid flag */ 495 if (!(tlb->prot & PAGE_VALID)) { 496 return false; 497 } 498 mask = ~(tlb->size - 1); 499 qemu_log_mask(CPU_LOG_MMU, "%s: TLB %d address " TARGET_FMT_lx 500 " PID %u <=> " TARGET_FMT_lx " " TARGET_FMT_lx " %u %x\n", 501 __func__, i, address, pid, tlb->EPN, 502 mask, (uint32_t)tlb->PID, tlb->prot); 503 /* Check PID */ 504 if (tlb->PID != 0 && tlb->PID != pid) { 505 return false; 506 } 507 /* Check effective address */ 508 if ((address & mask) != tlb->EPN) { 509 return false; 510 } 511 *raddrp = (tlb->RPN & mask) | (address & ~mask); 512 return true; 513 } 514 515 /* Generic TLB search function for PowerPC embedded implementations */ 516 int ppcemb_tlb_search(CPUPPCState *env, target_ulong address, uint32_t pid) 517 { 518 ppcemb_tlb_t *tlb; 519 hwaddr raddr; 520 int i; 521 522 for (i = 0; i < env->nb_tlb; i++) { 523 tlb = &env->tlb.tlbe[i]; 524 if (ppcemb_tlb_check(env, tlb, &raddr, address, pid, i)) { 525 return i; 526 } 527 } 528 return -1; 529 } 530 531 static int mmu40x_get_physical_address(CPUPPCState *env, hwaddr *raddr, 532 int *prot, target_ulong address, 533 MMUAccessType access_type) 534 { 535 ppcemb_tlb_t *tlb; 536 int i, ret, zsel, zpr, pr; 537 538 ret = -1; 539 pr = FIELD_EX64(env->msr, MSR, PR); 540 for (i = 0; i < env->nb_tlb; i++) { 541 tlb = &env->tlb.tlbe[i]; 542 if (!ppcemb_tlb_check(env, tlb, raddr, address, 543 env->spr[SPR_40x_PID], i)) { 544 continue; 545 } 546 zsel = (tlb->attr >> 4) & 0xF; 547 zpr = (env->spr[SPR_40x_ZPR] >> (30 - (2 * zsel))) & 0x3; 548 qemu_log_mask(CPU_LOG_MMU, 549 "%s: TLB %d zsel %d zpr %d ty %d attr %08x\n", 550 __func__, i, zsel, zpr, access_type, tlb->attr); 551 /* Check execute enable bit */ 552 switch (zpr) { 553 case 0x2: 554 if (pr != 0) { 555 goto check_perms; 556 } 557 /* fall through */ 558 case 0x3: 559 /* All accesses granted */ 560 *prot = PAGE_RWX; 561 ret = 0; 562 break; 563 564 case 0x0: 565 if (pr != 0) { 566 /* Raise Zone protection fault. */ 567 env->spr[SPR_40x_ESR] = 1 << 22; 568 *prot = 0; 569 ret = -2; 570 break; 571 } 572 /* fall through */ 573 case 0x1: 574 check_perms: 575 /* Check from TLB entry */ 576 *prot = tlb->prot; 577 if (check_prot_access_type(*prot, access_type)) { 578 ret = 0; 579 } else { 580 env->spr[SPR_40x_ESR] = 0; 581 ret = -2; 582 } 583 break; 584 } 585 } 586 qemu_log_mask(CPU_LOG_MMU, "%s: access %s " TARGET_FMT_lx " => " 587 HWADDR_FMT_plx " %d %d\n", __func__, 588 ret < 0 ? "refused" : "granted", address, 589 ret < 0 ? 0 : *raddr, *prot, ret); 590 591 return ret; 592 } 593 594 static bool mmubooke_check_pid(CPUPPCState *env, ppcemb_tlb_t *tlb, 595 hwaddr *raddr, target_ulong addr, int i) 596 { 597 if (ppcemb_tlb_check(env, tlb, raddr, addr, env->spr[SPR_BOOKE_PID], i)) { 598 if (!env->nb_pids) { 599 /* Extend the physical address to 36 bits */ 600 *raddr |= (uint64_t)(tlb->RPN & 0xF) << 32; 601 } 602 return true; 603 } else if (!env->nb_pids) { 604 return false; 605 } 606 if (env->spr[SPR_BOOKE_PID1] && 607 ppcemb_tlb_check(env, tlb, raddr, addr, env->spr[SPR_BOOKE_PID1], i)) { 608 return true; 609 } 610 if (env->spr[SPR_BOOKE_PID2] && 611 ppcemb_tlb_check(env, tlb, raddr, addr, env->spr[SPR_BOOKE_PID2], i)) { 612 return true; 613 } 614 return false; 615 } 616 617 static int mmubooke_check_tlb(CPUPPCState *env, ppcemb_tlb_t *tlb, 618 hwaddr *raddr, int *prot, target_ulong address, 619 MMUAccessType access_type, int i) 620 { 621 if (!mmubooke_check_pid(env, tlb, raddr, address, i)) { 622 qemu_log_mask(CPU_LOG_MMU, "%s: TLB entry not found\n", __func__); 623 return -1; 624 } 625 626 /* Check the address space */ 627 if ((access_type == MMU_INST_FETCH ? 628 FIELD_EX64(env->msr, MSR, IR) : 629 FIELD_EX64(env->msr, MSR, DR)) != (tlb->attr & 1)) { 630 qemu_log_mask(CPU_LOG_MMU, "%s: AS doesn't match\n", __func__); 631 return -1; 632 } 633 634 if (FIELD_EX64(env->msr, MSR, PR)) { 635 *prot = tlb->prot & 0xF; 636 } else { 637 *prot = (tlb->prot >> 4) & 0xF; 638 } 639 if (check_prot_access_type(*prot, access_type)) { 640 qemu_log_mask(CPU_LOG_MMU, "%s: good TLB!\n", __func__); 641 return 0; 642 } 643 644 qemu_log_mask(CPU_LOG_MMU, "%s: no prot match: %x\n", __func__, *prot); 645 return access_type == MMU_INST_FETCH ? -3 : -2; 646 } 647 648 static int mmubooke_get_physical_address(CPUPPCState *env, hwaddr *raddr, 649 int *prot, target_ulong address, 650 MMUAccessType access_type) 651 { 652 ppcemb_tlb_t *tlb; 653 int i, ret = -1; 654 655 for (i = 0; i < env->nb_tlb; i++) { 656 tlb = &env->tlb.tlbe[i]; 657 ret = mmubooke_check_tlb(env, tlb, raddr, prot, address, 658 access_type, i); 659 if (ret != -1) { 660 break; 661 } 662 } 663 qemu_log_mask(CPU_LOG_MMU, 664 "%s: access %s " TARGET_FMT_lx " => " HWADDR_FMT_plx 665 " %d %d\n", __func__, ret < 0 ? "refused" : "granted", 666 address, ret < 0 ? -1 : *raddr, ret == -1 ? 0 : *prot, ret); 667 return ret; 668 } 669 670 hwaddr booke206_tlb_to_page_size(CPUPPCState *env, ppcmas_tlb_t *tlb) 671 { 672 int tlbm_size; 673 674 tlbm_size = (tlb->mas1 & MAS1_TSIZE_MASK) >> MAS1_TSIZE_SHIFT; 675 676 return 1024ULL << tlbm_size; 677 } 678 679 /* TLB check function for MAS based SoftTLBs */ 680 int ppcmas_tlb_check(CPUPPCState *env, ppcmas_tlb_t *tlb, hwaddr *raddrp, 681 target_ulong address, uint32_t pid) 682 { 683 hwaddr mask; 684 uint32_t tlb_pid; 685 686 if (!FIELD_EX64(env->msr, MSR, CM)) { 687 /* In 32bit mode we can only address 32bit EAs */ 688 address = (uint32_t)address; 689 } 690 691 /* Check valid flag */ 692 if (!(tlb->mas1 & MAS1_VALID)) { 693 return -1; 694 } 695 696 mask = ~(booke206_tlb_to_page_size(env, tlb) - 1); 697 qemu_log_mask(CPU_LOG_MMU, "%s: TLB ADDR=0x" TARGET_FMT_lx 698 " PID=0x%x MAS1=0x%x MAS2=0x%" PRIx64 " mask=0x%" 699 HWADDR_PRIx " MAS7_3=0x%" PRIx64 " MAS8=0x%" PRIx32 "\n", 700 __func__, address, pid, tlb->mas1, tlb->mas2, mask, 701 tlb->mas7_3, tlb->mas8); 702 703 /* Check PID */ 704 tlb_pid = (tlb->mas1 & MAS1_TID_MASK) >> MAS1_TID_SHIFT; 705 if (tlb_pid != 0 && tlb_pid != pid) { 706 return -1; 707 } 708 709 /* Check effective address */ 710 if ((address & mask) != (tlb->mas2 & MAS2_EPN_MASK)) { 711 return -1; 712 } 713 714 if (raddrp) { 715 *raddrp = (tlb->mas7_3 & mask) | (address & ~mask); 716 } 717 718 return 0; 719 } 720 721 static bool is_epid_mmu(int mmu_idx) 722 { 723 return mmu_idx == PPC_TLB_EPID_STORE || mmu_idx == PPC_TLB_EPID_LOAD; 724 } 725 726 static uint32_t mmubooke206_esr(int mmu_idx, MMUAccessType access_type) 727 { 728 uint32_t esr = 0; 729 if (access_type == MMU_DATA_STORE) { 730 esr |= ESR_ST; 731 } 732 if (is_epid_mmu(mmu_idx)) { 733 esr |= ESR_EPID; 734 } 735 return esr; 736 } 737 738 /* 739 * Get EPID register given the mmu_idx. If this is regular load, 740 * construct the EPID access bits from current processor state 741 * 742 * Get the effective AS and PR bits and the PID. The PID is returned 743 * only if EPID load is requested, otherwise the caller must detect 744 * the correct EPID. Return true if valid EPID is returned. 745 */ 746 static bool mmubooke206_get_as(CPUPPCState *env, 747 int mmu_idx, uint32_t *epid_out, 748 bool *as_out, bool *pr_out) 749 { 750 if (is_epid_mmu(mmu_idx)) { 751 uint32_t epidr; 752 if (mmu_idx == PPC_TLB_EPID_STORE) { 753 epidr = env->spr[SPR_BOOKE_EPSC]; 754 } else { 755 epidr = env->spr[SPR_BOOKE_EPLC]; 756 } 757 *epid_out = (epidr & EPID_EPID) >> EPID_EPID_SHIFT; 758 *as_out = !!(epidr & EPID_EAS); 759 *pr_out = !!(epidr & EPID_EPR); 760 return true; 761 } else { 762 *as_out = FIELD_EX64(env->msr, MSR, DS); 763 *pr_out = FIELD_EX64(env->msr, MSR, PR); 764 return false; 765 } 766 } 767 768 /* Check if the tlb found by hashing really matches */ 769 static int mmubooke206_check_tlb(CPUPPCState *env, ppcmas_tlb_t *tlb, 770 hwaddr *raddr, int *prot, 771 target_ulong address, 772 MMUAccessType access_type, int mmu_idx) 773 { 774 uint32_t epid; 775 bool as, pr; 776 bool use_epid = mmubooke206_get_as(env, mmu_idx, &epid, &as, &pr); 777 778 if (!use_epid) { 779 if (ppcmas_tlb_check(env, tlb, raddr, address, 780 env->spr[SPR_BOOKE_PID]) >= 0) { 781 goto found_tlb; 782 } 783 784 if (env->spr[SPR_BOOKE_PID1] && 785 ppcmas_tlb_check(env, tlb, raddr, address, 786 env->spr[SPR_BOOKE_PID1]) >= 0) { 787 goto found_tlb; 788 } 789 790 if (env->spr[SPR_BOOKE_PID2] && 791 ppcmas_tlb_check(env, tlb, raddr, address, 792 env->spr[SPR_BOOKE_PID2]) >= 0) { 793 goto found_tlb; 794 } 795 } else { 796 if (ppcmas_tlb_check(env, tlb, raddr, address, epid) >= 0) { 797 goto found_tlb; 798 } 799 } 800 801 qemu_log_mask(CPU_LOG_MMU, "%s: No TLB entry found for effective address " 802 "0x" TARGET_FMT_lx "\n", __func__, address); 803 return -1; 804 805 found_tlb: 806 807 /* Check the address space and permissions */ 808 if (access_type == MMU_INST_FETCH) { 809 /* There is no way to fetch code using epid load */ 810 assert(!use_epid); 811 as = FIELD_EX64(env->msr, MSR, IR); 812 } 813 814 if (as != ((tlb->mas1 & MAS1_TS) >> MAS1_TS_SHIFT)) { 815 qemu_log_mask(CPU_LOG_MMU, "%s: AS doesn't match\n", __func__); 816 return -1; 817 } 818 819 *prot = 0; 820 if (pr) { 821 if (tlb->mas7_3 & MAS3_UR) { 822 *prot |= PAGE_READ; 823 } 824 if (tlb->mas7_3 & MAS3_UW) { 825 *prot |= PAGE_WRITE; 826 } 827 if (tlb->mas7_3 & MAS3_UX) { 828 *prot |= PAGE_EXEC; 829 } 830 } else { 831 if (tlb->mas7_3 & MAS3_SR) { 832 *prot |= PAGE_READ; 833 } 834 if (tlb->mas7_3 & MAS3_SW) { 835 *prot |= PAGE_WRITE; 836 } 837 if (tlb->mas7_3 & MAS3_SX) { 838 *prot |= PAGE_EXEC; 839 } 840 } 841 if (check_prot_access_type(*prot, access_type)) { 842 qemu_log_mask(CPU_LOG_MMU, "%s: good TLB!\n", __func__); 843 return 0; 844 } 845 846 qemu_log_mask(CPU_LOG_MMU, "%s: no prot match: %x\n", __func__, *prot); 847 return access_type == MMU_INST_FETCH ? -3 : -2; 848 } 849 850 static int mmubooke206_get_physical_address(CPUPPCState *env, hwaddr *raddr, 851 int *prot, target_ulong address, 852 MMUAccessType access_type, 853 int mmu_idx) 854 { 855 ppcmas_tlb_t *tlb; 856 int i, j, ret = -1; 857 858 for (i = 0; i < BOOKE206_MAX_TLBN; i++) { 859 int ways = booke206_tlb_ways(env, i); 860 for (j = 0; j < ways; j++) { 861 tlb = booke206_get_tlbm(env, i, address, j); 862 if (!tlb) { 863 continue; 864 } 865 ret = mmubooke206_check_tlb(env, tlb, raddr, prot, address, 866 access_type, mmu_idx); 867 if (ret != -1) { 868 goto found_tlb; 869 } 870 } 871 } 872 873 found_tlb: 874 875 qemu_log_mask(CPU_LOG_MMU, "%s: access %s " TARGET_FMT_lx " => " 876 HWADDR_FMT_plx " %d %d\n", __func__, 877 ret < 0 ? "refused" : "granted", address, 878 ret < 0 ? -1 : *raddr, ret == -1 ? 0 : *prot, ret); 879 return ret; 880 } 881 882 static const char *book3e_tsize_to_str[32] = { 883 "1K", "2K", "4K", "8K", "16K", "32K", "64K", "128K", "256K", "512K", 884 "1M", "2M", "4M", "8M", "16M", "32M", "64M", "128M", "256M", "512M", 885 "1G", "2G", "4G", "8G", "16G", "32G", "64G", "128G", "256G", "512G", 886 "1T", "2T" 887 }; 888 889 static void mmubooke_dump_mmu(CPUPPCState *env) 890 { 891 ppcemb_tlb_t *entry; 892 int i; 893 894 #ifdef CONFIG_KVM 895 if (kvm_enabled() && !env->kvm_sw_tlb) { 896 qemu_printf("Cannot access KVM TLB\n"); 897 return; 898 } 899 #endif 900 901 qemu_printf("\nTLB:\n"); 902 qemu_printf("Effective Physical Size PID Prot " 903 "Attr\n"); 904 905 entry = &env->tlb.tlbe[0]; 906 for (i = 0; i < env->nb_tlb; i++, entry++) { 907 hwaddr ea, pa; 908 target_ulong mask; 909 uint64_t size = (uint64_t)entry->size; 910 char size_buf[20]; 911 912 /* Check valid flag */ 913 if (!(entry->prot & PAGE_VALID)) { 914 continue; 915 } 916 917 mask = ~(entry->size - 1); 918 ea = entry->EPN & mask; 919 pa = entry->RPN & mask; 920 /* Extend the physical address to 36 bits */ 921 pa |= (hwaddr)(entry->RPN & 0xF) << 32; 922 if (size >= 1 * MiB) { 923 snprintf(size_buf, sizeof(size_buf), "%3" PRId64 "M", size / MiB); 924 } else { 925 snprintf(size_buf, sizeof(size_buf), "%3" PRId64 "k", size / KiB); 926 } 927 qemu_printf("0x%016" PRIx64 " 0x%016" PRIx64 " %s %-5u %08x %08x\n", 928 (uint64_t)ea, (uint64_t)pa, size_buf, (uint32_t)entry->PID, 929 entry->prot, entry->attr); 930 } 931 932 } 933 934 static void mmubooke206_dump_one_tlb(CPUPPCState *env, int tlbn, int offset, 935 int tlbsize) 936 { 937 ppcmas_tlb_t *entry; 938 int i; 939 940 qemu_printf("\nTLB%d:\n", tlbn); 941 qemu_printf("Effective Physical Size TID TS SRWX" 942 " URWX WIMGE U0123\n"); 943 944 entry = &env->tlb.tlbm[offset]; 945 for (i = 0; i < tlbsize; i++, entry++) { 946 hwaddr ea, pa, size; 947 int tsize; 948 949 if (!(entry->mas1 & MAS1_VALID)) { 950 continue; 951 } 952 953 tsize = (entry->mas1 & MAS1_TSIZE_MASK) >> MAS1_TSIZE_SHIFT; 954 size = 1024ULL << tsize; 955 ea = entry->mas2 & ~(size - 1); 956 pa = entry->mas7_3 & ~(size - 1); 957 958 qemu_printf("0x%016" PRIx64 " 0x%016" PRIx64 " %4s %-5u %1u S%c%c%c" 959 " U%c%c%c %c%c%c%c%c U%c%c%c%c\n", 960 (uint64_t)ea, (uint64_t)pa, 961 book3e_tsize_to_str[tsize], 962 (entry->mas1 & MAS1_TID_MASK) >> MAS1_TID_SHIFT, 963 (entry->mas1 & MAS1_TS) >> MAS1_TS_SHIFT, 964 entry->mas7_3 & MAS3_SR ? 'R' : '-', 965 entry->mas7_3 & MAS3_SW ? 'W' : '-', 966 entry->mas7_3 & MAS3_SX ? 'X' : '-', 967 entry->mas7_3 & MAS3_UR ? 'R' : '-', 968 entry->mas7_3 & MAS3_UW ? 'W' : '-', 969 entry->mas7_3 & MAS3_UX ? 'X' : '-', 970 entry->mas2 & MAS2_W ? 'W' : '-', 971 entry->mas2 & MAS2_I ? 'I' : '-', 972 entry->mas2 & MAS2_M ? 'M' : '-', 973 entry->mas2 & MAS2_G ? 'G' : '-', 974 entry->mas2 & MAS2_E ? 'E' : '-', 975 entry->mas7_3 & MAS3_U0 ? '0' : '-', 976 entry->mas7_3 & MAS3_U1 ? '1' : '-', 977 entry->mas7_3 & MAS3_U2 ? '2' : '-', 978 entry->mas7_3 & MAS3_U3 ? '3' : '-'); 979 } 980 } 981 982 static void mmubooke206_dump_mmu(CPUPPCState *env) 983 { 984 int offset = 0; 985 int i; 986 987 #ifdef CONFIG_KVM 988 if (kvm_enabled() && !env->kvm_sw_tlb) { 989 qemu_printf("Cannot access KVM TLB\n"); 990 return; 991 } 992 #endif 993 994 for (i = 0; i < BOOKE206_MAX_TLBN; i++) { 995 int size = booke206_tlb_size(env, i); 996 997 if (size == 0) { 998 continue; 999 } 1000 1001 mmubooke206_dump_one_tlb(env, i, offset, size); 1002 offset += size; 1003 } 1004 } 1005 1006 static void mmu6xx_dump_BATs(CPUPPCState *env, int type) 1007 { 1008 target_ulong *BATlt, *BATut, *BATu, *BATl; 1009 target_ulong BEPIl, BEPIu, bl; 1010 int i; 1011 1012 switch (type) { 1013 case ACCESS_CODE: 1014 BATlt = env->IBAT[1]; 1015 BATut = env->IBAT[0]; 1016 break; 1017 default: 1018 BATlt = env->DBAT[1]; 1019 BATut = env->DBAT[0]; 1020 break; 1021 } 1022 1023 for (i = 0; i < env->nb_BATs; i++) { 1024 BATu = &BATut[i]; 1025 BATl = &BATlt[i]; 1026 BEPIu = *BATu & 0xF0000000; 1027 BEPIl = *BATu & 0x0FFE0000; 1028 bl = (*BATu & 0x00001FFC) << 15; 1029 qemu_printf("%s BAT%d BATu " TARGET_FMT_lx 1030 " BATl " TARGET_FMT_lx "\n\t" TARGET_FMT_lx " " 1031 TARGET_FMT_lx " " TARGET_FMT_lx "\n", 1032 type == ACCESS_CODE ? "code" : "data", i, 1033 *BATu, *BATl, BEPIu, BEPIl, bl); 1034 } 1035 } 1036 1037 static void mmu6xx_dump_mmu(CPUPPCState *env) 1038 { 1039 PowerPCCPU *cpu = env_archcpu(env); 1040 ppc6xx_tlb_t *tlb; 1041 target_ulong sr; 1042 int type, way, entry, i; 1043 1044 qemu_printf("HTAB base = 0x%"HWADDR_PRIx"\n", ppc_hash32_hpt_base(cpu)); 1045 qemu_printf("HTAB mask = 0x%"HWADDR_PRIx"\n", ppc_hash32_hpt_mask(cpu)); 1046 1047 qemu_printf("\nSegment registers:\n"); 1048 for (i = 0; i < 32; i++) { 1049 sr = env->sr[i]; 1050 if (sr & 0x80000000) { 1051 qemu_printf("%02d T=%d Ks=%d Kp=%d BUID=0x%03x " 1052 "CNTLR_SPEC=0x%05x\n", i, 1053 sr & 0x80000000 ? 1 : 0, sr & 0x40000000 ? 1 : 0, 1054 sr & 0x20000000 ? 1 : 0, (uint32_t)((sr >> 20) & 0x1FF), 1055 (uint32_t)(sr & 0xFFFFF)); 1056 } else { 1057 qemu_printf("%02d T=%d Ks=%d Kp=%d N=%d VSID=0x%06x\n", i, 1058 sr & 0x80000000 ? 1 : 0, sr & 0x40000000 ? 1 : 0, 1059 sr & 0x20000000 ? 1 : 0, sr & 0x10000000 ? 1 : 0, 1060 (uint32_t)(sr & 0x00FFFFFF)); 1061 } 1062 } 1063 1064 qemu_printf("\nBATs:\n"); 1065 mmu6xx_dump_BATs(env, ACCESS_INT); 1066 mmu6xx_dump_BATs(env, ACCESS_CODE); 1067 1068 qemu_printf("\nTLBs [EPN EPN + SIZE]\n"); 1069 for (type = 0; type < 2; type++) { 1070 for (way = 0; way < env->nb_ways; way++) { 1071 for (entry = env->nb_tlb * type + env->tlb_per_way * way; 1072 entry < (env->nb_tlb * type + env->tlb_per_way * (way + 1)); 1073 entry++) { 1074 1075 tlb = &env->tlb.tlb6[entry]; 1076 qemu_printf("%s TLB %02d/%02d way:%d %s [" 1077 TARGET_FMT_lx " " TARGET_FMT_lx "]\n", 1078 type ? "code" : "data", entry % env->nb_tlb, 1079 env->nb_tlb, way, 1080 pte_is_valid(tlb->pte0) ? "valid" : "inval", 1081 tlb->EPN, tlb->EPN + TARGET_PAGE_SIZE); 1082 } 1083 } 1084 } 1085 } 1086 1087 void dump_mmu(CPUPPCState *env) 1088 { 1089 switch (env->mmu_model) { 1090 case POWERPC_MMU_BOOKE: 1091 mmubooke_dump_mmu(env); 1092 break; 1093 case POWERPC_MMU_BOOKE206: 1094 mmubooke206_dump_mmu(env); 1095 break; 1096 case POWERPC_MMU_SOFT_6xx: 1097 mmu6xx_dump_mmu(env); 1098 break; 1099 #if defined(TARGET_PPC64) 1100 case POWERPC_MMU_64B: 1101 case POWERPC_MMU_2_03: 1102 case POWERPC_MMU_2_06: 1103 case POWERPC_MMU_2_07: 1104 dump_slb(env_archcpu(env)); 1105 break; 1106 case POWERPC_MMU_3_00: 1107 if (ppc64_v3_radix(env_archcpu(env))) { 1108 qemu_log_mask(LOG_UNIMP, "%s: the PPC64 MMU is unsupported\n", 1109 __func__); 1110 } else { 1111 dump_slb(env_archcpu(env)); 1112 } 1113 break; 1114 #endif 1115 default: 1116 qemu_log_mask(LOG_UNIMP, "%s: unimplemented\n", __func__); 1117 } 1118 } 1119 1120 static void booke206_update_mas_tlb_miss(CPUPPCState *env, target_ulong address, 1121 MMUAccessType access_type, int mmu_idx) 1122 { 1123 uint32_t epid; 1124 bool as, pr; 1125 uint32_t missed_tid = 0; 1126 bool use_epid = mmubooke206_get_as(env, mmu_idx, &epid, &as, &pr); 1127 1128 if (access_type == MMU_INST_FETCH) { 1129 as = FIELD_EX64(env->msr, MSR, IR); 1130 } 1131 env->spr[SPR_BOOKE_MAS0] = env->spr[SPR_BOOKE_MAS4] & MAS4_TLBSELD_MASK; 1132 env->spr[SPR_BOOKE_MAS1] = env->spr[SPR_BOOKE_MAS4] & MAS4_TSIZED_MASK; 1133 env->spr[SPR_BOOKE_MAS2] = env->spr[SPR_BOOKE_MAS4] & MAS4_WIMGED_MASK; 1134 env->spr[SPR_BOOKE_MAS3] = 0; 1135 env->spr[SPR_BOOKE_MAS6] = 0; 1136 env->spr[SPR_BOOKE_MAS7] = 0; 1137 1138 /* AS */ 1139 if (as) { 1140 env->spr[SPR_BOOKE_MAS1] |= MAS1_TS; 1141 env->spr[SPR_BOOKE_MAS6] |= MAS6_SAS; 1142 } 1143 1144 env->spr[SPR_BOOKE_MAS1] |= MAS1_VALID; 1145 env->spr[SPR_BOOKE_MAS2] |= address & MAS2_EPN_MASK; 1146 1147 if (!use_epid) { 1148 switch (env->spr[SPR_BOOKE_MAS4] & MAS4_TIDSELD_PIDZ) { 1149 case MAS4_TIDSELD_PID0: 1150 missed_tid = env->spr[SPR_BOOKE_PID]; 1151 break; 1152 case MAS4_TIDSELD_PID1: 1153 missed_tid = env->spr[SPR_BOOKE_PID1]; 1154 break; 1155 case MAS4_TIDSELD_PID2: 1156 missed_tid = env->spr[SPR_BOOKE_PID2]; 1157 break; 1158 } 1159 env->spr[SPR_BOOKE_MAS6] |= env->spr[SPR_BOOKE_PID] << 16; 1160 } else { 1161 missed_tid = epid; 1162 env->spr[SPR_BOOKE_MAS6] |= missed_tid << 16; 1163 } 1164 env->spr[SPR_BOOKE_MAS1] |= (missed_tid << MAS1_TID_SHIFT); 1165 1166 1167 /* next victim logic */ 1168 env->spr[SPR_BOOKE_MAS0] |= env->last_way << MAS0_ESEL_SHIFT; 1169 env->last_way++; 1170 env->last_way &= booke206_tlb_ways(env, 0) - 1; 1171 env->spr[SPR_BOOKE_MAS0] |= env->last_way << MAS0_NV_SHIFT; 1172 } 1173 1174 static bool ppc_booke_xlate(PowerPCCPU *cpu, vaddr eaddr, 1175 MMUAccessType access_type, 1176 hwaddr *raddrp, int *psizep, int *protp, 1177 int mmu_idx, bool guest_visible) 1178 { 1179 CPUState *cs = CPU(cpu); 1180 CPUPPCState *env = &cpu->env; 1181 hwaddr raddr; 1182 int prot, ret; 1183 1184 if (env->mmu_model == POWERPC_MMU_BOOKE206) { 1185 ret = mmubooke206_get_physical_address(env, &raddr, &prot, eaddr, 1186 access_type, mmu_idx); 1187 } else { 1188 ret = mmubooke_get_physical_address(env, &raddr, &prot, eaddr, 1189 access_type); 1190 } 1191 if (ret == 0) { 1192 *raddrp = raddr; 1193 *protp = prot; 1194 *psizep = TARGET_PAGE_BITS; 1195 return true; 1196 } else if (!guest_visible) { 1197 return false; 1198 } 1199 1200 log_cpu_state_mask(CPU_LOG_MMU, cs, 0); 1201 env->error_code = 0; 1202 switch (ret) { 1203 case -1: 1204 /* No matches in page tables or TLB */ 1205 if (env->mmu_model == POWERPC_MMU_BOOKE206) { 1206 booke206_update_mas_tlb_miss(env, eaddr, access_type, mmu_idx); 1207 } 1208 cs->exception_index = (access_type == MMU_INST_FETCH) ? 1209 POWERPC_EXCP_ITLB : POWERPC_EXCP_DTLB; 1210 env->spr[SPR_BOOKE_DEAR] = eaddr; 1211 env->spr[SPR_BOOKE_ESR] = mmubooke206_esr(mmu_idx, access_type); 1212 break; 1213 case -2: 1214 /* Access rights violation */ 1215 cs->exception_index = (access_type == MMU_INST_FETCH) ? 1216 POWERPC_EXCP_ISI : POWERPC_EXCP_DSI; 1217 if (access_type != MMU_INST_FETCH) { 1218 env->spr[SPR_BOOKE_DEAR] = eaddr; 1219 env->spr[SPR_BOOKE_ESR] = mmubooke206_esr(mmu_idx, access_type); 1220 } 1221 break; 1222 case -3: 1223 /* No execute protection violation */ 1224 cs->exception_index = POWERPC_EXCP_ISI; 1225 env->spr[SPR_BOOKE_ESR] = 0; 1226 break; 1227 } 1228 1229 return false; 1230 } 1231 1232 static bool ppc_real_mode_xlate(PowerPCCPU *cpu, vaddr eaddr, 1233 MMUAccessType access_type, 1234 hwaddr *raddrp, int *psizep, int *protp) 1235 { 1236 CPUPPCState *env = &cpu->env; 1237 1238 if (access_type == MMU_INST_FETCH ? !FIELD_EX64(env->msr, MSR, IR) 1239 : !FIELD_EX64(env->msr, MSR, DR)) { 1240 *raddrp = eaddr; 1241 *protp = PAGE_RWX; 1242 *psizep = TARGET_PAGE_BITS; 1243 return true; 1244 } else if (env->mmu_model == POWERPC_MMU_REAL) { 1245 cpu_abort(CPU(cpu), "PowerPC in real mode shold not do translation\n"); 1246 } 1247 return false; 1248 } 1249 1250 static bool ppc_40x_xlate(PowerPCCPU *cpu, vaddr eaddr, 1251 MMUAccessType access_type, 1252 hwaddr *raddrp, int *psizep, int *protp, 1253 int mmu_idx, bool guest_visible) 1254 { 1255 CPUState *cs = CPU(cpu); 1256 CPUPPCState *env = &cpu->env; 1257 int ret; 1258 1259 if (ppc_real_mode_xlate(cpu, eaddr, access_type, raddrp, psizep, protp)) { 1260 return true; 1261 } 1262 1263 ret = mmu40x_get_physical_address(env, raddrp, protp, eaddr, access_type); 1264 if (ret == 0) { 1265 *psizep = TARGET_PAGE_BITS; 1266 return true; 1267 } else if (!guest_visible) { 1268 return false; 1269 } 1270 1271 log_cpu_state_mask(CPU_LOG_MMU, cs, 0); 1272 if (access_type == MMU_INST_FETCH) { 1273 switch (ret) { 1274 case -1: 1275 /* No matches in page tables or TLB */ 1276 cs->exception_index = POWERPC_EXCP_ITLB; 1277 env->error_code = 0; 1278 env->spr[SPR_40x_DEAR] = eaddr; 1279 env->spr[SPR_40x_ESR] = 0x00000000; 1280 break; 1281 case -2: 1282 /* Access rights violation */ 1283 cs->exception_index = POWERPC_EXCP_ISI; 1284 env->error_code = 0x08000000; 1285 break; 1286 default: 1287 g_assert_not_reached(); 1288 } 1289 } else { 1290 switch (ret) { 1291 case -1: 1292 /* No matches in page tables or TLB */ 1293 cs->exception_index = POWERPC_EXCP_DTLB; 1294 env->error_code = 0; 1295 env->spr[SPR_40x_DEAR] = eaddr; 1296 if (access_type == MMU_DATA_STORE) { 1297 env->spr[SPR_40x_ESR] = 0x00800000; 1298 } else { 1299 env->spr[SPR_40x_ESR] = 0x00000000; 1300 } 1301 break; 1302 case -2: 1303 /* Access rights violation */ 1304 cs->exception_index = POWERPC_EXCP_DSI; 1305 env->error_code = 0; 1306 env->spr[SPR_40x_DEAR] = eaddr; 1307 if (access_type == MMU_DATA_STORE) { 1308 env->spr[SPR_40x_ESR] |= 0x00800000; 1309 } 1310 break; 1311 default: 1312 g_assert_not_reached(); 1313 } 1314 } 1315 return false; 1316 } 1317 1318 static bool ppc_6xx_xlate(PowerPCCPU *cpu, vaddr eaddr, 1319 MMUAccessType access_type, 1320 hwaddr *raddrp, int *psizep, int *protp, 1321 int mmu_idx, bool guest_visible) 1322 { 1323 CPUState *cs = CPU(cpu); 1324 CPUPPCState *env = &cpu->env; 1325 mmu_ctx_t ctx; 1326 int type; 1327 int ret; 1328 1329 if (ppc_real_mode_xlate(cpu, eaddr, access_type, raddrp, psizep, protp)) { 1330 return true; 1331 } 1332 1333 if (access_type == MMU_INST_FETCH) { 1334 /* code access */ 1335 type = ACCESS_CODE; 1336 } else if (guest_visible) { 1337 /* data access */ 1338 type = env->access_type; 1339 } else { 1340 type = ACCESS_INT; 1341 } 1342 1343 ctx.prot = 0; 1344 ctx.hash[0] = 0; 1345 ctx.hash[1] = 0; 1346 ret = mmu6xx_get_physical_address(env, &ctx, eaddr, access_type, type); 1347 if (ret == 0) { 1348 *raddrp = ctx.raddr; 1349 *protp = ctx.prot; 1350 *psizep = TARGET_PAGE_BITS; 1351 return true; 1352 } else if (!guest_visible) { 1353 return false; 1354 } 1355 1356 log_cpu_state_mask(CPU_LOG_MMU, cs, 0); 1357 if (type == ACCESS_CODE) { 1358 switch (ret) { 1359 case -1: 1360 /* No matches in page tables or TLB */ 1361 cs->exception_index = POWERPC_EXCP_IFTLB; 1362 env->error_code = 1 << 18; 1363 env->spr[SPR_IMISS] = eaddr; 1364 env->spr[SPR_ICMP] = 0x80000000 | ctx.ptem; 1365 goto tlb_miss; 1366 case -2: 1367 /* Access rights violation */ 1368 cs->exception_index = POWERPC_EXCP_ISI; 1369 env->error_code = 0x08000000; 1370 break; 1371 case -3: 1372 /* No execute protection violation */ 1373 cs->exception_index = POWERPC_EXCP_ISI; 1374 env->error_code = 0x10000000; 1375 break; 1376 case -4: 1377 /* Direct store exception */ 1378 /* No code fetch is allowed in direct-store areas */ 1379 cs->exception_index = POWERPC_EXCP_ISI; 1380 env->error_code = 0x10000000; 1381 break; 1382 } 1383 } else { 1384 switch (ret) { 1385 case -1: 1386 /* No matches in page tables or TLB */ 1387 if (access_type == MMU_DATA_STORE) { 1388 cs->exception_index = POWERPC_EXCP_DSTLB; 1389 env->error_code = 1 << 16; 1390 } else { 1391 cs->exception_index = POWERPC_EXCP_DLTLB; 1392 env->error_code = 0; 1393 } 1394 env->spr[SPR_DMISS] = eaddr; 1395 env->spr[SPR_DCMP] = 0x80000000 | ctx.ptem; 1396 tlb_miss: 1397 env->error_code |= ctx.key << 19; 1398 env->spr[SPR_HASH1] = ppc_hash32_hpt_base(cpu) + 1399 get_pteg_offset32(cpu, ctx.hash[0]); 1400 env->spr[SPR_HASH2] = ppc_hash32_hpt_base(cpu) + 1401 get_pteg_offset32(cpu, ctx.hash[1]); 1402 break; 1403 case -2: 1404 /* Access rights violation */ 1405 cs->exception_index = POWERPC_EXCP_DSI; 1406 env->error_code = 0; 1407 env->spr[SPR_DAR] = eaddr; 1408 if (access_type == MMU_DATA_STORE) { 1409 env->spr[SPR_DSISR] = 0x0A000000; 1410 } else { 1411 env->spr[SPR_DSISR] = 0x08000000; 1412 } 1413 break; 1414 case -4: 1415 /* Direct store exception */ 1416 switch (type) { 1417 case ACCESS_FLOAT: 1418 /* Floating point load/store */ 1419 cs->exception_index = POWERPC_EXCP_ALIGN; 1420 env->error_code = POWERPC_EXCP_ALIGN_FP; 1421 env->spr[SPR_DAR] = eaddr; 1422 break; 1423 case ACCESS_RES: 1424 /* lwarx, ldarx or stwcx. */ 1425 cs->exception_index = POWERPC_EXCP_DSI; 1426 env->error_code = 0; 1427 env->spr[SPR_DAR] = eaddr; 1428 if (access_type == MMU_DATA_STORE) { 1429 env->spr[SPR_DSISR] = 0x06000000; 1430 } else { 1431 env->spr[SPR_DSISR] = 0x04000000; 1432 } 1433 break; 1434 case ACCESS_EXT: 1435 /* eciwx or ecowx */ 1436 cs->exception_index = POWERPC_EXCP_DSI; 1437 env->error_code = 0; 1438 env->spr[SPR_DAR] = eaddr; 1439 if (access_type == MMU_DATA_STORE) { 1440 env->spr[SPR_DSISR] = 0x06100000; 1441 } else { 1442 env->spr[SPR_DSISR] = 0x04100000; 1443 } 1444 break; 1445 default: 1446 printf("DSI: invalid exception (%d)\n", ret); 1447 cs->exception_index = POWERPC_EXCP_PROGRAM; 1448 env->error_code = POWERPC_EXCP_INVAL | POWERPC_EXCP_INVAL_INVAL; 1449 env->spr[SPR_DAR] = eaddr; 1450 break; 1451 } 1452 break; 1453 } 1454 } 1455 return false; 1456 } 1457 1458 /*****************************************************************************/ 1459 1460 bool ppc_xlate(PowerPCCPU *cpu, vaddr eaddr, MMUAccessType access_type, 1461 hwaddr *raddrp, int *psizep, int *protp, 1462 int mmu_idx, bool guest_visible) 1463 { 1464 switch (cpu->env.mmu_model) { 1465 #if defined(TARGET_PPC64) 1466 case POWERPC_MMU_3_00: 1467 if (ppc64_v3_radix(cpu)) { 1468 return ppc_radix64_xlate(cpu, eaddr, access_type, raddrp, 1469 psizep, protp, mmu_idx, guest_visible); 1470 } 1471 /* fall through */ 1472 case POWERPC_MMU_64B: 1473 case POWERPC_MMU_2_03: 1474 case POWERPC_MMU_2_06: 1475 case POWERPC_MMU_2_07: 1476 return ppc_hash64_xlate(cpu, eaddr, access_type, 1477 raddrp, psizep, protp, mmu_idx, guest_visible); 1478 #endif 1479 1480 case POWERPC_MMU_32B: 1481 return ppc_hash32_xlate(cpu, eaddr, access_type, raddrp, 1482 psizep, protp, mmu_idx, guest_visible); 1483 case POWERPC_MMU_BOOKE: 1484 case POWERPC_MMU_BOOKE206: 1485 return ppc_booke_xlate(cpu, eaddr, access_type, raddrp, 1486 psizep, protp, mmu_idx, guest_visible); 1487 case POWERPC_MMU_SOFT_4xx: 1488 return ppc_40x_xlate(cpu, eaddr, access_type, raddrp, 1489 psizep, protp, mmu_idx, guest_visible); 1490 case POWERPC_MMU_SOFT_6xx: 1491 return ppc_6xx_xlate(cpu, eaddr, access_type, raddrp, 1492 psizep, protp, mmu_idx, guest_visible); 1493 case POWERPC_MMU_REAL: 1494 return ppc_real_mode_xlate(cpu, eaddr, access_type, raddrp, psizep, 1495 protp); 1496 case POWERPC_MMU_MPC8xx: 1497 cpu_abort(env_cpu(&cpu->env), "MPC8xx MMU model is not implemented\n"); 1498 default: 1499 cpu_abort(CPU(cpu), "Unknown or invalid MMU model\n"); 1500 } 1501 } 1502 1503 hwaddr ppc_cpu_get_phys_page_debug(CPUState *cs, vaddr addr) 1504 { 1505 PowerPCCPU *cpu = POWERPC_CPU(cs); 1506 hwaddr raddr; 1507 int s, p; 1508 1509 /* 1510 * Some MMUs have separate TLBs for code and data. If we only 1511 * try an MMU_DATA_LOAD, we may not be able to read instructions 1512 * mapped by code TLBs, so we also try a MMU_INST_FETCH. 1513 */ 1514 if (ppc_xlate(cpu, addr, MMU_DATA_LOAD, &raddr, &s, &p, 1515 ppc_env_mmu_index(&cpu->env, false), false) || 1516 ppc_xlate(cpu, addr, MMU_INST_FETCH, &raddr, &s, &p, 1517 ppc_env_mmu_index(&cpu->env, true), false)) { 1518 return raddr & TARGET_PAGE_MASK; 1519 } 1520 return -1; 1521 } 1522