LVM na Matryoshka wanafanana nini?

Siku njema.
Ningependa kushiriki na jumuiya uzoefu wangu wa vitendo wa kujenga mfumo wa kuhifadhi data kwa KVM kwa kutumia md RAID + LVM.

Mpango huo utajumuisha:

  • Kujenga md RAID 1 kutoka NVMe SSD.
  • Kukusanya md RAID 6 kutoka kwa SATA SSD na anatoa za kawaida.
  • Vipengele vya uendeshaji wa TRIM/DISCARD kwenye SSD RAID 1/6.
  • Kuunda safu inayoweza kusongeshwa ya md RAID 1/6 kwenye seti ya kawaida ya diski.
  • Kufunga mfumo kwenye NVMe RAID 1 wakati hakuna usaidizi wa NVMe kwenye BIOS.
  • Kutumia kashe ya LVM na LVM nyembamba.
  • Kwa kutumia vijipicha vya BTRFS na kutuma/kupokea kwa hifadhi rudufu.
  • Kutumia vijipicha vyembamba vya LVM na thin_delta kwa chelezo za mtindo wa BTRFS.

Ikiwa una nia, tafadhali tazama paka.

Taarifa

Mwandishi hatawajibiki kwa matokeo ya kutumia au kutotumia nyenzo/mifano/msimbo/vidokezo/data kutoka kwa makala haya. Kwa kusoma au kutumia nyenzo hii kwa njia yoyote, unachukua jukumu la matokeo yote ya vitendo hivi. Matokeo yanayowezekana ni pamoja na:

  • NVMe SSD zilizokaanga.
  • Imetumia rasilimali ya kurekodi kabisa na kutofaulu kwa viendeshi vya SSD.
  • Kupoteza kabisa data zote kwenye hifadhi zote, ikiwa ni pamoja na nakala za chelezo.
  • Vifaa vya kompyuta vibaya.
  • Wakati uliopotea, mishipa na pesa.
  • Matokeo mengine yoyote ambayo hayajaorodheshwa hapo juu.

Iron

Zilizopatikana zilikuwa:

Ubao wa mama kuanzia mwaka wa 2013 wenye chipset ya Z87, iliyokamilika na Intel Core i7 / Haswell.

  • Kichakataji cores 4, nyuzi 8
  • RAM ya GB 32 ya DDR3
  • 1 x 16 au 2 x 8 PCIe 3.0
  • 1 x 4 + 1 x 1 PCIe 2.0
  • Viunganishi vya SATA 6 vya GB 6 x 3

Adapta ya SAS LSI SAS9211-8I ilimulika kwa hali ya IT / HBA. Firmware iliyowezeshwa na RAID imebadilishwa kimakusudi na programu dhibiti ya HBA hadi:

  1. Unaweza kutupa adapta hii wakati wowote na kuibadilisha na nyingine yoyote uliyokutana nayo.
  2. TRIM/Discard ilifanya kazi kawaida kwenye diski, kwa sababu... katika firmware ya RAID amri hizi hazitumiki kabisa, na HBA, kwa ujumla, haijali ni amri gani zinazopitishwa kwenye basi.

Anatoa ngumu - vipande 8 vya HGST Travelstar 7K1000 yenye uwezo wa TB 1 katika kipengele cha fomu 2.5, kama vile kompyuta ndogo. Hifadhi hizi hapo awali zilikuwa katika safu ya RAID 6. Pia watakuwa na matumizi katika mfumo mpya. Ili kuhifadhi nakala za ndani.

Kwa kuongeza:

Vipande 6 mfano wa SATA SSD Samsung 860 QVO 2TB. SSD hizi zilihitaji kiasi kikubwa, uwepo wa cache ya SLC, kuegemea, na bei ya chini ilihitajika. Usaidizi wa kutupa/sifuri ulihitajika, ambao unaangaliwa na mstari katika dmesg:

kernel: ata1.00: Enabling discard_zeroes_data

Vipande 2 vya mfano wa NVMe SSD Samsung SSD 970 EVO 500GB.

Kwa SSD hizi, kasi ya kusoma/kuandika bila mpangilio na uwezo wa rasilimali kwa mahitaji yako ni muhimu. Radiator kwa ajili yao. Lazima. Kabisa. Vinginevyo, kaanga hadi crispy wakati wa maingiliano ya kwanza ya RAID.

Adapta ya StarTech PEX8M2E2 ya 2 x NVMe SSD iliyosakinishwa kwenye slot ya PCIe 3.0 8x. Hii, tena, ni HBA tu, lakini kwa NVMe. Inatofautiana na adapta za bei nafuu kwa kuwa hauhitaji usaidizi wa bifurcation ya PCIe kutoka kwa ubao wa mama kutokana na kuwepo kwa kubadili PCIe iliyojengwa. Itafanya kazi hata katika mfumo wa zamani zaidi na PCIe, hata ikiwa ni yanayopangwa x1 PCIe 1.0. Kwa kawaida, kwa kasi inayofaa. Hakuna RAID hapo. Hakuna BIOS iliyojengwa kwenye ubao. Kwa hivyo, mfumo wako hautajifunza kichawi kuanza na NVMe, hata kidogo kufanya shukrani ya NVMe RAID kwa kifaa hiki.

Sehemu hii ilitokana tu na uwepo wa 8x PCIe 3.0 moja tu ya bure kwenye mfumo, na, ikiwa kuna nafasi 2 za bure, inaweza kubadilishwa kwa urahisi na senti mbili za PEX4M2E1 au analogues, ambazo zinaweza kununuliwa popote kwa bei ya 600. rubles.

Kukataliwa kwa kila aina ya vifaa au chipset / BIOS RAID zilizojengwa zilifanywa kwa makusudi, ili kuwa na uwezo wa kubadilisha kabisa mfumo mzima, isipokuwa SSD / HDD wenyewe, wakati wa kuhifadhi data zote. Kwa hakika, ili uweze kuokoa hata mfumo wa uendeshaji uliowekwa wakati wa kuhamia vifaa vipya / tofauti kabisa. Jambo kuu ni kwamba kuna bandari za SATA na PCIe. Ni kama CD moja kwa moja au kiendeshi cha flash inayoweza kuwashwa, haraka sana na kikubwa kidogo.

HumorVinginevyo, unajua kinachotokea - wakati mwingine unahitaji haraka kuchukua safu nzima na wewe kuchukua. Lakini sitaki kupoteza data. Kwa kufanya hivyo, vyombo vya habari vyote vilivyotajwa vinapatikana kwa urahisi kwenye slides katika bays 5.25 za kesi ya kawaida.

Kweli, na, kwa kweli, kwa kujaribu mbinu tofauti za caching ya SSD kwenye Linux.

Uvamizi wa vifaa ni boring. Washa. Inafanya kazi au haifanyi kazi. Na kwa mdadm kuna chaguzi kila wakati.

Programu

Hapo awali, Debian 8 Jessie iliwekwa kwenye vifaa, vilivyo karibu na EOL. RAID 6 ilikusanywa kutoka kwa HDD zilizotajwa hapo juu zilizooanishwa na LVM. Iliendesha mashine za kawaida katika kvm/libvirt.

Kwa sababu Mwandishi ana uzoefu unaofaa katika kuunda anatoa za SATA/NVMe zinazoweza kusongeshwa, na pia, ili kutovunja kiolezo cha kawaida cha apt, Ubuntu 18.04 ilichaguliwa kama mfumo unaolengwa, ambao tayari umeimarishwa vya kutosha, lakini bado una miaka 3. msaada katika siku zijazo.

Mfumo uliotajwa una viendeshi vyote vya vifaa tunavyohitaji nje ya boksi. Hatuhitaji programu au viendeshi vya watu wengine.

Maandalizi ya ufungaji

Ili kufunga mfumo tunahitaji Picha ya Desktop ya Ubuntu. Mfumo wa seva una aina fulani ya kisakinishi chenye nguvu, ambacho kinaonyesha uhuru mwingi ambao hauwezi kuzimwa kwa kusukuma kizigeu cha mfumo wa UEFI kwenye moja ya diski, na kuharibu uzuri wote. Ipasavyo, imewekwa tu katika hali ya UEFI. Haitoi chaguo zozote.

Hatufurahishwi na hili.

Kwa nini?Kwa bahati mbaya, UEFI boot haiendani sana na RAID ya programu ya boot, kwa sababu ... Hakuna mtu anayetupa uhifadhi wa kizigeu cha UEFI ESP. Kuna mapishi mkondoni ambayo yanapendekeza kuweka kizigeu cha ESP kwenye gari la flash kwenye bandari ya USB, lakini hii ni hatua ya kutofaulu. Kuna mapishi kwa kutumia programu ya mdadm RAID 1 na toleo la metadata 0.9 ambayo haizuii UEFI BIOS kuona kizigeu hiki, lakini hii inaishi hadi wakati wa furaha wakati BIOS au OS nyingine ya vifaa inaandika kitu kwa ESP na kusahau kusawazisha na zingine. vioo.

Kwa kuongeza, boot ya UEFI inategemea NVRAM, ambayo haitasonga pamoja na disks kwenye mfumo mpya, kwa sababu ni sehemu ya ubao wa mama.

Kwa hivyo, hatutabuni tena gurudumu jipya. Tayari tunayo baiskeli ya babu iliyotengenezwa tayari, iliyojaribiwa kwa muda, ambayo sasa inaitwa Legacy/BIOS boot, yenye jina la fahari la CSM kwenye mifumo inayoendana na UEFI. Tutaondoa tu kwenye rafu, kulainisha, kusukuma matairi na kuifuta kwa kitambaa cha uchafu.

Toleo la desktop la Ubuntu pia haliwezi kusanikishwa ipasavyo na Kiboreshaji cha Urithi, lakini hapa, kama wanasema, angalau kuna chaguzi.

Na kwa hiyo, tunakusanya vifaa na kupakia mfumo kutoka kwa gari la bootable la Ubuntu Live. Tutahitaji kupakua vifurushi, kwa hivyo tutakuwekea mtandao unaokufaa. Ikiwa haifanyi kazi, unaweza kupakia vifurushi muhimu kwenye gari la flash mapema.

Tunaingia kwenye mazingira ya Eneo-kazi, tuzindua emulator ya terminal, na tunaenda:

#sudo bash

Vipi…?Mstari hapo juu ndio kichochezi cha kisheria cha holiwars kuhusu sudo. C bΠΎfursa kubwa zaidi zije naΠΎwajibu mkubwa zaidi. Swali ni ikiwa unaweza kuchukua mwenyewe. Watu wengi wanafikiria kuwa kutumia sudo kwa njia hii sio mwangalifu. Hata hivyo:

#apt-get install mdadm lvm2 thin-provisioning-tools btrfs-tools util-linux lsscsi nvme-cli mc

Kwanini sio ZFS...?Tunaposakinisha programu kwenye kompyuta yetu, kimsingi tunakopesha maunzi yetu kwa wasanidi programu hii ili kuendesha.
Tunapoamini programu hii kwa usalama wa data yetu, tunachukua mkopo sawa na gharama ya kurejesha data hii, ambayo tutalazimika kulipa siku moja.

Kwa mtazamo huu, ZFS ni Ferrari, na mdadm+lvm ni kama baiskeli.

Kwa kweli, mwandishi anapendelea kukopesha baiskeli kwa mkopo kwa watu wasiojulikana badala ya Ferrari. Huko, bei ya suala sio juu. Hakuna haja ya haki. Rahisi kuliko sheria za trafiki. Maegesho ni bure. Uwezo wa kuvuka nchi ni bora zaidi. Unaweza daima kuunganisha miguu kwa baiskeli, na unaweza kutengeneza baiskeli kwa mikono yako mwenyewe.

Kwa nini basi BTRFS...?Ili kuwasha mfumo wa uendeshaji, tunahitaji mfumo wa faili ambao unatumika katika Legacy/BIOS GRUB nje ya boksi, na wakati huo huo unaauni vijipicha vya moja kwa moja. Tutatumia kwa kizigeu cha /boot. Kwa kuongezea, mwandishi anapendelea kutumia FS hii kwa / (mizizi), bila kusahau kumbuka kuwa kwa programu nyingine yoyote unaweza kuunda sehemu tofauti kwenye LVM na kuziweka kwenye saraka zinazohitajika.

Hatutahifadhi picha zozote za mashine pepe au hifadhidata kwenye FS hii.
FS hii itatumika tu kuunda vijipicha vya mfumo bila kuizima na kisha kuhamisha vijipicha hivi kwenye diski chelezo kwa kutumia send/receve.

