org.ehcache.internal.store.offheap
Class AbstractOffHeapStore<K,V>

java.lang.Object
  extended by org.ehcache.internal.store.offheap.AbstractOffHeapStore<K,V>
All Implemented Interfaces:
ConfigurationChangeSupport, Store<K,V>, AuthoritativeTier<K,V>, LowerCachingTier<K,V>
Direct Known Subclasses:
OffHeapDiskStore, OffHeapStore

public abstract class AbstractOffHeapStore<K,V>
extends java.lang.Object
implements AuthoritativeTier<K,V>, LowerCachingTier<K,V>


Nested Class Summary
 
Nested classes/interfaces inherited from interface org.ehcache.spi.cache.tiering.AuthoritativeTier
AuthoritativeTier.Provider
 
Nested classes/interfaces inherited from interface org.ehcache.spi.cache.Store
Store.Configuration<K,V>, Store.Iterator<T>, Store.ValueHolder<V>
 
Nested classes/interfaces inherited from interface org.ehcache.spi.cache.tiering.LowerCachingTier
LowerCachingTier.Provider
 
Field Summary
protected  org.ehcache.internal.store.offheap.AbstractOffHeapStore.BackingMapEvictionListener<K,V> mapEvictionListener
           
 
Constructor Summary
AbstractOffHeapStore(java.lang.String statisticsTag, Store.Configuration<K,V> config, TimeSource timeSource)
           
 
Method Summary
protected abstract  EhcacheOffHeapBackingMap<K,OffHeapValueHolder<V>> backingMap()
           
 java.util.Map<K,Store.ValueHolder<V>> bulkCompute(java.util.Set<? extends K> keys, Function<java.lang.Iterable<? extends java.util.Map.Entry<? extends K,? extends V>>,java.lang.Iterable<? extends java.util.Map.Entry<? extends K,? extends V>>> remappingFunction)
          Compute a value for every key passed in the Set keys argument, using the remappingFunction to compute the value.
 java.util.Map<K,Store.ValueHolder<V>> bulkCompute(java.util.Set<? extends K> keys, Function<java.lang.Iterable<? extends java.util.Map.Entry<? extends K,? extends V>>,java.lang.Iterable<? extends java.util.Map.Entry<? extends K,? extends V>>> remappingFunction, NullaryFunction<java.lang.Boolean> replaceEqual)
          Compute a value for every key passed in the Set keys argument, using the remappingFunction to compute the value.
 java.util.Map<K,Store.ValueHolder<V>> bulkComputeIfAbsent(java.util.Set<? extends K> keys, Function<java.lang.Iterable<? extends K>,java.lang.Iterable<? extends java.util.Map.Entry<? extends K,? extends V>>> mappingFunction)
          Compute a value for every key passed in the Set keys argument using the mappingFunction to compute the value.
 void clear()
          Removes all of the mappings from this map.
 Store.ValueHolder<V> compute(K key, BiFunction<? super K,? super V,? extends V> mappingFunction)
          Compute the value for the given key by invoking the given function to produce the value.
 Store.ValueHolder<V> compute(K key, BiFunction<? super K,? super V,? extends V> mappingFunction, NullaryFunction<java.lang.Boolean> replaceEqual)
          Compute the value for the given key by invoking the given function to produce the value.
 Store.ValueHolder<V> computeIfAbsent(K key, Function<? super K,? extends V> mappingFunction)
          Compute the value for the given key (only if absent or expired) by invoking the given function to produce the value.
 Store.ValueHolder<V> computeIfAbsentAndFault(K key, Function<? super K,? extends V> mappingFunction)
          Marks the mapping as not evictable and performs computeIfAbsent() atomically.
 Store.ValueHolder<V> computeIfPresent(K key, BiFunction<? super K,? super V,? extends V> remappingFunction)
          Compute the value for the given key (only if present and non-expired) by invoking the given function to produce the value.
 Store.ValueHolder<V> computeIfPresent(K key, BiFunction<? super K,? super V,? extends V> remappingFunction, NullaryFunction<java.lang.Boolean> replaceEqual)
          Compute the value for the given key (only if present and non-expired) by invoking the given function to produce the value.
 boolean containsKey(K key)
          Returns true if this store contains the specified key and the entry is not expired.
 void disableStoreEventNotifications()
          Disables store event notifications.
 void enableStoreEventNotifications(StoreEventListener<K,V> listener)
          Enables notifications for store-initiated events, i.e.
 boolean flush(K key, Store.ValueHolder<V> valueFlushed)
          This marks the entry as evictable again.
 Store.ValueHolder<V> get(K key)
          Returns the ValueHolder to which the specified key is mapped, or null if this store contains no mapping for the key or if it was evicted (or became expired) since it was initially installed.
 Store.ValueHolder<V> getAndFault(K key)
          Marks the mapping as not evictable and returns it atomically.
 Store.ValueHolder<V> getAndRemove(K key)
          Return the value holder currently in the caching tier and remove it.
 void handleOversizeMappingException(K key, org.terracotta.offheapstore.exceptions.OversizeMappingException cause)
           
 void handleOversizeMappingException(K key, org.terracotta.offheapstore.exceptions.OversizeMappingException cause, java.util.concurrent.atomic.AtomicBoolean invokeValve)
           
 Store.ValueHolder<V> installMapping(K key, Function<K,Store.ValueHolder<V>> source)
          Either return the value holder currently in the caching tier, or compute and store it when it isn't present.
 void invalidate(K key)
          Remove a mapping.
 void invalidate(K key, NullaryFunction<K> function)
          Remove a mapping, then call a function under the same lock scope irrespectively of a mapping being there or not.
 Store.Iterator<Cache.Entry<K,Store.ValueHolder<V>>> iterator()
          Returns an iterator over the elements in this store.
 void put(K key, V value)
          Maps the specified key to the specified value in this store.
 Store.ValueHolder<V> putIfAbsent(K key, V value)
          Maps the specified key to the specified value in this store, unless a non-expired mapping already exists.
 void registerEmergencyValve(java.util.concurrent.Callable<java.lang.Void> valve)
           
 void remove(K key)
          Removes the key (and its corresponding value) from this store.
 boolean remove(K key, V value)
          Removes the entry for a key only if currently mapped to a given value and the entry is not expired This is equivalent to
 Store.ValueHolder<V> replace(K key, V value)
          Replaces the entry for a key only if currently mapped to some value and the entry is not expired.
 boolean replace(K key, V oldValue, V newValue)
          Replaces the entry for a key only if currently mapped to a given value and the entry is not expired.
 void setInvalidationListener(CachingTier.InvalidationListener<K,V> invalidationListener)
          Set the caching tier's invalidation listener.
