учебники, программирование, основы, введение в,

 

Файловая система: идеология и структура

Файлы устройств Solaris
Каждому физическому устройству в Solaris обязательно соответствует файл устройства. Файл устройства по сути - это указатель на область кода ядра, в которой находится драйвер устройства. Файлы устройств располагаются в каталоге /dev и его подкаталогах. Такое расположение является стандартным для всех систем UNIX. Однако на самом деле в Solaris все файлы в каталоге /dev являются символическими ссылками на "настоящие" файлы устройств, которые располагаются в подкаталогах каталога /devices. Там эти файлы сгруппированы по отношению к своему месту в конфигурации компьютера. Подробнее это рассматривается ниже в разделе "Каталог /devices". О символических ссылках говорится также в лекции 5 раздела "Ссылки".
Файлы устройств имеют специальные типы: файл символьного устройства и файл блочного устройства.
Вывод программы ls иллюстрирует это:
ls -l /devices/pseudo/
...
crw-rw-rw- 1 root sys 26, 0 Мар 17 10:56 ptsl@0:ttyp0
crw-rw-rw- 1 root sys 26, 1 Мар 17 10:56 ptsl@0:ttyp1
crw-rw-rw- 1 root sys 26, 2 Мар 17 10:56 ptsl@0:ttyp2
crw-rw-rw- 1 root sys 26, 3 Мар 17 10:56 ptsl@0:ttyp3
...
ls -l /devices/pci@0,0/pci-ide@7,1/ide@0
...
brw-r----- 1 root sys 102, 0 Мар 17 10:56 cmdk@0,0:a
crw-r----- 1 root sys 102, 0 Мар 17 10:56 cmdk@0,0:a,raw
brw-r----- 1 root sys 102, 1 Мар 24 21:19 cmdk@0,0:b
crw-r----- 1 root sys 102, 1 Мар 17 10:56 cmdk@0,0:b,raw
...

Файл устройства является псевдофайлом, он не размещен на диске, о нем есть только запись, которая используется при доступе к устройству. Первое число, которое стоит в поле длины файла в выводе программы ls для файлов устройств, - это major-номер, а второе, после запятой - minor-номер. Первый из них означает номер типа устройств и одновременно - позицию в ядре, в которой следует искать драйвер устройства. Второй - номер экземпляра устройства данного типа. Поэтому файлы однотипных устройств в вышеприведенном выводе ls имеют одинаковые major-номера.
Устройство каждого типа имеет свой major-номер. Major-номера назначаются автоматически программой add_drv. Соответствие имени драйвера и major-номера определяется в файле /etc/name_to_major.
В Solaris каждое устройство имеет три разных имени: логическое имя, физическое имя и экземплярное имя.
Логические имена - это имена файлов устройств, которые хранятся в /dev.
Физические имена - это имена файлов устройств, хранящихся в /devices.
Экземплярные имена - это укороченные физические имена устройств, которые ядро назначает устройствам.
Ниже рассмотрен пример назначения всех перечисленных типов имен.
Файлы разделов дисков в Solaris
Мы предполагаем, что читатель знаком с физическим устройством жестких дисков, поэтому здесь не объясняются термины "головка", "дорожка", "цилиндр", "сектор" и другие. Все они являются общими для описания любых жестких дисков в любых компьютерах, независимо от архитектуры или используемой операционной системы.
Жесткий диск принято делить на разделы (в Solaris их называют slices). Раздел - это группа расположенных рядом цилиндров. Смысл разделения диска на разделы состоит в том, чтобы:

  • минимизировать расстояние, которое потребуется головке диска для считывания фрагментов одного файла;
  • разделить данные разных типов, чтобы обезопасить системные данные от возможной порчи пользовательскими программами;
  • зарезервировать под системные нужды достаточное пространство на диске так, чтобы несистемные файлы не могли его занять.

В Solaris на одном физическом жестком диске может быть до восьми разделов, которые принято нумеровать цифрами от 0 до 7.
Каждому разделу соответствует свой файл устройства в каталоге /dev/dsk. Пространство под разделы выделяется цилиндрами. Раздел однозначно определяется номерами начального и конечного цилиндров. В Solaris принята следующая концепция именования таких файлов устройств: в имени устройства учитываются номер контроллера, SCSI ID (target number), номер диска (LUN - Logical Unit Number) и номер раздела на диске. Если это диск IDE, то роль SCSI ID играет пара master/slave (соответственно, 0/1). Для встроенных дисков SCSI и любых дисков IDE номер диска равен 0. Это иллюстрирует.
Так, для системы с дисками SCSI /dev/dsk/c0t0d0s0 будет указывать на нулевой контроллер SCSI (c0), диск со SCSI ID 0 (t0), диск номер 0 на этом SCSI контроллере (d0), нулевой раздел на этом диске (s0).
Как показано на при создании файла устройства для раздела, который находится на IDE-диске, в названии файла учитываются номер адаптера IDE (как правило, в компьютерах x86 используют системные платы с одним адаптером, который поддерживает два канала IDE), номер канала (он кодируется как SCSI ID, как показано в ), номер диска (всегда d0) и номер раздела (первый раздел на диске - s0 и т.д., подобно разделам на SCSI-дисках).


Таблица 5.1. Соответствие между SCSI ID и позицией IDE-диска в подсистеме IDE

Номер диска в подсистеме IDE

Позиция диска в подсистеме IDE

0

primary master

1

primary slave

2

secondary master

3

secondary slave

