Úvod od překladatele: Na pozadí masivního vstupu různých druhů kontejnerů do našich životů může být docela zajímavé a užitečné zjistit, s jakými technologiemi to všechno kdysi začalo. Některé z nich lze užitečně používat dodnes, ale ne každý si takové metody pamatuje (nebo ví, zda se nechytily při jejich překotném vývoji). Jednou z takových technologií je User Mode Linux. Autor originálu hodně makal, zjišťoval, který ze starých vývojů ještě funguje a který ne, a dal dohromady něco jako návod krok za krokem, jak si pořídit homebrew UML ve 2k19. A ano, pozvali jsme k Habrovi autora původního příspěvku Cadey, takže pokud máte nějaké dotazy - ptejte se v angličtině v komentářích.
Uživatelský režim v Linuxu je ve skutečnosti portem linuxového jádra pro sebe. Tento režim vám umožňuje spouštět úplné linuxové jádro jako uživatelský proces a vývojáři jej běžně používají k testování ovladačů. Tento režim je ale také užitečný jako obecný izolační nástroj, jehož princip je podobný provozu virtuálních strojů. Tento režim poskytuje větší izolaci než Docker, ale méně než plnohodnotný virtuální stroj, jako je KVM nebo Virtual Box.
Obecně se Uživatelský režim může zdát jako zvláštní a obtížně použitelný nástroj, ale stále má své využití. Přeci jen se jedná o plnohodnotné linuxové jádro běžící od neprivilegovaného uživatele. Tato funkce umožňuje spustit potenciálně nedůvěryhodný kód bez jakéhokoli ohrožení hostitelského počítače. A protože se jedná o plnohodnotné jádro, jeho procesy jsou izolované od hostitelského stroje, tzn procesy běžící v uživatelském režimu nebudou pro hostitele viditelné. Toto není jako obvyklý kontejner Docker, v takovém případě hostitelský počítač vždy vidí procesy uvnitř úložiště. Podívejte se na tento kousek pstree z jednoho z mých serverů:
A porovnejte to s pstree linuxového jádra v uživatelském režimu:
linux─┬─5*[linux]
└─slirp
Při práci s kontejnery Docker vidím z hostitele názvy procesů, které v hostu běží. V uživatelském režimu Linux to není možné. Co to znamená? To znamená, že monitorovací nástroje, které běží prostřednictvím auditovacího subsystému Linuxu nevidět procesy běžící v hostujícím systému. Ale v některých situacích se tato vlastnost může stát dvousečným mečem.
Obecně platí, že celý příspěvek níže je sbírkou výzkumů a hrubých pokusů o dosažení požadovaného výsledku. K tomu jsem musel používat různé starodávné nástroje, číst zdrojové kódy jádra, provádět intenzivní ladění kódu napsaného v dobách, kdy jsem byl ještě na základní škole, a také si pohrát s sestaveními Heroku pomocí speciální binárky, abych našel nástroje, které jsem potřeboval. . Všechna tato práce vedla lidi na mém IRC k tomu, aby mi říkali magie. Doufám, že tento příspěvek poslouží jako spolehlivá dokumentace pro někoho, kdo může zkusit to samé s novějšími jádry a verzemi OS.
Nastavení
Nastavení uživatelského režimu Linuxu se provádí v několika krocích:
instalace závislostí na hostiteli;
stažení linuxového jádra;
konfigurace sestavení jádra;
sestavení jádra;
binární instalace;
konfigurace souborového systému hosta;
výběr parametrů spouštění jádra;
nastavení sítě pro hosty;
spuštění hostujícího jádra.
Předpokládám, že pokud se pro to rozhodnete sami, s největší pravděpodobností uděláte vše popsané v nějakém systému Ubuntu nebo Debianu. Zkoušel jsem implementovat vše výše uvedené ve své oblíbené distribuci - Alpine, ale nic z toho nebylo, zřejmě kvůli tomu, že jádro Linuxu má pevně vázané glibc-ismy pro ovladače v uživatelském režimu. Až problém konečně pochopím, plánuji to nahlásit upstreamu.
Instalace závislostí na hostiteli
Ubuntu vyžaduje pro sestavení linuxového jádra alespoň následující balíčky (za předpokladu čisté instalace):
Pamatujte, že spuštění instalačního programu nabídky jádra Linuxu bude vyžadovat instalaci libncurses-dev. Ujistěte se prosím, že je nainstalován pomocí následujícího příkazu (jako root nebo pomocí sudo):
apt-get -y install libncurses-dev
Stažení jádra
Rozhodněte se, kde stáhnout a poté sestavit jádro. Pro tuto operaci budete muset přidělit asi 1,3 GB místa na pevném disku, takže se ujistěte, že ho máte.
Nyní vstoupíme do adresáře vytvořeného při rozbalování tarballu:
cd linux-5.1.16
Nastavení sestavení jádra
Systém sestavení jádra je sada Makefiles с mnoho vlastní nástroje a skripty pro automatizaci procesu. Nejprve otevřete interaktivní instalační program:
make ARCH=um menuconfig
Částečně vytvoří a zobrazí dialogové okno za vás. Když '[Select]', budete moci konfigurovat pomocí kláves Space nebo Enter. V okně se jako obvykle pohybujte šipkami na klávesnici „nahoru“ a „dolů“ a vyberte prvky – „vlevo“ nebo „vpravo“.
Ukazatel pohledu —> znamená, že se nacházíte v podnabídce, ke které se dostanete klávesou Enter. Cesta z toho je zjevně přes '[Exit]".
Zahrňte následující možnosti do „[Select]“ a ujistěte se, že mají vedle sebe „[*]“:
UML-specific Options:
- Host filesystem
Networking support (enable this to get the submenu to show up):
- Networking options:
- TCP/IP Networking
UML Network devices:
- Virtual network device
- SLiRP transport
To je vše, toto okno můžete opustit postupným výběrem '[Exit]'. Jen se ujistěte, že jste na konci vyzváni k uložení konfigurace a vyberte '[Yes]".
Doporučuji, abyste si po přečtení tohoto příspěvku pohráli s možnostmi sestavení jádra. Prostřednictvím těchto experimentů se můžete hodně naučit, pokud jde o pochopení práce nízkoúrovňové mechaniky jádra a vlivu různých příznaků na jeho sestavení.
Budování jádra
Linuxové jádro je velký program, který dělá spoustu věcí. I s tak minimální konfigurací na starém hardwaru může trvat poměrně dlouho sestavení. Sestavte jádro pomocí následujícího příkazu:
make ARCH=um -j$(nproc)
Proč? Tento příkaz řekne našemu staviteli, aby v procesu sestavení použil všechna dostupná jádra CPU a vlákna. tým $(nproc) na konci Build nahradí výstup příkazu nproc, která je součástí coreutils ve standardním sestavení Ubuntu.
Po nějaké době bude naše jádro zkompilováno do spustitelného souboru ./linux.
Instalace binárního souboru
Protože uživatelský režim v Linuxu vytváří běžný binární soubor, můžete jej nainstalovat jako jakýkoli jiný nástroj. Udělal jsem to takto:
mkdir -p ~/bin
cp linux ~/bin/linux
Také stojí za to se o tom přesvědčit ~/bin je ve vašem $PATH:
export PATH=$PATH:$HOME/bin
Nastavení systému souborů hosta
Vytvořte adresář pro hostovaný souborový systém:
mkdir -p $HOME/prefix/uml-demo
cd $HOME/prefix
Otevřete alpinelinux.org a in sekce ke stažení najít skutečný odkaz ke stažení MINI ROOT FILESYSTEM. V době psaní tohoto článku to bylo:
Nyní zadejte adresář souborového systému hosta a rozbalte archiv:
cd uml-demo
tar xf ../alpine-rootfs.tgz
Popsané akce vytvoří malou šablonu souborového systému. Vzhledem k povaze systému bude extrémně obtížné instalovat balíčky přes Alpine apk manager. Ale tento FS bude stačit k posouzení obecné myšlenky.
Potřebujeme také nástroj tini ke snížení spotřeby paměti zombie procesy naše hostující jádro.
wget -O tini https://github.com/krallin/tini/releases/download/v0.18.0/tini-static
chmod +x tini
Vytvoření příkazového řádku jádra
Linuxové jádro, stejně jako většina ostatních programů, má argumenty příkazového řádku, ke kterým lze přistupovat zadáním klíče --help.
Sám — pomoc
linux --help
User Mode Linux v5.1.16
available at http://user-mode-linux.sourceforge.net/
--showconfig
Prints the config file that this UML binary was generated from.
iomem=<name>,<file>
Configure <file> as an IO memory region named <name>.
mem=<Amount of desired ram>
This controls how much "physical" memory the kernel allocates
for the system. The size is specified as a number followed by
one of 'k', 'K', 'm', 'M', which have the obvious meanings.
This is not related to the amount of memory in the host. It can
be more, and the excess, if it's ever used, will just be swapped out.
Example: mem=64M
--help
Prints this message.
debug
this flag is not needed to run gdb on UML in skas mode
root=<file containing the root fs>
This is actually used by the generic kernel in exactly the same
way as in any other kernel. If you configure a number of block
devices and want to boot off something other than ubd0, you
would use something like:
root=/dev/ubd5
--version
Prints the version number of the kernel.
umid=<name>
This is used to assign a unique identity to this UML machine and
is used for naming the pid file and management console socket.
con[0-9]*=<channel description>
Attach a console or serial line to a host channel. See
http://user-mode-linux.sourceforge.net/old/input.html for a complete
description of this switch.
eth[0-9]+=<transport>,<options>
Configure a network device.
aio=2.4
This is used to force UML to use 2.4-style AIO even when 2.6 AIO is
available. 2.4 AIO is a single thread that handles one request at a
time, synchronously. 2.6 AIO is a thread which uses the 2.6 AIO
interface to handle an arbitrary number of pending requests. 2.6 AIO
is not available in tt mode, on 2.4 hosts, or when UML is built with
/usr/include/linux/aio_abi.h not available. Many distributions don't
include aio_abi.h, so you will need to copy it from a kernel tree to
your /usr/include/linux in order to build an AIO-capable UML
nosysemu
Turns off syscall emulation patch for ptrace (SYSEMU).
SYSEMU is a performance-patch introduced by Laurent Vivier. It changes
behaviour of ptrace() and helps reduce host context switch rates.
To make it work, you need a kernel patch for your host, too.
See http://perso.wanadoo.fr/laurent.vivier/UML/ for further
information.
uml_dir=<directory>
The location to place the pid and umid files.
quiet
Turns off information messages during boot.
hostfs=<root dir>,<flags>,...
This is used to set hostfs parameters. The root directory argument
is used to confine all hostfs mounts to within the specified directory
tree on the host. If this isn't specified, then a user inside UML can
mount anything on the host that's accessible to the user that's running
it.
The only flag currently supported is 'append', which specifies that all
files opened by hostfs will be opened in append mode.
Tento panel zvýrazňuje hlavní parametry spouštění. Spusťte jádro s minimální požadovanou sadou možností:
linux
root=/dev/root
rootfstype=hostfs
rootflags=$HOME/prefix/uml-demo
rw
mem=64M
init=/bin/sh
Výše uvedené řádky říkají našemu jádru následující:
Předpokládejme, že kořenový souborový systém je pseudo zařízení /dev/root.
Vybrat hostfs jako ovladač kořenového souborového systému.
Připojte hostovaný souborový systém, který jsme vytvořili, na kořenové zařízení.
A ano, v režimu čtení-zápis.
Použijte pouze 64 MB RAM (můžete použít mnohem méně v závislosti na tom, co plánujete dělat, ale 64 MB se zdá jako optimální množství).
Automaticky se spustí jádro /bin/sh как init-proces.
Spusťte tento příkaz a měli byste získat něco jako následující:
Ještě jeden list
Core dump limits :
soft - 0
hard - NONE
Checking that ptrace can change system call numbers...OK
Checking syscall emulation patch for ptrace...OK
Checking advanced syscall emulation patch for ptrace...OK
Checking environment variables for a tempdir...none found
Checking if /dev/shm is on tmpfs...OK
Checking PROT_EXEC mmap in /dev/shm...OK
Adding 32137216 bytes to physical memory to account for exec-shield gap
Linux version 5.1.16 (cadey@kahless) (gcc version 7.4.0 (Ubuntu 7.4.0-1ubuntu1~18.04.1)) #30 Sun Jul 7 18:57:19 UTC 2019
Built 1 zonelists, mobility grouping on. Total pages: 23898
Kernel command line: root=/dev/root rootflags=/home/cadey/dl/uml/alpine rootfstype=hostfs rw mem=64M init=/bin/sh
Dentry cache hash table entries: 16384 (order: 5, 131072 bytes)
Inode-cache hash table entries: 8192 (order: 4, 65536 bytes)
Memory: 59584K/96920K available (2692K kernel code, 708K rwdata, 588K rodata, 104K init, 244K bss, 37336K reserved, 0K cma-reserved)
SLUB: HWalign=64, Order=0-3, MinObjects=0, CPUs=1, Nodes=1
NR_IRQS: 15
clocksource: timer: mask: 0xffffffffffffffff max_cycles: 0x1cd42e205, max_idle_ns: 881590404426 ns
Calibrating delay loop... 7479.29 BogoMIPS (lpj=37396480)
pid_max: default: 32768 minimum: 301
Mount-cache hash table entries: 512 (order: 0, 4096 bytes)
Mountpoint-cache hash table entries: 512 (order: 0, 4096 bytes)
Checking that host ptys support output SIGIO...Yes
Checking that host ptys support SIGIO on close...No, enabling workaround
devtmpfs: initialized
random: get_random_bytes called from setup_net+0x48/0x1e0 with crng_init=0
Using 2.6 host AIO
clocksource: jiffies: mask: 0xffffffff max_cycles: 0xffffffff, max_idle_ns: 19112604462750000 ns
futex hash table entries: 256 (order: 0, 6144 bytes)
NET: Registered protocol family 16
clocksource: Switched to clocksource timer
NET: Registered protocol family 2
tcp_listen_portaddr_hash hash table entries: 256 (order: 0, 4096 bytes)
TCP established hash table entries: 1024 (order: 1, 8192 bytes)
TCP bind hash table entries: 1024 (order: 1, 8192 bytes)
TCP: Hash tables configured (established 1024 bind 1024)
UDP hash table entries: 256 (order: 1, 8192 bytes)
UDP-Lite hash table entries: 256 (order: 1, 8192 bytes)
NET: Registered protocol family 1
console [stderr0] disabled
mconsole (version 2) initialized on /home/cadey/.uml/tEwIjm/mconsole
Checking host MADV_REMOVE support...OK
workingset: timestamp_bits=62 max_order=14 bucket_order=0
Block layer SCSI generic (bsg) driver version 0.4 loaded (major 254)
io scheduler noop registered (default)
io scheduler bfq registered
loop: module loaded
NET: Registered protocol family 17
Initialized stdio console driver
Using a channel type which is configured out of UML
setup_one_line failed for device 1 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 2 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 3 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 4 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 5 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 6 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 7 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 8 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 9 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 10 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 11 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 12 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 13 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 14 : Configuration failed
Using a channel type which is configured out of UML
setup_one_line failed for device 15 : Configuration failed
Console initialized on /dev/tty0
console [tty0] enabled
console [mc-1] enabled
Failed to initialize ubd device 0 :Couldn't determine size of device's file
VFS: Mounted root (hostfs filesystem) on device 0:11.
devtmpfs: mounted
This architecture does not have kernel memory protection.
Run /bin/sh as init process
/bin/sh: can't access tty; job control turned off
random: fast init done
/ #
Výše uvedené manipulace nám dají hostující systém minimálně, bez věcí jako /proc nebo přiřazený název hostitele. Zkuste například následující příkazy:
- uname -av
- cat /proc/self/pid
- hostname
Chcete-li se odhlásit z hosta, zadejte exit nebo stiskněte control-d. To zabije shell a následuje panika jádra:
/ # exit
Kernel panic - not syncing: Attempted to kill init! exitcode=0x00000000
fish: “./linux root=/dev/root rootflag…” terminated by signal SIGABRT (Abort)
Tuto paniku jádra jsme dostali, protože jádro Linuxu si myslí, že proces inicializace vždy běží. Bez něj již systém nemůže fungovat a padá. Ale protože se jedná o proces v uživatelském režimu, výsledný výstup se sám odešle SIGABRT, což má za následek výstup.
Nastavení sítě pro hosty
A tady se to začíná kazit. Síť v uživatelském režimu Linux je místo, kde se celý koncept omezeného „uživatelského režimu“ začíná rozpadat. Koneckonců, obvykle na úrovni systému je síť omezená výsadní z pochopitelných důvodů pro nás všechny.
Poznámka. per .: si můžete přečíst více o různých možnostech práce se sítí v UML zde.
Cesta do Slirp
Existuje však prastarý a téměř nepodporovaný nástroj tzv Slirp, se kterým může Linux v uživatelském režimu komunikovat se sítí. Funguje podobně jako zásobník TCP/IP na uživatelské úrovni a ke spuštění nevyžaduje žádná systémová oprávnění. Tento nástroj byl vydáno v roce 1995a poslední aktualizace je datována 2006 let. Slirp je velmi starý. Za dobu bez podpory a aktualizací zašly kompilátory tak daleko, že nyní lze tento nástroj označit pouze jako kódová hniloba.
Pojďme si tedy stáhnout Slirp z repozitářů Ubuntu a zkusit jej spustit:
sudo apt-get install slirp
/usr/bin/slirp
Slirp v1.0.17 (BETA)
Copyright (c) 1995,1996 Danny Gasparovski and others.
All rights reserved.
This program is copyrighted, free software.
Please read the file COPYRIGHT that came with the Slirp
package for the terms and conditions of the copyright.
IP address of Slirp host: 127.0.0.1
IP address of your DNS(s): 1.1.1.1, 10.77.0.7
Your address is 10.0.2.15
(or anything else you want)
Type five zeroes (0) to exit.
[autodetect SLIP/CSLIP, MTU 1500, MRU 1500, 115200 baud]
SLiRP Ready ...
fish: “/usr/bin/slirp” terminated by signal SIGSEGV (Address boundary error)
Ach bohové. Pojďme nainstalovat Slirpův debugger a uvidíme, jestli dokážeme zjistit, co se zde děje:
sudo apt-get install gdb slirp-dbgsym
gdb /usr/bin/slirp
GNU gdb (Ubuntu 8.1-0ubuntu3) 8.1.0.20180409-git
Copyright (C) 2018 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law. Type "show copying"
and "show warranty" for details.
This GDB was configured as "x86_64-linux-gnu".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:
<http://www.gnu.org/software/gdb/documentation/>.
For help, type "help".
Type "apropos word" to search for commands related to "word"...
Reading symbols from /usr/bin/slirp...Reading symbols from /usr/lib/debug/.build-id/c6/2e75b69581a1ad85f72ac32c0d7af913d4861f.debug...done.
done.
(gdb) run
Starting program: /usr/bin/slirp
Slirp v1.0.17 (BETA)
Copyright (c) 1995,1996 Danny Gasparovski and others.
All rights reserved.
This program is copyrighted, free software.
Please read the file COPYRIGHT that came with the Slirp
package for the terms and conditions of the copyright.
IP address of Slirp host: 127.0.0.1
IP address of your DNS(s): 1.1.1.1, 10.77.0.7
Your address is 10.0.2.15
(or anything else you want)
Type five zeroes (0) to exit.
[autodetect SLIP/CSLIP, MTU 1500, MRU 1500, 115200 baud]
SLiRP Ready ...
Program received signal SIGSEGV, Segmentation fault.
ip_slowtimo () at ip_input.c:457
457 ip_input.c: No such file or directory.
Chyba v nás bije tento řádek. Podívejme se na stacktrace, třeba nám tam něco pomůže:
(gdb) bt full
#0 ip_slowtimo () at ip_input.c:457
fp = 0x55784a40
#1 0x000055555556a57c in main_loop () at ./main.c:980
so = <optimized out>
so_next = <optimized out>
timeout = {tv_sec = 0, tv_usec = 0}
ret = 0
nfds = 0
ttyp = <optimized out>
ttyp2 = <optimized out>
best_time = <optimized out>
tmp_time = <optimized out>
#2 0x000055555555b116 in main (argc=1, argv=0x7fffffffdc58) at ./main.c:95
No locals.
Zde vidíme, že k havárii dochází během startu hlavní smyčky, když se slirp pokouší zkontrolovat timeouty. V tuto chvíli jsem musel pokusy o ladění vzdát. Ale uvidíme, jestli Slirp postavený z sort funguje. Archiv jsem znovu stáhl přímo z webu SourceForge, protože přetáhnout něco odtud přes příkazový řádek je bolest:
cd ~/dl
wget https://xena.greedo.xeserv.us/files/slirp-1.0.16.tar.gz
tar xf slirp-1.0.16.tar.gz
cd slirp-1.0.16/src
./configure --prefix=$HOME/prefix/slirp
make
Zde vidíme upozornění na nedefinované vestavěné funkce, tedy na nemožnost propojit výsledný binární soubor. Zdá se, že mezi rokem 2006 a tímto bodem přestalo gcc produkovat symboly používané ve vestavěných funkcích přechodných kompilovaných souborů. Zkusme klíčové slovo nahradit inline na prázdný komentář a podívejte se na výsledek:
vi slirp.h
:6
a
<enter>
#define inline /**/
<escape>
:wq
make
Ani náhodou. Tohle taky nejde. Stále nemohu najít symboly pro tyto funkce.
V tuto chvíli jsem to vzdal a začal hledat na Github Sestavovací balíčky Heroku. Moje teorie byla, že nějaký balíček sestavení Heroku bude obsahovat binární soubory, které jsem potřeboval. Nakonec mě hledání vedlo právě tady. Stáhl jsem a rozbalil uml.tar.gz a našel následující:
total 6136
-rwxr-xr-x 1 cadey cadey 79744 Dec 10 2017 ifconfig*
-rwxr-xr-x 1 cadey cadey 373 Dec 13 2017 init*
-rwxr-xr-x 1 cadey cadey 149688 Dec 10 2017 insmod*
-rwxr-xr-x 1 cadey cadey 66600 Dec 10 2017 route*
-rwxr-xr-x 1 cadey cadey 181056 Jun 26 2015 slirp*
-rwxr-xr-x 1 cadey cadey 5786592 Dec 15 2017 uml*
-rwxr-xr-x 1 cadey cadey 211 Dec 13 2017 uml_run*
Toto je binární slirp! Pracuje?
./slirp
Slirp v1.0.17 (BETA) FULL_BOLT
Copyright (c) 1995,1996 Danny Gasparovski and others.
All rights reserved.
This program is copyrighted, free software.
Please read the file COPYRIGHT that came with the Slirp
package for the terms and conditions of the copyright.
IP address of Slirp host: 127.0.0.1
IP address of your DNS(s): 1.1.1.1, 10.77.0.7
Your address is 10.0.2.15
(or anything else you want)
Type five zeroes (0) to exit.
[autodetect SLIP/CSLIP, MTU 1500, MRU 1500]
SLiRP Ready ...
Nehavaruje - takže by to mělo fungovat! Zasadíme tuto dvojhvězdu ~/bin/slirp:
cp slirp ~/bin/slirp
V případě, že jej tvůrce balíčku odstraní, I udělal zrcadlo.
První dva konfigurační příkazy /proc и /sys nutné pro práci ifconfig, který nastavuje síťové rozhraní pro komunikaci se Slirpem. tým route nastaví směrovací tabulku jádra tak, aby vynutila odesílání veškerého provozu tunelem Slirp. Zkontrolujeme to pomocí DNS dotazu:
Poznámka k .: Původní příspěvek byl zjevně napsán na ploše s kabelovou síťovou kartou nebo jinou konfigurací, která nevyžadovala další ovladače. Na notebooku s WiFi 8265 od Intelu dochází k chybě při zvedání sítě
/ # ifconfig eth0 10.0.2.14 netmask 255.255.255.240 broadcast 10.0.2.15
slirp_tramp failed - errno = 2
ifconfig: ioctl 0x8914 failed: No such file or directory
/ #
Zjevně jádro nemůže komunikovat s ovladačem síťové karty. Pokus o kompilaci firmwaru do jádra bohužel situaci nevyřešil. V době publikace nebylo možné najít řešení v této konfiguraci. Na jednodušších konfiguracích (například ve Virtualboxu) se rozhraní zvedne správně.
Pojďme automatizovat přesměrování pomocí následujícího shell skriptu:
linux
root=/dev/root
rootfstype=hostfs
rootflags=$HOME/prefix/uml-demo
rw
mem=64M
eth0=slirp,,$HOME/bin/slirp
init=/init.sh
A zopakujme si:
SLiRP Ready ...
networking set up
/bin/sh: can't access tty; job control turned off
nslookup google.com 8.8.8.8
Server: 8.8.8.8
Address 1: 8.8.8.8 dns.google
Name: google.com
Address 1: 172.217.12.206 lga25s63-in-f14.1e100.net
Address 2: 2607:f8b0:4004:800::200e iad30s09-in-x0e.1e100.net
Síť je stabilní!
docker soubor
Abych vám to všechno usnadnil, shromáždil jsem dockerfile, který automatizuje většinu popsaných kroků a měl by vám poskytnout funkční konfiguraci. také mám předkonfigurované jádro, která má vše, co je popsáno v příspěvku. Je ale důležité pochopit, že jsem zde nastínil pouze minimální nastavení.
Doufám, že vám tento příspěvek pomohl pochopit, jak vychovat hostující jádro. Ukázalo se, že je to nějaké monstrum, ale publikace byla koncipována jako komplexní průvodce vytvářením, instalací a konfigurací uživatelského režimu v Linuxu pod moderními verzemi operačních systémů této rodiny. Další kroky by měly zahrnovat instalaci služeb a dalšího softwaru již uvnitř hostujícího systému. Vzhledem k tomu, že obrázky kontejnerů Docker jsou pouze zveřejněné tarbally, měli byste být schopni extrahovat obrázek pomocí docker exporta poté určete jeho instalační cestu v kořenovém adresáři souborového systému hostujícího jádra. No, pak spusťte skript shellu.
Zvláštní poděkování patří Rkeene z #lobsters na Freenode. Bez jeho pomoci při ladění Slirp bych se tak daleko nedostal. Nemám ponětí, jak jeho systém Slackware správně funguje se slirpem, ale moje systémy Ubuntu a Alpine neakceptovaly slirp a navrhla mi binární Rkeene. Ale stačí mi, že mi aspoň něco funguje.