diff --git a/ihaskell.cabal b/ihaskell.cabal
--- a/ihaskell.cabal
+++ b/ihaskell.cabal
@@ -7,13 +7,13 @@
 -- PVP summary:      +--+------- breaking API changes
 --                   |  | +----- non-breaking API additions
 --                   |  | | +--- code changes with no API change
-version:             0.10.2.2
+version:             0.10.3.0
 
 -- A short (one-line) description of the package.
-synopsis:            A Haskell backend kernel for the IPython project.
+synopsis:            A Haskell backend kernel for the Jupyter project.
 
 -- A longer description of the package.
-description:         IHaskell is a Haskell backend kernel for the IPython project. This allows using Haskell via
+description:         IHaskell is a Haskell backend kernel for the Jupyter project. This allows using Haskell via
                      a console or notebook interface. Additional packages may be installed to provide richer data visualizations.
 
 -- URL for the project homepage or repository.
diff --git a/main/Main.hs b/main/Main.hs
--- a/main/Main.hs
+++ b/main/Main.hs
@@ -309,7 +309,10 @@
   -- Run code and publish to the frontend as we go.
   let widgetMessageHandler = widgetHandler send replyHeader
       publish = publishResult send replyHeader displayed updateNeeded pOut (usePager state)
-  updatedState <- evaluate state (T.unpack code) publish widgetMessageHandler
+  (updatedState, errorOccurred) <- evaluate state (T.unpack code) publish widgetMessageHandler
+  let executeReplyStatus = case errorOccurred of
+        Success -> Ok
+        Failure -> Err
 
   -- Take pager output if we're using the pager.
   pager <- if usePager state
@@ -320,7 +323,7 @@
                      { header = replyHeader
                      , pagerOutput = pager
                      , executionCounter = execCount
-                     , status = Ok
+                     , status = executeReplyStatus
                      })
 
 -- Check for a trailing empty line. If it doesn't exist, we assume the code is incomplete,
diff --git a/src/IHaskell/Display.hs b/src/IHaskell/Display.hs
--- a/src/IHaskell/Display.hs
+++ b/src/IHaskell/Display.hs
@@ -48,9 +48,6 @@
     encode64,
     base64,
 
-    -- ** Utilities
-    switchToTmpDir,
-
     -- * Internal only use
     displayFromChanEncoded,
     serializeDisplay,
@@ -64,10 +61,8 @@
 
 import           Data.Binary as Binary
 import qualified Data.ByteString.Base64 as Base64
-import           System.Directory (getTemporaryDirectory, setCurrentDirectory)
 
 import           Control.Concurrent.STM (atomically)
-import           Control.Exception (try)
 import           Control.Concurrent.STM.TChan
 import           System.IO.Unsafe (unsafePerformIO)
 
@@ -184,12 +179,3 @@
 -- execution call ends.
 printDisplay :: IHaskellDisplay a => a -> IO ()
 printDisplay disp = display disp >>= atomically . writeTChan displayChan
-
--- | Convenience function for client libraries. Switch to a temporary directory so that any files we
--- create aren't visible. On Unix, this is usually /tmp.
-switchToTmpDir :: IO ()
-switchToTmpDir = void (try switchDir :: IO (Either SomeException ()))
-  where
-    switchDir =
-      getTemporaryDirectory >>=
-      setCurrentDirectory
diff --git a/src/IHaskell/Eval/Evaluate.hs b/src/IHaskell/Eval/Evaluate.hs
--- a/src/IHaskell/Eval/Evaluate.hs
+++ b/src/IHaskell/Eval/Evaluate.hs
@@ -383,7 +383,7 @@
          -> String                       -- ^ Haskell code or other interpreter commands.
          -> Publisher                    -- ^ Function used to publish data outputs.
          -> (KernelState -> [WidgetMsg] -> IO KernelState) -- ^ Function to handle widget messages
-         -> Interpreter KernelState
+         -> Interpreter (KernelState, ErrorOccurred)
 evaluate kernelState code output widgetHandler = do
   cmds <- parseString (cleanString code)
   let execCount = getExecutionCounter kernelState
@@ -393,7 +393,7 @@
       justError _ = Nothing
       errs = mapMaybe (justError . unloc) cmds
 
-  updated <- case errs of
+  (updated, errorOccurred) <- case errs of
                -- Only run things if there are no parse errors.
                [] -> do
 
@@ -412,16 +412,16 @@
                    liftIO $ output
                      (FinalResult (evalResult out) [] [])
                      (evalStatus out)
-                 return kernelState
+                 return (kernelState, Failure)
 
-  return updated { getExecutionCounter = execCount + 1 }
+  return (updated { getExecutionCounter = execCount + 1 }, errorOccurred)
 
   where
     noResults (Display res) = null res
     noResults (ManyDisplay res) = all noResults res
 
-    runUntilFailure :: KernelState -> [CodeBlock] -> Interpreter KernelState
-    runUntilFailure state [] = return state
+    runUntilFailure :: KernelState -> [CodeBlock] -> Interpreter (KernelState, ErrorOccurred)
+    runUntilFailure state [] = return (state, Success)
     runUntilFailure state (cmd:rest) = do
       evalOut <- evalCommand output cmd state
 
