Type 7 – Floats & control tokens¶
This type combines two completely unrelated types of items – floating point numbers and special values such as true, false, null, etc. We refer to these special values as ‘control values’ or ‘ctrls’ for short throughout the code.
Just like integers, they have different possible width (resulting in different value ranges and precisions).
-
enum
cbor_float_width
¶ Possible widths of CBOR_TYPE_FLOAT_CTRL items.
Values:
-
CBOR_FLOAT_0
¶ Internal use - ctrl and special values.
-
CBOR_FLOAT_16
¶ Half float.
-
CBOR_FLOAT_32
¶ Single float.
-
CBOR_FLOAT_64
¶ Double.
-
Corresponding cbor_type |
CBOR_TYPE_FLOAT_CTRL |
Number of allocations | One per lifetime |
Storage requirements | sizeof(cbor_item_t) + 1/4/8 |
Getting metadata¶
-
bool
cbor_float_ctrl_is_ctrl
(const cbor_item_t *item)¶ Is this a ctrl value?
- Return
- Is this a ctrl value?
- Parameters
item[borrow]
: A float or ctrl item
-
cbor_float_width
cbor_float_get_width
(const cbor_item_t *item)¶ Get the float width.
- Return
- The width.
- Parameters
item[borrow]
: A float or ctrl item
-
bool
cbor_ctrl_is_bool
(const cbor_item_t *item)¶ Is this ctrl item a boolean?
- Return
- Is this ctrl item a boolean?
- Parameters
item[borrow]
: A ctrl item
Reading data¶
-
float
cbor_float_get_float2
(const cbor_item_t *item)¶ Get a half precision float.
The item must have the corresponding width
- Return
- half precision value
- Parameters
borrow]
: A half precision float
-
float
cbor_float_get_float4
(const cbor_item_t *item)¶ Get a single precision float.
The item must have the corresponding width
- Return
- single precision value
- Parameters
borrow]
: A signle precision float
-
double
cbor_float_get_float8
(const cbor_item_t *item)¶ Get a double precision float.
The item must have the corresponding width
- Return
- double precision value
- Parameters
borrow]
: A double precision float
-
double
cbor_float_get_float
(const cbor_item_t *item)¶ Get the float value represented as double.
Can be used regardless of the width.
- Return
- double precision value
- Parameters
borrow]
: Any float
-
uint8_t
cbor_ctrl_value
(const cbor_item_t *item)¶ Reads the control value.
- Return
- the simple value
- Parameters
item[borrow]
: A ctrl item
Creating new items¶
-
cbor_item_t *
cbor_new_ctrl
()¶ Constructs a new ctrl item.
The width cannot be changed once the item is created
- Return
- new 1B ctrl or
NULL
upon memory allocation failure
-
cbor_item_t *
cbor_new_float2
()¶ Constructs a new float item.
The width cannot be changed once the item is created
- Return
- new 2B float or
NULL
upon memory allocation failure
-
cbor_item_t *
cbor_new_float4
()¶ Constructs a new float item.
The width cannot be changed once the item is created
- Return
- new 4B float or
NULL
upon memory allocation failure
-
cbor_item_t *
cbor_new_float8
()¶ Constructs a new float item.
The width cannot be changed once the item is created
- Return
- new 8B float or
NULL
upon memory allocation failure
-
cbor_item_t *
cbor_new_null
()¶ Constructs new null ctrl item.
- Return
- new null ctrl item or
NULL
upon memory allocation failure
-
cbor_item_t *
cbor_new_undef
()¶ Constructs new undef ctrl item.
- Return
- new undef ctrl item or
NULL
upon memory allocation failure
Building items¶
-
cbor_item_t *
cbor_build_bool
(bool value)¶ Constructs new boolean ctrl item.
- Return
- new boolen ctrl item or
NULL
upon memory allocation failure - Parameters
value
: The value to use
-
cbor_item_t *
cbor_build_ctrl
(uint8_t value)¶ Constructs a ctrl item.
- Return
- new ctrl item or
NULL
upon memory allocation failure - Parameters
value
: the value to use
-
cbor_item_t *
cbor_build_float2
(float value)¶ Constructs a new float.
- Return
- new float
- Parameters
value
: the value to use
-
cbor_item_t *
cbor_build_float4
(float value)¶ Constructs a new float.
- Return
- new float or
NULL
upon memory allocation failure - Parameters
value
: the value to use
-
cbor_item_t *
cbor_build_float8
(double value)¶ Constructs a new float.
- Return
- new float or
NULL
upon memory allocation failure - Parameters
value
: the value to use
Manipulating existing items¶
-
void
cbor_set_ctrl
(cbor_item_t *item, uint8_t value)¶ Assign a control value.
Warning
It is possible to produce an invalid CBOR value by assigning a
invalid value using this mechanism. Please consult the standard before use.
- Parameters
item[borrow]
: A ctrl itemvalue
: The simple value to assign. Please consult the standard for allowed values
-
void
cbor_set_float2
(cbor_item_t *item, float value)¶ Assigns a float value.
- Parameters
item[borrow]
: A half precision floatvalue
: The value to assign
-
void
cbor_set_float4
(cbor_item_t *item, float value)¶ Assigns a float value.
- Parameters
item[borrow]
: A single precision floatvalue
: The value to assign
-
void
cbor_set_float8
(cbor_item_t *item, double value)¶ Assigns a float value.
- Parameters
item[borrow]
: A double precision floatvalue
: The value to assign
Half floats¶
CBOR supports two bytes wide (“half-precision”) floats which are not supported by the C language. libcbor represents them using float <https://en.cppreference.com/w/c/language/type> values throughout the API, which has important implications when manipulating these values.
In particular, if a user uses some of the manipulation APIs
(e.g. cbor_set_float2()
, cbor_new_float2()
)
to introduce a value that doesn’t have an exect half-float representation,
the encoding semantics are given by cbor_encode_half()
as follows:
-
size_t
cbor_encode_half
(float, unsigned char *, size_t)¶ Encodes a half-precision float.
Since there is no native representation or semantics for half floats in the language, we use single-precision floats, as every value that can be expressed as a half-float can also be expressed as a float.
This however means that not all floats passed to this function can be unambiguously encoded. The behavior is as follows:
- Infinity, NaN are preserved
- Zero is preserved
- Denormalized numbers keep their sign bit and 10 most significant bit of the significand
- All other numbers
- If the logical value of the exponent is < -24, the output is zero
- If the logical value of the exponent is between -23 and -14, the output is cut off to represent the ‘magnitude’ of the input, by which we mean (-1)^{signbit} x 1.0e{exponent}. The value in the significand is lost.
- In all other cases, the sign bit, the exponent, and 10 most significant bits of the significand are kept
- Return
- number of bytes written
- Parameters
value
:buffer
: Target bufferbuffer_size
: Available space in the buffer