Restarting a windows service - windows

I want to schedule a restart of my custom services
automatically using a batch file with net stop, net start.
When net stop runs does it abort anything that is being done
immediately?
Just wondering what will happen if in the middle of processing?
Malcolm

It will call into your code asynchronously and it will be up to you to deal with it. You could enact a clean or abort as you see fit.

It really depends on how the service is implemented. "net stop" essentially calls into the service and says "would you kindly stop". Most services will comply with this command and stop in a timely fashion. However there are the bad services which do not comply and refuse to stop. In this case, net stop will take no further action.

It really depends on the service. I suspect most will try to get into a good state before stopping. It isn't a kill.

A service registers to receive events (via RegisterServiceCtrlHandler). When you do a net stop the registered callback will receive a callback with the SERVICE_CONTROL_STOP operation. How the service responds to that callback is up to the service implementation. It would make sense for the service to do regular application shutdown processing.

Like the others said, when you call net stop, it will invoke the OnStop in the Windows Service. If the OnStop does not kill all the threads in the app, or doesn't shut everything down properly, your service might not stop. (I've seen this happen in one of our WCF services: we didn't close the ServiceHost in OnStop, and therefore, the app would not stop at our command - we'd have to kill the process by hand.)
One common pattern I've seen is to try calling stop on the service, and if it doesn't die within a timeout (10 seconds), kill the process by force. As an alternative to batch files, PowerShell has some pretty good support for dealing with services.

Related

Should I process WM_ENDSESSION, WM_QUERYENDSESSION, both or neither?

If a system is trying to shut down, an app can block this shutdown by overriding OnQueryEndSession() and returning FALSE. Surely that means WM_ENDSESSION is the only definitive message to respond to regarding shutdown.
On the other hand, the top answer to this question quotes no less than Raymond Chen as saying that responding to WM_ENDSESSION is essentially pointless. So this is confusing.
Is there some kind of "best practice" principles to apply in deciding which of these messages (if any) one should respond to for doing what kinds of application shutdown work?
In particular, if neither message is handled, will a shutdown process cause an application to be closed as if the user had closed the application manually (e.g. click on red X close button)?
This article from Microsoft gives a very comprehensive discussion of end-of-session best practice both pre- and post-Vista. The article makes it quite clear that one should assume that if one receives a WM_QUERYENDSESSION then shutdown will occur at some point.
As soon as all applications have responded to the WM_ENDSESSION message, or been forced to terminate within 5 seconds of receiving the WM_ENDSESSION message, Windows may shut down at any time. This may limit what can be done in response to WM_ENDSESSION.
If an application requires more time to clean itself up:
If your application may need more than 5 seconds to complete its shutdown processing in response to WM_ENDSESSION, it should call ShutdownBlockReasonCreate() in its WM_QUERYENDSESSION handler, and promptly respond TRUE to WM_QUERYENDSESSION so as not to block shutdown. It should then perform all shutdown processing in its WM_ENDSESSION handler.
Windows will apparently not send any additional messages to your application to allow it to exit "gracefully" (e.g. WM_CLOSE). Rather, it will simply call TerminateProcess. If you want a graceful close, you have to build it yourself within the above constraints.
You do need to close down your application in WM_ENDSESSION, at least if you want to support the Restart Manager API. I think both MSDN and Raymond are wrong here. (Maybe it changed recently, or they overlooked the Restart Manager?)
The Restart Manager API is used by installers to close and restart exes which have files locked that they need to replace. To support being restarted by it, you call RegisterApplicationRestart and then need to have a window which handles WM_QUERYENDSESSION and WM_ENDSESSION.
If you don't shut down your app in the WM_ENDSESSION handler than it will simply keep running and block the Restart Manager, and in turn the installers trying to use it.
I found this out the hard way. MSDN explicitly says you don't need to call PostQuitMessage, but if I don't do that then my process keep running.
I suspect the documentation didn't realise the Restart Manager is different, and less forceful, compared to what happens when the entire OS shuts down.
(Edit: I should add, this was with a simple ATL COM EXE server, but as far as I can tell there was nothing about that complicating things, and Windows simply wasn't triggering a WM_QUIT to the message loop unless I did it myself.)

What is the correct way to self-terminate a MacOS XPC service?

I've successfully followed the Daemons and Service Guide - Creating XPC Services tutorial, along with the SandboxedFetch sample code and have a working Client / Service setup that is using the new NSXPCConnection class.
What still isn't entirely clear to me is how to properly self-terminate the service application once it has finished its job. I recognize that in many cases, the service is expected to remain alive, but in the use-case I have in mind, the service will be used to only to do some processing that I'd otherwise not perform in the main application. Once that processing is finished, there's no reason for the service application to remain. If the client needs another service at a later date, it can just re-create a new one.
Since the service is a lightweight, non-nibbed, NSApplication, I was trying to self-terminate it by calling invalidate from inside applicationWillTerminate, but that triggers an EXC_BAD_ACCESS exception almost every time. Calling invalidate on the service's [NSXPCListener serviceListener] generates slightly less reliable crashes, but it still crashes.
Calling invalidate from within the client application on its NSXPCConnection also generates an EXC_BAD_ACCESS exception almost every time.
So I'm curious what the correct sequence of steps is to cleanly shutdown the XPC service and then quit the service application. Ideally, the service would self-terminate after it has made its last XPC call to the client.
Attached is a small screenshot of what one of the exception's stacktrace looks like. (Yes, that's a webview that's loading in the service. Once the webview has finished loading, I want the service to self-terminate)
My first reaction is that you should not bother to terminate. When memory pressure occurs and your service is idle, launchd will kill your service. Exiting probably isn't in anyone's best interest because your service will take time to launch again. Don't terminate and you won't have to figure out why your attempt crashes.
But if for some reason you are determined to terminate, don't try so hard. Just do whatever you need to do to clean up (flush buffers, close network connections gracefully so the server doesn't suffer, whatever) and call exit. Although you seem to be using NSApplication, your service is not an application in any sense that the user cares about and there is no compelling reason to act like one in this respect. The host application needs to be able to cope with your service crashing anyway, so your deliberately exiting unceremoniously is just fine.
By the way, using NSApplication in an XPC service probably isn't the best idea because there's no supported way to declare that you want that. This might help explain why it isn't working as well as you'd like, though this paragraph should not be construed as a proper analysis of the crash. :-)

