(2020) Pokud používáte linuxové jádro 5.1 nebo vyšší, můžete použít io_uring
rozhraní pro souborové I/O a získat vynikající asynchronní provoz.
V porovnání se stávajícím libaio
/KAIO rozhraní, io_uring
má následující výhody:
- Zachovává asynchronní chování při provádění I/O s vyrovnávací pamětí (a nejen při provádění přímých I/O)
- Snazší použití (zejména při použití
liburing
pomocná knihovna) - Volitelně může pracovat formou dotazování (ale k aktivaci tohoto režimu budete potřebovat vyšší oprávnění)
- Menší režie účetního prostoru na I/O
- Nižší režie CPU díky menšímu počtu přepínání režimů systémového volání v uživatelském prostoru/jádru (v dnešní době je to velký problém kvůli dopadu zmírňování přízraků/rozpadu)
- Deskriptory souborů a vyrovnávací paměti lze předem zaregistrovat, aby se ušetřil čas mapování/rušení mapování
- Rychlejší (může dosáhnout vyšší celkové propustnosti, vstupy/výstupy mají nižší latenci)
- "Propojený režim" může vyjadřovat závislosti mezi I/O (>=5.3 jádro)
- Umí pracovat s I/O na bázi soketu (
recvmsg()
/sendmsg()
jsou podporovány od>=5.3, viz zprávy zmiňující slovo support v historii git io_uring.c) - Podporuje pokus o zrušení I/O ve frontě (>=5,5)
- Může požádat o vstup/výstup vždy být proveden z asynchronního kontextu spíše než ve výchozím nastavení, kdy se pouze vrátí zpět k přepínání I/O do asynchronního kontextu, když vložená cesta odeslání spustí blokování (>=5.6 jádro)
- Růst podpory pro provádění asynchronních operací nad
read
/write
(např.fsync
(>=5,1),fallocate
(>=5,6),splice
(>=5,7) a více) - Větší dynamika rozvoje
- Nebude blokovat pokaždé, když hvězdy nejsou dokonale zarovnány
V porovnání s POSIX AIO od glibc, io_uring
má následující výhody:
- Hodně rychlejší a efektivnější (nižší režijní výhody uvedené výše zde platí ještě více)
- Rozhraní je podporováno jádrem a NEPOUŽÍVÁ fond vláken uživatelského prostoru
- Při provádění I/O s vyrovnávací pamětí se vytváří méně kopií dat.
- Žádný zápas se signály
- Glibc POSIX AIO nemůže mít více než jeden I/O v provozu na jednom deskriptoru souboru, zatímco
io_uring
určitě může!
Dokument Efficient IO with io_uring jde mnohem podrobněji do io_uring
výhody a použití. Dokument Co je nového v io_uring popisuje nové funkce přidané do io_uring
mezi jádry 5.2 - 5.5, zatímco článek Rychlý růst io_uringLWN popisuje, které funkce byly k dispozici v každém z jader 5.1 - 5.5, s pohledem dopředu na to, co bude v 5.6 (viz také seznam článků io_uring LWN). K dispozici je také videoprezentace Faster IO through io_uring Kernel Recipes (snímky) z konce roku 2019 a video prezentace (slides) Co je nového s io_uring Kernel Recipes z poloviny roku 2022 od io_uring
autor Jens Axboe. A konečně, tutoriál Lord of the io_uring poskytuje úvod do io_uring
použití.
io_uring
komunitu lze kontaktovat prostřednictvím mailing listu io_uring a archivy mailing listu io_uring ukazují denní provoz na začátku roku 2021.
Re "podpora částečných I/O ve smyslu recv()
vs read()
":do jádra 5.3 byla vložena oprava, která se automaticky pokusí io_uring
krátká čtení a další potvrzení šly do jádra 5.4, které ladí chování tak, aby se automaticky staralo pouze o krátká čtení při práci s "běžnými" soubory na požadavcích, které nemají nastaveno REQ_F_NOWAIT
flag (vypadá to, že si můžete vyžádat REQ_F_NOWAIT
přes IOCB_NOWAIT
nebo otevřením souboru pomocí O_NONBLOCK
). Tak můžete získat recv()
style- "krátké" I/O chování z io_uring
taky.
Software/projekty využívající io_uring
Přestože je rozhraní mladé (jeho první inkarnace dorazila v květnu 2019), některý open-source software používá io_uring
"ve volné přírodě":
- fio (jehož autorem je také Jens Axboe) má backend io_uring ioengine (ve skutečnosti byl představen již ve fio-3.13 z února 2019!). Prezentace „Vylepšený výkon úložiště pomocí nového I/O rozhraní linuxového jádra I/O Interface SNIA“ (slides) od dvou inženýrů společnosti Intel uvádí, že byli schopni získat dvojnásobný IOPS při jedné pracovní zátěži a méně než poloviční průměrnou latenci při hloubce fronty 1 na další zátěž při porovnání
io_uring
ioengine nalibaio
ioengine na zařízení Optane. - Projekt SPDK přidal podporu pro použití io_uring (!) pro blokový přístup k zařízení ve své verzi 19.04 (ale samozřejmě to není backend, který byste obvykle používali SPDK pro jiné účely než pro benchmarking). V poslední době se také zdá, že přidali podporu pro použití se sockety ve verzi 20.04...
- Ceph provedl backend io_uring v prosinci 2019, který byl součástí jeho vydání 15.1.0. Autor odevzdání zveřejnil komentář na githubu, který ukazuje, že některý backend io_uring má určité výhry a ztráty oproti backendu libaio (z hlediska IOPS, šířky pásma a latence) v závislosti na pracovní zátěži.
- RocksDB potvrdil
io_uring
backend pro MultiRead v prosinci 2019 a byl součástí jeho vydání 6.7.3. Jens uvádíio_uring
pomohly dramaticky snížit latenci. - libev vydala 4.31 s počátečním
io_uring
backend v prosinci 2019. Zatímco některé z původních bodů autora byly řešeny v novějších jádrech, v době psaní tohoto článku (polovina roku 2021) má autor libev několik vybraných slov oio_uring
's vyspělost a před implementací dalších vylepšení zaujímá vyčkávací přístup. - QEMU provedla io_uring backend v lednu 2020 a byla součástí vydání QEMU 5.0. V PDF prezentaci "io_uring in QEMU:high-performance disk IO for Linux" Julia Suvorova ukazuje
io_uring
backend překonávajícíthreads
aaio
backendy na jednom pracovním zatížení náhodných 16K bloků. - Samba sloučila
io_uring
Backend VFS v únoru 2020 a byl součástí vydání Samba 4.12. V "Linux io_uring VFS backend." Vlákno konference Samba, Stefan Metzmacher (autor odevzdání) říkáio_uring
modul byl schopen prosadit zhruba o 19 % vyšší propustnost (ve srovnání s některým nespecifikovaným backendem) v syntetickém testu. Můžete si také přečíst PDF prezentaci „Async VFS Future“ od Stefana, kde najdete některé motivace za změnami. - Používá jej experimentální C++ libunifex na Facebooku (budete ale také potřebovat jádro 5.6+)
- Rezaví lidé psali obaly, aby vytvořili
io_uring
přístupnější čisté rzi. rio je jedna knihovna, o které se trochu mluví, a autor říká, že dosáhla vyšší propustnosti ve srovnání s použitím synchronizačních volání zabalených do vláken. Autor přednesl prezentaci o své databázi a knihovně na FOSDEM 2020, která zahrnovala sekci vychvalující přednostiio_uring
. - Knihovna rzi Glommio používá výhradně
io_uring
. Autor (Glauber Costa) publikoval dokument s názvem Moderní úložiště je hodně rychlé. Špatná jsou rozhraní API, která ukazují, že pečlivým vyladěním může Glommio dosáhnout více než 2,5násobku výkonu oproti běžnému (neio_uring
) systémová volání při provádění sekvenčního I/O na zařízení Optane. - Gluster sloučil io_uring posix xlator v říjnu 2020 a byl součástí vydání Gluster 9.0. Autor potvrzení uvádí, že výkon „nebyl o nic horší než běžná systémová volání pwrite/pread“.
Software vyšetřující pomocí io_uring
- Vývojář PostgreSQL Andres Freund byl jednou z hnacích sil za
io_uring
vylepšení (např. řešení pro omezení sporů o inody souborového systému). K dispozici je prezentace "Asynchronní IO pro PostgreSQL" (pozor, video je přerušeno do 5 minut) (PDF), která motivuje potřebu změn PostgreSQL a demonstruje některé experimentální výsledky. Vyjádřil naději, že získá svůj volitelnýio_uring
podporu do PostgreSQL 14 a zdá se, že si je velmi dobře vědom toho, co funguje a co nefunguje, dokonce až na úrovni jádra. V prosinci 2020 Andres dále diskutuje o svém PostgreSQLio_uring
práce ve vláknu konference "Blocking I/O, async I/O and io_uring" pgsql-hackers a zmínky o probíhající práci si můžete prohlédnout na https://github.com/anarazel/postgres/tree/aio. - Projekt Netty má repozitář inkubátoru pracující na
io_uring
podpora, která potřebuje jádro 5.9 - libuv má požadavek na stažení a přidává
io_uring
podporu, ale její postup do projektu byl pomalý - SwiftNIO přidáno
io_uring
podpora pro eventing (ale ne syscalls) v dubnu 2020 a Linux:úplné vydání io_uring I/O nastiňuje plány na další integraci - Projekt Tokio Rust vyvinul důkaz konceptu tokio-uring
Podpora distribuce Linuxu pro io_uring
- (Konec roku 2020) Nejnovější jádro umožňující HWE Ubuntu 18.04 je 5.4, takže
io_uring
lze použít systémová volání. Tato distribuce neobsahuje předbaleníliburing
pomocnou knihovnu, ale můžete si ji vytvořit sami. - Počáteční jádro Ubuntu 20.04 je 5.4, takže
io_uring
lze použít systémová volání. Jak je uvedeno výše, distribuce nepředbalíliburing
. - Počáteční jádro Fedory 32 je 5.6 a má zabalený
liburing
takžeio_uring
je použitelný. - SLES 15 SP2 má jádro 5.3, takže
io_uring
lze použít systémová volání. Tato distribuce neobsahuje předbaleníliburing
pomocnou knihovnu, ale můžete si ji vytvořit sami. - (polovina roku 2021) Výchozí jádro RHEL 8 ne podpora
io_uring
(předchozí verze této odpovědi omylem uvedla, že ano). Existuje článek o podpoře Add io_uring Red Hat Knowledge Base (obsah je za předplatitelským paywallem), který je „ve vývoji“. - (polovina roku 2022) Výchozí jádro RHEL 9 ne podpora
io_uring
. Jádro je dostatečně nové (5.14), ale podporujeio_uring
je výslovně zakázáno.
Doufejme, že io_uring
přinese lepší asynchronní souborový I/O příběh pro Linux.
(Abychom dodali této odpovědi tenkou vrstvu důvěryhodnosti, někdy v minulosti Jens Axboe (správce blokové vrstvy linuxového jádra a vynálezce io_uring
) se domníval, že tato odpověď by mohla stát za to, abychom hlasovali pro :-)
Skutečná odpověď, na kterou nepřímo poukázal Peter Teoh, je založena na io_setup() a io_submit(). Konkrétně funkce „aio_“ uvedené Peterem jsou součástí emulace na uživatelské úrovni glibc založené na vláknech, což není efektivní implementace. Skutečná odpověď je v:
io_submit(2)
io_setup(2)
io_cancel(2)
io_destroy(2)
io_getevents(2)
Všimněte si, že manuálová stránka z let 2012-08 uvádí, že tato implementace ještě nedospěla do bodu, kdy by mohla nahradit emulaci uživatelského prostoru glibc:
http://man7.org/linux/man-pages/man7/aio.7.html
tato implementace ještě nedospěla do bodu, kdy lze implementaci POSIXAIO kompletně reimplementovat pomocí volání kernelsystem.
Takže podle nejnovější dokumentace jádra, kterou jsem našel, Linux ještě nemá vyspělý asynchronní I/O model založený na jádře. A pokud předpokládám, že dokumentovaný model je skutečně vyspělý, stále nepodporuje částečné I/O ve smyslu recv() vs read().