Сказанное выше об именовании файлов устройств дисков IDE относится к системам на платформе SPARC. На платформе х86 файлы устройств, соответствующие разделам дисков IDE, именуются несколько иначе. Файлы, соответствующие разделам fdisk, обозначаются cNdMpK, где после с идет номер контроллера, после d - номер диска, а после p - номер раздела fdisk. На каждом из разделов fdisk может быть создано несколько подразделов (slices), если этот раздел fdisk является разделом типа Solaris. Любой раздел fdisk имеет свой тип, он указывается в таблице Master Boot Record (MBR), в которой описаны все разделы fdisk-диска.
По умолчанию при установке Solaris на IDE-диск на платформе IA (x86) программа-установщик создает два раздела fdisk - загрузочный (примерно 20 Мб) с программой-загрузчиком и раздел, на котором будут находиться все остальные части системы, а также пользовательские файлы. Первый раздел fdisk имеет тип FAT, а второй - тип Solaris. На втором разделе создаются подразделы (slices). Они именуются по такому же принципу, как и разделы на дисках систем SPARC, но без указания SCSI ID: c0d0s0, c0d0s1 и т.д.
Каждому файлу из каталога /dev/dsk соответствует файл устройства прямого доступа (raw disk) в каталоге /dev/rdsk:
# ls /dev/dsk
c0d0p0 c0d0s1 c0d0s15 c0d0s7 c1t0d0p3 c1t0d0s12 c1t0d0s4
c0d0p1 c0d0s10 c0d0s2 c0d0s8 c1t0d0p4 c1t0d0s13 c1t0d0s5
c0d0p2 c0d0s11 c0d0s3 c0d0s9 c1t0d0s0 c1t0d0s14 c1t0d0s6
c0d0p3 c0d0s12 c0d0s4 c1t0d0p0 c1t0d0s1 c1t0d0s15 c1t0d0s7
c0d0p4 c0d0s13 c0d0s5 c1t0d0p1 c1t0d0s10 c1t0d0s2 c1t0d0s8
c0d0s0 c0d0s14 c0d0s6 c1t0d0p2 c1t0d0s11 c1t0d0s3 c1t0d0s9

# ls /dev/rdsk
c0d0p0 c0d0s1 c0d0s15 c0d0s7 c1t0d0p3 c1t0d0s12 c1t0d0s4
c0d0p1 c0d0s10 c0d0s2 c0d0s8 c1t0d0p4 c1t0d0s13 c1t0d0s5
c0d0p2 c0d0s11 c0d0s3 c0d0s9 c1t0d0s0 c1t0d0s14 c1t0d0s6
c0d0p3 c0d0s12 c0d0s4 c1t0d0p0 c1t0d0s1 c1t0d0s15 c1t0d0s7
c0d0p4 c0d0s13 c0d0s5 c1t0d0p1 c1t0d0s10 c1t0d0s2 c1t0d0s8
c0d0s0 c0d0s14 c0d0s6 c1t0d0p2 c1t0d0s11 c1t0d0s3 c1t0d0s9

В Solaris принято, что раздел номер 2 (slice 2) представляет собой весь диск, т.е. является репрезентацией всего диска в целом, со всеми его разделами. Иначе говоря, на диске на самом деле может быть создано до 7 разделов, а восьмой (раздел 2) всегда охватывает все эти разделы вместе. Поэтому в разделе 2 нельзя создать файловую систему и записывать туда файлы: он служит для системных надобностей. В частности, в структурах, адресуемых через раздел 2, хранятся сведения о диске в целом: реальный размер, число цилиндров и т.п.
Замечание о разных типах имен устройств можно проиллюстрировать на примере именования разделов диска. Так, разделам SCSI-диска со SCSI ID, равным 6, присоединенным к нулевому контроллеру, будут соответствовать логические имена устройств (разделов диска) от /dev/dsk/c0t6d0s0 до /dev/dsk/c0t6d0s7, физические имена от /devices/pci@1f,0/pci@1,1/scsi@6/sd@0,0:a до /devices/pci@1f,0/pci@1,1/scsi@6/sd@0,0:g. При этом диску в целом будет соответствовать экземплярное имя sd6.

Каталог /devices

Каталог /devices отражает аппаратную конфигурацию компьютера. Дерево его подкаталогов строится в соответствии с реальными подключениями устройств к шинам и контроллерам. Поэтому для компьютеров различных архитектур структура дерева подкаталогов /devices будет разной. Содержание этих подкаталогов будет разным для разных компьютеров, даже если они имеют одинаковую архитектуру, потому что компьютеры могут иметь разную конфигурацию: неодинаковое количество жестких дисков, различные контроллеры интерфейсов (SCSI, IDE), по-разному подсоединенные к ним диски. Например, для компьютера x86 дерево может быть таким:

./pseudo
./isa
./isa/fdc@1,3f0
./isa/i8042@1,60
./pci@0,0
./pci@0,0/pci8086,7191@1
./pci@0,0/pci-ide@2,1/ide@0
./pci@0,0/pci-ide@2,1/ide@1
./pci@0,0/pci-ide@2,1
    

Это пример дерева каталогов Solaris 9, установленного на ноутбук IBM ThinkPad 390X.
Полный список всех устройств компьютера, с которыми система Solaris готова работать, содержится в файле /etc/path_to_inst.
Файл /etc/path_to_inst содержит соответствия физических имен устройств и номеров экземпляров устройств (тех, что называются minor-номерами устройств). Чтобы эти соответствия сохранялись от загрузки к загрузке, система записывает их в файл /etc/path_to_inst. Этот файл во время загрузки доступен только для чтения, он может быть изменен с помощью программ add_drv(1M) и drvconfig(1M).
Обычно системному администратору незачем изменять этот файл. Для просмотра полного списка устройств следует использовать команду prtconf:

prtconf
    

Для просмотра списка устройств, фактически работающих в системе, используйте

prtconf | grep -v not
    

Это позволяет отфильтровать в выводе prtconf строки, содержащие слово "not", например, "device not attached". Более подробно об изменении аппаратной конфигурации и добавлении драйверов устройств говорится в лекции 11.

Разбиение диска на разделы

