IPv6 Address

typedef struct cardano_ipv6_t cardano_ipv6_t

Represents an IPv6 address.

Each instance of cardano_ipv6_t holds a single IPv6 address in network byte order (big endian).


cardano_error_t cardano_ipv6_new(const byte_t *data, size_t size, cardano_ipv6_t **ipv6)

Creates and initializes a new instance of an IPv6 address.

This function allocates and initializes a new instance of cardano_ipv6_t. The IPv6 address is created from a byte array representing the address in network byte order (big endian).

Usage Example:

cardano_ipv6_t* ipv6 = NULL;
byte_t data[] = {0x20, 0x01, 0x0d, 0xb8, 0x85, 0xa3, 0x00, 0x00, 0x00, 0x00, 0x8a, 0x2e, 0x03, 0x70, 0x73, 0x34}; // Example IPv6 address
size_t size = sizeof(data);

// Attempt to create a new IPv6 object
cardano_error_t result = cardano_ipv6_new(data, size, &ipv6);

if (result == CARDANO_SUCCESS)
{
  // Use the ipv6
  // Once done, ensure to clean up and release the ipv6
  cardano_ipv6_unref(&ipv6);
}

Parameters:
const byte_t *data

[in] A pointer to a byte array containing the 16 bytes of the IPv6 address.

size_t size

[in] The size of the byte array, which should be exactly 16 bytes.

cardano_ipv6_t **ipv6

[out] On successful initialization, this will point to the newly created cardano_ipv6_t object. The object represents a “strong reference” to the IPv6 address, meaning that it is fully initialized and ready for use. The caller is responsible for managing the lifecycle of this object. Specifically, once the IPv6 address is no longer needed, the caller must release it by calling cardano_ipv6_unref.

Returns:

cardano_error_t indicating the outcome of the operation. Returns CARDANO_SUCCESS if the IPv6 address was successfully created, or an appropriate error code indicating the failure reason.


cardano_error_t cardano_ipv6_from_string(const char *string, size_t size, cardano_ipv6_t **ipv6)

Initializes a new IPv6 address from a string representation.

This function allocates and initializes a cardano_ipv6_t object from a string that represents an IPv6 address in colon-separated hexadecimal notation (e.g., “2001:0db8:85a3:0000:0000:8a2e:0370:7334”). The function parses the string and converts it into a numerical IP address.

Usage Example:

const char* ip_string = "2001:0db8:85a3:0000:0000:8a2e:0370:7334"; // Example IPv6 address
cardano_ipv6_t* ipv6 = NULL;
cardano_error_t result = cardano_ipv6_from_string(ip_string, strlen(ip_string), &ipv6);

if (result == CARDANO_SUCCESS)
{
  // Use the ipv6

  // Once done, ensure to clean up and release the ipv6
  cardano_ipv6_unref(&ipv6);
}
else
{
  printf("Failed to create IPv6 address: %s\n", ip_string);
}

Note

This implementation does not support converting or representing IPv6 addresses in their canonical form. Addresses are stored and handled as they are provided without normalization to canonical form.

Parameters:
const char *string

[in] A pointer to a character array containing the IPv6 address in colon-separated hexadecimal notation.

size_t size

[in] The length of the string, which should be a valid length for an IPv6 address in this format.

cardano_ipv6_t **ipv6

[out] On successful parsing and initialization, this will point to the newly created cardano_ipv6_t object. The object represents a “strong reference” to the IPv6 address, meaning that it is fully initialized and ready for use. The caller is responsible for managing the lifecycle of this object. Specifically, once the IPv6 address is no longer needed, the caller must release it by calling cardano_ipv6_unref.

Returns:

cardano_error_t indicating the outcome of the operation. Returns CARDANO_SUCCESS if the IPv6 address was successfully parsed and created, or an appropriate error code indicating the failure reason, such as invalid format or out of memory errors.


cardano_error_t cardano_ipv6_from_cbor(cardano_cbor_reader_t *reader, cardano_ipv6_t **ipv6)

