* [RFC] arm/mm: add a protection when flushing anonymous pages
@ 2012-10-01 3:08 Jason Lin
2012-10-01 3:50 ` Jason Lin
0 siblings, 1 reply; 7+ messages in thread
From: Jason Lin @ 2012-10-01 3:08 UTC (permalink / raw)
To: linux-arm-kernel
Dear all:
When I do LTP direct I/O tests, it produced a cache coherence issue
caused by flush_pfn_alias() (arch/arm/mm/flush.c).
I think we should to disable preemption or lock before setting page
table and enable preemption or unlock after flushing pages
Any comments are appreciated.
Thanks.
^ permalink raw reply [flat|nested] 7+ messages in thread
* [RFC] arm/mm: add a protection when flushing anonymous pages
2012-10-01 3:08 [RFC] arm/mm: add a protection when flushing anonymous pages Jason Lin
@ 2012-10-01 3:50 ` Jason Lin
2012-10-02 7:07 ` Andrew Yan-Pai Chen
0 siblings, 1 reply; 7+ messages in thread
From: Jason Lin @ 2012-10-01 3:50 UTC (permalink / raw)
To: linux-arm-kernel
Dear all:
By the way, I used the CPU with VIPT cache.
Thanks.
2012/10/1 Jason Lin <kernel.jason@gmail.com>:
> Dear all:
> When I do LTP direct I/O tests, it produced a cache coherence issue
> caused by flush_pfn_alias() (arch/arm/mm/flush.c).
> I think we should to disable preemption or lock before setting page
> table and enable preemption or unlock after flushing pages
>
> Any comments are appreciated.
> Thanks.
^ permalink raw reply [flat|nested] 7+ messages in thread
* [RFC] arm/mm: add a protection when flushing anonymous pages
2012-10-01 3:50 ` Jason Lin
@ 2012-10-02 7:07 ` Andrew Yan-Pai Chen
2012-10-05 7:55 ` Andrew Yan-Pai Chen
2012-10-05 9:10 ` Russell King - ARM Linux
0 siblings, 2 replies; 7+ messages in thread
From: Andrew Yan-Pai Chen @ 2012-10-02 7:07 UTC (permalink / raw)
To: linux-arm-kernel
On Mon, Oct 1, 2012 at 11:50 AM, Jason Lin <kernel.jason@gmail.com> wrote:
>
> Dear all:
> By the way, I used the CPU with VIPT cache.
> Thanks.
>
> 2012/10/1 Jason Lin <kernel.jason@gmail.com>:
> > Dear all:
> > When I do LTP direct I/O tests, it produced a cache coherence issue
> > caused by flush_pfn_alias() (arch/arm/mm/flush.c).
> > I think we should to disable preemption or lock before setting page
> > table and enable preemption or unlock after flushing pages
> >
> > Any comments are appreciated.
> > Thanks.
>
> _______________________________________________
> linux-arm-kernel mailing list
> linux-arm-kernel at lists.infradead.org
> http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
[RFC PATCH] make flush_pfn_alias() nonpreemptible
Since flush_pfn_alias() is preemptible, it is possible to be
preempted just after set_top_pte() is done. If the process
which preempts the previous happened to invoke flush_pfn_alias()
with the same colour vaddr as that of the previous, the same
top pte will be overwritten. When switching back to the previous,
it attempts to flush cache lines with incorrect mapping. Then
no lines (or wrong lines) will be flushed because of the nature
of vipt caches.
diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c
index 40ca11e..bd07918 100644
--- a/arch/arm/mm/flush.c
+++ b/arch/arm/mm/flush.c
@@ -27,6 +27,8 @@ static void flush_pfn_alias(unsigned long pfn,
unsigned long vaddr)
unsigned long to = FLUSH_ALIAS_START + (CACHE_COLOUR(vaddr) <<
PAGE_SHIFT);
const int zero = 0;
+ preempt_disable();
+
set_top_pte(to, pfn_pte(pfn, PAGE_KERNEL));
asm( "mcrr p15, 0, %1, %0, c14\n"
@@ -34,6 +36,8 @@ static void flush_pfn_alias(unsigned long pfn,
unsigned long vaddr)
:
: "r" (to), "r" (to + PAGE_SIZE - L1_CACHE_BYTES), "r" (zero)
: "cc");
+
+ preempt_enable();
}
--
Regards,
Andrew
^ permalink raw reply related [flat|nested] 7+ messages in thread
* [RFC] arm/mm: add a protection when flushing anonymous pages
2012-10-02 7:07 ` Andrew Yan-Pai Chen
@ 2012-10-05 7:55 ` Andrew Yan-Pai Chen
2012-10-05 9:10 ` Russell King - ARM Linux
1 sibling, 0 replies; 7+ messages in thread
From: Andrew Yan-Pai Chen @ 2012-10-05 7:55 UTC (permalink / raw)
To: linux-arm-kernel
On Tue, Oct 2, 2012 at 3:07 PM, Andrew Yan-Pai Chen
<yanpai.chen@gmail.com> wrote:
> On Mon, Oct 1, 2012 at 11:50 AM, Jason Lin <kernel.jason@gmail.com> wrote:
>>
>> Dear all:
>> By the way, I used the CPU with VIPT cache.
>> Thanks.
>>
>> 2012/10/1 Jason Lin <kernel.jason@gmail.com>:
>> > Dear all:
>> > When I do LTP direct I/O tests, it produced a cache coherence issue
>> > caused by flush_pfn_alias() (arch/arm/mm/flush.c).
>> > I think we should to disable preemption or lock before setting page
>> > table and enable preemption or unlock after flushing pages
>> >
>> > Any comments are appreciated.
>> > Thanks.
>>
>> _______________________________________________
>> linux-arm-kernel mailing list
>> linux-arm-kernel at lists.infradead.org
>> http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
>
> [RFC PATCH] make flush_pfn_alias() nonpreemptible
>
> Since flush_pfn_alias() is preemptible, it is possible to be
> preempted just after set_top_pte() is done. If the process
> which preempts the previous happened to invoke flush_pfn_alias()
> with the same colour vaddr as that of the previous, the same
> top pte will be overwritten. When switching back to the previous,
> it attempts to flush cache lines with incorrect mapping. Then
> no lines (or wrong lines) will be flushed because of the nature
> of vipt caches.
>
> diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c
> index 40ca11e..bd07918 100644
> --- a/arch/arm/mm/flush.c
> +++ b/arch/arm/mm/flush.c
> @@ -27,6 +27,8 @@ static void flush_pfn_alias(unsigned long pfn,
> unsigned long vaddr)
> unsigned long to = FLUSH_ALIAS_START + (CACHE_COLOUR(vaddr) <<
> PAGE_SHIFT);
> const int zero = 0;
>
> + preempt_disable();
> +
> set_top_pte(to, pfn_pte(pfn, PAGE_KERNEL));
>
> asm( "mcrr p15, 0, %1, %0, c14\n"
> @@ -34,6 +36,8 @@ static void flush_pfn_alias(unsigned long pfn,
> unsigned long vaddr)
> :
> : "r" (to), "r" (to + PAGE_SIZE - L1_CACHE_BYTES), "r" (zero)
> : "cc");
> +
> + preempt_enable();
> }
>
> --
> Regards,
> Andrew
Hi Russell,
We met the problem when running the direct I/O test (diotest03) in LTP
testsuite on PB1176.
And we got the error messages:
bufcmp: offset 224: Expected: 0x1b, got 0x1a
diotest03 1 TFAIL : comparsion failed; child=11 offset=1069056
diotest03 2 TFAIL : Read Direct-child 11 failed
...
The error was gone after applying this patch.
Any idea would be appreciated.
--
Regards,
Andrew
^ permalink raw reply [flat|nested] 7+ messages in thread
* [RFC] arm/mm: add a protection when flushing anonymous pages
2012-10-02 7:07 ` Andrew Yan-Pai Chen
2012-10-05 7:55 ` Andrew Yan-Pai Chen
@ 2012-10-05 9:10 ` Russell King - ARM Linux
2012-10-05 10:09 ` Andrew Yan-Pai Chen
1 sibling, 1 reply; 7+ messages in thread
From: Russell King - ARM Linux @ 2012-10-05 9:10 UTC (permalink / raw)
To: linux-arm-kernel
On Tue, Oct 02, 2012 at 03:07:33PM +0800, Andrew Yan-Pai Chen wrote:
> [RFC PATCH] make flush_pfn_alias() nonpreemptible
>
> Since flush_pfn_alias() is preemptible, it is possible to be
> preempted just after set_top_pte() is done. If the process
> which preempts the previous happened to invoke flush_pfn_alias()
> with the same colour vaddr as that of the previous, the same
> top pte will be overwritten. When switching back to the previous,
> it attempts to flush cache lines with incorrect mapping. Then
> no lines (or wrong lines) will be flushed because of the nature
> of vipt caches.
>
> diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c
> index 40ca11e..bd07918 100644
> --- a/arch/arm/mm/flush.c
> +++ b/arch/arm/mm/flush.c
> @@ -27,6 +27,8 @@ static void flush_pfn_alias(unsigned long pfn,
> unsigned long vaddr)
> unsigned long to = FLUSH_ALIAS_START + (CACHE_COLOUR(vaddr) <<
> PAGE_SHIFT);
> const int zero = 0;
>
> + preempt_disable();
> +
> set_top_pte(to, pfn_pte(pfn, PAGE_KERNEL));
>
> asm( "mcrr p15, 0, %1, %0, c14\n"
> @@ -34,6 +36,8 @@ static void flush_pfn_alias(unsigned long pfn,
> unsigned long vaddr)
> :
> : "r" (to), "r" (to + PAGE_SIZE - L1_CACHE_BYTES), "r" (zero)
> : "cc");
> +
> + preempt_enable();
> }
This looks like it's quite correct, but if you look at the file a little
deeper, you'll notice that flush_icache_alias() potentially suffers the
same issue.
They should probably both also have a comment indicating that they're not
to be called for SMP setups (because there's no locking for that.)
^ permalink raw reply [flat|nested] 7+ messages in thread
* [RFC] arm/mm: add a protection when flushing anonymous pages
2012-10-05 9:10 ` Russell King - ARM Linux
@ 2012-10-05 10:09 ` Andrew Yan-Pai Chen
2012-10-09 6:01 ` Andrew Yan-Pai Chen
0 siblings, 1 reply; 7+ messages in thread
From: Andrew Yan-Pai Chen @ 2012-10-05 10:09 UTC (permalink / raw)
To: linux-arm-kernel
On Fri, Oct 5, 2012 at 5:10 PM, Russell King - ARM Linux
<linux@arm.linux.org.uk> wrote:
> On Tue, Oct 02, 2012 at 03:07:33PM +0800, Andrew Yan-Pai Chen wrote:
>> [RFC PATCH] make flush_pfn_alias() nonpreemptible
>>
>> Since flush_pfn_alias() is preemptible, it is possible to be
>> preempted just after set_top_pte() is done. If the process
>> which preempts the previous happened to invoke flush_pfn_alias()
>> with the same colour vaddr as that of the previous, the same
>> top pte will be overwritten. When switching back to the previous,
>> it attempts to flush cache lines with incorrect mapping. Then
>> no lines (or wrong lines) will be flushed because of the nature
>> of vipt caches.
>>
>> diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c
>> index 40ca11e..bd07918 100644
>> --- a/arch/arm/mm/flush.c
>> +++ b/arch/arm/mm/flush.c
>> @@ -27,6 +27,8 @@ static void flush_pfn_alias(unsigned long pfn,
>> unsigned long vaddr)
>> unsigned long to = FLUSH_ALIAS_START + (CACHE_COLOUR(vaddr) <<
>> PAGE_SHIFT);
>> const int zero = 0;
>>
>> + preempt_disable();
>> +
>> set_top_pte(to, pfn_pte(pfn, PAGE_KERNEL));
>>
>> asm( "mcrr p15, 0, %1, %0, c14\n"
>> @@ -34,6 +36,8 @@ static void flush_pfn_alias(unsigned long pfn,
>> unsigned long vaddr)
>> :
>> : "r" (to), "r" (to + PAGE_SIZE - L1_CACHE_BYTES), "r" (zero)
>> : "cc");
>> +
>> + preempt_enable();
>> }
>
> This looks like it's quite correct, but if you look at the file a little
> deeper, you'll notice that flush_icache_alias() potentially suffers the
> same issue.
>
> They should probably both also have a comment indicating that they're not
> to be called for SMP setups (because there's no locking for that.)
OK. I will resend the patch later.
Thanks!
--
Regards,
Andrew
^ permalink raw reply [flat|nested] 7+ messages in thread
* [RFC] arm/mm: add a protection when flushing anonymous pages
2012-10-05 10:09 ` Andrew Yan-Pai Chen
@ 2012-10-09 6:01 ` Andrew Yan-Pai Chen
0 siblings, 0 replies; 7+ messages in thread
From: Andrew Yan-Pai Chen @ 2012-10-09 6:01 UTC (permalink / raw)
To: linux-arm-kernel
On Fri, Oct 5, 2012 at 6:09 PM, Andrew Yan-Pai Chen
<yanpai.chen@gmail.com> wrote:
> On Fri, Oct 5, 2012 at 5:10 PM, Russell King - ARM Linux
> <linux@arm.linux.org.uk> wrote:
>> On Tue, Oct 02, 2012 at 03:07:33PM +0800, Andrew Yan-Pai Chen wrote:
>>> [RFC PATCH] make flush_pfn_alias() nonpreemptible
>>>
>>> Since flush_pfn_alias() is preemptible, it is possible to be
>>> preempted just after set_top_pte() is done. If the process
>>> which preempts the previous happened to invoke flush_pfn_alias()
>>> with the same colour vaddr as that of the previous, the same
>>> top pte will be overwritten. When switching back to the previous,
>>> it attempts to flush cache lines with incorrect mapping. Then
>>> no lines (or wrong lines) will be flushed because of the nature
>>> of vipt caches.
>>>
>>> diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c
>>> index 40ca11e..bd07918 100644
>>> --- a/arch/arm/mm/flush.c
>>> +++ b/arch/arm/mm/flush.c
>>> @@ -27,6 +27,8 @@ static void flush_pfn_alias(unsigned long pfn,
>>> unsigned long vaddr)
>>> unsigned long to = FLUSH_ALIAS_START + (CACHE_COLOUR(vaddr) <<
>>> PAGE_SHIFT);
>>> const int zero = 0;
>>>
>>> + preempt_disable();
>>> +
>>> set_top_pte(to, pfn_pte(pfn, PAGE_KERNEL));
>>>
>>> asm( "mcrr p15, 0, %1, %0, c14\n"
>>> @@ -34,6 +36,8 @@ static void flush_pfn_alias(unsigned long pfn,
>>> unsigned long vaddr)
>>> :
>>> : "r" (to), "r" (to + PAGE_SIZE - L1_CACHE_BYTES), "r" (zero)
>>> : "cc");
>>> +
>>> + preempt_enable();
>>> }
>>
>> This looks like it's quite correct, but if you look at the file a little
>> deeper, you'll notice that flush_icache_alias() potentially suffers the
>> same issue.
>>
>> They should probably both also have a comment indicating that they're not
>> to be called for SMP setups (because there's no locking for that.)
>
> OK. I will resend the patch later.
> Thanks!
>
> --
> Regards,
> Andrew
Hi Russell,
Is flush_icache_alias() not to be called for SMP setups?
It seems that processors with a vipt non-aliasing D-cache but a vipt
aliasing I-cache
(such like cortex-a9) will call this function.
So perhaps we should have a lock in this case?
--
Regards,
Andrew
^ permalink raw reply [flat|nested] 7+ messages in thread
end of thread, other threads:[~2012-10-09 6:01 UTC | newest]
Thread overview: 7+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2012-10-01 3:08 [RFC] arm/mm: add a protection when flushing anonymous pages Jason Lin
2012-10-01 3:50 ` Jason Lin
2012-10-02 7:07 ` Andrew Yan-Pai Chen
2012-10-05 7:55 ` Andrew Yan-Pai Chen
2012-10-05 9:10 ` Russell King - ARM Linux
2012-10-05 10:09 ` Andrew Yan-Pai Chen
2012-10-09 6:01 ` Andrew Yan-Pai Chen
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).