Kwa kuongezea, mwandishi kwa ujumla anapendelea kuweka kiwango cha chini zaidi cha programu moja kwa moja kwenye maunzi na kuendesha programu nyingine zote katika mashine pepe kwa kutumia vitu kama vile kusambaza GPU na vidhibiti Seva ya PCI-USB hadi KVM kupitia IOMMU.

Vitu pekee vilivyobaki kwenye maunzi ni uhifadhi wa data, uboreshaji na chelezo.

Ikiwa unaamini ZFS zaidi, basi, kimsingi, kwa programu maalum zinaweza kubadilishwa.

Walakini, mwandishi hupuuza kwa makusudi vioo/RAID vilivyojengwa ndani na vipengee vya upunguzaji wa kazi ambavyo ZFS, BRTFS na LVM wanazo.

Kama hoja ya ziada, BTRFS ina uwezo wa kubadilisha maandishi nasibu kuwa yale yanayofuatana, ambayo yana athari chanya sana kwa kasi ya kulandanisha vijipicha/chelezo kwenye HDD.

Wacha tuchague tena vifaa vyote:

#udevadm control --reload-rules && udevadm trigger

Wacha tuangalie pande zote:

#lsscsi && nvme list
[0:0:0:0] disk ATA Samsung SSD 860 2B6Q /dev/sda
[1:0:0:0] disk ATA Samsung SSD 860 2B6Q /dev/sdb
[2:0:0:0] disk ATA Samsung SSD 860 2B6Q /dev/sdc
[3:0:0:0] disk ATA Samsung SSD 860 2B6Q /dev/sdd
[4:0:0:0] disk ATA Samsung SSD 860 2B6Q /dev/sde
[5:0:0:0] disk ATA Samsung SSD 860 2B6Q /dev/sdf
[6:0:0:0] disk ATA HGST HTS721010A9 A3J0 /dev/sdg
[6:0:1:0] disk ATA HGST HTS721010A9 A3J0 /dev/sdh
[6:0:2:0] disk ATA HGST HTS721010A9 A3J0 /dev/sdi
[6:0:3:0] disk ATA HGST HTS721010A9 A3B0 /dev/sdj
[6:0:4:0] disk ATA HGST HTS721010A9 A3B0 /dev/sdk
[6:0:5:0] disk ATA HGST HTS721010A9 A3B0 /dev/sdl
[6:0:6:0] disk ATA HGST HTS721010A9 A3J0 /dev/sdm
[6:0:7:0] disk ATA HGST HTS721010A9 A3J0 /dev/sdn
Node SN Model Namespace Usage Format FW Rev
---------------- -------------------- ---------------------------------------- --------- -------------------------- ---------------- --------
/dev/nvme0n1 S466NXXXXXXX15L Samsung SSD 970 EVO 500GB 1 0,00 GB / 500,11 GB 512 B + 0 B 2B2QEXE7
/dev/nvme1n1 S5H7NXXXXXXX48N Samsung SSD 970 EVO 500GB 1 0,00 GB / 500,11 GB 512 B + 0 B 2B2QEXE7

Mpangilio wa diski

NVMe SSD

Lakini hatutawaweka alama kwa njia yoyote. Vivyo hivyo, BIOS yetu haioni anatoa hizi. Kwa hivyo, wataenda kabisa kwa programu ya RAID. Hata hatutaunda sehemu hapo. Ikiwa unataka kufuata "kanuni" au "kimsingi", unda kizigeu kimoja kikubwa, kama HDD.

HDATA ya SATA

Hakuna haja ya kubuni chochote maalum hapa. Tutaunda sehemu moja kwa kila kitu. Tutaunda kizigeu kwa sababu BIOS inaona diski hizi na inaweza hata kujaribu boot kutoka kwao. Tutaweka GRUB kwenye diski hizi baadaye ili mfumo uweze kufanya hivi ghafla.

#cat >hdd.part << EOF
label: dos
label-id: 0x00000000
device: /dev/sdg
unit: sectors

/dev/sdg1 : start= 2048, size= 1953523120, type=fd, bootable
EOF
#sfdisk /dev/sdg < hdd.part
#sfdisk /dev/sdh < hdd.part
#sfdisk /dev/sdi < hdd.part
#sfdisk /dev/sdj < hdd.part
#sfdisk /dev/sdk < hdd.part
#sfdisk /dev/sdl < hdd.part
#sfdisk /dev/sdm < hdd.part
#sfdisk /dev/sdn < hdd.part

SATA SSD

Hapa ndipo mambo yanapotuvutia.

Kwanza, hifadhi zetu zina ukubwa wa TB 2. Hii iko ndani ya safu inayokubalika ya MBR, ambayo ndiyo tutatumia. Ikiwa ni lazima, inaweza kubadilishwa na GPT. Diski za GPT zina safu ya uoanifu inayoruhusu mifumo inayooana na MBR kuona sehemu 4 za kwanza ikiwa ziko ndani ya terabaiti 2 za kwanza. Jambo kuu ni kwamba ugawaji wa boot na ugawaji wa bios_grub kwenye diski hizi unapaswa kuwa mwanzoni. Hii hata hukuruhusu kuwasha kutoka kwa viendeshi vya GPT Legacy/BIOS.

Lakini hii si kesi yetu.

Hapa tutaunda sehemu mbili. Ya kwanza itakuwa na ukubwa wa GB 1 na itatumika kwa RAID 1 /boot.

Ya pili itatumika kwa RAID 6 na itachukua nafasi yote ya bure iliyobaki isipokuwa kwa eneo ndogo ambalo halijatengwa mwishoni mwa gari.

Je, eneo hili lisilo na alama ni lipi?Kulingana na vyanzo kwenye mtandao, SSD zetu za SATA zina kashe ya SLC inayoweza kupanuliwa kwa ukubwa kuanzia gigabytes 6 hadi 78. Tunapata gigabytes 6 "bila malipo" kutokana na tofauti kati ya "gigabytes" na "gibibytes" kwenye karatasi ya data ya gari. Gigabytes 72 zilizobaki zimetengwa kutoka kwa nafasi isiyotumiwa.

Hapa ni lazima ieleweke kwamba tuna cache SLC, na nafasi ni ulichukua katika 4 bit MLC mode. Ambayo kwetu kwa ufanisi ina maana kwamba kwa kila gigabytes 4 za nafasi ya bure tutapata tu gigabyte 1 ya cache ya SLC.

Zidisha gigabaiti 72 kwa 4 na upate gigabaiti 288. Hii ni nafasi ya bure ambayo hatutaweka alama ili kuruhusu viendeshi kutumia kikamilifu kache ya SLC.

Kwa hivyo, tutapata kwa ufanisi hadi gigabytes 312 za cache ya SLC kutoka kwa jumla ya anatoa sita. Kati ya viendeshi vyote, 2 zitatumika katika RAID kwa upunguzaji wa kazi.

Kiasi hiki cha kashe kitaturuhusu mara chache sana katika maisha halisi kukutana na hali ambayo uandishi hauendi kwenye kashe. Hii inafidia kasoro ya kusikitisha zaidi ya kumbukumbu ya QLC - kasi ya chini sana ya uandishi wakati data imeandikwa kwa kupita kache. Ikiwa mizigo yako hailingani na hili, basi ninapendekeza ufikirie kwa bidii kuhusu muda gani SSD yako itaendelea chini ya mzigo huo, kwa kuzingatia TBW kutoka kwa karatasi ya data.

#cat >ssd.part << EOF
label: dos
label-id: 0x00000000
device: /dev/sda
unit: sectors

/dev/sda1 : start= 2048, size= 2097152, type=fd, bootable
/dev/sda2 : start= 2099200, size= 3300950016, type=fd
EOF
#sfdisk /dev/sda < ssd.part
#sfdisk /dev/sdb < ssd.part
#sfdisk /dev/sdc < ssd.part
#sfdisk /dev/sdd < ssd.part
#sfdisk /dev/sde < ssd.part
#sfdisk /dev/sdf < ssd.part

Kuunda safu

Kwanza, tunahitaji kubadili jina la mashine. Hii ni muhimu kwa sababu jina la mwenyeji ni sehemu ya jina la safu mahali fulani ndani ya mdadm na huathiri kitu mahali fulani. Bila shaka, safu zinaweza kuitwa jina baadaye, lakini hii ni hatua isiyo ya lazima.

#mcedit /etc/hostname
#mcedit /etc/hosts
#hostname
vdesk0

NVMe SSD

#mdadm --create --verbose --assume-clean /dev/md0 --level=1 --raid-devices=2 /dev/nvme[0-1]n1

Kwa nini -chukulia-safi...?Ili kuzuia kuanzisha safu. Kwa viwango vyote vya RAID 1 na 6 hii ni halali. Kila kitu kinaweza kufanya kazi bila kuanzishwa ikiwa ni safu mpya. Kwa kuongezea, kuanzisha safu ya SSD juu ya uundaji ni upotezaji wa rasilimali ya TBW. Tunatumia TRIM/DISCARD inapowezekana kwenye safu zilizounganishwa za SSD ili "kuzianzisha".

Kwa safu za SSD, RAID 1 DISCARD inatumika nje ya kisanduku.

Kwa safu za SSD RAID 6 DISCARD, lazima uiwashe katika vigezo vya moduli ya kernel.

Hii inapaswa kufanywa tu ikiwa SSD zote zinazotumiwa katika safu ya kiwango cha 4/5/6 katika mfumo huu zina usaidizi wa kufanya kazi kwa discard_zeroes_data. Wakati mwingine hukutana na anatoa za ajabu ambazo huambia kernel kwamba kazi hii inaungwa mkono, lakini kwa kweli haipo, au kazi haifanyi kazi kila wakati. Kwa sasa, msaada unapatikana karibu kila mahali, hata hivyo, kuna anatoa za zamani na firmware yenye makosa. Kwa sababu hii, usaidizi wa DISCARD umezimwa kwa chaguomsingi kwa RAID 6.

Tahadhari, amri ifuatayo itaharibu data zote kwenye viendeshi vya NVMe kwa "kuanzisha" safu na "zero".

#blkdiscard /dev/md0

Ikiwa kitu kitaenda vibaya, jaribu kubainisha hatua.

#blkdiscard --step 65536 /dev/md0

SATA SSD

#mdadm --create --verbose --assume-clean /dev/md1 --level=1 --raid-devices=6 /dev/sd[a-f]1
#blkdiscard /dev/md1
#mdadm --create --verbose --assume-clean /dev/md2 --chunk-size=512 --level=6 --raid-devices=6 /dev/sd[a-f]2

Mbona mkubwa hivyo...?Kuongeza ukubwa wa chunk kuna athari chanya kwa kasi ya usomaji nasibu katika vizuizi hadi ukubwa wa chunk. Hii hutokea kwa sababu operesheni moja ya ukubwa unaofaa au ndogo inaweza kukamilika kabisa kwenye kifaa kimoja. Kwa hivyo, IOPS kutoka kwa vifaa vyote ni muhtasari. Kulingana na takwimu, 99% ya IO haizidi 512K.

RAID 6 IOPS kwa kuandika daima chini ya au sawa na IOPS ya kiendeshi kimoja. Wakati, kama usomaji wa nasibu, IOPS inaweza kuwa kubwa mara kadhaa kuliko ile ya gari moja, na hapa saizi ya kizuizi ni muhimu sana.
Mwandishi haoni maana ya kujaribu kuongeza kigezo ambacho ni kibaya katika muundo-msingi wa RAID 6 na badala yake huongeza kile ambacho RAID 6 ni nzuri.
Tutafidia uandishi mbaya wa nasibu wa RAID 6 na kashe ya NVMe na hila za utoaji mwembamba.

Bado hatujawasha DISCARD kwa RAID 6. Kwa hivyo "hatutaanzisha" safu hii kwa sasa. Tutafanya hivi baadaye, baada ya kusakinisha OS.

HDATA ya SATA

#mdadm --create --verbose --assume-clean /dev/md3 --chunk-size=512 --level=6 --raid-devices=8 /dev/sd[g-n]1

LVM kwenye NVMe RAID

Kwa kasi, tunataka kuweka mfumo wa faili wa mizizi kwenye NVMe RAID 1 ambayo ni /dev/md0.
Walakini, bado tutahitaji safu hii ya haraka kwa mahitaji mengine, kama vile kubadilishana, metadata na LVM-cache na metadata nyembamba ya LVM, kwa hivyo tutaunda LVM VG kwenye safu hii.

