{-# LANGUAGE TypeApplications #-}


-- | Copyright  : Will Thompson, Iñaki García Etxebarria and Jonas Platte
-- License    : LGPL-2.1
-- Maintainer : Iñaki García Etxebarria
-- 
-- Contains the public fields of a GByteArray.

#if (MIN_VERSION_haskell_gi_overloading(1,0,0) && !defined(__HADDOCK_VERSION__))
#define ENABLE_OVERLOADING
#endif

module GI.GLib.Structs.ByteArray
    (

-- * Exported types
    ByteArray(..)                           ,
    newZeroByteArray                        ,
    noByteArray                             ,


 -- * Methods
-- ** Overloaded methods #method:Overloaded methods#

#if defined(ENABLE_OVERLOADING)
    ResolveByteArrayMethod                  ,
#endif


-- ** free #method:free#

    byteArrayFree                           ,


-- ** freeToBytes #method:freeToBytes#

    byteArrayFreeToBytes                    ,


-- ** new #method:new#

    byteArrayNew                            ,


-- ** newTake #method:newTake#

    byteArrayNewTake                        ,


-- ** unref #method:unref#

    byteArrayUnref                          ,




 -- * Properties
-- ** data #attr:data#
-- | a pointer to the element data. The data may be moved as
--     elements are added to the t'GI.GLib.Structs.ByteArray.ByteArray'

#if defined(ENABLE_OVERLOADING)
    byteArray_data                          ,
#endif
    getByteArrayData                        ,
    setByteArrayData                        ,


-- ** len #attr:len#
-- | the number of elements in the t'GI.GLib.Structs.ByteArray.ByteArray'

#if defined(ENABLE_OVERLOADING)
    byteArray_len                           ,
#endif
    getByteArrayLen                         ,
    setByteArrayLen                         ,




    ) where

import Data.GI.Base.ShortPrelude
import qualified Data.GI.Base.ShortPrelude as SP
import qualified Data.GI.Base.Overloading as O
import qualified Prelude as P

import qualified Data.GI.Base.Attributes as GI.Attributes
import qualified Data.GI.Base.ManagedPtr as B.ManagedPtr
import qualified Data.GI.Base.GClosure as B.GClosure
import qualified Data.GI.Base.GError as B.GError
import qualified Data.GI.Base.GVariant as B.GVariant
import qualified Data.GI.Base.GValue as B.GValue
import qualified Data.GI.Base.GParamSpec as B.GParamSpec
import qualified Data.GI.Base.CallStack as B.CallStack
import qualified Data.GI.Base.Properties as B.Properties
import qualified Data.GI.Base.Signals as B.Signals
import qualified Data.Text as T
import qualified Data.ByteString.Char8 as B
import qualified Data.Map as Map
import qualified Foreign.Ptr as FP
import qualified GHC.OverloadedLabels as OL

import {-# SOURCE #-} qualified GI.GLib.Structs.Bytes as GLib.Bytes

-- | Memory-managed wrapper type.
newtype ByteArray = ByteArray (ManagedPtr ByteArray)
    deriving (Eq)
foreign import ccall "g_byte_array_get_type" c_g_byte_array_get_type ::
    IO GType

instance BoxedObject ByteArray where
    boxedType _ = c_g_byte_array_get_type

-- | Convert 'ByteArray' to and from 'Data.GI.Base.GValue.GValue' with 'Data.GI.Base.GValue.toGValue' and 'Data.GI.Base.GValue.fromGValue'.
instance B.GValue.IsGValue ByteArray where
    toGValue o = do
        gtype <- c_g_byte_array_get_type
        B.ManagedPtr.withManagedPtr o (B.GValue.buildGValue gtype B.GValue.set_boxed)

    fromGValue gv = do
        ptr <- B.GValue.get_boxed gv :: IO (Ptr ByteArray)
        B.ManagedPtr.newBoxed ByteArray ptr



-- | Construct a `ByteArray` struct initialized to zero.
newZeroByteArray :: MonadIO m => m ByteArray
newZeroByteArray = liftIO $ callocBoxedBytes 8 >>= wrapBoxed ByteArray

instance tag ~ 'AttrSet => Constructible ByteArray tag where
    new _ attrs = do
        o <- newZeroByteArray
        GI.Attributes.set o attrs
        return o


-- | A convenience alias for `Nothing` :: `Maybe` `ByteArray`.
noByteArray :: Maybe ByteArray
noByteArray = Nothing

-- | Get the value of the “@data@” field.
-- When <https://github.com/haskell-gi/haskell-gi/wiki/Overloading overloading> is enabled, this is equivalent to
-- 
-- @
-- 'Data.GI.Base.Attributes.get' byteArray #data
-- @
getByteArrayData :: MonadIO m => ByteArray -> m Word8
getByteArrayData s = liftIO $ withManagedPtr s $ \ptr -> do
    val <- peek (ptr `plusPtr` 0) :: IO Word8
    return val

-- | Set the value of the “@data@” field.
-- When <https://github.com/haskell-gi/haskell-gi/wiki/Overloading overloading> is enabled, this is equivalent to
-- 
-- @
-- 'Data.GI.Base.Attributes.set' byteArray [ #data 'Data.GI.Base.Attributes.:=' value ]
-- @
setByteArrayData :: MonadIO m => ByteArray -> Word8 -> m ()
setByteArrayData s val = liftIO $ withManagedPtr s $ \ptr -> do
    poke (ptr `plusPtr` 0) (val :: Word8)

#if defined(ENABLE_OVERLOADING)
data ByteArrayDataFieldInfo
instance AttrInfo ByteArrayDataFieldInfo where
    type AttrBaseTypeConstraint ByteArrayDataFieldInfo = (~) ByteArray
    type AttrAllowedOps ByteArrayDataFieldInfo = '[ 'AttrSet, 'AttrGet]
    type AttrSetTypeConstraint ByteArrayDataFieldInfo = (~) Word8
    type AttrTransferTypeConstraint ByteArrayDataFieldInfo = (~)Word8
    type AttrTransferType ByteArrayDataFieldInfo = Word8
    type AttrGetType ByteArrayDataFieldInfo = Word8
    type AttrLabel ByteArrayDataFieldInfo = "data"
    type AttrOrigin ByteArrayDataFieldInfo = ByteArray
    attrGet = getByteArrayData
    attrSet = setByteArrayData
    attrConstruct = undefined
    attrClear = undefined
    attrTransfer _ v = do
        return v

byteArray_data :: AttrLabelProxy "data"
byteArray_data = AttrLabelProxy

#endif


-- | Get the value of the “@len@” field.
-- When <https://github.com/haskell-gi/haskell-gi/wiki/Overloading overloading> is enabled, this is equivalent to
-- 
-- @
-- 'Data.GI.Base.Attributes.get' byteArray #len
-- @
getByteArrayLen :: MonadIO m => ByteArray -> m Word32
getByteArrayLen s = liftIO $ withManagedPtr s $ \ptr -> do
    val <- peek (ptr `plusPtr` 4) :: IO Word32
    return val

-- | Set the value of the “@len@” field.
-- When <https://github.com/haskell-gi/haskell-gi/wiki/Overloading overloading> is enabled, this is equivalent to
-- 
-- @
-- 'Data.GI.Base.Attributes.set' byteArray [ #len 'Data.GI.Base.Attributes.:=' value ]
-- @
setByteArrayLen :: MonadIO m => ByteArray -> Word32 -> m ()
setByteArrayLen s val = liftIO $ withManagedPtr s $ \ptr -> do
    poke (ptr `plusPtr` 4) (val :: Word32)

#if defined(ENABLE_OVERLOADING)
data ByteArrayLenFieldInfo
instance AttrInfo ByteArrayLenFieldInfo where
    type AttrBaseTypeConstraint ByteArrayLenFieldInfo = (~) ByteArray
    type AttrAllowedOps ByteArrayLenFieldInfo = '[ 'AttrSet, 'AttrGet]
    type AttrSetTypeConstraint ByteArrayLenFieldInfo = (~) Word32
    type AttrTransferTypeConstraint ByteArrayLenFieldInfo = (~)Word32
    type AttrTransferType ByteArrayLenFieldInfo = Word32
    type AttrGetType ByteArrayLenFieldInfo = Word32
    type AttrLabel ByteArrayLenFieldInfo = "len"
    type AttrOrigin ByteArrayLenFieldInfo = ByteArray
    attrGet = getByteArrayLen
    attrSet = setByteArrayLen
    attrConstruct = undefined
    attrClear = undefined
    attrTransfer _ v = do
        return v

byteArray_len :: AttrLabelProxy "len"
byteArray_len = AttrLabelProxy

#endif



#if defined(ENABLE_OVERLOADING)
instance O.HasAttributeList ByteArray
type instance O.AttributeList ByteArray = ByteArrayAttributeList
type ByteArrayAttributeList = ('[ '("data", ByteArrayDataFieldInfo), '("len", ByteArrayLenFieldInfo)] :: [(Symbol, *)])
#endif

-- method ByteArray::free
-- method type : MemberFunction
-- Args: [ Arg
--           { argCName = "array"
--           , argType = TByteArray
--           , direction = DirectionIn
--           , mayBeNull = False
--           , argDoc =
--               Documentation
--                 { rawDocText = Just "a #GByteArray" , sinceVersion = Nothing }
--           , argScope = ScopeTypeInvalid
--           , argClosure = -1
--           , argDestroy = -1
--           , argCallerAllocates = False
--           , transfer = TransferNothing
--           }
--       , Arg
--           { argCName = "free_segment"
--           , argType = TBasicType TBoolean
--           , direction = DirectionIn
--           , mayBeNull = False
--           , argDoc =
--               Documentation
--                 { rawDocText =
--                     Just "if %TRUE the actual byte data is freed as well"
--                 , sinceVersion = Nothing
--                 }
--           , argScope = ScopeTypeInvalid
--           , argClosure = -1
--           , argDestroy = -1
--           , argCallerAllocates = False
--           , transfer = TransferNothing
--           }
--       ]
-- Lengths: []
-- returnType: Just (TBasicType TUInt8)
-- throws : False
-- Skip return : False

foreign import ccall "g_byte_array_free" g_byte_array_free ::
    Ptr GByteArray ->                       -- array : TByteArray
    CInt ->                                 -- free_segment : TBasicType TBoolean
    IO Word8

-- | Frees the memory allocated by the t'GI.GLib.Structs.ByteArray.ByteArray'. If /@freeSegment@/ is
-- 'P.True' it frees the actual byte data. If the reference count of
-- /@array@/ is greater than one, the t'GI.GLib.Structs.ByteArray.ByteArray' wrapper is preserved but
-- the size of /@array@/ will be set to zero.
byteArrayFree ::
    (B.CallStack.HasCallStack, MonadIO m) =>
    ByteString
    -- ^ /@array@/: a t'GI.GLib.Structs.ByteArray.ByteArray'
    -> Bool
    -- ^ /@freeSegment@/: if 'P.True' the actual byte data is freed as well
    -> m Word8
    -- ^ __Returns:__ the element data if /@freeSegment@/ is 'P.False', otherwise
    --          'P.Nothing'.  The element data should be freed using 'GI.GLib.Functions.free'.
byteArrayFree array freeSegment = liftIO $ do
    array' <- packGByteArray array
    let freeSegment' = (fromIntegral . fromEnum) freeSegment
    result <- g_byte_array_free array' freeSegment'
    unrefGByteArray array'
    return result

#if defined(ENABLE_OVERLOADING)
#endif

-- method ByteArray::free_to_bytes
-- method type : MemberFunction
-- Args: [ Arg
--           { argCName = "array"
--           , argType = TByteArray
--           , direction = DirectionIn
--           , mayBeNull = False
--           , argDoc =
--               Documentation
--                 { rawDocText = Just "a #GByteArray" , sinceVersion = Nothing }
--           , argScope = ScopeTypeInvalid
--           , argClosure = -1
--           , argDestroy = -1
--           , argCallerAllocates = False
--           , transfer = TransferEverything
--           }
--       ]
-- Lengths: []
-- returnType: Just (TInterface Name { namespace = "GLib" , name = "Bytes" })
-- throws : False
-- Skip return : False

foreign import ccall "g_byte_array_free_to_bytes" g_byte_array_free_to_bytes ::
    Ptr GByteArray ->                       -- array : TByteArray
    IO (Ptr GLib.Bytes.Bytes)

-- | Transfers the data from the t'GI.GLib.Structs.ByteArray.ByteArray' into a new immutable t'GI.GLib.Structs.Bytes.Bytes'.
-- 
-- The t'GI.GLib.Structs.ByteArray.ByteArray' is freed unless the reference count of /@array@/ is greater
-- than one, the t'GI.GLib.Structs.ByteArray.ByteArray' wrapper is preserved but the size of /@array@/
-- will be set to zero.
-- 
-- This is identical to using 'GI.GLib.Structs.Bytes.bytesNewTake' and 'GI.GLib.Functions.byteArrayFree'
-- together.
-- 
-- /Since: 2.32/
byteArrayFreeToBytes ::
    (B.CallStack.HasCallStack, MonadIO m) =>
    ByteString
    -- ^ /@array@/: a t'GI.GLib.Structs.ByteArray.ByteArray'
    -> m GLib.Bytes.Bytes
    -- ^ __Returns:__ a new immutable t'GI.GLib.Structs.Bytes.Bytes' representing same
    --     byte data that was in the array
byteArrayFreeToBytes array = liftIO $ do
    array' <- packGByteArray array
    result <- g_byte_array_free_to_bytes array'
    checkUnexpectedReturnNULL "byteArrayFreeToBytes" result
    result' <- (wrapBoxed GLib.Bytes.Bytes) result
    return result'

#if defined(ENABLE_OVERLOADING)
#endif

-- method ByteArray::new
-- method type : MemberFunction
-- Args: []
-- Lengths: []
-- returnType: Just TByteArray
-- throws : False
-- Skip return : False

foreign import ccall "g_byte_array_new" g_byte_array_new ::
    IO (Ptr GByteArray)

-- | Creates a new t'GI.GLib.Structs.ByteArray.ByteArray' with a reference count of 1.
byteArrayNew ::
    (B.CallStack.HasCallStack, MonadIO m) =>
    m ByteString
    -- ^ __Returns:__ the new t'GI.GLib.Structs.ByteArray.ByteArray'
byteArrayNew  = liftIO $ do
    result <- g_byte_array_new
    checkUnexpectedReturnNULL "byteArrayNew" result
    result' <- unpackGByteArray result
    unrefGByteArray result
    return result'

#if defined(ENABLE_OVERLOADING)
#endif

-- method ByteArray::new_take
-- method type : MemberFunction
-- Args: [ Arg
--           { argCName = "data"
--           , argType = TCArray False (-1) 1 (TBasicType TUInt8)
--           , direction = DirectionIn
--           , mayBeNull = False
--           , argDoc =
--               Documentation
--                 { rawDocText = Just "byte data for the array"
--                 , sinceVersion = Nothing
--                 }
--           , argScope = ScopeTypeInvalid
--           , argClosure = -1
--           , argDestroy = -1
--           , argCallerAllocates = False
--           , transfer = TransferEverything
--           }
--       , Arg
--           { argCName = "len"
--           , argType = TBasicType TUInt32
--           , direction = DirectionIn
--           , mayBeNull = False
--           , argDoc =
--               Documentation
--                 { rawDocText = Just "length of @data" , sinceVersion = Nothing }
--           , argScope = ScopeTypeInvalid
--           , argClosure = -1
--           , argDestroy = -1
--           , argCallerAllocates = False
--           , transfer = TransferNothing
--           }
--       ]
-- Lengths: [ Arg
--              { argCName = "len"
--              , argType = TBasicType TUInt32
--              , direction = DirectionIn
--              , mayBeNull = False
--              , argDoc =
--                  Documentation
--                    { rawDocText = Just "length of @data" , sinceVersion = Nothing }
--              , argScope = ScopeTypeInvalid
--              , argClosure = -1
--              , argDestroy = -1
--              , argCallerAllocates = False
--              , transfer = TransferNothing
--              }
--          ]
-- returnType: Just TByteArray
-- throws : False
-- Skip return : False

foreign import ccall "g_byte_array_new_take" g_byte_array_new_take ::
    Ptr Word8 ->                            -- data : TCArray False (-1) 1 (TBasicType TUInt8)
    Word32 ->                               -- len : TBasicType TUInt32
    IO (Ptr GByteArray)

-- | Create byte array containing the data. The data will be owned by the array
-- and will be freed with 'GI.GLib.Functions.free', i.e. it could be allocated using 'GI.GLib.Functions.strdup'.
-- 
-- /Since: 2.32/
byteArrayNewTake ::
    (B.CallStack.HasCallStack, MonadIO m) =>
    ByteString
    -- ^ /@data@/: byte data for the array
    -> m ByteString
    -- ^ __Returns:__ a new t'GI.GLib.Structs.ByteArray.ByteArray'
byteArrayNewTake data_ = liftIO $ do
    let len = fromIntegral $ B.length data_
    data_' <- packByteString data_
    result <- g_byte_array_new_take data_' len
    checkUnexpectedReturnNULL "byteArrayNewTake" result
    result' <- unpackGByteArray result
    unrefGByteArray result
    return result'

#if defined(ENABLE_OVERLOADING)
#endif

-- XXX Could not generate method ByteArray::steal
-- Error was : Not implemented: "Don't know how to allocate \"len\" of type TBasicType TUInt32"
-- method ByteArray::unref
-- method type : MemberFunction
-- Args: [ Arg
--           { argCName = "array"
--           , argType = TByteArray
--           , direction = DirectionIn
--           , mayBeNull = False
--           , argDoc =
--               Documentation
--                 { rawDocText = Just "A #GByteArray" , sinceVersion = Nothing }
--           , argScope = ScopeTypeInvalid
--           , argClosure = -1
--           , argDestroy = -1
--           , argCallerAllocates = False
--           , transfer = TransferNothing
--           }
--       ]
-- Lengths: []
-- returnType: Nothing
-- throws : False
-- Skip return : False

foreign import ccall "g_byte_array_unref" g_byte_array_unref ::
    Ptr GByteArray ->                       -- array : TByteArray
    IO ()

-- | Atomically decrements the reference count of /@array@/ by one. If the
-- reference count drops to 0, all memory allocated by the array is
-- released. This function is thread-safe and may be called from any
-- thread.
-- 
-- /Since: 2.22/
byteArrayUnref ::
    (B.CallStack.HasCallStack, MonadIO m) =>
    ByteString
    -- ^ /@array@/: A t'GI.GLib.Structs.ByteArray.ByteArray'
    -> m ()
byteArrayUnref array = liftIO $ do
    array' <- packGByteArray array
    g_byte_array_unref array'
    unrefGByteArray array'
    return ()

#if defined(ENABLE_OVERLOADING)
#endif

#if defined(ENABLE_OVERLOADING)
type family ResolveByteArrayMethod (t :: Symbol) (o :: *) :: * where
    ResolveByteArrayMethod l o = O.MethodResolutionFailed l o

instance (info ~ ResolveByteArrayMethod t ByteArray, O.MethodInfo info ByteArray p) => OL.IsLabel t (ByteArray -> p) where
#if MIN_VERSION_base(4,10,0)
    fromLabel = O.overloadedMethod @info
#else
    fromLabel _ = O.overloadedMethod @info
#endif

#endif