From mboxrd@z Thu Jan 1 00:00:00 1970 From: srinivasa Subject: Corruption in "b_assoc_buffer" list of bufferhead structure. Date: Tue, 09 May 2006 11:41:58 +0530 Message-ID: <446032AE.8030600@in.ibm.com> Mime-Version: 1.0 Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit Return-path: Received: from ausmtp04.au.ibm.com ([202.81.18.152]:35067 "EHLO ausmtp04.au.ibm.com") by vger.kernel.org with ESMTP id S1750759AbWEIRXh (ORCPT ); Tue, 9 May 2006 13:23:37 -0400 Received: from sd0208e0.au.ibm.com (d23rh904.au.ibm.com [202.81.18.202]) by ausmtp04.au.ibm.com (8.13.6/8.13.5) with ESMTP id k496LTqj120320 for ; Tue, 9 May 2006 16:21:59 +1000 Received: from d23av04.au.ibm.com (d23av04.au.ibm.com [9.190.250.237]) by sd0208e0.au.ibm.com (8.12.10/NCO/VER6.8) with ESMTP id k496Drs6190856 for ; Tue, 9 May 2006 16:14:03 +1000 Received: from d23av04.au.ibm.com (loopback [127.0.0.1]) by d23av04.au.ibm.com (8.12.11/8.13.3) with ESMTP id k496AWAs017597 for ; Tue, 9 May 2006 16:10:33 +1000 To: linux-fsdevel@vger.kernel.org, srinivds@in.ibm.com Sender: linux-fsdevel-owner@vger.kernel.org List-Id: linux-fsdevel.vger.kernel.org Hi I have got a oops in which "b_assoc_buffer" list of bufferhead is getting corrupted with strange values. It looks like a race problem ,which is not reproducable at everytime. When I looked in to the code,I found that "b_assoc_buffer" list is protected by a spinlock on "private_lock" of struct address_space. But there is one situation,where I suspect the chance of corruption. that is in try_to_free_buffers() of fs/buffer.c When mapping becomes NULL, there is no lock protection and if 2 or more processors passes this condition and executes drop_buffers() simultaneously, there may be a chance of list corruption. So could somebody please explain whether this situation exists or not? ====================================================================== int try_to_free_buffers(struct page *page) { struct address_space * const mapping = page->mapping; struct buffer_head *buffers_to_free = NULL; int ret = 0; BUG_ON(!PageLocked(page)); if (PageWriteback(page)) return 0; if (mapping == NULL) { /* can this still happen? */ <<<>>>>> ret = drop_buffers(page, &buffers_to_free); goto out; } spin_lock(&mapping->private_lock); ret = drop_buffers(page, &buffers_to_free); if (ret) { /* * If the filesystem writes its buffers by hand (eg ext3) * then we can have clean buffers against a dirty page. We * clean the page here; otherwise later reattachment of buffers * could encounter a non-uptodate page, which is unresolvable. * This only applies in the rare case where try_to_free_buffers * succeeds but the page is not freed. */ clear_page_dirty(page); } spin_unlock(&mapping->private_lock); ========================================================================================= Thanks Srinivasa DS