proxygen
SSLSessionCacheManager.h
Go to the documentation of this file.
1 /*
2  * Copyright 2017-present Facebook, Inc.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 #pragma once
17 
19 #include <wangle/ssl/SSLStats.h>
20 
22 #include <mutex>
23 #include <folly/hash/Hash.h>
25 
26 namespace wangle {
27 
28 class SSLStats;
29 
34 
38 class LocalSSLSessionCache: private boost::noncopyable {
39  public:
40  LocalSSLSessionCache(uint32_t maxCacheSize, uint32_t cacheCullSize);
41 
43  std::lock_guard<std::mutex> g(lock);
44  // EvictingCacheMap dtor doesn't free values
46  }
47 
48  SSLSessionCacheMap sessionCache;
51 
52  private:
53 
54  void pruneSessionCallback(const std::string& sessionId,
55  SSL_SESSION* session);
56 };
57 
63 class ShardedLocalSSLSessionCache : private boost::noncopyable {
64  public:
65  ShardedLocalSSLSessionCache(uint32_t n_buckets, uint32_t maxCacheSize,
66  uint32_t cacheCullSize);
67 
68  SSL_SESSION* lookupSession(const std::string& sessionId);
69 
70  void storeSession(const std::string& sessionId, SSL_SESSION* session,
71  SSLStats* stats);
72 
73  void removeSession(const std::string& sessionId);
74 
75  size_t hash(const std::string& key) {
76  return folly::Hash()(key) % caches_.size();
77  }
78 
79  std::vector< std::unique_ptr<LocalSSLSessionCache> > caches_;
80 };
81 
82 /* A socket/DestructorGuard pair */
83 typedef std::pair<folly::AsyncSSLSocket *,
84  std::unique_ptr<folly::DelayedDestruction::DestructorGuard>>
86 
93 struct PendingLookup {
95  SSL_SESSION* session;
96  std::list<AttachedLookup> waiters;
97 
99  request_in_progress = true;
100  session = nullptr;
101  }
102 };
103 
104 /* Maps SSL session id to a PendingLookup structure */
105 typedef std::map<std::string, PendingLookup> PendingLookupMap;
106 
136 class SSLSessionCacheManager : private boost::noncopyable {
137  public:
145  uint32_t maxCacheSize,
146  uint32_t cacheCullSize,
147  folly::SSLContext* ctx,
148  const std::string& context,
149  SSLStats* stats,
150  const std::shared_ptr<SSLCacheProvider>& externalCache);
151 
152  virtual ~SSLSessionCacheManager();
153 
158  static void shutdown();
159 
165  void onGetSuccess(SSLCacheProvider::CacheContext* cacheCtx,
166  const std::string& value);
167 
174  void onGetSuccess(SSLCacheProvider::CacheContext* cacheCtx,
175  std::unique_ptr<folly::IOBuf> valueBuf);
176 
183  void onGetFailure(SSLCacheProvider::CacheContext* cacheCtx);
184 
185  private:
186 
188  std::shared_ptr<ShardedLocalSSLSessionCache> localCache_;
189  PendingLookupMap pendingLookups_;
190  SSLStats* stats_{nullptr};
191  std::shared_ptr<SSLCacheProvider> externalCache_;
192 
196  int newSession(SSL* ssl, SSL_SESSION* session);
197 
203  void removeSession(SSL_CTX* ctx, SSL_SESSION* session);
204 
210  SSL_SESSION* getSession(SSL* ssl, unsigned char* session_id,
211  int id_len, int* copyflag);
212 
219  void restoreSession(SSLCacheProvider::CacheContext* cacheCtx,
220  const uint8_t* data,
221  size_t length);
222 
226  bool storeCacheRecord(const std::string& sessionId, SSL_SESSION* session);
227 
231  bool lookupCacheRecord(const std::string& sessionId,
232  folly::AsyncSSLSocket* sslSock);
233 
237  void restartSSLAccept(const SSLCacheProvider::CacheContext* cacheCtx);
238 
242  static std::shared_ptr<ShardedLocalSSLSessionCache> getLocalCache(
243  uint32_t maxCacheSize, uint32_t cacheCullSize);
244 
249  static int newSessionCallback(SSL* ssl, SSL_SESSION* session);
250  static void removeSessionCallback(SSL_CTX* ctx, SSL_SESSION* session);
251 
252 #if FOLLY_OPENSSL_IS_110
253  using session_callback_arg_session_id_t = const unsigned char*;
254 #else
255  using session_callback_arg_session_id_t = unsigned char*;
256 #endif
257 
258  static SSL_SESSION* getSessionCallback(
259  SSL* ssl,
261  int id_len,
262  int* copyflag);
263 
265  static std::shared_ptr<ShardedLocalSSLSessionCache> sCache_;
267 };
268 
269 } // namespace wangle
std::pair< folly::AsyncSSLSocket *, std::unique_ptr< folly::DelayedDestruction::DestructorGuard > > AttachedLookup
std::map< std::string, PendingLookup > PendingLookupMap
std::vector< std::unique_ptr< LocalSSLSessionCache > > caches_
context
Definition: CMakeCache.txt:563
void pruneSessionCallback(const std::string &sessionId, SSL_SESSION *session)
std::list< AttachedLookup > waiters
LocalSSLSessionCache(uint32_t maxCacheSize, uint32_t cacheCullSize)
static std::shared_ptr< ShardedLocalSSLSessionCache > sCache_
void shutdown(Counter &)
static const char *const value
Definition: Conv.cpp:50
folly::EvictingCacheMap< std::string, SSL_SESSION * > SSLSessionCacheMap
std::shared_ptr< ShardedLocalSSLSessionCache > localCache_
std::mutex mutex
const char * string
Definition: Conv.cpp:212
g_t g(f_t)
std::shared_ptr< SSLCacheProvider > externalCache_
void clear(PruneHookCall pruneHook=nullptr)
static constexpr uint64_t data[1]
Definition: Fingerprint.cpp:43
size_t hash(const std::string &key)