summaryrefslogtreecommitdiffstats
path: root/chromium/third_party/tlslite/patches/channel_id.patch
blob: 0fe16924b5712e3ae95f4a3c4dfc6a929b10c638 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
diff --git a/third_party/tlslite/tlslite/constants.py b/third_party/tlslite/tlslite/constants.py
index d52e596..79ad145 100755
--- a/third_party/tlslite/tlslite/constants.py
+++ b/third_party/tlslite/tlslite/constants.py
@@ -31,6 +31,7 @@ class HandshakeType:
     client_key_exchange = 16
     finished = 20
     next_protocol = 67
+    encrypted_extensions = 203
 
 class ContentType:
     change_cipher_spec = 20
@@ -45,6 +46,7 @@ class ExtensionType:    # RFC 6066 / 4366
     cert_type = 9       # RFC 6091
     tack = 0xF300
     supports_npn = 13172
+    channel_id = 30032
     
 class NameType:
     host_name = 0
diff --git a/third_party/tlslite/tlslite/messages.py b/third_party/tlslite/tlslite/messages.py
index 7ef4e3f..246082e 100755
--- a/third_party/tlslite/tlslite/messages.py
+++ b/third_party/tlslite/tlslite/messages.py
@@ -112,6 +112,7 @@ class ClientHello(HandshakeMsg):
         self.tack = False
         self.supports_npn = False
         self.server_name = bytearray(0)
+        self.channel_id = False
 
     def create(self, version, random, session_id, cipher_suites,
                certificate_types=None, srpUsername=None,
@@ -179,6 +180,8 @@ class ClientHello(HandshakeMsg):
                             if name_type == NameType.host_name:
                                 self.server_name = hostNameBytes
                                 break
+                    elif extType == ExtensionType.channel_id:
+                        self.channel_id = True
                     else:
                         _ = p.getFixBytes(extLength)
                     index2 = p.index
@@ -243,6 +246,7 @@ class ServerHello(HandshakeMsg):
         self.tackExt = None
         self.next_protos_advertised = None
         self.next_protos = None
+        self.channel_id = False
 
     def create(self, version, random, session_id, cipher_suite,
                certificate_type, tackExt, next_protos_advertised):
@@ -329,6 +333,9 @@ class ServerHello(HandshakeMsg):
             w2.add(ExtensionType.supports_npn, 2)
             w2.add(len(encoded_next_protos_advertised), 2)
             w2.addFixSeq(encoded_next_protos_advertised, 1)
+        if self.channel_id:
+            w2.add(ExtensionType.channel_id, 2)
+            w2.add(0, 2)
         if len(w2.bytes):
             w.add(len(w2.bytes), 2)
             w.bytes += w2.bytes        
@@ -656,6 +663,28 @@ class Finished(HandshakeMsg):
         w.addFixSeq(self.verify_data, 1)
         return self.postWrite(w)
 
+class EncryptedExtensions(HandshakeMsg):
+    def __init__(self):
+        self.channel_id_key = None
+        self.channel_id_proof = None
+
+    def parse(self, p):
+        p.startLengthCheck(3)
+        soFar = 0
+        while soFar != p.lengthCheck:
+            extType = p.get(2)
+            extLength = p.get(2)
+            if extType == ExtensionType.channel_id:
+                if extLength != 32*4:
+                    raise SyntaxError()
+                self.channel_id_key = p.getFixBytes(64)
+                self.channel_id_proof = p.getFixBytes(64)
+            else:
+                p.getFixBytes(extLength)
+            soFar += 4 + extLength
+        p.stopLengthCheck()
+        return self
+
 class ApplicationData(object):
     def __init__(self):
         self.contentType = ContentType.application_data
diff --git a/third_party/tlslite/tlslite/tlsconnection.py b/third_party/tlslite/tlslite/tlsconnection.py
index 8415592..e7c5140 100755
--- a/third_party/tlslite/tlslite/tlsconnection.py
+++ b/third_party/tlslite/tlslite/tlsconnection.py
@@ -1155,6 +1155,7 @@ class TLSConnection(TLSRecordLayer):
         serverHello.create(self.version, getRandomBytes(32), sessionID, \
                             cipherSuite, CertificateType.x509, tackExt,
                             nextProtos)
+        serverHello.channel_id = clientHello.channel_id
 
         # Perform the SRP key exchange
         clientCertChain = None
@@ -1191,7 +1192,7 @@ class TLSConnection(TLSRecordLayer):
         for result in self._serverFinished(premasterSecret, 
                                 clientHello.random, serverHello.random,
                                 cipherSuite, settings.cipherImplementations,
-                                nextProtos):
+                                nextProtos, clientHello.channel_id):
                 if result in (0,1): yield result
                 else: break
         masterSecret = result
@@ -1609,7 +1610,8 @@ class TLSConnection(TLSRecordLayer):
 
 
     def _serverFinished(self,  premasterSecret, clientRandom, serverRandom,
-                        cipherSuite, cipherImplementations, nextProtos):
+                        cipherSuite, cipherImplementations, nextProtos,
+                        doingChannelID):
         masterSecret = calcMasterSecret(self.version, premasterSecret,
                                       clientRandom, serverRandom)
         
@@ -1620,7 +1622,8 @@ class TLSConnection(TLSRecordLayer):
 
         #Exchange ChangeCipherSpec and Finished messages
         for result in self._getFinished(masterSecret, 
-                        expect_next_protocol=nextProtos is not None):
+                        expect_next_protocol=nextProtos is not None,
+                        expect_channel_id=doingChannelID):
             yield result
 
         for result in self._sendFinished(masterSecret):
@@ -1657,7 +1660,8 @@ class TLSConnection(TLSRecordLayer):
         for result in self._sendMsg(finished):
             yield result
 
-    def _getFinished(self, masterSecret, expect_next_protocol=False, nextProto=None):
+    def _getFinished(self, masterSecret, expect_next_protocol=False, nextProto=None,
+                     expect_channel_id=False):
         #Get and check ChangeCipherSpec
         for result in self._getMsg(ContentType.change_cipher_spec):
             if result in (0,1):
@@ -1690,6 +1694,20 @@ class TLSConnection(TLSRecordLayer):
         if nextProto:
             self.next_proto = nextProto
 
+        #Server Finish - Are we waiting for a EncryptedExtensions?
+        if expect_channel_id:
+            for result in self._getMsg(ContentType.handshake, HandshakeType.encrypted_extensions):
+                if result in (0,1):
+                    yield result
+            if result is None:
+                for result in self._sendError(AlertDescription.unexpected_message,
+                                             "Didn't get EncryptedExtensions message"):
+                    yield result
+            encrypted_extensions = result
+            self.channel_id = result.channel_id_key
+        else:
+            self.channel_id = None
+
         #Calculate verification data
         verifyData = self._calcFinished(masterSecret, False)
 
diff --git a/third_party/tlslite/tlslite/tlsrecordlayer.py b/third_party/tlslite/tlslite/tlsrecordlayer.py
index b0833fe..ff08cbf 100755
--- a/third_party/tlslite/tlslite/tlsrecordlayer.py
+++ b/third_party/tlslite/tlslite/tlsrecordlayer.py
@@ -800,6 +800,8 @@ class TLSRecordLayer(object):
                     yield Finished(self.version).parse(p)
                 elif subType == HandshakeType.next_protocol:
                     yield NextProtocol().parse(p)
+                elif subType == HandshakeType.encrypted_extensions:
+                    yield EncryptedExtensions().parse(p)
                 else:
                     raise AssertionError()