* [PATCH 0/2] Fix ptrace software breakpoints
@ 2010-07-15 15:53 Will Deacon
2010-07-15 15:53 ` [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID Will Deacon
` (2 more replies)
0 siblings, 3 replies; 15+ messages in thread
From: Will Deacon @ 2010-07-15 15:53 UTC (permalink / raw)
To: linux-arm-kernel
When using GDB on a quad-core Cortex-A9 (Versatile Express) board, software
breakpoints do not work if the inferior is scheduled onto a different CPU from
the debugger.
When GDB changes the code of another context via the ptrace POKETEXT mechanism,
the I-cache must be invalidated before the inferior is allowed to resume. If a
copy-on-write is triggered by the copy_to_user_page function, the new page
mappings must be used by the inferior in order to pick up the new instructions.
This patch series addresses this problem by:
(a) Providing a workaround for a known TLB issue on some revisions of the Cortex-A9.
(b) Performing correct I-cache invalidation in the flush_ptrace_access code.
All feedback/comments/tested-bys welcome.
Cc: Rob Clark <rob@ti.com>
Cc: Catalin Marinas <catalin.marinas@arm.com>
Will Deacon (2):
ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a
faulty ASID
ARM: flush_ptrace_access: invalidate all I-caches
arch/arm/Kconfig | 12 ++++++++++++
arch/arm/include/asm/tlbflush.h | 8 ++++++++
arch/arm/mm/flush.c | 4 ++--
3 files changed, 22 insertions(+), 2 deletions(-)
^ permalink raw reply [flat|nested] 15+ messages in thread* [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID 2010-07-15 15:53 [PATCH 0/2] Fix ptrace software breakpoints Will Deacon @ 2010-07-15 15:53 ` Will Deacon 2010-07-15 15:53 ` [PATCH 2/2] ARM: flush_ptrace_access: invalidate all I-caches Will Deacon 2010-07-15 16:21 ` [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID Shilimkar, Santosh 2010-07-16 4:15 ` [PATCH 0/2] Fix ptrace software breakpoints Rob Clark 2010-07-27 1:30 ` Rob Clark 2 siblings, 2 replies; 15+ messages in thread From: Will Deacon @ 2010-07-15 15:53 UTC (permalink / raw) To: linux-arm-kernel On versions of the Cortex-A9 prior to r2p0, performing TLB invalidations by ASID match can result in the incorrect ASID being broadcast to other CPUs. As a consequence of this, the targetted TLB entries are not invalidated across the system. This workaround changes the TLB flushing routines to invalidate entries regardless of the ASID. Acked-by: Catalin Marinas <catalin.marinas@arm.com> Signed-off-by: Will Deacon <will.deacon@arm.com> --- arch/arm/Kconfig | 12 ++++++++++++ arch/arm/include/asm/tlbflush.h | 8 ++++++++ 2 files changed, 20 insertions(+), 0 deletions(-) diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig index 98922f7..4824fb4 100644 --- a/arch/arm/Kconfig +++ b/arch/arm/Kconfig @@ -1027,6 +1027,18 @@ config PL310_ERRATA_588369 is not correctly implemented in PL310 as clean lines are not invalidated as a result of these operations. Note that this errata uses Texas Instrument's secure monitor api. + +config ARM_ERRATA_720789 + bool "ARM errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID" + depends on CPU_V7 && SMP + help + This option enables the workaround for the 720789 Cortex-A9 (prior to + r2p0) erratum. A faulty ASID can be sent to the other CPUs for the + broadcasted CP15 TLB maintenance operations TLBIASIDIS and TLBIMVAIS. + As a consequence of this erratum, some TLB entries which should be + invalidated are not, resulting in an incoherency in the system page + tables. The workaround changes the TLB flushing routines to invalidate + entries regardless of the ASID. endmenu source "arch/arm/common/Kconfig" diff --git a/arch/arm/include/asm/tlbflush.h b/arch/arm/include/asm/tlbflush.h index bd863d8..33b546a 100644 --- a/arch/arm/include/asm/tlbflush.h +++ b/arch/arm/include/asm/tlbflush.h @@ -378,7 +378,11 @@ static inline void local_flush_tlb_mm(struct mm_struct *mm) if (tlb_flag(TLB_V6_I_ASID)) asm("mcr p15, 0, %0, c8, c5, 2" : : "r" (asid) : "cc"); if (tlb_flag(TLB_V7_UIS_ASID)) +#ifdef CONFIG_ARM_ERRATA_720789 + asm("mcr p15, 0, %0, c8, c3, 0" : : "r" (zero) : "cc"); +#else asm("mcr p15, 0, %0, c8, c3, 2" : : "r" (asid) : "cc"); +#endif if (tlb_flag(TLB_BTB)) { /* flush the branch target cache */ @@ -424,7 +428,11 @@ local_flush_tlb_page(struct vm_area_struct *vma, unsigned long uaddr) if (tlb_flag(TLB_V6_I_PAGE)) asm("mcr p15, 0, %0, c8, c5, 1" : : "r" (uaddr) : "cc"); if (tlb_flag(TLB_V7_UIS_PAGE)) +#ifdef CONFIG_ARM_ERRATA_720789 + asm("mcr p15, 0, %0, c8, c3, 3" : : "r" (uaddr & PAGE_MASK) : "cc"); +#else asm("mcr p15, 0, %0, c8, c3, 1" : : "r" (uaddr) : "cc"); +#endif if (tlb_flag(TLB_BTB)) { /* flush the branch target cache */ -- 1.6.3.3 ^ permalink raw reply related [flat|nested] 15+ messages in thread
* [PATCH 2/2] ARM: flush_ptrace_access: invalidate all I-caches 2010-07-15 15:53 ` [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID Will Deacon @ 2010-07-15 15:53 ` Will Deacon 2010-07-15 16:32 ` Russell King - ARM Linux 2010-07-15 16:21 ` [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID Shilimkar, Santosh 1 sibling, 1 reply; 15+ messages in thread From: Will Deacon @ 2010-07-15 15:53 UTC (permalink / raw) To: linux-arm-kernel copy_to_user_page can be used by access_process_vm to write to an executable page of a process using a mapping acquired by kmap. For systems with I-cache aliasing, flushing the I-cache using the Kernel mapping may leave stale data in the I-cache if the user mapping is of a different colour. This patch replaces the coherent_kern_range call in flush_ptrace_access with a D-cache flush followed by a system-wide I-cache invalidation. This is required on all systems where the size of a way in the I-cache is larger than PAGE_SIZE. Acked-by: Catalin Marinas <catalin.marinas@arm.com> Signed-off-by: Will Deacon <will.deacon@arm.com> --- arch/arm/mm/flush.c | 4 ++-- 1 files changed, 2 insertions(+), 2 deletions(-) diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c index c6844cb..45896a9 100644 --- a/arch/arm/mm/flush.c +++ b/arch/arm/mm/flush.c @@ -120,8 +120,8 @@ void flush_ptrace_access(struct vm_area_struct *vma, struct page *page, /* VIPT non-aliasing cache */ if (vma->vm_flags & VM_EXEC) { - unsigned long addr = (unsigned long)kaddr; - __cpuc_coherent_kern_range(addr, addr + len); + __cpuc_flush_dcache_area(kaddr, len); + __flush_icache_all(); #ifdef CONFIG_SMP if (cache_ops_need_broadcast()) smp_call_function(flush_ptrace_access_other, -- 1.6.3.3 ^ permalink raw reply related [flat|nested] 15+ messages in thread
* [PATCH 2/2] ARM: flush_ptrace_access: invalidate all I-caches 2010-07-15 15:53 ` [PATCH 2/2] ARM: flush_ptrace_access: invalidate all I-caches Will Deacon @ 2010-07-15 16:32 ` Russell King - ARM Linux 2010-07-15 16:43 ` Will Deacon 2010-08-04 11:24 ` Will Deacon 0 siblings, 2 replies; 15+ messages in thread From: Russell King - ARM Linux @ 2010-07-15 16:32 UTC (permalink / raw) To: linux-arm-kernel On Thu, Jul 15, 2010 at 04:53:58PM +0100, Will Deacon wrote: > copy_to_user_page can be used by access_process_vm to write to an > executable page of a process using a mapping acquired by kmap. > For systems with I-cache aliasing, flushing the I-cache using the > Kernel mapping may leave stale data in the I-cache if the user > mapping is of a different colour. > > This patch replaces the coherent_kern_range call in flush_ptrace_access > with a D-cache flush followed by a system-wide I-cache invalidation. > This is required on all systems where the size of a way in the I-cache > is larger than PAGE_SIZE. > > Acked-by: Catalin Marinas <catalin.marinas@arm.com> > Signed-off-by: Will Deacon <will.deacon@arm.com> > --- > arch/arm/mm/flush.c | 4 ++-- > 1 files changed, 2 insertions(+), 2 deletions(-) > > diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c > index c6844cb..45896a9 100644 > --- a/arch/arm/mm/flush.c > +++ b/arch/arm/mm/flush.c > @@ -120,8 +120,8 @@ void flush_ptrace_access(struct vm_area_struct *vma, struct page *page, > > /* VIPT non-aliasing cache */ > if (vma->vm_flags & VM_EXEC) { > - unsigned long addr = (unsigned long)kaddr; > - __cpuc_coherent_kern_range(addr, addr + len); > + __cpuc_flush_dcache_area(kaddr, len); > + __flush_icache_all(); NAK. If we have aliases in the I-cache, there's probably more places that need to be fixed - and in any case I think the VIPT aliasing case should be used in that instance. This code is for non-aliasing D and I caches, and works as follows. 1. We flush the data out of the D cache, line by line, on at least the local CPU (and optionally the other CPUs.) Since we disable preemption, we will own the cache lines. 2. We invalidate the I cache, line by line, on at least local CPU (and optionally the other CPUs.) 3. If the I-cache invalidate wasn't broadcast, we flush the entire I-cache on the other CPUs. So, what CPUs report themselves as having VIPT non-aliasing caches but actually have an aliasing I-cache? ^ permalink raw reply [flat|nested] 15+ messages in thread
* [PATCH 2/2] ARM: flush_ptrace_access: invalidate all I-caches 2010-07-15 16:32 ` Russell King - ARM Linux @ 2010-07-15 16:43 ` Will Deacon 2010-07-15 16:54 ` Catalin Marinas 2010-07-19 16:23 ` Will Deacon 2010-08-04 11:24 ` Will Deacon 1 sibling, 2 replies; 15+ messages in thread From: Will Deacon @ 2010-07-15 16:43 UTC (permalink / raw) To: linux-arm-kernel Hi Russell, > > diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c > > index c6844cb..45896a9 100644 > > --- a/arch/arm/mm/flush.c > > +++ b/arch/arm/mm/flush.c > > @@ -120,8 +120,8 @@ void flush_ptrace_access(struct vm_area_struct *vma, struct page *page, > > > > /* VIPT non-aliasing cache */ > > if (vma->vm_flags & VM_EXEC) { > > - unsigned long addr = (unsigned long)kaddr; > > - __cpuc_coherent_kern_range(addr, addr + len); > > + __cpuc_flush_dcache_area(kaddr, len); > > + __flush_icache_all(); > > NAK. > > If we have aliases in the I-cache, there's probably more places that > need to be fixed - and in any case I think the VIPT aliasing case > should be used in that instance. > > This code is for non-aliasing D and I caches, and works as follows. > > 1. We flush the data out of the D cache, line by line, on at least the > local CPU (and optionally the other CPUs.) Since we disable > preemption, we will own the cache lines. > > 2. We invalidate the I cache, line by line, on at least local CPU > (and optionally the other CPUs.) (1) and (2) are done in __cpuc_coherent_kern_range. The problem is that the (2) part doesn't deal with aliases and only invalidates for the given MVA. > 3. If the I-cache invalidate wasn't broadcast, we flush the entire > I-cache on the other CPUs. Yep. > So, what CPUs report themselves as having VIPT non-aliasing caches but > actually have an aliasing I-cache? As far as I understand, all ARM cores have aliasing I-caches if it's a VIPT cache with way size greater than the page size. The D-cache has additional logic for handling aliasing which is what the VIPT non-aliasing characteristics refer to. Will ^ permalink raw reply [flat|nested] 15+ messages in thread
* [PATCH 2/2] ARM: flush_ptrace_access: invalidate all I-caches 2010-07-15 16:43 ` Will Deacon @ 2010-07-15 16:54 ` Catalin Marinas 2010-07-19 16:23 ` Will Deacon 1 sibling, 0 replies; 15+ messages in thread From: Catalin Marinas @ 2010-07-15 16:54 UTC (permalink / raw) To: linux-arm-kernel On Thu, 2010-07-15 at 17:43 +0100, Will Deacon wrote: > Russell King wrote: > > So, what CPUs report themselves as having VIPT non-aliasing caches but > > actually have an aliasing I-cache? > > As far as I understand, all ARM cores have aliasing I-caches if it's a > VIPT cache with way size greater than the page size. The D-cache has > additional logic for handling aliasing which is what the VIPT non-aliasing > characteristics refer to. Just to confirm what Will said (and I checked this in the past with our lead architect) - if the CTR reports VIPT I-cache, it is a true VIPT I-cache with potential aliases if the way size is greater than the page size (e.g. on vexpress, C-A9 has 32K I-cache and 4 ways). On the D side, the VIPT on ARMv7 is always non-aliasing (e.g. it behaves like PIPT). Anyway, it's not that bad since most places where this matters use __flush_icache_all(). This includes my patches for cache maintenance via set_pte_at(). -- Catalin ^ permalink raw reply [flat|nested] 15+ messages in thread
* [PATCH 2/2] ARM: flush_ptrace_access: invalidate all I-caches 2010-07-15 16:43 ` Will Deacon 2010-07-15 16:54 ` Catalin Marinas @ 2010-07-19 16:23 ` Will Deacon 1 sibling, 0 replies; 15+ messages in thread From: Will Deacon @ 2010-07-19 16:23 UTC (permalink / raw) To: linux-arm-kernel Russell, > > > diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c > > > index c6844cb..45896a9 100644 > > > --- a/arch/arm/mm/flush.c > > > +++ b/arch/arm/mm/flush.c > > > @@ -120,8 +120,8 @@ void flush_ptrace_access(struct vm_area_struct *vma, struct page *page, > > > > > > /* VIPT non-aliasing cache */ > > > if (vma->vm_flags & VM_EXEC) { > > > - unsigned long addr = (unsigned long)kaddr; > > > - __cpuc_coherent_kern_range(addr, addr + len); > > > + __cpuc_flush_dcache_area(kaddr, len); > > > + __flush_icache_all(); > > > > NAK. > > > > If we have aliases in the I-cache, there's probably more places that > > need to be fixed - and in any case I think the VIPT aliasing case > > should be used in that instance. So I looked into this problem a bit more in order to confirm it's an aliasing issue. GDB sets breakpoints inside ld-linux.so so that it can control the loading of shared libraries and insert any pending breakpoints. If the inferior has a PID of 3233, we can see the dynamic loader living at 0x40000000: root at will-lucid-nfs:~/tmp# cat /proc/3233/maps ... 40000000-40016000 r-xp 00000000 00:0b 3493469 /lib/ld-2.11.1.so 40016000-40017000 rw-p 00000000 00:00 0 4001d000-4001f000 rw-p 00015000 00:0b 3493469 /lib/ld-2.11.1.so GDB tries to insert a breakpoint on __dl_debug_state, at address 0x40002590. Some examples of when this works (I hacked flush_ptrace_access to print uaddr and dst): [ 110.910000] writing to user address 0x40002590 using Kernel mapping 0xbfe6c590 ... [ 147.530000] writing to user address 0x40002590 using Kernel mapping 0xbfe7e590 Now, this can fail with a SIGILL: (gdb) start Temporary breakpoint 1 at 0x83b4: file test.c, line 7. Starting program: /root/tmp/test Program received signal SIGILL, Illegal instruction. 0x40002590 in ?? () from /lib/ld-linux.so.3 This happens when GDB has removed a breakpoint instruction, but it still exists in the I-cache because the mapping used to invalidate the relevant way was of a different colour. In dmesg, we see: [ 150.780000] writing to user address 0x40002590 using Kernel mapping 0xbfe8b590 The I-cache in use is a 4-way 32KB cache, so we need 13 bits to represent an index into an 8KB way and a byte index into the resulting line. Since the top bit is not invariant to address translation, we have two colours. Looking at the GDB examples: 0x40002590 and 0xbfe6c590 have bit 12 == 0, so they are the same colour. 0x40002590 and 0xbfe7e590 have bit 12 == 0, so they are the same colour. 0x40002590 and 0xbfe8b590 have bit 12 == 0 and bit 12 == 1 respectively. In the last case, the wrong colour is invalidated in the I-cache and a SIGILL occurs. This problem can be fixed either by invalidating the whole I-cache (which is what is done in the patch I posted) or we could invalidate the correct colour, but this would mean implementing something like kmap_coherent from the MIPS world. It would be good to get this fixed. Do you still object to my original patch or can I submit it to the patch system if I get some tested-bys? Thanks, Will ^ permalink raw reply [flat|nested] 15+ messages in thread
* [PATCH 2/2] ARM: flush_ptrace_access: invalidate all I-caches 2010-07-15 16:32 ` Russell King - ARM Linux 2010-07-15 16:43 ` Will Deacon @ 2010-08-04 11:24 ` Will Deacon 1 sibling, 0 replies; 15+ messages in thread From: Will Deacon @ 2010-08-04 11:24 UTC (permalink / raw) To: linux-arm-kernel Hi Russell, > Subject: Re: [PATCH 2/2] ARM: flush_ptrace_access: invalidate all I-caches > > On Thu, Jul 15, 2010 at 04:53:58PM +0100, Will Deacon wrote: > > copy_to_user_page can be used by access_process_vm to write to an > > executable page of a process using a mapping acquired by kmap. > > For systems with I-cache aliasing, flushing the I-cache using the > > Kernel mapping may leave stale data in the I-cache if the user > > mapping is of a different colour. > > > > This patch replaces the coherent_kern_range call in flush_ptrace_access > > with a D-cache flush followed by a system-wide I-cache invalidation. > > This is required on all systems where the size of a way in the I-cache > > is larger than PAGE_SIZE. > > > > Acked-by: Catalin Marinas <catalin.marinas@arm.com> > > Signed-off-by: Will Deacon <will.deacon@arm.com> > > --- > > arch/arm/mm/flush.c | 4 ++-- > > 1 files changed, 2 insertions(+), 2 deletions(-) > > > > diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c > > index c6844cb..45896a9 100644 > > --- a/arch/arm/mm/flush.c > > +++ b/arch/arm/mm/flush.c > > @@ -120,8 +120,8 @@ void flush_ptrace_access(struct vm_area_struct *vma, struct page *page, > > > > /* VIPT non-aliasing cache */ > > if (vma->vm_flags & VM_EXEC) { > > - unsigned long addr = (unsigned long)kaddr; > > - __cpuc_coherent_kern_range(addr, addr + len); > > + __cpuc_flush_dcache_area(kaddr, len); > > + __flush_icache_all(); > > NAK. > How about something like this instead?: diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c index c6844cb..6b03043 100644 --- a/arch/arm/mm/flush.c +++ b/arch/arm/mm/flush.c @@ -20,10 +20,9 @@ #include "mm.h" -#ifdef CONFIG_CPU_CACHE_VIPT - #define ALIAS_FLUSH_START 0xffff4000 +#ifdef CONFIG_CPU_CACHE_VIPT static void flush_pfn_alias(unsigned long pfn, unsigned long vaddr) { unsigned long to = ALIAS_FLUSH_START + (CACHE_COLOUR(vaddr) << PAGE_SHIFT); @@ -93,6 +92,18 @@ void flush_cache_page(struct vm_area_struct *vma, unsigned long user_addr, unsig #define flush_pfn_alias(pfn,vaddr) do { } while (0) #endif +static void flush_icache_alias(unsigned long pfn, unsigned long vaddr, unsigned long len) +{ + unsigned long colour = CACHE_COLOUR(vaddr); + unsigned long offset = vaddr & (PAGE_SIZE - 1); + unsigned long to; + + set_pte_ext(TOP_PTE(ALIAS_FLUSH_START) + colour, pfn_pte(pfn, PAGE_KERNEL), 0); + to = ALIAS_FLUSH_START + (colour << PAGE_SHIFT) + offset; + flush_tlb_kernel_page(to); + flush_icache_range(to, to + len); +} + #ifdef CONFIG_SMP static void flush_ptrace_access_other(void *args) { @@ -120,8 +131,7 @@ void flush_ptrace_access(struct vm_area_struct *vma, struct page *page, /* VIPT non-aliasing cache */ if (vma->vm_flags & VM_EXEC) { - unsigned long addr = (unsigned long)kaddr; - __cpuc_coherent_kern_range(addr, addr + len); + flush_icache_alias(page_to_pfn(page), uaddr, len); #ifdef CONFIG_SMP if (cache_ops_need_broadcast()) smp_call_function(flush_ptrace_access_other, That way we only use __flush_icache_all for non-aliasing D-caches in the case that we have to broadcast the flushing using IPI. Will ^ permalink raw reply related [flat|nested] 15+ messages in thread
* [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID 2010-07-15 15:53 ` [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID Will Deacon 2010-07-15 15:53 ` [PATCH 2/2] ARM: flush_ptrace_access: invalidate all I-caches Will Deacon @ 2010-07-15 16:21 ` Shilimkar, Santosh 2010-07-15 16:32 ` Will Deacon 1 sibling, 1 reply; 15+ messages in thread From: Shilimkar, Santosh @ 2010-07-15 16:21 UTC (permalink / raw) To: linux-arm-kernel Will, > -----Original Message----- > From: linux-arm-kernel-bounces at lists.infradead.org [mailto:linux-arm- > kernel-bounces at lists.infradead.org] On Behalf Of Will Deacon > Sent: Thursday, July 15, 2010 9:24 PM > To: linux-arm-kernel at lists.infradead.org > Cc: Will Deacon > Subject: [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can > broadcast a faulty ASID > > On versions of the Cortex-A9 prior to r2p0, performing TLB invalidations > by > ASID match can result in the incorrect ASID being broadcast to other CPUs. > As a consequence of this, the targetted TLB entries are not invalidated > across the system. > > This workaround changes the TLB flushing routines to invalidate entries > regardless of the ASID. > Just a curious question. How costly is this ? > Acked-by: Catalin Marinas <catalin.marinas@arm.com> > Signed-off-by: Will Deacon <will.deacon@arm.com> > --- > arch/arm/Kconfig | 12 ++++++++++++ > arch/arm/include/asm/tlbflush.h | 8 ++++++++ > 2 files changed, 20 insertions(+), 0 deletions(-) > > diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig > index 98922f7..4824fb4 100644 > --- a/arch/arm/Kconfig > +++ b/arch/arm/Kconfig > @@ -1027,6 +1027,18 @@ config PL310_ERRATA_588369 > is not correctly implemented in PL310 as clean lines are not > invalidated as a result of these operations. Note that this > errata > uses Texas Instrument's secure monitor api. > + > +config ARM_ERRATA_720789 > + bool "ARM errata: TLBIASIDIS and TLBIMVAIS operations can broadcast > a faulty ASID" > + depends on CPU_V7 && SMP > + help > + This option enables the workaround for the 720789 Cortex-A9 (prior > to > + r2p0) erratum. A faulty ASID can be sent to the other CPUs for the > + broadcasted CP15 TLB maintenance operations TLBIASIDIS and > TLBIMVAIS. > + As a consequence of this erratum, some TLB entries which should be > + invalidated are not, resulting in an incoherency in the system > page > + tables. The workaround changes the TLB flushing routines to > invalidate > + entries regardless of the ASID. > endmenu > > source "arch/arm/common/Kconfig" > diff --git a/arch/arm/include/asm/tlbflush.h > b/arch/arm/include/asm/tlbflush.h > index bd863d8..33b546a 100644 > --- a/arch/arm/include/asm/tlbflush.h > +++ b/arch/arm/include/asm/tlbflush.h > @@ -378,7 +378,11 @@ static inline void local_flush_tlb_mm(struct > mm_struct *mm) > if (tlb_flag(TLB_V6_I_ASID)) > asm("mcr p15, 0, %0, c8, c5, 2" : : "r" (asid) : "cc"); > if (tlb_flag(TLB_V7_UIS_ASID)) > +#ifdef CONFIG_ARM_ERRATA_720789 > + asm("mcr p15, 0, %0, c8, c3, 0" : : "r" (zero) : "cc"); > +#else > asm("mcr p15, 0, %0, c8, c3, 2" : : "r" (asid) : "cc"); > +#endif > > if (tlb_flag(TLB_BTB)) { > /* flush the branch target cache */ > @@ -424,7 +428,11 @@ local_flush_tlb_page(struct vm_area_struct *vma, > unsigned long uaddr) > if (tlb_flag(TLB_V6_I_PAGE)) > asm("mcr p15, 0, %0, c8, c5, 1" : : "r" (uaddr) : "cc"); > if (tlb_flag(TLB_V7_UIS_PAGE)) > +#ifdef CONFIG_ARM_ERRATA_720789 > + asm("mcr p15, 0, %0, c8, c3, 3" : : "r" (uaddr & PAGE_MASK) : > "cc"); > +#else > asm("mcr p15, 0, %0, c8, c3, 1" : : "r" (uaddr) : "cc"); > +#endif > > if (tlb_flag(TLB_BTB)) { > /* flush the branch target cache */ > -- > 1.6.3.3 > > > _______________________________________________ > linux-arm-kernel mailing list > linux-arm-kernel at lists.infradead.org > http://lists.infradead.org/mailman/listinfo/linux-arm-kernel ^ permalink raw reply [flat|nested] 15+ messages in thread
* [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID 2010-07-15 16:21 ` [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID Shilimkar, Santosh @ 2010-07-15 16:32 ` Will Deacon 2010-07-15 16:43 ` Shilimkar, Santosh 0 siblings, 1 reply; 15+ messages in thread From: Will Deacon @ 2010-07-15 16:32 UTC (permalink / raw) To: linux-arm-kernel Hi Santosh, > > Subject: [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can > > broadcast a faulty ASID > > > > On versions of the Cortex-A9 prior to r2p0, performing TLB invalidations > > by > > ASID match can result in the incorrect ASID being broadcast to other CPUs. > > As a consequence of this, the targetted TLB entries are not invalidated > > across the system. > > > > This workaround changes the TLB flushing routines to invalidate entries > > regardless of the ASID. > > > Just a curious question. How costly is this ? I think the cost really depends on whether or not the evicted TLB entries are available in the D-cache. If they are, then a TLB miss occurring because of this workaround will hit in the data cache and the overhead will be small. Missing in the D-cache is certainly going to add an overhead, but that depends on your memory system. Of course, this workaround should only be enabled on platforms that suffer from the erratum, where it's worth sacrificing a few cycles in order to get a working virtual memory system! Will ^ permalink raw reply [flat|nested] 15+ messages in thread
* [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID 2010-07-15 16:32 ` Will Deacon @ 2010-07-15 16:43 ` Shilimkar, Santosh 0 siblings, 0 replies; 15+ messages in thread From: Shilimkar, Santosh @ 2010-07-15 16:43 UTC (permalink / raw) To: linux-arm-kernel > -----Original Message----- > From: Will Deacon [mailto:will.deacon at arm.com] > Sent: Thursday, July 15, 2010 10:02 PM > To: Shilimkar, Santosh; linux-arm-kernel at lists.infradead.org > Subject: RE: [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations > can broadcast a faulty ASID > > Hi Santosh, > > > > Subject: [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations > can > > > broadcast a faulty ASID > > > > > > On versions of the Cortex-A9 prior to r2p0, performing TLB > invalidations > > > by > > > ASID match can result in the incorrect ASID being broadcast to other > CPUs. > > > As a consequence of this, the targetted TLB entries are not > invalidated > > > across the system. > > > > > > This workaround changes the TLB flushing routines to invalidate > entries > > > regardless of the ASID. > > > > > Just a curious question. How costly is this ? > > I think the cost really depends on whether or not the evicted TLB entries > are available in the D-cache. If they are, then a TLB miss occurring > because > of this workaround will hit in the data cache and the overhead will be > small. > Missing in the D-cache is certainly going to add an overhead, but that > depends > on your memory system. > > Of course, this workaround should only be enabled on platforms that suffer > from the erratum, where it's worth sacrificing a few cycles in order to > get > a working virtual memory system! Thanks for quick response!! Regards Santosh ^ permalink raw reply [flat|nested] 15+ messages in thread
* [PATCH 0/2] Fix ptrace software breakpoints 2010-07-15 15:53 [PATCH 0/2] Fix ptrace software breakpoints Will Deacon 2010-07-15 15:53 ` [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID Will Deacon @ 2010-07-16 4:15 ` Rob Clark 2010-07-20 17:23 ` Will Deacon 2010-07-27 1:30 ` Rob Clark 2 siblings, 1 reply; 15+ messages in thread From: Rob Clark @ 2010-07-16 4:15 UTC (permalink / raw) To: linux-arm-kernel fyi, my gdb test (git://github.com/robclark/gdb-test.git) seems to be passing reliable so far (I haven't seen it fail once yet) with these patches.. without these patches, it was triggering passing the breakpoing 90+% of the time. I'll keep you posted if I notice any issues, but so far so good! thx BR, -R On Jul 15, 2010, at 10:53 AM, Will Deacon wrote: > When using GDB on a quad-core Cortex-A9 (Versatile Express) board, software > breakpoints do not work if the inferior is scheduled onto a different CPU from > the debugger. > > When GDB changes the code of another context via the ptrace POKETEXT mechanism, > the I-cache must be invalidated before the inferior is allowed to resume. If a > copy-on-write is triggered by the copy_to_user_page function, the new page > mappings must be used by the inferior in order to pick up the new instructions. > > This patch series addresses this problem by: > > (a) Providing a workaround for a known TLB issue on some revisions of the Cortex-A9. > (b) Performing correct I-cache invalidation in the flush_ptrace_access code. > > All feedback/comments/tested-bys welcome. > > Cc: Rob Clark <rob@ti.com> > Cc: Catalin Marinas <catalin.marinas@arm.com> > > Will Deacon (2): > ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a > faulty ASID > ARM: flush_ptrace_access: invalidate all I-caches > > arch/arm/Kconfig | 12 ++++++++++++ > arch/arm/include/asm/tlbflush.h | 8 ++++++++ > arch/arm/mm/flush.c | 4 ++-- > 3 files changed, 22 insertions(+), 2 deletions(-) ^ permalink raw reply [flat|nested] 15+ messages in thread
* [PATCH 0/2] Fix ptrace software breakpoints 2010-07-16 4:15 ` [PATCH 0/2] Fix ptrace software breakpoints Rob Clark @ 2010-07-20 17:23 ` Will Deacon 0 siblings, 0 replies; 15+ messages in thread From: Will Deacon @ 2010-07-20 17:23 UTC (permalink / raw) To: linux-arm-kernel Hi Rob, > fyi, my gdb test (git://github.com/robclark/gdb-test.git) seems to be passing reliable so far (I > haven't seen it fail once yet) with these patches.. without these patches, it was triggering passing > the breakpoing 90+% of the time. > > I'll keep you posted if I notice any issues, but so far so good! Does this mean you haven't seen it fail yet :)? If so, any chance I could have a tested-by please? Will ^ permalink raw reply [flat|nested] 15+ messages in thread
* [PATCH 0/2] Fix ptrace software breakpoints 2010-07-15 15:53 [PATCH 0/2] Fix ptrace software breakpoints Will Deacon 2010-07-15 15:53 ` [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID Will Deacon 2010-07-16 4:15 ` [PATCH 0/2] Fix ptrace software breakpoints Rob Clark @ 2010-07-27 1:30 ` Rob Clark 2010-07-27 9:43 ` Will Deacon 2 siblings, 1 reply; 15+ messages in thread From: Rob Clark @ 2010-07-27 1:30 UTC (permalink / raw) To: linux-arm-kernel On 07/15/2010 10:53 AM, Will Deacon wrote: > When using GDB on a quad-core Cortex-A9 (Versatile Express) board, software > breakpoints do not work if the inferior is scheduled onto a different CPU from > the debugger. > > When GDB changes the code of another context via the ptrace POKETEXT mechanism, > the I-cache must be invalidated before the inferior is allowed to resume. If a > copy-on-write is triggered by the copy_to_user_page function, the new page > mappings must be used by the inferior in order to pick up the new instructions. > > This patch series addresses this problem by: > > (a) Providing a workaround for a known TLB issue on some revisions of the Cortex-A9. > (b) Performing correct I-cache invalidation in the flush_ptrace_access code. > > All feedback/comments/tested-bys welcome. > > Cc: Rob Clark<rob@ti.com> > Cc: Catalin Marinas<catalin.marinas@arm.com> > > Will Deacon (2): > ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a > faulty ASID > ARM: flush_ptrace_access: invalidate all I-caches > > arch/arm/Kconfig | 12 ++++++++++++ > arch/arm/include/asm/tlbflush.h | 8 ++++++++ > arch/arm/mm/flush.c | 4 ++-- > 3 files changed, 22 insertions(+), 2 deletions(-) > Tested on omap4430 (cortex-a9 SMP).. with this patchset I have yet to see it fail, in regular use nor in the test case I wrote to show the problem (git://github.com/robclark/gdb-test.git). Without these patches, I'd see SIGILL and missed breakpoints 90+% of the time in regular use of gdb (basically gdb was unusable unless I booted with nosmp or disabled cache), and 100% of the time in my gdb-test. Tested-by: Rob Clark<rob@ti.com> ^ permalink raw reply [flat|nested] 15+ messages in thread
* [PATCH 0/2] Fix ptrace software breakpoints 2010-07-27 1:30 ` Rob Clark @ 2010-07-27 9:43 ` Will Deacon 0 siblings, 0 replies; 15+ messages in thread From: Will Deacon @ 2010-07-27 9:43 UTC (permalink / raw) To: linux-arm-kernel Hi Rob, > > Will Deacon (2): > > ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a > > faulty ASID > > ARM: flush_ptrace_access: invalidate all I-caches > > > > arch/arm/Kconfig | 12 ++++++++++++ > > arch/arm/include/asm/tlbflush.h | 8 ++++++++ > > arch/arm/mm/flush.c | 4 ++-- > > 3 files changed, 22 insertions(+), 2 deletions(-) > > > > Tested on omap4430 (cortex-a9 SMP).. with this patchset I have yet to > see it fail, in regular use nor in the test case I wrote to show the > problem (git://github.com/robclark/gdb-test.git). Without these > patches, I'd see SIGILL and missed breakpoints 90+% of the time in > regular use of gdb (basically gdb was unusable unless I booted with > nosmp or disabled cache), and 100% of the time in my gdb-test. > > Tested-by: Rob Clark<rob@ti.com> Thanks for testing this. I've seen the same results on my Versatile Express board running Ubuntu Lucid. Russell - can I submit these to the patch system please or do you have any outstanding concerns? Cheers, Will ^ permalink raw reply [flat|nested] 15+ messages in thread
end of thread, other threads:[~2010-08-04 11:24 UTC | newest] Thread overview: 15+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2010-07-15 15:53 [PATCH 0/2] Fix ptrace software breakpoints Will Deacon 2010-07-15 15:53 ` [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID Will Deacon 2010-07-15 15:53 ` [PATCH 2/2] ARM: flush_ptrace_access: invalidate all I-caches Will Deacon 2010-07-15 16:32 ` Russell King - ARM Linux 2010-07-15 16:43 ` Will Deacon 2010-07-15 16:54 ` Catalin Marinas 2010-07-19 16:23 ` Will Deacon 2010-08-04 11:24 ` Will Deacon 2010-07-15 16:21 ` [PATCH 1/2] ARM: errata: TLBIASIDIS and TLBIMVAIS operations can broadcast a faulty ASID Shilimkar, Santosh 2010-07-15 16:32 ` Will Deacon 2010-07-15 16:43 ` Shilimkar, Santosh 2010-07-16 4:15 ` [PATCH 0/2] Fix ptrace software breakpoints Rob Clark 2010-07-20 17:23 ` Will Deacon 2010-07-27 1:30 ` Rob Clark 2010-07-27 9:43 ` Will Deacon
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for NNTP newsgroup(s).