Каждый диск состоит из нескольких разделов. Все разделы, кроме раздела для свопинга, имеют точки монтирования. Вся файловая система UNIX представляет собой единое дерево. К нему можно присоединять (монтировать) новые "ветви".
Предположим, что для начала у нас есть только корень дерева (корневой раздел). Он изображен большим эллипсом. Мы можем присоединить к нашей файловой системе еще один раздел (в нем хранятся какие-то каталоги, но пока он не имеет имени в нашей файловой системе). Присоединяемый раздел обозначен малым эллипсом:
Для присоединения мы должны указать, в какое место существующей файловой системы (точку монтирования) следует смонтировать новый раздел. После монтирования все каталоги нового раздела будут доступны в качестве подкаталогов точки монтирования. При этом истинная структура файловой системы оказывается прозрачной для пользователя. После того как раздел смонтирован, пользователь не отличит каталоги одного раздела от каталогов другого. Предположим, мы смонтировали раздел в каталог /usr :
Посмотреть, какие разделы в какие точки монтирования присоединены, можно командой mount:

mount
/ on /dev/dsk/c0d0s0
read/write/setuid/intr/largefiles/xattr/onerror=panic/dev=
   1980000 on Sat Jan 31 20:08:40 2004
/boot on /dev/dsk/c0d0p0:boot
   read/write/setuid/nohidden/nofoldcase/dev=19a3010
   on Sat Jan 31 20:08:38 2004
/proc on /proc read/write/setuid/dev=2d80000
   on Sat Jan 31 20:08:39 2004
/etc/mnttab on mnttab read/write/setuid/dev=2e40000
   on Sat Jan 31 20:08:39 2004
/dev/fd on fd read/write/setuid/dev=2e80000
   on Sat Jan 31 20:08:42 2004
/var/run on swap read/write/setuid/xattr/dev=1
   on Sat Jan 31 20:08:45 2004
/tmp on swap read/write/setuid/xattr/dev=2
   on Sat Jan 31 20:08:48 2004
/export/home on /dev/dsk/c0d0s7
read/write/setuid/intr/largefiles/xattr/onerror=panic/dev=
1980007 on Sat Jan 31 20:08:48 2004
/floppy/noname on /vol/dev/diskette0/noname
   read/write/setuid/nohidden/nofoldcase/dev=1740002
   on Sat Jan 31 21:34:36 2004
    

Обратите внимание на то, что если каталог является точкой монтирования, то он находится на отдельном разделе, а если нет - то он расположен на том же разделе, что и родительский каталог. Например, каталог /usr расположен на отдельном разделе, а каталог /etc - в том же разделе, что и каталог /.
Разбиение диска на разделы производится в двух случаях: при установке системы и при подключении нового диска. Разбиение на разделы следует спланировать так, чтобы в будущем размеры разделов были достаточны для установки программ и размещения файлов данных. В Solaris должны быть созданы как минимум два раздела: корневой (root) раздел, монтируемый в файловой системе в корень ее дерева и обозначаемый символом "/" (слэш), и раздел для свопинга. Последний не имеет точки монтирования, так как не принадлежит к файловой системе и не размечается, а используется для прямых чтения страниц с диска и записи страниц на диск.
Для более надежной и быстрой работы системы принято, кроме упомянутых разделов, создавать разделы с точками монтирования /usr, /export/home и, возможно /opt. Далее мы будем называть разделы по именам точек монтирования (например, раздел /usr).
В корневом каталоге системы располагается несколько файлов и ряд обязательных для работы системы подкаталогов. Это подкаталоги /bin, /sbin, /dev, /devices, /etc, /tmp. Кроме того, обычно есть подкаталоги /usr и /opt, а также /export, они обычно являются точками монтирования других разделов.
Корневой каталог в типичной установке Solaris (набор программ Entire Distribution - подробнее см. лекции 3 и 4) занимает 200 Мб (при условии, что каталоги /usr, /var и /export/home размещены в других разделах). При установке системы ему следует выделить 300 Мб - с запасом. Каталог /usr займет не меньше 1400 Мб, /var - не менее 100 Мб. Для каталога /var имеет смысл выделить больше места, т.к. именно в нем будут содержаться быстро растущие в размере файлы протоколов, почтовые ящики пользователей и прочее. Приведенные объемы разделов справедливы для варианта установки с набором программ Entire Distribution.
Вообще говоря, перед планированием разделов следует подумать о том, как будет использоваться компьютер под управлением Solaris. Если это будет сервер Oracle, надо зарезервировать один неразмеченный (неотформатированный) раздел под базы данных Oracle. Если планируется сделать почтовый сервер, то следует отвести под раздел /var достаточно места для размещения всех почтовых ящиков в каталоге /var/mail, а если это будет файловый сервер, надо сделать отдельный большой раздел для хранения файлов пользователей (например, /export/home).
Таким образом, фактическое пространство, которое следует отвести под каталог /var, зависит от назначения компьютера. Исходя из собственного опыта, я всегда создаю для /var раздел размером как минимум 256 Мб в системах с небольшой нагрузкой (почтовый сервер, http-cache и ftp для сети из 10-50 компьютеров) и до 2-3 Гб в системах со средней нагрузкой (почтовый сервер, http-cache, СУБД типа MySQL, web-сервер с 5-10 виртуальными хостами в сети из 50-150 компьютеров).
При установке системы программа-установщик предложит вам разумные значения по умолчанию. Если специфика устанавливаемой системы требует изменений, можно нажать кнопку Modify в окне Lay Out File Systems и затем изменить размеры разделов там, где требуется. Окно Lay Out File Systems появляется ближе к концу работы установщика, после выбора типа установки. О типах установки (установка базового комплекта, установка полного комплекта ПО Solaris и т.п.) подробнее рассказано в лекциях 3 и 4.
При установке нового диска его разметку поможет провести программа format. Эта программа также может использоваться для получения информации о геометрии диска, для низкоуровнего форматирования SCSI-дисков и восстановления некоторой служебной информации после сбоев.

Разметка нового диска

