異なるスレッドからメソッドを呼び出すことに関して質問があります。さて、私はUSBデバイスと通信するためにWinUSBドライバーを使用しています。デバイスからデータを読み取るための別のスレッドがあります。デバイスへのコマンドはメインスレッド内で設定されます。実際、私はWinUSB_WritePipeメソッドとWinUSB_ReadPipeメソッドを使用してそのような操作を行っています。データが読み取られるスレッドでは、構造が重複している非同期の読み取りメソッドとWaitForMultipleObjectを使用します。私のデバイスには設定する必要のあるいくつかの機能があり、これはメインスレッドのGUIを介して行われます。
私はいくつかの奇妙な行動を観察しています。私の質問は、このメソッドへの呼び出し(たとえば、mutexを使用)をロックして、一度に1つのスレッドだけがメソッドにアクセスまたは呼び出す必要があるかどうかです。
古い方法:
type TMyThread = TThread
protected
procedure Execute; override;
end;
procedure TMyThread.Execute;
begin
while not Terminated do
begin
WinUsb_ReadPipe(Pipe, Amount, Overlapped)
ErrNo := GetLastError;
if ErrNo = ERROR_IO_PENDING then
begin
wRes = WaitForMultipleObjects(2, @HndEvt, false);
if wRes = WAIT_OBJECT_0 then
begin
ResetEvent(Overlapped.hEvent);
WinUSB_GetOVerlappedResult
DoSomethingWithData; // Do something
end;
end;
end;
end;
MainThread:
begin
// Set device sample rate
WinUSB_WritePipe (Pipe, Amount, Data, ...)
end;
新しい方法:
type TMyThread = TThread
protected
procedure Execute; override;
public
procedure Lock;
procedure Unlock;
constructor Create(ASuspended: boolean); override;
destructor Destroy; override;
end;
constructor TMyThread.Create(ASuspended: boolean);
begin
hMtx := CreateMutex(nil, false, nil);
end;
destructor TMyThread.Destroy(ASuspended: boolean);
begin
CloseHandle(hMtx);
end;
procedure TMyThread.Lock;
begin
WaitForSingleObject(hMtx, 10000);
end;
procedure TMyThread.Unlock;
begin
ReleaseMutex(hMtx);
end;
procedure TMyThread.Execute;
begin
while not Terminated do
begin
Lock;
WinUsb_ReadPipe(Pipe, Amount, Overlapped)
Unlock;
ErrNo := GetLastError;
if ErrNo = ERROR_IO_PENDING then
begin
wRes = WaitForMultipleObjects(2, @HndEvt, false);
if wRes = WAIT_OBJECT_0 then
begin
ResetEvent(Overlapped.hEvent);
Lock;
WinUSB_GetOVerlappedResult
Unlock;
DoSomethingWithData; // Do something
end;
end;
end;
end;
MainThread:
begin
// Set device sample rate
Lock; // same mutex as in TMYThread
WinUSB_WritePipe (Pipe, Amount, Data, ...)
Unlock; // same mutex as in TMYThread
end;
これは非常に単純化されたコードであり、問題を説明するためだけのものであり、プログラミングスキルを反映していません。:)もちろん、同じミューテックスでロックしてから、メインスレッドで同じメソッドを呼び出します。
問題をできるだけ単純に説明したいと思います...繰り返しますが、これらのメソッドへの呼び出しを別のスレッドでロックする必要がありますか?
よろしくお願いします。本当に感謝しています!
Br、Nix