#pvcreate /dev/md0
#vgcreate root /dev/md0

Wacha tuunda kizigeu cha mfumo wa faili wa mizizi.

#lvcreate -L 128G --name root root

Wacha tuunda kizigeu cha kubadilishana kulingana na saizi ya RAM.

#lvcreate -L 32G --name swap root

Ufungaji wa OS

Kwa jumla, tuna kila kitu muhimu ili kufunga mfumo.

Zindua mchawi wa usakinishaji wa mfumo kutoka kwa mazingira ya Ubuntu Live. Ufungaji wa kawaida. Tu katika hatua ya kuchagua disks kwa ajili ya ufungaji, unahitaji kutaja zifuatazo:

  • /dev/md1, - mahali pa kuweka /boot, FS - BTRFS
  • /dev/mzizi/mzizi (aka /dev/mapper/mzizi-mzizi), - mahali pa kuweka / (mizizi), FS - BTRFS
  • /dev/root/swap (aka /dev/mapper/root-swap), - tumia kama kizigeu cha kubadilishana
  • Sakinisha bootloader kwenye /dev/sda

Unapochagua BTRFS kama mfumo wa faili mzizi, kisakinishi kitaunda kiatomati juzuu mbili za BTRFS zinazoitwa "@" kwa ajili ya / (mzizi), na "@home" kwa /home.

Wacha tuanze ufungaji ...

Usakinishaji utaisha na kisanduku kidadisi cha modal kinachoonyesha hitilafu katika kusakinisha kipakiaji. Kwa bahati mbaya, hutaweza kuondoka kidirisha hiki kwa kutumia njia za kawaida na kuendelea na usakinishaji. Tunatoka kwenye mfumo na kuingia tena, na kuishia kwenye desktop safi ya Ubuntu Live. Fungua terminal, na tena:

#sudo bash

Unda mazingira ya chroot ili kuendelea na usakinishaji:

#mkdir /mnt/chroot
#mount -o defaults,space_cache,noatime,nodiratime,discard,subvol=@ /dev/mapper/root-root /mnt/chroot
#mount -o defaults,space_cache,noatime,nodiratime,discard,subvol=@home /dev/mapper/root-root /mnt/chroot/home
#mount -o defaults,space_cache,noatime,nodiratime,discard /dev/md1 /mnt/chroot/boot
#mount --bind /proc /mnt/chroot/proc
#mount --bind /sys /mnt/chroot/sys
#mount --bind /dev /mnt/chroot/dev

Wacha tusanidi mtandao na jina la mwenyeji katika chroot:

#cat /etc/hostname >/mnt/chroot/etc/hostname
#cat /etc/hosts >/mnt/chroot/etc/hosts
#cat /etc/resolv.conf >/mnt/chroot/etc/resolv.conf

Wacha tuende kwenye mazingira ya chroot:

#chroot /mnt/chroot

Kwanza kabisa, tutatoa vifurushi:

apt-get install --reinstall mdadm lvm2 thin-provisioning-tools btrfs-tools util-linux lsscsi nvme-cli mc debsums hdparm

Wacha tuangalie na turekebishe vifurushi vyote ambavyo vilisakinishwa vibaya kwa sababu ya usakinishaji usio kamili wa mfumo:

#CORRUPTED_PACKAGES=$(debsums -s 2>&1 | awk '{print $6}' | uniq)
#apt-get install --reinstall $CORRUPTED_PACKAGES

Ikiwa kitu hakifanyiki, unaweza kuhitaji kuhariri /etc/apt/sources.list kwanza

Wacha turekebishe vigezo vya moduli ya RAID 6 ili kuwezesha TRIM/DISCARD:

#cat >/etc/modprobe.d/raid456.conf << EOF
options raid456 devices_handle_discard_safely=1
EOF

Wacha tubadilishe safu zetu kidogo:

#cat >/etc/udev/rules.d/60-md.rules << EOF
SUBSYSTEM=="block", KERNEL=="md*", ACTION=="change", TEST=="md/stripe_cache_size", ATTR{md/stripe_cache_size}="32768"
SUBSYSTEM=="block", KERNEL=="md*", ACTION=="change", TEST=="md/sync_speed_min", ATTR{md/sync_speed_min}="48000"
SUBSYSTEM=="block", KERNEL=="md*", ACTION=="change", TEST=="md/sync_speed_max", ATTR{md/sync_speed_max}="300000"
EOF
#cat >/etc/udev/rules.d/62-hdparm.rules << EOF
SUBSYSTEM=="block", ACTION=="add|change", KERNEL=="sd[a-z]", ATTR{queue/rotational}=="1", RUN+="/sbin/hdparm -B 254 /dev/%k"
EOF
#cat >/etc/udev/rules.d/63-blockdev.rules << EOF
SUBSYSTEM=="block", ACTION=="add|change", KERNEL=="sd[a-z]", ATTR{queue/rotational}=="1", RUN+="/sbin/blockdev --setra 1024 /dev/%k"
SUBSYSTEM=="block", ACTION=="add|change", KERNEL=="md*", RUN+="/sbin/blockdev --setra 0 /dev/%k"
EOF

Ilikuwa nini..?Tumeunda seti ya sheria za udev ambazo zitafanya yafuatayo:

  • Weka ukubwa wa kashe ya kuzuia kwa RAID 2020 ili kutosha kwa 6. Thamani ya chaguo-msingi, inaonekana, haijabadilika tangu kuundwa kwa Linux, na haijatosha kwa muda mrefu.
  • Hifadhi kiwango cha chini cha IO kwa muda wa ukaguzi/usawazishaji wa safu. Hii ni kuzuia safu zako kukwama katika hali ya ulandanishi wa milele chini ya mzigo.
  • Weka kikomo cha juu cha IO wakati wa ukaguzi/usawazishaji wa safu. Hii ni muhimu ili kusawazisha/kuangalia RAID za SSD zisikaanga viendeshi vyako kuwa crisp. Hii ni kweli hasa kwa NVMe. (Je! unakumbuka kuhusu radiator? Sikuwa natania.)
  • Kataza diski kusimamisha mzunguko wa spindle (HDD) kupitia APM na uweke muda wa kuisha kwa vidhibiti vya diski hadi saa 7. Unaweza kuzima kabisa APM ikiwa hifadhi zako zinaweza kuifanya (-B 255). Kwa thamani ya chaguo-msingi, viendeshi vitaacha baada ya sekunde tano. Kisha OS inataka kuweka upya kashe ya diski, diski zitazunguka tena, na kila kitu kitaanza tena. Diski zina upeo mdogo wa idadi ya mizunguko ya spindle. Mzunguko rahisi kama huo wa kawaida unaweza kuua diski zako kwa urahisi katika miaka kadhaa. Sio diski zote zinakabiliwa na hii, lakini yetu ni "laptop", na mipangilio inayofaa ya chaguo-msingi, ambayo hufanya RAID ionekane kama mini-MAID.
  • Sakinisha usomaji kwenye diski (zinazozunguka) megabyte 1 - vizuizi viwili mfululizo/chunk RAID 6
  • Lemaza kusoma mbele kwenye safu zenyewe.

Wacha tuhariri /etc/fstab:

#cat >/etc/fstab << EOF
# /etc/fstab: static file system information.
#
# Use 'blkid' to print the universally unique identifier for a
# device; this may be used with UUID= as a more robust way to name devices
# that works even if disks are added and removed. See fstab(5).
# file-system mount-point type options dump pass
/dev/mapper/root-root / btrfs defaults,space_cache,noatime,nodiratime,discard,subvol=@ 0 1
UUID=$(blkid -o value -s UUID /dev/md1) /boot btrfs defaults,space_cache,noatime,nodiratime,discard 0 2
/dev/mapper/root-root /home btrfs defaults,space_cache,noatime,nodiratime,discard,subvol=@home 0 2
/dev/mapper/root-swap none swap sw 0 0
EOF

Kwanini hivyo..?Tutatafuta kizigeu cha /boot na UUID. Kutaja kwa safu kunaweza kubadilika kinadharia.

Tutatafuta sehemu zilizobaki kwa majina ya LVM kwenye nukuu ya /dev/mapper/vg-lv, kwa sababu wao kutambua partitions kipekee kabisa.

Hatutumii UUID kwa LVM kwa sababu UUID ya juzuu za LVM na vijipicha vyake vinaweza kuwa sawa.Panda /dev/mapper/root-root.. mara mbili?Ndiyo. Hasa. Kipengele cha BTRFS. Mfumo huu wa faili unaweza kuwekwa mara kadhaa na subvols tofauti.

Kwa sababu ya kipengele hiki hiki, ninapendekeza usiwahi kuunda vijipicha vya LVM vya viwango amilifu vya BTRFS. Unaweza kupata mshangao unapoanzisha upya.

Wacha tufanye upya usanidi wa mdadm:

#/usr/share/mdadm/mkconf | sed 's/#DEVICE/DEVICE/g' >/etc/mdadm/mdadm.conf

Wacha turekebishe mipangilio ya LVM:

#cat >>/etc/lvm/lvmlocal.conf << EOF

activation {
thin_pool_autoextend_threshold=90
thin_pool_autoextend_percent=5
}
allocation {
cache_pool_max_chunks=2097152
}
devices {
global_filter=["r|^/dev/.*_corig$|","r|^/dev/.*_cdata$|","r|^/dev/.*_cmeta$|","r|^/dev/.*gpv$|","r|^/dev/images/.*$|","r|^/dev/mapper/images.*$|","r|^/dev/backup/.*$|","r|^/dev/mapper/backup.*$|"] issue_discards=1
}
EOF

Ilikuwa nini..?Tumewezesha upanuzi wa kiotomatiki wa madimbwi membamba ya LVM baada ya kufikia 90% ya nafasi inayokaliwa kwa 5% ya kiasi.

Tumeongeza idadi ya juu zaidi ya vizuizi vya kache kwa akiba ya LVM.

Tumezuia LVM kutafuta kiasi cha LVM (PV) kwenye:

  • vifaa vyenye kashe ya LVM (cdata)
  • vifaa vilivyohifadhiwa kwa kutumia kashe ya LVM, kupitisha kashe ( _kori). Katika kesi hii, kifaa kilichohifadhiwa yenyewe bado kitachanganuliwa kupitia kache (tu )
  • vifaa vyenye metadata ya kache ya LVM (cmeta)
  • vifaa vyote katika VG vilivyo na picha za majina. Hapa tutakuwa na picha za diski za mashine pepe, na hatutaki LVM kwenye seva pangishi kuamilisha kiasi cha OS ya mgeni.
  • vifaa vyote katika VG na chelezo ya jina. Hapa tutakuwa na nakala za nakala za picha za mashine pepe.
  • vifaa vyote ambavyo jina lake huishia na "gpv" (kiasi halisi cha mgeni)

Tumewasha usaidizi wa DISCARD wakati wa kufuta nafasi kwenye LVM VG. Kuwa mwangalifu. Hii itafanya kufuta LV kwenye SSD kutumia wakati mwingi. Hii inatumika hasa kwa SSD RAID 6. Hata hivyo, kwa mujibu wa mpango huo, tutatumia utoaji nyembamba, hivyo hii haitatuzuia kabisa.

Wacha tusasishe picha ya initramfs:

#update-initramfs -u -k all

Sakinisha na usanidi grub:

#apt-get install grub-pc
#apt-get purge os-prober
#dpkg-reconfigure grub-pc

Ni diski gani unapaswa kuchagua?Wote ambao ni sd*. Mfumo lazima uweze boot kutoka kwa gari lolote la SATA la kufanya kazi au SSD.

Kwa nini waliongeza os-prober..?Kwa uhuru mwingi na mikono ya kucheza.

Haifanyi kazi ipasavyo ikiwa mojawapo ya RAID iko katika hali duni. Inajaribu kutafuta OS kwenye partitions ambazo hutumiwa katika mashine pepe zinazoendesha kwenye maunzi haya.

Ikiwa unahitaji, unaweza kuiacha, lakini kumbuka yote hapo juu. Ninapendekeza kutafuta mapishi ya kuondokana na mikono ya naughty mtandaoni.

Kwa hili tumekamilisha ufungaji wa awali. Ni wakati wa kuanza upya kwenye OS mpya iliyosanikishwa. Usisahau kuondoa CD/USB inayoweza kuwashwa.

#exit
#reboot

Chagua SSD zozote za SATA kama kifaa cha kuwasha.

LVM kwenye SATA SSD

