SELinux Module Packaging in FC5
Paul Howarth
paul at city-fan.org
Fri May 26 12:59:44 UTC 2006
Stephen Smalley wrote:
> On Thu, 2006-05-18 at 14:18 +0100, Paul Howarth wrote:
>> Another query regarding policy module packages in RPMs:
>>
>> Supposing a package is installed when the system has SELinux disabled.
>>
>> What would happen if semodule was called to install a policy module?
>>
>> If the result is that nothing happens (or semodule bombs out with an
>> error of some sort), what would then happen if the system subsequently
>> had SELinux enabled and the system was relabelled? Would the package
>> containing the policy module have to be reinstalled?
>>
>> I'd try it myself but I can't bring myself to disable SELinux on any of
>> my boxes and go through the whole relabelling process.
>
> If policy is installed on the system, then semodule (actually
> libsemanage) will install the module and rebuild the generated files,
> but will not try to load policy into the kernel since SELinux is
> disabled. Then, if you enable SELinux, the module will already be
> included in the policy.
>
> If policy is not installed on the system, then semodule will abort with
> an error like this:
> semodule: SELinux policy is not managed or store cannot be accessed.
>
> Note also that one should generally use semodule -s <policytype> as in
> the selinux-policy .spec file to indicate which kind of policy your
> module is built for (targeted, strict, mls). Then, if the system is
> running a different kind of policy, semodule will know to install the
> module to the proper location (not the active policy) and to not try to
> load it.
OK, just to recap where I think we're up to. Here are the relevant parts
of my current spec file for the application "contagged", which will
have a policy module package included:
*** Top of spec, so that FC4/FC5 packages can build from same SRPM:
# FC5 and later include SELinux policy module packages
%if 0%{?fedora} < 5
%define selinux_module 0
%define selinux_variants %{nil}
%else
%define selinux_module 1
%define selinux_variants mls strict targeted
%endif
*** Buildreq needed for building .pp files:
%if %{selinux_module}
# selinux-policy >= 2.2.40 needed because of #190561
BuildRequires: checkpolicy, selinux-policy >= 2.2.40
%endif
*** Build .pp file for each base policy (SELinux directory contains
te/fc/if files):
%build
%if %{selinux_module}
cd SELinux
for selinuxvariant in %{selinux_variants}
do
%{__make} NAME=${selinuxvariant} verbose=@ \
-f /usr/share/selinux/devel/Makefile
%{__mv} SELinux/contagged.pp contagged.pp.${selinuxvariant}
%{__make} NAME=${selinuxvariant} \
-f /usr/share/selinux/devel/Makefile clean
done
cd -
%endif
*** Install .pp files
%install
... usual stuff ...
# Install SELinux policy modules
%if %{selinux_module}
for selinuxvariant in %{selinux_variants}
do
%{__install} -d %{buildroot}%{_datadir}/selinux/${selinuxvariant}
%{__install} -p -m 644 contagged.pp.${selinuxvariant} \
%{buildroot}%{_datadir}/selinux/${selinuxvariant}/contagged.pp
done
%endif
*** post-install scriptlet installs policy modules and fixes contexts:
%if %{selinux_module}
%post
# Install SELinux policy modules
if [ -x /usr/sbin/semodule ]; then
for selinuxvariant in %{selinux_variants}
do
/usr/sbin/semodule -s ${selinuxvariant} -i \
%{_datadir}/selinux/${selinuxvariant}/contagged.pp \
&> /dev/null || :
done
fi
# Fix up non-standard directory context
[ -x /sbin/restorecon ] && /sbin/restorecon \
%{_localstatedir}/cache/contagged || :
%endif
*** pre-uninstall script removes policy modules (and removes app's
cache, not SELinux-related)):
%postun
# Clean up after package removal
if [ $1 -eq 0 ]; then
# Clean out the cache
%{__rm} -f %{_localstatedir}/cache/contagged/*.tpl.php
/bin/rmdir %{_localstatedir}/cache/contagged &> /dev/null || :
%if %{selinux_module}
# Remove SELinux policy modules
if [ -x /usr/sbin/semodule ]; then
for selinuxvariant in %{selinux_variants}
do
/usr/sbin/semodule -s ${selinuxvariant} -r contagged || :
done
fi
%endif
fi
*** %files section includes policy module packages:
%files
... usual stuff ...
%if %{selinux_module}
%dir %{_datadir}/selinux/*
%{_datadir}/selinux/*/contagged.pp
%endif
Now Dan tells me in #190561 that one .pp file should be OK for all base
policies if there is no MLS-specific stuff in the policy. So:
* If there was MLS-specific stuff in the policy module, would the
approach above be correct?
* As there is no MLS-specific stuff in my package, I'd be inclined to
make a single .pp file, put it in %{_datadir}/selinux/share/contagged.pp
and just load that one .pp file for each base policy in %post
Dan also comments in #190561 that "ou only need to install it with
semodule, you do not need to intall the pp file"; I don't get this, as
how will semodule be able to access the .pp file if it isn't installed
with the package...
I'm also considering adding some horrible hack like this:
%if %{selinux_module}
%define selinux_policyver %(sed -e
's,.*selinux-policy-\\([^/]*\\)/.*,\\1,'
/usr/share/selinux/devel/policyhelp)
Conflicts: selinux-policy < %{selinux_policyver}
%endif
to avoid problems like this:
http://www.redhat.com/archives/fedora-selinux-list/2006-May/msg00102.html
My overall plan for this package is:
1. In conjuction with fedora-selinux-list, make this as clean a package
as possible SELinux-wise, such that it can form a good example for
others wishing to include policy module packages in their RPM packages.
2. In conjuction with fedora-extras-list, do the same from the point of
view of a PHP web application (the usual difficulty with these is that
upstream writes them in such a way that they're designed to be untarred
somewhere under /var/www and then just work, but that's not
FHS-compliant and not a good example).
3. Get the package accepted into Fedora Extras.
4. Include documentation on the wiki at
http://fedoraproject.org/wiki/Packaging/SELinux explaining why things in
the package are done the way they are, as a guide for other packagers.
Paul.
More information about the fedora-selinux-list
mailing list