protected static
<K,V> Predicate<java.util.Map.Entry<K,OffHeapValueHolder<V>>>
wrap(EvictionVeto<? super K,? super V> delegate, TimeSource timeSource)
           
 
Methods inherited from class java.lang.Object
clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
 
Methods inherited from interface org.ehcache.spi.cache.ConfigurationChangeSupport
getConfigurationChangeListeners
 

Field Detail

mapEvictionListener

protected org.ehcache.internal.store.offheap.AbstractOffHeapStore.BackingMapEvictionListener<K,V> mapEvictionListener
Constructor Detail

AbstractOffHeapStore

public AbstractOffHeapStore(java.lang.String statisticsTag,
                            Store.Configuration<K,V> config,
                            TimeSource timeSource)
Method Detail

get

public Store.ValueHolder<V> get(K key)
                         throws CacheAccessException
Description copied from interface: Store
Returns the ValueHolder to which the specified key is mapped, or null if this store contains no mapping for the key or if it was evicted (or became expired) since it was initially installed.

More formally, if this store contains a non-expired mapping from a key k to a ValueHolder v such that key.equals(k), then this method returns v; otherwise it returns null. (There can be at most one such mapping.)

Specified by:
get in interface Store<K,V>
Throws:
CacheAccessException - if the mapping can't be retrieved

containsKey

public boolean containsKey(K key)
                    throws CacheAccessException
Description copied from interface: Store
Returns true if this store contains the specified key and the entry is not expired. More formally, returns true if and only if this store contains a key k such that (o.equals(k)).

Specified by:
containsKey in interface Store<K,V>
Parameters:
key - key whose presence in this store is to be tested
Returns:
true if this store contains the specified non-expired element
Throws:
CacheAccessException - if the presence can't be tested for

