
- •Введение
- •Лабораторная работа 1.
- •Регистрация пользователя в системе
- •Выход из системы
- •Выполнение простых команд
- •Группирование команд
- •Задание для самостоятельной работы
- •Контрольные вопросы
- •Задание для самостоятельной работы
- •Контрольные вопросы
- •Задание для самостоятельной работы
- •Контрольные вопросы
- •Задание для самостоятельной работы
- •Контрольные вопросы
- •Литература
- •5.3. Задание для самостоятельной работы
- •5.4. Контрольные вопросы
- •Задание для самостоятельной работы
- •Контрольные вопросы
- •Задание для самостоятельной работы
- •Формат файла /etc/passwd
- •Формат файла /etc/shadow
- •Формат файла /etc/group
- •Создание нового пользователя
- •Переключение между пользователями
- •Файлы инициализации пользователей
- •Файлы, регламентирующие работу пользователей
- •Задания для самостоятельной работы
- •Контрольные вопросы
- •9.3. Права доступа к каталогам
- •9.4. Смена прав доступа на файлы
- •9.5. Маска на вновь создаваемые файлы
- •9.6. Дополнительные атрибуты файла
- •9.7. Списки управления доступом
- •Задания для самостоятельной работы
- •Контрольные вопросы
- •10.3. Метасимволы или шаблоны
- •10.4. История команд
- •10.5. Псевдонимы
- •10.6. Перенаправление ввода и вывода
- •10.7. Конвейеры
- •10.8. Приглашение ко вводу
- •10.9. Сценарии оболочки
- •10.10. Задания для самостоятельной работы
- •10.11. Контрольные вопросы
- •11.3. Системный вызов open()
- •11.4. Системный вызов read()
- •11.5. Системный вызов write()
- •11.6. Системный вызов lseek()
- •11.7. Системный вызов close()
- •11.8. Задания для самостоятельной работы
- •11.9. Контрольные вопросы
- •12.3. Системный вызов fork
- •12.4. Системный вызов exit
- •12.5. Системный вызов wait
- •12.6. Системный вызов exec
- •12.7. Системные вызовы наследования пользовательских дескрипторов файла
- •12.8. Задания для самостоятельной работы
- •12.9. Контрольные вопросы
- •13.3. Системный вызов signal
- •13.4. Системный вызов pause
- •13.5. Системный вызов alarm
- •13.6. Управление непредусмотренными событиями
- •13.7. Неименованные каналы
- •13.8. Именованные каналы
- •13.9. Задания для самостоятельной работы
- •13.10. Контрольные вопросы
- •Литература
- •Заключение
- •Учебное издание
- •Системное программирование Лабораторный практикум
11.5. Системный вызов write()
Системный вызов write() позволяет записывать информацию в файл. Преимущество write() состоит в том, что он обходит дополнительный этап буферирования, обеспечиваемый библиотечными функциями С, и поэтому является очень быстрым. Синтаксис системного вызова следующий: ssize_t write (int fd, void* buf, size_t count). Системный вызов write() копирует count байтов из буфера buf в файл, заданный дескриптором файла fd. Байты записываются, начиная с текущей позиции файлового указателя, который затем обновляется. Если флаг O_APPEND был установлен для fd, позиция файлового указателя перемешается на конец файла перед каждой записью. Если системный вызов завершился успешно, write() возвращает количество записанных байтов, иначе возвращает -1.
Пример. Запись в файл. Следующие строки демонстрируют выполнение записи:
charsWritten = write (fd, buffer, charsRead);
if (charsWritten != charsRead) fatalError();
11.6. Системный вызов lseek()
Системный вызов lseek() позволяет изменять текущую позицию дескриптора файла. Синтаксис системного вызова следующий: off_t lseek (int fd, off_t offset, int mode), где fd – дескриптор файла, offset – смещение. Параметр mode описывает, как смещение должно интерпретироваться. Три возможных режима определены в файле /usr/include/stdio.h и имеют значения, представленные в таблице 11.4.
Таблица 11.4
Режимы смещения
Величина |
Описание |
SEEK_SET |
Смещение offset относительно начала файла |
SEEK_CUR |
Смещение offset относительно текущей позиции файла |
SEEK_END |
Смещение offset относительно конца файла |
Системный вызов lseek() завершается с ошибкой, если будет осуществлена попытка перемещения за начало файла. Если системный вызов завершился успешно, lseek() возвращает текущую позицию файла, иначе возвращает -1.
11.7. Системный вызов close()
Системный вызов close() позволяет освободить дескриптор файла. Синтаксис системного вызова следующий: int close (int fd), где fd – дескриптор файла. Если fd – последний дескриптор файла, связанный с конкретным открытым файлом, ресурсы ядра, отведенные для файла, освобождаются. Если осуществляется попытка закрытия файла, который уже закрыт, происходит ошибка. При нормальном завершении системный вызов close() возвращает 0, иначе возвращает -1.
Пример. Закрытие файла. Следующая строка демонстрирует выполнение закрытия файла:
close (fd);
11.8. Задания для самостоятельной работы
1. Напишите программу на языке Си копирования файла в файл с использованием описанных выше системных вызовов.
2. Напишите программу на языке Си организации файла прямого доступа с использованием системного вызова lseek().
3. Напишите программу на языке Си, которая переставляет символы строки из ввода в обратном порядке и посылает их на стандартный вывод.
4. Разработайте программу на языке Си, которая в результате своего выполнения создавала бы файл с именем name и помещала в него N логических блоков, не содержащих никакой информации, а размер логического блока был бы равен S байт.
5. Разработайте программу на языке Си, которая последовательно обрабатывала бы несколько текстовых файлов так, чтобы число этих файлов можно было бы указать в командной строке.