Российский производитель и разработчик сертифицированного измерительного оборудования с 1987 года


В продолжение темы E14-140 - Проблема. Вопрос к пр

Вы не вошли.

 Поиск | Регистрация | Вход 

Олег Косарев
22.11.2009 04:59:12
#1

Гость

В продолжение темы E14-140 - Проблема. Вопрос к пр

Здравствййте всем снова!

  Это а продолжение темы "E14-140 - Проблема. Вопрос к производителям!"

  Вот нашел у себя в программе ЧТО грузит ОС и вызывает потерю данных с перемешиванием каналов.

  Это оказался вызов
Synchronize(frmOsc.Draw)

Это вызывается из потока, котоый опрашивает АЦП (после получения порции данных).
Метод Draw сканирует буфер данных и выводит на экран в форме графика/осциллограммы. График сделан на основе TChart. (Конечно было бы лучше написать что-то свое и более быстрое, но нет времени).
Тупо убрал Synchronize и напрямую вызываю frmOsc.Draw. Это конечно же не правильно. НО эксперимет показывает что это именно Synchronize все тормозил. теперь даже с маленьким буфером вызвать такой

Олег Косарев
22.11.2009 05:15:39
#2

Гость

Re: В продолжение темы E14-140 - Проблема. Вопрос к пр

... такой
сбой с перестановкой каналов практически невозможно. Как не странно нормально работает.

Но при большом размере буфера и высокой частоте АЦП иногда TChart не успевает перерисоваться вовремя и возникаяет коллизия доступа к буферу - поток начинает его обновлять а TChart еще читает в это время. Ну правильно, синхронизации то нет никакой.
Просто уменьшил разрешение вывода графика в TChart при большом буфере - беру не каждую точку а напрмер каждую десятую... Все нормально. Приоритетная задача - это запись в файл а не график.
  Но все-таки  это не правильно. И не хочется больше связываться в данном месте с
Synchronize. Но наверно нужна синхронизация доступа к буферам работающая более быстро. Подскажиьте, чем можно заменить? Может быть PostMessage???

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

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

Олег Косарев
22.11.2009 12:09:14
#3

Гость

Re: В продолжение темы E14-140 - Проблема. Вопрос к пр

без синхронизации все работает, как ни странно. очень редко возникает ошибка "List Ondex out bounds()" от Tchart осциллографа.

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

22.11.2009 21:57:23
#4

Сотрудник "Л Кард"
Откуда: Москва
Здесь с 23.04.2014
Сообщений: 3,727

Re: В продолжение темы E14-140 - Проблема. Вопрос к пр

из главного буфера делайте копии данных  для локальных задач типа прорисовки. Копируется все сейчас очень быстро. А так почитайте http://www.frolov-lib.ru/ 26 и 27 книжки.

Олег Косарев
23.11.2009 03:39:05
#5

Гость

Re: В продолжение темы E14-140 - Проблема. Вопрос к пр

>А так почитайте http://www.frolov-lib.ru/ 26 и >27 книжки.

  Спасибо за ссылку на очень полезные книги.

Сделал так. Объявил флаг занятости - глобальную переменную boolean. если флаг False поток выставляет в TRUE и запускает рисование. В конце рисования процедура выставляет флаг занятости в FALSE, на всяк случай через таймаут в 55 мс - через таймер.
  Это с реентером в процедуру. А с буфером может придется так и сделать как вы посоветовали.

23.11.2009 11:17:22
#6

Сотрудник "Л Кард"
Откуда: Москва
Здесь с 23.04.2014
Сообщений: 3,727

Re: В продолжение темы E14-140 - Проблема. Вопрос к пр

Я надеюсь Вы понимаете что это не атомарная операция.....

23.11.2009 11:24:47
#7

Сотрудник "Л Кард"
Здесь с 18.04.2014
Сообщений: 810

Re: В продолжение темы E14-140 - Проблема. Вопрос к пр

Вот все и выяснилось... Конечно, поток реального времени не должен ждать GUI.

Согласен с Poul - для задач типа отрисовки лучше сделать собственный буфер (thread-safe) и копировать в него данные. Если нет места - выбросить блок (можно выставить флажок предупреждения).
Моя любимая структура для этой цели - кольцевой FIFO-буфер по схеме буфера клавиатуры DOS (с указателями на голову и хвост). Такой буфер хорош тем, что если есть один поток чтения и один поток записи, то можно обойтись без mutex/'ов.

Олег Косарев
28.11.2009 09:04:26
#8

Гость

Re: В продолжение темы E14-140 - Проблема. Вопрос к пр

ну вот, все отлично работает наконец-то. Никаких ошибок. Даже на маленьком ноуте ASUS EEE-pc 701 с дохленьким процессором. При этом запись данных ведется на воткнутую в УСБ флешку. При этом у него загрух процессора около 7 процентов. Вот уже вторые сутки пишет без ошибок... smile))

28.11.2009 20:32:18
#9

Сотрудник "Л Кард"
Здесь с 17.04.2014
Сообщений: 674

Re: В продолжение темы E14-140 - Проблема. Вопрос к пр

Рады за Вас. Успехов!