Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/arch/sparc/sparc Well, what do you know.. the TLB contex...
details: https://anonhg.NetBSD.org/src/rev/04a4da7d2d75
branches: trunk
changeset: 473006:04a4da7d2d75
user: pk <pk%NetBSD.org@localhost>
date: Sun May 16 16:37:45 1999 +0000
description:
Well, what do you know.. the TLB context flush has been coded with the
wrong `type' field all these years. Fix this and add a TLB region flush
as well. Also take care of a few inconsequential nits.
diffstat:
sys/arch/sparc/sparc/pmap.c | 53 ++++++++++++++++++++++++++++----------------
1 files changed, 33 insertions(+), 20 deletions(-)
diffs (134 lines):
diff -r 8d4de811c833 -r 04a4da7d2d75 sys/arch/sparc/sparc/pmap.c
--- a/sys/arch/sparc/sparc/pmap.c Sun May 16 14:47:52 1999 +0000
+++ b/sys/arch/sparc/sparc/pmap.c Sun May 16 16:37:45 1999 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: pmap.c,v 1.142 1999/04/25 10:30:02 pk Exp $ */
+/* $NetBSD: pmap.c,v 1.143 1999/05/16 16:37:45 pk Exp $ */
/*
* Copyright (c) 1996
@@ -520,14 +520,20 @@
*/
#if defined(SUN4M)
-
-/* Macros which implement SRMMU TLB flushing/invalidation */
-
-#define tlb_flush_page(va) sta((va & ~0xfff) | ASI_SRMMUFP_L3, ASI_SRMMUFP,0)
-#define tlb_flush_segment(vreg, vseg) sta((vreg << RGSHIFT) | (vseg << SGSHIFT)\
- | ASI_SRMMUFP_L2, ASI_SRMMUFP,0)
-#define tlb_flush_context() sta(ASI_SRMMUFP_L1, ASI_SRMMUFP, 0)
-#define tlb_flush_all() sta(ASI_SRMMUFP_LN, ASI_SRMMUFP, 0)
+/*
+ * Macros which implement SRMMU TLB flushing/invalidation
+ */
+#define tlb_flush_page(va) \
+ sta(((va) & ~0xfff) | ASI_SRMMUFP_L3, ASI_SRMMUFP, 0)
+
+#define tlb_flush_segment(vr, vs) \
+ sta(((vr)<<RGSHIFT) | ((vs)<<SGSHIFT) | ASI_SRMMUFP_L2, ASI_SRMMUFP,0)
+
+#define tlb_flush_region(vr) \
+ sta(((vr) << RGSHIFT) | ASI_SRMMUFP_L1, ASI_SRMMUFP, 0)
+
+#define tlb_flush_context() sta(ASI_SRMMUFP_L0, ASI_SRMMUFP, 0)
+#define tlb_flush_all() sta(ASI_SRMMUFP_LN, ASI_SRMMUFP, 0)
static u_int VA2PA __P((caddr_t));
static u_long srmmu_bypass_read __P((u_long));
@@ -551,7 +557,8 @@
/* Try each level in turn until we find a valid pte. Otherwise panic */
pte = lda(((u_int)addr & ~0xfff) | ASI_SRMMUFP_L3, ASI_SRMMUFP);
-(void)lda(SRMMU_SFSR, ASI_SRMMU);
+ /* Unlock fault status; required on Hypersparc modules */
+ (void)lda(SRMMU_SFSR, ASI_SRMMU);
if ((pte & SRMMU_TETYPE) == SRMMU_TEPTE)
return (((pte & SRMMU_PPNMASK) << SRMMU_PPNPASHIFT) |
((u_int)addr & 0xfff));
@@ -2883,7 +2890,8 @@
#if defined(SUN4_MMU3L)
/* Reserve one region for temporary mappings */
- tregion = --nregion;
+ if (HASSUN4_MMU3L)
+ tregion = --nregion;
#endif
/*
@@ -4507,7 +4515,7 @@
if (--rp->rg_nsegmap == 0) {
if (pm->pm_ctx)
- tlb_flush_context(); /* Paranoia? */
+ tlb_flush_region(vr); /* Paranoia? */
setpgt4m(&pm->pm_reg_ptps[vr], SRMMU_TEINVALID);
free(rp->rg_segmap, M_VMPMAP);
rp->rg_segmap = NULL;
@@ -4515,7 +4523,7 @@
}
}
}
-#endif /* sun4m */
+#endif /* SUN4M */
/*
* Lower (make more strict) the protection on the specified
@@ -5027,7 +5035,7 @@
if (--rp->rg_nsegmap == 0) {
if (pm->pm_ctx)
- tlb_flush_context();
+ tlb_flush_region(vr);
setpgt4m(&pm->pm_reg_ptps[vr], SRMMU_TEINVALID);
free(rp->rg_segmap, M_VMPMAP);
rp->rg_segmap = NULL;
@@ -5834,7 +5842,10 @@
/*
* Might be a change: fetch old pte
*/
- tlb_flush_page(va);
+ if (pm->pm_ctx) {
+ setcontext4m(pm->pm_ctxnum);
+ tlb_flush_page(va);
+ }
tpte = pte[VA_SUN4M_VPG(va)];
if ((tpte & SRMMU_TETYPE) == SRMMU_TEPTE) {
@@ -5860,8 +5871,8 @@
*/
#ifdef DEBUG
if (pmapdebug & PDB_SWITCHMAP)
-printf("%s[%d]: pmap_enu: changing existing va(0x%x)=>pa(pte=0x%x) entry\n",
- curproc->p_comm, curproc->p_pid, (int)va, (int)pte);
+printf("%s[%d]: pmap_enu: changing existing va 0x%x: pte 0x%x=>0x%x\n",
+ curproc->p_comm, curproc->p_pid, (int)va, tpte, pteproto);
#endif
if ((tpte & SRMMU_PGTYPE) == PG_SUN4M_OBMEM) {
addr = ptoa( (tpte & SRMMU_PPNMASK) >>
@@ -6465,12 +6476,12 @@
setpgt4m(vpage_pte[1], dpte);
qcopy(sva, dva, NBPG); /* loads cache, so we must ... */
cache_flush_page((int)sva);
+ tlb_flush_page((int)sva);
setpgt4m(vpage_pte[0], SRMMU_TEINVALID);
+ tlb_flush_page((int)dva);
setpgt4m(vpage_pte[1], SRMMU_TEINVALID);
- tlb_flush_page((int)sva);
- tlb_flush_page((int)dva);
}
-#endif /* Sun4M */
+#endif /* SUN4M */
/*
* Turn a cdevsw d_mmap value into a byte address for pmap_enter.
@@ -6511,7 +6522,9 @@
if ((pte & SRMMU_PGTYPE) == PG_SUN4M_OBMEM)
cache_flush_page((int)va);
+
pa = ptoa((pte & SRMMU_PPNMASK) >> SRMMU_PPNSHIFT);
+
if ((pte & SRMMU_PGTYPE) == PG_SUN4M_OBMEM &&
managed(pa)) {
pv_changepte4m(pvhead(pa), 0, SRMMU_PG_C);
Home |
Main Index |
Thread Index |
Old Index