diff options
author | David S. Miller <davem@sunset.davemloft.net> | 2006-02-13 00:10:07 -0500 |
---|---|---|
committer | David S. Miller <davem@sunset.davemloft.net> | 2006-03-20 04:12:32 -0500 |
commit | cf627156c450cd5a0741b31f55181db3400d4887 (patch) | |
tree | e8f44d2509f5544ee5b5d583da3e10ac99ca3629 /arch/sparc64/mm | |
parent | ff02e0d26f139ad95ec3a7e94f88faccaa180dff (diff) |
[SPARC64]: Use inline patching for critical PTE operations.
This handles the SUN4U vs SUN4V PTE layout differences
with near zero performance cost.
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'arch/sparc64/mm')
-rw-r--r-- | arch/sparc64/mm/init.c | 211 |
1 files changed, 3 insertions, 208 deletions
diff --git a/arch/sparc64/mm/init.c b/arch/sparc64/mm/init.c index 81f9f4bffaff..6f860c39db82 100644 --- a/arch/sparc64/mm/init.c +++ b/arch/sparc64/mm/init.c | |||
@@ -1502,217 +1502,12 @@ unsigned long pte_sz_bits(unsigned long sz) | |||
1502 | pte_t mk_pte_io(unsigned long page, pgprot_t prot, int space, unsigned long page_size) | 1502 | pte_t mk_pte_io(unsigned long page, pgprot_t prot, int space, unsigned long page_size) |
1503 | { | 1503 | { |
1504 | pte_t pte; | 1504 | pte_t pte; |
1505 | if (tlb_type == hypervisor) { | 1505 | |
1506 | pte_val(pte) = (((page) | pgprot_val(prot) | _PAGE_E_4V) & | 1506 | pte_val(pte) = page | pgprot_val(pgprot_noncached(prot)); |
1507 | ~(unsigned long)_PAGE_CACHE_4V); | ||
1508 | } else { | ||
1509 | pte_val(pte) = (((page) | pgprot_val(prot) | _PAGE_E_4U) & | ||
1510 | ~(unsigned long)_PAGE_CACHE_4U); | ||
1511 | } | ||
1512 | pte_val(pte) |= (((unsigned long)space) << 32); | 1507 | pte_val(pte) |= (((unsigned long)space) << 32); |
1513 | pte_val(pte) |= pte_sz_bits(page_size); | 1508 | pte_val(pte) |= pte_sz_bits(page_size); |
1514 | return pte; | ||
1515 | } | ||
1516 | |||
1517 | unsigned long pte_present(pte_t pte) | ||
1518 | { | ||
1519 | return (pte_val(pte) & | ||
1520 | ((tlb_type == hypervisor) ? | ||
1521 | _PAGE_PRESENT_4V : _PAGE_PRESENT_4U)); | ||
1522 | } | ||
1523 | |||
1524 | unsigned long pte_file(pte_t pte) | ||
1525 | { | ||
1526 | return (pte_val(pte) & | ||
1527 | ((tlb_type == hypervisor) ? | ||
1528 | _PAGE_FILE_4V : _PAGE_FILE_4U)); | ||
1529 | } | ||
1530 | |||
1531 | unsigned long pte_read(pte_t pte) | ||
1532 | { | ||
1533 | return (pte_val(pte) & | ||
1534 | ((tlb_type == hypervisor) ? | ||
1535 | _PAGE_READ_4V : _PAGE_READ_4U)); | ||
1536 | } | ||
1537 | |||
1538 | unsigned long pte_exec(pte_t pte) | ||
1539 | { | ||
1540 | return (pte_val(pte) & | ||
1541 | ((tlb_type == hypervisor) ? | ||
1542 | _PAGE_EXEC_4V : _PAGE_EXEC_4U)); | ||
1543 | } | ||
1544 | |||
1545 | unsigned long pte_write(pte_t pte) | ||
1546 | { | ||
1547 | return (pte_val(pte) & | ||
1548 | ((tlb_type == hypervisor) ? | ||
1549 | _PAGE_WRITE_4V : _PAGE_WRITE_4U)); | ||
1550 | } | ||
1551 | |||
1552 | unsigned long pte_dirty(pte_t pte) | ||
1553 | { | ||
1554 | return (pte_val(pte) & | ||
1555 | ((tlb_type == hypervisor) ? | ||
1556 | _PAGE_MODIFIED_4V : _PAGE_MODIFIED_4U)); | ||
1557 | } | ||
1558 | |||
1559 | unsigned long pte_young(pte_t pte) | ||
1560 | { | ||
1561 | return (pte_val(pte) & | ||
1562 | ((tlb_type == hypervisor) ? | ||
1563 | _PAGE_ACCESSED_4V : _PAGE_ACCESSED_4U)); | ||
1564 | } | ||
1565 | 1509 | ||
1566 | pte_t pte_wrprotect(pte_t pte) | 1510 | return pte; |
1567 | { | ||
1568 | unsigned long mask = _PAGE_WRITE_4U | _PAGE_W_4U; | ||
1569 | |||
1570 | if (tlb_type == hypervisor) | ||
1571 | mask = _PAGE_WRITE_4V | _PAGE_W_4V; | ||
1572 | |||
1573 | return __pte(pte_val(pte) & ~mask); | ||
1574 | } | ||
1575 | |||
1576 | pte_t pte_rdprotect(pte_t pte) | ||
1577 | { | ||
1578 | unsigned long mask = _PAGE_R | _PAGE_READ_4U; | ||
1579 | |||
1580 | if (tlb_type == hypervisor) | ||
1581 | mask = _PAGE_R | _PAGE_READ_4V; | ||
1582 | |||
1583 | return __pte(pte_val(pte) & ~mask); | ||
1584 | } | ||
1585 | |||
1586 | pte_t pte_mkclean(pte_t pte) | ||
1587 | { | ||
1588 | unsigned long mask = _PAGE_MODIFIED_4U | _PAGE_W_4U; | ||
1589 | |||
1590 | if (tlb_type == hypervisor) | ||
1591 | mask = _PAGE_MODIFIED_4V | _PAGE_W_4V; | ||
1592 | |||
1593 | return __pte(pte_val(pte) & ~mask); | ||
1594 | } | ||
1595 | |||
1596 | pte_t pte_mkold(pte_t pte) | ||
1597 | { | ||
1598 | unsigned long mask = _PAGE_R | _PAGE_ACCESSED_4U; | ||
1599 | |||
1600 | if (tlb_type == hypervisor) | ||
1601 | mask = _PAGE_R | _PAGE_ACCESSED_4V; | ||
1602 | |||
1603 | return __pte(pte_val(pte) & ~mask); | ||
1604 | } | ||
1605 | |||
1606 | pte_t pte_mkyoung(pte_t pte) | ||
1607 | { | ||
1608 | unsigned long mask = _PAGE_R | _PAGE_ACCESSED_4U; | ||
1609 | |||
1610 | if (tlb_type == hypervisor) | ||
1611 | mask = _PAGE_R | _PAGE_ACCESSED_4V; | ||
1612 | |||
1613 | return __pte(pte_val(pte) | mask); | ||
1614 | } | ||
1615 | |||
1616 | pte_t pte_mkwrite(pte_t pte) | ||
1617 | { | ||
1618 | unsigned long mask = _PAGE_WRITE_4U; | ||
1619 | |||
1620 | if (tlb_type == hypervisor) | ||
1621 | mask = _PAGE_WRITE_4V; | ||
1622 | |||
1623 | return __pte(pte_val(pte) | mask); | ||
1624 | } | ||
1625 | |||
1626 | pte_t pte_mkdirty(pte_t pte) | ||
1627 | { | ||
1628 | unsigned long mask = _PAGE_MODIFIED_4U | _PAGE_W_4U; | ||
1629 | |||
1630 | if (tlb_type == hypervisor) | ||
1631 | mask = _PAGE_MODIFIED_4V | _PAGE_W_4V; | ||
1632 | |||
1633 | return __pte(pte_val(pte) | mask); | ||
1634 | } | ||
1635 | |||
1636 | pte_t pte_mkhuge(pte_t pte) | ||
1637 | { | ||
1638 | unsigned long mask = _PAGE_SZHUGE_4U; | ||
1639 | |||
1640 | if (tlb_type == hypervisor) | ||
1641 | mask = _PAGE_SZHUGE_4V; | ||
1642 | |||
1643 | return __pte(pte_val(pte) | mask); | ||
1644 | } | ||
1645 | |||
1646 | pte_t pgoff_to_pte(unsigned long off) | ||
1647 | { | ||
1648 | unsigned long bit = _PAGE_FILE_4U; | ||
1649 | |||
1650 | if (tlb_type == hypervisor) | ||
1651 | bit = _PAGE_FILE_4V; | ||
1652 | |||
1653 | return __pte((off << PAGE_SHIFT) | bit); | ||
1654 | } | ||
1655 | |||
1656 | pgprot_t pgprot_noncached(pgprot_t prot) | ||
1657 | { | ||
1658 | unsigned long val = pgprot_val(prot); | ||
1659 | unsigned long off = _PAGE_CP_4U | _PAGE_CV_4U; | ||
1660 | unsigned long on = _PAGE_E_4U; | ||
1661 | |||
1662 | if (tlb_type == hypervisor) { | ||
1663 | off = _PAGE_CP_4V | _PAGE_CV_4V; | ||
1664 | on = _PAGE_E_4V; | ||
1665 | } | ||
1666 | |||
1667 | return __pgprot((val & ~off) | on); | ||
1668 | } | ||
1669 | |||
1670 | pte_t pfn_pte(unsigned long pfn, pgprot_t prot) | ||
1671 | { | ||
1672 | unsigned long sz_bits = _PAGE_SZBITS_4U; | ||
1673 | |||
1674 | if (tlb_type == hypervisor) | ||
1675 | sz_bits = _PAGE_SZBITS_4V; | ||
1676 | |||
1677 | return __pte((pfn << PAGE_SHIFT) | pgprot_val(prot) | sz_bits); | ||
1678 | } | ||
1679 | |||
1680 | unsigned long pte_pfn(pte_t pte) | ||
1681 | { | ||
1682 | unsigned long mask = _PAGE_PADDR_4U; | ||
1683 | |||
1684 | if (tlb_type == hypervisor) | ||
1685 | mask = _PAGE_PADDR_4V; | ||
1686 | |||
1687 | return (pte_val(pte) & mask) >> PAGE_SHIFT; | ||
1688 | } | ||
1689 | |||
1690 | pte_t pte_modify(pte_t orig_pte, pgprot_t new_prot) | ||
1691 | { | ||
1692 | unsigned long preserve_mask; | ||
1693 | unsigned long val; | ||
1694 | |||
1695 | preserve_mask = (_PAGE_PADDR_4U | | ||
1696 | _PAGE_MODIFIED_4U | | ||
1697 | _PAGE_ACCESSED_4U | | ||
1698 | _PAGE_CP_4U | | ||
1699 | _PAGE_CV_4U | | ||
1700 | _PAGE_E_4U | | ||
1701 | _PAGE_PRESENT_4U | | ||
1702 | _PAGE_SZBITS_4U); | ||
1703 | if (tlb_type == hypervisor) | ||
1704 | preserve_mask = (_PAGE_PADDR_4V | | ||
1705 | _PAGE_MODIFIED_4V | | ||
1706 | _PAGE_ACCESSED_4V | | ||
1707 | _PAGE_CP_4V | | ||
1708 | _PAGE_CV_4V | | ||
1709 | _PAGE_E_4V | | ||
1710 | _PAGE_PRESENT_4V | | ||
1711 | _PAGE_SZBITS_4V); | ||
1712 | |||
1713 | val = (pte_val(orig_pte) & preserve_mask); | ||
1714 | |||
1715 | return __pte(val | (pgprot_val(new_prot) & ~preserve_mask)); | ||
1716 | } | 1511 | } |
1717 | 1512 | ||
1718 | static unsigned long kern_large_tte(unsigned long paddr) | 1513 | static unsigned long kern_large_tte(unsigned long paddr) |