Como parar corretamente um serviço do Windows .NET multi-threaded?

Eu tenho um serviço do windows escrito em c # que cria uma carga de caminhões de threads e faz muitas conexões de rede (WMI, SNMP, TCP simples, http). Ao tentar parar o serviço do Windows usando o snap-in MSC de Serviços, a chamada para parar o serviço retorna com relativa rapidez, mas o processo continua a ser executado por aproximadamente 30 segundos ou mais.

A principal questão é qual poderia ser a razão pela qual está levando mais de 30 segundos para parar. O que posso procurar e como faço para procurá-lo?

A questão secundária é por que o serviço msc snap-in (controlador de serviço) está retornando, embora o processo ainda esteja em execução. Existe uma maneira de fazê-lo retornar somente quando o processo é realmente morto?

Aqui está o código no método OnStop do serviço

protected override void OnStop()
{
   //doing some tracing
   //......

   //doing some minor single threaded cleanup here
   //......

   base.OnStop();

   //doing some tracing here
}

Editar em resposta a respostas de limpeza de thread

Muitos de vocês responderam que eu deveria acompanhar todos os meus tópicos e depois limpá-los. Eu não acho que isso seja uma abordagem prática. Em primeiro lugar, não tenho acesso a todos os threads gerenciados em um único local. O software é muito grande, com diferentes componentes, projetos e até mesmo dlls de terceiros que poderiam estar criando threads. Não há nenhuma maneira que eu possa acompanhar todos eles em um único local ou ter um sinalizador que todos os segmentos verificam (mesmo se eu pudesse ter todos os segmentos verificando um sinalizador, muitos segmentos estão bloqueando coisas como semáforos. Quando estão bloqueando, eles podem Eu vou ter que fazê-los esperar com um tempo limite, então verifique esta bandeira global e espere novamente).

A bandeira IsBackround é uma coisa interessante para verificar. Novamente, como posso descobrir se tenho algum encadeamento forro em execução? Vou ter que verificar todas as seções do código que cria um thread. Existe alguma outra maneira, talvez uma ferramenta que possa me ajudar a descobrir isso.

Em última análise, porém, o processo pára. Parece que preciso esperar por algo. No entanto, se eu esperar no método OnStop por uma quantidade de tempo X, o processo levará cerca de 30 segundos + X para parar. Não importa o que eu tente fazer, parece que o processo precisa de aproximadamente 30 segundos (nem sempre 30 segundos, pode variar) depois que o OnStop retorna para o processo realmente parar.

questionAnswers(7)

yourAnswerToTheQuestion