s3-rpc_server: Log authorization to DCE/RPC for anonymous and ncacn_np pass-though
[Samba.git] / source3 / rpc_server / srv_pipe.c
blobbd56be6b79e6fc82c45890ecb86997083e5a2861
1 /*
2 * Unix SMB/CIFS implementation.
3 * RPC Pipe client / server routines
4 * Almost completely rewritten by (C) Jeremy Allison 2005 - 2010
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 3 of the License, or
9 * (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, see <http://www.gnu.org/licenses/>.
20 /* this module apparently provides an implementation of DCE/RPC over a
21 * named pipe (IPC$ connection using SMBtrans). details of DCE/RPC
22 * documentation are available (in on-line form) from the X-Open group.
24 * this module should provide a level of abstraction between SMB
25 * and DCE/RPC, while minimising the amount of mallocs, unnecessary
26 * data copies, and network traffic.
30 #include "includes.h"
31 #include "system/filesys.h"
32 #include "srv_pipe_internal.h"
33 #include "../librpc/gen_ndr/ndr_dcerpc.h"
34 #include "../librpc/rpc/rpc_common.h"
35 #include "dcesrv_auth_generic.h"
36 #include "rpc_server.h"
37 #include "rpc_dce.h"
38 #include "smbd/smbd.h"
39 #include "auth.h"
40 #include "ntdomain.h"
41 #include "rpc_server/srv_pipe.h"
42 #include "rpc_server/rpc_contexts.h"
43 #include "lib/param/param.h"
44 #include "librpc/ndr/ndr_table.h"
45 #include "auth/gensec/gensec.h"
46 #include "librpc/ndr/ndr_dcerpc.h"
47 #include "lib/tsocket/tsocket.h"
48 #include "../librpc/gen_ndr/ndr_samr.h"
49 #include "../librpc/gen_ndr/ndr_lsa.h"
50 #include "../librpc/gen_ndr/ndr_netlogon.h"
51 #include "../librpc/gen_ndr/ndr_epmapper.h"
52 #include "../librpc/gen_ndr/ndr_echo.h"
53 #include "../librpc/gen_ndr/ndr_winspool.h"
55 #undef DBGC_CLASS
56 #define DBGC_CLASS DBGC_RPC_SRV
58 static NTSTATUS pipe_auth_verify_final(struct pipes_struct *p);
60 /**
61 * Dump everything from the start of the end up of the provided data
62 * into a file, but only at debug level >= 50
63 **/
64 static void dump_pdu_region(const char *name, int v,
65 DATA_BLOB *data, size_t start, size_t end)
67 int fd, i;
68 char *fname = NULL;
69 ssize_t sz;
71 if (DEBUGLEVEL < 50) return;
73 if (start > data->length || end > data->length || start > end) return;
75 for (i = 1; i < 100; i++) {
76 if (v != -1) {
77 fname = talloc_asprintf(talloc_tos(),
78 "/tmp/%s_%d.%d.prs",
79 name, v, i);
80 } else {
81 fname = talloc_asprintf(talloc_tos(),
82 "/tmp/%s_%d.prs",
83 name, i);
85 if (!fname) {
86 return;
88 fd = open(fname, O_WRONLY|O_CREAT|O_EXCL, 0644);
89 if (fd != -1 || errno != EEXIST) break;
91 if (fd != -1) {
92 sz = write(fd, data->data + start, end - start);
93 i = close(fd);
94 if ((sz != end - start) || (i != 0) ) {
95 DEBUG(0, ("Error writing/closing %s: %ld!=%ld %d\n",
96 fname, (unsigned long)sz,
97 (unsigned long)end - start, i));
98 } else {
99 DEBUG(0,("created %s\n", fname));
102 TALLOC_FREE(fname);
105 static DATA_BLOB generic_session_key(void)
107 return data_blob_const("SystemLibraryDTC", 16);
110 /*******************************************************************
111 Generate the next PDU to be returned from the data.
112 ********************************************************************/
114 static NTSTATUS create_next_packet(TALLOC_CTX *mem_ctx,
115 struct pipe_auth_data *auth,
116 uint32_t call_id,
117 DATA_BLOB *rdata,
118 size_t data_sent_length,
119 DATA_BLOB *frag,
120 size_t *pdu_size)
122 union dcerpc_payload u;
123 uint8_t pfc_flags;
124 size_t data_left;
125 size_t data_to_send;
126 size_t frag_len;
127 size_t pad_len = 0;
128 size_t auth_len = 0;
129 NTSTATUS status;
131 ZERO_STRUCT(u.response);
133 /* Set up rpc packet pfc flags. */
134 if (data_sent_length == 0) {
135 pfc_flags = DCERPC_PFC_FLAG_FIRST;
136 } else {
137 pfc_flags = 0;
140 /* Work out how much we can fit in a single PDU. */
141 data_left = rdata->length - data_sent_length;
143 /* Ensure there really is data left to send. */
144 if (!data_left) {
145 DEBUG(0, ("No data left to send !\n"));
146 return NT_STATUS_BUFFER_TOO_SMALL;
149 status = dcerpc_guess_sizes(auth,
150 DCERPC_RESPONSE_LENGTH,
151 data_left,
152 RPC_MAX_PDU_FRAG_LEN,
153 &data_to_send, &frag_len,
154 &auth_len, &pad_len);
155 if (!NT_STATUS_IS_OK(status)) {
156 return status;
159 /* Set up the alloc hint. This should be the data left to send. */
160 u.response.alloc_hint = data_left;
162 /* Work out if this PDU will be the last. */
163 if (data_sent_length + data_to_send >= rdata->length) {
164 pfc_flags |= DCERPC_PFC_FLAG_LAST;
167 /* Prepare data to be NDR encoded. */
168 u.response.stub_and_verifier =
169 data_blob_const(rdata->data + data_sent_length, data_to_send);
171 /* Store the packet in the data stream. */
172 status = dcerpc_push_ncacn_packet(mem_ctx, DCERPC_PKT_RESPONSE,
173 pfc_flags, auth_len, call_id,
174 &u, frag);
175 if (!NT_STATUS_IS_OK(status)) {
176 DEBUG(0, ("Failed to marshall RPC Packet.\n"));
177 return status;
180 if (auth_len) {
181 /* Set the proper length on the pdu, including padding.
182 * Only needed if an auth trailer will be appended. */
183 dcerpc_set_frag_length(frag, frag->length
184 + pad_len
185 + DCERPC_AUTH_TRAILER_LENGTH
186 + auth_len);
189 if (auth_len) {
190 status = dcerpc_add_auth_footer(auth, pad_len, frag);
191 if (!NT_STATUS_IS_OK(status)) {
192 data_blob_free(frag);
193 return status;
197 *pdu_size = data_to_send;
198 return NT_STATUS_OK;
201 /*******************************************************************
202 Generate the next PDU to be returned from the data in p->rdata.
203 ********************************************************************/
205 bool create_next_pdu(struct pipes_struct *p)
207 size_t pdu_size = 0;
208 NTSTATUS status;
211 * If we're in the fault state, keep returning fault PDU's until
212 * the pipe gets closed. JRA.
214 if (p->fault_state) {
215 setup_fault_pdu(p, NT_STATUS(p->fault_state));
216 return true;
219 status = create_next_packet(p->mem_ctx, &p->auth,
220 p->call_id, &p->out_data.rdata,
221 p->out_data.data_sent_length,
222 &p->out_data.frag, &pdu_size);
223 if (!NT_STATUS_IS_OK(status)) {
224 DEBUG(0, ("Failed to create packet with error %s, "
225 "(auth level %u / type %u)\n",
226 nt_errstr(status),
227 (unsigned int)p->auth.auth_level,
228 (unsigned int)p->auth.auth_type));
229 return false;
232 /* Setup the counts for this PDU. */
233 p->out_data.data_sent_length += pdu_size;
234 p->out_data.current_pdu_sent = 0;
235 return true;
239 static bool pipe_init_outgoing_data(struct pipes_struct *p);
241 /*******************************************************************
242 Marshall a bind_nak pdu.
243 *******************************************************************/
245 static bool setup_bind_nak(struct pipes_struct *p, struct ncacn_packet *pkt)
247 NTSTATUS status;
248 union dcerpc_payload u;
250 /* Free any memory in the current return data buffer. */
251 pipe_init_outgoing_data(p);
254 * Initialize a bind_nak header.
257 ZERO_STRUCT(u);
259 u.bind_nak.reject_reason = 0;
262 * Marshall directly into the outgoing PDU space. We
263 * must do this as we need to set to the bind response
264 * header and are never sending more than one PDU here.
267 status = dcerpc_push_ncacn_packet(p->mem_ctx,
268 DCERPC_PKT_BIND_NAK,
269 DCERPC_PFC_FLAG_FIRST |
270 DCERPC_PFC_FLAG_LAST,
272 pkt->call_id,
274 &p->out_data.frag);
275 if (!NT_STATUS_IS_OK(status)) {
276 return False;
279 p->out_data.data_sent_length = 0;
280 p->out_data.current_pdu_sent = 0;
282 set_incoming_fault(p);
283 TALLOC_FREE(p->auth.auth_ctx);
284 p->auth.auth_level = DCERPC_AUTH_LEVEL_NONE;
285 p->auth.auth_type = DCERPC_AUTH_TYPE_NONE;
286 p->pipe_bound = False;
287 p->allow_bind = false;
288 p->allow_alter = false;
289 p->allow_auth3 = false;
291 return True;
294 /*******************************************************************
295 Marshall a fault pdu.
296 *******************************************************************/
298 bool setup_fault_pdu(struct pipes_struct *p, NTSTATUS fault_status)
300 NTSTATUS status;
301 union dcerpc_payload u;
303 /* Free any memory in the current return data buffer. */
304 pipe_init_outgoing_data(p);
307 * Initialize a fault header.
310 ZERO_STRUCT(u);
312 u.fault.status = NT_STATUS_V(fault_status);
315 * Marshall directly into the outgoing PDU space. We
316 * must do this as we need to set to the bind response
317 * header and are never sending more than one PDU here.
320 status = dcerpc_push_ncacn_packet(p->mem_ctx,
321 DCERPC_PKT_FAULT,
322 DCERPC_PFC_FLAG_FIRST |
323 DCERPC_PFC_FLAG_LAST |
324 DCERPC_PFC_FLAG_DID_NOT_EXECUTE,
326 p->call_id,
328 &p->out_data.frag);
329 if (!NT_STATUS_IS_OK(status)) {
330 return False;
333 p->out_data.data_sent_length = 0;
334 p->out_data.current_pdu_sent = 0;
336 return True;
339 /*******************************************************************
340 Ensure a bind request has the correct abstract & transfer interface.
341 Used to reject unknown binds from Win2k.
342 *******************************************************************/
344 static bool check_bind_req(struct pipes_struct *p,
345 struct ndr_syntax_id* abstract,
346 struct ndr_syntax_id* transfer,
347 uint32_t context_id)
349 struct pipe_rpc_fns *context_fns;
350 bool ok;
351 const char *interface_name = NULL;
353 DEBUG(3,("check_bind_req for %s context_id=%u\n",
354 ndr_interface_name(&abstract->uuid,
355 abstract->if_version),
356 (unsigned)context_id));
358 ok = ndr_syntax_id_equal(transfer, &ndr_transfer_syntax_ndr);
359 if (!ok) {
360 DEBUG(1,("check_bind_req unknown transfer syntax for "
361 "%s context_id=%u\n",
362 ndr_interface_name(&abstract->uuid,
363 abstract->if_version),
364 (unsigned)context_id));
365 return false;
368 for (context_fns = p->contexts;
369 context_fns != NULL;
370 context_fns = context_fns->next)
372 if (context_fns->context_id != context_id) {
373 continue;
376 ok = ndr_syntax_id_equal(&context_fns->syntax,
377 abstract);
378 if (ok) {
379 return true;
382 DEBUG(1,("check_bind_req: changing abstract syntax for "
383 "%s context_id=%u into %s not supported\n",
384 ndr_interface_name(&context_fns->syntax.uuid,
385 context_fns->syntax.if_version),
386 (unsigned)context_id,
387 ndr_interface_name(&abstract->uuid,
388 abstract->if_version)));
389 return false;
392 /* we have to check all now since win2k introduced a new UUID on the lsaprpc pipe */
393 if (!rpc_srv_pipe_exists_by_id(abstract)) {
394 return false;
397 DEBUG(3, ("check_bind_req: %s -> %s rpc service\n",
398 rpc_srv_get_pipe_cli_name(abstract),
399 rpc_srv_get_pipe_srv_name(abstract)));
401 ok = init_pipe_handles(p, abstract);
402 if (!ok) {
403 DEBUG(1, ("Failed to init pipe handles!\n"));
404 return false;
407 context_fns = talloc_zero(p, struct pipe_rpc_fns);
408 if (context_fns == NULL) {
409 DEBUG(0,("check_bind_req: talloc() failed!\n"));
410 return false;
413 interface_name = ndr_interface_name(&abstract->uuid,
414 abstract->if_version);
415 SMB_ASSERT(interface_name != NULL);
417 context_fns->next = context_fns->prev = NULL;
418 context_fns->n_cmds = rpc_srv_get_pipe_num_cmds(abstract);
419 context_fns->cmds = rpc_srv_get_pipe_cmds(abstract);
420 context_fns->context_id = context_id;
421 context_fns->syntax = *abstract;
423 context_fns->allow_connect = lp_allow_dcerpc_auth_level_connect();
425 * for the samr, lsarpc and netlogon interfaces we don't allow "connect"
426 * auth_level by default.
428 ok = ndr_syntax_id_equal(abstract, &ndr_table_samr.syntax_id);
429 if (ok) {
430 context_fns->allow_connect = false;
432 ok = ndr_syntax_id_equal(abstract, &ndr_table_lsarpc.syntax_id);
433 if (ok) {
434 context_fns->allow_connect = false;
436 ok = ndr_syntax_id_equal(abstract, &ndr_table_netlogon.syntax_id);
437 if (ok) {
438 context_fns->allow_connect = false;
441 * for the epmapper and echo interfaces we allow "connect"
442 * auth_level by default.
444 ok = ndr_syntax_id_equal(abstract, &ndr_table_epmapper.syntax_id);
445 if (ok) {
446 context_fns->allow_connect = true;
448 ok = ndr_syntax_id_equal(abstract, &ndr_table_rpcecho.syntax_id);
449 if (ok) {
450 context_fns->allow_connect = true;
453 * every interface can be modified to allow "connect" auth_level by
454 * using a parametric option like:
455 * allow dcerpc auth level connect:<interface>
456 * e.g.
457 * allow dcerpc auth level connect:samr = yes
459 context_fns->allow_connect = lp_parm_bool(-1,
460 "allow dcerpc auth level connect",
461 interface_name, context_fns->allow_connect);
463 ok = ndr_syntax_id_equal(abstract, &ndr_table_iremotewinspool.syntax_id);
464 if (ok) {
465 context_fns->min_auth_level = DCERPC_AUTH_LEVEL_PACKET;
468 /* add to the list of open contexts */
470 DLIST_ADD( p->contexts, context_fns );
472 return True;
476 * Is a named pipe known?
477 * @param[in] pipename Just the filename
478 * @result Do we want to serve this?
480 bool is_known_pipename(const char *pipename, struct ndr_syntax_id *syntax)
482 NTSTATUS status;
484 if (lp_disable_spoolss() && strequal(pipename, "spoolss")) {
485 DEBUG(10, ("refusing spoolss access\n"));
486 return false;
489 if (rpc_srv_get_pipe_interface_by_cli_name(pipename, syntax)) {
490 return true;
493 status = smb_probe_module("rpc", pipename);
494 if (!NT_STATUS_IS_OK(status)) {
495 DEBUG(10, ("is_known_pipename: %s unknown\n", pipename));
496 return false;
498 DEBUG(10, ("is_known_pipename: %s loaded dynamically\n", pipename));
501 * Scan the list again for the interface id
503 if (rpc_srv_get_pipe_interface_by_cli_name(pipename, syntax)) {
504 return true;
507 DEBUG(10, ("is_known_pipename: pipe %s did not register itself!\n",
508 pipename));
510 return false;
513 /*******************************************************************
514 Handle an NTLMSSP bind auth.
515 *******************************************************************/
517 static bool pipe_auth_generic_bind(struct pipes_struct *p,
518 struct ncacn_packet *pkt,
519 struct dcerpc_auth *auth_info,
520 const char *service_description,
521 DATA_BLOB *response)
523 TALLOC_CTX *mem_ctx = pkt;
524 struct gensec_security *gensec_security = NULL;
525 NTSTATUS status;
527 status = auth_generic_server_authtype_start(p,
528 auth_info->auth_type,
529 auth_info->auth_level,
530 &auth_info->credentials,
531 response,
532 p->remote_address,
533 p->local_address,
534 service_description,
535 &gensec_security);
536 if (!NT_STATUS_IS_OK(status) &&
537 !NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED))
539 DEBUG(0, (__location__ ": auth_generic_server_authtype_start[%u/%u] failed: %s\n",
540 auth_info->auth_type, auth_info->auth_level, nt_errstr(status)));
541 return false;
544 /* Make sure data is bound to the memctx, to be freed the caller */
545 talloc_steal(mem_ctx, response->data);
547 p->auth.auth_ctx = gensec_security;
548 p->auth.auth_type = auth_info->auth_type;
549 p->auth.auth_level = auth_info->auth_level;
550 p->auth.auth_context_id = auth_info->auth_context_id;
552 if (pkt->pfc_flags & DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN) {
553 p->auth.client_hdr_signing = true;
554 p->auth.hdr_signing = gensec_have_feature(gensec_security,
555 GENSEC_FEATURE_SIGN_PKT_HEADER);
558 if (p->auth.hdr_signing) {
559 gensec_want_feature(gensec_security,
560 GENSEC_FEATURE_SIGN_PKT_HEADER);
563 if (NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
564 return true;
567 status = pipe_auth_verify_final(p);
568 if (!NT_STATUS_IS_OK(status)) {
569 DEBUG(0, ("pipe_auth_verify_final failed: %s\n",
570 nt_errstr(status)));
571 return false;
574 return true;
577 /*******************************************************************
578 Process an NTLMSSP authentication response.
579 If this function succeeds, the user has been authenticated
580 and their domain, name and calling workstation stored in
581 the pipe struct.
582 *******************************************************************/
584 static bool pipe_auth_generic_verify_final(TALLOC_CTX *mem_ctx,
585 struct gensec_security *gensec_security,
586 enum dcerpc_AuthLevel auth_level,
587 struct auth_session_info **session_info)
589 NTSTATUS status;
590 bool ret;
592 DEBUG(5, (__location__ ": checking user details\n"));
594 /* Finally - if the pipe negotiated integrity (sign) or privacy (seal)
595 ensure the underlying NTLMSSP flags are also set. If not we should
596 refuse the bind. */
598 status = auth_generic_server_check_flags(gensec_security,
599 (auth_level >=
600 DCERPC_AUTH_LEVEL_PACKET),
601 (auth_level ==
602 DCERPC_AUTH_LEVEL_PRIVACY));
603 if (!NT_STATUS_IS_OK(status)) {
604 DEBUG(0, (__location__ ": Client failed to negotatie proper "
605 "security for rpc connection\n"));
606 return false;
609 TALLOC_FREE(*session_info);
611 status = auth_generic_server_get_user_info(gensec_security,
612 mem_ctx, session_info);
613 if (!NT_STATUS_IS_OK(status)) {
614 DEBUG(0, (__location__ ": failed to obtain the server info "
615 "for authenticated user: %s\n", nt_errstr(status)));
616 return false;
619 if ((*session_info)->security_token == NULL) {
620 DEBUG(1, ("Auth module failed to provide nt_user_token\n"));
621 return false;
624 if ((*session_info)->unix_token == NULL) {
625 DEBUG(1, ("Auth module failed to provide unix_token\n"));
626 return false;
630 * We're an authenticated bind over smb, so the session key needs to
631 * be set to "SystemLibraryDTC". Weird, but this is what Windows
632 * does. See the RPC-SAMBA3SESSIONKEY.
635 ret = session_info_set_session_key((*session_info), generic_session_key());
636 if (!ret) {
637 DEBUG(0, ("Failed to set session key!\n"));
638 return false;
641 return true;
644 static NTSTATUS pipe_auth_verify_final(struct pipes_struct *p)
646 struct gensec_security *gensec_security;
647 bool ok;
649 if (p->auth.auth_type == DCERPC_AUTH_TYPE_NONE) {
650 p->pipe_bound = true;
651 return NT_STATUS_OK;
654 gensec_security = p->auth.auth_ctx;
656 ok = pipe_auth_generic_verify_final(p, gensec_security,
657 p->auth.auth_level,
658 &p->session_info);
659 if (!ok) {
660 return NT_STATUS_ACCESS_DENIED;
663 p->pipe_bound = true;
665 return NT_STATUS_OK;
668 /*******************************************************************
669 Respond to a pipe bind request.
670 *******************************************************************/
672 static bool api_pipe_bind_req(struct pipes_struct *p,
673 struct ncacn_packet *pkt)
675 struct dcerpc_auth auth_info = {0};
676 uint16_t assoc_gid;
677 NTSTATUS status;
678 struct ndr_syntax_id id;
679 uint8_t pfc_flags = 0;
680 union dcerpc_payload u;
681 struct dcerpc_ack_ctx bind_ack_ctx;
682 DATA_BLOB auth_resp = data_blob_null;
683 DATA_BLOB auth_blob = data_blob_null;
684 const struct ndr_interface_table *table;
685 const char *secondary_address = NULL;
687 if (!p->allow_bind) {
688 DEBUG(2,("Pipe not in allow bind state\n"));
689 return setup_bind_nak(p, pkt);
691 p->allow_bind = false;
693 status = dcerpc_verify_ncacn_packet_header(pkt,
694 DCERPC_PKT_BIND,
695 pkt->u.bind.auth_info.length,
696 0, /* required flags */
697 DCERPC_PFC_FLAG_FIRST |
698 DCERPC_PFC_FLAG_LAST |
699 DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN |
700 0x08 | /* this is not defined, but should be ignored */
701 DCERPC_PFC_FLAG_CONC_MPX |
702 DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
703 DCERPC_PFC_FLAG_MAYBE |
704 DCERPC_PFC_FLAG_OBJECT_UUID);
705 if (!NT_STATUS_IS_OK(status)) {
706 DEBUG(1, ("api_pipe_bind_req: invalid pdu: %s\n",
707 nt_errstr(status)));
708 NDR_PRINT_DEBUG(ncacn_packet, pkt);
709 goto err_exit;
712 if (pkt->u.bind.num_contexts == 0) {
713 DEBUG(1, ("api_pipe_bind_req: no rpc contexts around\n"));
714 goto err_exit;
717 if (pkt->u.bind.ctx_list[0].num_transfer_syntaxes == 0) {
718 DEBUG(1, ("api_pipe_bind_req: no transfer syntaxes around\n"));
719 goto err_exit;
723 * Try and find the correct pipe name to ensure
724 * that this is a pipe name we support.
726 id = pkt->u.bind.ctx_list[0].abstract_syntax;
728 table = ndr_table_by_uuid(&id.uuid);
729 if (table == NULL) {
730 DEBUG(0,("unknown interface\n"));
731 return false;
734 if (rpc_srv_pipe_exists_by_id(&id)) {
735 DEBUG(3, ("api_pipe_bind_req: %s -> %s rpc service\n",
736 rpc_srv_get_pipe_cli_name(&id),
737 rpc_srv_get_pipe_srv_name(&id)));
738 } else {
739 status = smb_probe_module(
740 "rpc", dcerpc_default_transport_endpoint(pkt,
741 NCACN_NP, table));
743 if (NT_STATUS_IS_ERR(status)) {
744 DEBUG(3,("api_pipe_bind_req: Unknown rpc service name "
745 "%s in bind request.\n",
746 ndr_interface_name(&id.uuid,
747 id.if_version)));
749 return setup_bind_nak(p, pkt);
752 if (rpc_srv_get_pipe_interface_by_cli_name(
753 dcerpc_default_transport_endpoint(pkt,
754 NCACN_NP, table),
755 &id)) {
756 DEBUG(3, ("api_pipe_bind_req: %s -> %s rpc service\n",
757 rpc_srv_get_pipe_cli_name(&id),
758 rpc_srv_get_pipe_srv_name(&id)));
759 } else {
760 DEBUG(0, ("module %s doesn't provide functions for "
761 "pipe %s!\n",
762 ndr_interface_name(&id.uuid,
763 id.if_version),
764 ndr_interface_name(&id.uuid,
765 id.if_version)));
766 return setup_bind_nak(p, pkt);
770 DEBUG(5,("api_pipe_bind_req: make response. %d\n", __LINE__));
772 if (pkt->u.bind.assoc_group_id != 0) {
773 assoc_gid = pkt->u.bind.assoc_group_id;
774 } else {
775 assoc_gid = 0x53f0;
779 * Create the bind response struct.
782 /* If the requested abstract synt uuid doesn't match our client pipe,
783 reject the bind_ack & set the transfer interface synt to all 0's,
784 ver 0 (observed when NT5 attempts to bind to abstract interfaces
785 unknown to NT4)
786 Needed when adding entries to a DACL from NT5 - SK */
788 if (check_bind_req(p,
789 &pkt->u.bind.ctx_list[0].abstract_syntax,
790 &pkt->u.bind.ctx_list[0].transfer_syntaxes[0],
791 pkt->u.bind.ctx_list[0].context_id)) {
793 bind_ack_ctx.result = 0;
794 bind_ack_ctx.reason.value = 0;
795 bind_ack_ctx.syntax = pkt->u.bind.ctx_list[0].transfer_syntaxes[0];
796 } else {
797 /* Rejection reason: abstract syntax not supported */
798 bind_ack_ctx.result = DCERPC_BIND_PROVIDER_REJECT;
799 bind_ack_ctx.reason.value = DCERPC_BIND_REASON_ASYNTAX;
800 bind_ack_ctx.syntax = ndr_syntax_id_null;
804 * Check if this is an authenticated bind request.
806 if (pkt->auth_length) {
808 * Decode the authentication verifier.
810 status = dcerpc_pull_auth_trailer(pkt, pkt,
811 &pkt->u.bind.auth_info,
812 &auth_info, NULL, true);
813 if (!NT_STATUS_IS_OK(status)) {
814 DEBUG(0, ("Unable to unmarshall dcerpc_auth.\n"));
815 goto err_exit;
818 if (!pipe_auth_generic_bind(p, pkt,
819 &auth_info,
820 table->name,
821 &auth_resp)) {
822 goto err_exit;
824 } else {
825 p->auth.auth_type = DCERPC_AUTH_TYPE_NONE;
826 p->auth.auth_level = DCERPC_AUTH_LEVEL_NONE;
827 p->auth.auth_context_id = 0;
830 * Log the authorization to this RPC interface. This
831 * covered ncacn_np pass-through auth, and anonymous
832 * DCE/RPC (eg epmapper, netlogon etc)
834 log_successful_authz_event(p->remote_address,
835 p->local_address,
836 table->name,
837 derpc_transport_string_by_transport(p->transport),
838 p->session_info);
841 ZERO_STRUCT(u.bind_ack);
842 u.bind_ack.max_xmit_frag = RPC_MAX_PDU_FRAG_LEN;
843 u.bind_ack.max_recv_frag = RPC_MAX_PDU_FRAG_LEN;
844 u.bind_ack.assoc_group_id = assoc_gid;
846 switch (p->transport) {
847 case NCACN_IP_TCP:
848 secondary_address = talloc_asprintf(pkt, "%d",
849 tsocket_address_inet_port(p->local_address));
850 break;
851 case NCACN_NP:
852 default:
853 /* name has to be \PIPE\xxxxx */
854 secondary_address =
855 talloc_asprintf(pkt, "\\PIPE\\%s",
856 rpc_srv_get_pipe_srv_name(&id));
857 break;
860 if (secondary_address == NULL) {
861 DEBUG(0, ("Out of memory!\n"));
862 goto err_exit;
865 u.bind_ack.secondary_address = secondary_address;
866 u.bind_ack.secondary_address_size =
867 strlen(u.bind_ack.secondary_address) + 1;
869 u.bind_ack.num_results = 1;
870 u.bind_ack.ctx_list = &bind_ack_ctx;
872 /* NOTE: We leave the auth_info empty so we can calculate the padding
873 * later and then append the auth_info --simo */
876 * Marshall directly into the outgoing PDU space. We
877 * must do this as we need to set to the bind response
878 * header and are never sending more than one PDU here.
881 pfc_flags = DCERPC_PFC_FLAG_FIRST | DCERPC_PFC_FLAG_LAST;
883 if (p->auth.hdr_signing) {
884 pfc_flags |= DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN;
887 status = dcerpc_push_ncacn_packet(p->mem_ctx,
888 DCERPC_PKT_BIND_ACK,
889 pfc_flags,
890 auth_resp.length,
891 pkt->call_id,
893 &p->out_data.frag);
894 if (!NT_STATUS_IS_OK(status)) {
895 DEBUG(0, ("Failed to marshall bind_ack packet. (%s)\n",
896 nt_errstr(status)));
897 goto err_exit;
900 if (auth_resp.length) {
901 status = dcerpc_push_dcerpc_auth(pkt,
902 p->auth.auth_type,
903 p->auth.auth_level,
904 0, /* pad_len */
905 p->auth.auth_context_id,
906 &auth_resp,
907 &auth_blob);
908 if (!NT_STATUS_IS_OK(status)) {
909 DEBUG(0, ("Marshalling of dcerpc_auth failed.\n"));
910 goto err_exit;
914 /* Now that we have the auth len store it into the right place in
915 * the dcerpc header */
916 dcerpc_set_frag_length(&p->out_data.frag,
917 p->out_data.frag.length + auth_blob.length);
919 if (auth_blob.length) {
921 if (!data_blob_append(p->mem_ctx, &p->out_data.frag,
922 auth_blob.data, auth_blob.length)) {
923 DEBUG(0, ("Append of auth info failed.\n"));
924 goto err_exit;
929 * Setup the lengths for the initial reply.
932 p->out_data.data_sent_length = 0;
933 p->out_data.current_pdu_sent = 0;
935 TALLOC_FREE(auth_blob.data);
937 if (bind_ack_ctx.result == 0) {
938 p->allow_alter = true;
939 p->allow_auth3 = true;
940 if (p->auth.auth_type == DCERPC_AUTH_TYPE_NONE) {
941 status = pipe_auth_verify_final(p);
942 if (!NT_STATUS_IS_OK(status)) {
943 DEBUG(0, ("pipe_auth_verify_final failed: %s\n",
944 nt_errstr(status)));
945 goto err_exit;
948 } else {
949 goto err_exit;
952 return True;
954 err_exit:
956 data_blob_free(&p->out_data.frag);
957 TALLOC_FREE(auth_blob.data);
958 return setup_bind_nak(p, pkt);
961 /*******************************************************************
962 This is the "stage3" response after a bind request and reply.
963 *******************************************************************/
965 bool api_pipe_bind_auth3(struct pipes_struct *p, struct ncacn_packet *pkt)
967 struct dcerpc_auth auth_info;
968 DATA_BLOB response = data_blob_null;
969 struct gensec_security *gensec_security;
970 NTSTATUS status;
972 DEBUG(5, ("api_pipe_bind_auth3: decode request. %d\n", __LINE__));
974 if (!p->allow_auth3) {
975 DEBUG(1, ("Pipe not in allow auth3 state.\n"));
976 goto err;
979 status = dcerpc_verify_ncacn_packet_header(pkt,
980 DCERPC_PKT_AUTH3,
981 pkt->u.auth3.auth_info.length,
982 0, /* required flags */
983 DCERPC_PFC_FLAG_FIRST |
984 DCERPC_PFC_FLAG_LAST |
985 DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN |
986 0x08 | /* this is not defined, but should be ignored */
987 DCERPC_PFC_FLAG_CONC_MPX |
988 DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
989 DCERPC_PFC_FLAG_MAYBE |
990 DCERPC_PFC_FLAG_OBJECT_UUID);
991 if (!NT_STATUS_IS_OK(status)) {
992 DEBUG(1, ("api_pipe_bind_auth3: invalid pdu: %s\n",
993 nt_errstr(status)));
994 NDR_PRINT_DEBUG(ncacn_packet, pkt);
995 goto err;
998 /* We can only finish if the pipe is unbound for now */
999 if (p->pipe_bound) {
1000 DEBUG(0, (__location__ ": Pipe already bound, "
1001 "AUTH3 not supported!\n"));
1002 goto err;
1005 if (pkt->auth_length == 0) {
1006 DEBUG(1, ("No auth field sent for auth3 request!\n"));
1007 goto err;
1011 * Decode the authentication verifier response.
1014 status = dcerpc_pull_auth_trailer(pkt, pkt,
1015 &pkt->u.auth3.auth_info,
1016 &auth_info, NULL, true);
1017 if (!NT_STATUS_IS_OK(status)) {
1018 DEBUG(1, ("Failed to unmarshall dcerpc_auth.\n"));
1019 goto err;
1022 /* We must NEVER look at auth_info->auth_pad_len here,
1023 * as old Samba client code gets it wrong and sends it
1024 * as zero. JRA.
1027 if (auth_info.auth_type != p->auth.auth_type) {
1028 DEBUG(1, ("Auth type mismatch! Client sent %d, "
1029 "but auth was started as type %d!\n",
1030 auth_info.auth_type, p->auth.auth_type));
1031 goto err;
1034 if (auth_info.auth_level != p->auth.auth_level) {
1035 DEBUG(1, ("Auth level mismatch! Client sent %d, "
1036 "but auth was started as level %d!\n",
1037 auth_info.auth_level, p->auth.auth_level));
1038 goto err;
1041 if (auth_info.auth_context_id != p->auth.auth_context_id) {
1042 DEBUG(0, ("Auth context id mismatch! Client sent %u, "
1043 "but auth was started as level %u!\n",
1044 (unsigned)auth_info.auth_context_id,
1045 (unsigned)p->auth.auth_context_id));
1046 goto err;
1049 gensec_security = p->auth.auth_ctx;
1051 status = auth_generic_server_step(gensec_security,
1052 pkt, &auth_info.credentials,
1053 &response);
1055 if (NT_STATUS_EQUAL(status,
1056 NT_STATUS_MORE_PROCESSING_REQUIRED) ||
1057 response.length) {
1058 DEBUG(1, (__location__ ": This was supposed to be the final "
1059 "leg, but crypto machinery claims a response is "
1060 "needed, aborting auth!\n"));
1061 data_blob_free(&response);
1062 goto err;
1064 if (!NT_STATUS_IS_OK(status)) {
1065 DEBUG(2, ("Auth failed (%s)\n", nt_errstr(status)));
1066 goto err;
1069 /* Now verify auth was indeed successful and extract server info */
1070 status = pipe_auth_verify_final(p);
1071 if (!NT_STATUS_IS_OK(status)) {
1072 DEBUG(2, ("Auth Verify failed (%s)\n", nt_errstr(status)));
1073 goto err;
1076 return true;
1078 err:
1079 p->pipe_bound = false;
1080 p->allow_bind = false;
1081 p->allow_alter = false;
1082 p->allow_auth3 = false;
1084 TALLOC_FREE(p->auth.auth_ctx);
1085 return false;
1088 /****************************************************************************
1089 Deal with an alter context call. Can be third part of 3 leg auth request for
1090 SPNEGO calls.
1091 ****************************************************************************/
1093 static bool api_pipe_alter_context(struct pipes_struct *p,
1094 struct ncacn_packet *pkt)
1096 struct dcerpc_auth auth_info = {0};
1097 uint16_t assoc_gid;
1098 NTSTATUS status;
1099 union dcerpc_payload u;
1100 struct dcerpc_ack_ctx alter_ack_ctx;
1101 DATA_BLOB auth_resp = data_blob_null;
1102 DATA_BLOB auth_blob = data_blob_null;
1103 struct gensec_security *gensec_security;
1105 DEBUG(5,("api_pipe_alter_context: make response. %d\n", __LINE__));
1107 if (!p->allow_alter) {
1108 DEBUG(1, ("Pipe not in allow alter state.\n"));
1109 goto err_exit;
1112 status = dcerpc_verify_ncacn_packet_header(pkt,
1113 DCERPC_PKT_ALTER,
1114 pkt->u.alter.auth_info.length,
1115 0, /* required flags */
1116 DCERPC_PFC_FLAG_FIRST |
1117 DCERPC_PFC_FLAG_LAST |
1118 DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN |
1119 0x08 | /* this is not defined, but should be ignored */
1120 DCERPC_PFC_FLAG_CONC_MPX |
1121 DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
1122 DCERPC_PFC_FLAG_MAYBE |
1123 DCERPC_PFC_FLAG_OBJECT_UUID);
1124 if (!NT_STATUS_IS_OK(status)) {
1125 DEBUG(1, ("api_pipe_alter_context: invalid pdu: %s\n",
1126 nt_errstr(status)));
1127 NDR_PRINT_DEBUG(ncacn_packet, pkt);
1128 goto err_exit;
1131 if (pkt->u.alter.num_contexts == 0) {
1132 DEBUG(1, ("api_pipe_alter_context: no rpc contexts around\n"));
1133 goto err_exit;
1136 if (pkt->u.alter.ctx_list[0].num_transfer_syntaxes == 0) {
1137 DEBUG(1, ("api_pipe_alter_context: no transfer syntaxes around\n"));
1138 goto err_exit;
1141 if (pkt->u.alter.assoc_group_id != 0) {
1142 assoc_gid = pkt->u.alter.assoc_group_id;
1143 } else {
1144 assoc_gid = 0x53f0;
1148 * Create the bind response struct.
1151 /* If the requested abstract synt uuid doesn't match our client pipe,
1152 reject the alter_ack & set the transfer interface synt to all 0's,
1153 ver 0 (observed when NT5 attempts to bind to abstract interfaces
1154 unknown to NT4)
1155 Needed when adding entries to a DACL from NT5 - SK */
1157 if (check_bind_req(p,
1158 &pkt->u.alter.ctx_list[0].abstract_syntax,
1159 &pkt->u.alter.ctx_list[0].transfer_syntaxes[0],
1160 pkt->u.alter.ctx_list[0].context_id)) {
1162 alter_ack_ctx.result = 0;
1163 alter_ack_ctx.reason.value = 0;
1164 alter_ack_ctx.syntax = pkt->u.alter.ctx_list[0].transfer_syntaxes[0];
1165 } else {
1166 /* Rejection reason: abstract syntax not supported */
1167 alter_ack_ctx.result = DCERPC_BIND_PROVIDER_REJECT;
1168 alter_ack_ctx.reason.value = DCERPC_BIND_REASON_ASYNTAX;
1169 alter_ack_ctx.syntax = ndr_syntax_id_null;
1173 * Check if this is an authenticated alter context request.
1175 if (pkt->auth_length) {
1176 /* We can only finish if the pipe is unbound for now */
1177 if (p->pipe_bound) {
1178 DEBUG(0, (__location__ ": Pipe already bound, "
1179 "Altering Context not yet supported!\n"));
1180 goto err_exit;
1183 status = dcerpc_pull_auth_trailer(pkt, pkt,
1184 &pkt->u.alter.auth_info,
1185 &auth_info, NULL, true);
1186 if (!NT_STATUS_IS_OK(status)) {
1187 DEBUG(0, ("Unable to unmarshall dcerpc_auth.\n"));
1188 goto err_exit;
1191 if (auth_info.auth_type != p->auth.auth_type) {
1192 DEBUG(0, ("Auth type mismatch! Client sent %d, "
1193 "but auth was started as type %d!\n",
1194 auth_info.auth_type, p->auth.auth_type));
1195 goto err_exit;
1198 if (auth_info.auth_level != p->auth.auth_level) {
1199 DEBUG(0, ("Auth level mismatch! Client sent %d, "
1200 "but auth was started as level %d!\n",
1201 auth_info.auth_level, p->auth.auth_level));
1202 goto err_exit;
1205 if (auth_info.auth_context_id != p->auth.auth_context_id) {
1206 DEBUG(0, ("Auth context id mismatch! Client sent %u, "
1207 "but auth was started as level %u!\n",
1208 (unsigned)auth_info.auth_context_id,
1209 (unsigned)p->auth.auth_context_id));
1210 goto err_exit;
1213 gensec_security = p->auth.auth_ctx;
1214 status = auth_generic_server_step(gensec_security,
1215 pkt,
1216 &auth_info.credentials,
1217 &auth_resp);
1218 if (NT_STATUS_IS_OK(status)) {
1219 /* third leg of auth, verify auth info */
1220 status = pipe_auth_verify_final(p);
1221 if (!NT_STATUS_IS_OK(status)) {
1222 DEBUG(0, ("Auth Verify failed (%s)\n",
1223 nt_errstr(status)));
1224 goto err_exit;
1226 } else if (NT_STATUS_EQUAL(status,
1227 NT_STATUS_MORE_PROCESSING_REQUIRED)) {
1228 DEBUG(10, ("More auth legs required.\n"));
1229 } else {
1230 DEBUG(0, ("Auth step returned an error (%s)\n",
1231 nt_errstr(status)));
1232 goto err_exit;
1236 ZERO_STRUCT(u.alter_resp);
1237 u.alter_resp.max_xmit_frag = RPC_MAX_PDU_FRAG_LEN;
1238 u.alter_resp.max_recv_frag = RPC_MAX_PDU_FRAG_LEN;
1239 u.alter_resp.assoc_group_id = assoc_gid;
1241 /* secondary address CAN be NULL
1242 * as the specs say it's ignored.
1243 * It MUST be NULL to have the spoolss working.
1245 u.alter_resp.secondary_address = "";
1246 u.alter_resp.secondary_address_size = 1;
1248 u.alter_resp.num_results = 1;
1249 u.alter_resp.ctx_list = &alter_ack_ctx;
1251 /* NOTE: We leave the auth_info empty so we can calculate the padding
1252 * later and then append the auth_info --simo */
1255 * Marshall directly into the outgoing PDU space. We
1256 * must do this as we need to set to the bind response
1257 * header and are never sending more than one PDU here.
1260 status = dcerpc_push_ncacn_packet(p->mem_ctx,
1261 DCERPC_PKT_ALTER_RESP,
1262 DCERPC_PFC_FLAG_FIRST |
1263 DCERPC_PFC_FLAG_LAST,
1264 auth_resp.length,
1265 pkt->call_id,
1267 &p->out_data.frag);
1268 if (!NT_STATUS_IS_OK(status)) {
1269 DEBUG(0, ("Failed to marshall alter_resp packet. (%s)\n",
1270 nt_errstr(status)));
1271 goto err_exit;
1274 if (auth_resp.length) {
1275 status = dcerpc_push_dcerpc_auth(pkt,
1276 p->auth.auth_type,
1277 p->auth.auth_level,
1278 0, /* pad_len */
1279 p->auth.auth_context_id,
1280 &auth_resp,
1281 &auth_blob);
1282 if (!NT_STATUS_IS_OK(status)) {
1283 DEBUG(0, ("Marshalling of dcerpc_auth failed.\n"));
1284 goto err_exit;
1288 /* Now that we have the auth len store it into the right place in
1289 * the dcerpc header */
1290 dcerpc_set_frag_length(&p->out_data.frag,
1291 p->out_data.frag.length +
1292 auth_blob.length);
1294 if (auth_resp.length) {
1295 if (!data_blob_append(p->mem_ctx, &p->out_data.frag,
1296 auth_blob.data, auth_blob.length)) {
1297 DEBUG(0, ("Append of auth info failed.\n"));
1298 goto err_exit;
1303 * Setup the lengths for the initial reply.
1306 p->out_data.data_sent_length = 0;
1307 p->out_data.current_pdu_sent = 0;
1309 TALLOC_FREE(auth_blob.data);
1310 return True;
1312 err_exit:
1314 data_blob_free(&p->out_data.frag);
1315 TALLOC_FREE(auth_blob.data);
1316 return setup_bind_nak(p, pkt);
1319 static bool api_rpcTNP(struct pipes_struct *p, struct ncacn_packet *pkt,
1320 const struct api_struct *api_rpc_cmds, int n_cmds,
1321 const struct ndr_syntax_id *syntax);
1323 static bool srv_pipe_check_verification_trailer(struct pipes_struct *p,
1324 struct ncacn_packet *pkt,
1325 struct pipe_rpc_fns *pipe_fns)
1327 TALLOC_CTX *frame = talloc_stackframe();
1328 struct dcerpc_sec_verification_trailer *vt = NULL;
1329 const uint32_t bitmask1 =
1330 p->auth.client_hdr_signing ? DCERPC_SEC_VT_CLIENT_SUPPORTS_HEADER_SIGNING : 0;
1331 const struct dcerpc_sec_vt_pcontext pcontext = {
1332 .abstract_syntax = pipe_fns->syntax,
1333 .transfer_syntax = ndr_transfer_syntax_ndr,
1335 const struct dcerpc_sec_vt_header2 header2 =
1336 dcerpc_sec_vt_header2_from_ncacn_packet(pkt);
1337 struct ndr_pull *ndr;
1338 enum ndr_err_code ndr_err;
1339 bool ret = false;
1341 ndr = ndr_pull_init_blob(&p->in_data.data, frame);
1342 if (ndr == NULL) {
1343 goto done;
1346 ndr_err = ndr_pop_dcerpc_sec_verification_trailer(ndr, frame, &vt);
1347 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
1348 goto done;
1351 ret = dcerpc_sec_verification_trailer_check(vt, &bitmask1,
1352 &pcontext, &header2);
1353 done:
1354 TALLOC_FREE(frame);
1355 return ret;
1358 /****************************************************************************
1359 Find the correct RPC function to call for this request.
1360 If the pipe is authenticated then become the correct UNIX user
1361 before doing the call.
1362 ****************************************************************************/
1364 static bool api_pipe_request(struct pipes_struct *p,
1365 struct ncacn_packet *pkt)
1367 TALLOC_CTX *frame = talloc_stackframe();
1368 bool ret = False;
1369 struct pipe_rpc_fns *pipe_fns;
1370 const char *interface_name = NULL;
1372 if (!p->pipe_bound) {
1373 DEBUG(1, ("Pipe not bound!\n"));
1374 data_blob_free(&p->out_data.rdata);
1375 TALLOC_FREE(frame);
1376 return false;
1379 /* get the set of RPC functions for this context */
1380 pipe_fns = find_pipe_fns_by_context(p->contexts,
1381 pkt->u.request.context_id);
1382 if (pipe_fns == NULL) {
1383 DEBUG(0, ("No rpc function table associated with context "
1384 "[%d]\n",
1385 pkt->u.request.context_id));
1386 data_blob_free(&p->out_data.rdata);
1387 TALLOC_FREE(frame);
1388 return false;
1391 interface_name = ndr_interface_name(&pipe_fns->syntax.uuid,
1392 pipe_fns->syntax.if_version);
1393 SMB_ASSERT(interface_name != NULL);
1395 if (p->auth.auth_level < pipe_fns->min_auth_level) {
1397 DEBUG(1, ("%s: auth level required for %s: 0x%x, got: 0x%0x\n",
1398 __func__, interface_name,
1399 pipe_fns->min_auth_level,
1400 p->auth.auth_level));
1402 setup_fault_pdu(p, NT_STATUS(DCERPC_FAULT_ACCESS_DENIED));
1403 TALLOC_FREE(frame);
1404 return true;
1407 switch (p->auth.auth_level) {
1408 case DCERPC_AUTH_LEVEL_NONE:
1409 case DCERPC_AUTH_LEVEL_PACKET:
1410 case DCERPC_AUTH_LEVEL_INTEGRITY:
1411 case DCERPC_AUTH_LEVEL_PRIVACY:
1412 break;
1413 default:
1414 if (!pipe_fns->allow_connect) {
1415 char *addr;
1417 addr = tsocket_address_string(p->remote_address, frame);
1419 DEBUG(1, ("%s: restrict auth_level_connect access "
1420 "to [%s] with auth[type=0x%x,level=0x%x] "
1421 "on [%s] from [%s]\n",
1422 __func__, interface_name,
1423 p->auth.auth_type,
1424 p->auth.auth_level,
1425 derpc_transport_string_by_transport(p->transport),
1426 addr));
1428 setup_fault_pdu(p, NT_STATUS(DCERPC_FAULT_ACCESS_DENIED));
1429 TALLOC_FREE(frame);
1430 return true;
1432 break;
1435 if (!srv_pipe_check_verification_trailer(p, pkt, pipe_fns)) {
1436 DEBUG(1, ("srv_pipe_check_verification_trailer: failed\n"));
1437 set_incoming_fault(p);
1438 setup_fault_pdu(p, NT_STATUS(DCERPC_FAULT_ACCESS_DENIED));
1439 data_blob_free(&p->out_data.rdata);
1440 TALLOC_FREE(frame);
1441 return true;
1444 if (!become_authenticated_pipe_user(p->session_info)) {
1445 DEBUG(1, ("Failed to become pipe user!\n"));
1446 data_blob_free(&p->out_data.rdata);
1447 TALLOC_FREE(frame);
1448 return false;
1451 DEBUG(5, ("Requested %s rpc service\n", interface_name));
1453 ret = api_rpcTNP(p, pkt, pipe_fns->cmds, pipe_fns->n_cmds,
1454 &pipe_fns->syntax);
1455 unbecome_authenticated_pipe_user();
1457 TALLOC_FREE(frame);
1458 return ret;
1461 /*******************************************************************
1462 Calls the underlying RPC function for a named pipe.
1463 ********************************************************************/
1465 static bool api_rpcTNP(struct pipes_struct *p, struct ncacn_packet *pkt,
1466 const struct api_struct *api_rpc_cmds, int n_cmds,
1467 const struct ndr_syntax_id *syntax)
1469 int fn_num;
1470 uint32_t offset1;
1471 const struct ndr_interface_table *table;
1473 /* interpret the command */
1474 DEBUG(4,("api_rpcTNP: %s op 0x%x - ",
1475 ndr_interface_name(&syntax->uuid, syntax->if_version),
1476 pkt->u.request.opnum));
1478 table = ndr_table_by_uuid(&syntax->uuid);
1479 if (table == NULL) {
1480 DEBUG(0,("unknown interface\n"));
1481 return false;
1484 if (DEBUGLEVEL >= 50) {
1485 fstring name;
1486 slprintf(name, sizeof(name)-1, "in_%s",
1487 dcerpc_default_transport_endpoint(pkt, NCACN_NP, table));
1488 dump_pdu_region(name, pkt->u.request.opnum,
1489 &p->in_data.data, 0,
1490 p->in_data.data.length);
1493 for (fn_num = 0; fn_num < n_cmds; fn_num++) {
1494 if (api_rpc_cmds[fn_num].opnum == pkt->u.request.opnum &&
1495 api_rpc_cmds[fn_num].fn != NULL) {
1496 DEBUG(3, ("api_rpcTNP: rpc command: %s\n",
1497 api_rpc_cmds[fn_num].name));
1498 break;
1502 if (fn_num == n_cmds) {
1504 * For an unknown RPC just return a fault PDU but
1505 * return True to allow RPC's on the pipe to continue
1506 * and not put the pipe into fault state. JRA.
1508 DEBUG(4, ("unknown\n"));
1509 setup_fault_pdu(p, NT_STATUS(DCERPC_FAULT_OP_RNG_ERROR));
1510 return True;
1513 offset1 = p->out_data.rdata.length;
1515 DEBUG(6, ("api_rpc_cmds[%d].fn == %p\n",
1516 fn_num, api_rpc_cmds[fn_num].fn));
1517 /* do the actual command */
1518 if(!api_rpc_cmds[fn_num].fn(p)) {
1519 DEBUG(0,("api_rpcTNP: %s: %s failed.\n",
1520 ndr_interface_name(&syntax->uuid, syntax->if_version),
1521 api_rpc_cmds[fn_num].name));
1522 data_blob_free(&p->out_data.rdata);
1523 return False;
1526 if (p->fault_state) {
1527 DEBUG(4,("api_rpcTNP: fault(%d) return.\n", p->fault_state));
1528 setup_fault_pdu(p, NT_STATUS(p->fault_state));
1529 p->fault_state = 0;
1530 return true;
1533 if (DEBUGLEVEL >= 50) {
1534 fstring name;
1535 slprintf(name, sizeof(name)-1, "out_%s",
1536 dcerpc_default_transport_endpoint(pkt, NCACN_NP, table));
1537 dump_pdu_region(name, pkt->u.request.opnum,
1538 &p->out_data.rdata, offset1,
1539 p->out_data.rdata.length);
1542 DEBUG(5,("api_rpcTNP: called %s successfully\n",
1543 ndr_interface_name(&syntax->uuid, syntax->if_version)));
1545 /* Check for buffer underflow in rpc parsing */
1546 if ((DEBUGLEVEL >= 10) &&
1547 (pkt->frag_length < p->in_data.data.length)) {
1548 DEBUG(10, ("api_rpcTNP: rpc input buffer underflow (parse error?)\n"));
1549 dump_data(10, p->in_data.data.data + pkt->frag_length,
1550 p->in_data.data.length - pkt->frag_length);
1553 return True;
1556 /****************************************************************************
1557 Initialise an outgoing packet.
1558 ****************************************************************************/
1560 static bool pipe_init_outgoing_data(struct pipes_struct *p)
1562 output_data *o_data = &p->out_data;
1564 /* Reset the offset counters. */
1565 o_data->data_sent_length = 0;
1566 o_data->current_pdu_sent = 0;
1568 data_blob_free(&o_data->frag);
1570 /* Free any memory in the current return data buffer. */
1571 data_blob_free(&o_data->rdata);
1573 return True;
1576 /****************************************************************************
1577 Sets the fault state on incoming packets.
1578 ****************************************************************************/
1580 void set_incoming_fault(struct pipes_struct *p)
1582 data_blob_free(&p->in_data.data);
1583 p->in_data.pdu_needed_len = 0;
1584 p->in_data.pdu.length = 0;
1585 p->fault_state = DCERPC_NCA_S_PROTO_ERROR;
1587 p->allow_alter = false;
1588 p->allow_auth3 = false;
1589 p->pipe_bound = false;
1591 DEBUG(10, ("Setting fault state\n"));
1594 static NTSTATUS dcesrv_auth_request(struct pipe_auth_data *auth,
1595 struct ncacn_packet *pkt,
1596 DATA_BLOB *raw_pkt)
1598 NTSTATUS status;
1599 size_t hdr_size = DCERPC_REQUEST_LENGTH;
1601 DEBUG(10, ("Checking request auth.\n"));
1603 if (pkt->pfc_flags & DCERPC_PFC_FLAG_OBJECT_UUID) {
1604 hdr_size += 16;
1607 /* in case of sealing this function will unseal the data in place */
1608 status = dcerpc_check_auth(auth, pkt,
1609 &pkt->u.request.stub_and_verifier,
1610 hdr_size, raw_pkt);
1611 if (!NT_STATUS_IS_OK(status)) {
1612 return status;
1615 return NT_STATUS_OK;
1618 /****************************************************************************
1619 Processes a request pdu. This will do auth processing if needed, and
1620 appends the data into the complete stream if the LAST flag is not set.
1621 ****************************************************************************/
1623 static bool process_request_pdu(struct pipes_struct *p, struct ncacn_packet *pkt)
1625 NTSTATUS status;
1626 DATA_BLOB data;
1627 struct dcerpc_sec_vt_header2 hdr2;
1629 if (!p->pipe_bound) {
1630 DEBUG(0,("process_request_pdu: rpc request with no bind.\n"));
1631 set_incoming_fault(p);
1632 return False;
1636 * We don't ignore DCERPC_PFC_FLAG_PENDING_CANCEL.
1637 * TODO: we can reject it with DCERPC_FAULT_NO_CALL_ACTIVE later.
1639 status = dcerpc_verify_ncacn_packet_header(pkt,
1640 DCERPC_PKT_REQUEST,
1641 pkt->u.request.stub_and_verifier.length,
1642 0, /* required_flags */
1643 DCERPC_PFC_FLAG_FIRST |
1644 DCERPC_PFC_FLAG_LAST |
1645 0x08 | /* this is not defined, but should be ignored */
1646 DCERPC_PFC_FLAG_CONC_MPX |
1647 DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
1648 DCERPC_PFC_FLAG_MAYBE |
1649 DCERPC_PFC_FLAG_OBJECT_UUID);
1650 if (!NT_STATUS_IS_OK(status)) {
1651 DEBUG(1, ("process_request_pdu: invalid pdu: %s\n",
1652 nt_errstr(status)));
1653 NDR_PRINT_DEBUG(ncacn_packet, pkt);
1654 set_incoming_fault(p);
1655 return false;
1658 hdr2 = dcerpc_sec_vt_header2_from_ncacn_packet(pkt);
1659 if (pkt->pfc_flags & DCERPC_PFC_FLAG_FIRST) {
1660 p->header2 = hdr2;
1661 } else {
1662 if (!dcerpc_sec_vt_header2_equal(&hdr2, &p->header2)) {
1663 set_incoming_fault(p);
1664 return false;
1668 /* Store the opnum */
1669 p->opnum = pkt->u.request.opnum;
1671 status = dcesrv_auth_request(&p->auth, pkt, &p->in_data.pdu);
1672 if (!NT_STATUS_IS_OK(status)) {
1673 DEBUG(0, ("Failed to check packet auth. (%s)\n",
1674 nt_errstr(status)));
1675 set_incoming_fault(p);
1676 return false;
1679 data = pkt->u.request.stub_and_verifier;
1682 * Check the data length doesn't go over the 15Mb limit.
1683 * increased after observing a bug in the Windows NT 4.0 SP6a
1684 * spoolsv.exe when the response to a GETPRINTERDRIVER2 RPC
1685 * will not fit in the initial buffer of size 0x1068 --jerry 22/01/2002
1688 if (p->in_data.data.length + data.length > MAX_RPC_DATA_SIZE) {
1689 DEBUG(0, ("process_request_pdu: "
1690 "rpc data buffer too large (%u) + (%u)\n",
1691 (unsigned int)p->in_data.data.length,
1692 (unsigned int)data.length));
1693 set_incoming_fault(p);
1694 return False;
1698 * Append the data portion into the buffer and return.
1701 if (data.length) {
1702 if (!data_blob_append(p->mem_ctx, &p->in_data.data,
1703 data.data, data.length)) {
1704 DEBUG(0, ("Unable to append data size %u "
1705 "to parse buffer of size %u.\n",
1706 (unsigned int)data.length,
1707 (unsigned int)p->in_data.data.length));
1708 set_incoming_fault(p);
1709 return False;
1713 if (!(pkt->pfc_flags & DCERPC_PFC_FLAG_LAST)) {
1714 return true;
1718 * Ok - we finally have a complete RPC stream.
1719 * Call the rpc command to process it.
1722 return api_pipe_request(p, pkt);
1725 void process_complete_pdu(struct pipes_struct *p, struct ncacn_packet *pkt)
1727 bool reply = false;
1729 /* Store the call_id */
1730 p->call_id = pkt->call_id;
1732 DEBUG(10, ("Processing packet type %u\n", (unsigned int)pkt->ptype));
1734 if (!pipe_init_outgoing_data(p)) {
1735 goto done;
1738 switch (pkt->ptype) {
1739 case DCERPC_PKT_REQUEST:
1740 reply = process_request_pdu(p, pkt);
1741 break;
1743 case DCERPC_PKT_PING: /* CL request - ignore... */
1744 DEBUG(0, ("Error - Connectionless packet type %u received\n",
1745 (unsigned int)pkt->ptype));
1746 break;
1748 case DCERPC_PKT_RESPONSE: /* No responses here. */
1749 DEBUG(0, ("Error - DCERPC_PKT_RESPONSE received from client"));
1750 break;
1752 case DCERPC_PKT_FAULT:
1753 case DCERPC_PKT_WORKING:
1754 /* CL request - reply to a ping when a call in process. */
1755 case DCERPC_PKT_NOCALL:
1756 /* CL - server reply to a ping call. */
1757 case DCERPC_PKT_REJECT:
1758 case DCERPC_PKT_ACK:
1759 case DCERPC_PKT_CL_CANCEL:
1760 case DCERPC_PKT_FACK:
1761 case DCERPC_PKT_CANCEL_ACK:
1762 DEBUG(0, ("Error - Connectionless packet type %u received\n",
1763 (unsigned int)pkt->ptype));
1764 break;
1766 case DCERPC_PKT_BIND:
1768 * We assume that a pipe bind is only in one pdu.
1770 reply = api_pipe_bind_req(p, pkt);
1771 break;
1773 case DCERPC_PKT_BIND_ACK:
1774 case DCERPC_PKT_BIND_NAK:
1775 DEBUG(0, ("Error - DCERPC_PKT_BINDACK/DCERPC_PKT_BINDNACK "
1776 "packet type %u received.\n",
1777 (unsigned int)pkt->ptype));
1778 break;
1781 case DCERPC_PKT_ALTER:
1783 * We assume that a pipe bind is only in one pdu.
1785 reply = api_pipe_alter_context(p, pkt);
1786 break;
1788 case DCERPC_PKT_ALTER_RESP:
1789 DEBUG(0, ("Error - DCERPC_PKT_ALTER_RESP received: "
1790 "Should only be server -> client.\n"));
1791 break;
1793 case DCERPC_PKT_AUTH3:
1795 * The third packet in an auth exchange.
1797 reply = api_pipe_bind_auth3(p, pkt);
1798 break;
1800 case DCERPC_PKT_SHUTDOWN:
1801 DEBUG(0, ("Error - DCERPC_PKT_SHUTDOWN received: "
1802 "Should only be server -> client.\n"));
1803 break;
1805 case DCERPC_PKT_CO_CANCEL:
1806 /* For now just free all client data and continue
1807 * processing. */
1808 DEBUG(3,("process_complete_pdu: DCERPC_PKT_CO_CANCEL."
1809 " Abandoning rpc call.\n"));
1810 /* As we never do asynchronous RPC serving, we can
1811 * never cancel a call (as far as I know).
1812 * If we ever did we'd have to send a cancel_ack reply.
1813 * For now, just free all client data and continue
1814 * processing. */
1815 reply = True;
1816 break;
1818 #if 0
1819 /* Enable this if we're doing async rpc. */
1820 /* We must check the outstanding callid matches. */
1821 if (pipe_init_outgoing_data(p)) {
1822 /* Send a cancel_ack PDU reply. */
1823 /* We should probably check the auth-verifier here. */
1824 reply = setup_cancel_ack_reply(p, pkt);
1826 break;
1827 #endif
1829 case DCERPC_PKT_ORPHANED:
1830 /* We should probably check the auth-verifier here.
1831 * For now just free all client data and continue
1832 * processing. */
1833 DEBUG(3, ("process_complete_pdu: DCERPC_PKT_ORPHANED."
1834 " Abandoning rpc call.\n"));
1835 reply = True;
1836 break;
1838 default:
1839 DEBUG(0, ("process_complete_pdu: "
1840 "Unknown rpc type = %u received.\n",
1841 (unsigned int)pkt->ptype));
1842 break;
1845 done:
1846 if (!reply) {
1847 DEBUG(3,("DCE/RPC fault sent!"));
1848 set_incoming_fault(p);
1849 setup_fault_pdu(p, NT_STATUS(DCERPC_NCA_S_PROTO_ERROR));
1851 /* pkt and p->in_data.pdu.data freed by caller */