aboutsummaryrefslogtreecommitdiffstats
path: root/mm/mmap.c
diff options
context:
space:
mode:
authorDavidlohr Bueso <davidlohr@hp.com>2014-01-21 18:49:15 -0500
committerLinus Torvalds <torvalds@linux-foundation.org>2014-01-21 19:19:44 -0500
commit363ee17f0f405faff74d9aaf93d21d5f41d5102d (patch)
tree4ff07b1b36a024b455467ac78e07fec6f18a6780 /mm/mmap.c
parent49f0ce5f92321cdcf741e35f385669a421013cb7 (diff)
mm/mmap.c: add mlock_future_check() helper
Both do_brk and do_mmap_pgoff verify that we are actually capable of locking future pages if the corresponding VM_LOCKED flags are used. Encapsulate this logic into a single mlock_future_check() helper function. Signed-off-by: Davidlohr Bueso <davidlohr@hp.com> Cc: Rik van Riel <riel@redhat.com> Reviewed-by: Michel Lespinasse <walken@google.com> Cc: Vlastimil Babka <vbabka@suse.cz> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'mm/mmap.c')
-rw-r--r--mm/mmap.c45
1 files changed, 23 insertions, 22 deletions
diff --git a/mm/mmap.c b/mm/mmap.c
index 39552de6e1db..a0e7153a79e6 100644
--- a/mm/mmap.c
+++ b/mm/mmap.c
@@ -1191,6 +1191,24 @@ static inline unsigned long round_hint_to_min(unsigned long hint)
1191 return hint; 1191 return hint;
1192} 1192}
1193 1193
1194static inline int mlock_future_check(struct mm_struct *mm,
1195 unsigned long flags,
1196 unsigned long len)
1197{
1198 unsigned long locked, lock_limit;
1199
1200 /* mlock MCL_FUTURE? */
1201 if (flags & VM_LOCKED) {
1202 locked = len >> PAGE_SHIFT;
1203 locked += mm->locked_vm;
1204 lock_limit = rlimit(RLIMIT_MEMLOCK);
1205 lock_limit >>= PAGE_SHIFT;
1206 if (locked > lock_limit && !capable(CAP_IPC_LOCK))
1207 return -EAGAIN;
1208 }
1209 return 0;
1210}
1211
1194/* 1212/*
1195 * The caller must hold down_write(&current->mm->mmap_sem). 1213 * The caller must hold down_write(&current->mm->mmap_sem).
1196 */ 1214 */
@@ -1252,16 +1270,8 @@ unsigned long do_mmap_pgoff(struct file *file, unsigned long addr,
1252 if (!can_do_mlock()) 1270 if (!can_do_mlock())
1253 return -EPERM; 1271 return -EPERM;
1254 1272
1255 /* mlock MCL_FUTURE? */ 1273 if (mlock_future_check(mm, vm_flags, len))
1256 if (vm_flags & VM_LOCKED) { 1274 return -EAGAIN;
1257 unsigned long locked, lock_limit;
1258 locked = len >> PAGE_SHIFT;
1259 locked += mm->locked_vm;
1260 lock_limit = rlimit(RLIMIT_MEMLOCK);
1261 lock_limit >>= PAGE_SHIFT;
1262 if (locked > lock_limit && !capable(CAP_IPC_LOCK))
1263 return -EAGAIN;
1264 }
1265 1275
1266 if (file) { 1276 if (file) {
1267 struct inode *inode = file_inode(file); 1277 struct inode *inode = file_inode(file);
@@ -2592,18 +2602,9 @@ static unsigned long do_brk(unsigned long addr, unsigned long len)
2592 if (error & ~PAGE_MASK) 2602 if (error & ~PAGE_MASK)
2593 return error; 2603 return error;
2594 2604
2595 /* 2605 error = mlock_future_check(mm, mm->def_flags, len);
2596 * mlock MCL_FUTURE? 2606 if (error)
2597 */ 2607 return error;
2598 if (mm->def_flags & VM_LOCKED) {
2599 unsigned long locked, lock_limit;
2600 locked = len >> PAGE_SHIFT;
2601 locked += mm->locked_vm;
2602 lock_limit = rlimit(RLIMIT_MEMLOCK);
2603 lock_limit >>= PAGE_SHIFT;
2604 if (locked > lock_limit && !capable(CAP_IPC_LOCK))
2605 return -EAGAIN;
2606 }
2607 2608
2608 /* 2609 /*
2609 * mm->mmap_sem is required to protect against another thread 2610 * mm->mmap_sem is required to protect against another thread