summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBen Gamari <ben@smart-cactus.org>2021-10-12 19:24:26 -0400
committerBen Gamari <ben@smart-cactus.org>2021-10-12 19:24:26 -0400
commita714de8dc47b16dee880ef84ad0c96e251d4d1a0 (patch)
tree7f38dbb40199c39efc3282365f7da6e89b5c040d
parent2d5a6417743c4db23a7f532fa6ba4fcb76b48085 (diff)
downloadhaskell-a714de8dc47b16dee880ef84ad0c96e251d4d1a0.tar.gz
hi
-rw-r--r--libraries/base/GHC/Conc/Sync.hs23
1 files changed, 22 insertions, 1 deletions
diff --git a/libraries/base/GHC/Conc/Sync.hs b/libraries/base/GHC/Conc/Sync.hs
index f5fea1ddb8..9e3553e082 100644
--- a/libraries/base/GHC/Conc/Sync.hs
+++ b/libraries/base/GHC/Conc/Sync.hs
@@ -4,6 +4,7 @@
{-# LANGUAGE RankNTypes #-}
{-# LANGUAGE UnboxedTuples #-}
{-# LANGUAGE UnliftedFFITypes #-}
+{-# LANGUAGE BangPatterns #-}
{-# LANGUAGE Unsafe #-}
{-# OPTIONS_HADDOCK not-home #-}
@@ -634,9 +635,10 @@ threadLabel :: ThreadId -> IO (Maybe String)
threadLabel (ThreadId t) = IO $ \s ->
case threadLabel# t s of
(# s', 1#, lbl #) ->
- let lbl' = Just (utf8DecodeCharByteArray# lbl 0)
+ let lbl' = Just (utf8DecodeByteArray lbl)
in (# s', lbl' #)
(# s', 0#, _ #) -> (# s', Nothing #)
+ _ -> error "threadLabel: impossible"
-- | Make a weak pointer to a 'ThreadId'. It can be important to do
-- this if you want to hold a reference to a 'ThreadId' while still
@@ -1029,3 +1031,22 @@ utf8DecodeCharByteArray# ba# off# =
#else
utf8DecodeChar# (\i# -> word8ToWord# (indexWord8Array# ba# (i# +# off#)))
#endif
+
+utf8DecodeByteArray :: ByteArray# -> [Char]
+utf8DecodeByteArray ba#
+ = unsafeDupablePerformIO $
+ let len# = sizeofByteArray# ba# in
+ utf8DecodeLazy# (return ()) (utf8DecodeCharByteArray# ba#) len#
+
+{-# INLINE utf8DecodeLazy# #-}
+utf8DecodeLazy# :: (IO ()) -> (Int# -> (# Char#, Int# #)) -> Int# -> IO [Char]
+utf8DecodeLazy# retain decodeChar# len#
+ = unpack 0#
+ where
+ unpack i#
+ | isTrue# (i# >=# len#) = retain >> return []
+ | otherwise =
+ case decodeChar# i# of
+ (# c#, nBytes# #) -> do
+ rest <- unsafeDupableInterleaveIO $ unpack (i# +# nBytes#)
+ return (C# c# : rest)