Creates a cardano_ipv6_t from a CBOR reader.

This function parses CBOR data using a provided cardano_cbor_reader_t and constructs a cardano_ipv6_t object. It assumes that the CBOR reader is set up correctly and that the CBOR data corresponds to the structure expected for a ipv6.

Usage Example:

cardano_cbor_reader_t* reader = cardano_cbor_reader_new(cbor_data, data_size);
cardano_ipv6_t* ipv6 = NULL;

cardano_error_t result = cardano_ipv6_from_cbor(reader, &ipv6);

if (result == CARDANO_SUCCESS)
{
  // Use the ipv6

  // Once done, ensure to clean up and release the ipv6
  cardano_ipv6_unref(&ipv6);
}
else
{
  const char* error = cardano_cbor_reader_get_last_error(reader);
  printf("Failed to decode ipv6: %s\n", error);
}

cardano_cbor_reader_unref(&reader); // Cleanup the CBOR reader

Note

If the function fails, the last error can be retrieved by calling cardano_cbor_reader_get_last_error with the reader. The caller is responsible for freeing the created cardano_ipv6_t object by calling cardano_ipv6_unref when it is no longer needed.

Parameters:
cardano_cbor_reader_t *reader

[in] A pointer to an initialized cardano_cbor_reader_t that is ready to read the CBOR-encoded data.

cardano_ipv6_t **ipv6

[out] A pointer to a pointer of cardano_ipv6_t that will be set to the address of the newly created ipv6 object upon successful decoding.

Returns:

A cardano_error_t value indicating the outcome of the operation. Returns CARDANO_SUCCESS if the object was successfully created, or an appropriate error code if an error occurred.


cardano_error_t cardano_ipv6_to_cbor(const cardano_ipv6_t *ipv6, cardano_cbor_writer_t *writer)

Serializes protocol version into CBOR format using a CBOR writer.

This function serializes the given cardano_ipv6_t object using a cardano_cbor_writer_t.

Usage Example:

cardano_ipv6_t* ipv6 = ...;
cardano_cbor_writer_t* writer = cardano_cbor_writer_new();

if (writer)
{
  cardano_error_t result = cardano_ipv6_to_cbor(ipv6, writer);

  if (result == CARDANO_SUCCESS)
  {
    // Use the writer's buffer containing the serialized data
  }
  else
  {
    const char* error_message = cardano_cbor_writer_get_last_error(writer);
    printf("Serialization failed: %s\n", error_message);
  }

  cardano_cbor_writer_unref(&writer);
}

cardano_ipv6_unref(&ipv6);

Parameters:
const cardano_ipv6_t *ipv6

[in] A constant pointer to the cardano_ipv6_t object that is to be serialized.

cardano_cbor_writer_t *writer

[out] A pointer to a cardano_cbor_writer_t where the CBOR serialized data will be written. The writer must already be initialized and ready to accept the data.

Returns:

Returns CARDANO_SUCCESS if the serialization is successful. If the ipv6 or writer is NULL, returns CARDANO_ERROR_POINTER_IS_NULL.


size_t cardano_ipv6_get_bytes_size(const cardano_ipv6_t *ipv6)

Retrieves the size of the byte array representation of an IPv6 address.

This function returns the size of the byte array that would be needed to store the binary representation of an IPv6 address. Since IPv6 addresses always consist of sixteen bytes (128 bits), this function will consistently return a size of 16 bytes.

Usage Example:

cardano_ipv6_t* ipv6 = ...; // Assume ipv6 is already initialized
size_t ipv6_size = cardano_ipv6_get_bytes_size(ipv6);
printf("Size of the IPv6 byte array: %zu bytes\n", ipv6_size);

Parameters:
const cardano_ipv6_t *ipv6

[in] A constant pointer to an initialized cardano_ipv6_t object.

Returns:

The size in bytes of the byte array needed to represent the IPv6 address, which is always 16 bytes for standard IPv6 addresses.


const byte_t *cardano_ipv6_get_bytes(const cardano_ipv6_t *ipv6)

