|
|
  |
Логирование данных в файл. |
|
|
|
Mar 20 2018, 12:28
|
Гуру
     
Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713

|
Цитата(Jenya7 @ Mar 20 2018, 14:14)  у меня ОС с задачами. выделить одну задачу на забор пакетов из очереди и записи в файл? Как тут уже сказали - должна быть отдельная задача, которая вычитывает данные из очереди и пишет их в файл. Но кроме того, и многозадачное добавление данных в очередь тоже должно быть потокобезопасным. Цитата(Jenya7 @ Mar 20 2018, 14:24)  какие? только не говорите sprintf  Нет. Я говорил уже не раз на форуме: stdlib IAR-а (и многих других компиляторов) имеет внутреннюю функцию: extern "C" int _Printf( void *(*)(void *, int), void *, const char *, va_list *);
Она не декларирована в IAR-овских хидерах, но все прочие декларированные вовне printf, sprintf, vsprintf и всё это семейство внутри вызывают именно её. Она обладает максимальными возможностями из всего этого семейства printf*, включает всё. Я у себя в проектах IAR использую только её. И никаких других sprintf() или чего-то ещё.
|
|
|
|
|
Mar 20 2018, 12:31
|
Профессионал
    
Группа: Участник
Сообщений: 1 778
Регистрация: 29-03-12
Пользователь №: 71 075

|
Цитата(jcxz @ Mar 20 2018, 17:24)  Как тут уже сказали - должна быть отдельная задача, которая вычитывает данные из очереди и пишет их в файл. Но кроме того, и многозадачное добавление данных в очередь тоже должно быть потокобезопасным. а я вот туплю - как инициализировать семафор. я пользовался уже готовыми semTake, semGive. Цитата(jcxz @ Mar 20 2018, 17:28)  Нет. Я говорил уже не раз на форуме: stdlib IAR-а (и многих других компиляторов) имеет внутреннюю функцию: extern "C" int _Printf( void *(*)(void *, int), void *, const char *, va_list *); Она не декларирована в IAR-овских хидерах, но все прочие декларированные вовне printf, sprintf, vsprintf и всё это семейство внутри вызывают именно её. Она обладает максимальными возможностями из всего этого семейства printf*, включает всё. Я у себя в проектах IAR использую только её. И никаких других sprintf() или чего-то ещё. вы уж меня извините но тащить этого монстра в свой проект я не буду.
|
|
|
|
|
Mar 20 2018, 12:38
|
Гуру
     
Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713

|
Цитата(Jenya7 @ Mar 20 2018, 14:30)  а я вот туплю - как инициализировать семафор. я пользовался уже готовыми semTake, semGive. Я не знаю как это делать в vxWork - не использовал её. Но да - потокобезопасное добавление данных в очередь можно сделать на базе семафора. Это один из вариантов. Другие варианты: а) критическая секция; б) интерфейс на базе аналога InterlockedCompareExchangePointer() + дин.память; в)...? Цитата(Jenya7 @ Mar 20 2018, 14:31)  вы уж меня извините но тащить этого монстра в свой проект я не буду.  В смысле?? А это разве не Ваше?: Цитата(Jenya7 @ Mar 20 2018, 11:02)  У меня по всему коду разбросанны сообщения типа printf ("LIB ID = %d\n", lib_id); Читайте внимательнее мои посты: Любая printf*-функция внутри вызывает _Printf() (в IAR). Воспользуйтесь отладчиком чтобы убедиться. Так что Вы затащили ещё большего "монстра" к себе
|
|
|
|
|
Mar 20 2018, 12:53
|
Профессионал
    
Группа: Участник
Сообщений: 1 778
Регистрация: 29-03-12
Пользователь №: 71 075

|
Цитата(jcxz @ Mar 20 2018, 17:38)  Я не знаю как это делать в vxWork - не использовал её. Но да - потокобезопасное добавление данных в очередь можно сделать на базе семафора. Это один из вариантов. Другие варианты: а) критическая секция; б) интерфейс на базе аналога InterlockedCompareExchangePointer() + дин.память; в)...? В смысле?? А это разве не Ваше?: Читайте внимательнее мои посты: Любая printf*-функция внутри вызывает _Printf() (в IAR). Воспользуйтесь отладчиком чтобы убедиться. Так что Вы затащили ещё большего "монстра" к себе  нет. это - printf ("LIB ID = %d\n", lib_id); - в vxWork - там мне не важно, там у меня мощный камень и ОС. но в проектах на IAR я printf не использую.
|
|
|
|
|
Mar 20 2018, 13:02
|

Познающий...
     
Группа: Свой
Сообщений: 2 963
Регистрация: 1-09-05
Из: г. Иркутск
Пользователь №: 8 125

|
QUOTE (Jenya7 @ Mar 20 2018, 18:12)  я не думаю что очередь дает какие то преимущества. Эстетические) Процессы асинхронно просто вызывают некую функцию CODE pushMsgToLog(...) , которая уже внутри помещает сообщение в очередь. Получается естественно. Другая задача асинхронно читает очередь, и получив очередное сообщение, форматирует его, готовит к записи в соответствующий файл.
--------------------
Выбор.
|
|
|
|
|
Mar 20 2018, 13:08
|
Профессионал
    
Группа: Свой
Сообщений: 1 214
Регистрация: 23-12-04
Пользователь №: 1 643

