librpc: gensec is our security provider abstraction, remove a void *
[obnox/samba/samba-obnox.git] / source3 / rpc_server / srv_pipe.c
1 /* 
2  *  Unix SMB/CIFS implementation.
3  *  RPC Pipe client / server routines
4  *  Almost completely rewritten by (C) Jeremy Allison 2005 - 2010
5  *  
6  *  This program is free software; you can redistribute it and/or modify
7  *  it under the terms of the GNU General Public License as published by
8  *  the Free Software Foundation; either version 3 of the License, or
9  *  (at your option) any later version.
10  *  
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.
15  *  
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/>.
18  */
19
20 /*  this module apparently provides an implementation of DCE/RPC over a
21  *  named pipe (IPC$ connection using SMBtrans).  details of DCE/RPC
22  *  documentation are available (in on-line form) from the X-Open group.
23  *
24  *  this module should provide a level of abstraction between SMB
25  *  and DCE/RPC, while minimising the amount of mallocs, unnecessary
26  *  data copies, and network traffic.
27  *
28  */
29
30 #include "includes.h"
31 #include "system/filesys.h"
32 #include "srv_pipe_internal.h"
33 #include "../librpc/gen_ndr/dcerpc.h"
34 #include "../librpc/rpc/rpc_common.h"
35 #include "dcesrv_auth_generic.h"
36 #include "rpc_server.h"
37 #include "rpc_dce.h"
38 #include "smbd/smbd.h"
39 #include "auth.h"
40 #include "ntdomain.h"
41 #include "rpc_server/srv_pipe.h"
42 #include "rpc_server/rpc_contexts.h"
43 #include "lib/param/param.h"
44 #include "librpc/ndr/ndr_table.h"
45 #include "auth/gensec/gensec.h"
46 #include "librpc/ndr/ndr_dcerpc.h"
47
48 #undef DBGC_CLASS
49 #define DBGC_CLASS DBGC_RPC_SRV
50
51 static NTSTATUS pipe_auth_verify_final(struct pipes_struct *p);
52
53 /**
54  * Dump everything from the start of the end up of the provided data
55  * into a file, but only at debug level >= 50
56  **/
57 static void dump_pdu_region(const char *name, int v,
58                             DATA_BLOB *data, size_t start, size_t end)
59 {
60         int fd, i;
61         char *fname = NULL;
62         ssize_t sz;
63
64         if (DEBUGLEVEL < 50) return;
65
66         if (start > data->length || end > data->length || start > end) return;
67
68         for (i = 1; i < 100; i++) {
69                 if (v != -1) {
70                         fname = talloc_asprintf(talloc_tos(),
71                                                 "/tmp/%s_%d.%d.prs",
72                                                 name, v, i);
73                 } else {
74                         fname = talloc_asprintf(talloc_tos(),
75                                                 "/tmp/%s_%d.prs",
76                                                 name, i);
77                 }
78                 if (!fname) {
79                         return;
80                 }
81                 fd = open(fname, O_WRONLY|O_CREAT|O_EXCL, 0644);
82                 if (fd != -1 || errno != EEXIST) break;
83         }
84         if (fd != -1) {
85                 sz = write(fd, data->data + start, end - start);
86                 i = close(fd);
87                 if ((sz != end - start) || (i != 0) ) {
88                         DEBUG(0, ("Error writing/closing %s: %ld!=%ld %d\n",
89                                   fname, (unsigned long)sz,
90                                   (unsigned long)end - start, i));
91                 } else {
92                         DEBUG(0,("created %s\n", fname));
93                 }
94         }
95         TALLOC_FREE(fname);
96 }
97
98 static DATA_BLOB generic_session_key(void)
99 {
100         return data_blob_const("SystemLibraryDTC", 16);
101 }
102
103 /*******************************************************************
104  Generate the next PDU to be returned from the data.
105 ********************************************************************/
106
107 static NTSTATUS create_next_packet(TALLOC_CTX *mem_ctx,
108                                    struct pipe_auth_data *auth,
109                                    uint32_t call_id,
110                                    DATA_BLOB *rdata,
111                                    size_t data_sent_length,
112                                    DATA_BLOB *frag,
113                                    size_t *pdu_size)
114 {
115         union dcerpc_payload u;
116         uint8_t pfc_flags;
117         size_t data_left;
118         size_t data_to_send;
119         size_t frag_len;
120         size_t pad_len = 0;
121         size_t auth_len = 0;
122         NTSTATUS status;
123
124         ZERO_STRUCT(u.response);
125
126         /* Set up rpc packet pfc flags. */
127         if (data_sent_length == 0) {
128                 pfc_flags = DCERPC_PFC_FLAG_FIRST;
129         } else {
130                 pfc_flags = 0;
131         }
132
133         /* Work out how much we can fit in a single PDU. */
134         data_left = rdata->length - data_sent_length;
135
136         /* Ensure there really is data left to send. */
137         if (!data_left) {
138                 DEBUG(0, ("No data left to send !\n"));
139                 return NT_STATUS_BUFFER_TOO_SMALL;
140         }
141
142         status = dcerpc_guess_sizes(auth,
143                                     DCERPC_RESPONSE_LENGTH,
144                                     data_left,
145                                     RPC_MAX_PDU_FRAG_LEN,
146                                     SERVER_NDR_PADDING_SIZE,
147                                     &data_to_send, &frag_len,
148                                     &auth_len, &pad_len);
149         if (!NT_STATUS_IS_OK(status)) {
150                 return status;
151         }
152
153         /* Set up the alloc hint. This should be the data left to send. */
154         u.response.alloc_hint = data_left;
155
156         /* Work out if this PDU will be the last. */
157         if (data_sent_length + data_to_send >= rdata->length) {
158                 pfc_flags |= DCERPC_PFC_FLAG_LAST;
159         }
160
161         /* Prepare data to be NDR encoded. */
162         u.response.stub_and_verifier =
163                 data_blob_const(rdata->data + data_sent_length, data_to_send);
164
165         /* Store the packet in the data stream. */
166         status = dcerpc_push_ncacn_packet(mem_ctx, DCERPC_PKT_RESPONSE,
167                                           pfc_flags, auth_len, call_id,
168                                           &u, frag);
169         if (!NT_STATUS_IS_OK(status)) {
170                 DEBUG(0, ("Failed to marshall RPC Packet.\n"));
171                 return status;
172         }
173
174         if (auth_len) {
175                 /* Set the proper length on the pdu, including padding.
176                  * Only needed if an auth trailer will be appended. */
177                 dcerpc_set_frag_length(frag, frag->length
178                                                 + pad_len
179                                                 + DCERPC_AUTH_TRAILER_LENGTH
180                                                 + auth_len);
181         }
182
183         if (auth_len) {
184                 status = dcerpc_add_auth_footer(auth, pad_len, frag);
185                 if (!NT_STATUS_IS_OK(status)) {
186                         data_blob_free(frag);
187                         return status;
188                 }
189         }
190
191         *pdu_size = data_to_send;
192         return NT_STATUS_OK;
193 }
194
195 /*******************************************************************
196  Generate the next PDU to be returned from the data in p->rdata. 
197 ********************************************************************/
198
199 bool create_next_pdu(struct pipes_struct *p)
200 {
201         size_t pdu_size = 0;
202         NTSTATUS status;
203
204         /*
205          * If we're in the fault state, keep returning fault PDU's until
206          * the pipe gets closed. JRA.
207          */
208         if (p->fault_state) {
209                 setup_fault_pdu(p, NT_STATUS(p->fault_state));
210                 return true;
211         }
212
213         status = create_next_packet(p->mem_ctx, &p->auth,
214                                     p->call_id, &p->out_data.rdata,
215                                     p->out_data.data_sent_length,
216                                     &p->out_data.frag, &pdu_size);
217         if (!NT_STATUS_IS_OK(status)) {
218                 DEBUG(0, ("Failed to create packet with error %s, "
219                           "(auth level %u / type %u)\n",
220                           nt_errstr(status),
221                           (unsigned int)p->auth.auth_level,
222                           (unsigned int)p->auth.auth_type));
223                 return false;
224         }
225
226         /* Setup the counts for this PDU. */
227         p->out_data.data_sent_length += pdu_size;
228         p->out_data.current_pdu_sent = 0;
229         return true;
230 }
231
232
233 static bool pipe_init_outgoing_data(struct pipes_struct *p);
234
235 /*******************************************************************
236  Marshall a bind_nak pdu.
237 *******************************************************************/
238
239 static bool setup_bind_nak(struct pipes_struct *p, struct ncacn_packet *pkt)
240 {
241         NTSTATUS status;
242         union dcerpc_payload u;
243
244         /* Free any memory in the current return data buffer. */
245         pipe_init_outgoing_data(p);
246
247         /*
248          * Initialize a bind_nak header.
249          */
250
251         ZERO_STRUCT(u);
252
253         u.bind_nak.reject_reason  = 0;
254
255         /*
256          * Marshall directly into the outgoing PDU space. We
257          * must do this as we need to set to the bind response
258          * header and are never sending more than one PDU here.
259          */
260
261         status = dcerpc_push_ncacn_packet(p->mem_ctx,
262                                           DCERPC_PKT_BIND_NAK,
263                                           DCERPC_PFC_FLAG_FIRST |
264                                                 DCERPC_PFC_FLAG_LAST,
265                                           0,
266                                           pkt->call_id,
267                                           &u,
268                                           &p->out_data.frag);
269         if (!NT_STATUS_IS_OK(status)) {
270                 return False;
271         }
272
273         p->out_data.data_sent_length = 0;
274         p->out_data.current_pdu_sent = 0;
275
276         TALLOC_FREE(p->auth.auth_ctx);
277         p->auth.auth_level = DCERPC_AUTH_LEVEL_NONE;
278         p->auth.auth_type = DCERPC_AUTH_TYPE_NONE;
279         p->pipe_bound = False;
280
281         return True;
282 }
283
284 /*******************************************************************
285  Marshall a fault pdu.
286 *******************************************************************/
287
288 bool setup_fault_pdu(struct pipes_struct *p, NTSTATUS fault_status)
289 {
290         NTSTATUS status;
291         union dcerpc_payload u;
292
293         /* Free any memory in the current return data buffer. */
294         pipe_init_outgoing_data(p);
295
296         /*
297          * Initialize a fault header.
298          */
299
300         ZERO_STRUCT(u);
301
302         u.fault.status          = NT_STATUS_V(fault_status);
303         u.fault._pad            = data_blob_talloc_zero(p->mem_ctx, 4);
304
305         /*
306          * Marshall directly into the outgoing PDU space. We
307          * must do this as we need to set to the bind response
308          * header and are never sending more than one PDU here.
309          */
310
311         status = dcerpc_push_ncacn_packet(p->mem_ctx,
312                                           DCERPC_PKT_FAULT,
313                                           DCERPC_PFC_FLAG_FIRST |
314                                            DCERPC_PFC_FLAG_LAST |
315                                            DCERPC_PFC_FLAG_DID_NOT_EXECUTE,
316                                           0,
317                                           p->call_id,
318                                           &u,
319                                           &p->out_data.frag);
320         if (!NT_STATUS_IS_OK(status)) {
321                 return False;
322         }
323
324         p->out_data.data_sent_length = 0;
325         p->out_data.current_pdu_sent = 0;
326
327         return True;
328 }
329
330 /*******************************************************************
331  Ensure a bind request has the correct abstract & transfer interface.
332  Used to reject unknown binds from Win2k.
333 *******************************************************************/
334
335 static bool check_bind_req(struct pipes_struct *p,
336                            struct ndr_syntax_id* abstract,
337                            struct ndr_syntax_id* transfer,
338                            uint32_t context_id)
339 {
340         struct pipe_rpc_fns *context_fns;
341         bool ok;
342
343         DEBUG(3,("check_bind_req for %s\n",
344                  ndr_interface_name(&abstract->uuid,
345                                     abstract->if_version)));
346
347         /* we have to check all now since win2k introduced a new UUID on the lsaprpc pipe */
348         if (rpc_srv_pipe_exists_by_id(abstract) &&
349            ndr_syntax_id_equal(transfer, &ndr_transfer_syntax_ndr)) {
350                 DEBUG(3, ("check_bind_req: %s -> %s rpc service\n",
351                           rpc_srv_get_pipe_cli_name(abstract),
352                           rpc_srv_get_pipe_srv_name(abstract)));
353         } else {
354                 return false;
355         }
356
357         ok = init_pipe_handles(p, abstract);
358         if (!ok) {
359                 DEBUG(1, ("Failed to init pipe handles!\n"));
360                 return false;
361         }
362
363         context_fns = talloc(p, struct pipe_rpc_fns);
364         if (context_fns == NULL) {
365                 DEBUG(0,("check_bind_req: talloc() failed!\n"));
366                 return false;
367         }
368
369         context_fns->next = context_fns->prev = NULL;
370         context_fns->n_cmds = rpc_srv_get_pipe_num_cmds(abstract);
371         context_fns->cmds = rpc_srv_get_pipe_cmds(abstract);
372         context_fns->context_id = context_id;
373         context_fns->syntax = *abstract;
374
375         /* add to the list of open contexts */
376
377         DLIST_ADD( p->contexts, context_fns );
378
379         return True;
380 }
381
382 /**
383  * Is a named pipe known?
384  * @param[in] pipename          Just the filename
385  * @result                      Do we want to serve this?
386  */
387 bool is_known_pipename(const char *pipename, struct ndr_syntax_id *syntax)
388 {
389         NTSTATUS status;
390
391         if (lp_disable_spoolss() && strequal(pipename, "spoolss")) {
392                 DEBUG(10, ("refusing spoolss access\n"));
393                 return false;
394         }
395
396         if (rpc_srv_get_pipe_interface_by_cli_name(pipename, syntax)) {
397                 return true;
398         }
399
400         status = smb_probe_module("rpc", pipename);
401         if (!NT_STATUS_IS_OK(status)) {
402                 DEBUG(10, ("is_known_pipename: %s unknown\n", pipename));
403                 return false;
404         }
405         DEBUG(10, ("is_known_pipename: %s loaded dynamically\n", pipename));
406
407         /*
408          * Scan the list again for the interface id
409          */
410         if (rpc_srv_get_pipe_interface_by_cli_name(pipename, syntax)) {
411                 return true;
412         }
413
414         DEBUG(10, ("is_known_pipename: pipe %s did not register itself!\n",
415                    pipename));
416
417         return false;
418 }
419
420 /*******************************************************************
421  Handle an NTLMSSP bind auth.
422 *******************************************************************/
423
424 static bool pipe_auth_generic_bind(struct pipes_struct *p,
425                                    struct ncacn_packet *pkt,
426                                    struct dcerpc_auth *auth_info,
427                                    DATA_BLOB *response)
428 {
429         TALLOC_CTX *mem_ctx = pkt;
430         struct gensec_security *gensec_security = NULL;
431         NTSTATUS status;
432
433         status = auth_generic_server_authtype_start(p,
434                                                     auth_info->auth_type,
435                                                     auth_info->auth_level,
436                                                     &auth_info->credentials,
437                                                     response,
438                                                     p->remote_address,
439                                                     &gensec_security);
440         if (!NT_STATUS_IS_OK(status) &&
441             !NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED))
442         {
443                 DEBUG(0, (__location__ ": auth_generic_server_authtype_start[%u/%u] failed: %s\n",
444                           auth_info->auth_type, auth_info->auth_level, nt_errstr(status)));
445                 return false;
446         }
447
448         /* Make sure data is bound to the memctx, to be freed the caller */
449         talloc_steal(mem_ctx, response->data);
450
451         p->auth.auth_ctx = gensec_security;
452         p->auth.auth_type = auth_info->auth_type;
453
454         if (pkt->pfc_flags & DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN) {
455                 p->auth.client_hdr_signing = true;
456                 p->auth.hdr_signing = gensec_have_feature(gensec_security,
457                                                 GENSEC_FEATURE_SIGN_PKT_HEADER);
458         }
459
460         if (p->auth.hdr_signing) {
461                 gensec_want_feature(gensec_security,
462                                     GENSEC_FEATURE_SIGN_PKT_HEADER);
463         }
464
465         if (NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
466                 return true;
467         }
468
469         status = pipe_auth_verify_final(p);
470         if (!NT_STATUS_IS_OK(status)) {
471                 DEBUG(0, ("pipe_auth_verify_final failed: %s\n",
472                           nt_errstr(status)));
473                 return false;
474         }
475
476         return true;
477 }
478
479 /*******************************************************************
480  Process an NTLMSSP authentication response.
481  If this function succeeds, the user has been authenticated
482  and their domain, name and calling workstation stored in
483  the pipe struct.
484 *******************************************************************/
485
486 static bool pipe_auth_generic_verify_final(TALLOC_CTX *mem_ctx,
487                                 struct gensec_security *gensec_security,
488                                 enum dcerpc_AuthLevel auth_level,
489                                 struct auth_session_info **session_info)
490 {
491         NTSTATUS status;
492         bool ret;
493
494         DEBUG(5, (__location__ ": checking user details\n"));
495
496         /* Finally - if the pipe negotiated integrity (sign) or privacy (seal)
497            ensure the underlying NTLMSSP flags are also set. If not we should
498            refuse the bind. */
499
500         status = auth_generic_server_check_flags(gensec_security,
501                                             (auth_level ==
502                                                 DCERPC_AUTH_LEVEL_INTEGRITY),
503                                             (auth_level ==
504                                                 DCERPC_AUTH_LEVEL_PRIVACY));
505         if (!NT_STATUS_IS_OK(status)) {
506                 DEBUG(0, (__location__ ": Client failed to negotatie proper "
507                           "security for rpc connection\n"));
508                 return false;
509         }
510
511         TALLOC_FREE(*session_info);
512
513         status = auth_generic_server_get_user_info(gensec_security,
514                                                 mem_ctx, session_info);
515         if (!NT_STATUS_IS_OK(status)) {
516                 DEBUG(0, (__location__ ": failed to obtain the server info "
517                           "for authenticated user: %s\n", nt_errstr(status)));
518                 return false;
519         }
520
521         if ((*session_info)->security_token == NULL) {
522                 DEBUG(1, ("Auth module failed to provide nt_user_token\n"));
523                 return false;
524         }
525
526         if ((*session_info)->unix_token == NULL) {
527                 DEBUG(1, ("Auth module failed to provide unix_token\n"));
528                 return false;
529         }
530
531         /*
532          * We're an authenticated bind over smb, so the session key needs to
533          * be set to "SystemLibraryDTC". Weird, but this is what Windows
534          * does. See the RPC-SAMBA3SESSIONKEY.
535          */
536
537         ret = session_info_set_session_key((*session_info), generic_session_key());
538         if (!ret) {
539                 DEBUG(0, ("Failed to set session key!\n"));
540                 return false;
541         }
542
543         return true;
544 }
545
546 static NTSTATUS pipe_auth_verify_final(struct pipes_struct *p)
547 {
548         struct gensec_security *gensec_security;
549         bool ok;
550
551         if (p->auth.auth_type == DCERPC_AUTH_TYPE_NONE) {
552                 p->pipe_bound = true;
553                 return NT_STATUS_OK;
554         }
555
556         gensec_security = p->auth.auth_ctx;
557
558         ok = pipe_auth_generic_verify_final(p, gensec_security,
559                                             p->auth.auth_level,
560                                             &p->session_info);
561         if (!ok) {
562                 return NT_STATUS_ACCESS_DENIED;
563         }
564
565         p->pipe_bound = true;
566
567         return NT_STATUS_OK;
568 }
569
570 /*******************************************************************
571  Respond to a pipe bind request.
572 *******************************************************************/
573
574 static bool api_pipe_bind_req(struct pipes_struct *p,
575                                 struct ncacn_packet *pkt)
576 {
577         struct dcerpc_auth auth_info;
578         uint16 assoc_gid;
579         unsigned int auth_type = DCERPC_AUTH_TYPE_NONE;
580         NTSTATUS status;
581         struct ndr_syntax_id id;
582         uint8_t pfc_flags = 0;
583         union dcerpc_payload u;
584         struct dcerpc_ack_ctx bind_ack_ctx;
585         DATA_BLOB auth_resp = data_blob_null;
586         DATA_BLOB auth_blob = data_blob_null;
587         const struct ndr_interface_table *table;
588
589         /* No rebinds on a bound pipe - use alter context. */
590         if (p->pipe_bound) {
591                 DEBUG(2,("Rejecting bind request on bound rpc connection\n"));
592                 return setup_bind_nak(p, pkt);
593         }
594
595         if (pkt->u.bind.num_contexts == 0) {
596                 DEBUG(0, ("api_pipe_bind_req: no rpc contexts around\n"));
597                 goto err_exit;
598         }
599
600         /*
601          * Try and find the correct pipe name to ensure
602          * that this is a pipe name we support.
603          */
604         id = pkt->u.bind.ctx_list[0].abstract_syntax;
605
606         table = ndr_table_by_uuid(&id.uuid);
607         if (table == NULL) {
608                 DEBUG(0,("unknown interface\n"));
609                 return false;
610         }
611
612         if (rpc_srv_pipe_exists_by_id(&id)) {
613                 DEBUG(3, ("api_pipe_bind_req: %s -> %s rpc service\n",
614                           rpc_srv_get_pipe_cli_name(&id),
615                           rpc_srv_get_pipe_srv_name(&id)));
616         } else {
617                 status = smb_probe_module(
618                         "rpc", dcerpc_default_transport_endpoint(pkt,
619                                 NCACN_NP, table));
620
621                 if (NT_STATUS_IS_ERR(status)) {
622                         DEBUG(3,("api_pipe_bind_req: Unknown rpc service name "
623                                  "%s in bind request.\n",
624                                  ndr_interface_name(&id.uuid,
625                                                     id.if_version)));
626
627                         return setup_bind_nak(p, pkt);
628                 }
629
630                 if (rpc_srv_get_pipe_interface_by_cli_name(
631                                 dcerpc_default_transport_endpoint(pkt,
632                                         NCACN_NP, table),
633                                 &id)) {
634                         DEBUG(3, ("api_pipe_bind_req: %s -> %s rpc service\n",
635                                   rpc_srv_get_pipe_cli_name(&id),
636                                   rpc_srv_get_pipe_srv_name(&id)));
637                 } else {
638                         DEBUG(0, ("module %s doesn't provide functions for "
639                                   "pipe %s!\n",
640                                   ndr_interface_name(&id.uuid,
641                                                      id.if_version),
642                                   ndr_interface_name(&id.uuid,
643                                                      id.if_version)));
644                         return setup_bind_nak(p, pkt);
645                 }
646         }
647
648         DEBUG(5,("api_pipe_bind_req: make response. %d\n", __LINE__));
649
650         if (pkt->u.bind.assoc_group_id != 0) {
651                 assoc_gid = pkt->u.bind.assoc_group_id;
652         } else {
653                 assoc_gid = 0x53f0;
654         }
655
656         /*
657          * Create the bind response struct.
658          */
659
660         /* If the requested abstract synt uuid doesn't match our client pipe,
661                 reject the bind_ack & set the transfer interface synt to all 0's,
662                 ver 0 (observed when NT5 attempts to bind to abstract interfaces
663                 unknown to NT4)
664                 Needed when adding entries to a DACL from NT5 - SK */
665
666         if (check_bind_req(p,
667                         &pkt->u.bind.ctx_list[0].abstract_syntax,
668                         &pkt->u.bind.ctx_list[0].transfer_syntaxes[0],
669                         pkt->u.bind.ctx_list[0].context_id)) {
670
671                 bind_ack_ctx.result = 0;
672                 bind_ack_ctx.reason.value = 0;
673                 bind_ack_ctx.syntax = pkt->u.bind.ctx_list[0].transfer_syntaxes[0];
674         } else {
675                 p->pipe_bound = False;
676                 /* Rejection reason: abstract syntax not supported */
677                 bind_ack_ctx.result = DCERPC_BIND_PROVIDER_REJECT;
678                 bind_ack_ctx.reason.value = DCERPC_BIND_REASON_ASYNTAX;
679                 bind_ack_ctx.syntax = ndr_syntax_id_null;
680         }
681
682         /*
683          * Check if this is an authenticated bind request.
684          */
685         if (pkt->auth_length) {
686                 /* Quick length check. Won't catch a bad auth footer,
687                  * prevents overrun. */
688
689                 if (pkt->frag_length < RPC_HEADER_LEN +
690                                         DCERPC_AUTH_TRAILER_LENGTH +
691                                         pkt->auth_length) {
692                         DEBUG(0,("api_pipe_bind_req: auth_len (%u) "
693                                 "too long for fragment %u.\n",
694                                 (unsigned int)pkt->auth_length,
695                                 (unsigned int)pkt->frag_length));
696                         goto err_exit;
697                 }
698
699                 /*
700                  * Decode the authentication verifier.
701                  */
702                 status = dcerpc_pull_dcerpc_auth(pkt,
703                                                  &pkt->u.bind.auth_info,
704                                                  &auth_info, p->endian);
705                 if (!NT_STATUS_IS_OK(status)) {
706                         DEBUG(0, ("Unable to unmarshall dcerpc_auth.\n"));
707                         goto err_exit;
708                 }
709
710                 auth_type = auth_info.auth_type;
711
712                 /* Work out if we have to sign or seal etc. */
713                 switch (auth_info.auth_level) {
714                 case DCERPC_AUTH_LEVEL_INTEGRITY:
715                         p->auth.auth_level = DCERPC_AUTH_LEVEL_INTEGRITY;
716                         break;
717                 case DCERPC_AUTH_LEVEL_PRIVACY:
718                         p->auth.auth_level = DCERPC_AUTH_LEVEL_PRIVACY;
719                         break;
720                 case DCERPC_AUTH_LEVEL_CONNECT:
721                         p->auth.auth_level = DCERPC_AUTH_LEVEL_CONNECT;
722                         break;
723                 default:
724                         DEBUG(0, ("Unexpected auth level (%u).\n",
725                                 (unsigned int)auth_info.auth_level ));
726                         goto err_exit;
727                 }
728
729                 switch (auth_type) {
730                 case DCERPC_AUTH_TYPE_NONE:
731                         break;
732
733                 default:
734                         if (!pipe_auth_generic_bind(p, pkt,
735                                                     &auth_info, &auth_resp)) {
736                                 goto err_exit;
737                         }
738                         break;
739                 }
740         }
741
742         if (auth_type == DCERPC_AUTH_TYPE_NONE) {
743                 /* Unauthenticated bind request. */
744                 /* We're finished - no more packets. */
745                 p->auth.auth_type = DCERPC_AUTH_TYPE_NONE;
746                 /* We must set the pipe auth_level here also. */
747                 p->auth.auth_level = DCERPC_AUTH_LEVEL_NONE;
748                 p->pipe_bound = True;
749                 /* The session key was initialized from the SMB
750                  * session in make_internal_rpc_pipe_p */
751         }
752
753         ZERO_STRUCT(u.bind_ack);
754         u.bind_ack.max_xmit_frag = RPC_MAX_PDU_FRAG_LEN;
755         u.bind_ack.max_recv_frag = RPC_MAX_PDU_FRAG_LEN;
756         u.bind_ack.assoc_group_id = assoc_gid;
757
758         /* name has to be \PIPE\xxxxx */
759         u.bind_ack.secondary_address =
760                         talloc_asprintf(pkt, "\\PIPE\\%s",
761                                         rpc_srv_get_pipe_srv_name(&id));
762         if (!u.bind_ack.secondary_address) {
763                 DEBUG(0, ("Out of memory!\n"));
764                 goto err_exit;
765         }
766         u.bind_ack.secondary_address_size =
767                                 strlen(u.bind_ack.secondary_address) + 1;
768
769         u.bind_ack.num_results = 1;
770         u.bind_ack.ctx_list = &bind_ack_ctx;
771
772         /* NOTE: We leave the auth_info empty so we can calculate the padding
773          * later and then append the auth_info --simo */
774
775         /*
776          * Marshall directly into the outgoing PDU space. We
777          * must do this as we need to set to the bind response
778          * header and are never sending more than one PDU here.
779          */
780
781         pfc_flags = DCERPC_PFC_FLAG_FIRST | DCERPC_PFC_FLAG_LAST;
782
783         if (p->auth.hdr_signing) {
784                 pfc_flags |= DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN;
785         }
786
787         status = dcerpc_push_ncacn_packet(p->mem_ctx,
788                                           DCERPC_PKT_BIND_ACK,
789                                           pfc_flags,
790                                           auth_resp.length,
791                                           pkt->call_id,
792                                           &u,
793                                           &p->out_data.frag);
794         if (!NT_STATUS_IS_OK(status)) {
795                 DEBUG(0, ("Failed to marshall bind_ack packet. (%s)\n",
796                           nt_errstr(status)));
797         }
798
799         if (auth_resp.length) {
800
801                 status = dcerpc_push_dcerpc_auth(pkt,
802                                                  auth_type,
803                                                  auth_info.auth_level,
804                                                  0,
805                                                  1, /* auth_context_id */
806                                                  &auth_resp,
807                                                  &auth_blob);
808                 if (!NT_STATUS_IS_OK(status)) {
809                         DEBUG(0, ("Marshalling of dcerpc_auth failed.\n"));
810                         goto err_exit;
811                 }
812         }
813
814         /* Now that we have the auth len store it into the right place in
815          * the dcerpc header */
816         dcerpc_set_frag_length(&p->out_data.frag,
817                                 p->out_data.frag.length + auth_blob.length);
818
819         if (auth_blob.length) {
820
821                 if (!data_blob_append(p->mem_ctx, &p->out_data.frag,
822                                         auth_blob.data, auth_blob.length)) {
823                         DEBUG(0, ("Append of auth info failed.\n"));
824                         goto err_exit;
825                 }
826         }
827
828         /*
829          * Setup the lengths for the initial reply.
830          */
831
832         p->out_data.data_sent_length = 0;
833         p->out_data.current_pdu_sent = 0;
834
835         TALLOC_FREE(auth_blob.data);
836         return True;
837
838   err_exit:
839
840         data_blob_free(&p->out_data.frag);
841         TALLOC_FREE(auth_blob.data);
842         return setup_bind_nak(p, pkt);
843 }
844
845 /*******************************************************************
846  This is the "stage3" response after a bind request and reply.
847 *******************************************************************/
848
849 bool api_pipe_bind_auth3(struct pipes_struct *p, struct ncacn_packet *pkt)
850 {
851         struct dcerpc_auth auth_info;
852         DATA_BLOB response = data_blob_null;
853         struct gensec_security *gensec_security;
854         NTSTATUS status;
855
856         DEBUG(5, ("api_pipe_bind_auth3: decode request. %d\n", __LINE__));
857
858         if (pkt->auth_length == 0) {
859                 DEBUG(1, ("No auth field sent for bind request!\n"));
860                 goto err;
861         }
862
863         /* Ensure there's enough data for an authenticated request. */
864         if (pkt->frag_length < RPC_HEADER_LEN
865                                 + DCERPC_AUTH_TRAILER_LENGTH
866                                 + pkt->auth_length) {
867                         DEBUG(1,("api_pipe_ntlmssp_auth_process: auth_len "
868                                 "%u is too large.\n",
869                         (unsigned int)pkt->auth_length));
870                 goto err;
871         }
872
873         /*
874          * Decode the authentication verifier response.
875          */
876
877         status = dcerpc_pull_dcerpc_auth(pkt,
878                                          &pkt->u.auth3.auth_info,
879                                          &auth_info, p->endian);
880         if (!NT_STATUS_IS_OK(status)) {
881                 DEBUG(1, ("Failed to unmarshall dcerpc_auth.\n"));
882                 goto err;
883         }
884
885         /* We must NEVER look at auth_info->auth_pad_len here,
886          * as old Samba client code gets it wrong and sends it
887          * as zero. JRA.
888          */
889
890         if (auth_info.auth_type != p->auth.auth_type) {
891                 DEBUG(1, ("Auth type mismatch! Client sent %d, "
892                           "but auth was started as type %d!\n",
893                           auth_info.auth_type, p->auth.auth_type));
894                 goto err;
895         }
896
897         gensec_security = p->auth.auth_ctx;
898
899         status = auth_generic_server_step(gensec_security,
900                                           pkt, &auth_info.credentials,
901                                           &response);
902
903         if (NT_STATUS_EQUAL(status,
904                             NT_STATUS_MORE_PROCESSING_REQUIRED) ||
905             response.length) {
906                 DEBUG(1, (__location__ ": This was supposed to be the final "
907                           "leg, but crypto machinery claims a response is "
908                           "needed, aborting auth!\n"));
909                 data_blob_free(&response);
910                 goto err;
911         }
912         if (!NT_STATUS_IS_OK(status)) {
913                 DEBUG(2, ("Auth failed (%s)\n", nt_errstr(status)));
914                 goto err;
915         }
916
917         /* Now verify auth was indeed successful and extract server info */
918         status = pipe_auth_verify_final(p);
919         if (!NT_STATUS_IS_OK(status)) {
920                 DEBUG(2, ("Auth Verify failed (%s)\n", nt_errstr(status)));
921                 goto err;
922         }
923
924         return true;
925
926 err:
927
928         TALLOC_FREE(p->auth.auth_ctx);
929         return false;
930 }
931
932 /****************************************************************************
933  Deal with an alter context call. Can be third part of 3 leg auth request for
934  SPNEGO calls.
935 ****************************************************************************/
936
937 static bool api_pipe_alter_context(struct pipes_struct *p,
938                                         struct ncacn_packet *pkt)
939 {
940         struct dcerpc_auth auth_info;
941         uint16 assoc_gid;
942         NTSTATUS status;
943         union dcerpc_payload u;
944         struct dcerpc_ack_ctx bind_ack_ctx;
945         DATA_BLOB auth_resp = data_blob_null;
946         DATA_BLOB auth_blob = data_blob_null;
947         int pad_len = 0;
948         struct gensec_security *gensec_security;
949
950         DEBUG(5,("api_pipe_alter_context: make response. %d\n", __LINE__));
951
952         if (pkt->u.bind.assoc_group_id != 0) {
953                 assoc_gid = pkt->u.bind.assoc_group_id;
954         } else {
955                 assoc_gid = 0x53f0;
956         }
957
958         /*
959          * Create the bind response struct.
960          */
961
962         /* If the requested abstract synt uuid doesn't match our client pipe,
963                 reject the bind_ack & set the transfer interface synt to all 0's,
964                 ver 0 (observed when NT5 attempts to bind to abstract interfaces
965                 unknown to NT4)
966                 Needed when adding entries to a DACL from NT5 - SK */
967
968         if (check_bind_req(p,
969                         &pkt->u.bind.ctx_list[0].abstract_syntax,
970                         &pkt->u.bind.ctx_list[0].transfer_syntaxes[0],
971                         pkt->u.bind.ctx_list[0].context_id)) {
972
973                 bind_ack_ctx.result = 0;
974                 bind_ack_ctx.reason.value = 0;
975                 bind_ack_ctx.syntax = pkt->u.bind.ctx_list[0].transfer_syntaxes[0];
976         } else {
977                 p->pipe_bound = False;
978                 /* Rejection reason: abstract syntax not supported */
979                 bind_ack_ctx.result = DCERPC_BIND_PROVIDER_REJECT;
980                 bind_ack_ctx.reason.value = DCERPC_BIND_REASON_ASYNTAX;
981                 bind_ack_ctx.syntax = ndr_syntax_id_null;
982         }
983
984         /*
985          * Check if this is an authenticated alter context request.
986          */
987         if (pkt->auth_length) {
988                 /* Quick length check. Won't catch a bad auth footer,
989                  * prevents overrun. */
990
991                 if (pkt->frag_length < RPC_HEADER_LEN +
992                                         DCERPC_AUTH_TRAILER_LENGTH +
993                                         pkt->auth_length) {
994                         DEBUG(0,("api_pipe_alter_context: auth_len (%u) "
995                                 "too long for fragment %u.\n",
996                                 (unsigned int)pkt->auth_length,
997                                 (unsigned int)pkt->frag_length ));
998                         goto err_exit;
999                 }
1000
1001                 status = dcerpc_pull_dcerpc_auth(pkt,
1002                                                  &pkt->u.bind.auth_info,
1003                                                  &auth_info, p->endian);
1004                 if (!NT_STATUS_IS_OK(status)) {
1005                         DEBUG(0, ("Unable to unmarshall dcerpc_auth.\n"));
1006                         goto err_exit;
1007                 }
1008
1009                 /* We can only finish if the pipe is unbound for now */
1010                 if (p->pipe_bound) {
1011                         DEBUG(0, (__location__ ": Pipe already bound, "
1012                                   "Altering Context not yet supported!\n"));
1013                         goto err_exit;
1014                 }
1015
1016                 if (auth_info.auth_type != p->auth.auth_type) {
1017                         DEBUG(0, ("Auth type mismatch! Client sent %d, "
1018                                   "but auth was started as type %d!\n",
1019                                   auth_info.auth_type, p->auth.auth_type));
1020                         goto err_exit;
1021                 }
1022
1023                 gensec_security = p->auth.auth_ctx;
1024                 status = auth_generic_server_step(gensec_security,
1025                                                   pkt,
1026                                                   &auth_info.credentials,
1027                                                   &auth_resp);
1028                 if (NT_STATUS_IS_OK(status)) {
1029                         /* third leg of auth, verify auth info */
1030                         status = pipe_auth_verify_final(p);
1031                         if (!NT_STATUS_IS_OK(status)) {
1032                                 DEBUG(0, ("Auth Verify failed (%s)\n",
1033                                           nt_errstr(status)));
1034                                 goto err_exit;
1035                         }
1036                 } else if (NT_STATUS_EQUAL(status,
1037                                         NT_STATUS_MORE_PROCESSING_REQUIRED)) {
1038                         DEBUG(10, ("More auth legs required.\n"));
1039                 } else {
1040                         DEBUG(0, ("Auth step returned an error (%s)\n",
1041                                   nt_errstr(status)));
1042                         goto err_exit;
1043                 }
1044         }
1045
1046         ZERO_STRUCT(u.alter_resp);
1047         u.alter_resp.max_xmit_frag = RPC_MAX_PDU_FRAG_LEN;
1048         u.alter_resp.max_recv_frag = RPC_MAX_PDU_FRAG_LEN;
1049         u.alter_resp.assoc_group_id = assoc_gid;
1050
1051         /* secondary address CAN be NULL
1052          * as the specs say it's ignored.
1053          * It MUST be NULL to have the spoolss working.
1054          */
1055         u.alter_resp.secondary_address = "";
1056         u.alter_resp.secondary_address_size = 1;
1057
1058         u.alter_resp.num_results = 1;
1059         u.alter_resp.ctx_list = &bind_ack_ctx;
1060
1061         /* NOTE: We leave the auth_info empty so we can calculate the padding
1062          * later and then append the auth_info --simo */
1063
1064         /*
1065          * Marshall directly into the outgoing PDU space. We
1066          * must do this as we need to set to the bind response
1067          * header and are never sending more than one PDU here.
1068          */
1069
1070         status = dcerpc_push_ncacn_packet(p->mem_ctx,
1071                                           DCERPC_PKT_ALTER_RESP,
1072                                           DCERPC_PFC_FLAG_FIRST |
1073                                                 DCERPC_PFC_FLAG_LAST,
1074                                           auth_resp.length,
1075                                           pkt->call_id,
1076                                           &u,
1077                                           &p->out_data.frag);
1078         if (!NT_STATUS_IS_OK(status)) {
1079                 DEBUG(0, ("Failed to marshall bind_ack packet. (%s)\n",
1080                           nt_errstr(status)));
1081         }
1082
1083         if (auth_resp.length) {
1084
1085                 /* Work out any padding needed before the auth footer. */
1086                 pad_len = p->out_data.frag.length % SERVER_NDR_PADDING_SIZE;
1087                 if (pad_len) {
1088                         pad_len = SERVER_NDR_PADDING_SIZE - pad_len;
1089                         DEBUG(10, ("auth pad_len = %u\n",
1090                                    (unsigned int)pad_len));
1091                 }
1092
1093                 status = dcerpc_push_dcerpc_auth(pkt,
1094                                                  auth_info.auth_type,
1095                                                  auth_info.auth_level,
1096                                                  pad_len,
1097                                                  1, /* auth_context_id */
1098                                                  &auth_resp,
1099                                                  &auth_blob);
1100                 if (!NT_STATUS_IS_OK(status)) {
1101                         DEBUG(0, ("Marshalling of dcerpc_auth failed.\n"));
1102                         goto err_exit;
1103                 }
1104         }
1105
1106         /* Now that we have the auth len store it into the right place in
1107          * the dcerpc header */
1108         dcerpc_set_frag_length(&p->out_data.frag,
1109                                 p->out_data.frag.length +
1110                                         pad_len + auth_blob.length);
1111
1112         if (auth_resp.length) {
1113                 if (pad_len) {
1114                         char pad[SERVER_NDR_PADDING_SIZE];
1115                         memset(pad, '\0', SERVER_NDR_PADDING_SIZE);
1116                         if (!data_blob_append(p->mem_ctx,
1117                                                 &p->out_data.frag,
1118                                                 pad, pad_len)) {
1119                                 DEBUG(0, ("api_pipe_bind_req: failed to add "
1120                                           "%u bytes of pad data.\n",
1121                                           (unsigned int)pad_len));
1122                                 goto err_exit;
1123                         }
1124                 }
1125
1126                 if (!data_blob_append(p->mem_ctx, &p->out_data.frag,
1127                                         auth_blob.data, auth_blob.length)) {
1128                         DEBUG(0, ("Append of auth info failed.\n"));
1129                         goto err_exit;
1130                 }
1131         }
1132
1133         /*
1134          * Setup the lengths for the initial reply.
1135          */
1136
1137         p->out_data.data_sent_length = 0;
1138         p->out_data.current_pdu_sent = 0;
1139
1140         TALLOC_FREE(auth_blob.data);
1141         return True;
1142
1143   err_exit:
1144
1145         data_blob_free(&p->out_data.frag);
1146         TALLOC_FREE(auth_blob.data);
1147         return setup_bind_nak(p, pkt);
1148 }
1149
1150 static bool api_rpcTNP(struct pipes_struct *p, struct ncacn_packet *pkt,
1151                        const struct api_struct *api_rpc_cmds, int n_cmds,
1152                        const struct ndr_syntax_id *syntax);
1153
1154 static bool srv_pipe_check_verification_trailer(struct pipes_struct *p,
1155                                                 struct ncacn_packet *pkt,
1156                                                 struct pipe_rpc_fns *pipe_fns)
1157 {
1158         TALLOC_CTX *frame = talloc_stackframe();
1159         struct dcerpc_sec_verification_trailer *vt = NULL;
1160         const uint32_t bitmask1 =
1161                 p->auth.client_hdr_signing ? DCERPC_SEC_VT_CLIENT_SUPPORTS_HEADER_SIGNING : 0;
1162         const struct dcerpc_sec_vt_pcontext pcontext = {
1163                 .abstract_syntax = pipe_fns->syntax,
1164                 .transfer_syntax = ndr_transfer_syntax_ndr,
1165         };
1166         const struct dcerpc_sec_vt_header2 header2 =
1167                dcerpc_sec_vt_header2_from_ncacn_packet(pkt);
1168         struct ndr_pull *ndr;
1169         enum ndr_err_code ndr_err;
1170         bool ret = false;
1171
1172         ndr = ndr_pull_init_blob(&p->in_data.data, frame);
1173         if (ndr == NULL) {
1174                 goto done;
1175         }
1176
1177         ndr_err = ndr_pop_dcerpc_sec_verification_trailer(ndr, frame, &vt);
1178         if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
1179                 goto done;
1180         }
1181
1182         ret = dcerpc_sec_verification_trailer_check(vt, &bitmask1,
1183                                                     &pcontext, &header2);
1184 done:
1185         TALLOC_FREE(frame);
1186         return ret;
1187 }
1188
1189 /****************************************************************************
1190  Find the correct RPC function to call for this request.
1191  If the pipe is authenticated then become the correct UNIX user
1192  before doing the call.
1193 ****************************************************************************/
1194
1195 static bool api_pipe_request(struct pipes_struct *p,
1196                                 struct ncacn_packet *pkt)
1197 {
1198         TALLOC_CTX *frame = talloc_stackframe();
1199         bool ret = False;
1200         struct pipe_rpc_fns *pipe_fns;
1201
1202         if (!p->pipe_bound) {
1203                 DEBUG(1, ("Pipe not bound!\n"));
1204                 data_blob_free(&p->out_data.rdata);
1205                 TALLOC_FREE(frame);
1206                 return false;
1207         }
1208
1209         /* get the set of RPC functions for this context */
1210         pipe_fns = find_pipe_fns_by_context(p->contexts,
1211                                             pkt->u.request.context_id);
1212         if (pipe_fns == NULL) {
1213                 DEBUG(0, ("No rpc function table associated with context "
1214                           "[%d]\n",
1215                           pkt->u.request.context_id));
1216                 data_blob_free(&p->out_data.rdata);
1217                 TALLOC_FREE(frame);
1218                 return false;
1219         }
1220
1221         if (!srv_pipe_check_verification_trailer(p, pkt, pipe_fns)) {
1222                 DEBUG(1, ("srv_pipe_check_verification_trailer: failed\n"));
1223                 setup_fault_pdu(p, NT_STATUS(DCERPC_FAULT_ACCESS_DENIED));
1224                 data_blob_free(&p->out_data.rdata);
1225                 TALLOC_FREE(frame);
1226                 return true;
1227         }
1228
1229         if (!become_authenticated_pipe_user(p->session_info)) {
1230                 DEBUG(1, ("Failed to become pipe user!\n"));
1231                 data_blob_free(&p->out_data.rdata);
1232                 TALLOC_FREE(frame);
1233                 return false;
1234         }
1235
1236         DEBUG(5, ("Requested %s rpc service\n",
1237                   ndr_interface_name(&pipe_fns->syntax.uuid,
1238                                      pipe_fns->syntax.if_version)));
1239
1240         ret = api_rpcTNP(p, pkt, pipe_fns->cmds, pipe_fns->n_cmds,
1241                          &pipe_fns->syntax);
1242         unbecome_authenticated_pipe_user();
1243
1244         TALLOC_FREE(frame);
1245         return ret;
1246 }
1247
1248 /*******************************************************************
1249  Calls the underlying RPC function for a named pipe.
1250  ********************************************************************/
1251
1252 static bool api_rpcTNP(struct pipes_struct *p, struct ncacn_packet *pkt,
1253                        const struct api_struct *api_rpc_cmds, int n_cmds,
1254                        const struct ndr_syntax_id *syntax)
1255 {
1256         int fn_num;
1257         uint32_t offset1;
1258         const struct ndr_interface_table *table;
1259
1260         /* interpret the command */
1261         DEBUG(4,("api_rpcTNP: %s op 0x%x - ",
1262                  ndr_interface_name(&syntax->uuid, syntax->if_version),
1263                  pkt->u.request.opnum));
1264
1265         table = ndr_table_by_uuid(&syntax->uuid);
1266         if (table == NULL) {
1267                 DEBUG(0,("unknown interface\n"));
1268                 return false;
1269         }
1270
1271         if (DEBUGLEVEL >= 50) {
1272                 fstring name;
1273                 slprintf(name, sizeof(name)-1, "in_%s",
1274                          dcerpc_default_transport_endpoint(pkt, NCACN_NP, table));
1275                 dump_pdu_region(name, pkt->u.request.opnum,
1276                                 &p->in_data.data, 0,
1277                                 p->in_data.data.length);
1278         }
1279
1280         for (fn_num = 0; fn_num < n_cmds; fn_num++) {
1281                 if (api_rpc_cmds[fn_num].opnum == pkt->u.request.opnum &&
1282                     api_rpc_cmds[fn_num].fn != NULL) {
1283                         DEBUG(3, ("api_rpcTNP: rpc command: %s\n",
1284                                   api_rpc_cmds[fn_num].name));
1285                         break;
1286                 }
1287         }
1288
1289         if (fn_num == n_cmds) {
1290                 /*
1291                  * For an unknown RPC just return a fault PDU but
1292                  * return True to allow RPC's on the pipe to continue
1293                  * and not put the pipe into fault state. JRA.
1294                  */
1295                 DEBUG(4, ("unknown\n"));
1296                 setup_fault_pdu(p, NT_STATUS(DCERPC_FAULT_OP_RNG_ERROR));
1297                 return True;
1298         }
1299
1300         offset1 = p->out_data.rdata.length;
1301
1302         DEBUG(6, ("api_rpc_cmds[%d].fn == %p\n", 
1303                 fn_num, api_rpc_cmds[fn_num].fn));
1304         /* do the actual command */
1305         if(!api_rpc_cmds[fn_num].fn(p)) {
1306                 DEBUG(0,("api_rpcTNP: %s: %s failed.\n",
1307                          ndr_interface_name(&syntax->uuid, syntax->if_version),
1308                          api_rpc_cmds[fn_num].name));
1309                 data_blob_free(&p->out_data.rdata);
1310                 return False;
1311         }
1312
1313         if (p->fault_state) {
1314                 DEBUG(4,("api_rpcTNP: fault(%d) return.\n", p->fault_state));
1315                 setup_fault_pdu(p, NT_STATUS(p->fault_state));
1316                 p->fault_state = 0;
1317                 return true;
1318         }
1319
1320         if (DEBUGLEVEL >= 50) {
1321                 fstring name;
1322                 slprintf(name, sizeof(name)-1, "out_%s",
1323                          dcerpc_default_transport_endpoint(pkt, NCACN_NP, table));
1324                 dump_pdu_region(name, pkt->u.request.opnum,
1325                                 &p->out_data.rdata, offset1,
1326                                 p->out_data.rdata.length);
1327         }
1328
1329         DEBUG(5,("api_rpcTNP: called %s successfully\n",
1330                  ndr_interface_name(&syntax->uuid, syntax->if_version)));
1331
1332         /* Check for buffer underflow in rpc parsing */
1333         if ((DEBUGLEVEL >= 10) &&
1334             (pkt->frag_length < p->in_data.data.length)) {
1335                 DEBUG(10, ("api_rpcTNP: rpc input buffer underflow (parse error?)\n"));
1336                 dump_data(10, p->in_data.data.data + pkt->frag_length,
1337                               p->in_data.data.length - pkt->frag_length);
1338         }
1339
1340         return True;
1341 }
1342
1343 /****************************************************************************
1344  Initialise an outgoing packet.
1345 ****************************************************************************/
1346
1347 static bool pipe_init_outgoing_data(struct pipes_struct *p)
1348 {
1349         output_data *o_data = &p->out_data;
1350
1351         /* Reset the offset counters. */
1352         o_data->data_sent_length = 0;
1353         o_data->current_pdu_sent = 0;
1354
1355         data_blob_free(&o_data->frag);
1356
1357         /* Free any memory in the current return data buffer. */
1358         data_blob_free(&o_data->rdata);
1359
1360         return True;
1361 }
1362
1363 /****************************************************************************
1364  Sets the fault state on incoming packets.
1365 ****************************************************************************/
1366
1367 void set_incoming_fault(struct pipes_struct *p)
1368 {
1369         data_blob_free(&p->in_data.data);
1370         p->in_data.pdu_needed_len = 0;
1371         p->in_data.pdu.length = 0;
1372         p->fault_state = DCERPC_FAULT_CANT_PERFORM;
1373
1374         DEBUG(10, ("Setting fault state\n"));
1375 }
1376
1377 static NTSTATUS dcesrv_auth_request(struct pipe_auth_data *auth,
1378                                     struct ncacn_packet *pkt,
1379                                     DATA_BLOB *raw_pkt)
1380 {
1381         NTSTATUS status;
1382         size_t hdr_size = DCERPC_REQUEST_LENGTH;
1383         size_t pad_len;
1384
1385         DEBUG(10, ("Checking request auth.\n"));
1386
1387         if (pkt->pfc_flags & DCERPC_PFC_FLAG_OBJECT_UUID) {
1388                 hdr_size += 16;
1389         }
1390
1391         /* in case of sealing this function will unseal the data in place */
1392         status = dcerpc_check_auth(auth, pkt,
1393                                    &pkt->u.request.stub_and_verifier,
1394                                    hdr_size, raw_pkt,
1395                                    &pad_len);
1396         if (!NT_STATUS_IS_OK(status)) {
1397                 return status;
1398         }
1399
1400
1401         /* remove padding and auth trailer,
1402          * this way the caller will get just the data */
1403         if (pkt->auth_length) {
1404                 size_t trail_len = pad_len
1405                                         + DCERPC_AUTH_TRAILER_LENGTH
1406                                         + pkt->auth_length;
1407                 if (pkt->u.request.stub_and_verifier.length < trail_len) {
1408                         return NT_STATUS_INFO_LENGTH_MISMATCH;
1409                 }
1410                 pkt->u.request.stub_and_verifier.length -= trail_len;
1411         }
1412
1413         return NT_STATUS_OK;
1414 }
1415
1416 /****************************************************************************
1417  Processes a request pdu. This will do auth processing if needed, and
1418  appends the data into the complete stream if the LAST flag is not set.
1419 ****************************************************************************/
1420
1421 static bool process_request_pdu(struct pipes_struct *p, struct ncacn_packet *pkt)
1422 {
1423         NTSTATUS status;
1424         DATA_BLOB data;
1425         struct dcerpc_sec_vt_header2 hdr2;
1426
1427         if (!p->pipe_bound) {
1428                 DEBUG(0,("process_request_pdu: rpc request with no bind.\n"));
1429                 set_incoming_fault(p);
1430                 return False;
1431         }
1432
1433         hdr2 = dcerpc_sec_vt_header2_from_ncacn_packet(pkt);
1434         if (pkt->pfc_flags & DCERPC_PFC_FLAG_FIRST) {
1435                 p->header2 = hdr2;
1436         } else {
1437                 if (!dcerpc_sec_vt_header2_equal(&hdr2, &p->header2)) {
1438                         set_incoming_fault(p);
1439                         return false;
1440                 }
1441         }
1442
1443         /* Store the opnum */
1444         p->opnum = pkt->u.request.opnum;
1445
1446         status = dcesrv_auth_request(&p->auth, pkt, &p->in_data.pdu);
1447         if (!NT_STATUS_IS_OK(status)) {
1448                 DEBUG(0, ("Failed to check packet auth. (%s)\n",
1449                           nt_errstr(status)));
1450                 set_incoming_fault(p);
1451                 return false;
1452         }
1453
1454         data = pkt->u.request.stub_and_verifier;
1455
1456         /*
1457          * Check the data length doesn't go over the 15Mb limit.
1458          * increased after observing a bug in the Windows NT 4.0 SP6a
1459          * spoolsv.exe when the response to a GETPRINTERDRIVER2 RPC
1460          * will not fit in the initial buffer of size 0x1068   --jerry 22/01/2002
1461          */
1462
1463         if (p->in_data.data.length + data.length > MAX_RPC_DATA_SIZE) {
1464                 DEBUG(0, ("process_request_pdu: "
1465                           "rpc data buffer too large (%u) + (%u)\n",
1466                           (unsigned int)p->in_data.data.length,
1467                           (unsigned int)data.length));
1468                 set_incoming_fault(p);
1469                 return False;
1470         }
1471
1472         /*
1473          * Append the data portion into the buffer and return.
1474          */
1475
1476         if (data.length) {
1477                 if (!data_blob_append(p->mem_ctx, &p->in_data.data,
1478                                           data.data, data.length)) {
1479                         DEBUG(0, ("Unable to append data size %u "
1480                                   "to parse buffer of size %u.\n",
1481                                   (unsigned int)data.length,
1482                                   (unsigned int)p->in_data.data.length));
1483                         set_incoming_fault(p);
1484                         return False;
1485                 }
1486         }
1487
1488         if (!(pkt->pfc_flags & DCERPC_PFC_FLAG_LAST)) {
1489                 return true;
1490         }
1491
1492         /*
1493          * Ok - we finally have a complete RPC stream.
1494          * Call the rpc command to process it.
1495          */
1496
1497         return api_pipe_request(p, pkt);
1498 }
1499
1500 void process_complete_pdu(struct pipes_struct *p, struct ncacn_packet *pkt)
1501 {
1502         bool reply = false;
1503
1504         /* Store the call_id */
1505         p->call_id = pkt->call_id;
1506
1507         DEBUG(10, ("Processing packet type %u\n", (unsigned int)pkt->ptype));
1508
1509         if (!pipe_init_outgoing_data(p)) {
1510                 goto done;
1511         }
1512
1513         switch (pkt->ptype) {
1514         case DCERPC_PKT_REQUEST:
1515                 reply = process_request_pdu(p, pkt);
1516                 break;
1517
1518         case DCERPC_PKT_PING: /* CL request - ignore... */
1519                 DEBUG(0, ("Error - Connectionless packet type %u received\n",
1520                           (unsigned int)pkt->ptype));
1521                 break;
1522
1523         case DCERPC_PKT_RESPONSE: /* No responses here. */
1524                 DEBUG(0, ("Error - DCERPC_PKT_RESPONSE received from client"));
1525                 break;
1526
1527         case DCERPC_PKT_FAULT:
1528         case DCERPC_PKT_WORKING:
1529                 /* CL request - reply to a ping when a call in process. */
1530         case DCERPC_PKT_NOCALL:
1531                 /* CL - server reply to a ping call. */
1532         case DCERPC_PKT_REJECT:
1533         case DCERPC_PKT_ACK:
1534         case DCERPC_PKT_CL_CANCEL:
1535         case DCERPC_PKT_FACK:
1536         case DCERPC_PKT_CANCEL_ACK:
1537                 DEBUG(0, ("Error - Connectionless packet type %u received\n",
1538                           (unsigned int)pkt->ptype));
1539                 break;
1540
1541         case DCERPC_PKT_BIND:
1542                 /*
1543                  * We assume that a pipe bind is only in one pdu.
1544                  */
1545                 reply = api_pipe_bind_req(p, pkt);
1546                 break;
1547
1548         case DCERPC_PKT_BIND_ACK:
1549         case DCERPC_PKT_BIND_NAK:
1550                 DEBUG(0, ("Error - DCERPC_PKT_BINDACK/DCERPC_PKT_BINDNACK "
1551                           "packet type %u received.\n",
1552                           (unsigned int)pkt->ptype));
1553                 break;
1554
1555
1556         case DCERPC_PKT_ALTER:
1557                 /*
1558                  * We assume that a pipe bind is only in one pdu.
1559                  */
1560                 reply = api_pipe_alter_context(p, pkt);
1561                 break;
1562
1563         case DCERPC_PKT_ALTER_RESP:
1564                 DEBUG(0, ("Error - DCERPC_PKT_ALTER_RESP received: "
1565                           "Should only be server -> client.\n"));
1566                 break;
1567
1568         case DCERPC_PKT_AUTH3:
1569                 /*
1570                  * The third packet in an auth exchange.
1571                  */
1572                 reply = api_pipe_bind_auth3(p, pkt);
1573                 break;
1574
1575         case DCERPC_PKT_SHUTDOWN:
1576                 DEBUG(0, ("Error - DCERPC_PKT_SHUTDOWN received: "
1577                           "Should only be server -> client.\n"));
1578                 break;
1579
1580         case DCERPC_PKT_CO_CANCEL:
1581                 /* For now just free all client data and continue
1582                  * processing. */
1583                 DEBUG(3,("process_complete_pdu: DCERPC_PKT_CO_CANCEL."
1584                          " Abandoning rpc call.\n"));
1585                 /* As we never do asynchronous RPC serving, we can
1586                  * never cancel a call (as far as I know).
1587                  * If we ever did we'd have to send a cancel_ack reply.
1588                  * For now, just free all client data and continue
1589                  * processing. */
1590                 reply = True;
1591                 break;
1592
1593 #if 0
1594                 /* Enable this if we're doing async rpc. */
1595                 /* We must check the outstanding callid matches. */
1596                 if (pipe_init_outgoing_data(p)) {
1597                         /* Send a cancel_ack PDU reply. */
1598                         /* We should probably check the auth-verifier here. */
1599                         reply = setup_cancel_ack_reply(p, pkt);
1600                 }
1601                 break;
1602 #endif
1603
1604         case DCERPC_PKT_ORPHANED:
1605                 /* We should probably check the auth-verifier here.
1606                  * For now just free all client data and continue
1607                  * processing. */
1608                 DEBUG(3, ("process_complete_pdu: DCERPC_PKT_ORPHANED."
1609                           " Abandoning rpc call.\n"));
1610                 reply = True;
1611                 break;
1612
1613         default:
1614                 DEBUG(0, ("process_complete_pdu: "
1615                           "Unknown rpc type = %u received.\n",
1616                           (unsigned int)pkt->ptype));
1617                 break;
1618         }
1619
1620 done:
1621         if (!reply) {
1622                 DEBUG(3,("DCE/RPC fault sent!"));
1623                 set_incoming_fault(p);
1624                 setup_fault_pdu(p, NT_STATUS(DCERPC_FAULT_OP_RNG_ERROR));
1625         }
1626         /* pkt and p->in_data.pdu.data freed by caller */
1627 }
1628