2 * Unix SMB/CIFS implementation.
3 * RPC Pipe client routines
4 * Largely rewritten by Jeremy Allison 2005.
5 * Heavily modified by Simo Sorce 2010.
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 3 of the License, or
10 * (at your option) any later version.
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, see <http://www.gnu.org/licenses/>.
22 #include "../lib/util/tevent_ntstatus.h"
23 #include "librpc/gen_ndr/ndr_epmapper_c.h"
24 #include "../librpc/gen_ndr/ndr_schannel.h"
25 #include "../librpc/gen_ndr/ndr_dssetup.h"
26 #include "../libcli/auth/schannel.h"
27 #include "../libcli/auth/spnego.h"
28 #include "../libcli/auth/ntlmssp.h"
29 #include "ntlmssp_wrap.h"
30 #include "librpc/gen_ndr/ndr_dcerpc.h"
31 #include "librpc/rpc/dcerpc.h"
32 #include "librpc/crypto/gse.h"
33 #include "librpc/crypto/spnego.h"
39 #define DBGC_CLASS DBGC_RPC_CLI
41 /********************************************************************
42 Pipe description for a DEBUG
43 ********************************************************************/
44 static const char *rpccli_pipe_txt(TALLOC_CTX *mem_ctx,
45 struct rpc_pipe_client *cli)
47 char *result = talloc_asprintf(mem_ctx, "host %s", cli->desthost);
54 /********************************************************************
56 ********************************************************************/
58 static uint32 get_rpc_call_id(void)
60 static uint32 call_id = 0;
64 /*******************************************************************
65 Use SMBreadX to get rest of one fragment's worth of rpc data.
66 Reads the whole size or give an error message
67 ********************************************************************/
69 struct rpc_read_state {
70 struct event_context *ev;
71 struct rpc_cli_transport *transport;
77 static void rpc_read_done(struct tevent_req *subreq);
79 static struct tevent_req *rpc_read_send(TALLOC_CTX *mem_ctx,
80 struct event_context *ev,
81 struct rpc_cli_transport *transport,
82 uint8_t *data, size_t size)
84 struct tevent_req *req, *subreq;
85 struct rpc_read_state *state;
87 req = tevent_req_create(mem_ctx, &state, struct rpc_read_state);
92 state->transport = transport;
97 DEBUG(5, ("rpc_read_send: data_to_read: %u\n", (unsigned int)size));
99 subreq = transport->read_send(state, ev, (uint8_t *)data, size,
101 if (subreq == NULL) {
104 tevent_req_set_callback(subreq, rpc_read_done, req);
112 static void rpc_read_done(struct tevent_req *subreq)
114 struct tevent_req *req = tevent_req_callback_data(
115 subreq, struct tevent_req);
116 struct rpc_read_state *state = tevent_req_data(
117 req, struct rpc_read_state);
121 status = state->transport->read_recv(subreq, &received);
123 if (!NT_STATUS_IS_OK(status)) {
124 tevent_req_nterror(req, status);
128 state->num_read += received;
129 if (state->num_read == state->size) {
130 tevent_req_done(req);
134 subreq = state->transport->read_send(state, state->ev,
135 state->data + state->num_read,
136 state->size - state->num_read,
137 state->transport->priv);
138 if (tevent_req_nomem(subreq, req)) {
141 tevent_req_set_callback(subreq, rpc_read_done, req);
144 static NTSTATUS rpc_read_recv(struct tevent_req *req)
146 return tevent_req_simple_recv_ntstatus(req);
149 struct rpc_write_state {
150 struct event_context *ev;
151 struct rpc_cli_transport *transport;
157 static void rpc_write_done(struct tevent_req *subreq);
159 static struct tevent_req *rpc_write_send(TALLOC_CTX *mem_ctx,
160 struct event_context *ev,
161 struct rpc_cli_transport *transport,
162 const uint8_t *data, size_t size)
164 struct tevent_req *req, *subreq;
165 struct rpc_write_state *state;
167 req = tevent_req_create(mem_ctx, &state, struct rpc_write_state);
172 state->transport = transport;
175 state->num_written = 0;
177 DEBUG(5, ("rpc_write_send: data_to_write: %u\n", (unsigned int)size));
179 subreq = transport->write_send(state, ev, data, size, transport->priv);
180 if (subreq == NULL) {
183 tevent_req_set_callback(subreq, rpc_write_done, req);
190 static void rpc_write_done(struct tevent_req *subreq)
192 struct tevent_req *req = tevent_req_callback_data(
193 subreq, struct tevent_req);
194 struct rpc_write_state *state = tevent_req_data(
195 req, struct rpc_write_state);
199 status = state->transport->write_recv(subreq, &written);
201 if (!NT_STATUS_IS_OK(status)) {
202 tevent_req_nterror(req, status);
206 state->num_written += written;
208 if (state->num_written == state->size) {
209 tevent_req_done(req);
213 subreq = state->transport->write_send(state, state->ev,
214 state->data + state->num_written,
215 state->size - state->num_written,
216 state->transport->priv);
217 if (tevent_req_nomem(subreq, req)) {
220 tevent_req_set_callback(subreq, rpc_write_done, req);
223 static NTSTATUS rpc_write_recv(struct tevent_req *req)
225 return tevent_req_simple_recv_ntstatus(req);
229 /****************************************************************************
230 Try and get a PDU's worth of data from current_pdu. If not, then read more
232 ****************************************************************************/
234 struct get_complete_frag_state {
235 struct event_context *ev;
236 struct rpc_pipe_client *cli;
241 static void get_complete_frag_got_header(struct tevent_req *subreq);
242 static void get_complete_frag_got_rest(struct tevent_req *subreq);
244 static struct tevent_req *get_complete_frag_send(TALLOC_CTX *mem_ctx,
245 struct event_context *ev,
246 struct rpc_pipe_client *cli,
249 struct tevent_req *req, *subreq;
250 struct get_complete_frag_state *state;
254 req = tevent_req_create(mem_ctx, &state,
255 struct get_complete_frag_state);
261 state->frag_len = RPC_HEADER_LEN;
264 received = pdu->length;
265 if (received < RPC_HEADER_LEN) {
266 if (!data_blob_realloc(mem_ctx, pdu, RPC_HEADER_LEN)) {
267 status = NT_STATUS_NO_MEMORY;
270 subreq = rpc_read_send(state, state->ev,
271 state->cli->transport,
272 pdu->data + received,
273 RPC_HEADER_LEN - received);
274 if (subreq == NULL) {
275 status = NT_STATUS_NO_MEMORY;
278 tevent_req_set_callback(subreq, get_complete_frag_got_header,
283 state->frag_len = dcerpc_get_frag_length(pdu);
284 if (state->frag_len < RPC_HEADER_LEN) {
285 tevent_req_nterror(req, NT_STATUS_RPC_PROTOCOL_ERROR);
286 return tevent_req_post(req, ev);
290 * Ensure we have frag_len bytes of data.
292 if (received < state->frag_len) {
293 if (!data_blob_realloc(NULL, pdu, state->frag_len)) {
294 status = NT_STATUS_NO_MEMORY;
297 subreq = rpc_read_send(state, state->ev,
298 state->cli->transport,
299 pdu->data + received,
300 state->frag_len - received);
301 if (subreq == NULL) {
302 status = NT_STATUS_NO_MEMORY;
305 tevent_req_set_callback(subreq, get_complete_frag_got_rest,
310 status = NT_STATUS_OK;
312 if (NT_STATUS_IS_OK(status)) {
313 tevent_req_done(req);
315 tevent_req_nterror(req, status);
317 return tevent_req_post(req, ev);
320 static void get_complete_frag_got_header(struct tevent_req *subreq)
322 struct tevent_req *req = tevent_req_callback_data(
323 subreq, struct tevent_req);
324 struct get_complete_frag_state *state = tevent_req_data(
325 req, struct get_complete_frag_state);
328 status = rpc_read_recv(subreq);
330 if (!NT_STATUS_IS_OK(status)) {
331 tevent_req_nterror(req, status);
335 state->frag_len = dcerpc_get_frag_length(state->pdu);
336 if (state->frag_len < RPC_HEADER_LEN) {
337 tevent_req_nterror(req, NT_STATUS_RPC_PROTOCOL_ERROR);
341 if (!data_blob_realloc(NULL, state->pdu, state->frag_len)) {
342 tevent_req_nterror(req, NT_STATUS_NO_MEMORY);
347 * We're here in this piece of code because we've read exactly
348 * RPC_HEADER_LEN bytes into state->pdu.
351 subreq = rpc_read_send(state, state->ev, state->cli->transport,
352 state->pdu->data + RPC_HEADER_LEN,
353 state->frag_len - RPC_HEADER_LEN);
354 if (tevent_req_nomem(subreq, req)) {
357 tevent_req_set_callback(subreq, get_complete_frag_got_rest, req);
360 static void get_complete_frag_got_rest(struct tevent_req *subreq)
362 struct tevent_req *req = tevent_req_callback_data(
363 subreq, struct tevent_req);
366 status = rpc_read_recv(subreq);
368 if (!NT_STATUS_IS_OK(status)) {
369 tevent_req_nterror(req, status);
372 tevent_req_done(req);
375 static NTSTATUS get_complete_frag_recv(struct tevent_req *req)
377 return tevent_req_simple_recv_ntstatus(req);
380 /****************************************************************************
381 Do basic authentication checks on an incoming pdu.
382 ****************************************************************************/
384 static NTSTATUS cli_pipe_validate_current_pdu(TALLOC_CTX *mem_ctx,
385 struct rpc_pipe_client *cli,
386 struct ncacn_packet *pkt,
388 uint8_t expected_pkt_type,
390 DATA_BLOB *reply_pdu)
392 struct dcerpc_response *r;
393 NTSTATUS ret = NT_STATUS_OK;
397 * Point the return values at the real data including the RPC
398 * header. Just in case the caller wants it.
402 /* Ensure we have the correct type. */
403 switch (pkt->ptype) {
404 case DCERPC_PKT_ALTER_RESP:
405 case DCERPC_PKT_BIND_ACK:
407 /* Client code never receives this kind of packets */
411 case DCERPC_PKT_RESPONSE:
413 r = &pkt->u.response;
415 /* Here's where we deal with incoming sign/seal. */
416 ret = dcerpc_check_auth(cli->auth, pkt,
417 &r->stub_and_verifier,
418 DCERPC_RESPONSE_LENGTH,
420 if (!NT_STATUS_IS_OK(ret)) {
424 if (pkt->frag_length < DCERPC_RESPONSE_LENGTH + pad_len) {
425 return NT_STATUS_BUFFER_TOO_SMALL;
428 /* Point the return values at the NDR data. */
429 rdata->data = r->stub_and_verifier.data;
431 if (pkt->auth_length) {
432 /* We've already done integer wrap tests in
433 * dcerpc_check_auth(). */
434 rdata->length = r->stub_and_verifier.length
436 - DCERPC_AUTH_TRAILER_LENGTH
439 rdata->length = r->stub_and_verifier.length;
442 DEBUG(10, ("Got pdu len %lu, data_len %lu, ss_len %u\n",
443 (long unsigned int)pdu->length,
444 (long unsigned int)rdata->length,
445 (unsigned int)pad_len));
448 * If this is the first reply, and the allocation hint is
449 * reasonable, try and set up the reply_pdu DATA_BLOB to the
453 if ((reply_pdu->length == 0) &&
454 r->alloc_hint && (r->alloc_hint < 15*1024*1024)) {
455 if (!data_blob_realloc(mem_ctx, reply_pdu,
457 DEBUG(0, ("reply alloc hint %d too "
458 "large to allocate\n",
459 (int)r->alloc_hint));
460 return NT_STATUS_NO_MEMORY;
466 case DCERPC_PKT_BIND_NAK:
467 DEBUG(1, (__location__ ": Bind NACK received from %s!\n",
468 rpccli_pipe_txt(talloc_tos(), cli)));
469 /* Use this for now... */
470 return NT_STATUS_NETWORK_ACCESS_DENIED;
472 case DCERPC_PKT_FAULT:
474 DEBUG(1, (__location__ ": RPC fault code %s received "
476 dcerpc_errstr(talloc_tos(),
477 pkt->u.fault.status),
478 rpccli_pipe_txt(talloc_tos(), cli)));
480 return dcerpc_fault_to_nt_status(pkt->u.fault.status);
483 DEBUG(0, (__location__ "Unknown packet type %u received "
485 (unsigned int)pkt->ptype,
486 rpccli_pipe_txt(talloc_tos(), cli)));
487 return NT_STATUS_INVALID_INFO_CLASS;
490 if (pkt->ptype != expected_pkt_type) {
491 DEBUG(3, (__location__ ": Connection to %s got an unexpected "
492 "RPC packet type - %u, not %u\n",
493 rpccli_pipe_txt(talloc_tos(), cli),
494 pkt->ptype, expected_pkt_type));
495 return NT_STATUS_INVALID_INFO_CLASS;
498 /* Do this just before return - we don't want to modify any rpc header
499 data before now as we may have needed to do cryptographic actions on
502 if ((pkt->ptype == DCERPC_PKT_BIND_ACK) &&
503 !(pkt->pfc_flags & DCERPC_PFC_FLAG_LAST)) {
504 DEBUG(5, (__location__ ": bug in server (AS/U?), setting "
505 "fragment first/last ON.\n"));
506 pkt->pfc_flags |= DCERPC_PFC_FLAG_FIRST | DCERPC_PFC_FLAG_LAST;
512 /****************************************************************************
513 Call a remote api on an arbitrary pipe. takes param, data and setup buffers.
514 ****************************************************************************/
516 struct cli_api_pipe_state {
517 struct event_context *ev;
518 struct rpc_cli_transport *transport;
523 static void cli_api_pipe_trans_done(struct tevent_req *subreq);
524 static void cli_api_pipe_write_done(struct tevent_req *subreq);
525 static void cli_api_pipe_read_done(struct tevent_req *subreq);
527 static struct tevent_req *cli_api_pipe_send(TALLOC_CTX *mem_ctx,
528 struct event_context *ev,
529 struct rpc_cli_transport *transport,
530 uint8_t *data, size_t data_len,
531 uint32_t max_rdata_len)
533 struct tevent_req *req, *subreq;
534 struct cli_api_pipe_state *state;
537 req = tevent_req_create(mem_ctx, &state, struct cli_api_pipe_state);
542 state->transport = transport;
544 if (max_rdata_len < RPC_HEADER_LEN) {
546 * For a RPC reply we always need at least RPC_HEADER_LEN
547 * bytes. We check this here because we will receive
548 * RPC_HEADER_LEN bytes in cli_trans_sock_send_done.
550 status = NT_STATUS_INVALID_PARAMETER;
554 if (transport->trans_send != NULL) {
555 subreq = transport->trans_send(state, ev, data, data_len,
556 max_rdata_len, transport->priv);
557 if (subreq == NULL) {
560 tevent_req_set_callback(subreq, cli_api_pipe_trans_done, req);
565 * If the transport does not provide a "trans" routine, i.e. for
566 * example the ncacn_ip_tcp transport, do the write/read step here.
569 subreq = rpc_write_send(state, ev, transport, data, data_len);
570 if (subreq == NULL) {
573 tevent_req_set_callback(subreq, cli_api_pipe_write_done, req);
577 tevent_req_nterror(req, status);
578 return tevent_req_post(req, ev);
584 static void cli_api_pipe_trans_done(struct tevent_req *subreq)
586 struct tevent_req *req = tevent_req_callback_data(
587 subreq, struct tevent_req);
588 struct cli_api_pipe_state *state = tevent_req_data(
589 req, struct cli_api_pipe_state);
592 status = state->transport->trans_recv(subreq, state, &state->rdata,
595 if (!NT_STATUS_IS_OK(status)) {
596 tevent_req_nterror(req, status);
599 tevent_req_done(req);
602 static void cli_api_pipe_write_done(struct tevent_req *subreq)
604 struct tevent_req *req = tevent_req_callback_data(
605 subreq, struct tevent_req);
606 struct cli_api_pipe_state *state = tevent_req_data(
607 req, struct cli_api_pipe_state);
610 status = rpc_write_recv(subreq);
612 if (!NT_STATUS_IS_OK(status)) {
613 tevent_req_nterror(req, status);
617 state->rdata = TALLOC_ARRAY(state, uint8_t, RPC_HEADER_LEN);
618 if (tevent_req_nomem(state->rdata, req)) {
623 * We don't need to use rpc_read_send here, the upper layer will cope
624 * with a short read, transport->trans_send could also return less
625 * than state->max_rdata_len.
627 subreq = state->transport->read_send(state, state->ev, state->rdata,
629 state->transport->priv);
630 if (tevent_req_nomem(subreq, req)) {
633 tevent_req_set_callback(subreq, cli_api_pipe_read_done, req);
636 static void cli_api_pipe_read_done(struct tevent_req *subreq)
638 struct tevent_req *req = tevent_req_callback_data(
639 subreq, struct tevent_req);
640 struct cli_api_pipe_state *state = tevent_req_data(
641 req, struct cli_api_pipe_state);
645 status = state->transport->read_recv(subreq, &received);
647 if (!NT_STATUS_IS_OK(status)) {
648 tevent_req_nterror(req, status);
651 state->rdata_len = received;
652 tevent_req_done(req);
655 static NTSTATUS cli_api_pipe_recv(struct tevent_req *req, TALLOC_CTX *mem_ctx,
656 uint8_t **prdata, uint32_t *prdata_len)
658 struct cli_api_pipe_state *state = tevent_req_data(
659 req, struct cli_api_pipe_state);
662 if (tevent_req_is_nterror(req, &status)) {
666 *prdata = talloc_move(mem_ctx, &state->rdata);
667 *prdata_len = state->rdata_len;
671 /****************************************************************************
672 Send data on an rpc pipe via trans. The data must be the last
673 pdu fragment of an NDR data stream.
675 Receive response data from an rpc pipe, which may be large...
677 Read the first fragment: unfortunately have to use SMBtrans for the first
678 bit, then SMBreadX for subsequent bits.
680 If first fragment received also wasn't the last fragment, continue
681 getting fragments until we _do_ receive the last fragment.
683 Request/Response PDU's look like the following...
685 |<------------------PDU len----------------------------------------------->|
686 |<-HDR_LEN-->|<--REQ LEN------>|.............|<-AUTH_HDRLEN->|<-AUTH_LEN-->|
688 +------------+-----------------+-------------+---------------+-------------+
689 | RPC HEADER | REQ/RESP HEADER | DATA ...... | AUTH_HDR | AUTH DATA |
690 +------------+-----------------+-------------+---------------+-------------+
692 Where the presence of the AUTH_HDR and AUTH DATA are dependent on the
693 signing & sealing being negotiated.
695 ****************************************************************************/
697 struct rpc_api_pipe_state {
698 struct event_context *ev;
699 struct rpc_pipe_client *cli;
700 uint8_t expected_pkt_type;
702 DATA_BLOB incoming_frag;
703 struct ncacn_packet *pkt;
707 size_t reply_pdu_offset;
711 static void rpc_api_pipe_trans_done(struct tevent_req *subreq);
712 static void rpc_api_pipe_got_pdu(struct tevent_req *subreq);
713 static void rpc_api_pipe_auth3_done(struct tevent_req *subreq);
715 static struct tevent_req *rpc_api_pipe_send(TALLOC_CTX *mem_ctx,
716 struct event_context *ev,
717 struct rpc_pipe_client *cli,
718 DATA_BLOB *data, /* Outgoing PDU */
719 uint8_t expected_pkt_type)
721 struct tevent_req *req, *subreq;
722 struct rpc_api_pipe_state *state;
723 uint16_t max_recv_frag;
726 req = tevent_req_create(mem_ctx, &state, struct rpc_api_pipe_state);
732 state->expected_pkt_type = expected_pkt_type;
733 state->incoming_frag = data_blob_null;
734 state->reply_pdu = data_blob_null;
735 state->reply_pdu_offset = 0;
736 state->endianess = DCERPC_DREP_LE;
739 * Ensure we're not sending too much.
741 if (data->length > cli->max_xmit_frag) {
742 status = NT_STATUS_INVALID_PARAMETER;
746 DEBUG(5,("rpc_api_pipe: %s\n", rpccli_pipe_txt(talloc_tos(), cli)));
748 if (state->expected_pkt_type == DCERPC_PKT_AUTH3) {
749 subreq = rpc_write_send(state, ev, cli->transport,
750 data->data, data->length);
751 if (subreq == NULL) {
754 tevent_req_set_callback(subreq, rpc_api_pipe_auth3_done, req);
758 /* get the header first, then fetch the rest once we have
759 * the frag_length available */
760 max_recv_frag = RPC_HEADER_LEN;
762 subreq = cli_api_pipe_send(state, ev, cli->transport,
763 data->data, data->length, max_recv_frag);
764 if (subreq == NULL) {
767 tevent_req_set_callback(subreq, rpc_api_pipe_trans_done, req);
771 tevent_req_nterror(req, status);
772 return tevent_req_post(req, ev);
778 static void rpc_api_pipe_auth3_done(struct tevent_req *subreq)
780 struct tevent_req *req =
781 tevent_req_callback_data(subreq,
785 status = rpc_write_recv(subreq);
787 if (!NT_STATUS_IS_OK(status)) {
788 tevent_req_nterror(req, status);
792 tevent_req_done(req);
795 static void rpc_api_pipe_trans_done(struct tevent_req *subreq)
797 struct tevent_req *req = tevent_req_callback_data(
798 subreq, struct tevent_req);
799 struct rpc_api_pipe_state *state = tevent_req_data(
800 req, struct rpc_api_pipe_state);
802 uint8_t *rdata = NULL;
803 uint32_t rdata_len = 0;
805 status = cli_api_pipe_recv(subreq, state, &rdata, &rdata_len);
807 if (!NT_STATUS_IS_OK(status)) {
808 DEBUG(5, ("cli_api_pipe failed: %s\n", nt_errstr(status)));
809 tevent_req_nterror(req, status);
814 DEBUG(3,("rpc_api_pipe: %s failed to return data.\n",
815 rpccli_pipe_txt(talloc_tos(), state->cli)));
816 tevent_req_done(req);
821 * Move data on state->incoming_frag.
823 state->incoming_frag.data = talloc_move(state, &rdata);
824 state->incoming_frag.length = rdata_len;
825 if (!state->incoming_frag.data) {
826 tevent_req_nterror(req, NT_STATUS_NO_MEMORY);
830 /* Ensure we have enough data for a pdu. */
831 subreq = get_complete_frag_send(state, state->ev, state->cli,
832 &state->incoming_frag);
833 if (tevent_req_nomem(subreq, req)) {
836 tevent_req_set_callback(subreq, rpc_api_pipe_got_pdu, req);
839 static void rpc_api_pipe_got_pdu(struct tevent_req *subreq)
841 struct tevent_req *req = tevent_req_callback_data(
842 subreq, struct tevent_req);
843 struct rpc_api_pipe_state *state = tevent_req_data(
844 req, struct rpc_api_pipe_state);
846 DATA_BLOB rdata = data_blob_null;
848 status = get_complete_frag_recv(subreq);
850 if (!NT_STATUS_IS_OK(status)) {
851 DEBUG(5, ("get_complete_frag failed: %s\n",
853 tevent_req_nterror(req, status);
857 state->pkt = talloc(state, struct ncacn_packet);
859 tevent_req_nterror(req, NT_STATUS_NO_MEMORY);
863 status = dcerpc_pull_ncacn_packet(state->pkt,
864 &state->incoming_frag,
867 if (!NT_STATUS_IS_OK(status)) {
868 tevent_req_nterror(req, status);
872 if (state->incoming_frag.length != state->pkt->frag_length) {
873 DEBUG(5, ("Incorrect pdu length %u, expected %u\n",
874 (unsigned int)state->incoming_frag.length,
875 (unsigned int)state->pkt->frag_length));
876 tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER);
880 status = cli_pipe_validate_current_pdu(state,
881 state->cli, state->pkt,
882 &state->incoming_frag,
883 state->expected_pkt_type,
887 DEBUG(10,("rpc_api_pipe: got frag len of %u at offset %u: %s\n",
888 (unsigned)state->incoming_frag.length,
889 (unsigned)state->reply_pdu_offset,
892 if (!NT_STATUS_IS_OK(status)) {
893 tevent_req_nterror(req, status);
897 if ((state->pkt->pfc_flags & DCERPC_PFC_FLAG_FIRST)
898 && (state->pkt->drep[0] != DCERPC_DREP_LE)) {
900 * Set the data type correctly for big-endian data on the
903 DEBUG(10,("rpc_api_pipe: On %s PDU data format is "
905 rpccli_pipe_txt(talloc_tos(), state->cli)));
906 state->endianess = 0x00; /* BIG ENDIAN */
909 * Check endianness on subsequent packets.
911 if (state->endianess != state->pkt->drep[0]) {
912 DEBUG(0,("rpc_api_pipe: Error : Endianness changed from %s to "
914 state->endianess?"little":"big",
915 state->pkt->drep[0]?"little":"big"));
916 tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER);
920 /* Now copy the data portion out of the pdu into rbuf. */
921 if (state->reply_pdu.length < state->reply_pdu_offset + rdata.length) {
922 if (!data_blob_realloc(NULL, &state->reply_pdu,
923 state->reply_pdu_offset + rdata.length)) {
924 tevent_req_nterror(req, NT_STATUS_NO_MEMORY);
929 memcpy(state->reply_pdu.data + state->reply_pdu_offset,
930 rdata.data, rdata.length);
931 state->reply_pdu_offset += rdata.length;
933 /* reset state->incoming_frag, there is no need to free it,
934 * it will be reallocated to the right size the next time
936 state->incoming_frag.length = 0;
938 if (state->pkt->pfc_flags & DCERPC_PFC_FLAG_LAST) {
939 /* make sure the pdu length is right now that we
940 * have all the data available (alloc hint may
941 * have allocated more than was actually used) */
942 state->reply_pdu.length = state->reply_pdu_offset;
943 DEBUG(10,("rpc_api_pipe: %s returned %u bytes.\n",
944 rpccli_pipe_txt(talloc_tos(), state->cli),
945 (unsigned)state->reply_pdu.length));
946 tevent_req_done(req);
950 subreq = get_complete_frag_send(state, state->ev, state->cli,
951 &state->incoming_frag);
952 if (tevent_req_nomem(subreq, req)) {
955 tevent_req_set_callback(subreq, rpc_api_pipe_got_pdu, req);
958 static NTSTATUS rpc_api_pipe_recv(struct tevent_req *req, TALLOC_CTX *mem_ctx,
959 struct ncacn_packet **pkt,
960 DATA_BLOB *reply_pdu)
962 struct rpc_api_pipe_state *state = tevent_req_data(
963 req, struct rpc_api_pipe_state);
966 if (tevent_req_is_nterror(req, &status)) {
970 /* return data to caller and assign it ownership of memory */
972 reply_pdu->data = talloc_move(mem_ctx, &state->reply_pdu.data);
973 reply_pdu->length = state->reply_pdu.length;
974 state->reply_pdu.length = 0;
976 data_blob_free(&state->reply_pdu);
980 *pkt = talloc_steal(mem_ctx, state->pkt);
986 /*******************************************************************
987 Creates spnego auth bind.
988 ********************************************************************/
990 static NTSTATUS create_spnego_auth_bind_req(TALLOC_CTX *mem_ctx,
991 struct pipe_auth_data *auth,
992 DATA_BLOB *auth_token)
994 struct spnego_context *spnego_ctx;
995 DATA_BLOB in_token = data_blob_null;
998 spnego_ctx = talloc_get_type_abort(auth->auth_ctx,
999 struct spnego_context);
1001 /* Negotiate the initial auth token */
1002 status = spnego_get_client_auth_token(mem_ctx, spnego_ctx,
1003 &in_token, auth_token);
1004 if (!NT_STATUS_IS_OK(status)) {
1008 DEBUG(5, ("Created GSS Authentication Token:\n"));
1009 dump_data(5, auth_token->data, auth_token->length);
1011 return NT_STATUS_OK;
1014 /*******************************************************************
1015 Creates krb5 auth bind.
1016 ********************************************************************/
1018 static NTSTATUS create_gssapi_auth_bind_req(TALLOC_CTX *mem_ctx,
1019 struct pipe_auth_data *auth,
1020 DATA_BLOB *auth_token)
1022 struct gse_context *gse_ctx;
1023 DATA_BLOB in_token = data_blob_null;
1026 gse_ctx = talloc_get_type_abort(auth->auth_ctx,
1027 struct gse_context);
1029 /* Negotiate the initial auth token */
1030 status = gse_get_client_auth_token(mem_ctx, gse_ctx,
1033 if (!NT_STATUS_IS_OK(status)) {
1037 DEBUG(5, ("Created GSS Authentication Token:\n"));
1038 dump_data(5, auth_token->data, auth_token->length);
1040 return NT_STATUS_OK;
1043 /*******************************************************************
1044 Creates NTLMSSP auth bind.
1045 ********************************************************************/
1047 static NTSTATUS create_ntlmssp_auth_rpc_bind_req(struct rpc_pipe_client *cli,
1048 DATA_BLOB *auth_token)
1050 struct auth_ntlmssp_state *ntlmssp_ctx;
1051 DATA_BLOB null_blob = data_blob_null;
1054 ntlmssp_ctx = talloc_get_type_abort(cli->auth->auth_ctx,
1055 struct auth_ntlmssp_state);
1057 DEBUG(5, ("create_ntlmssp_auth_rpc_bind_req: Processing NTLMSSP Negotiate\n"));
1058 status = auth_ntlmssp_update(ntlmssp_ctx, null_blob, auth_token);
1060 if (!NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
1061 data_blob_free(auth_token);
1065 DEBUG(5, ("create_ntlmssp_auth_rpc_bind_req: NTLMSSP Negotiate:\n"));
1066 dump_data(5, auth_token->data, auth_token->length);
1068 return NT_STATUS_OK;
1071 /*******************************************************************
1072 Creates schannel auth bind.
1073 ********************************************************************/
1075 static NTSTATUS create_schannel_auth_rpc_bind_req(struct rpc_pipe_client *cli,
1076 DATA_BLOB *auth_token)
1079 struct NL_AUTH_MESSAGE r;
1081 /* Use lp_workgroup() if domain not specified */
1083 if (!cli->auth->domain || !cli->auth->domain[0]) {
1084 cli->auth->domain = talloc_strdup(cli, lp_workgroup());
1085 if (cli->auth->domain == NULL) {
1086 return NT_STATUS_NO_MEMORY;
1091 * Now marshall the data into the auth parse_struct.
1094 r.MessageType = NL_NEGOTIATE_REQUEST;
1095 r.Flags = NL_FLAG_OEM_NETBIOS_DOMAIN_NAME |
1096 NL_FLAG_OEM_NETBIOS_COMPUTER_NAME;
1097 r.oem_netbios_domain.a = cli->auth->domain;
1098 r.oem_netbios_computer.a = global_myname();
1100 status = dcerpc_push_schannel_bind(cli, &r, auth_token);
1101 if (!NT_STATUS_IS_OK(status)) {
1105 return NT_STATUS_OK;
1108 /*******************************************************************
1109 Creates the internals of a DCE/RPC bind request or alter context PDU.
1110 ********************************************************************/
1112 static NTSTATUS create_bind_or_alt_ctx_internal(TALLOC_CTX *mem_ctx,
1113 enum dcerpc_pkt_type ptype,
1115 const struct ndr_syntax_id *abstract,
1116 const struct ndr_syntax_id *transfer,
1117 const DATA_BLOB *auth_info,
1120 uint16 auth_len = auth_info->length;
1122 union dcerpc_payload u;
1123 struct dcerpc_ctx_list ctx_list;
1126 auth_len -= DCERPC_AUTH_TRAILER_LENGTH;
1129 ctx_list.context_id = 0;
1130 ctx_list.num_transfer_syntaxes = 1;
1131 ctx_list.abstract_syntax = *abstract;
1132 ctx_list.transfer_syntaxes = (struct ndr_syntax_id *)discard_const(transfer);
1134 u.bind.max_xmit_frag = RPC_MAX_PDU_FRAG_LEN;
1135 u.bind.max_recv_frag = RPC_MAX_PDU_FRAG_LEN;
1136 u.bind.assoc_group_id = 0x0;
1137 u.bind.num_contexts = 1;
1138 u.bind.ctx_list = &ctx_list;
1139 u.bind.auth_info = *auth_info;
1141 status = dcerpc_push_ncacn_packet(mem_ctx,
1143 DCERPC_PFC_FLAG_FIRST |
1144 DCERPC_PFC_FLAG_LAST,
1149 if (!NT_STATUS_IS_OK(status)) {
1150 DEBUG(0, ("Failed to marshall bind/alter ncacn_packet.\n"));
1154 return NT_STATUS_OK;
1157 /*******************************************************************
1158 Creates a DCE/RPC bind request.
1159 ********************************************************************/
1161 static NTSTATUS create_rpc_bind_req(TALLOC_CTX *mem_ctx,
1162 struct rpc_pipe_client *cli,
1163 struct pipe_auth_data *auth,
1165 const struct ndr_syntax_id *abstract,
1166 const struct ndr_syntax_id *transfer,
1169 DATA_BLOB auth_token = data_blob_null;
1170 DATA_BLOB auth_info = data_blob_null;
1171 NTSTATUS ret = NT_STATUS_OK;
1173 switch (auth->auth_type) {
1174 case DCERPC_AUTH_TYPE_SCHANNEL:
1175 ret = create_schannel_auth_rpc_bind_req(cli, &auth_token);
1176 if (!NT_STATUS_IS_OK(ret)) {
1181 case DCERPC_AUTH_TYPE_NTLMSSP:
1182 ret = create_ntlmssp_auth_rpc_bind_req(cli, &auth_token);
1183 if (!NT_STATUS_IS_OK(ret)) {
1188 case DCERPC_AUTH_TYPE_SPNEGO:
1189 ret = create_spnego_auth_bind_req(cli, auth, &auth_token);
1190 if (!NT_STATUS_IS_OK(ret)) {
1195 case DCERPC_AUTH_TYPE_KRB5:
1196 ret = create_gssapi_auth_bind_req(mem_ctx, auth, &auth_token);
1197 if (!NT_STATUS_IS_OK(ret)) {
1202 case DCERPC_AUTH_TYPE_NCALRPC_AS_SYSTEM:
1203 auth_token = data_blob_talloc(mem_ctx,
1204 "NCALRPC_AUTH_TOKEN",
1208 case DCERPC_AUTH_TYPE_NONE:
1212 /* "Can't" happen. */
1213 return NT_STATUS_INVALID_INFO_CLASS;
1216 if (auth_token.length != 0) {
1217 ret = dcerpc_push_dcerpc_auth(cli,
1220 0, /* auth_pad_length */
1221 1, /* auth_context_id */
1224 if (!NT_STATUS_IS_OK(ret)) {
1227 data_blob_free(&auth_token);
1230 ret = create_bind_or_alt_ctx_internal(mem_ctx,
1240 /*******************************************************************
1242 Does an rpc request on a pipe. Incoming data is NDR encoded in in_data.
1243 Reply is NDR encoded in out_data. Splits the data stream into RPC PDU's
1244 and deals with signing/sealing details.
1245 ********************************************************************/
1247 struct rpc_api_pipe_req_state {
1248 struct event_context *ev;
1249 struct rpc_pipe_client *cli;
1252 DATA_BLOB *req_data;
1253 uint32_t req_data_sent;
1255 DATA_BLOB reply_pdu;
1258 static void rpc_api_pipe_req_write_done(struct tevent_req *subreq);
1259 static void rpc_api_pipe_req_done(struct tevent_req *subreq);
1260 static NTSTATUS prepare_next_frag(struct rpc_api_pipe_req_state *state,
1261 bool *is_last_frag);
1263 struct tevent_req *rpc_api_pipe_req_send(TALLOC_CTX *mem_ctx,
1264 struct event_context *ev,
1265 struct rpc_pipe_client *cli,
1267 DATA_BLOB *req_data)
1269 struct tevent_req *req, *subreq;
1270 struct rpc_api_pipe_req_state *state;
1274 req = tevent_req_create(mem_ctx, &state,
1275 struct rpc_api_pipe_req_state);
1281 state->op_num = op_num;
1282 state->req_data = req_data;
1283 state->req_data_sent = 0;
1284 state->call_id = get_rpc_call_id();
1285 state->reply_pdu = data_blob_null;
1286 state->rpc_out = data_blob_null;
1288 if (cli->max_xmit_frag < DCERPC_REQUEST_LENGTH
1289 + RPC_MAX_SIGN_SIZE) {
1290 /* Server is screwed up ! */
1291 status = NT_STATUS_INVALID_PARAMETER;
1295 status = prepare_next_frag(state, &is_last_frag);
1296 if (!NT_STATUS_IS_OK(status)) {
1301 subreq = rpc_api_pipe_send(state, ev, state->cli,
1303 DCERPC_PKT_RESPONSE);
1304 if (subreq == NULL) {
1307 tevent_req_set_callback(subreq, rpc_api_pipe_req_done, req);
1309 subreq = rpc_write_send(state, ev, cli->transport,
1310 state->rpc_out.data,
1311 state->rpc_out.length);
1312 if (subreq == NULL) {
1315 tevent_req_set_callback(subreq, rpc_api_pipe_req_write_done,
1321 tevent_req_nterror(req, status);
1322 return tevent_req_post(req, ev);
1328 static NTSTATUS prepare_next_frag(struct rpc_api_pipe_req_state *state,
1331 size_t data_sent_thistime;
1338 union dcerpc_payload u;
1340 data_left = state->req_data->length - state->req_data_sent;
1342 status = dcerpc_guess_sizes(state->cli->auth,
1343 DCERPC_REQUEST_LENGTH, data_left,
1344 state->cli->max_xmit_frag,
1345 CLIENT_NDR_PADDING_SIZE,
1346 &data_sent_thistime,
1347 &frag_len, &auth_len, &pad_len);
1348 if (!NT_STATUS_IS_OK(status)) {
1352 if (state->req_data_sent == 0) {
1353 flags = DCERPC_PFC_FLAG_FIRST;
1356 if (data_sent_thistime == data_left) {
1357 flags |= DCERPC_PFC_FLAG_LAST;
1360 data_blob_free(&state->rpc_out);
1362 ZERO_STRUCT(u.request);
1364 u.request.alloc_hint = state->req_data->length;
1365 u.request.context_id = 0;
1366 u.request.opnum = state->op_num;
1368 status = dcerpc_push_ncacn_packet(state,
1375 if (!NT_STATUS_IS_OK(status)) {
1379 /* explicitly set frag_len here as dcerpc_push_ncacn_packet() can't
1380 * compute it right for requests because the auth trailer is missing
1382 dcerpc_set_frag_length(&state->rpc_out, frag_len);
1384 /* Copy in the data. */
1385 if (!data_blob_append(NULL, &state->rpc_out,
1386 state->req_data->data + state->req_data_sent,
1387 data_sent_thistime)) {
1388 return NT_STATUS_NO_MEMORY;
1391 switch (state->cli->auth->auth_level) {
1392 case DCERPC_AUTH_LEVEL_NONE:
1393 case DCERPC_AUTH_LEVEL_CONNECT:
1394 case DCERPC_AUTH_LEVEL_PACKET:
1396 case DCERPC_AUTH_LEVEL_INTEGRITY:
1397 case DCERPC_AUTH_LEVEL_PRIVACY:
1398 status = dcerpc_add_auth_footer(state->cli->auth, pad_len,
1400 if (!NT_STATUS_IS_OK(status)) {
1405 return NT_STATUS_INVALID_PARAMETER;
1408 state->req_data_sent += data_sent_thistime;
1409 *is_last_frag = ((flags & DCERPC_PFC_FLAG_LAST) != 0);
1414 static void rpc_api_pipe_req_write_done(struct tevent_req *subreq)
1416 struct tevent_req *req = tevent_req_callback_data(
1417 subreq, struct tevent_req);
1418 struct rpc_api_pipe_req_state *state = tevent_req_data(
1419 req, struct rpc_api_pipe_req_state);
1423 status = rpc_write_recv(subreq);
1424 TALLOC_FREE(subreq);
1425 if (!NT_STATUS_IS_OK(status)) {
1426 tevent_req_nterror(req, status);
1430 status = prepare_next_frag(state, &is_last_frag);
1431 if (!NT_STATUS_IS_OK(status)) {
1432 tevent_req_nterror(req, status);
1437 subreq = rpc_api_pipe_send(state, state->ev, state->cli,
1439 DCERPC_PKT_RESPONSE);
1440 if (tevent_req_nomem(subreq, req)) {
1443 tevent_req_set_callback(subreq, rpc_api_pipe_req_done, req);
1445 subreq = rpc_write_send(state, state->ev,
1446 state->cli->transport,
1447 state->rpc_out.data,
1448 state->rpc_out.length);
1449 if (tevent_req_nomem(subreq, req)) {
1452 tevent_req_set_callback(subreq, rpc_api_pipe_req_write_done,
1457 static void rpc_api_pipe_req_done(struct tevent_req *subreq)
1459 struct tevent_req *req = tevent_req_callback_data(
1460 subreq, struct tevent_req);
1461 struct rpc_api_pipe_req_state *state = tevent_req_data(
1462 req, struct rpc_api_pipe_req_state);
1465 status = rpc_api_pipe_recv(subreq, state, NULL, &state->reply_pdu);
1466 TALLOC_FREE(subreq);
1467 if (!NT_STATUS_IS_OK(status)) {
1468 tevent_req_nterror(req, status);
1471 tevent_req_done(req);
1474 NTSTATUS rpc_api_pipe_req_recv(struct tevent_req *req, TALLOC_CTX *mem_ctx,
1475 DATA_BLOB *reply_pdu)
1477 struct rpc_api_pipe_req_state *state = tevent_req_data(
1478 req, struct rpc_api_pipe_req_state);
1481 if (tevent_req_is_nterror(req, &status)) {
1483 * We always have to initialize to reply pdu, even if there is
1484 * none. The rpccli_* caller routines expect this.
1486 *reply_pdu = data_blob_null;
1490 /* return data to caller and assign it ownership of memory */
1491 reply_pdu->data = talloc_move(mem_ctx, &state->reply_pdu.data);
1492 reply_pdu->length = state->reply_pdu.length;
1493 state->reply_pdu.length = 0;
1495 return NT_STATUS_OK;
1498 /****************************************************************************
1499 Check the rpc bind acknowledge response.
1500 ****************************************************************************/
1502 static bool check_bind_response(const struct dcerpc_bind_ack *r,
1503 const struct ndr_syntax_id *transfer)
1505 struct dcerpc_ack_ctx ctx;
1507 if (r->secondary_address_size == 0) {
1508 DEBUG(4,("Ignoring length check -- ASU bug (server didn't fill in the pipe name correctly)"));
1511 if (r->num_results < 1 || !r->ctx_list) {
1515 ctx = r->ctx_list[0];
1517 /* check the transfer syntax */
1518 if ((ctx.syntax.if_version != transfer->if_version) ||
1519 (memcmp(&ctx.syntax.uuid, &transfer->uuid, sizeof(transfer->uuid)) !=0)) {
1520 DEBUG(2,("bind_rpc_pipe: transfer syntax differs\n"));
1524 if (r->num_results != 0x1 || ctx.result != 0) {
1525 DEBUG(2,("bind_rpc_pipe: bind denied results: %d reason: %x\n",
1526 r->num_results, ctx.reason));
1529 DEBUG(5,("check_bind_response: accepted!\n"));
1533 /*******************************************************************
1534 Creates a DCE/RPC bind authentication response.
1535 This is the packet that is sent back to the server once we
1536 have received a BIND-ACK, to finish the third leg of
1537 the authentication handshake.
1538 ********************************************************************/
1540 static NTSTATUS create_rpc_bind_auth3(TALLOC_CTX *mem_ctx,
1541 struct rpc_pipe_client *cli,
1543 enum dcerpc_AuthType auth_type,
1544 enum dcerpc_AuthLevel auth_level,
1545 DATA_BLOB *pauth_blob,
1549 union dcerpc_payload u;
1553 status = dcerpc_push_dcerpc_auth(mem_ctx,
1556 0, /* auth_pad_length */
1557 1, /* auth_context_id */
1559 &u.auth3.auth_info);
1560 if (!NT_STATUS_IS_OK(status)) {
1564 status = dcerpc_push_ncacn_packet(mem_ctx,
1566 DCERPC_PFC_FLAG_FIRST |
1567 DCERPC_PFC_FLAG_LAST,
1572 data_blob_free(&u.auth3.auth_info);
1573 if (!NT_STATUS_IS_OK(status)) {
1574 DEBUG(0,("create_bind_or_alt_ctx_internal: failed to marshall RPC_HDR_RB.\n"));
1578 return NT_STATUS_OK;
1581 /*******************************************************************
1582 Creates a DCE/RPC bind alter context authentication request which
1583 may contain a spnego auth blobl
1584 ********************************************************************/
1586 static NTSTATUS create_rpc_alter_context(TALLOC_CTX *mem_ctx,
1587 enum dcerpc_AuthType auth_type,
1588 enum dcerpc_AuthLevel auth_level,
1590 const struct ndr_syntax_id *abstract,
1591 const struct ndr_syntax_id *transfer,
1592 const DATA_BLOB *pauth_blob, /* spnego auth blob already created. */
1595 DATA_BLOB auth_info;
1598 status = dcerpc_push_dcerpc_auth(mem_ctx,
1601 0, /* auth_pad_length */
1602 1, /* auth_context_id */
1605 if (!NT_STATUS_IS_OK(status)) {
1609 status = create_bind_or_alt_ctx_internal(mem_ctx,
1616 data_blob_free(&auth_info);
1620 /****************************************************************************
1622 ****************************************************************************/
1624 struct rpc_pipe_bind_state {
1625 struct event_context *ev;
1626 struct rpc_pipe_client *cli;
1629 uint32_t rpc_call_id;
1632 static void rpc_pipe_bind_step_one_done(struct tevent_req *subreq);
1633 static NTSTATUS rpc_bind_next_send(struct tevent_req *req,
1634 struct rpc_pipe_bind_state *state,
1635 DATA_BLOB *credentials);
1636 static NTSTATUS rpc_bind_finish_send(struct tevent_req *req,
1637 struct rpc_pipe_bind_state *state,
1638 DATA_BLOB *credentials);
1640 struct tevent_req *rpc_pipe_bind_send(TALLOC_CTX *mem_ctx,
1641 struct event_context *ev,
1642 struct rpc_pipe_client *cli,
1643 struct pipe_auth_data *auth)
1645 struct tevent_req *req, *subreq;
1646 struct rpc_pipe_bind_state *state;
1649 req = tevent_req_create(mem_ctx, &state, struct rpc_pipe_bind_state);
1654 DEBUG(5,("Bind RPC Pipe: %s auth_type %u, auth_level %u\n",
1655 rpccli_pipe_txt(talloc_tos(), cli),
1656 (unsigned int)auth->auth_type,
1657 (unsigned int)auth->auth_level ));
1661 state->rpc_call_id = get_rpc_call_id();
1663 cli->auth = talloc_move(cli, &auth);
1665 /* Marshall the outgoing data. */
1666 status = create_rpc_bind_req(state, cli,
1669 &cli->abstract_syntax,
1670 &cli->transfer_syntax,
1673 if (!NT_STATUS_IS_OK(status)) {
1677 subreq = rpc_api_pipe_send(state, ev, cli, &state->rpc_out,
1678 DCERPC_PKT_BIND_ACK);
1679 if (subreq == NULL) {
1682 tevent_req_set_callback(subreq, rpc_pipe_bind_step_one_done, req);
1686 tevent_req_nterror(req, status);
1687 return tevent_req_post(req, ev);
1693 static void rpc_pipe_bind_step_one_done(struct tevent_req *subreq)
1695 struct tevent_req *req = tevent_req_callback_data(
1696 subreq, struct tevent_req);
1697 struct rpc_pipe_bind_state *state = tevent_req_data(
1698 req, struct rpc_pipe_bind_state);
1699 struct pipe_auth_data *pauth = state->cli->auth;
1700 struct auth_ntlmssp_state *ntlmssp_ctx;
1701 struct spnego_context *spnego_ctx;
1702 struct gse_context *gse_ctx;
1703 struct ncacn_packet *pkt = NULL;
1704 struct dcerpc_auth auth;
1705 DATA_BLOB auth_token = data_blob_null;
1708 status = rpc_api_pipe_recv(subreq, talloc_tos(), &pkt, NULL);
1709 TALLOC_FREE(subreq);
1710 if (!NT_STATUS_IS_OK(status)) {
1711 DEBUG(3, ("rpc_pipe_bind: %s bind request returned %s\n",
1712 rpccli_pipe_txt(talloc_tos(), state->cli),
1713 nt_errstr(status)));
1714 tevent_req_nterror(req, status);
1719 tevent_req_done(req);
1723 if (!check_bind_response(&pkt->u.bind_ack, &state->cli->transfer_syntax)) {
1724 DEBUG(2, ("rpc_pipe_bind: check_bind_response failed.\n"));
1725 tevent_req_nterror(req, NT_STATUS_BUFFER_TOO_SMALL);
1729 state->cli->max_xmit_frag = pkt->u.bind_ack.max_xmit_frag;
1730 state->cli->max_recv_frag = pkt->u.bind_ack.max_recv_frag;
1732 switch(pauth->auth_type) {
1734 case DCERPC_AUTH_TYPE_NONE:
1735 case DCERPC_AUTH_TYPE_NCALRPC_AS_SYSTEM:
1736 case DCERPC_AUTH_TYPE_SCHANNEL:
1737 /* Bind complete. */
1738 tevent_req_done(req);
1741 case DCERPC_AUTH_TYPE_NTLMSSP:
1742 case DCERPC_AUTH_TYPE_SPNEGO:
1743 case DCERPC_AUTH_TYPE_KRB5:
1744 /* Paranoid lenght checks */
1745 if (pkt->frag_length < DCERPC_AUTH_TRAILER_LENGTH
1746 + pkt->auth_length) {
1747 tevent_req_nterror(req,
1748 NT_STATUS_INFO_LENGTH_MISMATCH);
1751 /* get auth credentials */
1752 status = dcerpc_pull_dcerpc_auth(talloc_tos(),
1753 &pkt->u.bind_ack.auth_info,
1755 if (!NT_STATUS_IS_OK(status)) {
1756 DEBUG(0, ("Failed to pull dcerpc auth: %s.\n",
1757 nt_errstr(status)));
1758 tevent_req_nterror(req, status);
1768 * For authenticated binds we may need to do 3 or 4 leg binds.
1771 switch(pauth->auth_type) {
1773 case DCERPC_AUTH_TYPE_NONE:
1774 case DCERPC_AUTH_TYPE_NCALRPC_AS_SYSTEM:
1775 case DCERPC_AUTH_TYPE_SCHANNEL:
1776 /* Bind complete. */
1777 tevent_req_done(req);
1780 case DCERPC_AUTH_TYPE_NTLMSSP:
1781 ntlmssp_ctx = talloc_get_type_abort(pauth->auth_ctx,
1782 struct auth_ntlmssp_state);
1783 status = auth_ntlmssp_update(ntlmssp_ctx,
1784 auth.credentials, &auth_token);
1785 if (NT_STATUS_EQUAL(status,
1786 NT_STATUS_MORE_PROCESSING_REQUIRED)) {
1787 status = rpc_bind_next_send(req, state,
1789 } else if (NT_STATUS_IS_OK(status)) {
1790 status = rpc_bind_finish_send(req, state,
1795 case DCERPC_AUTH_TYPE_SPNEGO:
1796 spnego_ctx = talloc_get_type_abort(pauth->auth_ctx,
1797 struct spnego_context);
1798 status = spnego_get_client_auth_token(state,
1802 if (!NT_STATUS_IS_OK(status)) {
1805 if (auth_token.length == 0) {
1806 /* Bind complete. */
1807 tevent_req_done(req);
1810 if (spnego_require_more_processing(spnego_ctx)) {
1811 status = rpc_bind_next_send(req, state,
1814 status = rpc_bind_finish_send(req, state,
1819 case DCERPC_AUTH_TYPE_KRB5:
1820 gse_ctx = talloc_get_type_abort(pauth->auth_ctx,
1821 struct gse_context);
1822 status = gse_get_client_auth_token(state,
1826 if (!NT_STATUS_IS_OK(status)) {
1830 if (gse_require_more_processing(gse_ctx)) {
1831 status = rpc_bind_next_send(req, state, &auth_token);
1833 status = rpc_bind_finish_send(req, state, &auth_token);
1841 if (!NT_STATUS_IS_OK(status)) {
1842 tevent_req_nterror(req, status);
1847 DEBUG(0,("cli_finish_bind_auth: unknown auth type %u\n",
1848 (unsigned int)state->cli->auth->auth_type));
1849 tevent_req_nterror(req, NT_STATUS_INTERNAL_ERROR);
1852 static NTSTATUS rpc_bind_next_send(struct tevent_req *req,
1853 struct rpc_pipe_bind_state *state,
1854 DATA_BLOB *auth_token)
1856 struct pipe_auth_data *auth = state->cli->auth;
1857 struct tevent_req *subreq;
1860 /* Now prepare the alter context pdu. */
1861 data_blob_free(&state->rpc_out);
1863 status = create_rpc_alter_context(state,
1867 &state->cli->abstract_syntax,
1868 &state->cli->transfer_syntax,
1871 if (!NT_STATUS_IS_OK(status)) {
1875 subreq = rpc_api_pipe_send(state, state->ev, state->cli,
1876 &state->rpc_out, DCERPC_PKT_ALTER_RESP);
1877 if (subreq == NULL) {
1878 return NT_STATUS_NO_MEMORY;
1880 tevent_req_set_callback(subreq, rpc_pipe_bind_step_one_done, req);
1881 return NT_STATUS_OK;
1884 static NTSTATUS rpc_bind_finish_send(struct tevent_req *req,
1885 struct rpc_pipe_bind_state *state,
1886 DATA_BLOB *auth_token)
1888 struct pipe_auth_data *auth = state->cli->auth;
1889 struct tevent_req *subreq;
1892 state->auth3 = true;
1894 /* Now prepare the auth3 context pdu. */
1895 data_blob_free(&state->rpc_out);
1897 status = create_rpc_bind_auth3(state, state->cli,
1903 if (!NT_STATUS_IS_OK(status)) {
1907 subreq = rpc_api_pipe_send(state, state->ev, state->cli,
1908 &state->rpc_out, DCERPC_PKT_AUTH3);
1909 if (subreq == NULL) {
1910 return NT_STATUS_NO_MEMORY;
1912 tevent_req_set_callback(subreq, rpc_pipe_bind_step_one_done, req);
1913 return NT_STATUS_OK;
1916 NTSTATUS rpc_pipe_bind_recv(struct tevent_req *req)
1918 return tevent_req_simple_recv_ntstatus(req);
1921 NTSTATUS rpc_pipe_bind(struct rpc_pipe_client *cli,
1922 struct pipe_auth_data *auth)
1924 TALLOC_CTX *frame = talloc_stackframe();
1925 struct event_context *ev;
1926 struct tevent_req *req;
1927 NTSTATUS status = NT_STATUS_OK;
1929 ev = event_context_init(frame);
1931 status = NT_STATUS_NO_MEMORY;
1935 req = rpc_pipe_bind_send(frame, ev, cli, auth);
1937 status = NT_STATUS_NO_MEMORY;
1941 if (!tevent_req_poll(req, ev)) {
1942 status = map_nt_error_from_unix(errno);
1946 status = rpc_pipe_bind_recv(req);
1952 #define RPCCLI_DEFAULT_TIMEOUT 10000 /* 10 seconds. */
1954 unsigned int rpccli_set_timeout(struct rpc_pipe_client *rpc_cli,
1955 unsigned int timeout)
1959 if (rpc_cli->transport == NULL) {
1960 return RPCCLI_DEFAULT_TIMEOUT;
1963 if (rpc_cli->transport->set_timeout == NULL) {
1964 return RPCCLI_DEFAULT_TIMEOUT;
1967 old = rpc_cli->transport->set_timeout(rpc_cli->transport->priv, timeout);
1969 return RPCCLI_DEFAULT_TIMEOUT;
1975 bool rpccli_is_connected(struct rpc_pipe_client *rpc_cli)
1977 if (rpc_cli == NULL) {
1981 if (rpc_cli->transport == NULL) {
1985 return rpc_cli->transport->is_connected(rpc_cli->transport->priv);
1988 struct rpccli_bh_state {
1989 struct rpc_pipe_client *rpc_cli;
1992 static bool rpccli_bh_is_connected(struct dcerpc_binding_handle *h)
1994 struct rpccli_bh_state *hs = dcerpc_binding_handle_data(h,
1995 struct rpccli_bh_state);
1997 return rpccli_is_connected(hs->rpc_cli);
2000 static uint32_t rpccli_bh_set_timeout(struct dcerpc_binding_handle *h,
2003 struct rpccli_bh_state *hs = dcerpc_binding_handle_data(h,
2004 struct rpccli_bh_state);
2006 return rpccli_set_timeout(hs->rpc_cli, timeout);
2009 struct rpccli_bh_raw_call_state {
2015 static void rpccli_bh_raw_call_done(struct tevent_req *subreq);
2017 static struct tevent_req *rpccli_bh_raw_call_send(TALLOC_CTX *mem_ctx,
2018 struct tevent_context *ev,
2019 struct dcerpc_binding_handle *h,
2020 const struct GUID *object,
2023 const uint8_t *in_data,
2026 struct rpccli_bh_state *hs = dcerpc_binding_handle_data(h,
2027 struct rpccli_bh_state);
2028 struct tevent_req *req;
2029 struct rpccli_bh_raw_call_state *state;
2031 struct tevent_req *subreq;
2033 req = tevent_req_create(mem_ctx, &state,
2034 struct rpccli_bh_raw_call_state);
2038 state->in_data.data = discard_const_p(uint8_t, in_data);
2039 state->in_data.length = in_length;
2041 ok = rpccli_bh_is_connected(h);
2043 tevent_req_nterror(req, NT_STATUS_INVALID_CONNECTION);
2044 return tevent_req_post(req, ev);
2047 subreq = rpc_api_pipe_req_send(state, ev, hs->rpc_cli,
2048 opnum, &state->in_data);
2049 if (tevent_req_nomem(subreq, req)) {
2050 return tevent_req_post(req, ev);
2052 tevent_req_set_callback(subreq, rpccli_bh_raw_call_done, req);
2057 static void rpccli_bh_raw_call_done(struct tevent_req *subreq)
2059 struct tevent_req *req =
2060 tevent_req_callback_data(subreq,
2062 struct rpccli_bh_raw_call_state *state =
2063 tevent_req_data(req,
2064 struct rpccli_bh_raw_call_state);
2067 state->out_flags = 0;
2069 /* TODO: support bigendian responses */
2071 status = rpc_api_pipe_req_recv(subreq, state, &state->out_data);
2072 TALLOC_FREE(subreq);
2073 if (!NT_STATUS_IS_OK(status)) {
2074 tevent_req_nterror(req, status);
2078 tevent_req_done(req);
2081 static NTSTATUS rpccli_bh_raw_call_recv(struct tevent_req *req,
2082 TALLOC_CTX *mem_ctx,
2085 uint32_t *out_flags)
2087 struct rpccli_bh_raw_call_state *state =
2088 tevent_req_data(req,
2089 struct rpccli_bh_raw_call_state);
2092 if (tevent_req_is_nterror(req, &status)) {
2093 tevent_req_received(req);
2097 *out_data = talloc_move(mem_ctx, &state->out_data.data);
2098 *out_length = state->out_data.length;
2099 *out_flags = state->out_flags;
2100 tevent_req_received(req);
2101 return NT_STATUS_OK;
2104 struct rpccli_bh_disconnect_state {
2108 static struct tevent_req *rpccli_bh_disconnect_send(TALLOC_CTX *mem_ctx,
2109 struct tevent_context *ev,
2110 struct dcerpc_binding_handle *h)
2112 struct rpccli_bh_state *hs = dcerpc_binding_handle_data(h,
2113 struct rpccli_bh_state);
2114 struct tevent_req *req;
2115 struct rpccli_bh_disconnect_state *state;
2118 req = tevent_req_create(mem_ctx, &state,
2119 struct rpccli_bh_disconnect_state);
2124 ok = rpccli_bh_is_connected(h);
2126 tevent_req_nterror(req, NT_STATUS_INVALID_CONNECTION);
2127 return tevent_req_post(req, ev);
2131 * TODO: do a real async disconnect ...
2133 * For now the caller needs to free rpc_cli
2137 tevent_req_done(req);
2138 return tevent_req_post(req, ev);
2141 static NTSTATUS rpccli_bh_disconnect_recv(struct tevent_req *req)
2145 if (tevent_req_is_nterror(req, &status)) {
2146 tevent_req_received(req);
2150 tevent_req_received(req);
2151 return NT_STATUS_OK;
2154 static bool rpccli_bh_ref_alloc(struct dcerpc_binding_handle *h)
2159 static void rpccli_bh_do_ndr_print(struct dcerpc_binding_handle *h,
2161 const void *_struct_ptr,
2162 const struct ndr_interface_call *call)
2164 void *struct_ptr = discard_const(_struct_ptr);
2166 if (DEBUGLEVEL < 10) {
2170 if (ndr_flags & NDR_IN) {
2171 ndr_print_function_debug(call->ndr_print,
2176 if (ndr_flags & NDR_OUT) {
2177 ndr_print_function_debug(call->ndr_print,
2184 static const struct dcerpc_binding_handle_ops rpccli_bh_ops = {
2186 .is_connected = rpccli_bh_is_connected,
2187 .set_timeout = rpccli_bh_set_timeout,
2188 .raw_call_send = rpccli_bh_raw_call_send,
2189 .raw_call_recv = rpccli_bh_raw_call_recv,
2190 .disconnect_send = rpccli_bh_disconnect_send,
2191 .disconnect_recv = rpccli_bh_disconnect_recv,
2193 .ref_alloc = rpccli_bh_ref_alloc,
2194 .do_ndr_print = rpccli_bh_do_ndr_print,
2197 /* initialise a rpc_pipe_client binding handle */
2198 struct dcerpc_binding_handle *rpccli_bh_create(struct rpc_pipe_client *c)
2200 struct dcerpc_binding_handle *h;
2201 struct rpccli_bh_state *hs;
2203 h = dcerpc_binding_handle_create(c,
2208 struct rpccli_bh_state,
2218 bool rpccli_get_pwd_hash(struct rpc_pipe_client *rpc_cli, uint8_t nt_hash[16])
2220 struct auth_ntlmssp_state *a = NULL;
2221 struct cli_state *cli;
2223 if (rpc_cli->auth->auth_type == DCERPC_AUTH_TYPE_NTLMSSP) {
2224 a = talloc_get_type_abort(rpc_cli->auth->auth_ctx,
2225 struct auth_ntlmssp_state);
2226 } else if (rpc_cli->auth->auth_type == DCERPC_AUTH_TYPE_SPNEGO) {
2227 struct spnego_context *spnego_ctx;
2228 enum spnego_mech auth_type;
2232 spnego_ctx = talloc_get_type_abort(rpc_cli->auth->auth_ctx,
2233 struct spnego_context);
2234 status = spnego_get_negotiated_mech(spnego_ctx,
2235 &auth_type, &auth_ctx);
2236 if (!NT_STATUS_IS_OK(status)) {
2240 if (auth_type == SPNEGO_NTLMSSP) {
2241 a = talloc_get_type_abort(auth_ctx,
2242 struct auth_ntlmssp_state);
2247 memcpy(nt_hash, auth_ntlmssp_get_nt_hash(a), 16);
2251 cli = rpc_pipe_np_smb_conn(rpc_cli);
2255 E_md4hash(cli->password ? cli->password : "", nt_hash);
2259 NTSTATUS rpccli_ncalrpc_bind_data(TALLOC_CTX *mem_ctx,
2260 struct pipe_auth_data **presult)
2262 struct pipe_auth_data *result;
2264 result = talloc(mem_ctx, struct pipe_auth_data);
2265 if (result == NULL) {
2266 return NT_STATUS_NO_MEMORY;
2269 result->auth_type = DCERPC_AUTH_TYPE_NCALRPC_AS_SYSTEM;
2270 result->auth_level = DCERPC_AUTH_LEVEL_CONNECT;
2272 result->user_name = talloc_strdup(result, "");
2273 result->domain = talloc_strdup(result, "");
2274 if ((result->user_name == NULL) || (result->domain == NULL)) {
2275 TALLOC_FREE(result);
2276 return NT_STATUS_NO_MEMORY;
2280 return NT_STATUS_OK;
2283 NTSTATUS rpccli_anon_bind_data(TALLOC_CTX *mem_ctx,
2284 struct pipe_auth_data **presult)
2286 struct pipe_auth_data *result;
2288 result = talloc(mem_ctx, struct pipe_auth_data);
2289 if (result == NULL) {
2290 return NT_STATUS_NO_MEMORY;
2293 result->auth_type = DCERPC_AUTH_TYPE_NONE;
2294 result->auth_level = DCERPC_AUTH_LEVEL_NONE;
2296 result->user_name = talloc_strdup(result, "");
2297 result->domain = talloc_strdup(result, "");
2298 if ((result->user_name == NULL) || (result->domain == NULL)) {
2299 TALLOC_FREE(result);
2300 return NT_STATUS_NO_MEMORY;
2304 return NT_STATUS_OK;
2307 static int cli_auth_ntlmssp_data_destructor(struct pipe_auth_data *auth)
2309 TALLOC_FREE(auth->auth_ctx);
2313 static NTSTATUS rpccli_ntlmssp_bind_data(TALLOC_CTX *mem_ctx,
2314 enum dcerpc_AuthType auth_type,
2315 enum dcerpc_AuthLevel auth_level,
2317 const char *username,
2318 const char *password,
2319 struct pipe_auth_data **presult)
2321 struct auth_ntlmssp_state *ntlmssp_ctx;
2322 struct pipe_auth_data *result;
2325 result = talloc(mem_ctx, struct pipe_auth_data);
2326 if (result == NULL) {
2327 return NT_STATUS_NO_MEMORY;
2330 result->auth_type = auth_type;
2331 result->auth_level = auth_level;
2333 result->user_name = talloc_strdup(result, username);
2334 result->domain = talloc_strdup(result, domain);
2335 if ((result->user_name == NULL) || (result->domain == NULL)) {
2336 status = NT_STATUS_NO_MEMORY;
2340 status = auth_ntlmssp_client_start(NULL,
2343 lp_client_ntlmv2_auth(),
2345 if (!NT_STATUS_IS_OK(status)) {
2349 talloc_set_destructor(result, cli_auth_ntlmssp_data_destructor);
2351 status = auth_ntlmssp_set_username(ntlmssp_ctx, username);
2352 if (!NT_STATUS_IS_OK(status)) {
2356 status = auth_ntlmssp_set_domain(ntlmssp_ctx, domain);
2357 if (!NT_STATUS_IS_OK(status)) {
2361 status = auth_ntlmssp_set_password(ntlmssp_ctx, password);
2362 if (!NT_STATUS_IS_OK(status)) {
2367 * Turn off sign+seal to allow selected auth level to turn it back on.
2369 auth_ntlmssp_and_flags(ntlmssp_ctx, ~(NTLMSSP_NEGOTIATE_SIGN |
2370 NTLMSSP_NEGOTIATE_SEAL));
2372 if (auth_level == DCERPC_AUTH_LEVEL_INTEGRITY) {
2373 auth_ntlmssp_or_flags(ntlmssp_ctx, NTLMSSP_NEGOTIATE_SIGN);
2374 } else if (auth_level == DCERPC_AUTH_LEVEL_PRIVACY) {
2375 auth_ntlmssp_or_flags(ntlmssp_ctx, NTLMSSP_NEGOTIATE_SEAL |
2376 NTLMSSP_NEGOTIATE_SIGN);
2379 result->auth_ctx = ntlmssp_ctx;
2381 return NT_STATUS_OK;
2384 TALLOC_FREE(result);
2388 NTSTATUS rpccli_schannel_bind_data(TALLOC_CTX *mem_ctx, const char *domain,
2389 enum dcerpc_AuthLevel auth_level,
2390 struct netlogon_creds_CredentialState *creds,
2391 struct pipe_auth_data **presult)
2393 struct schannel_state *schannel_auth;
2394 struct pipe_auth_data *result;
2396 result = talloc(mem_ctx, struct pipe_auth_data);
2397 if (result == NULL) {
2398 return NT_STATUS_NO_MEMORY;
2401 result->auth_type = DCERPC_AUTH_TYPE_SCHANNEL;
2402 result->auth_level = auth_level;
2404 result->user_name = talloc_strdup(result, "");
2405 result->domain = talloc_strdup(result, domain);
2406 if ((result->user_name == NULL) || (result->domain == NULL)) {
2410 schannel_auth = talloc(result, struct schannel_state);
2411 if (schannel_auth == NULL) {
2415 schannel_auth->state = SCHANNEL_STATE_START;
2416 schannel_auth->seq_num = 0;
2417 schannel_auth->initiator = true;
2418 schannel_auth->creds = netlogon_creds_copy(result, creds);
2420 result->auth_ctx = schannel_auth;
2422 return NT_STATUS_OK;
2425 TALLOC_FREE(result);
2426 return NT_STATUS_NO_MEMORY;
2430 * Create an rpc pipe client struct, connecting to a tcp port.
2432 static NTSTATUS rpc_pipe_open_tcp_port(TALLOC_CTX *mem_ctx, const char *host,
2434 const struct ndr_syntax_id *abstract_syntax,
2435 struct rpc_pipe_client **presult)
2437 struct rpc_pipe_client *result;
2438 struct sockaddr_storage addr;
2442 result = TALLOC_ZERO_P(mem_ctx, struct rpc_pipe_client);
2443 if (result == NULL) {
2444 return NT_STATUS_NO_MEMORY;
2447 result->abstract_syntax = *abstract_syntax;
2448 result->transfer_syntax = ndr_transfer_syntax;
2450 result->desthost = talloc_strdup(result, host);
2451 result->srv_name_slash = talloc_asprintf_strupper_m(
2452 result, "\\\\%s", result->desthost);
2453 if ((result->desthost == NULL) || (result->srv_name_slash == NULL)) {
2454 status = NT_STATUS_NO_MEMORY;
2458 result->max_xmit_frag = RPC_MAX_PDU_FRAG_LEN;
2459 result->max_recv_frag = RPC_MAX_PDU_FRAG_LEN;
2461 if (!resolve_name(host, &addr, NBT_NAME_SERVER, false)) {
2462 status = NT_STATUS_NOT_FOUND;
2466 status = open_socket_out(&addr, port, 60*1000, &fd);
2467 if (!NT_STATUS_IS_OK(status)) {
2470 set_socket_options(fd, lp_socket_options());
2472 status = rpc_transport_sock_init(result, fd, &result->transport);
2473 if (!NT_STATUS_IS_OK(status)) {
2478 result->transport->transport = NCACN_IP_TCP;
2480 result->binding_handle = rpccli_bh_create(result);
2481 if (result->binding_handle == NULL) {
2482 TALLOC_FREE(result);
2483 return NT_STATUS_NO_MEMORY;
2487 return NT_STATUS_OK;
2490 TALLOC_FREE(result);
2495 * Determine the tcp port on which a dcerpc interface is listening
2496 * for the ncacn_ip_tcp transport via the endpoint mapper of the
2499 static NTSTATUS rpc_pipe_get_tcp_port(const char *host,
2500 const struct ndr_syntax_id *abstract_syntax,
2504 struct rpc_pipe_client *epm_pipe = NULL;
2505 struct dcerpc_binding_handle *epm_handle = NULL;
2506 struct pipe_auth_data *auth = NULL;
2507 struct dcerpc_binding *map_binding = NULL;
2508 struct dcerpc_binding *res_binding = NULL;
2509 struct epm_twr_t *map_tower = NULL;
2510 struct epm_twr_t *res_towers = NULL;
2511 struct policy_handle *entry_handle = NULL;
2512 uint32_t num_towers = 0;
2513 uint32_t max_towers = 1;
2514 struct epm_twr_p_t towers;
2515 TALLOC_CTX *tmp_ctx = talloc_stackframe();
2516 uint32_t result = 0;
2518 if (pport == NULL) {
2519 status = NT_STATUS_INVALID_PARAMETER;
2523 if (ndr_syntax_id_equal(abstract_syntax,
2524 &ndr_table_epmapper.syntax_id)) {
2526 return NT_STATUS_OK;
2529 /* open the connection to the endpoint mapper */
2530 status = rpc_pipe_open_tcp_port(tmp_ctx, host, 135,
2531 &ndr_table_epmapper.syntax_id,
2534 if (!NT_STATUS_IS_OK(status)) {
2537 epm_handle = epm_pipe->binding_handle;
2539 status = rpccli_anon_bind_data(tmp_ctx, &auth);
2540 if (!NT_STATUS_IS_OK(status)) {
2544 status = rpc_pipe_bind(epm_pipe, auth);
2545 if (!NT_STATUS_IS_OK(status)) {
2549 /* create tower for asking the epmapper */
2551 map_binding = TALLOC_ZERO_P(tmp_ctx, struct dcerpc_binding);
2552 if (map_binding == NULL) {
2553 status = NT_STATUS_NO_MEMORY;
2557 map_binding->transport = NCACN_IP_TCP;
2558 map_binding->object = *abstract_syntax;
2559 map_binding->host = host; /* needed? */
2560 map_binding->endpoint = "0"; /* correct? needed? */
2562 map_tower = TALLOC_ZERO_P(tmp_ctx, struct epm_twr_t);
2563 if (map_tower == NULL) {
2564 status = NT_STATUS_NO_MEMORY;
2568 status = dcerpc_binding_build_tower(tmp_ctx, map_binding,
2569 &(map_tower->tower));
2570 if (!NT_STATUS_IS_OK(status)) {
2574 /* allocate further parameters for the epm_Map call */
2576 res_towers = TALLOC_ARRAY(tmp_ctx, struct epm_twr_t, max_towers);
2577 if (res_towers == NULL) {
2578 status = NT_STATUS_NO_MEMORY;
2581 towers.twr = res_towers;
2583 entry_handle = TALLOC_ZERO_P(tmp_ctx, struct policy_handle);
2584 if (entry_handle == NULL) {
2585 status = NT_STATUS_NO_MEMORY;
2589 /* ask the endpoint mapper for the port */
2591 status = dcerpc_epm_Map(epm_handle,
2593 CONST_DISCARD(struct GUID *,
2594 &(abstract_syntax->uuid)),
2602 if (!NT_STATUS_IS_OK(status)) {
2606 if (result != EPMAPPER_STATUS_OK) {
2607 status = NT_STATUS_UNSUCCESSFUL;
2611 if (num_towers != 1) {
2612 status = NT_STATUS_UNSUCCESSFUL;
2616 /* extract the port from the answer */
2618 status = dcerpc_binding_from_tower(tmp_ctx,
2619 &(towers.twr->tower),
2621 if (!NT_STATUS_IS_OK(status)) {
2625 /* are further checks here necessary? */
2626 if (res_binding->transport != NCACN_IP_TCP) {
2627 status = NT_STATUS_UNSUCCESSFUL;
2631 *pport = (uint16_t)atoi(res_binding->endpoint);
2634 TALLOC_FREE(tmp_ctx);
2639 * Create a rpc pipe client struct, connecting to a host via tcp.
2640 * The port is determined by asking the endpoint mapper on the given
2643 NTSTATUS rpc_pipe_open_tcp(TALLOC_CTX *mem_ctx, const char *host,
2644 const struct ndr_syntax_id *abstract_syntax,
2645 struct rpc_pipe_client **presult)
2650 status = rpc_pipe_get_tcp_port(host, abstract_syntax, &port);
2651 if (!NT_STATUS_IS_OK(status)) {
2655 return rpc_pipe_open_tcp_port(mem_ctx, host, port,
2656 abstract_syntax, presult);
2659 /********************************************************************
2660 Create a rpc pipe client struct, connecting to a unix domain socket
2661 ********************************************************************/
2662 NTSTATUS rpc_pipe_open_ncalrpc(TALLOC_CTX *mem_ctx, const char *socket_path,
2663 const struct ndr_syntax_id *abstract_syntax,
2664 struct rpc_pipe_client **presult)
2666 struct rpc_pipe_client *result;
2667 struct sockaddr_un addr;
2671 result = talloc_zero(mem_ctx, struct rpc_pipe_client);
2672 if (result == NULL) {
2673 return NT_STATUS_NO_MEMORY;
2676 result->abstract_syntax = *abstract_syntax;
2677 result->transfer_syntax = ndr_transfer_syntax;
2679 result->desthost = get_myname(result);
2680 result->srv_name_slash = talloc_asprintf_strupper_m(
2681 result, "\\\\%s", result->desthost);
2682 if ((result->desthost == NULL) || (result->srv_name_slash == NULL)) {
2683 status = NT_STATUS_NO_MEMORY;
2687 result->max_xmit_frag = RPC_MAX_PDU_FRAG_LEN;
2688 result->max_recv_frag = RPC_MAX_PDU_FRAG_LEN;
2690 fd = socket(AF_UNIX, SOCK_STREAM, 0);
2692 status = map_nt_error_from_unix(errno);
2697 addr.sun_family = AF_UNIX;
2698 strlcpy(addr.sun_path, socket_path, sizeof(addr.sun_path));
2700 if (sys_connect(fd, (struct sockaddr *)(void *)&addr) == -1) {
2701 DEBUG(0, ("connect(%s) failed: %s\n", socket_path,
2704 return map_nt_error_from_unix(errno);
2707 status = rpc_transport_sock_init(result, fd, &result->transport);
2708 if (!NT_STATUS_IS_OK(status)) {
2713 result->transport->transport = NCALRPC;
2715 result->binding_handle = rpccli_bh_create(result);
2716 if (result->binding_handle == NULL) {
2717 TALLOC_FREE(result);
2718 return NT_STATUS_NO_MEMORY;
2722 return NT_STATUS_OK;
2725 TALLOC_FREE(result);
2729 struct rpc_pipe_client_np_ref {
2730 struct cli_state *cli;
2731 struct rpc_pipe_client *pipe;
2734 static int rpc_pipe_client_np_ref_destructor(struct rpc_pipe_client_np_ref *np_ref)
2736 DLIST_REMOVE(np_ref->cli->pipe_list, np_ref->pipe);
2740 /****************************************************************************
2741 Open a named pipe over SMB to a remote server.
2743 * CAVEAT CALLER OF THIS FUNCTION:
2744 * The returned rpc_pipe_client saves a copy of the cli_state cli pointer,
2745 * so be sure that this function is called AFTER any structure (vs pointer)
2746 * assignment of the cli. In particular, libsmbclient does structure
2747 * assignments of cli, which invalidates the data in the returned
2748 * rpc_pipe_client if this function is called before the structure assignment
2751 ****************************************************************************/
2753 static NTSTATUS rpc_pipe_open_np(struct cli_state *cli,
2754 const struct ndr_syntax_id *abstract_syntax,
2755 struct rpc_pipe_client **presult)
2757 struct rpc_pipe_client *result;
2759 struct rpc_pipe_client_np_ref *np_ref;
2761 /* sanity check to protect against crashes */
2764 return NT_STATUS_INVALID_HANDLE;
2767 result = TALLOC_ZERO_P(NULL, struct rpc_pipe_client);
2768 if (result == NULL) {
2769 return NT_STATUS_NO_MEMORY;
2772 result->abstract_syntax = *abstract_syntax;
2773 result->transfer_syntax = ndr_transfer_syntax;
2774 result->desthost = talloc_strdup(result, cli->desthost);
2775 result->srv_name_slash = talloc_asprintf_strupper_m(
2776 result, "\\\\%s", result->desthost);
2778 result->max_xmit_frag = RPC_MAX_PDU_FRAG_LEN;
2779 result->max_recv_frag = RPC_MAX_PDU_FRAG_LEN;
2781 if ((result->desthost == NULL) || (result->srv_name_slash == NULL)) {
2782 TALLOC_FREE(result);
2783 return NT_STATUS_NO_MEMORY;
2786 status = rpc_transport_np_init(result, cli, abstract_syntax,
2787 &result->transport);
2788 if (!NT_STATUS_IS_OK(status)) {
2789 TALLOC_FREE(result);
2793 result->transport->transport = NCACN_NP;
2795 np_ref = talloc(result->transport, struct rpc_pipe_client_np_ref);
2796 if (np_ref == NULL) {
2797 TALLOC_FREE(result);
2798 return NT_STATUS_NO_MEMORY;
2801 np_ref->pipe = result;
2803 DLIST_ADD(np_ref->cli->pipe_list, np_ref->pipe);
2804 talloc_set_destructor(np_ref, rpc_pipe_client_np_ref_destructor);
2806 result->binding_handle = rpccli_bh_create(result);
2807 if (result->binding_handle == NULL) {
2808 TALLOC_FREE(result);
2809 return NT_STATUS_NO_MEMORY;
2813 return NT_STATUS_OK;
2816 /****************************************************************************
2817 Open a pipe to a remote server.
2818 ****************************************************************************/
2820 static NTSTATUS cli_rpc_pipe_open(struct cli_state *cli,
2821 enum dcerpc_transport_t transport,
2822 const struct ndr_syntax_id *interface,
2823 struct rpc_pipe_client **presult)
2825 switch (transport) {
2827 return rpc_pipe_open_tcp(NULL, cli->desthost, interface,
2830 return rpc_pipe_open_np(cli, interface, presult);
2832 return NT_STATUS_NOT_IMPLEMENTED;
2836 /****************************************************************************
2837 Open a named pipe to an SMB server and bind anonymously.
2838 ****************************************************************************/
2840 NTSTATUS cli_rpc_pipe_open_noauth_transport(struct cli_state *cli,
2841 enum dcerpc_transport_t transport,
2842 const struct ndr_syntax_id *interface,
2843 struct rpc_pipe_client **presult)
2845 struct rpc_pipe_client *result;
2846 struct pipe_auth_data *auth;
2849 status = cli_rpc_pipe_open(cli, transport, interface, &result);
2850 if (!NT_STATUS_IS_OK(status)) {
2854 status = rpccli_anon_bind_data(result, &auth);
2855 if (!NT_STATUS_IS_OK(status)) {
2856 DEBUG(0, ("rpccli_anon_bind_data returned %s\n",
2857 nt_errstr(status)));
2858 TALLOC_FREE(result);
2863 * This is a bit of an abstraction violation due to the fact that an
2864 * anonymous bind on an authenticated SMB inherits the user/domain
2865 * from the enclosing SMB creds
2868 TALLOC_FREE(auth->user_name);
2869 TALLOC_FREE(auth->domain);
2871 auth->user_name = talloc_strdup(auth, cli->user_name);
2872 auth->domain = talloc_strdup(auth, cli->domain);
2873 auth->user_session_key = data_blob_talloc(auth,
2874 cli->user_session_key.data,
2875 cli->user_session_key.length);
2877 if ((auth->user_name == NULL) || (auth->domain == NULL)) {
2878 TALLOC_FREE(result);
2879 return NT_STATUS_NO_MEMORY;
2882 status = rpc_pipe_bind(result, auth);
2883 if (!NT_STATUS_IS_OK(status)) {
2885 if (ndr_syntax_id_equal(interface,
2886 &ndr_table_dssetup.syntax_id)) {
2887 /* non AD domains just don't have this pipe, avoid
2888 * level 0 statement in that case - gd */
2891 DEBUG(lvl, ("cli_rpc_pipe_open_noauth: rpc_pipe_bind for pipe "
2892 "%s failed with error %s\n",
2893 get_pipe_name_from_syntax(talloc_tos(), interface),
2894 nt_errstr(status) ));
2895 TALLOC_FREE(result);
2899 DEBUG(10,("cli_rpc_pipe_open_noauth: opened pipe %s to machine "
2900 "%s and bound anonymously.\n",
2901 get_pipe_name_from_syntax(talloc_tos(), interface),
2905 return NT_STATUS_OK;
2908 /****************************************************************************
2909 ****************************************************************************/
2911 NTSTATUS cli_rpc_pipe_open_noauth(struct cli_state *cli,
2912 const struct ndr_syntax_id *interface,
2913 struct rpc_pipe_client **presult)
2915 return cli_rpc_pipe_open_noauth_transport(cli, NCACN_NP,
2916 interface, presult);
2919 /****************************************************************************
2920 Open a named pipe to an SMB server and bind using NTLMSSP or SPNEGO NTLMSSP
2921 ****************************************************************************/
2923 NTSTATUS cli_rpc_pipe_open_ntlmssp(struct cli_state *cli,
2924 const struct ndr_syntax_id *interface,
2925 enum dcerpc_transport_t transport,
2926 enum dcerpc_AuthLevel auth_level,
2928 const char *username,
2929 const char *password,
2930 struct rpc_pipe_client **presult)
2932 struct rpc_pipe_client *result;
2933 struct pipe_auth_data *auth = NULL;
2934 enum dcerpc_AuthType auth_type = DCERPC_AUTH_TYPE_NTLMSSP;
2937 status = cli_rpc_pipe_open(cli, transport, interface, &result);
2938 if (!NT_STATUS_IS_OK(status)) {
2942 status = rpccli_ntlmssp_bind_data(result,
2943 auth_type, auth_level,
2944 domain, username, password,
2946 if (!NT_STATUS_IS_OK(status)) {
2947 DEBUG(0, ("rpccli_ntlmssp_bind_data returned %s\n",
2948 nt_errstr(status)));
2952 status = rpc_pipe_bind(result, auth);
2953 if (!NT_STATUS_IS_OK(status)) {
2954 DEBUG(0, ("cli_rpc_pipe_open_ntlmssp_internal: cli_rpc_pipe_bind failed with error %s\n",
2955 nt_errstr(status) ));
2959 DEBUG(10,("cli_rpc_pipe_open_ntlmssp_internal: opened pipe %s to "
2960 "machine %s and bound NTLMSSP as user %s\\%s.\n",
2961 get_pipe_name_from_syntax(talloc_tos(), interface),
2962 cli->desthost, domain, username ));
2965 return NT_STATUS_OK;
2969 TALLOC_FREE(result);
2973 /****************************************************************************
2975 Open a named pipe to an SMB server and bind using schannel (bind type 68)
2976 using session_key. sign and seal.
2978 The *pdc will be stolen onto this new pipe
2979 ****************************************************************************/
2981 NTSTATUS cli_rpc_pipe_open_schannel_with_key(struct cli_state *cli,
2982 const struct ndr_syntax_id *interface,
2983 enum dcerpc_transport_t transport,
2984 enum dcerpc_AuthLevel auth_level,
2986 struct netlogon_creds_CredentialState **pdc,
2987 struct rpc_pipe_client **presult)
2989 struct rpc_pipe_client *result;
2990 struct pipe_auth_data *auth;
2993 status = cli_rpc_pipe_open(cli, transport, interface, &result);
2994 if (!NT_STATUS_IS_OK(status)) {
2998 status = rpccli_schannel_bind_data(result, domain, auth_level,
3000 if (!NT_STATUS_IS_OK(status)) {
3001 DEBUG(0, ("rpccli_schannel_bind_data returned %s\n",
3002 nt_errstr(status)));
3003 TALLOC_FREE(result);
3007 status = rpc_pipe_bind(result, auth);
3008 if (!NT_STATUS_IS_OK(status)) {
3009 DEBUG(0, ("cli_rpc_pipe_open_schannel_with_key: "
3010 "cli_rpc_pipe_bind failed with error %s\n",
3011 nt_errstr(status) ));
3012 TALLOC_FREE(result);
3017 * The credentials on a new netlogon pipe are the ones we are passed
3018 * in - copy them over
3020 result->dc = netlogon_creds_copy(result, *pdc);
3021 if (result->dc == NULL) {
3022 TALLOC_FREE(result);
3023 return NT_STATUS_NO_MEMORY;
3026 DEBUG(10,("cli_rpc_pipe_open_schannel_with_key: opened pipe %s to machine %s "
3027 "for domain %s and bound using schannel.\n",
3028 get_pipe_name_from_syntax(talloc_tos(), interface),
3029 cli->desthost, domain ));
3032 return NT_STATUS_OK;
3035 /****************************************************************************
3036 Open a named pipe to an SMB server and bind using krb5 (bind type 16).
3037 The idea is this can be called with service_princ, username and password all
3038 NULL so long as the caller has a TGT.
3039 ****************************************************************************/
3041 NTSTATUS cli_rpc_pipe_open_krb5(struct cli_state *cli,
3042 const struct ndr_syntax_id *interface,
3043 enum dcerpc_transport_t transport,
3044 enum dcerpc_AuthLevel auth_level,
3046 const char *username,
3047 const char *password,
3048 struct rpc_pipe_client **presult)
3050 struct rpc_pipe_client *result;
3051 struct pipe_auth_data *auth;
3052 struct gse_context *gse_ctx;
3055 status = cli_rpc_pipe_open(cli, transport, interface, &result);
3056 if (!NT_STATUS_IS_OK(status)) {
3060 auth = talloc(result, struct pipe_auth_data);
3062 status = NT_STATUS_NO_MEMORY;
3065 auth->auth_type = DCERPC_AUTH_TYPE_KRB5;
3066 auth->auth_level = auth_level;
3071 auth->user_name = talloc_strdup(auth, username);
3072 if (!auth->user_name) {
3073 status = NT_STATUS_NO_MEMORY;
3077 /* Fixme, should we fetch/set the Realm ? */
3078 auth->domain = talloc_strdup(auth, "");
3079 if (!auth->domain) {
3080 status = NT_STATUS_NO_MEMORY;
3084 status = gse_init_client(auth,
3085 (auth_level == DCERPC_AUTH_LEVEL_INTEGRITY),
3086 (auth_level == DCERPC_AUTH_LEVEL_PRIVACY),
3087 NULL, server, "cifs", username, password,
3088 GSS_C_DCE_STYLE, &gse_ctx);
3089 if (!NT_STATUS_IS_OK(status)) {
3090 DEBUG(0, ("gse_init_client returned %s\n",
3091 nt_errstr(status)));
3094 auth->auth_ctx = gse_ctx;
3096 status = rpc_pipe_bind(result, auth);
3097 if (!NT_STATUS_IS_OK(status)) {
3098 DEBUG(0, ("cli_rpc_pipe_bind failed with error %s\n",
3099 nt_errstr(status)));
3104 return NT_STATUS_OK;
3107 TALLOC_FREE(result);
3111 NTSTATUS cli_rpc_pipe_open_spnego_krb5(struct cli_state *cli,
3112 const struct ndr_syntax_id *interface,
3113 enum dcerpc_transport_t transport,
3114 enum dcerpc_AuthLevel auth_level,
3116 const char *username,
3117 const char *password,
3118 struct rpc_pipe_client **presult)
3120 struct rpc_pipe_client *result;
3121 struct pipe_auth_data *auth;
3122 struct spnego_context *spnego_ctx;
3125 status = cli_rpc_pipe_open(cli, transport, interface, &result);
3126 if (!NT_STATUS_IS_OK(status)) {
3130 auth = talloc(result, struct pipe_auth_data);
3132 status = NT_STATUS_NO_MEMORY;
3135 auth->auth_type = DCERPC_AUTH_TYPE_SPNEGO;
3136 auth->auth_level = auth_level;
3141 auth->user_name = talloc_strdup(auth, username);
3142 if (!auth->user_name) {
3143 status = NT_STATUS_NO_MEMORY;
3147 /* Fixme, should we fetch/set the Realm ? */
3148 auth->domain = talloc_strdup(auth, "");
3149 if (!auth->domain) {
3150 status = NT_STATUS_NO_MEMORY;
3154 status = spnego_gssapi_init_client(auth,
3155 (auth->auth_level ==
3156 DCERPC_AUTH_LEVEL_INTEGRITY),
3157 (auth->auth_level ==
3158 DCERPC_AUTH_LEVEL_PRIVACY),
3160 NULL, server, "cifs",
3163 if (!NT_STATUS_IS_OK(status)) {
3164 DEBUG(0, ("spnego_init_client returned %s\n",
3165 nt_errstr(status)));
3168 auth->auth_ctx = spnego_ctx;
3170 status = rpc_pipe_bind(result, auth);
3171 if (!NT_STATUS_IS_OK(status)) {
3172 DEBUG(0, ("cli_rpc_pipe_bind failed with error %s\n",
3173 nt_errstr(status)));
3178 return NT_STATUS_OK;
3181 TALLOC_FREE(result);
3185 NTSTATUS cli_rpc_pipe_open_spnego_ntlmssp(struct cli_state *cli,
3186 const struct ndr_syntax_id *interface,
3187 enum dcerpc_transport_t transport,
3188 enum dcerpc_AuthLevel auth_level,
3190 const char *username,
3191 const char *password,
3192 struct rpc_pipe_client **presult)
3194 struct rpc_pipe_client *result;
3195 struct pipe_auth_data *auth;
3196 struct spnego_context *spnego_ctx;
3199 status = cli_rpc_pipe_open(cli, transport, interface, &result);
3200 if (!NT_STATUS_IS_OK(status)) {
3204 auth = talloc(result, struct pipe_auth_data);
3206 status = NT_STATUS_NO_MEMORY;
3209 auth->auth_type = DCERPC_AUTH_TYPE_SPNEGO;
3210 auth->auth_level = auth_level;
3215 auth->user_name = talloc_strdup(auth, username);
3216 if (!auth->user_name) {
3217 status = NT_STATUS_NO_MEMORY;
3224 auth->domain = talloc_strdup(auth, domain);
3225 if (!auth->domain) {
3226 status = NT_STATUS_NO_MEMORY;
3230 status = spnego_ntlmssp_init_client(auth,
3231 (auth->auth_level ==
3232 DCERPC_AUTH_LEVEL_INTEGRITY),
3233 (auth->auth_level ==
3234 DCERPC_AUTH_LEVEL_PRIVACY),
3236 domain, username, password,
3238 if (!NT_STATUS_IS_OK(status)) {
3239 DEBUG(0, ("spnego_init_client returned %s\n",
3240 nt_errstr(status)));
3243 auth->auth_ctx = spnego_ctx;
3245 status = rpc_pipe_bind(result, auth);
3246 if (!NT_STATUS_IS_OK(status)) {
3247 DEBUG(0, ("cli_rpc_pipe_bind failed with error %s\n",
3248 nt_errstr(status)));
3253 return NT_STATUS_OK;
3256 TALLOC_FREE(result);
3260 NTSTATUS cli_get_session_key(TALLOC_CTX *mem_ctx,
3261 struct rpc_pipe_client *cli,
3262 DATA_BLOB *session_key)
3264 struct pipe_auth_data *a = cli->auth;
3265 struct schannel_state *schannel_auth;
3266 struct auth_ntlmssp_state *ntlmssp_ctx;
3267 struct spnego_context *spnego_ctx;
3268 struct gse_context *gse_ctx;
3269 DATA_BLOB sk = data_blob_null;
3270 bool make_dup = false;
3272 if (!session_key || !cli) {
3273 return NT_STATUS_INVALID_PARAMETER;
3277 return NT_STATUS_INVALID_PARAMETER;
3280 switch (cli->auth->auth_type) {
3281 case DCERPC_AUTH_TYPE_SCHANNEL:
3282 schannel_auth = talloc_get_type_abort(a->auth_ctx,
3283 struct schannel_state);
3284 sk = data_blob_const(schannel_auth->creds->session_key, 16);
3287 case DCERPC_AUTH_TYPE_SPNEGO:
3288 spnego_ctx = talloc_get_type_abort(a->auth_ctx,
3289 struct spnego_context);
3290 sk = spnego_get_session_key(mem_ctx, spnego_ctx);
3293 case DCERPC_AUTH_TYPE_NTLMSSP:
3294 ntlmssp_ctx = talloc_get_type_abort(a->auth_ctx,
3295 struct auth_ntlmssp_state);
3296 sk = auth_ntlmssp_get_session_key(ntlmssp_ctx);
3299 case DCERPC_AUTH_TYPE_KRB5:
3300 gse_ctx = talloc_get_type_abort(a->auth_ctx,
3301 struct gse_context);
3302 sk = gse_get_session_key(mem_ctx, gse_ctx);
3305 case DCERPC_AUTH_TYPE_NCALRPC_AS_SYSTEM:
3306 case DCERPC_AUTH_TYPE_NONE:
3307 sk = data_blob_const(a->user_session_key.data,
3308 a->user_session_key.length);
3316 return NT_STATUS_NO_USER_SESSION_KEY;
3320 *session_key = data_blob_dup_talloc(mem_ctx, &sk);
3325 return NT_STATUS_OK;