From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1752058AbcFUOPs (ORCPT ); Tue, 21 Jun 2016 10:15:48 -0400 Received: from szxga03-in.huawei.com ([119.145.14.66]:51502 "EHLO szxga03-in.huawei.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751975AbcFUOPr (ORCPT ); Tue, 21 Jun 2016 10:15:47 -0400 From: zhongjiang To: , CC: , Subject: [PATCH] mm/huge_memory: fix the memory leak due to the race Date: Tue, 21 Jun 2016 22:05:56 +0800 Message-ID: <1466517956-13875-1-git-send-email-zhongjiang@huawei.com> X-Mailer: git-send-email 1.7.12.4 MIME-Version: 1.0 Content-Type: text/plain X-Originating-IP: [10.175.102.37] X-CFilter-Loop: Reflected X-Mirapoint-Virus-RAPID-Raw: score=unknown(0), refid=str=0001.0A090203.57694A09.002F,ss=1,re=0.000,recu=0.000,reip=0.000,cl=1,cld=1,fgs=0, ip=0.0.0.0, so=2013-05-26 15:14:31, dmn=2013-03-21 17:37:32 X-Mirapoint-Loop-Id: 0c67ac814e3bf517f78202ab2f01586f Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org From: zhong jiang with great pressure, I run some test cases. As a result, I found that the THP is not freed, it is detected by check_mm(). BUG: Bad rss-counter state mm:ffff8827edb70000 idx:1 val:512 Consider the following race : CPU0 CPU1 __handle_mm_fault() wp_huge_pmd() do_huge_pmd_wp_page() pmdp_huge_clear_flush_notify() (pmd_none = true) exit_mmap() unmap_vmas() zap_pmd_range() pmd_none_or_trans_huge_or_clear_bad() (result in memory leak) set_pmd_at() because of CPU0 have allocated huge page before pmdp_huge_clear_notify, and it make the pmd entry to be null. Therefore, The memory leak can occur. The patch fix the scenario that the pmd entry can lead to be null. Signed-off-by: zhong jiang --- mm/huge_memory.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/mm/huge_memory.c b/mm/huge_memory.c index e10a4fe..ef04b94 100644 --- a/mm/huge_memory.c +++ b/mm/huge_memory.c @@ -1340,11 +1340,11 @@ alloc: pmd_t entry; entry = mk_huge_pmd(new_page, vma->vm_page_prot); entry = maybe_pmd_mkwrite(pmd_mkdirty(entry), vma); - pmdp_huge_clear_flush_notify(vma, haddr, pmd); + pmdp_invalidate(vma, haddr, pmd); page_add_new_anon_rmap(new_page, vma, haddr, true); mem_cgroup_commit_charge(new_page, memcg, false, true); lru_cache_add_active_or_unevictable(new_page, vma); - set_pmd_at(mm, haddr, pmd, entry); + pmd_populate(mm, pmd, entry); update_mmu_cache_pmd(vma, address, pmd); if (!page) { add_mm_counter(mm, MM_ANONPAGES, HPAGE_PMD_NR); -- 1.8.3.1