put

public void put(K key,
                V value)
         throws CacheAccessException
Description copied from interface: Store
Maps the specified key to the specified value in this store. Neither the key nor the value can be null.

The ValueHolder can be retrieved by calling the get method with a key that is equal to the original key.

Specified by:
put in interface Store<K,V>
Parameters:
key - key with which the specified value is to be associated
value - value to be associated with the specified key
Throws:
CacheAccessException - if the mapping can't be installed

putIfAbsent

public Store.ValueHolder<V> putIfAbsent(K key,
                                        V value)
                                 throws java.lang.NullPointerException,
                                        CacheAccessException
Description copied from interface: Store
Maps the specified key to the specified value in this store, unless a non-expired mapping already exists. This is equivalent to
   if (!store.containsKey(key))
       store.put(key, value);
       return null;
   else
       return store.get(key);
except that the action is performed atomically. The ValueHolder can be retrieved by calling the get method with a key that is equal to the original key.

Neither the key nor the value can be null.

Specified by:
putIfAbsent in interface Store<K,V>
Parameters:
key - key with which the specified value is to be associated
value - value to be associated with the specified key
Returns:
the ValueHolder to which the specified key was previously mapped, or null if no such mapping existed or the mapping was expired
Throws:
java.lang.NullPointerException - if the specified key or value is null
CacheAccessException - if the mapping can't be installed

remove

public void remove(K key)
            throws CacheAccessException
Description copied from interface: Store
Removes the key (and its corresponding value) from this store. This method does nothing if the key is not mapped.

Specified by:
remove in interface Store<K,V>
Parameters:
key - the key that needs to be removed
Throws:
CacheAccessException - if the mapping can't be removed

remove

public boolean remove(K key,
                      V value)
               throws CacheAccessException
Description copied from interface: Store
Removes the entry for a key only if currently mapped to a given value and the entry is not expired This is equivalent to
   if (store.containsKey(key) && store.get(key).equals(value)) {
       store.remove(key);
       return true;
   } else return false;
except that the action is performed atomically.

Specified by:
remove in interface Store<K,V>
Parameters:
key - key with which the specified value is associated
value - value expected to be associated with the specified key
Returns:
true if the value was removed
Throws:
CacheAccessException - if the mapping can't be removed

replace

public Store.ValueHolder<V> replace(K key,
                                    V value)
                             throws java.lang.NullPointerException,
                                    CacheAccessException
Description copied from interface: Store
Replaces the entry for a key only if currently mapped to some value and the entry is not expired. This is equivalent to
   V oldValue = store.get(key);
   if (oldValue != null) {
     map.put(key, value);
   }
   return oldValue; 
except that the action is performed atomically.

Specified by:
replace in interface Store<K,V>
Parameters:
key - key with which the specified value is associated
value - value expected to be associated with the specified key
Returns:
the ValueHolder to which the specified key was previously mapped, or null if no such mapping existed
Throws:
java.lang.NullPointerException - if the specified key or value is null
CacheAccessException - if the mapping can't be replaced

replace

public boolean replace(K key,
                       V oldValue,
                       V newValue)
                throws java.lang.NullPointerException,
                       java.lang.IllegalArgumentException,
                       CacheAccessException
Description copied from interface: Store
Replaces the entry for a key only if currently mapped to a given value and the entry is not expired. This is equivalent to
   if (store.containsKey(key) && store.get(key).equals(oldValue)) {
       store.put(key, newValue);
       return true;
   } else return false;
except that the action is performed atomically.

Specified by:
replace in interface Store<K,V>
Parameters:
key - key with which the specified value is associated
oldValue - value expected to be associated with the specified key
newValue - value to be associated with the specified key
Returns:
true if the value was replaced
Throws:
java.lang.NullPointerException - if the specified key or value is null
CacheAccessException - if the mapping can't be replaced
java.lang.IllegalArgumentException

clear

public void clear()
           throws CacheAccessException
Description copied from interface: Store
Removes all of the mappings from this map. This method provides no guarantee in terms of atomicity.

Specified by:
clear in interface Store<K,V>
Specified by:
clear in interface LowerCachingTier<K,V>
Throws:
CacheAccessException - if the store couldn't be partially or entirely be cleared.

