• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

randombit / botan / 30496461195

29 Jul 2026 08:43PM UTC coverage: 89.519% (+0.09%) from 89.425%
30496461195

push

github

web-flow
Merge pull request #5776 from Rohde-Schwarz/fix/tls_anvil

116233 of 129841 relevant lines covered (89.52%)

10620449.77 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

88.61
/src/lib/tls/tls_client.cpp
1
/*
2
* TLS Client
3
* (C) 2004-2011,2012,2015,2016 Jack Lloyd
4
*     2016 Matthias Gierlings
5
*     2017 Harry Reimann, Rohde & Schwarz Cybersecurity
6
*     2021 Elektrobit Automotive GmbH
7
*
8
* Botan is released under the Simplified BSD License (see license.txt)
9
*/
10

11
#include <botan/tls_client.h>
12

13
#include <botan/tls_policy.h>
14
#include <botan/x509cert.h>
15
#include <botan/internal/tls_channel_impl.h>
16

17
#if defined(BOTAN_HAS_TLS_12)
18
   #include <botan/internal/tls_client_impl_12.h>
19
#endif
20

21
#if defined(BOTAN_HAS_TLS_13)
22
   #include <botan/internal/tls_client_impl_13.h>
23
#endif
24

25
namespace Botan::TLS {
26

27
/*
28
* TLS Client Constructor
29
*/
30
Client::Client(const std::shared_ptr<Callbacks>& callbacks,
3,895✔
31
               const std::shared_ptr<Session_Manager>& session_manager,
32
               const std::shared_ptr<Credentials_Manager>& creds,
33
               const std::shared_ptr<const Policy>& policy,
34
               const std::shared_ptr<RandomNumberGenerator>& rng,
35
               Server_Information info,
36
               Protocol_Version offer_version,
37
               const std::vector<std::string>& next_protocols,
38
               size_t io_buf_sz) {
3,895✔
39
   BOTAN_ARG_CHECK(policy->acceptable_protocol_version(offer_version),
3,895✔
40
                   "Policy does not allow to offer requested protocol version");
41

42
#if defined(BOTAN_HAS_TLS_13)
43
   if(offer_version == Protocol_Version::TLS_V13) {
3,895✔
44
      m_impl = std::make_unique<Client_Impl_13>(
1,255✔
45
         callbacks, session_manager, creds, policy, rng, std::move(info), next_protocols);
1,255✔
46

47
      if(m_impl->expects_downgrade()) {
1,255✔
48
         m_impl->set_io_buffer_size(io_buf_sz);
1,185✔
49
      }
50

51
      if(m_impl->is_downgrading()) {
1,255✔
52
         // TLS 1.3 implementation found a resumable TLS 1.2 session and
53
         // requested a downgrade right away.
54
         downgrade();
116✔
55
      }
56

57
      return;
1,255✔
58
   }
59
#endif
60

61
#if defined(BOTAN_HAS_TLS_12)
62
   if(offer_version.is_pre_tls_13()) {
2,640✔
63
      m_impl = std::make_unique<Client_Impl_12>(callbacks,
10,560✔
64
                                                session_manager,
65
                                                creds,
66
                                                policy,
67
                                                rng,
68
                                                std::move(info),
69
                                                offer_version.is_datagram_protocol(),
2,640✔
70
                                                next_protocols,
71
                                                io_buf_sz);
2,640✔
72
      return;
2,640✔
73
   }
74
#endif
75

76
   BOTAN_UNUSED(callbacks, session_manager, creds, policy, rng, info, offer_version, next_protocols, io_buf_sz);
×
77
   throw Not_Implemented("Requested TLS version to be offered is not available in this build");
×
78
}
×
79

80
Client::~Client() = default;
5,755✔
81

82
size_t Client::downgrade() {
604✔
83
   BOTAN_ASSERT_NOMSG(m_impl->is_downgrading());
604✔
84

85
#if defined(BOTAN_HAS_TLS_12)
86
   auto info = m_impl->extract_downgrade_info();
604✔
87
   m_impl = std::make_unique<Client_Impl_12>(*info);
1,208✔
88

89
   if(!info->peer_transcript.empty()) {
604✔
90
      // replay peer data received so far
91
      return m_impl->from_peer(info->peer_transcript);
488✔
92
   } else {
93
      // the downgrade happened due to a resumable TLS 1.2 session
94
      // before any data was transferred
95
      return 0;
96
   }
97
#else
98
   // If TLS 1.2 is not available, we will never downgrade, the downgrade info
99
   // won't even be created and `is_downgrading()` would always return false.
100
   BOTAN_ASSERT_UNREACHABLE();
101
#endif
102
}
604✔
103

104
size_t Client::from_peer(std::span<const uint8_t> data) {
85,163✔
105
   auto read = m_impl->from_peer(data);
85,163✔
106

107
   if(m_impl->is_downgrading()) {
82,749✔
108
      read = downgrade();
488✔
109
   }
110

111
   return read;
82,658✔
112
}
113

114
bool Client::is_handshake_complete() const {
2,714✔
115
   return m_impl->is_handshake_complete();
2,714✔
116
}
117

118
bool Client::is_active() const {
1,348✔
119
   return m_impl->is_active();
1,348✔
120
}
121

122
std::optional<std::chrono::milliseconds> Client::next_retransmission_timeout() const {
30✔
123
   return m_impl->next_retransmission_timeout();
30✔
124
}
125

126
bool Client::is_closed() const {
581✔
127
   return m_impl->is_closed();
581✔
128
}
129

130
bool Client::is_closed_for_reading() const {
×
131
   return m_impl->is_closed_for_reading();
×
132
}
133

134
bool Client::is_closed_for_writing() const {
164✔
135
   return m_impl->is_closed_for_writing();
164✔
136
}
137

138
std::vector<X509_Certificate> Client::peer_cert_chain() const {
×
139
   return m_impl->peer_cert_chain();
×
140
}
141

142
std::shared_ptr<const Public_Key> Client::peer_raw_public_key() const {
1✔
143
   return m_impl->peer_raw_public_key();
1✔
144
}
145

146
std::optional<std::string> Client::external_psk_identity() const {
×
147
   return m_impl->external_psk_identity();
×
148
}
149

150
SymmetricKey Client::key_material_export(std::string_view label, std::string_view context, size_t length) const {
265✔
151
   return m_impl->key_material_export(label, context, length);
265✔
152
}
153

154
void Client::renegotiate(bool force_full_renegotiation) {
2✔
155
   m_impl->renegotiate(force_full_renegotiation);
2✔
156
}
2✔
157

158
void Client::update_traffic_keys(bool request_peer_update) {
1✔
159
   m_impl->update_traffic_keys(request_peer_update);
1✔
160
}
1✔
161

162
bool Client::secure_renegotiation_supported() const {
11✔
163
   return m_impl->secure_renegotiation_supported();
11✔
164
}
165

166
void Client::to_peer(std::span<const uint8_t> data) {
2,394✔
167
   m_impl->to_peer(data);
2,394✔
168
}
2,394✔
169

170
void Client::send_alert(const Alert& alert) {
1,069✔
171
   m_impl->send_alert(alert);
1,069✔
172
}
1,069✔
173

174
void Client::send_warning_alert(Alert::Type type) {
129✔
175
   m_impl->send_warning_alert(type);
129✔
176
}
129✔
177

178
void Client::send_fatal_alert(Alert::Type type) {
16✔
179
   m_impl->send_fatal_alert(type);
16✔
180
}
16✔
181

182
void Client::close() {
238✔
183
   m_impl->close();
238✔
184
}
238✔
185

186
bool Client::timeout_check() {
65✔
187
   return m_impl->timeout_check();
65✔
188
}
189

190
std::string Client::application_protocol() const {
1,370✔
191
   return m_impl->application_protocol();
1,370✔
192
}
193

194
}  // namespace Botan::TLS
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE TRIAL · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc