[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[PATCH 2.5.63] Teach page_mapped about the anon flag
- To: Andrew Morton <akpm@digeo.com>
- Subject: [PATCH 2.5.63] Teach page_mapped about the anon flag
- From: Dave McCracken <dmccr@us.ibm.com>
- Date: Mon, 03 Mar 2003 15:06:21 -0600
- cc: linux-kernel@vger.kernel.org, linux-mm@kvack.org
- Fake-Sender: owner-linux-mm@kvack.org
- In-Reply-To: <20030227142450.1c6a6b72.akpm@digeo.com>
- Original-Recipient: rfc822;linux-mm-archive@humbolt.geo.uu.nl
- References: <20030227025900.1205425a.akpm@digeo.com><200302280822.09409.kernel@kolivas.org><20030227134403.776bf2e3.akpm@digeo.com><118810000.1046383273@baldur.austin.ibm.com><20030227142450.1c6a6b72.akpm@digeo.com>
- Sender: Rik van Riel <riel@nl.linux.org>
--On Thursday, February 27, 2003 14:24:50 -0800 Andrew Morton
<akpm@digeo.com> wrote:
> I'm just looking at page_mapped(). It is now implicitly assuming that the
> architecture's representation of a zero-count atomic_t is all-bits-zero.
>
> This is not true on sparc32 if some other CPU is in the middle of an
> atomic_foo() against that counter. Maybe the assumption is false on other
> architectures too.
>
> So page_mapped() really should be performing an atomic_read() if that is
> appropriate to the particular page. I guess this involves testing
> page->mapping. Which is stable only when the page is locked or
> mapping->page_lock is held.
>
> It appears that all page_mapped() callers are inside lock_page() at
> present, so a quick audit and addition of a comment would be appropriate
> there please.
I'm not at all confident that page_mapped() is adequately protected.
Here's a patch that explicitly handles the atomic_t case.
Dave McCracken
======================================================================
Dave McCracken IBM Linux Base Kernel Team 1-512-838-3059
dmccr@us.ibm.com T/L 678-3059
--- 2.5.63-objrmap/include/linux/mm.h 2003-02-27 15:58:34.000000000 -0600
+++ 2.5.63-objfix/include/linux/mm.h 2003-02-28 14:21:56.000000000 -0600
@@ -363,10 +363,16 @@
* Return true if this page is mapped into pagetables. Subtle: test pte.direct
* rather than pte.chain. Because sometimes pte.direct is 64-bit, and .chain
* is only 32-bit.
+ *
+ * If the page is an object-mapped page, we need to do an atomic read of
+ * pte.mapcount instead, since atomic values may not be zero in the upper bits.
*/
static inline int page_mapped(struct page *page)
{
- return page->pte.direct != 0;
+ if (PageAnon(page))
+ return page->pte.direct != 0;
+ else
+ return atomic_read(&page->pte.mapcount) != 0;
}
/*