Предположим, мы подключили новый диск, и это IDE primary slave диск. Для того чтобы создать на нем файловую систему, потребуется создать на новом диске разделы (по крайней мере один) и затем в каждом из разделов создать новую файловую систему.
Создание разделов на диске выполняется с помощью команды format или fdisk. Последняя применяется только для платформы x86. Однако из format можно вызвать fdisk, и предпочтительнее делать именно так. Почему - будет ясно из следующего описания.
После подключения нового диска нет надобности перенастраивать ядро Solaris, если диски этого типа в системе уже есть. Например, если у вас уже есть один IDE-диск и система с ним уже работает, незачем перезапускать систему с ключом r или создавать файл /reconfigure и перезапускаться для обнаружения нового устройства. Достаточно создать новые файлы устройств в каталогах /devices и /dev. Для этого в более ранних версиях Solaris использовалась программа disks, а в Solaris 9 следует запустить devfsadm. При запуске без параметров новый диск будет обнаружен и требуемые файлы будут добавлены в каталоги /devices, /dev/dsk и /dev/rdsk.
Теперь любая программа работы с диском, требующая файл устройства в каталоге /dev/rdsk, уже может работать с диском. Запустим программу format. В меню программы следует выбрать диск, а затем выбрать запуск fdisk. После этого мы будем работать в среде программы fdisk. Ее интерфейс нам знаком по другим системам, нужно лишь обратить внимание на то, что есть возможность создавать разделы нескольких типов. Если мы добавляем дополнительный диск для работы с ним из среды Solaris, то следует выбрать тип Solaris. Раздел на новом диске не должен быть помечен как "активный", если только с него не будет загружаться какая-нибудь система в будущем.
Можно запустить программу fdisk самостоятельно, без предварительного вызова программы format, но последняя все равно будет нужна на следующем этапе.
После создания раздела следует выйти из fdisk и в программе format выбрать partition->print.
Если определен размер только одного подраздела (partition), а именно - подраздела номер 2, это говорит о том, что для созданного раздела fdisk следует определить подразделы. Если это отвечает вашим намерениям, достаточно создать всего один подраздел размером с весь раздел fdisk. Это можно сделать через меню Partition программы format. Выбрав partition->номер подраздела (например, 0), будет легко задать его размер.
Теперь необходимо выбрать пункт label для записи получившейся таблицы разделов на диск.
После этого можно создать новую файловую систему на получившемся подразделе. Помните: разделы fdisk для Solaris - это лишь место для размещения подразделов типа Solaris (slices). А на этих подразделах как раз и существует файловая система UFS и располагаются файлы и каталоги. Файловую систему на новом диске создадим командой newfs.
Программа mkfs позволяет создавать файловые системы разных типов, включая UFS, а newfs является более удобным интерфейсом к mkfs исключительно для создания файловых систем UFS:

# newfs /dev/rdsk/c0d1s0
newfs: construct a new file system /dev/rdsk/c0d1s0: (y/n)? y
/dev/rdsk/c0d1s0: 2060352 sectors in 2044 cylinders of 16
tracks, 63 sectors
    1006,0MB in 128 cyl groups (16 c/g, 7,88MB/g, 3776 i/g)
