Using Mock to test package builds

From FedoraProject

(Difference between revisions)
Jump to: navigation, search
m (Fix format)
m (What is Mock?: wikilink)
(17 intermediate revisions by 12 users not shown)
Line 2: Line 2:
  
 
== What is Mock? ==
 
== What is Mock? ==
Mock takes a srpm and builds it in a chroot.  This ensures that your [http://fedoraproject.org/wiki/Packaging/Guidelines#BuildRequires BuildRequires]  lines are correct, that there are no missing dependencies, and that it builds cleanly.
+
Mock takes a srpm and builds it in a chroot.  This ensures that your [[Packaging:Guidelines#BuildRequires_2|BuildRequires]]  lines are correct, that there are no missing dependencies, and that it builds cleanly.
 
The [[Projects/Mock|Mock project page]] has more information on Mock.
 
The [[Projects/Mock|Mock project page]] has more information on Mock.
  
Line 16: Line 16:
 
  # cd /etc/mock
 
  # cd /etc/mock
 
  # ln -s --force SOMECONFIG.cfg default.cfg
 
  # ln -s --force SOMECONFIG.cfg default.cfg
 +
 +
(An example of SOMECONFIG.cfg is "fedora-14-x86_64.cfg"; see the /etc/mock directory for the existing mock configurations.)
  
 
=== Setting up local mirror ===
 
=== Setting up local mirror ===
  
If you want to set up a local mirror, see:
+
If you want to set up a local mirror, refer [[Docs/Drafts/MockSetupUsingLocalMirror]]
* http://fedoraproject.org/wiki/MockSetupUsingLocalMirror { Currently: http://fedoraproject.org/wiki/Docs/Drafts/MockSetupUsingLocalMirror }
+
 
 +
=== Proxy Configurations ===
 +
 
 +
If you're behind a proxy, add the proxy info to the desired cfg file in /etc/mock in the same format that you would add it to your yum.conf.
 +
See '''man yum.conf''' for details on how to do it.
  
 
== How do I use Mock? ==
 
== How do I use Mock? ==
  
=== Using Mock outside your CVS sandbox ===
+
Mock accepts a number of commands.  Mock accepts commands in old-style format (e.g., "rebuild" or "init" without a leading "--"), but these are deprecated; use commands with a leading "--" instead.
 +
 
 +
=== Using Mock outside your git sandbox ===
  
 
Add your user name to the mock group
 
Add your user name to the mock group
  
<code>usermod -a -G mock myusername</code>
+
<code>sudo usermod -a -G mock myusername</code>
  
 
Create your srpm using 'rpmbuild -bs'. Then change to the directory where your srpm was created.
 
Create your srpm using 'rpmbuild -bs'. Then change to the directory where your srpm was created.
Line 34: Line 42:
 
Now you can start mock with
 
Now you can start mock with
  
<code>mock -r <configfile> rebuild package-1.2-3.src.rpm</code>
+
<code>mock -r <configfile> --rebuild package-1.2-3.src.rpm</code>
  
where <configfile> is the name of a configuration from <code>/etc/mock/</code> (do not include the <code>.cfg</code> extension).
+
where <configfile> is the name of a configuration from <code>/etc/mock/</code> (do not include the <code>.cfg</code> extension). Passing -r is not necessary if you have set a default config file via a symlink as shown above.  --rebuild is the default option.  So the following would work equally well
 +
 
 +
<code>mock package-1.2-3.src.rpm</code>
 +
 
 +
The --verbose option is useful if you want more output to be shown for debugging purposes. 
  
 
If using mock version older than 0.8.8 or on a system with python 2.4, and building i386 packages on x86_64, prepend <code>setarch i386</code> to the mock command line:
 
If using mock version older than 0.8.8 or on a system with python 2.4, and building i386 packages on x86_64, prepend <code>setarch i386</code> to the mock command line:
<code>setarch i386 mock -r <configfile> rebuild package-1.2-3.src.rpm</code>
+
 
 +
<code>setarch i386 mock -r <configfile> --rebuild package-1.2-3.src.rpm</code>
  
 
Newer versions of mock no longer need the setarch command, although it does not hurt anything if it is there.
 
Newer versions of mock no longer need the setarch command, although it does not hurt anything if it is there.
  
=== Using Mock inside your CVS sandbox ===
+
=== Using Mock inside your git sandbox ===
  
You only need to type 'make mockbuild' to start a mock build. The used architecture depends
+
You only need to type 'fedpkg mockbuild' to start a mock build. The used architecture depends
 
on the directory where you start the mock build.
 
on the directory where you start the mock build.
  
Line 56: Line 69:
 
  mock -r MOCK_CONFIG --init
 
  mock -r MOCK_CONFIG --init
  
(An example of MOCK_CONFIG is "fedora-12-x86_64"; see the /etc/mock directory for the existing mock configurations.)
+
(An example of MOCK_CONFIG is "fedora-14-x86_64"; see the /etc/mock directory for the existing mock configurations.)
  
 
Install the packages you need to build the program (named in BuildRequires) from the yum repositories and/or local RPMs.  In practice, you may need to do a number of these (for the different package dependencies); you can list multiple packages on the same line:
 
Install the packages you need to build the program (named in BuildRequires) from the yum repositories and/or local RPMs.  In practice, you may need to do a number of these (for the different package dependencies); you can list multiple packages on the same line:
 
  mock -r MOCK_CONFIG --install PACKAGE_NAME_OR_PATH_TO_RPM
 
  mock -r MOCK_CONFIG --install PACKAGE_NAME_OR_PATH_TO_RPM
 +
 +
Current versions of mock should permit you to now build from the source RPM. If that does not work then the "--copyin" method below should be used. The --no-clean option is necessary since by default the chroot is cleaned prior to building.
 +
mock -r MOCK_CONFIG --no-clean /PATH/TO/SRPM
  
 
Copy in the source RPM into /tmp (we'll copy in and do a build inside the shell, to work around the checks that detect that the packages aren't in the repository):
 
Copy in the source RPM into /tmp (we'll copy in and do a build inside the shell, to work around the checks that detect that the packages aren't in the repository):
Line 68: Line 84:
 
  cd
 
  cd
 
  rpmbuild --rebuild /tmp/SRPM_NAME
 
  rpmbuild --rebuild /tmp/SRPM_NAME
 
  
  
Line 88: Line 103:
  
 
-->
 
-->
 +
 +
== Speeding up ==
 +
 +
<ul>
 +
  <li><code>/etc/mock/site-defaults.cfg</code>
 +
  <ul>
 +
    <li>Disable the package state plugin: <pre>config_opts['plugin_conf']['package_state_enable'] = False</pre></li>
 +
    <li>Parallelize builds: <pre>config_opts['macros']['%_smp_mflags'] = "-j17"</pre></li>
 +
    <li>Improve ccache hits between package version builds (may break -debuginfos!):
 +
      <pre>config_opts['files']['etc/profile.d/zz-local.sh'] = """
 +
unset CCACHE_HASHDIR
 +
"""</pre></li>
 +
    <li>Compress ccache: <pre>config_opts['plugin_conf']['ccache_opts']['compress'] = True</pre></li>
 +
    <li>Use lzo compression for root cache:
 +
      <pre>config_opts['plugin_conf']['root_cache_opts']['compress_program'] = "lzop"
 +
config_opts['plugin_conf']['root_cache_opts']['extension'] = ".lzo"</pre></li>
 +
    </ul>
 +
  </li>
 +
  <li>Per-repo config files
 +
    <ul>
 +
      <li>Parallelize (de)compression within rpmbuild:
 +
        <pre>config_opts['chroot_setup_cmd'] = 'install @buildsys-build /usr/bin/pigz /usr/bin/lbzip2'
 +
config_opts['macros']['%__gzip'] = '/usr/bin/pigz'
 +
config_opts['macros']['%__bzip2'] = '/usr/bin/lbzip2'</pre></li>
 +
    </ul>
 +
  </li>
 +
</ul>
 +
 +
== Using [http://clang-analyzer.llvm.org/scan-build.html scan-build] for unmodified packages ==
 +
 +
* Add <code>/usr/bin/scan-build</code> to per-chroot config files' <code>chroot_setup_cmd</code> for which you want to use it, for example:
 +
<pre>config_opts['chroot_setup_cmd'] = 'install @buildsys-build /usr/bin/scan-build'</pre>
 +
 +
* Set up a shell alias and use it instead of plain mock (everything on one line):
 +
<pre>alias mock-scan-build="mock --define '__scan_build /usr/bin/scan-build' --define '_configure %__scan_build ./configure' --define '__cmake %__scan_build %{_bindir}/cmake' --define '__make %__scan_build %{_bindir}/make' --define '___build_template #!%{___build_shell}\\"$'\n'"alias make=\"%__make\" cmake=\"%__cmake\"\\"$'\n'"%{___build_pre}\\"$'\n'"%{nil}'"</pre>
 +
 +
* See generated reports in the chroot's <code>/tmp</code>
  
 
== Caching in mock 0.8.x and later ==
 
== Caching in mock 0.8.x and later ==
Line 152: Line 204:
 
'''Don't use the mirrorservice.org mirror; they [https://www.redhat.com/archives/fedora-extras-list/2006-September/msg00022.html prevent downstream caching]  via the HTTP header "Cache-Control: no-store". '''
 
'''Don't use the mirrorservice.org mirror; they [https://www.redhat.com/archives/fedora-extras-list/2006-September/msg00022.html prevent downstream caching]  via the HTTP header "Cache-Control: no-store". '''
  
If you're using squid, you don't want mock+squid to use a random mirror for downloading packages.  Change the config files in /etc/mock/*.cfg to use a single fast-for-you mirror in a <code>baseurl</code> entry, and don't use <code>mirrorlist</code>s.
+
If you're using squid, you don't want mock+squid to use a random mirror for downloading packages.  Change the config files in /etc/mock/*.cfg to use a single fast-for-you mirror in a <code>baseurl</code> entry, and don't use <code>mirrorlist</code>s. You can use [https://gist.github.com/4478541 this script] for that.
 
+
  
 
== Using tmpfs to avoid disk access ==
 
== Using tmpfs to avoid disk access ==
Line 177: Line 228:
 
a variety of possible exploits.
 
a variety of possible exploits.
 
This presents at least two sets of problems when using mock in FC5:
 
This presents at least two sets of problems when using mock in FC5:
1. When [[Legacy/Mock| building packages for legacy distributions]] , the build process can involve loading old shared libraries that do not have separate sections for, say, executable code and writable data. This leads to <code>execmod</code> denials when a process running in the <code>unconfined_t</code> domain tries to load such a library, unless the library is labelled <code>textrel_shlib_t</code>.
+
# When [[Legacy/Mock| building packages for legacy distributions]] , the build process can involve loading old shared libraries that do not have separate sections for, say, executable code and writable data. This leads to <code>execmod</code> denials when a process running in the <code>unconfined_t</code> domain tries to load such a library, unless the library is labelled <code>textrel_shlib_t</code>.
1. When building packages using ''mono'' (the same might apply to ''java''), the <code>mono</code> process would normally run in its own less-constrained domain (<code>mono_t</code>); when running under mock, <code>mono</code> runs in the <code>unconfined_t</code> domain, which can result in <code>execstack</code> and <code>execheap</code> denials.
+
# When building packages using ''mono'' (the same might apply to ''java''), the <code>mono</code> process would normally run in its own less-constrained domain (<code>mono_t</code>); when running under mock, <code>mono</code> runs in the <code>unconfined_t</code> domain, which can result in <code>execstack</code> and <code>execheap</code> denials.
 
Whilst it is possible to turn off these checks using SELinux booleans, this is not a desirable thing to do for all processes.
 
Whilst it is possible to turn off these checks using SELinux booleans, this is not a desirable thing to do for all processes.
 
Another solution would be to ensure that all files were labelled correctly in the chroot and that SELinux domain transitions ocurred when needed. However, this is not possible because processes running under mock are told by the dummy <code>libselinux</code> that SELinux is disabled.
 
Another solution would be to ensure that all files were labelled correctly in the chroot and that SELinux domain transitions ocurred when needed. However, this is not possible because processes running under mock are told by the dummy <code>libselinux</code> that SELinux is disabled.
Line 217: Line 268:
  
 
* Create a config file that points to the repo(s) of your choice, where your test packages are
 
* Create a config file that points to the repo(s) of your choice, where your test packages are
* mock -r <config-name> init
+
mock -r <config-name> --init
* /usr/sbin/mock-helper yum --installroot /var/lib/mock/<config-name>/root install <your packages>
+
mock -r <config-name> --install <your packages>
* mock -r <config-name> shell
+
mock -r <config-name> --shell
  
 
Why use mock to shell, why not chroot directly?  Using mock to "shell" will allow mock to create the mountpoints you'll probably need inside the chroot.  If you want to manage your mounts manually, do so by all means.
 
Why use mock to shell, why not chroot directly?  Using mock to "shell" will allow mock to create the mountpoints you'll probably need inside the chroot.  If you want to manage your mounts manually, do so by all means.
 +
 +
== Testing graphical applications inside mock ==
 +
 +
To test graphical applications or tcl/tk bindings inside mock you have to enable other hosts using xhost (or at least the one you need):
 +
<pre>
 +
xhost +
 +
</pre>
 +
 +
and then set the DISPLAY environment variable inside the chroot:
 +
 +
<pre>
 +
export DISPLAY=:0.0
 +
</pre>
  
 
[[Category:Package Maintainers]]
 
[[Category:Package Maintainers]]

Revision as of 13:04, 20 January 2014

This page is a collection of bits people have found useful when working with mock.

Contents

What is Mock?

Mock takes a srpm and builds it in a chroot. This ensures that your BuildRequires lines are correct, that there are no missing dependencies, and that it builds cleanly. The Mock project page has more information on Mock.

How do I set up Mock?

First, install the mock package, which is available from Fedora Package Collection.

Default configuration

When using mock, you can use the "-r" option to select a particular test configuration. If there's one configuration that system users will normally use, you can set that as the default:

# cd /etc/mock
# ln -s --force SOMECONFIG.cfg default.cfg

(An example of SOMECONFIG.cfg is "fedora-14-x86_64.cfg"; see the /etc/mock directory for the existing mock configurations.)

Setting up local mirror

If you want to set up a local mirror, refer Docs/Drafts/MockSetupUsingLocalMirror

Proxy Configurations

If you're behind a proxy, add the proxy info to the desired cfg file in /etc/mock in the same format that you would add it to your yum.conf. See man yum.conf for details on how to do it.

How do I use Mock?

Mock accepts a number of commands. Mock accepts commands in old-style format (e.g., "rebuild" or "init" without a leading "--"), but these are deprecated; use commands with a leading "--" instead.

Using Mock outside your git sandbox

Add your user name to the mock group

sudo usermod -a -G mock myusername

Create your srpm using 'rpmbuild -bs'. Then change to the directory where your srpm was created.

Now you can start mock with

mock -r <configfile> --rebuild package-1.2-3.src.rpm

where <configfile> is the name of a configuration from /etc/mock/ (do not include the .cfg extension). Passing -r is not necessary if you have set a default config file via a symlink as shown above. --rebuild is the default option. So the following would work equally well

mock package-1.2-3.src.rpm

The --verbose option is useful if you want more output to be shown for debugging purposes.

If using mock version older than 0.8.8 or on a system with python 2.4, and building i386 packages on x86_64, prepend setarch i386 to the mock command line:

setarch i386 mock -r <configfile> --rebuild package-1.2-3.src.rpm

Newer versions of mock no longer need the setarch command, although it does not hurt anything if it is there.

Using Mock inside your git sandbox

You only need to type 'fedpkg mockbuild' to start a mock build. The used architecture depends on the directory where you start the mock build.

Building packages that depend on packages not in a repository

If you're building some package P that depends on another package Q, and Q is not in a repository, you can still use mock. Here's one way to do that.

First, initialize the mock repository:

mock -r MOCK_CONFIG --init

(An example of MOCK_CONFIG is "fedora-14-x86_64"; see the /etc/mock directory for the existing mock configurations.)

Install the packages you need to build the program (named in BuildRequires) from the yum repositories and/or local RPMs. In practice, you may need to do a number of these (for the different package dependencies); you can list multiple packages on the same line:

mock -r MOCK_CONFIG --install PACKAGE_NAME_OR_PATH_TO_RPM

Current versions of mock should permit you to now build from the source RPM. If that does not work then the "--copyin" method below should be used. The --no-clean option is necessary since by default the chroot is cleaned prior to building.

mock -r MOCK_CONFIG --no-clean /PATH/TO/SRPM

Copy in the source RPM into /tmp (we'll copy in and do a build inside the shell, to work around the checks that detect that the packages aren't in the repository):

mock -r MOCK_CONFIG --copyin /PATH/TO/SRPM /tmp

Shell into the mock environment and perform the build:

mock -r MOCK_CONFIG --shell
cd
rpmbuild --rebuild /tmp/SRPM_NAME


Speeding up

  • /etc/mock/site-defaults.cfg
    • Disable the package state plugin:
      config_opts['plugin_conf']['package_state_enable'] = False
    • Parallelize builds:
      config_opts['macros']['%_smp_mflags'] = "-j17"
    • Improve ccache hits between package version builds (may break -debuginfos!):
      config_opts['files']['etc/profile.d/zz-local.sh'] = """
      unset CCACHE_HASHDIR
      """
    • Compress ccache:
      config_opts['plugin_conf']['ccache_opts']['compress'] = True
    • Use lzo compression for root cache:
      config_opts['plugin_conf']['root_cache_opts']['compress_program'] = "lzop"
      config_opts['plugin_conf']['root_cache_opts']['extension'] = ".lzo"
  • Per-repo config files
    • Parallelize (de)compression within rpmbuild:
      config_opts['chroot_setup_cmd'] = 'install @buildsys-build /usr/bin/pigz /usr/bin/lbzip2'
      config_opts['macros']['%__gzip'] = '/usr/bin/pigz'
      config_opts['macros']['%__bzip2'] = '/usr/bin/lbzip2'

Using scan-build for unmodified packages

  • Add /usr/bin/scan-build to per-chroot config files' chroot_setup_cmd for which you want to use it, for example:
config_opts['chroot_setup_cmd'] = 'install @buildsys-build /usr/bin/scan-build'
  • Set up a shell alias and use it instead of plain mock (everything on one line):
alias mock-scan-build="mock --define '__scan_build /usr/bin/scan-build' --define '_configure %__scan_build ./configure' --define '__cmake %__scan_build %{_bindir}/cmake' --define '__make %__scan_build %{_bindir}/make' --define '___build_template #!%{___build_shell}\\"$'\n'"alias make=\"%__make\" cmake=\"%__cmake\"\\"$'\n'"%{___build_pre}\\"$'\n'"%{nil}'"
  • See generated reports in the chroot's /tmp

Caching in mock 0.8.x and later

Mock 0.8.x introduces three different types of caches: 1) root cache, 2) yum cache, and 3) ccache. These caches greatly speed up mock.

Look in /etc/mock/defaults.cfg for documentation on configuring each of these caches. You can configure the directory where they are stored, the maximum age of the caches, and (for ccache only) the max disk usage for the cache.

Root cache

Starting with mock 0.5, mock can automatically cache the standard buildroot for each environment in a local tar file (/var/cache/mock/$CONFIG/root_cache/*). It then unpacks this tar file to populate the buildroot, rather than downloading the buildroot RPMs fresh each time. After unpacking the buildroot from the root cache, mock does a yum update to make sure that the buildroot is up-to-date prior to installing additional BuildRequires for a package build.

The root cache is enabled by default in mock 0.8.x and later. To disable, see the documentation in /etc/mock/defaults.cfg. The root cache can be disabled globally or per-chroot. The root caches are automatically deleted and recreated every 15 days to prevent them from being too stale.

Keep in mind that the root cache can affect reproducibility of your build, especially in environments where the set of base RPMs is updated often (eg. rawhide). Disable the root cache in environments where build reproducibility is of utmost importance.

yum cache

By default, yum stores downloaded RPMs in a directory under /var/cache/yum. The yum cache feature bind mounts the chroot /var/cache/yum to a common directory outside the chroot environment (such as /var/cache/mock/$CONFIG/yum_cache/) where it can be saved and re-used by subsequent builds. This ensures that yum does not need to download each RPM fresh over the network for every build. This feature is enabled by default.

ccache

The ccache tool is a utility that wraps calls to compilers such as 'gcc' and caches the output. When called to compile the same program a second time (with the same cmdline args, gcc-version, and header files), ccache will instead pull the cached version rather than running the compiler afresh.

Using Squid to Speed Up Mock package downloads

The cached buildroots trick above is much faster than using squid alone, but you can also use squid in addition to the cached buildroots, particularly if you are at the slow end of an Internet connection.

The root cache will contain the standard buildroot packages, but as it gets older, the yum update after unpacking it may have to update several packages. In addition, some packages aren't in the standard buildroot, but are often needed (e.g. pkgconfig). These can be faster served from a squid cache than from downloading them from the Internet for each package build.

Install the squid package which is available from Fedora Package Collection.

Some items worth changing in /etc/squid/squid.conf:

  • Maximum Object Size. Normally, this is 4MB. However, some of the base packages like glibc can be larger than 16MB, and if you're building say Eclipse plugins, that's 60MB. So make it large.

maximum_object_size 409600 KB

  • Cache Replacement Policy. Normally, lru is fine. But in our case, we want to keep the largest objects around longer, and just download the smaller objects if we can.

cache_replacement_policy heap LFUDA

  • Cache Size. Normal size is 100MB. This isn't going to cut it. This needs to be at least 1GB, more if you regularly build for multiple Fedora releases and multiple architectures.

cache_dir ufs /var/spool/squid 1000 16 256

Then start squid, and configure it to start on startup.

To make the build user automatically use the squid cache, type:

echo export http_proxy=\"http://localhost:3128\" >> /home/build/.bash_profile

If you only want to use squid for particular mock configurations (perhaps you have local mirrors of some distributions and don't need squid for those), you can, instead of setting the http_proxy environment variable, set up the proxy configuration in the yum.conf part of each mock configuration file:

config_opts['yum.conf']  = """
[main] 
...
proxy=http://localhost:3128/

...
"""

Edit /etc/mock/*.cfg to not use mirror lists

Don't use the mirrorservice.org mirror; they prevent downstream caching via the HTTP header "Cache-Control: no-store".

If you're using squid, you don't want mock+squid to use a random mirror for downloading packages. Change the config files in /etc/mock/*.cfg to use a single fast-for-you mirror in a baseurl entry, and don't use mirrorlists. You can use this script for that.

Using tmpfs to avoid disk access

It's not clear that tmpfs is a huge win anymore, now that autocache works and is a standard feature.

When having enough RAM (1.5-2 GB), using a tmpfs can speedup the 'prep' phase significantly. With 1.5GB RAM on a Celeron 2.8 GHz, populating the buildroot will take 2-5s (seconds) on subsequent builds.

You can either mount /var/lib/mock as a tmpfs, or you can mount each of the build directories under /var/lib/mock as separate tmpfs file systems. The latter lets you use the autocache above and keeps the autocache files on disk, rather than in the tmpfs. If you erase and recreate the autocaches often, keeping them in tmpfs makes sense. If you don't recreate them often, then you should use per-build-directory tmpfs mounts instead.


Using mock under SELinux

Using SELinux in conjuction with chroot-ed environments such as mock presents a number of problems, such as needing to replicate all default file contexts with the chroot directory prefix, which is an administrative nightmare. The approach used by mock is very simple, though it only works with the targeted policy: preload a dummy libselinux that makes all child processes think that SELinux is disabled. With mock itself running as an unconfined process, this generally works well.

Problems with SELinux memory protection

However, from FC5 onwards, the SELinux unconfined_t domain is no longer fully unconfined by SELinux; memory protection is implemented to protect most user processes against a variety of possible exploits. This presents at least two sets of problems when using mock in FC5:

  1. When building packages for legacy distributions , the build process can involve loading old shared libraries that do not have separate sections for, say, executable code and writable data. This leads to execmod denials when a process running in the unconfined_t domain tries to load such a library, unless the library is labelled textrel_shlib_t.
  2. When building packages using mono (the same might apply to java), the mono process would normally run in its own less-constrained domain (mono_t); when running under mock, mono runs in the unconfined_t domain, which can result in execstack and execheap denials.

Whilst it is possible to turn off these checks using SELinux booleans, this is not a desirable thing to do for all processes. Another solution would be to ensure that all files were labelled correctly in the chroot and that SELinux domain transitions ocurred when needed. However, this is not possible because processes running under mock are told by the dummy libselinux that SELinux is disabled.

SELinux policy module for mock

The following solution to these issues creates an SELinux policy for mock that has two aspects:

  1. It runs mock in its own domain (mock_t) that is as unconstrained as any process that needs to run under it needs to be, which so far means that it allows execheap and execmod, just like the mono_t domain does.
  2. It labels all files installed under /var/lib/mock (where mock sets up its chroot environments) with the special context type mock_var_lib_t, for which execmod is allowed for processes in the mock_t domain.

This solution relaxes SELinux protection sufficiently for mock to be able to work, without compromising the protection afforded to the normal unconfined domain.

To install the policy module:

# make -f /usr/share/selinux/devel/Makefile
Compliling targeted mock module
/usr/bin/checkmodule:  loading policy configuration from tmp/mock.tmp
/usr/bin/checkmodule:  policy configuration loaded
/usr/bin/checkmodule:  writing binary representation (version 5) to tmp/mock.mod
Creating targeted mock.pp policy package
rm tmp/mock.mod.fc tmp/mock.mod
Warning (medium size).png
The selinux-policy-devel and checkpolicy packages are required

If the policy module is loaded before the mock package is installed, /var/lib/mock will be labelled as mock_var_lib_t and /usr/bin/mock will be labelled as mock_exec_t at installation time. Otherwise, it's necessary to use restorecon to fix the file contexts:

# restorecon -R /var/lib/mock /usr/bin/mock
Note.png
This policy would probably work for mach as well, just by adding these two lines to mock.fc:
/usr/bin/mach       -- gen_context(system_u:object_r:mock_exec_t,s0)
/var/lib/mach(/.*)?    gen_context(system_u:object_r:mock_var_lib_t,s0)

Using mock as a chroot sandbox tool

Mock can be used to create chroots for testing things, not just building packages. Here is a quick howto:

  • Create a config file that points to the repo(s) of your choice, where your test packages are
mock -r <config-name> --init
mock -r <config-name> --install <your packages>
mock -r <config-name> --shell

Why use mock to shell, why not chroot directly? Using mock to "shell" will allow mock to create the mountpoints you'll probably need inside the chroot. If you want to manage your mounts manually, do so by all means.

Testing graphical applications inside mock

To test graphical applications or tcl/tk bindings inside mock you have to enable other hosts using xhost (or at least the one you need):

xhost + 

and then set the DISPLAY environment variable inside the chroot:

export DISPLAY=:0.0