Kwa wakati huu, tayari tumeingia kwenye OS mpya, kusanidi mtandao, apt, kufungua emulator ya terminal, na kuzindua:

#sudo bash

Hebu tuendelee.

"Anzisha" safu kutoka SATA SSD:

#blkdiscard /dev/md2

Ikiwa haifanyi kazi, basi jaribu:

#blkdiscard --step 65536 /dev/md2
Unda LVM VG kwenye SATA SSD:

#pvcreate /dev/md2
#vgcreate data /dev/md2

Kwa nini VG nyingine..?Kwa kweli, tayari tunayo VG inayoitwa mzizi. Kwa nini usiongeze kila kitu kwenye VG moja?

Ikiwa kuna PV kadhaa kwenye VG, basi ili VG iamilishwe kwa usahihi, PV zote lazima ziwepo (mtandaoni). Isipokuwa ni LVM RAID, ambayo hatutumii kwa makusudi.

Tunataka kweli kwamba ikiwa kuna kushindwa (kusoma kupoteza data) kwenye safu yoyote ya RAID 6, mfumo wa uendeshaji utaanza kawaida na kutupa fursa ya kutatua tatizo.

Ili kufanya hivyo, katika ngazi ya kwanza ya uondoaji tutatenga kila aina ya "vyombo vya habari" vya kimwili katika VG tofauti.

Kuzungumza kisayansi, safu tofauti za RAID ni za "vikoa vya kutegemewa" tofauti. Haupaswi kuunda alama ya ziada ya kutofaulu kwao kwa kuibandika kwenye VG moja.

Uwepo wa LVM katika kiwango cha "vifaa" utaturuhusu kukata vipande kiholela vya safu tofauti za RAID kwa kuzichanganya kwa njia tofauti. Kwa mfano - kukimbia wakati huo huo bcache + LVM nyembamba, bcache + BTRFS, kashe ya LVM + LVM nyembamba, usanidi changamano wa ZFS na kache, au mchanganyiko mwingine wowote wa kuzimu ili kujaribu na kulinganisha yote.

Katika kiwango cha "vifaa", hatutatumia chochote isipokuwa viwango vya "nene" vya LVM vya zamani. Isipokuwa kwa sheria hii inaweza kuwa kizigeu chelezo.

Nadhani kufikia wakati huu, wasomaji wengi walikuwa tayari wameanza kushuku kitu kuhusu mwanasesere wa kiota.

LVM kwenye SATA HDD

#pvcreate /dev/md3
#vgcreate backup /dev/md3

VG mpya tena..?Kwa kweli tunataka kwamba ikiwa safu ya diski tutakayotumia kuhifadhi nakala ya data itashindwa, mfumo wetu wa uendeshaji utaendelea kufanya kazi kama kawaida, huku tukidumisha ufikiaji wa data isiyo ya chelezo kama kawaida. Kwa hiyo, ili kuepuka matatizo ya uanzishaji wa VG, tunaunda VG tofauti.

Kuanzisha kashe ya LVM

Wacha tuunde LV kwenye NVMe RAID 1 ili kuitumia kama kifaa cha kuhifadhi.

#lvcreate -L 70871154688B --name cache root

Mbona kuna kidogo sana...?Ukweli ni kwamba SSD zetu za NVMe pia zina kashe ya SLC. Gigabaiti 4 za "bure" na gigabytes 18 za nguvu kutokana na nafasi ya bure iliyochukuliwa katika MLC ya 3-bit. Mara tu kache hii itakapomalizika, SSD za NVMe hazitakuwa haraka zaidi kuliko SSD yetu ya SATA iliyo na kashe. Kwa kweli, kwa sababu hii, haina mantiki kwetu kufanya kizigeu cha kache ya LVM kuwa kubwa zaidi kuliko saizi ya mara mbili ya kashe ya SLC ya kiendeshi cha NVMe. Kwa anatoa za NVMe zinazotumiwa, mwandishi anaona kuwa ni sawa kutengeneza gigabytes 32-64 za cache.

Ukubwa wa sehemu uliyopewa unahitajika ili kupanga gigabaiti 64 za akiba, metadata ya akiba na hifadhi rudufu ya metadata.

Kwa kuongeza, ninaona kuwa baada ya kuzima kwa mfumo chafu, LVM itaweka alama kwenye kashe nzima kama chafu na itasawazisha tena. Zaidi ya hayo, hii itarudiwa kila wakati lvchange inatumiwa kwenye kifaa hiki hadi mfumo utakapowashwa tena. Kwa hiyo, ninapendekeza mara moja kurejesha cache kwa kutumia script inayofaa.

Wacha tuunde LV kwenye SATA RAID 6 ili kuitumia kama kifaa kilichohifadhiwa.

#lvcreate -L 3298543271936B --name cache data

Mbona terabytes tatu tu..?Ili, ikiwa ni lazima, unaweza kutumia SATA SSD RAID 6 kwa mahitaji mengine. Ukubwa wa nafasi iliyohifadhiwa inaweza kuongezeka kwa nguvu, kwa kuruka, bila kuacha mfumo. Ili kufanya hivyo, unahitaji kusimamisha kwa muda na kuwezesha kache tena, lakini faida tofauti ya LVM-cache juu, kwa mfano, bcache ni kwamba hii inaweza kufanywa kwa kuruka.

Hebu tuunde VG mpya kwa caching.

#pvcreate /dev/root/cache
#pvcreate /dev/data/cache
#vgcreate cache /dev/root/cache /dev/data/cache

Wacha tuunde LV kwenye kifaa kilichohifadhiwa.

#lvcreate -L 3298539077632B --name cachedata cache /dev/data/cache

Hapa tulichukua mara moja nafasi yote ya bure kwenye /dev/data/cache ili sehemu zingine zote muhimu ziundwe mara moja kwenye /dev/root/cache. Ikiwa umeunda kitu mahali pasipofaa, unaweza kukisogeza kwa kutumia pvmove.

Wacha tuunda na kuwezesha kashe:

#lvcreate -y -L 64G -n cache cache /dev/root/cache
#lvcreate -y -L 1G -n cachemeta cache /dev/root/cache
#lvconvert -y --type cache-pool --cachemode writeback --chunksize 64k --poolmetadata cache/cachemeta cache/cache
#lvconvert -y --type cache --cachepool cache/cache cache/cachedata

Mbona dogo hivi..?Kupitia majaribio ya vitendo, mwandishi aliweza kugundua kuwa matokeo bora hupatikana ikiwa saizi ya kizuizi cha kache ya LVM inalingana na saizi ya kizuizi nyembamba cha LVM. Zaidi ya hayo, kadiri ukubwa unavyopungua, ndivyo usanidi unavyofanya kazi katika kurekodi bila mpangilio.

64k ndio saizi ya chini ya kizuizi inayoruhusiwa kwa nyembamba ya LVM.

Kuwa makini kuandika..!Ndiyo. Aina hii ya akiba inaahirisha ulandanishi wa uandishi kwa kifaa kilichoakibishwa. Hii ina maana kwamba ikiwa cache itapotea, unaweza kupoteza data kwenye kifaa kilichohifadhiwa. Baadaye, mwandishi atakuambia ni hatua gani, pamoja na NVMe RAID 1, zinaweza kuchukuliwa ili kulipa fidia kwa hatari hii.

Aina hii ya akiba ilichaguliwa kimakusudi ili kufidia utendakazi duni wa uandishi wa nasibu wa RAID 6.

Wacha tuangalie kile tulichonacho:

#lvs -a -o lv_name,lv_size,devices --units B cache
LV LSize Devices
[cache] 68719476736B cache_cdata(0)
[cache_cdata] 68719476736B /dev/root/cache(0)
[cache_cmeta] 1073741824B /dev/root/cache(16384)
cachedata 3298539077632B cachedata_corig(0)
[cachedata_corig] 3298539077632B /dev/data/cache(0)
[lvol0_pmspare] 1073741824B /dev/root/cache(16640)

[cachedata_corig] pekee inapaswa kupatikana kwenye /dev/data/cache. Ikiwa kuna kitu kibaya, basi tumia pvmove.

Unaweza kulemaza kashe ikiwa ni lazima kwa amri moja:

#lvconvert -y --uncache cache/cachedata

Hii inafanywa mtandaoni. LVM itasawazisha tu kashe kwa diski, kuiondoa, na kubadilisha jina la cachedata_corig kurudi kwenye kachedata.

Kuanzisha LVM nyembamba

Wacha tukadirie takriban nafasi ngapi tunayohitaji kwa metadata nyembamba ya LVM:

#thin_metadata_size --block-size=64k --pool-size=6terabytes --max-thins=100000 -u bytes
thin_metadata_size - 3385794560 bytes estimated metadata area size for "--block-size=64kibibytes --pool-size=6terabytes --max-thins=100000"

Zungusha hadi gigabaiti 4: 4294967296B

Zidisha kwa mbili na uongeze 4194304B kwa metadata ya LVM PV: 8594128896B
Wacha tuunde kizigeu tofauti kwenye NVMe RAID 1 ili kuweka metadata nyembamba ya LVM na nakala yao ya chelezo juu yake:

#lvcreate -L 8594128896B --name images root

Kwa nini..?Hapa swali linaweza kutokea: kwa nini uweke metadata nyembamba ya LVM kando ikiwa bado itahifadhiwa kwenye NVMe na itafanya kazi haraka.

Ingawa kasi ni muhimu hapa, ni mbali na sababu kuu. Jambo ni kwamba cache ni hatua ya kushindwa. Kitu kinaweza kutokea kwake, na ikiwa metadata nyembamba ya LVM imehifadhiwa, itasababisha kila kitu kupotea kabisa. Bila metadata kamili, itakuwa karibu haiwezekani kukusanya kiasi nyembamba.

Kwa kuhamisha metadata hadi kwa sauti tofauti isiyo na kache, lakini kwa haraka, tunahakikisha usalama wa metadata iwapo akiba itapotea au kuharibika. Katika kesi hii, uharibifu wote unaosababishwa na upotezaji wa cache utawekwa ndani ya kiasi nyembamba, ambayo itarahisisha utaratibu wa kurejesha kwa amri za ukubwa. Kwa uwezekano mkubwa, uharibifu huu utarejeshwa kwa kutumia kumbukumbu za FS.

Kwa kuongezea, ikiwa picha ya kiasi nyembamba ilichukuliwa hapo awali, na baada ya hapo kashe ilisawazishwa kikamilifu angalau mara moja, basi, kwa sababu ya muundo wa ndani wa LVM nyembamba, uadilifu wa snapshot utahakikishwa katika tukio la upotezaji wa kashe. .

Wacha tuunde VG mpya ambayo itawajibika kwa utoaji mwembamba:

#pvcreate /dev/root/images
#pvcreate /dev/cache/cachedata
#vgcreate images /dev/root/images /dev/cache/cachedata

Wacha tutengeneze bwawa:

#lvcreate -L 274877906944B --poolmetadataspare y --poolmetadatasize 4294967296B --chunksize 64k -Z y -T images/thin-pool
Kwa nini -Z yMbali na kile ambacho hali hii inakusudiwa - kuzuia data kutoka kwa mashine moja ya mtandaoni kuvuja hadi kwa mashine nyingine ya mtandaoni wakati wa kusambaza tena nafasi - sifuri hutumiwa kuongeza kasi ya uandishi wa nasibu katika vizuizi vidogo kuliko 64k. Maandishi yoyote yaliyo chini ya 64k kwa eneo ambalo halijagawiwa hapo awali la ujazo mwembamba yatapangiliwa kingo 64K kwenye akiba. Hii itawawezesha operesheni kufanywa kabisa kupitia cache, kwa kupita kifaa kilichohifadhiwa.

Wacha tuhamishe LV kwa PV zinazolingana:

#pvmove -n images/thin-pool_tdata /dev/root/images /dev/cache/cachedata
#pvmove -n images/lvol0_pmspare /dev/cache/cachedata /dev/root/images
#pvmove -n images/thin-pool_tmeta /dev/cache/cachedata /dev/root/images

Hebu tuangalie:

#lvs -a -o lv_name,lv_size,devices --units B images
LV LSize Devices
[lvol0_pmspare] 4294967296B /dev/root/images(0)
thin-pool 274877906944B thin-pool_tdata(0)
[thin-pool_tdata] 274877906944B /dev/cache/cachedata(0)
[thin-pool_tmeta] 4294967296B /dev/root/images(1024)

Wacha tuunda kiasi nyembamba kwa majaribio:

