hs-bindgen-runtime
Safe HaskellSafe-Inferred
LanguageGHC2021

HsBindgen.Runtime.CEnum

Description

C enumerations

This module is intended to be imported qualified.

import HsBindgen.Runtime.Prelude
import HsBindgen.Runtime.CEnum qualified as CEnum
Synopsis

Type classes

class Integral (CEnumZ a) => CEnum a where Source #

C enumeration

This class implements an API for Haskell representations of C enumerations. C enum declarations only declare values; they do not limit the range of the corresponding integral type. They may have negative values, non-sequential values, and multiple names for a single value.

At a low level, hs-bindgen generates a newtype wrapper around the integral representation type to represent a C enum. An instance of this class is generated automatically. A Show instance defined using showsCEnum is also generated by default. Bounded and Enum instances are not generated automatically because values do not technically need to be declared. Users may optionally derive these instances using AsCEnum or AsSeqentialCEnum when appropriate.

This class may also be used with Haskell sum-type representations of enumerations.

Minimal complete definition

declaredValues, readPrecUndeclared

Associated Types

type CEnumZ a Source #

Integral representation type

Methods

toCEnum :: CEnumZ a -> a Source #

Construct a value from the integral representation

fromCEnum . toCEnum === id

default toCEnum :: Coercible a (CEnumZ a) => CEnumZ a -> a Source #

fromCEnum :: a -> CEnumZ a Source #

Get the integral representation for a value

toCEnum . fromCEnum === id

If a has an Ord instance, it should be compatible with the Ord instance on the underlying integral value:

\x y -> (x <= y) === (fromCEnum x <= fromCEnum y)

default fromCEnum :: Coercible a (CEnumZ a) => a -> CEnumZ a Source #

declaredValues :: proxy a -> DeclaredValues a Source #

Declared values and associated names

showsUndeclared :: proxy a -> Int -> CEnumZ a -> ShowS Source #

Show undeclared value

Like any Show related function, this should generate a valid Haskell expression. In this case, a valid Haskell expression for values outside of the set of declared values (that is, for which isDeclared will return False).

The default definition just shows the underlying integer value; this is valid if the Haskell wrapper has a Num instance. If the Haskell type is simply a newtype wrapper around the underlying C type, you can use showsWrappedUndeclared. Finally, if the Haskell type cannot represent undeclared values, this can be defined using error.

showsUndeclared _ = \_ x ->
  error $ "Unexpected value " ++ show x ++ " for type Foo"

default showsUndeclared :: Show (CEnumZ a) => proxy a -> Int -> CEnumZ a -> ShowS Source #

readPrecUndeclared :: ReadPrec a Source #

isDeclared :: a -> Bool Source #

Determine if the specified value is declared

This has a default definition in terms of getDeclaredValues, but you may wish to override this with a more efficient implementation (in particular, see seqIsDeclared).

mkDeclared :: CEnumZ a -> Maybe a Source #

Construct a value only if it is declared

See also seqMkDeclared.

class CEnum a => SequentialCEnum a where Source #

C enumeration with sequential values

Bounded and Enum methods may be implemented more efficiently when the values of an enumeration are sequential. An instance of this class is generated automatically in this case. Users may optionally derive these instances using AsSequentialCEnum when appropriate.

This class may also be used with Haskell sum-type representations of enumerations.

all isDeclared [minDeclaredValue..maxDeclaredValue]

Methods

minDeclaredValue :: a Source #

The minimum declared value

minDeclaredValue == minimum (filter isDeclared (map toCEnum [minBound..]))

maxDeclaredValue :: a Source #

The maximum declared value

maxDeclaredValue == maximum (filter isDeclared (map toCEnum [minBound..]))

Deriving via support

newtype AsCEnum a Source #

Type used to derive classes using DerivingVia a type with a CEnum instance

When the values are sequential, AsSequentialCEnum provides better performance and should therefore be used instead.

The following classes may be derived:

  • Bounded may be derived using the bounds of the declared values. This is not derived by default.
  • Enum may be derived using the bounds of the declared values. This instance assumes that only the declared values are valid and throws a CEnumException if passed a value that is not declared. This is not derived by default.

