Line 1:
Line 1:
[[Category: Development]]
[[Category: Development]]
−
[[Category: Empty articles]]
+
[[Category: Under the hood]]
+
+
=== Compatible applications ===
+
+
On x86_64 there are two types of compatible applications:
+
* ia32 - compiled to run on i686 target, can be executed on x86_64 with <code>IA32_EMULATION</code> config option set.
+
* x32 - specially compiled binaries to run on x86_64 machine with <code>CONFIG_X86_X32</code> config option set.
+
+
Both of them uses 4 byte pointers thus can address no more than 4Gb of virtual memory.<br />
+
But x32 uses full 64-bit register set (and thus can't be launched on i686 host natively).<br />
+
Both of them requires additional environment on x86_64 as Glibc, libraries, and compiler support.<br />
+
x32 is rarely distributed (at this moment only [https://wiki.debian.org/X32Port Debian x32 port can be easily found]).<br />
+
So, CRIU will support ia32 C/R at this moment, x32 support may be quite easily added on top of ia32 as needed patches have already added in kernel with ia32 C/R support.<br />
+
The following text uses ''compatible'' and ''32-bit'' in the meaning of ia32 applications unless otherwise specified.
+
+
=== Difference between native and compat applications ===
+
+
From the CPU's point of view, 32-bit compatibility mode applications differ to 64-bit application by current CS (code segment selector): if corresponding value of L-bit from flags of entry in descriptors table is set the CPU will be in 64-bit mode when this segment descriptor is being used. There are some other differences between 32 and 64-bit selectors, one can read about them [https://www.malwaretech.com/2014/02/the-0x33-segment-selector-heavens-gate.html in the article "The 0x33 Segment Selector (Heavens Gate)"]. Code selectors for both bits are defined in kernel headers as <code>__USER32_CS</code> and <code>__USER_CS</code> and corresponds to descriptors in GDT (Global Descriptors Table). One can change 64-bit mode to compatibility mode by swapping CS value (e.g., with longjump).
+
+
From the Linux kernel's point of view, applications differ by values set during exec of application such as <code>mmap_base</code> or thread info flags <code>TIF_ADDR32</code>/<code>TIF_IA32</code>/<code>TIF_X32</code>.
+
Both native and compat applications can do 32 or 64-bit syscalls.
+
+
=== Approaches to C/R compatible applications ===
+
+
C/R of compatible applications can be done differently, this section describes cons/pros of each, to address decision why C/R of 32-bit tasks done ''that'' way and not some other.
+
+
==== Restore with exec() of 32-bit dummy binary vs from 64-bit CRIU ====
+
+
Restore of 32-bit application can be done with some daemon that runs in 32-bit mode and communicates with CRIU binary (or 32-bit CRIU subprocess).<br />
+
'''Pros''':
+
* no kernel patches expected (not quite true: vDSO mremap() still needed support)
+
+
'''Cons''':
+
* CRIU code base does not have special restore daemon to communicate with - code needs to be reworked
+
* 64-bit app can have 32-bit child, which could be a parent to 64-bit and so on - need to re-exec native 64-bit CRIU from 32-bit dummy (or 32-bit CRIU)
+
* need to send to the daemon properties of restoring processes, open fds to images, share memory with parsed ps_tree and so on... The number of IPC calls will slow down restore
+
* restoring becomes more complicated, and if looking forward to restoring user/pid sub-namespaces, it will be too entangled
+
* no optimized inheritance for task's properties those erase with exec()
+
+
==== Restore with a flag to sigreturn() or arch_prctl() ====
+
+
==== Seizing with two 32-bit and 64-bit parasites ====
+
+
==== Current approach ====
+
+
=== Needs to be done (TODO) ===
+
+
==== List of failed tests ====
+
+
==== Bug with mmaping over 4Gb ====