Durable Data Storage ug Linux File APIs

Ako, nga nagsiksik sa kalig-on sa pagtipig sa datos sa mga sistema sa panganod, nakahukom sa pagsulay sa akong kaugalingon, aron sa pagsiguro nga akong nasabtan ang mga batakang butang. Ako nagsugod pinaagi sa pagbasa sa NVMe spec aron masabtan kung unsa ang mga garantiya bahin sa pagpadayon sa datos (sa ato pa, garantiya nga magamit ang datos pagkahuman sa pagkapakyas sa sistema) hatagan kami mga disk sa NMVe. Gihimo nako ang mosunod nga mga nag-unang konklusyon: kinahanglan nimo nga tagdon ang mga datos nga nadaot gikan sa higayon nga gihatag ang mando sa pagsulat sa datos, ug hangtod sa higayon nga gisulat kini sa medium nga pagtipig. Bisan pa, sa kadaghanan nga mga programa, ang mga tawag sa sistema luwas nga gigamit sa pagsulat sa datos.

Niini nga artikulo, akong gisuhid ang mga mekanismo sa pagpadayon nga gihatag sa Linux file APIs. Ingon og ang tanan kinahanglan nga yano dinhi: ang programa nagtawag sa mando write(), ug human makompleto ang operasyon niini nga sugo, ang datos luwas nga tipigan sa disk. Apan write() nagkopya lamang sa datos sa aplikasyon ngadto sa kernel cache nga nahimutang sa RAM. Aron mapugos ang sistema sa pagsulat sa datos sa disk, kinahanglan nga gamiton ang pipila ka dugang nga mga mekanismo.

Durable Data Storage ug Linux File APIs

Sa kinatibuk-an, kini nga materyal usa ka hugpong sa mga nota nga may kalabutan sa akong nakat-unan sa usa ka hilisgutan nga interesado kanako. Kung maghisgot kami sa mubo bahin sa labing hinungdanon, nahimo nga aron maorganisar ang malungtaron nga pagtipig sa datos, kinahanglan nimo gamiton ang mando fdatasync() o ablihi ang mga file nga adunay bandila O_DSYNC. Kung interesado ka nga mahibal-an ang dugang bahin sa kung unsa ang mahitabo sa data sa paagi gikan sa code hangtod sa disk, tan-awa kini artikulo.

Mga bahin sa paggamit sa write() function

Sistema nga tawag write() gihubit sa sumbanan IEEE POSIX isip usa ka pagsulay sa pagsulat sa datos ngadto sa usa ka file descriptor. Human sa malampuson nga pagkompleto sa trabaho write() Ang mga operasyon sa pagbasa sa datos kinahanglan nga ibalik ang eksakto nga mga byte nga gisulat kaniadto, nga buhaton kini bisan kung ang datos gi-access gikan sa ubang mga proseso o mga hilo (tan-awa katugbang nga seksyon sa POSIX standard). kini mao ang, sa seksyon sa interaksyon sa mga hilo nga adunay normal nga mga operasyon sa file, adunay usa ka nota nga nag-ingon nga kung duha ka mga hilo ang matag usa nagtawag niini nga mga gimbuhaton, nan ang matag tawag kinahanglan nga makita ang tanan nga gipakita nga mga sangputanan nga ang pagpatuman sa lain nga tawag mosangpot, o dili makita sa tanan walay mga sangputanan. Nagdala kini sa konklusyon nga ang tanan nga mga operasyon sa I/O sa file kinahanglan adunay usa ka lock sa kapanguhaan nga gitrabaho.