Retrieves a pointer to the byte array representation of an IPv6 address.

This function provides access to the raw byte data that represents an IPv6 address within a cardano_ipv6_t object. The returned pointer points to an internal data structure of the IPv6 object and must not be modified or freed by the caller. The data remains valid as long as the IPv6 object exists and has not been deallocated.

Usage Example:

cardano_ipv6_t* ipv6 = ...; // Assume ipv6 is already initialized
const byte_t* ipv6_bytes = cardano_ipv6_get_bytes(ipv6);

if (ipv6_bytes)
{
    printf("IPv6 Address: %u.%u.%u.%u\n", ipv6_bytes[0], ipv6_bytes[1], ipv6_bytes[2], ipv6_bytes[3]);
}
else
{
    printf("Invalid IPv6 object provided.\n");
}

Note

This function does not transfer ownership of the byte array to the caller. The returned pointer must not be freed or modified, and it should be used only while the ipv6 object is valid.

Parameters:
const cardano_ipv6_t *ipv6

[in] A constant pointer to an initialized cardano_ipv6_t object.

Returns:

A constant pointer to the byte array representing the IPv6 address. The array consists of 6 bytes corresponding to the IPv6 address in network byte order. Returns NULL if the input pointer is NULL.


size_t cardano_ipv6_get_string_size(const cardano_ipv6_t *ipv6)

Retrieves the size necessary to store the string representation of an IPv6 address.

This function calculates the length of the string required to represent the IPv6 address contained within a cardano_ipv6_t object, including the null terminator. This size is useful when allocating a buffer to store the string representation of the IPv6 address.

Usage Example:

cardano_ipv6_t* ipv6 = ...; // Assume ipv6 is already initialized
size_t ipv6_size = cardano_ipv6_get_string_size(ipv6);
printf("Size of the IPv6 string: %zu chars\n", ipv6_size);

Note

This function returns 0 if the ipv6 pointer is NULL.

Parameters:
const cardano_ipv6_t *ipv6

[in] A constant pointer to an initialized cardano_ipv6_t object.

Returns:

The size in bytes required to store the IPv6 address as a null-terminated string. If the input pointer is NULL, returns 0, indicating an error or uninitialized IPv6 object.


const char *cardano_ipv6_get_string(const cardano_ipv6_t *ipv6)

Retrieves the string representation of an IPv6 address.

This function provides access to the string representation of the IPv6 address contained within a cardano_ipv6_t object. The string is formatted in the standard colon-separated notation used for IPv6 addresses (e.g., “2001:0db8:85a3:0000:0000:8a2e:0370:7334”).

Usage Example:

cardano_ipv6_t* ipv6 = ...; // Assume ipv6 is already initialized
const char* ipv6_string = cardano_ipv6_get_string(ipv6);

if (ipv6_string != NULL)
{
  printf("IPv6 Address: %s\n", ipv6_string);
}
else
{
  printf("Failed to retrieve IPv6 string representation.\n");
}

Note

This function returns NULL if the ipv6 pointer is NULL.

Parameters:
const cardano_ipv6_t *ipv6

[in] A constant pointer to an initialized cardano_ipv6_t object.

Returns:

A constant pointer to a null-terminated string representing the IPv6 address. If the input pointer is NULL, returns NULL to indicate an error or uninitialized IPv6 object. The caller should not attempt to modify or free the returned string, as it points to internal memory managed by the cardano_ipv6_t object. The memory for the string will be freed when the cardano_ipv6_t object is destroyed.


void cardano_ipv6_unref(cardano_ipv6_t **ipv6)

Decrements the reference count of a cardano_ipv6_t object.

This function is responsible for managing the lifecycle of a cardano_ipv6_t object by decreasing its reference count. When the reference count reaches zero, the ipv6 is finalized; its associated resources are released, and its memory is deallocated.

Usage Example:

cardano_ipv6_t* ipv6 = cardano_ipv6_new(major, minor);

// Perform operations with the ipv6...

