{-# LINE 1 "System/Posix/Signals.hsc" #-}{-# LANGUAGE CApiFFI, CPP, DeriveDataTypeable, NondecreasingIndentation #-}{-# OPTIONS_GHC -fno-cse #-}-- global variables{-# LANGUAGE Trustworthy #-}------------------------------------------------------------------------------- |-- Module : System.Posix.Signals-- Copyright : (c) The University of Glasgow 2002-- License : BSD-style (see the file libraries/base/LICENSE)---- Maintainer : libraries@haskell.org-- Stability : provisional-- Portability : non-portable (requires POSIX)---- POSIX signal support-------------------------------------------------------------------------------
#include "HsUnixConfig.h"
{-# LINE 22 "System/Posix/Signals.hsc" #-}{-# LINE 24 "System/Posix/Signals.hsc" #-}moduleSystem.Posix.Signals(-- * The Signal typeSignal ,-- * Specific signalsnullSignal ,internalAbort ,sigABRT ,realTimeAlarm ,sigALRM ,busError ,sigBUS ,processStatusChanged ,sigCHLD ,continueProcess ,sigCONT ,floatingPointException ,sigFPE ,lostConnection ,sigHUP ,illegalInstruction ,sigILL ,keyboardSignal ,sigINT ,killProcess ,sigKILL ,openEndedPipe ,sigPIPE ,keyboardTermination ,sigQUIT ,segmentationViolation ,sigSEGV ,softwareStop ,sigSTOP ,softwareTermination ,sigTERM ,keyboardStop ,sigTSTP ,backgroundRead ,sigTTIN ,backgroundWrite ,sigTTOU ,userDefinedSignal1 ,sigUSR1 ,userDefinedSignal2 ,sigUSR2 ,{-# LINE 52 "System/Posix/Signals.hsc" #-}pollableEvent,sigPOLL ,{-# LINE 54 "System/Posix/Signals.hsc" #-}profilingTimerExpired,sigPROF ,badSystemCall ,sigSYS ,breakpointTrap ,sigTRAP ,urgentDataAvailable ,sigURG ,virtualTimerExpired ,sigVTALRM ,cpuTimeLimitExceeded ,sigXCPU ,fileSizeLimitExceeded ,sigXFSZ ,-- * Sending signalsraiseSignal ,signalProcess ,signalProcessGroup ,-- * Handling signalsHandler (Default ,Ignore ,Catch ,CatchOnce ,CatchInfo ,CatchInfoOnce ),SignalInfo (..),SignalSpecificInfo (..),installHandler ,-- * Signal setsSignalSet ,emptySignalSet ,fullSignalSet ,reservedSignals ,addSignal ,deleteSignal ,inSignalSet ,-- * The process signal maskgetSignalMask ,setSignalMask ,blockSignals ,unblockSignals ,-- * The alarm timerscheduleAlarm ,-- * Waiting for signalsgetPendingSignals ,awaitSignal ,-- * The @NOCLDSTOP@ flagsetStoppedChildFlag ,queryStoppedChildFlag ,-- MISSING FUNCTIONALITY:-- sigaction(), (inc. the sigaction structure + flags etc.)-- the siginfo structure-- sigaltstack()-- sighold, sigignore, sigpause, sigrelse, sigset-- siginterrupt)whereimportData.WordimportForeign.CimportForeign.ForeignPtrimportForeign.MarshalimportForeign.PtrimportForeign.Storable{-# LINE 108 "System/Posix/Signals.hsc" #-}importSystem.IO.Unsafe(unsafePerformIO)importSystem.Posix.TypesimportSystem.Posix.InternalsimportSystem.Posix.Process importSystem.Posix.Process.Internals importData.Dynamic{-# LINE 124 "System/Posix/Signals.hsc" #-}
#include "rts/Signals.h"
{-# LINE 126 "System/Posix/Signals.hsc" #-}importGHC.Conchiding(Signal){-# LINE 132 "System/Posix/Signals.hsc" #-}-- ------------------------------------------------------------------------------- Specific signalsnullSignal ::Signal nullSignal :: CInt
nullSignal =CInt
0-- | Process abort signal.sigABRT ::CIntsigABRT :: CInt
sigABRT =CONST_SIGABRT-- | Alarm clock.sigALRM ::CIntsigALRM :: CInt
sigALRM =CONST_SIGALRM-- | Access to an undefined portion of a memory object.sigBUS ::CIntsigBUS :: CInt
sigBUS =CONST_SIGBUS-- | Child process terminated, stopped, or continued.sigCHLD ::CIntsigCHLD :: CInt
sigCHLD =CONST_SIGCHLD-- | Continue executing, if stopped.sigCONT ::CIntsigCONT :: CInt
sigCONT =CONST_SIGCONT-- | Erroneous arithmetic operation.sigFPE ::CIntsigFPE :: CInt
sigFPE =CONST_SIGFPE-- | Hangup.sigHUP ::CIntsigHUP :: CInt
sigHUP =CONST_SIGHUP-- | Illegal instruction.sigILL ::CIntsigILL :: CInt
sigILL =CONST_SIGILL-- | Terminal interrupt signal.sigINT ::CIntsigINT :: CInt
sigINT =CONST_SIGINT-- | Kill (cannot be caught or ignored).sigKILL ::CIntsigKILL :: CInt
sigKILL =CONST_SIGKILL-- | Write on a pipe with no one to read it.sigPIPE ::CIntsigPIPE :: CInt
sigPIPE =CONST_SIGPIPE-- | Terminal quit signal.sigQUIT ::CIntsigQUIT :: CInt
sigQUIT =CONST_SIGQUIT-- | Invalid memory reference.sigSEGV ::CIntsigSEGV :: CInt
sigSEGV =CONST_SIGSEGV-- | Stop executing (cannot be caught or ignored).sigSTOP ::CIntsigSTOP :: CInt
sigSTOP =CONST_SIGSTOP-- | Termination signal.sigTERM ::CIntsigTERM :: CInt
sigTERM =CONST_SIGTERM-- | Terminal stop signal.sigTSTP ::CIntsigTSTP :: CInt
sigTSTP =CONST_SIGTSTP-- | Background process attempting read.sigTTIN ::CIntsigTTIN :: CInt
sigTTIN =CONST_SIGTTIN-- | Background process attempting write.sigTTOU ::CIntsigTTOU :: CInt
sigTTOU =CONST_SIGTTOU-- | User-defined signal 1.sigUSR1 ::CIntsigUSR1 :: CInt
sigUSR1 =CONST_SIGUSR1-- | User-defined signal 2.sigUSR2 ::CIntsigUSR2 :: CInt
sigUSR2 =CONST_SIGUSR2{-# LINE 220 "System/Posix/Signals.hsc" #-}-- | Pollable event.sigPOLL ::CIntsigPOLL :: CInt
sigPOLL =CONST_SIGPOLL{-# LINE 224 "System/Posix/Signals.hsc" #-}-- | Profiling timer expired.sigPROF ::CIntsigPROF :: CInt
sigPROF =CONST_SIGPROF-- | Bad system call.sigSYS ::CIntsigSYS :: CInt
sigSYS =CONST_SIGSYS-- | Trace/breakpoint trap.sigTRAP ::CIntsigTRAP :: CInt
sigTRAP =CONST_SIGTRAP-- | High bandwidth data is available at a socket.sigURG ::CIntsigURG :: CInt
sigURG =CONST_SIGURG-- | Virtual timer expired.sigVTALRM ::CIntsigVTALRM :: CInt
sigVTALRM =CONST_SIGVTALRM-- | CPU time limit exceeded.sigXCPU ::CIntsigXCPU :: CInt
sigXCPU =CONST_SIGXCPU-- | File size limit exceeded.sigXFSZ ::CIntsigXFSZ :: CInt
sigXFSZ =CONST_SIGXFSZ-- | Alias for 'sigABRT'.internalAbort ::Signal internalAbort :: CInt
internalAbort =CInt
sigABRT -- | Alias for 'sigALRM'.realTimeAlarm ::Signal realTimeAlarm :: CInt
realTimeAlarm =CInt
sigALRM -- | Alias for 'sigBUS'.busError ::Signal busError :: CInt
busError =CInt
sigBUS -- | Alias for 'sigCHLD'.processStatusChanged ::Signal processStatusChanged :: CInt
processStatusChanged =CInt
sigCHLD -- | Alias for 'sigCONT'.continueProcess ::Signal continueProcess :: CInt
continueProcess =CInt
sigCONT -- | Alias for 'sigFPE'.floatingPointException ::Signal floatingPointException :: CInt
floatingPointException =CInt
sigFPE -- | Alias for 'sigHUP'.lostConnection ::Signal lostConnection :: CInt
lostConnection =CInt
sigHUP -- | Alias for 'sigILL'.illegalInstruction ::Signal illegalInstruction :: CInt
illegalInstruction =CInt
sigILL -- | Alias for 'sigINT'.keyboardSignal ::Signal keyboardSignal :: CInt
keyboardSignal =CInt
sigINT -- | Alias for 'sigKILL'.killProcess ::Signal killProcess :: CInt
killProcess =CInt
sigKILL -- | Alias for 'sigPIPE'.openEndedPipe ::Signal openEndedPipe :: CInt
openEndedPipe =CInt
sigPIPE -- | Alias for 'sigQUIT'.keyboardTermination ::Signal keyboardTermination :: CInt
keyboardTermination =CInt
sigQUIT -- | Alias for 'sigSEGV'.segmentationViolation ::Signal segmentationViolation :: CInt
segmentationViolation =CInt
sigSEGV -- | Alias for 'sigSTOP'.softwareStop ::Signal softwareStop :: CInt
softwareStop =CInt
sigSTOP -- | Alias for 'sigTERM'.softwareTermination ::Signal softwareTermination :: CInt
softwareTermination =CInt
sigTERM -- | Alias for 'sigTSTP'.keyboardStop ::Signal keyboardStop :: CInt
keyboardStop =CInt
sigTSTP -- | Alias for 'sigTTIN'.backgroundRead ::Signal backgroundRead :: CInt
backgroundRead =CInt
sigTTIN -- | Alias for 'sigTTOU'.backgroundWrite ::Signal backgroundWrite :: CInt
backgroundWrite =CInt
sigTTOU -- | Alias for 'sigUSR1'.userDefinedSignal1 ::Signal userDefinedSignal1 :: CInt
userDefinedSignal1 =CInt
sigUSR1 -- | Alias for 'sigUSR2'.userDefinedSignal2 ::Signal userDefinedSignal2 :: CInt
userDefinedSignal2 =CInt
sigUSR2 {-# LINE 334 "System/Posix/Signals.hsc" #-}-- | Alias for 'sigPOLL'.pollableEvent ::Signal pollableEvent :: CInt
pollableEvent =CInt
sigPOLL {-# LINE 338 "System/Posix/Signals.hsc" #-}-- | Alias for 'sigPROF'.profilingTimerExpired ::Signal profilingTimerExpired :: CInt
profilingTimerExpired =CInt
sigPROF -- | Alias for 'sigSYS'.badSystemCall ::Signal badSystemCall :: CInt
badSystemCall =CInt
sigSYS -- | Alias for 'sigTRAP'.breakpointTrap ::Signal breakpointTrap :: CInt
breakpointTrap =CInt
sigTRAP -- | Alias for 'sigURG'.urgentDataAvailable ::Signal urgentDataAvailable :: CInt
urgentDataAvailable =CInt
sigURG -- | Alias for 'sigVTALRM'.virtualTimerExpired ::Signal virtualTimerExpired :: CInt
virtualTimerExpired =CInt
sigVTALRM -- | Alias for 'sigXCPU'.cpuTimeLimitExceeded ::Signal cpuTimeLimitExceeded :: CInt
cpuTimeLimitExceeded =CInt
sigXCPU -- | Alias for 'sigXFSZ'.fileSizeLimitExceeded ::Signal fileSizeLimitExceeded :: CInt
fileSizeLimitExceeded =CInt
sigXFSZ -- ------------------------------------------------------------------------------- Signal-related functions-- | @signalProcess int pid@ calls @kill@ to signal process @pid@-- with interrupt signal @int@.signalProcess ::Signal ->ProcessID->IO(){-# LINE 380 "System/Posix/Signals.hsc" #-}signalProcess :: CInt -> ProcessID -> IO ()
signalProcess CInt
sig ProcessID
pid =String -> IO CInt -> IO ()
forall a. (Eq a, Num a) => String -> IO a -> IO ()
throwErrnoIfMinus1_String
"signalProcess"(ProcessID -> CInt -> IO CInt
c_kill ProcessID
pid CInt
sig )foreignimportccallunsafe"kill"c_kill ::CPid->CInt->IOCInt{-# LINE 388 "System/Posix/Signals.hsc" #-}-- | @signalProcessGroup int pgid@ calls @kill@ to signal-- all processes in group @pgid@ with interrupt signal @int@.signalProcessGroup ::Signal ->ProcessGroupID->IO(){-# LINE 400 "System/Posix/Signals.hsc" #-}signalProcessGroup :: CInt -> ProcessID -> IO ()
signalProcessGroup CInt
sig ProcessID
pgid =String -> IO CInt -> IO ()
forall a. (Eq a, Num a) => String -> IO a -> IO ()
throwErrnoIfMinus1_String
"signalProcessGroup"(ProcessID -> CInt -> IO CInt
c_killpg ProcessID
pgid CInt
sig )foreignimportccallunsafe"killpg"c_killpg ::CPid->CInt->IOCInt{-# LINE 408 "System/Posix/Signals.hsc" #-}-- | @raiseSignal int@ calls @kill@ to signal the current process-- with interrupt signal @int@.raiseSignal ::Signal ->IO(){-# LINE 419 "System/Posix/Signals.hsc" #-}raiseSignal :: CInt -> IO ()
raiseSignal CInt
sig =String -> IO CInt -> IO ()
forall a. (Eq a, Num a) => String -> IO a -> IO ()
throwErrnoIfMinus1_String
"raiseSignal"(CInt -> IO CInt
c_raise CInt
sig )-- See also note in GHC's rts/RtsUtils.c-- This is somewhat fragile because we need to keep the-- `#if`-conditional in sync with GHC's runtime.{-# LINE 429 "System/Posix/Signals.hsc" #-}foreignimportccallunsafe"raise"c_raise ::CInt->IOCInt{-# LINE 432 "System/Posix/Signals.hsc" #-}{-# LINE 434 "System/Posix/Signals.hsc" #-}typeSignal =CInt-- | The actions to perform when a signal is received.dataHandler =Default -- ^ Sets the disposition of the signal to @SIG_DFL@, which-- means we want the default action associated with the-- signal. For example, the default action for @SIGTERM@ (and-- various other signals) is to terminate the process.|Ignore -- ^ Set the disposition of the signal to @SIG_IGN@, which-- means we want to /ignore/ the signal. Ignored signals will-- not be delivered to the process, and if also /blocked/ will-- not be added to the pending set for later delivery (if/when-- unblocked). Some signals (e.g. @SIGSTOP@ and @SIGKILL@)-- cannot be caught or ignored.-- not yet: | Hold|Catch (IO())-- ^ signal handler is not reset|CatchOnce (IO())-- ^ signal handler is automatically reset (via @SA_RESETHAND@)|CatchInfo (SignalInfo ->IO())-- ^ @since 2.7.0.0|CatchInfoOnce (SignalInfo ->IO())-- ^ @since 2.7.0.0deriving(Typeable)-- | Information about a received signal (derived from @siginfo_t@).---- @since 2.7.0.0dataSignalInfo =SignalInfo {SignalInfo -> CInt
siginfoSignal ::Signal ,SignalInfo -> Errno
siginfoError ::Errno,SignalInfo -> SignalSpecificInfo
siginfoSpecific ::SignalSpecificInfo }-- | Information specific to a particular type of signal-- (derived from @siginfo_t@).---- @since 2.7.0.0dataSignalSpecificInfo =NoSignalSpecificInfo |SigChldInfo {SignalSpecificInfo -> ProcessID
siginfoPid ::ProcessID,SignalSpecificInfo -> UserID
siginfoUid ::UserID,SignalSpecificInfo -> ProcessStatus
siginfoStatus ::ProcessStatus }-- | @installHandler int handler iset@ calls @sigaction@ to install an-- interrupt handler for signal @int@. If @handler@ is @Default@,-- @SIG_DFL@ is installed; if @handler@ is @Ignore@, @SIG_IGN@ is-- installed; if @handler@ is @Catch action@, a handler is installed-- which will invoke @action@ in a new thread when (or shortly after) the-- signal is received.-- If @iset@ is @Just s@, then the @sa_mask@ of the @sigaction@ structure-- is set to @s@; otherwise it is cleared. The previously installed-- signal handler for @int@ is returnedinstallHandler ::Signal ->Handler ->MaybeSignalSet -- ^ other signals to block->IOHandler -- ^ old handler{-# LINE 506 "System/Posix/Signals.hsc" #-}installHandler :: CInt -> Handler -> Maybe SignalSet -> IO Handler
installHandler CInt
sig Handler
handler Maybe SignalSet
_maybe_mask =doIO ()
ensureIOManagerIsRunning-- for the threaded RTS-- if we're setting the action to DFL or IGN, we should do that *first*-- if we're setting a handler,-- if the previous action was handle, then setHandler is ok-- if the previous action was IGN/DFL, then setHandler followed by sig_install(CInt
old_action ,Maybe (HandlerFun, Dynamic)
old_handler )<-caseHandler
handler ofHandler
Ignore ->doCInt
old_action <-CInt -> CInt -> Ptr CSigset -> IO CInt
stg_sig_install CInt
sig STG_SIG_IGNnullPtrMaybe (HandlerFun, Dynamic)
old_handler <-CInt
-> Maybe (HandlerFun, Dynamic) -> IO (Maybe (HandlerFun, Dynamic))
setHandlerCInt
sig Maybe (HandlerFun, Dynamic)
forall a. Maybe a
Nothing(CInt, Maybe (HandlerFun, Dynamic))
-> IO (CInt, Maybe (HandlerFun, Dynamic))
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(CInt
old_action ,Maybe (HandlerFun, Dynamic)
old_handler )Handler
Default ->doCInt
old_action <-CInt -> CInt -> Ptr CSigset -> IO CInt
stg_sig_install CInt
sig STG_SIG_DFLnullPtrMaybe (HandlerFun, Dynamic)
old_handler <-CInt
-> Maybe (HandlerFun, Dynamic) -> IO (Maybe (HandlerFun, Dynamic))
setHandlerCInt
sig Maybe (HandlerFun, Dynamic)
forall a. Maybe a
Nothing(CInt, Maybe (HandlerFun, Dynamic))
-> IO (CInt, Maybe (HandlerFun, Dynamic))
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(CInt
old_action ,Maybe (HandlerFun, Dynamic)
old_handler )Handler
_some_kind_of_catch ->do-- I don't think it's possible to get CatchOnce right. If-- there's a signal in flight, then we might run the handler-- more than once.letdyn :: Dynamic
dyn =Handler -> Dynamic
forall a. Typeable a => a -> Dynamic
toDynHandler
handler Maybe (HandlerFun, Dynamic)
old_handler <-caseHandler
handler ofCatch IO ()
action ->CInt
-> Maybe (HandlerFun, Dynamic) -> IO (Maybe (HandlerFun, Dynamic))
setHandlerCInt
sig ((HandlerFun, Dynamic) -> Maybe (HandlerFun, Dynamic)
forall a. a -> Maybe a
Just(IO () -> HandlerFun
forall a b. a -> b -> a
constIO ()
action ,Dynamic
dyn ))CatchOnce IO ()
action ->CInt
-> Maybe (HandlerFun, Dynamic) -> IO (Maybe (HandlerFun, Dynamic))
setHandlerCInt
sig ((HandlerFun, Dynamic) -> Maybe (HandlerFun, Dynamic)
forall a. a -> Maybe a
Just(IO () -> HandlerFun
forall a b. a -> b -> a
constIO ()
action ,Dynamic
dyn ))CatchInfo SignalInfo -> IO ()
action ->CInt
-> Maybe (HandlerFun, Dynamic) -> IO (Maybe (HandlerFun, Dynamic))
setHandlerCInt
sig ((HandlerFun, Dynamic) -> Maybe (HandlerFun, Dynamic)
forall a. a -> Maybe a
Just((SignalInfo -> IO ()) -> HandlerFun
getinfo SignalInfo -> IO ()
action ,Dynamic
dyn ))CatchInfoOnce SignalInfo -> IO ()
action ->CInt
-> Maybe (HandlerFun, Dynamic) -> IO (Maybe (HandlerFun, Dynamic))
setHandlerCInt
sig ((HandlerFun, Dynamic) -> Maybe (HandlerFun, Dynamic)
forall a. a -> Maybe a
Just((SignalInfo -> IO ()) -> HandlerFun
getinfo SignalInfo -> IO ()
action ,Dynamic
dyn )){-# LINE 539 "System/Posix/Signals.hsc" #-}letaction :: CInt
action =caseHandler
handler ofCatch IO ()
_->STG_SIG_HANCatchOnce IO ()
_->STG_SIG_RSTCatchInfo SignalInfo -> IO ()
_->STG_SIG_HANCatchInfoOnce SignalInfo -> IO ()
_->STG_SIG_RST{-# LINE 548 "System/Posix/Signals.hsc" #-}CInt
old_action <-CInt -> CInt -> Ptr CSigset -> IO CInt
stg_sig_install CInt
sig CInt
action Ptr CSigset
forall a. Ptr a
nullPtr-- mask is pointless, so leave it NULL(CInt, Maybe (HandlerFun, Dynamic))
-> IO (CInt, Maybe (HandlerFun, Dynamic))
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(CInt
old_action ,Maybe (HandlerFun, Dynamic)
old_handler )case(Maybe (HandlerFun, Dynamic)
old_handler ,CInt
old_action )of(Maybe (HandlerFun, Dynamic)
_,STG_SIG_DFL)->return$Default(Maybe (HandlerFun, Dynamic)
_,STG_SIG_IGN)->return$Ignore(Maybe (HandlerFun, Dynamic)
Nothing,CInt
_)->Handler -> IO Handler
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(Handler -> IO Handler) -> Handler -> IO Handler
forall a b. (a -> b) -> a -> b
$Handler
Ignore (Just(HandlerFun
_,Dynamic
dyn ),CInt
_)|JustHandler
h <-Dynamic -> Maybe Handler
forall a. Typeable a => Dynamic -> Maybe a
fromDynamicDynamic
dyn ->Handler -> IO Handler
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
returnHandler
h |JustIO ()
io <-Dynamic -> Maybe (IO ())
forall a. Typeable a => Dynamic -> Maybe a
fromDynamicDynamic
dyn ->Handler -> IO Handler
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(IO () -> Handler
Catch IO ()
io )-- handlers put there by the base package have type IO ()|Bool
otherwise->Handler -> IO Handler
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
returnHandler
Default foreignimportccallunsafestg_sig_install ::CInt-- sig no.->CInt-- action code (STG_SIG_HAN etc.)->PtrCSigset-- (in, out) blocked->IOCInt-- (ret) old action codegetinfo ::(SignalInfo ->IO())->ForeignPtrWord8->IO()getinfo :: (SignalInfo -> IO ()) -> HandlerFun
getinfo SignalInfo -> IO ()
handler ForeignPtr Word8
fp_info =doSignalInfo
si <-ForeignPtr Word8 -> IO SignalInfo
unmarshalSigInfo ForeignPtr Word8
fp_info SignalInfo -> IO ()
handler SignalInfo
si unmarshalSigInfo ::ForeignPtrWord8->IOSignalInfo unmarshalSigInfo :: ForeignPtr Word8 -> IO SignalInfo
unmarshalSigInfo ForeignPtr Word8
fp =doForeignPtr Word8 -> (Ptr Word8 -> IO SignalInfo) -> IO SignalInfo
forall a b. ForeignPtr a -> (Ptr a -> IO b) -> IO b
withForeignPtrForeignPtr Word8
fp ((Ptr Word8 -> IO SignalInfo) -> IO SignalInfo)
-> (Ptr Word8 -> IO SignalInfo) -> IO SignalInfo
forall a b. (a -> b) -> a -> b
$\Ptr Word8
p ->doCInt
sig <-((\Ptr Word8
hsc_ptr ->Ptr Word8 -> Int -> IO CInt
forall b. Ptr b -> Int -> IO CInt
forall a b. Storable a => Ptr b -> Int -> IO a
peekByteOffPtr Word8
hsc_ptr Int
0))Ptr Word8
p {-# LINE 580 "System/Posix/Signals.hsc" #-}errno<-((\hsc_ptr->peekByteOffhsc_ptr4))p{-# LINE 581 "System/Posix/Signals.hsc" #-}extra<-casesigof_|sig==sigCHLD->dopid<-((\hsc_ptr->peekByteOffhsc_ptr16))p{-# LINE 584 "System/Posix/Signals.hsc" #-}uid<-((\hsc_ptr->peekByteOffhsc_ptr20))p{-# LINE 585 "System/Posix/Signals.hsc" #-}wstat<-((\hsc_ptr->peekByteOffhsc_ptr24))p{-# LINE 586 "System/Posix/Signals.hsc" #-}pstat<-decipherWaitStatuswstatreturnSigChldInfo{siginfoPid=pid,siginfoUid=uid,siginfoStatus=pstat}_|otherwise->returnNoSignalSpecificInfoSignalInfo -> IO SignalInfo
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
returnSignalInfo {siginfoSignal :: CInt
siginfoSignal =CInt
sig ,siginfoError :: Errno
siginfoError =CInt -> Errno
ErrnoCInt
errno ,siginfoSpecific :: SignalSpecificInfo
siginfoSpecific =SignalSpecificInfo
extra }{-# LINE 599 "System/Posix/Signals.hsc" #-}{-# LINE 608 "System/Posix/Signals.hsc" #-}-- ------------------------------------------------------------------------------- Alarms-- | @scheduleAlarm i@ calls @alarm@ to schedule a real time-- alarm at least @i@ seconds in the future.scheduleAlarm ::Int->IOIntscheduleAlarm :: Int -> IO Int
scheduleAlarm Int
secs =doCUInt
r <-CUInt -> IO CUInt
c_alarm (Int -> CUInt
forall a b. (Integral a, Num b) => a -> b
fromIntegralInt
secs )Int -> IO Int
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(CUInt -> Int
forall a b. (Integral a, Num b) => a -> b
fromIntegralCUInt
r )foreignimportccallunsafe"alarm"c_alarm ::CUInt->IOCUInt{-# LINE 623 "System/Posix/Signals.hsc" #-}-- ------------------------------------------------------------------------------- The NOCLDSTOP flag{-# LINE 638 "System/Posix/Signals.hsc" #-}foreignimportccall"&nocldstop"nocldstop ::PtrInt-- | Tells the system whether or not to set the @SA_NOCLDSTOP@ flag when-- installing new signal handlers.setStoppedChildFlag ::Bool->IOBoolsetStoppedChildFlag :: Bool -> IO Bool
setStoppedChildFlag Bool
b =doInt
rc <-Ptr Int -> IO Int
forall a. Storable a => Ptr a -> IO a
peekPtr Int
nocldstop Ptr Int -> Int -> IO ()
forall a. Storable a => Ptr a -> a -> IO ()
pokePtr Int
nocldstop (Int -> IO ()) -> Int -> IO ()
forall a b. (a -> b) -> a -> b
$Bool -> Int
forall a. Enum a => a -> Int
fromEnum(Bool -> Bool
notBool
b )Bool -> IO Bool
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(Int
rc Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
==(Int
0::Int))-- | Queries the current state of the stopped child flag.queryStoppedChildFlag ::IOBoolqueryStoppedChildFlag :: IO Bool
queryStoppedChildFlag =doInt
rc <-Ptr Int -> IO Int
forall a. Storable a => Ptr a -> IO a
peekPtr Int
nocldstop Bool -> IO Bool
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(Int
rc Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
==(Int
0::Int)){-# LINE 656 "System/Posix/Signals.hsc" #-}-- ------------------------------------------------------------------------------- Manipulating signal sets{-# LINE 661 "System/Posix/Signals.hsc" #-}newtypeSignalSet =SignalSet (ForeignPtrCSigset){-# LINE 669 "System/Posix/Signals.hsc" #-}{-# LINE 704 "System/Posix/Signals.hsc" #-}emptySignalSet ::SignalSet emptySignalSet :: SignalSet
emptySignalSet =IO SignalSet -> SignalSet
forall a. IO a -> a
unsafePerformIO(IO SignalSet -> SignalSet) -> IO SignalSet -> SignalSet
forall a b. (a -> b) -> a -> b
$doForeignPtr CSigset
fp <-Int -> IO (ForeignPtr CSigset)
forall a. Int -> IO (ForeignPtr a)
mallocForeignPtrBytesInt
sizeof_sigset_tString -> IO CInt -> IO ()
forall a. (Eq a, Num a) => String -> IO a -> IO ()
throwErrnoIfMinus1_String
"emptySignalSet"(ForeignPtr CSigset -> (Ptr CSigset -> IO CInt) -> IO CInt
forall a b. ForeignPtr a -> (Ptr a -> IO b) -> IO b
withForeignPtrForeignPtr CSigset
fp ((Ptr CSigset -> IO CInt) -> IO CInt)
-> (Ptr CSigset -> IO CInt) -> IO CInt
forall a b. (a -> b) -> a -> b
$Ptr CSigset -> IO CInt
c_sigemptyset)SignalSet -> IO SignalSet
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(ForeignPtr CSigset -> SignalSet
SignalSet ForeignPtr CSigset
fp )fullSignalSet ::SignalSet fullSignalSet :: SignalSet
fullSignalSet =IO SignalSet -> SignalSet
forall a. IO a -> a
unsafePerformIO(IO SignalSet -> SignalSet) -> IO SignalSet -> SignalSet
forall a b. (a -> b) -> a -> b
$doForeignPtr CSigset
fp <-Int -> IO (ForeignPtr CSigset)
forall a. Int -> IO (ForeignPtr a)
mallocForeignPtrBytesInt
sizeof_sigset_tString -> IO CInt -> IO ()
forall a. (Eq a, Num a) => String -> IO a -> IO ()
throwErrnoIfMinus1_String
"fullSignalSet"(ForeignPtr CSigset -> (Ptr CSigset -> IO CInt) -> IO CInt
forall a b. ForeignPtr a -> (Ptr a -> IO b) -> IO b
withForeignPtrForeignPtr CSigset
fp ((Ptr CSigset -> IO CInt) -> IO CInt)
-> (Ptr CSigset -> IO CInt) -> IO CInt
forall a b. (a -> b) -> a -> b
$Ptr CSigset -> IO CInt
c_sigfillset )SignalSet -> IO SignalSet
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(ForeignPtr CSigset -> SignalSet
SignalSet ForeignPtr CSigset
fp )-- | A set of signals reserved for use by the implementation. In GHC, this will normally-- include either `sigVTALRM` or `sigALRM`.reservedSignals ::SignalSet reservedSignals :: SignalSet
reservedSignals =CInt -> SignalSet -> SignalSet
addSignal CInt
rtsTimerSignal SignalSet
emptySignalSet foreignimportccallrtsTimerSignal ::CIntinfixr`addSignal` ,`deleteSignal` addSignal ::Signal ->SignalSet ->SignalSet addSignal :: CInt -> SignalSet -> SignalSet
addSignal CInt
sig (SignalSet ForeignPtr CSigset
fp1 )=IO SignalSet -> SignalSet
forall a. IO a -> a
unsafePerformIO(IO SignalSet -> SignalSet) -> IO SignalSet -> SignalSet
forall a b. (a -> b) -> a -> b
$doForeignPtr CSigset
fp2 <-Int -> IO (ForeignPtr CSigset)
forall a. Int -> IO (ForeignPtr a)
mallocForeignPtrBytesInt
sizeof_sigset_tForeignPtr CSigset -> (Ptr CSigset -> IO ()) -> IO ()
forall a b. ForeignPtr a -> (Ptr a -> IO b) -> IO b
withForeignPtrForeignPtr CSigset
fp1 ((Ptr CSigset -> IO ()) -> IO ())
-> (Ptr CSigset -> IO ()) -> IO ()
forall a b. (a -> b) -> a -> b
$\Ptr CSigset
p1 ->ForeignPtr CSigset -> (Ptr CSigset -> IO ()) -> IO ()
forall a b. ForeignPtr a -> (Ptr a -> IO b) -> IO b
withForeignPtrForeignPtr CSigset
fp2 ((Ptr CSigset -> IO ()) -> IO ())
-> (Ptr CSigset -> IO ()) -> IO ()
forall a b. (a -> b) -> a -> b
$\Ptr CSigset
p2 ->doPtr CSigset -> Ptr CSigset -> Int -> IO ()
forall a. Ptr a -> Ptr a -> Int -> IO ()
copyBytesPtr CSigset
p2 Ptr CSigset
p1 Int
sizeof_sigset_tString -> IO CInt -> IO ()
forall a. (Eq a, Num a) => String -> IO a -> IO ()
throwErrnoIfMinus1_String
"addSignal"(Ptr CSigset -> CInt -> IO CInt
c_sigaddsetPtr CSigset
p2 CInt
sig )SignalSet -> IO SignalSet
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(ForeignPtr CSigset -> SignalSet
SignalSet ForeignPtr CSigset
fp2 )deleteSignal ::Signal ->SignalSet ->SignalSet deleteSignal :: CInt -> SignalSet -> SignalSet
deleteSignal CInt
sig (SignalSet ForeignPtr CSigset
fp1 )=IO SignalSet -> SignalSet
forall a. IO a -> a
unsafePerformIO(IO SignalSet -> SignalSet) -> IO SignalSet -> SignalSet
forall a b. (a -> b) -> a -> b
$doForeignPtr CSigset
fp2 <-Int -> IO (ForeignPtr CSigset)
forall a. Int -> IO (ForeignPtr a)
mallocForeignPtrBytesInt
sizeof_sigset_tForeignPtr CSigset -> (Ptr CSigset -> IO ()) -> IO ()
forall a b. ForeignPtr a -> (Ptr a -> IO b) -> IO b
withForeignPtrForeignPtr CSigset
fp1 ((Ptr CSigset -> IO ()) -> IO ())
-> (Ptr CSigset -> IO ()) -> IO ()
forall a b. (a -> b) -> a -> b
$\Ptr CSigset
p1 ->ForeignPtr CSigset -> (Ptr CSigset -> IO ()) -> IO ()
forall a b. ForeignPtr a -> (Ptr a -> IO b) -> IO b
withForeignPtrForeignPtr CSigset
fp2 ((Ptr CSigset -> IO ()) -> IO ())
-> (Ptr CSigset -> IO ()) -> IO ()
forall a b. (a -> b) -> a -> b
$\Ptr CSigset
p2 ->doPtr CSigset -> Ptr CSigset -> Int -> IO ()
forall a. Ptr a -> Ptr a -> Int -> IO ()
copyBytesPtr CSigset
p2 Ptr CSigset
p1 Int
sizeof_sigset_tString -> IO CInt -> IO ()
forall a. (Eq a, Num a) => String -> IO a -> IO ()
throwErrnoIfMinus1_String
"deleteSignal"(Ptr CSigset -> CInt -> IO CInt
c_sigdelset Ptr CSigset
p2 CInt
sig )SignalSet -> IO SignalSet
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(ForeignPtr CSigset -> SignalSet
SignalSet ForeignPtr CSigset
fp2 )inSignalSet ::Signal ->SignalSet ->BoolinSignalSet :: CInt -> SignalSet -> Bool
inSignalSet CInt
sig (SignalSet ForeignPtr CSigset
fp )=IO Bool -> Bool
forall a. IO a -> a
unsafePerformIO(IO Bool -> Bool) -> IO Bool -> Bool
forall a b. (a -> b) -> a -> b
$ForeignPtr CSigset -> (Ptr CSigset -> IO Bool) -> IO Bool
forall a b. ForeignPtr a -> (Ptr a -> IO b) -> IO b
withForeignPtrForeignPtr CSigset
fp ((Ptr CSigset -> IO Bool) -> IO Bool)
-> (Ptr CSigset -> IO Bool) -> IO Bool
forall a b. (a -> b) -> a -> b
$\Ptr CSigset
p ->doCInt
r <-String -> IO CInt -> IO CInt
forall a. (Eq a, Num a) => String -> IO a -> IO a
throwErrnoIfMinus1String
"inSignalSet"(Ptr CSigset -> CInt -> IO CInt
c_sigismember Ptr CSigset
p CInt
sig )Bool -> IO Bool
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(CInt
r CInt -> CInt -> Bool
forall a. Eq a => a -> a -> Bool
/=CInt
0){-# LINE 750 "System/Posix/Signals.hsc" #-}{-# LINE 774 "System/Posix/Signals.hsc" #-}-- | @getSignalMask@ calls @sigprocmask@ to determine the-- set of interrupts which are currently being blocked.getSignalMask ::IOSignalSet getSignalMask :: IO SignalSet
getSignalMask =doForeignPtr CSigset
fp <-Int -> IO (ForeignPtr CSigset)
forall a. Int -> IO (ForeignPtr a)
mallocForeignPtrBytesInt
sizeof_sigset_tForeignPtr CSigset -> (Ptr CSigset -> IO ()) -> IO ()
forall a b. ForeignPtr a -> (Ptr a -> IO b) -> IO b
withForeignPtrForeignPtr CSigset
fp ((Ptr CSigset -> IO ()) -> IO ())
-> (Ptr CSigset -> IO ()) -> IO ()
forall a b. (a -> b) -> a -> b
$\Ptr CSigset
p ->String -> IO CInt -> IO ()
forall a. (Eq a, Num a) => String -> IO a -> IO ()
throwErrnoIfMinus1_String
"getSignalMask"(CInt -> Ptr CSigset -> Ptr CSigset -> IO CInt
c_sigprocmaskCInt
0Ptr CSigset
forall a. Ptr a
nullPtrPtr CSigset
p )SignalSet -> IO SignalSet
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(ForeignPtr CSigset -> SignalSet
SignalSet ForeignPtr CSigset
fp )sigProcMask ::String->CInt->SignalSet ->IO()sigProcMask :: String -> CInt -> SignalSet -> IO ()
sigProcMask String
fn CInt
how (SignalSet ForeignPtr CSigset
set )=ForeignPtr CSigset -> (Ptr CSigset -> IO ()) -> IO ()
forall a b. ForeignPtr a -> (Ptr a -> IO b) -> IO b
withForeignPtrForeignPtr CSigset
set ((Ptr CSigset -> IO ()) -> IO ())
-> (Ptr CSigset -> IO ()) -> IO ()
forall a b. (a -> b) -> a -> b
$\Ptr CSigset
p_set ->String -> IO CInt -> IO ()
forall a. (Eq a, Num a) => String -> IO a -> IO ()
throwErrnoIfMinus1_String
fn (CInt -> Ptr CSigset -> Ptr CSigset -> IO CInt
c_sigprocmaskCInt
how Ptr CSigset
p_set Ptr CSigset
forall a. Ptr a
nullPtr)-- | @setSignalMask mask@ calls @sigprocmask@ with-- @SIG_SETMASK@ to block all interrupts in @mask@.setSignalMask ::SignalSet ->IO()setSignalMask :: SignalSet -> IO ()
setSignalMask SignalSet
set =String -> CInt -> SignalSet -> IO ()
sigProcMask String
"setSignalMask"(CONST_SIG_SETMASK::CInt)set-- | @blockSignals mask@ calls @sigprocmask@ with-- @SIG_BLOCK@ to add all interrupts in @mask@ to the-- set of blocked interrupts.blockSignals ::SignalSet ->IO()blockSignals :: SignalSet -> IO ()
blockSignals SignalSet
set =String -> CInt -> SignalSet -> IO ()
sigProcMask String
"blockSignals"(CONST_SIG_BLOCK::CInt)set-- | @unblockSignals mask@ calls @sigprocmask@ with-- @SIG_UNBLOCK@ to remove all interrupts in @mask@ from the-- set of blocked interrupts.unblockSignals ::SignalSet ->IO()unblockSignals :: SignalSet -> IO ()
unblockSignals SignalSet
set =String -> CInt -> SignalSet -> IO ()
sigProcMask String
"unblockSignals"(CONST_SIG_UNBLOCK::CInt)set{-# LINE 807 "System/Posix/Signals.hsc" #-}{-# LINE 821 "System/Posix/Signals.hsc" #-}-- | @getPendingSignals@ calls @sigpending@ to obtain-- the set of interrupts which have been received but are currently blocked.getPendingSignals ::IOSignalSet getPendingSignals :: IO SignalSet
getPendingSignals =doForeignPtr CSigset
fp <-Int -> IO (ForeignPtr CSigset)
forall a. Int -> IO (ForeignPtr a)
mallocForeignPtrBytesInt
sizeof_sigset_tForeignPtr CSigset -> (Ptr CSigset -> IO ()) -> IO ()
forall a b. ForeignPtr a -> (Ptr a -> IO b) -> IO b
withForeignPtrForeignPtr CSigset
fp ((Ptr CSigset -> IO ()) -> IO ())
-> (Ptr CSigset -> IO ()) -> IO ()
forall a b. (a -> b) -> a -> b
$\Ptr CSigset
p ->String -> IO CInt -> IO ()
forall a. (Eq a, Num a) => String -> IO a -> IO ()
throwErrnoIfMinus1_String
"getPendingSignals"(Ptr CSigset -> IO CInt
c_sigpending Ptr CSigset
p )SignalSet -> IO SignalSet
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return(ForeignPtr CSigset -> SignalSet
SignalSet ForeignPtr CSigset
fp )-- | @awaitSignal iset@ suspends execution until an interrupt is received.-- If @iset@ is @Just s@, @awaitSignal@ calls @sigsuspend@, installing-- @s@ as the new signal mask before suspending execution; otherwise, it-- calls @sigsuspend@ with current signal mask. Note that RTS-- scheduler signal (either 'virtualTimerExpired' or 'realTimeAlarm')-- could cause premature termination of this call. It might be necessary to block that-- signal before invocation of @awaitSignal@ with 'blockSignals' 'reservedSignals'.---- @awaitSignal@ returns when signal was received and processed by a-- signal handler, or if the signal could not be caught. If you have-- installed any signal handlers with @installHandler@, it may be wise-- to call @yield@ directly after @awaitSignal@ to ensure that the-- signal handler runs as promptly as possible.awaitSignal ::MaybeSignalSet ->IO()awaitSignal :: Maybe SignalSet -> IO ()
awaitSignal Maybe SignalSet
maybe_sigset =doForeignPtr CSigset
fp <-caseMaybe SignalSet
maybe_sigset ofMaybe SignalSet
Nothing->doSignalSet ForeignPtr CSigset
fp <-IO SignalSet
getSignalMask ;ForeignPtr CSigset -> IO (ForeignPtr CSigset)
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
returnForeignPtr CSigset
fp Just(SignalSet ForeignPtr CSigset
fp )->ForeignPtr CSigset -> IO (ForeignPtr CSigset)
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
returnForeignPtr CSigset
fp ForeignPtr CSigset -> (Ptr CSigset -> IO ()) -> IO ()
forall a b. ForeignPtr a -> (Ptr a -> IO b) -> IO b
withForeignPtrForeignPtr CSigset
fp ((Ptr CSigset -> IO ()) -> IO ())
-> (Ptr CSigset -> IO ()) -> IO ()
forall a b. (a -> b) -> a -> b
$\Ptr CSigset
p ->doCInt
_<-Ptr CSigset -> IO CInt
c_sigsuspend Ptr CSigset
p () -> IO ()
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return()-- ignore the return value; according to the docs it can only ever be-- (-1) with errno set to EINTR.-- XXX My manpage says it can also return EFAULT. And why is ignoring-- EINTR the right thing to do?{-# LINE 858 "System/Posix/Signals.hsc" #-}{-# LINE 860 "System/Posix/Signals.hsc" #-}foreignimportccallunsafe"sigsuspend"c_sigsuspend ::PtrCSigset->IOCIntforeignimportcapiunsafe"signal.h sigdelset"c_sigdelset ::PtrCSigset->CInt->IOCIntforeignimportcapiunsafe"signal.h sigfillset"c_sigfillset ::PtrCSigset->IOCIntforeignimportcapiunsafe"signal.h sigismember"c_sigismember ::PtrCSigset->CInt->IOCIntforeignimportccallunsafe"sigpending"c_sigpending ::PtrCSigset->IOCInt{-# LINE 877 "System/Posix/Signals.hsc" #-}

AltStyle によって変換されたページ (->オリジナル) /