Nagpasabot ba kini nga ang operasyon write() atomic ba? Gikan sa teknikal nga punto sa panglantaw, oo. Ang mga operasyon sa pagbasa sa datos kinahanglan nga ibalik ang tanan o wala sa kung unsa ang gisulat write(). Apan ang operasyon write(), uyon sa sumbanan, dili kinahanglan nga tapuson, nga gisulat ang tanan nga gihangyo kaniya nga isulat. Gitugotan ang pagsulat sa bahin lamang sa datos. Pananglitan, mahimo kaming adunay duha ka mga sapa matag usa nagdugang 1024 bytes sa usa ka file nga gihulagway sa parehas nga deskriptor sa file. Gikan sa punto sa panglantaw sa sumbanan, ang resulta mahimong madawat kung ang matag usa sa pagsulat nga mga operasyon makadugang lamang sa usa ka byte sa file. Kini nga mga operasyon magpabilin nga atomic, apan pagkahuman nila makompleto, ang mga datos nga ilang gisulat sa file mahimong gub-on. dinhi makaiikag kaayo nga diskusyon bahin niini nga hilisgutan sa Stack Overflow.

fsync() ug fdatasync() functions

Ang labing kadali nga paagi sa pag-flush sa data sa disk mao ang pagtawag sa function fsync(). Kini nga function naghangyo sa operating system nga ibalhin ang tanan nga giusab nga mga bloke gikan sa cache ngadto sa disk. Naglakip kini sa tanan nga metadata sa file (oras sa pag-access, oras sa pagbag-o sa file, ug uban pa). Nagtuo ko nga kini nga metadata panagsa ra gikinahanglan, busa kung nahibal-an nimo nga dili kini importante kanimo, mahimo nimong gamiton ang function fdatasync(). ang tabang sa fdatasync() kini nag-ingon nga sa panahon sa operasyon niini nga function, ang ingon nga usa ka kantidad sa metadata maluwas sa disk, nga mao ang "gikinahanglan alang sa husto nga pagpatuman sa mosunod nga data sa pagbasa sa mga operasyon." Ug mao gyud kini ang giatiman sa kadaghanan sa mga aplikasyon.

Usa ka problema nga mahimong motumaw dinhi mao nga kini nga mga mekanismo dili garantiya nga ang file makit-an pagkahuman sa usa ka posible nga kapakyasan. Sa partikular, kung ang usa ka bag-ong file gihimo, kinahanglan nga tawagan ang usa fsync() alang sa direktoryo nga naglangkob niini. Kung dili, pagkahuman sa pagkahagsa, mahimo’g mogawas nga wala kini nga file. Ang hinungdan niini mao nga ubos sa UNIX, tungod sa paggamit sa mga gahi nga mga link, ang usa ka file mahimong maglungtad sa daghang mga direktoryo. Busa, sa pagtawag fsync() walay paagi nga mahibal-an sa usa ka file kung unsang data sa direktoryo ang kinahanglan usab nga i-flush sa disk (dinhi mabasa nimo ang dugang bahin niini). Morag ang ext4 file system makahimo awtomatiko pag-apply fsync() ngadto sa mga direktoryo nga adunay katugbang nga mga payl, apan dili kini mahitabo sa ubang mga file system.

Kini nga mekanismo mahimong ipatuman nga lahi sa lainlaing mga sistema sa file. akong gigamit blktrace aron mahibal-an kung unsang mga operasyon sa disk ang gigamit sa ext4 ug XFS file system. Ang duha nag-isyu sa naandan nga pagsulat nga mga mando sa disk alang sa sulud sa mga file ug sa file system journal, pag-flush sa cache ug paggawas pinaagi sa paghimo sa usa ka FUA (Force Unit Access, pagsulat sa data direkta sa disk, pag-bypass sa cache) pagsulat sa journal. Lagmit ilang gibuhat kana aron makumpirma ang kamatuoran sa transaksyon. Sa mga drive nga dili mosuporta sa FUA, kini maoy hinungdan sa duha ka cache flushes. Gipakita kana sa akong mga eksperimento fdatasync() mas paspas gamay fsync(). Utility blktrace nagpaila niana fdatasync() kasagaran mosulat og gamay nga data sa disk (sa ext4 fsync() nagsulat 20 KiB, ug fdatasync() - 16 KiB). Usab, akong nahibal-an nga ang XFS mas paspas kay sa ext4. Ug dinhi uban sa tabang blktrace nakahibalo niana fdatasync() nag-flush og gamay nga data sa disk (4 KiB sa XFS).

