Хрестоматия по программированию на Си в Unix



Системные вызовы и взаимодействие с UNIX. Хрестоматия по программированию на Си в Unix - стр. 12


"Подвисание" файлов в памяти ядра значительно ускоряет работу программ, т.к. работа с памятью гораздо быстрее, чем с диском. Если блок надо считать/записать, а он уже есть в кэше, то реального обращения к диску не происходит. Зато, если случится сбой питания (или кто-то неаккуратно выключит машину), а некоторые буфера еще не были сброшены на диск - то часть изменений в файлах будет потеряна. Для принудительной записи всех измененных кэш-буферов на диск существует сисвызов "синхронизации" содержимого дисков и памяти

sync(); // synchronize

Вызов sync делается раз в 30 секунд специальным служебным процессом /etc/update, запускаемым при загрузке системы. Для работы с файлами, которые должны гарантированно быть корректными на диске, используется открытие файла

fd = open( имя, O_RDWR | O_SYNC);

которое означает, что при каждом write блок из кэш-буфера немедленно записывается на диск. Это делает работу надежнее, но существенно медленнее.

Специальные файлы устройств не могут быть созданы вызовом creat, создающим только обычные файлы. Файлы устройств создаются вызовом mknod:

#include <sys/sysmacros.h>

dev_t dev = makedev(major, minor); /* (major << 8) | minor */ mknod( имяФайла, кодыДоступа|тип, dev);

где dev - пара (мажор,минор) создаваемого устройства; кодыДоступа - коды доступа к файлу (0777); тип - это одна из констант S_IFIFO, S_IFCHR, S_IFBLK из include-файла <sys/stat.h>.

mknod доступен для выполнения только суперпользователю (за исключением случая S_IFIFO). Если бы это было не так, то можно было бы создать файл устройства, связанный с существующим диском, и читать информацию с него напрямую, в обход механизмов логической файловой системы и защиты файлов кодами доступа.

Можно создать файл устройства с мажором и/или минором, не отвечающим никакому реальному устройству (нет такого драйвера или минор слишком велик). Открытие таких устройств выдает код ошибки ENODEV.

Из нашей программы мы можем вызовом stat() узнать код устройства, на котором расположен файл. Он будет содержаться в поле dev_t st_dev; а если файл является специальным файлом (интерфейсом драйвера устройства), то код самого этого устройства можно узнать из поля dev_t st_rdev; Рассмотрим пример, который выясняет, относятся ли два имени к одному и тому же файлу:

#include <sys/types.h>




Содержание  Назад  Вперед