реклама на сайте
подробности

 
 
> Использование очереди сообщений
Harvester
сообщение Nov 27 2009, 08:25
Сообщение #1


Местный
***

Группа: Участник
Сообщений: 338
Регистрация: 1-02-06
Из: Королев, М.О.
Пользователь №: 13 846



Здравствуйте.

Помогите пожалуйста разобраться с использованием очереди сообщений.
У меня есть процесс (A), периодически передающий пакеты по UART. Второй процесс (cool.gif может в произвольные моменты требовать от
него передачи пакетов, определяемых пользователем. Для этого я собираюсь использовать очередь сообщений.
Но ведь в очередь заносится только указатель на пакет, а как быть с самими данными, особенно если пришло несколько запросов подряд?

Правильно ли я понимаю, что мне необходимо помимо очереди создать что-то вроде кольцевого буфера и обернуть функции POST и PEND для очереди сообщений в свои функции, которые будут брать/класть указатель из/в очереди, извлекать данные из буфера и обслуживать указатели этого буфера?

Спасибо.

PS. Пока писал сообщение, в голову пришла ещё одна мысль - процесс B динамически выделяет память, а процесс A после вычитывания сообщения её освобождает.


--------------------
-Да как так-то?/-Да как-то так/-Ну так-то да
Go to the top of the page
 
+Quote Post
 
Start new topic
Ответов
Dima_G
сообщение Nov 27 2009, 08:32
Сообщение #2


Местный
***

Группа: Свой
Сообщений: 279
Регистрация: 2-07-08
Из: Новосибирск
Пользователь №: 38 699



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

Динамически выделять / освобождать память не сильно хорошая идея в embedded системах
Go to the top of the page
 
+Quote Post
Harvester
сообщение Nov 27 2009, 08:45
Сообщение #3


Местный
***

Группа: Участник
Сообщений: 338
Регистрация: 1-02-06
Из: Королев, М.О.
Пользователь №: 13 846



Цитата(Dima_G @ Nov 27 2009, 11:32) *
Все зависит от того - что подразумеватеся под элементом очереди. Если буфер (+указатель на следующий элемент), то дополнительного пула не нужно))))

Динамически выделять / освобождать память не сильно хорошая идея в embedded системах


В большинстве осей, в той же uC/OS в очереди хранятся именно указатели.

А по второму замечанию - полностью согласен. Потому, наверное, эта идея пришла только в самый последний момент (как самая негодная) smile.gif

Сообщение отредактировал Harvester - Nov 27 2009, 08:47


--------------------
-Да как так-то?/-Да как-то так/-Ну так-то да
Go to the top of the page
 
+Quote Post
Dima_G
сообщение Nov 27 2009, 08:53
Сообщение #4


Местный
***

Группа: Свой
Сообщений: 279
Регистрация: 2-07-08
Из: Новосибирск
Пользователь №: 38 699



Цитата(Harvester @ Nov 27 2009, 12:45) *
В большинстве осей, в той же uC/OS в очереди хранятся именно указатели.


Ну а что мешает сделать свою очередь?

Ни либо на указателях я бы делал так:
хранил отдельно пул буферов

Создал бы очередь - обозвал бы ее FreeQueue
Создал бы очередь в драйвере - назвал TxQueue;

Далее - приложение берет из очереди FreeQueue указатель (считай - буфер), заполняет буфер и помещает указатель на него в TxQueue

Драйвер обнаруживет в TxQueue пакет, обрабатывает его (передает), и помещает в FreeQueue


как-то так smile.gif
Go to the top of the page
 
+Quote Post
Harvester
сообщение Nov 27 2009, 11:38
Сообщение #5


Местный
***

Группа: Участник
Сообщений: 338
Регистрация: 1-02-06
Из: Королев, М.О.
Пользователь №: 13 846



Цитата(Dima_G @ Nov 27 2009, 11:53) *
Ну а что мешает сделать свою очередь?

Ни либо на указателях я бы делал так:
хранил отдельно пул буферов

Создал бы очередь - обозвал бы ее FreeQueue
Создал бы очередь в драйвере - назвал TxQueue;

