NBD

From DCEwiki
Jump to navigation Jump to search

Network Block Device je specificky linuxová technologie síťového sdílení blokových zařízení, postavená na konceptu klient/server, kterou začal programovat Pavel Machek v dubnu 1997.

Aplikace

Původní implementace NBD byla velmi jednoduchá a měla svá omezení. Proto vzniklo postupem času několik forků, které se snažily její možnosti dále rozšířit a vylepšit. Její vývoj však stále probíhá a tak vývoj těchto forků časem byl ukončen, neboť vlastnosti kterými se odlišovaly byly postupně implementovány.

Kupř. vývoj ENBD (Enhanced Network Block Device), které vylepšovalo přístup ke vzdálenému blokovému zařízení probíhal od prosince 2001 do listopadu 2002 a skončil přechodem na kernel řady 2.6.

Dalším forkem, který zůstal pro svou úzkou specializaci omezen prakticky pouze na jednu distribuci bylo GNBD ( GFS Network Block Device) od Red Hatu. Šlo v podstatě o NBD optimalizované pro použití s clusterovým souborovým systémem GFS2 a podporou připojení několika klientských aplikací k jednomu serveru najednou. (Původní NBD aplikace umožňovala připojit k jedné instanci serveru pouze jednoho klienta).

Jen pro úplnost bych zmínil ještě DNBD (Distributed Network Block Device) což zase byla read-only implementace NBD pro použití u bezdiskových klientských stanic, jejíž vývoj probíhal od dubna 2008 do června 2009.

Prozatím poslední samostatnou implementací NBD je xNBD, které rozšiřuje původní koncept o možnost provádět na straně serveru živou migraci blokových zařízení zároveň s migrací běžících virtuálních strojů mezi fyzickými stroji skrze WAN. To je prozatím nejvýznamnější vlastnost, která ještě není do původní vývojové větve NBD aplikací nějakým způsobem implementována.


Jak NBD funguje?

Server
který na vzdáleném stroji vyčkává a nabízí na vybraném rozhraní a portu blokové zařízení (nebo soubor), nevyžaduje žádný speciální ovladač, může v podstatě běžet na libovolné platformě podporující síťování přes TCP/IP protokol.
Klient
Klientská aplikace, která zajišťuje připojení vzdáleného stroje k lokálnímu blokovému zařízení je úzce svázaná s linuxovým jádrem a vyžaduje zavedený modul nbd.

Jak už bylo zmíněno, NBD je typická aplikace klient/server, přičemž NBD server, který propaguje do sítě buď lokální blokové zařízení, nebo obraz disku či CD & etc., je většinou realizován jako userspace aplikace, kdežto klient provede na úrovni userspace pouze připojení vzdáleného serveru k lokálnímu blokovému NBD zařízení. Ostatní komunikace již probíhá na úrovni jádra.

Opravdu vyčerpávající popis fungování NBD naleznete na webu v článku http://www.linuxjournal.com/article/3778

Server

jak už bylo zmíněno v úvodu, na rozdíl od klienta, není server závislý na platformě a tak existuje jak variace původního NBD serveru pro MS Windows XP, tak "platformně nezávislý" (alébrž Java) NBD server v Javě, které vytvořil vývojář Folkert van Heusden.

Z pohledu uživatele linuxu je důležitá informace, že z hlediska vlastní NBD komunikace

  • nezáleží na tom jaký klient spojení realizoval
  • a nezáleží na tom, co za server je na druhé straně

Pochopitelně každý NBD server má svá specifika, kupř. xNDB implementace serveru kromě toho, že funguje jako klasický NBD server, může běžet zároveň jako server v režimu proxy. QEMU NBD server zase umožňuje zpropagovat jako raw zařízení image virtualizačních nástrojů (qcow2, vmdk, vdi,...). Atd.

Klient

U NBD na použité klientské aplikaci v zásadě nezáleží, protože klient pouze zprostředkuje připojení, ovšem další komunikace již probíhá na úrovni jádra. Nicméně klientská aplikace může mít implementovány další funkce, které navyšují její užitnou hodnotu. O těchto možnostech viz níže.

