Rev 1288 | Rev 1621 | Go to most recent revision | Show entire file | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed
| Rev 1288 | Rev 1411 | ||
|---|---|---|---|
| Line 427... | Line 427... | ||
| 427 | * @param istate Structure with saved interruption state. |
427 | * @param istate Structure with saved interruption state. |
| 428 | */ |
428 | */ |
| 429 | void alternate_instruction_tlb_fault(__u64 vector, istate_t *istate) |
429 | void alternate_instruction_tlb_fault(__u64 vector, istate_t *istate) |
| 430 | { |
430 | { |
| 431 | region_register rr; |
431 | region_register rr; |
| - | 432 | rid_t rid; |
|
| 432 | __address va; |
433 | __address va; |
| 433 | pte_t *t; |
434 | pte_t *t; |
| 434 | 435 | ||
| 435 | va = istate->cr_ifa; /* faulting address */ |
436 | va = istate->cr_ifa; /* faulting address */ |
| - | 437 | rr.word = rr_read(VA2VRN(va)); |
|
| - | 438 | rid = rr.map.rid; |
|
| - | 439 | ||
| 436 | page_table_lock(AS, true); |
440 | page_table_lock(AS, true); |
| 437 | t = page_mapping_find(AS, va); |
441 | t = page_mapping_find(AS, va); |
| 438 | if (t) { |
442 | if (t) { |
| 439 | /* |
443 | /* |
| 440 | * The mapping was found in software page hash table. |
444 | * The mapping was found in software page hash table. |
| Line 445... | Line 449... | ||
| 445 | } else { |
449 | } else { |
| 446 | /* |
450 | /* |
| 447 | * Forward the page fault to address space page fault handler. |
451 | * Forward the page fault to address space page fault handler. |
| 448 | */ |
452 | */ |
| 449 | page_table_unlock(AS, true); |
453 | page_table_unlock(AS, true); |
| 450 | if (as_page_fault(va, istate) == AS_PF_FAULT) { |
454 | if (as_page_fault(va, PF_ACCESS_EXEC, istate) == AS_PF_FAULT) { |
| 451 | panic("%s: va=%p, rid=%d, iip=%p\n", __FUNCTION__, istate->cr_ifa, rr.map.rid, istate->cr_iip); |
455 | panic("%s: va=%p, rid=%d, iip=%p\n", __FUNCTION__, va, rid, istate->cr_iip); |
| 452 | } |
456 | } |
| 453 | } |
457 | } |
| 454 | } |
458 | } |
| 455 | 459 | ||
| 456 | /** Data TLB fault handler for faults with VHPT turned off. |
460 | /** Data TLB fault handler for faults with VHPT turned off. |
| Line 491... | Line 495... | ||
| 491 | } else { |
495 | } else { |
| 492 | /* |
496 | /* |
| 493 | * Forward the page fault to address space page fault handler. |
497 | * Forward the page fault to address space page fault handler. |
| 494 | */ |
498 | */ |
| 495 | page_table_unlock(AS, true); |
499 | page_table_unlock(AS, true); |
| 496 | if (as_page_fault(va, istate) == AS_PF_FAULT) { |
500 | if (as_page_fault(va, PF_ACCESS_READ, istate) == AS_PF_FAULT) { |
| 497 | panic("%s: va=%p, rid=%d, iip=%p\n", __FUNCTION__, va, rid, istate->cr_iip); |
501 | panic("%s: va=%p, rid=%d, iip=%p\n", __FUNCTION__, va, rid, istate->cr_iip); |
| 498 | } |
502 | } |
| 499 | } |
503 | } |
| 500 | } |
504 | } |
| 501 | 505 | ||
| Line 516... | Line 520... | ||
| 516 | * @param vector Interruption vector. |
520 | * @param vector Interruption vector. |
| 517 | * @param istate Structure with saved interruption state. |
521 | * @param istate Structure with saved interruption state. |
| 518 | */ |
522 | */ |
| 519 | void data_dirty_bit_fault(__u64 vector, istate_t *istate) |
523 | void data_dirty_bit_fault(__u64 vector, istate_t *istate) |
| 520 | { |
524 | { |
| - | 525 | region_register rr; |
|
| - | 526 | rid_t rid; |
|
| - | 527 | __address va; |
|
| 521 | pte_t *t; |
528 | pte_t *t; |
| - | 529 | ||
| - | 530 | va = istate->cr_ifa; /* faulting address */ |
|
| - | 531 | rr.word = rr_read(VA2VRN(va)); |
|
| - | 532 | rid = rr.map.rid; |
|
| 522 | 533 | ||
| 523 | page_table_lock(AS, true); |
534 | page_table_lock(AS, true); |
| 524 | t = page_mapping_find(AS, istate->cr_ifa); |
535 | t = page_mapping_find(AS, va); |
| 525 | ASSERT(t && t->p); |
536 | ASSERT(t && t->p); |
| 526 | if (t && t->p) { |
537 | if (t && t->p && t->w) { |
| 527 | /* |
538 | /* |
| 528 | * Update the Dirty bit in page tables and reinsert |
539 | * Update the Dirty bit in page tables and reinsert |
| 529 | * the mapping into DTC. |
540 | * the mapping into DTC. |
| 530 | */ |
541 | */ |
| 531 | t->d = true; |
542 | t->d = true; |
| 532 | dtc_pte_copy(t); |
543 | dtc_pte_copy(t); |
| - | 544 | } else { |
|
| - | 545 | if (as_page_fault(va, PF_ACCESS_WRITE, istate) == AS_PF_FAULT) { |
|
| - | 546 | panic("%s: va=%p, rid=%d, iip=%p\n", __FUNCTION__, va, rid, istate->cr_iip); |
|
| - | 547 | t->d = true; |
|
| - | 548 | dtc_pte_copy(t); |
|
| - | 549 | } |
|
| 533 | } |
550 | } |
| 534 | page_table_unlock(AS, true); |
551 | page_table_unlock(AS, true); |
| 535 | } |
552 | } |
| 536 | 553 | ||
| 537 | /** Instruction access bit fault handler. |
554 | /** Instruction access bit fault handler. |
| Line 539... | Line 556... | ||
| 539 | * @param vector Interruption vector. |
556 | * @param vector Interruption vector. |
| 540 | * @param istate Structure with saved interruption state. |
557 | * @param istate Structure with saved interruption state. |
| 541 | */ |
558 | */ |
| 542 | void instruction_access_bit_fault(__u64 vector, istate_t *istate) |
559 | void instruction_access_bit_fault(__u64 vector, istate_t *istate) |
| 543 | { |
560 | { |
| - | 561 | region_register rr; |
|
| - | 562 | rid_t rid; |
|
| - | 563 | __address va; |
|
| 544 | pte_t *t; |
564 | pte_t *t; |
| - | 565 | ||
| - | 566 | va = istate->cr_ifa; /* faulting address */ |
|
| - | 567 | rr.word = rr_read(VA2VRN(va)); |
|
| - | 568 | rid = rr.map.rid; |
|
| 545 | 569 | ||
| 546 | page_table_lock(AS, true); |
570 | page_table_lock(AS, true); |
| 547 | t = page_mapping_find(AS, istate->cr_ifa); |
571 | t = page_mapping_find(AS, va); |
| 548 | ASSERT(t && t->p); |
572 | ASSERT(t && t->p); |
| 549 | if (t && t->p) { |
573 | if (t && t->p && t->x) { |
| 550 | /* |
574 | /* |
| 551 | * Update the Accessed bit in page tables and reinsert |
575 | * Update the Accessed bit in page tables and reinsert |
| 552 | * the mapping into ITC. |
576 | * the mapping into ITC. |
| 553 | */ |
577 | */ |
| 554 | t->a = true; |
578 | t->a = true; |
| 555 | itc_pte_copy(t); |
579 | itc_pte_copy(t); |
| - | 580 | } else { |
|
| - | 581 | if (as_page_fault(va, PF_ACCESS_EXEC, istate) == AS_PF_FAULT) { |
|
| - | 582 | panic("%s: va=%p, rid=%d, iip=%p\n", __FUNCTION__, va, rid, istate->cr_iip); |
|
| - | 583 | t->a = true; |
|
| - | 584 | itc_pte_copy(t); |
|
| - | 585 | } |
|
| 556 | } |
586 | } |
| 557 | page_table_unlock(AS, true); |
587 | page_table_unlock(AS, true); |
| 558 | } |
588 | } |
| 559 | 589 | ||
| 560 | /** Data access bit fault handler. |
590 | /** Data access bit fault handler. |
| Line 562... | Line 592... | ||
| 562 | * @param vector Interruption vector. |
592 | * @param vector Interruption vector. |
| 563 | * @param istate Structure with saved interruption state. |
593 | * @param istate Structure with saved interruption state. |
| 564 | */ |
594 | */ |
| 565 | void data_access_bit_fault(__u64 vector, istate_t *istate) |
595 | void data_access_bit_fault(__u64 vector, istate_t *istate) |
| 566 | { |
596 | { |
| - | 597 | region_register rr; |
|
| - | 598 | rid_t rid; |
|
| - | 599 | __address va; |
|
| 567 | pte_t *t; |
600 | pte_t *t; |
| 568 | 601 | ||
| - | 602 | va = istate->cr_ifa; /* faulting address */ |
|
| - | 603 | rr.word = rr_read(VA2VRN(va)); |
|
| - | 604 | rid = rr.map.rid; |
|
| - | 605 | ||
| 569 | page_table_lock(AS, true); |
606 | page_table_lock(AS, true); |
| 570 | t = page_mapping_find(AS, istate->cr_ifa); |
607 | t = page_mapping_find(AS, va); |
| 571 | ASSERT(t && t->p); |
608 | ASSERT(t && t->p); |
| 572 | if (t && t->p) { |
609 | if (t && t->p) { |
| 573 | /* |
610 | /* |
| 574 | * Update the Accessed bit in page tables and reinsert |
611 | * Update the Accessed bit in page tables and reinsert |
| 575 | * the mapping into DTC. |
612 | * the mapping into DTC. |
| 576 | */ |
613 | */ |
| 577 | t->a = true; |
614 | t->a = true; |
| 578 | dtc_pte_copy(t); |
615 | dtc_pte_copy(t); |
| - | 616 | } else { |
|
| - | 617 | if (as_page_fault(va, PF_ACCESS_READ, istate) == AS_PF_FAULT) { |
|
| - | 618 | panic("%s: va=%p, rid=%d, iip=%p\n", __FUNCTION__, va, rid, istate->cr_iip); |
|
| - | 619 | t->a = true; |
|
| - | 620 | itc_pte_copy(t); |
|
| - | 621 | } |
|
| 579 | } |
622 | } |
| 580 | page_table_unlock(AS, true); |
623 | page_table_unlock(AS, true); |
| 581 | } |
624 | } |
| 582 | 625 | ||
| 583 | /** Page not present fault handler. |
626 | /** Page not present fault handler. |
| Line 586... | Line 629... | ||
| 586 | * @param istate Structure with saved interruption state. |
629 | * @param istate Structure with saved interruption state. |
| 587 | */ |
630 | */ |
| 588 | void page_not_present(__u64 vector, istate_t *istate) |
631 | void page_not_present(__u64 vector, istate_t *istate) |
| 589 | { |
632 | { |
| 590 | region_register rr; |
633 | region_register rr; |
| - | 634 | rid_t rid; |
|
| 591 | __address va; |
635 | __address va; |
| 592 | pte_t *t; |
636 | pte_t *t; |
| 593 | 637 | ||
| 594 | va = istate->cr_ifa; /* faulting address */ |
638 | va = istate->cr_ifa; /* faulting address */ |
| - | 639 | rr.word = rr_read(VA2VRN(va)); |
|
| - | 640 | rid = rr.map.rid; |
|
| - | 641 | ||
| 595 | page_table_lock(AS, true); |
642 | page_table_lock(AS, true); |
| 596 | t = page_mapping_find(AS, va); |
643 | t = page_mapping_find(AS, va); |
| 597 | ASSERT(t); |
644 | ASSERT(t); |
| 598 | 645 | ||
| 599 | if (t->p) { |
646 | if (t->p) { |
| Line 606... | Line 653... | ||
| 606 | else |
653 | else |
| 607 | dtc_pte_copy(t); |
654 | dtc_pte_copy(t); |
| 608 | page_table_unlock(AS, true); |
655 | page_table_unlock(AS, true); |
| 609 | } else { |
656 | } else { |
| 610 | page_table_unlock(AS, true); |
657 | page_table_unlock(AS, true); |
| 611 | if (as_page_fault(va, istate) == AS_PF_FAULT) { |
658 | if (as_page_fault(va, PF_ACCESS_READ, istate) == AS_PF_FAULT) { |
| 612 | panic("%s: va=%p, rid=%d\n", __FUNCTION__, va, rr.map.rid); |
659 | panic("%s: va=%p, rid=%d\n", __FUNCTION__, va, rid); |
| 613 | } |
660 | } |
| 614 | } |
661 | } |
| 615 | } |
662 | } |