mirror of
https://salsa.debian.org/freeipa-team/freeipa.git
synced 2025-02-25 18:55:28 -06:00
Add SELinux user mapping framework.
This will allow one to define what SELinux context a given user gets on a given machine. A rule can contain a set of users and hosts or it can point to an existing HBAC rule that defines them. https://fedorahosted.org/freeipa/ticket/755
This commit is contained in:
committed by
Alexander Bokovoy
parent
a1c9e3618c
commit
55512dc938
@@ -123,5 +123,15 @@ netgroup = [
|
||||
|
||||
automember = [
|
||||
u'top',
|
||||
u'automemberregexrule'
|
||||
u'automemberregexrule',
|
||||
]
|
||||
|
||||
selinuxusermap = [
|
||||
u'ipaassociation',
|
||||
u'ipaselinuxusermap',
|
||||
]
|
||||
|
||||
hbacrule = [
|
||||
u'ipaassociation',
|
||||
u'ipahbacrule',
|
||||
]
|
||||
|
||||
600
tests/test_xmlrpc/test_selinuxusermap_plugin.py
Normal file
600
tests/test_xmlrpc/test_selinuxusermap_plugin.py
Normal file
@@ -0,0 +1,600 @@
|
||||
# Authors:
|
||||
# Rob Crittenden <rcritten@redhat.com>
|
||||
#
|
||||
# Copyright (C) 2011 Red Hat
|
||||
# see file 'COPYING' for use and warranty information
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation, either version 3 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
"""
|
||||
Test the `ipalib/plugins/selinuxusermap.py` module.
|
||||
"""
|
||||
|
||||
from ipalib import api, errors
|
||||
from tests.test_xmlrpc import objectclasses
|
||||
from xmlrpc_test import Declarative, fuzzy_digits, fuzzy_uuid
|
||||
from ipalib.dn import *
|
||||
from tests.util import Fuzzy
|
||||
|
||||
rule1 = u'selinuxrule1'
|
||||
selinuxuser1 = u'guest_u:s0'
|
||||
selinuxuser2 = u'xguest_u:s0'
|
||||
|
||||
user1 = u'tuser1'
|
||||
group1 = u'testgroup1'
|
||||
host1 = u'testhost1.%s' % api.env.domain
|
||||
hostdn1 = DN(('fqdn',host1),('cn','computers'),('cn','accounts'),
|
||||
api.env.basedn)
|
||||
hbacrule1 = u'testhbacrule1'
|
||||
|
||||
fuzzy_selinuxusermapdn = Fuzzy(
|
||||
'ipauniqueid=[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12},%s,%s' % (api.env.container_selinux, api.env.basedn)
|
||||
)
|
||||
fuzzy_hbacruledn = Fuzzy(
|
||||
'ipauniqueid=[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12},%s,%s' % (api.env.container_hbac, api.env.basedn)
|
||||
)
|
||||
|
||||
class test_selinuxusermap(Declarative):
|
||||
cleanup_commands = [
|
||||
('selinuxusermap_del', [rule1], {}),
|
||||
('group_del', [group1], {}),
|
||||
('user_del', [user1], {}),
|
||||
('host_del', [host1], {}),
|
||||
('hbacrule_del', [hbacrule1], {}),
|
||||
]
|
||||
|
||||
tests = [
|
||||
|
||||
dict(
|
||||
desc='Try to retrieve non-existent %r' % rule1,
|
||||
command=('selinuxusermap_show', [rule1], {}),
|
||||
expected=errors.NotFound(reason='no such entry'),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Try to update non-existent %r' % rule1,
|
||||
command=('selinuxusermap_mod', [rule1], dict(description=u'Foo')),
|
||||
expected=errors.NotFound(reason='no such entry'),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Try to delete non-existent %r' % rule1,
|
||||
command=('selinuxusermap_del', [rule1], {}),
|
||||
expected=errors.NotFound(reason='no such entry'),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Create rule %r' % rule1,
|
||||
command=(
|
||||
'selinuxusermap_add', [rule1], dict(ipaselinuxuser=selinuxuser1)
|
||||
),
|
||||
expected=dict(
|
||||
value=rule1,
|
||||
summary=u'Added SELinux User Map "%s"' % rule1,
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser1],
|
||||
objectclass=objectclasses.selinuxusermap,
|
||||
ipauniqueid=[fuzzy_uuid],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
dn=fuzzy_selinuxusermapdn,
|
||||
),
|
||||
),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Try to create duplicate %r' % rule1,
|
||||
command=(
|
||||
'selinuxusermap_add', [rule1], dict(ipaselinuxuser=selinuxuser1)
|
||||
),
|
||||
expected=errors.DuplicateEntry(),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Retrieve rule %r' % rule1,
|
||||
command=('selinuxusermap_show', [rule1], {}),
|
||||
expected=dict(
|
||||
value=rule1,
|
||||
summary=None,
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser1],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
dn=fuzzy_selinuxusermapdn,
|
||||
),
|
||||
),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Update rule %r' % rule1,
|
||||
command=(
|
||||
'selinuxusermap_mod', [rule1], dict(ipaselinuxuser=selinuxuser2)
|
||||
),
|
||||
expected=dict(
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser2],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
),
|
||||
summary=u'Modified SELinux User Map "%s"' % rule1,
|
||||
value=rule1,
|
||||
),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Retrieve %r to verify update' % rule1,
|
||||
command=('selinuxusermap_show', [rule1], {}),
|
||||
expected=dict(
|
||||
value=rule1,
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser2],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
dn=fuzzy_selinuxusermapdn,
|
||||
),
|
||||
summary=None,
|
||||
),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Search for rule %r' % rule1,
|
||||
command=('selinuxusermap_find', [], dict(cn=rule1)),
|
||||
expected=dict(
|
||||
count=1,
|
||||
truncated=False,
|
||||
result=[
|
||||
dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser2],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
dn=fuzzy_selinuxusermapdn,
|
||||
),
|
||||
],
|
||||
summary=u'1 SELinux User Map matched',
|
||||
),
|
||||
),
|
||||
|
||||
|
||||
###############
|
||||
# Create additional entries needed for testing
|
||||
dict(
|
||||
desc='Create %r' % user1,
|
||||
command=(
|
||||
'user_add', [], dict(givenname=u'Test', sn=u'User1')
|
||||
),
|
||||
expected=dict(
|
||||
value=user1,
|
||||
summary=u'Added user "%s"' % user1,
|
||||
result=dict(
|
||||
gecos=[u'Test User1'],
|
||||
givenname=[u'Test'],
|
||||
homedirectory=[u'/home/%s' % user1],
|
||||
krbprincipalname=[u'%s@%s' % (user1, api.env.realm)],
|
||||
loginshell=[u'/bin/sh'],
|
||||
objectclass=objectclasses.user,
|
||||
sn=[u'User1'],
|
||||
uid=[user1],
|
||||
uidnumber=[fuzzy_digits],
|
||||
gidnumber=[fuzzy_digits],
|
||||
displayname=[u'Test User1'],
|
||||
cn=[u'Test User1'],
|
||||
initials=[u'TU'],
|
||||
ipauniqueid=[fuzzy_uuid],
|
||||
krbpwdpolicyreference=lambda x: [DN(i) for i in x] == \
|
||||
[DN(('cn','global_policy'),('cn',api.env.realm),
|
||||
('cn','kerberos'),api.env.basedn)],
|
||||
mepmanagedentry=lambda x: [DN(i) for i in x] == \
|
||||
[DN(('cn',user1),('cn','groups'),('cn','accounts'),
|
||||
api.env.basedn)],
|
||||
memberof_group=[u'ipausers'],
|
||||
dn=lambda x: DN(x) == \
|
||||
DN(('uid',user1),('cn','users'),('cn','accounts'),
|
||||
api.env.basedn),
|
||||
has_keytab=False,
|
||||
has_password=False,
|
||||
),
|
||||
),
|
||||
),
|
||||
|
||||
dict(
|
||||
desc='Create group %r' % group1,
|
||||
command=(
|
||||
'group_add', [group1], dict(description=u'Test desc 1')
|
||||
),
|
||||
expected=dict(
|
||||
value=group1,
|
||||
summary=u'Added group "%s"' % group1,
|
||||
result=dict(
|
||||
cn=[group1],
|
||||
description=[u'Test desc 1'],
|
||||
gidnumber=[fuzzy_digits],
|
||||
objectclass=objectclasses.group + [u'posixgroup'],
|
||||
ipauniqueid=[fuzzy_uuid],
|
||||
dn=lambda x: DN(x) == \
|
||||
DN(('cn',group1),('cn','groups'),('cn','accounts'),
|
||||
api.env.basedn),
|
||||
),
|
||||
),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Add member %r to %r' % (user1, group1),
|
||||
command=(
|
||||
'group_add_member', [group1], dict(user=user1)
|
||||
),
|
||||
expected=dict(
|
||||
completed=1,
|
||||
failed=dict(
|
||||
member=dict(
|
||||
group=tuple(),
|
||||
user=tuple(),
|
||||
),
|
||||
),
|
||||
result={
|
||||
'dn': lambda x: DN(x) == \
|
||||
DN(('cn',group1),('cn','groups'),('cn','accounts'),
|
||||
api.env.basedn),
|
||||
'member_user': (user1,),
|
||||
'gidnumber': [fuzzy_digits],
|
||||
'cn': [group1],
|
||||
'description': [u'Test desc 1'],
|
||||
},
|
||||
),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Create host %r' % host1,
|
||||
command=('host_add', [host1],
|
||||
dict(
|
||||
description=u'Test host 1',
|
||||
l=u'Undisclosed location 1',
|
||||
force=True,
|
||||
),
|
||||
),
|
||||
expected=dict(
|
||||
value=host1,
|
||||
summary=u'Added host "%s"' % host1,
|
||||
result=dict(
|
||||
dn=lambda x: DN(x) == hostdn1,
|
||||
fqdn=[host1],
|
||||
description=[u'Test host 1'],
|
||||
l=[u'Undisclosed location 1'],
|
||||
krbprincipalname=[u'host/%s@%s' % (host1, api.env.realm)],
|
||||
objectclass=objectclasses.host,
|
||||
ipauniqueid=[fuzzy_uuid],
|
||||
managedby_host=[host1],
|
||||
has_keytab=False,
|
||||
has_password=False,
|
||||
),
|
||||
),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Create HBAC rule %r' % hbacrule1,
|
||||
command=(
|
||||
'hbacrule_add', [hbacrule1], {}
|
||||
),
|
||||
expected=dict(
|
||||
value=hbacrule1,
|
||||
summary=u'Added HBAC rule "%s"' % hbacrule1,
|
||||
result=dict(
|
||||
cn=[hbacrule1],
|
||||
objectclass=objectclasses.hbacrule,
|
||||
ipauniqueid=[fuzzy_uuid],
|
||||
accessruletype=[u'allow'],
|
||||
ipaenabledflag=[u'TRUE'],
|
||||
dn=fuzzy_hbacruledn,
|
||||
),
|
||||
),
|
||||
),
|
||||
|
||||
|
||||
###############
|
||||
# Fill out rule with members and/or pointers to HBAC rules
|
||||
dict(
|
||||
desc='Add user to %r' % rule1,
|
||||
command=('selinuxusermap_add_user', [rule1], dict(user=user1)),
|
||||
expected=dict(
|
||||
failed=dict(memberuser=dict(group=[], user=[])),
|
||||
completed=1,
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser2],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
memberuser_user = [user1],
|
||||
dn=fuzzy_selinuxusermapdn,
|
||||
),
|
||||
)
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Add non-existent user to %r' % rule1,
|
||||
command=('selinuxusermap_add_user', [rule1], dict(user=u'notfound')),
|
||||
expected=dict(
|
||||
failed=dict(memberuser=dict(group=[], user=[(u'notfound', u'no such entry')])),
|
||||
completed=0,
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser2],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
memberuser_user = [user1],
|
||||
dn=fuzzy_selinuxusermapdn,
|
||||
),
|
||||
)
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Remove user from %r' % rule1,
|
||||
command=('selinuxusermap_remove_user', [rule1], dict(user=user1)),
|
||||
expected=dict(
|
||||
failed=dict(memberuser=dict(group=[], user=[])),
|
||||
completed=1,
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser2],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
dn=fuzzy_selinuxusermapdn,
|
||||
),
|
||||
)
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Remove non-existent user to %r' % rule1,
|
||||
command=('selinuxusermap_remove_user', [rule1], dict(user=u'notfound')),
|
||||
expected=dict(
|
||||
failed=dict(memberuser=dict(group=[], user=[(u'notfound', u'This entry is not a member')])),
|
||||
completed=0,
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser2],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
dn=fuzzy_selinuxusermapdn,
|
||||
),
|
||||
)
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Add group to %r' % rule1,
|
||||
command=('selinuxusermap_add_user', [rule1], dict(group=group1)),
|
||||
expected=dict(
|
||||
failed=dict(memberuser=dict(group=[], user=[])),
|
||||
completed=1,
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser2],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
memberuser_group = [group1],
|
||||
dn=fuzzy_selinuxusermapdn,
|
||||
),
|
||||
)
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Add host to %r' % rule1,
|
||||
command=('selinuxusermap_add_host', [rule1], dict(host=host1)),
|
||||
expected=dict(
|
||||
failed=dict(memberhost=dict(hostgroup=[], host=[])),
|
||||
completed=1,
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser2],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
memberhost_host = [host1],
|
||||
memberuser_group = [group1],
|
||||
dn=fuzzy_selinuxusermapdn,
|
||||
),
|
||||
)
|
||||
),
|
||||
|
||||
|
||||
###############
|
||||
# Test enabling and disabling
|
||||
dict(
|
||||
desc='Disable %r' % rule1,
|
||||
command=('selinuxusermap_disable', [rule1], {}),
|
||||
expected=dict(
|
||||
result=True,
|
||||
value=rule1,
|
||||
summary=u'Disabled SELinux User Map "%s"' % rule1,
|
||||
)
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Disable %r again' % rule1,
|
||||
command=('selinuxusermap_disable', [rule1], {}),
|
||||
expected=errors.AlreadyInactive(),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Enable %r' % rule1,
|
||||
command=('selinuxusermap_enable', [rule1], {}),
|
||||
expected=dict(
|
||||
result=True,
|
||||
value=rule1,
|
||||
summary=u'Enabled SELinux User Map "%s"' % rule1,
|
||||
)
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Re-enable %r again' % rule1,
|
||||
command=('selinuxusermap_enable', [rule1], {}),
|
||||
expected=errors.AlreadyActive(),
|
||||
),
|
||||
|
||||
|
||||
# Point to an HBAC Rule
|
||||
dict(
|
||||
desc='Add an HBAC rule to %r that has other members' % rule1,
|
||||
command=(
|
||||
'selinuxusermap_mod', [rule1], dict(seealso=hbacrule1)
|
||||
),
|
||||
expected=errors.MutuallyExclusiveError(reason=u'cannot have both'),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Remove host from %r' % rule1,
|
||||
command=('selinuxusermap_remove_host', [rule1], dict(host=host1)),
|
||||
expected=dict(
|
||||
failed=dict(memberhost=dict(hostgroup=[], host=[])),
|
||||
completed=1,
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser2],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
memberuser_group = [group1],
|
||||
dn=fuzzy_selinuxusermapdn,
|
||||
),
|
||||
)
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Remove group from %r' % rule1,
|
||||
command=('selinuxusermap_remove_user', [rule1], dict(group=group1)),
|
||||
expected=dict(
|
||||
failed=dict(memberuser=dict(group=[], user=[])),
|
||||
completed=1,
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser2],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
dn=fuzzy_selinuxusermapdn,
|
||||
),
|
||||
)
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Add non-existent HBAC rule to %r' % rule1,
|
||||
command=(
|
||||
'selinuxusermap_mod', [rule1], dict(seealso=u'notfound')
|
||||
),
|
||||
expected=errors.NotFound(reason='no such entry'),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Add an HBAC rule to %r' % rule1,
|
||||
command=(
|
||||
'selinuxusermap_mod', [rule1], dict(seealso=hbacrule1)
|
||||
),
|
||||
expected=dict(
|
||||
result=dict(
|
||||
cn=[rule1],
|
||||
ipaselinuxuser=[selinuxuser2],
|
||||
ipaenabledflag = [u'TRUE'],
|
||||
seealso = hbacrule1,
|
||||
),
|
||||
summary=u'Modified SELinux User Map "%s"' % rule1,
|
||||
value=rule1,
|
||||
),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Add user to %r that has HBAC' % rule1,
|
||||
command=('selinuxusermap_add_user', [rule1], dict(user=user1)),
|
||||
expected=errors.MutuallyExclusiveError(reason=u'cannot have both'),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Add host to %r that has HBAC' % rule1,
|
||||
command=('selinuxusermap_add_host', [rule1], dict(host=host1)),
|
||||
expected=errors.MutuallyExclusiveError(reason=u'cannot have both'),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Try to delete HBAC rule pointed to by %r' % rule1,
|
||||
command=('hbacrule_del', [hbacrule1], {}),
|
||||
expected=errors.DependentEntry(key=hbacrule1, label=u'SELinux User Map', dependent=rule1)
|
||||
),
|
||||
|
||||
|
||||
# Test clean up
|
||||
dict(
|
||||
desc='Delete %r' % rule1,
|
||||
command=('selinuxusermap_del', [rule1], {}),
|
||||
expected=dict(
|
||||
result=dict(failed=u''),
|
||||
value=rule1,
|
||||
summary=u'Deleted SELinux User Map "%s"' % rule1,
|
||||
)
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Try to delete non-existent %r' % rule1,
|
||||
command=('selinuxusermap_del', [rule1], {}),
|
||||
expected=errors.NotFound(reason='no such entry'),
|
||||
),
|
||||
|
||||
|
||||
# Some negative tests
|
||||
dict(
|
||||
desc='Create rule with unknown user%r' % rule1,
|
||||
command=(
|
||||
'selinuxusermap_add', [rule1], dict(ipaselinuxuser=u'notfound')
|
||||
),
|
||||
expected=errors.NotFound(reason='no such entry'),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Create rule with invalid user bad+user',
|
||||
command=(
|
||||
'selinuxusermap_add', [rule1], dict(ipaselinuxuser=u'bad+user')
|
||||
),
|
||||
expected=errors.ValidationError(name='ipaselinuxuser', error='invalid name'),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Create rule with invalid MCS xguest_u:s999',
|
||||
command=(
|
||||
'selinuxusermap_add', [rule1], dict(ipaselinuxuser=u'xguest_u:s999')
|
||||
),
|
||||
expected=errors.ValidationError(name='ipaselinuxuser', error='invalid name'),
|
||||
),
|
||||
|
||||
|
||||
dict(
|
||||
desc='Create rule with invalid MLS xguest_u:s0:p88',
|
||||
command=(
|
||||
'selinuxusermap_add', [rule1], dict(ipaselinuxuser=u'xguest_u:s0:p88')
|
||||
),
|
||||
expected=errors.ValidationError(name='ipaselinuxuser', error='invalid name'),
|
||||
),
|
||||
|
||||
]
|
||||
Reference in New Issue
Block a user