C++ : Running a background task all the time on machine - c++

I want to make an MFC app which leave a thread/process running in the background all the time that keeps track of something like hard disk size.
Whenever the hard disk size goes beyond lets say 90% it shows a warning dialog (also MFC dialog of same app).
I am not sure how to do it.
I tried the windows service option, but it doesn't seem much reliable to me , as most of the times, the service is not successfully installed, or if installed it doesn't get started successfully.
What other options do I have to achieve it?
Any help is appreciated.

Create a worker thread which keep on monitoring the disk space.
Create a user defined message in the main thread and provide a handler for it
When disk space goes more than 90%, Post a message (Post the user defined message that you created)
From the main thread handler for the user defined message "Display the warning message"
Note: Services are not suitable for this task as they don't like user interactions.

Related

How to report correctly the abrupt end of another process in Linux?

I'm working on a embedded solution where two apps are working: one is the user interface and the other runs in the background providing data for the UI.
Recently I came across with a memory leak or similar error that is making Linux kill the secondary process, leaving the UI in a stopped situation without telling anything for the user about what is going on. I reached the problem by reading Linux's message log file and the software's print on terminal "Kill -myapp".
My question is: how could I notice such an event (and other similar) coming from the secondary software so I could properly report it to the user and log it? I mean, it's easy to have a look time to time in the process 'tree' to see if the secondary app is running and, if it's not, report a "some event happened" in the UI and it's also plausible to have a error-handler system inside the secondary app that makes it write in a log file what just happened and make the UI read that file for new entries from time to time, but how could the UI app knows with better details what is going on in such more abrupt events? (in this case, "Linux killed process", but it could be a "segmentation pipe" or any other) (and if there is another, better solution that this "constant read a log file produced by the secondary app", I'ld also like to know)
Notes: the UI is written in C++/Qt and the secondary app is in C. Although a solution using the Qt library would be welcomed, I think it would be better for the entire programming community if a more generalized solution was given.
You can create a signal handler for POSIX signals such as SIGKILL in the backend process and notify the ui using for example another signal with sigqueue. Any IPC mechanism should work, as long as it's async safe. Read more about signals: tutorial and manual
It may still be a good idea to check from the ui side periodically because the handler might not succeed.
As for a better way to check if process is alive compared to reading the log file:
Check if process exists given its pid

How to detect if computer is shutting down to save session

I am making an RPG game with C++/x86 asm. My question is related to the C++ component. In C++/win32 how would I detect if the computer is shutting down or turning off, or whatever else - so that I can save the game session. My game has a 'save' option, but if the user or another program decides to shut off the computer how can I detect this with some kind of API hook so that I can instantly save the game session to the text file.
Now please don't suggest an option by creating a thread to run passively as I want to keep the file size to a minimum, so if you can suggest some sort of WM_ hook that would be great. I'd refer to MSDN but I don't want to be searching for hours through their WM directory.
You can handle session saving in response to the WM_ENDSESSION message. Note that after your message handler returns from handling this, your process may be terminated at any time, so you need to save it directly during the message handler, and not just set a flag to let some later code handle the saving, because that later code might not get to execute.
A comment suggests the WM_QUERYENDSESSION message. This has a slightly different meaning: it gives applications the chance to complain about the session ending, and gives the user a chance to not log off / shut down the system. Based on your question, you have no intention of preventing any such thing, so WM_ENDSESSION seems like a better match to me.

How to make a c++ program which is waiting for some event, appear responsive?

I am using visual studio 2010 to develop a windows form application using c++.
This program waits for an event like connection request and displays a message
But this program is shown as "not responding" in windows task manager.
Is there any way to make the program appear responsive ??
The standard practice for this situation is to use multi-threading. Create a background thread to wait for the connection request or whatever event you need that might cause the primary thread to block.
This allows the user interface of your application to remain responsive. If you don't use a thread, the primary UI thread will be blocked waiting for the request and can't handle other events such as drawing the form, responding to window events, etc.
In Windows programming, any activity that is going to take a significant amount of time should be threaded. This isn't a hard rule, but a pragmatic amount of threading will make a world of different in giving your application a smooth, responsive feel. The primary thread should be reserved for drawing and handling user interaction.
A Google search will give you plenty of examples, but here is a decent one to get you started.

Working with a shut-down state of a user session on Windows?