Lokální bloková NBD zařízení ( /dev/nbd0, /dev/nbd1,... ), ke kterým klient připojí image (nebo zařízení) vypublikované na straně serveru, vytváří linuxové jádro až po načtení modulu nbd. Prostřednictvím konfigurace tohoto modulu lze ovlivnit počet vytvořených NBD zařízení a také to, zda-li se budou automaticky tvořit bloková zařízení pro případné diskové oddíly, nebo ne.

Upozornění Je-li nbd modul zakompilován přímo do jádra, tak si nejsem jist. zda-li lze jeho výchozí hodnoty dodatečně měnit.

Počet NBD zařízení

Maximální možný počet NBD zařízení, který lze vytvořit byl dříve omezen na 256, ovšem to dnes již neplatí. Není-li však v konfiguraci modulu uvedeno jinak, je použita výchozí hodnota - tedy 16. Změnit tuto výchozí hodnotu lze (u Debianu) změnit prostřednictvím hodnoty nbds_max umístěné do některého souboru s příponou .conf, v adresáři /etc/modprobe.d

Poznámka U Debianu je takový konfigurační soubor součástí instalačního balíku nbd-client - /etc/modprobe.d/nbd-client.conf

Stačí tedy příslušné hodnoty upravit, případně doplnit v něm.

Počet diskových oddílů

Vypublikovat lze jak jednotlivý diskový oddíl, tak celé blokové zařízení. Obsahuje-li toto blokové zařízení nějaké diskové oddíly, záleží na tom, jaká byla modulu nbd předána hodnota max_part. Ve výchozí konfiguraci jádra je nulová, ale součástí instalačního balíčku nbd klienta u Debianu je výchozí konfigurační soubor, ve kterém je nastavena výchozí hodnota 8, což znamená, že v případě kdy je připojeno přes NBD vzdálené blokové zařízení, které má méně jak 8 diskových oddílů, jsou jádrem automaticky vytvořena příslušná bloková zařízení, která lze namountovat.


Poznámka V případě že je počet diskových oddílů na NBD zařízení vyšší, nebo je hodnota max_part nulová (výchozí stav), můžete použít pro mountování diskového oddílu parametr offset. Chcete-li však mít možnost mountovat jednotlivé diskové oddíly nezávisle, musíte hodnotu max_part odpovídajícím způsobem navýšit.

Ukázka konfigurace nbd modulu

Poznámka
root@stroj~# ls /dev/nbd*
ls: nelze přistoupit k /dev/nbd*: Adresář nebo soubor neexistuje
root@stroj~# cat /etc/modprobe.d/nbd-client.conf
options nbd nbds_max=7 max_part=15
root@stroj~# modprobe nbd
root@stroj~# ls /dev/nbd*
/dev/nbd0  /dev/nbd1  /dev/nbd2  /dev/nbd3  /dev/nbd4  /dev/nbd5  /dev/nbd6

Jak přidat NBD zařízení za běhu

Na základě tohoto konfiguračního souboru se ale příslušná zařízení vytvoří pouze v okamžiku zavedení modulu. Pokud už je modul zavedený a my potřebujeme další nbd zařízení, musí být vytvořeno manuálně.

Nejprve zjistíme kolik zařízení vlastně máme aktuálne k dispozici, a jaká je aktuálně nejvyšší hodnota minor čísla

Poznámka
root@stroj~# ls -l /dev/nbd*
...
brw-rw---T 1 root disk 43, 15 Nov 23 14:20 /dev/nbd15

Číslo 43 je tzv. major číslo, které specifikuje typ zařízení. Číslo minor má hodnotu 15, tzn. že v systému existuje v tuto chvíli 16 zařízení typu nbd a je tedy třeba přidat další zařízení s číslem 16, která musí mít nastavena práva stejně jako ostatní zařízení stejného typu.

Pro vytvoření nového blokového zařízení použijeme příkaz mknod (parametr b říká že jde o blokové zařízení) a pro nastavení práv utility chown a chmod

