Botan  2.18.1
Crypto and TLS for C++11
tls_channel.cpp
Go to the documentation of this file.
1 /*
2 * TLS Channels
3 * (C) 2011,2012,2014,2015,2016 Jack Lloyd
4 * 2016 Matthias Gierlings
5 *
6 * Botan is released under the Simplified BSD License (see license.txt)
7 */
8 
9 #include <botan/tls_channel.h>
10 #include <botan/tls_policy.h>
11 #include <botan/tls_messages.h>
12 #include <botan/kdf.h>
13 #include <botan/internal/tls_handshake_state.h>
14 #include <botan/internal/tls_record.h>
15 #include <botan/internal/tls_seq_numbers.h>
16 #include <botan/internal/rounding.h>
17 #include <botan/internal/stl_util.h>
18 #include <botan/loadstor.h>
19 
20 namespace Botan {
21 
22 namespace TLS {
23 
24 size_t TLS::Channel::IO_BUF_DEFAULT_SIZE = 10*1024;
25 
27  Session_Manager& session_manager,
29  const Policy& policy,
30  bool is_server,
31  bool is_datagram,
32  size_t reserved_io_buffer_size) :
33  m_is_server(is_server),
34  m_is_datagram(is_datagram),
35  m_callbacks(callbacks),
36  m_session_manager(session_manager),
37  m_policy(policy),
38  m_rng(rng),
39  m_has_been_closed(false)
40  {
41  init(reserved_io_buffer_size);
42  }
43 
45  data_cb app_data_cb,
46  alert_cb recv_alert_cb,
47  handshake_cb hs_cb,
48  handshake_msg_cb hs_msg_cb,
49  Session_Manager& session_manager,
51  const Policy& policy,
52  bool is_server,
53  bool is_datagram,
54  size_t io_buf_sz) :
55  m_is_server(is_server),
56  m_is_datagram(is_datagram),
57  m_compat_callbacks(new Compat_Callbacks(
58  /*
59  this Channel constructor is also deprecated so its ok that it
60  relies on a deprecated API
61  */
62  Compat_Callbacks::SILENCE_DEPRECATION_WARNING::PLEASE,
63  out, app_data_cb, recv_alert_cb, hs_cb, hs_msg_cb)),
64  m_callbacks(*m_compat_callbacks.get()),
65  m_session_manager(session_manager),
66  m_policy(policy),
67  m_rng(rng),
68  m_has_been_closed(false)
69  {
70  init(io_buf_sz);
71  }
72 
73 void Channel::init(size_t io_buf_sz)
74  {
75  /* epoch 0 is plaintext, thus null cipher state */
76  m_write_cipher_states[0] = nullptr;
77  m_read_cipher_states[0] = nullptr;
78 
79  m_writebuf.reserve(io_buf_sz);
80  m_readbuf.reserve(io_buf_sz);
81  }
82 
83 void Channel::reset_state()
84  {
85  m_active_state.reset();
86  m_pending_state.reset();
87  m_readbuf.clear();
88  m_write_cipher_states.clear();
89  m_read_cipher_states.clear();
90  }
91 
93  {
94  // This operation only makes sense for DTLS
95  BOTAN_ASSERT_NOMSG(m_is_datagram);
96  m_active_state.reset();
97  m_read_cipher_states.clear();
98  m_write_cipher_states.clear();
99 
100  m_write_cipher_states[0] = nullptr;
101  m_read_cipher_states[0] = nullptr;
102 
103  if(m_sequence_numbers)
104  m_sequence_numbers->reset();
105  }
106 
108  {
109  // So unique_ptr destructors run correctly
110  }
111 
112 Connection_Sequence_Numbers& Channel::sequence_numbers() const
113  {
114  BOTAN_ASSERT(m_sequence_numbers, "Have a sequence numbers object");
115  return *m_sequence_numbers;
116  }
117 
118 std::shared_ptr<Connection_Cipher_State> Channel::read_cipher_state_epoch(uint16_t epoch) const
119  {
120  auto i = m_read_cipher_states.find(epoch);
121  if(i == m_read_cipher_states.end())
122  throw Internal_Error("TLS::Channel No read cipherstate for epoch " + std::to_string(epoch));
123  return i->second;
124  }
125 
126 std::shared_ptr<Connection_Cipher_State> Channel::write_cipher_state_epoch(uint16_t epoch) const
127  {
128  auto i = m_write_cipher_states.find(epoch);
129  if(i == m_write_cipher_states.end())
130  throw Internal_Error("TLS::Channel No write cipherstate for epoch " + std::to_string(epoch));
131  return i->second;
132  }
133 
134 std::vector<X509_Certificate> Channel::peer_cert_chain() const
135  {
136  if(auto active = active_state())
137  return get_peer_cert_chain(*active);
138  return std::vector<X509_Certificate>();
139  }
140 
141 bool Channel::save_session(const Session& session)
142  {
143  return callbacks().tls_session_established(session);
144  }
145 
147  {
148  if(pending_state())
149  throw Internal_Error("create_handshake_state called during handshake");
150 
151  if(auto active = active_state())
152  {
153  Protocol_Version active_version = active->version();
154 
155  if(active_version.is_datagram_protocol() != version.is_datagram_protocol())
156  {
158  "Active state using version " + active_version.to_string() +
159  " cannot change to " + version.to_string() + " in pending");
160  }
161  }
162 
163  if(!m_sequence_numbers)
164  {
165  if(version.is_datagram_protocol())
166  m_sequence_numbers.reset(new Datagram_Sequence_Numbers);
167  else
168  m_sequence_numbers.reset(new Stream_Sequence_Numbers);
169  }
170 
171  using namespace std::placeholders;
172 
173  std::unique_ptr<Handshake_IO> io;
174  if(version.is_datagram_protocol())
175  {
176  io.reset(new Datagram_Handshake_IO(
177  std::bind(&Channel::send_record_under_epoch, this, _1, _2, _3),
178  sequence_numbers(),
179  static_cast<uint16_t>(m_policy.dtls_default_mtu()),
180  m_policy.dtls_initial_timeout(),
181  m_policy.dtls_maximum_timeout()));
182  }
183  else
184  {
185  io.reset(new Stream_Handshake_IO(std::bind(&Channel::send_record, this, _1, _2)));
186  }
187 
188  m_pending_state.reset(new_handshake_state(io.release()));
189 
190  if(auto active = active_state())
191  m_pending_state->set_version(active->version());
192 
193  return *m_pending_state.get();
194  }
195 
197  {
198  if(m_pending_state)
199  return m_pending_state->handshake_io().timeout_check();
200 
201  //FIXME: scan cipher suites and remove epochs older than 2*MSL
202  return false;
203  }
204 
205 void Channel::renegotiate(bool force_full_renegotiation)
206  {
207  if(pending_state()) // currently in handshake?
208  return;
209 
210  if(auto active = active_state())
211  {
212  if(force_full_renegotiation == false)
213  force_full_renegotiation = !policy().allow_resumption_for_renegotiation();
214 
215  initiate_handshake(create_handshake_state(active->version()),
216  force_full_renegotiation);
217  }
218  else
219  throw Invalid_State("Cannot renegotiate on inactive connection");
220  }
221 
223  {
224  auto pending = pending_state();
225 
226  BOTAN_ASSERT(pending && pending->server_hello(),
227  "Have received server hello");
228 
229  if(pending->server_hello()->compression_method() != 0)
230  throw Internal_Error("Negotiated unknown compression algorithm");
231 
232  sequence_numbers().new_read_cipher_state();
233 
234  const uint16_t epoch = sequence_numbers().current_read_epoch();
235 
236  BOTAN_ASSERT(m_read_cipher_states.count(epoch) == 0,
237  "No read cipher state currently set for next epoch");
238 
239  // flip side as we are reading
240  std::shared_ptr<Connection_Cipher_State> read_state(
241  new Connection_Cipher_State(pending->version(),
242  (side == CLIENT) ? SERVER : CLIENT,
243  false,
244  pending->ciphersuite(),
245  pending->session_keys(),
246  pending->server_hello()->supports_encrypt_then_mac()));
247 
248  m_read_cipher_states[epoch] = read_state;
249  }
250 
252  {
253  auto pending = pending_state();
254 
255  BOTAN_ASSERT(pending && pending->server_hello(),
256  "Have received server hello");
257 
258  if(pending->server_hello()->compression_method() != 0)
259  throw Internal_Error("Negotiated unknown compression algorithm");
260 
261  sequence_numbers().new_write_cipher_state();
262 
263  const uint16_t epoch = sequence_numbers().current_write_epoch();
264 
265  BOTAN_ASSERT(m_write_cipher_states.count(epoch) == 0,
266  "No write cipher state currently set for next epoch");
267 
268  std::shared_ptr<Connection_Cipher_State> write_state(
269  new Connection_Cipher_State(pending->version(),
270  side,
271  true,
272  pending->ciphersuite(),
273  pending->session_keys(),
274  pending->server_hello()->supports_encrypt_then_mac()));
275 
276  m_write_cipher_states[epoch] = write_state;
277  }
278 
279 bool Channel::is_active() const
280  {
281  if(is_closed())
282  return false;
283  return (active_state() != nullptr);
284  }
285 
286 bool Channel::is_closed() const
287  {
288  return m_has_been_closed;
289  }
290 
292  {
293  std::swap(m_active_state, m_pending_state);
294  m_pending_state.reset();
295 
296  if(!m_active_state->version().is_datagram_protocol())
297  {
298  // TLS is easy just remove all but the current state
299  const uint16_t current_epoch = sequence_numbers().current_write_epoch();
300 
301  const auto not_current_epoch =
302  [current_epoch](uint16_t epoch) { return (epoch != current_epoch); };
303 
304  map_remove_if(not_current_epoch, m_write_cipher_states);
305  map_remove_if(not_current_epoch, m_read_cipher_states);
306  }
307 
309  }
310 
311 size_t Channel::received_data(const std::vector<uint8_t>& buf)
312  {
313  return this->received_data(buf.data(), buf.size());
314  }
315 
316 size_t Channel::received_data(const uint8_t input[], size_t input_size)
317  {
318  const bool allow_epoch0_restart = m_is_datagram && m_is_server && policy().allow_dtls_epoch0_restart();
319 
320  try
321  {
322  while(input_size)
323  {
324  size_t consumed = 0;
325 
326  auto get_epoch = [this](uint16_t epoch) { return read_cipher_state_epoch(epoch); };
327 
328  const Record_Header record =
329  read_record(m_is_datagram,
330  m_readbuf,
331  input,
332  input_size,
333  consumed,
334  m_record_buf,
335  m_sequence_numbers.get(),
336  get_epoch,
337  allow_epoch0_restart);
338 
339  const size_t needed = record.needed();
340 
341  BOTAN_ASSERT(consumed > 0, "Got to eat something");
342 
343  BOTAN_ASSERT(consumed <= input_size,
344  "Record reader consumed sane amount");
345 
346  input += consumed;
347  input_size -= consumed;
348 
349  BOTAN_ASSERT(input_size == 0 || needed == 0,
350  "Got a full record or consumed all input");
351 
352  if(input_size == 0 && needed != 0)
353  return needed; // need more data to complete record
354 
355  // Ignore invalid records in DTLS
356  if(m_is_datagram && record.type() == NO_RECORD)
357  {
358  return 0;
359  }
360 
361  if(m_record_buf.size() > MAX_PLAINTEXT_SIZE)
363  "TLS plaintext record is larger than allowed maximum");
364 
365 
366  const bool epoch0_restart = m_is_datagram && record.epoch() == 0 && active_state();
367  BOTAN_ASSERT_IMPLICATION(epoch0_restart, allow_epoch0_restart, "Allowed state");
368 
369  const bool initial_record = epoch0_restart || (!pending_state() && !active_state());
370 
371  if(record.type() != ALERT)
372  {
373  if(initial_record)
374  {
375  // For initial records just check for basic sanity
376  if(record.version().major_version() != 3 &&
377  record.version().major_version() != 0xFE)
378  {
380  "Received unexpected record version in initial record");
381  }
382  }
383  else if(auto pending = pending_state())
384  {
385  if(pending->server_hello() != nullptr && record.version() != pending->version())
386  {
387  if(record.version() != pending->version())
388  {
390  "Received unexpected record version");
391  }
392  }
393  }
394  else if(auto active = active_state())
395  {
396  if(record.version() != active->version())
397  {
399  "Received unexpected record version");
400  }
401  }
402  }
403 
404  if(record.type() == HANDSHAKE || record.type() == CHANGE_CIPHER_SPEC)
405  {
406  if(m_has_been_closed)
407  throw TLS_Exception(Alert::UNEXPECTED_MESSAGE, "Received handshake data after connection closure");
408  process_handshake_ccs(m_record_buf, record.sequence(), record.type(), record.version(), epoch0_restart);
409  }
410  else if(record.type() == APPLICATION_DATA)
411  {
412  if(m_has_been_closed)
413  throw TLS_Exception(Alert::UNEXPECTED_MESSAGE, "Received application data after connection closure");
414  if(pending_state() != nullptr)
415  throw TLS_Exception(Alert::UNEXPECTED_MESSAGE, "Can't interleave application and handshake data");
416  process_application_data(record.sequence(), m_record_buf);
417  }
418  else if(record.type() == ALERT)
419  {
420  process_alert(m_record_buf);
421  }
422  else if(record.type() != NO_RECORD)
423  throw Unexpected_Message("Unexpected record type " +
424  std::to_string(record.type()) +
425  " from counterparty");
426  }
427 
428  return 0; // on a record boundary
429  }
430  catch(TLS_Exception& e)
431  {
432  send_fatal_alert(e.type());
433  throw;
434  }
436  {
438  throw;
439  }
440  catch(Decoding_Error&)
441  {
443  throw;
444  }
445  catch(...)
446  {
448  throw;
449  }
450  }
451 
452 void Channel::process_handshake_ccs(const secure_vector<uint8_t>& record,
453  uint64_t record_sequence,
454  Record_Type record_type,
455  Protocol_Version record_version,
456  bool epoch0_restart)
457  {
458  if(!m_pending_state)
459  {
460  // No pending handshake, possibly new:
461  if(record_version.is_datagram_protocol() && !epoch0_restart)
462  {
463  if(m_sequence_numbers)
464  {
465  /*
466  * Might be a peer retransmit under epoch - 1 in which
467  * case we must retransmit last flight
468  */
469  sequence_numbers().read_accept(record_sequence);
470 
471  const uint16_t epoch = record_sequence >> 48;
472 
473  if(epoch == sequence_numbers().current_read_epoch())
474  {
475  create_handshake_state(record_version);
476  }
477  else if(epoch == sequence_numbers().current_read_epoch() - 1)
478  {
479  BOTAN_ASSERT(m_active_state, "Have active state here");
480  m_active_state->handshake_io().add_record(record.data(),
481  record.size(),
482  record_type,
483  record_sequence);
484  }
485  }
486  else
487  {
488  create_handshake_state(record_version);
489  }
490  }
491  else
492  {
493  create_handshake_state(record_version);
494  }
495  }
496 
497  // May have been created in above conditional
498  if(m_pending_state)
499  {
500  m_pending_state->handshake_io().add_record(record.data(),
501  record.size(),
502  record_type,
503  record_sequence);
504 
505  while(auto pending = m_pending_state.get())
506  {
507  auto msg = pending->get_next_handshake_msg();
508 
509  if(msg.first == HANDSHAKE_NONE) // no full handshake yet
510  break;
511 
512  process_handshake_msg(active_state(), *pending,
513  msg.first, msg.second, epoch0_restart);
514 
515  if(!m_pending_state)
516  break;
517  }
518  }
519  }
520 
521 void Channel::process_application_data(uint64_t seq_no, const secure_vector<uint8_t>& record)
522  {
523  if(!active_state())
524  throw Unexpected_Message("Application data before handshake done");
525 
526  callbacks().tls_record_received(seq_no, record.data(), record.size());
527  }
528 
529 void Channel::process_alert(const secure_vector<uint8_t>& record)
530  {
531  Alert alert_msg(record);
532 
533  if(alert_msg.type() == Alert::NO_RENEGOTIATION)
534  m_pending_state.reset();
535 
536  callbacks().tls_alert(alert_msg);
537 
538  if(alert_msg.is_fatal())
539  {
540  if(auto active = active_state())
541  m_session_manager.remove_entry(active->server_hello()->session_id());
542  }
543 
544  if(alert_msg.type() == Alert::CLOSE_NOTIFY)
545  send_warning_alert(Alert::CLOSE_NOTIFY); // reply in kind
546 
547  if(alert_msg.type() == Alert::CLOSE_NOTIFY || alert_msg.is_fatal())
548  {
549  m_has_been_closed = true;
550  }
551  }
552 
553 void Channel::write_record(Connection_Cipher_State* cipher_state, uint16_t epoch,
554  uint8_t record_type, const uint8_t input[], size_t length)
555  {
556  BOTAN_ASSERT(m_pending_state || m_active_state, "Some connection state exists");
557 
558  const Protocol_Version record_version =
559  (m_pending_state) ? (m_pending_state->version()) : (m_active_state->version());
560 
561  const uint64_t next_seq = sequence_numbers().next_write_sequence(epoch);
562 
563  if(cipher_state == nullptr)
564  {
565  TLS::write_unencrypted_record(m_writebuf, record_type, record_version, next_seq,
566  input, length);
567  }
568  else
569  {
570  TLS::write_record(m_writebuf, record_type, record_version, next_seq,
571  input, length, *cipher_state, m_rng);
572  }
573 
574  callbacks().tls_emit_data(m_writebuf.data(), m_writebuf.size());
575  }
576 
577 void Channel::send_record_array(uint16_t epoch, uint8_t type, const uint8_t input[], size_t length)
578  {
579  if(length == 0)
580  return;
581 
582  /*
583  * In versions without an explicit IV field (only TLS v1.0 now that
584  * SSLv3 has been removed) send a single byte record first to randomize
585  * the following (implicit) IV of the following record.
586  *
587  * This isn't needed in TLS v1.1 or higher.
588  *
589  * An empty record also works but apparently some implementations do
590  * not like this (https://bugzilla.mozilla.org/show_bug.cgi?id=665814)
591  *
592  * See https://www.openssl.org/~bodo/tls-cbc.txt for background.
593  */
594 
595  auto cipher_state = write_cipher_state_epoch(epoch);
596 
597  if(type == APPLICATION_DATA && m_active_state->version().supports_explicit_cbc_ivs() == false)
598  {
599  while(length)
600  {
601  write_record(cipher_state.get(), epoch, type, input, 1);
602  input += 1;
603  length -= 1;
604 
605  const size_t sending = std::min<size_t>(length, MAX_PLAINTEXT_SIZE);
606  write_record(cipher_state.get(), epoch, type, input, sending);
607 
608  input += sending;
609  length -= sending;
610  }
611  }
612  else
613  {
614  while(length)
615  {
616  const size_t sending = std::min<size_t>(length, MAX_PLAINTEXT_SIZE);
617  write_record(cipher_state.get(), epoch, type, input, sending);
618 
619  input += sending;
620  length -= sending;
621  }
622  }
623  }
624 
625 void Channel::send_record(uint8_t record_type, const std::vector<uint8_t>& record)
626  {
627  send_record_array(sequence_numbers().current_write_epoch(),
628  record_type, record.data(), record.size());
629  }
630 
631 void Channel::send_record_under_epoch(uint16_t epoch, uint8_t record_type,
632  const std::vector<uint8_t>& record)
633  {
634  send_record_array(epoch, record_type, record.data(), record.size());
635  }
636 
637 void Channel::send(const uint8_t buf[], size_t buf_size)
638  {
639  if(!is_active())
640  throw Invalid_State("Data cannot be sent on inactive TLS connection");
641 
642  send_record_array(sequence_numbers().current_write_epoch(),
643  APPLICATION_DATA, buf, buf_size);
644  }
645 
646 void Channel::send(const std::string& string)
647  {
648  this->send(cast_char_ptr_to_uint8(string.data()), string.size());
649  }
650 
651 void Channel::send_alert(const Alert& alert)
652  {
653  if(alert.is_valid() && !is_closed())
654  {
655  try
656  {
657  send_record(ALERT, alert.serialize());
658  }
659  catch(...) { /* swallow it */ }
660  }
661 
662  if(alert.type() == Alert::NO_RENEGOTIATION)
663  m_pending_state.reset();
664 
665  if(alert.is_fatal())
666  {
667  if(auto active = active_state())
668  {
669  m_session_manager.remove_entry(active->server_hello()->session_id());
670  }
671  reset_state();
672  }
673 
674  if(alert.type() == Alert::CLOSE_NOTIFY || alert.is_fatal())
675  {
676  m_has_been_closed = true;
677  }
678  }
679 
681  {
682  const bool secure_renegotiation = client_hello->secure_renegotiation();
683 
684  if(auto active = active_state())
685  {
686  const bool active_sr = active->client_hello()->secure_renegotiation();
687 
688  if(active_sr != secure_renegotiation)
690  "Client changed its mind about secure renegotiation");
691  }
692 
693  if(secure_renegotiation)
694  {
695  const std::vector<uint8_t>& data = client_hello->renegotiation_info();
696 
699  "Client sent bad values for secure renegotiation");
700  }
701  }
702 
704  {
705  const bool secure_renegotiation = server_hello->secure_renegotiation();
706 
707  if(auto active = active_state())
708  {
709  const bool active_sr = active->server_hello()->secure_renegotiation();
710 
711  if(active_sr != secure_renegotiation)
713  "Server changed its mind about secure renegotiation");
714  }
715 
716  if(secure_renegotiation)
717  {
718  const std::vector<uint8_t>& data = server_hello->renegotiation_info();
719 
722  "Server sent bad values for secure renegotiation");
723  }
724  }
725 
727  {
728  if(auto active = active_state())
729  return active->client_finished()->verify_data();
730  return std::vector<uint8_t>();
731  }
732 
734  {
735  if(auto active = active_state())
736  {
737  std::vector<uint8_t> buf = active->client_finished()->verify_data();
738  buf += active->server_finished()->verify_data();
739  return buf;
740  }
741 
742  return std::vector<uint8_t>();
743  }
744 
746  {
747  if(auto active = active_state())
748  return active->server_hello()->secure_renegotiation();
749 
750  if(auto pending = pending_state())
751  if(auto hello = pending->server_hello())
752  return hello->secure_renegotiation();
753 
754  return false;
755  }
756 
758  const std::string& context,
759  size_t length) const
760  {
761  if(auto active = active_state())
762  {
763  if(pending_state() != nullptr)
764  throw Invalid_State("Channel::key_material_export cannot export during renegotiation");
765 
766  std::unique_ptr<KDF> prf(active->protocol_specific_prf());
767 
768  const secure_vector<uint8_t>& master_secret =
769  active->session_keys().master_secret();
770 
771  std::vector<uint8_t> salt;
772  salt += active->client_hello()->random();
773  salt += active->server_hello()->random();
774 
775  if(context != "")
776  {
777  size_t context_size = context.length();
778  if(context_size > 0xFFFF)
779  throw Invalid_Argument("key_material_export context is too long");
780  salt.push_back(get_byte(0, static_cast<uint16_t>(context_size)));
781  salt.push_back(get_byte(1, static_cast<uint16_t>(context_size)));
782  salt += to_byte_vector(context);
783  }
784 
785  return prf->derive_key(length, master_secret, salt, to_byte_vector(label));
786  }
787  else
788  {
789  throw Invalid_State("Channel::key_material_export connection not active");
790  }
791  }
792 
793 }
794 
795 }
Protocol_Version version() const
Definition: tls_record.h:101
Record_Header read_record(bool is_datagram, secure_vector< uint8_t > &readbuf, const uint8_t input[], size_t input_len, size_t &consumed, secure_vector< uint8_t > &recbuf, Connection_Sequence_Numbers *sequence_numbers, get_cipherstate_fn get_cipherstate, bool allow_epoch0_restart)
Definition: tls_record.cpp:514
virtual bool tls_session_established(const Session &session)=0
virtual std::vector< X509_Certificate > get_peer_cert_chain(const Handshake_State &state) const =0
uint64_t sequence() const
Definition: tls_record.h:107
Channel(Callbacks &callbacks, Session_Manager &session_manager, RandomNumberGenerator &rng, const Policy &policy, bool is_server, bool is_datagram, size_t io_buf_sz=IO_BUF_DEFAULT_SIZE)
Definition: tls_channel.cpp:26
Record_Type type() const
Definition: tls_record.h:118
virtual void remove_entry(const std::vector< uint8_t > &session_id)=0
bool is_closed() const
Type type() const
Definition: tls_alert.h:80
bool is_fatal() const
Definition: tls_alert.h:75
std::function< void(Alert, const uint8_t[], size_t)> alert_cb
Definition: tls_channel.h:42
SymmetricKey key_material_export(const std::string &label, const std::string &context, size_t length) const
std::vector< uint8_t > renegotiation_info() const
void change_cipher_spec_reader(Connection_Side side)
std::vector< uint8_t > serialize() const
Definition: tls_alert.cpp:31
constexpr uint8_t get_byte(size_t byte_num, T input)
Definition: loadstor.h:41
void change_cipher_spec_writer(Connection_Side side)
const uint8_t * cast_char_ptr_to_uint8(const char *s)
Definition: mem_ops.h:190
size_t needed() const
Definition: tls_record.h:99
void send_warning_alert(Alert::Type type)
Definition: tls_channel.h:139
std::function< void(const uint8_t[], size_t)> output_fn
Definition: tls_channel.h:40
bool secure_renegotiation_supported() const
virtual void tls_alert(Alert alert)=0
Handshake_State & create_handshake_state(Protocol_Version version)
#define BOTAN_ASSERT_NOMSG(expr)
Definition: assert.h:68
std::string to_string(const BER_Object &obj)
Definition: asn1_obj.cpp:213
MechanismType type
#define BOTAN_ASSERT(expr, assertion_made)
Definition: assert.h:55
uint16_t epoch() const
Definition: tls_record.h:113
void send_alert(const Alert &alert)
std::vector< uint8_t > secure_renegotiation_data_for_client_hello() const
std::vector< X509_Certificate > peer_cert_chain() const
virtual void tls_record_received(uint64_t seq_no, const uint8_t data[], size_t size)=0
std::string to_string() const
Definition: tls_version.cpp:15
void reset_active_association_state()
Definition: tls_channel.cpp:92
std::function< bool(const Session &)> handshake_cb
Definition: tls_channel.h:43
void send(const uint8_t buf[], size_t buf_size)
bool save_session(const Session &session)
std::vector< uint8_t > secure_renegotiation_data_for_server_hello() const
static size_t IO_BUF_DEFAULT_SIZE
Definition: tls_channel.h:45
virtual Handshake_State * new_handshake_state(class Handshake_IO *io)=0
std::vector< uint8_t > renegotiation_info() const
Definition: tls_messages.h:239
Definition: alg_id.cpp:13
std::vector< uint8_t > to_byte_vector(const std::string &s)
Definition: stl_util.h:20
void send_fatal_alert(Alert::Type type)
Definition: tls_channel.h:144
void secure_renegotiation_check(const Client_Hello *client_hello)
size_t received_data(const uint8_t buf[], size_t buf_size)
virtual uint64_t next_write_sequence(uint16_t)=0
Alert::Type type() const
Definition: tls_exceptn.h:24
std::function< void(const uint8_t[], size_t)> data_cb
Definition: tls_channel.h:41
virtual void tls_session_activated()
Definition: tls_callbacks.h:97
bool secure_renegotiation() const
Definition: tls_messages.h:234
virtual bool allow_dtls_epoch0_restart() const
Definition: tls_policy.cpp:350
void map_remove_if(Pred pred, T &assoc)
Definition: stl_util.h:96
void write_record(secure_vector< uint8_t > &output, uint8_t record_type, Protocol_Version version, uint64_t record_sequence, const uint8_t *message, size_t message_len, Connection_Cipher_State &cs, RandomNumberGenerator &rng)
Definition: tls_record.cpp:224
Callbacks & callbacks() const
Definition: tls_channel.h:242
virtual uint16_t current_write_epoch() const =0
virtual void tls_emit_data(const uint8_t data[], size_t size)=0
void renegotiate(bool force_full_renegotiation=false)
uint8_t major_version() const
Definition: tls_version.h:79
#define BOTAN_ASSERT_IMPLICATION(expr1, expr2, msg)
Definition: assert.h:94
const Policy & policy() const
Definition: tls_channel.h:238
virtual bool allow_resumption_for_renegotiation() const
Definition: tls_policy.cpp:345
bool is_valid() const
Definition: tls_alert.h:70
virtual void read_accept(uint64_t seq)=0
std::vector< T, secure_allocator< T > > secure_vector
Definition: secmem.h:65
virtual uint16_t current_read_epoch() const =0
void write_unencrypted_record(secure_vector< uint8_t > &output, uint8_t record_type, Protocol_Version version, uint64_t record_sequence, const uint8_t *message, size_t message_len)
Definition: tls_record.cpp:210
virtual void process_handshake_msg(const Handshake_State *active_state, Handshake_State &pending_state, Handshake_Type type, const std::vector< uint8_t > &contents, bool epoch0_restart)=0
bool is_active() const
std::function< void(const Handshake_Message &)> handshake_msg_cb
Definition: tls_channel.h:44
virtual void initiate_handshake(Handshake_State &state, bool force_full_renegotiation)=0