Say, if I open a Notepad, type something in it and don't save it, then call the following API from the same user session:
ExitWindowsEx(EWX_LOGOFF, SHTDN_REASON_MAJOR_OTHER | SHTDN_REASON_MINOR_OTHER | SHTDN_REASON_FLAG_PLANNED);
That user session will enter a "shut-down state", where OS will show an overlay window displaying a message that Notepad prevents system from logging off a user. This overlay will not go away until a user clicks "Cancel" or "Force Quit" buttons.
So two part question:
Is there any way to know which processes blocked logging-off/shut-down process?
Is there any way to cancel this user-session "shut-down state" programmatically?
PS. This state can be detected by calling GetSystemMetrics(SM_SHUTTINGDOWN);
EDIT: Contrary to the answer below, I am not trying to stop system from shutting down, nor that any user-mode process is "hung."
EDIT2: Here's a screenshot of the overlay I'm trying to cancel/close:
Question 2: "Is there any way to cancel this shut-down state programmatically?"
The short is answer is not really. And neither should you want to really stop shutdown programatically UNLESS: shutting down will result in serious data loss or significantly affect the user experience on a subsequent system start up. But to mention just one example: imagine a computer is overheating - stopping shutdown programmatically could result in a fried system (and a very irate user).
System shutdown is also not the only thing you need to monitor. There's also hibernate and suspend events (have a look at WM_POWERBROADCAST message).
That said, Windows provides a plethora of mechanisms for detecting system shutdown. For instance:
If your application has a message pump you can choose to return FALSE when Windows polls running applications to vote on WM_QUERYENDSESSION , however Windows from Vista onwards will still force a shutdown after a time-out. From Vista onwards you can (and need to) ShutdownBlockReasonCreate after returning false to WM_QUERYENDSESSION.
If your application is running as a service you can use RegisterServiceCtrHandlerEx and then SetServiceStatus to get a 3 minute shutdown extension grace by setting SERVICE_ACCEPT_PRESHUTDOWN which will get you a SERVICE_CONTROL_PRESHUTDOWN notification. Naturally, you won't receive logoff notification because a service is not affected by logoff. Pre-Vista you can register for SERVICE_CONTROL_SHUTDOWN notification.
Console applications (and gui apps as well but it does not make sense) can use SetConsoleCtrlHandler to be notified of CTRL_LOGOFF and CTRL_SHUTDOWN_EVENT.
At a much lower level one can try hooking API functions such as NTShutdown or even NtSetSystemPowerState which apparently is "the last thing called during ANY type of reboot". But I would strongly suggest not to attempt this.
That said there are ways to really strongly insist that the system should not be shutdown.
Consider the following:
1.) Try to register your application to be first in line to receive Shutdown notification. Something like:
// http://msdn.microsoft.com/en-us/library/windows/desktop/ms686227(v=vs.85).aspx
if(!SetProcessShutdownParameters(0x4ff, 0)) // greedy highest documented System reserved FirstShutdown
{
// Fallback
if(!SetProcessShutdownParameters(0x3ff, 0)) // highest notification range for applications
{
// shouldn't happen
}
}
2.) Return FALSE on WM_QUERYENDSESSION
From Vista onwards call ShutdownBlockReasonCreate() after returning false on WM_QUERYENDSESSION.
3.) Tell Windows that you need the system to stay up and available. Have a look at
http://msdn.microsoft.com/en-us/library/windows/desktop/aa373208(v=vs.85).aspx
SetThreadExecutionState(ES_CONTINUOUS | ES_SYSTEM_REQUIRED | ES_DISPLAY_REQUIRED);
4.) Clean up, call ShutdownBlockReasonDestroy() on Vista onwards, and THEN shutdown the system cleanly.
You could also try the undocumented function (at least it's not on MSDN anymore) CancelShutdown in "user32.dll" which at some point (still may) used to function very much like calling shutdown.exe with the abort flag.
Your mileage may vary.
Following your edit which makes your question clearer:
If you monitor WM_QUERYENDSESSION and respond FALSE to it you can poll from your still running process for a predetermined period of time and then issue an ExitWindowsEx call with flag EWX_FORCEIFHUNG, for example on WM_ENDSESSION. Or you could actually call this pre-emptively on receiving WM_QUERYENDSESSION - the problem is: what if forcing the shutdown results in serious data loss? You're not doing the user of the system any good at that point.
Update following your comments:
How about this:
To find out blocking application:
Register your app with SetProcessShutdownParameters to be first in
line to get WM_QUERYENDSESSION.
Respond FALSE to WM_QUERYENDSESSION and on Vista onwards call
ShutdownBlockReasonCreate to buy yourself the time.
Get the first window in the chain HWND top = GetTopWindow(NULL)
Get the process ThreadId from hwnd GetWindowThreadProcessId() (compare it with your running app's ;) )
Use SendMessageTimeOut with a message to the hWnd - if you receive
no response (timeout) you may have found the blocking window. Go to step 6.
If not skip to 7.
Use OpenProcess() with the handle returned from
GetWindowThreadProcessId to get a process handle and call
GetModuleBaseName() to get the name of the hung process.
If you haven't found the hung window, enumerate the next Window with
GetNextWindow() and go back to step 4.
You can also try using the enumerate window handle technique above to find out if you can get a handle to the "hung window" overlay. Having this might give you a chance to do a send key to cancel the state. My bet is that you won't be able to access it but I haven't tried :)
Again your mileage may vary :)

Why can't my MFC app exit completely?

I made a MFC application which probably has two threads, one for receiving data from a socket using UDP protocol and one is the main thread of MFC app. While any data is received some objects, created in the main thread by new operator, would be notified to fetch the data through apply the observer design pattern. The problem is that sometimes after I clicked the close system button, the GUI of the app disappeared, but its process can still be found in the Task Manager. If I stop the data source (UDP client) this problem would never happen. Other important and maybe helpful information is listed below:
The Observer design pattern was implemented with STL container list. I have used the critical section protection in the Attach, Detach and Notify functions.
I deleted the observer objects before closing the UDP socket.
The data transfer rate may be a little faster than process data, because after closing the data source the data process is still working.
I can't figure out what lead my app can not exit completely. Please give me some clues.
This is usually caused by a thread you created and not exit it programmatically when you exit the appliation. There must be a while clause in your thread. The way to find where it is still running is:
use debug mode to start you application and click the exit button the top right corner to exit it.
Check from task manager and see if it is still running
if it is, excute Debug->Break All,
Open threads windows, double click each thread, you will find where your code is still looping.
Typically a process won't terminate because there's still a foreground thread running somewhere. You must ensure that your socket library isn't running any thread when you want to close your application.
First thing, with MFC, please use the notification based methods to get notifications on message arrivals, connections etc. So you can get rid of threads if you have.
It's quite easy to attache to a debugger and Break see which threads are existing and waiting for what.
Alternatively you can use ProcessExplorer with proper symbol configuration to see the call stacks of the threads available for the particular process.
The application can two kind of issues to exit, one could be infinite loop and other might be waiting/deadlock (e.g. socket read command is a blocking call). You can easily deduce the problem by attaching to debugger.
Otherwise please provide further information about the threads, code snippet possible.