Poznámka
root@stroj~# mknod -m660 /dev/nbd9 b 43 16
root@stroj~# chown root.disk /dev/nbd9
root@stroj~# chmod 666 /dev/nbd9
Poznámka Stejný postup platí i pro zařízení typu loop, jejichž počet je ve výchozím stavu omezený na 8. S tím rozdílem - že hledáme a tvoříme zařízení /dev/loop, které nemá hodnotu major 43 ale 7

Implementace

GNU NBD

GNU NBD se poslední dobou vyvíjí takovým směrem, jako by bylo záměrem jeho vývojářů integrovat server i klienta do jedné aplikace.

  • Podoruje autorizaci (qemu-nbd ani xNBD autorizaci nepodporují)
  • Umožňuje nabídnout jako jedno zařízení soubor rozdělený do více kusů (multiple file)
  • Umožňuje omezit počet připojených klientů
  • Umožňuje omezit server na jedno síťové rozhraní
  • Podporuje vytvoření PID souboru

NBD klient

QEMU NBD

  • Umožňuje pracovat přímo se soubory formátu QCOW2
  • Při lokálním použití umí fungovat současně i jako klient. Tj. že umí připojit soubor přímo na NBD zařízení
  • Umožňuje nabídnout jako jedno zařízení soubor rozdělený do více kusů (multiple file)
  • Stejně jako NBD server umožňuje omezit počet připojených klientů
  • Umožňuje omezit server na jedno síťové rozhraní (IPv4)

Velkou výhodou QEMU NBD serveru je, že umožňuje relativně jednoduše kopírovat data z virtuálních disků, ovšem z hlediska stability patří k těm nejméně spolehlivým.

Existuje QEMU NBD klient?

Ano. QEMU má jednoduchého klienta implementovaného přímo v QEMU, takže lze virtuální disk předat do virtuálu rovnou prostřednictvím připojení na NBD server.

  • Výhodou je, že tím odpadá nutnost použití externího klienta.
  • Bohužel v případě, kdy se spojení přeruší neumí QEMU provést reconnect.
root@stroj:~# modprobe nbd max_part=16
root@stroj:~# qemu-nbd -c /dev/nbd0 /mnt/disk.vmdk
root@stroj:~# partprobe /dev/nbd0
Poznámka Příkaz partprobe zajistí vytvoření příslušných zařízení pro jednotlivé diskové oddíly, pokud na připojeném disku existují

xNBD

xNBD je celý soubor utilit, které se snaží zaplnit mezery, které dosud má GNU NBD. Z hlediska stability patří xNBD server k držákům (což o GNU NBD serveru s čistým svědomím napsat nemohu). Během půlročního provozu jsem nezaznamenal jediný pád spojení mezi NBD serverem a lokálním zařízením, který by byl zaviněný chybou v této aplikaci.

Spouštění a obsluha xNBD serveru prostřednictvím utility xnbd-wrapper

xnbd-wrapper je utilita, která umožňuje..

  • spouštět..
  • vylistovávat..
  • a zastavovat..

.. jednotlivé instance xNBD serverů, aniž by bylo nutné provést provádět nové načtení konfiguračního souboru /etc/xnbd.conf prostřednictvím init skriptu /etc/init.d/xnbd-common

Poznámka

Používáte-li Debian, tak poměrně záhy zjistíte, že spouštění xNBD serverů na základě konfigurace v /etc/xnbd.conf nezajišťuje žádná z nativních utilit xNBD, ale obslužný skript, napsaný maintainerem tohoto balíku v Debianu - Arno Töllem. Tento skript - xnbd-register, který spouští jednotlivé instance serverů přes xnbd-wrapper-ctl je sám napsaný v pythonu a pracuje s ním rovněž init skript /etc/init.d/xnbd-common. Bohužel je velmi jednoduchý a nelze přes něj řešit více než jednu spouštěnou instanci xnbd-wrapperu.

Upozornění xNBD server, není-li spouštěn v režimu proxy, by měl být vždy spouštěn prostřednictvím utility xnbd-wrapper, kterou používá pro spuštění také init skript.

Jedním z důvodů je mimo jiné to, že instance xnbd-server, která je spuštěná přímo, naslouchá sice na zvoleném portu, ale na všech síťových rozhraních, kdežto xnbd-wrapper umožňuje určit nejenom na jakém portu, ale i na jakém rozhraní má server naslouchat.


