    {-# LANGUAGE CPP #-}
    {-# LANGUAGE DeriveDataTypeable #-}
    {-# LANGUAGE DeriveGeneric #-}

    -- | Compact representation of short 'Strings'
    --
    -- This module is designed to be import qualified
    --
    -- @
    -- import Distribution.Utils.ShortText (ShortText)
    -- import qualified Distribution.Utils.ShortText as ShortText
    -- @
    module Distribution.Utils.ShortText
      ( -- * 'ShortText' type
        ShortText
      , toShortText
      , fromShortText
      , unsafeFromUTF8BS

        -- * Operations
      , null
      , length

        -- * internal utilities
      , decodeStringUtf8
      , encodeStringUtf8
      ) where

    import Distribution.Compat.Prelude hiding (length, null)
    import Prelude ()

    import Distribution.Utils.String (decodeStringUtf8, encodeStringUtf8)
    import Distribution.Utils.Structured (Structured (..), nominalStructure)

    #if defined(MIN_VERSION_bytestring)
    # if MIN_VERSION_bytestring(0,10,4)
    # define HAVE_SHORTBYTESTRING 1
    # endif
    #endif

    -- Hack for GHC bootstrapping
    --
    -- Currently (as of GHC 8.1), GHC bootstraps Cabal by building
    -- binary and Cabal in one giant ghc --make command.  This
    -- means no MIN_VERSION_binary macro is available.
    --
    -- We could try to cleverly figure something out in this case,
    -- but there is a better plan: just use the unoptimized version
    -- of the Binary instance.  We're not going to use it for anything
    -- real in any case.
    --
    -- WARNING: Don't use MIN_VERSION_binary to smooth over a BC-break!
    --
    #ifndef MIN_VERSION_binary
    #define MIN_VERSION_binary(x, y, z) 0
    #endif

    import qualified Data.ByteString as BS
    import qualified Data.List as List

    #if HAVE_SHORTBYTESTRING
    import qualified Data.ByteString.Short as BS.Short
    #else
    import Distribution.Utils.Generic (fromUTF8BS)
    #endif

    -- | Construct 'ShortText' from 'String'
    toShortText :: String -> ShortText

    -- | Convert 'ShortText' to 'String'
    fromShortText :: ShortText -> String

    -- | Convert from UTF-8 encoded strict 'ByteString'.
    --
    -- @since 3.2.0.0
    unsafeFromUTF8BS :: BS.ByteString -> ShortText

    -- | Text whether 'ShortText' is empty.
    --
    -- @since 3.2.0.0
    null :: ShortText -> Bool

    -- | Compact representation of short 'Strings'
    --
    -- The data is stored internally as UTF8 in an
    -- 'BS.Short.ShortByteString' when compiled against @bytestring >=
    -- 0.10.4@, and otherwise the fallback is to use plain old non-compat
    -- '[Char]'.
    --
    -- Note: This type is for internal uses (such as e.g. 'PackageName')
    -- and shall not be exposed in Cabal's API
    --
    -- @since 2.0.0.2
    #if HAVE_SHORTBYTESTRING
    newtype ShortText = ST { ShortText -> ShortByteString
    unST :: BS.Short.ShortByteString }
                      deriving (ShortText -> ShortText -> Bool
    (ShortText -> ShortText -> Bool)
    -> (ShortText -> ShortText -> Bool) -> Eq ShortText
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: ShortText -> ShortText -> Bool
    == :: ShortText -> ShortText -> Bool
    $c/= :: ShortText -> ShortText -> Bool
    /= :: ShortText -> ShortText -> Bool
    Eq,Eq ShortText
    Eq ShortText =>
    (ShortText -> ShortText -> Ordering)
    -> (ShortText -> ShortText -> Bool)
    -> (ShortText -> ShortText -> Bool)
    -> (ShortText -> ShortText -> Bool)
    -> (ShortText -> ShortText -> Bool)
    -> (ShortText -> ShortText -> ShortText)
    -> (ShortText -> ShortText -> ShortText)
    -> Ord ShortText
    ShortText -> ShortText -> Bool
    ShortText -> ShortText -> Ordering
    ShortText -> ShortText -> ShortText
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: ShortText -> ShortText -> Ordering
    compare :: ShortText -> ShortText -> Ordering
    $c< :: ShortText -> ShortText -> Bool
    < :: ShortText -> ShortText -> Bool
    $c<= :: ShortText -> ShortText -> Bool
    <= :: ShortText -> ShortText -> Bool
    $c> :: ShortText -> ShortText -> Bool
    > :: ShortText -> ShortText -> Bool
    $c>= :: ShortText -> ShortText -> Bool
    >= :: ShortText -> ShortText -> Bool
    $cmax :: ShortText -> ShortText -> ShortText
    max :: ShortText -> ShortText -> ShortText
    $cmin :: ShortText -> ShortText -> ShortText
    min :: ShortText -> ShortText -> ShortText
    Ord,(forall x. ShortText -> Rep ShortText x)
    -> (forall x. Rep ShortText x -> ShortText) -> Generic ShortText
    forall x. Rep ShortText x -> ShortText
    forall x. ShortText -> Rep ShortText x
    forall a.
    (forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
    $cfrom :: forall x. ShortText -> Rep ShortText x
    from :: forall x. ShortText -> Rep ShortText x
    $cto :: forall x. Rep ShortText x -> ShortText
    to :: forall x. Rep ShortText x -> ShortText
    Generic,Typeable ShortText
    Typeable ShortText =>
    (forall (c :: * -> *).
     (forall d b. Data d => c (d -> b) -> d -> c b)
     -> (forall g. g -> c g) -> ShortText -> c ShortText)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c ShortText)
    -> (ShortText -> Constr)
    -> (ShortText -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c ShortText))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c ShortText))
    -> ((forall b. Data b => b -> b) -> ShortText -> ShortText)
    -> (forall r r'.
        (r -> r' -> r)
        -> r -> (forall d. Data d => d -> r') -> ShortText -> r)
    -> (forall r r'.
        (r' -> r -> r)
        -> r -> (forall d. Data d => d -> r') -> ShortText -> r)
    -> (forall u. (forall d. Data d => d -> u) -> ShortText -> [u])
    -> (forall u.
        Int -> (forall d. Data d => d -> u) -> ShortText -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> ShortText -> m ShortText)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> ShortText -> m ShortText)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> ShortText -> m ShortText)
    -> Data ShortText
    ShortText -> Constr
    ShortText -> DataType
    (forall b. Data b => b -> b) -> ShortText -> ShortText
    forall a.
    Typeable a =>
    (forall (c :: * -> *).
     (forall d b. Data d => c (d -> b) -> d -> c b)
     -> (forall g. g -> c g) -> a -> c a)
    -> (forall (c :: * -> *).
        (forall b r. Data b => c (b -> r) -> c r)
        -> (forall r. r -> c r) -> Constr -> c a)
    -> (a -> Constr)
    -> (a -> DataType)
    -> (forall (t :: * -> *) (c :: * -> *).
        Typeable t =>
        (forall d. Data d => c (t d)) -> Maybe (c a))
    -> (forall (t :: * -> * -> *) (c :: * -> *).
        Typeable t =>
        (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
    -> ((forall b. Data b => b -> b) -> a -> a)
    -> (forall r r'.
        (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall r r'.
        (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
    -> (forall u. (forall d. Data d => d -> u) -> a -> [u])
    -> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
    -> (forall (m :: * -> *).
        Monad m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> (forall (m :: * -> *).
        MonadPlus m =>
        (forall d. Data d => d -> m d) -> a -> m a)
    -> Data a
    forall u. Int -> (forall d. Data d => d -> u) -> ShortText -> u
    forall u. (forall d. Data d => d -> u) -> ShortText -> [u]
    forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> ShortText -> r
    forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> ShortText -> r
    forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> ShortText -> m ShortText
    forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> ShortText -> m ShortText
    forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c ShortText
    forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> ShortText -> c ShortText
    forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c ShortText)
    forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c ShortText)
    $cgfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> ShortText -> c ShortText
    gfoldl :: forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> ShortText -> c ShortText
    $cgunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c ShortText
    gunfold :: forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c ShortText
    $ctoConstr :: ShortText -> Constr
    toConstr :: ShortText -> Constr
    $cdataTypeOf :: ShortText -> DataType
    dataTypeOf :: ShortText -> DataType
    $cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c ShortText)
    dataCast1 :: forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c ShortText)
    $cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c ShortText)
    dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c ShortText)
    $cgmapT :: (forall b. Data b => b -> b) -> ShortText -> ShortText
    gmapT :: (forall b. Data b => b -> b) -> ShortText -> ShortText
    $cgmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> ShortText -> r
    gmapQl :: forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> ShortText -> r
    $cgmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> ShortText -> r
    gmapQr :: forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> ShortText -> r
    $cgmapQ :: forall u. (forall d. Data d => d -> u) -> ShortText -> [u]
    gmapQ :: forall u. (forall d. Data d => d -> u) -> ShortText -> [u]
    $cgmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> ShortText -> u
    gmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> ShortText -> u
    $cgmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> ShortText -> m ShortText
    gmapM :: forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> ShortText -> m ShortText
    $cgmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> ShortText -> m ShortText
    gmapMp :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> ShortText -> m ShortText
    $cgmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> ShortText -> m ShortText
    gmapMo :: forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> ShortText -> m ShortText
    Data,Typeable)

    # if MIN_VERSION_binary(0,8,1)
    instance Binary ShortText where
        put :: ShortText -> Put
    put = ShortByteString -> Put
    forall t. Binary t => t -> Put
    put (ShortByteString -> Put)
    -> (ShortText -> ShortByteString) -> ShortText -> Put
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ShortText -> ShortByteString
    unST
        get :: Get ShortText
    get = (ShortByteString -> ShortText)
    -> Get ShortByteString -> Get ShortText
    forall a b. (a -> b) -> Get a -> Get b
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    fmap ShortByteString -> ShortText
    ST Get ShortByteString
    forall t. Binary t => Get t
    get
    # else
    instance Binary ShortText where
        put = put . BS.Short.fromShort . unST
        get = fmap (ST . BS.Short.toShort) get
    # endif

    toShortText :: String -> ShortText
    toShortText = ShortByteString -> ShortText
    ST (ShortByteString -> ShortText)
    -> (String -> ShortByteString) -> String -> ShortText
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . [Word8] -> ShortByteString
    BS.Short.pack ([Word8] -> ShortByteString)
    -> (String -> [Word8]) -> String -> ShortByteString
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . String -> [Word8]
    encodeStringUtf8

    fromShortText :: ShortText -> String
    fromShortText = [Word8] -> String
    decodeStringUtf8 ([Word8] -> String)
    -> (ShortText -> [Word8]) -> ShortText -> String
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ShortByteString -> [Word8]
    BS.Short.unpack (ShortByteString -> [Word8])
    -> (ShortText -> ShortByteString) -> ShortText -> [Word8]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ShortText -> ShortByteString
    unST

    unsafeFromUTF8BS :: ByteString -> ShortText
    unsafeFromUTF8BS = ShortByteString -> ShortText
    ST (ShortByteString -> ShortText)
    -> (ByteString -> ShortByteString) -> ByteString -> ShortText
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ByteString -> ShortByteString
    BS.Short.toShort

    null :: ShortText -> Bool
    null = ShortByteString -> Bool
    BS.Short.null (ShortByteString -> Bool)
    -> (ShortText -> ShortByteString) -> ShortText -> Bool
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ShortText -> ShortByteString
    unST
    #else
    newtype ShortText = ST { unST :: String }
                      deriving (Eq,Ord,Generic,Data,Typeable)

    instance Binary ShortText where
        put = put . encodeStringUtf8 . unST
        get = fmap (ST . decodeStringUtf8) get

    toShortText = ST

    fromShortText = unST

    unsafeFromUTF8BS = ST . fromUTF8BS

    null = List.null . unST
    #endif

    instance Structured ShortText where structure :: Proxy ShortText -> Structure
    structure = Proxy ShortText -> Structure
    forall {k} (a :: k). Typeable a => Proxy a -> Structure
    nominalStructure

    instance NFData ShortText where
      rnf :: ShortText -> ()
    rnf = ShortByteString -> ()
    forall a. NFData a => a -> ()
    rnf (ShortByteString -> ())
    -> (ShortText -> ShortByteString) -> ShortText -> ()
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ShortText -> ShortByteString
    unST

    instance Show ShortText where
      show :: ShortText -> String
    show = ShowS
    forall a. Show a => a -> String
    show ShowS -> (ShortText -> String) -> ShortText -> String
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ShortText -> String
    fromShortText

    instance Read ShortText where
      readsPrec :: Int -> ReadS ShortText
    readsPrec Int
    p = ((String, String) -> (ShortText, String))
    -> [(String, String)] -> [(ShortText, String)]
    forall a b. (a -> b) -> [a] -> [b]
    map ((String -> ShortText) -> (String, String) -> (ShortText, String)
    forall b c d. (b -> c) -> (b, d) -> (c, d)
    forall (a :: * -> * -> *) b c d.
    Arrow a =>
    a b c -> a (b, d) (c, d)
    first String -> ShortText
    toShortText) ([(String, String)] -> [(ShortText, String)])
    -> (String -> [(String, String)]) -> ReadS ShortText
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Int -> String -> [(String, String)]
    forall a. Read a => Int -> ReadS a
    readsPrec Int
    p

    instance Semigroup ShortText where
      ST ShortByteString
    a <> :: ShortText -> ShortText -> ShortText
    <> ST ShortByteString
    b = ShortByteString -> ShortText
    ST (ShortByteString -> ShortByteString -> ShortByteString
    forall a. Monoid a => a -> a -> a
    mappend ShortByteString
    a ShortByteString
    b)

    instance Monoid ShortText where
      mempty :: ShortText
    mempty = ShortByteString -> ShortText
    ST ShortByteString
    forall a. Monoid a => a
    mempty
      mappend :: ShortText -> ShortText -> ShortText
    mappend = ShortText -> ShortText -> ShortText
    forall a. Semigroup a => a -> a -> a
    (<>)

    instance IsString ShortText where
      fromString :: String -> ShortText
    fromString = String -> ShortText
    toShortText

    -- | /O(n)/. Length in characters. /Slow/ as converts to string.
    --
    -- @since 3.2.0.0
    length :: ShortText -> Int
    length :: ShortText -> Int
    length = String -> Int
    forall a. [a] -> Int
    forall (t :: * -> *) a. Foldable t => t a -> Int
    List.length (String -> Int) -> (ShortText -> String) -> ShortText -> Int
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ShortText -> String
    fromShortText

    -- Note: avoid using it, we use it @cabal check@ implementation, where it's ok.