enableStoreEventNotifications

public void enableStoreEventNotifications(StoreEventListener<K,V> listener)
Description copied from interface: Store
Enables notifications for store-initiated events, i.e. eviction and expiration.

Specified by:
enableStoreEventNotifications in interface Store<K,V>
Parameters:
listener - listener to notify

disableStoreEventNotifications

public void disableStoreEventNotifications()
Description copied from interface: Store
Disables store event notifications.

Specified by:
disableStoreEventNotifications in interface Store<K,V>

iterator

public Store.Iterator<Cache.Entry<K,Store.ValueHolder<V>>> iterator()
Description copied from interface: Store
Returns an iterator over the elements in this store. The elements are returned in no particular order (unless this set is an instance of some class that provides a guarantee).

Specified by:
iterator in interface Store<K,V>
Returns:
an iterator over the mappings in this set

compute

public Store.ValueHolder<V> compute(K key,
                                    BiFunction<? super K,? super V,? extends V> mappingFunction)
                             throws CacheAccessException
Description copied from interface: Store
Compute the value for the given key by invoking the given function to produce the value. The entire operation is performed atomically. This is equivalent to calling Store.compute(Object, BiFunction, NullaryFunction) with a "replaceEquals" function that returns Boolean.TRUE

Specified by:
compute in interface Store<K,V>
Throws:
CacheAccessException

compute

public Store.ValueHolder<V> compute(K key,
                                    BiFunction<? super K,? super V,? extends V> mappingFunction,
                                    NullaryFunction<java.lang.Boolean> replaceEqual)
                             throws CacheAccessException
Description copied from interface: Store
Compute the value for the given key by invoking the given function to produce the value. The entire operation is performed atomically.

Specified by:
compute in interface Store<K,V>
Parameters:
key - the key to operate on
mappingFunction - the function that will produce the value. The function will be supplied with the key and existing value (or null if no entry exists) as parameters. The function should return the desired new value for the entry or null to remove the entry. If the method throws an unchecked exception the Store will not be modified (the caller will receive the exception)
replaceEqual - If the existing value in the store is Object.equals(Object) to the value returned from the mappingFunction this function will be invoked. If this function returns Boolean.FALSE then the existing entry in the store will not be replaced with a new entry and the existing entry will have its access time updated
Returns:
the new value associated with the key or null if none
Throws:
CacheAccessException

computeIfAbsent

public Store.ValueHolder<V> computeIfAbsent(K key,
                                            Function<? super K,? extends V> mappingFunction)
                                     throws CacheAccessException
Description copied from interface: Store
Compute the value for the given key (only if absent or expired) by invoking the given function to produce the value. The entire operation is performed atomically.

Specified by:
computeIfAbsent in interface Store<K,V>
Parameters:
key - the key to operate on
mappingFunction - the function that will produce the value. The function will be supplied with the key as a parameter. The function return the desired new value for the entry or null to remove the entry. If the method throws an unchecked exception the Store will not be modified (the caller will receive the exception)
Returns:
the new value associated with the key or null if none
Throws:
CacheAccessException

computeIfPresent

public Store.ValueHolder<V> computeIfPresent(K key,
                                             BiFunction<? super K,? super V,? extends V> remappingFunction)
                                      throws CacheAccessException
Description copied from interface: Store
Compute the value for the given key (only if present and non-expired) by invoking the given function to produce the value. The entire operation is performed atomically.

This is equivalent to calling Store.computeIfPresent(Object, BiFunction, NullaryFunction) with a "replaceEquals" function that returns Boolean.TRUE

Specified by:
computeIfPresent in interface Store<K,V>
Throws:
CacheAccessException

computeIfPresent

public Store.ValueHolder<V> computeIfPresent(K key,
                                             BiFunction<? super K,? super V,? extends V> remappingFunction,
                                             NullaryFunction<java.lang.Boolean> replaceEqual)
                                      throws CacheAccessException
Description copied from interface: Store
Compute the value for the given key (only if present and non-expired) by invoking the given function to produce the value. The entire operation is performed atomically.