Далее - приложение берет из очереди FreeQueue указатель (считай - буфер), заполняет буфер и помещает указатель на него в TxQueue

Драйвер обнаруживет в TxQueue пакет, обрабатывает его (передает), и помещает в FreeQueue


как-то так smile.gif

А ведь так можно вообще обойтись без очереди - использовать пул буферов и счётный семафор!


--------------------
-Да как так-то?/-Да как-то так/-Ну так-то да
Go to the top of the page
 
+Quote Post
zltigo
сообщение Nov 27 2009, 11:59
Сообщение #6


Гуру
******

Группа: Свой
Сообщений: 13 372
Регистрация: 27-11-04
Из: Riga, Latvia
Пользователь №: 1 244



Цитата(Harvester @ Nov 27 2009, 14:38) *
А ведь так можно вообще обойтись без очереди - использовать пул буферов и счётный семафор!

Нафига организовывать очередь руками из дополнительного буфера и семафора, если их поддержка УЖЕ ЕСТЬ в системе.
Если очередь можно пользовать только для указателей, то нужно только добавить к ней один буфер и все.

Цитата(Harvester @ Nov 27 2009, 11:45) *
В большинстве осей, в той же uC/OS в очереди хранятся именно указатели.

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


Цитата(Dima_G @ Nov 27 2009, 11:32) *
Динамически выделять / освобождать память не сильно хорошая идея в embedded системах

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


--------------------
Feci, quod potui, faciant meliora potentes
Go to the top of the page
 
+Quote Post
Dima_G
сообщение Nov 27 2009, 12:23
Сообщение #7


Местный
***

Группа: Свой
Сообщений: 279
Регистрация: 2-07-08
Из: Новосибирск
Пользователь №: 38 699



Цитата(zltigo @ Nov 27 2009, 15:59) *
Нафига организовывать очередь руками из дополнительного буфера и семафора, если их поддержка УЖЕ ЕСТЬ в системе.
Если очередь можно пользовать только для указателей, то нужно только добавить к ней один буфер и все.


Под буфером, Вы имеете в виду - циклический буфер?

Мне большей частью удобнее НЕ использовать системные очереди. Исключительно из-за их "сишной" природы, как следствие - потери информации о типе вложенного объекта
Go to the top of the page
 
+Quote Post
zltigo
сообщение Nov 27 2009, 13:03
Сообщение #8


Гуру
******

Группа: Свой
Сообщений: 13 372
Регистрация: 27-11-04
Из: Riga, Latvia
Пользователь №: 1 244



Цитата(Dima_G @ Nov 27 2009, 15:23) *
Под буфером, Вы имеете в виду - циклический буфер?

Совершенно не имеет значения какой - любой, какой оптимален для данного типа данных, нагрузки и прочего. Довольно часто очень просто и удобно реализуются линейные под фрейм расположенные внутри кольцевого. А если фреймы фиксированной длинны, то сам бог велел так делать - 0 недостатков.
Цитата
Мне большей частью удобнее НЕ использовать системные очереди. Исключительно из-за их "сишной" природы, как следствие - потери информации о типе вложенного объекта

Еруда полная, а не причина, либо тип фиксирован, либо Вы его по любому будете восстанавливать по, например, заголовку.


Цитата(Harvester @ Nov 27 2009, 15:47) *
И если очередь не полна,значит, как минимум, одно из самых ранних сообщение уже вычитано и отправитель может писать данные в очередную секцию кольцевого буфера.

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


--------------------
Feci, quod potui, faciant meliora potentes
Go to the top of the page
 
+Quote Post
Harvester
сообщение Nov 27 2009, 13:41
Сообщение #9


Местный
***

Группа: Участник
Сообщений: 338
Регистрация: 1-02-06
Из: Королев, М.О.
Пользователь №: 13 846



Цитата(zltigo @ Nov 27 2009, 16:03) *
И если полна, то тоже может, ибо должны быть ДВА указателя - на чтение, который проходит через очередь до процесса передачи читающий из буфера передачи и отдельно болтающийся указатель на запись, по которому вне зависимости (ну кроме контроля за фатальным переполнением) от наличия в буфере непереданных фреймов осуществляется запись.

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


