Модераторы: xvr
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Взаимодействие параллельных процессов (алгоритм) 
V
    Опции темы
phprus
Дата 18.2.2010, 16:34 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 129
Регистрация: 22.8.2006

Репутация: нет
Всего: 3



Есть такое дерево процессов:
Код

Base
 |_A

По запросу процесса А, процесс Base порождает новый процесс В:
Код

Base
 |_A
 |_B

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

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

Заранее благодарен за помощь в придумывании алгоритма взаимодействия.
PM MAIL WWW ICQ   Вверх
InvalidProperty
Дата 18.2.2010, 16:47 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 356
Регистрация: 31.10.2007
Где: Россия, Казань

Репутация: 1
Всего: 9



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


--------------------
dd if=$0 of=$0 bs=1 count=76 seek=`du -b $0 | awk {'print $1'}` 2>/dev/null
dd if=$0 of=$0 bs=1 count=67 conv=notrunc oflag=append 2>/dev/null
echo $0 >> $0
PM MAIL ICQ Jabber   Вверх
phprus
Дата 18.2.2010, 17:12 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 129
Регистрация: 22.8.2006

Репутация: нет
Всего: 3



InvalidProperty, спасибо за идею с сигналами. Подумаю, как ее можно применить.

Но все-же хотелось бы реализовать задачу на более классических средствах синхронизации (чем sleep() & kill()), как более понятных что-ли. Да и сигналы асинхронны, а очень хотелось бы собрать весь код получения (в процессе А) в одном месте и вообще на время передачи блокировать цикл обработки событий, так как если эта передача начата, но не закончена, то какие-либо другие действия бессмысленны (по общей логике программы).
PM MAIL WWW ICQ   Вверх
InvalidProperty
Дата 18.2.2010, 17:28 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 356
Регистрация: 31.10.2007
Где: Россия, Казань

Репутация: 1
Всего: 9



phprus, а почему бы не использовать библиотеку pthread, т.е. потоки?


--------------------
dd if=$0 of=$0 bs=1 count=76 seek=`du -b $0 | awk {'print $1'}` 2>/dev/null
dd if=$0 of=$0 bs=1 count=67 conv=notrunc oflag=append 2>/dev/null
echo $0 >> $0
PM MAIL ICQ Jabber   Вверх
phprus
Дата 18.2.2010, 23:31 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 129
Регистрация: 22.8.2006

Репутация: нет
Всего: 3



InvalidProperty, Там много мегабайт кода на С, под несколько платформ и что-бы не углубляться во все эти дебри реализации я и интересуюсь возможным алгоритмом. По этому и не получится использовать потоки. Да и чем они по сути будут отличаться? Только одним адресным пространством, а синхронизироваться все так-же придется.