Specified by:
computeIfPresent in interface Store<K,V>
Parameters:
key - the key to operate on
remappingFunction - the function that will produce the value. The function will be supplied with the key and existing value as parameters. The function should return the desired new value for the entry or null to remove the entry. If the method throws an unchecked exception the Store will not be modified (the caller will receive the exception)
replaceEqual - If the existing value in the store is Object.equals(Object) to the value returned from the mappingFunction this function will be invoked. If this function returns Boolean.FALSE then the existing entry in the store will not be replaced with a new entry and the existing entry will have its access time updated
Returns:
the new value associated with the key or null if none
Throws:
CacheAccessException

bulkCompute

public java.util.Map<K,Store.ValueHolder<V>> bulkCompute(java.util.Set<? extends K> keys,
                                                         Function<java.lang.Iterable<? extends java.util.Map.Entry<? extends K,? extends V>>,java.lang.Iterable<? extends java.util.Map.Entry<? extends K,? extends V>>> remappingFunction)
                                                  throws CacheAccessException
Description copied from interface: Store
Compute a value for every key passed in the Set keys argument, using the remappingFunction to compute the value.

This is equivalent to calling Store.bulkCompute(Set, Function, NullaryFunction) with a "replaceEquals" function that returns Boolean.TRUE

Specified by:
bulkCompute in interface Store<K,V>
Throws:
CacheAccessException

bulkCompute

public java.util.Map<K,Store.ValueHolder<V>> bulkCompute(java.util.Set<? extends K> keys,
                                                         Function<java.lang.Iterable<? extends java.util.Map.Entry<? extends K,? extends V>>,java.lang.Iterable<? extends java.util.Map.Entry<? extends K,? extends V>>> remappingFunction,
                                                         NullaryFunction<java.lang.Boolean> replaceEqual)
                                                  throws CacheAccessException
Description copied from interface: Store
Compute a value for every key passed in the Set keys argument, using the remappingFunction to compute the value.

The function gets an Iterable of Map.Entry key/value pairs, where each entry's value is its currently stored value, or null if nothing is stored under the key. It is expected that the function returns an Iterable of Map.Entry key/value pairs containing an entry for each key that was passed to it. This returned Iterable should also iterate in the same order as the input Iterable. If an entry's value is null, its mapping will be removed from the store.

The function may be called multiple times per bulkCompute call, depending on how the store wants or does not want to batch computations. Note: This method guarantees atomicity of computations for each individual key in keys. Implementations may choose to provide coarser grained atomicity.

Specified by:
bulkCompute in interface Store<K,V>
Parameters:
keys - the keys to compute a new value for.
remappingFunction - the function that generates new values.
replaceEqual - If the existing value in the store is Object.equals(Object) to the value returned from the mappingFunction this function will be invoked. If this function returns Boolean.FALSE then the existing entry in the store will not be replaced with a new entry and the existing entry will have its access time updated
Returns:
a Map of key/value pairs for each key in keys to the value computed.
Throws:
CacheAccessException

bulkComputeIfAbsent

public java.util.Map<K,Store.ValueHolder<V>> bulkComputeIfAbsent(java.util.Set<? extends K> keys,
                                                                 Function<java.lang.Iterable<? extends K>,java.lang.Iterable<? extends java.util.Map.Entry<? extends K,? extends V>>> mappingFunction)
                                                          throws CacheAccessException
Description copied from interface: Store
Compute a value for every key passed in the Set keys argument using the mappingFunction to compute the value. The function gets an Iterable of Map.Entry key/value pairs, where each entry's value is its currently stored value for each key that is not mapped in the store. It is expected that the function returns an Iterable of Map.Entry key/value pairs containing an entry for each key that was passed to it. This returned Iterable should also iterate in the same order as the input Iterable. The function may be called multiple times per bulkComputeIfAbsent call, depending on how the store wants or does not want to batch computations. Note: This method guarantees atomicity of computations for each individual key in keys. Implementations may choose to provide coarser grained atomicity.

Specified by:
bulkComputeIfAbsent in interface Store<K,V>
Parameters:
keys - the keys to compute a new value for, if they're not in the store.
mappingFunction - the function that generates new values.
Returns:
a Map of key/value pairs for each key in keys to the previously missing value.
Throws:
CacheAccessException

getAndFault

