summaryrefslogtreecommitdiff
path: root/src/node_crypto_clienthello.cc
diff options
context:
space:
mode:
Diffstat (limited to 'src/node_crypto_clienthello.cc')
-rw-r--r--src/node_crypto_clienthello.cc23
1 files changed, 17 insertions, 6 deletions
diff --git a/src/node_crypto_clienthello.cc b/src/node_crypto_clienthello.cc
index 227d64cfaa..70603e95c5 100644
--- a/src/node_crypto_clienthello.cc
+++ b/src/node_crypto_clienthello.cc
@@ -87,39 +87,46 @@ bool ClientHelloParser::ParseRecordHeader(const uint8_t* data, size_t avail) {
void ClientHelloParser::ParseHeader(const uint8_t* data, size_t avail) {
+ ClientHello hello;
+
// >= 5 + frame size bytes for frame parsing
if (body_offset_ + frame_len_ > avail)
return;
// Skip unsupported frames and gather some data from frame
+ // Check hello protocol version
+ if (!(data[body_offset_ + 4] == 0x03 && data[body_offset_ + 5] <= 0x03))
+ goto fail;
+#ifndef OPENSSL_NO_SSL2
+ if (!(data[body_offset_ + 4] == 0x00 && data[body_offset_ + 5] == 0x02))
+ goto fail;
+#endif
- // TODO(indutny): Check hello protocol version
if (data[body_offset_] == kClientHello) {
if (state_ == kTLSHeader) {
if (!ParseTLSClientHello(data, avail))
- return End();
+ goto fail;
} else if (state_ == kSSL2Header) {
#ifdef OPENSSL_NO_SSL2
if (!ParseSSL2ClientHello(data, avail))
- return End();
+ goto fail;
#else
abort(); // Unreachable
#endif // OPENSSL_NO_SSL2
} else {
// We couldn't get here, but whatever
- return End();
+ goto fail;
}
// Check if we overflowed (do not reply with any private data)
if (session_id_ == NULL ||
session_size_ > 32 ||
session_id_ + session_size_ > data + avail) {
- return End();
+ goto fail;
}
}
state_ = kPaused;
- ClientHello hello;
hello.session_id_ = session_id_;
hello.session_size_ = session_size_;
hello.has_ticket_ = tls_ticket_ != NULL && tls_ticket_size_ != 0;
@@ -127,6 +134,10 @@ void ClientHelloParser::ParseHeader(const uint8_t* data, size_t avail) {
hello.servername_ = servername_;
hello.servername_size_ = static_cast<uint8_t>(servername_size_);
onhello_cb_(cb_arg_, hello);
+ return;
+
+ fail:
+ return End();
}