Главная страница
Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2005.09.11;
Скачать: CL | DM;

Вниз

Проверка очереди Com порта неработает.   Найти похожие ветки 

 
Kolan ©   (2005-07-19 12:45) [0]

Проблема вот в чём:
 Хочу считать всё что есть в буфере. Для чего написал процедуру:

function TStringWriteComm.ReadWholeBufferAsString: string;
var
 Queue: Integer;
 Buffer: array of Byte;
 I: Integer;                    
begin
 Queue := DataInBuffer;
 SetLength(Buffer, Queue);
 Read(Buffer, Queue);
 Result := "";
 for I := Low(Buffer) to High(Buffer) do
 begin
   Result := Result + Chr(Buffer[I]);
 end;
end;


и
function TStringWriteComm.DataInBuffer: Integer;
var
 ComStat: TComStat;
 lpErrors: DWORD;
 Handle: THandle;
begin
   Handle := ComPort;
   if ClearCommError(Handle, lpErrors, @ComStat) then
   begin
     Result := ComStat.cbInQue;
   end
   else
     Result := 0;
end;


Но вот интересно. Если запустить это дело то в очереди ничего нет(те DataInBuffer возвращает 0). Если ставить точки останова до или после строки Queue := DataInBuffer; тоже самое причем сколько раз не повторяй(пробовал в цикле).

А если пройтиси пошагово или поставить BreakPoint на эту строку то всё OK и в очереди данные есть. Данные в порте точно есть.

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

Кстати если сделать
Sleep(10);
Queue := DataInBuffer;

То работает тоже. почему так?

PS решение Sleep(10); мне не подходит.


 
Digitman ©   (2005-07-19 13:05) [1]

Queue := DataInBuffer;
if Queue > 0 then ..


 
Kolan ©   (2005-07-19 13:33) [2]

Так в том и дело что Queue равно 0.
А если пошагово иду то нет.
Или вот шас для того чтобы продолжить работу заменил просто на чтение без проверки и читает нормально.


 
Digitman ©   (2005-07-19 13:37) [3]


> в том и дело что Queue равно 0.


значит в этот момент действительно нет актуально приянятых данных


 
Kolan ©   (2005-07-19 13:46) [4]

Да нет есть. Это эхо ответ.
Как понять вот это

Queue := ComPort.DataInBuffer; (**)
 ComPort.Read(Buffer, Length(S));
 Echo := ArrayToString(Buffer);
(*)

Ставлю BreakPoint на (*) и вижу Queue = 0; А в
Buffer прочитанно 4 байта?

Ставлю BreakPoint на (**) иду по F7 и в Queue 4 байта?


 
Digitman ©   (2005-07-19 15:13) [5]

в период между остановом на брейкпойнте и последующим F7 (этот период вряд ли будет менее сотен м/секунд) поступили данные в приемный буфер порта, их ты и получил нажав F7


 
Kolan ©   (2005-07-19 16:09) [6]

Попробую обяснить чего я не понимаю.
Тестовый пример:
begin
 ComPort.WriteString("w");
 K := 0;
 for I := 1 to 1000 do
 begin
   Queue := ComPort.DataInBuffer;
   K := K + 1;
 end;
 K := 0; (*)
end;


Break на (*). Queue = 0; Значит за 1000 проверок очередь не изменилась.

begin
 ComPort.WriteString("w");
 K := 0;
 for I := 1 to 1000 do
 begin
   Queue := ComPort.DataInBuffer;
   S := ComPort.ReadAsString(1);
   K := K + 1; (*)
 end;
 K := 0;
end;

Break на (*). Queue = 0; S = "w" Значит очередь всеже не пустая так как пришел ответ.

Во втором тесте ответ был уже на первом шаге цикла.
А первый тест показал, что очередь равно 0 всё 1000. Как так?


 
Digitman ©   (2005-07-20 10:37) [7]

А ты почему не анализируешь lpErrors после возврата из ClearCommError() ?


> S = "w" Значит очередь всеже не пустая так как пришел ответ.


что за дивайс к порту подключен ?
или у тебя лупбэк организован для целей отладки ?


 
Kolan ©   (2005-07-20 12:32) [8]


> А ты почему не анализируешь lpErrors после возврата из ClearCommError()
> ?

Сделал в примере [6] ответ такой
Queue = 0; S = "w" lpErrors = 0;


> что за дивайс к порту подключен ?
> или у тебя лупбэк организован для целей отладки ?


Работаю с RS-485; Есть преобразователь RS-232 <-> Rs-485. У него есть эхо. Я шлю команду получив эхо устанавливаю RST и читаю ответ.

Работая над проектом возникла идея, хотел узнать у вас можно ли вообще такое сделать:

1:
Имеется два потока. Один (может и главный) убирает RTS и шлёт команды, а второй выгребает всё что есть в потре и анализирует. Если встретил эхо то еще и включает RTS.

2: Почти тоже самое, но эхо проверяет первый поток и он влючает RTS, а второй только забирает всё что приходит и парсит.

PS. А мож есть такое сообшение системы возникающее когда что-то приходит в порт?

С уважением,
 Kolan


 
Digitman ©   (2005-07-20 12:43) [9]


> мож есть такое сообшение системы возникающее когда что-то
> приходит в порт?


сообщения нет, но зато с ком-портом можно работать в асинхронно, в overlapped-режиме по событиям

под НТ есть Read/WriteFileEx - эти ф-ции, кр.всего того что делают Read/WriteFile, позволяют еще и организовать нотификацию о событиях ввода/вывода вызовом колбэк-функции


 
tesseract ©   (2005-07-24 19:53) [10]

PS. А мож есть такое сообшение системы возникающее когда что-то
приходит в порт?

>>> WaitCommEvent с EV_RXCHAR not EV_RING

Я сдесь в каком-то посте исходник передавал, пошукай



Страницы: 1 вся ветка

Текущий архив: 2005.09.11;
Скачать: CL | DM;

Наверх




Память: 0.49 MB
Время: 0.024 c
1-1124352482
cvg
2005-08-18 12:08
2005.09.11
Ошибка при вызове DivMod


4-1121892537
Dot
2005-07-21 00:48
2005.09.11
загрузка процессора


4-1121967182
Creep1
2005-07-21 21:33
2005.09.11
Поймать событие сворачивания/разворачивания окна


1-1124462191
murz
2005-08-19 18:36
2005.09.11
Сжатие приложений


1-1123694728
Starcom
2005-08-10 21:25
2005.09.11
Как у MessageDlg сделать фон к примеру Белым?