- 0.1.0
- Initial record
- Thread Safe Cache
The storm tracking Cryptographic Materials Cache (storm tracking CMC) is a built-in implementation of the CMC interface provided by the AWS Encryption SDK.
It provides thread safe access to a Local CMC, and prevents excessive parallel requests to the underlying cryptographic materials provider.
The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119.
On initialization of the storm tracking CMC, the caller MUST provide exactly what is required by a Local CMC.
Initialization MUST also provide
The implementation MUST instantiate a Local CMC to do the actual caching.
A number of seconds (at least 1, default 10).
If an entry will expire within this amount of time, attempts will be made to refresh the cache.
This should be significantly less than the TTL for any item put into the cache.
A number of seconds (at least 1, default 1).
While within the grace period, attempts to refresh the cache are made no more often than once per interval.
A number (at least 1, default 20).
The maximum number of individual keys for which lookups can be in flight.
A number (at least 1, default 20).
An entry that has been in flight for this long is no longer considered in flight.
A number of milliseconds (at least 1, default 20).
If the implementation must block, and no more intelligent signaling is used, then the implementation should sleep for this many milliseconds before reexamining the state of the cache.
The settings need to be consistent.
Here are examples of ambiguous or inconsistent settings:
- A grace interval that exceeds the grace period is inconsistent because only one attempt is made per grace interval and the grace period will end before the next interval.
- An in flight TTL that exceeds the grace period is inconsistent because the grace period will expire before the in flight TTL.
- An in flight TTL that is less than the grace interval is inconsistent because only one attempt is made per grace interval and even if the in flight TTL expires before the interval another attempt should not start.
Therefore
- The Grace Interval MUST be less than or equal to the Grace Period.
- The Inflight TTL MUST be less than or equal to the Grace Period.
- The Grace Interval MUST be less than or equal to the Inflight TTL.
For most purposes, the Grace Period should be several times larger than the Grace Interval.
The interface MUST be exactly the same as a Local CMC, even if used in a multi-threaded context, with two exceptions
- GetCacheEntry might return NoSuchEntry, even though there is really an entry.
- GetCacheEntry might block for a time before returning a result.
Specifics for these two exceptions are outlined below.
Any time the storm tracking CMC returns NoSuchEntry from GetCacheEntry,
that key is said to be in flight
until that same key is written with PutCacheEntry.
For each in flight key, the storm tracking CMC MUST keep track of the most recent time that NoSuchEntry was returned, with accuracy to the second.
PutCacheEntry MUST mark the key as not in flight.
A time now
MUST be considered within the grace period for an entry that expires
at a time expiry
if (expiry - gracePeriod) <= now
A time now
MUST be considered within the grace interval
of an inflight entry at inflight
time
if now < (inflight + graceInterval)
If GetCacheEntry is called for a key :
The implementation MUST call the Local CMC to find the cached materials for the key, if any.
If the key is found in the cache, it is returned, unless the current time is within the grace period, and no other thread is currently fetching new materials. Specifically --
-
If the number of things inflight is greater than or equal to the FanOut GetCacheEntry MUST return the cache entry.
-
If the key's expiration is not within the grace period, GetCacheEntry MUST return the cache entry.
-
If the key's expiration is within the grace period, and the key is not inflight GetCacheEntry MUST return NoSuchEntry and mark that key as inflight at the current time.
-
If the key's expiration is within the grace period, and the key is inflight and the inflight time is within the grace interval GetCacheEntry MUST return the cache entry.
-
If the key's expiration is within the grace period, and the key is inflight and the inflight time is not within the grace interval GetCacheEntry MUST return NoSuchEntry and update the key as inflight at the current time.
If the key is not found in the cache, one thread receives NoSuchEntry, while others are blocked until an entry appears. Specifically --
-
If the number of things inflight is greater than or equal to the FanOut GetCacheEntry MUST block until a FanOut slot is available, or the key appears in the cache.
-
If the key is not inflight GetCacheEntry MUST return NoSuchEntry and mark that key as inflight at the current time.
-
If the key is inflight and the current time is within the grace interval GetCacheEntry MUST block until a FanOut slot is available, or the key appears in the cache.
-
If the key is inflight and the current time is not within the grace interval GetCacheEntry MUST return NoSuchEntry and update the key as inflight at the current time.