* [PATCH] SELinux: allow default source/target selectors for user/role/range
@ 2012-03-07 0:28 Eric Paris
2012-03-07 2:43 ` Harry Ciao
` (2 more replies)
0 siblings, 3 replies; 6+ messages in thread
From: Eric Paris @ 2012-03-07 0:28 UTC (permalink / raw)
To: sds; +Cc: selinux, Eric Paris
When new objects are created we have great and flexible rules to
determine the type of the new object. We aren't quite as flexible or
mature when it comes to determining the user, role, and range. This
patch adds a new ability to specify the place a new objects user, role,
and range should come from. For users and roles it can come from either
the source or the target of the operation. aka for files the user can
either come from the source (the running process and todays default) or
it can come from the target (aka the parent directory of the new file)
examples always are done with
directory context: system_u:object_r:mnt_t:s0-s0:c0.c512
process context: unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c1023
[no rule]
unconfined_u:object_r:mnt_t:s0 test_none
[default user source]
unconfined_u:object_r:mnt_t:s0 test_user_source
[default user target]
system_u:object_r:mnt_t:s0 test_user_target
[default role source]
unconfined_u:unconfined_r:mnt_t:s0 test_role_source
[default role target]
unconfined_u:object_r:mnt_t:s0 test_role_target
[default range source low]
unconfined_u:object_r:mnt_t:s0 test_range_source_low
[default range source high]
unconfined_u:object_r:mnt_t:s0:c0.c1023 test_range_source_high
[default range source low-high]
unconfined_u:object_r:mnt_t:s0-s0:c0.c1023 test_range_source_low-high
[default range target low]
unconfined_u:object_r:mnt_t:s0 test_range_target_low
[default range target high]
unconfined_u:object_r:mnt_t:s0:c0.c512 test_range_target_high
[default range target low-high]
unconfined_u:object_r:mnt_t:s0-s0:c0.c512 test_range_target_low-high
Signed-off-by: Eric Paris <eparis@redhat.com>
---
security/selinux/include/security.h | 3 ++-
security/selinux/ss/context.h | 20 ++++++++++++++++++++
security/selinux/ss/mls.c | 19 +++++++++++++++++++
security/selinux/ss/policydb.c | 25 +++++++++++++++++++++++++
security/selinux/ss/policydb.h | 13 +++++++++++++
security/selinux/ss/services.c | 32 +++++++++++++++++++++++---------
6 files changed, 102 insertions(+), 10 deletions(-)
diff --git a/security/selinux/include/security.h b/security/selinux/include/security.h
index d871e8a..ba53400 100644
--- a/security/selinux/include/security.h
+++ b/security/selinux/include/security.h
@@ -31,13 +31,14 @@
#define POLICYDB_VERSION_BOUNDARY 24
#define POLICYDB_VERSION_FILENAME_TRANS 25
#define POLICYDB_VERSION_ROLETRANS 26
+#define POLICYDB_VERSION_NEW_OBJECT_DEFAULTS 27
/* Range of policy versions we understand*/
#define POLICYDB_VERSION_MIN POLICYDB_VERSION_BASE
#ifdef CONFIG_SECURITY_SELINUX_POLICYDB_VERSION_MAX
#define POLICYDB_VERSION_MAX CONFIG_SECURITY_SELINUX_POLICYDB_VERSION_MAX_VALUE
#else
-#define POLICYDB_VERSION_MAX POLICYDB_VERSION_ROLETRANS
+#define POLICYDB_VERSION_MAX POLICYDB_VERSION_NEW_OBJECT_DEFAULTS
#endif
/* Mask for just the mount related flags */
diff --git a/security/selinux/ss/context.h b/security/selinux/ss/context.h
index 45e8fb0..212e347 100644
--- a/security/selinux/ss/context.h
+++ b/security/selinux/ss/context.h
@@ -74,6 +74,26 @@ out:
return rc;
}
+/*
+ * Sets both levels in the MLS range of 'dst' to the high level of 'src'.
+ */
+static inline int mls_context_cpy_high(struct context *dst, struct context *src)
+{
+ int rc;
+
+ dst->range.level[0].sens = src->range.level[1].sens;
+ rc = ebitmap_cpy(&dst->range.level[0].cat, &src->range.level[1].cat);
+ if (rc)
+ goto out;
+
+ dst->range.level[1].sens = src->range.level[1].sens;
+ rc = ebitmap_cpy(&dst->range.level[1].cat, &src->range.level[1].cat);
+ if (rc)
+ ebitmap_destroy(&dst->range.level[0].cat);
+out:
+ return rc;
+}
+
static inline int mls_context_cmp(struct context *c1, struct context *c2)
{
return ((c1->range.level[0].sens == c2->range.level[0].sens) &&
diff --git a/security/selinux/ss/mls.c b/security/selinux/ss/mls.c
index fbf9c58..2e3013d 100644
--- a/security/selinux/ss/mls.c
+++ b/security/selinux/ss/mls.c
@@ -517,6 +517,7 @@ int mls_compute_sid(struct context *scontext,
{
struct range_trans rtr;
struct mls_range *r;
+ struct class_datum *cladatum;
if (!policydb.mls_enabled)
return 0;
@@ -530,6 +531,24 @@ int mls_compute_sid(struct context *scontext,
r = hashtab_search(policydb.range_tr, &rtr);
if (r)
return mls_range_set(newcontext, r);
+
+ cladatum = policydb.class_val_to_struct[tclass - 1];
+
+ switch (cladatum->default_range) {
+ case DEFAULT_SOURCE_LOW:
+ return mls_context_cpy_low(newcontext, scontext);
+ case DEFAULT_SOURCE_HIGH:
+ return mls_context_cpy_high(newcontext, scontext);
+ case DEFAULT_SOURCE_LOW_HIGH:
+ return mls_context_cpy(newcontext, scontext);
+ case DEFAULT_TARGET_LOW:
+ return mls_context_cpy_low(newcontext, tcontext);
+ case DEFAULT_TARGET_HIGH:
+ return mls_context_cpy_high(newcontext, tcontext);
+ case DEFAULT_TARGET_LOW_HIGH:
+ return mls_context_cpy(newcontext, tcontext);
+ }
+
/* Fallthrough */
case AVTAB_CHANGE:
if ((tclass == policydb.process_class) || (sock == true))
diff --git a/security/selinux/ss/policydb.c b/security/selinux/ss/policydb.c
index a7f61d5..2bb9c2f 100644
--- a/security/selinux/ss/policydb.c
+++ b/security/selinux/ss/policydb.c
@@ -133,6 +133,11 @@ static struct policydb_compat_info policydb_compat[] = {
.sym_num = SYM_NUM,
.ocon_num = OCON_NUM,
},
+ {
+ .version = POLICYDB_VERSION_NEW_OBJECT_DEFAULTS,
+ .sym_num = SYM_NUM,
+ .ocon_num = OCON_NUM,
+ },
};
static struct policydb_compat_info *policydb_lookup_compat(int version)
@@ -1306,6 +1311,16 @@ static int class_read(struct policydb *p, struct hashtab *h, void *fp)
goto bad;
}
+ if (p->policyvers >= POLICYDB_VERSION_NEW_OBJECT_DEFAULTS) {
+ rc = next_entry(buf, fp, sizeof(u32) * 3);
+ if (rc)
+ goto bad;
+
+ cladatum->default_user = le32_to_cpu(buf[0]);
+ cladatum->default_role = le32_to_cpu(buf[1]);
+ cladatum->default_range = le32_to_cpu(buf[2]);
+ }
+
rc = hashtab_insert(h, key, cladatum);
if (rc)
goto bad;
@@ -2832,6 +2847,16 @@ static int class_write(void *vkey, void *datum, void *ptr)
if (rc)
return rc;
+ if (p->policyvers >= POLICYDB_VERSION_NEW_OBJECT_DEFAULTS) {
+ buf[0] = cpu_to_le32(cladatum->default_user);
+ buf[1] = cpu_to_le32(cladatum->default_role);
+ buf[2] = cpu_to_le32(cladatum->default_range);
+
+ rc = put_entry(buf, sizeof(uint32_t), 3, fp);
+ if (rc)
+ return rc;
+ }
+
return 0;
}
diff --git a/security/selinux/ss/policydb.h b/security/selinux/ss/policydb.h
index b846c03..a949f1a 100644
--- a/security/selinux/ss/policydb.h
+++ b/security/selinux/ss/policydb.h
@@ -60,6 +60,19 @@ struct class_datum {
struct symtab permissions; /* class-specific permission symbol table */
struct constraint_node *constraints; /* constraints on class permissions */
struct constraint_node *validatetrans; /* special transition rules */
+ /* Options how a new object user and role should be decided */
+#define DEFAULT_SOURCE 1
+#define DEFAULT_TARGET 2
+ char default_user;
+ char default_role;
+/* Options how a new object range should be decided */
+#define DEFAULT_SOURCE_LOW 1
+#define DEFAULT_SOURCE_HIGH 2
+#define DEFAULT_SOURCE_LOW_HIGH 3
+#define DEFAULT_TARGET_LOW 4
+#define DEFAULT_TARGET_HIGH 5
+#define DEFAULT_TARGET_LOW_HIGH 6
+ char default_range;
};
/* Role attributes */
diff --git a/security/selinux/ss/services.c b/security/selinux/ss/services.c
index 185f849..579c8b0 100644
--- a/security/selinux/ss/services.c
+++ b/security/selinux/ss/services.c
@@ -1389,6 +1389,7 @@ static int security_compute_sid(u32 ssid,
u32 *out_sid,
bool kern)
{
+ struct class_datum *cladatum;
struct context *scontext = NULL, *tcontext = NULL, newcontext;
struct role_trans *roletr = NULL;
struct avtab_key avkey;
@@ -1437,12 +1438,17 @@ static int security_compute_sid(u32 ssid,
goto out_unlock;
}
+ cladatum = policydb.class_val_to_struct[tclass - 1];
/* Set the user identity. */
switch (specified) {
case AVTAB_TRANSITION:
case AVTAB_CHANGE:
- /* Use the process user identity. */
- newcontext.user = scontext->user;
+ if (cladatum->default_user == DEFAULT_TARGET)
+ /* Use the process user identity. */
+ newcontext.user = tcontext->user;
+ else
+ /* notice this gets both DEFAULT_SOURCE and unset */
+ newcontext.user = scontext->user;
break;
case AVTAB_MEMBER:
/* Use the related object owner. */
@@ -1450,17 +1456,25 @@ static int security_compute_sid(u32 ssid,
break;
}
- /* Set the role and type to default values. */
- if ((tclass == policydb.process_class) || (sock == true)) {
- /* Use the current role and type of process. */
+ /* Set the role to default values. */
+ if (cladatum->default_role == DEFAULT_SOURCE) {
newcontext.role = scontext->role;
- newcontext.type = scontext->type;
+ } else if (cladatum->default_role == DEFAULT_TARGET) {
+ newcontext.role = tcontext->role;
} else {
- /* Use the well-defined object role. */
- newcontext.role = OBJECT_R_VAL;
+ if ((tclass == policydb.process_class) || (sock == true))
+ newcontext.role = scontext->role;
+ else
+ newcontext.role = OBJECT_R_VAL;
+ }
+
+ /* Set the type to default values. */
+ if ((tclass == policydb.process_class) || (sock == true))
+ /* Use the type of process. */
+ newcontext.type = scontext->type;
+ else
/* Use the type of the related object. */
newcontext.type = tcontext->type;
- }
/* Look for a type transition/member/change rule. */
avkey.source_type = scontext->type;
--
1.7.1
--
This message was distributed to subscribers of the selinux mailing list.
If you no longer wish to subscribe, send mail to majordomo@tycho.nsa.gov with
the words "unsubscribe selinux" without quotes as the message.
^ permalink raw reply related [flat|nested] 6+ messages in thread* Re: [PATCH] SELinux: allow default source/target selectors for user/role/range
2012-03-07 0:28 [PATCH] SELinux: allow default source/target selectors for user/role/range Eric Paris
@ 2012-03-07 2:43 ` Harry Ciao
2012-03-07 14:12 ` Eric Paris
2012-03-07 8:34 ` Harry Ciao
2012-03-07 14:37 ` Stephen Smalley
2 siblings, 1 reply; 6+ messages in thread
From: Harry Ciao @ 2012-03-07 2:43 UTC (permalink / raw)
To: Eric Paris; +Cc: sds, selinux
On 03/07/2012 08:28 AM, Eric Paris wrote:
> When new objects are created we have great and flexible rules to
> determine the type of the new object.
Shouldn't we introduce a default_type for class_datum as well? So far
the process and various socket classes will inherit the creating
process's domain, that is, DEFAULT_SOURCE as in your example, whilst for
any other classes the type of the newly created object will follow the
containing directory, that is, DEFAULT_TARGET.
Above logic has been hard-coded in security_compute_sid, which is a
matter of policy and should be moved from security server to refpolicy.
--
This message was distributed to subscribers of the selinux mailing list.
If you no longer wish to subscribe, send mail to majordomo@tycho.nsa.gov with
the words "unsubscribe selinux" without quotes as the message.
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: [PATCH] SELinux: allow default source/target selectors for user/role/range
2012-03-07 2:43 ` Harry Ciao
@ 2012-03-07 14:12 ` Eric Paris
0 siblings, 0 replies; 6+ messages in thread
From: Eric Paris @ 2012-03-07 14:12 UTC (permalink / raw)
To: qingtao.cao; +Cc: sds, selinux
On Wed, 2012-03-07 at 10:43 +0800, Harry Ciao wrote:
>
> On 03/07/2012 08:28 AM, Eric Paris wrote:
> > When new objects are created we have great and flexible rules to
> > determine the type of the new object.
>
> Shouldn't we introduce a default_type for class_datum as well? So far
> the process and various socket classes will inherit the creating
> process's domain, that is, DEFAULT_SOURCE as in your example, whilst for
> any other classes the type of the newly created object will follow the
> containing directory, that is, DEFAULT_TARGET.
>
> Above logic has been hard-coded in security_compute_sid, which is a
> matter of policy and should be moved from security server to refpolicy.
Agreed, but we cannot remove the old defaults. They still need to be
available in case someone loads an old policy. We could create a new
policy capability which when enabled would require policy to define all
of the defaults, but I don't think it's worth it, since any definition
in policy with this new rule type will overwrite the defaults in the
security server.
A mistake I made was only showing examples of this with files. The new
rule syntax is:
default_user { file process } source;
default_range { socket } target low-high;
So the tclass of the created object is part of the decision.
-Eric
--
This message was distributed to subscribers of the selinux mailing list.
If you no longer wish to subscribe, send mail to majordomo@tycho.nsa.gov with
the words "unsubscribe selinux" without quotes as the message.
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: [PATCH] SELinux: allow default source/target selectors for user/role/range
2012-03-07 0:28 [PATCH] SELinux: allow default source/target selectors for user/role/range Eric Paris
2012-03-07 2:43 ` Harry Ciao
@ 2012-03-07 8:34 ` Harry Ciao
2012-03-07 14:23 ` Eric Paris
2012-03-07 14:37 ` Stephen Smalley
2 siblings, 1 reply; 6+ messages in thread
From: Harry Ciao @ 2012-03-07 8:34 UTC (permalink / raw)
To: Eric Paris; +Cc: sds, selinux
Comments embedded below.
On 03/07/2012 08:28 AM, Eric Paris wrote:
> When new objects are created we have great and flexible rules to
> determine the type of the new object. We aren't quite as flexible or
> mature when it comes to determining the user, role, and range. This
> patch adds a new ability to specify the place a new objects user, role,
> and range should come from. For users and roles it can come from either
> the source or the target of the operation. aka for files the user can
> either come from the source (the running process and todays default) or
> it can come from the target (aka the parent directory of the new file)
>
> examples always are done with
> directory context: system_u:object_r:mnt_t:s0-s0:c0.c512
> process context: unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c1023
>
> [no rule]
> unconfined_u:object_r:mnt_t:s0 test_none
> [default user source]
> unconfined_u:object_r:mnt_t:s0 test_user_source
> [default user target]
> system_u:object_r:mnt_t:s0 test_user_target
> [default role source]
> unconfined_u:unconfined_r:mnt_t:s0 test_role_source
> [default role target]
> unconfined_u:object_r:mnt_t:s0 test_role_target
> [default range source low]
> unconfined_u:object_r:mnt_t:s0 test_range_source_low
> [default range source high]
> unconfined_u:object_r:mnt_t:s0:c0.c1023 test_range_source_high
> [default range source low-high]
> unconfined_u:object_r:mnt_t:s0-s0:c0.c1023 test_range_source_low-high
> [default range target low]
> unconfined_u:object_r:mnt_t:s0 test_range_target_low
> [default range target high]
> unconfined_u:object_r:mnt_t:s0:c0.c512 test_range_target_high
> [default range target low-high]
> unconfined_u:object_r:mnt_t:s0-s0:c0.c512 test_range_target_low-high
>
> Signed-off-by: Eric Paris<eparis@redhat.com>
> ---
> security/selinux/include/security.h | 3 ++-
> security/selinux/ss/context.h | 20 ++++++++++++++++++++
> security/selinux/ss/mls.c | 19 +++++++++++++++++++
> security/selinux/ss/policydb.c | 25 +++++++++++++++++++++++++
> security/selinux/ss/policydb.h | 13 +++++++++++++
> security/selinux/ss/services.c | 32 +++++++++++++++++++++++---------
> 6 files changed, 102 insertions(+), 10 deletions(-)
>
> diff --git a/security/selinux/include/security.h b/security/selinux/include/security.h
> index d871e8a..ba53400 100644
> --- a/security/selinux/include/security.h
> +++ b/security/selinux/include/security.h
> @@ -31,13 +31,14 @@
> #define POLICYDB_VERSION_BOUNDARY 24
> #define POLICYDB_VERSION_FILENAME_TRANS 25
> #define POLICYDB_VERSION_ROLETRANS 26
> +#define POLICYDB_VERSION_NEW_OBJECT_DEFAULTS 27
>
> /* Range of policy versions we understand*/
> #define POLICYDB_VERSION_MIN POLICYDB_VERSION_BASE
> #ifdef CONFIG_SECURITY_SELINUX_POLICYDB_VERSION_MAX
> #define POLICYDB_VERSION_MAX CONFIG_SECURITY_SELINUX_POLICYDB_VERSION_MAX_VALUE
> #else
> -#define POLICYDB_VERSION_MAX POLICYDB_VERSION_ROLETRANS
> +#define POLICYDB_VERSION_MAX POLICYDB_VERSION_NEW_OBJECT_DEFAULTS
> #endif
>
> /* Mask for just the mount related flags */
> diff --git a/security/selinux/ss/context.h b/security/selinux/ss/context.h
> index 45e8fb0..212e347 100644
> --- a/security/selinux/ss/context.h
> +++ b/security/selinux/ss/context.h
> @@ -74,6 +74,26 @@ out:
> return rc;
> }
>
> +/*
> + * Sets both levels in the MLS range of 'dst' to the high level of 'src'.
> + */
> +static inline int mls_context_cpy_high(struct context *dst, struct context *src)
> +{
> + int rc;
> +
> + dst->range.level[0].sens = src->range.level[1].sens;
> + rc = ebitmap_cpy(&dst->range.level[0].cat,&src->range.level[1].cat);
> + if (rc)
> + goto out;
> +
> + dst->range.level[1].sens = src->range.level[1].sens;
> + rc = ebitmap_cpy(&dst->range.level[1].cat,&src->range.level[1].cat);
> + if (rc)
> + ebitmap_destroy(&dst->range.level[0].cat);
> +out:
> + return rc;
> +}
> +
> static inline int mls_context_cmp(struct context *c1, struct context *c2)
> {
> return ((c1->range.level[0].sens == c2->range.level[0].sens)&&
> diff --git a/security/selinux/ss/mls.c b/security/selinux/ss/mls.c
> index fbf9c58..2e3013d 100644
> --- a/security/selinux/ss/mls.c
> +++ b/security/selinux/ss/mls.c
> @@ -517,6 +517,7 @@ int mls_compute_sid(struct context *scontext,
> {
> struct range_trans rtr;
> struct mls_range *r;
> + struct class_datum *cladatum;
>
> if (!policydb.mls_enabled)
> return 0;
> @@ -530,6 +531,24 @@ int mls_compute_sid(struct context *scontext,
> r = hashtab_search(policydb.range_tr,&rtr);
> if (r)
> return mls_range_set(newcontext, r);
> +
> + cladatum = policydb.class_val_to_struct[tclass - 1];
> +
> + switch (cladatum->default_range) {
> + case DEFAULT_SOURCE_LOW:
> + return mls_context_cpy_low(newcontext, scontext);
> + case DEFAULT_SOURCE_HIGH:
> + return mls_context_cpy_high(newcontext, scontext);
> + case DEFAULT_SOURCE_LOW_HIGH:
> + return mls_context_cpy(newcontext, scontext);
> + case DEFAULT_TARGET_LOW:
> + return mls_context_cpy_low(newcontext, tcontext);
> + case DEFAULT_TARGET_HIGH:
> + return mls_context_cpy_high(newcontext, tcontext);
> + case DEFAULT_TARGET_LOW_HIGH:
> + return mls_context_cpy(newcontext, tcontext);
How about introducing a default case to take care of when default_range
is unset ? where mls_context_cpy_low(newcontext, scontext) could be
leveraged to handle such case.
> + }
> +
> /* Fallthrough */
> case AVTAB_CHANGE:
> if ((tclass == policydb.process_class) || (sock == true))
> diff --git a/security/selinux/ss/policydb.c b/security/selinux/ss/policydb.c
> index a7f61d5..2bb9c2f 100644
> --- a/security/selinux/ss/policydb.c
> +++ b/security/selinux/ss/policydb.c
> @@ -133,6 +133,11 @@ static struct policydb_compat_info policydb_compat[] = {
> .sym_num = SYM_NUM,
> .ocon_num = OCON_NUM,
> },
> + {
> + .version = POLICYDB_VERSION_NEW_OBJECT_DEFAULTS,
> + .sym_num = SYM_NUM,
> + .ocon_num = OCON_NUM,
> + },
> };
>
> static struct policydb_compat_info *policydb_lookup_compat(int version)
> @@ -1306,6 +1311,16 @@ static int class_read(struct policydb *p, struct hashtab *h, void *fp)
> goto bad;
> }
>
> + if (p->policyvers>= POLICYDB_VERSION_NEW_OBJECT_DEFAULTS) {
> + rc = next_entry(buf, fp, sizeof(u32) * 3);
> + if (rc)
> + goto bad;
> +
> + cladatum->default_user = le32_to_cpu(buf[0]);
> + cladatum->default_role = le32_to_cpu(buf[1]);
> + cladatum->default_range = le32_to_cpu(buf[2]);
> + }
> +
> rc = hashtab_insert(h, key, cladatum);
> if (rc)
> goto bad;
> @@ -2832,6 +2847,16 @@ static int class_write(void *vkey, void *datum, void *ptr)
> if (rc)
> return rc;
>
> + if (p->policyvers>= POLICYDB_VERSION_NEW_OBJECT_DEFAULTS) {
> + buf[0] = cpu_to_le32(cladatum->default_user);
> + buf[1] = cpu_to_le32(cladatum->default_role);
> + buf[2] = cpu_to_le32(cladatum->default_range);
> +
> + rc = put_entry(buf, sizeof(uint32_t), 3, fp);
> + if (rc)
> + return rc;
> + }
> +
> return 0;
> }
>
> diff --git a/security/selinux/ss/policydb.h b/security/selinux/ss/policydb.h
> index b846c03..a949f1a 100644
> --- a/security/selinux/ss/policydb.h
> +++ b/security/selinux/ss/policydb.h
> @@ -60,6 +60,19 @@ struct class_datum {
> struct symtab permissions; /* class-specific permission symbol table */
> struct constraint_node *constraints; /* constraints on class permissions */
> struct constraint_node *validatetrans; /* special transition rules */
> + /* Options how a new object user and role should be decided */
> +#define DEFAULT_SOURCE 1
> +#define DEFAULT_TARGET 2
> + char default_user;
> + char default_role;
> +/* Options how a new object range should be decided */
> +#define DEFAULT_SOURCE_LOW 1
> +#define DEFAULT_SOURCE_HIGH 2
> +#define DEFAULT_SOURCE_LOW_HIGH 3
> +#define DEFAULT_TARGET_LOW 4
> +#define DEFAULT_TARGET_HIGH 5
> +#define DEFAULT_TARGET_LOW_HIGH 6
> + char default_range;
> };
>
> /* Role attributes */
> diff --git a/security/selinux/ss/services.c b/security/selinux/ss/services.c
> index 185f849..579c8b0 100644
> --- a/security/selinux/ss/services.c
> +++ b/security/selinux/ss/services.c
> @@ -1389,6 +1389,7 @@ static int security_compute_sid(u32 ssid,
> u32 *out_sid,
> bool kern)
> {
> + struct class_datum *cladatum;
> struct context *scontext = NULL, *tcontext = NULL, newcontext;
> struct role_trans *roletr = NULL;
> struct avtab_key avkey;
> @@ -1437,12 +1438,17 @@ static int security_compute_sid(u32 ssid,
> goto out_unlock;
> }
>
> + cladatum = policydb.class_val_to_struct[tclass - 1];
> /* Set the user identity. */
> switch (specified) {
> case AVTAB_TRANSITION:
> case AVTAB_CHANGE:
> - /* Use the process user identity. */
> - newcontext.user = scontext->user;
> + if (cladatum->default_user == DEFAULT_TARGET)
> + /* Use the process user identity. */
> + newcontext.user = tcontext->user;
> + else
> + /* notice this gets both DEFAULT_SOURCE and unset */
> + newcontext.user = scontext->user;
> break;
> case AVTAB_MEMBER:
> /* Use the related object owner. */
> @@ -1450,17 +1456,25 @@ static int security_compute_sid(u32 ssid,
> break;
> }
>
> - /* Set the role and type to default values. */
> - if ((tclass == policydb.process_class) || (sock == true)) {
> - /* Use the current role and type of process. */
> + /* Set the role to default values. */
> + if (cladatum->default_role == DEFAULT_SOURCE) {
> newcontext.role = scontext->role;
> - newcontext.type = scontext->type;
> + } else if (cladatum->default_role == DEFAULT_TARGET) {
> + newcontext.role = tcontext->role;
> } else {
> - /* Use the well-defined object role. */
> - newcontext.role = OBJECT_R_VAL;
> + if ((tclass == policydb.process_class) || (sock == true))
> + newcontext.role = scontext->role;
> + else
> + newcontext.role = OBJECT_R_VAL;
OBJECT_R_VAL will be fallen back on when the default_role is unset, I
assume the above if-else condition could be eliminated if the
default_role for the process and various socket classes are specifically
defined as DEFAULT_SOURCE.
> + }
> +
> + /* Set the type to default values. */
> + if ((tclass == policydb.process_class) || (sock == true))
> + /* Use the type of process. */
> + newcontext.type = scontext->type;
> + else
If default_type would be employed then the process and all socket
classes won't have to be differentiated from other classes. Moreover,
the support for the "socket labeling" behavior would be obsolete now
that we have a much better solution and could be properly reverted.
Thanks,
Harry
> /* Use the type of the related object. */
> newcontext.type = tcontext->type;
> - }
>
> /* Look for a type transition/member/change rule. */
> avkey.source_type = scontext->type;
--
This message was distributed to subscribers of the selinux mailing list.
If you no longer wish to subscribe, send mail to majordomo@tycho.nsa.gov with
the words "unsubscribe selinux" without quotes as the message.
^ permalink raw reply [flat|nested] 6+ messages in thread* Re: [PATCH] SELinux: allow default source/target selectors for user/role/range
2012-03-07 8:34 ` Harry Ciao
@ 2012-03-07 14:23 ` Eric Paris
0 siblings, 0 replies; 6+ messages in thread
From: Eric Paris @ 2012-03-07 14:23 UTC (permalink / raw)
To: qingtao.cao; +Cc: sds, selinux
On Wed, 2012-03-07 at 16:34 +0800, Harry Ciao wrote:
> Comments embedded below.
[lots of snipping throughout]
> > @@ -530,6 +531,24 @@ int mls_compute_sid(struct context *scontext,
> > r = hashtab_search(policydb.range_tr,&rtr);
> > if (r)
> > return mls_range_set(newcontext, r);
> > +
> > + cladatum = policydb.class_val_to_struct[tclass - 1];
> > +
> > + switch (cladatum->default_range) {
> > + case DEFAULT_SOURCE_LOW:
> > + return mls_context_cpy_low(newcontext, scontext);
> > + case DEFAULT_SOURCE_HIGH:
> > + return mls_context_cpy_high(newcontext, scontext);
> > + case DEFAULT_SOURCE_LOW_HIGH:
> > + return mls_context_cpy(newcontext, scontext);
> > + case DEFAULT_TARGET_LOW:
> > + return mls_context_cpy_low(newcontext, tcontext);
> > + case DEFAULT_TARGET_HIGH:
> > + return mls_context_cpy_high(newcontext, tcontext);
> > + case DEFAULT_TARGET_LOW_HIGH:
> > + return mls_context_cpy(newcontext, tcontext);
>
> How about introducing a default case to take care of when default_range
> is unset ? where mls_context_cpy_low(newcontext, scontext) could be
> leveraged to handle such case.
Notice the fallthrough. I added a few more lines of context. We do
exactly what you ask for. If unset nothing changes from today. If set
we get the defaults policy set.
> > + }
> > +
> > /* Fallthrough */
> > case AVTAB_CHANGE:
> > if ((tclass == policydb.process_class) || (sock == true))
/* Use the process MLS attributes. */
return mls_context_cpy(newcontext, scontext);
else
/* Use the process effective MLS attributes. */
return mls_context_cpy_low(newcontext, scontext);
> > @@ -1450,17 +1456,25 @@ static int security_compute_sid(u32 ssid,
> > break;
> > }
> >
> > - /* Set the role and type to default values. */
> > - if ((tclass == policydb.process_class) || (sock == true)) {
> > - /* Use the current role and type of process. */
> > + /* Set the role to default values. */
> > + if (cladatum->default_role == DEFAULT_SOURCE) {
> > newcontext.role = scontext->role;
> > - newcontext.type = scontext->type;
> > + } else if (cladatum->default_role == DEFAULT_TARGET) {
> > + newcontext.role = tcontext->role;
> > } else {
> > - /* Use the well-defined object role. */
> > - newcontext.role = OBJECT_R_VAL;
> > + if ((tclass == policydb.process_class) || (sock == true))
> > + newcontext.role = scontext->role;
> > + else
> > + newcontext.role = OBJECT_R_VAL;
>
> OBJECT_R_VAL will be fallen back on when the default_role is unset, I
> assume the above if-else condition could be eliminated if the
> default_role for the process and various socket classes are specifically
> defined as DEFAULT_SOURCE.
Yes, it absolutely could. But we don't want to force a policy upgrade
to upgrade the kernel. Thus we can't get rid of the legacy process/sock
handling. I feel like any other option here would make the code worse,
not better looking.
> > + }
> > +
> > + /* Set the type to default values. */
> > + if ((tclass == policydb.process_class) || (sock == true))
> > + /* Use the type of process. */
> > + newcontext.type = scontext->type;
> > + else
>
> If default_type would be employed then the process and all socket
> classes won't have to be differentiated from other classes. Moreover,
> the support for the "socket labeling" behavior would be obsolete now
> that we have a much better solution and could be properly reverted.
Yup. If it only weren't for those blasted users that don't update
everything every time I might want them to *smile*
Thanks for the comments! Though, I don't think there is a lot we can do
to really make the code better while still supporting old systems.
-Eric
--
This message was distributed to subscribers of the selinux mailing list.
If you no longer wish to subscribe, send mail to majordomo@tycho.nsa.gov with
the words "unsubscribe selinux" without quotes as the message.
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: [PATCH] SELinux: allow default source/target selectors for user/role/range
2012-03-07 0:28 [PATCH] SELinux: allow default source/target selectors for user/role/range Eric Paris
2012-03-07 2:43 ` Harry Ciao
2012-03-07 8:34 ` Harry Ciao
@ 2012-03-07 14:37 ` Stephen Smalley
2 siblings, 0 replies; 6+ messages in thread
From: Stephen Smalley @ 2012-03-07 14:37 UTC (permalink / raw)
To: Eric Paris; +Cc: selinux
On Tue, 2012-03-06 at 19:28 -0500, Eric Paris wrote:
> When new objects are created we have great and flexible rules to
> determine the type of the new object. We aren't quite as flexible or
> mature when it comes to determining the user, role, and range. This
> patch adds a new ability to specify the place a new objects user, role,
> and range should come from. For users and roles it can come from either
> the source or the target of the operation. aka for files the user can
> either come from the source (the running process and todays default) or
> it can come from the target (aka the parent directory of the new file)
>
> examples always are done with
> directory context: system_u:object_r:mnt_t:s0-s0:c0.c512
> process context: unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c1023
>
> [no rule]
> unconfined_u:object_r:mnt_t:s0 test_none
> [default user source]
> unconfined_u:object_r:mnt_t:s0 test_user_source
> [default user target]
> system_u:object_r:mnt_t:s0 test_user_target
> [default role source]
> unconfined_u:unconfined_r:mnt_t:s0 test_role_source
> [default role target]
> unconfined_u:object_r:mnt_t:s0 test_role_target
> [default range source low]
> unconfined_u:object_r:mnt_t:s0 test_range_source_low
> [default range source high]
> unconfined_u:object_r:mnt_t:s0:c0.c1023 test_range_source_high
> [default range source low-high]
> unconfined_u:object_r:mnt_t:s0-s0:c0.c1023 test_range_source_low-high
> [default range target low]
> unconfined_u:object_r:mnt_t:s0 test_range_target_low
> [default range target high]
> unconfined_u:object_r:mnt_t:s0:c0.c512 test_range_target_high
> [default range target low-high]
> unconfined_u:object_r:mnt_t:s0-s0:c0.c512 test_range_target_low-high
Very nice. Harry's point about also supporting configurable defaults
(source or target) for the type field also makes sense. Some comments
below.
> diff --git a/security/selinux/ss/services.c b/security/selinux/ss/services.c
> index 185f849..579c8b0 100644
> --- a/security/selinux/ss/services.c
> +++ b/security/selinux/ss/services.c
> @@ -1389,6 +1389,7 @@ static int security_compute_sid(u32 ssid,
> u32 *out_sid,
> bool kern)
> {
> + struct class_datum *cladatum;
> struct context *scontext = NULL, *tcontext = NULL, newcontext;
> struct role_trans *roletr = NULL;
> struct avtab_key avkey;
> @@ -1437,12 +1438,17 @@ static int security_compute_sid(u32 ssid,
> goto out_unlock;
> }
>
> + cladatum = policydb.class_val_to_struct[tclass - 1];
Need to check that tclass is in the legal range first, as in
context_struct_compute_av() and security_validate_transition().
> /* Set the user identity. */
> switch (specified) {
> case AVTAB_TRANSITION:
> case AVTAB_CHANGE:
> - /* Use the process user identity. */
> - newcontext.user = scontext->user;
> + if (cladatum->default_user == DEFAULT_TARGET)
> + /* Use the process user identity. */
Comment is no longer correct.
> @@ -1450,17 +1456,25 @@ static int security_compute_sid(u32 ssid,
> break;
> }
>
> - /* Set the role and type to default values. */
> - if ((tclass == policydb.process_class) || (sock == true)) {
> - /* Use the current role and type of process. */
> + /* Set the role to default values. */
> + if (cladatum->default_role == DEFAULT_SOURCE) {
> newcontext.role = scontext->role;
> - newcontext.type = scontext->type;
> + } else if (cladatum->default_role == DEFAULT_TARGET) {
> + newcontext.role = tcontext->role;
> } else {
> - /* Use the well-defined object role. */
> - newcontext.role = OBJECT_R_VAL;
> + if ((tclass == policydb.process_class) || (sock == true))
> + newcontext.role = scontext->role;
> + else
> + newcontext.role = OBJECT_R_VAL;
> + }
> +
> + /* Set the type to default values. */
> + if ((tclass == policydb.process_class) || (sock == true))
> + /* Use the type of process. */
> + newcontext.type = scontext->type;
> + else
> /* Use the type of the related object. */
> newcontext.type = tcontext->type;
> - }
I guess it isn't required, but isn't it nicer to use { } around the
block when there is a comment line? Just for readability?
--
Stephen Smalley
National Security Agency
--
This message was distributed to subscribers of the selinux mailing list.
If you no longer wish to subscribe, send mail to majordomo@tycho.nsa.gov with
the words "unsubscribe selinux" without quotes as the message.
^ permalink raw reply [flat|nested] 6+ messages in thread
end of thread, other threads:[~2012-03-07 14:37 UTC | newest]
Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2012-03-07 0:28 [PATCH] SELinux: allow default source/target selectors for user/role/range Eric Paris
2012-03-07 2:43 ` Harry Ciao
2012-03-07 14:12 ` Eric Paris
2012-03-07 8:34 ` Harry Ciao
2012-03-07 14:23 ` Eric Paris
2012-03-07 14:37 ` Stephen Smalley
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.