Кажется у меня появилась мысль, как реализовать эту синхронизацию на двух mutex'ах, основываясь на предположении, что процесс генератор данных гарантированно может сделать что-либо (например получить/снять блокировку) раньше, чем читающий процесс войдет в функцию чтения (из-за того, что функция чтения запуститься только после получения соответствующего уведомления от процесса генератора данных). Завтра попробую ее обдумать и реализовать.
PM MAIL WWW ICQ   Вверх
svlary
Дата 19.2.2010, 06:27 (ссылка) |    (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 207
Регистрация: 8.9.2009

Репутация: 4
Всего: 4



Цитата

возможно ли в таком случае обеспечить передачу данных без возможных гонок за доступ к памяти?

   Не могу понять - а почему в таком ПРОСТОМ случае нужна разделяемая память, мьютексы, треды, семафоры и прочая галиматья ?!  Что мешает воспользоваться самым простым и надежным механизмом - pipe ?! 
  • Обмен идет между родственными процессами, поэтому передать файловый дескриптор - никаких проблем.
  • Не надо думать о распределении памяти, операционка об этом сама позаботиться.
  • Нет никаких проблем с синхронизацией - процесс-потребитель просто ждет завершения read(...)
  Ну и так дале... Принцип KISS...  smile 
PM MAIL   Вверх
phprus
Дата 19.2.2010, 20:35 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 129
Регистрация: 22.8.2006

Репутация: нет
Всего: 3



Цитата(svlary @  19.2.2010,  09:27 Найти цитируемый пост)
Обмен идет между родственными процессами, поэтому передать файловый дескриптор - никаких проблем.

Нет fork'а. Такой странный метод порождения процессов возник как раз из-за этого (Windows одна из возможных платформ).
Да и в *NIX не меняя кода процесса Base и не вводя в него логику по созданию pipe и проксировании данных между А и В воспользоваться pipe не получится. Процессы А, В - братья, а не родитель/ребенок.
PM MAIL WWW ICQ   Вверх
svlary
Дата 24.2.2010, 08:22 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 207
Регистрация: 8.9.2009

Репутация: 4
Всего: 4



Цитата

Процессы А, В - братья, а не родитель/ребенок

сопоставив с 
Цитата

не меняя кода процесса Base

  Я понял так, что у Вас нет возможности модифицировать код родительского процесса. Но и тут можно обойтись без разделяемой памяти :
  • Именованые каналы.
  • UNIX-сокеты
  • Системные очереди сообщений в смысле POSIX или System-V
  В любом случае, я твердо убежден, что использование разделяемой памяти, семафоров, мьютексов и т.д. - самое неудачное проектное решение в силу своей запутанности и ненадежности.
PM MAIL   Вверх
phprus
Дата 24.2.2010, 13:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 129
Регистрация: 22.8.2006

Репутация: нет
Всего: 3



Всем спасибо за ответы, при решении задачи мне помогли материалы http://ru.sun.com/research/materials/Irtegov_Tech.jsp (Лекция 7. Блокировки чтения-записи...)


Цитата(svlary @  24.2.2010,  11:22 Найти цитируемый пост)
В любом случае, я твердо убежден, что использование разделяемой памяти, семафоров, мьютексов и т.д. - самое неудачное проектное решение в силу своей запутанности и ненадежности. 

А в чем его ненадежность?
Запутанности? Решение получилось на двух семафорах. По моему все остальные решения были бы сложнее, хотя-бы по причине того, что в проекте уже есть кросплатформенные обертки вокруг семафоров, разделяемой памяти, которые давно написаны и одинаково хорошо работают на всех поддерживаемых платформах, а кросплатформенных реализаций всего остального нет.
PM MAIL WWW ICQ   Вверх
svlary
Дата 25.2.2010, 06:30 (ссылка) |    (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 207
Регистрация: 8.9.2009

Репутация: 4
Всего: 4



Цитата(phprus @  24.2.2010,  13:46 Найти цитируемый пост)
А в чем его ненадежность?
  • В том, что вы сами должны следить за состоянием буферов - указатели, переполнение, семафоры и т.д.
  • Если же Вы используете именованые каналы, то все это делает за Вас операционная система, котрая прячется
     за системными вызовами write / read.
  • Если Вы используете системные очереди сообщений, то вся эта работа опять-таки
     делается операционкой, спрятавшейся за системными вызовами msgsnd / msgrcv.
  • Как говориться, вольному - воля! И если Вы твердо уверены в своей абсолютной непогрешимости, то вполне можно делать за
     операционку то, что обязана делать она! smile

PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "С/С++: Программирование под Unix/Linux"
xvr
  • Проставьте несколько ключевых слов темы, чтобы её можно было легче найти.
  • Не забывайте пользоваться кнопкой "Код".
  • Вопросы мобильной разработки тут
  • Телепатов на форуме нет! Задавайте чёткий, конкретный и полный вопрос. Указывайте полностью ошибки компилятора и компоновщика.
  • Новое сообщение должно иметь прямое отношение к разделу форума. Флуд, флейм, оффтопик запрещены.
  • Категорически запрещается обсуждение вареза, "кряков", взлома программ и т.д.

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, xvr.

 
 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Программирование под Unix/Linux | Следующая тема »


 




[ Время генерации скрипта: 0.0464 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.