私のプロジェクトには、スレッド自体、他のスレッド、またはVCL(メインアプリ)によって変更される可能性のあるスレッドがあります。したがって、私はすべてのデータアクセスにTCriticalSection.Acquire/Releaseを使用しています。
通常の状況では、次のコードは期待どおりに機能します。Acquireに入り、DoCallbackと同期してから、ロックを解除します。ただし、他のコンテキストのいずれかがすでにロックされているときにロックを取得した場合、以下のコードの実行はSynchronizeで停止します。今回は、DoCallbackメソッドに入りません。
Synchronizeメソッドをスキップして(SynchronizeのコードがVCLを呼び出す場合でも)、CriticalSection自体に依存する必要がありますか?この動作の理由は何ですか?
メインスレッドのコード:
fData:= nil;
try
fSingleRequest.Acquire;
if fItem <> nil then
begin
fData:= fItem.Request;
SubmitRequest();
fCallbackData:= fItem.fExtraData;
fCallback:= fItem.fCallback;
Synchronize(DoCallback); // <-- this line is called
end;
finally
fSingleRequest.Release; // <-- this isn't under the specific situation
end;