diff options
Diffstat (limited to 'docs/usermanual/reference/fakeroot.xml')
-rw-r--r-- | docs/usermanual/reference/fakeroot.xml | 186 |
1 files changed, 186 insertions, 0 deletions
diff --git a/docs/usermanual/reference/fakeroot.xml b/docs/usermanual/reference/fakeroot.xml new file mode 100644 index 0000000000..5eb6a48eb0 --- /dev/null +++ b/docs/usermanual/reference/fakeroot.xml @@ -0,0 +1,186 @@ +<?xml version="1.0" encoding="UTF-8"?> +<section id="fakeroot" xreflabel="fakeroot"> + <title>fakeroot (device node handling)</title> + + <para>The fakeroot program is designed to allow non-root users to perform + actions that would normally require root privileges as part of the package + generation process. It is used by the <xref linkend="rootfs_ipkg_class" /> + for root filesystem creation and by the <xref linkend="image_class" /> + for the creation of filesystem images. Some recipes also use fakeroot to + assist with parts of the package installation (usually) or building where + root privligeses are expected by the package.</para> + + <para>In particular fakeroot deals with:</para> + + <itemizedlist> + <listitem> + <para>Device nodes; and</para> + </listitem> + + <listitem> + <para>Ownership and group (uid & gid) management.</para> + </listitem> + </itemizedlist> + + <section> + <title>How fakeroot works</title> + + <para>First of all we'll look at an example of how the fakeroot process + works when used manually.</para> + + <para>If we attempt to create a device node as a normal non-root user then + the command will fail, telling is that we do not have permission to create + device nodes:<screen>~%> mknod hdc b 22 0 +mknod: `hdc': Operation not permitted</screen>Yet the <xref + linkend="image_class" /> is able to create device nodes and include + them in the final images, all without the need to have root + privileges.</para> + + <para>Let's try and create that node again, this time we'll run the + commands from within a fakeroot process:<screen>~%> ./tmp/staging/x86_64-linux/bin/fakeroot +~#> mknod hdc b 22 0 +~#> ls -l hdc +brw------- 1 root root 22, 0 Aug 18 13:20 hdc +~#></screen>So it looks like we have successfully managed to create a + device node, even though we did not have to give a password for the root + user. In reality this device node still doesn't exist, it just looks like + it exits. Fakeroot is lying to the shell process and telling it that + <emphasis>"yes, this file exists and these are it's + properties"</emphasis>. We'll talk more about how fakeroot actually works + in a minute.</para> + + <para>In this case <command>hdc</command> is the cd-rom drive, so let's + try and actually mount the cd-rom:<screen>~#> mkdir disk +~#> mount hdc disk +ERROR: ld.so: object 'libfakeroot.so.0' from LD_PRELOAD cannot be preloaded: ignored. +mount: only root can do that +~#></screen>So even though it appears we have root permissions, and that we + created a device node, you see that the system gives an error about + libfakeroot and about not being able to run mount because we are not + root.</para> + + <para>If we exit the fakeroot process and then look at the device node + this is what we see:<screen>~#> exit +~%> ls -l hdc +brw------- 1 user user 22, 0 Aug 18 13:20 hdc +~#></screen></para> + + <para>Note that it isn't a device node at all, just an empty file owned by + the current user!</para> + + <para>So what exactly is fakeroot doing? It's using + <command>LD_PRELOAD</command> to load a shared library into program which + replaces calls into libc, such as open and stat, and then returns + information to make it look like certain commands succeeded without + actually performing those commands. So when creating a device node + fakeroot will:</para> + + <orderedlist> + <listitem> + <para>Intercept the mknod system call and instead of creating a device + node it'll just create an empty file, owned by the user who run + fakeroot;</para> + </listitem> + + <listitem> + <para>It remembers the fact that mknod was called by root and it + remembers the properties of the device node;</para> + </listitem> + + <listitem> + <para>When a program, such as ls, calls stat on the file fakeroot + remembers that it was device node, owned by root, and modifies that + stat information to return this to ls. So ls sees a device node even + though one doesn't exist.</para> + </listitem> + </orderedlist> + + <para>When we tried to run mount we received the error <command>"ERROR: + ld.so: object 'libfakeroot.so.0' from LD_PRELOAD cannot be preloaded: + ignored."</command>. This is due to the fact that mount is an suid root + binary, and for security reasons <command>LD_PRELOAD</command> is disabled + on suid binaries.</para> + + <para>There are some very important points to remember when dealing with + fakeroot:</para> + + <orderedlist> + <listitem> + <para>All information regarding devices nodes, uid and gids will be + lost when fakeroot exists;</para> + </listitem> + + <listitem> + <para>None of the device nodes, uids or gids will appear on disk. + However if you tar up a directory from within fakeroot (for example), + all of these device, uids and gids will appear correctly in the tar + archive;</para> + </listitem> + + <listitem> + <para>Any suid binaries will not interact with fakeroot;</para> + </listitem> + + <listitem> + <para>Any static binaries will not interact with fakeroot;</para> + </listitem> + </orderedlist> + </section> + + <section> + <title>Root filesystem, images and fakeroot</title> + + <para>Many people have been confused by the generated root filesystem not + containing any valid device nodes. This is in fact the expected + behaviour.</para> + + <para>When you look at a generated root filesystem you'll notice that the + device nodes all appear to be incorrectly created:<screen>~%> ls -l tmp/rootfs/dev | grep ttySC +-rw-r--r-- 1 root root 0 Aug 16 13:07 ttySC0 +-rw-r--r-- 1 root root 0 Aug 16 13:07 ttySC1 +-rw-r--r-- 1 root root 0 Aug 16 13:07 ttySC2 +~%></screen>These are empty files and not device nodes at all.</para> + + <para>If we look in the image files generated from that root filesystem + then everything is actually ok:<screen>~%> tar -ztvf tmp/deploy/images/titan-titan-20060816030639.rootfs.tar.gz | grep " ./dev/ttySC" +crw-r----- root/root 204,8 2006-08-16 13:07:12 ./dev/ttySC0 +crw-r----- root/root 204,9 2006-08-16 13:07:12 ./dev/ttySC1 +crw-r----- root/root 204,10 2006-08-16 13:07:12 ./dev/ttySC2 +~%></screen>The images are created from within the same fakeroot process as + the creation of the root filesystem and therefore it correctly picks up + all of the special files and permissions from fakeroot.</para> + + <para><emphasis role="bold">NOTE: This means that you cannot use the root + filesystem in tmp/rootfs directly on your target device. You need to use + the .tar.gz image and uncompress it, as root, in order to generate a root + filesystem which is suitable for use directly on the target (or as an NFS + root).</emphasis></para> + </section> + + <section> + <title>Recipes and fakeroot</title> + + <para>Some applications require that you have root permissions to run + their installation routine, and this is another area where fakeroot can + help. In a recipe the method for a standard task, such as the + <command>do_install</command> method for the <emphasis>install</emphasis> + task:<screen>do_install() { + install -d ${D}${bindir} ${D}${sbindir} ${D}${mandir}/man8 \ + ${D}${sysconfdir}/default \ + ${D}${sysconfdir}/init.d \ + ${D}${datadir}/arpwatch + + oe_runmake install DESTDIR=${D} + oe_runmake install-man DESTDIR=${D} + ...</screen>can be modified to run within a fakeroot environment by + prefixing the method name with fakeroot:<screen><emphasis role="bold">fakeroot</emphasis> do_install() { + install -d ${D}${bindir} ${D}${sbindir} ${D}${mandir}/man8 \ + ${D}${sysconfdir}/default \ + ${D}${sysconfdir}/init.d \ + ${D}${datadir}/arpwatch + + oe_runmake install DESTDIR=${D} + oe_runmake install-man DESTDIR=${D} + ...</screen></para> + </section> +</section>
\ No newline at end of file |