diff options
| -rw-r--r-- | security/selinux/hooks.c | 38 | ||||
| -rw-r--r-- | security/selinux/include/objsec.h | 2 | ||||
| -rw-r--r-- | security/selinux/include/security.h | 6 |
3 files changed, 24 insertions, 22 deletions
diff --git a/security/selinux/hooks.c b/security/selinux/hooks.c index 00815973d412..473adc5f4f9a 100644 --- a/security/selinux/hooks.c +++ b/security/selinux/hooks.c | |||
| @@ -431,7 +431,7 @@ static int sb_finish_set_opts(struct super_block *sb) | |||
| 431 | } | 431 | } |
| 432 | } | 432 | } |
| 433 | 433 | ||
| 434 | sbsec->initialized = 1; | 434 | sbsec->flags |= SE_SBINITIALIZED; |
| 435 | 435 | ||
| 436 | if (sbsec->behavior > ARRAY_SIZE(labeling_behaviors)) | 436 | if (sbsec->behavior > ARRAY_SIZE(labeling_behaviors)) |
| 437 | printk(KERN_ERR "SELinux: initialized (dev %s, type %s), unknown behavior\n", | 437 | printk(KERN_ERR "SELinux: initialized (dev %s, type %s), unknown behavior\n", |
| @@ -487,17 +487,13 @@ static int selinux_get_mnt_opts(const struct super_block *sb, | |||
| 487 | 487 | ||
| 488 | security_init_mnt_opts(opts); | 488 | security_init_mnt_opts(opts); |
| 489 | 489 | ||
| 490 | if (!sbsec->initialized) | 490 | if (!(sbsec->flags & SE_SBINITIALIZED)) |
| 491 | return -EINVAL; | 491 | return -EINVAL; |
| 492 | 492 | ||
| 493 | if (!ss_initialized) | 493 | if (!ss_initialized) |
| 494 | return -EINVAL; | 494 | return -EINVAL; |
| 495 | 495 | ||
| 496 | /* | 496 | tmp = sbsec->flags & SE_MNTMASK; |
| 497 | * if we ever use sbsec flags for anything other than tracking mount | ||
| 498 | * settings this is going to need a mask | ||
| 499 | */ | ||
| 500 | tmp = sbsec->flags; | ||
| 501 | /* count the number of mount options for this sb */ | 497 | /* count the number of mount options for this sb */ |
| 502 | for (i = 0; i < 8; i++) { | 498 | for (i = 0; i < 8; i++) { |
| 503 | if (tmp & 0x01) | 499 | if (tmp & 0x01) |
| @@ -562,8 +558,10 @@ out_free: | |||
| 562 | static int bad_option(struct superblock_security_struct *sbsec, char flag, | 558 | static int bad_option(struct superblock_security_struct *sbsec, char flag, |
| 563 | u32 old_sid, u32 new_sid) | 559 | u32 old_sid, u32 new_sid) |
| 564 | { | 560 | { |
| 561 | char mnt_flags = sbsec->flags & SE_MNTMASK; | ||
| 562 | |||
| 565 | /* check if the old mount command had the same options */ | 563 | /* check if the old mount command had the same options */ |
| 566 | if (sbsec->initialized) | 564 | if (sbsec->flags & SE_SBINITIALIZED) |
| 567 | if (!(sbsec->flags & flag) || | 565 | if (!(sbsec->flags & flag) || |
| 568 | (old_sid != new_sid)) | 566 | (old_sid != new_sid)) |
| 569 | return 1; | 567 | return 1; |
| @@ -571,8 +569,8 @@ static int bad_option(struct superblock_security_struct *sbsec, char flag, | |||
| 571 | /* check if we were passed the same options twice, | 569 | /* check if we were passed the same options twice, |
| 572 | * aka someone passed context=a,context=b | 570 | * aka someone passed context=a,context=b |
| 573 | */ | 571 | */ |
| 574 | if (!sbsec->initialized) | 572 | if (!(sbsec->flags & SE_SBINITIALIZED)) |
| 575 | if (sbsec->flags & flag) | 573 | if (mnt_flags & flag) |
| 576 | return 1; | 574 | return 1; |
| 577 | return 0; | 575 | return 0; |
| 578 | } | 576 | } |
| @@ -626,7 +624,7 @@ static int selinux_set_mnt_opts(struct super_block *sb, | |||
| 626 | * this sb does not set any security options. (The first options | 624 | * this sb does not set any security options. (The first options |
| 627 | * will be used for both mounts) | 625 | * will be used for both mounts) |
| 628 | */ | 626 | */ |
| 629 | if (sbsec->initialized && (sb->s_type->fs_flags & FS_BINARY_MOUNTDATA) | 627 | if ((sbsec->flags & SE_SBINITIALIZED) && (sb->s_type->fs_flags & FS_BINARY_MOUNTDATA) |
| 630 | && (num_opts == 0)) | 628 | && (num_opts == 0)) |
| 631 | goto out; | 629 | goto out; |
| 632 | 630 | ||
| @@ -690,19 +688,19 @@ static int selinux_set_mnt_opts(struct super_block *sb, | |||
| 690 | } | 688 | } |
| 691 | } | 689 | } |
| 692 | 690 | ||
| 693 | if (sbsec->initialized) { | 691 | if (sbsec->flags & SE_SBINITIALIZED) { |
| 694 | /* previously mounted with options, but not on this attempt? */ | 692 | /* previously mounted with options, but not on this attempt? */ |
| 695 | if (sbsec->flags && !num_opts) | 693 | if ((sbsec->flags & SE_MNTMASK) && !num_opts) |
| 696 | goto out_double_mount; | 694 | goto out_double_mount; |
| 697 | rc = 0; | 695 | rc = 0; |
| 698 | goto out; | 696 | goto out; |
| 699 | } | 697 | } |
| 700 | 698 | ||
| 701 | if (strcmp(sb->s_type->name, "proc") == 0) | 699 | if (strcmp(sb->s_type->name, "proc") == 0) |
| 702 | sbsec->proc = 1; | 700 | sbsec->flags |= SE_SBPROC; |
| 703 | 701 | ||
| 704 | /* Determine the labeling behavior to use for this filesystem type. */ | 702 | /* Determine the labeling behavior to use for this filesystem type. */ |
| 705 | rc = security_fs_use(sbsec->proc ? "proc" : sb->s_type->name, &sbsec->behavior, &sbsec->sid); | 703 | rc = security_fs_use((sbsec->flags & SE_SBPROC) ? "proc" : sb->s_type->name, &sbsec->behavior, &sbsec->sid); |
| 706 | if (rc) { | 704 | if (rc) { |
| 707 | printk(KERN_WARNING "%s: security_fs_use(%s) returned %d\n", | 705 | printk(KERN_WARNING "%s: security_fs_use(%s) returned %d\n", |
| 708 | __func__, sb->s_type->name, rc); | 706 | __func__, sb->s_type->name, rc); |
| @@ -806,10 +804,10 @@ static void selinux_sb_clone_mnt_opts(const struct super_block *oldsb, | |||
| 806 | } | 804 | } |
| 807 | 805 | ||
| 808 | /* how can we clone if the old one wasn't set up?? */ | 806 | /* how can we clone if the old one wasn't set up?? */ |
| 809 | BUG_ON(!oldsbsec->initialized); | 807 | BUG_ON(!(oldsbsec->flags & SE_SBINITIALIZED)); |
| 810 | 808 | ||
| 811 | /* if fs is reusing a sb, just let its options stand... */ | 809 | /* if fs is reusing a sb, just let its options stand... */ |
| 812 | if (newsbsec->initialized) | 810 | if (newsbsec->flags & SE_SBINITIALIZED) |
| 813 | return; | 811 | return; |
| 814 | 812 | ||
| 815 | mutex_lock(&newsbsec->lock); | 813 | mutex_lock(&newsbsec->lock); |
| @@ -1209,7 +1207,7 @@ static int inode_doinit_with_dentry(struct inode *inode, struct dentry *opt_dent | |||
| 1209 | goto out_unlock; | 1207 | goto out_unlock; |
| 1210 | 1208 | ||
| 1211 | sbsec = inode->i_sb->s_security; | 1209 | sbsec = inode->i_sb->s_security; |
| 1212 | if (!sbsec->initialized) { | 1210 | if (!(sbsec->flags & SE_SBINITIALIZED)) { |
| 1213 | /* Defer initialization until selinux_complete_init, | 1211 | /* Defer initialization until selinux_complete_init, |
| 1214 | after the initial policy is loaded and the security | 1212 | after the initial policy is loaded and the security |
| 1215 | server is ready to handle calls. */ | 1213 | server is ready to handle calls. */ |
| @@ -1326,7 +1324,7 @@ static int inode_doinit_with_dentry(struct inode *inode, struct dentry *opt_dent | |||
| 1326 | /* Default to the fs superblock SID. */ | 1324 | /* Default to the fs superblock SID. */ |
| 1327 | isec->sid = sbsec->sid; | 1325 | isec->sid = sbsec->sid; |
| 1328 | 1326 | ||
| 1329 | if (sbsec->proc && !S_ISLNK(inode->i_mode)) { | 1327 | if ((sbsec->flags & SE_SBPROC) && !S_ISLNK(inode->i_mode)) { |
| 1330 | struct proc_inode *proci = PROC_I(inode); | 1328 | struct proc_inode *proci = PROC_I(inode); |
| 1331 | if (proci->pde) { | 1329 | if (proci->pde) { |
| 1332 | isec->sclass = inode_mode_to_security_class(inode->i_mode); | 1330 | isec->sclass = inode_mode_to_security_class(inode->i_mode); |
| @@ -2585,7 +2583,7 @@ static int selinux_inode_init_security(struct inode *inode, struct inode *dir, | |||
| 2585 | } | 2583 | } |
| 2586 | 2584 | ||
| 2587 | /* Possibly defer initialization to selinux_complete_init. */ | 2585 | /* Possibly defer initialization to selinux_complete_init. */ |
| 2588 | if (sbsec->initialized) { | 2586 | if (sbsec->flags & SE_SBINITIALIZED) { |
| 2589 | struct inode_security_struct *isec = inode->i_security; | 2587 | struct inode_security_struct *isec = inode->i_security; |
| 2590 | isec->sclass = inode_mode_to_security_class(inode->i_mode); | 2588 | isec->sclass = inode_mode_to_security_class(inode->i_mode); |
| 2591 | isec->sid = newsid; | 2589 | isec->sid = newsid; |
diff --git a/security/selinux/include/objsec.h b/security/selinux/include/objsec.h index 3cc45168f674..c4e062336ef3 100644 --- a/security/selinux/include/objsec.h +++ b/security/selinux/include/objsec.h | |||
| @@ -60,9 +60,7 @@ struct superblock_security_struct { | |||
| 60 | u32 def_sid; /* default SID for labeling */ | 60 | u32 def_sid; /* default SID for labeling */ |
| 61 | u32 mntpoint_sid; /* SECURITY_FS_USE_MNTPOINT context for files */ | 61 | u32 mntpoint_sid; /* SECURITY_FS_USE_MNTPOINT context for files */ |
| 62 | unsigned int behavior; /* labeling behavior */ | 62 | unsigned int behavior; /* labeling behavior */ |
| 63 | unsigned char initialized; /* initialization flag */ | ||
| 64 | unsigned char flags; /* which mount options were specified */ | 63 | unsigned char flags; /* which mount options were specified */ |
| 65 | unsigned char proc; /* proc fs */ | ||
| 66 | struct mutex lock; | 64 | struct mutex lock; |
| 67 | struct list_head isec_head; | 65 | struct list_head isec_head; |
| 68 | spinlock_t isec_lock; | 66 | spinlock_t isec_lock; |
diff --git a/security/selinux/include/security.h b/security/selinux/include/security.h index 72447370bc95..ff4e19ccd8f8 100644 --- a/security/selinux/include/security.h +++ b/security/selinux/include/security.h | |||
| @@ -37,10 +37,16 @@ | |||
| 37 | #define POLICYDB_VERSION_MAX POLICYDB_VERSION_BOUNDARY | 37 | #define POLICYDB_VERSION_MAX POLICYDB_VERSION_BOUNDARY |
| 38 | #endif | 38 | #endif |
| 39 | 39 | ||
| 40 | /* Mask for just the mount related flags */ | ||
| 41 | #define SE_MNTMASK 0x0f | ||
| 42 | /* Super block security struct flags for mount options */ | ||
| 40 | #define CONTEXT_MNT 0x01 | 43 | #define CONTEXT_MNT 0x01 |
| 41 | #define FSCONTEXT_MNT 0x02 | 44 | #define FSCONTEXT_MNT 0x02 |
| 42 | #define ROOTCONTEXT_MNT 0x04 | 45 | #define ROOTCONTEXT_MNT 0x04 |
| 43 | #define DEFCONTEXT_MNT 0x08 | 46 | #define DEFCONTEXT_MNT 0x08 |
| 47 | /* Non-mount related flags */ | ||
| 48 | #define SE_SBINITIALIZED 0x10 | ||
| 49 | #define SE_SBPROC 0x20 | ||
| 44 | 50 | ||
| 45 | #define CONTEXT_STR "context=" | 51 | #define CONTEXT_STR "context=" |
| 46 | #define FSCONTEXT_STR "fscontext=" | 52 | #define FSCONTEXT_STR "fscontext=" |
