2 * Unix SMB/CIFS implementation.
3 * RPC Pipe client / server routines
4 * Largely rewritten by Jeremy Allison 2005.
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/>.
21 #include "librpc/gen_ndr/cli_epmapper.h"
22 #include "../librpc/gen_ndr/ndr_schannel.h"
23 #include "../librpc/gen_ndr/ndr_lsa.h"
24 #include "../librpc/gen_ndr/ndr_dssetup.h"
25 #include "../librpc/gen_ndr/ndr_samr.h"
26 #include "../librpc/gen_ndr/ndr_netlogon.h"
27 #include "../librpc/gen_ndr/ndr_srvsvc.h"
28 #include "../librpc/gen_ndr/ndr_wkssvc.h"
29 #include "../librpc/gen_ndr/ndr_winreg.h"
30 #include "../librpc/gen_ndr/ndr_spoolss.h"
31 #include "../librpc/gen_ndr/ndr_dfs.h"
32 #include "../librpc/gen_ndr/ndr_echo.h"
33 #include "../librpc/gen_ndr/ndr_initshutdown.h"
34 #include "../librpc/gen_ndr/ndr_svcctl.h"
35 #include "../librpc/gen_ndr/ndr_eventlog.h"
36 #include "../librpc/gen_ndr/ndr_ntsvcs.h"
37 #include "../librpc/gen_ndr/ndr_epmapper.h"
38 #include "../librpc/gen_ndr/ndr_drsuapi.h"
39 #include "../libcli/auth/schannel.h"
40 #include "../libcli/auth/spnego.h"
42 #include "../libcli/auth/ntlmssp.h"
43 #include "rpc_client/cli_netlogon.h"
46 #define DBGC_CLASS DBGC_RPC_CLI
48 static const char *get_pipe_name_from_iface(
49 TALLOC_CTX *mem_ctx, const struct ndr_interface_table *interface)
52 const struct ndr_interface_string_array *ep = interface->endpoints;
55 for (i=0; i<ep->count; i++) {
56 if (strncmp(ep->names[i], "ncacn_np:[\\pipe\\", 16) == 0) {
65 * extract the pipe name without \\pipe from for example
66 * ncacn_np:[\\pipe\\epmapper]
68 p = strchr(ep->names[i]+15, ']');
72 return talloc_strndup(mem_ctx, ep->names[i]+15, p - ep->names[i] - 15);
75 static const struct ndr_interface_table **interfaces;
77 bool smb_register_ndr_interface(const struct ndr_interface_table *interface)
79 int num_interfaces = talloc_array_length(interfaces);
80 const struct ndr_interface_table **tmp;
83 for (i=0; i<num_interfaces; i++) {
84 if (ndr_syntax_id_equal(&interfaces[i]->syntax_id,
85 &interface->syntax_id)) {
90 tmp = talloc_realloc(NULL, interfaces,
91 const struct ndr_interface_table *,
94 DEBUG(1, ("smb_register_ndr_interface: talloc failed\n"));
98 interfaces[num_interfaces] = interface;
102 static bool initialize_interfaces(void)
104 if (!smb_register_ndr_interface(&ndr_table_lsarpc)) {
107 if (!smb_register_ndr_interface(&ndr_table_dssetup)) {
110 if (!smb_register_ndr_interface(&ndr_table_samr)) {
113 if (!smb_register_ndr_interface(&ndr_table_netlogon)) {
116 if (!smb_register_ndr_interface(&ndr_table_srvsvc)) {
119 if (!smb_register_ndr_interface(&ndr_table_wkssvc)) {
122 if (!smb_register_ndr_interface(&ndr_table_winreg)) {
125 if (!smb_register_ndr_interface(&ndr_table_spoolss)) {
128 if (!smb_register_ndr_interface(&ndr_table_netdfs)) {
131 if (!smb_register_ndr_interface(&ndr_table_rpcecho)) {
134 if (!smb_register_ndr_interface(&ndr_table_initshutdown)) {
137 if (!smb_register_ndr_interface(&ndr_table_svcctl)) {
140 if (!smb_register_ndr_interface(&ndr_table_eventlog)) {
143 if (!smb_register_ndr_interface(&ndr_table_ntsvcs)) {
146 if (!smb_register_ndr_interface(&ndr_table_epmapper)) {
149 if (!smb_register_ndr_interface(&ndr_table_drsuapi)) {
155 const struct ndr_interface_table *get_iface_from_syntax(
156 const struct ndr_syntax_id *syntax)
161 if (interfaces == NULL) {
162 if (!initialize_interfaces()) {
166 num_interfaces = talloc_array_length(interfaces);
168 for (i=0; i<num_interfaces; i++) {
169 if (ndr_syntax_id_equal(&interfaces[i]->syntax_id, syntax)) {
170 return interfaces[i];
177 /****************************************************************************
178 Return the pipe name from the interface.
179 ****************************************************************************/
181 const char *get_pipe_name_from_syntax(TALLOC_CTX *mem_ctx,
182 const struct ndr_syntax_id *syntax)
184 const struct ndr_interface_table *interface;
188 interface = get_iface_from_syntax(syntax);
189 if (interface != NULL) {
190 result = get_pipe_name_from_iface(mem_ctx, interface);
191 if (result != NULL) {
197 * Here we should ask \\epmapper, but for now our code is only
198 * interested in the known pipes mentioned in pipe_names[]
201 guid_str = GUID_string(talloc_tos(), &syntax->uuid);
202 if (guid_str == NULL) {
205 result = talloc_asprintf(mem_ctx, "Interface %s.%d", guid_str,
206 (int)syntax->if_version);
207 TALLOC_FREE(guid_str);
209 if (result == NULL) {
215 /********************************************************************
216 Map internal value to wire value.
217 ********************************************************************/
219 static int map_pipe_auth_type_to_rpc_auth_type(enum pipe_auth_type auth_type)
223 case PIPE_AUTH_TYPE_NONE:
224 return DCERPC_AUTH_TYPE_NONE;
226 case PIPE_AUTH_TYPE_NTLMSSP:
227 return DCERPC_AUTH_TYPE_NTLMSSP;
229 case PIPE_AUTH_TYPE_SPNEGO_NTLMSSP:
230 case PIPE_AUTH_TYPE_SPNEGO_KRB5:
231 return DCERPC_AUTH_TYPE_SPNEGO;
233 case PIPE_AUTH_TYPE_SCHANNEL:
234 return DCERPC_AUTH_TYPE_SCHANNEL;
236 case PIPE_AUTH_TYPE_KRB5:
237 return DCERPC_AUTH_TYPE_KRB5;
240 DEBUG(0,("map_pipe_auth_type_to_rpc_type: unknown pipe "
242 (unsigned int)auth_type ));
248 /********************************************************************
249 Pipe description for a DEBUG
250 ********************************************************************/
251 static const char *rpccli_pipe_txt(TALLOC_CTX *mem_ctx,
252 struct rpc_pipe_client *cli)
254 char *result = talloc_asprintf(mem_ctx, "host %s", cli->desthost);
255 if (result == NULL) {
261 /********************************************************************
263 ********************************************************************/
265 static uint32 get_rpc_call_id(void)
267 static uint32 call_id = 0;
272 * Realloc pdu to have a least "size" bytes
275 static bool rpc_grow_buffer(prs_struct *pdu, size_t size)
279 if (prs_data_size(pdu) >= size) {
283 extra_size = size - prs_data_size(pdu);
285 if (!prs_force_grow(pdu, extra_size)) {
286 DEBUG(0, ("rpc_grow_buffer: Failed to grow parse struct by "
287 "%d bytes.\n", (int)extra_size));
291 DEBUG(5, ("rpc_grow_buffer: grew buffer by %d bytes to %u\n",
292 (int)extra_size, prs_data_size(pdu)));
297 /*******************************************************************
298 Use SMBreadX to get rest of one fragment's worth of rpc data.
299 Reads the whole size or give an error message
300 ********************************************************************/
302 struct rpc_read_state {
303 struct event_context *ev;
304 struct rpc_cli_transport *transport;
310 static void rpc_read_done(struct tevent_req *subreq);
312 static struct tevent_req *rpc_read_send(TALLOC_CTX *mem_ctx,
313 struct event_context *ev,
314 struct rpc_cli_transport *transport,
315 uint8_t *data, size_t size)
317 struct tevent_req *req, *subreq;
318 struct rpc_read_state *state;
320 req = tevent_req_create(mem_ctx, &state, struct rpc_read_state);
325 state->transport = transport;
330 DEBUG(5, ("rpc_read_send: data_to_read: %u\n", (unsigned int)size));
332 subreq = transport->read_send(state, ev, (uint8_t *)data, size,
334 if (subreq == NULL) {
337 tevent_req_set_callback(subreq, rpc_read_done, req);
345 static void rpc_read_done(struct tevent_req *subreq)
347 struct tevent_req *req = tevent_req_callback_data(
348 subreq, struct tevent_req);
349 struct rpc_read_state *state = tevent_req_data(
350 req, struct rpc_read_state);
354 status = state->transport->read_recv(subreq, &received);
356 if (!NT_STATUS_IS_OK(status)) {
357 tevent_req_nterror(req, status);
361 state->num_read += received;
362 if (state->num_read == state->size) {
363 tevent_req_done(req);
367 subreq = state->transport->read_send(state, state->ev,
368 state->data + state->num_read,
369 state->size - state->num_read,
370 state->transport->priv);
371 if (tevent_req_nomem(subreq, req)) {
374 tevent_req_set_callback(subreq, rpc_read_done, req);
377 static NTSTATUS rpc_read_recv(struct tevent_req *req)
379 return tevent_req_simple_recv_ntstatus(req);
382 struct rpc_write_state {
383 struct event_context *ev;
384 struct rpc_cli_transport *transport;
390 static void rpc_write_done(struct tevent_req *subreq);
392 static struct tevent_req *rpc_write_send(TALLOC_CTX *mem_ctx,
393 struct event_context *ev,
394 struct rpc_cli_transport *transport,
395 const uint8_t *data, size_t size)
397 struct tevent_req *req, *subreq;
398 struct rpc_write_state *state;
400 req = tevent_req_create(mem_ctx, &state, struct rpc_write_state);
405 state->transport = transport;
408 state->num_written = 0;
410 DEBUG(5, ("rpc_write_send: data_to_write: %u\n", (unsigned int)size));
412 subreq = transport->write_send(state, ev, data, size, transport->priv);
413 if (subreq == NULL) {
416 tevent_req_set_callback(subreq, rpc_write_done, req);
423 static void rpc_write_done(struct tevent_req *subreq)
425 struct tevent_req *req = tevent_req_callback_data(
426 subreq, struct tevent_req);
427 struct rpc_write_state *state = tevent_req_data(
428 req, struct rpc_write_state);
432 status = state->transport->write_recv(subreq, &written);
434 if (!NT_STATUS_IS_OK(status)) {
435 tevent_req_nterror(req, status);
439 state->num_written += written;
441 if (state->num_written == state->size) {
442 tevent_req_done(req);
446 subreq = state->transport->write_send(state, state->ev,
447 state->data + state->num_written,
448 state->size - state->num_written,
449 state->transport->priv);
450 if (tevent_req_nomem(subreq, req)) {
453 tevent_req_set_callback(subreq, rpc_write_done, req);
456 static NTSTATUS rpc_write_recv(struct tevent_req *req)
458 return tevent_req_simple_recv_ntstatus(req);
462 static NTSTATUS parse_rpc_header(struct rpc_pipe_client *cli,
463 struct rpc_hdr_info *prhdr,
467 * This next call sets the endian bit correctly in current_pdu. We
468 * will propagate this to rbuf later.
471 if(!smb_io_rpc_hdr("rpc_hdr ", prhdr, pdu, 0)) {
472 DEBUG(0, ("get_current_pdu: Failed to unmarshall RPC_HDR.\n"));
473 return NT_STATUS_BUFFER_TOO_SMALL;
476 if (prhdr->frag_len > cli->max_recv_frag) {
477 DEBUG(0, ("cli_pipe_get_current_pdu: Server sent fraglen %d,"
478 " we only allow %d\n", (int)prhdr->frag_len,
479 (int)cli->max_recv_frag));
480 return NT_STATUS_BUFFER_TOO_SMALL;
486 /****************************************************************************
487 Try and get a PDU's worth of data from current_pdu. If not, then read more
489 ****************************************************************************/
491 struct get_complete_frag_state {
492 struct event_context *ev;
493 struct rpc_pipe_client *cli;
494 struct rpc_hdr_info *prhdr;
498 static void get_complete_frag_got_header(struct tevent_req *subreq);
499 static void get_complete_frag_got_rest(struct tevent_req *subreq);
501 static struct tevent_req *get_complete_frag_send(TALLOC_CTX *mem_ctx,
502 struct event_context *ev,
503 struct rpc_pipe_client *cli,
504 struct rpc_hdr_info *prhdr,
507 struct tevent_req *req, *subreq;
508 struct get_complete_frag_state *state;
512 req = tevent_req_create(mem_ctx, &state,
513 struct get_complete_frag_state);
519 state->prhdr = prhdr;
522 pdu_len = prs_data_size(pdu);
523 if (pdu_len < RPC_HEADER_LEN) {
524 if (!rpc_grow_buffer(pdu, RPC_HEADER_LEN)) {
525 status = NT_STATUS_NO_MEMORY;
528 subreq = rpc_read_send(
530 state->cli->transport,
531 (uint8_t *)(prs_data_p(state->pdu) + pdu_len),
532 RPC_HEADER_LEN - pdu_len);
533 if (subreq == NULL) {
534 status = NT_STATUS_NO_MEMORY;
537 tevent_req_set_callback(subreq, get_complete_frag_got_header,
542 status = parse_rpc_header(cli, prhdr, pdu);
543 if (!NT_STATUS_IS_OK(status)) {
548 * Ensure we have frag_len bytes of data.
550 if (pdu_len < prhdr->frag_len) {
551 if (!rpc_grow_buffer(pdu, prhdr->frag_len)) {
552 status = NT_STATUS_NO_MEMORY;
555 subreq = rpc_read_send(state, state->ev,
556 state->cli->transport,
557 (uint8_t *)(prs_data_p(pdu) + pdu_len),
558 prhdr->frag_len - pdu_len);
559 if (subreq == NULL) {
560 status = NT_STATUS_NO_MEMORY;
563 tevent_req_set_callback(subreq, get_complete_frag_got_rest,
568 status = NT_STATUS_OK;
570 if (NT_STATUS_IS_OK(status)) {
571 tevent_req_done(req);
573 tevent_req_nterror(req, status);
575 return tevent_req_post(req, ev);
578 static void get_complete_frag_got_header(struct tevent_req *subreq)
580 struct tevent_req *req = tevent_req_callback_data(
581 subreq, struct tevent_req);
582 struct get_complete_frag_state *state = tevent_req_data(
583 req, struct get_complete_frag_state);
586 status = rpc_read_recv(subreq);
588 if (!NT_STATUS_IS_OK(status)) {
589 tevent_req_nterror(req, status);
593 status = parse_rpc_header(state->cli, state->prhdr, state->pdu);
594 if (!NT_STATUS_IS_OK(status)) {
595 tevent_req_nterror(req, status);
599 if (!rpc_grow_buffer(state->pdu, state->prhdr->frag_len)) {
600 tevent_req_nterror(req, NT_STATUS_NO_MEMORY);
605 * We're here in this piece of code because we've read exactly
606 * RPC_HEADER_LEN bytes into state->pdu.
609 subreq = rpc_read_send(
610 state, state->ev, state->cli->transport,
611 (uint8_t *)(prs_data_p(state->pdu) + RPC_HEADER_LEN),
612 state->prhdr->frag_len - RPC_HEADER_LEN);
613 if (tevent_req_nomem(subreq, req)) {
616 tevent_req_set_callback(subreq, get_complete_frag_got_rest, req);
619 static void get_complete_frag_got_rest(struct tevent_req *subreq)
621 struct tevent_req *req = tevent_req_callback_data(
622 subreq, struct tevent_req);
625 status = rpc_read_recv(subreq);
627 if (!NT_STATUS_IS_OK(status)) {
628 tevent_req_nterror(req, status);
631 tevent_req_done(req);
634 static NTSTATUS get_complete_frag_recv(struct tevent_req *req)
636 return tevent_req_simple_recv_ntstatus(req);
639 /****************************************************************************
640 NTLMSSP specific sign/seal.
641 Virtually identical to rpc_server/srv_pipe.c:api_pipe_ntlmssp_auth_process.
642 In fact I should probably abstract these into identical pieces of code... JRA.
643 ****************************************************************************/
645 static NTSTATUS cli_pipe_verify_ntlmssp(struct rpc_pipe_client *cli, RPC_HDR *prhdr,
646 prs_struct *current_pdu,
647 uint8 *p_ss_padding_len)
649 RPC_HDR_AUTH auth_info;
650 uint32 save_offset = prs_offset(current_pdu);
651 uint32 auth_len = prhdr->auth_len;
652 struct ntlmssp_state *ntlmssp_state = cli->auth->a_u.ntlmssp_state;
653 unsigned char *data = NULL;
655 unsigned char *full_packet_data = NULL;
656 size_t full_packet_data_len;
660 if (cli->auth->auth_level == DCERPC_AUTH_LEVEL_NONE
661 || cli->auth->auth_level == DCERPC_AUTH_LEVEL_CONNECT) {
665 if (!ntlmssp_state) {
666 return NT_STATUS_INVALID_PARAMETER;
669 /* Ensure there's enough data for an authenticated response. */
670 if (auth_len > RPC_MAX_PDU_FRAG_LEN ||
671 prhdr->frag_len < RPC_HEADER_LEN + RPC_HDR_RESP_LEN +
672 RPC_HDR_AUTH_LEN + auth_len) {
673 DEBUG(0,("cli_pipe_verify_ntlmssp: auth_len %u is too large.\n",
674 (unsigned int)auth_len ));
675 return NT_STATUS_BUFFER_TOO_SMALL;
679 * We need the full packet data + length (minus auth stuff) as well as the packet data + length
680 * after the RPC header.
681 * We need to pass in the full packet (minus auth len) to the NTLMSSP sign and check seal
682 * functions as NTLMv2 checks the rpc headers also.
685 data = (unsigned char *)(prs_data_p(current_pdu) + RPC_HEADER_LEN + RPC_HDR_RESP_LEN);
686 data_len = (size_t)(prhdr->frag_len - RPC_HEADER_LEN - RPC_HDR_RESP_LEN - RPC_HDR_AUTH_LEN - auth_len);
688 full_packet_data = (unsigned char *)prs_data_p(current_pdu);
689 full_packet_data_len = prhdr->frag_len - auth_len;
691 /* Pull the auth header and the following data into a blob. */
692 /* NB. The offset of the auth_header is relative to the *end*
693 * of the packet, not the start. */
694 if(!prs_set_offset(current_pdu, prhdr->frag_len - RPC_HDR_AUTH_LEN - auth_len)) {
695 DEBUG(0,("cli_pipe_verify_ntlmssp: cannot move offset to %u.\n",
696 (unsigned int)RPC_HEADER_LEN + (unsigned int)RPC_HDR_RESP_LEN + (unsigned int)data_len ));
697 return NT_STATUS_BUFFER_TOO_SMALL;
700 if(!smb_io_rpc_hdr_auth("hdr_auth", &auth_info, current_pdu, 0)) {
701 DEBUG(0,("cli_pipe_verify_ntlmssp: failed to unmarshall RPC_HDR_AUTH.\n"));
702 return NT_STATUS_BUFFER_TOO_SMALL;
705 /* Ensure auth_pad_len fits into the packet. */
706 if (RPC_HEADER_LEN + RPC_HDR_REQ_LEN + auth_info.auth_pad_len +
707 RPC_HDR_AUTH_LEN + auth_len > prhdr->frag_len) {
708 DEBUG(0,("cli_pipe_verify_ntlmssp: auth_info.auth_pad_len "
709 "too large (%u), auth_len (%u), frag_len = (%u).\n",
710 (unsigned int)auth_info.auth_pad_len,
711 (unsigned int)auth_len,
712 (unsigned int)prhdr->frag_len ));
713 return NT_STATUS_BUFFER_TOO_SMALL;
717 auth_blob.data = (unsigned char *)prs_data_p(current_pdu) + prs_offset(current_pdu);
718 auth_blob.length = auth_len;
720 switch (cli->auth->auth_level) {
721 case DCERPC_AUTH_LEVEL_PRIVACY:
722 /* Data is encrypted. */
723 status = ntlmssp_unseal_packet(ntlmssp_state,
726 full_packet_data_len,
728 if (!NT_STATUS_IS_OK(status)) {
729 DEBUG(0,("cli_pipe_verify_ntlmssp: failed to unseal "
730 "packet from %s. Error was %s.\n",
731 rpccli_pipe_txt(talloc_tos(), cli),
732 nt_errstr(status) ));
736 case DCERPC_AUTH_LEVEL_INTEGRITY:
737 /* Data is signed. */
738 status = ntlmssp_check_packet(ntlmssp_state,
741 full_packet_data_len,
743 if (!NT_STATUS_IS_OK(status)) {
744 DEBUG(0,("cli_pipe_verify_ntlmssp: check signing failed on "
745 "packet from %s. Error was %s.\n",
746 rpccli_pipe_txt(talloc_tos(), cli),
747 nt_errstr(status) ));
752 DEBUG(0, ("cli_pipe_verify_ntlmssp: unknown internal "
753 "auth level %d\n", cli->auth->auth_level));
754 return NT_STATUS_INVALID_INFO_CLASS;
758 * Return the current pointer to the data offset.
761 if(!prs_set_offset(current_pdu, save_offset)) {
762 DEBUG(0,("api_pipe_auth_process: failed to set offset back to %u\n",
763 (unsigned int)save_offset ));
764 return NT_STATUS_BUFFER_TOO_SMALL;
768 * Remember the padding length. We must remove it from the real data
769 * stream once the sign/seal is done.
772 *p_ss_padding_len = auth_info.auth_pad_len;
777 /****************************************************************************
778 schannel specific sign/seal.
779 ****************************************************************************/
781 static NTSTATUS cli_pipe_verify_schannel(struct rpc_pipe_client *cli, RPC_HDR *prhdr,
782 prs_struct *current_pdu,
783 uint8 *p_ss_padding_len)
785 RPC_HDR_AUTH auth_info;
786 uint32 auth_len = prhdr->auth_len;
787 uint32 save_offset = prs_offset(current_pdu);
788 struct schannel_state *schannel_auth =
789 cli->auth->a_u.schannel_auth;
795 if (cli->auth->auth_level == DCERPC_AUTH_LEVEL_NONE
796 || cli->auth->auth_level == DCERPC_AUTH_LEVEL_CONNECT) {
800 if (auth_len < RPC_AUTH_SCHANNEL_SIGN_OR_SEAL_CHK_LEN) {
801 DEBUG(0,("cli_pipe_verify_schannel: auth_len %u.\n", (unsigned int)auth_len ));
802 return NT_STATUS_INVALID_PARAMETER;
805 if (!schannel_auth) {
806 return NT_STATUS_INVALID_PARAMETER;
809 /* Ensure there's enough data for an authenticated response. */
810 if ((auth_len > RPC_MAX_PDU_FRAG_LEN) ||
811 (RPC_HEADER_LEN + RPC_HDR_RESP_LEN + RPC_HDR_AUTH_LEN + auth_len > prhdr->frag_len)) {
812 DEBUG(0,("cli_pipe_verify_schannel: auth_len %u is too large.\n",
813 (unsigned int)auth_len ));
814 return NT_STATUS_INVALID_PARAMETER;
817 data_len = prhdr->frag_len - RPC_HEADER_LEN - RPC_HDR_RESP_LEN - RPC_HDR_AUTH_LEN - auth_len;
819 /* Pull the auth header and the following data into a blob. */
820 /* NB. The offset of the auth_header is relative to the *end*
821 * of the packet, not the start. */
822 if(!prs_set_offset(current_pdu,
823 prhdr->frag_len - RPC_HDR_AUTH_LEN - auth_len)) {
824 DEBUG(0,("cli_pipe_verify_schannel: cannot move "
826 (unsigned int)(prhdr->frag_len -
827 RPC_HDR_AUTH_LEN - auth_len) ));
828 return NT_STATUS_BUFFER_TOO_SMALL;
831 if(!smb_io_rpc_hdr_auth("hdr_auth", &auth_info, current_pdu, 0)) {
832 DEBUG(0,("cli_pipe_verify_schannel: failed to unmarshall RPC_HDR_AUTH.\n"));
833 return NT_STATUS_BUFFER_TOO_SMALL;
836 /* Ensure auth_pad_len fits into the packet. */
837 if (RPC_HEADER_LEN + RPC_HDR_REQ_LEN + auth_info.auth_pad_len +
838 RPC_HDR_AUTH_LEN + auth_len > prhdr->frag_len) {
839 DEBUG(0,("cli_pipe_verify_schannel: auth_info.auth_pad_len "
840 "too large (%u), auth_len (%u), frag_len = (%u).\n",
841 (unsigned int)auth_info.auth_pad_len,
842 (unsigned int)auth_len,
843 (unsigned int)prhdr->frag_len ));
844 return NT_STATUS_BUFFER_TOO_SMALL;
847 if (auth_info.auth_type != DCERPC_AUTH_TYPE_SCHANNEL) {
848 DEBUG(0,("cli_pipe_verify_schannel: Invalid auth info %d on schannel\n",
849 auth_info.auth_type));
850 return NT_STATUS_BUFFER_TOO_SMALL;
853 blob = data_blob_const(prs_data_p(current_pdu) + prs_offset(current_pdu), auth_len);
855 if (DEBUGLEVEL >= 10) {
856 dump_NL_AUTH_SIGNATURE(talloc_tos(), &blob);
859 data = (uint8_t *)prs_data_p(current_pdu)+RPC_HEADER_LEN+RPC_HDR_RESP_LEN;
861 switch (cli->auth->auth_level) {
862 case DCERPC_AUTH_LEVEL_PRIVACY:
863 status = netsec_incoming_packet(schannel_auth,
870 case DCERPC_AUTH_LEVEL_INTEGRITY:
871 status = netsec_incoming_packet(schannel_auth,
879 status = NT_STATUS_INTERNAL_ERROR;
883 if (!NT_STATUS_IS_OK(status)) {
884 DEBUG(3,("cli_pipe_verify_schannel: failed to decode PDU "
885 "Connection to %s (%s).\n",
886 rpccli_pipe_txt(talloc_tos(), cli),
888 return NT_STATUS_INVALID_PARAMETER;
892 * Return the current pointer to the data offset.
895 if(!prs_set_offset(current_pdu, save_offset)) {
896 DEBUG(0,("api_pipe_auth_process: failed to set offset back to %u\n",
897 (unsigned int)save_offset ));
898 return NT_STATUS_BUFFER_TOO_SMALL;
902 * Remember the padding length. We must remove it from the real data
903 * stream once the sign/seal is done.
906 *p_ss_padding_len = auth_info.auth_pad_len;
911 /****************************************************************************
912 Do the authentication checks on an incoming pdu. Check sign and unseal etc.
913 ****************************************************************************/
915 static NTSTATUS cli_pipe_validate_rpc_response(struct rpc_pipe_client *cli, RPC_HDR *prhdr,
916 prs_struct *current_pdu,
917 uint8 *p_ss_padding_len)
919 NTSTATUS ret = NT_STATUS_OK;
921 /* Paranioa checks for auth_len. */
922 if (prhdr->auth_len) {
923 if (prhdr->auth_len > prhdr->frag_len) {
924 return NT_STATUS_INVALID_PARAMETER;
927 if (prhdr->auth_len + (unsigned int)RPC_HDR_AUTH_LEN < prhdr->auth_len ||
928 prhdr->auth_len + (unsigned int)RPC_HDR_AUTH_LEN < (unsigned int)RPC_HDR_AUTH_LEN) {
929 /* Integer wrap attempt. */
930 return NT_STATUS_INVALID_PARAMETER;
935 * Now we have a complete RPC request PDU fragment, try and verify any auth data.
938 switch(cli->auth->auth_type) {
939 case PIPE_AUTH_TYPE_NONE:
940 if (prhdr->auth_len) {
941 DEBUG(3, ("cli_pipe_validate_rpc_response: "
942 "Connection to %s - got non-zero "
944 rpccli_pipe_txt(talloc_tos(), cli),
945 (unsigned int)prhdr->auth_len ));
946 return NT_STATUS_INVALID_PARAMETER;
950 case PIPE_AUTH_TYPE_NTLMSSP:
951 case PIPE_AUTH_TYPE_SPNEGO_NTLMSSP:
952 ret = cli_pipe_verify_ntlmssp(cli, prhdr, current_pdu, p_ss_padding_len);
953 if (!NT_STATUS_IS_OK(ret)) {
958 case PIPE_AUTH_TYPE_SCHANNEL:
959 ret = cli_pipe_verify_schannel(cli, prhdr, current_pdu, p_ss_padding_len);
960 if (!NT_STATUS_IS_OK(ret)) {
965 case PIPE_AUTH_TYPE_KRB5:
966 case PIPE_AUTH_TYPE_SPNEGO_KRB5:
968 DEBUG(3, ("cli_pipe_validate_rpc_response: Connection "
969 "to %s - unknown internal auth type %u.\n",
970 rpccli_pipe_txt(talloc_tos(), cli),
971 cli->auth->auth_type ));
972 return NT_STATUS_INVALID_INFO_CLASS;
978 /****************************************************************************
979 Do basic authentication checks on an incoming pdu.
980 ****************************************************************************/
982 static NTSTATUS cli_pipe_validate_current_pdu(struct rpc_pipe_client *cli, RPC_HDR *prhdr,
983 prs_struct *current_pdu,
984 uint8 expected_pkt_type,
987 prs_struct *return_data)
990 NTSTATUS ret = NT_STATUS_OK;
991 uint32 current_pdu_len = prs_data_size(current_pdu);
993 if (current_pdu_len != prhdr->frag_len) {
994 DEBUG(5,("cli_pipe_validate_current_pdu: incorrect pdu length %u, expected %u\n",
995 (unsigned int)current_pdu_len, (unsigned int)prhdr->frag_len ));
996 return NT_STATUS_INVALID_PARAMETER;
1000 * Point the return values at the real data including the RPC
1001 * header. Just in case the caller wants it.
1003 *ppdata = prs_data_p(current_pdu);
1004 *pdata_len = current_pdu_len;
1006 /* Ensure we have the correct type. */
1007 switch (prhdr->pkt_type) {
1008 case DCERPC_PKT_ALTER_RESP:
1009 case DCERPC_PKT_BIND_ACK:
1011 /* Alter context and bind ack share the same packet definitions. */
1015 case DCERPC_PKT_RESPONSE:
1017 RPC_HDR_RESP rhdr_resp;
1018 uint8 ss_padding_len = 0;
1020 if(!smb_io_rpc_hdr_resp("rpc_hdr_resp", &rhdr_resp, current_pdu, 0)) {
1021 DEBUG(5,("cli_pipe_validate_current_pdu: failed to unmarshal RPC_HDR_RESP.\n"));
1022 return NT_STATUS_BUFFER_TOO_SMALL;
1025 /* Here's where we deal with incoming sign/seal. */
1026 ret = cli_pipe_validate_rpc_response(cli, prhdr,
1027 current_pdu, &ss_padding_len);
1028 if (!NT_STATUS_IS_OK(ret)) {
1032 /* Point the return values at the NDR data. Remember to remove any ss padding. */
1033 *ppdata = prs_data_p(current_pdu) + RPC_HEADER_LEN + RPC_HDR_RESP_LEN;
1035 if (current_pdu_len < RPC_HEADER_LEN + RPC_HDR_RESP_LEN + ss_padding_len) {
1036 return NT_STATUS_BUFFER_TOO_SMALL;
1039 *pdata_len = current_pdu_len - RPC_HEADER_LEN - RPC_HDR_RESP_LEN - ss_padding_len;
1041 /* Remember to remove the auth footer. */
1042 if (prhdr->auth_len) {
1043 /* We've already done integer wrap tests on auth_len in
1044 cli_pipe_validate_rpc_response(). */
1045 if (*pdata_len < RPC_HDR_AUTH_LEN + prhdr->auth_len) {
1046 return NT_STATUS_BUFFER_TOO_SMALL;
1048 *pdata_len -= (RPC_HDR_AUTH_LEN + prhdr->auth_len);
1051 DEBUG(10,("cli_pipe_validate_current_pdu: got pdu len %u, data_len %u, ss_len %u\n",
1052 current_pdu_len, *pdata_len, ss_padding_len ));
1055 * If this is the first reply, and the allocation hint is reasonably, try and
1056 * set up the return_data parse_struct to the correct size.
1059 if ((prs_data_size(return_data) == 0) && rhdr_resp.alloc_hint && (rhdr_resp.alloc_hint < 15*1024*1024)) {
1060 if (!prs_set_buffer_size(return_data, rhdr_resp.alloc_hint)) {
1061 DEBUG(0,("cli_pipe_validate_current_pdu: reply alloc hint %u "
1062 "too large to allocate\n",
1063 (unsigned int)rhdr_resp.alloc_hint ));
1064 return NT_STATUS_NO_MEMORY;
1071 case DCERPC_PKT_BIND_NAK:
1072 DEBUG(1, ("cli_pipe_validate_current_pdu: Bind NACK "
1073 "received from %s!\n",
1074 rpccli_pipe_txt(talloc_tos(), cli)));
1075 /* Use this for now... */
1076 return NT_STATUS_NETWORK_ACCESS_DENIED;
1078 case DCERPC_PKT_FAULT:
1080 RPC_HDR_RESP rhdr_resp;
1081 RPC_HDR_FAULT fault_resp;
1083 if(!smb_io_rpc_hdr_resp("rpc_hdr_resp", &rhdr_resp, current_pdu, 0)) {
1084 DEBUG(5,("cli_pipe_validate_current_pdu: failed to unmarshal RPC_HDR_RESP.\n"));
1085 return NT_STATUS_BUFFER_TOO_SMALL;
1088 if(!smb_io_rpc_hdr_fault("fault", &fault_resp, current_pdu, 0)) {
1089 DEBUG(5,("cli_pipe_validate_current_pdu: failed to unmarshal RPC_HDR_FAULT.\n"));
1090 return NT_STATUS_BUFFER_TOO_SMALL;
1093 DEBUG(1, ("cli_pipe_validate_current_pdu: RPC fault "
1094 "code %s received from %s!\n",
1095 dcerpc_errstr(talloc_tos(), NT_STATUS_V(fault_resp.status)),
1096 rpccli_pipe_txt(talloc_tos(), cli)));
1097 if (NT_STATUS_IS_OK(fault_resp.status)) {
1098 return NT_STATUS_UNSUCCESSFUL;
1100 return fault_resp.status;
1105 DEBUG(0, ("cli_pipe_validate_current_pdu: unknown packet type %u received "
1107 (unsigned int)prhdr->pkt_type,
1108 rpccli_pipe_txt(talloc_tos(), cli)));
1109 return NT_STATUS_INVALID_INFO_CLASS;
1112 if (prhdr->pkt_type != expected_pkt_type) {
1113 DEBUG(3, ("cli_pipe_validate_current_pdu: Connection to %s "
1114 "got an unexpected RPC packet type - %u, not %u\n",
1115 rpccli_pipe_txt(talloc_tos(), cli),
1117 expected_pkt_type));
1118 return NT_STATUS_INVALID_INFO_CLASS;
1121 /* Do this just before return - we don't want to modify any rpc header
1122 data before now as we may have needed to do cryptographic actions on
1125 if ((prhdr->pkt_type == DCERPC_PKT_BIND_ACK) && !(prhdr->flags & DCERPC_PFC_FLAG_LAST)) {
1126 DEBUG(5,("cli_pipe_validate_current_pdu: bug in server (AS/U?), "
1127 "setting fragment first/last ON.\n"));
1128 prhdr->flags |= DCERPC_PFC_FLAG_FIRST|DCERPC_PFC_FLAG_LAST;
1131 return NT_STATUS_OK;
1134 /****************************************************************************
1135 Ensure we eat the just processed pdu from the current_pdu prs_struct.
1136 Normally the frag_len and buffer size will match, but on the first trans
1137 reply there is a theoretical chance that buffer size > frag_len, so we must
1139 ****************************************************************************/
1141 static NTSTATUS cli_pipe_reset_current_pdu(struct rpc_pipe_client *cli, RPC_HDR *prhdr, prs_struct *current_pdu)
1143 uint32 current_pdu_len = prs_data_size(current_pdu);
1145 if (current_pdu_len < prhdr->frag_len) {
1146 return NT_STATUS_BUFFER_TOO_SMALL;
1150 if (current_pdu_len == (uint32)prhdr->frag_len) {
1151 prs_mem_free(current_pdu);
1152 prs_init_empty(current_pdu, prs_get_mem_context(current_pdu), UNMARSHALL);
1153 /* Make current_pdu dynamic with no memory. */
1154 prs_give_memory(current_pdu, 0, 0, True);
1155 return NT_STATUS_OK;
1159 * Oh no ! More data in buffer than we processed in current pdu.
1160 * Cheat. Move the data down and shrink the buffer.
1163 memcpy(prs_data_p(current_pdu), prs_data_p(current_pdu) + prhdr->frag_len,
1164 current_pdu_len - prhdr->frag_len);
1166 /* Remember to set the read offset back to zero. */
1167 prs_set_offset(current_pdu, 0);
1169 /* Shrink the buffer. */
1170 if (!prs_set_buffer_size(current_pdu, current_pdu_len - prhdr->frag_len)) {
1171 return NT_STATUS_BUFFER_TOO_SMALL;
1174 return NT_STATUS_OK;
1177 /****************************************************************************
1178 Call a remote api on an arbitrary pipe. takes param, data and setup buffers.
1179 ****************************************************************************/
1181 struct cli_api_pipe_state {
1182 struct event_context *ev;
1183 struct rpc_cli_transport *transport;
1188 static void cli_api_pipe_trans_done(struct tevent_req *subreq);
1189 static void cli_api_pipe_write_done(struct tevent_req *subreq);
1190 static void cli_api_pipe_read_done(struct tevent_req *subreq);
1192 static struct tevent_req *cli_api_pipe_send(TALLOC_CTX *mem_ctx,
1193 struct event_context *ev,
1194 struct rpc_cli_transport *transport,
1195 uint8_t *data, size_t data_len,
1196 uint32_t max_rdata_len)
1198 struct tevent_req *req, *subreq;
1199 struct cli_api_pipe_state *state;
1202 req = tevent_req_create(mem_ctx, &state, struct cli_api_pipe_state);
1207 state->transport = transport;
1209 if (max_rdata_len < RPC_HEADER_LEN) {
1211 * For a RPC reply we always need at least RPC_HEADER_LEN
1212 * bytes. We check this here because we will receive
1213 * RPC_HEADER_LEN bytes in cli_trans_sock_send_done.
1215 status = NT_STATUS_INVALID_PARAMETER;
1219 if (transport->trans_send != NULL) {
1220 subreq = transport->trans_send(state, ev, data, data_len,
1221 max_rdata_len, transport->priv);
1222 if (subreq == NULL) {
1225 tevent_req_set_callback(subreq, cli_api_pipe_trans_done, req);
1230 * If the transport does not provide a "trans" routine, i.e. for
1231 * example the ncacn_ip_tcp transport, do the write/read step here.
1234 subreq = rpc_write_send(state, ev, transport, data, data_len);
1235 if (subreq == NULL) {
1238 tevent_req_set_callback(subreq, cli_api_pipe_write_done, req);
1241 status = NT_STATUS_INVALID_PARAMETER;
1244 tevent_req_nterror(req, status);
1245 return tevent_req_post(req, ev);
1251 static void cli_api_pipe_trans_done(struct tevent_req *subreq)
1253 struct tevent_req *req = tevent_req_callback_data(
1254 subreq, struct tevent_req);
1255 struct cli_api_pipe_state *state = tevent_req_data(
1256 req, struct cli_api_pipe_state);
1259 status = state->transport->trans_recv(subreq, state, &state->rdata,
1261 TALLOC_FREE(subreq);
1262 if (!NT_STATUS_IS_OK(status)) {
1263 tevent_req_nterror(req, status);
1266 tevent_req_done(req);
1269 static void cli_api_pipe_write_done(struct tevent_req *subreq)
1271 struct tevent_req *req = tevent_req_callback_data(
1272 subreq, struct tevent_req);
1273 struct cli_api_pipe_state *state = tevent_req_data(
1274 req, struct cli_api_pipe_state);
1277 status = rpc_write_recv(subreq);
1278 TALLOC_FREE(subreq);
1279 if (!NT_STATUS_IS_OK(status)) {
1280 tevent_req_nterror(req, status);
1284 state->rdata = TALLOC_ARRAY(state, uint8_t, RPC_HEADER_LEN);
1285 if (tevent_req_nomem(state->rdata, req)) {
1290 * We don't need to use rpc_read_send here, the upper layer will cope
1291 * with a short read, transport->trans_send could also return less
1292 * than state->max_rdata_len.
1294 subreq = state->transport->read_send(state, state->ev, state->rdata,
1296 state->transport->priv);
1297 if (tevent_req_nomem(subreq, req)) {
1300 tevent_req_set_callback(subreq, cli_api_pipe_read_done, req);
1303 static void cli_api_pipe_read_done(struct tevent_req *subreq)
1305 struct tevent_req *req = tevent_req_callback_data(
1306 subreq, struct tevent_req);
1307 struct cli_api_pipe_state *state = tevent_req_data(
1308 req, struct cli_api_pipe_state);
1312 status = state->transport->read_recv(subreq, &received);
1313 TALLOC_FREE(subreq);
1314 if (!NT_STATUS_IS_OK(status)) {
1315 tevent_req_nterror(req, status);
1318 state->rdata_len = received;
1319 tevent_req_done(req);
1322 static NTSTATUS cli_api_pipe_recv(struct tevent_req *req, TALLOC_CTX *mem_ctx,
1323 uint8_t **prdata, uint32_t *prdata_len)
1325 struct cli_api_pipe_state *state = tevent_req_data(
1326 req, struct cli_api_pipe_state);
1329 if (tevent_req_is_nterror(req, &status)) {
1333 *prdata = talloc_move(mem_ctx, &state->rdata);
1334 *prdata_len = state->rdata_len;
1335 return NT_STATUS_OK;
1338 /****************************************************************************
1339 Send data on an rpc pipe via trans. The prs_struct data must be the last
1340 pdu fragment of an NDR data stream.
1342 Receive response data from an rpc pipe, which may be large...
1344 Read the first fragment: unfortunately have to use SMBtrans for the first
1345 bit, then SMBreadX for subsequent bits.
1347 If first fragment received also wasn't the last fragment, continue
1348 getting fragments until we _do_ receive the last fragment.
1350 Request/Response PDU's look like the following...
1352 |<------------------PDU len----------------------------------------------->|
1353 |<-HDR_LEN-->|<--REQ LEN------>|.............|<-AUTH_HDRLEN->|<-AUTH_LEN-->|
1355 +------------+-----------------+-------------+---------------+-------------+
1356 | RPC HEADER | REQ/RESP HEADER | DATA ...... | AUTH_HDR | AUTH DATA |
1357 +------------+-----------------+-------------+---------------+-------------+
1359 Where the presence of the AUTH_HDR and AUTH DATA are dependent on the
1360 signing & sealing being negotiated.
1362 ****************************************************************************/
1364 struct rpc_api_pipe_state {
1365 struct event_context *ev;
1366 struct rpc_pipe_client *cli;
1367 uint8_t expected_pkt_type;
1369 prs_struct incoming_frag;
1370 struct rpc_hdr_info rhdr;
1372 prs_struct incoming_pdu; /* Incoming reply */
1373 uint32_t incoming_pdu_offset;
1376 static int rpc_api_pipe_state_destructor(struct rpc_api_pipe_state *state)
1378 prs_mem_free(&state->incoming_frag);
1379 prs_mem_free(&state->incoming_pdu);
1383 static void rpc_api_pipe_trans_done(struct tevent_req *subreq);
1384 static void rpc_api_pipe_got_pdu(struct tevent_req *subreq);
1386 static struct tevent_req *rpc_api_pipe_send(TALLOC_CTX *mem_ctx,
1387 struct event_context *ev,
1388 struct rpc_pipe_client *cli,
1389 prs_struct *data, /* Outgoing PDU */
1390 uint8_t expected_pkt_type)
1392 struct tevent_req *req, *subreq;
1393 struct rpc_api_pipe_state *state;
1394 uint16_t max_recv_frag;
1397 req = tevent_req_create(mem_ctx, &state, struct rpc_api_pipe_state);
1403 state->expected_pkt_type = expected_pkt_type;
1404 state->incoming_pdu_offset = 0;
1406 prs_init_empty(&state->incoming_frag, state, UNMARSHALL);
1408 prs_init_empty(&state->incoming_pdu, state, UNMARSHALL);
1409 /* Make incoming_pdu dynamic with no memory. */
1410 prs_give_memory(&state->incoming_pdu, NULL, 0, true);
1412 talloc_set_destructor(state, rpc_api_pipe_state_destructor);
1415 * Ensure we're not sending too much.
1417 if (prs_offset(data) > cli->max_xmit_frag) {
1418 status = NT_STATUS_INVALID_PARAMETER;
1422 DEBUG(5,("rpc_api_pipe: %s\n", rpccli_pipe_txt(talloc_tos(), cli)));
1424 max_recv_frag = cli->max_recv_frag;
1427 max_recv_frag = RPC_HEADER_LEN + 10 + (sys_random() % 32);
1430 subreq = cli_api_pipe_send(state, ev, cli->transport,
1431 (uint8_t *)prs_data_p(data),
1432 prs_offset(data), max_recv_frag);
1433 if (subreq == NULL) {
1436 tevent_req_set_callback(subreq, rpc_api_pipe_trans_done, req);
1440 tevent_req_nterror(req, status);
1441 return tevent_req_post(req, ev);
1447 static void rpc_api_pipe_trans_done(struct tevent_req *subreq)
1449 struct tevent_req *req = tevent_req_callback_data(
1450 subreq, struct tevent_req);
1451 struct rpc_api_pipe_state *state = tevent_req_data(
1452 req, struct rpc_api_pipe_state);
1454 uint8_t *rdata = NULL;
1455 uint32_t rdata_len = 0;
1458 status = cli_api_pipe_recv(subreq, state, &rdata, &rdata_len);
1459 TALLOC_FREE(subreq);
1460 if (!NT_STATUS_IS_OK(status)) {
1461 DEBUG(5, ("cli_api_pipe failed: %s\n", nt_errstr(status)));
1462 tevent_req_nterror(req, status);
1466 if (rdata == NULL) {
1467 DEBUG(3,("rpc_api_pipe: %s failed to return data.\n",
1468 rpccli_pipe_txt(talloc_tos(), state->cli)));
1469 tevent_req_done(req);
1474 * Give the memory received from cli_trans as dynamic to the current
1475 * pdu. Duplicating it sucks, but prs_struct doesn't know about talloc
1478 rdata_copy = (char *)memdup(rdata, rdata_len);
1480 if (tevent_req_nomem(rdata_copy, req)) {
1483 prs_give_memory(&state->incoming_frag, rdata_copy, rdata_len, true);
1485 /* Ensure we have enough data for a pdu. */
1486 subreq = get_complete_frag_send(state, state->ev, state->cli,
1487 &state->rhdr, &state->incoming_frag);
1488 if (tevent_req_nomem(subreq, req)) {
1491 tevent_req_set_callback(subreq, rpc_api_pipe_got_pdu, req);
1494 static void rpc_api_pipe_got_pdu(struct tevent_req *subreq)
1496 struct tevent_req *req = tevent_req_callback_data(
1497 subreq, struct tevent_req);
1498 struct rpc_api_pipe_state *state = tevent_req_data(
1499 req, struct rpc_api_pipe_state);
1502 uint32_t rdata_len = 0;
1504 status = get_complete_frag_recv(subreq);
1505 TALLOC_FREE(subreq);
1506 if (!NT_STATUS_IS_OK(status)) {
1507 DEBUG(5, ("get_complete_frag failed: %s\n",
1508 nt_errstr(status)));
1509 tevent_req_nterror(req, status);
1513 status = cli_pipe_validate_current_pdu(
1514 state->cli, &state->rhdr, &state->incoming_frag,
1515 state->expected_pkt_type, &rdata, &rdata_len,
1516 &state->incoming_pdu);
1518 DEBUG(10,("rpc_api_pipe: got frag len of %u at offset %u: %s\n",
1519 (unsigned)prs_data_size(&state->incoming_frag),
1520 (unsigned)state->incoming_pdu_offset,
1521 nt_errstr(status)));
1523 if (!NT_STATUS_IS_OK(status)) {
1524 tevent_req_nterror(req, status);
1528 if ((state->rhdr.flags & DCERPC_PFC_FLAG_FIRST)
1529 && (state->rhdr.pack_type[0] == 0)) {
1531 * Set the data type correctly for big-endian data on the
1534 DEBUG(10,("rpc_api_pipe: On %s PDU data format is "
1536 rpccli_pipe_txt(talloc_tos(), state->cli)));
1537 prs_set_endian_data(&state->incoming_pdu, RPC_BIG_ENDIAN);
1540 * Check endianness on subsequent packets.
1542 if (state->incoming_frag.bigendian_data
1543 != state->incoming_pdu.bigendian_data) {
1544 DEBUG(0,("rpc_api_pipe: Error : Endianness changed from %s to "
1546 state->incoming_pdu.bigendian_data?"big":"little",
1547 state->incoming_frag.bigendian_data?"big":"little"));
1548 tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER);
1552 /* Now copy the data portion out of the pdu into rbuf. */
1553 if (!prs_force_grow(&state->incoming_pdu, rdata_len)) {
1554 tevent_req_nterror(req, NT_STATUS_NO_MEMORY);
1558 memcpy(prs_data_p(&state->incoming_pdu) + state->incoming_pdu_offset,
1559 rdata, (size_t)rdata_len);
1560 state->incoming_pdu_offset += rdata_len;
1562 status = cli_pipe_reset_current_pdu(state->cli, &state->rhdr,
1563 &state->incoming_frag);
1564 if (!NT_STATUS_IS_OK(status)) {
1565 tevent_req_nterror(req, status);
1569 if (state->rhdr.flags & DCERPC_PFC_FLAG_LAST) {
1570 DEBUG(10,("rpc_api_pipe: %s returned %u bytes.\n",
1571 rpccli_pipe_txt(talloc_tos(), state->cli),
1572 (unsigned)prs_data_size(&state->incoming_pdu)));
1573 tevent_req_done(req);
1577 subreq = get_complete_frag_send(state, state->ev, state->cli,
1578 &state->rhdr, &state->incoming_frag);
1579 if (tevent_req_nomem(subreq, req)) {
1582 tevent_req_set_callback(subreq, rpc_api_pipe_got_pdu, req);
1585 static NTSTATUS rpc_api_pipe_recv(struct tevent_req *req, TALLOC_CTX *mem_ctx,
1586 prs_struct *reply_pdu)
1588 struct rpc_api_pipe_state *state = tevent_req_data(
1589 req, struct rpc_api_pipe_state);
1592 if (tevent_req_is_nterror(req, &status)) {
1596 *reply_pdu = state->incoming_pdu;
1597 reply_pdu->mem_ctx = mem_ctx;
1600 * Prevent state->incoming_pdu from being freed in
1601 * rpc_api_pipe_state_destructor()
1603 prs_init_empty(&state->incoming_pdu, state, UNMARSHALL);
1605 return NT_STATUS_OK;
1608 /*******************************************************************
1609 Creates krb5 auth bind.
1610 ********************************************************************/
1612 static NTSTATUS create_krb5_auth_bind_req( struct rpc_pipe_client *cli,
1613 enum dcerpc_AuthLevel auth_level,
1614 RPC_HDR_AUTH *pauth_out,
1615 prs_struct *auth_data)
1619 struct kerberos_auth_struct *a = cli->auth->a_u.kerberos_auth;
1620 DATA_BLOB tkt = data_blob_null;
1621 DATA_BLOB tkt_wrapped = data_blob_null;
1623 /* We may change the pad length before marshalling. */
1624 init_rpc_hdr_auth(pauth_out, DCERPC_AUTH_TYPE_KRB5, (int)auth_level, 0, 1);
1626 DEBUG(5, ("create_krb5_auth_bind_req: creating a service ticket for principal %s\n",
1627 a->service_principal ));
1629 /* Create the ticket for the service principal and return it in a gss-api wrapped blob. */
1631 ret = cli_krb5_get_ticket(a->service_principal, 0, &tkt,
1632 &a->session_key, (uint32)AP_OPTS_MUTUAL_REQUIRED, NULL, NULL, NULL);
1635 DEBUG(1,("create_krb5_auth_bind_req: cli_krb5_get_ticket for principal %s "
1637 a->service_principal,
1638 error_message(ret) ));
1640 data_blob_free(&tkt);
1641 prs_mem_free(auth_data);
1642 return NT_STATUS_INVALID_PARAMETER;
1645 /* wrap that up in a nice GSS-API wrapping */
1646 tkt_wrapped = spnego_gen_krb5_wrap(tkt, TOK_ID_KRB_AP_REQ);
1648 data_blob_free(&tkt);
1650 /* Auth len in the rpc header doesn't include auth_header. */
1651 if (!prs_copy_data_in(auth_data, (char *)tkt_wrapped.data, tkt_wrapped.length)) {
1652 data_blob_free(&tkt_wrapped);
1653 prs_mem_free(auth_data);
1654 return NT_STATUS_NO_MEMORY;
1657 DEBUG(5, ("create_krb5_auth_bind_req: Created krb5 GSS blob :\n"));
1658 dump_data(5, tkt_wrapped.data, tkt_wrapped.length);
1660 data_blob_free(&tkt_wrapped);
1661 return NT_STATUS_OK;
1663 return NT_STATUS_INVALID_PARAMETER;
1667 /*******************************************************************
1668 Creates SPNEGO NTLMSSP auth bind.
1669 ********************************************************************/
1671 static NTSTATUS create_spnego_ntlmssp_auth_rpc_bind_req( struct rpc_pipe_client *cli,
1672 enum dcerpc_AuthLevel auth_level,
1673 RPC_HDR_AUTH *pauth_out,
1674 prs_struct *auth_data)
1677 DATA_BLOB null_blob = data_blob_null;
1678 DATA_BLOB request = data_blob_null;
1679 DATA_BLOB spnego_msg = data_blob_null;
1681 /* We may change the pad length before marshalling. */
1682 init_rpc_hdr_auth(pauth_out, DCERPC_AUTH_TYPE_SPNEGO, (int)auth_level, 0, 1);
1684 DEBUG(5, ("create_spnego_ntlmssp_auth_rpc_bind_req: Processing NTLMSSP Negotiate\n"));
1685 nt_status = ntlmssp_update(cli->auth->a_u.ntlmssp_state,
1689 if (!NT_STATUS_EQUAL(nt_status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
1690 data_blob_free(&request);
1691 prs_mem_free(auth_data);
1695 /* Wrap this in SPNEGO. */
1696 spnego_msg = gen_negTokenInit(OID_NTLMSSP, request);
1698 data_blob_free(&request);
1700 /* Auth len in the rpc header doesn't include auth_header. */
1701 if (!prs_copy_data_in(auth_data, (char *)spnego_msg.data, spnego_msg.length)) {
1702 data_blob_free(&spnego_msg);
1703 prs_mem_free(auth_data);
1704 return NT_STATUS_NO_MEMORY;
1707 DEBUG(5, ("create_spnego_ntlmssp_auth_rpc_bind_req: NTLMSSP Negotiate:\n"));
1708 dump_data(5, spnego_msg.data, spnego_msg.length);
1710 data_blob_free(&spnego_msg);
1711 return NT_STATUS_OK;
1714 /*******************************************************************
1715 Creates NTLMSSP auth bind.
1716 ********************************************************************/
1718 static NTSTATUS create_ntlmssp_auth_rpc_bind_req( struct rpc_pipe_client *cli,
1719 enum dcerpc_AuthLevel auth_level,
1720 RPC_HDR_AUTH *pauth_out,
1721 prs_struct *auth_data)
1724 DATA_BLOB null_blob = data_blob_null;
1725 DATA_BLOB request = data_blob_null;
1727 /* We may change the pad length before marshalling. */
1728 init_rpc_hdr_auth(pauth_out, DCERPC_AUTH_TYPE_NTLMSSP, (int)auth_level, 0, 1);
1730 DEBUG(5, ("create_ntlmssp_auth_rpc_bind_req: Processing NTLMSSP Negotiate\n"));
1731 nt_status = ntlmssp_update(cli->auth->a_u.ntlmssp_state,
1735 if (!NT_STATUS_EQUAL(nt_status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
1736 data_blob_free(&request);
1737 prs_mem_free(auth_data);
1741 /* Auth len in the rpc header doesn't include auth_header. */
1742 if (!prs_copy_data_in(auth_data, (char *)request.data, request.length)) {
1743 data_blob_free(&request);
1744 prs_mem_free(auth_data);
1745 return NT_STATUS_NO_MEMORY;
1748 DEBUG(5, ("create_ntlmssp_auth_rpc_bind_req: NTLMSSP Negotiate:\n"));
1749 dump_data(5, request.data, request.length);
1751 data_blob_free(&request);
1752 return NT_STATUS_OK;
1755 /*******************************************************************
1756 Creates schannel auth bind.
1757 ********************************************************************/
1759 static NTSTATUS create_schannel_auth_rpc_bind_req( struct rpc_pipe_client *cli,
1760 enum dcerpc_AuthLevel auth_level,
1761 RPC_HDR_AUTH *pauth_out,
1762 prs_struct *auth_data)
1764 struct NL_AUTH_MESSAGE r;
1765 enum ndr_err_code ndr_err;
1768 /* We may change the pad length before marshalling. */
1769 init_rpc_hdr_auth(pauth_out, DCERPC_AUTH_TYPE_SCHANNEL, (int)auth_level, 0, 1);
1771 /* Use lp_workgroup() if domain not specified */
1773 if (!cli->auth->domain || !cli->auth->domain[0]) {
1774 cli->auth->domain = talloc_strdup(cli, lp_workgroup());
1775 if (cli->auth->domain == NULL) {
1776 return NT_STATUS_NO_MEMORY;
1781 * Now marshall the data into the auth parse_struct.
1784 r.MessageType = NL_NEGOTIATE_REQUEST;
1785 r.Flags = NL_FLAG_OEM_NETBIOS_DOMAIN_NAME |
1786 NL_FLAG_OEM_NETBIOS_COMPUTER_NAME;
1787 r.oem_netbios_domain.a = cli->auth->domain;
1788 r.oem_netbios_computer.a = global_myname();
1790 ndr_err = ndr_push_struct_blob(&blob, talloc_tos(), &r,
1791 (ndr_push_flags_fn_t)ndr_push_NL_AUTH_MESSAGE);
1792 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
1793 DEBUG(0,("Failed to marshall NL_AUTH_MESSAGE.\n"));
1794 prs_mem_free(auth_data);
1795 return ndr_map_error2ntstatus(ndr_err);
1798 if (DEBUGLEVEL >= 10) {
1799 NDR_PRINT_DEBUG(NL_AUTH_MESSAGE, &r);
1802 if (!prs_copy_data_in(auth_data, (const char *)blob.data, blob.length))
1804 prs_mem_free(auth_data);
1805 return NT_STATUS_NO_MEMORY;
1808 return NT_STATUS_OK;
1811 /*******************************************************************
1812 Creates the internals of a DCE/RPC bind request or alter context PDU.
1813 ********************************************************************/
1815 static NTSTATUS create_bind_or_alt_ctx_internal(enum dcerpc_pkt_type pkt_type,
1816 prs_struct *rpc_out,
1818 const struct ndr_syntax_id *abstract,
1819 const struct ndr_syntax_id *transfer,
1820 RPC_HDR_AUTH *phdr_auth,
1821 prs_struct *pauth_info)
1825 RPC_CONTEXT rpc_ctx;
1826 uint16 auth_len = prs_offset(pauth_info);
1827 uint8 ss_padding_len = 0;
1828 uint16 frag_len = 0;
1830 /* create the RPC context. */
1831 init_rpc_context(&rpc_ctx, 0 /* context id */, abstract, transfer);
1833 /* create the bind request RPC_HDR_RB */
1834 init_rpc_hdr_rb(&hdr_rb, RPC_MAX_PDU_FRAG_LEN, RPC_MAX_PDU_FRAG_LEN, 0x0, &rpc_ctx);
1836 /* Start building the frag length. */
1837 frag_len = RPC_HEADER_LEN + RPC_HDR_RB_LEN(&hdr_rb);
1839 /* Do we need to pad ? */
1841 uint16 data_len = RPC_HEADER_LEN + RPC_HDR_RB_LEN(&hdr_rb);
1842 if (data_len % CLIENT_NDR_PADDING_SIZE) {
1843 ss_padding_len = CLIENT_NDR_PADDING_SIZE - (data_len % CLIENT_NDR_PADDING_SIZE);
1844 phdr_auth->auth_pad_len = ss_padding_len;
1846 frag_len += RPC_HDR_AUTH_LEN + auth_len + ss_padding_len;
1849 /* Create the request RPC_HDR */
1850 init_rpc_hdr(&hdr, pkt_type, DCERPC_PFC_FLAG_FIRST|DCERPC_PFC_FLAG_LAST, rpc_call_id, frag_len, auth_len);
1852 /* Marshall the RPC header */
1853 if(!smb_io_rpc_hdr("hdr" , &hdr, rpc_out, 0)) {
1854 DEBUG(0,("create_bind_or_alt_ctx_internal: failed to marshall RPC_HDR.\n"));
1855 return NT_STATUS_NO_MEMORY;
1858 /* Marshall the bind request data */
1859 if(!smb_io_rpc_hdr_rb("", &hdr_rb, rpc_out, 0)) {
1860 DEBUG(0,("create_bind_or_alt_ctx_internal: failed to marshall RPC_HDR_RB.\n"));
1861 return NT_STATUS_NO_MEMORY;
1865 * Grow the outgoing buffer to store any auth info.
1869 if (ss_padding_len) {
1870 char pad[CLIENT_NDR_PADDING_SIZE];
1871 memset(pad, '\0', CLIENT_NDR_PADDING_SIZE);
1872 if (!prs_copy_data_in(rpc_out, pad, ss_padding_len)) {
1873 DEBUG(0,("create_bind_or_alt_ctx_internal: failed to marshall padding.\n"));
1874 return NT_STATUS_NO_MEMORY;
1878 if(!smb_io_rpc_hdr_auth("hdr_auth", phdr_auth, rpc_out, 0)) {
1879 DEBUG(0,("create_bind_or_alt_ctx_internal: failed to marshall RPC_HDR_AUTH.\n"));
1880 return NT_STATUS_NO_MEMORY;
1884 if(!prs_append_prs_data( rpc_out, pauth_info)) {
1885 DEBUG(0,("create_bind_or_alt_ctx_internal: failed to grow parse struct to add auth.\n"));
1886 return NT_STATUS_NO_MEMORY;
1890 return NT_STATUS_OK;
1893 /*******************************************************************
1894 Creates a DCE/RPC bind request.
1895 ********************************************************************/
1897 static NTSTATUS create_rpc_bind_req(struct rpc_pipe_client *cli,
1898 prs_struct *rpc_out,
1900 const struct ndr_syntax_id *abstract,
1901 const struct ndr_syntax_id *transfer,
1902 enum pipe_auth_type auth_type,
1903 enum dcerpc_AuthLevel auth_level)
1905 RPC_HDR_AUTH hdr_auth;
1906 prs_struct auth_info;
1907 NTSTATUS ret = NT_STATUS_OK;
1909 ZERO_STRUCT(hdr_auth);
1910 if (!prs_init(&auth_info, RPC_HDR_AUTH_LEN, prs_get_mem_context(rpc_out), MARSHALL))
1911 return NT_STATUS_NO_MEMORY;
1913 switch (auth_type) {
1914 case PIPE_AUTH_TYPE_SCHANNEL:
1915 ret = create_schannel_auth_rpc_bind_req(cli, auth_level, &hdr_auth, &auth_info);
1916 if (!NT_STATUS_IS_OK(ret)) {
1917 prs_mem_free(&auth_info);
1922 case PIPE_AUTH_TYPE_NTLMSSP:
1923 ret = create_ntlmssp_auth_rpc_bind_req(cli, auth_level, &hdr_auth, &auth_info);
1924 if (!NT_STATUS_IS_OK(ret)) {
1925 prs_mem_free(&auth_info);
1930 case PIPE_AUTH_TYPE_SPNEGO_NTLMSSP:
1931 ret = create_spnego_ntlmssp_auth_rpc_bind_req(cli, auth_level, &hdr_auth, &auth_info);
1932 if (!NT_STATUS_IS_OK(ret)) {
1933 prs_mem_free(&auth_info);
1938 case PIPE_AUTH_TYPE_KRB5:
1939 ret = create_krb5_auth_bind_req(cli, auth_level, &hdr_auth, &auth_info);
1940 if (!NT_STATUS_IS_OK(ret)) {
1941 prs_mem_free(&auth_info);
1946 case PIPE_AUTH_TYPE_NONE:
1950 /* "Can't" happen. */
1951 return NT_STATUS_INVALID_INFO_CLASS;
1954 ret = create_bind_or_alt_ctx_internal(DCERPC_PKT_BIND,
1962 prs_mem_free(&auth_info);
1966 /*******************************************************************
1967 Create and add the NTLMSSP sign/seal auth header and data.
1968 ********************************************************************/
1970 static NTSTATUS add_ntlmssp_auth_footer(struct rpc_pipe_client *cli,
1972 uint32 ss_padding_len,
1973 prs_struct *outgoing_pdu)
1975 RPC_HDR_AUTH auth_info;
1977 DATA_BLOB auth_blob = data_blob_null;
1978 uint16 data_and_pad_len = prs_offset(outgoing_pdu) - RPC_HEADER_LEN - RPC_HDR_RESP_LEN;
1980 if (!cli->auth->a_u.ntlmssp_state) {
1981 return NT_STATUS_INVALID_PARAMETER;
1984 /* Init and marshall the auth header. */
1985 init_rpc_hdr_auth(&auth_info,
1986 map_pipe_auth_type_to_rpc_auth_type(
1987 cli->auth->auth_type),
1988 cli->auth->auth_level,
1990 1 /* context id. */);
1992 if(!smb_io_rpc_hdr_auth("hdr_auth", &auth_info, outgoing_pdu, 0)) {
1993 DEBUG(0,("add_ntlmssp_auth_footer: failed to marshall RPC_HDR_AUTH.\n"));
1994 data_blob_free(&auth_blob);
1995 return NT_STATUS_NO_MEMORY;
1998 switch (cli->auth->auth_level) {
1999 case DCERPC_AUTH_LEVEL_PRIVACY:
2000 /* Data portion is encrypted. */
2001 status = ntlmssp_seal_packet(cli->auth->a_u.ntlmssp_state,
2002 (unsigned char *)prs_data_p(outgoing_pdu) + RPC_HEADER_LEN + RPC_HDR_RESP_LEN,
2004 (unsigned char *)prs_data_p(outgoing_pdu),
2005 (size_t)prs_offset(outgoing_pdu),
2007 if (!NT_STATUS_IS_OK(status)) {
2008 data_blob_free(&auth_blob);
2013 case DCERPC_AUTH_LEVEL_INTEGRITY:
2014 /* Data is signed. */
2015 status = ntlmssp_sign_packet(cli->auth->a_u.ntlmssp_state,
2016 (unsigned char *)prs_data_p(outgoing_pdu) + RPC_HEADER_LEN + RPC_HDR_RESP_LEN,
2018 (unsigned char *)prs_data_p(outgoing_pdu),
2019 (size_t)prs_offset(outgoing_pdu),
2021 if (!NT_STATUS_IS_OK(status)) {
2022 data_blob_free(&auth_blob);
2029 smb_panic("bad auth level");
2031 return NT_STATUS_INVALID_PARAMETER;
2034 /* Finally marshall the blob. */
2036 if (!prs_copy_data_in(outgoing_pdu, (const char *)auth_blob.data, NTLMSSP_SIG_SIZE)) {
2037 DEBUG(0,("add_ntlmssp_auth_footer: failed to add %u bytes auth blob.\n",
2038 (unsigned int)NTLMSSP_SIG_SIZE));
2039 data_blob_free(&auth_blob);
2040 return NT_STATUS_NO_MEMORY;
2043 data_blob_free(&auth_blob);
2044 return NT_STATUS_OK;
2047 /*******************************************************************
2048 Create and add the schannel sign/seal auth header and data.
2049 ********************************************************************/
2051 static NTSTATUS add_schannel_auth_footer(struct rpc_pipe_client *cli,
2053 uint32 ss_padding_len,
2054 prs_struct *outgoing_pdu)
2056 RPC_HDR_AUTH auth_info;
2057 struct schannel_state *sas = cli->auth->a_u.schannel_auth;
2058 char *data_p = prs_data_p(outgoing_pdu) + RPC_HEADER_LEN + RPC_HDR_RESP_LEN;
2059 size_t data_and_pad_len = prs_offset(outgoing_pdu) - RPC_HEADER_LEN - RPC_HDR_RESP_LEN;
2064 return NT_STATUS_INVALID_PARAMETER;
2067 /* Init and marshall the auth header. */
2068 init_rpc_hdr_auth(&auth_info,
2069 map_pipe_auth_type_to_rpc_auth_type(cli->auth->auth_type),
2070 cli->auth->auth_level,
2072 1 /* context id. */);
2074 if(!smb_io_rpc_hdr_auth("hdr_auth", &auth_info, outgoing_pdu, 0)) {
2075 DEBUG(0,("add_schannel_auth_footer: failed to marshall RPC_HDR_AUTH.\n"));
2076 return NT_STATUS_NO_MEMORY;
2079 DEBUG(10,("add_schannel_auth_footer: SCHANNEL seq_num=%d\n",
2082 switch (cli->auth->auth_level) {
2083 case DCERPC_AUTH_LEVEL_PRIVACY:
2084 status = netsec_outgoing_packet(sas,
2091 case DCERPC_AUTH_LEVEL_INTEGRITY:
2092 status = netsec_outgoing_packet(sas,
2100 status = NT_STATUS_INTERNAL_ERROR;
2104 if (!NT_STATUS_IS_OK(status)) {
2105 DEBUG(1,("add_schannel_auth_footer: failed to process packet: %s\n",
2106 nt_errstr(status)));
2110 if (DEBUGLEVEL >= 10) {
2111 dump_NL_AUTH_SIGNATURE(talloc_tos(), &blob);
2114 /* Finally marshall the blob. */
2115 if (!prs_copy_data_in(outgoing_pdu, (const char *)blob.data, blob.length)) {
2116 return NT_STATUS_NO_MEMORY;
2119 return NT_STATUS_OK;
2122 /*******************************************************************
2123 Calculate how much data we're going to send in this packet, also
2124 work out any sign/seal padding length.
2125 ********************************************************************/
2127 static uint32 calculate_data_len_tosend(struct rpc_pipe_client *cli,
2131 uint32 *p_ss_padding)
2133 uint32 data_space, data_len;
2136 if ((data_left > 0) && (sys_random() % 2)) {
2137 data_left = MAX(data_left/2, 1);
2141 switch (cli->auth->auth_level) {
2142 case DCERPC_AUTH_LEVEL_NONE:
2143 case DCERPC_AUTH_LEVEL_CONNECT:
2144 data_space = cli->max_xmit_frag - RPC_HEADER_LEN - RPC_HDR_REQ_LEN;
2145 data_len = MIN(data_space, data_left);
2148 *p_frag_len = RPC_HEADER_LEN + RPC_HDR_REQ_LEN + data_len;
2151 case DCERPC_AUTH_LEVEL_INTEGRITY:
2152 case DCERPC_AUTH_LEVEL_PRIVACY:
2153 /* Treat the same for all authenticated rpc requests. */
2154 switch(cli->auth->auth_type) {
2155 case PIPE_AUTH_TYPE_SPNEGO_NTLMSSP:
2156 case PIPE_AUTH_TYPE_NTLMSSP:
2157 *p_auth_len = NTLMSSP_SIG_SIZE;
2159 case PIPE_AUTH_TYPE_SCHANNEL:
2160 *p_auth_len = RPC_AUTH_SCHANNEL_SIGN_OR_SEAL_CHK_LEN;
2163 smb_panic("bad auth type");
2167 data_space = cli->max_xmit_frag - RPC_HEADER_LEN - RPC_HDR_REQ_LEN -
2168 RPC_HDR_AUTH_LEN - *p_auth_len;
2170 data_len = MIN(data_space, data_left);
2172 if (data_len % CLIENT_NDR_PADDING_SIZE) {
2173 *p_ss_padding = CLIENT_NDR_PADDING_SIZE - (data_len % CLIENT_NDR_PADDING_SIZE);
2175 *p_frag_len = RPC_HEADER_LEN + RPC_HDR_REQ_LEN + /* Normal headers. */
2176 data_len + *p_ss_padding + /* data plus padding. */
2177 RPC_HDR_AUTH_LEN + *p_auth_len; /* Auth header and auth data. */
2181 smb_panic("bad auth level");
2187 /*******************************************************************
2189 Does an rpc request on a pipe. Incoming data is NDR encoded in in_data.
2190 Reply is NDR encoded in out_data. Splits the data stream into RPC PDU's
2191 and deals with signing/sealing details.
2192 ********************************************************************/
2194 struct rpc_api_pipe_req_state {
2195 struct event_context *ev;
2196 struct rpc_pipe_client *cli;
2199 prs_struct *req_data;
2200 uint32_t req_data_sent;
2201 prs_struct outgoing_frag;
2202 prs_struct reply_pdu;
2205 static int rpc_api_pipe_req_state_destructor(struct rpc_api_pipe_req_state *s)
2207 prs_mem_free(&s->outgoing_frag);
2208 prs_mem_free(&s->reply_pdu);
2212 static void rpc_api_pipe_req_write_done(struct tevent_req *subreq);
2213 static void rpc_api_pipe_req_done(struct tevent_req *subreq);
2214 static NTSTATUS prepare_next_frag(struct rpc_api_pipe_req_state *state,
2215 bool *is_last_frag);
2217 struct tevent_req *rpc_api_pipe_req_send(TALLOC_CTX *mem_ctx,
2218 struct event_context *ev,
2219 struct rpc_pipe_client *cli,
2221 prs_struct *req_data)
2223 struct tevent_req *req, *subreq;
2224 struct rpc_api_pipe_req_state *state;
2228 req = tevent_req_create(mem_ctx, &state,
2229 struct rpc_api_pipe_req_state);
2235 state->op_num = op_num;
2236 state->req_data = req_data;
2237 state->req_data_sent = 0;
2238 state->call_id = get_rpc_call_id();
2240 if (cli->max_xmit_frag
2241 < RPC_HEADER_LEN + RPC_HDR_REQ_LEN + RPC_MAX_SIGN_SIZE) {
2242 /* Server is screwed up ! */
2243 status = NT_STATUS_INVALID_PARAMETER;
2247 prs_init_empty(&state->reply_pdu, state, UNMARSHALL);
2249 if (!prs_init(&state->outgoing_frag, cli->max_xmit_frag,
2254 talloc_set_destructor(state, rpc_api_pipe_req_state_destructor);
2256 status = prepare_next_frag(state, &is_last_frag);
2257 if (!NT_STATUS_IS_OK(status)) {
2262 subreq = rpc_api_pipe_send(state, ev, state->cli,
2263 &state->outgoing_frag,
2264 DCERPC_PKT_RESPONSE);
2265 if (subreq == NULL) {
2268 tevent_req_set_callback(subreq, rpc_api_pipe_req_done, req);
2270 subreq = rpc_write_send(
2271 state, ev, cli->transport,
2272 (uint8_t *)prs_data_p(&state->outgoing_frag),
2273 prs_offset(&state->outgoing_frag));
2274 if (subreq == NULL) {
2277 tevent_req_set_callback(subreq, rpc_api_pipe_req_write_done,
2283 tevent_req_nterror(req, status);
2284 return tevent_req_post(req, ev);
2290 static NTSTATUS prepare_next_frag(struct rpc_api_pipe_req_state *state,
2294 RPC_HDR_REQ hdr_req;
2295 uint32_t data_sent_thistime;
2299 uint32_t ss_padding;
2301 char pad[8] = { 0, };
2304 data_left = prs_offset(state->req_data) - state->req_data_sent;
2306 data_sent_thistime = calculate_data_len_tosend(
2307 state->cli, data_left, &frag_len, &auth_len, &ss_padding);
2309 if (state->req_data_sent == 0) {
2310 flags = DCERPC_PFC_FLAG_FIRST;
2313 if (data_sent_thistime == data_left) {
2314 flags |= DCERPC_PFC_FLAG_LAST;
2317 if (!prs_set_offset(&state->outgoing_frag, 0)) {
2318 return NT_STATUS_NO_MEMORY;
2321 /* Create and marshall the header and request header. */
2322 init_rpc_hdr(&hdr, DCERPC_PKT_REQUEST, flags, state->call_id, frag_len,
2325 if (!smb_io_rpc_hdr("hdr ", &hdr, &state->outgoing_frag, 0)) {
2326 return NT_STATUS_NO_MEMORY;
2329 /* Create the rpc request RPC_HDR_REQ */
2330 init_rpc_hdr_req(&hdr_req, prs_offset(state->req_data),
2333 if (!smb_io_rpc_hdr_req("hdr_req", &hdr_req,
2334 &state->outgoing_frag, 0)) {
2335 return NT_STATUS_NO_MEMORY;
2338 /* Copy in the data, plus any ss padding. */
2339 if (!prs_append_some_prs_data(&state->outgoing_frag,
2340 state->req_data, state->req_data_sent,
2341 data_sent_thistime)) {
2342 return NT_STATUS_NO_MEMORY;
2345 /* Copy the sign/seal padding data. */
2346 if (!prs_copy_data_in(&state->outgoing_frag, pad, ss_padding)) {
2347 return NT_STATUS_NO_MEMORY;
2350 /* Generate any auth sign/seal and add the auth footer. */
2351 switch (state->cli->auth->auth_type) {
2352 case PIPE_AUTH_TYPE_NONE:
2353 status = NT_STATUS_OK;
2355 case PIPE_AUTH_TYPE_NTLMSSP:
2356 case PIPE_AUTH_TYPE_SPNEGO_NTLMSSP:
2357 status = add_ntlmssp_auth_footer(state->cli, &hdr, ss_padding,
2358 &state->outgoing_frag);
2360 case PIPE_AUTH_TYPE_SCHANNEL:
2361 status = add_schannel_auth_footer(state->cli, &hdr, ss_padding,
2362 &state->outgoing_frag);
2365 status = NT_STATUS_INVALID_PARAMETER;
2369 state->req_data_sent += data_sent_thistime;
2370 *is_last_frag = ((flags & DCERPC_PFC_FLAG_LAST) != 0);
2375 static void rpc_api_pipe_req_write_done(struct tevent_req *subreq)
2377 struct tevent_req *req = tevent_req_callback_data(
2378 subreq, struct tevent_req);
2379 struct rpc_api_pipe_req_state *state = tevent_req_data(
2380 req, struct rpc_api_pipe_req_state);
2384 status = rpc_write_recv(subreq);
2385 TALLOC_FREE(subreq);
2386 if (!NT_STATUS_IS_OK(status)) {
2387 tevent_req_nterror(req, status);
2391 status = prepare_next_frag(state, &is_last_frag);
2392 if (!NT_STATUS_IS_OK(status)) {
2393 tevent_req_nterror(req, status);
2398 subreq = rpc_api_pipe_send(state, state->ev, state->cli,
2399 &state->outgoing_frag,
2400 DCERPC_PKT_RESPONSE);
2401 if (tevent_req_nomem(subreq, req)) {
2404 tevent_req_set_callback(subreq, rpc_api_pipe_req_done, req);
2406 subreq = rpc_write_send(
2408 state->cli->transport,
2409 (uint8_t *)prs_data_p(&state->outgoing_frag),
2410 prs_offset(&state->outgoing_frag));
2411 if (tevent_req_nomem(subreq, req)) {
2414 tevent_req_set_callback(subreq, rpc_api_pipe_req_write_done,
2419 static void rpc_api_pipe_req_done(struct tevent_req *subreq)
2421 struct tevent_req *req = tevent_req_callback_data(
2422 subreq, struct tevent_req);
2423 struct rpc_api_pipe_req_state *state = tevent_req_data(
2424 req, struct rpc_api_pipe_req_state);
2427 status = rpc_api_pipe_recv(subreq, state, &state->reply_pdu);
2428 TALLOC_FREE(subreq);
2429 if (!NT_STATUS_IS_OK(status)) {
2430 tevent_req_nterror(req, status);
2433 tevent_req_done(req);
2436 NTSTATUS rpc_api_pipe_req_recv(struct tevent_req *req, TALLOC_CTX *mem_ctx,
2437 prs_struct *reply_pdu)
2439 struct rpc_api_pipe_req_state *state = tevent_req_data(
2440 req, struct rpc_api_pipe_req_state);
2443 if (tevent_req_is_nterror(req, &status)) {
2445 * We always have to initialize to reply pdu, even if there is
2446 * none. The rpccli_* caller routines expect this.
2448 prs_init_empty(reply_pdu, mem_ctx, UNMARSHALL);
2452 *reply_pdu = state->reply_pdu;
2453 reply_pdu->mem_ctx = mem_ctx;
2456 * Prevent state->req_pdu from being freed in
2457 * rpc_api_pipe_req_state_destructor()
2459 prs_init_empty(&state->reply_pdu, state, UNMARSHALL);
2461 return NT_STATUS_OK;
2465 /****************************************************************************
2466 Set the handle state.
2467 ****************************************************************************/
2469 static bool rpc_pipe_set_hnd_state(struct rpc_pipe_client *cli,
2470 const char *pipe_name, uint16 device_state)
2472 bool state_set = False;
2474 uint16 setup[2]; /* only need 2 uint16 setup parameters */
2475 char *rparam = NULL;
2477 uint32 rparam_len, rdata_len;
2479 if (pipe_name == NULL)
2482 DEBUG(5,("Set Handle state Pipe[%x]: %s - device state:%x\n",
2483 cli->fnum, pipe_name, device_state));
2485 /* create parameters: device state */
2486 SSVAL(param, 0, device_state);
2488 /* create setup parameters. */
2490 setup[1] = cli->fnum; /* pipe file handle. got this from an SMBOpenX. */
2492 /* send the data on \PIPE\ */
2493 if (cli_api_pipe(cli->cli, "\\PIPE\\",
2494 setup, 2, 0, /* setup, length, max */
2495 param, 2, 0, /* param, length, max */
2496 NULL, 0, 1024, /* data, length, max */
2497 &rparam, &rparam_len, /* return param, length */
2498 &rdata, &rdata_len)) /* return data, length */
2500 DEBUG(5, ("Set Handle state: return OK\n"));
2511 /****************************************************************************
2512 Check the rpc bind acknowledge response.
2513 ****************************************************************************/
2515 static bool check_bind_response(RPC_HDR_BA *hdr_ba,
2516 const struct ndr_syntax_id *transfer)
2518 if ( hdr_ba->addr.len == 0) {
2519 DEBUG(4,("Ignoring length check -- ASU bug (server didn't fill in the pipe name correctly)"));
2522 /* check the transfer syntax */
2523 if ((hdr_ba->transfer.if_version != transfer->if_version) ||
2524 (memcmp(&hdr_ba->transfer.uuid, &transfer->uuid, sizeof(transfer->uuid)) !=0)) {
2525 DEBUG(2,("bind_rpc_pipe: transfer syntax differs\n"));
2529 if (hdr_ba->res.num_results != 0x1 || hdr_ba->res.result != 0) {
2530 DEBUG(2,("bind_rpc_pipe: bind denied results: %d reason: %x\n",
2531 hdr_ba->res.num_results, hdr_ba->res.reason));
2534 DEBUG(5,("check_bind_response: accepted!\n"));
2538 /*******************************************************************
2539 Creates a DCE/RPC bind authentication response.
2540 This is the packet that is sent back to the server once we
2541 have received a BIND-ACK, to finish the third leg of
2542 the authentication handshake.
2543 ********************************************************************/
2545 static NTSTATUS create_rpc_bind_auth3(struct rpc_pipe_client *cli,
2547 enum pipe_auth_type auth_type,
2548 enum dcerpc_AuthLevel auth_level,
2549 DATA_BLOB *pauth_blob,
2550 prs_struct *rpc_out)
2553 RPC_HDR_AUTH hdr_auth;
2556 /* Create the request RPC_HDR */
2557 init_rpc_hdr(&hdr, DCERPC_PKT_AUTH3, DCERPC_PFC_FLAG_FIRST|DCERPC_PFC_FLAG_LAST, rpc_call_id,
2558 RPC_HEADER_LEN + 4 /* pad */ + RPC_HDR_AUTH_LEN + pauth_blob->length,
2559 pauth_blob->length );
2562 if(!smb_io_rpc_hdr("hdr", &hdr, rpc_out, 0)) {
2563 DEBUG(0,("create_rpc_bind_auth3: failed to marshall RPC_HDR.\n"));
2564 return NT_STATUS_NO_MEMORY;
2568 I'm puzzled about this - seems to violate the DCE RPC auth rules,
2569 about padding - shouldn't this pad to length CLIENT_NDR_PADDING_SIZE ? JRA.
2572 /* 4 bytes padding. */
2573 if (!prs_uint32("pad", rpc_out, 0, &pad)) {
2574 DEBUG(0,("create_rpc_bind_auth3: failed to marshall 4 byte pad.\n"));
2575 return NT_STATUS_NO_MEMORY;
2578 /* Create the request RPC_HDR_AUTHA */
2579 init_rpc_hdr_auth(&hdr_auth,
2580 map_pipe_auth_type_to_rpc_auth_type(auth_type),
2583 if(!smb_io_rpc_hdr_auth("hdr_auth", &hdr_auth, rpc_out, 0)) {
2584 DEBUG(0,("create_rpc_bind_auth3: failed to marshall RPC_HDR_AUTHA.\n"));
2585 return NT_STATUS_NO_MEMORY;
2589 * Append the auth data to the outgoing buffer.
2592 if(!prs_copy_data_in(rpc_out, (char *)pauth_blob->data, pauth_blob->length)) {
2593 DEBUG(0,("create_rpc_bind_auth3: failed to marshall auth blob.\n"));
2594 return NT_STATUS_NO_MEMORY;
2597 return NT_STATUS_OK;
2600 /*******************************************************************
2601 Creates a DCE/RPC bind alter context authentication request which
2602 may contain a spnego auth blobl
2603 ********************************************************************/
2605 static NTSTATUS create_rpc_alter_context(uint32 rpc_call_id,
2606 const struct ndr_syntax_id *abstract,
2607 const struct ndr_syntax_id *transfer,
2608 enum dcerpc_AuthLevel auth_level,
2609 const DATA_BLOB *pauth_blob, /* spnego auth blob already created. */
2610 prs_struct *rpc_out)
2612 RPC_HDR_AUTH hdr_auth;
2613 prs_struct auth_info;
2614 NTSTATUS ret = NT_STATUS_OK;
2616 ZERO_STRUCT(hdr_auth);
2617 if (!prs_init(&auth_info, RPC_HDR_AUTH_LEN, prs_get_mem_context(rpc_out), MARSHALL))
2618 return NT_STATUS_NO_MEMORY;
2620 /* We may change the pad length before marshalling. */
2621 init_rpc_hdr_auth(&hdr_auth, DCERPC_AUTH_TYPE_SPNEGO, (int)auth_level, 0, 1);
2623 if (pauth_blob->length) {
2624 if (!prs_copy_data_in(&auth_info, (const char *)pauth_blob->data, pauth_blob->length)) {
2625 prs_mem_free(&auth_info);
2626 return NT_STATUS_NO_MEMORY;
2630 ret = create_bind_or_alt_ctx_internal(DCERPC_PKT_ALTER,
2637 prs_mem_free(&auth_info);
2641 /****************************************************************************
2643 ****************************************************************************/
2645 struct rpc_pipe_bind_state {
2646 struct event_context *ev;
2647 struct rpc_pipe_client *cli;
2649 uint32_t rpc_call_id;
2652 static int rpc_pipe_bind_state_destructor(struct rpc_pipe_bind_state *state)
2654 prs_mem_free(&state->rpc_out);
2658 static void rpc_pipe_bind_step_one_done(struct tevent_req *subreq);
2659 static NTSTATUS rpc_finish_auth3_bind_send(struct tevent_req *req,
2660 struct rpc_pipe_bind_state *state,
2661 struct rpc_hdr_info *phdr,
2662 prs_struct *reply_pdu);
2663 static void rpc_bind_auth3_write_done(struct tevent_req *subreq);
2664 static NTSTATUS rpc_finish_spnego_ntlmssp_bind_send(struct tevent_req *req,
2665 struct rpc_pipe_bind_state *state,
2666 struct rpc_hdr_info *phdr,
2667 prs_struct *reply_pdu);
2668 static void rpc_bind_ntlmssp_api_done(struct tevent_req *subreq);
2670 struct tevent_req *rpc_pipe_bind_send(TALLOC_CTX *mem_ctx,
2671 struct event_context *ev,
2672 struct rpc_pipe_client *cli,
2673 struct cli_pipe_auth_data *auth)
2675 struct tevent_req *req, *subreq;
2676 struct rpc_pipe_bind_state *state;
2679 req = tevent_req_create(mem_ctx, &state, struct rpc_pipe_bind_state);
2684 DEBUG(5,("Bind RPC Pipe: %s auth_type %u, auth_level %u\n",
2685 rpccli_pipe_txt(talloc_tos(), cli),
2686 (unsigned int)auth->auth_type,
2687 (unsigned int)auth->auth_level ));
2691 state->rpc_call_id = get_rpc_call_id();
2693 prs_init_empty(&state->rpc_out, state, MARSHALL);
2694 talloc_set_destructor(state, rpc_pipe_bind_state_destructor);
2696 cli->auth = talloc_move(cli, &auth);
2698 /* Marshall the outgoing data. */
2699 status = create_rpc_bind_req(cli, &state->rpc_out,
2701 &cli->abstract_syntax,
2702 &cli->transfer_syntax,
2703 cli->auth->auth_type,
2704 cli->auth->auth_level);
2706 if (!NT_STATUS_IS_OK(status)) {
2710 subreq = rpc_api_pipe_send(state, ev, cli, &state->rpc_out,
2711 DCERPC_PKT_BIND_ACK);
2712 if (subreq == NULL) {
2715 tevent_req_set_callback(subreq, rpc_pipe_bind_step_one_done, req);
2719 tevent_req_nterror(req, status);
2720 return tevent_req_post(req, ev);
2726 static void rpc_pipe_bind_step_one_done(struct tevent_req *subreq)
2728 struct tevent_req *req = tevent_req_callback_data(
2729 subreq, struct tevent_req);
2730 struct rpc_pipe_bind_state *state = tevent_req_data(
2731 req, struct rpc_pipe_bind_state);
2732 prs_struct reply_pdu;
2733 struct rpc_hdr_info hdr;
2734 struct rpc_hdr_ba_info hdr_ba;
2737 status = rpc_api_pipe_recv(subreq, talloc_tos(), &reply_pdu);
2738 TALLOC_FREE(subreq);
2739 if (!NT_STATUS_IS_OK(status)) {
2740 DEBUG(3, ("rpc_pipe_bind: %s bind request returned %s\n",
2741 rpccli_pipe_txt(talloc_tos(), state->cli),
2742 nt_errstr(status)));
2743 tevent_req_nterror(req, status);
2747 /* Unmarshall the RPC header */
2748 if (!smb_io_rpc_hdr("hdr", &hdr, &reply_pdu, 0)) {
2749 DEBUG(0, ("rpc_pipe_bind: failed to unmarshall RPC_HDR.\n"));
2750 prs_mem_free(&reply_pdu);
2751 tevent_req_nterror(req, NT_STATUS_BUFFER_TOO_SMALL);
2755 if (!smb_io_rpc_hdr_ba("", &hdr_ba, &reply_pdu, 0)) {
2756 DEBUG(0, ("rpc_pipe_bind: Failed to unmarshall "
2758 prs_mem_free(&reply_pdu);
2759 tevent_req_nterror(req, NT_STATUS_BUFFER_TOO_SMALL);
2763 if (!check_bind_response(&hdr_ba, &state->cli->transfer_syntax)) {
2764 DEBUG(2, ("rpc_pipe_bind: check_bind_response failed.\n"));
2765 prs_mem_free(&reply_pdu);
2766 tevent_req_nterror(req, NT_STATUS_BUFFER_TOO_SMALL);
2770 state->cli->max_xmit_frag = hdr_ba.bba.max_tsize;
2771 state->cli->max_recv_frag = hdr_ba.bba.max_rsize;
2774 * For authenticated binds we may need to do 3 or 4 leg binds.
2777 switch(state->cli->auth->auth_type) {
2779 case PIPE_AUTH_TYPE_NONE:
2780 case PIPE_AUTH_TYPE_SCHANNEL:
2781 /* Bind complete. */
2782 prs_mem_free(&reply_pdu);
2783 tevent_req_done(req);
2786 case PIPE_AUTH_TYPE_NTLMSSP:
2787 /* Need to send AUTH3 packet - no reply. */
2788 status = rpc_finish_auth3_bind_send(req, state, &hdr,
2790 prs_mem_free(&reply_pdu);
2791 if (!NT_STATUS_IS_OK(status)) {
2792 tevent_req_nterror(req, status);
2796 case PIPE_AUTH_TYPE_SPNEGO_NTLMSSP:
2797 /* Need to send alter context request and reply. */
2798 status = rpc_finish_spnego_ntlmssp_bind_send(req, state, &hdr,
2800 prs_mem_free(&reply_pdu);
2801 if (!NT_STATUS_IS_OK(status)) {
2802 tevent_req_nterror(req, status);
2806 case PIPE_AUTH_TYPE_KRB5:
2810 DEBUG(0,("cli_finish_bind_auth: unknown auth type %u\n",
2811 (unsigned int)state->cli->auth->auth_type));
2812 prs_mem_free(&reply_pdu);
2813 tevent_req_nterror(req, NT_STATUS_INTERNAL_ERROR);
2817 static NTSTATUS rpc_finish_auth3_bind_send(struct tevent_req *req,
2818 struct rpc_pipe_bind_state *state,
2819 struct rpc_hdr_info *phdr,
2820 prs_struct *reply_pdu)
2822 DATA_BLOB server_response = data_blob_null;
2823 DATA_BLOB client_reply = data_blob_null;
2824 struct rpc_hdr_auth_info hdr_auth;
2825 struct tevent_req *subreq;
2828 if ((phdr->auth_len == 0)
2829 || (phdr->frag_len < phdr->auth_len + RPC_HDR_AUTH_LEN)) {
2830 return NT_STATUS_INVALID_PARAMETER;
2833 if (!prs_set_offset(
2835 phdr->frag_len - phdr->auth_len - RPC_HDR_AUTH_LEN)) {
2836 return NT_STATUS_INVALID_PARAMETER;
2839 if (!smb_io_rpc_hdr_auth("hdr_auth", &hdr_auth, reply_pdu, 0)) {
2840 return NT_STATUS_INVALID_PARAMETER;
2843 /* TODO - check auth_type/auth_level match. */
2845 server_response = data_blob_talloc(talloc_tos(), NULL, phdr->auth_len);
2846 prs_copy_data_out((char *)server_response.data, reply_pdu,
2849 status = ntlmssp_update(state->cli->auth->a_u.ntlmssp_state,
2850 server_response, &client_reply);
2852 if (!NT_STATUS_IS_OK(status)) {
2853 DEBUG(0, ("rpc_finish_auth3_bind: NTLMSSP update using server "
2854 "blob failed: %s.\n", nt_errstr(status)));
2858 prs_init_empty(&state->rpc_out, talloc_tos(), MARSHALL);
2860 status = create_rpc_bind_auth3(state->cli, state->rpc_call_id,
2861 state->cli->auth->auth_type,
2862 state->cli->auth->auth_level,
2863 &client_reply, &state->rpc_out);
2864 data_blob_free(&client_reply);
2866 if (!NT_STATUS_IS_OK(status)) {
2870 subreq = rpc_write_send(state, state->ev, state->cli->transport,
2871 (uint8_t *)prs_data_p(&state->rpc_out),
2872 prs_offset(&state->rpc_out));
2873 if (subreq == NULL) {
2874 return NT_STATUS_NO_MEMORY;
2876 tevent_req_set_callback(subreq, rpc_bind_auth3_write_done, req);
2877 return NT_STATUS_OK;
2880 static void rpc_bind_auth3_write_done(struct tevent_req *subreq)
2882 struct tevent_req *req = tevent_req_callback_data(
2883 subreq, struct tevent_req);
2886 status = rpc_write_recv(subreq);
2887 TALLOC_FREE(subreq);
2888 if (!NT_STATUS_IS_OK(status)) {
2889 tevent_req_nterror(req, status);
2892 tevent_req_done(req);
2895 static NTSTATUS rpc_finish_spnego_ntlmssp_bind_send(struct tevent_req *req,
2896 struct rpc_pipe_bind_state *state,
2897 struct rpc_hdr_info *phdr,
2898 prs_struct *reply_pdu)
2900 DATA_BLOB server_spnego_response = data_blob_null;
2901 DATA_BLOB server_ntlm_response = data_blob_null;
2902 DATA_BLOB client_reply = data_blob_null;
2903 DATA_BLOB tmp_blob = data_blob_null;
2904 RPC_HDR_AUTH hdr_auth;
2905 struct tevent_req *subreq;
2908 if ((phdr->auth_len == 0)
2909 || (phdr->frag_len < phdr->auth_len + RPC_HDR_AUTH_LEN)) {
2910 return NT_STATUS_INVALID_PARAMETER;
2913 /* Process the returned NTLMSSP blob first. */
2914 if (!prs_set_offset(
2916 phdr->frag_len - phdr->auth_len - RPC_HDR_AUTH_LEN)) {
2917 return NT_STATUS_INVALID_PARAMETER;
2920 if (!smb_io_rpc_hdr_auth("hdr_auth", &hdr_auth, reply_pdu, 0)) {
2921 return NT_STATUS_INVALID_PARAMETER;
2924 server_spnego_response = data_blob(NULL, phdr->auth_len);
2925 prs_copy_data_out((char *)server_spnego_response.data,
2926 reply_pdu, phdr->auth_len);
2929 * The server might give us back two challenges - tmp_blob is for the
2932 if (!spnego_parse_challenge(server_spnego_response,
2933 &server_ntlm_response, &tmp_blob)) {
2934 data_blob_free(&server_spnego_response);
2935 data_blob_free(&server_ntlm_response);
2936 data_blob_free(&tmp_blob);
2937 return NT_STATUS_INVALID_PARAMETER;
2940 /* We're finished with the server spnego response and the tmp_blob. */
2941 data_blob_free(&server_spnego_response);
2942 data_blob_free(&tmp_blob);
2944 status = ntlmssp_update(state->cli->auth->a_u.ntlmssp_state,
2945 server_ntlm_response, &client_reply);
2947 /* Finished with the server_ntlm response */
2948 data_blob_free(&server_ntlm_response);
2950 if (!NT_STATUS_IS_OK(status)) {
2951 DEBUG(0, ("rpc_finish_spnego_ntlmssp_bind: NTLMSSP update "
2952 "using server blob failed.\n"));
2953 data_blob_free(&client_reply);
2957 /* SPNEGO wrap the client reply. */
2958 tmp_blob = spnego_gen_auth(client_reply);
2959 data_blob_free(&client_reply);
2960 client_reply = tmp_blob;
2961 tmp_blob = data_blob_null;
2963 /* Now prepare the alter context pdu. */
2964 prs_init_empty(&state->rpc_out, state, MARSHALL);
2966 status = create_rpc_alter_context(state->rpc_call_id,
2967 &state->cli->abstract_syntax,
2968 &state->cli->transfer_syntax,
2969 state->cli->auth->auth_level,
2972 data_blob_free(&client_reply);
2974 if (!NT_STATUS_IS_OK(status)) {
2978 subreq = rpc_api_pipe_send(state, state->ev, state->cli,
2979 &state->rpc_out, DCERPC_PKT_ALTER_RESP);
2980 if (subreq == NULL) {
2981 return NT_STATUS_NO_MEMORY;
2983 tevent_req_set_callback(subreq, rpc_bind_ntlmssp_api_done, req);
2984 return NT_STATUS_OK;
2987 static void rpc_bind_ntlmssp_api_done(struct tevent_req *subreq)
2989 struct tevent_req *req = tevent_req_callback_data(
2990 subreq, struct tevent_req);
2991 struct rpc_pipe_bind_state *state = tevent_req_data(
2992 req, struct rpc_pipe_bind_state);
2993 DATA_BLOB server_spnego_response = data_blob_null;
2994 DATA_BLOB tmp_blob = data_blob_null;
2995 prs_struct reply_pdu;
2996 struct rpc_hdr_info hdr;
2997 struct rpc_hdr_auth_info hdr_auth;
3000 status = rpc_api_pipe_recv(subreq, talloc_tos(), &reply_pdu);
3001 TALLOC_FREE(subreq);
3002 if (!NT_STATUS_IS_OK(status)) {
3003 tevent_req_nterror(req, status);
3007 /* Get the auth blob from the reply. */
3008 if (!smb_io_rpc_hdr("rpc_hdr ", &hdr, &reply_pdu, 0)) {
3009 DEBUG(0, ("rpc_finish_spnego_ntlmssp_bind: Failed to "
3010 "unmarshall RPC_HDR.\n"));
3011 tevent_req_nterror(req, NT_STATUS_BUFFER_TOO_SMALL);
3015 if (!prs_set_offset(
3017 hdr.frag_len - hdr.auth_len - RPC_HDR_AUTH_LEN)) {
3018 tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER);
3022 if (!smb_io_rpc_hdr_auth("hdr_auth", &hdr_auth, &reply_pdu, 0)) {
3023 tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER);
3027 server_spnego_response = data_blob(NULL, hdr.auth_len);
3028 prs_copy_data_out((char *)server_spnego_response.data, &reply_pdu,
3031 /* Check we got a valid auth response. */
3032 if (!spnego_parse_auth_response(server_spnego_response, NT_STATUS_OK,
3033 OID_NTLMSSP, &tmp_blob)) {
3034 data_blob_free(&server_spnego_response);
3035 data_blob_free(&tmp_blob);
3036 tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER);
3040 data_blob_free(&server_spnego_response);
3041 data_blob_free(&tmp_blob);
3043 DEBUG(5,("rpc_finish_spnego_ntlmssp_bind: alter context request to "
3044 "%s.\n", rpccli_pipe_txt(talloc_tos(), state->cli)));
3045 tevent_req_done(req);
3048 NTSTATUS rpc_pipe_bind_recv(struct tevent_req *req)
3050 return tevent_req_simple_recv_ntstatus(req);
3053 NTSTATUS rpc_pipe_bind(struct rpc_pipe_client *cli,
3054 struct cli_pipe_auth_data *auth)
3056 TALLOC_CTX *frame = talloc_stackframe();
3057 struct event_context *ev;
3058 struct tevent_req *req;
3059 NTSTATUS status = NT_STATUS_OK;
3061 ev = event_context_init(frame);
3063 status = NT_STATUS_NO_MEMORY;
3067 req = rpc_pipe_bind_send(frame, ev, cli, auth);
3069 status = NT_STATUS_NO_MEMORY;
3073 if (!tevent_req_poll(req, ev)) {
3074 status = map_nt_error_from_unix(errno);
3078 status = rpc_pipe_bind_recv(req);
3084 #define RPCCLI_DEFAULT_TIMEOUT 10000 /* 10 seconds. */
3086 unsigned int rpccli_set_timeout(struct rpc_pipe_client *rpc_cli,
3087 unsigned int timeout)
3091 if (rpc_cli->transport == NULL) {
3092 return RPCCLI_DEFAULT_TIMEOUT;
3095 if (rpc_cli->transport->set_timeout == NULL) {
3096 return RPCCLI_DEFAULT_TIMEOUT;
3099 old = rpc_cli->transport->set_timeout(rpc_cli->transport->priv, timeout);
3101 return RPCCLI_DEFAULT_TIMEOUT;
3107 bool rpccli_is_connected(struct rpc_pipe_client *rpc_cli)
3109 if (rpc_cli == NULL) {
3113 if (rpc_cli->transport == NULL) {
3117 return rpc_cli->transport->is_connected(rpc_cli->transport->priv);
3120 bool rpccli_get_pwd_hash(struct rpc_pipe_client *rpc_cli, uint8_t nt_hash[16])
3122 struct cli_state *cli;
3124 if ((rpc_cli->auth->auth_type == PIPE_AUTH_TYPE_NTLMSSP)
3125 || (rpc_cli->auth->auth_type == PIPE_AUTH_TYPE_SPNEGO_NTLMSSP)) {
3126 memcpy(nt_hash, rpc_cli->auth->a_u.ntlmssp_state->nt_hash, 16);
3130 cli = rpc_pipe_np_smb_conn(rpc_cli);
3134 E_md4hash(cli->password ? cli->password : "", nt_hash);
3138 NTSTATUS rpccli_anon_bind_data(TALLOC_CTX *mem_ctx,
3139 struct cli_pipe_auth_data **presult)
3141 struct cli_pipe_auth_data *result;
3143 result = talloc(mem_ctx, struct cli_pipe_auth_data);
3144 if (result == NULL) {
3145 return NT_STATUS_NO_MEMORY;
3148 result->auth_type = PIPE_AUTH_TYPE_NONE;
3149 result->auth_level = DCERPC_AUTH_LEVEL_NONE;
3151 result->user_name = talloc_strdup(result, "");
3152 result->domain = talloc_strdup(result, "");
3153 if ((result->user_name == NULL) || (result->domain == NULL)) {
3154 TALLOC_FREE(result);
3155 return NT_STATUS_NO_MEMORY;
3159 return NT_STATUS_OK;
3162 static int cli_auth_ntlmssp_data_destructor(struct cli_pipe_auth_data *auth)
3164 ntlmssp_end(&auth->a_u.ntlmssp_state);
3168 static NTSTATUS rpccli_ntlmssp_bind_data(TALLOC_CTX *mem_ctx,
3169 enum pipe_auth_type auth_type,
3170 enum dcerpc_AuthLevel auth_level,
3172 const char *username,
3173 const char *password,
3174 struct cli_pipe_auth_data **presult)
3176 struct cli_pipe_auth_data *result;
3179 result = talloc(mem_ctx, struct cli_pipe_auth_data);
3180 if (result == NULL) {
3181 return NT_STATUS_NO_MEMORY;
3184 result->auth_type = auth_type;
3185 result->auth_level = auth_level;
3187 result->user_name = talloc_strdup(result, username);
3188 result->domain = talloc_strdup(result, domain);
3189 if ((result->user_name == NULL) || (result->domain == NULL)) {
3190 status = NT_STATUS_NO_MEMORY;
3194 status = ntlmssp_client_start(NULL,
3197 lp_client_ntlmv2_auth(),
3198 &result->a_u.ntlmssp_state);
3199 if (!NT_STATUS_IS_OK(status)) {
3203 talloc_set_destructor(result, cli_auth_ntlmssp_data_destructor);
3205 status = ntlmssp_set_username(result->a_u.ntlmssp_state, username);
3206 if (!NT_STATUS_IS_OK(status)) {
3210 status = ntlmssp_set_domain(result->a_u.ntlmssp_state, domain);
3211 if (!NT_STATUS_IS_OK(status)) {
3215 status = ntlmssp_set_password(result->a_u.ntlmssp_state, password);
3216 if (!NT_STATUS_IS_OK(status)) {
3221 * Turn off sign+seal to allow selected auth level to turn it back on.
3223 result->a_u.ntlmssp_state->neg_flags &=
3224 ~(NTLMSSP_NEGOTIATE_SIGN | NTLMSSP_NEGOTIATE_SEAL);
3226 if (auth_level == DCERPC_AUTH_LEVEL_INTEGRITY) {
3227 result->a_u.ntlmssp_state->neg_flags |= NTLMSSP_NEGOTIATE_SIGN;
3228 } else if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
3229 result->a_u.ntlmssp_state->neg_flags
3230 |= NTLMSSP_NEGOTIATE_SEAL | NTLMSSP_NEGOTIATE_SIGN;
3234 return NT_STATUS_OK;
3237 TALLOC_FREE(result);
3241 NTSTATUS rpccli_schannel_bind_data(TALLOC_CTX *mem_ctx, const char *domain,
3242 enum dcerpc_AuthLevel auth_level,
3243 struct netlogon_creds_CredentialState *creds,
3244 struct cli_pipe_auth_data **presult)
3246 struct cli_pipe_auth_data *result;
3248 result = talloc(mem_ctx, struct cli_pipe_auth_data);
3249 if (result == NULL) {
3250 return NT_STATUS_NO_MEMORY;
3253 result->auth_type = PIPE_AUTH_TYPE_SCHANNEL;
3254 result->auth_level = auth_level;
3256 result->user_name = talloc_strdup(result, "");
3257 result->domain = talloc_strdup(result, domain);
3258 if ((result->user_name == NULL) || (result->domain == NULL)) {
3262 result->a_u.schannel_auth = talloc(result, struct schannel_state);
3263 if (result->a_u.schannel_auth == NULL) {
3267 result->a_u.schannel_auth->state = SCHANNEL_STATE_START;
3268 result->a_u.schannel_auth->seq_num = 0;
3269 result->a_u.schannel_auth->initiator = true;
3270 result->a_u.schannel_auth->creds = creds;
3273 return NT_STATUS_OK;
3276 TALLOC_FREE(result);
3277 return NT_STATUS_NO_MEMORY;
3281 static int cli_auth_kerberos_data_destructor(struct kerberos_auth_struct *auth)
3283 data_blob_free(&auth->session_key);
3288 static NTSTATUS rpccli_kerberos_bind_data(TALLOC_CTX *mem_ctx,
3289 enum dcerpc_AuthLevel auth_level,
3290 const char *service_princ,
3291 const char *username,
3292 const char *password,
3293 struct cli_pipe_auth_data **presult)
3296 struct cli_pipe_auth_data *result;
3298 if ((username != NULL) && (password != NULL)) {
3299 int ret = kerberos_kinit_password(username, password, 0, NULL);
3301 return NT_STATUS_ACCESS_DENIED;
3305 result = talloc(mem_ctx, struct cli_pipe_auth_data);
3306 if (result == NULL) {
3307 return NT_STATUS_NO_MEMORY;
3310 result->auth_type = PIPE_AUTH_TYPE_KRB5;
3311 result->auth_level = auth_level;
3314 * Username / domain need fixing!
3316 result->user_name = talloc_strdup(result, "");
3317 result->domain = talloc_strdup(result, "");
3318 if ((result->user_name == NULL) || (result->domain == NULL)) {
3322 result->a_u.kerberos_auth = TALLOC_ZERO_P(
3323 result, struct kerberos_auth_struct);
3324 if (result->a_u.kerberos_auth == NULL) {
3327 talloc_set_destructor(result->a_u.kerberos_auth,
3328 cli_auth_kerberos_data_destructor);
3330 result->a_u.kerberos_auth->service_principal = talloc_strdup(
3331 result, service_princ);
3332 if (result->a_u.kerberos_auth->service_principal == NULL) {
3337 return NT_STATUS_OK;
3340 TALLOC_FREE(result);
3341 return NT_STATUS_NO_MEMORY;
3343 return NT_STATUS_NOT_SUPPORTED;
3348 * Create an rpc pipe client struct, connecting to a tcp port.
3350 static NTSTATUS rpc_pipe_open_tcp_port(TALLOC_CTX *mem_ctx, const char *host,
3352 const struct ndr_syntax_id *abstract_syntax,
3353 struct rpc_pipe_client **presult)
3355 struct rpc_pipe_client *result;
3356 struct sockaddr_storage addr;
3360 result = TALLOC_ZERO_P(mem_ctx, struct rpc_pipe_client);
3361 if (result == NULL) {
3362 return NT_STATUS_NO_MEMORY;
3365 result->abstract_syntax = *abstract_syntax;
3366 result->transfer_syntax = ndr_transfer_syntax;
3367 result->dispatch = cli_do_rpc_ndr;
3368 result->dispatch_send = cli_do_rpc_ndr_send;
3369 result->dispatch_recv = cli_do_rpc_ndr_recv;
3371 result->desthost = talloc_strdup(result, host);
3372 result->srv_name_slash = talloc_asprintf_strupper_m(
3373 result, "\\\\%s", result->desthost);
3374 if ((result->desthost == NULL) || (result->srv_name_slash == NULL)) {
3375 status = NT_STATUS_NO_MEMORY;
3379 result->max_xmit_frag = RPC_MAX_PDU_FRAG_LEN;
3380 result->max_recv_frag = RPC_MAX_PDU_FRAG_LEN;
3382 if (!resolve_name(host, &addr, 0, false)) {
3383 status = NT_STATUS_NOT_FOUND;
3387 status = open_socket_out(&addr, port, 60, &fd);
3388 if (!NT_STATUS_IS_OK(status)) {
3391 set_socket_options(fd, lp_socket_options());
3393 status = rpc_transport_sock_init(result, fd, &result->transport);
3394 if (!NT_STATUS_IS_OK(status)) {
3399 result->transport->transport = NCACN_IP_TCP;
3402 return NT_STATUS_OK;
3405 TALLOC_FREE(result);
3410 * Determine the tcp port on which a dcerpc interface is listening
3411 * for the ncacn_ip_tcp transport via the endpoint mapper of the
3414 static NTSTATUS rpc_pipe_get_tcp_port(const char *host,
3415 const struct ndr_syntax_id *abstract_syntax,
3419 struct rpc_pipe_client *epm_pipe = NULL;
3420 struct cli_pipe_auth_data *auth = NULL;
3421 struct dcerpc_binding *map_binding = NULL;
3422 struct dcerpc_binding *res_binding = NULL;
3423 struct epm_twr_t *map_tower = NULL;
3424 struct epm_twr_t *res_towers = NULL;
3425 struct policy_handle *entry_handle = NULL;
3426 uint32_t num_towers = 0;
3427 uint32_t max_towers = 1;
3428 struct epm_twr_p_t towers;
3429 TALLOC_CTX *tmp_ctx = talloc_stackframe();
3431 if (pport == NULL) {
3432 status = NT_STATUS_INVALID_PARAMETER;
3436 /* open the connection to the endpoint mapper */
3437 status = rpc_pipe_open_tcp_port(tmp_ctx, host, 135,
3438 &ndr_table_epmapper.syntax_id,
3441 if (!NT_STATUS_IS_OK(status)) {
3445 status = rpccli_anon_bind_data(tmp_ctx, &auth);
3446 if (!NT_STATUS_IS_OK(status)) {
3450 status = rpc_pipe_bind(epm_pipe, auth);
3451 if (!NT_STATUS_IS_OK(status)) {
3455 /* create tower for asking the epmapper */
3457 map_binding = TALLOC_ZERO_P(tmp_ctx, struct dcerpc_binding);
3458 if (map_binding == NULL) {
3459 status = NT_STATUS_NO_MEMORY;
3463 map_binding->transport = NCACN_IP_TCP;
3464 map_binding->object = *abstract_syntax;
3465 map_binding->host = host; /* needed? */
3466 map_binding->endpoint = "0"; /* correct? needed? */
3468 map_tower = TALLOC_ZERO_P(tmp_ctx, struct epm_twr_t);
3469 if (map_tower == NULL) {
3470 status = NT_STATUS_NO_MEMORY;
3474 status = dcerpc_binding_build_tower(tmp_ctx, map_binding,
3475 &(map_tower->tower));
3476 if (!NT_STATUS_IS_OK(status)) {
3480 /* allocate further parameters for the epm_Map call */
3482 res_towers = TALLOC_ARRAY(tmp_ctx, struct epm_twr_t, max_towers);
3483 if (res_towers == NULL) {
3484 status = NT_STATUS_NO_MEMORY;
3487 towers.twr = res_towers;
3489 entry_handle = TALLOC_ZERO_P(tmp_ctx, struct policy_handle);
3490 if (entry_handle == NULL) {
3491 status = NT_STATUS_NO_MEMORY;
3495 /* ask the endpoint mapper for the port */
3497 status = rpccli_epm_Map(epm_pipe,
3499 CONST_DISCARD(struct GUID *,
3500 &(abstract_syntax->uuid)),
3507 if (!NT_STATUS_IS_OK(status)) {
3511 if (num_towers != 1) {
3512 status = NT_STATUS_UNSUCCESSFUL;
3516 /* extract the port from the answer */
3518 status = dcerpc_binding_from_tower(tmp_ctx,
3519 &(towers.twr->tower),
3521 if (!NT_STATUS_IS_OK(status)) {
3525 /* are further checks here necessary? */
3526 if (res_binding->transport != NCACN_IP_TCP) {
3527 status = NT_STATUS_UNSUCCESSFUL;
3531 *pport = (uint16_t)atoi(res_binding->endpoint);
3534 TALLOC_FREE(tmp_ctx);
3539 * Create a rpc pipe client struct, connecting to a host via tcp.
3540 * The port is determined by asking the endpoint mapper on the given
3543 NTSTATUS rpc_pipe_open_tcp(TALLOC_CTX *mem_ctx, const char *host,
3544 const struct ndr_syntax_id *abstract_syntax,
3545 struct rpc_pipe_client **presult)
3550 status = rpc_pipe_get_tcp_port(host, abstract_syntax, &port);
3551 if (!NT_STATUS_IS_OK(status)) {
3555 return rpc_pipe_open_tcp_port(mem_ctx, host, port,
3556 abstract_syntax, presult);
3559 /********************************************************************
3560 Create a rpc pipe client struct, connecting to a unix domain socket
3561 ********************************************************************/
3562 NTSTATUS rpc_pipe_open_ncalrpc(TALLOC_CTX *mem_ctx, const char *socket_path,
3563 const struct ndr_syntax_id *abstract_syntax,
3564 struct rpc_pipe_client **presult)
3566 struct rpc_pipe_client *result;
3567 struct sockaddr_un addr;
3571 result = talloc_zero(mem_ctx, struct rpc_pipe_client);
3572 if (result == NULL) {
3573 return NT_STATUS_NO_MEMORY;
3576 result->abstract_syntax = *abstract_syntax;
3577 result->transfer_syntax = ndr_transfer_syntax;
3578 result->dispatch = cli_do_rpc_ndr;
3579 result->dispatch_send = cli_do_rpc_ndr_send;
3580 result->dispatch_recv = cli_do_rpc_ndr_recv;
3582 result->desthost = get_myname(result);
3583 result->srv_name_slash = talloc_asprintf_strupper_m(
3584 result, "\\\\%s", result->desthost);
3585 if ((result->desthost == NULL) || (result->srv_name_slash == NULL)) {
3586 status = NT_STATUS_NO_MEMORY;
3590 result->max_xmit_frag = RPC_MAX_PDU_FRAG_LEN;
3591 result->max_recv_frag = RPC_MAX_PDU_FRAG_LEN;
3593 fd = socket(AF_UNIX, SOCK_STREAM, 0);
3595 status = map_nt_error_from_unix(errno);
3600 addr.sun_family = AF_UNIX;
3601 strncpy(addr.sun_path, socket_path, sizeof(addr.sun_path));
3603 if (sys_connect(fd, (struct sockaddr *)(void *)&addr) == -1) {
3604 DEBUG(0, ("connect(%s) failed: %s\n", socket_path,
3607 return map_nt_error_from_unix(errno);
3610 status = rpc_transport_sock_init(result, fd, &result->transport);
3611 if (!NT_STATUS_IS_OK(status)) {
3616 result->transport->transport = NCALRPC;
3619 return NT_STATUS_OK;
3622 TALLOC_FREE(result);
3626 struct rpc_pipe_client_np_ref {
3627 struct cli_state *cli;
3628 struct rpc_pipe_client *pipe;
3631 static int rpc_pipe_client_np_ref_destructor(struct rpc_pipe_client_np_ref *np_ref)
3633 DLIST_REMOVE(np_ref->cli->pipe_list, np_ref->pipe);
3637 /****************************************************************************
3638 Open a named pipe over SMB to a remote server.
3640 * CAVEAT CALLER OF THIS FUNCTION:
3641 * The returned rpc_pipe_client saves a copy of the cli_state cli pointer,
3642 * so be sure that this function is called AFTER any structure (vs pointer)
3643 * assignment of the cli. In particular, libsmbclient does structure
3644 * assignments of cli, which invalidates the data in the returned
3645 * rpc_pipe_client if this function is called before the structure assignment
3648 ****************************************************************************/
3650 static NTSTATUS rpc_pipe_open_np(struct cli_state *cli,
3651 const struct ndr_syntax_id *abstract_syntax,
3652 struct rpc_pipe_client **presult)
3654 struct rpc_pipe_client *result;
3656 struct rpc_pipe_client_np_ref *np_ref;
3658 /* sanity check to protect against crashes */
3661 return NT_STATUS_INVALID_HANDLE;
3664 result = TALLOC_ZERO_P(NULL, struct rpc_pipe_client);
3665 if (result == NULL) {
3666 return NT_STATUS_NO_MEMORY;
3669 result->abstract_syntax = *abstract_syntax;
3670 result->transfer_syntax = ndr_transfer_syntax;
3671 result->dispatch = cli_do_rpc_ndr;
3672 result->dispatch_send = cli_do_rpc_ndr_send;
3673 result->dispatch_recv = cli_do_rpc_ndr_recv;
3674 result->desthost = talloc_strdup(result, cli->desthost);
3675 result->srv_name_slash = talloc_asprintf_strupper_m(
3676 result, "\\\\%s", result->desthost);
3678 result->max_xmit_frag = RPC_MAX_PDU_FRAG_LEN;
3679 result->max_recv_frag = RPC_MAX_PDU_FRAG_LEN;
3681 if ((result->desthost == NULL) || (result->srv_name_slash == NULL)) {
3682 TALLOC_FREE(result);
3683 return NT_STATUS_NO_MEMORY;
3686 status = rpc_transport_np_init(result, cli, abstract_syntax,
3687 &result->transport);
3688 if (!NT_STATUS_IS_OK(status)) {
3689 TALLOC_FREE(result);
3693 result->transport->transport = NCACN_NP;
3695 np_ref = talloc(result->transport, struct rpc_pipe_client_np_ref);
3696 if (np_ref == NULL) {
3697 TALLOC_FREE(result);
3698 return NT_STATUS_NO_MEMORY;
3701 np_ref->pipe = result;
3703 DLIST_ADD(np_ref->cli->pipe_list, np_ref->pipe);
3704 talloc_set_destructor(np_ref, rpc_pipe_client_np_ref_destructor);
3707 return NT_STATUS_OK;
3710 NTSTATUS rpc_pipe_open_local(TALLOC_CTX *mem_ctx,
3711 struct rpc_cli_smbd_conn *conn,
3712 const struct ndr_syntax_id *syntax,
3713 struct rpc_pipe_client **presult)
3715 struct rpc_pipe_client *result;
3716 struct cli_pipe_auth_data *auth;
3719 result = talloc(mem_ctx, struct rpc_pipe_client);
3720 if (result == NULL) {
3721 return NT_STATUS_NO_MEMORY;
3723 result->abstract_syntax = *syntax;
3724 result->transfer_syntax = ndr_transfer_syntax;
3725 result->dispatch = cli_do_rpc_ndr;
3726 result->dispatch_send = cli_do_rpc_ndr_send;
3727 result->dispatch_recv = cli_do_rpc_ndr_recv;
3728 result->max_xmit_frag = RPC_MAX_PDU_FRAG_LEN;
3729 result->max_recv_frag = RPC_MAX_PDU_FRAG_LEN;
3731 result->desthost = talloc_strdup(result, global_myname());
3732 result->srv_name_slash = talloc_asprintf_strupper_m(
3733 result, "\\\\%s", global_myname());
3734 if ((result->desthost == NULL) || (result->srv_name_slash == NULL)) {
3735 TALLOC_FREE(result);
3736 return NT_STATUS_NO_MEMORY;
3739 status = rpc_transport_smbd_init(result, conn, syntax,
3740 &result->transport);
3741 if (!NT_STATUS_IS_OK(status)) {
3742 DEBUG(1, ("rpc_transport_smbd_init failed: %s\n",
3743 nt_errstr(status)));
3744 TALLOC_FREE(result);
3748 status = rpccli_anon_bind_data(result, &auth);
3749 if (!NT_STATUS_IS_OK(status)) {
3750 DEBUG(1, ("rpccli_anon_bind_data failed: %s\n",
3751 nt_errstr(status)));
3752 TALLOC_FREE(result);
3756 status = rpc_pipe_bind(result, auth);
3757 if (!NT_STATUS_IS_OK(status)) {
3758 DEBUG(1, ("rpc_pipe_bind failed: %s\n", nt_errstr(status)));
3759 TALLOC_FREE(result);
3763 result->transport->transport = NCACN_INTERNAL;
3766 return NT_STATUS_OK;
3769 /****************************************************************************
3770 Open a pipe to a remote server.
3771 ****************************************************************************/
3773 static NTSTATUS cli_rpc_pipe_open(struct cli_state *cli,
3774 enum dcerpc_transport_t transport,
3775 const struct ndr_syntax_id *interface,
3776 struct rpc_pipe_client **presult)
3778 switch (transport) {
3780 return rpc_pipe_open_tcp(NULL, cli->desthost, interface,
3783 return rpc_pipe_open_np(cli, interface, presult);
3785 return NT_STATUS_NOT_IMPLEMENTED;
3789 /****************************************************************************
3790 Open a named pipe to an SMB server and bind anonymously.
3791 ****************************************************************************/
3793 NTSTATUS cli_rpc_pipe_open_noauth_transport(struct cli_state *cli,
3794 enum dcerpc_transport_t transport,
3795 const struct ndr_syntax_id *interface,
3796 struct rpc_pipe_client **presult)
3798 struct rpc_pipe_client *result;
3799 struct cli_pipe_auth_data *auth;
3802 status = cli_rpc_pipe_open(cli, transport, interface, &result);
3803 if (!NT_STATUS_IS_OK(status)) {
3807 status = rpccli_anon_bind_data(result, &auth);
3808 if (!NT_STATUS_IS_OK(status)) {
3809 DEBUG(0, ("rpccli_anon_bind_data returned %s\n",
3810 nt_errstr(status)));
3811 TALLOC_FREE(result);
3816 * This is a bit of an abstraction violation due to the fact that an
3817 * anonymous bind on an authenticated SMB inherits the user/domain
3818 * from the enclosing SMB creds
3821 TALLOC_FREE(auth->user_name);
3822 TALLOC_FREE(auth->domain);
3824 auth->user_name = talloc_strdup(auth, cli->user_name);
3825 auth->domain = talloc_strdup(auth, cli->domain);
3826 auth->user_session_key = data_blob_talloc(auth,
3827 cli->user_session_key.data,
3828 cli->user_session_key.length);
3830 if ((auth->user_name == NULL) || (auth->domain == NULL)) {
3831 TALLOC_FREE(result);
3832 return NT_STATUS_NO_MEMORY;
3835 status = rpc_pipe_bind(result, auth);
3836 if (!NT_STATUS_IS_OK(status)) {
3838 if (ndr_syntax_id_equal(interface,
3839 &ndr_table_dssetup.syntax_id)) {
3840 /* non AD domains just don't have this pipe, avoid
3841 * level 0 statement in that case - gd */
3844 DEBUG(lvl, ("cli_rpc_pipe_open_noauth: rpc_pipe_bind for pipe "
3845 "%s failed with error %s\n",
3846 get_pipe_name_from_syntax(talloc_tos(), interface),
3847 nt_errstr(status) ));
3848 TALLOC_FREE(result);
3852 DEBUG(10,("cli_rpc_pipe_open_noauth: opened pipe %s to machine "
3853 "%s and bound anonymously.\n",
3854 get_pipe_name_from_syntax(talloc_tos(), interface),
3858 return NT_STATUS_OK;
3861 /****************************************************************************
3862 ****************************************************************************/
3864 NTSTATUS cli_rpc_pipe_open_noauth(struct cli_state *cli,
3865 const struct ndr_syntax_id *interface,
3866 struct rpc_pipe_client **presult)
3868 return cli_rpc_pipe_open_noauth_transport(cli, NCACN_NP,
3869 interface, presult);
3872 /****************************************************************************
3873 Open a named pipe to an SMB server and bind using NTLMSSP or SPNEGO NTLMSSP
3874 ****************************************************************************/
3876 static NTSTATUS cli_rpc_pipe_open_ntlmssp_internal(struct cli_state *cli,
3877 const struct ndr_syntax_id *interface,
3878 enum dcerpc_transport_t transport,
3879 enum pipe_auth_type auth_type,
3880 enum dcerpc_AuthLevel auth_level,
3882 const char *username,
3883 const char *password,
3884 struct rpc_pipe_client **presult)
3886 struct rpc_pipe_client *result;
3887 struct cli_pipe_auth_data *auth;
3890 status = cli_rpc_pipe_open(cli, transport, interface, &result);
3891 if (!NT_STATUS_IS_OK(status)) {
3895 status = rpccli_ntlmssp_bind_data(
3896 result, auth_type, auth_level, domain, username,
3898 if (!NT_STATUS_IS_OK(status)) {
3899 DEBUG(0, ("rpccli_ntlmssp_bind_data returned %s\n",
3900 nt_errstr(status)));
3904 status = rpc_pipe_bind(result, auth);
3905 if (!NT_STATUS_IS_OK(status)) {
3906 DEBUG(0, ("cli_rpc_pipe_open_ntlmssp_internal: cli_rpc_pipe_bind failed with error %s\n",
3907 nt_errstr(status) ));
3911 DEBUG(10,("cli_rpc_pipe_open_ntlmssp_internal: opened pipe %s to "
3912 "machine %s and bound NTLMSSP as user %s\\%s.\n",
3913 get_pipe_name_from_syntax(talloc_tos(), interface),
3914 cli->desthost, domain, username ));
3917 return NT_STATUS_OK;
3921 TALLOC_FREE(result);
3925 /****************************************************************************
3927 Open a named pipe to an SMB server and bind using NTLMSSP (bind type 10)
3928 ****************************************************************************/
3930 NTSTATUS cli_rpc_pipe_open_ntlmssp(struct cli_state *cli,
3931 const struct ndr_syntax_id *interface,
3932 enum dcerpc_transport_t transport,
3933 enum dcerpc_AuthLevel auth_level,
3935 const char *username,
3936 const char *password,
3937 struct rpc_pipe_client **presult)
3939 return cli_rpc_pipe_open_ntlmssp_internal(cli,
3942 PIPE_AUTH_TYPE_NTLMSSP,
3950 /****************************************************************************
3952 Open a named pipe to an SMB server and bind using spnego NTLMSSP (bind type 9)
3953 ****************************************************************************/
3955 NTSTATUS cli_rpc_pipe_open_spnego_ntlmssp(struct cli_state *cli,
3956 const struct ndr_syntax_id *interface,
3957 enum dcerpc_transport_t transport,
3958 enum dcerpc_AuthLevel auth_level,
3960 const char *username,
3961 const char *password,
3962 struct rpc_pipe_client **presult)
3964 return cli_rpc_pipe_open_ntlmssp_internal(cli,
3967 PIPE_AUTH_TYPE_SPNEGO_NTLMSSP,
3975 /****************************************************************************
3976 Get a the schannel session key out of an already opened netlogon pipe.
3977 ****************************************************************************/
3978 static NTSTATUS get_schannel_session_key_common(struct rpc_pipe_client *netlogon_pipe,
3979 struct cli_state *cli,
3983 enum netr_SchannelType sec_chan_type = 0;
3984 unsigned char machine_pwd[16];
3985 const char *machine_account;
3988 /* Get the machine account credentials from secrets.tdb. */
3989 if (!get_trust_pw_hash(domain, machine_pwd, &machine_account,
3992 DEBUG(0, ("get_schannel_session_key: could not fetch "
3993 "trust account password for domain '%s'\n",
3995 return NT_STATUS_CANT_ACCESS_DOMAIN_INFO;
3998 status = rpccli_netlogon_setup_creds(netlogon_pipe,
3999 cli->desthost, /* server name */
4000 domain, /* domain */
4001 global_myname(), /* client name */
4002 machine_account, /* machine account name */
4007 if (!NT_STATUS_IS_OK(status)) {
4008 DEBUG(3, ("get_schannel_session_key_common: "
4009 "rpccli_netlogon_setup_creds failed with result %s "
4010 "to server %s, domain %s, machine account %s.\n",
4011 nt_errstr(status), cli->desthost, domain,
4016 if (((*pneg_flags) & NETLOGON_NEG_SCHANNEL) == 0) {
4017 DEBUG(3, ("get_schannel_session_key: Server %s did not offer schannel\n",
4019 return NT_STATUS_INVALID_NETWORK_RESPONSE;
4022 return NT_STATUS_OK;;
4025 /****************************************************************************
4026 Open a netlogon pipe and get the schannel session key.
4027 Now exposed to external callers.
4028 ****************************************************************************/
4031 NTSTATUS get_schannel_session_key(struct cli_state *cli,
4034 struct rpc_pipe_client **presult)
4036 struct rpc_pipe_client *netlogon_pipe = NULL;
4039 status = cli_rpc_pipe_open_noauth(cli, &ndr_table_netlogon.syntax_id,
4041 if (!NT_STATUS_IS_OK(status)) {
4045 status = get_schannel_session_key_common(netlogon_pipe, cli, domain,
4047 if (!NT_STATUS_IS_OK(status)) {
4048 TALLOC_FREE(netlogon_pipe);
4052 *presult = netlogon_pipe;
4053 return NT_STATUS_OK;
4056 /****************************************************************************
4058 Open a named pipe to an SMB server and bind using schannel (bind type 68)
4059 using session_key. sign and seal.
4061 The *pdc will be stolen onto this new pipe
4062 ****************************************************************************/
4064 NTSTATUS cli_rpc_pipe_open_schannel_with_key(struct cli_state *cli,
4065 const struct ndr_syntax_id *interface,
4066 enum dcerpc_transport_t transport,
4067 enum dcerpc_AuthLevel auth_level,
4069 struct netlogon_creds_CredentialState **pdc,
4070 struct rpc_pipe_client **presult)
4072 struct rpc_pipe_client *result;
4073 struct cli_pipe_auth_data *auth;
4076 status = cli_rpc_pipe_open(cli, transport, interface, &result);
4077 if (!NT_STATUS_IS_OK(status)) {
4081 status = rpccli_schannel_bind_data(result, domain, auth_level,
4083 if (!NT_STATUS_IS_OK(status)) {
4084 DEBUG(0, ("rpccli_schannel_bind_data returned %s\n",
4085 nt_errstr(status)));
4086 TALLOC_FREE(result);
4090 status = rpc_pipe_bind(result, auth);
4091 if (!NT_STATUS_IS_OK(status)) {
4092 DEBUG(0, ("cli_rpc_pipe_open_schannel_with_key: "
4093 "cli_rpc_pipe_bind failed with error %s\n",
4094 nt_errstr(status) ));
4095 TALLOC_FREE(result);
4100 * The credentials on a new netlogon pipe are the ones we are passed
4101 * in - reference them in
4103 result->dc = talloc_move(result, pdc);
4105 DEBUG(10,("cli_rpc_pipe_open_schannel_with_key: opened pipe %s to machine %s "
4106 "for domain %s and bound using schannel.\n",
4107 get_pipe_name_from_syntax(talloc_tos(), interface),
4108 cli->desthost, domain ));
4111 return NT_STATUS_OK;
4114 /****************************************************************************
4115 Open a named pipe to an SMB server and bind using schannel (bind type 68).
4116 Fetch the session key ourselves using a temporary netlogon pipe. This
4117 version uses an ntlmssp auth bound netlogon pipe to get the key.
4118 ****************************************************************************/
4120 static NTSTATUS get_schannel_session_key_auth_ntlmssp(struct cli_state *cli,
4122 const char *username,
4123 const char *password,
4125 struct rpc_pipe_client **presult)
4127 struct rpc_pipe_client *netlogon_pipe = NULL;
4130 status = cli_rpc_pipe_open_spnego_ntlmssp(
4131 cli, &ndr_table_netlogon.syntax_id, NCACN_NP,
4132 DCERPC_AUTH_LEVEL_PRIVACY,
4133 domain, username, password, &netlogon_pipe);
4134 if (!NT_STATUS_IS_OK(status)) {
4138 status = get_schannel_session_key_common(netlogon_pipe, cli, domain,
4140 if (!NT_STATUS_IS_OK(status)) {
4141 TALLOC_FREE(netlogon_pipe);
4145 *presult = netlogon_pipe;
4146 return NT_STATUS_OK;
4149 /****************************************************************************
4150 Open a named pipe to an SMB server and bind using schannel (bind type 68).
4151 Fetch the session key ourselves using a temporary netlogon pipe. This version
4152 uses an ntlmssp bind to get the session key.
4153 ****************************************************************************/
4155 NTSTATUS cli_rpc_pipe_open_ntlmssp_auth_schannel(struct cli_state *cli,
4156 const struct ndr_syntax_id *interface,
4157 enum dcerpc_transport_t transport,
4158 enum dcerpc_AuthLevel auth_level,
4160 const char *username,
4161 const char *password,
4162 struct rpc_pipe_client **presult)
4164 uint32_t neg_flags = NETLOGON_NEG_AUTH2_ADS_FLAGS;
4165 struct rpc_pipe_client *netlogon_pipe = NULL;
4166 struct rpc_pipe_client *result = NULL;
4169 status = get_schannel_session_key_auth_ntlmssp(
4170 cli, domain, username, password, &neg_flags, &netlogon_pipe);
4171 if (!NT_STATUS_IS_OK(status)) {
4172 DEBUG(0,("cli_rpc_pipe_open_ntlmssp_auth_schannel: failed to get schannel session "
4173 "key from server %s for domain %s.\n",
4174 cli->desthost, domain ));
4178 status = cli_rpc_pipe_open_schannel_with_key(
4179 cli, interface, transport, auth_level, domain, &netlogon_pipe->dc,
4182 /* Now we've bound using the session key we can close the netlog pipe. */
4183 TALLOC_FREE(netlogon_pipe);
4185 if (NT_STATUS_IS_OK(status)) {
4191 /****************************************************************************
4192 Open a named pipe to an SMB server and bind using schannel (bind type 68).
4193 Fetch the session key ourselves using a temporary netlogon pipe.
4194 ****************************************************************************/
4196 NTSTATUS cli_rpc_pipe_open_schannel(struct cli_state *cli,
4197 const struct ndr_syntax_id *interface,
4198 enum dcerpc_transport_t transport,
4199 enum dcerpc_AuthLevel auth_level,
4201 struct rpc_pipe_client **presult)
4203 uint32_t neg_flags = NETLOGON_NEG_AUTH2_ADS_FLAGS;
4204 struct rpc_pipe_client *netlogon_pipe = NULL;
4205 struct rpc_pipe_client *result = NULL;
4208 status = get_schannel_session_key(cli, domain, &neg_flags,
4210 if (!NT_STATUS_IS_OK(status)) {
4211 DEBUG(0,("cli_rpc_pipe_open_schannel: failed to get schannel session "
4212 "key from server %s for domain %s.\n",
4213 cli->desthost, domain ));
4217 status = cli_rpc_pipe_open_schannel_with_key(
4218 cli, interface, transport, auth_level, domain, &netlogon_pipe->dc,
4221 /* Now we've bound using the session key we can close the netlog pipe. */
4222 TALLOC_FREE(netlogon_pipe);
4224 if (NT_STATUS_IS_OK(status)) {
4231 /****************************************************************************
4232 Open a named pipe to an SMB server and bind using krb5 (bind type 16).
4233 The idea is this can be called with service_princ, username and password all
4234 NULL so long as the caller has a TGT.
4235 ****************************************************************************/
4237 NTSTATUS cli_rpc_pipe_open_krb5(struct cli_state *cli,
4238 const struct ndr_syntax_id *interface,
4239 enum dcerpc_AuthLevel auth_level,
4240 const char *service_princ,
4241 const char *username,
4242 const char *password,
4243 struct rpc_pipe_client **presult)
4246 struct rpc_pipe_client *result;
4247 struct cli_pipe_auth_data *auth;
4250 status = cli_rpc_pipe_open(cli, NCACN_NP, interface, &result);
4251 if (!NT_STATUS_IS_OK(status)) {
4255 status = rpccli_kerberos_bind_data(result, auth_level, service_princ,
4256 username, password, &auth);
4257 if (!NT_STATUS_IS_OK(status)) {
4258 DEBUG(0, ("rpccli_kerberos_bind_data returned %s\n",
4259 nt_errstr(status)));
4260 TALLOC_FREE(result);
4264 status = rpc_pipe_bind(result, auth);
4265 if (!NT_STATUS_IS_OK(status)) {
4266 DEBUG(0, ("cli_rpc_pipe_open_krb5: cli_rpc_pipe_bind failed "
4267 "with error %s\n", nt_errstr(status)));
4268 TALLOC_FREE(result);
4273 return NT_STATUS_OK;
4275 DEBUG(0,("cli_rpc_pipe_open_krb5: kerberos not found at compile time.\n"));
4276 return NT_STATUS_NOT_IMPLEMENTED;
4280 NTSTATUS cli_get_session_key(TALLOC_CTX *mem_ctx,
4281 struct rpc_pipe_client *cli,
4282 DATA_BLOB *session_key)
4284 if (!session_key || !cli) {
4285 return NT_STATUS_INVALID_PARAMETER;
4289 return NT_STATUS_INVALID_PARAMETER;
4292 switch (cli->auth->auth_type) {
4293 case PIPE_AUTH_TYPE_SCHANNEL:
4294 *session_key = data_blob_talloc(mem_ctx,
4295 cli->auth->a_u.schannel_auth->creds->session_key, 16);
4297 case PIPE_AUTH_TYPE_NTLMSSP:
4298 case PIPE_AUTH_TYPE_SPNEGO_NTLMSSP:
4299 *session_key = data_blob_talloc(mem_ctx,
4300 cli->auth->a_u.ntlmssp_state->session_key.data,
4301 cli->auth->a_u.ntlmssp_state->session_key.length);
4303 case PIPE_AUTH_TYPE_KRB5:
4304 case PIPE_AUTH_TYPE_SPNEGO_KRB5:
4305 *session_key = data_blob_talloc(mem_ctx,
4306 cli->auth->a_u.kerberos_auth->session_key.data,
4307 cli->auth->a_u.kerberos_auth->session_key.length);
4309 case PIPE_AUTH_TYPE_NONE:
4310 *session_key = data_blob_talloc(mem_ctx,
4311 cli->auth->user_session_key.data,
4312 cli->auth->user_session_key.length);
4315 return NT_STATUS_NO_USER_SESSION_KEY;
4318 return NT_STATUS_OK;