proxygen
AsyncFizzServer-inl.h
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2018-present, Facebook, Inc.
3  * All rights reserved.
4  *
5  * This source code is licensed under the BSD-style license found in the
6  * LICENSE file in the root directory of this source tree.
7  */
8 
10 
11 namespace fizz {
12 namespace server {
13 
14 template <typename SM>
17  const std::shared_ptr<FizzServerContext>& fizzContext,
18  const std::shared_ptr<ServerExtensions>& extensions)
19  : AsyncFizzBase(std::move(socket)),
20  fizzContext_(fizzContext),
21  extensions_(extensions),
22  visitor_(*this),
23  fizzServer_(state_, transportReadBuf_, visitor_, this) {}
24 
25 template <typename SM>
27  handshakeCallback_ = callback;
28 
29  fizzServer_.accept(transport_->getEventBase(), fizzContext_, extensions_);
31 }
32 
33 template <typename SM>
35  return !error() && transport_->good();
36 }
37 
38 template <typename SM>
40  return transport_->readable();
41 }
42 
43 template <typename SM>
45  return handshakeCallback_ || transport_->connecting();
46 }
47 
48 template <typename SM>
50  return transport_->error() || fizzServer_.inErrorState();
51 }
52 
53 template <typename SM>
55  return !fizzServer_.actionProcessing() && AsyncFizzBase::isDetachable();
56 }
57 
58 template <typename SM>
60  state_.executor() = evb;
62 }
63 
64 template <typename SM>
66  auto cert = getPeerCertificate();
67  if (cert) {
68  return cert->getX509();
69  } else {
70  return nullptr;
71  }
72 }
73 
74 template <typename SM>
76  auto cert = getSelfCertificate();
77  if (cert) {
78  return cert->getX509().get();
79  } else {
80  return nullptr;
81  }
82 }
83 
84 template <typename SM>
86  return getState().clientCert().get();
87 }
88 
89 template <typename SM>
91  return getState().serverCert().get();
92 }
93 
94 template <typename SM>
96  // Server always provides replay protection.
97  return true;
98 }
99 
100 template <typename SM>
103  LOG(FATAL) << "setReplaySafetyCallback() called on replay safe transport";
104 }
105 
106 template <typename SM>
108  if (getState().alpn()) {
109  return *getState().alpn();
110  } else {
111  return "";
112  }
113 }
114 
115 template <typename SM>
117  if (transport_->good()) {
118  fizzServer_.appClose();
119  } else {
120  DelayedDestruction::DestructorGuard dg(this);
122  folly::AsyncSocketException::END_OF_FILE, "socket closed locally");
123  deliverAllErrors(ase, false);
124  transport_->close();
125  }
126 }
127 
128 template <typename SM>
130  DelayedDestruction::DestructorGuard dg(this);
131  if (transport_->good()) {
132  fizzServer_.appClose();
133  }
135  folly::AsyncSocketException::END_OF_FILE, "socket closed locally");
136  deliverAllErrors(ase, false);
137  transport_->closeWithReset();
138 }
139 
140 template <typename SM>
142  DelayedDestruction::DestructorGuard dg(this);
143  if (transport_->good()) {
144  fizzServer_.appClose();
145  }
147  folly::AsyncSocketException::END_OF_FILE, "socket closed locally");
148  deliverAllErrors(ase, false);
149  transport_->closeNow();
150 }
151 
152 template <typename SM>
154  return getState().cipher();
155 }
156 
157 template <typename SM>
158 std::vector<SignatureScheme> AsyncFizzServerT<SM>::getSupportedSigSchemes()
159  const {
161 }
162 
163 template <typename SM>
166  const Buf& context,
167  uint16_t length) const {
168  return fizzServer_.getEkm(label, context, length);
169 }
170 
171 template <typename SM>
174  const Buf& context,
175  uint16_t length) const {
176  return fizzServer_.getEarlyEkm(label, context, length);
177 }
178 
179 template <typename SM>
182  std::unique_ptr<folly::IOBuf>&& buf,
184  if (error()) {
185  if (callback) {
186  callback->writeErr(
187  0,
190  "fizz app write in error state"));
191  }
192  return;
193  }
194 
195  AppWrite write;
196  write.callback = callback;
197  write.data = std::move(buf);
198  write.flags = flags;
199  fizzServer_.appWrite(std::move(write));
200 }
201 
202 template <typename SM>
204  const folly::AsyncSocketException& ex) {
205  DelayedDestruction::DestructorGuard dg(this);
206  deliverAllErrors(ex);
207 }
208 
209 template <typename SM>
211  fizzServer_.newTransportData();
212 }
213 
214 template <typename SM>
216  const folly::AsyncSocketException& ex,
217  bool closeTransport) {
219  fizzServer_.moveToErrorState(ex);
220  deliverError(ex, closeTransport);
221 }
222 
223 template <typename SM>
225  if (handshakeCallback_) {
226  auto callback = handshakeCallback_;
227  handshakeCallback_ = nullptr;
228  callback->fizzHandshakeError(this, std::move(ex));
229  }
230 }
231 
232 template <typename SM>
234  server_.deliverAppData(std::move(data.data));
235 }
236 
237 template <typename SM>
239  DCHECK(!data.contents.empty());
240  Buf allData = std::move(data.contents.front().data);
241  for (size_t i = 1; i < data.contents.size(); ++i) {
242  allData->prependChain(std::move(data.contents[i].data));
243  }
244  server_.transport_->writeChain(data.callback, std::move(allData), data.flags);
245 }
246 
247 template <typename SM>
250  if (server_.handshakeCallback_) {
251  auto callback = server_.handshakeCallback_;
252  server_.handshakeCallback_ = nullptr;
253  callback->fizzHandshakeSuccess(&server_);
254  }
255 }
256 
257 template <typename SM>
260  if (server_.handshakeCallback_) {
261  auto callback = server_.handshakeCallback_;
262  server_.handshakeCallback_ = nullptr;
263  callback->fizzHandshakeSuccess(&server_);
264  }
265 }
266 
267 template <typename SM>
271  server_.deliverHandshakeError(std::move(error.error));
272  server_.deliverAllErrors(ase);
273 }
274 
275 template <typename SM>
277  server_.fizzServer_.waitForData();
278 
279  if (server_.handshakeCallback_) {
280  // Make sure that the read callback is installed.
281  server_.startTransportReads();
282  }
283 }
284 
285 template <typename SM>
287  mutator(server_.state_);
288 }
289 
290 template <typename SM>
292  AttemptVersionFallback& fallback) {
293  if (!server_.handshakeCallback_) {
294  VLOG(2) << "fizz fallback without callback";
295  return;
296  }
297  auto callback = server_.handshakeCallback_;
298  server_.handshakeCallback_ = nullptr;
299  if (!server_.transportReadBuf_.empty()) {
300  fallback.clientHello->prependChain(server_.transportReadBuf_.move());
301  }
302  callback->fizzHandshakeAttemptFallback(std::move(fallback.clientHello));
303 }
304 } // namespace server
305 } // namespace fizz
const Cert * getPeerCertificate() const override
folly::fbstring what() const
const auto & getSupportedSigSchemes() const
folly::WriteFlags flags
Definition: Actions.h:43
virtual void deliverError(const folly::AsyncSocketException &ex, bool closeTransport=true)
flags
Definition: http_parser.h:127
HandshakeCallback * handshakeCallback_
const X509 * getSelfCert() const override
std::unique_ptr< X509, X509Deleter > X509UniquePtr
FizzServer< ActionMoveVisitor, SM > fizzServer_
void deliverAllErrors(const folly::AsyncSocketException &ex, bool closeTransport=true)
void setReplaySafetyCallback(folly::AsyncTransport::ReplaySafetyCallback *callback) override
context
Definition: CMakeCache.txt:563
constexpr detail::Map< Move > move
Definition: Base-inl.h:2567
folly::small_vector< TLSContent, 4 > contents
Definition: Actions.h:41
const Cert * getSelfCertificate() const override
StringPiece alpn
STL namespace.
AsyncFizzServerT(folly::AsyncTransportWrapper::UniquePtr socket, const std::shared_ptr< FizzServerContext > &fizzContext, const std::shared_ptr< ServerExtensions > &extensions=nullptr)
void writeAppData(folly::AsyncTransportWrapper::WriteCallback *callback, std::unique_ptr< folly::IOBuf > &&buf, folly::WriteFlags flags=folly::WriteFlags::NONE) override
folly::ssl::X509UniquePtr getPeerCert() const override
requires E e noexcept(noexcept(s.error(std::move(e))))
virtual Buf getEarlyEkm(folly::StringPiece label, const Buf &hashedContext, uint16_t length) const
void attachEventBase(folly::EventBase *eventBase) override
virtual void accept(HandshakeCallback *callback)
const State & getState() const
std::vector< SignatureScheme > getSupportedSigSchemes() const override
std::unique_ptr< AsyncTransportWrapper, Destructor > UniquePtr
folly::Executor * executor() const
Definition: State.h:76
const std::shared_ptr< const Cert > & clientCert() const
Definition: State.h:97
folly::Optional< CipherSuite > getCipher() const override
void write(folly::AsyncTransportWrapper::WriteCallback *callback, const void *buf, size_t bytes, folly::WriteFlags flags=folly::WriteFlags::NONE) override
std::basic_string< E, T, A > toStdString() const
Definition: FBString.h:1227
folly::exception_wrapper error
Definition: Actions.h:50
Definition: Actions.h:16
bool isDetachable() const override
std::string getApplicationProtocol() const noexceptoverride
NetworkSocket socket(int af, int type, int protocol)
Definition: NetOps.cpp:412
void attachEventBase(folly::EventBase *evb) override
virtual void startTransportReads()
folly::AsyncTransportWrapper::WriteCallback * callback
Definition: Actions.h:37
std::shared_ptr< ServerExtensions > extensions_
const FizzServerContext * context() const
Definition: State.h:83
const char * string
Definition: Conv.cpp:212
std::unique_ptr< folly::IOBuf > Buf
Definition: Types.h:22
const
Definition: upload.py:398
bool connecting() const override
virtual void writeErr(size_t bytesWritten, const AsyncSocketException &ex) noexcept=0
std::shared_ptr< FizzServerContext > fizzContext_
bool isReplaySafe() const override
const folly::Optional< std::string > & alpn() const
Definition: State.h:168
bool isDetachable() const override
static constexpr uint64_t data[1]
Definition: Fingerprint.cpp:43
std::shared_ptr< const Cert > serverCert() const
Definition: State.h:90
folly::Optional< CipherSuite > cipher() const
Definition: State.h:111
std::unique_ptr< folly::IOBuf > data
Definition: Params.h:54
virtual void fizzHandshakeError(AsyncFizzServerT *transport, folly::exception_wrapper ex) noexcept=0
std::unique_ptr< folly::IOBuf > clientHello
Definition: Actions.h:27
void deliverHandshakeError(folly::exception_wrapper ex)
void transportError(const folly::AsyncSocketException &ex) override
StringPiece label
std::unique_ptr< folly::IOBuf > data
Definition: Actions.h:23
folly::WriteFlags flags
Definition: Params.h:55
folly::AsyncTransportWrapper::WriteCallback * callback
Definition: Params.h:53
Buf getEkm(folly::StringPiece label, const Buf &hashedContext, uint16_t length) const override