patch-2.3.11 linux/include/asm-alpha/mmu_context.h
Next file: linux/include/asm-alpha/param.h
Previous file: linux/include/asm-alpha/hardirq.h
Back to the patch index
Back to the overall index
- Lines: 70
- Date:
Mon Jul 19 13:12:47 1999
- Orig file:
v2.3.10/linux/include/asm-alpha/mmu_context.h
- Orig date:
Tue Jun 22 10:46:52 1999
diff -u --recursive --new-file v2.3.10/linux/include/asm-alpha/mmu_context.h linux/include/asm-alpha/mmu_context.h
@@ -66,7 +66,11 @@
#endif /* __SMP__ */
#define WIDTH_HARDWARE_ASN 8
+#ifdef __SMP__
#define WIDTH_THIS_PROCESSOR 5
+#else
+#define WIDTH_THIS_PROCESSOR 0
+#endif
#define ASN_FIRST_VERSION (1UL << (WIDTH_THIS_PROCESSOR + WIDTH_HARDWARE_ASN))
#define HARDWARE_ASN_MASK ((1UL << WIDTH_HARDWARE_ASN) - 1)
@@ -95,12 +99,11 @@
unsigned long asn = cpu_last_asn(smp_processor_id());
unsigned long next = asn + 1;
- if ((next ^ asn) & ~MAX_ASN) {
+ if ((asn & HARDWARE_ASN_MASK) >= MAX_ASN) {
tbiap();
next = (asn & ~HARDWARE_ASN_MASK) + ASN_FIRST_VERSION;
}
cpu_last_asn(smp_processor_id()) = next;
- mm->context = next; /* full version + asn */
return next;
}
@@ -110,6 +113,12 @@
/* As described, ASN's are broken. But we can optimize for
switching between threads -- if the mm is unchanged from
current we needn't flush. */
+ /* ??? May not be needed because EV4 PALcode recognizes that
+ ASN's are broken and does a tbiap itself on swpctx, under
+ the "Must set ASN or flush" rule. At least this is true
+ for a 1992 SRM, reports Joseph Martin (jmartin@hlo.dec.com).
+ I'm going to leave this here anyway, just to Be Sure. -- r~ */
+
if (current->mm != p->mm)
tbiap();
}
@@ -119,17 +128,23 @@
{
/* Check if our ASN is of an older version, or on a different CPU,
and thus invalid. */
+ /* ??? If we have two threads on different cpus, we'll continually
+ fight over the context. Find a way to record a per-mm, per-cpu
+ value for the asn. */
- long asn = cpu_last_asn(smp_processor_id());
+ unsigned long asn = cpu_last_asn(smp_processor_id());
struct mm_struct *mm = p->mm;
- long mmc = mm->context;
+ unsigned long mmc = mm->context;
- if ((p->tss.mm_context ^ asn) & ~HARDWARE_ASN_MASK) {
- if ((mmc ^ asn) & ~HARDWARE_ASN_MASK)
- mmc = __get_new_mmu_context(p, mm);
- p->tss.mm_context = mmc;
- p->tss.asn = mmc & HARDWARE_ASN_MASK;
+ if ((mmc ^ asn) & ~HARDWARE_ASN_MASK) {
+ mmc = __get_new_mmu_context(p, mm);
+ mm->context = mmc;
}
+
+ /* Always update the PCB ASN. Another thread may have allocated
+ a new mm->context (via flush_tlb_mm) without the ASN serial
+ number wrapping. We have no way to detect when this is needed. */
+ p->tss.asn = mmc & HARDWARE_ASN_MASK;
}
#ifdef CONFIG_ALPHA_GENERIC
FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen (who was at: slshen@lbl.gov)