--------------------
-Да как так-то?/-Да как-то так/-Ну так-то да
Go to the top of the page
 
+Quote Post
zltigo
сообщение Nov 27 2009, 15:42
Сообщение #10


Гуру
******

Группа: Свой
Сообщений: 13 372
Регистрация: 27-11-04
Из: Riga, Latvia
Пользователь №: 1 244



Цитата(Harvester @ Nov 27 2009, 16:41) *
Что-то теперь я совсем запутался. 07.gif Как может указатель на запись"отдельно болтаться", если именно его необходимо класть в очередь после заполнения фрейма буфера.

Вопросы кто чем для кого является smile.gif возможен взгляд с разных сторон smile.gif. В очередь кладется указатель чтения - по нему процесс передачи читает из буфера, то, что он будет передавать smile.gif. Указатель записи это принадлежность функции, которая заполняет буфер передачи - по нему будет занесен фрейм и его значение до занесения фрейма будет помещено в очередь.
Цитата
И потом, если уж мы используем два указателя, т.е. организуем кольцевой буфер, то какой смысл в очереди? Проще ведь будет использовать счетный семафор, да и по ресурсам выгоднее.

То, что Вы пытаетесь описать, вообще буфера не требует smile.gif, поскольку Вы упорно предполагаете, что в кольцевом буфере по определению рассчитанном на МНОГО фреймов лежит ОДИН. Для одного нужен ОДИН указатель - нет вопросов. Если Мы действительно используем кольцевой буфер, как буфер, а не лишнюю приблуду, то в нем могут лежать МНОГО фреймов, для них нужно МНОГО указателей. Эти указатели и лежат в очереди до того момента, когда процесс передачи извлечет очередной и начнет по нему вытаскивать из буфера информацию.



Цитата(Dima_G @ Nov 27 2009, 17:57) *
соответственно, никто не застрахован от ошибок

Поверье мне, что ошибок Вы и так наделаете.
Цитата
В С++ можно использовать такой подход

Ненужные выкрутасы на ровном месте для ЧАСТНОГО случая. Ничего, кроме лишнего разнообразия в решении не дает.


--------------------
Feci, quod potui, faciant meliora potentes
Go to the top of the page
 
+Quote Post
Dima_G
сообщение Nov 27 2009, 16:11
Сообщение #11


Местный
***

Группа: Свой
Сообщений: 279
Регистрация: 2-07-08
Из: Новосибирск
Пользователь №: 38 699



Цитата(zltigo @ Nov 27 2009, 18:42) *
Поверье мне, что ошибок Вы и так наделаете.

Ненужные выкрутасы на ровном месте для ЧАСТНОГО случая. Ничего, кроме лишнего разнообразия в решении не дает.


Это я уже обсуждать не буду, а то тема сведется к холивару С vs С++.
Остановимся на том, что почему-то мне так удобнее smile.gif


Цитата(Andron_ @ Nov 27 2009, 19:12) *
а можно аргументировать? сам применяю new/delete и пытаюсь понять - будут грабли или нет.


Можно столкнуться с фрагментацией памяти
Ненормированное время выделения памяти
Нереентерабельность выделения памяти
Ну и мое ИМХО - при статическом распределении ресурсов система более предсказуема smile.gif

вот, почитайте - зедсь есть немного про это
http://www.embedded.com/story/OEG20020222S0026

Сообщение отредактировал Dima_G - Nov 27 2009, 16:15
Go to the top of the page
 
+Quote Post
zltigo
сообщение Nov 27 2009, 16:49
Сообщение #12


Гуру
******

Группа: Свой
Сообщений: 13 372
Регистрация: 27-11-04
Из: Riga, Latvia
Пользователь №: 1 244



Цитата(Dima_G @ Nov 27 2009, 19:11) *
Это я уже обсуждать не буду, а то тема сведется к холивару С vs С++.
Остановимся на том, что почему-то мне так удобнее smile.gif