super-block backups (for fsck -F ufs -o b=#) at:
 32, 16224, 32416, 48608, 64800, 80992, 97184, 113376, 129568,
145760, 161952, 178144, 194336, 210528, 226720, 242912, 258080,
274272, 290464, 306656, 322848, 339040, 355232, 371424, 387616,
403808, 420000, 436192, 452384, 468576, 484768, 500960, 516128,
532320, 548512, 564704, 580896, 597088, 613280, 629472, 645664,
661856, 678048, 694240, 710432, 726624, 742816, 759008, 774176,
790368, 806560, 822752, 838944, 855136, 871328, 887520, 903712,
919904, 936096, 952288, 968480, 984672, 1000864, 1017056, 1032224,
1048416, 1064608, 1080800, 1096992, 1113184, 1129376, 1145568,
1161760, 1177952, 1194144, 1210336, 1226528, 1242720, 1258912,
1275104, 1290272, 1306464, 1322656, 1338848, 1355040, 1371232,
1387424, 1403616, 1419808, 1436000, 1452192, 1468384, 1484576,
1500768, 1516960, 1533152, 1548320, 1564512, 1580704, 1596896,
1613088, 1629280, 1645472, 1661664, 1677856, 1694048, 1710240,
1726432, 1742624, 1758816, 1775008, 1791200, 1806368, 1822560,
1838752, 1854944, 1871136, 1887328, 1903520, 1919712, 1935904,
1952096, 1968288, 1984480, 2000672, 2016864, 2033056, 2049248,
    

Смонтируем получившуюся файловую систему в каталог /test:

# mount -F ufs /dev/dsk/c0d1s0 /test
# ls test
lost+found
    

Обратите внимание, при создании файловой системы в ней сразу создается каталог lost+found, это делается для того, чтобы при автоматическом восстановлении файлов после сбоя (при перезагрузке, например) программе fsck было куда записать потерявшиеся фрагменты файлов. Кроме того, в некоторые блоки (их список выводится при работе newfs или mkfs) записана резервная копия суперблока новой файловой системы.

Количество индексных дескрипторов в файловой системе

Количество индексных дескрипторов в создаваемой файловой системе типа UFS можно задать посредством указания параметра с ключом -i:

newfs -i nbpi raw_deivce_name
        

Например

newfs -i 2048 /dev/rdsk/c0d0p0
        

Параметр nbpi обозначает число байтов, приходящихся на один индексный дескриптор, что при известном объеме диска однозначно определяет число индексных дескрипторов в файловой системе.
Программы mkfs и newfs поддерживают еще ряд ключей, которые позволяют гибко описывать параметры создаваемой файловой системы.


Поддерживаемые типы файловых систем
Основной ("родной") файловой системой Solaris является UFS (Unix File System). Всего Solaris 9 поддерживает 13 файловых систем, перечисленных в.

Таблица 5.2. Файловые системы, поддерживаемые Solaris 9

Файловая система

Тип

Устройство

Описание

UFS

обычная

диск

родная файловая система Solaris

VxFS

обычная

диск

журналируемая система от Veritas Corp

QFS

обычная

диск

файловая система от LSC Inc.

pcfs

обычная

диск

MSDOS FAT и FAT32

hsfs

обычная

диск

файловая система High Sierra (для CD-ROM); она же - ISO9660

tmpfs

обычная

память

использует оперативную память и область свопинга

nfs

псевдосистема

сеть

файловая система для монтирования каталогов на других компьютерах (подобно разделяемым каталогам Windows)

cachefs

псевдосистема

другая ФС

использует локальный диск для кэширования удаленной файловой системы NFS

autofs

псевдосистема

другая ФС

использует динамические объекты для монтирования других файловых систем

specfs

псевдосистема

драйверы

файловая система файлов устройств /dev

procfs

псевдосистема

ядро

/proc - отображение процессов в структуру ФС

sockfs

псевдосистема

сеть

соединения типа "сокет"

fifos

псевдосистема

файлы

программные каналы (pipe API)

В довольно старых версиях UNIX поддерживалась всего одна файловая система. С увеличением разнообразия носителей возникла необходимость поддержки разнородных файловых систем на носителях разной природы. Так в 1985 году компания Sun Microsystems пришла к реализации концепции виртуальной файловой системы.
Виртуальная файловая система представляет собой абстрактную файловую систему, которая позволяет операционной системе одинаковым образом обращаться к файловым системам разных типов.
К 1985 году операционные системы фирмы Sun использовали Berkeley Fast Filesystem (FFS). Эта файловая система базировалась на концепции индексных дескрипторов, которая органично трансформировалась в концепцию виртуальных индексных дескрипторов в новой файловой системе UFS, вобравшей в себя структуру FFS и новые идеи организации виртуальной файловой системы. Взаимодействие независимого от конкретного типа файловой системы уровня виртуальной файловой системы и файловых систем строго определенных типов иллюстрирует
Файловая система UFS с 1985 года претерпела некоторые изменения. Так, начиная с выпуска Solaris 9 8/03 поддерживаются многотерабайтные разделы, в то время как до этого UFS в Solaris могла работать только с разделами размером до 1 Тб. В настоящее время большие разделы поддерживаются только в 64-разрядной версии Solaris 9.
Файловые системы UFS, VxFS и QFS, поддерживаемые в Solaris, отличаются по некоторым важным параметрам, влияющим на их надежность и производительность. Различные файловые системы обладают разными алгоритмами выделения пространства под файлы, а также механизмами журналирования.


Таблица 5.3. Некоторые свойства файловых систем UFS, VxFS и QFS

Файловая система

Как выделяется пространство под файл

Есть ли журналирование

UFS

блоками (block)

да

VxFS

экстентами (extent)

да

QFS

экстентами (extent)

нет

Выделение пространства блоками позволяет минимизировать фрагментацию файловой системы, в то время как выделение пространства экстентами (большими частями пространства диска, состоящими из многих блоков) - снизить объем служебной информации, которая записывается на диск.
В файловой системе UFS размер блока может составлять от 512 байт до 8192 байт, по умолчанию в Solaris принят размер 8192 байт
В Solaris поддерживается журналирование (logging) файловых систем UFS и VxFS. Журналирование позволяет записывать в журнал информацию обо всех начатых транзакциях. Если транзакция (т.е. операция записи на диск) по каким-то причинам не была завершена (например, отключилось питание), то после перезапуска системы файловая система будет автоматически возвращена в состояние, в котором она была до начала транзакции. Подобную функциональность предоставляет файловая система ext3fs в Linux, reiserfs для FreeBSD и Linux и некоторые другие.
В последние годы непременным условием использования файловой системы стала поддержка современных дисков больших объемов и больших файлов. Если несколько лет назад "большим" назывался диск объемом в 1 гигабайт, то сейчас дисковые массивы объемом в несколько терабайт становятся обычными для систем среднего класса. Скоро они придут в системы малых офисов и в дома, а сети предприятий начнут работать с серверами, в которых установлены дисковые массивы, содержащие десятки и сотни терабайт информации. Что на это отвечают создатели файловых систем для UNIX?
С 1991 года файловая система UFS претерпела заметные изменения - появилась версия UFS2, которая пока поддерживается только во FreeBSD 5.0. В Solaris модификация файловой системы позволила достичь предела поддерживаемого дискового объема одного раздела UFS в 1 терабайт.

Элементы файловой системы
Файловая система каждого из разделов диска состоит из нескольких структурных элементов. Это суперблок, таблица индексных дескрипторов, блоки описания файлов, блоки, содержащие списки управления доступом к файлам (ACL - Access Control Lists), каталоги и собственно файлы.
Термин "файловая система" в литературе используется для обозначения трех разных понятий:

  • Во-первых, файловая система - это набор правил и конструкций, описывающих то, как сохраняются файлы на диске. В этом смысле мы употребляем, например, выражение "файловая система FAT32", и "файловая система" здесь тождественна понятию "тип файловой системы".
  • Во-вторых, файловая система - это совокупность всех файлов, хранимых в компьютере.
  • В-третьих (и это значение термина характерно именно для UNIX-систем) файловая система - это совокупность всех файлов на разделе диска или устройстве.

В этой книге мы будем говорить о файловых системах во всех трех смыслах, и там, где из контекста неясно, что именно имеется в виду, будем отдельно оговаривать, в каком смысле мы употребляем это выражение.
Файловая система UFS содержит четыре основных компонента с управляющей информацией: загрузочный блок, суперблок, таблицу индексных дескрипторов (i-node table) и каталоги. Кроме того, в Solaris (начиная с версии 2.5, с 1995 года) в файловой системе хранятся списки управления доступом (ACL). Хранение списков ACL обеспечивают так называемые теневые индексные дескрипторы (shadow inodes).
В System V каждый раздел жесткого диска форматируется (размечается) для размещения на нем файловой системы UNIX, в BSD - один раздел жесткого диска разбивается на подразделы, каждый из которых форматируется. Мы называем "разделом UNIX" такой размеченный в формате файловой системы UNIX раздел или подраздел.
Загрузочный блок (boot block) - это, как правило, часть метки диска (disk label). В загрузочном блоке записана маленькая программа, которая при старте системы загружает ядро ОС с диска в оперативную память. Загрузочный блок располагается в первом секторе диска. Загрузочный блок имеет смысл только для первого раздела жесткого диска, однако место для него резервируется в каждом разделе.
Суперблок содержит общую информацию о файловой системе как совокупности файлов на данном разделе жесткого диска, в частности, размере раздела UNIX, числе свободных и занятых блоков и индексных дескрипторов, флаге целостности файловой системы. Этот флаг устанавливается при успешном завершении работы с файловой системой, например, при корректной остановке операционной системы. В случае, если компьютер выключили рубильником, не дождавшись корректной остановки системы, при следующем старте системы программа fsck автоматически начнет проверку дисков и выдаст сообщение "clean flag is not set in superblock". Копии суперблока записываются в нескольких блоках внутри каждого раздела для большей надежности. В файловой системе UFS записывается по одной копии суперблока на каждую группу цилиндров. Если выяснится, что оригинал суперблока в начале раздела поврежден, будет использована копия суперблока.
Таблица индексных дескрипторов (i-node table) содержит дескрипторы файлов. Дескриптор файла содержит сведения о типе файла, размещении файла на диске, правах доступа к нему, UID владельца файла, GID группы файла, время последнего доступа к файлу, время последней модификации файла, время последней модификации самого индексного дескриптора. Подробнее структура таблицы индексных дескрипторов рассмотрена в подразделе "Таблица индексных дескрипторов: детали".
Размер индексного дескриптора фиксирован и составляет в Solaris в UFS 128 байт.
Размер таблицы индексных дескрипторов фиксирован и задается при создании файловой системы на разделе. Программе mkfs (и, соответственно, newfs) можно явно указать требуемое количество байт данных, которые должны приходиться на один индексный дескриптор, что определит количество индексных дескрипторов на разделе. Например, если раздел состоит из 1000000 байт, и число байт на дескриптор составляет 1000, то будет создано 1000 индексных дескрипторов.

Таблица индексных дескрипторов: детали
В ранних версиях UNIX таблица индексных дескрипторов занимала фиксированное пространство в начале устройства; в файловых системах UFS современных систем эта таблица распределена по диску, потому что каждая часть таблицы отвечает за часть диска.
В файловых системах, которые основаны на FFS (ext2, ext3, UFS), диск разбит на группы цилиндров. Каждая группа цилиндров имеет свою копию суперблока, битовую карту свободных блоков этой группы цилиндров и таблицу индексных дескрипторов для файлов, расположенных на цилиндрах этой группы. Такая структура хороша тем, что, во-первых, ускоряется доступ к системным структурам данных, во-вторых, повышается устойчивость к сбоям диска. При повреждении одного участка поверхности диска теряется только небольшая часть служебной информации о файлах и диске (такая информация в документации часто называется метаданными - metadata).
Если метаданные расположены рядом с пользовательскими данными, уменьшается расстояние, на которое перемещаются головки жесткого диска при переходе от служебной информации к запрошенным данным. К тому же при переходе от одного цилиндра к другому времени уходит значительно больше, чем при считывании данных в пределах одного цилиндра.
Каждому файлу соответствует индексный дескриптор. Он хранит информацию о различных атрибутах файла и его размещении на диске. В индексном дескрипторе записаны:

  • тип файла;
  • права доступа к файлу;
  • идентификатор владельца файла;
  • идентификатор группы файла;
  • время последней модификации файла;
  • время последнего доступа к файлу;
  • время последней модификации самого индексного дескриптора;
  • число повторных использований индексного дескриптора (т.е. случаев, когда файл был стерт и его индексный дескриптор был использован для хранения данных о другом файле);
  • длину файла в байтах (для файлов устройств это поле имеет смысл сочетания major- и minor-номера устройства, см. раздел "Файлы устройств Solaris");
  • идентификатор файловой системы, в которой расположен файл;
  • количество ссылок на файл;
  • число блоков файла (требуется для поддержки работы с файлами, содержащими большие области, заполненные символами с кодом "ноль", т.е. пустое пространство; такие файлы называются holey files - файлы с пустотами);
  • номер теневого индексного дескриптора (если требуется);
  • структура из 15 номеров блоков, описывающая размещение файла на диске; каждый номер блока занимает 4 байта.

Структура, описывающая физическое размещение файла на диске, в UFS представляет собой последовательность из номеров блоков.
Если файл занимает более двенадцати блоков (т.е. его длина больше 12*8192 =98304 байт), то предпоследние три номера обозначают не номера блоков данных, а номера косвенных блоков (indirect blocks), в которых хранятся указатели на следующие блоки данных и, возможно, на следующие косвенные блоки.
Первые двенадцать номеров блоков содержат просто номера блоков данных. Тринадцатый номер - это номер косвенного блока первого уровня. В блоке первого уровня содержится до 2048 адресов блоков данных (речь идет о 8192-байтных блоках).
Четырнадцатый номер блока содержит номер косвенного блока второго уровня. Косвенный блок второго уровня содержит 2048 номеров косвенных блоков первого уровня, таким образом, через косвенный блок второго уровня адресуется до 20482 блоков данных.
В пятнадцатый номер блока записан номер косвенного блока третьего уровня. Косвенный блок третьего уровня содержит 2048 номеров косвенных блоков второго уровня, так что через косвенный блок третьего уровня адресуется до 20483 блоков данных.
Файл не может располагаться на разных разделах UNIX. Файл может быть фрагментирован, хотя файловая система построена так, чтобы свести фрагментацию к минимуму. Теоретически рекомендуется не заполнять файловую систему более, чем на 70%, чтобы не увеличивать фрагментацию при работе.
Максимальный размер файла может быть легко посчитан, так как мы знаем правила адресации блоков данных. Если размер блока равен 512 байт, то напрямую адресуемые из индексного дескриптора блоки в сумме дают размер 12 × 8192 байта = 98304 байта.
Адресуемые через номер косвенного блока первого уровня - 2048 × 8192 байта = 16777216 байт.
Адресуемые через номер косвенного блока второго уровня - 20482 × 8192 байта = 34359738368 байт.
Адресуемые через номер косвенного блока третьего уровня - 20483 × 8192 байта = 70368744177664 байта.
Вместе получается примерно 64 Тбайт. Однако Solaris 9, насколько об этом можно судить по доступным фактам, не поддерживает файлы размером более 1 Тбайт на данный момент.
Все современные системы UNIX используют 128-байтный индексный дескриптор, который вмещает больше информации и номер блока в нем занимает не 3 байта (как в прошлом), а 4. Поэтому адресовать можно весьма большие разделы.
28 байт в таком дескрипторе отводится под разные расширения, включая место для 32-разрядных идентификаторов владельца и группы файла, а также под 64-разрядные поля времен модификации. Введение 64-разрядных полей времени в UNIX вместо прежних 32-разрядных нужно для того, чтобы избежать "проблемы 2031 года", т.к. именно в этом году перестанет хватать 32 байт для представления времени в системах UNIX. Разработчики обоснованно полагают, что до тех пор все существующие системы UNIX будут заблаговременно переведены на 64-разрядную архитектуру.
Обычные индексные дескрипторы
Обычные индексные дескрипторы (i-nodes) используются повсюду во всех системах UNIX. В Solaris существует специальный тип индексных дескрипторов - теневые индексные дескрипторы. Они служат для хранения информации о расширенных правах доступа к файлам и каталогам.
Теневые индексные дескрипторы
Теневые индексные дескрипторы (shadow i-nodes) содержат информацию, позволяющую получать доступ к расширенным правам доступа (ACL) файла или каталога. Этот тип файловых дескрипторов существует в реализации файловой системы UFS в Solaris, начиная с версии 2.5.1. Solaris 9 поддерживает теневые индексные дескрипторы для файловых систем UFS (Unix File System), NFS (Network File System версий 2 и 3), CacheFS (Cache File System). Расширенные права доступа могут быть назначены в отношении каталогов, обычных файлов, символических ссылок и именованных каналов (FIFO).
Если файлу назначены расширенные права доступа (например, с помощью команды setfacl), то будет создан теневой индексный дескриптор для этого файла и в обычный индексный дескриптор этого файла будет записана ссылка на теневой индексный дескриптор. Теневой индексный дескриптор не имеет специального формата, он представляет собой точно такой же индексный дескриптор, как и обычный, но с указанием в поле типа дескриптора на то, что он - теневой.
Расширенные права доступа хранятся в специальном файле, который создается в момент назначения таких прав. Теневой дескриптор указывает на этот специальный файл. В Solaris разрешено создавать не более 1024 записей в таком файле - следовательно, расширенные права доступа могут содержать не более 1024 специфических определений прав. Этого с избытком хватает для установки каких угодно специфических прав доступа. Каждая запись ACL занимает 12 байт, поэтому обычно эти записи не требуют много места на диске. Однако при назначении специфических прав доступа большому числу объектов в файловой системе следует помнить о том, что для этого требуется дополнительный объем дисковой памяти.
Для назначения и просмотра расширенных прав доступа используются команды setfacl и getfacl, о которых более подробно рассказывается в лекции 6.

 

man lofiadm (как работать с образом диска)

Для работы с образом диска, записанным в файл, может оказаться полезной программа lofiadm, которая позволяет настроить обращение к файлу как к блочному устройству.
Эта программа управляет драйвером lofi, который позволяет связать файл с блочным псевдоустройством. После этого содержимое файла будет доступно посредством обращения к файлу этого блочного устройства. У системы будет полное впечатление, что это и есть устройство и его можно монтировать с помощью mount, проверять на корректность записей на нем с помощью fsck и т.п.
Программу lofiadm следует использовать для добавления таких псевдоустройств, удаления связи файла и псевдоустройства и вывода информации о таких устройствах в системе.
Например, можно смонтировать образ компакт-диска стандарта ISO, лежащего в файле ex.iso:

lofiadm -a /home/ivan/ex.iso /dev/lofi/1
    

Затем можно смонтировать новое устройство в системе:

mount -F hsfs -o ro /dev/lofi/1 /mnt
    

и проверить, видно ли оно:

df -k /mnt
Filesystem
   kbytes used avail capacity Mounted on
/dev/lofi/1
   512418 512418 0 100% /mnt
    

Для демонтирования псевдоустройства и его удаления из системы следует дать следующие команды:

umount /mnt
lofiadm -d /dev/lofi/1
    

Обратите внимание на возможность создания файловой системы на псевдоустройстве и появлении устройства прямого доступа (rlofi, аналогично rdsk) после выполнения lofiadm -a:

lofiadm -a /export/home/test
/dev/lofi/1
newfs /dev/rlofi/1
newfs: construct a new file system /dev/rlofi/1: (y/n)? y
/dev/rlofi/1:
  71638 sectors in 119 cylinders of 1 tracks, 602 sectors
35.0MB in 8 cyl groups (16 c/g, 4.70MB/g, 2240 i/g)
super-block backups (for fsck -F ufs -o b=#) at: 32,
9664, 19296, 28928, ...
    

К файлу, который смонтирован в качестве псевдоустройства с помощью lofiadm, нельзя обращаться напрямую, как к файлу. Это аналогично тому, что нельзя напрямую обращаться к диску для записи файла, а следует делать это через драйвер файловой системы. Надлежит устанавливать такие права доступа к файлам, монтируемым как устройства, чтобы предотвратить несанкционированный доступ к ним как к обычным файлам.
После перезагрузки связь файла и псевдоустройства теряется; если требуется сделать ее постоянной, надо написать скрипт, который будет запускаться при загрузке и добавлять соответствующее псевдоустройство в систему, а затем его монтировать.
Возможность управлять псевдоустройствами зависит от прав доступа к файлу /dev/lofictl. По умолчанию правом монтирования и демонирования псевдоустройств обладает только root.

Дерево каталогов

Файлы в UNIX разложены по каталогам. Каталоги образуют древовидную структуру: есть корневой каталог, который обозначается знаком "/" (слэш), и его подкаталоги. В каждом из последних есть свои подкаталоги и т.д. Ограничений на число файлов в каталоге нет. Разные каталоги ("ветви" дерева каталогов) могут размещаться на разных дисках, это незаметно для пользователя. Чтобы обратиться к файлу, не нужно знать о том, на каком физическом устройстве или разделе диска он записан. Это значит, что лихорадочный поиск по дискам С:, D: E:, K:, R:, Y: не знаком человеку, работающему с UNIX. Он лихорадочно ищет потерянные файлы в густой кроне UNIX-каталогов, начиная от корня.
Между прочим, забавно, что уже много лет все упорно называют деревом структуру каталогов, у которой корень находится наверху, а его ближайшие отростки-подкаталоги называются каталогами верхнего уровня: Кто из нас видел деревья, растущие кронами вниз?

Монтирование и демонтирование файловых систем

При старте системы после загрузки ядра и запуска процесса init инициируется проверка тех файловых систем, которые следует проверить и смонтировать автоматически. Их список содержится в файле /etc/vfstab. Типичный файл /etc/vfstab выглядит так:

#device             device            mount         FS    fsck mount   Mount
#to mount           to fsck           point         type  pass at boot Options
#
Fd                   -                 /dev/fd      fd    -    no      -
/proc                -                 /proc        proc  -    no      -
/dev/dsk/c0d0s1      -                 -            swap  -    no      -
/dev/dsk/c0d0s0      /dev/rdsk/c0d0s0  /            ufs   1    no      -
/dev/dsk/c0d0p0:boot -                 /boot        pcfs  -    no      -
/dev/dsk/c0d0s7/     dev/rdsk/c0d0s7   /export/home ufs   2    yes     -
swap                 -                 /tmp         tmpfs -    yes     -
    

Те файловые системы, которые в столбце mount at boot отмечены как yes, будут проверены и смонтированы при старте системы. Файловую систему можно смонтировать в любой момент, надо лишь указать ей в качестве точки монтирования пустой каталог, который уже создан и доступен в системе. Операцию монтирования и демонтирования файловой системы может осуществить только root.
Монтирование файловой системы выполняется командой mount:

mount device mount_point
    

Например

mount /dev/dsk/c0d1s0 /test
    

Для монтирования файловой системы, которая описана в /etc/vfstab, можно не указывать имя файла устройства, а сразу указать точку монтирования. Такую "сокращенную" команду mount можно применять только для монтирования файловых систем, перечисленных в /etc/vfstab.
При монтировании файловой системы следует явно указывать ее тип, если он отличается от UFS.
Демонтирование файловой системы делает ее недоступной для чтения и записи, файлы, которые расположены на демонтируемом разделе, конечно же, остаются на месте. Просто после демонтирования они не видны: точка монтирования снова превращается в пустой каталог, как это было до монтирования в нее диска или раздела.
Нельзя демонтировать занятую файловую систему. Занятой считается такая файловая система, файл которой открыт в настоящее время кем-то из пользователей, или каталог которой является текущим каталогом кого-то из работающих в системе пользователей.
Чтобы все-таки демонтировать файловую систему, следует найти и устранить причину ее занятости. Часто для этого достаточно просто самому выйти из того каталога, который собираешься демонтировать. Это типичная ошибка системного администратора: пытаться демонтировать /usr в тот момент, когда находишься в /usr/admin или подобном подкаталоге, который лежит в том же разделе, что и /usr.
Демонтирование файловой системы выполняется командой umount:

umount mount_point
    

Например

umount /mnt
    

Монтирование дискет и прочих сменных носителей

Для монтирования дискет, компакт-дисков и других сменных носителей в Solaris имеется специальная программа vold (Volume Management daemon). Она следит за тем, вставлен ли компакт-диск, дискета или, к примеру, zip-диск в соответствующее устройство. Как только диск оказывается в устройстве, vold вызывает программу volcheck, чтобы проверить, действительно ли в привод установили новый диск, а затем программу rmmount для монтирования диска в заранее определенную точку монтирования. Программа rmmount выясняет тип файловой системы вставленного диска, и, если этот тип поддерживается, монтирует диск. Список предопределенных точек монтирования можно посмотреть с помощью

man rmmount
    

Поведение rmmount определяется файлом конфигурации /etc/rmmount.conf.
Программу rmmount можно запускать и вручную. Кроме того, можно использовать команду volrmmount для форсирования операций перемонтирования или демонтирования файловой системы на сменном носителе. Более подробно об этой команде говорится в man volrmmount.

Проверка файловых систем

Широко известная из систем Windows программа scandisk имеет аналог в UNIX - программу fsck. В Solaris fsck по умолчанию проверяет все фаловые системы, перечисленные в /etc/vfstab. Обычно имеет смысл запускать fsck вручную с указанием конкретной файловой системы:

fsck /dev/dsk/c0d0s7
    

Программа fsck проверяет файловую систему и, если находит ошибки, исправляет их. Обнаружив ошибки, об исправлении которых она не может принять самостоятельное решение, fsck выдает сообщение об этом на терминал, с которого ее запустили, и ждет решения администратора.
Если в настоящий момент файловая система смонтирована, fsck не начинает ее проверку. Это правило можно обойти, если потребовать от fsck обращаться к диску как к символьному устройству, а не как к блочному:

fsck /dev/dsk/c0d0s7
/dev/dsk/c0d0s7 is a mounted file system, ignored
fsck /dev/rdsk/c0d0s7
** /dev/rdsk/c0d0s7
** Currently Mounted on /export/home
** Phase 1 - Check Blocks and Sizes
** Phase 2 - Check Pathnames
** Phase 3 - Check Connectivity
** Phase 4 - Check Reference Counts
** Phase 5 - Check Cyl groups
2 files, 9 used, 3823540 free (20 frags, 477940 blocks,
0.0% fragmentation)

 

 
На главную | Содержание | < Назад....Вперёд >
С вопросами и предложениями можно обращаться по nicivas@bk.ru. 2013 г.Яндекс.Метрика