#lvcreate -V 64G --thin-pool thin-pool --name test images

Tutasakinisha vifurushi vya majaribio na ufuatiliaji:

#apt-get install sysstat fio

Hivi ndivyo unavyoweza kuona tabia ya usanidi wetu wa hifadhi katika muda halisi:

#watch 'lvs --rows --reportformat basic --quiet -ocache_dirty_blocks,cache_settings cache/cachedata && (lvdisplay cache/cachedata | grep Cache) && (sar -p -d 2 1 | grep -E "sd|nvme|DEV|md1|md2|md3|md0" | grep -v Average | sort)'

Hivi ndivyo tunavyoweza kujaribu usanidi wetu:

#fio --loops=1 --size=64G --runtime=4 --filename=/dev/images/test --stonewall --ioengine=libaio --direct=1
--name=4kQD32read --bs=4k --iodepth=32 --rw=randread
--name=8kQD32read --bs=8k --iodepth=32 --rw=randread
--name=16kQD32read --bs=16k --iodepth=32 --rw=randread
--name=32KQD32read --bs=32k --iodepth=32 --rw=randread
--name=64KQD32read --bs=64k --iodepth=32 --rw=randread
--name=128KQD32read --bs=128k --iodepth=32 --rw=randread
--name=256KQD32read --bs=256k --iodepth=32 --rw=randread
--name=512KQD32read --bs=512k --iodepth=32 --rw=randread
--name=4Kread --bs=4k --rw=read
--name=8Kread --bs=8k --rw=read
--name=16Kread --bs=16k --rw=read
--name=32Kread --bs=32k --rw=read
--name=64Kread --bs=64k --rw=read
--name=128Kread --bs=128k --rw=read
--name=256Kread --bs=256k --rw=read
--name=512Kread --bs=512k --rw=read
--name=Seqread --bs=1m --rw=read
--name=Longread --bs=8m --rw=read
--name=Longwrite --bs=8m --rw=write
--name=Seqwrite --bs=1m --rw=write
--name=512Kwrite --bs=512k --rw=write
--name=256write --bs=256k --rw=write
--name=128write --bs=128k --rw=write
--name=64write --bs=64k --rw=write
--name=32write --bs=32k --rw=write
--name=16write --bs=16k --rw=write
--name=8write --bs=8k --rw=write
--name=4write --bs=4k --rw=write
--name=512KQD32write --bs=512k --iodepth=32 --rw=randwrite
--name=256KQD32write --bs=256k --iodepth=32 --rw=randwrite
--name=128KQD32write --bs=128k --iodepth=32 --rw=randwrite
--name=64KQD32write --bs=64k --iodepth=32 --rw=randwrite
--name=32KQD32write --bs=32k --iodepth=32 --rw=randwrite
--name=16KQD32write --bs=16k --iodepth=32 --rw=randwrite
--name=8KQD32write --bs=8k --iodepth=32 --rw=randwrite
--name=4kQD32write --bs=4k --iodepth=32 --rw=randwrite
| grep -E 'read|write|test' | grep -v ioengine

Kwa uangalifu! Rasilimali!Nambari hii itaendesha majaribio 36 tofauti, kila moja ikifanya kazi kwa sekunde 4. Nusu ya majaribio ni ya kurekodi. Unaweza kurekodi mengi kwenye NVMe katika sekunde 4. Hadi gigabytes 3 kwa sekunde. Kwa hivyo, kila majaribio ya uandishi yanaweza kula hadi gigabytes 216 za rasilimali ya SSD kutoka kwako.

Kusoma na kuandika mchanganyiko?Ndiyo. Inaleta maana kuendesha majaribio ya kusoma na kuandika kando. Kwa kuongezea, inaeleweka kuhakikisha kuwa kache zote zimesawazishwa ili maandishi yaliyotengenezwa hapo awali yasiathiri usomaji.

Matokeo yatatofautiana sana wakati wa uzinduzi wa kwanza na unaofuata kadri akiba na sauti nyembamba inavyojazwa, na pia kulingana na ikiwa mfumo uliweza kusawazisha akiba zilizojazwa wakati wa uzinduzi wa mwisho.

Miongoni mwa mambo mengine, ninapendekeza kupima kasi kwa kiasi kilichojaa tayari nyembamba ambayo snapshot ilichukuliwa tu. Mwandishi alipata fursa ya kuona jinsi maandishi ya nasibu yanavyoharakisha kwa kasi mara baada ya kuunda picha ya kwanza, haswa wakati kache bado haijajaa. Hii hutokea kwa sababu ya semantiki za uandishi wa kunakili-kwa-kuandika, upatanishi wa kache na vizuizi vyembamba vya kiasi, na ukweli kwamba uandishi wa nasibu kwa RAID 6 hubadilika kuwa usomaji wa nasibu kutoka kwa RAID 6 ikifuatiwa na uandishi kwa kashe. Katika usanidi wetu, usomaji wa nasibu kutoka kwa RAID 6 ni hadi mara 6 (idadi ya SATA SSD katika safu) kwa kasi zaidi kuliko kuandika. Kwa sababu vitalu vya CoW vinatengwa kwa mlolongo kutoka kwa bwawa nyembamba, kisha kurekodi, kwa sehemu kubwa, pia hugeuka kuwa mlolongo.

Vipengele hivi vyote viwili vinaweza kutumika kwa faida yako.

Cache "madhubuti" snapshots

Ili kupunguza hatari ya kupoteza data katika kesi ya uharibifu/hasara ya kache, mwandishi anapendekeza kuanzisha mazoezi ya kuzungusha vijipicha ili kuhakikisha uadilifu wao katika kesi hii.

Kwanza, kwa sababu metadata ya ujazo mwembamba hukaa kwenye kifaa ambacho hakijahifadhiwa, metadata itakuwa thabiti na hasara zinazowezekana zitatengwa ndani ya vizuizi vya data.

Mzunguko ufuatao wa kuzungusha muhtasari unahakikisha uadilifu wa data iliyo ndani ya vijisehemu iwapo kache itapotea:

  1. Kwa kila sauti nyembamba yenye jina <name>, tengeneza muhtasari kwa jina <name>.cached
  2. Wacha tuweke kizingiti cha uhamiaji kwa thamani ya juu inayofaa: #lvchange --quiet --cachesettings "migration_threshold=16384" cache/cachedata
  3. Kwenye kitanzi tunaangalia idadi ya vizuizi vichafu kwenye kashe: #lvs --rows --reportformat basic --quiet -ocache_dirty_blocks cache/cachedata | awk '{print $2}' mpaka tupate sifuri. Ikiwa sifuri haipo kwa muda mrefu sana, inaweza kuundwa kwa kubadili cache kwa muda kwa hali ya kuandika. Walakini, kwa kuzingatia sifa za kasi za safu zetu za SATA na NVMe SSD, pamoja na rasilimali yao ya TBW, utaweza kupata wakati huo haraka bila kubadilisha hali ya kache, au vifaa vyako vitakula kabisa rasilimali yake yote ndani. siku chache. Kwa sababu ya mapungufu ya rasilimali, mfumo, kimsingi, hauwezi kuwa chini ya 100% ya mzigo wa kuandika wakati wote. SSD zetu za NVMe chini ya mzigo wa uandishi wa 100% zitamaliza rasilimali kabisa Siku za 3-4. SSD za SATA zitadumu mara mbili tu. Kwa hivyo, tutafikiria kuwa mzigo mwingi huenda kwa kusoma, na tunayo mlipuko wa muda mfupi wa shughuli za juu sana pamoja na mzigo mdogo kwa wastani wa uandishi.
  4. Mara tu tulipopata (au kutengeneza) sufuri, tunabadilisha jina la <name>.cached hadi <name>.committed. <name>.committed ya zamani imefutwa.
  5. Kwa hiari, ikiwa kache imejaa 100%, inaweza kuundwa upya na hati, na hivyo kuifuta. Kwa kache iliyo na nusu tupu, mfumo hufanya kazi haraka sana wakati wa kuandika.
  6. Weka kizingiti cha uhamiaji hadi sifuri: #lvchange --quiet --cachesettings "migration_threshold=0" cache/cachedata Hii itazuia kache kwa muda kusawazisha kwa midia kuu.
  7. Tunasubiri hadi mabadiliko mengi yajikusanye kwenye kashe #lvs --rows --reportformat basic --quiet -ocache_dirty_blocks cache/cachedata | awk '{print $2}' au kipima saa kitazimwa.
  8. Tunarudia tena.

Kwa nini ugumu wa kizingiti cha uhamiaji ...?Jambo ni kwamba katika mazoezi halisi, kurekodi "nasibu" kwa kweli sio nasibu kabisa. Ikiwa tuliandika kitu kwa sekta ya kilobytes 4 kwa ukubwa, kuna uwezekano mkubwa kwamba katika dakika chache zijazo rekodi itafanywa kwa moja au moja ya sekta za jirani (+- 32K).

Kwa kuweka kizingiti cha uhamiaji hadi sifuri, tunaahirisha maingiliano ya kuandika kwenye SATA SSD na kujumlisha mabadiliko kadhaa kwenye kizuizi kimoja cha 64K kwenye kashe. Hii inaokoa kwa kiasi kikubwa rasilimali ya SATA SSD.

Kanuni iko wapi..?Kwa bahati mbaya, mwandishi anajiona hana uwezo wa kutosha katika ukuzaji wa maandishi ya bash kwa sababu amejifundisha 100% na anafanya maendeleo yanayoendeshwa na "google", kwa hivyo anaamini kuwa nambari mbaya inayotoka mikononi mwake haipaswi kutumiwa na mtu yeyote. mwingine.

Nadhani wataalamu katika uwanja huu wataweza kuonyesha kwa uhuru mantiki yote iliyoelezewa hapo juu, ikiwa ni lazima, na, labda, hata kuiunda kwa uzuri kama huduma ya mfumo, kama mwandishi alijaribu kufanya.

Mpango kama huo rahisi wa mzunguko wa snapshot utaturuhusu sio tu kuwa na snapshot moja iliyosawazishwa kikamilifu kwenye SATA SSD, lakini pia itaturuhusu, kwa kutumia matumizi ya thin_delta, kujua ni vizuizi gani vilibadilishwa baada ya uumbaji wake, na hivyo kubinafsisha uharibifu kwenye juzuu kuu, kurahisisha sana ahueni .

TRIM/DISCARD katika libvirt/KVM

Kwa sababu hifadhi ya data itatumika kwa KVM inayoendesha libvirt, basi itakuwa ni wazo nzuri kufundisha VM zetu sio tu kuchukua nafasi ya bure, lakini pia kuweka huru kile kisichohitajika tena.

Hii inafanywa kwa kuiga usaidizi wa TRIM/DISCARD kwenye diski pepe. Ili kufanya hivyo, unahitaji kubadilisha aina ya mtawala kwa virtio-scsi na uhariri xml.

#virsh edit vmname
<disk type='block' device='disk'>
<driver name='qemu' type='raw' cache='writethrough' io='threads' discard='unmap'/>
<source dev='/dev/images/vmname'/>
<backingStore/>
<target dev='sda' bus='scsi'/>
<alias name='scsi0-0-0-0'/>
<address type='drive' controller='0' bus='0' target='0' unit='0'/>
</disk>

<controller type='scsi' index='0' model='virtio-scsi'>
<alias name='scsi0'/>
<address type='pci' domain='0x0000' bus='0x04' slot='0x00' function='0x0'/>
</controller>

VITUKO kama hivyo kutoka kwa Mfumo wa Uendeshaji wa wageni huchakatwa kwa usahihi na LVM, na vizuizi vinaachiliwa kwa usahihi kwenye kashe na kwenye dimbwi nyembamba. Kwa upande wetu, hii hutokea hasa kwa namna ya kuchelewa, wakati wa kufuta snapshot inayofuata.

Hifadhi nakala ya BTRFS

Tumia maandishi yaliyotengenezwa tayari na uliokithiri tahadhari na kwa hatari ya mtu mwenyewe. Mwandishi aliandika msimbo huu mwenyewe na kwa ajili yake mwenyewe pekee. Nina hakika kuwa watumiaji wengi wenye uzoefu wa Linux wana zana zinazofanana, na hakuna haja ya kunakili za mtu mwingine.

Wacha tuunde sauti kwenye kifaa chelezo:

#lvcreate -L 256G --name backup backup

Wacha tuifomati katika BTRFS:

#mkfs.btrfs /dev/backup/backup

