Inter-revision diff: patch 3

Comparing v5 (message) to v9 (message)

--- v5
+++ v9
@@ -1,704 +1,88 @@
 From: "Aneesh Kumar K.V" <aneesh.kumar@linux.vnet.ibm.com>
 
-This patch convert different functions to take virtual page number
-instead of virtual address. Virtual page number is virtual address
-shifted right by VPN_SHIFT (12) bits. This enable us to have an
-address range of upto 76 bits.
+This patch simplify hpte_decode for easy switching of virtual address to
+virtual page number in the later patch
 
+Reviewed-by: Paul Mackerras <paulus@samba.org>
 Signed-off-by: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
 ---
- arch/powerpc/include/asm/mmu-hash64.h     |   73 ++++++++++++++++++----
- arch/powerpc/include/asm/pte-hash64-64k.h |   18 +++---
- arch/powerpc/kvm/book3s_32_mmu_host.c     |    2 +-
- arch/powerpc/kvm/book3s_64_mmu_host.c     |    2 +-
- arch/powerpc/mm/hash_low_64.S             |   97 ++++++++++++++++++-----------
- arch/powerpc/mm/hash_native_64.c          |   46 ++++++++++----
- arch/powerpc/mm/hash_utils_64.c           |    6 +-
- arch/powerpc/mm/hugetlbpage-hash64.c      |    2 +-
- arch/powerpc/mm/tlb_hash64.c              |    2 +-
- arch/powerpc/platforms/cell/beat_htab.c   |    2 +-
- arch/powerpc/platforms/pseries/lpar.c     |   20 +-----
- 11 files changed, 176 insertions(+), 94 deletions(-)
+ arch/powerpc/mm/hash_native_64.c |   49 ++++++++++++++++++++++----------------
+ 1 file changed, 28 insertions(+), 21 deletions(-)
 
