* Zero L2 page table page. * Use same KVA as in pmap_zero_page(). */
| 1637 | * Use same KVA as in pmap_zero_page(). |
| 1638 | */ |
| 1639 | static __inline vm_paddr_t |
| 1640 | pmap_pt2pg_zero(vm_page_t m) |
| 1641 | { |
| 1642 | pt2_entry_t *cmap2_pte2p; |
| 1643 | vm_paddr_t pa; |
| 1644 | struct pcpu *pc; |
| 1645 | |
| 1646 | pa = VM_PAGE_TO_PHYS(m); |
| 1647 | |
| 1648 | /* |
| 1649 | * XXX: For now, we map whole page even if it's already zero, |
| 1650 | * to sync it even if the sync is only DSB. |
| 1651 | */ |
| 1652 | sched_pin(); |
| 1653 | pc = get_pcpu(); |
| 1654 | cmap2_pte2p = pc->pc_cmap2_pte2p; |
| 1655 | mtx_lock(&pc->pc_cmap_lock); |
| 1656 | if (pte2_load(cmap2_pte2p) != 0) |
| 1657 | panic("%s: CMAP2 busy", __func__); |
| 1658 | pte2_store(cmap2_pte2p, PTE2_KERN_NG(pa, PTE2_AP_KRW, |
| 1659 | vm_page_pte2_attr(m))); |
| 1660 | /* Even VM_ALLOC_ZERO request is only advisory. */ |
| 1661 | if ((m->flags & PG_ZERO) == 0) |
| 1662 | pagezero(pc->pc_cmap2_addr); |
| 1663 | pte2_sync_range((pt2_entry_t *)pc->pc_cmap2_addr, PAGE_SIZE); |
| 1664 | pte2_clear(cmap2_pte2p); |
| 1665 | tlb_flush((vm_offset_t)pc->pc_cmap2_addr); |
| 1666 | |
| 1667 | /* |
| 1668 | * Unpin the thread before releasing the lock. Otherwise the thread |
| 1669 | * could be rescheduled while still bound to the current CPU, only |
| 1670 | * to unpin itself immediately upon resuming execution. |
| 1671 | */ |
| 1672 | sched_unpin(); |
| 1673 | mtx_unlock(&pc->pc_cmap_lock); |
| 1674 | |
| 1675 | return (pa); |
| 1676 | } |
| 1677 | |
| 1678 | /* |
| 1679 | * Init just allocated page as L2 page table(s) holder |
no test coverage detected