Текущий архив: 2003.10.02;
Скачать: CL | DM;
Вниз
Проблемы с портом Найти похожие ветки
← →
Замученный (2003-07-15 14:57) [0]Уважаемые граждане, помогите пожалуйста.
Имеется прибор, подключенный к com порту. Прибору посылаются различные команды, он на них реагирует и посылает в ответ определенную информацию.
Проблема в следующем. При посылке ему какой-то команды, перед ответом возникает определенная задержка, которой в принципе быть не должно (смотрел по осциллографу). Задержка где-то около 46 мсек. Это мешает работать.
В работе использовал различные компоненты для работы с портом. Везде тот же результат.
Что можно сделать??? Заранее благодарен.
← →
Kostya (2003-07-15 15:37) [1]Есть в инете модуль sadirectport -отличная вещь
нет проблем
← →
Замученный (2003-07-15 15:45) [2]А что же делать с задержкой??? и где найти это модуль???
← →
Лёша (2003-07-15 17:48) [3]Задержка - понятие растяжимое!
Где задержка?
← →
jack128 (2003-07-16 11:02) [4]Замученный © (15.07.03 14:57) В смысле задержка? Между запросом и ответом? и правильно, Ведь должно твое устройство подумать, что ответить..
← →
Замученный (2003-07-16 11:26) [5]Задержка между запросом и ответом.
Так устройство отвечает сразу же после посланной ему команды. Проверял на осциллографе.
Может вставку на асме сделать? Может поможет? Если кто код знает, помогите please, а то горю совсем. Буду благодарен за любую инфу
← →
pasha676 (2003-07-16 12:54) [6]Что задержка будет это понятно (правда должна быть махонькая, в пределах 2-3 мс а то и меньше). Непонятно чем она тебе мешает. Кстати как общаешься с устройством? Может задержка в коде.
← →
Лёша (2003-07-16 14:00) [7]То, что ты проверил на осциле, ничего не значит. Проверь PortMonitor"ом или другой гляделкой порта. Если убедишься, что обмен данными имеет место и данные корректны, проверь/настрой таймауты порта: COMMTIMEOUTS (GetCommTimeouts/SetCommTimeouts). Если не поможет, сообщи, будем копать дальше.
← →
Замученный (2003-07-16 15:24) [8]Устройство, которое рассматривается, позволяет мерять различные характеристики жидкости. Для этого применяется ряд коэффициентов. Данные коэффициенты в процессе работы сбиваются, в результате чего приходится их перепрограммировать. После записи каждого коэфф. устройство сообщает, что процесс записи коэфф. закончился удачно и ждет след., если он не приходит (в течение 10 мс.)выскакивает ошибка и процесс записи прекращается. В результате я могу лишь записать первый коэффициент, что у меня и получается.
Проверил PortMonitor"ом, обмен данными имеет место.
Что касается таймаутов то они такие (использую свойство TimeOuts компонента ComPort Library):
ReadInterval = 0;
ReadTotalConstant = 0;
ReadTotalMultiplier = 0;
WriteTotalConstant = 0;
WriteTotalMultiplier = 0;
← →
pasha676 (2003-07-16 16:52) [9]Если используешь компоненты, то надо рыться в них. Подсказать может только тот кто с этими компонентами работал и подобной проблеммой сталкивался.
← →
Замученный (2003-07-16 16:59) [10]Так откуда берется задержка, может быть это проблемы с системой и так должно быть
← →
Verg (2003-07-16 17:40) [11]Win32 - это не система реального времени и требовать какого-либо времени реакции приложения на событие нельзя.
Это в общем.
А потом, уточни все же между чем и чем задержка? Между тем как пролетел байт (по осцилу) и он "упал" в апликуху? Как ты мерял эту задержку?
← →
jack128 (2003-07-16 19:44) [12]Мне тоже интресно как можно замерить такую задержку...
И кстати укажи скорость и размер посылки от устройства, а то если скорость 300 bps и посылка в 10 байт, то около 30 мс и выходит ;-)
← →
Лёша (2003-07-16 20:31) [13]Попробуй:
ReadInterval := 100;
ReadTotalConstant ( см. MSDN "Serial Communications Functions") Попробуй:
ReadInterval := 100;
ReadTotalConstant := 100;
ReadTotalMultiplier := 100;
WriteTotalConstant := 100;
WriteTotalMultiplier:= 100;
когда присвоены значения "0" - таймауты не используютсья вообще. Кто знает, как работает твоя компонента, может это его сбивает. А лучше перепеши на WIN32 API - четко, быстро, без глюков и отладить легко. (см. MSDN "Serial Communications Functions")
← →
pasha676 (2003-07-17 09:06) [14]
> WIN32 API - четко, быстро, без глюков и отладить легко
Помоему это тоже выход. Во всяком случае контроля больше. Ведь не известно что там в компоненте понаписано.
← →
Замученный (2003-07-17 13:35) [15]Verg Задержка возникает между тем как была послана команда устройству и получен ответ в приложении. Задержку мерял сл. образом. Измерял время, после отправки и перед приемом, затем находил разницу.
Что касается скорости то она 2400 bps. Посылка 8 байт, 2 стопа.
Попробую сейчас покапаться в MSDN "Serial Communications Functions", может что и поможет. Если у кого есть код, буду рад принять.
← →
Замученный (2003-07-17 14:05) [16]Пробовал
ReadInterval := 100;
ReadTotalConstant := 100;
ReadTotalMultiplier := 100;
WriteTotalConstant := 100;
WriteTotalMultiplier:= 100;
После первого запуска 37 мс, а затем опять 46 мс. Что за чертовщина??? Может во всем виноват XP?
← →
Лёша (2003-07-17 14:53) [17]Так я и не понял где задержка...
| | | ( RS232) Так я и не понял где задержка...
| | | |
| [ПО] <-> [порт] <---> (RS232) <-> [порт] <-> [ПО] |
| | | | | | |
| | |
| |__________________ |
| _________T1_______||
| |
|______________________________ |
___________T2_________________|
Почувствуй разницу и проверь еще раз значение своей задержки!
1.
>Verg Задержка возникает между тем как была послана команда
>устройству и получен ответ в приложении. Задержку мерял сл.
>образом. Измерял время, после отправки и перед приемом,
>затем находил разницу.
T2
2. Т1
3. другие варианты
← →
Замученный (2003-07-17 15:30) [18]Приведу кусок кода, может поможет
Procedure TForm1.Tik;
Begin
ComPort1.Open; // Открываю порт
// Подготавливаю данные для отправки
dim_send[0]:= ord(chr(StrToInt("1")));
dim_send[1]:= ord(chr(StrToInt("$90")));
dim_send[2]:= ord(chr(StrToInt("0")));
// Отправляю 3 байта в порт
ComPort1.Write(dim_send,3);
End;
procedure TForm1.Button1Click(Sender: TObject);
Var
i,k:integer;
begin
// Щелкаем на кнопке, оправляем данные в порт и замеряем время
Tik;
Time1:=Time;
end;
// В порт что-то пришло, принимаем
procedure TForm1.ComPort1RxChar(Sender: TObject; Count: Integer);
var i,p:byte;
begin
// Измеряем время и декодируем его. Далее находим MSec2-MSec1
Time2:=Time;
DecodeTime(Time1,Hour1,Min1,Sec1,MSec1);
DecodeTime(Time2,Hour2,Min2,Sec2,MSec2);
// Принимаем данные
ComPort1.ReadStr(Answer,3);
end;
В итоге MSec2-MSec1 = 46
← →
pasha676 (2003-07-17 15:43) [19]так время замерять не совсем коректно. Особенно в виндах.
Где по твоей проге тратиться время?
Ты перед отправлением запоминаешь время. Символы бегут в компорт, оттуда в девай, девайс думает, девайс отвечает, символы ответа приходят в ком порт, генериться сообщение, сообщение генерит эвент ComPort1RxChar, тут ты опять запоминаешь время. Тебе не кажеться что ты меряешь время всего цикла?
С момента прихода символа, до вваливания в обработку ComPort - вот время задержки виндоуз. Где оно у тебя считается? И я не знаю.
← →
Замученный (2003-07-17 16:11) [20]Так мне надо проверить ответ девайса и если он положительный, то ему посылается новый коэффициент, если нет, то показываем ошибку.
Как же я буду проверять, какой сигнал от него пришел, не используя эвент ComPort1RxChar? Вот я и смотрю, сколько времени требуется, чтобы сигнал дошел до девайса и получен ответ, чтобы его обработать в проге.
Может я и не правильно меряю время, не знаю. Однако коэфф. не пишутся и девайс выдает ошибку, что время ожидания прошло и он прекращает запись.
Эвент ComPort1RxChar возникает, как только в порт приходит символ.
Пробовал не использовать этот этот эвент. Считывал данные постоянно - та же самая ситуация.
← →
jack128 (2003-07-17 16:12) [21]
> После записи каждого коэфф. устройство сообщает, что процесс
> записи коэфф. закончился удачно и ждет след., если он не
> приходит (в течение 10 мс.)выскакивает ошибка
> Что касается скорости то она 2400 bps. Посылка 8 байт, 2
> стопа.
.
Предположу, что у тебя dcb.ByteSize := 8; тогда (8 бит + 2стоп бита + 1 старт бит)*8 байт ответа от устройства/2400 bps = 88/2400 = 0,036 = 36 мс, а тебе нужно еще второй коэфициэнт отправить, тебе не кажется, что ты ну никак не успеваешь? 10 мс это уж ОЧЕНЬ мало для таких скоростей
← →
Замученный (2003-07-17 16:53) [22]Формат посылки - 11 бит: старт-бит(ноль), 8 бит данных, два стоп бита (единица), контроль по четности отсутствует.
В качестве теста выбрана команда $90 - проверка связи.
После распознавания этой комамнды девайс сразу же(без задержки) передает на ЭВМ трехбайтовое сообщение с кодом ответа $90.
Т.о., если я правильно понимаю имеем:
(8 бит + 2стоп бита + 1 старт бит)*3 байта ответа от устройства/2400 bps = 33/2400 = 0,00125 = 1,25 мс.
Я же имею 47 мс.
← →
jack128 (2003-07-17 17:19) [23]
> 33/2400 = 0,00125
Купи колькулятор полудше :-)
← →
jack128 (2003-07-17 17:25) [24]И все таки по поводу времени, ты учти что эти формулы учитывают только физическую передачу сигнала через канал связи и не учитывают что винда думает, переходные процессы в приемопередатчике (UART - так он на буржуйском завется?)идут, устройство тотже думает, UART устройства тоже тупит ;-) и все это вместе дает твои 50 мс...
← →
Замученный (2003-07-17 17:43) [25]jack128 Извиняюсь, облажался :(((
Так что можно что-то сделать или нет, как ты думаешь?
← →
Лёша (2003-07-17 19:58) [26]...да, затянулась ветка!
...а главное без толку...
← →
jack128 (2003-07-18 00:32) [27]
> Так что можно что-то сделать или нет, как ты думаешь?
ИМХО, нет (покрайней мере не под Windows). Если есть доступ к разработчикам устройства, то заставь их переписать программу контроллера (или пусть сами приведут пример рабочей программы)
← →
pasha676 (2003-07-18 10:13) [28]Что бы написать такой контроллер в девайсе, как задержка в 50мс и все падает (особенно при записи параметров), надо быть не совсем нормальным (особенно когда идет обмен по схеме "запрос-ответ"). Есть версия, что ты что то не то пихаешь в контроллер.
← →
Замученный (2003-07-18 12:57) [29]Пихаю я то, иначе бы он отвечал неправильно
← →
Verg (2003-07-18 14:42) [30]Под NT (2000) можно попробовать задрать приоритет процесса и потока:
SetPriorityClass(GetCurrentProcess(),REALTIME_PRIORITY_CLASS);
SetThreadPriority(GetCurrentThread, THREAD_PRIORITY_TIME_CRITICAL);
Только работать в таком потоке надо крайне аккуратно: для ввода с порта никакого полинга, только overlapped io+waitxxxxxx и т.п., а то повесишь все остальные потоки...
Может поможет, может нет - все зависит от того будут ли и сколько будет запущено еще таких же "умников" с REALTIME_PRIORITY_CLASS/THREAD_PRIORITY_TIME_CRITICAL.
А реально - только модернизацией самого устройства. Время-ориентированные протоколы обмена мало подходят для простых смертных приложений под винды. Либо писать специальный драйвер уровня ядра.
← →
Замученный (2003-07-18 14:46) [31]Читал, что можно работать с портом напрямую с помощью giveo.sys. Но как это делать не знаю. Может кто знает??
← →
N169 (2003-07-18 17:15) [32]>с портом напрямую ... giveo...
нет, мужик, тока хуже будет. Ибо теряем буферизацию --> вероятность потери данных увеличивается.
К тому же конфликтность с serial.sys
← →
jack128 (2003-07-18 21:57) [33]
> Verg © (18.07.03 14:42)
> Может поможет, может нет - все зависит от того будут ли
> и сколько будет запущено еще таких же "умников" с REALTIME_PRIORITY_CLASS/THREAD_PRIORITY_TIME_CRITICAL.
Самое смешное что системные процессы работают с меньшим приоритетом и к чему приведет такое положение вещей одному Гейтсу известно..
← →
AlexR (2003-07-19 23:05) [34]>Читал, что можно работать с портом напрямую с помощью giveo.sys. Но как это делать не знаю. Может кто знает??
goveio точно не поможет. Может драйвер попробовать? Но это не так-то просто.
← →
Verg (2003-07-20 09:52) [35]
> jack128 ©
Если поток будет грамотно работать, то ни к чему плохому не приведет, а если while true do; то энтя умрет вплоть до ресета.
← →
CaveDweller (2003-07-20 12:54) [36]Если такая задержка - то это похоже на таймер в компоненте, который каждые 50мс ходит в порт за данными. Я в своё время использовал API - функцию WaitCommEvent, которая возвращает управление сразу по событию в порте. Понятное дело, что функция запускалась в отдельном потоке. Думаю, что стоит попробовать API, тем более, что не так оно и сложно.
← →
jack128 (2003-07-20 14:21) [37]
> API - функцию WaitCommEvent,
ИМХО очень неудобно..Возиться с асинхронными операциями....И потом здесь это не поможет, почитай выше...
← →
AnS (2003-07-20 15:10) [38]Работал я с компонентом ComPort Library (писал программу обмена данными с ЭККА ЭРА-201). Компонент отличный и работает прекрасно.
Вопрос такой: твой девайс выдает что-то типа XOFF после приема пакета от тебя и XON после обработки пакета и ответа на него?
← →
Замученный (2003-07-21 13:02) [39]>твой девайс выдает что-то типа XOFF после приема пакета от тебя и XON после обработки пакета и ответа на него?
Девайсу отсылается команда вида 01 $90 00 (01 - номер устройства, $90 - команда проверки связи) при приеме данной команды должен вернуться ответ 01 $90 00 (команду принял). Именно ее я и получаю.
К тому же при посылке ему других команд, а их около 5, также получаю результат
Страницы: 1 вся ветка
Текущий архив: 2003.10.02;
Скачать: CL | DM;
Память: 0.55 MB
Время: 0.009 c