1diff --git a/third_party/tlslite/tlslite/constants.py b/third_party/tlslite/tlslite/constants.py 2index d132b78..ceaa903 100755 3--- a/third_party/tlslite/tlslite/constants.py 4+++ b/third_party/tlslite/tlslite/constants.py 5@@ -30,6 +30,7 @@ class HandshakeType: 6 certificate_verify = 15 7 client_key_exchange = 16 8 finished = 20 9+ certificate_status = 22 10 next_protocol = 67 11 encrypted_extensions = 203 12 13@@ -40,8 +41,12 @@ class ContentType: 14 application_data = 23 15 all = (20,21,22,23) 16 17+class CertificateStatusType: 18+ ocsp = 1 19+ 20 class ExtensionType: # RFC 6066 / 4366 21 server_name = 0 # RFC 6066 / 4366 22+ status_request = 5 # RFC 6066 / 4366 23 srp = 12 # RFC 5054 24 cert_type = 9 # RFC 6091 25 signed_cert_timestamps = 18 # RFC 6962 26diff --git a/third_party/tlslite/tlslite/messages.py b/third_party/tlslite/tlslite/messages.py 27index 5a2cd6c..532d86b 100755 28--- a/third_party/tlslite/tlslite/messages.py 29+++ b/third_party/tlslite/tlslite/messages.py 30@@ -114,6 +114,7 @@ class ClientHello(HandshakeMsg): 31 self.server_name = bytearray(0) 32 self.channel_id = False 33 self.support_signed_cert_timestamps = False 34+ self.status_request = False 35 36 def create(self, version, random, session_id, cipher_suites, 37 certificate_types=None, srpUsername=None, 38@@ -187,6 +188,19 @@ class ClientHello(HandshakeMsg): 39 if extLength: 40 raise SyntaxError() 41 self.support_signed_cert_timestamps = True 42+ elif extType == ExtensionType.status_request: 43+ # Extension contents are currently ignored. 44+ # According to RFC 6066, this is not strictly forbidden 45+ # (although it is suboptimal): 46+ # Servers that receive a client hello containing the 47+ # "status_request" extension MAY return a suitable 48+ # certificate status response to the client along with 49+ # their certificate. If OCSP is requested, they 50+ # SHOULD use the information contained in the extension 51+ # when selecting an OCSP responder and SHOULD include 52+ # request_extensions in the OCSP request. 53+ p.getFixBytes(extLength) 54+ self.status_request = True 55 else: 56 _ = p.getFixBytes(extLength) 57 index2 = p.index 58@@ -253,6 +267,7 @@ class ServerHello(HandshakeMsg): 59 self.next_protos = None 60 self.channel_id = False 61 self.signed_cert_timestamps = None 62+ self.status_request = False 63 64 def create(self, version, random, session_id, cipher_suite, 65 certificate_type, tackExt, next_protos_advertised): 66@@ -345,6 +360,9 @@ class ServerHello(HandshakeMsg): 67 if self.signed_cert_timestamps: 68 w2.add(ExtensionType.signed_cert_timestamps, 2) 69 w2.addVarSeq(bytearray(self.signed_cert_timestamps), 1, 2) 70+ if self.status_request: 71+ w2.add(ExtensionType.status_request, 2) 72+ w2.add(0, 2) 73 if len(w2.bytes): 74 w.add(len(w2.bytes), 2) 75 w.bytes += w2.bytes 76@@ -402,6 +420,37 @@ class Certificate(HandshakeMsg): 77 raise AssertionError() 78 return self.postWrite(w) 79 80+class CertificateStatus(HandshakeMsg): 81+ def __init__(self): 82+ HandshakeMsg.__init__(self, HandshakeType.certificate_status) 83+ 84+ def create(self, ocsp_response): 85+ self.ocsp_response = ocsp_response 86+ return self 87+ 88+ # Defined for the sake of completeness, even though we currently only 89+ # support sending the status message (server-side), not requesting 90+ # or receiving it (client-side). 91+ def parse(self, p): 92+ p.startLengthCheck(3) 93+ status_type = p.get(1) 94+ # Only one type is specified, so hardwire it. 95+ if status_type != CertificateStatusType.ocsp: 96+ raise SyntaxError() 97+ ocsp_response = p.getVarBytes(3) 98+ if not ocsp_response: 99+ # Can't be empty 100+ raise SyntaxError() 101+ self.ocsp_response = ocsp_response 102+ p.stopLengthCheck() 103+ return self 104+ 105+ def write(self): 106+ w = Writer() 107+ w.add(CertificateStatusType.ocsp, 1) 108+ w.addVarSeq(bytearray(self.ocsp_response), 1, 3) 109+ return self.postWrite(w) 110+ 111 class CertificateRequest(HandshakeMsg): 112 def __init__(self): 113 HandshakeMsg.__init__(self, HandshakeType.certificate_request) 114diff --git a/third_party/tlslite/tlslite/tlsconnection.py b/third_party/tlslite/tlslite/tlsconnection.py 115index bd92161..b9797d2 100755 116--- a/third_party/tlslite/tlslite/tlsconnection.py 117+++ b/third_party/tlslite/tlslite/tlsconnection.py 118@@ -967,7 +967,7 @@ class TLSConnection(TLSRecordLayer): 119 tacks=None, activationFlags=0, 120 nextProtos=None, anon=False, 121 tlsIntolerant=None, signedCertTimestamps=None, 122- fallbackSCSV=False): 123+ fallbackSCSV=False, ocspResponse=None): 124 """Perform a handshake in the role of server. 125 126 This function performs an SSL or TLS handshake. Depending on 127@@ -1051,6 +1051,16 @@ class TLSConnection(TLSRecordLayer): 128 TLS_FALLBACK_SCSV and thus reject connections using less than the 129 server's maximum TLS version that include this cipher suite. 130 131+ @type ocspResponse: str 132+ @param ocspResponse: An OCSP response (as a binary 8-bit string) that 133+ will be sent stapled in the handshake whenever the client announces 134+ support for the status_request extension. 135+ Note that the response is sent independent of the ClientHello 136+ status_request extension contents, and is thus only meant for testing 137+ environments. Real OCSP stapling is more complicated as it requires 138+ choosing a suitable response based on the ClientHello status_request 139+ extension contents. 140+ 141 @raise socket.error: If a socket error occurs. 142 @raise tlslite.errors.TLSAbruptCloseError: If the socket is closed 143 without a preceding alert. 144@@ -1064,7 +1074,7 @@ class TLSConnection(TLSRecordLayer): 145 tacks=tacks, activationFlags=activationFlags, 146 nextProtos=nextProtos, anon=anon, tlsIntolerant=tlsIntolerant, 147 signedCertTimestamps=signedCertTimestamps, 148- fallbackSCSV=fallbackSCSV): 149+ fallbackSCSV=fallbackSCSV, ocspResponse=ocspResponse): 150 pass 151 152 153@@ -1076,7 +1086,8 @@ class TLSConnection(TLSRecordLayer): 154 nextProtos=None, anon=False, 155 tlsIntolerant=None, 156 signedCertTimestamps=None, 157- fallbackSCSV=False 158+ fallbackSCSV=False, 159+ ocspResponse=None 160 ): 161 """Start a server handshake operation on the TLS connection. 162 163@@ -1098,7 +1109,8 @@ class TLSConnection(TLSRecordLayer): 164 nextProtos=nextProtos, anon=anon, 165 tlsIntolerant=tlsIntolerant, 166 signedCertTimestamps=signedCertTimestamps, 167- fallbackSCSV=fallbackSCSV) 168+ fallbackSCSV=fallbackSCSV, 169+ ocspResponse=ocspResponse) 170 for result in self._handshakeWrapperAsync(handshaker, checker): 171 yield result 172 173@@ -1108,7 +1120,8 @@ class TLSConnection(TLSRecordLayer): 174 settings, reqCAs, 175 tacks, activationFlags, 176 nextProtos, anon, 177- tlsIntolerant, signedCertTimestamps, fallbackSCSV): 178+ tlsIntolerant, signedCertTimestamps, fallbackSCSV, 179+ ocspResponse): 180 181 self._handshakeStart(client=False) 182 183@@ -1178,6 +1191,8 @@ class TLSConnection(TLSRecordLayer): 184 serverHello.channel_id = clientHello.channel_id 185 if clientHello.support_signed_cert_timestamps: 186 serverHello.signed_cert_timestamps = signedCertTimestamps 187+ if clientHello.status_request: 188+ serverHello.status_request = ocspResponse 189 190 # Perform the SRP key exchange 191 clientCertChain = None 192@@ -1194,7 +1209,7 @@ class TLSConnection(TLSRecordLayer): 193 for result in self._serverCertKeyExchange(clientHello, serverHello, 194 certChain, privateKey, 195 reqCert, reqCAs, cipherSuite, 196- settings): 197+ settings, ocspResponse): 198 if result in (0,1): yield result 199 else: break 200 (premasterSecret, clientCertChain) = result 201@@ -1471,7 +1486,7 @@ class TLSConnection(TLSRecordLayer): 202 def _serverCertKeyExchange(self, clientHello, serverHello, 203 serverCertChain, privateKey, 204 reqCert, reqCAs, cipherSuite, 205- settings): 206+ settings, ocspResponse): 207 #Send ServerHello, Certificate[, CertificateRequest], 208 #ServerHelloDone 209 msgs = [] 210@@ -1481,6 +1496,8 @@ class TLSConnection(TLSRecordLayer): 211 212 msgs.append(serverHello) 213 msgs.append(Certificate(CertificateType.x509).create(serverCertChain)) 214+ if serverHello.status_request: 215+ msgs.append(CertificateStatus().create(ocspResponse)) 216 if reqCert and reqCAs: 217 msgs.append(CertificateRequest().create(\ 218 [ClientCertificateType.rsa_sign], reqCAs)) 219