]> git.ipfire.org Git - ipfire-2.x.git/blob - src/patches/samba/CVE-2015-5370-v3-6.patch
Merge branch 'next' of ssh://git.ipfire.org/pub/git/ipfire-2.x into next-suricata
[ipfire-2.x.git] / src / patches / samba / CVE-2015-5370-v3-6.patch
1 From 8368c32cb69da82c8df36404ec8042c3046866ca Mon Sep 17 00:00:00 2001
2 From: Stefan Metzmacher <metze@samba.org>
3 Date: Thu, 16 Jul 2015 22:46:05 +0200
4 Subject: [PATCH 01/40] CVE-2015-5370: dcerpc.idl: add
5 DCERPC_{NCACN_PAYLOAD,FRAG}_MAX_SIZE defines
6 MIME-Version: 1.0
7 Content-Type: text/plain; charset=UTF-8
8 Content-Transfer-Encoding: 8bit
9
10 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
11
12 Signed-off-by: Stefan Metzmacher <metze@samba.org>
13 Reviewed-by: Günther Deschner <gd@samba.org>
14 ---
15 librpc/idl/dcerpc.idl | 2 ++
16 1 file changed, 2 insertions(+)
17
18 diff --git a/librpc/idl/dcerpc.idl b/librpc/idl/dcerpc.idl
19 index 75ef2ec..bbb42d1 100644
20 --- a/librpc/idl/dcerpc.idl
21 +++ b/librpc/idl/dcerpc.idl
22 @@ -475,9 +475,11 @@ interface dcerpc
23 const uint8 DCERPC_PFC_OFFSET = 3;
24 const uint8 DCERPC_DREP_OFFSET = 4;
25 const uint8 DCERPC_FRAG_LEN_OFFSET = 8;
26 + const uint32 DCERPC_FRAG_MAX_SIZE = 5840;
27 const uint8 DCERPC_AUTH_LEN_OFFSET = 10;
28 const uint8 DCERPC_CALL_ID_OFFSET = 12;
29 const uint8 DCERPC_NCACN_PAYLOAD_OFFSET = 16;
30 + const uint32 DCERPC_NCACN_PAYLOAD_MAX_SIZE = 0x400000; /* 4 MByte */
31
32 /* little-endian flag */
33 const uint8 DCERPC_DREP_LE = 0x10;
34 --
35 2.8.1
36
37
38 From e3043ba5aafdb0605ab14b11917d497b59d82bec Mon Sep 17 00:00:00 2001
39 From: Stefan Metzmacher <metze@samba.org>
40 Date: Sun, 28 Jun 2015 01:19:57 +0200
41 Subject: [PATCH 02/40] CVE-2015-5370: librpc/rpc: simplify and harden
42 dcerpc_pull_auth_trailer()
43 MIME-Version: 1.0
44 Content-Type: text/plain; charset=UTF-8
45 Content-Transfer-Encoding: 8bit
46
47 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
48
49 Signed-off-by: Stefan Metzmacher <metze@samba.org>
50 Reviewed-by: Günther Deschner <gd@samba.org>
51 ---
52 librpc/rpc/dcerpc_util.c | 63 ++++++++++++++++++++++++++++++++++++------------
53 librpc/rpc/rpc_common.h | 4 +--
54 2 files changed, 49 insertions(+), 18 deletions(-)
55
56 diff --git a/librpc/rpc/dcerpc_util.c b/librpc/rpc/dcerpc_util.c
57 index 97ef798..f936ef4 100644
58 --- a/librpc/rpc/dcerpc_util.c
59 +++ b/librpc/rpc/dcerpc_util.c
60 @@ -92,31 +92,44 @@ uint8_t dcerpc_get_endian_flag(DATA_BLOB *blob)
61 *
62 * @return - A NTSTATUS error code.
63 */
64 -NTSTATUS dcerpc_pull_auth_trailer(struct ncacn_packet *pkt,
65 +NTSTATUS dcerpc_pull_auth_trailer(const struct ncacn_packet *pkt,
66 TALLOC_CTX *mem_ctx,
67 - DATA_BLOB *pkt_trailer,
68 + const DATA_BLOB *pkt_trailer,
69 struct dcerpc_auth *auth,
70 - uint32_t *auth_length,
71 + uint32_t *_auth_length,
72 bool auth_data_only)
73 {
74 struct ndr_pull *ndr;
75 enum ndr_err_code ndr_err;
76 - uint32_t data_and_pad;
77 + uint16_t data_and_pad;
78 + uint16_t auth_length;
79 + uint32_t tmp_length;
80
81 - data_and_pad = pkt_trailer->length
82 - - (DCERPC_AUTH_TRAILER_LENGTH + pkt->auth_length);
83 + ZERO_STRUCTP(auth);
84 + if (_auth_length != NULL) {
85 + *_auth_length = 0;
86 + }
87
88 - /* paranoia check for pad size. This would be caught anyway by
89 - the ndr_pull_advance() a few lines down, but it scared
90 - Jeremy enough for him to call me, so we might as well check
91 - it now, just to prevent someone posting a bogus YouTube
92 - video in the future.
93 - */
94 - if (data_and_pad > pkt_trailer->length) {
95 - return NT_STATUS_INFO_LENGTH_MISMATCH;
96 + /* Paranoia checks for auth_length. The caller should check this... */
97 + if (pkt->auth_length > pkt->frag_length) {
98 + return NT_STATUS_INTERNAL_ERROR;
99 + }
100 + tmp_length = DCERPC_NCACN_PAYLOAD_OFFSET;
101 + tmp_length += DCERPC_AUTH_TRAILER_LENGTH;
102 + tmp_length += pkt->auth_length;
103 + if (tmp_length > pkt->frag_length) {
104 + return NT_STATUS_INTERNAL_ERROR;
105 + }
106 + if (pkt_trailer->length > UINT16_MAX) {
107 + return NT_STATUS_INTERNAL_ERROR;
108 }
109
110 - *auth_length = pkt_trailer->length - data_and_pad;
111 + auth_length = DCERPC_AUTH_TRAILER_LENGTH + pkt->auth_length;
112 + if (pkt_trailer->length < auth_length) {
113 + return NT_STATUS_RPC_PROTOCOL_ERROR;
114 + }
115 +
116 + data_and_pad = pkt_trailer->length - auth_length;
117
118 ndr = ndr_pull_init_blob(pkt_trailer, mem_ctx);
119 if (!ndr) {
120 @@ -136,14 +149,28 @@ NTSTATUS dcerpc_pull_auth_trailer(struct ncacn_packet *pkt,
121 ndr_err = ndr_pull_dcerpc_auth(ndr, NDR_SCALARS|NDR_BUFFERS, auth);
122 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
123 talloc_free(ndr);
124 + ZERO_STRUCTP(auth);
125 return ndr_map_error2ntstatus(ndr_err);
126 }
127
128 + if (data_and_pad < auth->auth_pad_length) {
129 + DEBUG(1, (__location__ ": ERROR: pad length mismatch. "
130 + "Calculated %u got %u\n",
131 + (unsigned)data_and_pad,
132 + (unsigned)auth->auth_pad_length));
133 + talloc_free(ndr);
134 + ZERO_STRUCTP(auth);
135 + return NT_STATUS_RPC_PROTOCOL_ERROR;
136 + }
137 +
138 if (auth_data_only && data_and_pad != auth->auth_pad_length) {
139 - DEBUG(1, (__location__ ": WARNING: pad length mismatch. "
140 + DEBUG(1, (__location__ ": ERROR: pad length mismatch. "
141 "Calculated %u got %u\n",
142 (unsigned)data_and_pad,
143 (unsigned)auth->auth_pad_length));
144 + talloc_free(ndr);
145 + ZERO_STRUCTP(auth);
146 + return NT_STATUS_RPC_PROTOCOL_ERROR;
147 }
148
149 DEBUG(6,(__location__ ": auth_pad_length %u\n",
150 @@ -152,6 +179,10 @@ NTSTATUS dcerpc_pull_auth_trailer(struct ncacn_packet *pkt,
151 talloc_steal(mem_ctx, auth->credentials.data);
152 talloc_free(ndr);
153
154 + if (_auth_length != NULL) {
155 + *_auth_length = auth_length;
156 + }
157 +
158 return NT_STATUS_OK;
159 }
160
161 diff --git a/librpc/rpc/rpc_common.h b/librpc/rpc/rpc_common.h
162 index fe8129d..98a2e95 100644
163 --- a/librpc/rpc/rpc_common.h
164 +++ b/librpc/rpc/rpc_common.h
165 @@ -158,9 +158,9 @@ uint8_t dcerpc_get_endian_flag(DATA_BLOB *blob);
166 *
167 * @return - A NTSTATUS error code.
168 */
169 -NTSTATUS dcerpc_pull_auth_trailer(struct ncacn_packet *pkt,
170 +NTSTATUS dcerpc_pull_auth_trailer(const struct ncacn_packet *pkt,
171 TALLOC_CTX *mem_ctx,
172 - DATA_BLOB *pkt_trailer,
173 + const DATA_BLOB *pkt_trailer,
174 struct dcerpc_auth *auth,
175 uint32_t *auth_length,
176 bool auth_data_only);
177 --
178 2.8.1
179
180
181 From 397300d996299400842938131691fbbeb88c2c82 Mon Sep 17 00:00:00 2001
182 From: Stefan Metzmacher <metze@samba.org>
183 Date: Mon, 29 Jun 2015 10:24:45 +0200
184 Subject: [PATCH 03/40] CVE-2015-5370: s3:librpc/rpc: don't call
185 dcerpc_pull_auth_trailer() if auth_length is 0
186 MIME-Version: 1.0
187 Content-Type: text/plain; charset=UTF-8
188 Content-Transfer-Encoding: 8bit
189
190 All other paranoia checks are done within dcerpc_pull_auth_trailer()
191 now.
192
193 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
194
195 Signed-off-by: Stefan Metzmacher <metze@samba.org>
196 Reviewed-by: Günther Deschner <gd@samba.org>
197 ---
198 source3/librpc/rpc/dcerpc_helpers.c | 12 ++----------
199 1 file changed, 2 insertions(+), 10 deletions(-)
200
201 diff --git a/source3/librpc/rpc/dcerpc_helpers.c b/source3/librpc/rpc/dcerpc_helpers.c
202 index 24f2f52..76f2acc 100644
203 --- a/source3/librpc/rpc/dcerpc_helpers.c
204 +++ b/source3/librpc/rpc/dcerpc_helpers.c
205 @@ -899,16 +899,8 @@ NTSTATUS dcerpc_check_auth(struct pipe_auth_data *auth,
206 return NT_STATUS_INVALID_PARAMETER;
207 }
208
209 - /* Paranioa checks for auth_length. */
210 - if (pkt->auth_length > pkt->frag_length) {
211 - return NT_STATUS_INFO_LENGTH_MISMATCH;
212 - }
213 - if (((unsigned int)pkt->auth_length
214 - + DCERPC_AUTH_TRAILER_LENGTH < (unsigned int)pkt->auth_length) ||
215 - ((unsigned int)pkt->auth_length
216 - + DCERPC_AUTH_TRAILER_LENGTH < DCERPC_AUTH_TRAILER_LENGTH)) {
217 - /* Integer wrap attempt. */
218 - return NT_STATUS_INFO_LENGTH_MISMATCH;
219 + if (pkt->auth_length == 0) {
220 + return NT_STATUS_INVALID_PARAMETER;
221 }
222
223 status = dcerpc_pull_auth_trailer(pkt, pkt, pkt_trailer,
224 --
225 2.8.1
226
227
228 From faa20091b4a456a5e29f852561f6f5e9863860e0 Mon Sep 17 00:00:00 2001
229 From: Stefan Metzmacher <metze@samba.org>
230 Date: Fri, 26 Jun 2015 08:10:46 +0200
231 Subject: [PATCH 04/40] CVE-2015-5370: librpc/rpc: add a
232 dcerpc_verify_ncacn_packet_header() helper function
233 MIME-Version: 1.0
234 Content-Type: text/plain; charset=UTF-8
235 Content-Transfer-Encoding: 8bit
236
237 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
238
239 Signed-off-by: Stefan Metzmacher <metze@samba.org>
240 Reviewed-by: Günther Deschner <gd@samba.org>
241 (cherry picked from commit 8266be48f455a5e541d0f7f62a1c8c38e0835976)
242 ---
243 librpc/rpc/dcerpc_util.c | 73 ++++++++++++++++++++++++++++++++++++++++++++++++
244 librpc/rpc/rpc_common.h | 5 ++++
245 2 files changed, 78 insertions(+)
246
247 diff --git a/librpc/rpc/dcerpc_util.c b/librpc/rpc/dcerpc_util.c
248 index f936ef4..2f599d5 100644
249 --- a/librpc/rpc/dcerpc_util.c
250 +++ b/librpc/rpc/dcerpc_util.c
251 @@ -186,6 +186,79 @@ NTSTATUS dcerpc_pull_auth_trailer(const struct ncacn_packet *pkt,
252 return NT_STATUS_OK;
253 }
254
255 +/**
256 +* @brief Verify the fields in ncacn_packet header.
257 +*
258 +* @param pkt - The ncacn_packet strcuture
259 +* @param ptype - The expected PDU type
260 +* @param max_auth_info - The maximum size of a possible auth trailer
261 +* @param required_flags - The required flags for the pdu.
262 +* @param optional_flags - The possible optional flags for the pdu.
263 +*
264 +* @return - A NTSTATUS error code.
265 +*/
266 +NTSTATUS dcerpc_verify_ncacn_packet_header(const struct ncacn_packet *pkt,
267 + enum dcerpc_pkt_type ptype,
268 + size_t max_auth_info,
269 + uint8_t required_flags,
270 + uint8_t optional_flags)
271 +{
272 + if (pkt->rpc_vers != 5) {
273 + return NT_STATUS_RPC_PROTOCOL_ERROR;
274 + }
275 +
276 + if (pkt->rpc_vers_minor != 0) {
277 + return NT_STATUS_RPC_PROTOCOL_ERROR;
278 + }
279 +
280 + if (pkt->auth_length > pkt->frag_length) {
281 + return NT_STATUS_RPC_PROTOCOL_ERROR;
282 + }
283 +
284 + if (pkt->ptype != ptype) {
285 + return NT_STATUS_RPC_PROTOCOL_ERROR;
286 + }
287 +
288 + if (max_auth_info > UINT16_MAX) {
289 + return NT_STATUS_INTERNAL_ERROR;
290 + }
291 +
292 + if (pkt->auth_length > 0) {
293 + size_t max_auth_length;
294 +
295 + if (max_auth_info <= DCERPC_AUTH_TRAILER_LENGTH) {
296 + return NT_STATUS_RPC_PROTOCOL_ERROR;
297 + }
298 + max_auth_length = max_auth_info - DCERPC_AUTH_TRAILER_LENGTH;
299 +
300 + if (pkt->auth_length > max_auth_length) {
301 + return NT_STATUS_RPC_PROTOCOL_ERROR;
302 + }
303 + }
304 +
305 + if ((pkt->pfc_flags & required_flags) != required_flags) {
306 + return NT_STATUS_RPC_PROTOCOL_ERROR;
307 + }
308 + if (pkt->pfc_flags & ~(optional_flags|required_flags)) {
309 + return NT_STATUS_RPC_PROTOCOL_ERROR;
310 + }
311 +
312 + if (pkt->drep[0] & ~DCERPC_DREP_LE) {
313 + return NT_STATUS_RPC_PROTOCOL_ERROR;
314 + }
315 + if (pkt->drep[1] != 0) {
316 + return NT_STATUS_RPC_PROTOCOL_ERROR;
317 + }
318 + if (pkt->drep[2] != 0) {
319 + return NT_STATUS_RPC_PROTOCOL_ERROR;
320 + }
321 + if (pkt->drep[3] != 0) {
322 + return NT_STATUS_RPC_PROTOCOL_ERROR;
323 + }
324 +
325 + return NT_STATUS_OK;
326 +}
327 +
328 struct dcerpc_read_ncacn_packet_state {
329 #if 0
330 struct {
331 diff --git a/librpc/rpc/rpc_common.h b/librpc/rpc/rpc_common.h
332 index 98a2e95..b3ae5b2 100644
333 --- a/librpc/rpc/rpc_common.h
334 +++ b/librpc/rpc/rpc_common.h
335 @@ -164,6 +164,11 @@ NTSTATUS dcerpc_pull_auth_trailer(const struct ncacn_packet *pkt,
336 struct dcerpc_auth *auth,
337 uint32_t *auth_length,
338 bool auth_data_only);
339 +NTSTATUS dcerpc_verify_ncacn_packet_header(const struct ncacn_packet *pkt,
340 + enum dcerpc_pkt_type ptype,
341 + size_t max_auth_info,
342 + uint8_t required_flags,
343 + uint8_t optional_flags);
344 struct tevent_req *dcerpc_read_ncacn_packet_send(TALLOC_CTX *mem_ctx,
345 struct tevent_context *ev,
346 struct tstream_context *stream);
347 --
348 2.8.1
349
350
351 From c176174588c1119a11066b6188ac50cd3c9603f4 Mon Sep 17 00:00:00 2001
352 From: Stefan Metzmacher <metze@samba.org>
353 Date: Tue, 7 Jul 2015 13:05:01 +0200
354 Subject: [PATCH 05/40] CVE-2015-5370: s3:rpc_client: move AS/U hack to the top
355 of cli_pipe_validate_current_pdu()
356 MIME-Version: 1.0
357 Content-Type: text/plain; charset=UTF-8
358 Content-Transfer-Encoding: 8bit
359
360 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
361
362 Signed-off-by: Stefan Metzmacher <metze@samba.org>
363 Reviewed-by: Günther Deschner <gd@samba.org>
364 (cherry picked from commit 665b874b6022bfcdec3f13a9f5a844e5d1784aba)
365 ---
366 source3/rpc_client/cli_pipe.c | 24 +++++++++++++-----------
367 1 file changed, 13 insertions(+), 11 deletions(-)
368
369 diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c
370 index 5ddabb7..295b88f 100644
371 --- a/source3/rpc_client/cli_pipe.c
372 +++ b/source3/rpc_client/cli_pipe.c
373 @@ -414,6 +414,19 @@ static NTSTATUS cli_pipe_validate_current_pdu(TALLOC_CTX *mem_ctx,
374 */
375 *rdata = *pdu;
376
377 + if ((pkt->ptype == DCERPC_PKT_BIND_ACK) &&
378 + !(pkt->pfc_flags & DCERPC_PFC_FLAG_LAST)) {
379 + /*
380 + * TODO: do we still need this hack which was introduced
381 + * in commit a42afcdcc7ab9aa9ed193ae36d3dbb10843447f0.
382 + *
383 + * I don't even know what AS/U might be...
384 + */
385 + DEBUG(5, (__location__ ": bug in server (AS/U?), setting "
386 + "fragment first/last ON.\n"));
387 + pkt->pfc_flags |= DCERPC_PFC_FLAG_FIRST | DCERPC_PFC_FLAG_LAST;
388 + }
389 +
390 /* Ensure we have the correct type. */
391 switch (pkt->ptype) {
392 case DCERPC_PKT_ALTER_RESP:
393 @@ -518,17 +531,6 @@ static NTSTATUS cli_pipe_validate_current_pdu(TALLOC_CTX *mem_ctx,
394 return NT_STATUS_RPC_PROTOCOL_ERROR;
395 }
396
397 - /* Do this just before return - we don't want to modify any rpc header
398 - data before now as we may have needed to do cryptographic actions on
399 - it before. */
400 -
401 - if ((pkt->ptype == DCERPC_PKT_BIND_ACK) &&
402 - !(pkt->pfc_flags & DCERPC_PFC_FLAG_LAST)) {
403 - DEBUG(5, (__location__ ": bug in server (AS/U?), setting "
404 - "fragment first/last ON.\n"));
405 - pkt->pfc_flags |= DCERPC_PFC_FLAG_FIRST | DCERPC_PFC_FLAG_LAST;
406 - }
407 -
408 return NT_STATUS_OK;
409 }
410
411 --
412 2.8.1
413
414
415 From b9ae0068be4dfc6f7d09144c353689ab01955b93 Mon Sep 17 00:00:00 2001
416 From: Stefan Metzmacher <metze@samba.org>
417 Date: Tue, 7 Jul 2015 13:05:01 +0200
418 Subject: [PATCH 06/40] CVE-2015-5370: s3:rpc_client: remove useless
419 frag_length check in rpc_api_pipe_got_pdu()
420 MIME-Version: 1.0
421 Content-Type: text/plain; charset=UTF-8
422 Content-Transfer-Encoding: 8bit
423
424 dcerpc_pull_ncacn_packet() already verifies this.
425
426 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
427
428 Signed-off-by: Stefan Metzmacher <metze@samba.org>
429 Reviewed-by: Günther Deschner <gd@samba.org>
430 (cherry picked from commit 9a3f045244b12ff9f77d2664396137c390042297)
431 ---
432 source3/rpc_client/cli_pipe.c | 8 --------
433 1 file changed, 8 deletions(-)
434
435 diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c
436 index 295b88f..2787fbc 100644
437 --- a/source3/rpc_client/cli_pipe.c
438 +++ b/source3/rpc_client/cli_pipe.c
439 @@ -898,14 +898,6 @@ static void rpc_api_pipe_got_pdu(struct tevent_req *subreq)
440 return;
441 }
442
443 - if (state->incoming_frag.length != state->pkt->frag_length) {
444 - DEBUG(5, ("Incorrect pdu length %u, expected %u\n",
445 - (unsigned int)state->incoming_frag.length,
446 - (unsigned int)state->pkt->frag_length));
447 - tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER);
448 - return;
449 - }
450 -
451 status = cli_pipe_validate_current_pdu(state,
452 state->cli, state->pkt,
453 &state->incoming_frag,
454 --
455 2.8.1
456
457
458 From 05688274f03e6086e3ba4d7b4cb4409f9c4d9cb1 Mon Sep 17 00:00:00 2001
459 From: Stefan Metzmacher <metze@samba.org>
460 Date: Fri, 26 Jun 2015 08:10:46 +0200
461 Subject: [PATCH 07/40] CVE-2015-5370: s4:rpc_server: no authentication is
462 indicated by pkt->auth_length == 0
463 MIME-Version: 1.0
464 Content-Type: text/plain; charset=UTF-8
465 Content-Transfer-Encoding: 8bit
466
467 pkt->u.*.auth_info.length is not the correct thing to check.
468
469 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
470
471 Signed-off-by: Stefan Metzmacher <metze@samba.org>
472 Reviewed-by: Günther Deschner <gd@samba.org>
473 (packported from commit c0236de09e542dbb168969d8ae9f0c150a75198e)
474 ---
475 source4/rpc_server/dcesrv_auth.c | 23 ++++++++++++++---------
476 1 file changed, 14 insertions(+), 9 deletions(-)
477
478 diff --git a/source4/rpc_server/dcesrv_auth.c b/source4/rpc_server/dcesrv_auth.c
479 index 1e6aa24..61f2176 100644
480 --- a/source4/rpc_server/dcesrv_auth.c
481 +++ b/source4/rpc_server/dcesrv_auth.c
482 @@ -46,7 +46,7 @@ bool dcesrv_auth_bind(struct dcesrv_call_state *call)
483 NTSTATUS status;
484 uint32_t auth_length;
485
486 - if (pkt->u.bind.auth_info.length == 0) {
487 + if (pkt->auth_length == 0) {
488 dce_conn->auth_state.auth_info = NULL;
489 return true;
490 }
491 @@ -108,7 +108,7 @@ NTSTATUS dcesrv_auth_bind_ack(struct dcesrv_call_state *call, struct ncacn_packe
492 struct dcesrv_connection *dce_conn = call->conn;
493 NTSTATUS status;
494
495 - if (!call->conn->auth_state.gensec_security) {
496 + if (call->pkt.auth_length == 0) {
497 return NT_STATUS_OK;
498 }
499
500 @@ -155,10 +155,16 @@ bool dcesrv_auth_auth3(struct dcesrv_call_state *call)
501 NTSTATUS status;
502 uint32_t auth_length;
503
504 - /* We can't work without an existing gensec state, and an new blob to feed it */
505 - if (!dce_conn->auth_state.auth_info ||
506 - !dce_conn->auth_state.gensec_security ||
507 - pkt->u.auth3.auth_info.length == 0) {
508 + if (pkt->auth_length == 0) {
509 + return false;
510 + }
511 +
512 + if (!dce_conn->auth_state.auth_info) {
513 + return false;
514 + }
515 +
516 + /* We can't work without an existing gensec state */
517 + if (!dce_conn->auth_state.gensec_security) {
518 return false;
519 }
520
521 @@ -203,7 +209,7 @@ bool dcesrv_auth_alter(struct dcesrv_call_state *call)
522 uint32_t auth_length;
523
524 /* on a pure interface change there is no auth blob */
525 - if (pkt->u.alter.auth_info.length == 0) {
526 + if (pkt->auth_length == 0) {
527 return true;
528 }
529
530 @@ -238,8 +244,7 @@ NTSTATUS dcesrv_auth_alter_ack(struct dcesrv_call_state *call, struct ncacn_pack
531
532 /* on a pure interface change there is no auth_info structure
533 setup */
534 - if (!call->conn->auth_state.auth_info ||
535 - dce_conn->auth_state.auth_info->credentials.length == 0) {
536 + if (call->pkt.auth_length == 0) {
537 return NT_STATUS_OK;
538 }
539
540 --
541 2.8.1
542
543
544 From 57230961cee9e82ab060b54b5fb8c2b19f672111 Mon Sep 17 00:00:00 2001
545 From: Stefan Metzmacher <metze@samba.org>
546 Date: Sat, 27 Jun 2015 10:31:48 +0200
547 Subject: [PATCH 08/40] CVE-2015-5370: s4:librpc/rpc: check pkt->auth_length
548 before calling dcerpc_pull_auth_trailer
549
550 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
551
552 Signed-off-by: Ralph Boehme <slow@samba.org>
553 (backported from 630dcb55ad7a3a89bcd8643c98a5cdbfb8735ef7)
554 ---
555 source4/librpc/rpc/dcerpc.c | 13 ++++++++++---
556 source4/rpc_server/dcesrv_auth.c | 5 +++++
557 2 files changed, 15 insertions(+), 3 deletions(-)
558
559 diff --git a/source4/librpc/rpc/dcerpc.c b/source4/librpc/rpc/dcerpc.c
560 index 742d710..cfbccd6 100644
561 --- a/source4/librpc/rpc/dcerpc.c
562 +++ b/source4/librpc/rpc/dcerpc.c
563 @@ -701,6 +701,14 @@ static NTSTATUS ncacn_pull_request_auth(struct dcecli_connection *c, TALLOC_CTX
564 return NT_STATUS_INVALID_LEVEL;
565 }
566
567 + if (pkt->auth_length == 0) {
568 + return NT_STATUS_INVALID_NETWORK_RESPONSE;
569 + }
570 +
571 + if (c->security_state.generic_state == NULL) {
572 + return NT_STATUS_INTERNAL_ERROR;
573 + }
574 +
575 status = dcerpc_pull_auth_trailer(pkt, mem_ctx,
576 &pkt->u.response.stub_and_verifier,
577 &auth, &auth_length, false);
578 @@ -1074,7 +1082,7 @@ static void dcerpc_bind_recv_handler(struct rpc_request *req,
579 }
580
581 /* the bind_ack might contain a reply set of credentials */
582 - if (conn->security_state.auth_info && pkt->u.bind_ack.auth_info.length) {
583 + if (conn->security_state.auth_info && pkt->auth_length) {
584 NTSTATUS status;
585 uint32_t auth_length;
586 status = dcerpc_pull_auth_trailer(pkt, conn, &pkt->u.bind_ack.auth_info,
587 @@ -1847,8 +1855,7 @@ static void dcerpc_alter_recv_handler(struct rpc_request *req,
588 }
589
590 /* the alter_resp might contain a reply set of credentials */
591 - if (recv_pipe->conn->security_state.auth_info &&
592 - pkt->u.alter_resp.auth_info.length) {
593 + if (recv_pipe->conn->security_state.auth_info && pkt->auth_length) {
594 struct dcecli_connection *conn = recv_pipe->conn;
595 NTSTATUS status;
596 uint32_t auth_length;
597 diff --git a/source4/rpc_server/dcesrv_auth.c b/source4/rpc_server/dcesrv_auth.c
598 index 61f2176..3051c1c 100644
599 --- a/source4/rpc_server/dcesrv_auth.c
600 +++ b/source4/rpc_server/dcesrv_auth.c
601 @@ -320,6 +320,11 @@ bool dcesrv_auth_request(struct dcesrv_call_state *call, DATA_BLOB *full_packet)
602 return false;
603 }
604
605 + if (pkt->auth_length == 0) {
606 + DEBUG(1,("dcesrv_auth_request: unexpected auth_length of 0\n"));
607 + return false;
608 + }
609 +
610 status = dcerpc_pull_auth_trailer(pkt, call,
611 &pkt->u.request.stub_and_verifier,
612 &auth, &auth_length, false);
613 --
614 2.8.1
615
616
617 From c35b0e37f7d37459f55d67a5037c08bea4d33acf Mon Sep 17 00:00:00 2001
618 From: Stefan Metzmacher <metze@samba.org>
619 Date: Sun, 28 Jun 2015 01:19:57 +0200
620 Subject: [PATCH 09/40] CVE-2015-5370: librpc/rpc: don't allow pkt->auth_length
621 == 0 in dcerpc_pull_auth_trailer()
622 MIME-Version: 1.0
623 Content-Type: text/plain; charset=UTF-8
624 Content-Transfer-Encoding: 8bit
625
626 All callers should have already checked that.
627
628 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
629
630 Signed-off-by: Stefan Metzmacher <metze@samba.org>
631 Reviewed-by: Günther Deschner <gd@samba.org>
632 (cherry picked from commit 1ed83c7657a3b405db1928db06c29f41d2738186)
633 ---
634 librpc/rpc/dcerpc_util.c | 5 +++++
635 1 file changed, 5 insertions(+)
636
637 diff --git a/librpc/rpc/dcerpc_util.c b/librpc/rpc/dcerpc_util.c
638 index 2f599d5..89b7597 100644
639 --- a/librpc/rpc/dcerpc_util.c
640 +++ b/librpc/rpc/dcerpc_util.c
641 @@ -111,6 +111,11 @@ NTSTATUS dcerpc_pull_auth_trailer(const struct ncacn_packet *pkt,
642 }
643
644 /* Paranoia checks for auth_length. The caller should check this... */
645 + if (pkt->auth_length == 0) {
646 + return NT_STATUS_INTERNAL_ERROR;
647 + }
648 +
649 + /* Paranoia checks for auth_length. The caller should check this... */
650 if (pkt->auth_length > pkt->frag_length) {
651 return NT_STATUS_INTERNAL_ERROR;
652 }
653 --
654 2.8.1
655
656
657 From 2341eb0cf8395b1fed628ee6779207d916827a5d Mon Sep 17 00:00:00 2001
658 From: Stefan Metzmacher <metze@samba.org>
659 Date: Thu, 9 Jul 2015 07:59:24 +0200
660 Subject: [PATCH 10/40] CVE-2015-5370: s3:librpc/rpc: remove auth trailer and
661 possible padding within dcerpc_check_auth()
662 MIME-Version: 1.0
663 Content-Type: text/plain; charset=UTF-8
664 Content-Transfer-Encoding: 8bit
665
666 This simplifies the callers a lot.
667
668 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
669
670 Signed-off-by: Stefan Metzmacher <metze@samba.org>
671 Reviewed-by: Günther Deschner <gd@samba.org>
672 (cherry picked from commit df3cdf072d1c1e6fd0a58e0374348758f5c65a49)
673 ---
674 source3/librpc/rpc/dcerpc.h | 5 ++---
675 source3/librpc/rpc/dcerpc_helpers.c | 31 ++++++++++++++++++++-----------
676 source3/rpc_client/cli_pipe.c | 33 ++++++++++-----------------------
677 source3/rpc_server/srv_pipe.c | 17 +----------------
678 4 files changed, 33 insertions(+), 53 deletions(-)
679
680 diff --git a/source3/librpc/rpc/dcerpc.h b/source3/librpc/rpc/dcerpc.h
681 index d14d8e0..e7cca9e 100644
682 --- a/source3/librpc/rpc/dcerpc.h
683 +++ b/source3/librpc/rpc/dcerpc.h
684 @@ -85,9 +85,8 @@ NTSTATUS dcerpc_add_auth_footer(struct pipe_auth_data *auth,
685 NTSTATUS dcerpc_check_auth(struct pipe_auth_data *auth,
686 struct ncacn_packet *pkt,
687 DATA_BLOB *pkt_trailer,
688 - size_t header_size,
689 - DATA_BLOB *raw_pkt,
690 - size_t *pad_len);
691 + uint8_t header_size,
692 + DATA_BLOB *raw_pkt);
693
694 /* The following definitions come from librpc/rpc/rpc_common.c */
695
696 diff --git a/source3/librpc/rpc/dcerpc_helpers.c b/source3/librpc/rpc/dcerpc_helpers.c
697 index 76f2acc..d871339 100644
698 --- a/source3/librpc/rpc/dcerpc_helpers.c
699 +++ b/source3/librpc/rpc/dcerpc_helpers.c
700 @@ -844,19 +844,18 @@ NTSTATUS dcerpc_add_auth_footer(struct pipe_auth_data *auth,
701 *
702 * @param auth The auth data for the connection
703 * @param pkt The actual ncacn_packet
704 -* @param pkt_trailer The stub_and_verifier part of the packet
705 +* @param pkt_trailer [in][out] The stub_and_verifier part of the packet,
706 +* the auth_trailer and padding will be removed.
707 * @param header_size The header size
708 * @param raw_pkt The whole raw packet data blob
709 -* @param pad_len [out] The padding length used in the packet
710 *
711 * @return A NTSTATUS error code
712 */
713 NTSTATUS dcerpc_check_auth(struct pipe_auth_data *auth,
714 struct ncacn_packet *pkt,
715 DATA_BLOB *pkt_trailer,
716 - size_t header_size,
717 - DATA_BLOB *raw_pkt,
718 - size_t *pad_len)
719 + uint8_t header_size,
720 + DATA_BLOB *raw_pkt)
721 {
722 struct schannel_state *schannel_auth;
723 struct auth_ntlmssp_state *ntlmssp_ctx;
724 @@ -868,6 +867,14 @@ NTSTATUS dcerpc_check_auth(struct pipe_auth_data *auth,
725 DATA_BLOB full_pkt;
726 DATA_BLOB data;
727
728 + /*
729 + * These check should be done in the caller.
730 + */
731 + SMB_ASSERT(raw_pkt->length == pkt->frag_length);
732 + SMB_ASSERT(header_size <= pkt->frag_length);
733 + SMB_ASSERT(pkt_trailer->length < pkt->frag_length);
734 + SMB_ASSERT((pkt_trailer->length + header_size) <= pkt->frag_length);
735 +
736 switch (auth->auth_level) {
737 case DCERPC_AUTH_LEVEL_PRIVACY:
738 DEBUG(10, ("Requested Privacy.\n"));
739 @@ -881,7 +888,6 @@ NTSTATUS dcerpc_check_auth(struct pipe_auth_data *auth,
740 if (pkt->auth_length != 0) {
741 break;
742 }
743 - *pad_len = 0;
744 return NT_STATUS_OK;
745
746 case DCERPC_AUTH_LEVEL_NONE:
747 @@ -890,7 +896,6 @@ NTSTATUS dcerpc_check_auth(struct pipe_auth_data *auth,
748 "authenticated connection!\n"));
749 return NT_STATUS_INVALID_PARAMETER;
750 }
751 - *pad_len = 0;
752 return NT_STATUS_OK;
753
754 default:
755 @@ -909,10 +914,11 @@ NTSTATUS dcerpc_check_auth(struct pipe_auth_data *auth,
756 return status;
757 }
758
759 + pkt_trailer->length -= auth_length;
760 data = data_blob_const(raw_pkt->data + header_size,
761 - pkt_trailer->length - auth_length);
762 - full_pkt = data_blob_const(raw_pkt->data,
763 - raw_pkt->length - auth_info.credentials.length);
764 + pkt_trailer->length);
765 + full_pkt = data_blob_const(raw_pkt->data, raw_pkt->length);
766 + full_pkt.length -= auth_info.credentials.length;
767
768 switch (auth->auth_type) {
769 case DCERPC_AUTH_TYPE_NONE:
770 @@ -988,10 +994,13 @@ NTSTATUS dcerpc_check_auth(struct pipe_auth_data *auth,
771 * pkt_trailer actually has a copy of the raw data, and they
772 * are still both used in later calls */
773 if (auth->auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
774 + if (pkt_trailer->length != data.length) {
775 + return NT_STATUS_INVALID_PARAMETER;
776 + }
777 memcpy(pkt_trailer->data, data.data, data.length);
778 }
779
780 - *pad_len = auth_info.auth_pad_length;
781 + pkt_trailer->length -= auth_info.auth_pad_length;
782 data_blob_free(&auth_info.credentials);
783 return NT_STATUS_OK;
784 }
785 diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c
786 index 2787fbc..776e2bf 100644
787 --- a/source3/rpc_client/cli_pipe.c
788 +++ b/source3/rpc_client/cli_pipe.c
789 @@ -404,9 +404,9 @@ static NTSTATUS cli_pipe_validate_current_pdu(TALLOC_CTX *mem_ctx,
790 DATA_BLOB *rdata,
791 DATA_BLOB *reply_pdu)
792 {
793 - struct dcerpc_response *r;
794 + const struct dcerpc_response *r = NULL;
795 + DATA_BLOB tmp_stub = data_blob_null;
796 NTSTATUS ret = NT_STATUS_OK;
797 - size_t pad_len = 0;
798
799 /*
800 * Point the return values at the real data including the RPC
801 @@ -440,37 +440,24 @@ static NTSTATUS cli_pipe_validate_current_pdu(TALLOC_CTX *mem_ctx,
802
803 r = &pkt->u.response;
804
805 + tmp_stub.data = r->stub_and_verifier.data;
806 + tmp_stub.length = r->stub_and_verifier.length;
807 +
808 /* Here's where we deal with incoming sign/seal. */
809 ret = dcerpc_check_auth(cli->auth, pkt,
810 - &r->stub_and_verifier,
811 + &tmp_stub,
812 DCERPC_RESPONSE_LENGTH,
813 - pdu, &pad_len);
814 + pdu);
815 if (!NT_STATUS_IS_OK(ret)) {
816 return ret;
817 }
818
819 - if (pkt->frag_length < DCERPC_RESPONSE_LENGTH + pad_len) {
820 - return NT_STATUS_BUFFER_TOO_SMALL;
821 - }
822 -
823 /* Point the return values at the NDR data. */
824 - rdata->data = r->stub_and_verifier.data;
825 -
826 - if (pkt->auth_length) {
827 - /* We've already done integer wrap tests in
828 - * dcerpc_check_auth(). */
829 - rdata->length = r->stub_and_verifier.length
830 - - pad_len
831 - - DCERPC_AUTH_TRAILER_LENGTH
832 - - pkt->auth_length;
833 - } else {
834 - rdata->length = r->stub_and_verifier.length;
835 - }
836 + *rdata = tmp_stub;
837
838 - DEBUG(10, ("Got pdu len %lu, data_len %lu, ss_len %u\n",
839 + DEBUG(10, ("Got pdu len %lu, data_len %lu\n",
840 (long unsigned int)pdu->length,
841 - (long unsigned int)rdata->length,
842 - (unsigned int)pad_len));
843 + (long unsigned int)rdata->length));
844
845 /*
846 * If this is the first reply, and the allocation hint is
847 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
848 index 964b843..0ab7dc6 100644
849 --- a/source3/rpc_server/srv_pipe.c
850 +++ b/source3/rpc_server/srv_pipe.c
851 @@ -1848,7 +1848,6 @@ static NTSTATUS dcesrv_auth_request(struct pipe_auth_data *auth,
852 {
853 NTSTATUS status;
854 size_t hdr_size = DCERPC_REQUEST_LENGTH;
855 - size_t pad_len;
856
857 DEBUG(10, ("Checking request auth.\n"));
858
859 @@ -1859,25 +1858,11 @@ static NTSTATUS dcesrv_auth_request(struct pipe_auth_data *auth,
860 /* in case of sealing this function will unseal the data in place */
861 status = dcerpc_check_auth(auth, pkt,
862 &pkt->u.request.stub_and_verifier,
863 - hdr_size, raw_pkt,
864 - &pad_len);
865 + hdr_size, raw_pkt);
866 if (!NT_STATUS_IS_OK(status)) {
867 return status;
868 }
869
870 -
871 - /* remove padding and auth trailer,
872 - * this way the caller will get just the data */
873 - if (pkt->auth_length) {
874 - size_t trail_len = pad_len
875 - + DCERPC_AUTH_TRAILER_LENGTH
876 - + pkt->auth_length;
877 - if (pkt->u.request.stub_and_verifier.length < trail_len) {
878 - return NT_STATUS_INFO_LENGTH_MISMATCH;
879 - }
880 - pkt->u.request.stub_and_verifier.length -= trail_len;
881 - }
882 -
883 return NT_STATUS_OK;
884 }
885
886 --
887 2.8.1
888
889
890 From 9ecba8f4635aa5dbd42e4838ce124a92395b64ab Mon Sep 17 00:00:00 2001
891 From: Stefan Metzmacher <metze@samba.org>
892 Date: Thu, 9 Jul 2015 07:59:24 +0200
893 Subject: [PATCH 11/40] CVE-2015-5370: s3:librpc/rpc: let dcerpc_check_auth()
894 auth_{type,level} against the expected values.
895 MIME-Version: 1.0
896 Content-Type: text/plain; charset=UTF-8
897 Content-Transfer-Encoding: 8bit
898
899 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
900
901 Signed-off-by: Stefan Metzmacher <metze@samba.org>
902 Reviewed-by: Günther Deschner <gd@samba.org>
903 (cherry picked from commit 19f489d32c03ff5fafd34fe86a075d782af1989a)
904 ---
905 source3/librpc/rpc/dcerpc_helpers.c | 8 ++++++++
906 1 file changed, 8 insertions(+)
907
908 diff --git a/source3/librpc/rpc/dcerpc_helpers.c b/source3/librpc/rpc/dcerpc_helpers.c
909 index d871339..c07835f 100644
910 --- a/source3/librpc/rpc/dcerpc_helpers.c
911 +++ b/source3/librpc/rpc/dcerpc_helpers.c
912 @@ -914,6 +914,14 @@ NTSTATUS dcerpc_check_auth(struct pipe_auth_data *auth,
913 return status;
914 }
915
916 + if (auth_info.auth_type != auth->auth_type) {
917 + return NT_STATUS_INVALID_PARAMETER;
918 + }
919 +
920 + if (auth_info.auth_level != auth->auth_level) {
921 + return NT_STATUS_INVALID_PARAMETER;
922 + }
923 +
924 pkt_trailer->length -= auth_length;
925 data = data_blob_const(raw_pkt->data + header_size,
926 pkt_trailer->length);
927 --
928 2.8.1
929
930
931 From 765c10dacf39a3c06c6b12651c205ac270e7fcea Mon Sep 17 00:00:00 2001
932 From: Stefan Metzmacher <metze@samba.org>
933 Date: Tue, 7 Jul 2015 13:05:01 +0200
934 Subject: [PATCH 12/40] CVE-2015-5370: s3:rpc_client: make use of
935 dcerpc_pull_auth_trailer()
936 MIME-Version: 1.0
937 Content-Type: text/plain; charset=UTF-8
938 Content-Transfer-Encoding: 8bit
939
940 The does much more validation than dcerpc_pull_dcerpc_auth().
941
942 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
943
944 Signed-off-by: Stefan Metzmacher <metze@samba.org>
945 Reviewed-by: Günther Deschner <gd@samba.org>
946 (cherry picked from commit acea87f158f02c3240abff45c3e54c7d5fa60b29)
947 ---
948 source3/rpc_client/cli_pipe.c | 20 ++++++--------------
949 1 file changed, 6 insertions(+), 14 deletions(-)
950
951 diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c
952 index 776e2bf..27e37f8 100644
953 --- a/source3/rpc_client/cli_pipe.c
954 +++ b/source3/rpc_client/cli_pipe.c
955 @@ -1938,20 +1938,15 @@ static void rpc_pipe_bind_step_one_done(struct tevent_req *subreq)
956 rpc_pipe_bind_step_two_trigger(req);
957 return;
958
959 - case DCERPC_AUTH_TYPE_NTLMSSP:
960 - case DCERPC_AUTH_TYPE_SPNEGO:
961 - case DCERPC_AUTH_TYPE_KRB5:
962 - /* Paranoid lenght checks */
963 - if (pkt->frag_length < DCERPC_AUTH_TRAILER_LENGTH
964 - + pkt->auth_length) {
965 - tevent_req_nterror(req,
966 - NT_STATUS_INFO_LENGTH_MISMATCH);
967 + default:
968 + if (pkt->auth_length == 0) {
969 + tevent_req_nterror(req, NT_STATUS_RPC_PROTOCOL_ERROR);
970 return;
971 }
972 /* get auth credentials */
973 - status = dcerpc_pull_dcerpc_auth(talloc_tos(),
974 - &pkt->u.bind_ack.auth_info,
975 - &auth, false);
976 + status = dcerpc_pull_auth_trailer(pkt, talloc_tos(),
977 + &pkt->u.bind_ack.auth_info,
978 + &auth, NULL, true);
979 if (!NT_STATUS_IS_OK(status)) {
980 DEBUG(0, ("Failed to pull dcerpc auth: %s.\n",
981 nt_errstr(status)));
982 @@ -1959,9 +1954,6 @@ static void rpc_pipe_bind_step_one_done(struct tevent_req *subreq)
983 return;
984 }
985 break;
986 -
987 - default:
988 - goto err_out;
989 }
990
991 /*
992 --
993 2.8.1
994
995
996 From b58616bbcc810b076e5fd9dd976272847f832b06 Mon Sep 17 00:00:00 2001
997 From: Stefan Metzmacher <metze@samba.org>
998 Date: Tue, 7 Jul 2015 13:05:01 +0200
999 Subject: [PATCH 13/40] CVE-2015-5370: s3:rpc_client: make use of
1000 dcerpc_verify_ncacn_packet_header() in cli_pipe_validate_current_pdu()
1001 MIME-Version: 1.0
1002 Content-Type: text/plain; charset=UTF-8
1003 Content-Transfer-Encoding: 8bit
1004
1005 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1006
1007 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1008 Reviewed-by: Günther Deschner <gd@samba.org>
1009 (cherry picked from commit 81bbffa14f5f6faa9801a3bf2d564d2762d49bb6)
1010 ---
1011 source3/rpc_client/cli_pipe.c | 111 ++++++++++++++++++++++++++++++++++++------
1012 1 file changed, 96 insertions(+), 15 deletions(-)
1013
1014 diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c
1015 index 27e37f8..6a22d38 100644
1016 --- a/source3/rpc_client/cli_pipe.c
1017 +++ b/source3/rpc_client/cli_pipe.c
1018 @@ -429,17 +429,89 @@ static NTSTATUS cli_pipe_validate_current_pdu(TALLOC_CTX *mem_ctx,
1019
1020 /* Ensure we have the correct type. */
1021 switch (pkt->ptype) {
1022 - case DCERPC_PKT_ALTER_RESP:
1023 + case DCERPC_PKT_BIND_NAK:
1024 + DEBUG(1, (__location__ ": Bind NACK received from %s!\n",
1025 + rpccli_pipe_txt(talloc_tos(), cli)));
1026 +
1027 + ret = dcerpc_verify_ncacn_packet_header(pkt,
1028 + DCERPC_PKT_BIND_NAK,
1029 + 0, /* max_auth_info */
1030 + DCERPC_PFC_FLAG_FIRST |
1031 + DCERPC_PFC_FLAG_LAST,
1032 + 0); /* optional flags */
1033 + if (!NT_STATUS_IS_OK(ret)) {
1034 + DEBUG(1, (__location__ ": Connection to %s got an unexpected "
1035 + "RPC packet type - %u, expected %u: %s\n",
1036 + rpccli_pipe_txt(talloc_tos(), cli),
1037 + pkt->ptype, expected_pkt_type,
1038 + nt_errstr(ret)));
1039 + NDR_PRINT_DEBUG(ncacn_packet, pkt);
1040 + return ret;
1041 + }
1042 +
1043 + /* Use this for now... */
1044 + return NT_STATUS_NETWORK_ACCESS_DENIED;
1045 +
1046 case DCERPC_PKT_BIND_ACK:
1047 + ret = dcerpc_verify_ncacn_packet_header(pkt,
1048 + expected_pkt_type,
1049 + pkt->u.bind_ack.auth_info.length,
1050 + DCERPC_PFC_FLAG_FIRST |
1051 + DCERPC_PFC_FLAG_LAST,
1052 + DCERPC_PFC_FLAG_CONC_MPX |
1053 + DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN);
1054 + if (!NT_STATUS_IS_OK(ret)) {
1055 + DEBUG(1, (__location__ ": Connection to %s got an unexpected "
1056 + "RPC packet type - %u, expected %u: %s\n",
1057 + rpccli_pipe_txt(talloc_tos(), cli),
1058 + pkt->ptype, expected_pkt_type,
1059 + nt_errstr(ret)));
1060 + NDR_PRINT_DEBUG(ncacn_packet, pkt);
1061 + return ret;
1062 + }
1063
1064 - /* Client code never receives this kind of packets */
1065 break;
1066
1067 + case DCERPC_PKT_ALTER_RESP:
1068 + ret = dcerpc_verify_ncacn_packet_header(pkt,
1069 + expected_pkt_type,
1070 + pkt->u.alter_resp.auth_info.length,
1071 + DCERPC_PFC_FLAG_FIRST |
1072 + DCERPC_PFC_FLAG_LAST,
1073 + DCERPC_PFC_FLAG_CONC_MPX |
1074 + DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN);
1075 + if (!NT_STATUS_IS_OK(ret)) {
1076 + DEBUG(1, (__location__ ": Connection to %s got an unexpected "
1077 + "RPC packet type - %u, expected %u: %s\n",
1078 + rpccli_pipe_txt(talloc_tos(), cli),
1079 + pkt->ptype, expected_pkt_type,
1080 + nt_errstr(ret)));
1081 + NDR_PRINT_DEBUG(ncacn_packet, pkt);
1082 + return ret;
1083 + }
1084 +
1085 + break;
1086
1087 case DCERPC_PKT_RESPONSE:
1088
1089 r = &pkt->u.response;
1090
1091 + ret = dcerpc_verify_ncacn_packet_header(pkt,
1092 + expected_pkt_type,
1093 + r->stub_and_verifier.length,
1094 + 0, /* required_flags */
1095 + DCERPC_PFC_FLAG_FIRST |
1096 + DCERPC_PFC_FLAG_LAST);
1097 + if (!NT_STATUS_IS_OK(ret)) {
1098 + DEBUG(1, (__location__ ": Connection to %s got an unexpected "
1099 + "RPC packet type - %u, expected %u: %s\n",
1100 + rpccli_pipe_txt(talloc_tos(), cli),
1101 + pkt->ptype, expected_pkt_type,
1102 + nt_errstr(ret)));
1103 + NDR_PRINT_DEBUG(ncacn_packet, pkt);
1104 + return ret;
1105 + }
1106 +
1107 tmp_stub.data = r->stub_and_verifier.data;
1108 tmp_stub.length = r->stub_and_verifier.length;
1109
1110 @@ -449,6 +521,12 @@ static NTSTATUS cli_pipe_validate_current_pdu(TALLOC_CTX *mem_ctx,
1111 DCERPC_RESPONSE_LENGTH,
1112 pdu);
1113 if (!NT_STATUS_IS_OK(ret)) {
1114 + DEBUG(1, (__location__ ": Connection to %s got an unexpected "
1115 + "RPC packet type - %u, expected %u: %s\n",
1116 + rpccli_pipe_txt(talloc_tos(), cli),
1117 + pkt->ptype, expected_pkt_type,
1118 + nt_errstr(ret)));
1119 + NDR_PRINT_DEBUG(ncacn_packet, pkt);
1120 return ret;
1121 }
1122
1123 @@ -478,14 +556,24 @@ static NTSTATUS cli_pipe_validate_current_pdu(TALLOC_CTX *mem_ctx,
1124
1125 break;
1126
1127 - case DCERPC_PKT_BIND_NAK:
1128 - DEBUG(1, (__location__ ": Bind NACK received from %s!\n",
1129 - rpccli_pipe_txt(talloc_tos(), cli)));
1130 - /* Use this for now... */
1131 - return NT_STATUS_NETWORK_ACCESS_DENIED;
1132 -
1133 case DCERPC_PKT_FAULT:
1134
1135 + ret = dcerpc_verify_ncacn_packet_header(pkt,
1136 + DCERPC_PKT_FAULT,
1137 + 0, /* max_auth_info */
1138 + DCERPC_PFC_FLAG_FIRST |
1139 + DCERPC_PFC_FLAG_LAST,
1140 + DCERPC_PFC_FLAG_DID_NOT_EXECUTE);
1141 + if (!NT_STATUS_IS_OK(ret)) {
1142 + DEBUG(1, (__location__ ": Connection to %s got an unexpected "
1143 + "RPC packet type - %u, expected %u: %s\n",
1144 + rpccli_pipe_txt(talloc_tos(), cli),
1145 + pkt->ptype, expected_pkt_type,
1146 + nt_errstr(ret)));
1147 + NDR_PRINT_DEBUG(ncacn_packet, pkt);
1148 + return ret;
1149 + }
1150 +
1151 DEBUG(1, (__location__ ": RPC fault code %s received "
1152 "from %s!\n",
1153 dcerpc_errstr(talloc_tos(),
1154 @@ -502,13 +590,6 @@ static NTSTATUS cli_pipe_validate_current_pdu(TALLOC_CTX *mem_ctx,
1155 return NT_STATUS_RPC_PROTOCOL_ERROR;
1156 }
1157
1158 - if (pkt->ptype != expected_pkt_type) {
1159 - DEBUG(3, (__location__ ": Connection to %s got an unexpected "
1160 - "RPC packet type - %u, not %u\n",
1161 - rpccli_pipe_txt(talloc_tos(), cli),
1162 - pkt->ptype, expected_pkt_type));
1163 - return NT_STATUS_RPC_PROTOCOL_ERROR;
1164 - }
1165
1166 if (pkt->call_id != call_id) {
1167 DEBUG(3, (__location__ ": Connection to %s got an unexpected "
1168 --
1169 2.8.1
1170
1171
1172 From 3e03b1e6d5b20c14d53763f22442bf510a8d6dcd Mon Sep 17 00:00:00 2001
1173 From: Stefan Metzmacher <metze@samba.org>
1174 Date: Fri, 10 Jul 2015 14:48:38 +0200
1175 Subject: [PATCH 14/40] CVE-2015-5370: s3:rpc_client: protect
1176 rpc_api_pipe_got_pdu() against too large payloads
1177 MIME-Version: 1.0
1178 Content-Type: text/plain; charset=UTF-8
1179 Content-Transfer-Encoding: 8bit
1180
1181 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1182
1183 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1184 Reviewed-by: Günther Deschner <gd@samba.org>
1185 (cherry picked from commit 98182969e761429e577064e1a0fd5cbc6b50d7d9)
1186 ---
1187 source3/rpc_client/cli_pipe.c | 5 +++++
1188 1 file changed, 5 insertions(+)
1189
1190 diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c
1191 index 6a22d38..755b458 100644
1192 --- a/source3/rpc_client/cli_pipe.c
1193 +++ b/source3/rpc_client/cli_pipe.c
1194 @@ -1007,6 +1007,11 @@ static void rpc_api_pipe_got_pdu(struct tevent_req *subreq)
1195 return;
1196 }
1197
1198 + if (state->reply_pdu_offset + rdata.length > MAX_RPC_DATA_SIZE) {
1199 + tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER);
1200 + return;
1201 + }
1202 +
1203 /* Now copy the data portion out of the pdu into rbuf. */
1204 if (state->reply_pdu.length < state->reply_pdu_offset + rdata.length) {
1205 if (!data_blob_realloc(NULL, &state->reply_pdu,
1206 --
1207 2.8.1
1208
1209
1210 From fa884c266be5d808d19955f92921417f435b2957 Mon Sep 17 00:00:00 2001
1211 From: Stefan Metzmacher <metze@samba.org>
1212 Date: Tue, 7 Jul 2015 22:51:18 +0200
1213 Subject: [PATCH 15/40] CVE-2015-5370: s3:rpc_client: verify auth_{type,level}
1214 in rpc_pipe_bind_step_one_done()
1215 MIME-Version: 1.0
1216 Content-Type: text/plain; charset=UTF-8
1217 Content-Transfer-Encoding: 8bit
1218
1219 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1220
1221 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1222 Reviewed-by: Günther Deschner <gd@samba.org>
1223 (cherry picked from commit df51c22bea7fbf906613ceb160f16f298b2e3106)
1224 ---
1225 source3/rpc_client/cli_pipe.c | 15 +++++++++++++++
1226 1 file changed, 15 insertions(+)
1227
1228 diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c
1229 index 755b458..1c4ff01 100644
1230 --- a/source3/rpc_client/cli_pipe.c
1231 +++ b/source3/rpc_client/cli_pipe.c
1232 @@ -2039,6 +2039,21 @@ static void rpc_pipe_bind_step_one_done(struct tevent_req *subreq)
1233 tevent_req_nterror(req, status);
1234 return;
1235 }
1236 +
1237 + if (auth.auth_type != pauth->auth_type) {
1238 + DEBUG(0, (__location__ " Auth type %u mismatch expected %u.\n",
1239 + auth.auth_type, pauth->auth_type));
1240 + tevent_req_nterror(req, NT_STATUS_RPC_PROTOCOL_ERROR);
1241 + return;
1242 + }
1243 +
1244 + if (auth.auth_level != pauth->auth_level) {
1245 + DEBUG(0, (__location__ " Auth level %u mismatch expected %u.\n",
1246 + auth.auth_level, pauth->auth_level));
1247 + tevent_req_nterror(req, NT_STATUS_RPC_PROTOCOL_ERROR);
1248 + return;
1249 + }
1250 +
1251 break;
1252 }
1253
1254 --
1255 2.8.1
1256
1257
1258 From 6d2767ad8b084590c572e90d1985ca6d7d36b188 Mon Sep 17 00:00:00 2001
1259 From: Stefan Metzmacher <metze@samba.org>
1260 Date: Tue, 7 Jul 2015 13:05:01 +0200
1261 Subject: [PATCH 16/40] CVE-2015-5370: s3:rpc_server: make use of
1262 dcerpc_pull_auth_trailer() in api_pipe_{bind_req,alter_context,bind_auth3}()
1263 MIME-Version: 1.0
1264 Content-Type: text/plain; charset=UTF-8
1265 Content-Transfer-Encoding: 8bit
1266
1267 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1268
1269 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1270 Reviewed-by: Günther Deschner <gd@samba.org>
1271 (cherry picked from commit 2a92546590a78760d2fe0e63067a3888dbce53be)
1272 ---
1273 source3/rpc_server/srv_pipe.c | 62 +++++++++----------------------------------
1274 1 file changed, 13 insertions(+), 49 deletions(-)
1275
1276 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
1277 index 0ab7dc6..40b1b8e 100644
1278 --- a/source3/rpc_server/srv_pipe.c
1279 +++ b/source3/rpc_server/srv_pipe.c
1280 @@ -1012,25 +1012,12 @@ static bool api_pipe_bind_req(struct pipes_struct *p,
1281 * Check if this is an authenticated bind request.
1282 */
1283 if (pkt->auth_length) {
1284 - /* Quick length check. Won't catch a bad auth footer,
1285 - * prevents overrun. */
1286 -
1287 - if (pkt->frag_length < RPC_HEADER_LEN +
1288 - DCERPC_AUTH_TRAILER_LENGTH +
1289 - pkt->auth_length) {
1290 - DEBUG(0,("api_pipe_bind_req: auth_len (%u) "
1291 - "too long for fragment %u.\n",
1292 - (unsigned int)pkt->auth_length,
1293 - (unsigned int)pkt->frag_length));
1294 - goto err_exit;
1295 - }
1296 -
1297 /*
1298 * Decode the authentication verifier.
1299 */
1300 - status = dcerpc_pull_dcerpc_auth(pkt,
1301 - &pkt->u.bind.auth_info,
1302 - &auth_info, p->endian);
1303 + status = dcerpc_pull_auth_trailer(pkt, pkt,
1304 + &pkt->u.bind.auth_info,
1305 + &auth_info, NULL, true);
1306 if (!NT_STATUS_IS_OK(status)) {
1307 DEBUG(0, ("Unable to unmarshall dcerpc_auth.\n"));
1308 goto err_exit;
1309 @@ -1233,23 +1220,13 @@ bool api_pipe_bind_auth3(struct pipes_struct *p, struct ncacn_packet *pkt)
1310 goto err;
1311 }
1312
1313 - /* Ensure there's enough data for an authenticated request. */
1314 - if (pkt->frag_length < RPC_HEADER_LEN
1315 - + DCERPC_AUTH_TRAILER_LENGTH
1316 - + pkt->auth_length) {
1317 - DEBUG(0,("api_pipe_ntlmssp_auth_process: auth_len "
1318 - "%u is too large.\n",
1319 - (unsigned int)pkt->auth_length));
1320 - goto err;
1321 - }
1322 -
1323 /*
1324 * Decode the authentication verifier response.
1325 */
1326
1327 - status = dcerpc_pull_dcerpc_auth(pkt,
1328 - &pkt->u.auth3.auth_info,
1329 - &auth_info, p->endian);
1330 + status = dcerpc_pull_auth_trailer(pkt, pkt,
1331 + &pkt->u.auth3.auth_info,
1332 + &auth_info, NULL, true);
1333 if (!NT_STATUS_IS_OK(status)) {
1334 DEBUG(0, ("Failed to unmarshall dcerpc_auth.\n"));
1335 goto err;
1336 @@ -1382,34 +1359,21 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
1337 * Check if this is an authenticated alter context request.
1338 */
1339 if (pkt->auth_length) {
1340 - /* Quick length check. Won't catch a bad auth footer,
1341 - * prevents overrun. */
1342 -
1343 - if (pkt->frag_length < RPC_HEADER_LEN +
1344 - DCERPC_AUTH_TRAILER_LENGTH +
1345 - pkt->auth_length) {
1346 - DEBUG(0,("api_pipe_alter_context: auth_len (%u) "
1347 - "too long for fragment %u.\n",
1348 - (unsigned int)pkt->auth_length,
1349 - (unsigned int)pkt->frag_length ));
1350 + /* We can only finish if the pipe is unbound for now */
1351 + if (p->pipe_bound) {
1352 + DEBUG(0, (__location__ ": Pipe already bound, "
1353 + "Altering Context not yet supported!\n"));
1354 goto err_exit;
1355 }
1356
1357 - status = dcerpc_pull_dcerpc_auth(pkt,
1358 - &pkt->u.bind.auth_info,
1359 - &auth_info, p->endian);
1360 + status = dcerpc_pull_auth_trailer(pkt, pkt,
1361 + &pkt->u.bind.auth_info,
1362 + &auth_info, NULL, true);
1363 if (!NT_STATUS_IS_OK(status)) {
1364 DEBUG(0, ("Unable to unmarshall dcerpc_auth.\n"));
1365 goto err_exit;
1366 }
1367
1368 - /* We can only finish if the pipe is unbound for now */
1369 - if (p->pipe_bound) {
1370 - DEBUG(0, (__location__ ": Pipe already bound, "
1371 - "Altering Context not yet supported!\n"));
1372 - goto err_exit;
1373 - }
1374 -
1375 if (auth_info.auth_type != p->auth.auth_type) {
1376 DEBUG(0, ("Auth type mismatch! Client sent %d, "
1377 "but auth was started as type %d!\n",
1378 --
1379 2.8.1
1380
1381
1382 From 7400ac11282d540d4f5f80d0f58ec99beabb7d8e Mon Sep 17 00:00:00 2001
1383 From: Stefan Metzmacher <metze@samba.org>
1384 Date: Wed, 23 Dec 2015 12:38:55 +0100
1385 Subject: [PATCH 17/40] CVE-2015-5370: s3:rpc_server: let a failing
1386 sec_verification_trailer mark the connection as broken
1387
1388 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1389
1390 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1391 (cherry picked from commit 189c0fbb7a3405f0893f23e5b8d755d259f98eaf)
1392 ---
1393 source3/rpc_server/srv_pipe.c | 1 +
1394 1 file changed, 1 insertion(+)
1395
1396 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
1397 index 40b1b8e..da9b91c 100644
1398 --- a/source3/rpc_server/srv_pipe.c
1399 +++ b/source3/rpc_server/srv_pipe.c
1400 @@ -1663,6 +1663,7 @@ static bool api_pipe_request(struct pipes_struct *p,
1401
1402 if (!srv_pipe_check_verification_trailer(p, pkt, pipe_fns)) {
1403 DEBUG(1, ("srv_pipe_check_verification_trailer: failed\n"));
1404 + set_incoming_fault(p);
1405 setup_fault_pdu(p, NT_STATUS(DCERPC_FAULT_ACCESS_DENIED));
1406 data_blob_free(&p->out_data.rdata);
1407 TALLOC_FREE(frame);
1408 --
1409 2.8.1
1410
1411
1412 From 55da4653f5986989e46be6320f96590f8ebb4ef7 Mon Sep 17 00:00:00 2001
1413 From: Stefan Metzmacher <metze@samba.org>
1414 Date: Tue, 7 Jul 2015 13:05:01 +0200
1415 Subject: [PATCH 18/40] CVE-2015-5370: s3:rpc_server: don't ignore failures of
1416 dcerpc_push_ncacn_packet()
1417 MIME-Version: 1.0
1418 Content-Type: text/plain; charset=UTF-8
1419 Content-Transfer-Encoding: 8bit
1420
1421 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1422
1423 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1424 Reviewed-by: Günther Deschner <gd@samba.org>
1425 (cherry picked from commit 25bf597124f217c55b5ca71a5ea9cb0ea83943e5)
1426 ---
1427 source3/rpc_server/srv_pipe.c | 2 ++
1428 1 file changed, 2 insertions(+)
1429
1430 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
1431 index da9b91c..71b4665 100644
1432 --- a/source3/rpc_server/srv_pipe.c
1433 +++ b/source3/rpc_server/srv_pipe.c
1434 @@ -1152,6 +1152,7 @@ static bool api_pipe_bind_req(struct pipes_struct *p,
1435 if (!NT_STATUS_IS_OK(status)) {
1436 DEBUG(0, ("Failed to marshall bind_ack packet. (%s)\n",
1437 nt_errstr(status)));
1438 + goto err_exit;
1439 }
1440
1441 if (auth_resp.length) {
1442 @@ -1469,6 +1470,7 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
1443 if (!NT_STATUS_IS_OK(status)) {
1444 DEBUG(0, ("Failed to marshall bind_ack packet. (%s)\n",
1445 nt_errstr(status)));
1446 + goto err_exit;
1447 }
1448
1449 if (auth_resp.length) {
1450 --
1451 2.8.1
1452
1453
1454 From 893c840a1aac6711a081eb8e25f2c2a6078fc373 Mon Sep 17 00:00:00 2001
1455 From: Stefan Metzmacher <metze@samba.org>
1456 Date: Tue, 7 Jul 2015 13:05:01 +0200
1457 Subject: [PATCH 19/40] CVE-2015-5370: s3:rpc_server: don't allow auth3 if the
1458 authentication was already finished
1459 MIME-Version: 1.0
1460 Content-Type: text/plain; charset=UTF-8
1461 Content-Transfer-Encoding: 8bit
1462
1463 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1464
1465 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1466 Reviewed-by: Günther Deschner <gd@samba.org>
1467 (cherry picked from commit 69280e6acef7c3941407d4308b659c5e90ed702d)
1468 ---
1469 source3/rpc_server/srv_pipe.c | 9 ++++++++-
1470 1 file changed, 8 insertions(+), 1 deletion(-)
1471
1472 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
1473 index 71b4665..4e5b50d4 100644
1474 --- a/source3/rpc_server/srv_pipe.c
1475 +++ b/source3/rpc_server/srv_pipe.c
1476 @@ -1216,8 +1216,15 @@ bool api_pipe_bind_auth3(struct pipes_struct *p, struct ncacn_packet *pkt)
1477
1478 DEBUG(5, ("api_pipe_bind_auth3: decode request. %d\n", __LINE__));
1479
1480 + /* We can only finish if the pipe is unbound for now */
1481 + if (p->pipe_bound) {
1482 + DEBUG(0, (__location__ ": Pipe already bound, "
1483 + "AUTH3 not supported!\n"));
1484 + goto err;
1485 + }
1486 +
1487 if (pkt->auth_length == 0) {
1488 - DEBUG(0, ("No auth field sent for bind request!\n"));
1489 + DEBUG(1, ("No auth field sent for auth3 request!\n"));
1490 goto err;
1491 }
1492
1493 --
1494 2.8.1
1495
1496
1497 From a66baed0c65b7acb4d76ef9ea3ae1248a6b5773a Mon Sep 17 00:00:00 2001
1498 From: Stefan Metzmacher <metze@samba.org>
1499 Date: Tue, 14 Jul 2015 16:18:45 +0200
1500 Subject: [PATCH 20/40] CVE-2015-5370: s3:rpc_server: let a failing auth3 mark
1501 the authentication as invalid
1502 MIME-Version: 1.0
1503 Content-Type: text/plain; charset=UTF-8
1504 Content-Transfer-Encoding: 8bit
1505
1506 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1507
1508 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1509 Reviewed-by: Günther Deschner <gd@samba.org>
1510 (cherry picked from commit 8c96ef7b4fbd925607b26d351b14ad9a95febd88)
1511 ---
1512 source3/rpc_server/srv_pipe.c | 2 +-
1513 1 file changed, 1 insertion(+), 1 deletion(-)
1514
1515 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
1516 index 4e5b50d4..d28ba8e 100644
1517 --- a/source3/rpc_server/srv_pipe.c
1518 +++ b/source3/rpc_server/srv_pipe.c
1519 @@ -1304,7 +1304,7 @@ bool api_pipe_bind_auth3(struct pipes_struct *p, struct ncacn_packet *pkt)
1520 return true;
1521
1522 err:
1523 -
1524 + p->pipe_bound = false;
1525 TALLOC_FREE(p->auth.auth_ctx);
1526 return false;
1527 }
1528 --
1529 2.8.1
1530
1531
1532 From e47becdf2c03d68662ab998c4608adb371ca2f08 Mon Sep 17 00:00:00 2001
1533 From: Stefan Metzmacher <metze@samba.org>
1534 Date: Tue, 7 Jul 2015 13:05:01 +0200
1535 Subject: [PATCH 21/40] CVE-2015-5370: s3:rpc_server: make sure auth_level
1536 isn't changed by alter_context or auth3
1537 MIME-Version: 1.0
1538 Content-Type: text/plain; charset=UTF-8
1539 Content-Transfer-Encoding: 8bit
1540
1541 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1542
1543 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1544 Reviewed-by: Günther Deschner <gd@samba.org>
1545 (cherry picked from commit 63d21d2546a1064be73582a499ec15b0e11e2708)
1546 ---
1547 source3/rpc_server/srv_pipe.c | 13 +++++++++++++
1548 1 file changed, 13 insertions(+)
1549
1550 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
1551 index d28ba8e..1b81a4c 100644
1552 --- a/source3/rpc_server/srv_pipe.c
1553 +++ b/source3/rpc_server/srv_pipe.c
1554 @@ -1252,6 +1252,13 @@ bool api_pipe_bind_auth3(struct pipes_struct *p, struct ncacn_packet *pkt)
1555 goto err;
1556 }
1557
1558 + if (auth_info.auth_level != p->auth.auth_level) {
1559 + DEBUG(1, ("Auth level mismatch! Client sent %d, "
1560 + "but auth was started as level %d!\n",
1561 + auth_info.auth_level, p->auth.auth_level));
1562 + goto err;
1563 + }
1564 +
1565 switch (auth_info.auth_type) {
1566 case DCERPC_AUTH_TYPE_NTLMSSP:
1567 ntlmssp_ctx = talloc_get_type_abort(p->auth.auth_ctx,
1568 @@ -1389,6 +1396,12 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
1569 goto err_exit;
1570 }
1571
1572 + if (auth_info.auth_level != p->auth.auth_level) {
1573 + DEBUG(0, ("Auth level mismatch! Client sent %d, "
1574 + "but auth was started as level %d!\n",
1575 + auth_info.auth_level, p->auth.auth_level));
1576 + goto err_exit;
1577 + }
1578
1579 switch (auth_info.auth_type) {
1580 case DCERPC_AUTH_TYPE_SPNEGO:
1581 --
1582 2.8.1
1583
1584
1585 From 687a4801391c946a62d07a7bdad096a97da0d432 Mon Sep 17 00:00:00 2001
1586 From: Jeremy Allison <jra@samba.org>
1587 Date: Tue, 7 Jul 2015 09:15:39 +0200
1588 Subject: [PATCH 22/40] CVE-2015-5370: s3:rpc_server: ensure that the message
1589 ordering doesn't violate the spec
1590 MIME-Version: 1.0
1591 Content-Type: text/plain; charset=UTF-8
1592 Content-Transfer-Encoding: 8bit
1593
1594 The first pdu is always a BIND.
1595
1596 REQUEST pdus are only allowed once the authentication
1597 is finished.
1598
1599 A simple anonymous authentication is finished after the BIND.
1600 Real authentication may need additional ALTER or AUTH3 exchanges.
1601
1602 Pair-Programmed-With: Stefan Metzmacher <metze@samba.org>
1603
1604 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1605
1606 Signed-off-by: Jeremy Allison <jra@samba.org>
1607 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1608 Reviewed-by: Günther Deschner <gd@samba.org>
1609 (cherry picked from commit 0239bfa562ee303c4ac204375b3c66ca287f6cb0)
1610 ---
1611 source3/include/ntdomain.h | 7 ++++++
1612 source3/rpc_server/rpc_ncacn_np.c | 1 +
1613 source3/rpc_server/rpc_server.c | 1 +
1614 source3/rpc_server/srv_pipe.c | 51 ++++++++++++++++++++++++++++++++++-----
1615 4 files changed, 54 insertions(+), 6 deletions(-)
1616
1617 diff --git a/source3/include/ntdomain.h b/source3/include/ntdomain.h
1618 index 650f1d0..b3c5451 100644
1619 --- a/source3/include/ntdomain.h
1620 +++ b/source3/include/ntdomain.h
1621 @@ -139,6 +139,13 @@ struct pipes_struct {
1622 bool pipe_bound;
1623
1624 /*
1625 + * States we can be in.
1626 + */
1627 + bool allow_alter;
1628 + bool allow_bind;
1629 + bool allow_auth3;
1630 +
1631 + /*
1632 * Set the DCERPC_FAULT to return.
1633 */
1634
1635 diff --git a/source3/rpc_server/rpc_ncacn_np.c b/source3/rpc_server/rpc_ncacn_np.c
1636 index efdee27..f2e9d10 100644
1637 --- a/source3/rpc_server/rpc_ncacn_np.c
1638 +++ b/source3/rpc_server/rpc_ncacn_np.c
1639 @@ -171,6 +171,7 @@ struct pipes_struct *make_internal_rpc_pipe_p(TALLOC_CTX *mem_ctx,
1640
1641 p->syntax = *syntax;
1642 p->transport = NCALRPC;
1643 + p->allow_bind = true;
1644
1645 DEBUG(4,("Created internal pipe %s (pipes_open=%d)\n",
1646 get_pipe_name_from_syntax(talloc_tos(), syntax), pipes_open));
1647 diff --git a/source3/rpc_server/rpc_server.c b/source3/rpc_server/rpc_server.c
1648 index 8ec55bb..376d26a 100644
1649 --- a/source3/rpc_server/rpc_server.c
1650 +++ b/source3/rpc_server/rpc_server.c
1651 @@ -102,6 +102,7 @@ static int make_server_pipes_struct(TALLOC_CTX *mem_ctx,
1652 p->syntax = id;
1653 p->transport = transport;
1654 p->ncalrpc_as_system = ncalrpc_as_system;
1655 + p->allow_bind = true;
1656
1657 p->mem_ctx = talloc_named(p, 0, "pipe %s %p", pipe_name, p);
1658 if (!p->mem_ctx) {
1659 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
1660 index 1b81a4c..41111aa 100644
1661 --- a/source3/rpc_server/srv_pipe.c
1662 +++ b/source3/rpc_server/srv_pipe.c
1663 @@ -279,6 +279,9 @@ static bool setup_bind_nak(struct pipes_struct *p, struct ncacn_packet *pkt)
1664 p->auth.auth_level = DCERPC_AUTH_LEVEL_NONE;
1665 p->auth.auth_type = DCERPC_AUTH_TYPE_NONE;
1666 p->pipe_bound = False;
1667 + p->allow_bind = false;
1668 + p->allow_alter = false;
1669 + p->allow_auth3 = false;
1670
1671 return True;
1672 }
1673 @@ -828,6 +831,11 @@ static NTSTATUS pipe_auth_verify_final(struct pipes_struct *p)
1674 void *mech_ctx;
1675 NTSTATUS status;
1676
1677 + if (p->auth.auth_type == DCERPC_AUTH_TYPE_NONE) {
1678 + p->pipe_bound = true;
1679 + return NT_STATUS_OK;
1680 + }
1681 +
1682 switch (p->auth.auth_type) {
1683 case DCERPC_AUTH_TYPE_NTLMSSP:
1684 ntlmssp_ctx = talloc_get_type_abort(p->auth.auth_ctx,
1685 @@ -919,13 +927,11 @@ static bool api_pipe_bind_req(struct pipes_struct *p,
1686 DATA_BLOB auth_resp = data_blob_null;
1687 DATA_BLOB auth_blob = data_blob_null;
1688
1689 - /* No rebinds on a bound pipe - use alter context. */
1690 - if (p->pipe_bound) {
1691 - DEBUG(2,("api_pipe_bind_req: rejecting bind request on bound "
1692 - "pipe %s.\n",
1693 - get_pipe_name_from_syntax(talloc_tos(), &p->syntax)));
1694 + if (!p->allow_bind) {
1695 + DEBUG(2,("Pipe not in allow bind state\n"));
1696 return setup_bind_nak(p, pkt);
1697 }
1698 + p->allow_bind = false;
1699
1700 if (pkt->u.bind.num_contexts == 0) {
1701 DEBUG(0, ("api_pipe_bind_req: no rpc contexts around\n"));
1702 @@ -1192,6 +1198,22 @@ static bool api_pipe_bind_req(struct pipes_struct *p,
1703 p->out_data.current_pdu_sent = 0;
1704
1705 TALLOC_FREE(auth_blob.data);
1706 +
1707 + if (bind_ack_ctx.result == 0) {
1708 + p->allow_alter = true;
1709 + p->allow_auth3 = true;
1710 + if (p->auth.auth_type == DCERPC_AUTH_TYPE_NONE) {
1711 + status = pipe_auth_verify_final(p);
1712 + if (!NT_STATUS_IS_OK(status)) {
1713 + DEBUG(0, ("pipe_auth_verify_final failed: %s\n",
1714 + nt_errstr(status)));
1715 + goto err_exit;
1716 + }
1717 + }
1718 + } else {
1719 + goto err_exit;
1720 + }
1721 +
1722 return True;
1723
1724 err_exit:
1725 @@ -1216,6 +1238,11 @@ bool api_pipe_bind_auth3(struct pipes_struct *p, struct ncacn_packet *pkt)
1726
1727 DEBUG(5, ("api_pipe_bind_auth3: decode request. %d\n", __LINE__));
1728
1729 + if (!p->allow_auth3) {
1730 + DEBUG(1, ("Pipe not in allow auth3 state.\n"));
1731 + goto err;
1732 + }
1733 +
1734 /* We can only finish if the pipe is unbound for now */
1735 if (p->pipe_bound) {
1736 DEBUG(0, (__location__ ": Pipe already bound, "
1737 @@ -1312,6 +1339,10 @@ bool api_pipe_bind_auth3(struct pipes_struct *p, struct ncacn_packet *pkt)
1738
1739 err:
1740 p->pipe_bound = false;
1741 + p->allow_bind = false;
1742 + p->allow_alter = false;
1743 + p->allow_auth3 = false;
1744 +
1745 TALLOC_FREE(p->auth.auth_ctx);
1746 return false;
1747 }
1748 @@ -1338,6 +1369,11 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
1749
1750 DEBUG(5,("api_pipe_alter_context: make response. %d\n", __LINE__));
1751
1752 + if (!p->allow_alter) {
1753 + DEBUG(1, ("Pipe not in allow alter state.\n"));
1754 + goto err_exit;
1755 + }
1756 +
1757 if (pkt->u.bind.assoc_group_id != 0) {
1758 assoc_gid = pkt->u.bind.assoc_group_id;
1759 } else {
1760 @@ -1363,7 +1399,6 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
1761 bind_ack_ctx.reason = 0;
1762 bind_ack_ctx.syntax = pkt->u.bind.ctx_list[0].transfer_syntaxes[0];
1763 } else {
1764 - p->pipe_bound = False;
1765 /* Rejection reason: abstract syntax not supported */
1766 bind_ack_ctx.result = DCERPC_BIND_PROVIDER_REJECT;
1767 bind_ack_ctx.reason = DCERPC_BIND_REASON_ASYNTAX;
1768 @@ -1826,6 +1861,10 @@ void set_incoming_fault(struct pipes_struct *p)
1769 p->in_data.pdu.length = 0;
1770 p->fault_state = DCERPC_FAULT_CANT_PERFORM;
1771
1772 + p->allow_alter = false;
1773 + p->allow_auth3 = false;
1774 + p->pipe_bound = false;
1775 +
1776 DEBUG(10, ("Setting fault state\n"));
1777 }
1778
1779 --
1780 2.8.1
1781
1782
1783 From 45701966d49ec1003f19c137a548c26915f75a99 Mon Sep 17 00:00:00 2001
1784 From: Stefan Metzmacher <metze@samba.org>
1785 Date: Tue, 7 Jul 2015 16:06:59 +0200
1786 Subject: [PATCH 23/40] CVE-2015-5370: s3:rpc_server: use 'alter' instead of
1787 'bind' for variables in api_pipe_alter_context()
1788 MIME-Version: 1.0
1789 Content-Type: text/plain; charset=UTF-8
1790 Content-Transfer-Encoding: 8bit
1791
1792 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1793
1794 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1795 Reviewed-by: Günther Deschner <gd@samba.org>
1796 (cherry picked from commit cdefee174d2f8920323e9e62966df4f4ced49ed3)
1797 ---
1798 source3/rpc_server/srv_pipe.c | 32 ++++++++++++++++----------------
1799 1 file changed, 16 insertions(+), 16 deletions(-)
1800
1801 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
1802 index 41111aa..382d94a 100644
1803 --- a/source3/rpc_server/srv_pipe.c
1804 +++ b/source3/rpc_server/srv_pipe.c
1805 @@ -1359,7 +1359,7 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
1806 uint16 assoc_gid;
1807 NTSTATUS status;
1808 union dcerpc_payload u;
1809 - struct dcerpc_ack_ctx bind_ack_ctx;
1810 + struct dcerpc_ack_ctx alter_ack_ctx;
1811 DATA_BLOB auth_resp = data_blob_null;
1812 DATA_BLOB auth_blob = data_blob_null;
1813 int pad_len = 0;
1814 @@ -1374,8 +1374,8 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
1815 goto err_exit;
1816 }
1817
1818 - if (pkt->u.bind.assoc_group_id != 0) {
1819 - assoc_gid = pkt->u.bind.assoc_group_id;
1820 + if (pkt->u.alter.assoc_group_id != 0) {
1821 + assoc_gid = pkt->u.alter.assoc_group_id;
1822 } else {
1823 assoc_gid = 0x53f0;
1824 }
1825 @@ -1385,24 +1385,24 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
1826 */
1827
1828 /* If the requested abstract synt uuid doesn't match our client pipe,
1829 - reject the bind_ack & set the transfer interface synt to all 0's,
1830 + reject the alter_ack & set the transfer interface synt to all 0's,
1831 ver 0 (observed when NT5 attempts to bind to abstract interfaces
1832 unknown to NT4)
1833 Needed when adding entries to a DACL from NT5 - SK */
1834
1835 if (check_bind_req(p,
1836 - &pkt->u.bind.ctx_list[0].abstract_syntax,
1837 - &pkt->u.bind.ctx_list[0].transfer_syntaxes[0],
1838 - pkt->u.bind.ctx_list[0].context_id)) {
1839 + &pkt->u.alter.ctx_list[0].abstract_syntax,
1840 + &pkt->u.alter.ctx_list[0].transfer_syntaxes[0],
1841 + pkt->u.alter.ctx_list[0].context_id)) {
1842
1843 - bind_ack_ctx.result = 0;
1844 - bind_ack_ctx.reason = 0;
1845 - bind_ack_ctx.syntax = pkt->u.bind.ctx_list[0].transfer_syntaxes[0];
1846 + alter_ack_ctx.result = 0;
1847 + alter_ack_ctx.reason = 0;
1848 + alter_ack_ctx.syntax = pkt->u.alter.ctx_list[0].transfer_syntaxes[0];
1849 } else {
1850 /* Rejection reason: abstract syntax not supported */
1851 - bind_ack_ctx.result = DCERPC_BIND_PROVIDER_REJECT;
1852 - bind_ack_ctx.reason = DCERPC_BIND_REASON_ASYNTAX;
1853 - bind_ack_ctx.syntax = null_ndr_syntax_id;
1854 + alter_ack_ctx.result = DCERPC_BIND_PROVIDER_REJECT;
1855 + alter_ack_ctx.reason = DCERPC_BIND_REASON_ASYNTAX;
1856 + alter_ack_ctx.syntax = null_ndr_syntax_id;
1857 }
1858
1859 /*
1860 @@ -1417,7 +1417,7 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
1861 }
1862
1863 status = dcerpc_pull_auth_trailer(pkt, pkt,
1864 - &pkt->u.bind.auth_info,
1865 + &pkt->u.alter.auth_info,
1866 &auth_info, NULL, true);
1867 if (!NT_STATUS_IS_OK(status)) {
1868 DEBUG(0, ("Unable to unmarshall dcerpc_auth.\n"));
1869 @@ -1503,7 +1503,7 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
1870 u.alter_resp.secondary_address_size = 1;
1871
1872 u.alter_resp.num_results = 1;
1873 - u.alter_resp.ctx_list = &bind_ack_ctx;
1874 + u.alter_resp.ctx_list = &alter_ack_ctx;
1875
1876 /* NOTE: We leave the auth_info empty so we can calculate the padding
1877 * later and then append the auth_info --simo */
1878 @@ -1523,7 +1523,7 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
1879 &u,
1880 &p->out_data.frag);
1881 if (!NT_STATUS_IS_OK(status)) {
1882 - DEBUG(0, ("Failed to marshall bind_ack packet. (%s)\n",
1883 + DEBUG(0, ("Failed to marshall alter_resp packet. (%s)\n",
1884 nt_errstr(status)));
1885 goto err_exit;
1886 }
1887 --
1888 2.8.1
1889
1890
1891 From 62b936e134a53662601b0f614f95dbca5ff7a369 Mon Sep 17 00:00:00 2001
1892 From: Stefan Metzmacher <metze@samba.org>
1893 Date: Tue, 7 Jul 2015 16:06:59 +0200
1894 Subject: [PATCH 24/40] CVE-2015-5370: s3:rpc_server: verify presentation
1895 context arrays
1896 MIME-Version: 1.0
1897 Content-Type: text/plain; charset=UTF-8
1898 Content-Transfer-Encoding: 8bit
1899
1900 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1901
1902 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1903 Reviewed-by: Günther Deschner <gd@samba.org>
1904 (cherry picked from commit 1e6b4abac14840e4cee1afc5d4811b0f0277eade)
1905 ---
1906 source3/rpc_server/srv_pipe.c | 17 ++++++++++++++++-
1907 1 file changed, 16 insertions(+), 1 deletion(-)
1908
1909 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
1910 index 382d94a..335af2a 100644
1911 --- a/source3/rpc_server/srv_pipe.c
1912 +++ b/source3/rpc_server/srv_pipe.c
1913 @@ -934,7 +934,12 @@ static bool api_pipe_bind_req(struct pipes_struct *p,
1914 p->allow_bind = false;
1915
1916 if (pkt->u.bind.num_contexts == 0) {
1917 - DEBUG(0, ("api_pipe_bind_req: no rpc contexts around\n"));
1918 + DEBUG(1, ("api_pipe_bind_req: no rpc contexts around\n"));
1919 + goto err_exit;
1920 + }
1921 +
1922 + if (pkt->u.bind.ctx_list[0].num_transfer_syntaxes == 0) {
1923 + DEBUG(1, ("api_pipe_bind_req: no transfer syntaxes around\n"));
1924 goto err_exit;
1925 }
1926
1927 @@ -1374,6 +1379,16 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
1928 goto err_exit;
1929 }
1930
1931 + if (pkt->u.alter.num_contexts == 0) {
1932 + DEBUG(1, ("api_pipe_alter_context: no rpc contexts around\n"));
1933 + goto err_exit;
1934 + }
1935 +
1936 + if (pkt->u.alter.ctx_list[0].num_transfer_syntaxes == 0) {
1937 + DEBUG(1, ("api_pipe_alter_context: no transfer syntaxes around\n"));
1938 + goto err_exit;
1939 + }
1940 +
1941 if (pkt->u.alter.assoc_group_id != 0) {
1942 assoc_gid = pkt->u.alter.assoc_group_id;
1943 } else {
1944 --
1945 2.8.1
1946
1947
1948 From 585e8aefafcb5f8c501cdf4454b375ebda82f7a6 Mon Sep 17 00:00:00 2001
1949 From: Stefan Metzmacher <metze@samba.org>
1950 Date: Tue, 7 Jul 2015 16:06:59 +0200
1951 Subject: [PATCH 25/40] CVE-2015-5370: s3:rpc_server: make use of
1952 dcerpc_verify_ncacn_packet_header() to verify incoming pdus
1953 MIME-Version: 1.0
1954 Content-Type: text/plain; charset=UTF-8
1955 Content-Transfer-Encoding: 8bit
1956
1957 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
1958
1959 Signed-off-by: Stefan Metzmacher <metze@samba.org>
1960 Reviewed-by: Günther Deschner <gd@samba.org>
1961 (cherry picked from commit e39fdceb25fc75b6f8c77c097bf8dbd2f4286618)
1962 ---
1963 source3/rpc_server/srv_pipe.c | 81 +++++++++++++++++++++++++++++++++++++++++++
1964 1 file changed, 81 insertions(+)
1965
1966 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
1967 index 335af2a..2f404b4 100644
1968 --- a/source3/rpc_server/srv_pipe.c
1969 +++ b/source3/rpc_server/srv_pipe.c
1970 @@ -42,6 +42,7 @@
1971 #include "auth.h"
1972 #include "ntdomain.h"
1973 #include "rpc_server/srv_pipe.h"
1974 +#include "../librpc/gen_ndr/ndr_dcerpc.h"
1975 #include "../librpc/ndr/ndr_dcerpc.h"
1976 #include "../librpc/gen_ndr/ndr_samr.h"
1977 #include "../librpc/gen_ndr/ndr_lsa.h"
1978 @@ -933,6 +934,25 @@ static bool api_pipe_bind_req(struct pipes_struct *p,
1979 }
1980 p->allow_bind = false;
1981
1982 + status = dcerpc_verify_ncacn_packet_header(pkt,
1983 + DCERPC_PKT_BIND,
1984 + pkt->u.bind.auth_info.length,
1985 + 0, /* required flags */
1986 + DCERPC_PFC_FLAG_FIRST |
1987 + DCERPC_PFC_FLAG_LAST |
1988 + DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN |
1989 + 0x08 | /* this is not defined, but should be ignored */
1990 + DCERPC_PFC_FLAG_CONC_MPX |
1991 + DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
1992 + DCERPC_PFC_FLAG_MAYBE |
1993 + DCERPC_PFC_FLAG_OBJECT_UUID);
1994 + if (!NT_STATUS_IS_OK(status)) {
1995 + DEBUG(1, ("api_pipe_bind_req: invalid pdu: %s\n",
1996 + nt_errstr(status)));
1997 + NDR_PRINT_DEBUG(ncacn_packet, pkt);
1998 + goto err_exit;
1999 + }
2000 +
2001 if (pkt->u.bind.num_contexts == 0) {
2002 DEBUG(1, ("api_pipe_bind_req: no rpc contexts around\n"));
2003 goto err_exit;
2004 @@ -1248,6 +1268,25 @@ bool api_pipe_bind_auth3(struct pipes_struct *p, struct ncacn_packet *pkt)
2005 goto err;
2006 }
2007
2008 + status = dcerpc_verify_ncacn_packet_header(pkt,
2009 + DCERPC_PKT_AUTH3,
2010 + pkt->u.auth3.auth_info.length,
2011 + 0, /* required flags */
2012 + DCERPC_PFC_FLAG_FIRST |
2013 + DCERPC_PFC_FLAG_LAST |
2014 + DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN |
2015 + 0x08 | /* this is not defined, but should be ignored */
2016 + DCERPC_PFC_FLAG_CONC_MPX |
2017 + DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
2018 + DCERPC_PFC_FLAG_MAYBE |
2019 + DCERPC_PFC_FLAG_OBJECT_UUID);
2020 + if (!NT_STATUS_IS_OK(status)) {
2021 + DEBUG(1, ("api_pipe_bind_auth3: invalid pdu: %s\n",
2022 + nt_errstr(status)));
2023 + NDR_PRINT_DEBUG(ncacn_packet, pkt);
2024 + goto err;
2025 + }
2026 +
2027 /* We can only finish if the pipe is unbound for now */
2028 if (p->pipe_bound) {
2029 DEBUG(0, (__location__ ": Pipe already bound, "
2030 @@ -1379,6 +1418,25 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
2031 goto err_exit;
2032 }
2033
2034 + status = dcerpc_verify_ncacn_packet_header(pkt,
2035 + DCERPC_PKT_ALTER,
2036 + pkt->u.alter.auth_info.length,
2037 + 0, /* required flags */
2038 + DCERPC_PFC_FLAG_FIRST |
2039 + DCERPC_PFC_FLAG_LAST |
2040 + DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN |
2041 + 0x08 | /* this is not defined, but should be ignored */
2042 + DCERPC_PFC_FLAG_CONC_MPX |
2043 + DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
2044 + DCERPC_PFC_FLAG_MAYBE |
2045 + DCERPC_PFC_FLAG_OBJECT_UUID);
2046 + if (!NT_STATUS_IS_OK(status)) {
2047 + DEBUG(1, ("api_pipe_alter_context: invalid pdu: %s\n",
2048 + nt_errstr(status)));
2049 + NDR_PRINT_DEBUG(ncacn_packet, pkt);
2050 + goto err_exit;
2051 + }
2052 +
2053 if (pkt->u.alter.num_contexts == 0) {
2054 DEBUG(1, ("api_pipe_alter_context: no rpc contexts around\n"));
2055 goto err_exit;
2056 @@ -1923,6 +1981,29 @@ static bool process_request_pdu(struct pipes_struct *p, struct ncacn_packet *pkt
2057 return False;
2058 }
2059
2060 + /*
2061 + * We don't ignore DCERPC_PFC_FLAG_PENDING_CANCEL.
2062 + * TODO: we can reject it with DCERPC_FAULT_NO_CALL_ACTIVE later.
2063 + */
2064 + status = dcerpc_verify_ncacn_packet_header(pkt,
2065 + DCERPC_PKT_REQUEST,
2066 + pkt->u.request.stub_and_verifier.length,
2067 + 0, /* required_flags */
2068 + DCERPC_PFC_FLAG_FIRST |
2069 + DCERPC_PFC_FLAG_LAST |
2070 + 0x08 | /* this is not defined, but should be ignored */
2071 + DCERPC_PFC_FLAG_CONC_MPX |
2072 + DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
2073 + DCERPC_PFC_FLAG_MAYBE |
2074 + DCERPC_PFC_FLAG_OBJECT_UUID);
2075 + if (!NT_STATUS_IS_OK(status)) {
2076 + DEBUG(1, ("process_request_pdu: invalid pdu: %s\n",
2077 + nt_errstr(status)));
2078 + NDR_PRINT_DEBUG(ncacn_packet, pkt);
2079 + set_incoming_fault(p);
2080 + return false;
2081 + }
2082 +
2083 /* Store the opnum */
2084 p->opnum = pkt->u.request.opnum;
2085
2086 --
2087 2.8.1
2088
2089
2090 From b16b1a5f331adc3bb2f3d0bee586ec084935a202 Mon Sep 17 00:00:00 2001
2091 From: Stefan Metzmacher <metze@samba.org>
2092 Date: Wed, 23 Dec 2015 12:40:58 +0100
2093 Subject: [PATCH 26/40] CVE-2015-5370: s3:rpc_server: disconnect the connection
2094 after a fatal FAULT pdu
2095 MIME-Version: 1.0
2096 Content-Type: text/plain; charset=UTF-8
2097 Content-Transfer-Encoding: 8bit
2098
2099 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2100
2101 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2102 Reviewed-by: Günther Deschner <gd@samba.org>
2103 (cherry picked from commit 664d7ace0e68b42d2de99583757e0a985647eb4b)
2104 ---
2105 source3/rpc_server/rpc_server.c | 12 ++++++++++++
2106 1 file changed, 12 insertions(+)
2107
2108 diff --git a/source3/rpc_server/rpc_server.c b/source3/rpc_server/rpc_server.c
2109 index 376d26a..3ba83e0 100644
2110 --- a/source3/rpc_server/rpc_server.c
2111 +++ b/source3/rpc_server/rpc_server.c
2112 @@ -664,6 +664,12 @@ static void named_pipe_packet_done(struct tevent_req *subreq)
2113 goto fail;
2114 }
2115
2116 + if (npc->p->fault_state != 0) {
2117 + DEBUG(2, ("Disconnect after fault\n"));
2118 + sys_errno = EINVAL;
2119 + goto fail;
2120 + }
2121 +
2122 /* clear out any data that may have been left around */
2123 npc->count = 0;
2124 TALLOC_FREE(npc->iov);
2125 @@ -1392,6 +1398,12 @@ static void dcerpc_ncacn_packet_done(struct tevent_req *subreq)
2126 goto fail;
2127 }
2128
2129 + if (ncacn_conn->p->fault_state != 0) {
2130 + DEBUG(2, ("Disconnect after fault\n"));
2131 + sys_errno = EINVAL;
2132 + goto fail;
2133 + }
2134 +
2135 /* clear out any data that may have been left around */
2136 ncacn_conn->count = 0;
2137 TALLOC_FREE(ncacn_conn->iov);
2138 --
2139 2.8.1
2140
2141
2142 From 642d2b7090e46a87bc94cabf29eccb09e329c125 Mon Sep 17 00:00:00 2001
2143 From: Stefan Metzmacher <metze@samba.org>
2144 Date: Wed, 23 Dec 2015 12:38:55 +0100
2145 Subject: [PATCH 27/40] CVE-2015-5370: s3:rpc_server: let a failing BIND mark
2146 the connection as broken
2147 MIME-Version: 1.0
2148 Content-Type: text/plain; charset=UTF-8
2149 Content-Transfer-Encoding: 8bit
2150
2151 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2152
2153 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2154 Reviewed-by: Günther Deschner <gd@samba.org>
2155 (cherry picked from commit 8d97085efd8782e48d0f1162e3f56756acb99472)
2156 ---
2157 source3/rpc_server/srv_pipe.c | 1 +
2158 1 file changed, 1 insertion(+)
2159
2160 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
2161 index 2f404b4..6275190 100644
2162 --- a/source3/rpc_server/srv_pipe.c
2163 +++ b/source3/rpc_server/srv_pipe.c
2164 @@ -276,6 +276,7 @@ static bool setup_bind_nak(struct pipes_struct *p, struct ncacn_packet *pkt)
2165 p->out_data.data_sent_length = 0;
2166 p->out_data.current_pdu_sent = 0;
2167
2168 + set_incoming_fault(p);
2169 TALLOC_FREE(p->auth.auth_ctx);
2170 p->auth.auth_level = DCERPC_AUTH_LEVEL_NONE;
2171 p->auth.auth_type = DCERPC_AUTH_TYPE_NONE;
2172 --
2173 2.8.1
2174
2175
2176 From f4aa07176636982d9be3c0ce2452fc43a8781d47 Mon Sep 17 00:00:00 2001
2177 From: Stefan Metzmacher <metze@samba.org>
2178 Date: Wed, 23 Dec 2015 12:38:55 +0100
2179 Subject: [PATCH 28/40] CVE-2015-5370: s3:rpc_server: use
2180 DCERPC_NCA_S_PROTO_ERROR FAULTs for protocol errors
2181 MIME-Version: 1.0
2182 Content-Type: text/plain; charset=UTF-8
2183 Content-Transfer-Encoding: 8bit
2184
2185 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2186
2187 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2188 Reviewed-by: Günther Deschner <gd@samba.org>
2189 (cherry picked from commit d30363f08efb81b22055d4445977c96df3737adf)
2190 ---
2191 source3/rpc_server/srv_pipe.c | 4 ++--
2192 1 file changed, 2 insertions(+), 2 deletions(-)
2193
2194 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
2195 index 6275190..3fb8855 100644
2196 --- a/source3/rpc_server/srv_pipe.c
2197 +++ b/source3/rpc_server/srv_pipe.c
2198 @@ -1933,7 +1933,7 @@ void set_incoming_fault(struct pipes_struct *p)
2199 data_blob_free(&p->in_data.data);
2200 p->in_data.pdu_needed_len = 0;
2201 p->in_data.pdu.length = 0;
2202 - p->fault_state = DCERPC_FAULT_CANT_PERFORM;
2203 + p->fault_state = DCERPC_NCA_S_PROTO_ERROR;
2204
2205 p->allow_alter = false;
2206 p->allow_auth3 = false;
2207 @@ -2254,7 +2254,7 @@ done:
2208 "pipe %s\n", get_pipe_name_from_syntax(talloc_tos(),
2209 &p->syntax)));
2210 set_incoming_fault(p);
2211 - setup_fault_pdu(p, NT_STATUS(DCERPC_FAULT_OP_RNG_ERROR));
2212 + setup_fault_pdu(p, NT_STATUS(DCERPC_NCA_S_PROTO_ERROR));
2213 TALLOC_FREE(pkt);
2214 } else {
2215 /*
2216 --
2217 2.8.1
2218
2219
2220 From ef175975f587d73092461c36b10e4c9cf1805727 Mon Sep 17 00:00:00 2001
2221 From: Stefan Metzmacher <metze@samba.org>
2222 Date: Sat, 11 Jul 2015 10:58:07 +0200
2223 Subject: [PATCH 29/40] CVE-2015-5370: s3:librpc/rpc: remove unused
2224 dcerpc_pull_dcerpc_auth()
2225 MIME-Version: 1.0
2226 Content-Type: text/plain; charset=UTF-8
2227 Content-Transfer-Encoding: 8bit
2228
2229 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2230
2231 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2232 Reviewed-by: Günther Deschner <gd@samba.org>
2233 (cherry picked from commit 02aef978ff8f16009a52c2d981d414d019bc8dd9)
2234 ---
2235 source3/librpc/rpc/dcerpc.h | 4 ----
2236 source3/librpc/rpc/dcerpc_helpers.c | 41 -------------------------------------
2237 2 files changed, 45 deletions(-)
2238
2239 diff --git a/source3/librpc/rpc/dcerpc.h b/source3/librpc/rpc/dcerpc.h
2240 index e7cca9e..9452e85 100644
2241 --- a/source3/librpc/rpc/dcerpc.h
2242 +++ b/source3/librpc/rpc/dcerpc.h
2243 @@ -71,10 +71,6 @@ NTSTATUS dcerpc_push_dcerpc_auth(TALLOC_CTX *mem_ctx,
2244 uint32_t auth_context_id,
2245 const DATA_BLOB *credentials,
2246 DATA_BLOB *blob);
2247 -NTSTATUS dcerpc_pull_dcerpc_auth(TALLOC_CTX *mem_ctx,
2248 - const DATA_BLOB *blob,
2249 - struct dcerpc_auth *r,
2250 - bool bigendian);
2251 NTSTATUS dcerpc_guess_sizes(struct pipe_auth_data *auth,
2252 size_t header_len, size_t data_left,
2253 size_t max_xmit_frag, size_t pad_alignment,
2254 diff --git a/source3/librpc/rpc/dcerpc_helpers.c b/source3/librpc/rpc/dcerpc_helpers.c
2255 index c07835f..e4d0e3a 100644
2256 --- a/source3/librpc/rpc/dcerpc_helpers.c
2257 +++ b/source3/librpc/rpc/dcerpc_helpers.c
2258 @@ -210,47 +210,6 @@ NTSTATUS dcerpc_push_dcerpc_auth(TALLOC_CTX *mem_ctx,
2259 }
2260
2261 /**
2262 -* @brief Decodes a dcerpc_auth blob
2263 -*
2264 -* @param mem_ctx The memory context on which to allocate the packet
2265 -* elements
2266 -* @param blob The blob of data to decode
2267 -* @param r An empty dcerpc_auth structure, must not be NULL
2268 -*
2269 -* @return a NTSTATUS error code
2270 -*/
2271 -NTSTATUS dcerpc_pull_dcerpc_auth(TALLOC_CTX *mem_ctx,
2272 - const DATA_BLOB *blob,
2273 - struct dcerpc_auth *r,
2274 - bool bigendian)
2275 -{
2276 - enum ndr_err_code ndr_err;
2277 - struct ndr_pull *ndr;
2278 -
2279 - ndr = ndr_pull_init_blob(blob, mem_ctx);
2280 - if (!ndr) {
2281 - return NT_STATUS_NO_MEMORY;
2282 - }
2283 - if (bigendian) {
2284 - ndr->flags |= LIBNDR_FLAG_BIGENDIAN;
2285 - }
2286 -
2287 - ndr_err = ndr_pull_dcerpc_auth(ndr, NDR_SCALARS|NDR_BUFFERS, r);
2288 -
2289 - if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
2290 - talloc_free(ndr);
2291 - return ndr_map_error2ntstatus(ndr_err);
2292 - }
2293 - talloc_free(ndr);
2294 -
2295 - if (DEBUGLEVEL >= 10) {
2296 - NDR_PRINT_DEBUG(dcerpc_auth, r);
2297 - }
2298 -
2299 - return NT_STATUS_OK;
2300 -}
2301 -
2302 -/**
2303 * @brief Calculate how much data we can in a packet, including calculating
2304 * auth token and pad lengths.
2305 *
2306 --
2307 2.8.1
2308
2309
2310 From 49d0e60d28d3b615d4ee368cd3f260b3a6386858 Mon Sep 17 00:00:00 2001
2311 From: Stefan Metzmacher <metze@samba.org>
2312 Date: Tue, 7 Jul 2015 13:05:01 +0200
2313 Subject: [PATCH 30/40] CVE-2015-5370: s3:rpc_server: check the transfer syntax
2314 in check_bind_req() first
2315 MIME-Version: 1.0
2316 Content-Type: text/plain; charset=UTF-8
2317 Content-Transfer-Encoding: 8bit
2318
2319 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2320
2321 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2322 Reviewed-by: Günther Deschner <gd@samba.org>
2323 (cherry picked from commit 9464684010461947fa98d8ee084069e9cf362625)
2324 ---
2325 source3/rpc_server/srv_pipe.c | 20 ++++++++++++++------
2326 1 file changed, 14 insertions(+), 6 deletions(-)
2327
2328 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
2329 index 3fb8855..0e6b073 100644
2330 --- a/source3/rpc_server/srv_pipe.c
2331 +++ b/source3/rpc_server/srv_pipe.c
2332 @@ -351,16 +351,24 @@ static bool check_bind_req(struct pipes_struct *p,
2333 DEBUG(3,("check_bind_req for %s\n",
2334 get_pipe_name_from_syntax(talloc_tos(), abstract)));
2335
2336 + ok = ndr_syntax_id_equal(transfer, &ndr_transfer_syntax);
2337 + if (!ok) {
2338 + DEBUG(1,("check_bind_req unknown transfer syntax for "
2339 + "%s context_id=%u\n",
2340 + get_pipe_name_from_syntax(talloc_tos(), abstract),
2341 + (unsigned)context_id));
2342 + return false;
2343 + }
2344 +
2345 /* we have to check all now since win2k introduced a new UUID on the lsaprpc pipe */
2346 - if (rpc_srv_pipe_exists_by_id(abstract) &&
2347 - ndr_syntax_id_equal(transfer, &ndr_transfer_syntax)) {
2348 - DEBUG(3, ("check_bind_req: \\PIPE\\%s -> \\PIPE\\%s\n",
2349 - rpc_srv_get_pipe_cli_name(abstract),
2350 - rpc_srv_get_pipe_srv_name(abstract)));
2351 - } else {
2352 + if (!rpc_srv_pipe_exists_by_id(abstract)) {
2353 return false;
2354 }
2355
2356 + DEBUG(3, ("check_bind_req: %s -> %s rpc service\n",
2357 + rpc_srv_get_pipe_cli_name(abstract),
2358 + rpc_srv_get_pipe_srv_name(abstract)));
2359 +
2360 context_fns = SMB_MALLOC_P(struct pipe_rpc_fns);
2361 if (context_fns == NULL) {
2362 DEBUG(0,("check_bind_req: malloc() failed!\n"));
2363 --
2364 2.8.1
2365
2366
2367 From 7ee6698f706e51568f53347f422ac6671cdba9a4 Mon Sep 17 00:00:00 2001
2368 From: Stefan Metzmacher <metze@samba.org>
2369 Date: Tue, 7 Jul 2015 13:05:01 +0200
2370 Subject: [PATCH 31/40] CVE-2015-5370: s3:rpc_server: don't allow an existing
2371 context to be changed in check_bind_req()
2372 MIME-Version: 1.0
2373 Content-Type: text/plain; charset=UTF-8
2374 Content-Transfer-Encoding: 8bit
2375
2376 An alter context can't change the syntax of an existing context,
2377 a new context_id will be used for that.
2378
2379 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2380
2381 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2382 Reviewed-by: Günther Deschner <gd@samba.org>
2383 (cherry picked from commit a995740d4e7fbd8fbb5c8c6280b73eaceae53574)
2384 ---
2385 source3/rpc_server/srv_pipe.c | 22 ++++++++++++++++++++++
2386 1 file changed, 22 insertions(+)
2387
2388 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
2389 index 0e6b073..4263a91 100644
2390 --- a/source3/rpc_server/srv_pipe.c
2391 +++ b/source3/rpc_server/srv_pipe.c
2392 @@ -360,6 +360,28 @@ static bool check_bind_req(struct pipes_struct *p,
2393 return false;
2394 }
2395
2396 + for (context_fns = p->contexts;
2397 + context_fns != NULL;
2398 + context_fns = context_fns->next)
2399 + {
2400 + if (context_fns->context_id != context_id) {
2401 + continue;
2402 + }
2403 +
2404 + ok = ndr_syntax_id_equal(&context_fns->syntax,
2405 + abstract);
2406 + if (ok) {
2407 + return true;
2408 + }
2409 +
2410 + DEBUG(1,("check_bind_req: changing abstract syntax for "
2411 + "%s context_id=%u into %s not supported\n",
2412 + get_pipe_name_from_syntax(talloc_tos(), &context_fns->syntax),
2413 + (unsigned)context_id,
2414 + get_pipe_name_from_syntax(talloc_tos(), abstract)));
2415 + return false;
2416 + }
2417 +
2418 /* we have to check all now since win2k introduced a new UUID on the lsaprpc pipe */
2419 if (!rpc_srv_pipe_exists_by_id(abstract)) {
2420 return false;
2421 --
2422 2.8.1
2423
2424
2425 From 79a238d0c868c7e182f49637b66f544dc1dd86da Mon Sep 17 00:00:00 2001
2426 From: Stefan Metzmacher <metze@samba.org>
2427 Date: Wed, 8 Jul 2015 00:01:37 +0200
2428 Subject: [PATCH 32/40] CVE-2015-5370: s3:rpc_client: pass struct
2429 pipe_auth_data to create_rpc_{bind_auth3,alter_context}()
2430 MIME-Version: 1.0
2431 Content-Type: text/plain; charset=UTF-8
2432 Content-Transfer-Encoding: 8bit
2433
2434 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2435
2436 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2437 Reviewed-by: Günther Deschner <gd@samba.org>
2438 (cherry picked from commit f556d9245c13d018d4e772f06d013ebe558703d9)
2439 ---
2440 source3/rpc_client/cli_pipe.c | 26 ++++++++++----------------
2441 1 file changed, 10 insertions(+), 16 deletions(-)
2442
2443 diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c
2444 index 1c4ff01..3af3d8f 100644
2445 --- a/source3/rpc_client/cli_pipe.c
2446 +++ b/source3/rpc_client/cli_pipe.c
2447 @@ -1816,9 +1816,8 @@ static bool check_bind_response(const struct dcerpc_bind_ack *r,
2448
2449 static NTSTATUS create_rpc_bind_auth3(TALLOC_CTX *mem_ctx,
2450 struct rpc_pipe_client *cli,
2451 - uint32 rpc_call_id,
2452 - enum dcerpc_AuthType auth_type,
2453 - enum dcerpc_AuthLevel auth_level,
2454 + struct pipe_auth_data *auth,
2455 + uint32_t rpc_call_id,
2456 DATA_BLOB *pauth_blob,
2457 DATA_BLOB *rpc_out)
2458 {
2459 @@ -1828,8 +1827,8 @@ static NTSTATUS create_rpc_bind_auth3(TALLOC_CTX *mem_ctx,
2460 u.auth3._pad = 0;
2461
2462 status = dcerpc_push_dcerpc_auth(mem_ctx,
2463 - auth_type,
2464 - auth_level,
2465 + auth->auth_type,
2466 + auth->auth_level,
2467 0, /* auth_pad_length */
2468 1, /* auth_context_id */
2469 pauth_blob,
2470 @@ -1861,9 +1860,8 @@ static NTSTATUS create_rpc_bind_auth3(TALLOC_CTX *mem_ctx,
2471 ********************************************************************/
2472
2473 static NTSTATUS create_rpc_alter_context(TALLOC_CTX *mem_ctx,
2474 - enum dcerpc_AuthType auth_type,
2475 - enum dcerpc_AuthLevel auth_level,
2476 - uint32 rpc_call_id,
2477 + struct pipe_auth_data *auth,
2478 + uint32_t rpc_call_id,
2479 const struct ndr_syntax_id *abstract,
2480 const struct ndr_syntax_id *transfer,
2481 const DATA_BLOB *pauth_blob, /* spnego auth blob already created. */
2482 @@ -1873,8 +1871,8 @@ static NTSTATUS create_rpc_alter_context(TALLOC_CTX *mem_ctx,
2483 NTSTATUS status;
2484
2485 status = dcerpc_push_dcerpc_auth(mem_ctx,
2486 - auth_type,
2487 - auth_level,
2488 + auth->auth_type,
2489 + auth->auth_level,
2490 0, /* auth_pad_length */
2491 1, /* auth_context_id */
2492 pauth_blob,
2493 @@ -2300,9 +2298,7 @@ static NTSTATUS rpc_bind_next_send(struct tevent_req *req,
2494 /* Now prepare the alter context pdu. */
2495 data_blob_free(&state->rpc_out);
2496
2497 - status = create_rpc_alter_context(state,
2498 - auth->auth_type,
2499 - auth->auth_level,
2500 + status = create_rpc_alter_context(state, auth,
2501 state->rpc_call_id,
2502 &state->cli->abstract_syntax,
2503 &state->cli->transfer_syntax,
2504 @@ -2335,10 +2331,8 @@ static NTSTATUS rpc_bind_finish_send(struct tevent_req *req,
2505 /* Now prepare the auth3 context pdu. */
2506 data_blob_free(&state->rpc_out);
2507
2508 - status = create_rpc_bind_auth3(state, state->cli,
2509 + status = create_rpc_bind_auth3(state, state->cli, auth,
2510 state->rpc_call_id,
2511 - auth->auth_type,
2512 - auth->auth_level,
2513 auth_token,
2514 &state->rpc_out);
2515 if (!NT_STATUS_IS_OK(status)) {
2516 --
2517 2.8.1
2518
2519
2520 From 18a50ed6ead11287ff72cb38f100d0f2641c3e7d Mon Sep 17 00:00:00 2001
2521 From: Stefan Metzmacher <metze@samba.org>
2522 Date: Wed, 8 Jul 2015 00:01:37 +0200
2523 Subject: [PATCH 33/40] CVE-2015-5370: s3:librpc/rpc: add auth_context_id to
2524 struct pipe_auth_data
2525 MIME-Version: 1.0
2526 Content-Type: text/plain; charset=UTF-8
2527 Content-Transfer-Encoding: 8bit
2528
2529 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2530
2531 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2532 Reviewed-by: Günther Deschner <gd@samba.org>
2533 (cherry picked from commit cbf20b43d7b40e3b6ccf044f6f51a5adff1f5e6d)
2534 ---
2535 source3/librpc/rpc/dcerpc.h | 1 +
2536 1 file changed, 1 insertion(+)
2537
2538 diff --git a/source3/librpc/rpc/dcerpc.h b/source3/librpc/rpc/dcerpc.h
2539 index 9452e85..c25b0f5 100644
2540 --- a/source3/librpc/rpc/dcerpc.h
2541 +++ b/source3/librpc/rpc/dcerpc.h
2542 @@ -42,6 +42,7 @@ struct pipe_auth_data {
2543 bool verified_bitmask1;
2544
2545 void *auth_ctx;
2546 + uint32_t auth_context_id;
2547
2548 /* Only the client code uses these 3 for now */
2549 char *domain;
2550 --
2551 2.8.1
2552
2553
2554 From 7dbaaca2a638406331d4653e1afdc18f7c8502f6 Mon Sep 17 00:00:00 2001
2555 From: Stefan Metzmacher <metze@samba.org>
2556 Date: Wed, 8 Jul 2015 00:01:37 +0200
2557 Subject: [PATCH 34/40] CVE-2015-5370: s3:rpc_client: make use of
2558 pipe_auth_data->auth_context_id
2559 MIME-Version: 1.0
2560 Content-Type: text/plain; charset=UTF-8
2561 Content-Transfer-Encoding: 8bit
2562
2563 This is better than using hardcoded values.
2564 We need to use auth_context_id = 1 for authenticated
2565 connections, as old Samba server (before this patchset)
2566 will use a hardcoded value of 1.
2567
2568 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2569
2570 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2571 Reviewed-by: Günther Deschner <gd@samba.org>
2572 (cherry picked from commit ae68d3f325c3880144b80385779c9445897646e6)
2573 ---
2574 source3/rpc_client/cli_pipe.c | 13 ++++++++++---
2575 1 file changed, 10 insertions(+), 3 deletions(-)
2576
2577 diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c
2578 index 3af3d8f..755d676 100644
2579 --- a/source3/rpc_client/cli_pipe.c
2580 +++ b/source3/rpc_client/cli_pipe.c
2581 @@ -1314,7 +1314,7 @@ static NTSTATUS create_rpc_bind_req(TALLOC_CTX *mem_ctx,
2582 auth->auth_type,
2583 auth->auth_level,
2584 0, /* auth_pad_length */
2585 - 1, /* auth_context_id */
2586 + auth->auth_context_id,
2587 &auth_token,
2588 &auth_info);
2589 if (!NT_STATUS_IS_OK(ret)) {
2590 @@ -1830,7 +1830,7 @@ static NTSTATUS create_rpc_bind_auth3(TALLOC_CTX *mem_ctx,
2591 auth->auth_type,
2592 auth->auth_level,
2593 0, /* auth_pad_length */
2594 - 1, /* auth_context_id */
2595 + auth->auth_context_id,
2596 pauth_blob,
2597 &u.auth3.auth_info);
2598 if (!NT_STATUS_IS_OK(status)) {
2599 @@ -1874,7 +1874,7 @@ static NTSTATUS create_rpc_alter_context(TALLOC_CTX *mem_ctx,
2600 auth->auth_type,
2601 auth->auth_level,
2602 0, /* auth_pad_length */
2603 - 1, /* auth_context_id */
2604 + auth->auth_context_id,
2605 pauth_blob,
2606 &auth_info);
2607 if (!NT_STATUS_IS_OK(status)) {
2608 @@ -2704,6 +2704,7 @@ NTSTATUS rpccli_ncalrpc_bind_data(TALLOC_CTX *mem_ctx,
2609
2610 result->auth_type = DCERPC_AUTH_TYPE_NCALRPC_AS_SYSTEM;
2611 result->auth_level = DCERPC_AUTH_LEVEL_CONNECT;
2612 + result->auth_context_id = 1;
2613
2614 result->user_name = talloc_strdup(result, "");
2615 result->domain = talloc_strdup(result, "");
2616 @@ -2728,6 +2729,7 @@ NTSTATUS rpccli_anon_bind_data(TALLOC_CTX *mem_ctx,
2617
2618 result->auth_type = DCERPC_AUTH_TYPE_NONE;
2619 result->auth_level = DCERPC_AUTH_LEVEL_NONE;
2620 + result->auth_context_id = 0;
2621
2622 result->user_name = talloc_strdup(result, "");
2623 result->domain = talloc_strdup(result, "");
2624 @@ -2765,6 +2767,7 @@ static NTSTATUS rpccli_ntlmssp_bind_data(TALLOC_CTX *mem_ctx,
2625
2626 result->auth_type = auth_type;
2627 result->auth_level = auth_level;
2628 + result->auth_context_id = 1;
2629
2630 result->user_name = talloc_strdup(result, username);
2631 result->domain = talloc_strdup(result, domain);
2632 @@ -2836,6 +2839,7 @@ NTSTATUS rpccli_schannel_bind_data(TALLOC_CTX *mem_ctx, const char *domain,
2633
2634 result->auth_type = DCERPC_AUTH_TYPE_SCHANNEL;
2635 result->auth_level = auth_level;
2636 + result->auth_context_id = 1;
2637
2638 result->user_name = talloc_strdup(result, "");
2639 result->domain = talloc_strdup(result, domain);
2640 @@ -3500,6 +3504,7 @@ NTSTATUS cli_rpc_pipe_open_krb5(struct cli_state *cli,
2641 }
2642 auth->auth_type = DCERPC_AUTH_TYPE_KRB5;
2643 auth->auth_level = auth_level;
2644 + auth->auth_context_id = 1;
2645
2646 if (!username) {
2647 username = "";
2648 @@ -3570,6 +3575,7 @@ NTSTATUS cli_rpc_pipe_open_spnego_krb5(struct cli_state *cli,
2649 }
2650 auth->auth_type = DCERPC_AUTH_TYPE_SPNEGO;
2651 auth->auth_level = auth_level;
2652 + auth->auth_context_id = 1;
2653
2654 if (!username) {
2655 username = "";
2656 @@ -3644,6 +3650,7 @@ NTSTATUS cli_rpc_pipe_open_spnego_ntlmssp(struct cli_state *cli,
2657 }
2658 auth->auth_type = DCERPC_AUTH_TYPE_SPNEGO;
2659 auth->auth_level = auth_level;
2660 + auth->auth_context_id = 1;
2661
2662 if (!username) {
2663 username = "";
2664 --
2665 2.8.1
2666
2667
2668 From 82cd4e90c70d1ababd5fa1ee61206e37edbf40e4 Mon Sep 17 00:00:00 2001
2669 From: Stefan Metzmacher <metze@samba.org>
2670 Date: Wed, 8 Jul 2015 00:01:37 +0200
2671 Subject: [PATCH 35/40] CVE-2015-5370: s3:rpc_server: make use of
2672 pipe_auth_data->auth_context_id
2673 MIME-Version: 1.0
2674 Content-Type: text/plain; charset=UTF-8
2675 Content-Transfer-Encoding: 8bit
2676
2677 This is better than using hardcoded values.
2678 We need to use the value the client used in the BIND request.
2679
2680 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2681
2682 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2683 Reviewed-by: Günther Deschner <gd@samba.org>
2684 (cherry picked from commit 2bc617293a5d8652e484af69660b3646f3d48690)
2685 ---
2686 source3/rpc_server/rpc_ncacn_np.c | 1 +
2687 source3/rpc_server/srv_pipe.c | 11 +++++++----
2688 2 files changed, 8 insertions(+), 4 deletions(-)
2689
2690 diff --git a/source3/rpc_server/rpc_ncacn_np.c b/source3/rpc_server/rpc_ncacn_np.c
2691 index f2e9d10..c0f24a6 100644
2692 --- a/source3/rpc_server/rpc_ncacn_np.c
2693 +++ b/source3/rpc_server/rpc_ncacn_np.c
2694 @@ -781,6 +781,7 @@ static NTSTATUS rpc_pipe_open_external(TALLOC_CTX *mem_ctx,
2695 }
2696 result->auth->auth_type = DCERPC_AUTH_TYPE_NONE;
2697 result->auth->auth_level = DCERPC_AUTH_LEVEL_NONE;
2698 + result->auth->auth_context_id = 0;
2699
2700 status = rpccli_anon_bind_data(result, &auth);
2701 if (!NT_STATUS_IS_OK(status)) {
2702 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
2703 index 4263a91..d6c4118 100644
2704 --- a/source3/rpc_server/srv_pipe.c
2705 +++ b/source3/rpc_server/srv_pipe.c
2706 @@ -534,6 +534,7 @@ static bool pipe_spnego_auth_bind(struct pipes_struct *p,
2707
2708 p->auth.auth_ctx = spnego_ctx;
2709 p->auth.auth_type = DCERPC_AUTH_TYPE_SPNEGO;
2710 + p->auth.auth_context_id = auth_info->auth_context_id;
2711
2712 DEBUG(10, ("SPNEGO auth started\n"));
2713
2714 @@ -644,6 +645,7 @@ static bool pipe_schannel_auth_bind(struct pipes_struct *p,
2715 /* We're finished with this bind - no more packets. */
2716 p->auth.auth_ctx = schannel_auth;
2717 p->auth.auth_type = DCERPC_AUTH_TYPE_SCHANNEL;
2718 + p->auth.auth_context_id = auth_info->auth_context_id;
2719
2720 p->pipe_bound = True;
2721
2722 @@ -688,6 +690,7 @@ static bool pipe_ntlmssp_auth_bind(struct pipes_struct *p,
2723
2724 p->auth.auth_ctx = ntlmssp_state;
2725 p->auth.auth_type = DCERPC_AUTH_TYPE_NTLMSSP;
2726 + p->auth.auth_context_id = auth_info->auth_context_id;
2727
2728 DEBUG(10, (__location__ ": NTLMSSP auth started\n"));
2729
2730 @@ -1173,6 +1176,7 @@ static bool api_pipe_bind_req(struct pipes_struct *p,
2731 p->pipe_bound = True;
2732 /* The session key was initialized from the SMB
2733 * session in make_internal_rpc_pipe_p */
2734 + p->auth.auth_context_id = 0;
2735 }
2736
2737 ZERO_STRUCT(u.bind_ack);
2738 @@ -1218,12 +1222,11 @@ static bool api_pipe_bind_req(struct pipes_struct *p,
2739 }
2740
2741 if (auth_resp.length) {
2742 -
2743 status = dcerpc_push_dcerpc_auth(pkt,
2744 auth_type,
2745 auth_info.auth_level,
2746 - 0,
2747 - 1, /* auth_context_id */
2748 + 0, /* pad_len */
2749 + p->auth.auth_context_id,
2750 &auth_resp,
2751 &auth_blob);
2752 if (!NT_STATUS_IS_OK(status)) {
2753 @@ -1646,7 +1649,7 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
2754 auth_info.auth_type,
2755 auth_info.auth_level,
2756 pad_len,
2757 - 1, /* auth_context_id */
2758 + p->auth.auth_context_id,
2759 &auth_resp,
2760 &auth_blob);
2761 if (!NT_STATUS_IS_OK(status)) {
2762 --
2763 2.8.1
2764
2765
2766 From 8d1fb1fcf58b08cbf27579382ea648aefb9e7dc6 Mon Sep 17 00:00:00 2001
2767 From: Stefan Metzmacher <metze@samba.org>
2768 Date: Wed, 8 Jul 2015 00:01:37 +0200
2769 Subject: [PATCH 36/40] CVE-2015-5370: s3:librpc/rpc: make use of
2770 auth->auth_context_id in dcerpc_add_auth_footer()
2771 MIME-Version: 1.0
2772 Content-Type: text/plain; charset=UTF-8
2773 Content-Transfer-Encoding: 8bit
2774
2775 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2776
2777 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2778 Reviewed-by: Günther Deschner <gd@samba.org>
2779 (cherry picked from commit 61faaa63e7e610308c72ae4c41a5c7b5b7312685)
2780 ---
2781 source3/librpc/rpc/dcerpc_helpers.c | 2 +-
2782 1 file changed, 1 insertion(+), 1 deletion(-)
2783
2784 diff --git a/source3/librpc/rpc/dcerpc_helpers.c b/source3/librpc/rpc/dcerpc_helpers.c
2785 index e4d0e3a..977a372 100644
2786 --- a/source3/librpc/rpc/dcerpc_helpers.c
2787 +++ b/source3/librpc/rpc/dcerpc_helpers.c
2788 @@ -741,7 +741,7 @@ NTSTATUS dcerpc_add_auth_footer(struct pipe_auth_data *auth,
2789 auth->auth_type,
2790 auth->auth_level,
2791 pad_len,
2792 - 1 /* context id. */,
2793 + auth->auth_context_id,
2794 &auth_blob,
2795 &auth_info);
2796 if (!NT_STATUS_IS_OK(status)) {
2797 --
2798 2.8.1
2799
2800
2801 From 2a44cfc65f7dc1ccfd2d6a5abe5d26e94a085aa9 Mon Sep 17 00:00:00 2001
2802 From: Stefan Metzmacher <metze@samba.org>
2803 Date: Wed, 8 Jul 2015 00:01:37 +0200
2804 Subject: [PATCH 37/40] CVE-2015-5370: s3:librpc/rpc: verify auth_context_id in
2805 dcerpc_check_auth()
2806 MIME-Version: 1.0
2807 Content-Type: text/plain; charset=UTF-8
2808 Content-Transfer-Encoding: 8bit
2809
2810 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2811
2812 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2813 Reviewed-by: Günther Deschner <gd@samba.org>
2814 (cherry picked from commit 0cf3151c843e2c779b534743b455e630d89e2ba9)
2815 ---
2816 source3/librpc/rpc/dcerpc_helpers.c | 4 ++++
2817 1 file changed, 4 insertions(+)
2818
2819 diff --git a/source3/librpc/rpc/dcerpc_helpers.c b/source3/librpc/rpc/dcerpc_helpers.c
2820 index 977a372..b00cf1bf 100644
2821 --- a/source3/librpc/rpc/dcerpc_helpers.c
2822 +++ b/source3/librpc/rpc/dcerpc_helpers.c
2823 @@ -881,6 +881,10 @@ NTSTATUS dcerpc_check_auth(struct pipe_auth_data *auth,
2824 return NT_STATUS_INVALID_PARAMETER;
2825 }
2826
2827 + if (auth_info.auth_context_id != auth->auth_context_id) {
2828 + return NT_STATUS_INVALID_PARAMETER;
2829 + }
2830 +
2831 pkt_trailer->length -= auth_length;
2832 data = data_blob_const(raw_pkt->data + header_size,
2833 pkt_trailer->length);
2834 --
2835 2.8.1
2836
2837
2838 From 68dcc277d5af506706d3fdac43891e43ccb4ceea Mon Sep 17 00:00:00 2001
2839 From: Stefan Metzmacher <metze@samba.org>
2840 Date: Tue, 7 Jul 2015 22:51:18 +0200
2841 Subject: [PATCH 38/40] CVE-2015-5370: s3:rpc_client: verify auth_context_id in
2842 rpc_pipe_bind_step_one_done()
2843 MIME-Version: 1.0
2844 Content-Type: text/plain; charset=UTF-8
2845 Content-Transfer-Encoding: 8bit
2846
2847 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2848
2849 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2850 Reviewed-by: Günther Deschner <gd@samba.org>
2851 (cherry picked from commit 93a0f92b8ebecb38f92d3b2c9a946b486ee91d3c)
2852 ---
2853 source3/rpc_client/cli_pipe.c | 8 ++++++++
2854 1 file changed, 8 insertions(+)
2855
2856 diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c
2857 index 755d676..ee33e80 100644
2858 --- a/source3/rpc_client/cli_pipe.c
2859 +++ b/source3/rpc_client/cli_pipe.c
2860 @@ -2052,6 +2052,14 @@ static void rpc_pipe_bind_step_one_done(struct tevent_req *subreq)
2861 return;
2862 }
2863
2864 + if (auth.auth_context_id != pauth->auth_context_id) {
2865 + DEBUG(0, (__location__ " Auth context id %u mismatch expected %u.\n",
2866 + (unsigned)auth.auth_context_id,
2867 + (unsigned)pauth->auth_context_id));
2868 + tevent_req_nterror(req, NT_STATUS_RPC_PROTOCOL_ERROR);
2869 + return;
2870 + }
2871 +
2872 break;
2873 }
2874
2875 --
2876 2.8.1
2877
2878
2879 From 8787dd5053974c1f42ae85a310e9522795f4ccfe Mon Sep 17 00:00:00 2001
2880 From: Stefan Metzmacher <metze@samba.org>
2881 Date: Wed, 8 Jul 2015 00:01:37 +0200
2882 Subject: [PATCH 39/40] CVE-2015-5370: s3:rpc_server: verify auth_context_id in
2883 api_pipe_{bind_auth3,alter_context}
2884 MIME-Version: 1.0
2885 Content-Type: text/plain; charset=UTF-8
2886 Content-Transfer-Encoding: 8bit
2887
2888 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2889
2890 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2891 Reviewed-by: Günther Deschner <gd@samba.org>
2892 (cherry picked from commit 3ef461d8304ee36184cd7a3963676eedff4ef1eb)
2893 ---
2894 source3/rpc_server/srv_pipe.c | 16 ++++++++++++++++
2895 1 file changed, 16 insertions(+)
2896
2897 diff --git a/source3/rpc_server/srv_pipe.c b/source3/rpc_server/srv_pipe.c
2898 index d6c4118..26c4ee0 100644
2899 --- a/source3/rpc_server/srv_pipe.c
2900 +++ b/source3/rpc_server/srv_pipe.c
2901 @@ -1364,6 +1364,14 @@ bool api_pipe_bind_auth3(struct pipes_struct *p, struct ncacn_packet *pkt)
2902 goto err;
2903 }
2904
2905 + if (auth_info.auth_context_id != p->auth.auth_context_id) {
2906 + DEBUG(0, ("Auth context id mismatch! Client sent %u, "
2907 + "but auth was started as level %u!\n",
2908 + (unsigned)auth_info.auth_context_id,
2909 + (unsigned)p->auth.auth_context_id));
2910 + goto err;
2911 + }
2912 +
2913 switch (auth_info.auth_type) {
2914 case DCERPC_AUTH_TYPE_NTLMSSP:
2915 ntlmssp_ctx = talloc_get_type_abort(p->auth.auth_ctx,
2916 @@ -1545,6 +1553,14 @@ static bool api_pipe_alter_context(struct pipes_struct *p,
2917 goto err_exit;
2918 }
2919
2920 + if (auth_info.auth_context_id != p->auth.auth_context_id) {
2921 + DEBUG(0, ("Auth context id mismatch! Client sent %u, "
2922 + "but auth was started as level %u!\n",
2923 + (unsigned)auth_info.auth_context_id,
2924 + (unsigned)p->auth.auth_context_id));
2925 + goto err_exit;
2926 + }
2927 +
2928 switch (auth_info.auth_type) {
2929 case DCERPC_AUTH_TYPE_SPNEGO:
2930 spnego_ctx = talloc_get_type_abort(p->auth.auth_ctx,
2931 --
2932 2.8.1
2933
2934
2935 From bf0040fb860527cb0c54ab0ef301153bdad650c0 Mon Sep 17 00:00:00 2001
2936 From: Stefan Metzmacher <metze@samba.org>
2937 Date: Tue, 22 Dec 2015 21:23:14 +0100
2938 Subject: [PATCH 40/40] CVE-2015-5370: s3:rpc_client: disconnect connection on
2939 protocol errors
2940 MIME-Version: 1.0
2941 Content-Type: text/plain; charset=UTF-8
2942 Content-Transfer-Encoding: 8bit
2943
2944 BUG: https://bugzilla.samba.org/show_bug.cgi?id=11344
2945
2946 Signed-off-by: Stefan Metzmacher <metze@samba.org>
2947 Reviewed-by: Günther Deschner <gd@samba.org>
2948 (cherry picked from commit 024d3b263a2879cee4fb7794d70f253c948cc043)
2949 ---
2950 source3/rpc_client/cli_pipe.c | 67 +++++++++++++++++++++++++++++++++++++++++--
2951 1 file changed, 64 insertions(+), 3 deletions(-)
2952
2953 diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c
2954 index ee33e80..a3810f0 100644
2955 --- a/source3/rpc_client/cli_pipe.c
2956 +++ b/source3/rpc_client/cli_pipe.c
2957 @@ -953,6 +953,12 @@ static void rpc_api_pipe_got_pdu(struct tevent_req *subreq)
2958
2959 state->pkt = talloc(state, struct ncacn_packet);
2960 if (!state->pkt) {
2961 + /*
2962 + * TODO: do a real async disconnect ...
2963 + *
2964 + * For now do it sync...
2965 + */
2966 + TALLOC_FREE(state->cli->transport);
2967 tevent_req_nterror(req, NT_STATUS_NO_MEMORY);
2968 return;
2969 }
2970 @@ -962,6 +968,12 @@ static void rpc_api_pipe_got_pdu(struct tevent_req *subreq)
2971 state->pkt,
2972 !state->endianess);
2973 if (!NT_STATUS_IS_OK(status)) {
2974 + /*
2975 + * TODO: do a real async disconnect ...
2976 + *
2977 + * For now do it sync...
2978 + */
2979 + TALLOC_FREE(state->cli->transport);
2980 tevent_req_nterror(req, status);
2981 return;
2982 }
2983 @@ -979,6 +991,28 @@ static void rpc_api_pipe_got_pdu(struct tevent_req *subreq)
2984 (unsigned)state->reply_pdu_offset,
2985 nt_errstr(status)));
2986
2987 + if (state->pkt->ptype != DCERPC_PKT_FAULT && !NT_STATUS_IS_OK(status)) {
2988 + /*
2989 + * TODO: do a real async disconnect ...
2990 + *
2991 + * For now do it sync...
2992 + */
2993 + TALLOC_FREE(state->cli->transport);
2994 + } else if (NT_STATUS_EQUAL(status, NT_STATUS_RPC_PROTOCOL_ERROR)) {
2995 + /*
2996 + * TODO: do a real async disconnect ...
2997 + *
2998 + * For now do it sync...
2999 + */
3000 + TALLOC_FREE(state->cli->transport);
3001 + } else if (NT_STATUS_EQUAL(status, NT_STATUS_RPC_SEC_PKG_ERROR)) {
3002 + /*
3003 + * TODO: do a real async disconnect ...
3004 + *
3005 + * For now do it sync...
3006 + */
3007 + TALLOC_FREE(state->cli->transport);
3008 + }
3009 if (!NT_STATUS_IS_OK(status)) {
3010 tevent_req_nterror(req, status);
3011 return;
3012 @@ -1003,12 +1037,24 @@ static void rpc_api_pipe_got_pdu(struct tevent_req *subreq)
3013 "%s\n",
3014 state->endianess?"little":"big",
3015 state->pkt->drep[0]?"little":"big"));
3016 - tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER);
3017 + /*
3018 + * TODO: do a real async disconnect ...
3019 + *
3020 + * For now do it sync...
3021 + */
3022 + TALLOC_FREE(state->cli->transport);
3023 + tevent_req_nterror(req, NT_STATUS_RPC_PROTOCOL_ERROR);
3024 return;
3025 }
3026
3027 if (state->reply_pdu_offset + rdata.length > MAX_RPC_DATA_SIZE) {
3028 - tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER);
3029 + /*
3030 + * TODO: do a real async disconnect ...
3031 + *
3032 + * For now do it sync...
3033 + */
3034 + TALLOC_FREE(state->cli->transport);
3035 + tevent_req_nterror(req, NT_STATUS_RPC_PROTOCOL_ERROR);
3036 return;
3037 }
3038
3039 @@ -1016,6 +1062,12 @@ static void rpc_api_pipe_got_pdu(struct tevent_req *subreq)
3040 if (state->reply_pdu.length < state->reply_pdu_offset + rdata.length) {
3041 if (!data_blob_realloc(NULL, &state->reply_pdu,
3042 state->reply_pdu_offset + rdata.length)) {
3043 + /*
3044 + * TODO: do a real async disconnect ...
3045 + *
3046 + * For now do it sync...
3047 + */
3048 + TALLOC_FREE(state->cli->transport);
3049 tevent_req_nterror(req, NT_STATUS_NO_MEMORY);
3050 return;
3051 }
3052 @@ -1045,6 +1097,14 @@ static void rpc_api_pipe_got_pdu(struct tevent_req *subreq)
3053 subreq = get_complete_frag_send(state, state->ev, state->cli,
3054 state->call_id,
3055 &state->incoming_frag);
3056 + if (subreq == NULL) {
3057 + /*
3058 + * TODO: do a real async disconnect ...
3059 + *
3060 + * For now do it sync...
3061 + */
3062 + TALLOC_FREE(state->cli->transport);
3063 + }
3064 if (tevent_req_nomem(subreq, req)) {
3065 return;
3066 }
3067 @@ -2574,8 +2634,9 @@ static struct tevent_req *rpccli_bh_disconnect_send(TALLOC_CTX *mem_ctx,
3068 /*
3069 * TODO: do a real async disconnect ...
3070 *
3071 - * For now the caller needs to free rpc_cli
3072 + * For now we do it sync...
3073 */
3074 + TALLOC_FREE(hs->rpc_cli->transport);
3075 hs->rpc_cli = NULL;
3076
3077 tevent_req_done(req);
3078 --
3079 2.8.1
3080