X-Git-Url: https://git.openpandora.org/cgi-bin/gitweb.cgi?p=pandora-kernel.git;a=blobdiff_plain;f=arch%2Farm%2Fmm%2Fcontext.c;h=fc84fcc743804d16241a99ee5cb1c86f650dd048;hp=9da43a0fdcdffc5ff09b4e8fd1bdf6d95ac0452b;hb=805f53f085346b6765eda02820721a14ce0d644f;hpb=901ea4a07988043ff8c6f4f275ab680a23b8bbcd diff --git a/arch/arm/mm/context.c b/arch/arm/mm/context.c index 9da43a0fdcdf..fc84fcc74380 100644 --- a/arch/arm/mm/context.c +++ b/arch/arm/mm/context.c @@ -14,7 +14,8 @@ #include #include -unsigned int cpu_last_asid = { 1 << ASID_BITS }; +static DEFINE_SPINLOCK(cpu_asid_lock); +unsigned int cpu_last_asid = ASID_FIRST_VERSION; /* * We fork()ed a process, and we need a new context for the child @@ -31,15 +32,16 @@ void __new_context(struct mm_struct *mm) { unsigned int asid; + spin_lock(&cpu_asid_lock); asid = ++cpu_last_asid; if (asid == 0) - asid = cpu_last_asid = 1 << ASID_BITS; + asid = cpu_last_asid = ASID_FIRST_VERSION; /* * If we've used up all our ASIDs, we need * to start a new version and flush the TLB. */ - if ((asid & ~ASID_MASK) == 0) { + if (unlikely((asid & ~ASID_MASK) == 0)) { asid = ++cpu_last_asid; /* set the reserved ASID before flushing the TLB */ asm("mcr p15, 0, %0, c13, c0, 1 @ set reserved context ID\n" @@ -47,7 +49,16 @@ void __new_context(struct mm_struct *mm) : "r" (0)); isb(); flush_tlb_all(); + if (icache_is_vivt_asid_tagged()) { + asm("mcr p15, 0, %0, c7, c5, 0 @ invalidate I-cache\n" + "mcr p15, 0, %0, c7, c5, 6 @ flush BTAC/BTB\n" + : + : "r" (0)); + dsb(); + } } + spin_unlock(&cpu_asid_lock); + mm->cpu_vm_mask = cpumask_of_cpu(smp_processor_id()); mm->context.id = asid; }