KEYS: Move the flags representing required permission to linux/key.h
[platform/adaptation/renesas_rcar/renesas_kernel.git] / security / selinux / hooks.c
index 4b34847..c8195b3 100644 (file)
@@ -470,6 +470,7 @@ next_inode:
                                list_entry(sbsec->isec_head.next,
                                           struct inode_security_struct, list);
                struct inode *inode = isec->inode;
+               list_del_init(&isec->list);
                spin_unlock(&sbsec->isec_lock);
                inode = igrab(inode);
                if (inode) {
@@ -478,7 +479,6 @@ next_inode:
                        iput(inode);
                }
                spin_lock(&sbsec->isec_lock);
-               list_del_init(&isec->list);
                goto next_inode;
        }
        spin_unlock(&sbsec->isec_lock);
@@ -668,7 +668,7 @@ static int selinux_set_mnt_opts(struct super_block *sb,
                if (flags[i] == SBLABEL_MNT)
                        continue;
                rc = security_context_to_sid(mount_options[i],
-                                            strlen(mount_options[i]), &sid);
+                                            strlen(mount_options[i]), &sid, GFP_KERNEL);
                if (rc) {
                        printk(KERN_WARNING "SELinux: security_context_to_sid"
                               "(%s) failed for (dev %s, type %s) errno=%d\n",
@@ -1418,15 +1418,33 @@ static int inode_doinit_with_dentry(struct inode *inode, struct dentry *opt_dent
                isec->sid = sbsec->sid;
 
                if ((sbsec->flags & SE_SBPROC) && !S_ISLNK(inode->i_mode)) {
-                       if (opt_dentry) {
-                               isec->sclass = inode_mode_to_security_class(inode->i_mode);
-                               rc = selinux_proc_get_sid(opt_dentry,
-                                                         isec->sclass,
-                                                         &sid);
-                               if (rc)
-                                       goto out_unlock;
-                               isec->sid = sid;
-                       }
+                       /* We must have a dentry to determine the label on
+                        * procfs inodes */
+                       if (opt_dentry)
+                               /* Called from d_instantiate or
+                                * d_splice_alias. */
+                               dentry = dget(opt_dentry);
+                       else
+                               /* Called from selinux_complete_init, try to
+                                * find a dentry. */
+                               dentry = d_find_alias(inode);
+                       /*
+                        * This can be hit on boot when a file is accessed
+                        * before the policy is loaded.  When we load policy we
+                        * may find inodes that have no dentry on the
+                        * sbsec->isec_head list.  No reason to complain as
+                        * these will get fixed up the next time we go through
+                        * inode_doinit() with a dentry, before these inodes
+                        * could be used again by userspace.
+                        */
+                       if (!dentry)
+                               goto out_unlock;
+                       isec->sclass = inode_mode_to_security_class(inode->i_mode);
+                       rc = selinux_proc_get_sid(dentry, isec->sclass, &sid);
+                       dput(dentry);
+                       if (rc)
+                               goto out_unlock;
+                       isec->sid = sid;
                }
                break;
        }
@@ -2489,7 +2507,8 @@ static int selinux_sb_remount(struct super_block *sb, void *data)
                if (flags[i] == SBLABEL_MNT)
                        continue;
                len = strlen(mount_options[i]);
-               rc = security_context_to_sid(mount_options[i], len, &sid);
+               rc = security_context_to_sid(mount_options[i], len, &sid,
+                                            GFP_KERNEL);
                if (rc) {
                        printk(KERN_WARNING "SELinux: security_context_to_sid"
                               "(%s) failed for (dev %s, type %s) errno=%d\n",
@@ -2893,7 +2912,7 @@ static int selinux_inode_setxattr(struct dentry *dentry, const char *name,
        if (rc)
                return rc;
 
-       rc = security_context_to_sid(value, size, &newsid);
+       rc = security_context_to_sid(value, size, &newsid, GFP_KERNEL);
        if (rc == -EINVAL) {
                if (!capable(CAP_MAC_ADMIN)) {
                        struct audit_buffer *ab;
@@ -3050,7 +3069,7 @@ static int selinux_inode_setsecurity(struct inode *inode, const char *name,
        if (!value || !size)
                return -EACCES;
 
-       rc = security_context_to_sid((void *)value, size, &newsid);
+       rc = security_context_to_sid((void *)value, size, &newsid, GFP_KERNEL);
        if (rc)
                return rc;
 
@@ -5529,7 +5548,7 @@ static int selinux_setprocattr(struct task_struct *p,
                        str[size-1] = 0;
                        size--;
                }
-               error = security_context_to_sid(value, size, &sid);
+               error = security_context_to_sid(value, size, &sid, GFP_KERNEL);
                if (error == -EINVAL && !strcmp(name, "fscreate")) {
                        if (!capable(CAP_MAC_ADMIN)) {
                                struct audit_buffer *ab;
@@ -5638,7 +5657,7 @@ static int selinux_secid_to_secctx(u32 secid, char **secdata, u32 *seclen)
 
 static int selinux_secctx_to_secid(const char *secdata, u32 seclen, u32 *secid)
 {
-       return security_context_to_sid(secdata, seclen, secid);
+       return security_context_to_sid(secdata, seclen, secid, GFP_KERNEL);
 }
 
 static void selinux_release_secctx(char *secdata, u32 seclen)
@@ -5704,7 +5723,7 @@ static void selinux_key_free(struct key *k)
 
 static int selinux_key_permission(key_ref_t key_ref,
                                  const struct cred *cred,
-                                 key_perm_t perm)
+                                 unsigned perm)
 {
        struct key *key;
        struct key_security_struct *ksec;