aboutsummaryrefslogtreecommitdiffstats
path: root/mm
diff options
context:
space:
mode:
authorYuanyuan Zhong <a6510c@motorola.com>2011-01-14 09:28:55 -0600
committerZiyan <jaraidaniel@gmail.com>2016-01-08 10:44:50 +0100
commit8a300ec0aa85c4520ee140dd6dfb8ef9f3c5a42f (patch)
tree27040d87681dc254639773a36149cca7e80b8140 /mm
parent95c015c61de96acca5bb4f3fd77f0cdab3322060 (diff)
downloadkernel_samsung_tuna-8a300ec0aa85c4520ee140dd6dfb8ef9f3c5a42f.tar.gz
kernel_samsung_tuna-8a300ec0aa85c4520ee140dd6dfb8ef9f3c5a42f.tar.bz2
kernel_samsung_tuna-8a300ec0aa85c4520ee140dd6dfb8ef9f3c5a42f.zip
mm:ashmem: avoid ashmem deadlock
This is propagation of change done in (CR). When system memory is low, allocating memory while holding the ashmem_mutex may try to directly reclaim memory. Then ashmem_shrink() is called in same thread. It will deadlock at acquiring ashmem_mutex. We end up with stack like this: Task name: app_process pid: 16442 cpu: 0 state: 0x2 exit_state: 0x0 stack base: 0xc876c000 Stack: [<c084ce20>] __schedule+0x664 [<c084dea4>] __mutex_lock_slowpath+0x220 [<c084ea48>] mutex_lock+0x20 [<c021f104>] ashmem_shrink+0x44 [<c01fe3a0>] shrink_slab+0x228 [<c01ff38c>] try_to_free_pages+0x3c8 [<c01f483c>] __alloc_pages_nodemask+0x4a8 [<c02236fc>] new_slab+0x70 [<c0224928>] __slab_alloc.clone.1+0x248 [<c0224bb4>] kmem_cache_alloc+0xa0 [<c020174c>] shmem_alloc_inode+0x14 [<c0243670>] alloc_inode+0x1c [<c02439e4>] new_inode_pseudo+0x8 [<c0243a24>] new_inode+0x8 [<c0200a0c>] shmem_get_inode+0x2c [<c0200c80>] shmem_file_setup+0x10c [<c021f030>] ashmem_mmap+0x8c [<c0212618>] mmap_region+0x2b8 [<c0212bc4>] sys_mmap_pgoff+0x8c [<c0106000>] ret_fast_syscall+0x0 This change lets ashmem_shrink() return failure if ashmem_mutex is not available. Memory will be reclaimed from others. Change-Id: I3b2193b6e4fca4eeafd558b919ba8a76894a33a1 Signed-off-by: Yuanyuan Zhong <a6510c@motorola.com> Reviewed-on: http://gerrit.pcs.mot.com/498700 Tested-by: Jira Key <JIRAKEY@motorola.com> Reviewed-by: Check Patch <CHEKPACH@motorola.com> Reviewed-by: Klocwork kwcheck <klocwork-kwcheck@sourceforge.mot.com> Reviewed-by: Jeffrey Carlyle <jeff.carlyle@motorola.com> Reviewed-on: http://gerrit.pcs.mot.com/520376 Tested-by: Jira Key <jirakey@motorola.com> Submit-Approved: Jira Key <jirakey@motorola.com>
Diffstat (limited to 'mm')
-rw-r--r--mm/ashmem.c3
1 files changed, 2 insertions, 1 deletions
diff --git a/mm/ashmem.c b/mm/ashmem.c
index c1078aa2972..62fab280cc7 100644
--- a/mm/ashmem.c
+++ b/mm/ashmem.c
@@ -364,7 +364,8 @@ static int ashmem_shrink(struct shrinker *s, struct shrink_control *sc)
if (!sc->nr_to_scan)
return lru_count;
- mutex_lock(&ashmem_mutex);
+ if (!mutex_trylock(&ashmem_mutex))
+ return -EBUSY;
list_for_each_entry_safe(range, next, &ashmem_lru_list, lru) {
struct inode *inode = range->asma->file->f_dentry->d_inode;
loff_t start = range->pgstart * PAGE_SIZE;