Dili klaro nga mga sitwasyon kung gigamit ang fsync()

Makahunahuna ko og tulo ka dili klaro nga mga sitwasyon mahitungod sa fsync()nga akong nakit-an sa praktis.

Ang una nga ingon nga insidente nahitabo kaniadtong 2008. Nianang panahona, ang interface sa Firefox 3 "frozen" kung daghang mga file ang gisulat sa disk. Ang problema mao nga ang pagpatuman sa interface migamit sa SQLite database sa pagtipig og impormasyon mahitungod sa estado niini. Pagkahuman sa matag pagbag-o nga nahitabo sa interface, gitawag ang function fsync(), nga naghatag ug maayong mga garantiya sa stable nga pagtipig sa datos. Sa kaniadto gigamit nga ext3 file system, ang function fsync() gi-flush sa disk ang tanan nga "hugaw" nga mga panid sa sistema, ug dili lamang ang mga may kalabutan sa katugbang nga file. Kini nagpasabut nga ang pag-klik sa usa ka buton sa Firefox mahimong hinungdan sa mga megabyte nga datos nga masulat sa usa ka magnetic disk, nga mahimo’g molungtad daghang mga segundo. Ang solusyon sa problema, kutob sa akong nasabtan gikan sa kini materyal, mao ang pagbalhin sa trabaho uban sa database ngadto sa asynchronous background nga mga buluhaton. Nagpasabot kini nga gigamit sa Firefox ang pagpatuman sa mas estrikto nga mga kinahanglanon sa pagpadayon sa pagtipig kay sa gikinahanglan, ug ang mga feature sa ext3 filesystem nagpasamot lamang niini nga problema.

Ang ikaduha nga problema nahitabo sa 2009. Dayon, human sa pagkahagsa sa sistema, ang mga tiggamit sa bag-ong ext4 file system nakakaplag nga daghang mga bag-ong gimugna nga mga file ang zero-length, apan wala kini mahitabo sa mas karaan nga ext3 file system. Sa miaging parapo, naghisgut ako kung giunsa ang ext3 naglabay sa daghang mga datos sa disk, nga nagpahinay sa mga butang. fsync(). Aron mapausbaw ang sitwasyon, ang ext4 nag-flush lamang niadtong mga "hugaw" nga mga panid nga may kalabutan sa usa ka partikular nga file. Ug ang datos sa ubang mga file nagpabilin sa panumduman sa mas taas nga panahon kaysa sa ext3. Gihimo kini aron mapauswag ang pasundayag (sa default, ang datos magpabilin sa kini nga estado sa 30 segundos, mahimo nimo kini i-configure gamit ang dirty_expire_centisecs; dinhi makakita ka ug dugang impormasyon bahin niini). Kini nagpasabot nga ang usa ka dako nga kantidad sa data mahimong dili na mabawi human sa usa ka crash. Ang solusyon niini nga problema mao ang paggamit fsync() sa mga aplikasyon nga kinahanglan nga maghatag lig-on nga pagtipig sa datos ug mapanalipdan sila kutob sa mahimo gikan sa mga sangputanan sa mga kapakyasan. Kalihokan fsync() mas epektibo ang pagtrabaho sa ext4 kaysa sa ext3. Ang disbentaha niini nga pamaagi mao nga ang paggamit niini, sama kaniadto, nagpahinay sa pipila ka mga operasyon, sama sa pag-instalar sa mga programa. Tan-awa ang mga detalye bahin niini dinhi ΠΈ dinhi.