V následujícím příkladu je spuštěn xnbd-wrapper bez jakéhokoliv publikovaného blokového zařízení, či obrazu disku, ovšem tak, aby naslouchal pouze na rozhraní s ip adresou 10.0.0.11

Poznámka
root@stroj~#  xnbd-wrapper --port 6000 --laddr 10.0.0.45 --socket /tmp/xnbd_wrapper.ctl
** Message: port: 6000
** Message: xnbd-binary: /usr/sbin/xnbd-server
no item
Poznámka Protože v systému již může naslouchat na standardním portu pro NBD (8520) wrapper, který byl spuštěn prostřednictvím init skriptu, co používá výchozí soket /tmp/xnbd.ctl, je při spouštění nastaven náhradní port a jiný soket.

Protože nebyl použit parametr --daemonize, ani --log, jsou záznamy o případné komunikaci vypisovány na standarní výstup, tedy přímo na konzoli. no item signalizuje, že wrapper zatím nemá přiřazen žádné zařízení, které by mohl publikovat.

Zastavení xNBD serveru prostřednictvím utility xnbd-wrapper-ctl

Za normálního stavu je spuštěn xnbd-wrapper s parametrem --daemonize. Zastavit jej lze prostřednictvím nastaveného soketu pomocí utility xnbd-wrapper-ctl

Poznámka
root@stroj~# xnbd-wrapper-ctl --socket /tmp/xnbd_wrapper.ctl --shutdown
All images terminated
root@stroj~#

Přidání zařízení k publikaci

Je-li xnbd-wrapper spuštěn, naslouchá na příslušném portu a vlastní instanci pro xNBD server spouští až v okamžiku, kdy mu přijde požadavek na připojení odpovídajícího vypublikovaného zařízení - to klient určí buďto jeho pořadovým číslem, nebo plnou cestou k publikovanému zařízení či souboru.

Aby to však bylo možné, je nutné nejprve prostřednictvím xnbd-wrapper-ctl odpovídající zařízení či soubor přidat.

Poznámka
root@stroj~# xnbd-wrapper-ctl --socket /tmp/xnbd_wrapper.ctl --add /cesta_k_souboru/disk_1.img

Vylistování publikovaných zařízení

Poznámka
root@stroj~# xnbd-wrapper-ctl --socket /tmp/xnbd_wrapper.ctl --list
1 : /cesta_k_souboru/disk_1.img
2 : /cesta_k_souboru/disk_1.img
3 : /cesta_k_souboru/disk_3.img

Odebrání zařízení

  • Zařízení lze odebrat pouze na základě jeho indexového čísla.
  • U ostatních zařízení se indexové číslo po odebrání nezmění
  • Je-li přidáno další zařízení, použije se první volné indexové číslo
Poznámka
root@stroj~# xnbd-wrapper-ctl --socket /tmp/xnbd_wrapper.ctl --remove 2
root@stroj~# xnbd-wrapper-ctl --socket /tmp/xnbd_wrapper.ctl --list
1 : /cesta_k_souboru/disk_1.img
3 : /cesta_k_souboru/disk_3.img
Upozornění Je-li odebrané zařízení připojeno, tak zůstane instance xNBD serveru spuštěná, dokud nedojde k ukončení spojení na straně klienta!

Má-li být instance ukončena ihned ze strany serveru, pak musí být ukončena odesláním příslušného signálu SIGQUIT (případně SIGTERM či SIGQUIT) pomocí kill procesu, který udržuje spojení. Tj. tomu, jehož rodičem je spuštěná příslušná instance aplikace xnbd-server, nikoliv utility xnbd-wrapper!

Spuštění xNBD serveru tak aby naslouchal na všech síťových rozhraních

Je-li žádoucí, aby xnbd-wrapper naslouchal na všech síťových rozhraních, stačí vypustit parametr --laddr

Spuštění xNBD serveru pro několik zařízení současně

