blob: 76f1e570aceea49799153b2f7b929e2677252a60 [file] [log] [blame]
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -08001/**
Ray Milkey269ffb92014-04-03 14:43:30 -07002 * Copyright 2011, Big Switch Networks, Inc.
3 * Originally created by David Erickson, Stanford University
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License"); you may
6 * not use this file except in compliance with the License. You may obtain
7 * a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
13 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
14 * License for the specific language governing permissions and limitations
15 * under the License.
16 **/
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080017
18package net.floodlightcontroller.util;
19
Yuta HIGUCHIafadeda2014-07-24 17:11:07 -070020import java.util.Set;
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080021import java.util.concurrent.ConcurrentMap;
22
Jonathan Harta99ec672014-04-03 11:30:34 -070023import com.googlecode.concurrentlinkedhashmap.ConcurrentLinkedHashMap;
24
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080025/**
26 * The key is any object/hash-code
27 * The value is time-stamp in milliseconds
28 * The time interval denotes the interval for which the entry should remain in the hashmap.
29 * If an entry is present in the Linkedhashmap, it does not mean that it's valid (recently seen)
Ray Milkey269ffb92014-04-03 14:43:30 -070030 *
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080031 * @param <K> Type of the values in this cache
32 */
Ray Milkey269ffb92014-04-03 14:43:30 -070033public class TimedCache<K> {
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080034 private final long timeoutInterval; //specified in milliseconds.
Ray Milkey269ffb92014-04-03 14:43:30 -070035 private ConcurrentMap<K, Long> cache;
36
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080037 /**
Ray Milkey269ffb92014-04-03 14:43:30 -070038 * @param capacity the maximum number of entries in the cache before the
39 * oldest entry is evicted.
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080040 * @param timeToLive specified in milliseconds
41 */
Ray Milkey269ffb92014-04-03 14:43:30 -070042 public TimedCache(int capacity, int timeToLive) {
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080043 cache = new ConcurrentLinkedHashMap.Builder<K, Long>()
Ray Milkey269ffb92014-04-03 14:43:30 -070044 .maximumWeightedCapacity(capacity)
45 .build();
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080046 this.timeoutInterval = timeToLive;
47 }
Ray Milkey269ffb92014-04-03 14:43:30 -070048
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080049 public long getTimeoutInterval() {
50 return this.timeoutInterval;
51 }
Ray Milkey269ffb92014-04-03 14:43:30 -070052
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080053 /**
54 * Always try to update the cache and set the last-seen value for this key.
Ray Milkey269ffb92014-04-03 14:43:30 -070055 * <p/>
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080056 * Return true, if a valid existing field was updated, else return false.
57 * (note: if multiple threads update simultaneously, one of them will succeed,
Ray Milkey269ffb92014-04-03 14:43:30 -070058 * other wills return false)
59 *
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080060 * @param key
61 * @return boolean
62 */
Ray Milkey269ffb92014-04-03 14:43:30 -070063 public boolean update(K key) {
Yuta HIGUCHIafadeda2014-07-24 17:11:07 -070064 long curr = System.currentTimeMillis();
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080065 Long prev = cache.putIfAbsent(key, curr);
Ray Milkey269ffb92014-04-03 14:43:30 -070066
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080067 if (prev == null) {
Ray Milkey269ffb92014-04-03 14:43:30 -070068 return false;
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080069 }
70
71 if (curr - prev > this.timeoutInterval) {
72 if (cache.replace(key, prev, curr)) {
Ray Milkey269ffb92014-04-03 14:43:30 -070073 return false;
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080074 }
75 }
Ray Milkey269ffb92014-04-03 14:43:30 -070076
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080077 return true;
78 }
Yuta HIGUCHIafadeda2014-07-24 17:11:07 -070079
80 /**
81 * Gets all the cached entries.
82 * <p/>
83 * Modification to the returned set will be reflected to the cache.
84 *
85 * @return cached entries
86 */
87 Set<K> getCachedEntries() {
88 return cache.keySet();
89 }
Umesh Krishnaswamy345ee992012-12-13 20:29:48 -080090}