public Store.ValueHolder<V> getAndFault(K key)
                                 throws CacheAccessException
Description copied from interface: AuthoritativeTier
Marks the mapping as not evictable and returns it atomically.

Specified by:
getAndFault in interface AuthoritativeTier<K,V>
Returns:
the value holder.
Throws:
CacheAccessException - if the mapping can't be retrieved or updated.

computeIfAbsentAndFault

public Store.ValueHolder<V> computeIfAbsentAndFault(K key,
                                                    Function<? super K,? extends V> mappingFunction)
                                             throws CacheAccessException
Description copied from interface: AuthoritativeTier
Marks the mapping as not evictable and performs computeIfAbsent() atomically.

Specified by:
computeIfAbsentAndFault in interface AuthoritativeTier<K,V>
Returns:
the value holder.
Throws:
CacheAccessException - if the mapping can't be retrieved or updated.

flush

public boolean flush(K key,
                     Store.ValueHolder<V> valueFlushed)
Description copied from interface: AuthoritativeTier
This marks the entry as evictable again. The ValueHolder must be an instance returned by the CachingTier.

Specified by:
flush in interface AuthoritativeTier<K,V>
Returns:
true if a mapping exists for that key, the mapping was faulted, and the value of the ValueHolder is equal to the value of the mapping in the AuthoritativeTier.

setInvalidationListener

public void setInvalidationListener(CachingTier.InvalidationListener<K,V> invalidationListener)
Description copied from interface: LowerCachingTier
Set the caching tier's invalidation listener. The invalidation listener can only be set once.

Specified by:
setInvalidationListener in interface LowerCachingTier<K,V>
Parameters:
invalidationListener - the listener.

invalidate

public void invalidate(K key)
                throws CacheAccessException
Description copied from interface: LowerCachingTier
Remove a mapping.

Specified by:
invalidate in interface LowerCachingTier<K,V>
Parameters:
key - the key.
Throws:
CacheAccessException

invalidate

public void invalidate(K key,
                       NullaryFunction<K> function)
                throws CacheAccessException
Description copied from interface: LowerCachingTier
Remove a mapping, then call a function under the same lock scope irrespectively of a mapping being there or not.

Specified by:
invalidate in interface LowerCachingTier<K,V>
Parameters:
key - the key.
function - the function to call.
Throws:
CacheAccessException

getAndRemove

public Store.ValueHolder<V> getAndRemove(K key)
                                  throws CacheAccessException
Return the value holder currently in the caching tier and remove it. Note that this implementation is atomic.

Specified by:
getAndRemove in interface LowerCachingTier<K,V>
Parameters:
key - the key.
Returns:
the value holder, or null.
Throws:
CacheAccessException

installMapping

public Store.ValueHolder<V> installMapping(K key,
                                           Function<K,Store.ValueHolder<V>> source)
                                    throws CacheAccessException
Either return the value holder currently in the caching tier, or compute and store it when it isn't present. Note that in case of expired value holders null will be returned and the mapping will be invalidated. Note that this implementation is only valid for a lower caching tier.

Specified by:
installMapping in interface LowerCachingTier<K,V>
Parameters:
key - the key.
source - the function that computes the value.
Returns:
the value holder, or null.
Throws:
CacheAccessException

registerEmergencyValve

public void registerEmergencyValve(java.util.concurrent.Callable<java.lang.Void> valve)

handleOversizeMappingException

public void handleOversizeMappingException(K key,
                                           org.terracotta.offheapstore.exceptions.OversizeMappingException cause)
                                    throws CacheAccessException
Throws:
CacheAccessException

handleOversizeMappingException

public void handleOversizeMappingException(K key,
                                           org.terracotta.offheapstore.exceptions.OversizeMappingException cause,
                                           java.util.concurrent.atomic.AtomicBoolean invokeValve)
                                    throws CacheAccessException
Throws:
CacheAccessException

backingMap

protected abstract EhcacheOffHeapBackingMap<K,OffHeapValueHolder<V>> backingMap()

wrap

protected static <K,V> Predicate<java.util.Map.Entry<K,OffHeapValueHolder<V>>> wrap(EvictionVeto<? super K,? super V> delegate,
                                                                                    TimeSource timeSource)