Partycje
Po tej lekcji: kursant rozumie różnicę między MBR a GPT, dzieli dysk na partycje w fdisk, gdisk i parted, nadaje im właściwe typy i wie, co zrobić przez partprobe, kiedy jądro nie widzi nowej partycji.
Wstęp
lsblk na maszynie wirtualnej, dysk sda podzielony na sda1 1G /boot, sda2 reszta
Popatrz na dowolny serwer. Prawie nigdy nie zobaczysz systemu plików położonego bezpośrednio na całym dysku. Zawsze jest sda1, sda2, nvme0n1p1. Dysk najpierw jest dzielony na kawałki, a dopiero na kawałkach stoją regały.
Dlaczego? Bo jeden kawałek musi być dla programu rozruchowego, drugi dla systemu, trzeci może na dane, które przeżyją reinstalację. Jak mieszkanie: niby można mieć jedno wielkie pomieszczenie z wanną obok łóżka i kuchenką przy szafie, ale ktoś kiedyś wymyślił ściany i ludzkość na tym zyskała.
Dziś stawiamy ściany. Trzema narzędziami, bo na egzaminie i w pracy spotkasz wszystkie trzy.
Uwaga: zła partycja na złym dysku to najszybszy sposób, żeby skasować komuś cały serwer. Ćwicz na maszynie wirtualnej z dodatkowym, pustym dyskiem albo na pliku, tak jak ja. Przed każdym zapisem sprawdź lsblk, czy na pewno masz przed sobą właściwy dysk. Dwa razy.
Tablica partycji, czyli plan mieszkania na drzwiach
Na samym początku dysku leży mała tabliczka: plan mieszkania. Mówi, gdzie zaczyna się i kończy każdy pokój. To tablica partycji. Są dwa standardy takich tabliczek.
MBR, Master Boot Record. Stara tabliczka z czasów pierwszych pecetów, wyryta na jednym 512-bajtowym sektorze na samym początku dysku. Ma miejsce na cztery wpisy. Cztery pokoje i koniec. Chcesz więcej? Jeden z czterech pokoi zamieniasz na korytarz, czyli partycję rozszerzoną, a w korytarzu robisz kolejne pomieszczenia, czyli partycje logiczne. Działa, ale wygląda jak mieszkanie po trzech remontach różnych ekip. Do tego MBR liczy sektory na 32 bitach, więc przy zwykłych sektorach po 512 bajtów nie ogarnie więcej niż 2 TiB. Dysk 4 TB z MBR to mieszkanie, w którym połowy pokoi nie ma na planie.
GPT, GUID Partition Table. Nowoczesna tabliczka, część standardu UEFI. Domyślnie 128 wpisów, gigantyczne rozmiary, każda partycja ma własny unikalny identyfikator i nazwę. A co najważniejsze: kopię planu trzyma też na końcu dysku. Zniszczysz początek, plan przeżyje na zapleczu.
Wybór? Nowy dysk: GPT. MBR tylko wtedy, gdy musisz, na przykład stary sprzęt startujący w trybie BIOS albo mały pendrive dla starego telewizora.
Przygotowanie: dysk z pliku
Na maszynie wirtualnej po prostu dodajesz drugi dysk w ustawieniach VirtualBoxa czy virt-managera i pojawi się jako sdb albo vdb. Ja robię dysk z pliku i podpinam go jako urządzenie:
truncate -s 2G dysk.img
sudo losetup -fP --show dysk.img/dev/loop8losetup podpina plik jako urządzenie blokowe /dev/loop8. -f bierze pierwszy wolny numer, -P każe jądru szukać na nim partycji, --show wypisuje, co dostaliśmy. Od teraz /dev/loop8 udaje dysk tak dobrze, że fdisk nie zauważy różnicy. Ty w każdej komendzie zamiast /dev/loop8 wpisz swój dysk.
fdisk: klasyk z menu
fdisk to interaktywne menu sterowane literkami. Jak bankomat ze starego filmu: wciskasz literę, on o coś pyta.
sudo fdisk /dev/loop8Wpisuję po kolei:
g, czyli nowa, pusta tablica GPT. Dla MBR byłobyo.n, nowa partycja. Numer zostawiam domyślny Enterem, początek też Enterem, a na koniec wpisuję+500M, czyli pięćset megabajtów od początku.njeszcze raz, numer i początek Enterem, koniec+1G.t, zmiana typu. Wybieram partycję2i wpisujęlvm.p, pokaż, co mam.
Created a new GPT disklabel (GUID: 9980810F-58C1-40A2-9741-B1787FD88291).
Created a new partition 1 of type 'Linux filesystem' and of size 500 MiB.
Created a new partition 2 of type 'Linux filesystem' and of size 1 GiB.
Changed type of partition 'Linux filesystem' to 'Linux LVM'.
Disklabel type: gpt
Device Start End Sectors Size Type
/dev/loop8p1 2048 1026047 1024000 500M Linux filesystem
/dev/loop8p2 1026048 3123199 2097152 1G Linux LVMI teraz najważniejsze. Wszystko do tej pory było tylko na kartce. fdisk mówi to zresztą na powitanie: Changes will remain in memory only, until you decide to write them. Zmiany są w pamięci, dopóki nie wciśniesz w, czyli „write”, zapisz. q wychodzi bez zapisywania. To Twój hamulec bezpieczeństwa: pomyliłeś się, q, nic się nie stało.
Command (m for help): w
The partition table has been altered.
Calling ioctl() to re-read partition table.
Syncing disks.Po co zmiana typu? Typ partycji to tabliczka na drzwiach pokoju: „kuchnia”, „łazienka”, „schowek”. Nic nie blokuje, ale narzędzia i ludzie się nią kierują. Najważniejsze dla admina: Linux filesystem na zwykłe dane, Linux LVM pod LVM, o którym za trzy lekcje, Linux swap pod pamięć wymiany, o której w lekcji sześćdziesiątym, i EFI System pod partycję rozruchową. W fdisk możesz wpisać skrót: lvm, swap, linux, zamiast szukać numeru na liście.
partprobe: kiedy jądro przespało zmianę
Sprawdzam, czy system widzi nowe partycje:
lsblk /dev/loop8NAME MAJ:MIN RM SIZE RO TYPE MOUNTPOINTS
loop8 7:8 0 2G 0 loopNic. Tablica jest zapisana na dysku, ale jądro dalej trzyma w pamięci stary plan. To się zdarza naprawdę, szczególnie gdy dysk jest w użyciu albo gdy ktoś zmieniał partycje innym narzędziem. Jak administracja budynku, która dostała nowy plan mieszkania, ale położyła go na stosie „do przeczytania w poniedziałek”.
partprobe każe jądru przeczytać plan od nowa:
sudo partprobe -s /dev/loop8
lsblk /dev/loop8/dev/loop8: gpt partitions 1 2
NAME MAJ:MIN RM SIZE RO TYPE MOUNTPOINTS
loop8 7:8 0 2G 0 loop
|-loop8p1 259:2 0 500M 0 part
`-loop8p2 259:3 0 1G 0 partSą. -s dopisuje krótkie podsumowanie. Na RHEL partprobe jest w pakiecie parted, na Ubuntu też, więc jeśli masz parted, masz i partprobe.
gdisk: fdisk w wersji GPT
gdisk wygląda prawie jak fdisk i powstał, kiedy fdisk jeszcze nie umiał GPT. Dziś fdisk umie, ale gdisk dalej jest w podręcznikach i na egzaminach. Jeśli go nie masz: sudo apt install gdisk [Ubuntu] albo sudo dnf install gdisk [RHEL].
Najpierw tylko podglądam:
sudo gdisk -l /dev/loop8Partition table scan:
MBR: protective
GPT: present
Found valid GPT with protective MBR; using GPT.
Partition table holds up to 128 entries
Partitions will be aligned on 2048-sector boundaries
Number Start (sector) End (sector) Size Code Name
1 2048 1026047 500.0 MiB 8300
2 1026048 3123199 1024.0 MiB 8E00Typy w gdisk to czterocyfrowe kody: 8300 Linux filesystem, 8E00 LVM, 8200 swap, EF00 partycja EFI. Komendy w środku są podobne: o nowa tablica GPT, n nowa partycja, t typ, c nazwa partycji, p podgląd, w zapis, q wyjście bez zapisu. Przy zapisie gdisk pyta jeszcze raz i krzyczy wielkimi literami:
Final checks complete. About to write GPT data. THIS WILL OVERWRITE EXISTING
PARTITIONS!!
Do you want to proceed? (Y/N): y
OK; writing new GUID partition table (GPT) to g.img.
Warning: The kernel is still using the old partition table.
The new table will be used at the next reboot or after you
run partprobe(8) or kpartx(8)Zobacz: sam gdisk podpowiada partprobe. Narzędzia też wiedzą, że jądro bywa śpiące.
parted: bez menu, za to od razu
parted działa inaczej niż dwaj poprzednicy. Można go używać jedną linijką, bez menu, co jest idealne do skryptów. I uwaga, ważna różnica: parted zapisuje zmiany od razu, bez żadnego w. Nie ma kartki w pamięci. Jest długopis po ścianie.
Podgląd z wolnym miejscem, w jednostkach MiB:
sudo parted /dev/loop8 unit MiB print freePartition Table: gpt
Number Start End Size File system Name Flags
0.02MiB 1.00MiB 0.98MiB Free Space
1 1.00MiB 501MiB 500MiB
2 501MiB 1525MiB 1024MiB lvm
1525MiB 2048MiB 523MiB Free SpaceZostało 523 MiB wolnego od 1525 MiB do końca. Robię tam trzecią partycję o nazwie kopie:
sudo parted -s /dev/loop8 mkpart kopie ext4 1525MiB 100%
sudo parted /dev/loop8 printNumber Start End Size File system Name Flags
1 1049kB 525MB 524MB
2 525MB 1599MB 1074MB lvm
3 1599MB 2146MB 547MB kopie-s to tryb „script”, czyli nie zadawaj pytań. mkpart przyjmuje nazwę, typ systemu plików, początek i koniec. 100% znaczy „do końca dysku”. Słowo ext4 w mkpart to tylko podpowiedź dla typu partycji. parted nie formatuje. Regały stawiasz dalej przez mkfs.
Pułapka z jednostkami: parted domyślnie pokazuje MB, czyli miliony bajtów, a fdisk MiB, czyli potęgi dwójki. 500 MiB to 524 MB. Ten sam pokój, dwie różne miarki. Dlatego przy tworzeniu zawsze pisz jednostkę wprost: MiB albo GiB.
Partycja jest, to stawiamy regały:
sudo partprobe /dev/loop8
sudo mkfs.ext4 -q -L KOPIE /dev/loop8p3
sudo blkid /dev/loop8p3/dev/loop8p3: LABEL="KOPIE" UUID="a694c353-a877-4681-b13f-855c71e1f462" BLOCK_SIZE="4096" TYPE="ext4" PARTLABEL="kopie" PARTUUID="5cd92bfb-ac3a-473f-8efd-d5ace7246411"Popatrz na końcówkę. Są dwa identyfikatory. UUID należy do systemu plików i zmieni się, gdy zrobisz mkfs od nowa. PARTUUID i PARTLABEL należą do partycji w tablicy GPT i przeżyją formatowanie. Jak numer mieszkania i nazwisko lokatora: lokator się wyprowadzi, numer zostaje.
Jak to działa pod spodem
Dysk to dla jądra długa taśma sektorów po 512 bajtów, czasem po 4096. Partycja to po prostu zapis „od sektora 2048 do sektora 1026047”. Nic więcej. Żadnych ścian w środku, tylko liczby na planie.
Dlaczego pierwsza partycja zaczyna się od sektora 2048, a nie od 34? 2048 sektorów po 512 bajtów to dokładnie 1 MiB. Wszystkie nowe narzędzia wyrównują partycje do pełnego mebibajta, bo dyski SSD i macierze pracują dużymi blokami. Partycja zaczynająca się w połowie bloku to jak meblościanka postawiona tak, że każda szafka zahacza o dwa panele podłogi: działa, ale wszystko robi się dwa razy.
GPT na dysku wygląda tak: sektor 0 to ochronny MBR, sektor 1 to nagłówek GPT, sektory od 2 do 33 to tablica 128 wpisów, a na samym końcu dysku leży kopia tablicy i kopia nagłówka. Dlatego fdisk pisze, że ostatni użyteczny sektor to 4194270, a nie 4194303: ostatnie 33 sektory są zajęte przez zapasowy plan.
Kiedy piszesz w, narzędzie zapisuje tablicę na dysk i prosi jądro przez wywołanie ioctl, żeby wczytało ją ponownie. Jądro tworzy wtedy urządzenia sdb1, sdb2 i ich odpowiedniki w /dev. Jeśli jądro odmówi albo przegapi prośbę, masz to, co widzieliśmy: tablica na dysku jest, urządzeń nie ma. Wtedy partprobe.
Ściąga flag
| Komenda | Flaga / klawisz | Co robi |
|---|---|---|
fdisk | -l | wypisuje tablice partycji |
fdisk (menu) | g / o | nowa tablica GPT / MBR |
fdisk (menu) | n | nowa partycja |
fdisk (menu) | t | typ partycji (aliasy: linux, lvm, swap) |
fdisk (menu) | d | usuwa partycję |
fdisk (menu) | p | pokazuje plan |
fdisk (menu) | w / q | zapisz i wyjdź / wyjdź bez zapisu |
gdisk | -l | wypisuje tablicę GPT |
gdisk (menu) | o, n, t, c, p, w, q | nowa tablica, partycja, typ, nazwa, podgląd, zapis, wyjście |
parted | -s | tryb skryptowy, bez pytań |
parted | mklabel gpt / msdos | nowa tablica GPT / MBR |
parted | mkpart NAZWA TYP OD DO | nowa partycja (zapis od razu) |
parted | unit MiB print free | plan w MiB z wolnym miejscem |
parted | rm N | usuwa partycję N |
partprobe | -s | przeładowuje tablicę w jądrze i pokazuje podsumowanie |
losetup | -fP --show PLIK | podpina plik jako dysk i szuka partycji |
losetup | -d URZĄDZENIE | odpina dysk z pliku |
⚠ Typowy błąd
Zrobiłeś partycję, od razu chcesz założyć system plików:
sudo mkfs.ext4 /dev/loop9p1mke2fs 1.47.0 (5-Feb-2023)
The file /dev/loop9p1 does not exist and no size was specified.Komunikat brzmi groźnie, ale znaczy tylko: „nie ma takiego urządzenia”. Partycja jest w tablicy, ale jądro jeszcze jej nie wystawiło. Zamiast od razu robić drugą partycję albo restartować, sprawdź:
lsblk /dev/loop9
sudo partprobe /dev/loop9
lsblk /dev/loop9NAME MAJ:MIN RM SIZE RO TYPE MOUNTPOINTS
loop9 7:9 0 1G 0 loop
NAME MAJ:MIN RM SIZE RO TYPE MOUNTPOINTS
loop9 7:9 0 1G 0 loop
`-loop9p1 259:1 0 300M 0 partI dopiero teraz mkfs. Druga wersja tego błędu jest gorsza: wpisujesz mkfs.ext4 /dev/sda1 zamiast /dev/sdb1, bo palec się omsknął. Wtedy żadna komenda nie pomoże. Dlatego przed każdym mkfs i fdisk patrzysz w lsblk: rozmiar, czy coś jest zamontowane, czy na pewno nowy dysk.
✎ Zadanie
Na maszynie wirtualnej dodaj drugi dysk 2 GB albo zrób go z pliku przez truncate i losetup -fP --show. Potem:
- W
fdiskzałóż tablicę GPT, partycję 1 o rozmiarze 500 MiB typu Linux filesystem i partycję 2 o rozmiarze 1 GiB typu Linux LVM. Zapisz. - Resztę dysku zajmij jedną linijką
partedjako partycję o nazwiekopie. - Sprawdź wynik w
lsblk,gdisk -liparted ... unit MiB print free. Jeślilsblknie widzi partycji, użyjpartprobe. - Załóż ext4 z etykietą
DANEna partycji 1 i zapisz sobie jej UUID zblkid. Przyda się w następnej lekcji.
Pokaż rozwiązanie
Mój „drugi dysk” to znowu plik, podpięty jako /dev/loop1. Ty masz /dev/sdb albo /dev/vdb.
sudo fdisk /dev/loop1 # g, n (+500M), n (+1G), t 2 lvm, w
sudo parted -s /dev/loop1 mkpart kopie ext4 1525MiB 100%
sudo partprobe /dev/loop1
lsblk -o NAME,SIZE,TYPE /dev/loop1
sudo parted /dev/loop1 unit MiB print free
sudo mkfs.ext4 -q -L DANE /dev/loop1p1
sudo blkid /dev/loop1p1NAME SIZE TYPE
loop1 2G loop
|-loop1p1 500M part
|-loop1p2 1G part
`-loop1p3 522M part
1 1.00MiB 501MiB 500MiB
2 501MiB 1525MiB 1024MiB lvm
3 1525MiB 2047MiB 522MiB kopie
2047MiB 2048MiB 0.98MiB Free Space
/dev/loop1p1: LABEL="DANE" UUID="3d211a77-05fd-4f40-af9e-a59e28329d1f" BLOCK_SIZE="4096" TYPE="ext4" PARTUUID="bba0b016-23b8-477d-8674-90aebdd64b03"Zwróć uwagę na ostatnią linijkę parted: „do końca dysku”, czyli 100%, zostawiło jeszcze prawie megabajt wolnego. To nie błąd. Na końcu dysku GPT trzyma zapasowy plan, a parted wyrównuje partycje do pełnych mebibajtów. Okruszek, który zostaje na talerzu z grzeczności.
UUID z ostatniej linijki zapisz. Za chwilę wpiszemy go do najważniejszego pliku tej lekcji.
Co dalej
Mamy partycję, mamy na niej system plików, mamy UUID. Brakuje jednego: drzwi z korytarza do tego pokoju. W następnej lekcji montowanie: mount, umount, „device is busy”, findmnt i plik /etc/fstab, w którym jedna literówka potrafi nie wpuścić serwera do własnego domu.