mirror of https://github.com/t1meshift/os_labs.git
39 lines
3.4 KiB
Markdown
39 lines
3.4 KiB
Markdown
|
# Лабораторная работа №8
|
|||
|
|
|||
|
> Разработка сервера с использованием цикла ожидания событий
|
|||
|
|
|||
|
На сервере создаётся и биндится сокет, слушается клиент. Далее в бесконечном цикле с
|
|||
|
использованием `select()` обрабатываются запросы (с возможностью подключения нескольких
|
|||
|
клиентов)
|
|||
|
|
|||
|
Для каждого запроса обрабатывается запрос в plain-text-формате, возвращается ответ в том же формате.
|
|||
|
|
|||
|
Для асинхронной работы использованы неблокирующие сокеты.
|
|||
|
Их отличие в том, что во время выполнения операции программа не блокирует своё исполнение.
|
|||
|
|
|||
|
Используя функцию `fcntl()`, сокеты переводятся в неблокирующий режим.
|
|||
|
Вызов любой функции с таким сокетом будет возвращать управление немедленно.
|
|||
|
|
|||
|
> Добавить обработку сигналов
|
|||
|
|
|||
|
Для обработки сигналов используем системный вызов `signal()`.
|
|||
|
|
|||
|
Существуют и другие подходы для создания сервера с циклом ожидания событий. Например, с использованием `fork()`,
|
|||
|
как это делается, например, в Apache2, где для обработки клиентов заранее делается массив форков (т.к. форк --
|
|||
|
дорогостоящая операция).
|
|||
|
Этот способ подразумевает создание дочернего процесса для обслуживания каждого нового клиента.
|
|||
|
При этом родительский процесс занимается только прослушиванием порта и приёмом соединений.
|
|||
|
|
|||
|
Но у такого подхода есть минусы.
|
|||
|
|
|||
|
1. Если клиентов очень много, создание нового процесса для обслуживания каждого из них может оказаться слишком
|
|||
|
дорогостоящей операцией (решается пулом пре-форков).
|
|||
|
2. Такой способ неявно подразумевает, что все клиенты обслуживаются независимо друг от друга.
|
|||
|
|
|||
|
Для решения этих проблем мы можем использовать `select()`.
|
|||
|
Его плюсы заключаются в разрешении вышеописанных проблем.
|
|||
|
|
|||
|
Минусы заключаются в том, что программы получаются более сложными по сравнению с первым способом,
|
|||
|
а также программа вынуждена отслеживать дескрипторы всех клиентов и работать с ними параллельно
|
|||
|
и каждый раз нужно пробегаться в цикле по дескрипторам всех сокетов и проверять, произошло ли какое-либо событие.
|