Jak bylo ukázáno výše, bloková zařízení lze přidávat a odebírat za běhu. Nicméně, zařízení, která se mají vypublikovat na síť ihned po spuštění, lze předat při spouštění utility xnbd-wrapper rovnou. Viz příklad.

Poznámka
root@stroj~# xnbd-wrapper --daemonize --port 6000 --laddr 10.0.0.45 --imgfile /cesta_k_souboru/disk_1.img --imgfile /cesta_k_souboru/disk_2.img --socket /tmp/xnbd_wrapper.ctl
** Message: port: 6000
** Message: xnbd-binary: /usr/sbin/xnbd-server
** Message: logfile /tmp/xnbd.log
root@stroj~#

xnbd-server

xNBD server nemusí být nezbytně spouštěn prostřednictvím utility xnbd-wrapper, ale může být spuštěn také samostatně. V takové případě:

  • musí mít nastaveno nekonfliktní číslo portu na kterém bude naslouchat
  • bude očekávat připojení na všech dostupných síťových rozhraních
  • bude muset být ukončen odesláním signálu SIGQUIT pomocí kill

Na druhou stranu však lze v takovém případě využít možností režimů TARGET, COW TARGET či PROXY.

xNBD server v režimu TARGET

  • xNBD server, spuštěný v režimu TARGET funguje jako každá jiná instance NBD serveru, ovšem s tím rozdílem, že naslouchá na všech síťových rozhraních a vyžaduje samostatný port.
  • Do režimu TARGET se může xNBD server dostat také přepnutím z režimu PROXY.

xNBD server v režimu COW TARGET

xNBD server, spuštěný v režimu COW TARGET funguje tak, jako by bylo publikované zařízení chráněno proti zápisu. tzn. že veškeré změny se ukládají do dočasného souboru, který se po ukončení spojení zahodí.

Zastavení instance xNBD serveru spuštěné v režimu TARGET

Je-li xNBD server spuštěn v režimu target s parametrem --daemonize, neumožňuje vytvořit ovládací soket. V takovém případě, není-li vytvořen ovládací soket, lze korektně ukončit jeho běh odesláním signálu SIGQUIT na příslušný proces pomocí příkazu kill


  • Umožňuje vypisovat monitorovací výstup buď na standarní konzoli, nebo do logovacího souboru (zatím co NBD server běží vždy jako démon a monitorovací výstup umožňuje nastavit až poslední verze)
  • Parametrem lze při startu určit, v jakém má běžet v režimu target|cow-target|proxy a pomocí utility xnbd-bgctl lze pak monitorovat a do určité míry i řídit jak se má nakládat s datovými bloky
  • Pomocí utility xnbd-wrapper lze spustit jednu instanci serveru pro několik blokových zařízení najednou a specifikovat přitom rovněž síťový interface na kterém má server naslouchat. Výhodou by mělo být, že by veškerá komunikace probíhala přes jeden port. Bohužel v době psaní tohoto článku se mě připojení klienta k blokovému zařízení přes wrapper nepodařilo rozběhat.
Poznámka Co kam je vlastně připojeno lze zjistit u XNBD pomocí příkazu lsof
user@stroj~: pidof xnbd-{client|server}
<číslo procesu> ...

Aktuální status procesu..

user@stroj~: sed '1 p ; d' /proc/<číslo procesu>/status
Main: proxy_wrk
user@stroj~: lsof -p <číslo procesu> [-ac {xnbd-client|proxy_wrk|target_wrk|proxy_main|xnbd-server}] -ai 4 -n -F | grep ^n
n*:24
n10.0.0.39:24->10.0.0.43:34743
proxy_wrk
Proces na straně proxy
target_wrk
Proces na straně target serveru, který zajišťuje připojení klienta..
proxy_main
Proces kterým je proxy připojena na target. Ve výpisu se zobrazí i připojení, které odpovídá target_wrk na straně target serveru.
xnbd-server
Hlavní serverový proces. Ve výpisu připojení se v případě že jde o proxy server nezobrazí připojení na target server
xnbd-client
Proces xnbd klienta. Ve výpisu se zobrazí připojení, které odpovídá target_wrk na straně target serveru, ev. proxy_wrk na straně proxy.