-diff --git a/arch/powerpc/include/asm/mmu-hash64.h b/arch/powerpc/include/asm/mmu-hash64.h
-index 1c65a59..60f8596 100644
---- a/arch/powerpc/include/asm/mmu-hash64.h
-+++ b/arch/powerpc/include/asm/mmu-hash64.h
-@@ -15,6 +15,10 @@
- #include <asm/asm-compat.h>
- #include <asm/page.h>
+diff --git a/arch/powerpc/mm/hash_native_64.c b/arch/powerpc/mm/hash_native_64.c
+index 90039bc..660b8bb 100644
+--- a/arch/powerpc/mm/hash_native_64.c
++++ b/arch/powerpc/mm/hash_native_64.c
+@@ -351,9 +351,10 @@ static void native_hpte_invalidate(unsigned long slot, unsigned long va,
+ static void hpte_decode(struct hash_pte *hpte, unsigned long slot,
+ 			int *psize, int *ssize, unsigned long *va)
+ {
++	unsigned long avpn, pteg, vpi;
+ 	unsigned long hpte_r = hpte->r;
+ 	unsigned long hpte_v = hpte->v;
+-	unsigned long avpn;
++	unsigned long vsid, seg_off;
+ 	int i, size, shift, penc;
  
-+#ifndef __ASSEMBLY__
-+#include <linux/bug.h>
-+#endif
+ 	if (!(hpte_v & HPTE_V_LARGE))
+@@ -380,32 +381,38 @@ static void hpte_decode(struct hash_pte *hpte, unsigned long slot,
+ 	}
+ 
+ 	/* This works for all page sizes, and for 256M and 1T segments */
++	*ssize = hpte_v >> HPTE_V_SSIZE_SHIFT;
+ 	shift = mmu_psize_defs[size].shift;
+-	avpn = (HPTE_V_AVPN_VAL(hpte_v) & ~mmu_psize_defs[size].avpnm) << 23;
+-
+-	if (shift < 23) {
+-		unsigned long vpi, vsid, pteg;
+ 
+-		pteg = slot / HPTES_PER_GROUP;
+-		if (hpte_v & HPTE_V_SECONDARY)
+-			pteg = ~pteg;
+-		switch (hpte_v >> HPTE_V_SSIZE_SHIFT) {
+-		case MMU_SEGSIZE_256M:
+-			vpi = ((avpn >> 28) ^ pteg) & htab_hash_mask;
+-			break;
+-		case MMU_SEGSIZE_1T:
+-			vsid = avpn >> 40;
++	avpn = (HPTE_V_AVPN_VAL(hpte_v) & ~mmu_psize_defs[size].avpnm);
++	pteg = slot / HPTES_PER_GROUP;
++	if (hpte_v & HPTE_V_SECONDARY)
++		pteg = ~pteg;
 +
- /*
-  * Segment table
-  */
-@@ -154,9 +158,25 @@ struct mmu_psize_def
- #define MMU_SEGSIZE_256M	0
- #define MMU_SEGSIZE_1T		1
- 
-+/*
-+ * encode page number shift.
-+ * in order to fit the 78 bit va in a 64 bit variable we shift the va by
-+ * 12 bits. This enable us to address upto 76 bit va.
-+ * For hpt hash from a va we can ignore the page size bits of va and for
-+ * hpte encoding we ignore up to 23 bits of va. So ignoring lower 12 bits ensure
-+ * we work in all cases including 4k page size.
-+ */
-+#define VPN_SHIFT	12
- 
- #ifndef __ASSEMBLY__
- 
-+static inline int segment_shift(int ssize)
-+{
-+	if (ssize == MMU_SEGSIZE_256M)
-+		return SID_SHIFT;
-+	return SID_SHIFT_1T;
-+}
-+
- /*
-  * The current system page and segment sizes
-  */
-@@ -180,6 +200,30 @@ extern unsigned long tce_alloc_start, tce_alloc_end;
- extern int mmu_ci_restrictions;
- 
- /*
-+ * This computes the AVPN and B fields of the first dword of a HPTE,
-+ * for use when we want to match an existing PTE.  The bottom 7 bits
-+ * of the returned value are zero.
-+ */
-+static inline unsigned long hpte_encode_avpn(unsigned long vpn, int psize,
-+					     int ssize)
-+{
-+	unsigned long v;
-+	/*
-+	 * The AVA field omits the low-order 23 bits of the 78 bits VA.
-+	 * These bits are not needed in the PTE, because the
-+	 * low-order b of these bits are part of the byte offset
-+	 * into the virtual page and, if b < 23, the high-order
-+	 * 23-b of these bits are always used in selecting the
-+	 * PTEGs to be searched
-+	 */
-+	BUILD_BUG_ON(VPN_SHIFT > 23);
-+	v = (vpn >> (23 - VPN_SHIFT)) & ~(mmu_psize_defs[psize].avpnm);
-+	v <<= HPTE_V_AVPN_SHIFT;
-+	v |= ((unsigned long) ssize) << HPTE_V_SSIZE_SHIFT;
-+	return v;
-+}
-+
-+/*
-  * This function sets the AVPN and L fields of the HPTE  appropriately
-  * for the page size
-  */
-@@ -187,11 +231,9 @@ static inline unsigned long hpte_encode_v(unsigned long va, int psize,
- 					  int ssize)
- {
- 	unsigned long v;
--	v = (va >> 23) & ~(mmu_psize_defs[psize].avpnm);
--	v <<= HPTE_V_AVPN_SHIFT;
-+	v = hpte_encode_avpn(va, psize, ssize);
- 	if (psize != MMU_PAGE_4K)
- 		v |= HPTE_V_LARGE;
--	v |= ((unsigned long) ssize) << HPTE_V_SSIZE_SHIFT;
- 	return v;
- }
- 
-@@ -216,14 +258,16 @@ static inline unsigned long hpte_encode_r(unsigned long pa, int psize)
++	switch (*ssize) {
++	case MMU_SEGSIZE_256M:
++		/* We only have 28 - 23 bits of seg_off in avpn */
++		seg_off = (avpn & 0x1f) << 23;
++		vsid    =  avpn >> 5;
++		/* We can find more bits from the pteg value */
++		if (shift < 23) {
++			vpi = (vsid ^ pteg) & htab_hash_mask;
++			seg_off |= vpi << shift;
++		}
++		*va = vsid << SID_SHIFT | seg_off;
++	case MMU_SEGSIZE_1T:
++		/* We only have 40 - 23 bits of seg_off in avpn */
++		seg_off = (avpn & 0x1ffff) << 23;
++		vsid    = avpn >> 17;
++		if (shift < 23) {
+ 			vpi = (vsid ^ (vsid << 25) ^ pteg) & htab_hash_mask;
+-			break;
+-		default:
+-			avpn = vpi = size = 0;
++			seg_off |= vpi << shift;
+ 		}
+-		avpn |= (vpi << mmu_psize_defs[size].shift);
++		*va = vsid << SID_SHIFT_1T | seg_off;
++	default:
++		*va = size = 0;
+ 	}
+-
+-	*va = avpn;
+ 	*psize = size;
+-	*ssize = hpte_v >> HPTE_V_SSIZE_SHIFT;
  }
  
  /*
-- * Build a VA given VSID, EA and segment size
-+ * Build a VPN_SHIFT bit shifted va given VSID, EA and segment size.
-  */
--static inline unsigned long hpt_va(unsigned long ea, unsigned long vsid,
-+static inline unsigned long hpt_vpn(unsigned long ea, unsigned long vsid,
- 				   int ssize)
- {
--	if (ssize == MMU_SEGSIZE_256M)
--		return (vsid << 28) | (ea & 0xfffffffUL);
--	return (vsid << 40) | (ea & 0xffffffffffUL);
-+	unsigned long mask;
-+	int s_shift = segment_shift(ssize);
-+
-+	mask = (1ul << (s_shift - VPN_SHIFT)) - 1;
-+	return (vsid << (s_shift - VPN_SHIFT)) | ((ea >> VPN_SHIFT) & mask);
- }
- 
- /*
-@@ -233,13 +277,20 @@ static inline unsigned long hpt_va(unsigned long ea, unsigned long vsid,
- static inline unsigned long hpt_hash(unsigned long va, unsigned int shift,
- 				     int ssize)
- {
-+	int mask;
- 	unsigned long hash, vsid;
- 
-+	BUG_ON(shift < VPN_SHIFT);
-+
- 	if (ssize == MMU_SEGSIZE_256M) {
--		hash = (va >> 28) ^ ((va & 0x0fffffffUL) >> shift);
-+		mask = (1ul << (SID_SHIFT - VPN_SHIFT)) - 1;
-+		hash = ((va >> (SID_SHIFT - VPN_SHIFT)) & 0x0000007fffffffff) ^
-+			(((va & mask) >> (shift - VPN_SHIFT)) & 0xffff);
- 	} else {
--		vsid = va >> 40;
--		hash = vsid ^ (vsid << 25) ^ ((va & 0xffffffffffUL) >> shift);
-+		mask = (1ul << (SID_SHIFT_1T - VPN_SHIFT)) - 1;
-+		vsid = va >> (SID_SHIFT_1T - VPN_SHIFT);
-+		hash = (vsid & 0xffffff) ^ ((vsid << 25) & 0x7fffffffff) ^
-+			(((va & mask) >> (shift - VPN_SHIFT)) & 0xfffffff);
- 	}
- 	return hash & 0x7fffffffffUL;
- }
-diff --git a/arch/powerpc/include/asm/pte-hash64-64k.h b/arch/powerpc/include/asm/pte-hash64-64k.h
-index 59247e8..eedf427 100644
---- a/arch/powerpc/include/asm/pte-hash64-64k.h
-+++ b/arch/powerpc/include/asm/pte-hash64-64k.h
-@@ -58,14 +58,16 @@
- /* Trick: we set __end to va + 64k, which happens works for
-  * a 16M page as well as we want only one iteration
-  */
--#define pte_iterate_hashed_subpages(rpte, psize, va, index, shift)	    \
--        do {                                                                \
--                unsigned long __end = va + PAGE_SIZE;                       \
--                unsigned __split = (psize == MMU_PAGE_4K ||                 \
--				    psize == MMU_PAGE_64K_AP);              \
--                shift = mmu_psize_defs[psize].shift;                        \
--		for (index = 0; va < __end; index++, va += (1L << shift)) { \
--		        if (!__split || __rpte_sub_valid(rpte, index)) do { \
-+#define pte_iterate_hashed_subpages(rpte, psize, vpn, index, shift)	\
-+	do {								\
-+		unsigned long __end = vpn + (1UL << (PAGE_SHIFT - VPN_SHIFT));	\
-+		unsigned __split = (psize == MMU_PAGE_4K ||		\
-+				    psize == MMU_PAGE_64K_AP);		\
-+		shift = mmu_psize_defs[psize].shift;			\
-+		for (index = 0; vpn < __end; index++,			\
-+			     vpn += (1L << (shift - VPN_SHIFT))) {	\
-+			if (!__split || __rpte_sub_valid(rpte, index))	\
-+				do {
- 
- #define pte_iterate_hashed_end() } while(0); } } while(0)
- 
-diff --git a/arch/powerpc/kvm/book3s_32_mmu_host.c b/arch/powerpc/kvm/book3s_32_mmu_host.c
-index f922c29..bf5dfb3 100644
---- a/arch/powerpc/kvm/book3s_32_mmu_host.c
-+++ b/arch/powerpc/kvm/book3s_32_mmu_host.c
-@@ -173,7 +173,7 @@ int kvmppc_mmu_map_page(struct kvm_vcpu *vcpu, struct kvmppc_pte *orig_pte)
- 	BUG_ON(!map);
- 
- 	vsid = map->host_vsid;
--	va = (vsid << SID_SHIFT) | (eaddr & ~ESID_MASK);
-+	va = (vsid << (SID_SHIFT - VPN_SHIFT)) | ((eaddr & ~ESID_MASK) >> VPN_SHIFT)
- 
- next_pteg:
- 	if (rr == 16) {
-diff --git a/arch/powerpc/kvm/book3s_64_mmu_host.c b/arch/powerpc/kvm/book3s_64_mmu_host.c
-index 10fc8ec..9d184f1 100644
---- a/arch/powerpc/kvm/book3s_64_mmu_host.c
-+++ b/arch/powerpc/kvm/book3s_64_mmu_host.c
-@@ -117,7 +117,7 @@ int kvmppc_mmu_map_page(struct kvm_vcpu *vcpu, struct kvmppc_pte *orig_pte)
- 	}
- 
- 	vsid = map->host_vsid;
--	va = hpt_va(orig_pte->eaddr, vsid, MMU_SEGSIZE_256M);
-+	va = hpt_vpn(orig_pte->eaddr, vsid, MMU_SEGSIZE_256M);
- 
- 	if (!orig_pte->may_write)
- 		rflags |= HPTE_R_PP;
-diff --git a/arch/powerpc/mm/hash_low_64.S b/arch/powerpc/mm/hash_low_64.S
-index a242b5d..534cc26 100644
---- a/arch/powerpc/mm/hash_low_64.S
-+++ b/arch/powerpc/mm/hash_low_64.S
-@@ -71,7 +71,7 @@ _GLOBAL(__hash_page_4K)
- 	/* Save non-volatile registers.
- 	 * r31 will hold "old PTE"
- 	 * r30 is "new PTE"
--	 * r29 is "va"
-+	 * r29 is vpn
- 	 * r28 is a hash value
- 	 * r27 is hashtab mask (maybe dynamic patched instead ?)
- 	 */
-@@ -119,10 +119,10 @@ BEGIN_FTR_SECTION
- 	cmpdi	r9,0			/* check segment size */
- 	bne	3f
- END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT)
--	/* Calc va and put it in r29 */
--	rldicr	r29,r5,28,63-28
--	rldicl	r3,r3,0,36
--	or	r29,r3,r29
-+	/* Calc vpn and put it in r29 */
-+	sldi	r29,r5,SID_SHIFT - VPN_SHIFT
-+	rldicl  r28,r3,64 - VPN_SHIFT,64 - (SID_SHIFT - VPN_SHIFT)
-+	or	r29,r28,r29
- 
- 	/* Calculate hash value for primary slot and store it in r28 */
- 	rldicl	r5,r5,0,25		/* vsid & 0x0000007fffffffff */
-@@ -130,14 +130,19 @@ END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT)
- 	xor	r28,r5,r0
- 	b	4f
- 
--3:	/* Calc VA and hash in r29 and r28 for 1T segment */
--	sldi	r29,r5,40		/* vsid << 40 */
--	clrldi	r3,r3,24		/* ea & 0xffffffffff */
-+3:	/* Calc vpn and put it in r29 */
-+	sldi	r29,r5,SID_SHIFT_1T - VPN_SHIFT
-+	rldicl  r28,r3,64 - VPN_SHIFT,64 - (SID_SHIFT_1T - VPN_SHIFT)
-+	or	r29,r28,r29
-+
-+	/*
-+	 * calculate hash value for primary slot and
-+	 * store it in r28 for 1T segment
-+	 */
- 	rldic	r28,r5,25,25		/* (vsid << 25) & 0x7fffffffff */
- 	clrldi	r5,r5,40		/* vsid & 0xffffff */
- 	rldicl	r0,r3,64-12,36		/* (ea >> 12) & 0xfffffff */
- 	xor	r28,r28,r5
--	or	r29,r3,r29		/* VA */
- 	xor	r28,r28,r0		/* hash */
- 
- 	/* Convert linux PTE bits into HW equivalents */
-@@ -193,7 +198,7 @@ htab_insert_pte:
- 
- 	/* Call ppc_md.hpte_insert */
- 	ld	r6,STK_PARM(r4)(r1)	/* Retrieve new pp bits */
--	mr	r4,r29			/* Retrieve va */
-+	mr	r4,r29			/* Retrieve vpn */
- 	li	r7,0			/* !bolted, !secondary */
- 	li	r8,MMU_PAGE_4K		/* page size */
- 	ld	r9,STK_PARM(r9)(r1)	/* segment size */
-@@ -216,7 +221,7 @@ _GLOBAL(htab_call_hpte_insert1)
- 	
- 	/* Call ppc_md.hpte_insert */
- 	ld	r6,STK_PARM(r4)(r1)	/* Retrieve new pp bits */
--	mr	r4,r29			/* Retrieve va */
-+	mr	r4,r29			/* Retrieve vpn */
- 	li	r7,HPTE_V_SECONDARY	/* !bolted, secondary */
- 	li	r8,MMU_PAGE_4K		/* page size */
- 	ld	r9,STK_PARM(r9)(r1)	/* segment size */
-@@ -286,7 +291,7 @@ htab_modify_pte:
- 	add	r3,r0,r3	/* add slot idx */
- 
- 	/* Call ppc_md.hpte_updatepp */
--	mr	r5,r29			/* va */
-+	mr	r5,r29			/* vpn */
- 	li	r6,MMU_PAGE_4K		/* page size */
- 	ld	r7,STK_PARM(r9)(r1)	/* segment size */
- 	ld	r8,STK_PARM(r8)(r1)	/* get "local" param */
-@@ -347,7 +352,7 @@ _GLOBAL(__hash_page_4K)
- 	/* Save non-volatile registers.
- 	 * r31 will hold "old PTE"
- 	 * r30 is "new PTE"
--	 * r29 is "va"
-+	 * r29 is vpn
- 	 * r28 is a hash value
- 	 * r27 is hashtab mask (maybe dynamic patched instead ?)
- 	 * r26 is the hidx mask
-@@ -402,10 +407,14 @@ BEGIN_FTR_SECTION
- 	cmpdi	r9,0			/* check segment size */
- 	bne	3f
- END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT)
--	/* Calc va and put it in r29 */
--	rldicr	r29,r5,28,63-28		/* r29 = (vsid << 28) */
--	rldicl	r3,r3,0,36		/* r3 = (ea & 0x0fffffff) */
--	or	r29,r3,r29		/* r29 = va */
-+	/* Calc vpn and put it in r29 */
-+	sldi	r29,r5,SID_SHIFT - VPN_SHIFT
-+	/*
-+	 * clrldi r3,r3,64 - SID_SHIFT -->  ea & 0xfffffff
-+	 * srdi	 r28,r3,VPN_SHIFT
-+	 */
-+	rldicl  r28,r3,64 - VPN_SHIFT,64 - (SID_SHIFT - VPN_SHIFT)
-+	or	r29,r28,r29
- 
- 	/* Calculate hash value for primary slot and store it in r28 */
- 	rldicl	r5,r5,0,25		/* vsid & 0x0000007fffffffff */
-@@ -413,14 +422,23 @@ END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT)
- 	xor	r28,r5,r0
- 	b	4f
- 
--3:	/* Calc VA and hash in r29 and r28 for 1T segment */
--	sldi	r29,r5,40		/* vsid << 40 */
--	clrldi	r3,r3,24		/* ea & 0xffffffffff */
-+3:	/* Calc vpn and put it in r29 */
-+	sldi	r29,r5,SID_SHIFT_1T - VPN_SHIFT
-+	/*
-+	 * clrldi r3,r3,64 - SID_SHIFT_1T -->  ea & 0xffffffffff
-+	 * srdi	r28,r3,VPN_SHIFT
-+	 */
-+	rldicl  r28,r3,64 - VPN_SHIFT,64 - (SID_SHIFT_1T - VPN_SHIFT)
-+	or	r29,r28,r29
-+
-+	/*
-+	 * Calculate hash value for primary slot and
-+	 * store it in r28  for 1T segment
-+	 */
- 	rldic	r28,r5,25,25		/* (vsid << 25) & 0x7fffffffff */
- 	clrldi	r5,r5,40		/* vsid & 0xffffff */
- 	rldicl	r0,r3,64-12,36		/* (ea >> 12) & 0xfffffff */
- 	xor	r28,r28,r5
--	or	r29,r3,r29		/* VA */
- 	xor	r28,r28,r0		/* hash */
- 
- 	/* Convert linux PTE bits into HW equivalents */
-@@ -496,7 +514,7 @@ htab_special_pfn:
- 
- 	/* Call ppc_md.hpte_insert */
- 	ld	r6,STK_PARM(r4)(r1)	/* Retrieve new pp bits */
--	mr	r4,r29			/* Retrieve va */
-+	mr	r4,r29			/* Retrieve vpn */
- 	li	r7,0			/* !bolted, !secondary */
- 	li	r8,MMU_PAGE_4K		/* page size */
- 	ld	r9,STK_PARM(r9)(r1)	/* segment size */
-@@ -523,7 +541,7 @@ _GLOBAL(htab_call_hpte_insert1)
- 
- 	/* Call ppc_md.hpte_insert */
- 	ld	r6,STK_PARM(r4)(r1)	/* Retrieve new pp bits */
--	mr	r4,r29			/* Retrieve va */
-+	mr	r4,r29			/* Retrieve vpn */
- 	li	r7,HPTE_V_SECONDARY	/* !bolted, secondary */
- 	li	r8,MMU_PAGE_4K		/* page size */
- 	ld	r9,STK_PARM(r9)(r1)	/* segment size */
-@@ -555,7 +573,7 @@ _GLOBAL(htab_call_hpte_remove)
- 	 * useless now that the segment has been switched to 4k pages.
- 	 */
- htab_inval_old_hpte:
--	mr	r3,r29			/* virtual addr */
-+	mr	r3,r29			/* vpn */
- 	mr	r4,r31			/* PTE.pte */
- 	li	r5,0			/* PTE.hidx */
- 	li	r6,MMU_PAGE_64K		/* psize */
-@@ -628,7 +646,7 @@ htab_modify_pte:
- 	add	r3,r0,r3	/* add slot idx */
- 
- 	/* Call ppc_md.hpte_updatepp */
--	mr	r5,r29			/* va */
-+	mr	r5,r29			/* vpn */
- 	li	r6,MMU_PAGE_4K		/* page size */
- 	ld	r7,STK_PARM(r9)(r1)	/* segment size */
- 	ld	r8,STK_PARM(r8)(r1)	/* get "local" param */
-@@ -684,7 +702,7 @@ _GLOBAL(__hash_page_64K)
- 	/* Save non-volatile registers.
- 	 * r31 will hold "old PTE"
- 	 * r30 is "new PTE"
--	 * r29 is "va"
-+	 * r29 is vpn
- 	 * r28 is a hash value
- 	 * r27 is hashtab mask (maybe dynamic patched instead ?)
- 	 */
-@@ -737,10 +755,10 @@ BEGIN_FTR_SECTION
- 	cmpdi	r9,0			/* check segment size */
- 	bne	3f
- END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT)
--	/* Calc va and put it in r29 */
--	rldicr	r29,r5,28,63-28
--	rldicl	r3,r3,0,36
--	or	r29,r3,r29
-+	/* Calc vpn and put it in r29 */
-+	sldi	r29,r5,SID_SHIFT - VPN_SHIFT
-+	rldicl  r28,r3,64 - VPN_SHIFT,64 - (SID_SHIFT - VPN_SHIFT)
-+	or	r29,r28,r29
- 
- 	/* Calculate hash value for primary slot and store it in r28 */
- 	rldicl	r5,r5,0,25		/* vsid & 0x0000007fffffffff */
-@@ -748,14 +766,19 @@ END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT)
- 	xor	r28,r5,r0
- 	b	4f
- 
--3:	/* Calc VA and hash in r29 and r28 for 1T segment */
--	sldi	r29,r5,40		/* vsid << 40 */
--	clrldi	r3,r3,24		/* ea & 0xffffffffff */
-+3:	/* Calc vpn and put it in r29 */
-+	sldi	r29,r5,SID_SHIFT_1T - VPN_SHIFT
-+	rldicl  r28,r3,64 - VPN_SHIFT,64 - (SID_SHIFT_1T - VPN_SHIFT)
-+	or	r29,r28,r29
-+
-+	/*
-+	 * calculate hash value for primary slot and
-+	 * store it in r28 for 1T segment
-+	 */
- 	rldic	r28,r5,25,25		/* (vsid << 25) & 0x7fffffffff */
- 	clrldi	r5,r5,40		/* vsid & 0xffffff */
- 	rldicl	r0,r3,64-16,40		/* (ea >> 16) & 0xffffff */
- 	xor	r28,r28,r5
--	or	r29,r3,r29		/* VA */
- 	xor	r28,r28,r0		/* hash */
- 
- 	/* Convert linux PTE bits into HW equivalents */
-@@ -814,7 +837,7 @@ ht64_insert_pte:
- 
- 	/* Call ppc_md.hpte_insert */
- 	ld	r6,STK_PARM(r4)(r1)	/* Retrieve new pp bits */
--	mr	r4,r29			/* Retrieve va */
-+	mr	r4,r29			/* Retrieve vpn */
- 	li	r7,0			/* !bolted, !secondary */
- 	li	r8,MMU_PAGE_64K
- 	ld	r9,STK_PARM(r9)(r1)	/* segment size */
-@@ -837,7 +860,7 @@ _GLOBAL(ht64_call_hpte_insert1)
- 
- 	/* Call ppc_md.hpte_insert */
- 	ld	r6,STK_PARM(r4)(r1)	/* Retrieve new pp bits */
--	mr	r4,r29			/* Retrieve va */
-+	mr	r4,r29			/* Retrieve vpn */
- 	li	r7,HPTE_V_SECONDARY	/* !bolted, secondary */
- 	li	r8,MMU_PAGE_64K
- 	ld	r9,STK_PARM(r9)(r1)	/* segment size */
-@@ -907,7 +930,7 @@ ht64_modify_pte:
- 	add	r3,r0,r3	/* add slot idx */
- 
- 	/* Call ppc_md.hpte_updatepp */
--	mr	r5,r29			/* va */
-+	mr	r5,r29			/* vpn */
- 	li	r6,MMU_PAGE_64K
- 	ld	r7,STK_PARM(r9)(r1)	/* segment size */
- 	ld	r8,STK_PARM(r8)(r1)	/* get "local" param */
-diff --git a/arch/powerpc/mm/hash_native_64.c b/arch/powerpc/mm/hash_native_64.c
-index 660b8bb..8e12798 100644
---- a/arch/powerpc/mm/hash_native_64.c
-+++ b/arch/powerpc/mm/hash_native_64.c
-@@ -39,22 +39,36 @@
- 
- DEFINE_RAW_SPINLOCK(native_tlbie_lock);
- 
--static inline void __tlbie(unsigned long va, int psize, int ssize)
-+static inline void __tlbie(unsigned long vpn, int psize, int ssize)
- {
-+	unsigned long va;
- 	unsigned int penc;
- 
--	/* clear top 16 bits, non SLS segment */
-+	/*
-+	 * We need 14 to 65 bits of va for a tlibe of 4K page
-+	 * With vpn we ignore the lower VPN_SHIFT bits already.
-+	 * And top two bits are already ignored because we can
-+	 * only accomadate 76 bits in a 64 bit vpn with a VPN_SHIFT
-+	 * of 12.
-+	 */
-+	BUILD_BUG_ON(VPN_SHIFT > (77 - 65));
-+	va = vpn << VPN_SHIFT;
-+	/*
-+	 * clear top 16 bits of 64bit va, non SLS segment
-+	 * Older versions of the architecture (2.02 and earler) require the
-+	 * masking of the top 16 bits.
-+	 */
- 	va &= ~(0xffffULL << 48);
- 
- 	switch (psize) {
- 	case MMU_PAGE_4K:
--		va &= ~0xffful;
- 		va |= ssize << 8;
- 		asm volatile(ASM_FTR_IFCLR("tlbie %0,0", PPC_TLBIE(%1,%0), %2)
- 			     : : "r" (va), "r"(0), "i" (CPU_FTR_ARCH_206)
- 			     : "memory");
- 		break;
- 	default:
-+		/* We need 14 to 14 + i bits of va */
- 		penc = mmu_psize_defs[psize].penc;
- 		va &= ~((1ul << mmu_psize_defs[psize].shift) - 1);
- 		va |= penc << 12;
-@@ -67,21 +81,28 @@ static inline void __tlbie(unsigned long va, int psize, int ssize)
- 	}
- }
- 
--static inline void __tlbiel(unsigned long va, int psize, int ssize)
-+static inline void __tlbiel(unsigned long vpn, int psize, int ssize)
- {
-+	unsigned long va;
- 	unsigned int penc;
- 
--	/* clear top 16 bits, non SLS segment */
-+	BUILD_BUG_ON(VPN_SHIFT > (77 - 65));
-+	va = vpn << VPN_SHIFT;
-+	/*
-+	 * clear top 16 bits of 64 bit va, non SLS segment
-+	 * Older versions of the architecture (2.02 and earler) require the
-+	 * masking of the top 16 bits.
-+	 */
- 	va &= ~(0xffffULL << 48);
- 
- 	switch (psize) {
- 	case MMU_PAGE_4K:
--		va &= ~0xffful;
- 		va |= ssize << 8;
- 		asm volatile(".long 0x7c000224 | (%0 << 11) | (0 << 21)"
- 			     : : "r"(va) : "memory");
- 		break;
- 	default:
-+		/* We need 14 to 14 + i bits of va */
- 		penc = mmu_psize_defs[psize].penc;
- 		va &= ~((1ul << mmu_psize_defs[psize].shift) - 1);
- 		va |= penc << 12;
-@@ -234,7 +255,7 @@ static long native_hpte_updatepp(unsigned long slot, unsigned long newpp,
- 
- 	want_v = hpte_encode_v(va, psize, ssize);
- 
--	DBG_LOW("    update(va=%016lx, avpnv=%016lx, hash=%016lx, newpp=%x)",
-+	DBG_LOW("    update(va=%016lx, avpnv=%016lx, group=%lx, newpp=%lx)",
- 		va, want_v & HPTE_V_AVPN, slot, newpp);
- 
- 	native_lock_hpte(hptep);
-@@ -300,7 +321,7 @@ static void native_hpte_updateboltedpp(unsigned long newpp, unsigned long ea,
- 	struct hash_pte *hptep;
- 
- 	vsid = get_kernel_vsid(ea, ssize);
--	va = hpt_va(ea, vsid, ssize);
-+	va = hpt_vpn(ea, vsid, ssize);
- 
- 	slot = native_hpte_find(va, psize, ssize);
- 	if (slot == -1)
-@@ -325,7 +346,7 @@ static void native_hpte_invalidate(unsigned long slot, unsigned long va,
- 
- 	local_irq_save(flags);
- 
--	DBG_LOW("    invalidate(va=%016lx, hash: %x)\n", va, slot);
-+	DBG_LOW("    invalidate(va=%016lx, hash: %lx)\n", va, slot);
- 
- 	want_v = hpte_encode_v(va, psize, ssize);
- 	native_lock_hpte(hptep);
-@@ -399,7 +420,7 @@ static void hpte_decode(struct hash_pte *hpte, unsigned long slot,
- 			vpi = (vsid ^ pteg) & htab_hash_mask;
- 			seg_off |= vpi << shift;
- 		}
--		*va = vsid << SID_SHIFT | seg_off;
-+		*va = vsid << (SID_SHIFT - VPN_SHIFT) | seg_off >> VPN_SHIFT;
- 	case MMU_SEGSIZE_1T:
- 		/* We only have 40 - 23 bits of seg_off in avpn */
- 		seg_off = (avpn & 0x1ffff) << 23;
-@@ -408,7 +429,7 @@ static void hpte_decode(struct hash_pte *hpte, unsigned long slot,
- 			vpi = (vsid ^ (vsid << 25) ^ pteg) & htab_hash_mask;
- 			seg_off |= vpi << shift;
- 		}
--		*va = vsid << SID_SHIFT_1T | seg_off;
-+		*va = vsid << (SID_SHIFT_1T - VPN_SHIFT) | seg_off >> VPN_SHIFT;
- 	default:
- 		*va = size = 0;
- 	}
-@@ -425,9 +446,10 @@ static void hpte_decode(struct hash_pte *hpte, unsigned long slot,
-  */
- static void native_hpte_clear(void)
- {
-+	unsigned long va = 0;
- 	unsigned long slot, slots, flags;
- 	struct hash_pte *hptep = htab_address;
--	unsigned long hpte_v, va;
-+	unsigned long hpte_v;
- 	unsigned long pteg_count;
- 	int psize, ssize;
- 
-diff --git a/arch/powerpc/mm/hash_utils_64.c b/arch/powerpc/mm/hash_utils_64.c
-index 377e5cb..975c7d1 100644
---- a/arch/powerpc/mm/hash_utils_64.c
-+++ b/arch/powerpc/mm/hash_utils_64.c
-@@ -192,7 +192,7 @@ int htab_bolt_mapping(unsigned long vstart, unsigned long vend,
- 	     vaddr += step, paddr += step) {
- 		unsigned long hash, hpteg;
- 		unsigned long vsid = get_kernel_vsid(vaddr, ssize);
--		unsigned long va = hpt_va(vaddr, vsid, ssize);
-+		unsigned long va  = hpt_vpn(vaddr, vsid, ssize);
- 		unsigned long tprot = prot;
- 
- 		/* Make kernel text executable */
-@@ -1208,7 +1208,7 @@ static void kernel_map_linear_page(unsigned long vaddr, unsigned long lmi)
- {
- 	unsigned long hash, hpteg;
- 	unsigned long vsid = get_kernel_vsid(vaddr, mmu_kernel_ssize);
--	unsigned long va = hpt_va(vaddr, vsid, mmu_kernel_ssize);
-+	unsigned long va = hpt_vpn(vaddr, vsid, mmu_kernel_ssize);
- 	unsigned long mode = htab_convert_pte_flags(PAGE_KERNEL);
- 	int ret;
- 
-@@ -1229,7 +1229,7 @@ static void kernel_unmap_linear_page(unsigned long vaddr, unsigned long lmi)
- {
- 	unsigned long hash, hidx, slot;
- 	unsigned long vsid = get_kernel_vsid(vaddr, mmu_kernel_ssize);
--	unsigned long va = hpt_va(vaddr, vsid, mmu_kernel_ssize);
-+	unsigned long va = hpt_vpn(vaddr, vsid, mmu_kernel_ssize);
- 
- 	hash = hpt_hash(va, PAGE_SHIFT, mmu_kernel_ssize);
- 	spin_lock(&linear_map_hash_lock);
-diff --git a/arch/powerpc/mm/hugetlbpage-hash64.c b/arch/powerpc/mm/hugetlbpage-hash64.c
-index cc5c273..1331403 100644
---- a/arch/powerpc/mm/hugetlbpage-hash64.c
-+++ b/arch/powerpc/mm/hugetlbpage-hash64.c
-@@ -25,7 +25,7 @@ int __hash_page_huge(unsigned long ea, unsigned long access, unsigned long vsid,
- 	BUG_ON(shift != mmu_psize_defs[mmu_psize].shift);
- 
- 	/* Search the Linux page table for a match with va */
--	va = hpt_va(ea, vsid, ssize);
-+	va = hpt_vpn(ea, vsid, ssize);
- 
- 	/* At this point, we have a pte (old_pte) which can be used to build
- 	 * or update an HPTE. There are 2 cases:
-diff --git a/arch/powerpc/mm/tlb_hash64.c b/arch/powerpc/mm/tlb_hash64.c
-index 31f1820..321c585 100644
---- a/arch/powerpc/mm/tlb_hash64.c
-+++ b/arch/powerpc/mm/tlb_hash64.c
-@@ -86,7 +86,7 @@ void hpte_need_flush(struct mm_struct *mm, unsigned long addr,
- 		vsid = get_kernel_vsid(addr, mmu_kernel_ssize);
- 		ssize = mmu_kernel_ssize;
- 	}
--	vaddr = hpt_va(addr, vsid, ssize);
-+	vaddr = hpt_vpn(addr, vsid, ssize);
- 	rpte = __real_pte(__pte(pte), ptep);
- 
- 	/*
-diff --git a/arch/powerpc/platforms/cell/beat_htab.c b/arch/powerpc/platforms/cell/beat_htab.c
-index b83077e..c8c7bf6 100644
---- a/arch/powerpc/platforms/cell/beat_htab.c
-+++ b/arch/powerpc/platforms/cell/beat_htab.c
-@@ -259,7 +259,7 @@ static void beat_lpar_hpte_updateboltedpp(unsigned long newpp,
- 	u64 dummy0, dummy1;
- 
- 	vsid = get_kernel_vsid(ea, MMU_SEGSIZE_256M);
--	va = hpt_va(ea, vsid, MMU_SEGSIZE_256M);
-+	va = hpt_vpn(ea, vsid, MMU_SEGSIZE_256M);
- 
- 	raw_spin_lock(&beat_htab_lock);
- 	slot = beat_lpar_hpte_find(va, psize);
-diff --git a/arch/powerpc/platforms/pseries/lpar.c b/arch/powerpc/platforms/pseries/lpar.c
-index 5f3ef87..2127529 100644
---- a/arch/powerpc/platforms/pseries/lpar.c
-+++ b/arch/powerpc/platforms/pseries/lpar.c
-@@ -227,22 +227,6 @@ static void pSeries_lpar_hptab_clear(void)
- }
- 
- /*
-- * This computes the AVPN and B fields of the first dword of a HPTE,
-- * for use when we want to match an existing PTE.  The bottom 7 bits
-- * of the returned value are zero.
-- */
--static inline unsigned long hpte_encode_avpn(unsigned long va, int psize,
--					     int ssize)
--{
--	unsigned long v;
--
--	v = (va >> 23) & ~(mmu_psize_defs[psize].avpnm);
--	v <<= HPTE_V_AVPN_SHIFT;
--	v |= ((unsigned long) ssize) << HPTE_V_SSIZE_SHIFT;
--	return v;
--}
--
--/*
-  * NOTE: for updatepp ops we are fortunate that the linux "newpp" bits and
-  * the low 3 bits of flags happen to line up.  So no transform is needed.
-  * We can probably optimize here and assume the high bits of newpp are
-@@ -326,7 +310,7 @@ static void pSeries_lpar_hpte_updateboltedpp(unsigned long newpp,
- 	unsigned long lpar_rc, slot, vsid, va, flags;
- 
- 	vsid = get_kernel_vsid(ea, ssize);
--	va = hpt_va(ea, vsid, ssize);
-+	va = hpt_vpn(ea, vsid, ssize);
- 
- 	slot = pSeries_lpar_hpte_find(va, psize, ssize);
- 	BUG_ON(slot == -1);
-@@ -361,7 +345,7 @@ static void pSeries_lpar_hpte_removebolted(unsigned long ea,
- 	unsigned long slot, vsid, va;
- 
- 	vsid = get_kernel_vsid(ea, ssize);
--	va = hpt_va(ea, vsid, ssize);
-+	va = hpt_vpn(ea, vsid, ssize);
- 
- 	slot = pSeries_lpar_hpte_find(va, psize, ssize);
- 	BUG_ON(slot == -1);
 -- 
 1.7.10
Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help