Unix2016/Занятие 21 (15 декабря)
Содержание
Файловая система
inode
inode, индексный дескриптор — это структура данных в традиционных для ОС UNIX файловых системах. В этой структуре хранится метаинформация о стандартных файлах, каталогах или других объектах файловой системы, кроме непосредственно данных и имени.
Каждый файл имеет свой индексный дескриптор, идентифицируемый по уникальному номеру (часто называемому i-номером или инодом) в файловой системе, в которой располагается сам файл.
Индексные дескрипторы хранят информацию о файлах, такую как принадлежность владельцу (пользователю и группе), режим доступа (чтение, запись, запуск на выполнение) и тип файла.
Атрибуты
- длина файла в байтах;
- идентификатор (ID) устройства (это идентифицирует устройство, содержащее файл);
- ID пользователя, являющегося владельцем файла;
- ID группы файла;
- режим файла, определяющий какие пользователи могут считывать, записывать и запускать файл;
- Timestamp указывает дату последнего изменения инода (ctime, change time), последней модификации содержимого файла (mtime, modification time), и последнего доступа (atime, access time);
- счетчик ссылок указывают количество жестких ссылок, указывающих на индексный дескриптор;
- указатели на блоки диска, хранящие содержимое файла.
Особенности
Файловые системы, использующие индексные дескрипторы, имеют несколько неочевидных особенностей:
- Если несколько имен указывают на один и тот же индексный дескриптор (жёсткие ссылки), то все имена считаются эквивалентными. Первое созданное имя никаким особым положением не обладает. Это отличается от поведения похожих символьных ссылок, которые зависят от первоначального имени.
- Индексный дескриптор может совсем не иметь ссылок. Обычно такой файл должен быть удален с диска (именно поэтому программы типа undelete в Unix не позволяют установить точное имя удалённого файла), а его ресурсы должны освободиться (это нормальный процесс удаления файла), но если какие-либо процессы ещё не закрыли файл, то они могут удерживать доступ к нему, а файл будет окончательно удален только после того, как будет закрыто последнее обращение к нему. Это относится и к исполняемым копиям, которые удерживаются открытыми процессами, их выполняющими. По этой причине при обновлении программы рекомендуется удалять старую копию и создавать новый индексный дескриптор для обновленной версии, чтобы никакие экземпляры старой версии не продолжали выполняться.
- Обычно нет возможности сопоставить открытый файл и его имя, по которому он был открыт. Операционная система преобразует имя файла в номер индексного дескриптора при первом же удобном случае, а затем «забывает» про использованное имя файла. Таким образом, функции библиотек getcwd() и getwd() начинают искать в родительском каталоге файл с индексным дескриптором, совпадающим с файлом «.» каталога; затем ищут родительский каталог для текущего, и так далее пока не достигнут «/» каталога. SVR4 и Linux используют дополнительную информацию (поля) в индексных дескрипторах для избежания подобного неудобства.
- Ранее было возможно применять жёсткие ссылки на каталоги. Это делало структуру каталогов ориентированным графом вместо дерева (то есть связного графа с N-1 ребрами и N узлами). Например, каталог имел возможность быть собственным родителем. Современные файловые системы не допускают подобных двусмысленностей, за исключением корневого каталога, который считается собственным родителем.
- Номер индексного дескриптора файла остается неизменным при перемещении файла в другой каталог на том же устройстве или при дефрагментации диска. Поэтому перемещения или каталога, содержащего файл, или его содержимого (или и того и другого вместе) недостаточно для предотвращения доступа к нему из уже запущенного процесса, если у процесса есть возможность вычислить номер индексного дескриптора. Это также обусловливает то, что полностью управляемое поведение индексных дескрипторов невозможно реализовать на множестве файловых систем, не произошедших от стандартной файловой системы UNIX, таких как FAT и его преемников, которые не имеют возможности хранить подобную постоянную 'неизменность', когда каталог файла и его содержимое перемещается.
Пример: восстановление удалённого незакрытого файла
sobols@sobols-VirtualBox:~/20161215/undelete$ less hello.txt & sobols@sobols-VirtualBox:~/20161215/undelete$ rm hello.txt sobols@sobols-VirtualBox:~/20161215/undelete$ pgrep less 4404 sobols@sobols-VirtualBox:~/20161215/undelete$ lsof -p 4404 COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME less 4404 sobols cwd DIR 8,1 4096 283261 /home/sobols/20161215/undelete less 4404 sobols rtd DIR 8,1 4096 2 / less 4404 sobols txt REG 8,1 169800 262220 /bin/less ... less 4404 sobols 4r REG 8,1 35711 283262 /home/sobols/20161215/undelete/hello.txt (deleted) sobols@sobols-VirtualBox:~/20161215/undelete$ ls /proc/4404/fd/ -l total 0 lrwx------ 1 sobols sobols 64 Снж 15 02:26 0 -> /dev/pts/0 lrwx------ 1 sobols sobols 64 Снж 15 02:26 1 -> /dev/pts/0 lrwx------ 1 sobols sobols 64 Снж 15 02:26 2 -> /dev/pts/0 lr-x------ 1 sobols sobols 64 Снж 15 02:26 3 -> /dev/tty lr-x------ 1 sobols sobols 64 Снж 15 02:26 4 -> /home/sobols/20161215/undelete/hello.txt (deleted) sobols@sobols-VirtualBox:~/20161215/undelete$ cp /proc/4404/fd/4 hello2.txt
Файловые системы
ext2
Second Extended File System (дословно: «вторая расширенная файловая система»), сокращённо ext2 (иногда ext2fs). Была разработана Реми Кардом взамен существующей тогда ext в 1992 г. По скорости и производительности работы она может служить эталоном в тестах производительности файловых систем.
Главный недостаток ext2 (и одна из причин демонстрации столь высокой производительности) заключается в том, что она не является журналируемой файловой системой. Он был устранён в файловой системе ext3 — следующей версии Extended File System, полностью совместимой с ext2.
ext3
Third extended file system (третья версия расширенной файловой системы), сокращённо ext3 или ext3fs — журналируемая файловая система.
Эта файловая система очень похожа на ext2, отличается только наличием журнала.
ext4
Fourth extended file system (четвёртая расширенная файловая система (ФС)), сокр. ext4, или ext4fs — журналируемая ФС, основана на ФС ext3, выпущена в 2006 г.
ReiserFS
XFS
ZFS
Btrfs
Сетевые ФС
Позволяют подключать (монтировать) удалённые файловые системы через сеть.
Сетевая ФС предоставляет клиентам прозрачный доступ к файлам и файловой системе сервера. В отличие от протоколов вроде FTP, ФС осуществляет доступ только к тем частям файла, к которым обратился процесс, и основное достоинство его в том, что он делает этот доступ прозрачным. Это означает, что любое приложение клиента, которое может работать с локальным файлом, с таким же успехом может работать и с сетевым файлом, без каких либо модификаций самой программы.
NFS
Network File System (NFS) — протокол сетевого доступа к файловым системам, первоначально разработан Sun Microsystems в 1984 году.
NFS абстрагирован от типов файловых систем как сервера, так и клиента, существует множество реализаций NFS-серверов и клиентов для различных операционных систем и аппаратных архитектур. Наиболее зрелая версия NFS — v.4.
Протокол удаленного вызова процедур (RPC) определяет формат всех взаимодействий между клиентом и сервером. Каждый запрос NFS посылается как пакет RPC.
Использует порты 111 (TCP и UDP) и 2049 (TCP и UDP). До NFSv2 включительно по умолчанию использовался UDP, начиная с NFSv3 используется TCP.
NSF до v3 включительно были stateless-протоколами. v4 уже является stateful.
nfsd — основной демон сервера.
На клиенте монтируется через mount:
sudo mount -t nfs 192.168.1.23:/data /mnt/nfs
SMB/CIFS
SMB (сокр. от англ. Server Message Block) — сетевой протокол прикладного уровня для удалённого доступа к файлам, принтерам и другим сетевым ресурсам. Первая версия протокола, также известная как Common Internet File System (CIFS), была разработана компаниями IBM, Microsoft, Intel и 3Com в 1980-х годах; вторая (SMB 2.0) была создана Microsoft и появилась в Windows Vista. В настоящее время SMB связан главным образом с операционными системами Microsoft Windows, где используется для реализации «Сети Microsoft Windows» (англ. Microsoft Windows Network) и «Совместного использования файлов и принтеров» (англ. File and Printer Sharing).
SMB может работать или непосредственно по TCP (порт 445), или поверх NetBIOS API (а он уже, в свою очередь, может использовать порты UDP 137, 138 и порты TCP 137, 139).
Samba — пакет программ, которые позволяют обращаться к сетевым дискам и принтерам на различных операционных системах по протоколу SMB/CIFS. Имеет клиентскую и серверную части.
Выводы
NFS опирается на подход, традиционный в UNIX-системах (способы блокирования файлов, кэширования, передачи информации о пользователях). Например, в NFS нет поддержки блокирования файла по режиму работы: нельзя, открыв файл, заблокировать другим его удаление, запись или чтение. В общем случае в CIFS нет сведений о unix permissions и uid и gid файла.
SMB-шары в Linux можно использовать ограниченно (не со всеми возможностями), а с NFS в роли клиента плохо работает Windows.
FUSE
Filesystem in Userspace (FUSE) — модуль для ядер Unix-подобных операционных систем, позволяет разработчикам создавать новые типы файловых систем, доступные для монтирования пользователями без привилегий (прежде всего — виртуальных файловых систем); это достигается за счёт запуска кода файловой системы в пользовательском пространстве, в то время как модуль FUSE предоставляет связующее звено для актуальных интерфейсов ядра. C использованием средств FUSE разработаны, в частности, SSHFS, NTFS-3G, GlusterFS.
Доступна для Linux, FreeBSD, OpenBSD, NetBSD (as puffs), OpenSolaris, Minix 3, Android и macOS.
Диски в оперативной памяти
Использование ramdisk в Linux (ramdisk, ramfs, tmpfs) или препарирование рамдисков
Выглядят как внешняя память, но находятся во внутренней памяти. На порядки быстрее HDD и SSD. При перезагрузке все данные теряются.
В Linux существуют три реализации технологии диска в оперативной памяти (три ступени эволюции). В статьях, которые можно найти в интернете, наблюдается путаница.
ramdisk
- представляется в виде блочного устройства /dev/ram (может быть несколько, нумеруются с 0);
- имеет строго фиксированный размер (изменить непросто, или опцией загрузки, или путём перекомпиляции ядра);
- должен быть отформатирован в какую-либо файловую систему (обычно рекомендуется ext2, т. к. журналирование не нужно);
- как и реальное устройство, точно так же использует возможности кеширования данных (page cache), лишние накладные расходы;
- не может использовать swap раздел, если не хватает свободной физической памяти.
ramfs
Это более грамотная и усовершенствованная реализация технологии. Особенностью ее является то, что нет необходимости создавать специальное блочное устройство и форматировать его.
mount -v -t ramfs ramfs /mnt/ramfs/
Mount options for ramfs: Ramfs is a memory based filesystem. Mount it and you have it. Unmount it and it is gone. Present since Linux 2.3.99pre4. There are no mount options.
То есть, остается просто смонтировать файловую систему ramfs и она у вас будет. При этом, использованная, но уже не используемая память теперь умеет освобождаться.
Недостатки такие. Фактически, при монтировании данного типа файловой системы не представляется возможным указать предельный размер. То есть, существует параметр задающий размер диска, но этот параметр задает размер куска, который отрубается от оперативной памяти сразу при монтировании (стартовый размер). При этом ограничить рост занимаемых данных более стартового размера невозможно. Этот недостаток требует от приложений, которые будут писать в что-либо ramfs, контроля размера записываемых данных.
tmpfs
На текущий момент, tmpfs это самый совершенный способ. Tmpfs ранее именовалась как shmfs (shared memory filesystem).
- раздел tmpfs можно ограничить по размеру,
- tmpfs при нехватке основной памяти научился использовать swap раздел;
- если размер рамдиска не указан явно, то диск монтируется в половину размера ОЗУ.
mount -t tmpfs tmpfs /mnt/tmpfs/ -o size=100M
Блокировки
Beej's Guide to Unix IPC: 6. File Locking
Атомарность файловых операций
rewrite existing file so that it gets replaced by new version atomically, only once fully written
mv, link, symlink, mkdir and some ways of opening files are atomic.
Отладка ФС
Можно посмотреть, в каких блоках физически размещается файл. How do I list a file's data blocks on Linux?
Ядро Linux
История
Разработка кода ядра была начата финским студентом Линусом Торвальдсом в 1991 году, на его имя зарегистрирована Торговая марка Linux.
Версии
- «Ванильные» (vanilla) ядра, то есть официальные ядра с сайта kernel.org без каких-либо сторонних изменений.
- Альтернативные ветки, которые могут быть взяты из различных источников. Как правило, разработчики дистрибутивов Linux поддерживают свои собственные версии ядра, например, включая в них драйверы устройств, которые ещё не включены в официальную версию.
Про отличия: What are the differences between the Ubuntu shipped kernel and the upstream kernel?
Нумерация версий
Сначала версии нумеровались 0.01, 0.02, 0.03, ... и до 1.0.
Затем начали использовать схему a.b.c (от версии 1.0 до версии 2.6). a — версия ядра, b — мажорная ревизия, c — минорная ревизия. Первое число изменялось при очень крупных переработках концепции ядра. Это было дважды в истории: в 1994 (version 1.0) и в 1996 (version 2.0). Чётность числа b определяла стабильность ядра: нечётные числа — разработческие версии, чётные числа — стабильные версии. Минорная версия c увеличивалась при фиксах багов и при исправлениях в безопасности.
В 2004 г. после релиза 2.6.0 схема нумерации версий поменялась. Префикс 2.6 сохранялся в течение семи лет, последняя цифра увеличивалась с каждым релизом раз в два-три месяца. Иногда при срочных фиксах добавлялось четвёртое число (2.6.8.1). Чётно-нечётная схема упразднена. Разработческие версии имеют суффикс -rc.
Версия 3.0, выпущенная в 2011 г., не имела каких-то серьёзных изменений концепции. Следовала после версии 2.6.39. Считается, что Линус так решил, потому что число стало слишком большим, и чтобы заодно отметить 20-летие Linux.
Затем релизы продолжили идти по времени, но с увеличением уже второй цифры, а не третьей.
После 3.19 выпустили версию 4.0 (в 2015 г.).
Разработка
Код написан в основном на C с некоторыми расширениями gcc и на ассемблере (с использованием AT&T-синтаксиса GNU Assembler).
Kernel Newbies: First Kernel Patch Kernel Newbies: Kernel Documentation
Изначально в разработке не использовалась автоматизированная система контроля версий из-за нелюбви Линуса к таким системам. В 2002 г. начали использовать BitKeeper, но это была коммерческая система. В 2005 г. Торвальдс и команда за две недели написали новую систему контроля версий — git.
Узнать версию ядра
uname -r