For declared values we have

toEnum   === coerce       . toCENum   . fromIntegral
fromEnum === fromIntegral . fromCEnum . coerce

In addition we guarantee that where pred or succ are defined, we have

\x -> (pred x < x) && (x < succ x)

Constructors

WrapCEnum 

Fields

Instances

Instances details
CEnum a => Bounded (AsCEnum a) Source # 
Instance details

Defined in HsBindgen.Runtime.CEnum

CEnum a => Enum (AsCEnum a) Source # 
Instance details

Defined in HsBindgen.Runtime.CEnum

Methods

succ :: AsCEnum a -> AsCEnum a #

pred :: AsCEnum a -> AsCEnum a #

toEnum :: Int -> AsCEnum a #

fromEnum :: AsCEnum a -> Int #

enumFrom :: AsCEnum a -> [AsCEnum a] #

enumFromThen :: AsCEnum a -> AsCEnum a -> [AsCEnum a] #

enumFromTo :: AsCEnum a -> AsCEnum a -> [AsCEnum a] #

enumFromThenTo :: AsCEnum a -> AsCEnum a -> AsCEnum a -> [AsCEnum a] #

newtype AsSequentialCEnum a Source #

Type used to derive classes using DerivingVia a type with a SequentialCEnum instance

The following classes may be derived:

  • Bounded may be derived using the bounds of the declared values. This is not derived by default.
  • Enum may be derived using the bounds of the declared values. This instance assumes that only the declared values are valid and throws a CEnumException if passed a value that is not declared. This is not derived by default.

AsSequentialCEnum should have the same properties as AsCEnum.

Constructors

WrapSequentialCEnum 

API

getNames :: forall a. CEnum a => a -> [String] Source #

Get all names associated with a value

An empty list is returned when the specified value is not declared.

Instance support

data DeclaredValues a Source #

Declared values (opaque)

declaredValuesFromList :: Ord (CEnumZ a) => [(CEnumZ a, NonEmpty String)] -> DeclaredValues a Source #

Construct DeclaredValues from a list of values and associated names

show :: forall a. CEnum a => a -> String Source #

Show the specified value

Examples for a hypothetical enumeration type, using generated defaults:

showCEnum StatusOK == "StatusOK"
showCEnum (StatusCode 418) == "StatusCode 418"

shows :: forall a. CEnum a => Int -> a -> ShowS Source #

Generalization of showCEnum (akin to showsPrec).

This function may be used in the definition of a Show instance for a newtype representation of a C enumeration.

When the value is declared, a corresponding name is returned. Otherwise, showsUndeclared is called.

showsWrappedUndeclared :: Show (CEnumZ a) => String -> proxy a -> Int -> CEnumZ a -> ShowS Source #

Helper function for defining showsUndeclared

This helper can be used in the case where a is a newtype wrapper around the underlying CEnumZ a.

readEither :: forall a. CEnum a => String -> Either String a Source #

Read a CEnum from string

Examples for a hypothetical enumeration type, using generated defaults:

(readEitherCEnum "StatusCode 200" :: StatusCode) == Right StatusOK
(readEitherCEnum "StatusOK" :: StatusCode) == Right StatusOK
(readEitherCEnum "StatusCode 123" :: StatusCode) == Right (StatusCode 123)

readPrec :: forall a. CEnum a => ReadPrec a Source #

Read a CEnum from string

This function may be used in the definition of a Read instance for a newtype representation of a C enumeration.

readPrecWrappedUndeclared :: forall a. (CEnum a, Read (CEnumZ a)) => String -> ReadPrec a Source #

Helper function for defining readPrecUndeclared

This helper can be used in the case where a is a newtype wrapper around the underlying CEnumZ a.

seqIsDeclared :: forall a. SequentialCEnum a => a -> Bool Source #

Determine if the specified value is declared

This implementation is optimized for SequentialCEnum.

seqMkDeclared :: forall a. SequentialCEnum a => CEnumZ a -> Maybe a Source #

Construct a value only if it is declared

This implementation is optimized for SequentialCEnum.

Exceptions