Wacha tuunda sehemu za mlima na kuweka vifungu vya mizizi ya mfumo wa faili:

#mkdir /backup
#mkdir /backup/btrfs
#mkdir /backup/btrfs/root
#mkdir /backup/btrfs/back
#ln -s /boot /backup/btrfs
# cat >>/etc/fstab << EOF

/dev/mapper/root-root /backup/btrfs/root btrfs defaults,space_cache,noatime,nodiratime 0 2
/dev/mapper/backup-backup /backup/btrfs/back btrfs defaults,space_cache,noatime,nodiratime 0 2
EOF
#mount -a
#update-initramfs -u
#update-grub

Wacha tuunde saraka za chelezo:

#mkdir /backup/btrfs/back/remote
#mkdir /backup/btrfs/back/remote/root
#mkdir /backup/btrfs/back/remote/boot

Wacha tuunde saraka kwa hati za chelezo:

#mkdir /root/btrfs-backup

Wacha tunakili hati:

Nambari nyingi za kutisha za bash. Tumia kwa hatari yako mwenyewe. Usiandike barua za hasira kwa mwandishi ...#cat >/root/btrfs-backup/btrfs-backup.sh << EOF
#!/bin/bash
PATH="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"

SCRIPT_FILE="$(realpath $0)"
SCRIPT_DIR="$(dirname $SCRIPT_FILE)"
SCRIPT_NAME="$(basename -s .sh $SCRIPT_FILE)"

LOCK_FILE="/dev/shm/$SCRIPT_NAME.lock"
DATE_PREFIX='%Y-%m-%d'
DATE_FORMAT=$DATE_PREFIX'-%H-%M-%S'
DATE_REGEX='[0-9][0-9][0-9][0-9]-[0-9][0-9]-[0-9][0-9]-[0-9][0-9]-[0-9][0-9]-[0-9][0-9]'
BASE_SUFFIX=".@base"
PEND_SUFFIX=".@pend"
SNAP_SUFFIX=".@snap"
MOUNTS="/backup/btrfs/"
BACKUPS="/backup/btrfs/back/remote/"

function terminate ()
{
echo "$1" >&2
exit 1
}

function wait_lock()
{
flock 98
}

function wait_lock_or_terminate()
{
echo "Wating for lock..."
wait_lock || terminate "Failed to get lock. Exiting..."
echo "Got lock..."
}

function suffix()
{
FORMATTED_DATE=$(date +"$DATE_FORMAT")
echo "$SNAP_SUFFIX.$FORMATTED_DATE"
}

function filter()
{
FORMATTED_DATE=$(date --date="$1" +"$DATE_PREFIX")
echo "$SNAP_SUFFIX.$FORMATTED_DATE"
}

function backup()
{
SOURCE_PATH="$MOUNTS$1"
TARGET_PATH="$BACKUPS$1"
SOURCE_BASE_PATH="$MOUNTS$1$BASE_SUFFIX"
TARGET_BASE_PATH="$BACKUPS$1$BASE_SUFFIX"
TARGET_BASE_DIR="$(dirname $TARGET_BASE_PATH)"
SOURCE_PEND_PATH="$MOUNTS$1$PEND_SUFFIX"
TARGET_PEND_PATH="$BACKUPS$1$PEND_SUFFIX"
if [ -d "$SOURCE_BASE_PATH" ] then
echo "$SOURCE_BASE_PATH found"
else
echo "$SOURCE_BASE_PATH File not found creating snapshot of $SOURCE_PATH to $SOURCE_BASE_PATH"
btrfs subvolume snapshot -r $SOURCE_PATH $SOURCE_BASE_PATH
sync
if [ -d "$TARGET_BASE_PATH" ] then
echo "$TARGET_BASE_PATH found out of sync with source... removing..."
btrfs subvolume delete -c $TARGET_BASE_PATH
sync
fi
fi
if [ -d "$TARGET_BASE_PATH" ] then
echo "$TARGET_BASE_PATH found"
else
echo "$TARGET_BASE_PATH not found. Synching to $TARGET_BASE_DIR"
btrfs send $SOURCE_BASE_PATH | btrfs receive $TARGET_BASE_DIR
sync
fi
if [ -d "$SOURCE_PEND_PATH" ] then
echo "$SOURCE_PEND_PATH found removing..."
btrfs subvolume delete -c $SOURCE_PEND_PATH
sync
fi
btrfs subvolume snapshot -r $SOURCE_PATH $SOURCE_PEND_PATH
sync
if [ -d "$TARGET_PEND_PATH" ] then
echo "$TARGET_PEND_PATH found removing..."
btrfs subvolume delete -c $TARGET_PEND_PATH
sync
fi
echo "Sending $SOURCE_PEND_PATH to $TARGET_PEND_PATH"
btrfs send -p $SOURCE_BASE_PATH $SOURCE_PEND_PATH | btrfs receive $TARGET_BASE_DIR
sync
TARGET_DATE_SUFFIX=$(suffix)
btrfs subvolume snapshot -r $TARGET_PEND_PATH "$TARGET_PATH$TARGET_DATE_SUFFIX"
sync
btrfs subvolume delete -c $SOURCE_BASE_PATH
sync
btrfs subvolume delete -c $TARGET_BASE_PATH
sync
mv $SOURCE_PEND_PATH $SOURCE_BASE_PATH
mv $TARGET_PEND_PATH $TARGET_BASE_PATH
sync
}

function list()
{
LIST_TARGET_BASE_PATH="$BACKUPS$1$BASE_SUFFIX"
LIST_TARGET_BASE_DIR="$(dirname $LIST_TARGET_BASE_PATH)"
LIST_TARGET_BASE_NAME="$(basename -s .$BASE_SUFFIX $LIST_TARGET_BASE_PATH)"
find "$LIST_TARGET_BASE_DIR" -maxdepth 1 -mindepth 1 -type d -printf "%fn" | grep "${LIST_TARGET_BASE_NAME/$BASE_SUFFIX/$SNAP_SUFFIX}.$DATE_REGEX"
}

function remove()
{
REMOVE_TARGET_BASE_PATH="$BACKUPS$1$BASE_SUFFIX"
REMOVE_TARGET_BASE_DIR="$(dirname $REMOVE_TARGET_BASE_PATH)"
btrfs subvolume delete -c $REMOVE_TARGET_BASE_DIR/$2
sync
}

function removeall()
{
DATE_OFFSET="$2"
FILTER="$(filter "$DATE_OFFSET")"
while read -r SNAPSHOT ; do
remove "$1" "$SNAPSHOT"
done < <(list "$1" | grep "$FILTER")

}

(
COMMAND="$1"
shift

case "$COMMAND" in
"--help")
echo "Help"
;;
"suffix")
suffix
;;
"filter")
filter "$1"
;;
"backup")
wait_lock_or_terminate
backup "$1"
;;
"list")
list "$1"
;;
"remove")
wait_lock_or_terminate
remove "$1" "$2"
;;
"removeall")
wait_lock_or_terminate
removeall "$1" "$2"
;;
*)
echo "None.."
;;
esac
) 98>$LOCK_FILE

EOF

Inafanya nini hata..?Ina seti ya amri rahisi za kuunda vijipicha vya BTRFS na kunakili kwa FS nyingine kwa kutumia kutuma/kupokea kwa BTRFS.

Uzinduzi wa kwanza unaweza kuwa mrefu, kwa sababu ... Mwanzoni, data zote zitanakiliwa. Uzinduzi zaidi utakuwa wa haraka sana, kwa sababu ... Mabadiliko pekee ndiyo yatakayonakiliwa.

Hati nyingine ambayo tutaweka kwenye cron:

Nambari zingine zaidi za bash#cat >/root/btrfs-backup/cron-daily.sh << EOF
#!/bin/bash
PATH="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"

SCRIPT_FILE="$(realpath $0)"
SCRIPT_DIR="$(dirname $SCRIPT_FILE)"
SCRIPT_NAME="$(basename -s .sh $SCRIPT_FILE)"

BACKUP_SCRIPT="$SCRIPT_DIR/btrfs-backup.sh"
RETENTION="-60 day"
$BACKUP_SCRIPT backup root/@
$BACKUP_SCRIPT removeall root/@ "$RETENTION"
$BACKUP_SCRIPT backup root/@home
$BACKUP_SCRIPT removeall root/@home "$RETENTION"
$BACKUP_SCRIPT backup boot/
$BACKUP_SCRIPT removeall boot/ "$RETENTION"
EOF

Inafanya nini..?Huunda na kusawazisha muhtasari wa nyongeza wa juzuu za BTRFS zilizoorodheshwa kwenye chelezo FS. Baada ya hayo, inafuta picha zote zilizoundwa siku 60 zilizopita. Baada ya kuzinduliwa, vijipicha vya tarehe vya juzuu zilizoorodheshwa vitaonekana kwenye saraka ndogo /backup/btrfs/back/remote/.

Wacha tupe haki za utekelezaji wa nambari:

#chmod +x /root/btrfs-backup/cron-daily.sh
#chmod +x /root/btrfs-backup/btrfs-backup.sh

Wacha tuiangalie na kuiweka kwenye cron:

#/usr/bin/nice -n 19 /usr/bin/ionice -c 3 /root/btrfs-backup/cron-daily.sh 2>&1 | /usr/bin/logger -t btrfs-backup
#cat /var/log/syslog | grep btrfs-backup
#crontab -e
0 2 * * * /usr/bin/nice -n 19 /usr/bin/ionice -c 3 /root/btrfs-backup/cron-daily.sh 2>&1 | /usr/bin/logger -t btrfs-backup

Chelezo nyembamba ya LVM

Wacha tuunda dimbwi nyembamba kwenye kifaa chelezo:

#lvcreate -L 274877906944B --poolmetadataspare y --poolmetadatasize 4294967296B --chunksize 64k -Z y -T backup/thin-pool

Wacha tusakinishe ddrescue, kwa sababu ... maandishi yatatumia zana hii:

#apt-get install gddrescue

Wacha tuunde saraka kwa maandishi:

#mkdir /root/lvm-thin-backup

Wacha tunakili maandishi:

Mshtuko mwingi ndani ...#cat >/root/lvm-thin-backup/lvm-thin-backup.sh << EOF
#!/bin/bash
PATH="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"

SCRIPT_FILE="$(realpath $0)"
SCRIPT_DIR="$(dirname $SCRIPT_FILE)"
SCRIPT_NAME="$(basename -s .sh $SCRIPT_FILE)"

LOCK_FILE="/dev/shm/$SCRIPT_NAME.lock"
DATE_PREFIX='%Y-%m-%d'
DATE_FORMAT=$DATE_PREFIX'-%H-%M-%S'
DATE_REGEX='[0-9][0-9][0-9][0-9]-[0-9][0-9]-[0-9][0-9]-[0-9][0-9]-[0-9][0-9]-[0-9][0-9]'
BASE_SUFFIX=".base"
PEND_SUFFIX=".pend"
SNAP_SUFFIX=".snap"
BACKUPS="backup"
BACKUPS_POOL="thin-pool"

export LVM_SUPPRESS_FD_WARNINGS=1

function terminate ()
{
echo "$1" >&2
exit 1
}

function wait_lock()
{
flock 98
}

function wait_lock_or_terminate()
{
echo "Wating for lock..."
wait_lock || terminate "Failed to get lock. Exiting..."
echo "Got lock..."
}

function suffix()
{
FORMATTED_DATE=$(date +"$DATE_FORMAT")
echo "$SNAP_SUFFIX.$FORMATTED_DATE"
}

function filter()
{
FORMATTED_DATE=$(date --date="$1" +"$DATE_PREFIX")
echo "$SNAP_SUFFIX.$FORMATTED_DATE"
}

function read_thin_id {
lvs --rows --reportformat basic --quiet -othin_id "$1/$2" | awk '{print $2}'
}

function read_pool_lv {
lvs --rows --reportformat basic --quiet -opool_lv "$1/$2" | awk '{print $2}'
}

function read_lv_dm_path {
lvs --rows --reportformat basic --quiet -olv_dm_path "$1/$2" | awk '{print $2}'
}

function read_lv_active {
lvs --rows --reportformat basic --quiet -olv_active "$1/$2" | awk '{print $2}'
}

function read_lv_chunk_size {
lvs --rows --reportformat basic --quiet --units b --nosuffix -ochunk_size "$1/$2" | awk '{print $2}'
}

function read_lv_size {
lvs --rows --reportformat basic --quiet --units b --nosuffix -olv_size "$1/$2" | awk '{print $2}'
}