cardano_ipv6_unref(&ipv6);
// At this point, ipv6 is NULL and cannot be used.

Note

After calling cardano_ipv6_unref, the pointer to the cardano_ipv6_t object will be set to NULL to prevent its reuse.

Parameters:
cardano_ipv6_t **ipv6

[inout] A pointer to the pointer of the ipv6 object. This double indirection allows the function to set the caller’s pointer to NULL, avoiding dangling pointer issues after the object has been freed.


void cardano_ipv6_ref(cardano_ipv6_t *ipv6)

Increases the reference count of the cardano_ipv6_t object.

This function is used to manually increment the reference count of an cardano_ipv6_t object, indicating that another part of the code has taken ownership of it. This ensures the object remains allocated and valid until all owners have released their reference by calling cardano_ipv6_unref.

Usage Example:

// Assuming ipv6 is a previously created ipv6 object

cardano_ipv6_ref(ipv6);

// Now ipv6 can be safely used elsewhere without worrying about premature deallocation

Note

Always ensure that for every call to cardano_ipv6_ref there is a corresponding call to cardano_ipv6_unref to prevent memory leaks.

Parameters:
cardano_ipv6_t *ipv6

A pointer to the cardano_ipv6_t object whose reference count is to be incremented.


size_t cardano_ipv6_refcount(const cardano_ipv6_t *ipv6)

Retrieves the current reference count of the cardano_ipv6_t object.

This function returns the number of active references to an cardano_ipv6_t object. It’s useful for debugging purposes or managing the lifecycle of the object in complex scenarios.

Usage Example:

// Assuming ipv6 is a previously created ipv6 object

size_t ref_count = cardano_ipv6_refcount(ipv6);

printf("Reference count: %zu\n", ref_count);

Warning

This function does not account for transitive references. A transitive reference occurs when an object holds a reference to another object, rather than directly to the cardano_ipv6_t. As such, the reported count may not fully represent the total number of conceptual references in cases where such transitive relationships exist.

Parameters:
const cardano_ipv6_t *ipv6

A pointer to the cardano_ipv6_t object whose reference count is queried. The object must not be NULL.

Returns:

The number of active references to the specified cardano_ipv6_t object. If the object is properly managed (i.e., every cardano_ipv6_ref call is matched with a cardano_ipv6_unref call), this count should reach zero right before the object is deallocated.


void cardano_ipv6_set_last_error(cardano_ipv6_t *ipv6, const char *message)

Sets the last error message for a given cardano_ipv6_t object.

Records an error message in the ipv6’s last_error buffer, overwriting any existing message. This is useful for storing descriptive error information that can be later retrieved. The message is truncated if it exceeds the buffer’s capacity.

Note

The error message is limited to 1023 characters, including the null terminator, due to the fixed size of the last_error buffer.

Parameters:
cardano_ipv6_t *ipv6

[in] A pointer to the cardano_ipv6_t instance whose last error message is to be set. If NULL, the function does nothing.

const char *message

[in] A null-terminated string containing the error message. If NULL, the ipv6’s last_error is set to an empty string, indicating no error.


const char *cardano_ipv6_get_last_error(const cardano_ipv6_t *ipv6)

Retrieves the last error message recorded for a specific ipv6.

This function returns a pointer to the null-terminated string containing the last error message set by cardano_ipv6_set_last_error for the given ipv6. If no error message has been set, or if the last_error buffer was explicitly cleared, an empty string is returned, indicating no error.

Note

The returned string points to internal storage within the object and must not be modified by the caller. The string remains valid until the next call to cardano_ipv6_set_last_error for the same ipv6, or until the ipv6 is deallocated.

Parameters:
const cardano_ipv6_t *ipv6

[in] A pointer to the cardano_ipv6_t instance whose last error message is to be retrieved. If the ipv6 is NULL, the function returns a generic error message indicating the null ipv6.

Returns:

A pointer to a null-terminated string containing the last error message for the specified ipv6. If the ipv6 is NULL, “Object is NULL.” is returned to indicate the error.