@@ -458,7 +458,7 @@
 
       case evalStatus evalOut of
         Success -> runUntilFailure newState rest
-        Failure -> return newState
+        Failure -> return (newState, Failure)
 
     storeItCommand execCount = Statement $ printf "let it%d = it" execCount
 
diff --git a/src/IHaskell/Eval/Util.hs b/src/IHaskell/Eval/Util.hs
--- a/src/IHaskell/Eval/Util.hs
+++ b/src/IHaskell/Eval/Util.hs
@@ -9,6 +9,7 @@
     setExtension,
     ExtFlag(..),
     setFlags,
+    setWayDynFlag,
 
     -- * Code Evaluation
     evalImport,
@@ -42,6 +43,7 @@
 import           GHC.Driver.Ppr
 import           GHC.Driver.Session
 import           GHC.Driver.Env.Types
+import           GHC.Platform.Ways
 import           GHC.Runtime.Context
 import           GHC.Types.Name (pprInfixName)
 import           GHC.Types.Name.Set
@@ -58,6 +60,7 @@
 import           GHC.Driver.Monad (modifySession)
 import           GHC.Driver.Session
 import           GHC.Driver.Types
+import           GHC.Driver.Ways
 import           GHC.Types.Name (pprInfixName)
 import           GHC.Types.Name.Set
 import qualified GHC.Driver.Session as DynFlags
@@ -119,6 +122,33 @@
     -- Check if a FlagSpec matches "No<ExtensionName>". In that case, we disable the extension.
     flagMatchesNo ex fs = ex == "No" ++ flagSpecName fs
 
+#if MIN_VERSION_ghc(9,2,0)
+-- Taken from GHC
+addWay' :: Way
+        -> DynFlags
+        -> DynFlags
+addWay' w dflags0 =
+  let platform = targetPlatform dflags0
+      dflags1 = dflags0 { targetWays_ = addWay w (targetWays_ dflags0) }
+      dflags2 = foldr setGeneralFlag' dflags1 (wayGeneralFlags platform w)
+      dflags3 = foldr unSetGeneralFlag' dflags2 (wayUnsetGeneralFlags platform w)
+  in dflags3
+#endif
+
+-- | Consult the RTS to find if GHC has been built with dynamic linking and then turn on the
+-- dynamic way for GHC. Otherwise it does nothing.
+setWayDynFlag :: DynFlags
+              -> DynFlags
+setWayDynFlag =
+  if hostIsDynamic
+  then addWay' WayDyn
+  else id
+#if MIN_VERSION_ghc(9,0,0)
+#else
+  where
+    hostIsDynamic = dynamicGhc
+#endif
+
 -- | Pretty-print dynamic flags (taken from 'InteractiveUI' module of `ghc-bin`)
 pprDynFlags :: Bool       -- ^ Whether to include flags which are on by default
             -> DynFlags
@@ -265,7 +295,8 @@
 #else
       allWarns = map unLoc warnings ++
 #endif
-                 ["-package not supported yet" | packageFlags flags /= packageFlags flags0]
+        -- Stack appears to duplicate package flags, so we use `nub` to work around this
+        ["-package not supported yet" | nub (packageFlags flags) /= nub (packageFlags flags0)]
       warnErrs = map ("Warning: " ++) allWarns
   return $ noParseErrs ++ warnErrs
 
@@ -331,7 +362,7 @@
 #endif
   let flag = flip xopt_set
       unflag = flip xopt_unset
-      dflags = flag ExtendedDefaultRules . unflag MonomorphismRestriction $ originalFlags
+      dflags = flag ExtendedDefaultRules . unflag MonomorphismRestriction $ setWayDynFlag originalFlags
 #if MIN_VERSION_ghc(8,2,0)
       pkgFlags =
         case sandboxPackages of
diff --git a/src/tests/IHaskell/Test/Completion.hs b/src/tests/IHaskell/Test/Completion.hs
--- a/src/tests/IHaskell/Test/Completion.hs
+++ b/src/tests/IHaskell/Test/Completion.hs
@@ -30,6 +30,7 @@
 import           IHaskell.Eval.Evaluate (Interpreter, liftIO)
 import           IHaskell.Eval.Completion (complete, CompletionType(..), completionType,
                                            completionTarget)
+import           IHaskell.Eval.Util (setWayDynFlag)
 import           IHaskell.Test.Util (replace, shouldBeAmong, ghc)
 
 -- | @readCompletePrompt "xs*ys"@ return @(xs, i)@ where i is the location of
@@ -67,9 +68,9 @@
 initCompleter = do
   flags <- getSessionDynFlags
 #if MIN_VERSION_ghc(9,2,0)
-  _ <- setSessionDynFlags $ flags { backend = Interpreter, ghcLink = LinkInMemory }
+  _ <- setSessionDynFlags $ setWayDynFlag flags { backend = Interpreter, ghcLink = LinkInMemory }
 #else
-  _ <- setSessionDynFlags $ flags { hscTarget = HscInterpreted, ghcLink = LinkInMemory }
+  _ <- setSessionDynFlags $ setWayDynFlag flags { hscTarget = HscInterpreted, ghcLink = LinkInMemory }
 #endif
 
   -- Import modules.