Ang ikatulo nga problema mahitungod sa fsync(), nagsugod sa 2018. Dayon, sulod sa gambalay sa proyekto sa PostgreSQL, nahibal-an nga kung ang function fsync() nakasugat og sayup, kini nagtimaan sa "hugaw" nga mga panid nga "limpyo". Ingon sa usa ka resulta, ang mosunod nga mga tawag fsync() walay buhaton sa maong mga panid. Tungod niini, ang giusab nga mga panid gitipigan sa panumduman ug wala gayud gisulat sa disk. Kini usa ka tinuud nga katalagman, tungod kay ang aplikasyon maghunahuna nga ang pipila nga mga datos gisulat sa disk, apan sa tinuud dili kini. Ang ingon nga mga kapakyasan fsync() talagsa ra, ang aplikasyon sa ingon nga mga sitwasyon halos wala’y mahimo aron mabuntog ang problema. Karong mga adlawa, kung kini mahitabo, ang PostgreSQL ug uban pang mga aplikasyon nahagsa. kini mao ang, sa artikulong "Mabawi ba ang mga Aplikasyon gikan sa mga Kapakyasan sa fsync?", kini nga problema gisusi sa detalye. Sa pagkakaron ang pinakamaayong solusyon niini nga problema mao ang paggamit sa Direct I/O sa bandila O_SYNC o may bandera O_DSYNC. Uban niini nga pamaagi, ang sistema magreport sa mga kasaypanan nga mahimong mahitabo sa paghimo sa piho nga mga operasyon sa pagsulat sa datos, apan kini nga pamaagi nagkinahanglan sa aplikasyon sa pagdumala sa mga buffer mismo. Basaha ang dugang bahin niini dinhi ΠΈ dinhi.

Pag-abli sa mga file gamit ang O_SYNC ug O_DSYNC nga mga bandera

Balikan nato ang paghisgot sa mga mekanismo sa Linux nga naghatag ug padayon nga pagtipig sa datos. Sa ato pa, naghisgot kami bahin sa paggamit sa bandila O_SYNC o bandera O_DSYNC sa pag-abli sa mga file gamit ang tawag sa sistema bukas (). Uban niini nga pamaagi, ang matag operasyon sa pagsulat sa datos gihimo ingon nga pagkahuman sa matag mando write() ang sistema gihatag, sa tinagsa, mga mando fsync() ΠΈ fdatasync(). ang Mga detalye sa POSIX kini gitawag nga "Synchronized I/O File Integrity Completion" ug "Data Integrity Completion". Ang panguna nga bentaha sa kini nga pamaagi mao nga usa ra ka tawag sa sistema ang kinahanglan ipatuman aron masiguro ang integridad sa datos, ug dili duha (pananglitan - write() ΠΈ fdatasync()). Ang panguna nga disbentaha niini nga pamaagi mao nga ang tanan nga mga operasyon sa pagsulat gamit ang katugbang nga deskriptor sa file ma-synchronize, nga mahimong limitahan ang abilidad sa pag-istruktura sa code sa aplikasyon.

Gigamit ang Direktang I/O nga adunay bandera nga O_DIRECT

Sistema nga tawag open() nagsuporta sa bandila O_DIRECT, nga gilaraw aron laktawan ang cache sa operating system, himuon ang mga operasyon sa I / O, direkta nga nakig-uban sa disk. Kini, sa daghang mga kaso, nagpasabut nga ang mga mando sa pagsulat nga gi-isyu sa programa direkta nga hubaron sa mga mando nga gitumong sa pagtrabaho sa disk. Apan, sa kinatibuk-an, kini nga mekanismo dili kapuli sa mga gimbuhaton fsync() o fdatasync(). Ang kamatuoran mao nga ang disk mismo mahimo paglangan o cache angay nga mga sugo alang sa pagsulat sa datos. Ug, mas grabe pa, sa pipila ka mga espesyal nga kaso, ang mga operasyon sa I / O gihimo kung gigamit ang bandila O_DIRECT, pagsibya ngadto sa tradisyonal nga buffered nga mga operasyon. Ang labing kadali nga paagi aron masulbad kini nga problema mao ang paggamit sa bandila aron maablihan ang mga file O_DSYNC, nga nagpasabut nga ang matag operasyon sa pagsulat sundan sa usa ka tawag fdatasync().

