Platform module¶
In Safe DDS, all operations related to the platform are executed by the Platform module, which has been designed to be responsible for the following tasks:
Handling of fatal errors, allowing for appropriate responses to critical issues that may arise during the library’s operation.
Control of timing mechanisms, providing platform specific timekeeping for various processes within the library.
There is another operation which is not strictly platform related, but that the platform shall at least provide a default implementation for:
Management of memory allocation calls, ensuring that all the possible memory allocations are performed via platform interfaces.
By delegating these essential functions to the platform module, it is possible to maintain a streamlined and organized structure within Safe DDS, ultimately contributing to its reliability, performance and portability.
Default platform¶
If Safe DDS has been built with any built-in platform support using the SAFEDDS_PLATFORM flag via CMake options, the default platform can be retrieved using the system-wide get_platform method.
Analogously, a system-wide default platform can be set using the set_platform method.
To get and use the default platform’s offered allocator, the get_default_allocator method can be used.
If requiring to use a different allocator than the default one, the user is responsible for injecting it to the classes that require an allocator.
This API will be used internally by multiple Safe DDS modules to perform platform related operations.
// Retrieve the default platform (depends on the platform implementation built).
platform::IPlatform& platform = get_platform();
// Retrieve the default allocator (depends on the platform implementation built).
platform::IAllocator& allocator = get_default_allocator();
// Setting a default platform at runtime.
CustomPlatform custom_platform;
set_platform(custom_platform);
Note
Setting a custom platform will not affect the default allocator.
IPlatform interface¶
IPlatform is the interface that all platform module implementation must implement.
API Reference
For more information about platform::IPlatform interface, check API Reference:
Error handling¶
Safe DDS will use the fatal_error method of the platform module to handle fatal errors during the library’s operation.
This method shall not return as it is called when the library is in an unrecoverable state.
Time keeping¶
Safe DDS will use the get_current_timepoint method of the platform module to retrieve the current time.
This method shall return a monotonic timepoint as an execution::TimePoint object and takes no arguments.
Example implementation¶
A naive IPlatform interface implementation could be:
class CustomPlatform :
public platform::IPlatform
{
execution::TimePoint get_current_timepoint() noexcept override
{
// Platform specific function to retrieve time (in this case in ms) [NOT PROVIDED]
size_t millis = system_get_millis();
execution::TimePoint timepoint = {};
timepoint.seconds = millis / 1000;
timepoint.nanoseconds = (millis % 1000) * 1000000;
return timepoint;
}
[[noreturn]] void fatal_error(
const platform::FatalErrorCode& error_code) noexcept override
{
printf("Fatal error: %s\n", get_fatal_error_message(error_code));
while (1)
{
}
}
};
IAllocator interface¶
IAllocator is the interface that all allocator implementations must implement.
API Reference
For more information about platform::IAllocator interface, check API Reference:
Memory management¶
Safe DDS memory operations are performed using the allocate method of a provided allocator.
This method is responsible for allocating memory blocks of the specified size with a certain alignment, and returning a pointer to the beginning of the allocated memory.
Safe DDS will provide mechanisms for controlling the memory allocations performed by the different modules.
It is important to note that the memory allocated by the default allocator will not be deallocated.
At DDS level, these memory allocations can be controlled by means of the PreallocMemoryConfig and related QoS policies. Those policies allows for specifying the maximum amount of elements that a certain entity will be able to allocate, and also allow for the application to specify how many of those elements shall be preallocated at creation time.
Note
For a complete reference of the different memory objects used in Safe DDS, please refer to Memory module.
The allocate function of platform::IAllocator returns a void * pointer to the beginning of the allocated memory and takes the following arguments:
sizeasuint32_tThe size of the memory block to be allocated.
alignmentasuint32_tThe alignment of the memory block to be allocated.
Example implementation¶
A naive IAllocator interface implementation could be:
class CustomAllocator :
public platform::IAllocator
{
void* allocate(
uint32_t size,
uint32_t /* alignment */) noexcept override
{
// It is not required to check alignment as calloc guarantees alignment for any type
return calloc(size, sizeof(uint8_t));
}
};