|
Приветствую! Цитата(haker_fox @ Mar 20 2018, 16:02)  Эстетические) ... И не только красота - правильная очередь и функция записи в нее позволить логровать например из прерываний или из других нехороших мест куда обычному printf вход заказан. Удачи! Rob.
|
|
|
|
|
Mar 20 2018, 13:30
|
Профессионал
    
Группа: Свой
Сообщений: 1 214
Регистрация: 23-12-04
Пользователь №: 1 643

|
Приветствую! Цитата(jcxz @ Mar 20 2018, 16:15)  Заказан кем? Достаточный размер стека и... вуаля! - sprintf прекрасно работает и из ISR.  Вобще то printf и sprintf это немного разные пчелы - жужжат по разному. И стек этот наверное прямо в мозгу программиста будет - чтобы инфу получал без IO функций. Удачи! Rob.
|
|
|
|
|
Mar 20 2018, 15:10
|
Гуру
     
Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713

|
Цитата(RobFPGA @ Mar 20 2018, 15:30)  Вобще то printf и sprintf это немного разные пчелы - жужжат по разному. И стек этот наверное прямо в мозгу программиста будет - чтобы инфу получал без IO функций.  Вы не поверите, но практически одинаковые! Так как внутри они почти сразу вызывают указанную мной _Printf(). Только одна в первом аргументе передаёт ей указатель на callback-функцию записи в ОЗУ, а другая - на callback-функцию записи в поток ввода/вывода. У меня, например, среди прочего _Printf() пишет прямо в поток TCP-сокета (расчленяя вывод на лету на отдельные кадры без промежуточного буфера и поддерживая ретрансмиссию тоже без буфера). Свои callback-функции для _Printf() невероятно расширяют её возможности. Всё ограничивается только фантазией программиста. А уж тривиальный вывод в буфер ограниченного размера делается через _Printf() на раз.
|
|
|
|
|
Mar 20 2018, 15:30
|
Профессионал
    
Группа: Свой
Сообщений: 1 214
Регистрация: 23-12-04
Пользователь №: 1 643

|
Приветствую! Цитата(jcxz @ Mar 20 2018, 18:10)  Вы не поверите, но практически одинаковые! Так как внутри они почти сразу вызывают указанную мной _Printf(). Только одна в первом аргументе передаёт ей указатель на callback-функцию записи в ОЗУ, а другая - на callback-функцию записи в поток ввода/вывода. Да неужели? поверю Вам на слово Но если они для Вас так одинаковы - что мешает Вам использовать printf в прерывании? Цитата(jcxz @ Mar 20 2018, 18:10)  У меня, например, среди прочего _Printf() пишет прямо в поток TCP-сокета (расчленяя вывод на лету на отдельные кадры без промежуточного буфера и поддерживая ретрансмиссию тоже без буфера). Свои callback-функции для _Printf() невероятно расширяют её возможности. Всё ограничивается только фантазией программиста. А уж тривиальный вывод в буфер ограниченного размера делается через _Printf() на раз. То есть пока ACK для сегмента не получим из printf не уйдем ? Да уж - фантазия программиста страшная штука - но моя только заставляла меня свои _Printf() писать падла  Удачи! Rob.
|
|
|
|
|
Mar 20 2018, 15:57
|
Гуру
     
Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713

|
Цитата(RobFPGA @ Mar 20 2018, 17:30)  Но если они для Вас так одинаковы - что мешает Вам использовать printf в прерывании? Ничего. Если будет нужно - использую. Цитата(RobFPGA @ Mar 20 2018, 17:30)  То есть пока ACK для сегмента не получим из printf не уйдем ? Да с чего бы? Для каждого отправляемого TCP-сегмента _Printf() естественно вызывается отдельно. У меня весь сетевой стек построен построен на callback-ах: от самого низа (Ethernet-DMA) до верхних HTTP и пр. - всё в пределах одной задачи ОС. Цитата(RobFPGA @ Mar 20 2018, 17:30)  моя только заставляла меня свои _Printf() писать падла  Свой лисапед? А зачем если готовый есть? Он вроде даже позволяет добавить обработку своих дополнительных букв %...
|
|
|
|
|
Mar 20 2018, 16:56
|
Профессионал
    
Группа: Свой
Сообщений: 1 214
Регистрация: 23-12-04
Пользователь №: 1 643

|
Приветствую! Цитата(jcxz @ Mar 20 2018, 18:57)  ... Свой лисапед? А зачем если готовый есть? Он вроде даже позволяет добавить обработку своих дополнительных букв %... Так я ж и говорю - неуемная фантазия программиста ну и ADuC812  - страшная штука! Успехов! Rob.
|
|
|
|
|
Mar 21 2018, 05:51
|

Ally
     
Группа: Модераторы
Сообщений: 6 232
Регистрация: 19-01-05
Пользователь №: 2 050

|
Цитата(haker_fox @ Mar 21 2018, 03:43)  Опасаюсь, что sprintf может задержать прерывание на время парсинга. А так - бросил в очередь. И пусть отдельная задача неспеша всё пишет. Эт ж зависит от реализации. sprintf не боле чем имя, которое может быть переопределено. В компиляторах даже обязывают проводить адаптацию нижнего уровня функций класса printf. Так что объективно рассуждать о них под embedded не имеет смысла, там может быть что угодно. В моих проектах printf применяется в прерываниях, поскольку выводит синхронно без циклов ожидания в канал RTT, профилирован и имеет известную глубину стека. Т.е. полностью детерминирован.
|
|
|
|
|
  |
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|