function activate_volume {
lvchange -ay -Ky "$1/$2"
}

function deactivate_volume {
lvchange -an "$1/$2"
}

function read_thin_metadata_snap {
dmsetup status "$1" | awk '{print $7}'
}

function thindiff()
{
DIFF_VG="$1"
DIFF_SOURCE="$2"
DIFF_TARGET="$3"
DIFF_SOURCE_POOL=$(read_pool_lv $DIFF_VG $DIFF_SOURCE)
DIFF_TARGET_POOL=$(read_pool_lv $DIFF_VG $DIFF_TARGET)

if [ "$DIFF_SOURCE_POOL" == "" ] then
(>&2 echo "Source LV is not thin.")
exit 1
fi

if [ "$DIFF_TARGET_POOL" == "" ] then
(>&2 echo "Target LV is not thin.")
exit 1
fi

if [ "$DIFF_SOURCE_POOL" != "$DIFF_TARGET_POOL" ] then
(>&2 echo "Source and target LVs belong to different thin pools.")
exit 1
fi

DIFF_POOL_PATH=$(read_lv_dm_path $DIFF_VG $DIFF_SOURCE_POOL)
DIFF_SOURCE_ID=$(read_thin_id $DIFF_VG $DIFF_SOURCE)
DIFF_TARGET_ID=$(read_thin_id $DIFF_VG $DIFF_TARGET)
DIFF_POOL_PATH_TPOOL="$DIFF_POOL_PATH-tpool"
DIFF_POOL_PATH_TMETA="$DIFF_POOL_PATH"_tmeta
DIFF_POOL_METADATA_SNAP=$(read_thin_metadata_snap $DIFF_POOL_PATH_TPOOL)

if [ "$DIFF_POOL_METADATA_SNAP" != "-" ] then
(>&2 echo "Thin pool metadata snapshot already exist. Assuming stale one. Will release metadata snapshot in 5 seconds.")
sleep 5
dmsetup message $DIFF_POOL_PATH_TPOOL 0 release_metadata_snap
fi

dmsetup message $DIFF_POOL_PATH_TPOOL 0 reserve_metadata_snap
DIFF_POOL_METADATA_SNAP=$(read_thin_metadata_snap $DIFF_POOL_PATH_TPOOL)

if [ "$DIFF_POOL_METADATA_SNAP" == "-" ] then
(>&2 echo "Failed to create thin pool metadata snapshot.")
exit 1
fi

#We keep output in variable because metadata snapshot need to be released early.
DIFF_DATA=$(thin_delta -m$DIFF_POOL_METADATA_SNAP --snap1 $DIFF_SOURCE_ID --snap2 $DIFF_TARGET_ID $DIFF_POOL_PATH_TMETA)

dmsetup message $DIFF_POOL_PATH_TPOOL 0 release_metadata_snap

echo $"$DIFF_DATA" | grep -E 'different|left_only|right_only' | sed 's/</"/g' | sed 's/ /"/g' | awk -F'"' '{print $6 "t" $8 "t" $11}' | sed 's/different/copy/g' | sed 's/left_only/copy/g' | sed 's/right_only/discard/g'

}

function thinsync()
{
SYNC_VG="$1"
SYNC_PEND="$2"
SYNC_BASE="$3"
SYNC_TARGET="$4"
SYNC_PEND_POOL=$(read_pool_lv $SYNC_VG $SYNC_PEND)
SYNC_BLOCK_SIZE=$(read_lv_chunk_size $SYNC_VG $SYNC_PEND_POOL)
SYNC_PEND_PATH=$(read_lv_dm_path $SYNC_VG $SYNC_PEND)

activate_volume $SYNC_VG $SYNC_PEND

while read -r SYNC_ACTION SYNC_OFFSET SYNC_LENGTH ; do
SYNC_OFFSET_BYTES=$((SYNC_OFFSET * SYNC_BLOCK_SIZE))
SYNC_LENGTH_BYTES=$((SYNC_LENGTH * SYNC_BLOCK_SIZE))
if [ "$SYNC_ACTION" == "copy" ] then
ddrescue --quiet --force --input-position=$SYNC_OFFSET_BYTES --output-position=$SYNC_OFFSET_BYTES --size=$SYNC_LENGTH_BYTES "$SYNC_PEND_PATH" "$SYNC_TARGET"
fi

if [ "$SYNC_ACTION" == "discard" ] then
blkdiscard -o $SYNC_OFFSET_BYTES -l $SYNC_LENGTH_BYTES "$SYNC_TARGET"
fi
done < <(thindiff "$SYNC_VG" "$SYNC_PEND" "$SYNC_BASE")
}

function discard_volume()
{
DISCARD_VG="$1"
DISCARD_LV="$2"
DISCARD_LV_PATH=$(read_lv_dm_path "$DISCARD_VG" "$DISCARD_LV")
if [ "$DISCARD_LV_PATH" != "" ] then
echo "$DISCARD_LV_PATH found"
else
echo "$DISCARD_LV not found in $DISCARD_VG"
exit 1
fi
DISCARD_LV_POOL=$(read_pool_lv $DISCARD_VG $DISCARD_LV)
DISCARD_LV_SIZE=$(read_lv_size "$DISCARD_VG" "$DISCARD_LV")
lvremove -y --quiet "$DISCARD_LV_PATH" || exit 1
lvcreate --thin-pool "$DISCARD_LV_POOL" -V "$DISCARD_LV_SIZE"B --name "$DISCARD_LV" "$DISCARD_VG" || exit 1
}

function backup()
{
SOURCE_VG="$1"
SOURCE_LV="$2"
TARGET_VG="$BACKUPS"
TARGET_LV="$SOURCE_VG-$SOURCE_LV"
SOURCE_BASE_LV="$SOURCE_LV$BASE_SUFFIX"
TARGET_BASE_LV="$TARGET_LV$BASE_SUFFIX"
SOURCE_PEND_LV="$SOURCE_LV$PEND_SUFFIX"
TARGET_PEND_LV="$TARGET_LV$PEND_SUFFIX"
SOURCE_BASE_LV_PATH=$(read_lv_dm_path "$SOURCE_VG" "$SOURCE_BASE_LV")
SOURCE_PEND_LV_PATH=$(read_lv_dm_path "$SOURCE_VG" "$SOURCE_PEND_LV")
TARGET_BASE_LV_PATH=$(read_lv_dm_path "$TARGET_VG" "$TARGET_BASE_LV")
TARGET_PEND_LV_PATH=$(read_lv_dm_path "$TARGET_VG" "$TARGET_PEND_LV")

if [ "$SOURCE_BASE_LV_PATH" != "" ] then
echo "$SOURCE_BASE_LV_PATH found"
else
echo "Source base not found creating snapshot of $SOURCE_VG/$SOURCE_LV to $SOURCE_VG/$SOURCE_BASE_LV"
lvcreate --quiet --snapshot --name "$SOURCE_BASE_LV" "$SOURCE_VG/$SOURCE_LV" || exit 1
SOURCE_BASE_LV_PATH=$(read_lv_dm_path "$SOURCE_VG" "$SOURCE_BASE_LV")
activate_volume "$SOURCE_VG" "$SOURCE_BASE_LV"
echo "Discarding $SOURCE_BASE_LV_PATH as we need to bootstrap."
SOURCE_BASE_POOL=$(read_pool_lv $SOURCE_VG $SOURCE_BASE_LV)
SOURCE_BASE_CHUNK_SIZE=$(read_lv_chunk_size $SOURCE_VG $SOURCE_BASE_POOL)
discard_volume "$SOURCE_VG" "$SOURCE_BASE_LV"
sync
if [ "$TARGET_BASE_LV_PATH" != "" ] then
echo "$TARGET_BASE_LV_PATH found out of sync with source... removing..."
lvremove -y --quiet $TARGET_BASE_LV_PATH || exit 1
TARGET_BASE_LV_PATH=$(read_lv_dm_path "$TARGET_VG" "$TARGET_BASE_LV")
sync
fi
fi
SOURCE_BASE_SIZE=$(read_lv_size "$SOURCE_VG" "$SOURCE_BASE_LV")
if [ "$TARGET_BASE_LV_PATH" != "" ] then
echo "$TARGET_BASE_LV_PATH found"
else
echo "$TARGET_VG/$TARGET_LV not found. Creating empty volume."
lvcreate --thin-pool "$BACKUPS_POOL" -V "$SOURCE_BASE_SIZE"B --name "$TARGET_BASE_LV" "$TARGET_VG" || exit 1
echo "Have to rebootstrap. Discarding source at $SOURCE_BASE_LV_PATH"
activate_volume "$SOURCE_VG" "$SOURCE_BASE_LV"
SOURCE_BASE_POOL=$(read_pool_lv $SOURCE_VG $SOURCE_BASE_LV)
SOURCE_BASE_CHUNK_SIZE=$(read_lv_chunk_size $SOURCE_VG $SOURCE_BASE_POOL)
discard_volume "$SOURCE_VG" "$SOURCE_BASE_LV"
TARGET_BASE_POOL=$(read_pool_lv $TARGET_VG $TARGET_BASE_LV)
TARGET_BASE_CHUNK_SIZE=$(read_lv_chunk_size $TARGET_VG $TARGET_BASE_POOL)
TARGET_BASE_LV_PATH=$(read_lv_dm_path "$TARGET_VG" "$TARGET_BASE_LV")
echo "Discarding target at $TARGET_BASE_LV_PATH"
discard_volume "$TARGET_VG" "$TARGET_BASE_LV"
sync
fi
if [ "$SOURCE_PEND_LV_PATH" != "" ] then
echo "$SOURCE_PEND_LV_PATH found removing..."
lvremove -y --quiet "$SOURCE_PEND_LV_PATH" || exit 1
sync
fi
lvcreate --quiet --snapshot --name "$SOURCE_PEND_LV" "$SOURCE_VG/$SOURCE_LV" || exit 1
SOURCE_PEND_LV_PATH=$(read_lv_dm_path "$SOURCE_VG" "$SOURCE_PEND_LV")
sync
if [ "$TARGET_PEND_LV_PATH" != "" ] then
echo "$TARGET_PEND_LV_PATH found removing..."
lvremove -y --quiet $TARGET_PEND_LV_PATH
sync
fi
lvcreate --quiet --snapshot --name "$TARGET_PEND_LV" "$TARGET_VG/$TARGET_BASE_LV" || exit 1
TARGET_PEND_LV_PATH=$(read_lv_dm_path "$TARGET_VG" "$TARGET_PEND_LV")
SOURCE_PEND_LV_SIZE=$(read_lv_size "$SOURCE_VG" "$SOURCE_PEND_LV")
lvresize -L "$SOURCE_PEND_LV_SIZE"B "$TARGET_PEND_LV_PATH"
activate_volume "$TARGET_VG" "$TARGET_PEND_LV"
echo "Synching $SOURCE_PEND_LV_PATH to $TARGET_PEND_LV_PATH"
thinsync "$SOURCE_VG" "$SOURCE_PEND_LV" "$SOURCE_BASE_LV" "$TARGET_PEND_LV_PATH" || exit 1
sync

TARGET_DATE_SUFFIX=$(suffix)
lvcreate --quiet --snapshot --name "$TARGET_LV$TARGET_DATE_SUFFIX" "$TARGET_VG/$TARGET_PEND_LV" || exit 1
sync
lvremove --quiet -y "$SOURCE_BASE_LV_PATH" || exit 1
sync
lvremove --quiet -y "$TARGET_BASE_LV_PATH" || exit 1
sync
lvrename -y "$SOURCE_VG/$SOURCE_PEND_LV" "$SOURCE_BASE_LV" || exit 1
lvrename -y "$TARGET_VG/$TARGET_PEND_LV" "$TARGET_BASE_LV" || exit 1
sync
deactivate_volume "$TARGET_VG" "$TARGET_BASE_LV"
deactivate_volume "$SOURCE_VG" "$SOURCE_BASE_LV"
}

