Distribution.Compat.Stack

Cabal-2.4.0.1: A framework for packaging Haskell software

Safe Haskell | Safe
Language | Haskell2010

Distribution.Compat.Stack

Synopsis

- type WithCallStack a = HasCallStack => a
- data CallStack
- annotateCallStackIO :: WithCallStack (IO a -> IO a)
- withFrozenCallStack :: HasCallStack => (HasCallStack -> a) -> a
- withLexicalCallStack :: (a -> WithCallStack (IO b)) -> WithCallStack (a -> IO b)
- callStack :: HasCallStack -> CallStack
- prettyCallStack :: CallStack -> String
- parentSrcLocPrefix :: WithCallStack String

# Documentation

type WithCallStack a = HasCallStack => a #

data CallStack Source #

`CallStack`s are a lightweight method of obtaining a partial call-stack at any point in the program.

A function can request its call-site with the `HasCallStack` constraint. For example, we can define

    putStrLnWithCallStack :: HasCallStack => String -> IO ()

as a variant of `putStrLn` that will get its call-site and print it, along with the string given as argument. We can access the call-stack inside `putStrLnWithCallStack` with `callStack`.

    putStrLnWithCallStack :: HasCallStack => String -> IO ()
    putStrLnWithCallStack msg = do
      putStrLn msg
      putStrLn (prettyCallStack callStack)

Thus, if we call `putStrLnWithCallStack` we will get a formatted call-stack alongside our string.

    >>> putStrLnWithCallStack "hello"
    hello
    CallStack (from HasCallStack):
      putStrLnWithCallStack, called at <interactive>:2:1 in interactive:Ghci1

GHC solves `HasCallStack` constraints in three steps:

1. If there is a `CallStack` in scope -- i.e. the enclosing function has a `HasCallStack` constraint -- GHC will append the new call-site to the existing `CallStack`.
2. If there is no `CallStack` in scope -- e.g. in the GHCi session above -- and the enclosing definition does not have an explicit type signature, GHC will infer a `HasCallStack` constraint for the enclosing definition (subject to the monomorphism restriction).
3. If there is no `CallStack` in scope and the enclosing definition has an explicit type signature, GHC will solve the `HasCallStack` constraint for the singleton `CallStack` containing just the current call-site.

`CallStack`s do not interact with the RTS and do not require compilation with `-prof`. On the other hand, as they are built up explicitly via the `HasCallStack` constraints, they will generally not contain as much information as the simulated call-stacks maintained by the RTS.

A `CallStack` is a `[(String, SrcLoc)]`. The `String` is the name of function that was called, the `SrcLoc` is the call-site. The list is ordered with the most recently called function at the head.

NOTE: The intrepid user may notice that `HasCallStack` is just an alias for an implicit parameter `?callStack :: CallStack`. This is an implementation detail and should not be considered part of the `CallStack` API, we may decide to change the implementation in the future.

Since: base-4.8.1.0

Instances

IsList CallStack | Be aware that 'fromList . toList = id' only for unfrozen `CallStack`s, since `toList` removes frozenness information. Since: base-4.9.0.0
Instance details Defined in GHC.Exts Associated Types type Item CallStack :: Type Source # Methods fromList :: [Item CallStack] -> CallStack Source # fromListN :: Int -> [Item CallStack] -> CallStack Source # toList :: CallStack -> [Item CallStack] Source #
Show CallStack | Since: base-4.9.0.0
Instance details Defined in GHC.Show Methods showsPrec :: Int -> CallStack -> ShowS Source # show :: CallStack -> String Source # showList :: [CallStack] -> ShowS Source #
NFData CallStack | Since: deepseq-1.4.2.0
Instance details Defined in Control.DeepSeq Methods rnf :: CallStack -> () Source #
type Item CallStack |
Instance details Defined in GHC.Exts type Item CallStack = (String, SrcLoc)

annotateCallStackIO :: WithCallStack (IO a -> IO a) #

This function is for when you *really* want to add a call stack to raised IO, but you don't have a `Verbosity` so you can't use `annotateIO`. If you have a `Verbosity`, please use that function instead.

withFrozenCallStack :: HasCallStack => (HasCallStack -> a) -> a Source #

Perform some computation without adding new entries to the `CallStack`.

Since: base-4.9.0.0

withLexicalCallStack :: (a -> WithCallStack (IO b)) -> WithCallStack (a -> IO b) #

callStack :: HasCallStack -> CallStack Source #

Return the current `CallStack`.

Does *not* include the call-site of `callStack`.

Since: base-4.9.0.0

prettyCallStack :: CallStack -> String Source #

Pretty print a `CallStack`.

Since: base-4.9.0.0

parentSrcLocPrefix :: WithCallStack String #

Give the *parent* of the person who invoked this; so it's most suitable for being called from a utility function. You probably want to call this using `withFrozenCallStack`; otherwise it's not very useful. We didn't implement this for base-4.8.1 because we cannot rely on freezing to have taken place.