installing a signal handler for a process? Can it be clarified that it cannot be uninstalled? - operating-system

I dont see any other sources on stack overflow, but is it true when you install a signal handler for a process, it therefore cannot be uninstalled? If this is true can you explain why?

This is not correct. You can uninstall a signal handler perfectly well, by calling signal or sigaction again to either replace your handler with a different signal handler, or change the action to SIG_DFL or SIG_IGN.

Related

How to detect Force Close on Mac OS X app

I have a Mac OS X app and I want to detect or catch the event when the user Force Close my app.
At first I thought applicationWillTerminate will do the work but it didn't:
func applicationWillTerminate(_ aNotification: Notification) {
print("applicationWillTerminate called")
}
Do you have any idea how can I do that?
Major credit goes to #caseynolan for putting work in here to come up with an answer. Unfortunately, there are, in fact, some major issues with the suggested approach.
First, signal handlers are per-process. There are other, legitimate uses of signals, and installing handlers will negatively impact their behavior without very careful work.
Second, signals interrupt a thread, and that thread can be doing anything, including holding locks. Examples of things that hold locks - malloc/free, the Objective-C runtime.
This is an part of a class of problems known as "async safety". If you check out "man sigaction" (note, sigaction is a much improved API over signal) you see that there are actually a very small number of functions that are safe to call from a signal handler. Calling unsafe functions, like NSLog, will sometimes work. But, will also sometimes deadlock, depending on what the thread was doing at the time.
Now, I will admit that my experience with signals does not include use of SIGTERM. However, since it can be delivered at any time, it still will be subject to async safety issues, even thought it is not a crash.
In short: it is almost certainly unsafe to run your code in a signal handler, and it will deadlock sometimes. And, those deadlocks will occur during unpredictable points of its execution.
Third, there are fatal events that aren't mapped to signals, on top of SIGKILL. This may not matter to do, depending on how strong a guarantee you need about detecting your process termination.
What I'd do Instead:
I think you're only safe option is to use a sentinel process. The idea is you start up a child process, and in that child, observe the parent. If/when that process disappears, you can then execute your code.
This is a safe, deadlock-risk free way to monitor for arbitrary process exits. However, it could be challenging to move your operations out-of-process. Unfortunately, I believe that's a necessary aspect of this, if you want it to be reliable.
Good luck!
Disclaimer: I'm not an expert, and researching for this post has stretched the limits of my rusty C/Objective-C knowledge. I don't know how the following code is viewed by Apple for submissions to the App Store, so YMMV.
The following has been shamelessly ripped from Wikipedia and reworked:
#import <Foundation/Foundation.h>
/**
This will handle signals for us, specifically SIGTERM.
*/
void handleSignal(int sig) {
if (sig == SIGTERM) {
// Caught a SIGTERM
}
/*
SIGTERM is a clear directive to quit, so we exit
and return the signal number for us to inspect if we desire.
We can actually omit the exit(), and everything
will still build normally.
If you Force Quit the application, it will still eventually
exit, suggesting a follow-up SIGKILL is sent.
*/
exit(sig);
}
/**
This will let us set a handler for a specific signal (SIGTERM in this case)
*/
void setHandler() {
if (signal(SIGTERM, handleSignal) == SIG_ERR) {
NSLog(#"Failed to set a signal handler.");
} else {
NSLog(#"Successfully set a signal handler.");
}
}
Call only asynchronous-safe functions within signal handlers. See here.
You could place the above in a C/Objective-C file and use it in Swift via a Bridging Header. Call setHandler() somewhere in the beginning of your application's lifecycle, e.g. in applicationDidFinishLaunching, and you should now have a chance to do some work before your app is Force Quit. I don't know how much time you get here, so I'd keep the workload as light as possible (avoid starting mission-critical stuff here, I guess?).
Here's some background info:
In a typical Quit
The Quit procedure is actually a part of Apple Events.
If the application is NSDocument-based, the behavior depends on the saving parameter, which has one of these three values:
NSSaveOptionsNo: The application quits without sending a close message to any document.
NSSaveOptionsYes: Each unmodified document is sent a close message; each modified document is sent the following message:
saveDocumentWithDelegate:didSaveSelector:contextInfo:
NSSaveOptionsAsk: (This is the default value if no saving parameter is supplied in the event.) If there are modified documents
open, the NSDocumentController sends itself this message:
reviewUnsavedDocumentsWithAlertTitle:cancellable:delegate:didReviewAllSelector:contextInfo:
If the application is not NSDocument-based, the application delegate is sent this message (if it is implemented):
applicationShouldTerminate:
You can modify the default behavior by implementing this method.
Source: How Cocoa Applications Handle Apple Events
During Force Quit
The application is sent a SIGTERM which can be caught and dealt with by your application. Ideally, the application would clean up and exit as gracefully as possible, but this isn't required, and the signal can even be ignored.
An impatient user (and I strongly suspect that Force Quit does this eventually) may send a SIGKILL, which cannot be ignored and totally goes over anything you as the developer can stop.
Extra Information and Resources:
What does Force Quit do in OS X?
What signals does OS X send for the Quit and Force Quit commands?
How Cocoa Applications Handle Apple Events
SIGTERM vs. SIGKILL - major.io
C Signal Handling - Wikipedia

Waiting for a Future to complete before making assertions

I have a Scala Play application and one of the controllers fires a Future which does some logging. I have a simple call back function which executes when the Future completes.
I have written a test to check whether this logging happens. The rough logic is as follows:
feature{
scenario{
Given()
// set up the call
When()
// make a FakeRequest via reverse routing - logging will done in a separate thread via a Future
Then()
Thread.sleep(50) // sleep to allow logging to finish
// check if the logging has been done
The issue is the Thread.sleep. I have added that call in to block the main testing thread in order to give enough time to elapse for the Future which does the logging in a separate thread to complete before actually doing the checks to see if the logging has been done.
My question is whether there is a better way to do this? In reality if my application is running and the logging is taking an inordinate amount of time, then the main thread which governs the application will not terminate until the Future that does the logging in a separate thread finishes. So I don't see a problem of putting in the Thread call above to simulate that. But I just want to confirm if this is correct.
For me, there is absolutely no other way than to do this. If I try to replicate how the app behaves in reality with my test, then the main thread for the test should complete and terminate even though the future for the logging is still going on; there is no call back in the test and neither should there be.
Assuming you're using ScalaTest ; you can use whenReady construct ; which periodically inspects the passed future, until it is either ready or the configured timeout has been surpassed;
see
http://www.artima.com/docs-scalatest-2.0.M5/org/scalatest/concurrent/Futures.html
http://doc.scalatest.org/2.0/index.html#org.scalatest.concurrent.ScalaFutures

Why a form is needed for a SetWinEventHook callback?

Currently, I'm using the powerful SetWinEventHook() function to catch some user-interface's actions like minimizing and maximizing from other window runned by programs on the computer.
So I inspired myself by using the code provided by BrendanMcK on this post and it does work (I mean: the callback function is called when an event occurs) until the line
MessageBox.Show("Something")
is present. But I don't want to use any form or window for this program..
After some research, I figured out this kind of hook needs a message loop to allow the redirection of messages from other window handles. Apparently, calling the thread using Application.Run() should do the trick, but I would prefer something cleaner, in the C# object itself.
So my question is: is it possible to create a message loop inside an object's method?
http://bytes.com/topic/c-sharp/answers/557342-thread-message-loop-c
No, the function doesn't require a window handle so no "form" is needed. But the MSDN docs for the function is quite explicit:
The client thread that calls SetWinEventHook must have a message loop in order to receive events.
A message loop is universal in any program that want to receive notifications that are generated externally by other processes or threads. It is the common solution to the producer-consumer problem. Clearly any GUI app has a need for such a solution, Windows messages are generated by the operating system. It isn't different for SetWinEventHook(), the accessibility events originate in other programs. There is no clean mechanism to "interrupt" a thread and make it run other code, the re-entrancy problems that causes are extremely difficult to deal with. The thread has to co-operate, it must be idle and ready to receive a notification to safely process it. A message loop solves that problem.
Pumping a message loop (calling Application.Run) in a method is certainly possible. But do keep in mind that the method won't return until you explicitly stop the loop with Application.ExitThread. There is therefore usually only one good place for that call, the Main() method of your program.
Starting your project with a Winforms or WPF project template is a very good way to get this right. You have no need to actually create a window, call Application.Run() without an argument, after pinvoking SetWinEventHook.

What's Android Equivalent of iOS's Post Notification and Delegate function?

I find the Post notification and delegate function are very useful in iOS. Once I finish a task I can notify another piece of code to do something. I am sending out notices for others to do the work.
Post Notification is when you sending notice right away, whereas delegate sometime down the line it will send a notice.
In Android I know there's event Listener, but that's only passive listening. What about me actively sending notices? Does Android have that equivalent?
Handler which can be fired right away or with postDelay() you can fire them later
You could either use a Handler to get notified from a running Thread or the AsyncTask which does run some code and after it's finished it notifies the UI Thread.
You are probably looking for a way to thread your application? Where there are other "worker" threads that do long computations (or do buffered IO stuff). The way you would do this is by creating an AsyncTask. Within an AsyncTask, there is a "doInBackground" method that seems to be what "delegate" is in your question. "onPostExecute" will handle whatever's returned in "doInBackground". More in the AsyncTask documentation.
Another option is to simply use a Handler and use postDelay() for later executions:

how to resume/suspend a pthread in iphone os?

Now i face a problem in my porting job, when i need to implement a thread class that will work in not only wince, symbian ,but also unix-like system, like iphone.
I own a suspend/resume interface to implement, anything is ok in wince/symbian except iphone, i use the posix pthread to finish my job, but i search the whole docsets for a resume/suspend-like interface. Things seem to be difficult, pthread in iphone own a pthread_create_suspended_np that can create a thread in a suspend mode. Now how can i resume or suspend a thread after the thread has run to its stuff in anytime.
BTW, i search Google for some help, it seems that someone else also have this problem .
Some guys suggest use the SIGHUP signal, but this will suspend the whole process, that's absolutely not ok .
Many thanks if you guys can tell me some solutions for this problem.
It's actually a bad idea to try and control threads externally. You never know what state they may be in when you suspend them. If they have a mutex lock on a resource that's needed elsewhere, you can easily end up with a deadlock situation.
We had to create a "safe" suspend functionality without resorting to any non-portable pthread extensions a while ago and I'll try to remember how we did it.
It consisted of a suspension mutex for each thread and a variable indicating that threads state. So the thread we wanted to suspend would have a loop (they mostly do) that went something like this:
while true:
set mystate = suspended
claim mymutex
yield
release mymutex
set mystate = running
do some work
and the code to suspend/resume the thread would be:
function suspend (state,mutex):
claim mutex
while state <> suspended:
yield
function resume (state,mutex):
release mutex
while state <> running:
yield
What the suspender would do is basically get a lock on the mutex and wait for the thread to enter suspended state (the writing to mystate was done only by the suspendee and did not have to be protected by another mutex). The suspend function did not return until it was guaranteed that the suspendee would be stopped.
Similarly, resuming the thread released the mutex so the suspendee could restart and then waited until it had restarted before returning.
This allowed suspension to take place but under the control of the thread being suspended. That was much safer since it could ensure it could only be suspended at safe points when it didn't have any locks that could deadlock the application.
To suspend and resume a running thread, I believe you need to use pthread_cond_wait. Basically, that suspends the calling thread until the condition variable becomes true. Of course, you need to also give each thread a way to figure out when to call the function.
you give me a clue to solve this problem , yet this method or pthread_cond_wait just wait/singal when design some kind of situation. How can i suspend the special pthread without know more info. about the thread, we just own a thread id, we suspend it in another thread, when we wanna resume the suspended thread, we just probably run the resume function in anywhere. can we do something like this? or any other idea ?
regards.