C++ тут АБСОЛЮТНО ни причем - на любом языке можете наваять оберток не имеющих никакого смысла и главное годящихся только для частного случая. Изобразить, например, "специальную очередь" для какого-либо фрейма можно по любому, только кроме лишнего исходного текста и лишних сущностей такие выкрутасы не дают ничего.



Цитата(Dima_G @ Nov 27 2009, 19:11) *
Можно столкнуться с фрагментацией памяти

А можно и нет, если принять меры.
Цитата
Ненормированное время выделения памяти

Ну не надо использовать, например, линукс с файлами подкачки и прочим. Хотя именно в том-же линуксе драйвера делают и много много более мрачные системные вызовы smile.gif
Цитата
Нереентерабельность выделения памяти

Ну это если совсем без головы на плечах.
Цитата
Ну и мое ИМХО - при статическом распределении ресурсов система более предсказуема smile.gif

Эх, конечно. Только вот если с ресурсами напряг и всем нарезать их про запас не хватает?


--------------------
Feci, quod potui, faciant meliora potentes
Go to the top of the page
 
+Quote Post
dxp
сообщение Nov 28 2009, 09:30
Сообщение #13


Adept
******

Группа: Свой
Сообщений: 3 469
Регистрация: 6-12-04
Из: Novosibirsk
Пользователь №: 1 343



Цитата(zltigo @ Nov 27 2009, 22:49) *
C++ тут АБСОЛЮТНО ни причем - на любом языке можете наваять оберток не имеющих никакого смысла и главное годящихся только для частного случая. Изобразить, например, "специальную очередь" для какого-либо фрейма можно по любому, только кроме лишнего исходного текста и лишних сущностей такие выкрутасы не дают ничего.

Вы хотите сказать, что очередь на основе void* ничем не хуже очереди на основе TypeName*? С точки зрения удобства и безопасности использования.


--------------------
«Отыщи всему начало, и ты многое поймёшь» К. Прутков
Go to the top of the page
 
+Quote Post
zltigo
сообщение Nov 28 2009, 10:07
Сообщение #14


Гуру
******

Группа: Свой
Сообщений: 13 372
Регистрация: 27-11-04
Из: Riga, Latvia
Пользователь №: 1 244



Цитата(dxp @ Nov 28 2009, 12:30) *
Вы хотите сказать, что очередь на основе void* ничем не хуже очереди на основе TypeName*? С точки зрения удобства и безопасности использования.


Я хочу сказать, что TypeName* ничем не лучше и делать нечто самодельное похожее на очередь ВМЕСТО механизма очередей системы, по причине того, что очередь с void* есть глупость.

Причем эта поделка не годится, если мы в очередь кладем разные сообщения. Да и если только один тип, то пользы от нее как от козла молока, ибо извлечение из очереди в большинстве случаев в одном месте и ошибиться с приведением (TypeName *) это надо сильно постараться, как и запихнуть в одном-нескольких местах программы очередь нечто другое. Эти экзерсисы что-то вроде подстелить несколько пучков соломки на землю для страховки при возможном падении с 5 этажа - хуже не будет, но и реальной пользы от лишних телодвижений никакой. Родить какую-нибудь конструкцию, например
Цитата
#define put_typename( x ) { TypeName *tmp = x; put( tmp ); }

для "защиты" и создания лишней "своей" очереди я могу и на 'C', только находясь в здравом уме делать такого не буду, а уж тем более изготавливать костыли с TypeName* ВМЕСТО штатной очереди.


--------------------
Feci, quod potui, faciant meliora potentes
Go to the top of the page
 
+Quote Post
Dima_G
сообщение Nov 28 2009, 17:40
Сообщение #15


Местный
***

Группа: Свой
Сообщений: 279
Регистрация: 2-07-08
Из: Новосибирск
Пользователь №: 38 699



