2 * Copyright (C) 1996-2018 The Squid Software Foundation and contributors
4 * Squid software is distributed under GPLv2+ license and includes
5 * contributions from numerous individuals and organizations.
6 * Please see the COPYING and CONTRIBUTORS files for details.
9 #ifndef SQUID_SECURITY_HANDSHAKE_H
10 #define SQUID_SECURITY_HANDSHAKE_H
12 #include "anyp/ProtocolVersion.h"
13 #include "base/YesNoNone.h"
14 #include "parser/BinaryTokenizer.h"
15 #include "security/forward.h"
17 #include <unordered_set>
22 class TlsDetails
: public RefCountable
25 typedef RefCount
<TlsDetails
> Pointer
;
28 /// Prints to os stream a human readable form of TlsDetails object
29 std::ostream
& print(std::ostream
&os
) const;
31 AnyP::ProtocolVersion tlsVersion
; ///< The TLS hello message version
32 AnyP::ProtocolVersion tlsSupportedVersion
; ///< The requested/used TLS version
33 bool compressionSupported
; ///< The requested/used compressed method
34 SBuf serverName
; ///< The SNI hostname, if any
36 bool tlsTicketsExtension
; ///< whether TLS tickets extension is enabled
37 bool hasTlsTicket
; ///< whether a TLS ticket is included
38 bool tlsStatusRequest
; ///< whether the TLS status request extension is set
39 bool unsupportedExtensions
; ///< whether any unsupported by Squid extensions are used
40 SBuf tlsAppLayerProtoNeg
; ///< The value of the TLS application layer protocol extension if it is enabled
41 /// The client random number
45 typedef std::unordered_set
<uint16_t> Ciphers
;
50 std::ostream
&operator <<(std::ostream
&os
, Security::TlsDetails
const &details
)
52 return details
.print(os
);
55 /// Incremental TLS/SSL Handshake parser.
59 /// The parsing states
60 typedef enum {atHelloNone
= 0, atHelloStarted
, atHelloReceived
, atCertificatesReceived
, atHelloDoneReceived
, atNstReceived
, atCcsReceived
, atFinishReceived
} ParserState
;
64 /// Parses the initial sequence of raw bytes sent by the TLS/SSL agent.
65 /// Returns true upon successful completion (e.g., got HelloDone).
66 /// Returns false if more data is needed.
68 bool parseHello(const SBuf
&data
);
70 TlsDetails::Pointer details
; ///< TLS handshake meta info or nil.
72 Security::CertList serverCertificates
; ///< parsed certificates chain
74 ParserState state
; ///< current parsing state.
76 bool resumingSession
; ///< True if this is a resuming session
79 bool isSslv2Record(const SBuf
&raw
) const;
81 void parseModernRecord();
82 void parseVersion2Record();
85 void parseChangeCipherCpecMessage();
86 void parseAlertMessage();
87 void parseHandshakeMessage();
88 void parseApplicationDataMessage();
89 void skipMessage(const char *msgType
);
91 bool parseRecordVersion2Try();
92 void parseVersion2HandshakeMessage(const SBuf
&raw
);
93 void parseClientHelloHandshakeMessage(const SBuf
&raw
);
94 void parseServerHelloHandshakeMessage(const SBuf
&raw
);
96 bool parseCompressionMethods(const SBuf
&raw
);
97 void parseExtensions(const SBuf
&raw
);
98 SBuf
parseSniExtension(const SBuf
&extensionData
) const;
100 void parseCiphers(const SBuf
&raw
);
101 void parseV23Ciphers(const SBuf
&raw
);
103 void parseServerCertificates(const SBuf
&raw
);
104 static CertPointer
ParseCertificate(const SBuf
&raw
);
106 unsigned int currentContentType
; ///< The current TLS/SSL record content type
108 const char *done
; ///< not nil if we got what we were looking for
110 /// concatenated TLSPlaintext.fragments of TLSPlaintext.type
113 /// TLS record layer (parsing uninterpreted data)
114 Parser::BinaryTokenizer tkRecords
;
116 /// TLS message layer (parsing fragments)
117 Parser::BinaryTokenizer tkMessages
;
119 /// Whether to use TLS parser or a V2 compatible parser
120 YesNoNone expectingModernRecords
;
125 #endif // SQUID_SECURITY_HANDSHAKE_H