function verify()
{
SOURCE_VG="$1"
SOURCE_LV="$2"
TARGET_VG="$BACKUPS"
TARGET_LV="$SOURCE_VG-$SOURCE_LV"
SOURCE_BASE_LV="$SOURCE_LV$BASE_SUFFIX"
TARGET_BASE_LV="$TARGET_LV$BASE_SUFFIX"
TARGET_BASE_LV_PATH=$(read_lv_dm_path "$TARGET_VG" "$TARGET_BASE_LV")
SOURCE_BASE_LV_PATH=$(read_lv_dm_path "$SOURCE_VG" "$SOURCE_BASE_LV")

if [ "$SOURCE_BASE_LV_PATH" != "" ] then
echo "$SOURCE_BASE_LV_PATH found"
else
echo "$SOURCE_BASE_LV_PATH not found"
exit 1
fi
if [ "$TARGET_BASE_LV_PATH" != "" ] then
echo "$TARGET_BASE_LV_PATH found"
else
echo "$TARGET_BASE_LV_PATH not found"
exit 1
fi
activate_volume "$TARGET_VG" "$TARGET_BASE_LV"
activate_volume "$SOURCE_VG" "$SOURCE_BASE_LV"
echo Comparing "$SOURCE_BASE_LV_PATH" with "$TARGET_BASE_LV_PATH"
cmp "$SOURCE_BASE_LV_PATH" "$TARGET_BASE_LV_PATH"
echo Done...
deactivate_volume "$TARGET_VG" "$TARGET_BASE_LV"
deactivate_volume "$SOURCE_VG" "$SOURCE_BASE_LV"
}

function resync()
{
SOURCE_VG="$1"
SOURCE_LV="$2"
TARGET_VG="$BACKUPS"
TARGET_LV="$SOURCE_VG-$SOURCE_LV"
SOURCE_BASE_LV="$SOURCE_LV$BASE_SUFFIX"
TARGET_BASE_LV="$TARGET_LV$BASE_SUFFIX"
TARGET_BASE_LV_PATH=$(read_lv_dm_path "$TARGET_VG" "$TARGET_BASE_LV")
SOURCE_BASE_LV_PATH=$(read_lv_dm_path "$SOURCE_VG" "$SOURCE_BASE_LV")

if [ "$SOURCE_BASE_LV_PATH" != "" ] then
echo "$SOURCE_BASE_LV_PATH found"
else
echo "$SOURCE_BASE_LV_PATH not found"
exit 1
fi
if [ "$TARGET_BASE_LV_PATH" != "" ] then
echo "$TARGET_BASE_LV_PATH found"
else
echo "$TARGET_BASE_LV_PATH not found"
exit 1
fi
activate_volume "$TARGET_VG" "$TARGET_BASE_LV"
activate_volume "$SOURCE_VG" "$SOURCE_BASE_LV"
SOURCE_BASE_POOL=$(read_pool_lv $SOURCE_VG $SOURCE_BASE_LV)
SYNC_BLOCK_SIZE=$(read_lv_chunk_size $SOURCE_VG $SOURCE_BASE_POOL)

echo Syncronizing "$SOURCE_BASE_LV_PATH" to "$TARGET_BASE_LV_PATH"

CMP_OFFSET=0
while [[ "$CMP_OFFSET" != "" ]] ; do
CMP_MISMATCH=$(cmp -i "$CMP_OFFSET" "$SOURCE_BASE_LV_PATH" "$TARGET_BASE_LV_PATH" | grep differ | awk '{print $5}' | sed 's/,//g' )
if [[ "$CMP_MISMATCH" != "" ]] ; then
CMP_OFFSET=$(( CMP_MISMATCH + CMP_OFFSET ))
SYNC_OFFSET_BYTES=$(( ( CMP_OFFSET / SYNC_BLOCK_SIZE ) * SYNC_BLOCK_SIZE ))
SYNC_LENGTH_BYTES=$(( SYNC_BLOCK_SIZE ))
echo "Synching $SYNC_LENGTH_BYTES bytes at $SYNC_OFFSET_BYTES from $SOURCE_BASE_LV_PATH to $TARGET_BASE_LV_PATH"
ddrescue --quiet --force --input-position=$SYNC_OFFSET_BYTES --output-position=$SYNC_OFFSET_BYTES --size=$SYNC_LENGTH_BYTES "$SOURCE_BASE_LV_PATH" "$TARGET_BASE_LV_PATH"
else
CMP_OFFSET=""
fi
done
echo Done...
deactivate_volume "$TARGET_VG" "$TARGET_BASE_LV"
deactivate_volume "$SOURCE_VG" "$SOURCE_BASE_LV"
}

function list()
{
LIST_SOURCE_VG="$1"
LIST_SOURCE_LV="$2"
LIST_TARGET_VG="$BACKUPS"
LIST_TARGET_LV="$LIST_SOURCE_VG-$LIST_SOURCE_LV"
LIST_TARGET_BASE_LV="$LIST_TARGET_LV$SNAP_SUFFIX"
lvs -olv_name | grep "$LIST_TARGET_BASE_LV.$DATE_REGEX"
}

function remove()
{
REMOVE_TARGET_VG="$BACKUPS"
REMOVE_TARGET_LV="$1"
lvremove -y "$REMOVE_TARGET_VG/$REMOVE_TARGET_LV"
sync
}

function removeall()
{
DATE_OFFSET="$3"
FILTER="$(filter "$DATE_OFFSET")"
while read -r SNAPSHOT ; do
remove "$SNAPSHOT"
done < <(list "$1" "$2" | grep "$FILTER")

}

(
COMMAND="$1"
shift

case "$COMMAND" in
"--help")
echo "Help"
;;
"suffix")
suffix
;;
"filter")
filter "$1"
;;
"backup")
wait_lock_or_terminate
backup "$1" "$2"
;;
"list")
list "$1" "$2"
;;
"thindiff")
thindiff "$1" "$2" "$3"
;;
"thinsync")
thinsync "$1" "$2" "$3" "$4"
;;
"verify")
wait_lock_or_terminate
verify "$1" "$2"
;;
"resync")
wait_lock_or_terminate
resync "$1" "$2"
;;
"remove")
wait_lock_or_terminate
remove "$1"
;;
"removeall")
wait_lock_or_terminate
removeall "$1" "$2" "$3"
;;
*)
echo "None.."
;;
esac
) 98>$LOCK_FILE

EOF

Inafanya nini...?Ina seti ya amri za kuchezea vijipicha vyembamba na kusawazisha tofauti kati ya vijipicha viwili vyembamba vilivyopokelewa kupitia thin_delta hadi kifaa kingine cha kuzuia kwa kutumia ddrescue na blkdiscard.

Hati nyingine ambayo tutaweka kwenye cron:

Bash kidogo zaidi#cat >/root/lvm-thin-backup/cron-daily.sh << EOF
#!/bin/bash
PATH="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"

SCRIPT_FILE="$(realpath $0)"
SCRIPT_DIR="$(dirname $SCRIPT_FILE)"
SCRIPT_NAME="$(basename -s .sh $SCRIPT_FILE)"

BACKUP_SCRIPT="$SCRIPT_DIR/lvm-thin-backup.sh"
RETENTION="-60 days"

$BACKUP_SCRIPT backup images linux-dev
$BACKUP_SCRIPT backup images win8
$BACKUP_SCRIPT backup images win8-data
#etc

$BACKUP_SCRIPT removeall images linux-dev "$RETENTION"
$BACKUP_SCRIPT removeall images win8 "$RETENTION"
$BACKUP_SCRIPT removeall images win8-data "$RETENTION"
#etc

EOF

Inafanya nini...?Hutumia hati iliyotangulia kuunda na kusawazisha nakala rudufu za viwango vyembamba vilivyoorodheshwa. Hati itaacha vijipicha visivyotumika vya majuzuu yaliyoorodheshwa, ambayo yanahitajika ili kufuatilia mabadiliko tangu ulandanishi wa mwisho.

Hati hii lazima ihaririwe, ikibainisha orodha ya juzuu nyembamba ambazo nakala za chelezo zinapaswa kutengenezwa. Majina yaliyotolewa ni kwa madhumuni ya kielelezo tu. Ukipenda, unaweza kuandika hati ambayo itasawazisha juzuu zote.

Wacha tupe haki:

#chmod +x /root/lvm-thin-backup/cron-daily.sh
#chmod +x /root/lvm-thin-backup/lvm-thin-backup.sh

Wacha tuiangalie na kuiweka kwenye cron:

#/usr/bin/nice -n 19 /usr/bin/ionice -c 3 /root/lvm-thin-backup/cron-daily.sh 2>&1 | /usr/bin/logger -t lvm-thin-backup
#cat /var/log/syslog | grep lvm-thin-backup
#crontab -e
0 3 * * * /usr/bin/nice -n 19 /usr/bin/ionice -c 3 /root/lvm-thin-backup/cron-daily.sh 2>&1 | /usr/bin/logger -t lvm-thin-backup

Uzinduzi wa kwanza utakuwa mrefu, kwa sababu ... majalada nyembamba yatalandanishwa kikamilifu kwa kunakili nafasi yote iliyotumika. Shukrani kwa metadata nyembamba ya LVM, tunajua ni vizuizi vipi vinatumika, kwa hivyo ni vizuizi vyembamba vilivyotumika tu ndivyo vitanakiliwa.

Uendeshaji unaofuata utanakili data kwa kasi kutokana na kubadilisha ufuatiliaji kupitia metadata nyembamba ya LVM.

Hebu tuone kilichotokea:

#time /root/btrfs-backup/cron-daily.sh
real 0m2,967s
user 0m0,225s
sys 0m0,353s

#time /root/lvm-thin-backup/cron-daily.sh
real 1m2,710s
user 0m12,721s
sys 0m6,671s

#ls -al /backup/btrfs/back/remote/*
/backup/btrfs/back/remote/boot:
total 0
drwxr-xr-x 1 root root 1260 ΠΌΠ°Ρ€ 26 09:11 .
drwxr-xr-x 1 root root 16 ΠΌΠ°Ρ€ 6 09:30 ..
drwxr-xr-x 1 root root 322 ΠΌΠ°Ρ€ 26 02:00 .@base
drwxr-xr-x 1 root root 516 ΠΌΠ°Ρ€ 6 09:39 [email protected]
drwxr-xr-x 1 root root 516 ΠΌΠ°Ρ€ 6 09:39 [email protected]
...
/backup/btrfs/back/remote/root:
total 0
drwxr-xr-x 1 root root 2820 ΠΌΠ°Ρ€ 26 09:11 .
drwxr-xr-x 1 root root 16 ΠΌΠ°Ρ€ 6 09:30 ..
drwxr-xr-x 1 root root 240 ΠΌΠ°Ρ€ 26 09:11 @.@base
drwxr-xr-x 1 root root 22 ΠΌΠ°Ρ€ 26 09:11 @home.@base
drwxr-xr-x 1 root root 22 ΠΌΠ°Ρ€ 6 09:39 @[email protected]
drwxr-xr-x 1 root root 22 ΠΌΠ°Ρ€ 6 09:39 @[email protected]
...
drwxr-xr-x 1 root root 240 ΠΌΠ°Ρ€ 6 09:39 @[email protected]
drwxr-xr-x 1 root root 240 ΠΌΠ°Ρ€ 6 09:39 @[email protected]
...

#lvs -olv_name,lv_size images && lvs -olv_name,lv_size backup
LV LSize
linux-dev 128,00g
linux-dev.base 128,00g
thin-pool 1,38t
win8 128,00g
win8-data 2,00t
win8-data.base 2,00t
win8.base 128,00g
LV LSize
backup 256,00g
images-linux-dev.base 128,00g
images-linux-dev.snap.2020-03-08-10-09-11 128,00g
images-linux-dev.snap.2020-03-08-10-09-25 128,00g
...
images-win8-data.base 2,00t
images-win8-data.snap.2020-03-16-14-11-55 2,00t
images-win8-data.snap.2020-03-16-14-19-50 2,00t
...
images-win8.base 128,00g
images-win8.snap.2020-03-17-04-51-46 128,00g
images-win8.snap.2020-03-18-03-02-49 128,00g
...
thin-pool <2,09t

Je, hii ina uhusiano gani na wanasesere wa kuatamia?

Uwezekano mkubwa zaidi, ikizingatiwa kwamba kiasi cha kimantiki cha LVM LV kinaweza kuwa LVM PV kiasi cha kimwili kwa VG nyingine. LVM inaweza kujirudia, kama wanasesere wa kiota. Hii inatoa LVM kubadilika sana.

PS

Katika makala inayofuata, tutajaribu kutumia mifumo kadhaa inayofanana ya uhifadhi wa simu/KVM kama msingi wa kuunda nguzo ya hifadhi/vm iliyosambazwa kijiografia yenye upungufu katika mabara kadhaa kwa kutumia kompyuta za mezani, Mtandao wa nyumbani na mitandao ya P2P.

Chanzo: mapenzi.com

Kuongeza maoni