Цитата(zltigo @ Nov 28 2009, 13:07) *
Причем эта поделка не годится, если мы в очередь кладем разные сообщения. Да и если только один тип, то пользы от нее как от козла молока, ибо извлечение из очереди в большинстве случаев в одном месте и ошибиться с приведением (TypeName *) это надо сильно постараться, как и запихнуть в одном-нескольких местах программы очередь нечто другое. Эти экзерсисы что-то вроде подстелить несколько пучков соломки на землю для страховки при возможном падении с 5 этажа - хуже не будет, но и реальной пользы от лишних телодвижений никакой. Родить какую-нибудь конструкцию, например

для "защиты" и создания лишней "своей" очереди я могу и на 'C', только находясь в здравом уме делать такого не буду, а уж тем более изготавливать костыли с TypeName* ВМЕСТО штатной очереди.



Ничего личного, но сразу видно отличие Сишного стиля мышления от Сиплюсового. wink.gif
В шаблонную очередь (пример выше) мы можем класть не только объектры ELEMENT, но и наследников от него. Это про "разные сообщения"
Далее - насчет "запихнуть не то - невозвожно". Да леко!
Я кончено понимаю, что специалист Вашего уровня никогда не ошибается, но у меня могут быть промашки - при 10 очередях и 20 типах объектов, которые "гуляют" по ним. И любые средства языка, которые хоть немного могут это предотвратить, я очень приветствую.
Go to the top of the page
 
+Quote Post

Сообщений в этой теме
- Harvester   Использование очереди сообщений   Nov 27 2009, 08:25
|||||- - zltigo   Цитата(Dima_G @ Nov 28 2009, 20:40) Это п...   Nov 28 2009, 18:03
||||- - dxp   Цитата(zltigo @ Nov 28 2009, 16:07) Я хоч...   Nov 29 2009, 15:55
||||- - zltigo   Цитата(dxp @ Nov 29 2009, 18:55) Нет ни о...   Dec 3 2009, 08:09
|||||- - Dima_G   Цитата(zltigo @ Dec 3 2009, 11:09) Вы пох...   Dec 3 2009, 08:26
||||- - zltigo   Цитата(dxp @ Nov 29 2009, 18:55) все выше...   Dec 3 2009, 08:58
||||- - dxp   Цитата(zltigo @ Dec 3 2009, 14:58) Самые ...   Dec 4 2009, 09:18
||||- - Dima_G   Цитата(dxp @ Dec 4 2009, 12:18) Не ...   Dec 4 2009, 09:50
||||- - zltigo   Цитата(dxp @ Dec 4 2009, 12:18) добавив ч...   Dec 4 2009, 10:06
||||- - dxp   Цитата(zltigo @ Dec 4 2009, 16:06) И выну...   Dec 5 2009, 07:22
|||- - Harvester   Цитата(zltigo @ Nov 27 2009, 18:42) Вопро...   Nov 30 2009, 07:36
||- - Dima_G   Цитата(zltigo @ Nov 27 2009, 16:03) Еруда...   Nov 27 2009, 14:57
|- - Harvester   Цитата(zltigo @ Nov 27 2009, 14:59) Нафиг...   Nov 27 2009, 12:47
- - Andron_   ЦитатаДинамически выделять / освобождать память не...   Nov 27 2009, 15:12
- - Ink   ЦитатаВ шаблонную очередь (пример выше) мы можем к...   Nov 29 2009, 02:14
- - Сергей Борщ   Цитата(Ink @ Nov 29 2009, 04:14) если вы ...   Nov 29 2009, 10:52
- - Ink   Цитата(Сергей Борщ @ Nov 29 2009, 13:52) ...   Nov 29 2009, 17:33
- - Сергей Борщ   Цитата(Ink @ Nov 29 2009, 19:33) если фун...   Nov 30 2009, 01:18
- - Ink   Цитата(Сергей Борщ @ Nov 30 2009, 04:18) ...   Dec 2 2009, 10:32
- - dxp   Цитата(Ink @ Dec 2 2009, 16:32) согласен,...   Dec 3 2009, 07:24


Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 21st July 2025 - 21:01
Рейтинг@Mail.ru


Страница сгенерированна за 0.01882 секунд с 7
ELECTRONIX ©2004-2016