Kini nahimo nga ang XFS filesystem bag-o lang nagdugang usa ka "paspas nga agianan" alang sa O_DIRECT|O_DSYNC- mga rekord sa datos. Kung ang block gi-overwrite gamit ang O_DIRECT|O_DSYNC, unya ang XFS, imbes nga i-flush ang cache, ipatuman ang FUA write command kung gisuportahan kini sa device. Gipamatud-an nako kini gamit ang utility blktrace sa usa ka Linux 5.4/Ubuntu 20.04 nga sistema. Kini nga pamaagi kinahanglan nga mas episyente, tungod kay kini nagsulat sa minimum nga gidaghanon sa data sa disk ug naggamit sa usa ka operasyon, dili duha (isulat ug i-flush ang cache). Nakakita ko og link sa pag-patch 2018 kernel nga nagpatuman niini nga mekanismo. Adunay pipila ka mga diskusyon bahin sa paggamit niini nga pag-optimize sa ubang mga filesystem, apan sa akong nahibal-an, ang XFS mao ra ang filesystem nga nagsuporta niini hangtod karon.

sync_file_range() function

Ang Linux adunay tawag sa sistema sync_file_range(), nga nagtugot kanimo sa pag-flush sa bahin lamang sa file ngadto sa disk, dili sa tibuok nga file. Kini nga tawag nagsugod sa usa ka asynchronous flush ug dili maghulat nga kini makompleto. Apan sa paghisgot sa sync_file_range() kini nga sugo giingon nga "very dangerous". Dili girekomenda nga gamiton kini. Mga bahin ug kapeligrohan sync_file_range() maayo kaayo nga gihulagway sa kini materyal nga. Sa partikular, kini nga tawag daw naggamit sa RocksDB aron makontrol kung ang kernel nag-flush sa "hugaw" nga datos sa disk. Apan sa samang higayon didto, aron maseguro ang lig-on nga pagtipig sa datos, gigamit usab kini fdatasync(). ang Code Ang RocksDB adunay pipila ka makapaikag nga mga komento sa kini nga hilisgutan. Pananglitan, kini sama sa tawag sync_file_range() sa diha nga ang paggamit sa ZFS dili flush data ngadto sa disk. Ang kasinatian nagsulti kanako nga ang panagsa ra nga gigamit nga code mahimong adunay mga bug. Busa, ako motambag batok sa paggamit niini nga sistema sa tawag gawas kon gikinahanglan gayud.

Mga tawag sa sistema aron matabangan nga masiguro ang pagpadayon sa datos

Nakahukom ko nga adunay tulo ka mga pamaagi nga magamit sa paghimo sa padayon nga I/O nga mga operasyon. Tanan sila nanginahanglan usa ka tawag sa function fsync() alang sa direktoryo diin gihimo ang file. Kini ang mga pamaagi:

  1. Function nga tawag fdatasync() o fsync() pagkahuman sa function write() (mas maayo gamiton fdatasync()).
  2. Ang pagtrabaho sa usa ka file descriptor giablihan sa usa ka bandila O_DSYNC o O_SYNC (mas maayo - nga adunay bandila O_DSYNC).
  3. Paggamit sa sugo pwritev2() uban sa bandila RWF_DSYNC o RWF_SYNC (mas maayo nga adunay bandila RWF_DSYNC).

Mga Nota sa Pagganap

