Fix sonar complains
[bgpcep.git] / pcep / impl / src / main / java / org / opendaylight / protocol / pcep / impl / PCEPPeerRegistry.java
1 /*
2  * Copyright (c) 2015 Cisco Systems, Inc. and others.  All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8
9 package org.opendaylight.protocol.pcep.impl;
10
11 import com.google.common.base.Optional;
12 import com.google.common.cache.Cache;
13 import com.google.common.cache.CacheBuilder;
14 import java.util.Arrays;
15 import java.util.HashMap;
16 import java.util.Map;
17 import java.util.concurrent.ExecutionException;
18 import java.util.concurrent.TimeUnit;
19 import javax.annotation.concurrent.GuardedBy;
20 import javax.annotation.concurrent.ThreadSafe;
21
22 @ThreadSafe
23 final class PCEPPeerRegistry {
24
25     /**
26      * The maximum lifetime for which we should hold on to a session ID before assuming it is okay to reuse it.
27      */
28     private static final long ID_CACHE_SECONDS = 3 * 3600;
29
30     /**
31      * The total amount of time we should remember a peer having been present, unless some other pressure forces us to
32      * forget about it due to {@link PEER_CACHE_SIZE}.
33      */
34     private static final long PEER_CACHE_SECONDS = 24 * 3600;
35
36     /**
37      * Maximum total number of peers we keep track of. Combined with {@link PEER_CACHE_SECONDS}, this defines how many
38      * peers we can see turn around.
39      */
40     private static final long PEER_CACHE_SIZE = 1024;
41
42     @GuardedBy("this")
43     private final Cache<ByteArrayWrapper, PeerRecord> formerClients = CacheBuilder.newBuilder().expireAfterAccess(PEER_CACHE_SECONDS,
44             TimeUnit.SECONDS).maximumSize(PEER_CACHE_SIZE).build();
45
46     @GuardedBy("this")
47     private final Map<ByteArrayWrapper, SessionReference> sessions = new HashMap<>();
48
49     protected interface SessionReference extends AutoCloseable {
50         Short getSessionId();
51     }
52
53
54     protected synchronized Optional<SessionReference> getSessionReference(final byte[] clientAddress) {
55         final SessionReference sessionReference = this.sessions.get(new ByteArrayWrapper(clientAddress));
56         if (sessionReference != null) {
57             return Optional.of(sessionReference);
58         }
59         return Optional.absent();
60     }
61
62     protected synchronized Optional<SessionReference> removeSessionReference(final byte[] clientAddress) {
63         final SessionReference sessionReference = this.sessions.remove(new ByteArrayWrapper(clientAddress));
64         if (sessionReference != null) {
65             return Optional.of(sessionReference);
66         }
67         return Optional.absent();
68     }
69
70     protected synchronized void putSessionReference(final byte[] clientAddress, final SessionReference sessionReference) {
71         this.sessions.put(new ByteArrayWrapper(clientAddress), sessionReference);
72     }
73
74     protected synchronized Short nextSession(final byte[] clientAddress) throws ExecutionException {
75         final PeerRecord peer = this.formerClients.get(new ByteArrayWrapper(clientAddress), () -> new PeerRecord(ID_CACHE_SECONDS, null));
76
77         return peer.allocId();
78     }
79
80     protected synchronized void releaseSession(final byte[] clientAddress, final short sessionId) throws ExecutionException {
81         this.formerClients.get(new ByteArrayWrapper(clientAddress), () -> new PeerRecord(ID_CACHE_SECONDS, sessionId));
82     }
83
84     private static final class ByteArrayWrapper {
85
86         private final byte[] byteArray;
87
88         public ByteArrayWrapper(final byte[] byteArray) {
89             this.byteArray = byteArray == null ? null : byteArray.clone();
90         }
91
92         @Override
93         public int hashCode() {
94             return Arrays.hashCode(this.byteArray);
95         }
96
97         @Override
98         public boolean equals(final Object obj) {
99             if (this == obj) {
100                 return true;
101             }
102             if (!(obj instanceof ByteArrayWrapper)) {
103                 return false;
104             }
105             return Arrays.equals(this.byteArray, ((ByteArrayWrapper) obj).byteArray);
106         }
107     }
108 }