in ports/Storage/src/aia_storage_config.c [201:308]
bool AiaStoreAlert( const char* alertToken, size_t alertTokenLen,
AiaTimepointSeconds_t scheduledTime,
AiaDurationMs_t duration, uint8_t alertType )
{
if( !alertToken )
{
AiaLogError( "Null alertToken" );
return false;
}
if( alertTokenLen != AIA_ALERT_TOKEN_CHARS )
{
AiaLogError( "Invalid alert token length" );
return false;
}
size_t allAlertsBytes = AiaGetAlertsSize();
size_t alertsBytesWithNewAlert =
allAlertsBytes + AIA_SIZE_OF_ALERT_IN_BYTES;
size_t startingOffset = allAlertsBytes;
size_t bytePosition;
bool updatingExistingAlert = false;
/**
* Load all alerts from persistent storage. Allocated additional space
* for a new alert though in case the token we are trying to insert does
* not exist in persistent storage yet.
*/
uint8_t* allAlertsBuffer = AiaCalloc( 1, alertsBytesWithNewAlert );
if( !allAlertsBuffer )
{
AiaLogError( "AiaCalloc failed, bytes=%zu.", alertsBytesWithNewAlert );
return false;
}
if( !AiaLoadAlerts( allAlertsBuffer, allAlertsBytes ) )
{
AiaLogError( "AiaLoadBlob failed" );
AiaFree( allAlertsBuffer );
return false;
}
/** Go through the tokens to find the first empty or matching one */
for( bytePosition = 0; bytePosition < alertsBytesWithNewAlert;
bytePosition += AIA_SIZE_OF_ALERT_IN_BYTES )
{
startingOffset = bytePosition;
if( '\0' == allAlertsBuffer[ bytePosition ] )
{
/** Found an empty token */
break;
}
else
{
/** Check if this token matches with what we are trying to insert */
if( !strncmp( (const char*)allAlertsBuffer + bytePosition,
alertToken, alertTokenLen ) )
{
updatingExistingAlert = true;
break;
}
}
}
/* Check if we have reached the alerts storage limit */
if( startingOffset == alertsBytesWithNewAlert )
{
AiaLogError(
"AiaStoreAlert failed: Maximum number of local alerts to store "
"reached." );
AiaFree( allAlertsBuffer );
return false;
}
/** Write the new alert token */
uint8_t* newAlertOffset = allAlertsBuffer + startingOffset;
memcpy( newAlertOffset, alertToken, alertTokenLen );
/** Write the other fields: scheduledTime, duration, alertType */
bytePosition = alertTokenLen;
for( size_t i = 0; i < sizeof( AiaTimepointSeconds_t );
++i, bytePosition++ )
{
newAlertOffset[ bytePosition ] = ( scheduledTime >> ( i * 8 ) );
}
for( size_t i = 0; i < sizeof( AiaDurationMs_t ); ++i, bytePosition++ )
{
newAlertOffset[ bytePosition ] = ( duration >> ( i * 8 ) );
}
for( size_t i = 0; i < sizeof( uint8_t ); ++i, bytePosition++ )
{
newAlertOffset[ bytePosition ] = ( alertType >> ( i * 8 ) );
}
/** Store the new blob in persistent storage */
size_t storeSize =
( updatingExistingAlert ? allAlertsBytes : alertsBytesWithNewAlert );
/** Store the new blob in persistent storage */
if( !AiaStoreBlob( AIA_ALL_ALERTS_STORAGE_KEY_V0, allAlertsBuffer,
storeSize ) )
{
AiaLogError( "AiaStoreBlob failed" );
AiaFree( allAlertsBuffer );
return false;
}
AiaFree( allAlertsBuffer );
return true;
}