📄 signal.texi
字号:
The @code{signal} function returns the action that was previously ineffect for the specified @var{signum}. You can save this value andrestore it later by calling @code{signal} again.If @code{signal} can't honor the request, it returns @code{SIG_ERR}instead. The following @code{errno} error conditions are defined forthis function:@table @code@item EINVALYou specified an invalid @var{signum}; or you tried to ignore or providea handler for @code{SIGKILL} or @code{SIGSTOP}.@end table@end deftypefunHere is a simple example of setting up a handler to delete temporaryfiles when certain fatal signals happen:@smallexample#include <signal.h>voidtermination_handler (int signum)@{ struct temp_file *p; for (p = temp_file_list; p; p = p->next) unlink (p->name);@}intmain (void)@{ @dots{} if (signal (SIGINT, termination_handler) == SIG_IGN) signal (SIGINT, SIG_IGN); if (signal (SIGHUP, termination_handler) == SIG_IGN) signal (SIGHUP, SIG_IGN); if (signal (SIGTERM, termination_handler) == SIG_IGN) signal (SIGTERM, SIG_IGN); @dots{}@}@end smallexample@noindentNote how if a given signal was previously set to be ignored, this codeavoids altering that setting. This is because non-job-control shellsoften ignore certain signals when starting children, and it is importantfor the children to respect this.We do not handle @code{SIGQUIT} or the program error signals in thisexample because these are designed to provide information for debugging(a core dump), and the temporary files may give useful information.@comment signal.h@comment SVID@deftypefun sighandler_t ssignal (int @var{signum}, sighandler_t @var{action})The @code{ssignal} function does the same thing as @code{signal}; it isprovided only for compatibility with SVID.@end deftypefun@comment signal.h@comment ANSI@deftypevr Macro sighandler_t SIG_ERRThe value of this macro is used as the return value from @code{signal}to indicate an error.@end deftypevr@ignore@comment RMS says that ``we don't do this''.Implementations might define additional macros for built-in signalactions that are suitable as a @var{action} argument to @code{signal},besides @code{SIG_IGN} and @code{SIG_DFL}. Identifiers whose namesbegin with @samp{SIG_} followed by an uppercase letter are reserved forthis purpose.@end ignore@node Advanced Signal Handling@subsection Advanced Signal Handling@cindex @code{sigaction} functionThe @code{sigaction} function has the same basic effect as@code{signal}: to specify how a signal should be handled by the process.However, @code{sigaction} offers more control, at the expense of morecomplexity. In particular, @code{sigaction} allows you to specifyadditional flags to control when the signal is generated and how thehandler is invoked.The @code{sigaction} function is declared in @file{signal.h}.@pindex signal.h@comment signal.h@comment POSIX.1@deftp {Data Type} {struct sigaction}Structures of type @code{struct sigaction} are used in the@code{sigaction} function to specify all the information about how tohandle a particular signal. This structure contains at least thefollowing members:@table @code@item sighandler_t sa_handlerThis is used in the same way as the @var{action} argument to the@code{signal} function. The value can be @code{SIG_DFL},@code{SIG_IGN}, or a function pointer. @xref{Basic Signal Handling}.@item sigset_t sa_maskThis specifies a set of signals to be blocked while the handler runs.Blocking is explained in @ref{Blocking for Handler}. Note that thesignal that was delivered is automatically blocked by default before itshandler is started; this is true regardless of the value in@code{sa_mask}. If you want that signal not to be blocked within itshandler, you must write code in the handler to unblock it.@item int sa_flagsThis specifies various flags which can affect the behavior of the signal. These are described in more detail in @ref{Flags for Sigaction}.@end table@end deftp@comment signal.h@comment POSIX.1@deftypefun int sigaction (int @var{signum}, const struct sigaction *@var{action}, struct sigaction *@var{old-action})The @var{action} argument is used to set up a new action for the signal@var{signum}, while the @var{old-action} argument is used to returninformation about the action previously associated with this symbol.(In other words, @var{old-action} has the same purpose as the@code{signal} function's return value---you can check to see what theold action in effect for the signal was, and restore it later if youwant.)Either @var{action} or @var{old-action} can be a null pointer. If@var{old-action} is a null pointer, this simply suppresses the returnof information about the old action. If @var{action} is a null pointer,the action associated with the signal @var{signum} is unchanged; thisallows you to inquire about how a signal is being handled without changingthat handling.The return value from @code{sigaction} is zero if it succeeds, and@code{-1} on failure. The following @code{errno} error conditions aredefined for this function:@table @code@item EINVALThe @var{signum} argument is not valid, or you are trying totrap or ignore @code{SIGKILL} or @code{SIGSTOP}.@end table@end deftypefun@node Signal and Sigaction@subsection Interaction of @code{signal} and @code{sigaction}It's possible to use both the @code{signal} and @code{sigaction}functions within a single program, but you have to be careful becausethey can interact in slightly strange ways.The @code{sigaction} function specifies more information than the@code{signal} function, so the return value from @code{signal} cannotexpress the full range of @code{sigaction} possibilities. Therefore, ifyou use @code{signal} to save and later reestablish an action, it maynot be able to reestablish properly a handler that was established with@code{sigaction}.To avoid having problems as a result, always use @code{sigaction} tosave and restore a handler if your program uses @code{sigaction} at all.Since @code{sigaction} is more general, it can properly save andreestablish any action, regardless of whether it was establishedoriginally with @code{signal} or @code{sigaction}.On some systems if you establish an action with @code{signal} and thenexamine it with @code{sigaction}, the handler address that you get maynot be the same as what you specified with @code{signal}. It may noteven be suitable for use as an action argument with @code{signal}. Butyou can rely on using it as an argument to @code{sigaction}. Thisproblem never happens on the GNU system.So, you're better off using one or the other of the mechanismsconsistently within a single program. @strong{Portability Note:} The basic @code{signal} function is a featureof ANSI C, while @code{sigaction} is part of the POSIX.1 standard. Ifyou are concerned about portability to non-POSIX systems, then youshould use the @code{signal} function instead.@node Sigaction Function Example@subsection @code{sigaction} Function ExampleIn @ref{Basic Signal Handling}, we gave an example of establishing asimple handler for termination signals using @code{signal}. Here is anequivalent example using @code{sigaction}:@smallexample#include <signal.h>voidtermination_handler (int signum)@{ struct temp_file *p; for (p = temp_file_list; p; p = p->next) unlink (p->name);@}intmain (void)@{ @dots{} struct sigaction new_action, old_action; /* @r{Set up the structure to specify the new action.} */ new_action.sa_handler = termination_handler; sigemptyset (&new_action.sa_mask); new_action.sa_flags = 0; sigaction (SIGINT, NULL, &old_action); if (old_action.sa_handler != SIG_IGN) sigaction (SIGINT, &new_action, NULL); sigaction (SIGHUP, NULL, &old_action); if (old_action.sa_handler != SIG_IGN) sigaction (SIGHUP, &new_action, NULL); sigaction (SIGTERM, NULL, &old_action); if (old_action.sa_handler != SIG_IGN) sigaction (SIGTERM, &new_action, NULL); @dots{}@}@end smallexampleThe program just loads the @code{new_action} structure with the desiredparameters and passes it in the @code{sigaction} call. The usage of@code{sigemptyset} is described later; see @ref{Blocking Signals}.As in the example using @code{signal}, we avoid handling signalspreviously set to be ignored. Here we can avoid altering the signalhandler even momentarily, by using the feature of @code{sigaction} thatlets us examine the current action without specifying a new one.Here is another example. It retrieves information about the currentaction for @code{SIGINT} without changing that action.@smallexamplestruct sigaction query_action;if (sigaction (SIGINT, NULL, &query_action) < 0) /* @r{@code{sigaction} returns -1 in case of error.} */ else if (query_action.sa_handler == SIG_DFL) /* @r{@code{SIGINT} is handled in the default, fatal manner.} */else if (query_action.sa_handler == SIG_IGN) /* @r{@code{SIGINT} is ignored.} */else /* @r{A programmer-defined signal handler is in effect.} */@end smallexample@node Flags for Sigaction@subsection Flags for @code{sigaction}@cindex signal flags@cindex flags for @code{sigaction}@cindex @code{sigaction} flagsThe @code{sa_flags} member of the @code{sigaction} structure is acatch-all for special features. Most of the time, @code{SA_RESTART} isa good value to use for this field.The value of @code{sa_flags} is interpreted as a bit mask. Thus, youshould choose the flags you want to set, @sc{or} those flags together,and store the result in the @code{sa_flags} member of your@code{sigaction} structure.Each signal number has its own set of flags. Each call to@code{sigaction} affects one particular signal number, and the flagsthat you specify apply only to that particular signal.In the GNU C library, establishing a handler with @code{signal} sets allthe flags to zero except for @code{SA_RESTART}, whose value depends onthe settings you have made with @code{siginterrupt}. @xref{InterruptedPrimitives}, to see what this is about.@pindex signal.hThese macros are defined in the header file @file{signal.h}.@comment signal.h@comment POSIX.1@deftypevr Macro int SA_NOCLDSTOPThis flag is meaningful only for the @code{SIGCHLD} signal. When theflag is set, the system delivers the signal for a terminated childprocess but not for one that is stopped. By default, @code{SIGCHLD} isdelivered for both terminated children and stopped children.Setting this flag for a signal other than @code{SIGCHLD} has no effect.@end deftypevr@comment signal.h@comment BSD@deftypevr Macro int SA_ONSTACKIf this flag is set for a particular signal number, the system uses thesignal stack when delivering that kind of signal. @xref{Signal Stack}.If a signal with this flag arrives and you have not set a signal stack,the system terminates the program with @code{SIGILL}.@end deftypevr@comment signal.h@comment BSD@deftypevr Macro int SA_RESTARTThis flag controls what happens when a signal is delivered duringcertain primitives (such as @code{open}, @code{read} or @code{write}),and the signal handler returns normally. There are two alternatives:the library function can resume, or it can return failure with errorcode @code{EINTR}.The choice is controlled by the @code{SA_RESTART} flag for theparticular kind of signal that was delivered. If the flag is set,returning from a handler resumes the library function. If the flag isclear, returning from a handler makes the function fail.@xref{Interrupted Primitives}.@end deftypevr@node Initial Signal Actions@subsection Initial Signal Actions@cindex initial signal actionsWhen a new process is created (@pxref{Creating a Process}), it inheritshandling of signals from its parent process. However, when you load anew process image using the @code{exec} function (@pxref{Executing aFile}), any signals that you've defined your own handlers for revert totheir @code{SIG_DFL} handling. (If you think about it a little, thismakes sense; the handler functions from the old program are specific tothat program, and aren't even present in the address space of the newprogram image.) Of course, the new program can establish its ownhandlers.When a program is run by a shell, the shell normally sets the initialactions for the child process to @code{SIG_DFL} or @code{SIG_IGN}, asappropriate. It's a good idea to check to make sure that the shell hasnot set up an initial action of @code{SIG_IGN} before you establish yourown signal handlers.Here is an example of how to establish a handler for @code{SIGHUP}, butnot if @code{SIGHUP} is currently ignored:@smallexample@group@dots{}struct sigaction temp;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -