서버 응용 프로그램에 다음이 있습니다. 싱글 톤 인 JobManager라는 클래스. JobManager에 일종의 작업을 추가 할 시간인지 계속 확인하는 다른 클래스 인 Scheduler. 클라이언트 응용 프로그램에서 사용자가 서버에 호출을 생성 뭔가를, 동시에교착 상태 델파이 설명/솔루션
TJobManager.Singleton.NewJobItem(parameterlist goes here...);
: 그렇게 할 시간이되면
는, 스케줄러는 그런 짓을. 내부적으로 서버는 자신에게 메시지를 보내고 그 메시지를 수신하는 클래스 중 하나는 JobManager입니다. JobManager이 메시지를 처리하고 그것의 자신의 방법 호출 목록에 새 작업을 추가하는 시간이다 것을 알고 :
CS.Acquire;
try
DoSomething;
CallAMethodWithAnotherCriticalSessionInternally;
finally
CS.Release;
end;
다음 NewJobItem 방법에
NewJobItem(parameter list...);
, 나는 이런 식으로 뭔가를
이 시점에서 시스템이 교착 상태에 도달했습니다 (CS.Acquire). 클라이언트와 서버 응용 프로그램 간의 통신은 Indy 10을 통해 이루어집니다. 메시지 처리기로 보내는 서버 응용 프로그램 메서드를 실행하는 RPC 호출이 Indy 스레드의 컨텍스트에서 실행되고 있다고 생각합니다.
스케줄러에는 자체 스레드가 실행 중이며 JobManager 메소드를 직접 호출합니다. 이 상황이 교착 상태가 발생하기 쉬운가? 누군가 교착 상태가 발생하는 이유를 이해하는 데 도움을 줄 수 있습니까?
클라이언트가 특정 작업을 수행하여 시스템을 잠글 때 가끔은 같은 지점의 중요 섹션에 다른 지점에서 두 번 도달하는이 지점을 찾을 수있었습니다. Scheduler 및 JobManager의 메시지 핸들러 메소드).
내가 그 추가 할 몇 가지 추가 정보를 원하시면 (이 어쨌든 바보가 될 수 있지만,이 ...)을 해봐요 안에이 내부 CS.Release가하고있는 또 다른
CS.Acquire;
try
Do other stuff...
finally
CS.Release;
end;
있다 외부 CS에 무엇이든. 알아봐? 그렇다면 스케줄러가 중요 섹션으로 들어가고 모든 잠금 및 잠금 해제가 엉망이 될 수 있습니다.
크리티컬 섹션의 목적은 다른 스레드에서 동시에 실행할 수없는 코드를 보호하기위한 것입니다. 따라서 같은 인스턴스의 중요 섹션에 두 번 이상 도달하면 OK입니다. 비판적 섹션은 그곳에서 일을하고 있으며 그것을 위해 설계되었습니다! 나쁜 점은 획득 스레드가 CS2를 획득하려고 기다리고 있기 때문에 CS2가 해제되지 않는 반면 CS2는 획득 스레드가 CS1 (DeadLock이라고 함)을 획득하기 위해 대기 중이므로 릴리스하지 않는 것입니다. 네가하는 말 때문에 교착 상태를 겪고 있는지 확신 할 수 없다. 왜 확신하니? – jachguate
메시지 핸들러 메소드에 따라 디버깅하는 동안 방금 중요한 섹션을 입력하고 스케줄러에서 오는 CS.Acquire 행의 내 중단 점에 다시 도달했습니다. F8을 다시 누르면 시스템이 중지되었습니다. – ronaldosantana
또한 Windows 메시지 처리 루프에서 교착 상태가 발생할 수 있습니다.ThreadA가 CS1을 잠근 다음 메시지 루프를 반복해야하는 호출을 수행 할 때. 스레드 B는 실제로 CS1 획득을 기다리는 동안 메시지 루프를 중지, 중단 또는 무기한으로 지연시키는 중 ... –