Чтение онлайн

на главную - закладки

Жанры

Основы программирования в Linux
Шрифт:

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

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

даже если этот процесс в данный момент — единственный пользователь очереди.

Вам нужно ответить лишь на один важный вопрос: как возвращать ответы клиентам? Простым решением было бы наличие одной очереди для сервера и по одной очереди для каждого клиента. Если одновременно существует много клиентов, такой подход может вызвать проблемы, т.к. потребуется большое количество очередей. Используя в сообщении поле идентификатора сообщения, вы сможете разрешить всем клиентам пользоваться одной очередью и адресовать ответные сообщения конкретным клиентским процессам с помощью включенного в сообщение идентификатора клиентского процесса. Далее каждый клиент может извлекать сообщения, адресованные только ему, оставляя сообщения для других клиентов в очереди.

Для преобразования приложения, работающего с базой данных компакт-дисков, с помощью средств IPC вам придется заменить только файл pipe_imp.c из сопроводительного программного кода к главе 13. Далее мы рассмотрим важные разделы замещающего файла ipc_imp.c.

Пересмотр функций сервера

Сначала нужно обновить серверные функции.

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

#include "cd_data.h"

#include "cliserv.h"

#include <sys/msg.h>

#define SERVER_MQUEUE 1234

#define CLIENT_MQUEUE 4321

struct msg_passed {

 long int msg_key; /* Используется для клиентского pid */

 message_db_t real message;

};

2. Две глобальные переменные хранят идентификаторы двух очередей, возвращаемые функцией

msgget
:

static int serv_qid = -1;

static int cli_qid = -1;

3. Сделайте сервер ответственным за создание обеих очередей сообщений:

int server starting {

#if DEBUG_TRACE

 printf("%d :- server_starting\n", getpid);

#endif

 serv_qid = msgget((key_t)SERVER_MQUEUE, 0666 | IPC_CREAT);

 if (serv_qid == -1) return(0);

 cli_qid = msgget((key_t)CLIENT_MQUEUE, 0666 | IPC_CREAT);

 if (cli_qid == -1) return(0);

 return(1);

}

4. За

удаление очереди, если она существует, также отвечает сервер. Когда сервер заканчивает работу, вы задаете недопустимые значения вашим глобальным переменным. Это позволит выловить любые ошибки при попытке сервера отправить сообщения после вызова функции
server_ending
:

void server_ending {

#if DEBUG_TRACE

 printf("%d :- server_ending\n", getpid);

#endif

 (void)msgctl(serv_qid, IPC_RMID, 0);

 (void)msgctl(cli_qid, IPC_RMID, 0);

 servqid = -1;

 cliqid = -1;

}

5. Серверная функция

read
читает из очереди сообщение любого типа (т.е. от любого клиента) и возвращает часть сообщения с данными (пропуская тип сообщения):

int read_request_from_client(message_db_t *rec_ptr) {

 struct msg_passed my_msg;

#if DEBUG_TRACE

 printf("%d :- read_request_from_client\n", getpid);

#endif

 if (msgrcv(serv_qid, (void *)&my_msg, sizeof(*rec_ptr), 0, 0) == -1) {

return(0);

 }

 *rec_ptr = my_msg.real_message;

 return(1);

}

6. При отправке сообщения для его адресации используется ID клиентского процесса, хранящийся в запросе:

int send_resp_to_client(const message_db_t mess_to_send) {

 struct msg_passed my_msg;

#if DEBUG_TRACE

 printf("%d :- send_resp_to_client\n", getpid);

#endif

 my_msg.real_message = mess_to_send;

 my_msg.msg_key = mess_to_send.client_pid;

 if (msgsnd(cli_qid, (void *)&my_msg, sizeof(mess_to_send), 0) == -1) {

return(0);

 }

 return(1);

}

Пересмотр функций клиента

Теперь нужно внести изменения в клиентские функции.

1. Когда клиент стартует, ему нужно найти идентификаторы серверной и клиентской очередей. Клиент не создает очереди. Если сервер не работает, эта функция завершится аварийно, поскольку не существует очередей сообщений.

int client starting {

#if DEBUG_TRACE

Поделиться:
Популярные книги

Воплощение Похоти

Некрасов Игорь
1. Воплощение Похоти
Фантастика:
юмористическое фэнтези
попаданцы
рпг
аниме
5.00
рейтинг книги
Воплощение Похоти

Запасная дочь

Зика Натаэль
Фантастика:
фэнтези
6.40
рейтинг книги
Запасная дочь

Октябрь, который ноябрь

Валин Юрий Павлович
Выйти из боя
Фантастика:
попаданцы
альтернативная история
4.60
рейтинг книги
Октябрь, который ноябрь

Барон нарушает правила

Ренгач Евгений
3. Закон сильного
Фантастика:
фэнтези
попаданцы
аниме
5.00
рейтинг книги
Барон нарушает правила

Я - злодейка в дораме. Сезон второй

Вострова Екатерина
2. Выжить в дораме
Фантастика:
уся
фэнтези
сянься
попаданцы
5.00
рейтинг книги
Я - злодейка в дораме. Сезон второй

Призыватель нулевого ранга. Том 2

Дубов Дмитрий
2. Эпоха Гардара
Фантастика:
попаданцы
аниме
фэнтези
5.00
рейтинг книги
Призыватель нулевого ранга. Том 2

На границе империй. Том 10. Часть 3

INDIGO
Вселенная EVE Online
Фантастика:
боевая фантастика
космическая фантастика
попаданцы
5.00
рейтинг книги
На границе империй. Том 10. Часть 3

Бастард Императора. Том 5

Орлов Андрей Юрьевич
5. Бастард Императора
Фантастика:
попаданцы
аниме
фэнтези
5.00
рейтинг книги
Бастард Императора. Том 5

Принятие

Хайд Адель
3. История Ирэн
Фантастика:
попаданцы
альтернативная история
фэнтези
6.00
рейтинг книги
Принятие

Неофит

Листратов Валерий
3. Ушедший Род
Фантастика:
попаданцы
аниме
фэнтези
5.00
рейтинг книги
Неофит

Кодекс Императора II

Сапфир Олег
2. Кодекс Императора
Фантастика:
аниме
фэнтези
попаданцы
5.00
рейтинг книги
Кодекс Императора II

Магнатъ

Кулаков Алексей Иванович
4. Александр Агренев
Приключения:
исторические приключения
8.83
рейтинг книги
Магнатъ

Двенадцатая реинкарнация. Трилогия

Богдашов Сергей Александрович
Фантастика:
боевая фантастика
5.60
рейтинг книги
Двенадцатая реинкарнация. Трилогия

Законы рода

Мельник Андрей
1. Граф Берестьев
Фантастика:
фэнтези
боевая фантастика
аниме
5.00
рейтинг книги
Законы рода