, který výrazně snižuje objem přenášených dat mezi výchozí instancí serveru a instancí spuštěnou v lokální síti.

Přenášejí se totiž vždy pouze data, která jsou aktuálně zapotřebí, a to směrem k proxy. Data pozměněná či přidaná se neposílají zpět, tak jako u klasického NBD serveru, ale ukládají do lokální image se kterou pracuje proxy. Dotažení zbylých dat, lze aktivovat příkazem teprve v případě potřeby a za běhu pak proxy přepnout do režimu target, aniž by došlo k odpojení připojených klientů-

Toho lze využít především při migraci virtuálních disků během živé migrace virtuálu, a tím eliminovat čas, který by jinak kompletní překopírování skrze WAN zabralo.

Velkou výhodou je, že xNBD server je zcela transparentní a vůči jiné instanci NBD serveru se chová jako normální klient. Lze tudíž jeho výhod využít zároveň s klasickou implementací NBD serveru, která umožňuje (na rozdíl od xNBD) přístup klientských aplikací omezit ať již pomocí aktorizace, nebo na úrovni síťového rozhraní.

Poznámka xNBD server sám o sobě neumožňuje specifikovat na jakém síťovém interface má naslouchat, a proto je součástí instalace xnbd-wrapper který to řeší za něj. Ten by měl umožnit zároveň skrze jednu instanci serveru publikovat více blokových zařízení najednou. Bohužel v době psaní tohoto článku tento wrapper nefunguje příliš uspokojivým způsobem.

xNBD server v režimu PROXY

Využití xNBD v režimu proxy při live snapshotu KVM virtuálu

Spuštění xnbd-server v režimu PROXY a přesun datových bloků do snapshotu blokového zařízení Paralelně s probíhajícím přesunem datových bloků lze spustit i provedení live snapshotu technikou "fake" migrace do souboru

Využití xNBD v režimu proxy při live migraci KVM virtuálu

Spuštění xnbd-serveru v režimu PROXY

spustit..

Spuštění virtuálního stroje s parametrem --incoming

spustit..
spustit..
První fáze - spuštění xnbd-server v režimu PROXY a virtuálního stroje s parametrem --incoming
Druhá fáze - spuštění migrace virtuálního stroje
Třetí fáze - dokončení migrace virtuálního stroje (zastavení jeho původní instance)
Čtvrtá fáze - přesun chybějících datových bloků
Pátá fáze - přepnutí xnbd-serveru z režimu PROXY do režimu TARGET a zastavení jeho původní instance

xNBD klient

Syntaxe xNBD klienta se od "obyčejného" NBD poněkud liší. Podporuje sice i syntaxi původního klienta, ale jeho vlastní syntaxe umožňuje předat k připojení několik vzdálených strojů současně. Klient se pokusí připojit první z nich, ale pokud je z nějakého důvodu nedostupný a připojení se do určité doby nepodaří, vyzkouší automaticky další stroj v pořadí.

Původní klient umožňuje předat pouze jedno připojení.

xNBD klient od verze 0.1.0-pre umožňuje také použít pro připojení local-linkovou IPv6 adresu (kterou lze zjistit dotazem přes multicast na příslušném rozhraní)

Parametry

--blocksize (výchozí 1024) min. 512 max. 4096

--timeout
Časový interval po kterém má klient zabalit pokusy o připojení a přejít k dalšímu stroji v seznamu.
--retry
umožňuje nastavit kolikrát se má klient o připojení pokusit, než přejde k dalšímu kontaktu
--recovery-command
umožňuje předat k vykonání nějaký příkaz v případě že došlo k neočekávanému ukončení spojení
--recovery-command-reboot
je drsnější variantou předchozího parametru, která v případě selhání spojení klientský stroj zrestartuje.

(Při testu ovšem došlo ke zpanikaření)

--exportname
V případě že

WatchDog

Utilitu xnbd-watchdog lze použít ke hlídání stavu nbd zařízení pokud nebyl pro jeho připojení použit xnbd-client s nastaveným parametrem --recovery-command, ale jiný klient, který neumožňuje zavolat skript, který by ošetřil výpadek připojení - např. nbd-client.