Is there a way to monitor a Windows service and alert people when it hangs/stops?

We have a service running on a Windows Server 2003 machine. This service watches a particular folder on an FTP server, and when files appear there, it invokes one of a few different executables to process them.
I've been asked to find a way for staff to be alerted in some way when this service hangs or stops.
Can anyone suggest anything with just this much information? If not, what else would you need to know?
Seems we could write ANOTHER service to watch THIS service, but then there's a chance THAT one would stop ... so we haven't resolved anything.
About the only thing that I know if is writing another application or service that monitors if that service is running; something like that shouldn't have any unexpected behavior and stop, hopefully.
Another thing to do is go to the service in Windows, go to its properties, and then go to recovery options. From here, you can set the behavior of a service if it is to fail. The options in Windows 7 are to restart the service or computer, or run a program. This program could send some sort of notification. However, I don't know if any or all of these options exist in Server 2003. This would also not likely work if the service were to just hang, but a service watching it probably wouldn't either.
Also, if you have the source code, you can override some of the service-related methods such as OnStop() (for C#) to send a notification, but I don't believe this works with a failure.
My personal choice would be to set the recovery options just to restart the service on failure, unless it repeatedly fails, which there is also an option for. But just do what you think will work best for you; there isn't really a fail-safe method to do it.
UPDATE:
I did check, and Server 2003 does indeed have the same recovery options in the service manager. As the guys said above, you can deal with that, but it is only in C++ from what I have seen; there is also a command prompt way to do it:
sc failure [servicename] reset= 0 actions= restart/60000
I found that command here and you can look at it more in its MSDN documentation. You could call this command from C# or other languages if you are not using C++, or use it directly from the command prompt if you do not have the source code.
Use ChangeServiceConfig2() to define Failure Actions for your service. You could use that to invoke an external command to issue the alert (or do pretty much anything else you want) if the service terminates unexpectedly.
The SCM (the component which handles services) has built-in auto-restart logic that you can take advantage of to restart your service, as necessary. Additionally and/or alternatively, you can configure 'custom actions' to be associated with a failure of the service - the custom action can include launching a program of your own, which could then log the failure, and perhaps manually restart your service.
You can read more about such custom actions on MSDN by looking at the documentation of the structure used to configure such actions: SERVICE_FAILURE_ACTIONS. Once you fill that structure, you notify the SCM by calling the ChangeServiceConfig2 function.
Please don't ask "well, what happens if my failure handler program crashes" :)

How to list Windows Services from within a Service

sc query state= all works as expected from the command line.
From within another Service, sc query state= all doesn't print anything to that sub-process' stdout (captured by the parent, of course).
Is there a permission/privilege that the Service needs in order to list/start/stop the other servies?
A little background: I am making a service that periodically restarts some misbehaving services.
Well, for one don't do that, at least not in a blocking manner. In order for your own service to respond to the SCM (Service Control Manager) in order to return its status, the service has to be able to execute its dispatcher code. This means that if you call this program and wait for it to exit you'll wait indefinitely. One way to mitigate this would be to put this into a separate thread so it's not blocking your dispatching and your service will continue to talk to the SCM.
Alternatively (and probably better) you could use the EnumServicesStatusEx function to talk to the SCM and inquire about the statuses of other services yourself. The function itself doesn't mention anything about being blocking, so you'd have to figure out yourself whether it is and then use a thread again to prevent your service from stopping to talk to the SCM.
One last note: if those misbehaving services are yours, you should more likely fix the respective code. I've had a share of legacy code and had one misbehaving service which got its own helper application as "fault action" (can be configured in service configuration as SERVICE_CONFIG_FAILURE_ACTIONS) that would go about and restart the service whenever it crashed. Once I took that code over, figured out the cause and fixed it, the service was stable again and that application isn't really needed anymore.

windows service doesn't stop

I have a problem concerning a windows service that I have implemented. The service does what it has to and logs various information but when I try to stop it, it doesn't seem to stop and keeps logging.
I am not very familiar with services, so if anyone knows why this is happening please tell me.
Edit: I have tested the service on two servers and the weird thing is that on one server it stops normally, but on the other it doesn't. That is what I don't understand.
IN case you have any threads ensure that you exit those threads in your stop routine. Some threads may still be lingering which is why it does not stop.
One possible reason could be because of some remaining thread (as mentioned by 'ckv').
Have you set proper handler using RegisterServiceCtrlHandler function?
Also make sure that the SERVICE_STATUS structure that you use has its dwControlsAccepted set to accept shutdown or stop (by setting SERVICE_ACCEPT_SHUTDOWN & SERVICE_ACCEPT_STOP). and don't forget to update the service status (using SetServiceStatus function) once the service is up and running.

Resources