Transições de estado do serviço
Um serviço é responsável por relatar alterações em seu estado para o SCM (gerenciador de controle de serviço). Os programas de controle de serviço e o sistema podem descobrir o estado de um serviço somente do SCM, portanto, é importante que um serviço relate seu estado corretamente. Um serviço relata seu estado chamando a função SetServiceStatus com um ponteiro para uma estrutura de SERVICE_STATUS totalmente inicializada. O membro dwCurrentState da estrutura contém o estado do serviço a ser relatado.
O estado inicial de um serviço é SERVICE_STOPPED. Quando o SCM inicia o serviço, ele define o estado do serviço como SERVICE_START_PENDING e chama a função ServiceMain do serviço. Em seguida, o serviço conclui sua inicialização usando uma das técnicas descritas em Service ServiceMain Function. Depois que o serviço concluir sua inicialização e estiver pronto para começar a receber solicitações de controle, o serviço chamará SetServiceStatus para relatar SERVICE_RUNNING e especificar as solicitações de controle que o serviço está preparado para aceitar. A transição de SERVICE_START_PENDING para SERVICE_RUNNING indica para o SCM e as ferramentas de monitoramento de serviço que o serviço iniciou com êxito. Se o serviço relatar um estado diferente de SERVICE_RUNNING, o SCM ou as ferramentas de monitoramento de serviço poderão marcar o serviço como tendo falhado ao iniciar.
O SCM envia apenas as solicitações de controle especificadas para o serviço (exceto para a solicitação de SERVICE_CONTROL_INTERROGATE, que sempre é enviada). Para obter uma lista das solicitações de controle que um serviço pode aceitar, consulte o membro dwControlsAccepted da estrutura SERVICE_STATUS . Para obter informações sobre como se registrar para receber eventos de dispositivo, consulte a função RegisterDeviceNotification .
O estado do serviço normalmente é alterado como resultado do tratamento de uma solicitação de controle. As solicitações de controle que fazem com que o estado do serviço seja alterado incluem SERVICE_CONTROL_STOP, SERVICE_CONTROL_PAUSE e SERVICE_CONTROL_CONTINUE. Se o serviço precisar fazer um processamento longo para lidar com qualquer uma dessas solicitações, ele deverá criar um thread secundário para executar o processamento longo e relatar o estado pendente correspondente ao SCM. (Para obter o melhor desempenho no Windows Vista e versões posteriores do Windows, o serviço deve usar um thread de trabalho de um pool de threads para essa finalidade.) Em seguida, o serviço deve relatar a transição de estado concluída quando o processamento longo for concluído. Para obter mais informações sobre como lidar com solicitações de controle, consulte Função de manipulador de controle de serviço.
Somente determinadas transições de estado de serviço são válidas. O diagrama a seguir mostra as transições válidas.
O estado do serviço relatado ao SCM determina como o SCM interage com o serviço. Por exemplo, se um serviço relatar SERVICE_STOP_PENDING, o SCM não transmitirá mais solicitações de controle para o serviço porque esse estado indica que o serviço está sendo desligado. O próximo estado relatado pelo serviço deve ser SERVICE_STOPPED porque esse é o único estado válido após SERVICE_STOP_PENDING. No entanto, se um serviço relatar uma transição que não é válida, o SCM não falhará na chamada.
O diagrama a seguir mostra as transições de estado do serviço com mais detalhes, incluindo as solicitações de controle iniciadas por um programa de controle de serviço (o cliente de serviço) e as chamadas SetServiceStatus que um serviço faz para relatar alterações de estado para o SCM. Conforme mencionado anteriormente, o SCM envia apenas solicitações de controle que o serviço especificou que ele aceitará, portanto, um serviço pode não receber todas as solicitações mostradas no diagrama.
Tópicos relacionados