내 이해는 Thread.Abort가 차단 된 스레드에서 ThreadAbortException을 발생시켜야한다는 것이지만 TcpListener.AcceptSocket
을 처리 할 때는 그렇지 않습니다. 여기에 문제의 가장 기본적인 그림입니다 :AcceptSocket은 Thread.Abort 요청을 준수하지 않습니다.
class Program
{
static void Main(string[] args)
{
Thread thread = new Thread(Listen);
thread.Start();
Thread.Sleep(1000); // give it a second to get going
Console.WriteLine("Aborting listener thread");
thread.Abort();
thread.Join();
Console.WriteLine("Listener thread finished press <enter> to end app.");
Console.ReadLine();
}
static void Listen()
{
try
{
Console.WriteLine("Starting to listen");
TcpListener listener = new TcpListener(IPAddress.Any, 4070);
listener.Start();
Socket socket = listener.AcceptSocket();
Console.WriteLine("Connected!");
return;
}
catch (ThreadAbortException exception)
{
Console.WriteLine("Abort requested");
}
}
}
thread.Abort()
호출이 AcceptSocket
을 중지하고 ThreadAbortException
핸들러를 실행한다. Howerver 이것은 일어나지 않습니다.
대신 BeginAcceptSocket
를 호출 ListenAsync에 대한 AcceptSocket
내 들어 래퍼 스와핑 : 그것은 "표시"이 경우
static void ListenAsync()
{
try
{
ManualResetEvent clientConnected = new ManualResetEvent(false);
Console.WriteLine("Starting to listen");
TcpListener listener = new TcpListener(IPAddress.Any, 4070);
listener.Start();
clientConnected.Reset();
var iasyncResult = listener.BeginAcceptSocket((ar) =>
{
Socket socket = listener.EndAcceptSocket(ar);
Console.WriteLine("Connected!");
clientConnected.Set();
}, null);
clientConnected.WaitOne();
return;
}
catch (ThreadAbortException exception)
{
Console.WriteLine("Abort requested");
}
}
를 잘 작동합니다. thread가 WaitOne를 실행하고있는 동안에 ThreadAbortException가 캐치됩니다. 그러나이 BeginAcceptSocket에 대한 호출에 의해 생성 된 스레드가 계속 실행 및 소켓을 받아 들일 수있다 마지막으로
(I 텔넷와 해당 포트를 열어이 문제를 확인), 나는 TheadAbortException
핸들러의 일부가 시도로 Listener.Stop
추가 EndAcceptSocket 호출을 따라 잡으십시오 (소켓은 Stop으로 처리되기 때문에)
소켓 연결을 수신하는 프로세스를 시작하고 중지하는 가장 좋은 방법입니까?
스레드를 죽이면 clientConnected 이벤트는 어떻게됩니까? 왜 물건을 버리는 거니? 한 번 받아 들인 소켓으로 무엇을합니까? –
'Thread.Abort'는 거의 항상 더러운 해킹이므로 피해야합니다. 너의 실이 우아하게 끝나게해라 ... 그 밑에있는 깔개를 잡아 당기지 마라. – spender