From: Mimi Zohar <zohar@us.ibm.com>
To: linux-security-module@vger.kernel.org
Cc: Mimi Zohar <zohar@linux.vnet.ibm.com>,
linux-kernel@vger.kernel.org, Al Viro <viro@ZenIV.linux.org.uk>,
Linus Torvalds <torvalds@linux-foundation.org>,
Mimi Zohar <zohar@us.ibm.com>
Subject: [PATCH] vfs: fix IMA lockdep circular locking dependency
Date: Sun, 13 May 2012 22:47:11 -0400 [thread overview]
Message-ID: <1336963631-3541-1-git-send-email-zohar@us.ibm.com> (raw)
From: Mimi Zohar <zohar@linux.vnet.ibm.com>
This patch has been updated to move the ima_file_mmap() call from
security_file_mmap() to the new vm_mmap() function.
---
The circular lockdep is caused by allocating the 'iint' for mmapped
files. Originally when an 'iint' was allocated for every inode
in inode_alloc_security(), before the inode was accessible, no
locking was necessary. Commits bc7d2a3e and 196f518 changed this
behavior and allocated the 'iint' on a per need basis, resulting in
the mmap_sem being taken before the i_mutex for mmapped files.
Possible unsafe locking scenario:
CPU0 CPU1
---- ----
lock(&mm->mmap_sem);
lock(&sb->s_type->i_mutex_key);
lock(&mm->mmap_sem);
lock(&sb->s_type->i_mutex_key);
The existing security_file_mmap() hook is after the mmap_sem is taken.
This patch moves the ima_file_mmap() call from security_file_mmap() to
prior to the mmap_sem being taken.
Changelog v2:
- With commit "6be5ceb VM: add "vm_mmap()" helper function", moving the
ima_file_mmap() call is simplified. This patch moves the ima_file_mmap()
call to vm_mmap(), and to binfmt_elf.c: elf_map().
Changelog v1:
- Instead of just pre-allocating the iint in a new hook, do ALL of the
work in the new/moved ima_file_mmap() hook. (Based on Eric Paris' suggestion.)
- Removed do_mmap_with_sem() helper function.
- export ima_file_mmap()
Signed-off-by: Mimi Zohar <zohar@us.ibm.com>
Acked-by: Eric Paris <eparis@redhat.com>
---
fs/binfmt_elf.c | 6 ++++++
mm/mmap.c | 11 +++++++++++
mm/nommu.c | 11 +++++++++++
security/integrity/ima/ima_main.c | 1 +
security/security.c | 7 +------
5 files changed, 30 insertions(+), 6 deletions(-)
diff --git a/fs/binfmt_elf.c b/fs/binfmt_elf.c
index 16f7354..0d0514f 100644
--- a/fs/binfmt_elf.c
+++ b/fs/binfmt_elf.c
@@ -28,6 +28,7 @@
#include <linux/highmem.h>
#include <linux/pagemap.h>
#include <linux/security.h>
+#include <linux/ima.h>
#include <linux/random.h>
#include <linux/elf.h>
#include <linux/utsname.h>
@@ -321,6 +322,7 @@ static unsigned long elf_map(struct file *filep, unsigned long addr,
unsigned long map_addr;
unsigned long size = eppnt->p_filesz + ELF_PAGEOFFSET(eppnt->p_vaddr);
unsigned long off = eppnt->p_offset - ELF_PAGEOFFSET(eppnt->p_vaddr);
+ unsigned long ret;
addr = ELF_PAGESTART(addr);
size = ELF_PAGEALIGN(size);
@@ -329,6 +331,10 @@ static unsigned long elf_map(struct file *filep, unsigned long addr,
if (!size)
return addr;
+ ret = ima_file_mmap(filep, prot);
+ if (ret < 0)
+ return ret;
+
down_write(¤t->mm->mmap_sem);
/*
* total_size is the size of the ELF (interpreter) image.
diff --git a/mm/mmap.c b/mm/mmap.c
index 848ef52..87e6948 100644
--- a/mm/mmap.c
+++ b/mm/mmap.c
@@ -20,6 +20,7 @@
#include <linux/fs.h>
#include <linux/personality.h>
#include <linux/security.h>
+#include <linux/ima.h>
#include <linux/hugetlb.h>
#include <linux/profile.h>
#include <linux/export.h>
@@ -1109,9 +1110,14 @@ unsigned long vm_mmap(struct file *file, unsigned long addr,
unsigned long ret;
struct mm_struct *mm = current->mm;
+ ret = ima_file_mmap(file, prot);
+ if (ret < 0)
+ goto err;
+
down_write(&mm->mmap_sem);
ret = do_mmap(file, addr, len, prot, flag, offset);
up_write(&mm->mmap_sem);
+err:
return ret;
}
EXPORT_SYMBOL(vm_mmap);
@@ -1147,10 +1153,15 @@ SYSCALL_DEFINE6(mmap_pgoff, unsigned long, addr, unsigned long, len,
flags &= ~(MAP_EXECUTABLE | MAP_DENYWRITE);
+ retval = ima_file_mmap(file, prot);
+ if (retval < 0)
+ goto err_out;
+
down_write(¤t->mm->mmap_sem);
retval = do_mmap_pgoff(file, addr, len, prot, flags, pgoff);
up_write(¤t->mm->mmap_sem);
+err_out:
if (file)
fput(file);
out:
diff --git a/mm/nommu.c b/mm/nommu.c
index bb8f4f0..2b13bd3 100644
--- a/mm/nommu.c
+++ b/mm/nommu.c
@@ -27,6 +27,7 @@
#include <linux/mount.h>
#include <linux/personality.h>
#include <linux/security.h>
+#include <linux/ima.h>
#include <linux/syscalls.h>
#include <linux/audit.h>
@@ -1490,9 +1491,14 @@ unsigned long vm_mmap(struct file *file, unsigned long addr,
unsigned long ret;
struct mm_struct *mm = current->mm;
+ ret = ima_file_mmap(file, prot);
+ if (ret < 0)
+ goto err;
+
down_write(&mm->mmap_sem);
ret = do_mmap(file, addr, len, prot, flag, offset);
up_write(&mm->mmap_sem);
+err:
return ret;
}
EXPORT_SYMBOL(vm_mmap);
@@ -1513,10 +1519,15 @@ SYSCALL_DEFINE6(mmap_pgoff, unsigned long, addr, unsigned long, len,
flags &= ~(MAP_EXECUTABLE | MAP_DENYWRITE);
+ retval = ima_file_mmap(file, prot);
+ if (retval < 0)
+ goto err_out;
+
down_write(¤t->mm->mmap_sem);
retval = do_mmap_pgoff(file, addr, len, prot, flags, pgoff);
up_write(¤t->mm->mmap_sem);
+err_out:
if (file)
fput(file);
out:
diff --git a/security/integrity/ima/ima_main.c b/security/integrity/ima/ima_main.c
index b17be79..91eda7f 100644
--- a/security/integrity/ima/ima_main.c
+++ b/security/integrity/ima/ima_main.c
@@ -176,6 +176,7 @@ int ima_file_mmap(struct file *file, unsigned long prot)
MAY_EXEC, FILE_MMAP);
return 0;
}
+EXPORT_SYMBOL_GPL(ima_file_mmap);
/**
* ima_bprm_check - based on policy, collect/store measurement.
diff --git a/security/security.c b/security/security.c
index bf619ff..e50bbf4 100644
--- a/security/security.c
+++ b/security/security.c
@@ -661,12 +661,7 @@ int security_file_mmap(struct file *file, unsigned long reqprot,
unsigned long prot, unsigned long flags,
unsigned long addr, unsigned long addr_only)
{
- int ret;
-
- ret = security_ops->file_mmap(file, reqprot, prot, flags, addr, addr_only);
- if (ret)
- return ret;
- return ima_file_mmap(file, prot);
+ return security_ops->file_mmap(file, reqprot, prot, flags, addr, addr_only);
}
int security_file_mprotect(struct vm_area_struct *vma, unsigned long reqprot,
--
1.7.7.6
next reply other threads:[~2012-05-14 2:47 UTC|newest]
Thread overview: 44+ messages / expand[flat|nested] mbox.gz Atom feed top
2012-05-14 2:47 Mimi Zohar [this message]
2012-05-15 0:29 ` James Morris
2012-05-15 0:51 ` Mimi Zohar
2012-05-15 15:14 ` James Morris
2012-05-15 16:06 ` Mimi Zohar
2012-05-15 17:19 ` Linus Torvalds
2012-05-15 18:36 ` Mimi Zohar
2012-05-15 18:41 ` Linus Torvalds
2012-05-15 19:42 ` Eric Paris
2012-05-15 20:07 ` Mimi Zohar
2012-05-15 21:43 ` Linus Torvalds
2012-05-16 0:37 ` Linus Torvalds
2012-05-16 0:42 ` Al Viro
2012-05-16 0:45 ` Linus Torvalds
2012-05-16 1:53 ` Linus Torvalds
2012-05-16 11:37 ` James Morris
2012-05-16 11:38 ` James Morris
2012-05-16 13:27 ` Mimi Zohar
2012-05-16 13:42 ` Eric Paris
2012-05-16 13:52 ` Mimi Zohar
2012-05-16 14:06 ` Eric Paris
2012-05-16 15:23 ` Linus Torvalds
2012-05-16 15:47 ` Mimi Zohar
2012-05-16 16:09 ` Linus Torvalds
2012-05-16 2:18 ` Al Viro
2012-05-23 21:18 ` Mimi Zohar
2012-05-30 4:34 ` Al Viro
2012-05-30 16:36 ` Al Viro
2012-05-30 19:42 ` Eric Paris
2012-05-30 20:24 ` Al Viro
2012-05-30 20:28 ` Linus Torvalds
2012-05-30 20:56 ` Al Viro
2012-05-30 21:04 ` Linus Torvalds
2012-05-30 21:36 ` Al Viro
2012-05-30 22:51 ` Linus Torvalds
2012-05-31 0:28 ` Al Viro
2012-05-31 0:40 ` Linus Torvalds
2012-05-31 0:56 ` Al Viro
2012-05-31 3:55 ` Mimi Zohar
2012-05-31 4:20 ` James Morris
2012-05-30 20:33 ` Mimi Zohar
2012-05-30 20:53 ` Al Viro
2012-05-16 14:13 ` Eric Paris
2012-05-16 15:13 ` Linus Torvalds
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1336963631-3541-1-git-send-email-zohar@us.ibm.com \
--to=zohar@us.ibm.com \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-security-module@vger.kernel.org \
--cc=torvalds@linux-foundation.org \
--cc=viro@ZenIV.linux.org.uk \
--cc=zohar@linux.vnet.ibm.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
all inboxes | Powered by JetHome®