Форум: "WinAPI";
Текущий архив: 2006.10.22;
Скачать: [xml.tar.bz2];
ВнизНеобходимо ли операции с СОМ портом, выполняемые из различных.. Найти похожие ветки
← →
Balkon (2006-06-08 12:45) [0]потоков, выносить в критические секции.
Спасибо за внимание.
← →
tesseract © (2006-06-08 13:08) [1]Если один поток - один порт, то в секции надо выносить только передачу данных в главный поток.
← →
Balkon (2006-06-08 13:41) [2]Спасибо.
А если порт один, а потоков несколько - пишущий, читающий и меняющий настройки (интерфейсный)?
← →
tesseract © (2006-06-08 13:52) [3]
> Спасибо.А если порт один, а потоков несколько - пишущий,
> читающий и меняющий настройки (интерфейсный)?
Это уже критические извращения, не делай так никогда.
← →
Balkon (2006-06-08 14:03) [4]:) странные мне вещи вы говорите.
Как же тогда реализовывать, скажем, опрос порта, в цыкле?
Я так понимаю что "спящий" до появления новых данных отдельный
поток опроса порта- это вполне оправданное решение.
← →
Сергей М. © (2006-06-08 14:13) [5]
> :) странные мне вещи вы говорите.
Да нет, вовсе не странные это вещи...
Транспортный поток должен быть один и тот же, его ф-ция - прием/передача неких данных... Подготовка/обработка же (передаваемых/принимаемых) данных должна в этом случае быть возложена на один или более других потоков.
← →
Сергей М. © (2006-06-08 14:19) [6]
> Как же тогда реализовывать, скажем, опрос порта, в цыкле?
А нечего его опрашивать !
Он сам сообщит о событиях, в нем произошедших ..
На то существует overlapped - режим и completion routines - режим ..
Без цикла здесь и вправду не обойтись, но цикл этот занимается не только и не столько неким "опросом", сколько ожиданием неких событий в неких подсистемах ввода-вывода, в частности - подсистеме файлововго ввода-вывода, к коей принадлежит и ввод-вывод подсистемы последовательных коммуникаций.
См. WinAPI Wait-функции.
← →
tesseract © (2006-06-08 14:21) [7]
> На то существует overlapped - режим и completion routines
> - режим ..
Лучше использовать маску EV_RXCHAR, тогда порт реально сообщит, что что-то пришло. а overlapped просто помогает дожаться нужного кол-ва данных.
← →
Balkon (2006-06-08 14:35) [8]Спасибо опять...
Не знаю зачем, но делаю отдельные потоки пишущий и читающий.
Вот кусок процедуры читающего потока:
FillChar(ReadOL, SizeOf(ReadOL), 0);
ReadOL.hEvent:= CreateEvent(nil, True, True, nil);
SetCommMask(FPortHandle, EV_RXCHAR);
while (not Terminated) do
begin
WaitCommEvent(FPortHandle, Mask, @ReadOL);
Signaled:= WaitForSingleObject(ReadOL.hEvent, 1000);
if (Signaled = WAIT_OBJECT_0)and
GetOverlappedResult(FPortHandle, ReadOL, BytesTrans, False) then
begin
If (Mask and EV_RXCHAR) <> 0 then
begin
...
И будте добры поясните, почему транспортный поток должен быть один и тот же? Вроде бы в различных компонентах и в книге Агурова чтение из порта выносится в отдельный поток. Или я что-то неправильно понял?
← →
Сергей М. © (2006-06-08 14:38) [9]
> Вот кусок процедуры читающего потока:
Давай уж тогда и кусок пишущего приводи ..
← →
Balkon (2006-06-08 14:46) [10]Сделано все для того, чтобы на посылку команды некому девайсу получить от него ответ, либо по таймауту повторить команду.
процедура пишушего потока:
FillChar(WriteOL, SizeOf(WriteOL), 0);
WriteOL.hEvent:= CreateEvent(nil, True, True, nil);
FinpAKRThread := TinpAKRThread.Create(false,FOwner,FPortHandle,FComandPackage,FThreadAnswer); //Создаю читающий поток
Try
WriteFile(FPortHandle, FComandPackage, SizeOf(FComandPackage), RealWrite, @WriteOL);
Signaled:= WaitForSingleObject(WriteOL.hEvent, INFINITE);
if (Signaled = WAIT_OBJECT_0) and
(GetOverlappedResult(FPortHandle, WriteOL, BytesTrans, False)) then
begin
FinpAKRThread.WaitFor;
Обмениваются данными потоки в критической секции.
← →
Balkon (2006-06-08 14:57) [11]Прошу прощения,
ухожу из сети.
Завтра с удовольствием почитаю совтеы и ответы ежели таковые будут.
Спасибо. Берегите сябя. ;)
← →
Сергей М. © (2006-06-08 15:14) [12]
> на посылку команды некому девайсу получить от него ответ
Ну и зачем при этом, спрашивается, два потока ?
Очевидно же - одного достаточно ...
function Get(Request: TSomeRequestType): TSomeResultType;
В теле подобной ф-ции, исполняемой контексте некоего транспортного потока, дивайсу посылаются данные в формате TSomeRequestTypeт и ожидается/возвращается от дивайса ответ в формате TSomeResultType.
Ы ?
← →
Balkon (2006-06-09 11:03) [13]Привет опять. Спасибо.
Переписал используя один поток, который при создании своем открывает порт и наоборот соотсно.
При создании потока в него передается команда, которую он должен плюнуть в девайс и дождаться либо правильного ответа, либо достижения определенного числа повторов команды без получения правильного ответа.
Ниже приведена реализация. Нет ли в ней чего зазорного?
procedure TAKRThread.Execute;
Var
CurrentState : TComStat;
AvaibleBytes, ErrCode, RealRead : Cardinal;
ReadOL : TOverLapped;
Signaled, Mask : DWORD;
BytesTrans : DWORD;
TmpPackage: TReadPackage;
Begin
if WriteAKRComand then
Try
FillChar(ReadOL, SizeOf(ReadOL), 0);
ReadOL.hEvent:= CreateEvent(nil, True, True, nil);
SetCommMask(FPortHandle, EV_RXCHAR);
while (not Terminated) do
begin
WaitCommEvent(FPortHandle, Mask, @ReadOL);
Signaled:= WaitForSingleObject(ReadOL.hEvent, 1000);
if (Signaled = WAIT_OBJECT_0)and
GetOverlappedResult(FPortHandle, ReadOL, BytesTrans, False) then
begin
If (Mask and EV_RXCHAR) <> 0 then
begin
ClearCommError(FPortHandle, ErrCode, @CurrentState);
AvaibleBytes:= CurrentState.cbInQue;
if (AvaibleBytes > 0) and
ReadFile(FPortHandle, TmpPackage, AvaibleBytes, RealRead, @ReadOL) then
CheckBytes(TmpPackage,AvaibleBytes);
End;
end
else
RepeatAKRComand;
End;
Finally
CloseHandle(ReadOL.hEvent);
SetCommMask(FPortHandle, 0);
End;
End;
function TAKRThread.WriteAKRComand: boolean;
var
Signaled, RealWrite, BytesTrans : Cardinal;
WriteOL : TOverLapped;
begin
FillChar(WriteOL, SizeOf(WriteOL), 0);
WriteOL.hEvent:= CreateEvent(nil, True, True, nil);
Try
WriteFile(FPortHandle, FComandPackage, SizeOf(FComandPackage), RealWrite, @WriteOL);
Signaled:= WaitForSingleObject(WriteOL.hEvent, INFINITE);
Result := (Signaled = WAIT_OBJECT_0) and
GetOverlappedResult(FPortHandle, WriteOL, BytesTrans, False);
Finally
CloseHandle(WriteOL.hEvent);
End;
end;
Процедура CheckBytes(TmpPackage,AvaibleBytes) проверяет после каждой порции прилетевший байт набрался ли ответ и анализирует его корректность.
← →
Сергей М. © (2006-06-09 12:05) [14]
> Нет ли в ней чего зазорного?
Есть.
Отсутствует анализ результатов, возвращаемых ф-циями Read/WriteFile, WaitCommEvent
← →
Balkon (2006-06-09 13:49) [15]Спасибо большое.
← →
Ihor Osov'yak © (2006-06-09 18:00) [16]Зависит от архитектуры приложения и способа работы с портом. Для примера, в своих поделках, имеющих отношение к ком-портам, хотя они почти все многопоточные, я ни разу не использовал критических секций. Не возникало необходимости.
← →
tesseract © (2006-06-10 09:30) [17]
> хотя они почти все многопоточные, я ни разу не использовал
> критических секций. Не возникало необходимости.
я просто для перестраховки их использовал. Вдруг чего, не так.
← →
Ihor Osov'yak © (2006-06-11 02:01) [18]2 tesseract,
вспомнил одну байку, из глубокого детсва...
- слуш, зачем ты два талона компостируешь?
- а вдруг один потеряю, а тут контроль?
- а если оба потеряешь?
- ну, на этот случай у меня проездной..
← →
tesseract © (2006-06-12 09:27) [19]
> Ihor Osov"yak © (11.06.06 02:01) [18]
Кто знает, вдруг больше потоков придёться создавать?
Страницы: 1 вся ветка
Форум: "WinAPI";
Текущий архив: 2006.10.22;
Скачать: [xml.tar.bz2];
Память: 0.5 MB
Время: 0.044 c