Wala nako gisukod pag-ayo ang nahimo sa lainlaing mga mekanismo nga akong gisusi. Ang mga kalainan nga akong namatikdan sa kapaspas sa ilang trabaho gamay ra kaayo. Nagpasabot kini nga mahimo kong masayop, ug nga sa ubang mga kondisyon ang parehas nga butang mahimong magpakita sa lainlaing mga sangputanan. Una, hisgutan nako kung unsa ang labi nga makaapekto sa pasundayag, ug dayon, kung unsa ang dili kaayo makaapekto sa pasundayag.

  1. Ang pag-overwrit sa data sa file mas paspas kay sa pagdugang sa datos sa usa ka file (ang performance gain mahimong 2-100%). Ang paglakip sa datos sa usa ka file nanginahanglan dugang nga mga pagbag-o sa metadata sa file, bisan pagkahuman sa tawag sa sistema fallocate(), apan ang gidak-on niini nga epekto mahimong magkalahi. Girekomenda ko, alang sa labing maayo nga performance, sa pagtawag fallocate() sa pag-allocate daan sa gikinahanglang luna. Unya kini nga luna kinahanglan nga tin-aw nga mapuno sa mga sero ug tawgon fsync(). Kini ang hinungdan nga ang katugbang nga mga bloke sa file system mamarkahan nga "gigahin" imbes nga "wala gigahin". Naghatag kini og gamay (mga 2%) nga pag-uswag sa performance. Usab, ang ubang mga disk mahimong adunay mas hinay nga unang block access nga operasyon kay sa uban. Kini nagpasabut nga ang pagpuno sa wanang nga adunay mga sero mahimong mosangput sa usa ka hinungdanon (mga 100%) nga pag-uswag sa pasundayag. Sa partikular, kini mahimong mahitabo sa mga disk. AWS EBS (Kini dili opisyal nga datos, dili nako makumpirma kini). Ang sama nga alang sa pagtipig. GCP Persistent Disk (ug kini opisyal na nga impormasyon, gikumpirma sa mga pagsulay). Ang ubang mga eksperto nagbuhat usab sa ingon obserbasyonnga may kalabutan sa lainlaing mga disk.
  2. Ang gamay nga tawag sa sistema, mas taas ang pasundayag (ang ganansya mahimong mga 5%). Murag tawag open() uban sa bandila O_DSYNC o tawag pwritev2() uban sa bandila RWF_SYNC mas paspas nga tawag fdatasync(). Nagduda ko nga ang punto dinhi mao nga sa kini nga pamaagi, ang kamatuoran nga mas gamay nga mga tawag sa sistema ang kinahanglan himuon aron masulbad ang parehas nga buluhaton (usa ka tawag imbis nga duha) adunay papel. Apan ang kalainan sa pasundayag gamay ra kaayo, aron dali nimo kini mabalewala ug magamit ang usa ka butang sa aplikasyon nga dili mosangpot sa komplikasyon sa lohika niini.

Kung interesado ka sa hilisgutan sa malungtarong pagtipig sa datos, aniay pipila ka mapuslanon nga mga materyales:

  • I/O Access nga mga pamaagi - usa ka kinatibuk-ang pagtan-aw sa mga sukaranan sa mga mekanismo sa input / output.
  • Pagsiguro nga ang data makaabot sa disk - usa ka istorya bahin sa kung unsa ang mahitabo sa data sa dalan gikan sa aplikasyon hangtod sa disk.
  • Kanus-a nimo kinahanglan i-fsync ang adunay sulod nga direktoryo - ang tubag sa pangutana kung kanus-a mag-aplay fsync() alang sa mga direktoryo. Sa laktod nga pagkasulti, kinahanglan nimo nga buhaton kini kung maghimo usa ka bag-ong file, ug ang hinungdan sa kini nga rekomendasyon mao nga sa Linux adunay daghang mga pakisayran sa parehas nga file.
  • SQL Server sa Linux: FUA Internals - ania ang usa ka paghulagway kung giunsa ang padayon nga pagtipig sa datos gipatuman sa SQL Server sa platform sa Linux. Adunay pipila ka makapaikag nga pagtandi tali sa Windows ug Linux system call dinhi. Hapit ko sigurado nga salamat sa kini nga materyal nga nahibal-an nako ang bahin sa pag-optimize sa FUA sa XFS.

Nawala na ba nimo ang datos nga imong gihunahuna nga luwas nga gitipig sa disk?

Durable Data Storage ug Linux File APIs

Durable Data Storage ug Linux File APIs

Source: www.habr.com