CVE-2021-23192: dcesrv_core: add better debugging to dcesrv_fault_disconnect()
[samba.git] / librpc / rpc / dcesrv_core.c
1 /*
2    Unix SMB/CIFS implementation.
3
4    server side dcerpc core code
5
6    Copyright (C) Andrew Tridgell 2003-2005
7    Copyright (C) Stefan (metze) Metzmacher 2004-2005
8    Copyright (C) Samuel Cabrero <scabrero@samba.org> 2019
9
10    This program is free software; you can redistribute it and/or modify
11    it under the terms of the GNU General Public License as published by
12    the Free Software Foundation; either version 3 of the License, or
13    (at your option) any later version.
14
15    This program is distributed in the hope that it will be useful,
16    but WITHOUT ANY WARRANTY; without even the implied warranty of
17    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18    GNU General Public License for more details.
19
20    You should have received a copy of the GNU General Public License
21    along with this program.  If not, see <http://www.gnu.org/licenses/>.
22 */
23
24 #include "includes.h"
25 #include "librpc/rpc/dcesrv_core.h"
26 #include "librpc/rpc/dcesrv_core_proto.h"
27 #include "librpc/rpc/dcerpc_util.h"
28 #include "librpc/gen_ndr/auth.h"
29 #include "auth/gensec/gensec.h"
30 #include "lib/util/dlinklist.h"
31 #include "libcli/security/security.h"
32 #include "param/param.h"
33 #include "lib/tsocket/tsocket.h"
34 #include "librpc/gen_ndr/ndr_dcerpc.h"
35 #include "lib/util/tevent_ntstatus.h"
36
37
38 #undef DBGC_CLASS
39 #define DBGC_CLASS DBGC_RPC_SRV
40
41 static NTSTATUS dcesrv_negotiate_contexts(struct dcesrv_call_state *call,
42                                 const struct dcerpc_bind *b,
43                                 struct dcerpc_ack_ctx *ack_ctx_list);
44
45 /*
46   see if two endpoints match
47 */
48 static bool endpoints_match(const struct dcerpc_binding *ep1,
49                             const struct dcerpc_binding *ep2)
50 {
51         enum dcerpc_transport_t t1;
52         enum dcerpc_transport_t t2;
53         const char *e1;
54         const char *e2;
55
56         t1 = dcerpc_binding_get_transport(ep1);
57         t2 = dcerpc_binding_get_transport(ep2);
58
59         e1 = dcerpc_binding_get_string_option(ep1, "endpoint");
60         e2 = dcerpc_binding_get_string_option(ep2, "endpoint");
61
62         if (t1 != t2) {
63                 return false;
64         }
65
66         if (!e1 || !e2) {
67                 return e1 == e2;
68         }
69
70         if (strcasecmp(e1, e2) != 0) {
71                 return false;
72         }
73
74         return true;
75 }
76
77 /*
78   find an endpoint in the dcesrv_context
79 */
80 _PUBLIC_ NTSTATUS dcesrv_find_endpoint(struct dcesrv_context *dce_ctx,
81                                 const struct dcerpc_binding *ep_description,
82                                 struct dcesrv_endpoint **_out)
83 {
84         struct dcesrv_endpoint *ep = NULL;
85         for (ep=dce_ctx->endpoint_list; ep; ep=ep->next) {
86                 if (endpoints_match(ep->ep_description, ep_description)) {
87                         *_out = ep;
88                         return NT_STATUS_OK;
89                 }
90         }
91         return NT_STATUS_NOT_FOUND;
92 }
93
94 /*
95   find a registered context_id from a bind or alter_context
96 */
97 static struct dcesrv_connection_context *dcesrv_find_context(struct dcesrv_connection *conn,
98                                                              uint16_t context_id)
99 {
100         struct dcesrv_connection_context *c;
101         for (c=conn->contexts;c;c=c->next) {
102                 if (c->context_id == context_id) return c;
103         }
104         return NULL;
105 }
106
107 /*
108   see if a uuid and if_version match to an interface
109 */
110 static bool interface_match(const struct dcesrv_interface *if1,
111                                                         const struct dcesrv_interface *if2)
112 {
113         return (if1->syntax_id.if_version == if2->syntax_id.if_version &&
114                         GUID_equal(&if1->syntax_id.uuid, &if2->syntax_id.uuid));
115 }
116
117 /*
118   find the interface operations on any endpoint with this binding
119 */
120 static const struct dcesrv_interface *find_interface_by_binding(struct dcesrv_context *dce_ctx,
121                                                                 struct dcerpc_binding *binding,
122                                                                 const struct dcesrv_interface *iface)
123 {
124         struct dcesrv_endpoint *ep;
125         for (ep=dce_ctx->endpoint_list; ep; ep=ep->next) {
126                 if (endpoints_match(ep->ep_description, binding)) {
127                         struct dcesrv_if_list *ifl;
128                         for (ifl=ep->interface_list; ifl; ifl=ifl->next) {
129                                 if (interface_match(ifl->iface, iface)) {
130                                         return ifl->iface;
131                                 }
132                         }
133                 }
134         }
135         return NULL;
136 }
137
138 /*
139   see if a uuid and if_version match to an interface
140 */
141 static bool interface_match_by_uuid(const struct dcesrv_interface *iface,
142                                     const struct GUID *uuid, uint32_t if_version)
143 {
144         return (iface->syntax_id.if_version == if_version &&
145                         GUID_equal(&iface->syntax_id.uuid, uuid));
146 }
147
148 /*
149   find the interface operations on an endpoint by uuid
150 */
151 _PUBLIC_ const struct dcesrv_interface *find_interface_by_uuid(const struct dcesrv_endpoint *endpoint,
152                                                       const struct GUID *uuid, uint32_t if_version)
153 {
154         struct dcesrv_if_list *ifl;
155         for (ifl=endpoint->interface_list; ifl; ifl=ifl->next) {
156                 if (interface_match_by_uuid(ifl->iface, uuid, if_version)) {
157                         return ifl->iface;
158                 }
159         }
160         return NULL;
161 }
162
163 /*
164   find the earlier parts of a fragmented call awaiting reassembily
165 */
166 static struct dcesrv_call_state *dcesrv_find_fragmented_call(struct dcesrv_connection *dce_conn, uint32_t call_id)
167 {
168         struct dcesrv_call_state *c;
169         for (c=dce_conn->incoming_fragmented_call_list;c;c=c->next) {
170                 if (c->pkt.call_id == call_id) {
171                         return c;
172                 }
173         }
174         return NULL;
175 }
176
177 /*
178   register an interface on an endpoint
179
180   An endpoint is one unix domain socket (for ncalrpc), one TCP port
181   (for ncacn_ip_tcp) or one (forwarded) named pipe (for ncacn_np).
182
183   Each endpoint can have many interfaces such as netlogon, lsa or
184   samr.  Some have essentially the full set.
185
186   This is driven from the set of interfaces listed in each IDL file
187   via the PIDL generated *__op_init_server() functions.
188 */
189 _PUBLIC_ NTSTATUS dcesrv_interface_register(struct dcesrv_context *dce_ctx,
190                                    const char *ep_name,
191                                    const char *ncacn_np_secondary_endpoint,
192                                    const struct dcesrv_interface *iface,
193                                    const struct security_descriptor *sd)
194 {
195         struct dcesrv_endpoint *ep;
196         struct dcesrv_if_list *ifl;
197         struct dcerpc_binding *binding;
198         struct dcerpc_binding *binding2 = NULL;
199         bool add_ep = false;
200         NTSTATUS status;
201         enum dcerpc_transport_t transport;
202         char *ep_string = NULL;
203         bool use_single_process = true;
204         const char *ep_process_string;
205
206         /*
207          * If we are not using handles, there is no need for force
208          * this service into using a single process.
209          *
210          * However, due to the way we listen for RPC packets, we can
211          * only do this if we have a single service per pipe or TCP
212          * port, so we still force a single combined process for
213          * ncalrpc.
214          */
215         if (iface->flags & DCESRV_INTERFACE_FLAGS_HANDLES_NOT_USED) {
216                 use_single_process = false;
217         }
218
219         status = dcerpc_parse_binding(dce_ctx, ep_name, &binding);
220
221         if (NT_STATUS_IS_ERR(status)) {
222                 DEBUG(0, ("Trouble parsing binding string '%s'\n", ep_name));
223                 return status;
224         }
225
226         transport = dcerpc_binding_get_transport(binding);
227         if (transport == NCACN_IP_TCP) {
228                 int port;
229                 char port_str[6];
230
231                 /*
232                  * First check if there is already a port specified, eg
233                  * for epmapper on ncacn_ip_tcp:[135]
234                  */
235                 const char *endpoint
236                         = dcerpc_binding_get_string_option(binding,
237                                                            "endpoint");
238                 if (endpoint == NULL) {
239                         port = lpcfg_parm_int(dce_ctx->lp_ctx, NULL,
240                                               "rpc server port", iface->name, 0);
241
242                         /*
243                          * For RPC services that are not set to use a single
244                          * process, we do not default to using the 'rpc server
245                          * port' because that would cause a double-bind on
246                          * that port.
247                          */
248                         if (port == 0 && !use_single_process) {
249                                 port = lpcfg_rpc_server_port(dce_ctx->lp_ctx);
250                         }
251                         if (port != 0) {
252                                 snprintf(port_str, sizeof(port_str), "%u", port);
253                                 status = dcerpc_binding_set_string_option(binding,
254                                                                           "endpoint",
255                                                                           port_str);
256                                 if (!NT_STATUS_IS_OK(status)) {
257                                         return status;
258                                 }
259                         }
260                 }
261         }
262
263         if (transport == NCACN_NP && ncacn_np_secondary_endpoint != NULL) {
264                 enum dcerpc_transport_t transport2;
265
266                 status = dcerpc_parse_binding(dce_ctx,
267                                               ncacn_np_secondary_endpoint,
268                                               &binding2);
269                 if (!NT_STATUS_IS_OK(status)) {
270                         DEBUG(0, ("Trouble parsing 2nd binding string '%s'\n",
271                                   ncacn_np_secondary_endpoint));
272                         return status;
273                 }
274
275                 transport2 = dcerpc_binding_get_transport(binding2);
276                 SMB_ASSERT(transport2 == transport);
277         }
278
279         /* see if the interface is already registered on the endpoint */
280         if (find_interface_by_binding(dce_ctx, binding, iface)!=NULL) {
281                 DEBUG(0,("dcesrv_interface_register: interface '%s' already registered on endpoint '%s'\n",
282                          iface->name, ep_name));
283                 return NT_STATUS_OBJECT_NAME_COLLISION;
284         }
285
286         /* check if this endpoint exists
287          */
288         status = dcesrv_find_endpoint(dce_ctx, binding, &ep);
289         if (NT_STATUS_IS_OK(status)) {
290                 /*
291                  * We want a new port on ncacn_ip_tcp for NETLOGON, so
292                  * it can be multi-process.  Other processes can also
293                  * listen on distinct ports, if they have one forced
294                  * in the code above with eg 'rpc server port:drsuapi = 1027'
295                  *
296                  * If we have mulitiple endpoints on port 0, they each
297                  * get an epemeral port (currently by walking up from
298                  * 1024).
299                  *
300                  * Because one endpoint can only have one process
301                  * model, we add a new IP_TCP endpoint for each model.
302                  *
303                  * This works in conjunction with the forced overwrite
304                  * of ep->use_single_process below.
305                  */
306                 if (ep->use_single_process != use_single_process
307                     && transport == NCACN_IP_TCP) {
308                         add_ep = true;
309                 }
310         }
311
312         if (NT_STATUS_EQUAL(status, NT_STATUS_NOT_FOUND) || add_ep) {
313                 ep = talloc_zero(dce_ctx, struct dcesrv_endpoint);
314                 if (!ep) {
315                         return NT_STATUS_NO_MEMORY;
316                 }
317                 ZERO_STRUCTP(ep);
318                 ep->ep_description = talloc_move(ep, &binding);
319                 ep->ep_2nd_description = talloc_move(ep, &binding2);
320                 add_ep = true;
321
322                 /* add mgmt interface */
323                 ifl = talloc_zero(ep, struct dcesrv_if_list);
324                 if (!ifl) {
325                         return NT_STATUS_NO_MEMORY;
326                 }
327
328                 ifl->iface = talloc_memdup(ifl,
329                                            dcesrv_get_mgmt_interface(),
330                                            sizeof(struct dcesrv_interface));
331                 if (ifl->iface == NULL) {
332                         talloc_free(ep);
333                         return NT_STATUS_NO_MEMORY;
334                 }
335
336                 DLIST_ADD(ep->interface_list, ifl);
337         } else if (!NT_STATUS_IS_OK(status)) {
338                 DBG_NOTICE("Failed to find endpoint: %s\n", nt_errstr(status));
339                 return status;
340         }
341
342         /*
343          * By default don't force into a single process, but if any
344          * interface on this endpoint on this service uses handles
345          * (most do), then we must force into single process mode
346          *
347          * By overwriting this each time a new interface is added to
348          * this endpoint, we end up with the most restrictive setting.
349          */
350         if (use_single_process) {
351                 ep->use_single_process = true;
352         }
353
354         /* talloc a new interface list element */
355         ifl = talloc_zero(ep, struct dcesrv_if_list);
356         if (!ifl) {
357                 return NT_STATUS_NO_MEMORY;
358         }
359
360         /* copy the given interface struct to the one on the endpoints interface list */
361         ifl->iface = talloc_memdup(ifl,
362                                    iface,
363                                    sizeof(struct dcesrv_interface));
364         if (ifl->iface == NULL) {
365                 talloc_free(ep);
366                 return NT_STATUS_NO_MEMORY;
367         }
368
369         /* if we have a security descriptor given,
370          * we should see if we can set it up on the endpoint
371          */
372         if (sd != NULL) {
373                 /* if there's currently no security descriptor given on the endpoint
374                  * we try to set it
375                  */
376                 if (ep->sd == NULL) {
377                         ep->sd = security_descriptor_copy(ep, sd);
378                 }
379
380                 /* if now there's no security descriptor given on the endpoint
381                  * something goes wrong, either we failed to copy the security descriptor
382                  * or there was already one on the endpoint
383                  */
384                 if (ep->sd != NULL) {
385                         DEBUG(0,("dcesrv_interface_register: interface '%s' failed to setup a security descriptor\n"
386                                  "                           on endpoint '%s'\n",
387                                 iface->name, ep_name));
388                         if (add_ep) free(ep);
389                         free(ifl);
390                         return NT_STATUS_OBJECT_NAME_COLLISION;
391                 }
392         }
393
394         /* finally add the interface on the endpoint */
395         DLIST_ADD(ep->interface_list, ifl);
396
397         /* if it's a new endpoint add it to the dcesrv_context */
398         if (add_ep) {
399                 DLIST_ADD(dce_ctx->endpoint_list, ep);
400         }
401
402         /* Re-get the string as we may have set a port */
403         ep_string = dcerpc_binding_string(dce_ctx, ep->ep_description);
404
405         if (use_single_process) {
406                 ep_process_string = "single process required";
407         } else {
408                 ep_process_string = "multi process compatible";
409         }
410
411         DBG_INFO("Interface '%s' registered on endpoint '%s' (%s)\n",
412                  iface->name, ep_string, ep_process_string);
413         TALLOC_FREE(ep_string);
414
415         return NT_STATUS_OK;
416 }
417
418 static NTSTATUS dcesrv_session_info_session_key(struct dcesrv_auth *auth,
419                                                 DATA_BLOB *session_key)
420 {
421         if (auth->session_info == NULL) {
422                 return NT_STATUS_NO_USER_SESSION_KEY;
423         }
424
425         if (auth->session_info->session_key.length == 0) {
426                 return NT_STATUS_NO_USER_SESSION_KEY;
427         }
428
429         *session_key = auth->session_info->session_key;
430         return NT_STATUS_OK;
431 }
432
433 static NTSTATUS dcesrv_remote_session_key(struct dcesrv_auth *auth,
434                                           DATA_BLOB *session_key)
435 {
436         if (auth->auth_type != DCERPC_AUTH_TYPE_NONE) {
437                 return NT_STATUS_NO_USER_SESSION_KEY;
438         }
439
440         return dcesrv_session_info_session_key(auth, session_key);
441 }
442
443 static NTSTATUS dcesrv_local_fixed_session_key(struct dcesrv_auth *auth,
444                                                DATA_BLOB *session_key)
445 {
446         return dcerpc_generic_session_key(session_key);
447 }
448
449 /*
450  * Fetch the authentication session key if available.
451  *
452  * This is the key generated by a gensec authentication.
453  *
454  */
455 _PUBLIC_ NTSTATUS dcesrv_auth_session_key(struct dcesrv_call_state *call,
456                                           DATA_BLOB *session_key)
457 {
458         struct dcesrv_auth *auth = call->auth_state;
459         SMB_ASSERT(auth->auth_finished);
460         return dcesrv_session_info_session_key(auth, session_key);
461 }
462
463 /*
464  * Fetch the transport session key if available.
465  * Typically this is the SMB session key
466  * or a fixed key for local transports.
467  *
468  * The key is always truncated to 16 bytes.
469 */
470 _PUBLIC_ NTSTATUS dcesrv_transport_session_key(struct dcesrv_call_state *call,
471                                                DATA_BLOB *session_key)
472 {
473         struct dcesrv_auth *auth = call->auth_state;
474         NTSTATUS status;
475
476         SMB_ASSERT(auth->auth_finished);
477
478         if (auth->session_key_fn == NULL) {
479                 return NT_STATUS_NO_USER_SESSION_KEY;
480         }
481
482         status = auth->session_key_fn(auth, session_key);
483         if (!NT_STATUS_IS_OK(status)) {
484                 return status;
485         }
486
487         session_key->length = MIN(session_key->length, 16);
488
489         return NT_STATUS_OK;
490 }
491
492 static struct dcesrv_auth *dcesrv_auth_create(struct dcesrv_connection *conn)
493 {
494         const struct dcesrv_endpoint *ep = conn->endpoint;
495         enum dcerpc_transport_t transport =
496                 dcerpc_binding_get_transport(ep->ep_description);
497         struct dcesrv_auth *auth = NULL;
498
499         auth = talloc_zero(conn, struct dcesrv_auth);
500         if (auth == NULL) {
501                 return NULL;
502         }
503
504         switch (transport) {
505         case NCACN_NP:
506                 auth->session_key_fn = dcesrv_remote_session_key;
507                 break;
508         case NCALRPC:
509         case NCACN_UNIX_STREAM:
510                 auth->session_key_fn = dcesrv_local_fixed_session_key;
511                 break;
512         default:
513                 /*
514                  * All other's get a NULL pointer, which
515                  * results in NT_STATUS_NO_USER_SESSION_KEY
516                  */
517                 break;
518         }
519
520         return auth;
521 }
522
523 /*
524   connect to a dcerpc endpoint
525 */
526 _PUBLIC_ NTSTATUS dcesrv_endpoint_connect(struct dcesrv_context *dce_ctx,
527                                 TALLOC_CTX *mem_ctx,
528                                 const struct dcesrv_endpoint *ep,
529                                 struct auth_session_info *session_info,
530                                 struct tevent_context *event_ctx,
531                                 uint32_t state_flags,
532                                 struct dcesrv_connection **_p)
533 {
534         struct dcesrv_auth *auth = NULL;
535         struct dcesrv_connection *p;
536
537         if (!session_info) {
538                 return NT_STATUS_ACCESS_DENIED;
539         }
540
541         p = talloc_zero(mem_ctx, struct dcesrv_connection);
542         NT_STATUS_HAVE_NO_MEMORY(p);
543
544         p->dce_ctx = dce_ctx;
545         p->endpoint = ep;
546         p->packet_log_dir = lpcfg_parm_string(dce_ctx->lp_ctx,
547                                               NULL,
548                                               "dcesrv",
549                                               "stubs directory");
550         p->event_ctx = event_ctx;
551         p->state_flags = state_flags;
552         p->allow_bind = true;
553         p->max_recv_frag = 5840;
554         p->max_xmit_frag = 5840;
555         p->max_total_request_size = DCERPC_NCACN_REQUEST_DEFAULT_MAX_SIZE;
556
557         p->support_hdr_signing = lpcfg_parm_bool(dce_ctx->lp_ctx,
558                                                  NULL,
559                                                  "dcesrv",
560                                                  "header signing",
561                                                  true);
562         p->max_auth_states = lpcfg_parm_ulong(dce_ctx->lp_ctx,
563                                               NULL,
564                                               "dcesrv",
565                                               "max auth states",
566                                               2049);
567
568         auth = dcesrv_auth_create(p);
569         if (auth == NULL) {
570                 talloc_free(p);
571                 return NT_STATUS_NO_MEMORY;
572         }
573
574         auth->session_info = talloc_reference(auth, session_info);
575         if (auth->session_info == NULL) {
576                 talloc_free(p);
577                 return NT_STATUS_NO_MEMORY;
578         }
579
580         p->default_auth_state = auth;
581
582         /*
583          * For now we only support NDR32.
584          */
585         p->preferred_transfer = &ndr_transfer_syntax_ndr;
586
587         *_p = p;
588         return NT_STATUS_OK;
589 }
590
591 /*
592   move a call from an existing linked list to the specified list. This
593   prevents bugs where we forget to remove the call from a previous
594   list when moving it.
595  */
596 static void dcesrv_call_set_list(struct dcesrv_call_state *call,
597                                  enum dcesrv_call_list list)
598 {
599         switch (call->list) {
600         case DCESRV_LIST_NONE:
601                 break;
602         case DCESRV_LIST_CALL_LIST:
603                 DLIST_REMOVE(call->conn->call_list, call);
604                 break;
605         case DCESRV_LIST_FRAGMENTED_CALL_LIST:
606                 DLIST_REMOVE(call->conn->incoming_fragmented_call_list, call);
607                 break;
608         case DCESRV_LIST_PENDING_CALL_LIST:
609                 DLIST_REMOVE(call->conn->pending_call_list, call);
610                 break;
611         }
612         call->list = list;
613         switch (list) {
614         case DCESRV_LIST_NONE:
615                 break;
616         case DCESRV_LIST_CALL_LIST:
617                 DLIST_ADD_END(call->conn->call_list, call);
618                 break;
619         case DCESRV_LIST_FRAGMENTED_CALL_LIST:
620                 DLIST_ADD_END(call->conn->incoming_fragmented_call_list, call);
621                 break;
622         case DCESRV_LIST_PENDING_CALL_LIST:
623                 DLIST_ADD_END(call->conn->pending_call_list, call);
624                 break;
625         }
626 }
627
628 static void dcesrv_call_disconnect_after(struct dcesrv_call_state *call,
629                                          const char *reason)
630 {
631         struct dcesrv_auth *a = NULL;
632
633         if (call->conn->terminate != NULL) {
634                 return;
635         }
636
637         call->conn->allow_bind = false;
638         call->conn->allow_alter = false;
639
640         call->conn->default_auth_state->auth_invalid = true;
641
642         for (a = call->conn->auth_states; a != NULL; a = a->next) {
643                 a->auth_invalid = true;
644         }
645
646         call->terminate_reason = talloc_strdup(call, reason);
647         if (call->terminate_reason == NULL) {
648                 call->terminate_reason = __location__;
649         }
650 }
651
652 /*
653   return a dcerpc bind_nak
654 */
655 static NTSTATUS dcesrv_bind_nak(struct dcesrv_call_state *call, uint32_t reason)
656 {
657         struct ncacn_packet pkt;
658         struct dcerpc_bind_nak_version version;
659         struct data_blob_list_item *rep;
660         NTSTATUS status;
661         static const uint8_t _pad[3] = { 0, };
662
663         /*
664          * We add the call to the pending_call_list
665          * in order to defer the termination.
666          */
667         dcesrv_call_disconnect_after(call, "dcesrv_bind_nak");
668
669         /* setup a bind_nak */
670         dcesrv_init_hdr(&pkt, lpcfg_rpc_big_endian(call->conn->dce_ctx->lp_ctx));
671         pkt.auth_length = 0;
672         pkt.call_id = call->pkt.call_id;
673         pkt.ptype = DCERPC_PKT_BIND_NAK;
674         pkt.pfc_flags = DCERPC_PFC_FLAG_FIRST | DCERPC_PFC_FLAG_LAST;
675         pkt.u.bind_nak.reject_reason = reason;
676         version.rpc_vers = 5;
677         version.rpc_vers_minor = 0;
678         pkt.u.bind_nak.num_versions = 1;
679         pkt.u.bind_nak.versions = &version;
680         pkt.u.bind_nak._pad = data_blob_const(_pad, sizeof(_pad));
681
682         rep = talloc_zero(call, struct data_blob_list_item);
683         if (!rep) {
684                 return NT_STATUS_NO_MEMORY;
685         }
686
687         status = dcerpc_ncacn_push_auth(&rep->blob, call, &pkt, NULL);
688         if (!NT_STATUS_IS_OK(status)) {
689                 return status;
690         }
691
692         dcerpc_set_frag_length(&rep->blob, rep->blob.length);
693
694         DLIST_ADD_END(call->replies, rep);
695         dcesrv_call_set_list(call, DCESRV_LIST_CALL_LIST);
696
697         if (call->conn->call_list && call->conn->call_list->replies) {
698                 if (call->conn->transport.report_output_data) {
699                         call->conn->transport.report_output_data(call->conn);
700                 }
701         }
702
703         return NT_STATUS_OK;
704 }
705
706 static NTSTATUS _dcesrv_fault_disconnect_flags(struct dcesrv_call_state *call,
707                                                uint32_t fault_code,
708                                                uint8_t extra_flags,
709                                                const char *func,
710                                                const char *location)
711 {
712         const char *reason = NULL;
713
714         reason = talloc_asprintf(call, "%s:%s: fault=%u (%s) flags=0x%x",
715                                  func, location,
716                                  fault_code,
717                                  dcerpc_errstr(call, fault_code),
718                                  extra_flags);
719         if (reason == NULL) {
720                 reason = location;
721         }
722
723         /*
724          * We add the call to the pending_call_list
725          * in order to defer the termination.
726          */
727
728         dcesrv_call_disconnect_after(call, reason);
729
730         return dcesrv_fault_with_flags(call, fault_code, extra_flags);
731 }
732
733 #define dcesrv_fault_disconnect(call, fault_code) \
734         _dcesrv_fault_disconnect_flags(call, fault_code, \
735                 DCERPC_PFC_FLAG_DID_NOT_EXECUTE, \
736                 __func__, __location__)
737
738 static int dcesrv_connection_context_destructor(struct dcesrv_connection_context *c)
739 {
740         DLIST_REMOVE(c->conn->contexts, c);
741
742         if (c->iface && c->iface->unbind) {
743                 c->iface->unbind(c, c->iface);
744                 c->iface = NULL;
745         }
746
747         return 0;
748 }
749
750 static void dcesrv_prepare_context_auth(struct dcesrv_call_state *dce_call)
751 {
752         struct loadparm_context *lp_ctx = dce_call->conn->dce_ctx->lp_ctx;
753         const struct dcesrv_endpoint *endpoint = dce_call->conn->endpoint;
754         enum dcerpc_transport_t transport =
755                 dcerpc_binding_get_transport(endpoint->ep_description);
756         struct dcesrv_connection_context *context = dce_call->context;
757         const struct dcesrv_interface *iface = context->iface;
758
759         context->min_auth_level = DCERPC_AUTH_LEVEL_NONE;
760
761         if (transport == NCALRPC) {
762                 context->allow_connect = true;
763                 return;
764         }
765
766         /*
767          * allow overwrite per interface
768          * allow dcerpc auth level connect:<interface>
769          */
770         context->allow_connect = lpcfg_allow_dcerpc_auth_level_connect(lp_ctx);
771         context->allow_connect = lpcfg_parm_bool(lp_ctx, NULL,
772                                         "allow dcerpc auth level connect",
773                                         iface->name,
774                                         context->allow_connect);
775 }
776
777 NTSTATUS dcesrv_interface_bind_require_integrity(struct dcesrv_connection_context *context,
778                                                  const struct dcesrv_interface *iface)
779 {
780         /*
781          * For connection oriented DCERPC DCERPC_AUTH_LEVEL_PACKET (4)
782          * has the same behavior as DCERPC_AUTH_LEVEL_INTEGRITY (5).
783          */
784         context->min_auth_level = DCERPC_AUTH_LEVEL_PACKET;
785         return NT_STATUS_OK;
786 }
787
788 NTSTATUS dcesrv_interface_bind_require_privacy(struct dcesrv_connection_context *context,
789                                                const struct dcesrv_interface *iface)
790 {
791         context->min_auth_level = DCERPC_AUTH_LEVEL_PRIVACY;
792         return NT_STATUS_OK;
793 }
794
795 _PUBLIC_ NTSTATUS dcesrv_interface_bind_reject_connect(struct dcesrv_connection_context *context,
796                                                        const struct dcesrv_interface *iface)
797 {
798         struct loadparm_context *lp_ctx = context->conn->dce_ctx->lp_ctx;
799         const struct dcesrv_endpoint *endpoint = context->conn->endpoint;
800         enum dcerpc_transport_t transport =
801                 dcerpc_binding_get_transport(endpoint->ep_description);
802
803         if (transport == NCALRPC) {
804                 context->allow_connect = true;
805                 return NT_STATUS_OK;
806         }
807
808         /*
809          * allow overwrite per interface
810          * allow dcerpc auth level connect:<interface>
811          */
812         context->allow_connect = false;
813         context->allow_connect = lpcfg_parm_bool(lp_ctx, NULL,
814                                         "allow dcerpc auth level connect",
815                                         iface->name,
816                                         context->allow_connect);
817         return NT_STATUS_OK;
818 }
819
820 _PUBLIC_ NTSTATUS dcesrv_interface_bind_allow_connect(struct dcesrv_connection_context *context,
821                                                       const struct dcesrv_interface *iface)
822 {
823         struct loadparm_context *lp_ctx = context->conn->dce_ctx->lp_ctx;
824         const struct dcesrv_endpoint *endpoint = context->conn->endpoint;
825         enum dcerpc_transport_t transport =
826                 dcerpc_binding_get_transport(endpoint->ep_description);
827
828         if (transport == NCALRPC) {
829                 context->allow_connect = true;
830                 return NT_STATUS_OK;
831         }
832
833         /*
834          * allow overwrite per interface
835          * allow dcerpc auth level connect:<interface>
836          */
837         context->allow_connect = true;
838         context->allow_connect = lpcfg_parm_bool(lp_ctx, NULL,
839                                         "allow dcerpc auth level connect",
840                                         iface->name,
841                                         context->allow_connect);
842         return NT_STATUS_OK;
843 }
844
845 struct dcesrv_conn_auth_wait_context {
846         struct tevent_req *req;
847         bool done;
848         NTSTATUS status;
849 };
850
851 struct dcesrv_conn_auth_wait_state {
852         uint8_t dummy;
853 };
854
855 static struct tevent_req *dcesrv_conn_auth_wait_send(TALLOC_CTX *mem_ctx,
856                                                      struct tevent_context *ev,
857                                                      void *private_data)
858 {
859         struct dcesrv_conn_auth_wait_context *auth_wait =
860                 talloc_get_type_abort(private_data,
861                 struct dcesrv_conn_auth_wait_context);
862         struct tevent_req *req = NULL;
863         struct dcesrv_conn_auth_wait_state *state = NULL;
864
865         req = tevent_req_create(mem_ctx, &state,
866                                 struct dcesrv_conn_auth_wait_state);
867         if (req == NULL) {
868                 return NULL;
869         }
870         auth_wait->req = req;
871
872         tevent_req_defer_callback(req, ev);
873
874         if (!auth_wait->done) {
875                 return req;
876         }
877
878         if (tevent_req_nterror(req, auth_wait->status)) {
879                 return tevent_req_post(req, ev);
880         }
881
882         tevent_req_done(req);
883         return tevent_req_post(req, ev);
884 }
885
886 static NTSTATUS dcesrv_conn_auth_wait_recv(struct tevent_req *req)
887 {
888         return tevent_req_simple_recv_ntstatus(req);
889 }
890
891 static NTSTATUS dcesrv_conn_auth_wait_setup(struct dcesrv_connection *conn)
892 {
893         struct dcesrv_conn_auth_wait_context *auth_wait = NULL;
894
895         if (conn->wait_send != NULL) {
896                 return NT_STATUS_INTERNAL_ERROR;
897         }
898
899         auth_wait = talloc_zero(conn, struct dcesrv_conn_auth_wait_context);
900         if (auth_wait == NULL) {
901                 return NT_STATUS_NO_MEMORY;
902         }
903
904         conn->wait_private = auth_wait;
905         conn->wait_send = dcesrv_conn_auth_wait_send;
906         conn->wait_recv = dcesrv_conn_auth_wait_recv;
907         return NT_STATUS_OK;
908 }
909
910 static void dcesrv_conn_auth_wait_finished(struct dcesrv_connection *conn,
911                                            NTSTATUS status)
912 {
913         struct dcesrv_conn_auth_wait_context *auth_wait =
914                 talloc_get_type_abort(conn->wait_private,
915                 struct dcesrv_conn_auth_wait_context);
916
917         auth_wait->done = true;
918         auth_wait->status = status;
919
920         if (auth_wait->req == NULL) {
921                 return;
922         }
923
924         if (tevent_req_nterror(auth_wait->req, status)) {
925                 return;
926         }
927
928         tevent_req_done(auth_wait->req);
929 }
930
931 static NTSTATUS dcesrv_auth_reply(struct dcesrv_call_state *call);
932
933 static void dcesrv_bind_done(struct tevent_req *subreq);
934
935 /*
936   handle a bind request
937 */
938 static NTSTATUS dcesrv_bind(struct dcesrv_call_state *call)
939 {
940         struct dcesrv_connection *conn = call->conn;
941         struct ncacn_packet *pkt = &call->ack_pkt;
942         NTSTATUS status;
943         uint32_t extra_flags = 0;
944         uint16_t max_req = 0;
945         uint16_t max_rep = 0;
946         struct dcerpc_binding *ep_2nd_description = NULL;
947         const char *endpoint = NULL;
948         struct dcesrv_auth *auth = call->auth_state;
949         struct dcerpc_ack_ctx *ack_ctx_list = NULL;
950         struct dcerpc_ack_ctx *ack_features = NULL;
951         struct tevent_req *subreq = NULL;
952         size_t i;
953
954         status = dcerpc_verify_ncacn_packet_header(&call->pkt,
955                         DCERPC_PKT_BIND,
956                         call->pkt.u.bind.auth_info.length,
957                         0, /* required flags */
958                         DCERPC_PFC_FLAG_FIRST |
959                         DCERPC_PFC_FLAG_LAST |
960                         DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN |
961                         0x08 | /* this is not defined, but should be ignored */
962                         DCERPC_PFC_FLAG_CONC_MPX |
963                         DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
964                         DCERPC_PFC_FLAG_MAYBE |
965                         DCERPC_PFC_FLAG_OBJECT_UUID);
966         if (!NT_STATUS_IS_OK(status)) {
967                 return dcesrv_bind_nak(call,
968                         DCERPC_BIND_NAK_REASON_PROTOCOL_VERSION_NOT_SUPPORTED);
969         }
970
971         /* max_recv_frag and max_xmit_frag result always in the same value! */
972         max_req = MIN(call->pkt.u.bind.max_xmit_frag,
973                       call->pkt.u.bind.max_recv_frag);
974         /*
975          * The values are between 2048 and 5840 tested against Windows 2012R2
976          * via ncacn_ip_tcp on port 135.
977          */
978         max_req = MAX(2048, max_req);
979         max_rep = MIN(max_req, call->conn->max_recv_frag);
980         /* They are truncated to an 8 byte boundary. */
981         max_rep &= 0xFFF8;
982
983         /* max_recv_frag and max_xmit_frag result always in the same value! */
984         call->conn->max_recv_frag = max_rep;
985         call->conn->max_xmit_frag = max_rep;
986
987         status = call->conn->dce_ctx->callbacks.assoc_group.find(call);
988         if (!NT_STATUS_IS_OK(status)) {
989                 DBG_NOTICE("Failed to find assoc_group 0x%08x: %s\n",
990                            call->pkt.u.bind.assoc_group_id, nt_errstr(status));
991                 return dcesrv_bind_nak(call, 0);
992         }
993
994         if (call->pkt.u.bind.num_contexts < 1) {
995                 return dcesrv_bind_nak(call, 0);
996         }
997
998         ack_ctx_list = talloc_zero_array(call, struct dcerpc_ack_ctx,
999                                          call->pkt.u.bind.num_contexts);
1000         if (ack_ctx_list == NULL) {
1001                 return dcesrv_bind_nak(call, 0);
1002         }
1003
1004         /*
1005          * Set some sane defaults (required by dcesrv_negotiate_contexts()/
1006          * dcesrv_check_or_create_context()) and do some protocol validation
1007          * and set sane defaults.
1008          */
1009         for (i = 0; i < call->pkt.u.bind.num_contexts; i++) {
1010                 const struct dcerpc_ctx_list *c = &call->pkt.u.bind.ctx_list[i];
1011                 struct dcerpc_ack_ctx *a = &ack_ctx_list[i];
1012                 bool is_feature = false;
1013                 uint64_t features = 0;
1014
1015                 if (c->num_transfer_syntaxes == 0) {
1016                         return dcesrv_bind_nak(call, 0);
1017                 }
1018
1019                 a->result = DCERPC_BIND_ACK_RESULT_PROVIDER_REJECTION;
1020                 a->reason.value = DCERPC_BIND_ACK_REASON_ABSTRACT_SYNTAX_NOT_SUPPORTED;
1021
1022                 /*
1023                  * It's only treated as bind time feature request, if the first
1024                  * transfer_syntax matches, all others are ignored.
1025                  */
1026                 is_feature = dcerpc_extract_bind_time_features(c->transfer_syntaxes[0],
1027                                                                &features);
1028                 if (!is_feature) {
1029                         continue;
1030                 }
1031
1032                 if (ack_features != NULL) {
1033                         /*
1034                          * Only one bind time feature context is allowed.
1035                          */
1036                         return dcesrv_bind_nak(call, 0);
1037                 }
1038                 ack_features = a;
1039
1040                 a->result = DCERPC_BIND_ACK_RESULT_NEGOTIATE_ACK;
1041                 a->reason.negotiate = 0;
1042                 if (features & DCERPC_BIND_TIME_SECURITY_CONTEXT_MULTIPLEXING) {
1043                         if (call->conn->max_auth_states != 0) {
1044                                 a->reason.negotiate |=
1045                                 DCERPC_BIND_TIME_SECURITY_CONTEXT_MULTIPLEXING;
1046                         }
1047                 }
1048                 if (features & DCERPC_BIND_TIME_KEEP_CONNECTION_ON_ORPHAN) {
1049                         a->reason.negotiate |=
1050                                 DCERPC_BIND_TIME_KEEP_CONNECTION_ON_ORPHAN;
1051                 }
1052
1053                 call->conn->assoc_group->bind_time_features = a->reason.negotiate;
1054         }
1055
1056         /*
1057          * Try to negotiate one new presentation context.
1058          *
1059          * Deep in here we locate the iface (by uuid) that the client
1060          * requested, from the list of interfaces on the
1061          * call->conn->endpoint, and call iface->bind() on that iface.
1062          *
1063          * call->conn was set up at the accept() of the socket, and
1064          * call->conn->endpoint has a list of interfaces restricted to
1065          * this port or pipe.
1066          */
1067         status = dcesrv_negotiate_contexts(call, &call->pkt.u.bind, ack_ctx_list);
1068         if (NT_STATUS_EQUAL(status, NT_STATUS_RPC_PROTOCOL_ERROR)) {
1069                 return dcesrv_bind_nak(call, 0);
1070         }
1071         if (!NT_STATUS_IS_OK(status)) {
1072                 return status;
1073         }
1074
1075         /*
1076          * At this point we still don't know which interface (eg
1077          * netlogon, lsa, drsuapi) the caller requested in this bind!
1078          * The most recently added context is available as the first
1079          * element in the linked list at call->conn->contexts, that is
1080          * call->conn->contexts->iface, but they may not have
1081          * requested one at all!
1082          */
1083
1084         if ((call->pkt.pfc_flags & DCERPC_PFC_FLAG_CONC_MPX) &&
1085             (call->state_flags & DCESRV_CALL_STATE_FLAG_MULTIPLEXED)) {
1086                 call->conn->state_flags |= DCESRV_CALL_STATE_FLAG_MULTIPLEXED;
1087                 extra_flags |= DCERPC_PFC_FLAG_CONC_MPX;
1088         }
1089
1090         if (call->state_flags & DCESRV_CALL_STATE_FLAG_PROCESS_PENDING_CALL) {
1091                 call->conn->state_flags |= DCESRV_CALL_STATE_FLAG_PROCESS_PENDING_CALL;
1092         }
1093
1094         /*
1095          * After finding the interface and setting up the NDR
1096          * transport negotiation etc, handle any authentication that
1097          * is being requested.
1098          */
1099         if (!dcesrv_auth_bind(call)) {
1100
1101                 if (auth->auth_level == DCERPC_AUTH_LEVEL_NONE) {
1102                         /*
1103                          * With DCERPC_AUTH_LEVEL_NONE, we get the
1104                          * reject_reason in auth->auth_context_id.
1105                          */
1106                         return dcesrv_bind_nak(call, auth->auth_context_id);
1107                 }
1108
1109                 /*
1110                  * This must a be a temporary failure e.g. talloc or invalid
1111                  * configuration, e.g. no machine account.
1112                  */
1113                 return dcesrv_bind_nak(call,
1114                                 DCERPC_BIND_NAK_REASON_TEMPORARY_CONGESTION);
1115         }
1116
1117         /* setup a bind_ack */
1118         dcesrv_init_hdr(pkt, lpcfg_rpc_big_endian(call->conn->dce_ctx->lp_ctx));
1119         pkt->auth_length = 0;
1120         pkt->call_id = call->pkt.call_id;
1121         pkt->ptype = DCERPC_PKT_BIND_ACK;
1122         pkt->pfc_flags = DCERPC_PFC_FLAG_FIRST | DCERPC_PFC_FLAG_LAST | extra_flags;
1123         pkt->u.bind_ack.max_xmit_frag = call->conn->max_xmit_frag;
1124         pkt->u.bind_ack.max_recv_frag = call->conn->max_recv_frag;
1125         pkt->u.bind_ack.assoc_group_id = call->conn->assoc_group->id;
1126
1127         ep_2nd_description = call->conn->endpoint->ep_2nd_description;
1128         if (ep_2nd_description == NULL) {
1129                 ep_2nd_description = call->conn->endpoint->ep_description;
1130         }
1131
1132         endpoint = dcerpc_binding_get_string_option(
1133                                 ep_2nd_description,
1134                                 "endpoint");
1135         if (endpoint == NULL) {
1136                 endpoint = "";
1137         }
1138
1139         pkt->u.bind_ack.secondary_address = endpoint;
1140         pkt->u.bind_ack.num_results = call->pkt.u.bind.num_contexts;
1141         pkt->u.bind_ack.ctx_list = ack_ctx_list;
1142         pkt->u.bind_ack.auth_info = data_blob_null;
1143
1144         status = dcesrv_auth_prepare_bind_ack(call, pkt);
1145         if (!NT_STATUS_IS_OK(status)) {
1146                 return dcesrv_bind_nak(call, 0);
1147         }
1148
1149         if (auth->auth_finished) {
1150                 return dcesrv_auth_reply(call);
1151         }
1152
1153         subreq = gensec_update_send(call, call->event_ctx,
1154                                     auth->gensec_security,
1155                                     call->in_auth_info.credentials);
1156         if (subreq == NULL) {
1157                 return NT_STATUS_NO_MEMORY;
1158         }
1159         tevent_req_set_callback(subreq, dcesrv_bind_done, call);
1160
1161         return dcesrv_conn_auth_wait_setup(conn);
1162 }
1163
1164 static void dcesrv_bind_done(struct tevent_req *subreq)
1165 {
1166         struct dcesrv_call_state *call =
1167                 tevent_req_callback_data(subreq,
1168                 struct dcesrv_call_state);
1169         struct dcesrv_connection *conn = call->conn;
1170         NTSTATUS status;
1171
1172         status = gensec_update_recv(subreq, call,
1173                                     &call->out_auth_info->credentials);
1174         TALLOC_FREE(subreq);
1175
1176         status = dcesrv_auth_complete(call, status);
1177         if (!NT_STATUS_IS_OK(status)) {
1178                 status = dcesrv_bind_nak(call, 0);
1179                 dcesrv_conn_auth_wait_finished(conn, status);
1180                 return;
1181         }
1182
1183         status = dcesrv_auth_reply(call);
1184         dcesrv_conn_auth_wait_finished(conn, status);
1185         return;
1186 }
1187
1188 static NTSTATUS dcesrv_auth_reply(struct dcesrv_call_state *call)
1189 {
1190         struct ncacn_packet *pkt = &call->ack_pkt;
1191         struct data_blob_list_item *rep = NULL;
1192         NTSTATUS status;
1193
1194         rep = talloc_zero(call, struct data_blob_list_item);
1195         if (!rep) {
1196                 return NT_STATUS_NO_MEMORY;
1197         }
1198
1199         status = dcerpc_ncacn_push_auth(&rep->blob,
1200                                         call,
1201                                         pkt,
1202                                         call->out_auth_info);
1203         if (!NT_STATUS_IS_OK(status)) {
1204                 return status;
1205         }
1206
1207         dcerpc_set_frag_length(&rep->blob, rep->blob.length);
1208
1209         DLIST_ADD_END(call->replies, rep);
1210         dcesrv_call_set_list(call, DCESRV_LIST_CALL_LIST);
1211
1212         if (call->conn->call_list && call->conn->call_list->replies) {
1213                 if (call->conn->transport.report_output_data) {
1214                         call->conn->transport.report_output_data(call->conn);
1215                 }
1216         }
1217
1218         return NT_STATUS_OK;
1219 }
1220
1221
1222 static void dcesrv_auth3_done(struct tevent_req *subreq);
1223
1224 /*
1225   handle a auth3 request
1226 */
1227 static NTSTATUS dcesrv_auth3(struct dcesrv_call_state *call)
1228 {
1229         struct dcesrv_connection *conn = call->conn;
1230         struct dcesrv_auth *auth = call->auth_state;
1231         struct tevent_req *subreq = NULL;
1232         NTSTATUS status;
1233
1234         if (!auth->auth_started) {
1235                 return dcesrv_fault_disconnect(call, DCERPC_NCA_S_PROTO_ERROR);
1236         }
1237
1238         if (auth->auth_finished) {
1239                 return dcesrv_fault_disconnect(call, DCERPC_NCA_S_PROTO_ERROR);
1240         }
1241
1242         status = dcerpc_verify_ncacn_packet_header(&call->pkt,
1243                         DCERPC_PKT_AUTH3,
1244                         call->pkt.u.auth3.auth_info.length,
1245                         0, /* required flags */
1246                         DCERPC_PFC_FLAG_FIRST |
1247                         DCERPC_PFC_FLAG_LAST |
1248                         DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN |
1249                         0x08 | /* this is not defined, but should be ignored */
1250                         DCERPC_PFC_FLAG_CONC_MPX |
1251                         DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
1252                         DCERPC_PFC_FLAG_MAYBE |
1253                         DCERPC_PFC_FLAG_OBJECT_UUID);
1254         if (!NT_STATUS_IS_OK(status)) {
1255                 return dcesrv_fault_disconnect(call, DCERPC_NCA_S_PROTO_ERROR);
1256         }
1257
1258         /* handle the auth3 in the auth code */
1259         if (!dcesrv_auth_prepare_auth3(call)) {
1260                 /*
1261                  * we don't send a reply to a auth3 request,
1262                  * except by a fault.
1263                  *
1264                  * In anycase we mark the connection as
1265                  * invalid.
1266                  */
1267                 auth->auth_invalid = true;
1268                 if (call->fault_code != 0) {
1269                         return dcesrv_fault_disconnect(call, call->fault_code);
1270                 }
1271                 TALLOC_FREE(call);
1272                 return NT_STATUS_OK;
1273         }
1274
1275         subreq = gensec_update_send(call, call->event_ctx,
1276                                     auth->gensec_security,
1277                                     call->in_auth_info.credentials);
1278         if (subreq == NULL) {
1279                 return NT_STATUS_NO_MEMORY;
1280         }
1281         tevent_req_set_callback(subreq, dcesrv_auth3_done, call);
1282
1283         return dcesrv_conn_auth_wait_setup(conn);
1284 }
1285
1286 static void dcesrv_auth3_done(struct tevent_req *subreq)
1287 {
1288         struct dcesrv_call_state *call =
1289                 tevent_req_callback_data(subreq,
1290                 struct dcesrv_call_state);
1291         struct dcesrv_connection *conn = call->conn;
1292         struct dcesrv_auth *auth = call->auth_state;
1293         NTSTATUS status;
1294
1295         status = gensec_update_recv(subreq, call,
1296                                     &call->out_auth_info->credentials);
1297         TALLOC_FREE(subreq);
1298
1299         status = dcesrv_auth_complete(call, status);
1300         if (!NT_STATUS_IS_OK(status)) {
1301                 /*
1302                  * we don't send a reply to a auth3 request,
1303                  * except by a fault.
1304                  *
1305                  * In anycase we mark the connection as
1306                  * invalid.
1307                  */
1308                 auth->auth_invalid = true;
1309                 if (call->fault_code != 0) {
1310                         status = dcesrv_fault_disconnect(call, call->fault_code);
1311                         dcesrv_conn_auth_wait_finished(conn, status);
1312                         return;
1313                 }
1314                 TALLOC_FREE(call);
1315                 dcesrv_conn_auth_wait_finished(conn, NT_STATUS_OK);
1316                 return;
1317         }
1318
1319         /*
1320          * we don't send a reply to a auth3 request.
1321          */
1322         TALLOC_FREE(call);
1323         dcesrv_conn_auth_wait_finished(conn, NT_STATUS_OK);
1324         return;
1325 }
1326
1327
1328 static NTSTATUS dcesrv_check_or_create_context(struct dcesrv_call_state *call,
1329                                 const struct dcerpc_bind *b,
1330                                 const struct dcerpc_ctx_list *ctx,
1331                                 struct dcerpc_ack_ctx *ack,
1332                                 bool validate_only,
1333                                 const struct ndr_syntax_id *supported_transfer)
1334 {
1335         uint32_t if_version;
1336         struct dcesrv_connection_context *context;
1337         const struct dcesrv_interface *iface;
1338         struct GUID uuid;
1339         NTSTATUS status;
1340         const struct ndr_syntax_id *selected_transfer = NULL;
1341         size_t i;
1342         bool ok;
1343
1344         if (b == NULL) {
1345                 return NT_STATUS_INTERNAL_ERROR;
1346         }
1347         if (ctx == NULL) {
1348                 return NT_STATUS_INTERNAL_ERROR;
1349         }
1350         if (ctx->num_transfer_syntaxes < 1) {
1351                 return NT_STATUS_INTERNAL_ERROR;
1352         }
1353         if (ack == NULL) {
1354                 return NT_STATUS_INTERNAL_ERROR;
1355         }
1356         if (supported_transfer == NULL) {
1357                 return NT_STATUS_INTERNAL_ERROR;
1358         }
1359
1360         switch (ack->result) {
1361         case DCERPC_BIND_ACK_RESULT_ACCEPTANCE:
1362         case DCERPC_BIND_ACK_RESULT_NEGOTIATE_ACK:
1363                 /*
1364                  * We is already completed.
1365                  */
1366                 return NT_STATUS_OK;
1367         default:
1368                 break;
1369         }
1370
1371         ack->result = DCERPC_BIND_ACK_RESULT_PROVIDER_REJECTION;
1372         ack->reason.value = DCERPC_BIND_ACK_REASON_ABSTRACT_SYNTAX_NOT_SUPPORTED;
1373
1374         if_version = ctx->abstract_syntax.if_version;
1375         uuid = ctx->abstract_syntax.uuid;
1376
1377         iface = find_interface_by_uuid(call->conn->endpoint, &uuid, if_version);
1378         if (iface == NULL) {
1379                 char *uuid_str = GUID_string(call, &uuid);
1380                 DEBUG(2,("Request for unknown dcerpc interface %s/%d\n", uuid_str, if_version));
1381                 talloc_free(uuid_str);
1382                 /*
1383                  * We report this only via ack->result
1384                  */
1385                 return NT_STATUS_OK;
1386         }
1387
1388         ack->result = DCERPC_BIND_ACK_RESULT_PROVIDER_REJECTION;
1389         ack->reason.value = DCERPC_BIND_ACK_REASON_TRANSFER_SYNTAXES_NOT_SUPPORTED;
1390
1391         if (validate_only) {
1392                 /*
1393                  * We report this only via ack->result
1394                  */
1395                 return NT_STATUS_OK;
1396         }
1397
1398         for (i = 0; i < ctx->num_transfer_syntaxes; i++) {
1399                 /*
1400                  * we only do NDR encoded dcerpc for now.
1401                  */
1402                 ok = ndr_syntax_id_equal(&ctx->transfer_syntaxes[i],
1403                                          supported_transfer);
1404                 if (ok) {
1405                         selected_transfer = supported_transfer;
1406                         break;
1407                 }
1408         }
1409
1410         context = dcesrv_find_context(call->conn, ctx->context_id);
1411         if (context != NULL) {
1412                 ok = ndr_syntax_id_equal(&context->iface->syntax_id,
1413                                          &ctx->abstract_syntax);
1414                 if (!ok) {
1415                         return NT_STATUS_RPC_PROTOCOL_ERROR;
1416                 }
1417
1418                 if (selected_transfer != NULL) {
1419                         ok = ndr_syntax_id_equal(&context->transfer_syntax,
1420                                                  selected_transfer);
1421                         if (!ok) {
1422                                 return NT_STATUS_RPC_PROTOCOL_ERROR;
1423                         }
1424
1425                         ack->result = DCERPC_BIND_ACK_RESULT_ACCEPTANCE;
1426                         ack->reason.value = DCERPC_BIND_ACK_REASON_NOT_SPECIFIED;
1427                         ack->syntax = context->transfer_syntax;
1428                 }
1429
1430                 /*
1431                  * We report this only via ack->result
1432                  */
1433                 return NT_STATUS_OK;
1434         }
1435
1436         if (selected_transfer == NULL) {
1437                 /*
1438                  * We report this only via ack->result
1439                  */
1440                 return NT_STATUS_OK;
1441         }
1442
1443         ack->result = DCERPC_BIND_ACK_RESULT_USER_REJECTION;
1444         ack->reason.value = DCERPC_BIND_ACK_REASON_LOCAL_LIMIT_EXCEEDED;
1445
1446         /* add this context to the list of available context_ids */
1447         context = talloc_zero(call->conn, struct dcesrv_connection_context);
1448         if (context == NULL) {
1449                 return NT_STATUS_NO_MEMORY;
1450         }
1451         context->conn = call->conn;
1452         context->context_id = ctx->context_id;
1453         context->iface = iface;
1454         context->transfer_syntax = *selected_transfer;
1455         DLIST_ADD(call->conn->contexts, context);
1456         call->context = context;
1457         talloc_set_destructor(context, dcesrv_connection_context_destructor);
1458
1459         dcesrv_prepare_context_auth(call);
1460
1461         /*
1462          * Multiplex is supported by default
1463          */
1464         call->state_flags |= DCESRV_CALL_STATE_FLAG_MULTIPLEXED;
1465
1466         status = iface->bind(context, iface);
1467         call->context = NULL;
1468         if (!NT_STATUS_IS_OK(status)) {
1469                 /* we don't want to trigger the iface->unbind() hook */
1470                 context->iface = NULL;
1471                 talloc_free(context);
1472                 /*
1473                  * We report this only via ack->result
1474                  */
1475                 return NT_STATUS_OK;
1476         }
1477
1478         ack->result = DCERPC_BIND_ACK_RESULT_ACCEPTANCE;
1479         ack->reason.value = DCERPC_BIND_ACK_REASON_NOT_SPECIFIED;
1480         ack->syntax = context->transfer_syntax;
1481         return NT_STATUS_OK;
1482 }
1483
1484 static NTSTATUS dcesrv_negotiate_contexts(struct dcesrv_call_state *call,
1485                                 const struct dcerpc_bind *b,
1486                                 struct dcerpc_ack_ctx *ack_ctx_list)
1487 {
1488         NTSTATUS status;
1489         size_t i;
1490         bool validate_only = false;
1491         bool preferred_ndr32;
1492
1493         /*
1494          * Try to negotiate one new presentation context,
1495          * using our preferred transfer syntax.
1496          */
1497         for (i = 0; i < b->num_contexts; i++) {
1498                 const struct dcerpc_ctx_list *c = &b->ctx_list[i];
1499                 struct dcerpc_ack_ctx *a = &ack_ctx_list[i];
1500
1501                 status = dcesrv_check_or_create_context(call, b, c, a,
1502                                                 validate_only,
1503                                                 call->conn->preferred_transfer);
1504                 if (!NT_STATUS_IS_OK(status)) {
1505                         return status;
1506                 }
1507
1508                 if (a->result == DCERPC_BIND_ACK_RESULT_ACCEPTANCE) {
1509                         /*
1510                          * We managed to negotiate one context.
1511                          *
1512                          * => we're done.
1513                          */
1514                         validate_only = true;
1515                 }
1516         }
1517
1518         preferred_ndr32 = ndr_syntax_id_equal(&ndr_transfer_syntax_ndr,
1519                                         call->conn->preferred_transfer);
1520         if (preferred_ndr32) {
1521                 /*
1522                  * We're done.
1523                  */
1524                 return NT_STATUS_OK;
1525         }
1526
1527         /*
1528          * Try to negotiate one new presentation context,
1529          * using NDR 32 as fallback.
1530          */
1531         for (i = 0; i < b->num_contexts; i++) {
1532                 const struct dcerpc_ctx_list *c = &b->ctx_list[i];
1533                 struct dcerpc_ack_ctx *a = &ack_ctx_list[i];
1534
1535                 status = dcesrv_check_or_create_context(call, b, c, a,
1536                                                 validate_only,
1537                                                 &ndr_transfer_syntax_ndr);
1538                 if (!NT_STATUS_IS_OK(status)) {
1539                         return status;
1540                 }
1541
1542                 if (a->result == DCERPC_BIND_ACK_RESULT_ACCEPTANCE) {
1543                         /*
1544                          * We managed to negotiate one context.
1545                          *
1546                          * => we're done.
1547                          */
1548                         validate_only = true;
1549                 }
1550         }
1551
1552         return NT_STATUS_OK;
1553 }
1554
1555 static void dcesrv_alter_done(struct tevent_req *subreq);
1556
1557 /*
1558   handle a alter context request
1559 */
1560 static NTSTATUS dcesrv_alter(struct dcesrv_call_state *call)
1561 {
1562         struct dcesrv_connection *conn = call->conn;
1563         NTSTATUS status;
1564         bool auth_ok = false;
1565         struct ncacn_packet *pkt = &call->ack_pkt;
1566         uint32_t extra_flags = 0;
1567         struct dcesrv_auth *auth = call->auth_state;
1568         struct dcerpc_ack_ctx *ack_ctx_list = NULL;
1569         struct tevent_req *subreq = NULL;
1570         size_t i;
1571
1572         if (!call->conn->allow_alter) {
1573                 return dcesrv_fault_disconnect(call, DCERPC_NCA_S_PROTO_ERROR);
1574         }
1575
1576         status = dcerpc_verify_ncacn_packet_header(&call->pkt,
1577                         DCERPC_PKT_ALTER,
1578                         call->pkt.u.alter.auth_info.length,
1579                         0, /* required flags */
1580                         DCERPC_PFC_FLAG_FIRST |
1581                         DCERPC_PFC_FLAG_LAST |
1582                         DCERPC_PFC_FLAG_SUPPORT_HEADER_SIGN |
1583                         0x08 | /* this is not defined, but should be ignored */
1584                         DCERPC_PFC_FLAG_CONC_MPX |
1585                         DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
1586                         DCERPC_PFC_FLAG_MAYBE |
1587                         DCERPC_PFC_FLAG_OBJECT_UUID);
1588         if (!NT_STATUS_IS_OK(status)) {
1589                 return dcesrv_fault_disconnect(call, DCERPC_NCA_S_PROTO_ERROR);
1590         }
1591
1592         auth_ok = dcesrv_auth_alter(call);
1593         if (!auth_ok) {
1594                 if (call->fault_code != 0) {
1595                         return dcesrv_fault_disconnect(call, call->fault_code);
1596                 }
1597         }
1598
1599         if (call->pkt.u.alter.num_contexts < 1) {
1600                 return dcesrv_fault_disconnect(call, DCERPC_NCA_S_PROTO_ERROR);
1601         }
1602
1603         ack_ctx_list = talloc_zero_array(call, struct dcerpc_ack_ctx,
1604                                          call->pkt.u.alter.num_contexts);
1605         if (ack_ctx_list == NULL) {
1606                 return NT_STATUS_NO_MEMORY;
1607         }
1608
1609         /*
1610          * Set some sane defaults (required by dcesrv_negotiate_contexts()/
1611          * dcesrv_check_or_create_context()) and do some protocol validation
1612          * and set sane defaults.
1613          */
1614         for (i = 0; i < call->pkt.u.alter.num_contexts; i++) {
1615                 const struct dcerpc_ctx_list *c = &call->pkt.u.alter.ctx_list[i];
1616                 struct dcerpc_ack_ctx *a = &ack_ctx_list[i];
1617
1618                 if (c->num_transfer_syntaxes == 0) {
1619                         return dcesrv_fault_disconnect(call,
1620                                         DCERPC_NCA_S_PROTO_ERROR);
1621                 }
1622
1623                 a->result = DCERPC_BIND_ACK_RESULT_PROVIDER_REJECTION;
1624                 a->reason.value = DCERPC_BIND_ACK_REASON_ABSTRACT_SYNTAX_NOT_SUPPORTED;
1625         }
1626
1627         /*
1628          * Try to negotiate one new presentation context.
1629          */
1630         status = dcesrv_negotiate_contexts(call, &call->pkt.u.alter, ack_ctx_list);
1631         if (NT_STATUS_EQUAL(status, NT_STATUS_RPC_PROTOCOL_ERROR)) {
1632                 return dcesrv_fault_disconnect(call, DCERPC_NCA_S_PROTO_ERROR);
1633         }
1634         if (!NT_STATUS_IS_OK(status)) {
1635                 return status;
1636         }
1637
1638         if ((call->pkt.pfc_flags & DCERPC_PFC_FLAG_CONC_MPX) &&
1639             (call->state_flags & DCESRV_CALL_STATE_FLAG_MULTIPLEXED)) {
1640                 call->conn->state_flags |= DCESRV_CALL_STATE_FLAG_MULTIPLEXED;
1641                 extra_flags |= DCERPC_PFC_FLAG_CONC_MPX;
1642         }
1643
1644         if (call->state_flags & DCESRV_CALL_STATE_FLAG_PROCESS_PENDING_CALL) {
1645                 call->conn->state_flags |= DCESRV_CALL_STATE_FLAG_PROCESS_PENDING_CALL;
1646         }
1647
1648         /* handle any authentication that is being requested */
1649         if (!auth_ok) {
1650                 if (call->in_auth_info.auth_type != auth->auth_type) {
1651                         return dcesrv_fault_disconnect(call,
1652                                         DCERPC_FAULT_SEC_PKG_ERROR);
1653                 }
1654                 return dcesrv_fault_disconnect(call, DCERPC_FAULT_ACCESS_DENIED);
1655         }
1656
1657         dcesrv_init_hdr(pkt, lpcfg_rpc_big_endian(call->conn->dce_ctx->lp_ctx));
1658         pkt->auth_length = 0;
1659         pkt->call_id = call->pkt.call_id;
1660         pkt->ptype = DCERPC_PKT_ALTER_RESP;
1661         pkt->pfc_flags = DCERPC_PFC_FLAG_FIRST | DCERPC_PFC_FLAG_LAST | extra_flags;
1662         pkt->u.alter_resp.max_xmit_frag = call->conn->max_xmit_frag;
1663         pkt->u.alter_resp.max_recv_frag = call->conn->max_recv_frag;
1664         pkt->u.alter_resp.assoc_group_id = call->conn->assoc_group->id;
1665         pkt->u.alter_resp.secondary_address = "";
1666         pkt->u.alter_resp.num_results = call->pkt.u.alter.num_contexts;
1667         pkt->u.alter_resp.ctx_list = ack_ctx_list;
1668         pkt->u.alter_resp.auth_info = data_blob_null;
1669
1670         status = dcesrv_auth_prepare_alter_ack(call, pkt);
1671         if (!NT_STATUS_IS_OK(status)) {
1672                 return dcesrv_fault_disconnect(call, DCERPC_FAULT_SEC_PKG_ERROR);
1673         }
1674
1675         if (auth->auth_finished) {
1676                 return dcesrv_auth_reply(call);
1677         }
1678
1679         subreq = gensec_update_send(call, call->event_ctx,
1680                                     auth->gensec_security,
1681                                     call->in_auth_info.credentials);
1682         if (subreq == NULL) {
1683                 return NT_STATUS_NO_MEMORY;
1684         }
1685         tevent_req_set_callback(subreq, dcesrv_alter_done, call);
1686
1687         return dcesrv_conn_auth_wait_setup(conn);
1688 }
1689
1690 static void dcesrv_alter_done(struct tevent_req *subreq)
1691 {
1692         struct dcesrv_call_state *call =
1693                 tevent_req_callback_data(subreq,
1694                 struct dcesrv_call_state);
1695         struct dcesrv_connection *conn = call->conn;
1696         NTSTATUS status;
1697
1698         status = gensec_update_recv(subreq, call,
1699                                     &call->out_auth_info->credentials);
1700         TALLOC_FREE(subreq);
1701
1702         status = dcesrv_auth_complete(call, status);
1703         if (!NT_STATUS_IS_OK(status)) {
1704                 status = dcesrv_fault_disconnect(call, DCERPC_FAULT_SEC_PKG_ERROR);
1705                 dcesrv_conn_auth_wait_finished(conn, status);
1706                 return;
1707         }
1708
1709         status = dcesrv_auth_reply(call);
1710         dcesrv_conn_auth_wait_finished(conn, status);
1711         return;
1712 }
1713
1714 /*
1715   possibly save the call for inspection with ndrdump
1716  */
1717 static void dcesrv_save_call(struct dcesrv_call_state *call, const char *why)
1718 {
1719 #ifdef DEVELOPER
1720         dcerpc_log_packet(call->conn->packet_log_dir,
1721                           call->context->iface->name,
1722                           call->pkt.u.request.opnum,
1723                           NDR_IN,
1724                           &call->pkt.u.request.stub_and_verifier,
1725                           why);
1726 #endif
1727 }
1728
1729 #ifdef DEVELOPER
1730 /*
1731   Save the call for use as a seed for fuzzing.
1732
1733   This is only enabled in a developer build, and only has effect if the
1734   "dcesrv fuzz directory" param is set.
1735 */
1736 void _dcesrv_save_ndr_fuzz_seed(DATA_BLOB call_blob,
1737                                 struct dcesrv_call_state *call,
1738                                 int flags)
1739 {
1740         const char *dump_dir = lpcfg_parm_string(call->conn->dce_ctx->lp_ctx,
1741                                                  NULL,
1742                                                  "dcesrv", "fuzz directory");
1743
1744         dcerpc_save_ndr_fuzz_seed(call,
1745                                   call_blob,
1746                                   dump_dir,
1747                                   call->context->iface->name,
1748                                   flags,
1749                                   call->pkt.u.request.opnum,
1750                                   call->ndr_pull->flags & LIBNDR_FLAG_NDR64);
1751 }
1752 #endif /*if DEVELOPER, enveloping _dcesrv_save_ndr_fuzz_seed() */
1753
1754
1755 static NTSTATUS dcesrv_check_verification_trailer(struct dcesrv_call_state *call)
1756 {
1757         TALLOC_CTX *frame = talloc_stackframe();
1758         const uint32_t bitmask1 = call->conn->client_hdr_signing ?
1759                 DCERPC_SEC_VT_CLIENT_SUPPORTS_HEADER_SIGNING : 0;
1760         const struct dcerpc_sec_vt_pcontext pcontext = {
1761                 .abstract_syntax = call->context->iface->syntax_id,
1762                 .transfer_syntax = call->context->transfer_syntax,
1763         };
1764         const struct dcerpc_sec_vt_header2 header2 =
1765                 dcerpc_sec_vt_header2_from_ncacn_packet(&call->pkt);
1766         enum ndr_err_code ndr_err;
1767         struct dcerpc_sec_verification_trailer *vt = NULL;
1768         NTSTATUS status = NT_STATUS_OK;
1769         bool ok;
1770
1771         SMB_ASSERT(call->pkt.ptype == DCERPC_PKT_REQUEST);
1772
1773         ndr_err = ndr_pop_dcerpc_sec_verification_trailer(call->ndr_pull,
1774                                                           frame, &vt);
1775         if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
1776                 status = ndr_map_error2ntstatus(ndr_err);
1777                 goto done;
1778         }
1779
1780         ok = dcerpc_sec_verification_trailer_check(vt, &bitmask1,
1781                                                    &pcontext, &header2);
1782         if (!ok) {
1783                 status = NT_STATUS_ACCESS_DENIED;
1784                 goto done;
1785         }
1786 done:
1787         TALLOC_FREE(frame);
1788         return status;
1789 }
1790
1791 /*
1792   handle a dcerpc request packet
1793 */
1794 static NTSTATUS dcesrv_request(struct dcesrv_call_state *call)
1795 {
1796         const struct dcesrv_endpoint *endpoint = call->conn->endpoint;
1797         struct dcesrv_auth *auth = call->auth_state;
1798         enum dcerpc_transport_t transport =
1799                 dcerpc_binding_get_transport(endpoint->ep_description);
1800         struct ndr_pull *pull;
1801         NTSTATUS status;
1802
1803         if (!auth->auth_finished) {
1804                 return dcesrv_fault_disconnect(call, DCERPC_NCA_S_PROTO_ERROR);
1805         }
1806
1807         /* if authenticated, and the mech we use can't do async replies, don't use them... */
1808         if (auth->gensec_security != NULL &&
1809             !gensec_have_feature(auth->gensec_security, GENSEC_FEATURE_ASYNC_REPLIES)) {
1810                 call->state_flags &= ~DCESRV_CALL_STATE_FLAG_MAY_ASYNC;
1811         }
1812
1813         if (call->context == NULL) {
1814                 return dcesrv_fault_with_flags(call, DCERPC_NCA_S_UNKNOWN_IF,
1815                                         DCERPC_PFC_FLAG_DID_NOT_EXECUTE);
1816         }
1817
1818         switch (auth->auth_level) {
1819         case DCERPC_AUTH_LEVEL_NONE:
1820         case DCERPC_AUTH_LEVEL_PACKET:
1821         case DCERPC_AUTH_LEVEL_INTEGRITY:
1822         case DCERPC_AUTH_LEVEL_PRIVACY:
1823                 break;
1824         default:
1825                 if (!call->context->allow_connect) {
1826                         char *addr;
1827
1828                         addr = tsocket_address_string(call->conn->remote_address,
1829                                                       call);
1830
1831                         DEBUG(2, ("%s: restrict auth_level_connect access "
1832                                   "to [%s] with auth[type=0x%x,level=0x%x] "
1833                                   "on [%s] from [%s]\n",
1834                                   __func__, call->context->iface->name,
1835                                   auth->auth_type,
1836                                   auth->auth_level,
1837                                   derpc_transport_string_by_transport(transport),
1838                                   addr));
1839                         return dcesrv_fault(call, DCERPC_FAULT_ACCESS_DENIED);
1840                 }
1841                 break;
1842         }
1843
1844         if (auth->auth_level < call->context->min_auth_level) {
1845                 char *addr;
1846
1847                 addr = tsocket_address_string(call->conn->remote_address, call);
1848
1849                 DEBUG(2, ("%s: restrict access by min_auth_level[0x%x] "
1850                           "to [%s] with auth[type=0x%x,level=0x%x] "
1851                           "on [%s] from [%s]\n",
1852                           __func__,
1853                           call->context->min_auth_level,
1854                           call->context->iface->name,
1855                           auth->auth_type,
1856                           auth->auth_level,
1857                           derpc_transport_string_by_transport(transport),
1858                           addr));
1859                 return dcesrv_fault(call, DCERPC_FAULT_ACCESS_DENIED);
1860         }
1861
1862         pull = ndr_pull_init_blob(&call->pkt.u.request.stub_and_verifier, call);
1863         NT_STATUS_HAVE_NO_MEMORY(pull);
1864
1865         pull->flags |= LIBNDR_FLAG_REF_ALLOC;
1866
1867         call->ndr_pull  = pull;
1868
1869         if (!(call->pkt.drep[0] & DCERPC_DREP_LE)) {
1870                 pull->flags |= LIBNDR_FLAG_BIGENDIAN;
1871         }
1872
1873         status = dcesrv_check_verification_trailer(call);
1874         if (!NT_STATUS_IS_OK(status)) {
1875                 uint32_t faultcode = DCERPC_FAULT_OTHER;
1876                 if (NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
1877                         faultcode = DCERPC_FAULT_ACCESS_DENIED;
1878                 }
1879                 DEBUG(10, ("dcesrv_check_verification_trailer failed: %s\n",
1880                            nt_errstr(status)));
1881                 return dcesrv_fault(call, faultcode);
1882         }
1883
1884         /* unravel the NDR for the packet */
1885         status = call->context->iface->ndr_pull(call, call, pull, &call->r);
1886         if (!NT_STATUS_IS_OK(status)) {
1887                 uint8_t extra_flags = 0;
1888                 if (call->fault_code == DCERPC_FAULT_OP_RNG_ERROR) {
1889                         /* we got an unknown call */
1890                         DEBUG(3,(__location__ ": Unknown RPC call %u on %s\n",
1891                                  call->pkt.u.request.opnum,
1892                                  call->context->iface->name));
1893                         dcesrv_save_call(call, "unknown");
1894                         extra_flags |= DCERPC_PFC_FLAG_DID_NOT_EXECUTE;
1895                 } else {
1896                         dcesrv_save_call(call, "pullfail");
1897                 }
1898
1899                 return dcesrv_fault_with_flags(call, call->fault_code, extra_flags);
1900         }
1901
1902         dcesrv_save_ndr_fuzz_seed(call->pkt.u.request.stub_and_verifier,
1903                                   call,
1904                                   NDR_IN);
1905
1906         if (pull->offset != pull->data_size) {
1907                 dcesrv_save_call(call, "extrabytes");
1908                 DEBUG(3,("Warning: %d extra bytes in incoming RPC request\n",
1909                          pull->data_size - pull->offset));
1910         }
1911
1912         /* call the dispatch function */
1913         status = call->context->iface->dispatch(call, call, call->r);
1914         if (!NT_STATUS_IS_OK(status)) {
1915                 DEBUG(5,("dcerpc fault in call %s:%02x - %s\n",
1916                          call->context->iface->name,
1917                          call->pkt.u.request.opnum,
1918                          dcerpc_errstr(pull, call->fault_code)));
1919                 return dcesrv_fault(call, call->fault_code);
1920         }
1921
1922         /* add the call to the pending list */
1923         dcesrv_call_set_list(call, DCESRV_LIST_PENDING_CALL_LIST);
1924
1925         if (call->state_flags & DCESRV_CALL_STATE_FLAG_ASYNC) {
1926                 return NT_STATUS_OK;
1927         }
1928
1929         return dcesrv_reply(call);
1930 }
1931
1932
1933 /*
1934   remove the call from the right list when freed
1935  */
1936 static int dcesrv_call_dequeue(struct dcesrv_call_state *call)
1937 {
1938         dcesrv_call_set_list(call, DCESRV_LIST_NONE);
1939         return 0;
1940 }
1941
1942 _PUBLIC_ const struct tsocket_address *dcesrv_connection_get_local_address(struct dcesrv_connection *conn)
1943 {
1944         return conn->local_address;
1945 }
1946
1947 _PUBLIC_ const struct tsocket_address *dcesrv_connection_get_remote_address(struct dcesrv_connection *conn)
1948 {
1949         return conn->remote_address;
1950 }
1951
1952 /*
1953   process some input to a dcerpc endpoint server.
1954 */
1955 static NTSTATUS dcesrv_process_ncacn_packet(struct dcesrv_connection *dce_conn,
1956                                             struct ncacn_packet *pkt,
1957                                             DATA_BLOB blob)
1958 {
1959         NTSTATUS status;
1960         struct dcesrv_call_state *call;
1961         struct dcesrv_call_state *existing = NULL;
1962         size_t num_auth_ctx = 0;
1963         enum dcerpc_AuthType auth_type = 0;
1964         enum dcerpc_AuthLevel auth_level = 0;
1965         uint32_t auth_context_id = 0;
1966
1967         call = talloc_zero(dce_conn, struct dcesrv_call_state);
1968         if (!call) {
1969                 data_blob_free(&blob);
1970                 talloc_free(pkt);
1971                 return NT_STATUS_NO_MEMORY;
1972         }
1973         call->conn              = dce_conn;
1974         call->event_ctx         = dce_conn->event_ctx;
1975         call->state_flags       = call->conn->state_flags;
1976         call->time              = timeval_current();
1977         call->list              = DCESRV_LIST_NONE;
1978
1979         talloc_steal(call, pkt);
1980         talloc_steal(call, blob.data);
1981         call->pkt = *pkt;
1982
1983         if (dce_conn->max_auth_states == 0) {
1984                 call->auth_state = dce_conn->default_auth_state;
1985         } else if (call->pkt.auth_length == 0) {
1986                 if (call->pkt.ptype == DCERPC_PKT_REQUEST &&
1987                     dce_conn->default_auth_level_connect != NULL)
1988                 {
1989                         call->auth_state = dce_conn->default_auth_level_connect;
1990                 } else {
1991                         call->auth_state = dce_conn->default_auth_state;
1992                 }
1993         }
1994
1995         if (call->auth_state == NULL) {
1996                 struct dcesrv_auth *a = NULL;
1997
1998                 auth_type = dcerpc_get_auth_type(&blob);
1999                 auth_level = dcerpc_get_auth_level(&blob);
2000                 auth_context_id = dcerpc_get_auth_context_id(&blob);
2001
2002                 if (call->pkt.ptype == DCERPC_PKT_REQUEST) {
2003                         dce_conn->default_auth_level_connect = NULL;
2004                         if (auth_level == DCERPC_AUTH_LEVEL_CONNECT) {
2005                                 dce_conn->got_explicit_auth_level_connect = true;
2006                         }
2007                 }
2008
2009                 for (a = dce_conn->auth_states; a != NULL; a = a->next) {
2010                         num_auth_ctx++;
2011
2012                         if (a->auth_type != auth_type) {
2013                                 continue;
2014                         }
2015                         if (a->auth_finished && a->auth_level != auth_level) {
2016                                 continue;
2017                         }
2018                         if (a->auth_context_id != auth_context_id) {
2019                                 continue;
2020                         }
2021
2022                         DLIST_PROMOTE(dce_conn->auth_states, a);
2023                         call->auth_state = a;
2024                         break;
2025                 }
2026         }
2027
2028         if (call->auth_state == NULL) {
2029                 struct dcesrv_auth *a = NULL;
2030
2031                 if (num_auth_ctx >= dce_conn->max_auth_states) {
2032                         return dcesrv_fault_disconnect(call,
2033                                         DCERPC_NCA_S_PROTO_ERROR);
2034                 }
2035
2036                 a = dcesrv_auth_create(dce_conn);
2037                 if (a == NULL) {
2038                         talloc_free(call);
2039                         return NT_STATUS_NO_MEMORY;
2040                 }
2041                 DLIST_ADD(dce_conn->auth_states, a);
2042                 if (call->pkt.ptype == DCERPC_PKT_REQUEST) {
2043                         /*
2044                          * This can never be valid.
2045                          */
2046                         a->auth_invalid = true;
2047                 }
2048                 call->auth_state = a;
2049         }
2050
2051         talloc_set_destructor(call, dcesrv_call_dequeue);
2052
2053         if (call->conn->allow_bind) {
2054                 /*
2055                  * Only one bind is possible per connection
2056                  */
2057                 call->conn->allow_bind = false;
2058                 return dcesrv_bind(call);
2059         }
2060
2061         /* we have to check the signing here, before combining the
2062            pdus */
2063         if (call->pkt.ptype == DCERPC_PKT_REQUEST) {
2064                 dcesrv_default_auth_state_prepare_request(call);
2065
2066                 if (call->auth_state->auth_started &&
2067                     !call->auth_state->auth_finished) {
2068                         return dcesrv_fault_disconnect(call,
2069                                         DCERPC_NCA_S_PROTO_ERROR);
2070                 }
2071
2072                 status = dcerpc_verify_ncacn_packet_header(&call->pkt,
2073                                 DCERPC_PKT_REQUEST,
2074                                 call->pkt.u.request.stub_and_verifier.length,
2075                                 0, /* required_flags */
2076                                 DCERPC_PFC_FLAG_FIRST |
2077                                 DCERPC_PFC_FLAG_LAST |
2078                                 DCERPC_PFC_FLAG_PENDING_CANCEL |
2079                                 0x08 | /* this is not defined, but should be ignored */
2080                                 DCERPC_PFC_FLAG_CONC_MPX |
2081                                 DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
2082                                 DCERPC_PFC_FLAG_MAYBE |
2083                                 DCERPC_PFC_FLAG_OBJECT_UUID);
2084                 if (!NT_STATUS_IS_OK(status)) {
2085                         return dcesrv_fault_disconnect(call,
2086                                         DCERPC_NCA_S_PROTO_ERROR);
2087                 }
2088
2089                 if (call->pkt.frag_length > DCERPC_FRAG_MAX_SIZE) {
2090                         /*
2091                          * We don't use dcesrv_fault_disconnect()
2092                          * here, because we don't want to set
2093                          * DCERPC_PFC_FLAG_DID_NOT_EXECUTE
2094                          *
2095                          * Note that we don't check against the negotiated
2096                          * max_recv_frag, but a hard coded value.
2097                          */
2098                         dcesrv_call_disconnect_after(call,
2099                                 "dcesrv_auth_request - frag_length too large");
2100                         return dcesrv_fault(call,
2101                                         DCERPC_NCA_S_PROTO_ERROR);
2102                 }
2103
2104                 if (call->pkt.pfc_flags & DCERPC_PFC_FLAG_FIRST) {
2105                         if (dce_conn->pending_call_list != NULL) {
2106                                 /*
2107                                  * concurrent requests are only allowed
2108                                  * if DCERPC_PFC_FLAG_CONC_MPX was negotiated.
2109                                  */
2110                                 if (!(dce_conn->state_flags & DCESRV_CALL_STATE_FLAG_MULTIPLEXED)) {
2111                                         dcesrv_call_disconnect_after(call,
2112                                                 "dcesrv_auth_request - "
2113                                                 "existing pending call without CONN_MPX");
2114                                         return dcesrv_fault(call,
2115                                                 DCERPC_NCA_S_PROTO_ERROR);
2116                                 }
2117                         }
2118                         /* only one request is possible in the fragmented list */
2119                         if (dce_conn->incoming_fragmented_call_list != NULL) {
2120                                 if (!(dce_conn->state_flags & DCESRV_CALL_STATE_FLAG_MULTIPLEXED)) {
2121                                         /*
2122                                          * Without DCERPC_PFC_FLAG_CONC_MPX
2123                                          * we need to return the FAULT on the
2124                                          * already existing call.
2125                                          *
2126                                          * This is important to get the
2127                                          * call_id and context_id right.
2128                                          */
2129                                         TALLOC_FREE(call);
2130                                         call = dce_conn->incoming_fragmented_call_list;
2131                                 }
2132                                 dcesrv_call_disconnect_after(call,
2133                                         "dcesrv_auth_request - "
2134                                         "existing fragmented call");
2135                                 return dcesrv_fault(call,
2136                                                 DCERPC_NCA_S_PROTO_ERROR);
2137                         }
2138                         if (call->pkt.pfc_flags & DCERPC_PFC_FLAG_PENDING_CANCEL) {
2139                                 return dcesrv_fault_disconnect(call,
2140                                                 DCERPC_FAULT_NO_CALL_ACTIVE);
2141                         }
2142                         call->context = dcesrv_find_context(call->conn,
2143                                                 call->pkt.u.request.context_id);
2144                         if (call->context == NULL) {
2145                                 return dcesrv_fault_with_flags(call, DCERPC_NCA_S_UNKNOWN_IF,
2146                                         DCERPC_PFC_FLAG_DID_NOT_EXECUTE);
2147                         }
2148                 } else {
2149                         const struct dcerpc_request *nr = &call->pkt.u.request;
2150                         const struct dcerpc_request *er = NULL;
2151                         int cmp;
2152
2153                         existing = dcesrv_find_fragmented_call(dce_conn,
2154                                                         call->pkt.call_id);
2155                         if (existing == NULL) {
2156                                 dcesrv_call_disconnect_after(call,
2157                                         "dcesrv_auth_request - "
2158                                         "no existing fragmented call");
2159                                 return dcesrv_fault(call,
2160                                                 DCERPC_NCA_S_PROTO_ERROR);
2161                         }
2162                         er = &existing->pkt.u.request;
2163
2164                         if (call->pkt.ptype != existing->pkt.ptype) {
2165                                 /* trying to play silly buggers are we? */
2166                                 return dcesrv_fault_disconnect(existing,
2167                                                 DCERPC_NCA_S_PROTO_ERROR);
2168                         }
2169                         cmp = memcmp(call->pkt.drep, existing->pkt.drep,
2170                                      sizeof(pkt->drep));
2171                         if (cmp != 0) {
2172                                 return dcesrv_fault_disconnect(existing,
2173                                                 DCERPC_NCA_S_PROTO_ERROR);
2174                         }
2175                         if (nr->context_id != er->context_id)  {
2176                                 return dcesrv_fault_disconnect(existing,
2177                                                 DCERPC_NCA_S_PROTO_ERROR);
2178                         }
2179                         if (nr->opnum != er->opnum)  {
2180                                 return dcesrv_fault_disconnect(existing,
2181                                                 DCERPC_NCA_S_PROTO_ERROR);
2182                         }
2183                 }
2184         }
2185
2186         if (call->pkt.ptype == DCERPC_PKT_REQUEST) {
2187                 bool ok;
2188                 uint8_t payload_offset = DCERPC_REQUEST_LENGTH;
2189
2190                 if (call->pkt.pfc_flags & DCERPC_PFC_FLAG_OBJECT_UUID) {
2191                         payload_offset += 16;
2192                 }
2193
2194                 ok = dcesrv_auth_pkt_pull(call, &blob,
2195                                           0, /* required_flags */
2196                                           DCERPC_PFC_FLAG_FIRST |
2197                                           DCERPC_PFC_FLAG_LAST |
2198                                           DCERPC_PFC_FLAG_PENDING_CANCEL |
2199                                           0x08 | /* this is not defined, but should be ignored */
2200                                           DCERPC_PFC_FLAG_CONC_MPX |
2201                                           DCERPC_PFC_FLAG_DID_NOT_EXECUTE |
2202                                           DCERPC_PFC_FLAG_MAYBE |
2203                                           DCERPC_PFC_FLAG_OBJECT_UUID,
2204                                           payload_offset,
2205                                           &call->pkt.u.request.stub_and_verifier);
2206                 if (!ok) {
2207                         /*
2208                          * We don't use dcesrv_fault_disconnect()
2209                          * here, because we don't want to set
2210                          * DCERPC_PFC_FLAG_DID_NOT_EXECUTE
2211                          */
2212                         dcesrv_call_disconnect_after(call,
2213                                                 "dcesrv_auth_request - failed");
2214                         if (call->fault_code == 0) {
2215                                 call->fault_code = DCERPC_FAULT_ACCESS_DENIED;
2216                         }
2217                         return dcesrv_fault(call, call->fault_code);
2218                 }
2219         }
2220
2221         /* see if this is a continued packet */
2222         if (existing != NULL) {
2223                 struct dcerpc_request *er = &existing->pkt.u.request;
2224                 const struct dcerpc_request *nr = &call->pkt.u.request;
2225                 size_t available;
2226                 size_t alloc_size;
2227                 size_t alloc_hint;
2228
2229                 /*
2230                  * Up to 4 MByte are allowed by all fragments
2231                  */
2232                 available = dce_conn->max_total_request_size;
2233                 if (er->stub_and_verifier.length > available) {
2234                         dcesrv_call_disconnect_after(existing,
2235                                 "dcesrv_auth_request - existing payload too large");
2236                         return dcesrv_fault(existing, DCERPC_FAULT_ACCESS_DENIED);
2237                 }
2238                 available -= er->stub_and_verifier.length;
2239                 if (nr->alloc_hint > available) {
2240                         dcesrv_call_disconnect_after(existing,
2241                                 "dcesrv_auth_request - alloc hint too large");
2242                         return dcesrv_fault(existing, DCERPC_FAULT_ACCESS_DENIED);
2243                 }
2244                 if (nr->stub_and_verifier.length > available) {
2245                         dcesrv_call_disconnect_after(existing,
2246                                 "dcesrv_auth_request - new payload too large");
2247                         return dcesrv_fault(existing, DCERPC_FAULT_ACCESS_DENIED);
2248                 }
2249                 alloc_hint = er->stub_and_verifier.length + nr->alloc_hint;
2250                 /* allocate at least 1 byte */
2251                 alloc_hint = MAX(alloc_hint, 1);
2252                 alloc_size = er->stub_and_verifier.length +
2253                              nr->stub_and_verifier.length;
2254                 alloc_size = MAX(alloc_size, alloc_hint);
2255
2256                 er->stub_and_verifier.data =
2257                         talloc_realloc(existing,
2258                                        er->stub_and_verifier.data,
2259                                        uint8_t, alloc_size);
2260                 if (er->stub_and_verifier.data == NULL) {
2261                         TALLOC_FREE(call);
2262                         return dcesrv_fault_with_flags(existing,
2263                                                        DCERPC_FAULT_OUT_OF_RESOURCES,
2264                                                        DCERPC_PFC_FLAG_DID_NOT_EXECUTE);
2265                 }
2266                 memcpy(er->stub_and_verifier.data +
2267                        er->stub_and_verifier.length,
2268                        nr->stub_and_verifier.data,
2269                        nr->stub_and_verifier.length);
2270                 er->stub_and_verifier.length += nr->stub_and_verifier.length;
2271
2272                 existing->pkt.pfc_flags |= (call->pkt.pfc_flags & DCERPC_PFC_FLAG_LAST);
2273
2274                 TALLOC_FREE(call);
2275                 call = existing;
2276         }
2277
2278         /* this may not be the last pdu in the chain - if its isn't then
2279            just put it on the incoming_fragmented_call_list and wait for the rest */
2280         if (call->pkt.ptype == DCERPC_PKT_REQUEST &&
2281             !(call->pkt.pfc_flags & DCERPC_PFC_FLAG_LAST)) {
2282                 /*
2283                  * Up to 4 MByte are allowed by all fragments
2284                  */
2285                 if (call->pkt.u.request.alloc_hint > dce_conn->max_total_request_size) {
2286                         dcesrv_call_disconnect_after(call,
2287                                 "dcesrv_auth_request - initial alloc hint too large");
2288                         return dcesrv_fault(call, DCERPC_FAULT_ACCESS_DENIED);
2289                 }
2290                 dcesrv_call_set_list(call, DCESRV_LIST_FRAGMENTED_CALL_LIST);
2291                 return NT_STATUS_OK;
2292         }
2293
2294         /* This removes any fragments we may have had stashed away */
2295         dcesrv_call_set_list(call, DCESRV_LIST_NONE);
2296
2297         switch (call->pkt.ptype) {
2298         case DCERPC_PKT_BIND:
2299                 status = dcesrv_bind_nak(call,
2300                         DCERPC_BIND_NAK_REASON_NOT_SPECIFIED);
2301                 break;
2302         case DCERPC_PKT_AUTH3:
2303                 status = dcesrv_auth3(call);
2304                 break;
2305         case DCERPC_PKT_ALTER:
2306                 status = dcesrv_alter(call);
2307                 break;
2308         case DCERPC_PKT_REQUEST:
2309                 status = dcesrv_request(call);
2310                 break;
2311         case DCERPC_PKT_CO_CANCEL:
2312         case DCERPC_PKT_ORPHANED:
2313                 /*
2314                  * Window just ignores CO_CANCEL and ORPHANED,
2315                  * so we do...
2316                  */
2317                 status = NT_STATUS_OK;
2318                 TALLOC_FREE(call);
2319                 break;
2320         case DCERPC_PKT_BIND_ACK:
2321         case DCERPC_PKT_BIND_NAK:
2322         case DCERPC_PKT_ALTER_RESP:
2323         case DCERPC_PKT_RESPONSE:
2324         case DCERPC_PKT_FAULT:
2325         case DCERPC_PKT_SHUTDOWN:
2326         default:
2327                 status = dcesrv_fault_disconnect(call, DCERPC_NCA_S_PROTO_ERROR);
2328                 break;
2329         }
2330
2331         /* if we are going to be sending a reply then add
2332            it to the list of pending calls. We add it to the end to keep the call
2333            list in the order we will answer */
2334         if (!NT_STATUS_IS_OK(status)) {
2335                 talloc_free(call);
2336         }
2337
2338         return status;
2339 }
2340
2341 _PUBLIC_ NTSTATUS dcesrv_init_context(TALLOC_CTX *mem_ctx,
2342                                       struct loadparm_context *lp_ctx,
2343                                       struct dcesrv_context_callbacks *cb,
2344                                       struct dcesrv_context **_dce_ctx)
2345 {
2346         struct dcesrv_context *dce_ctx;
2347
2348         dce_ctx = talloc_zero(mem_ctx, struct dcesrv_context);
2349         NT_STATUS_HAVE_NO_MEMORY(dce_ctx);
2350
2351         if (uid_wrapper_enabled()) {
2352                 setenv("UID_WRAPPER_MYUID", "1", 1);
2353         }
2354         dce_ctx->initial_euid = geteuid();
2355         if (uid_wrapper_enabled()) {
2356                 unsetenv("UID_WRAPPER_MYUID");
2357         }
2358
2359         dce_ctx->endpoint_list  = NULL;
2360         dce_ctx->lp_ctx = lp_ctx;
2361         dce_ctx->assoc_groups_idr = idr_init(dce_ctx);
2362         NT_STATUS_HAVE_NO_MEMORY(dce_ctx->assoc_groups_idr);
2363         dce_ctx->broken_connections = NULL;
2364         if (cb != NULL) {
2365                 dce_ctx->callbacks = *cb;
2366         }
2367
2368         *_dce_ctx = dce_ctx;
2369         return NT_STATUS_OK;
2370 }
2371
2372 _PUBLIC_ NTSTATUS dcesrv_reinit_context(struct dcesrv_context *dce_ctx)
2373 {
2374         NTSTATUS status;
2375
2376         status = dcesrv_shutdown_registered_ep_servers(dce_ctx);
2377         if (!NT_STATUS_IS_OK(status)) {
2378                 return status;
2379         }
2380
2381         /* Clear endpoints */
2382         while (dce_ctx->endpoint_list != NULL) {
2383                 struct dcesrv_endpoint *e = dce_ctx->endpoint_list;
2384                 DLIST_REMOVE(dce_ctx->endpoint_list, e);
2385                 TALLOC_FREE(e);
2386         }
2387
2388         /* Remove broken connections */
2389         dcesrv_cleanup_broken_connections(dce_ctx);
2390
2391         /* Reinit assoc group idr */
2392         TALLOC_FREE(dce_ctx->assoc_groups_idr);
2393         dce_ctx->assoc_groups_idr = idr_init(dce_ctx);
2394         if (dce_ctx->assoc_groups_idr == NULL) {
2395                 return NT_STATUS_NO_MEMORY;
2396         }
2397
2398         return NT_STATUS_OK;
2399 }
2400
2401 _PUBLIC_ NTSTATUS dcesrv_init_ep_servers(struct dcesrv_context *dce_ctx,
2402                                          const char **endpoint_servers)
2403 {
2404         NTSTATUS status;
2405         int i;
2406
2407         if (endpoint_servers == NULL) {
2408                 DBG_ERR("No endpoint servers configured\n");
2409                 return NT_STATUS_INTERNAL_ERROR;
2410         }
2411
2412         for (i=0;endpoint_servers[i];i++) {
2413                 status = dcesrv_init_ep_server(dce_ctx, endpoint_servers[i]);
2414                 if (!NT_STATUS_IS_OK(status)) {
2415                         DBG_ERR("failed to init endpoint server = '%s': %s\n",
2416                                 endpoint_servers[i], nt_errstr(status));
2417                         return status;
2418                 }
2419         }
2420
2421         return NT_STATUS_OK;
2422 }
2423
2424 /* the list of currently registered DCERPC endpoint servers.
2425  */
2426 static struct ep_server {
2427         struct dcesrv_endpoint_server *ep_server;
2428 } *ep_servers = NULL;
2429 static int num_ep_servers = 0;
2430
2431 _PUBLIC_ NTSTATUS dcesrv_init_registered_ep_servers(
2432                                         struct dcesrv_context *dce_ctx)
2433 {
2434         NTSTATUS status;
2435         int i;
2436
2437         for (i = 0; i < num_ep_servers; i++) {
2438                 status = dcesrv_init_ep_server(dce_ctx,
2439                                                ep_servers[i].ep_server->name);
2440                 if (!NT_STATUS_IS_OK(status)) {
2441                         return status;
2442                 }
2443         }
2444
2445         return NT_STATUS_OK;
2446 }
2447
2448 _PUBLIC_ NTSTATUS dcesrv_init_ep_server(struct dcesrv_context *dce_ctx,
2449                                         const char *ep_server_name)
2450 {
2451         struct dcesrv_endpoint_server *ep_server = NULL;
2452         NTSTATUS status;
2453
2454         ep_server = discard_const_p(struct dcesrv_endpoint_server,
2455                                     dcesrv_ep_server_byname(ep_server_name));
2456         if (ep_server == NULL) {
2457                 DBG_ERR("Failed to find endpoint server '%s'\n",
2458                         ep_server_name);
2459                 return NT_STATUS_INTERNAL_ERROR;
2460         }
2461
2462         if (ep_server->initialized) {
2463                 return NT_STATUS_OK;
2464         }
2465
2466         status = ep_server->init_server(dce_ctx, ep_server);
2467         if (!NT_STATUS_IS_OK(status)) {
2468                 DBG_ERR("Failed to init endpoint server '%s': %s\n",
2469                         ep_server_name, nt_errstr(status));
2470                 return status;
2471         }
2472
2473         ep_server->initialized = true;
2474
2475         return NT_STATUS_OK;
2476 }
2477
2478 _PUBLIC_ NTSTATUS dcesrv_shutdown_registered_ep_servers(
2479                                         struct dcesrv_context *dce_ctx)
2480 {
2481         NTSTATUS status;
2482         int i;
2483
2484         for (i = 0; i < num_ep_servers; i++) {
2485                 status = dcesrv_shutdown_ep_server(dce_ctx,
2486                                         ep_servers[i].ep_server->name);
2487                 if (!NT_STATUS_IS_OK(status)) {
2488                         return status;
2489                 }
2490         }
2491
2492         return NT_STATUS_OK;
2493 }
2494
2495 _PUBLIC_ NTSTATUS dcesrv_shutdown_ep_server(struct dcesrv_context *dce_ctx,
2496                                             const char *ep_server_name)
2497 {
2498         struct dcesrv_endpoint_server *ep_server = NULL;
2499         NTSTATUS status;
2500
2501         ep_server = discard_const_p(struct dcesrv_endpoint_server,
2502                                     dcesrv_ep_server_byname(ep_server_name));
2503         if (ep_server == NULL) {
2504                 DBG_ERR("Failed to find endpoint server '%s'\n",
2505                         ep_server_name);
2506                 return NT_STATUS_INTERNAL_ERROR;
2507         }
2508
2509         if (!ep_server->initialized) {
2510                 return NT_STATUS_OK;
2511         }
2512
2513         DBG_INFO("Shutting down DCE/RPC endpoint server '%s'\n",
2514                  ep_server_name);
2515
2516         status = ep_server->shutdown_server(dce_ctx, ep_server);
2517         if (!NT_STATUS_IS_OK(status)) {
2518                 DBG_ERR("Failed to shutdown endpoint server '%s': %s\n",
2519                         ep_server_name, nt_errstr(status));
2520                 return status;
2521         }
2522
2523         ep_server->initialized = false;
2524
2525         return NT_STATUS_OK;
2526 }
2527
2528 /*
2529   register a DCERPC endpoint server.
2530
2531   The 'name' can be later used by other backends to find the operations
2532   structure for this backend.
2533
2534 */
2535 _PUBLIC_ NTSTATUS dcerpc_register_ep_server(const struct dcesrv_endpoint_server *ep_server)
2536 {
2537
2538         if (dcesrv_ep_server_byname(ep_server->name) != NULL) {
2539                 /* its already registered! */
2540                 DEBUG(0,("DCERPC endpoint server '%s' already registered\n",
2541                          ep_server->name));
2542                 return NT_STATUS_OBJECT_NAME_COLLISION;
2543         }
2544
2545         ep_servers = realloc_p(ep_servers, struct ep_server, num_ep_servers+1);
2546         if (!ep_servers) {
2547                 smb_panic("out of memory in dcerpc_register");
2548         }
2549
2550         ep_servers[num_ep_servers].ep_server = smb_xmemdup(ep_server, sizeof(*ep_server));
2551         ep_servers[num_ep_servers].ep_server->name = smb_xstrdup(ep_server->name);
2552
2553         num_ep_servers++;
2554
2555         DEBUG(3,("DCERPC endpoint server '%s' registered\n",
2556                  ep_server->name));
2557
2558         return NT_STATUS_OK;
2559 }
2560
2561 /*
2562   return the operations structure for a named backend of the specified type
2563 */
2564 _PUBLIC_ const struct dcesrv_endpoint_server *dcesrv_ep_server_byname(const char *name)
2565 {
2566         int i;
2567
2568         for (i=0;i<num_ep_servers;i++) {
2569                 if (strcmp(ep_servers[i].ep_server->name, name) == 0) {
2570                         return ep_servers[i].ep_server;
2571                 }
2572         }
2573
2574         return NULL;
2575 }
2576
2577 /*
2578   return the DCERPC module version, and the size of some critical types
2579   This can be used by endpoint server modules to either detect compilation errors, or provide
2580   multiple implementations for different smbd compilation options in one module
2581 */
2582 const struct dcesrv_critical_sizes *dcerpc_module_version(void)
2583 {
2584         static const struct dcesrv_critical_sizes critical_sizes = {
2585                 DCERPC_MODULE_VERSION,
2586                 sizeof(struct dcesrv_context),
2587                 sizeof(struct dcesrv_endpoint),
2588                 sizeof(struct dcesrv_endpoint_server),
2589                 sizeof(struct dcesrv_interface),
2590                 sizeof(struct dcesrv_if_list),
2591                 sizeof(struct dcesrv_connection),
2592                 sizeof(struct dcesrv_call_state),
2593                 sizeof(struct dcesrv_auth),
2594                 sizeof(struct dcesrv_handle)
2595         };
2596
2597         return &critical_sizes;
2598 }
2599
2600 _PUBLIC_ void dcesrv_terminate_connection(struct dcesrv_connection *dce_conn, const char *reason)
2601 {
2602         struct dcesrv_context *dce_ctx = dce_conn->dce_ctx;
2603         struct dcesrv_auth *a = NULL;
2604
2605         dce_conn->wait_send = NULL;
2606         dce_conn->wait_recv = NULL;
2607         dce_conn->wait_private = NULL;
2608
2609         dce_conn->allow_bind = false;
2610         dce_conn->allow_alter = false;
2611
2612         dce_conn->default_auth_state->auth_invalid = true;
2613
2614         for (a = dce_conn->auth_states; a != NULL; a = a->next) {
2615                 a->auth_invalid = true;
2616         }
2617
2618         if (dce_conn->pending_call_list == NULL) {
2619                 char *full_reason = talloc_asprintf(dce_conn, "dcesrv: %s", reason);
2620
2621                 DLIST_REMOVE(dce_ctx->broken_connections, dce_conn);
2622                 dce_conn->transport.terminate_connection(dce_conn,
2623                                         full_reason ? full_reason : reason);
2624                 return;
2625         }
2626
2627         if (dce_conn->terminate != NULL) {
2628                 return;
2629         }
2630
2631         DEBUG(3,("dcesrv: terminating connection due to '%s' deferred due to pending calls\n",
2632                  reason));
2633         dce_conn->terminate = talloc_strdup(dce_conn, reason);
2634         if (dce_conn->terminate == NULL) {
2635                 dce_conn->terminate = "dcesrv: deferred terminating connection - no memory";
2636         }
2637         DLIST_ADD_END(dce_ctx->broken_connections, dce_conn);
2638 }
2639
2640 _PUBLIC_ void dcesrv_cleanup_broken_connections(struct dcesrv_context *dce_ctx)
2641 {
2642         struct dcesrv_connection *cur, *next;
2643
2644         next = dce_ctx->broken_connections;
2645         while (next != NULL) {
2646                 cur = next;
2647                 next = cur->next;
2648
2649                 if (cur->state_flags & DCESRV_CALL_STATE_FLAG_PROCESS_PENDING_CALL) {
2650                         struct dcesrv_connection_context *context_cur, *context_next;
2651
2652                         context_next = cur->contexts;
2653                         while (context_next != NULL) {
2654                                 context_cur = context_next;
2655                                 context_next = context_cur->next;
2656
2657                                 dcesrv_connection_context_destructor(context_cur);
2658                         }
2659                 }
2660
2661                 dcesrv_terminate_connection(cur, cur->terminate);
2662         }
2663 }
2664
2665 /* We need this include to be able to compile on some plateforms
2666  * (ie. freebsd 7.2) as it seems that <sys/uio.h> is not included
2667  * correctly.
2668  * It has to be that deep because otherwise we have a conflict on
2669  * const struct dcesrv_interface declaration.
2670  * This is mostly due to socket_wrapper defining #define bind swrap_bind
2671  * which conflict with the bind used before.
2672  */
2673 #include "system/network.h"
2674
2675 struct dcesrv_sock_reply_state {
2676         struct dcesrv_connection *dce_conn;
2677         struct dcesrv_call_state *call;
2678         struct iovec iov;
2679 };
2680
2681 static void dcesrv_sock_reply_done(struct tevent_req *subreq);
2682 static void dcesrv_call_terminate_step1(struct tevent_req *subreq);
2683
2684 _PUBLIC_ void dcesrv_sock_report_output_data(struct dcesrv_connection *dce_conn)
2685 {
2686         struct dcesrv_call_state *call;
2687
2688         call = dce_conn->call_list;
2689         if (!call || !call->replies) {
2690                 return;
2691         }
2692
2693         while (call->replies) {
2694                 struct data_blob_list_item *rep = call->replies;
2695                 struct dcesrv_sock_reply_state *substate;
2696                 struct tevent_req *subreq;
2697
2698                 substate = talloc_zero(call, struct dcesrv_sock_reply_state);
2699                 if (!substate) {
2700                         dcesrv_terminate_connection(dce_conn, "no memory");
2701                         return;
2702                 }
2703
2704                 substate->dce_conn = dce_conn;
2705                 substate->call = NULL;
2706
2707                 DLIST_REMOVE(call->replies, rep);
2708
2709                 if (call->replies == NULL && call->terminate_reason == NULL) {
2710                         substate->call = call;
2711                 }
2712
2713                 substate->iov.iov_base = (void *) rep->blob.data;
2714                 substate->iov.iov_len = rep->blob.length;
2715
2716                 subreq = tstream_writev_queue_send(substate,
2717                                                    dce_conn->event_ctx,
2718                                                    dce_conn->stream,
2719                                                    dce_conn->send_queue,
2720                                                    &substate->iov, 1);
2721                 if (!subreq) {
2722                         dcesrv_terminate_connection(dce_conn, "no memory");
2723                         return;
2724                 }
2725                 tevent_req_set_callback(subreq, dcesrv_sock_reply_done,
2726                                         substate);
2727         }
2728
2729         if (call->terminate_reason != NULL) {
2730                 struct tevent_req *subreq;
2731
2732                 subreq = tevent_queue_wait_send(call,
2733                                                 dce_conn->event_ctx,
2734                                                 dce_conn->send_queue);
2735                 if (!subreq) {
2736                         dcesrv_terminate_connection(dce_conn, __location__);
2737                         return;
2738                 }
2739                 tevent_req_set_callback(subreq, dcesrv_call_terminate_step1,
2740                                         call);
2741         }
2742
2743         DLIST_REMOVE(call->conn->call_list, call);
2744         call->list = DCESRV_LIST_NONE;
2745 }
2746
2747 static void dcesrv_sock_reply_done(struct tevent_req *subreq)
2748 {
2749         struct dcesrv_sock_reply_state *substate = tevent_req_callback_data(subreq,
2750                                                 struct dcesrv_sock_reply_state);
2751         int ret;
2752         int sys_errno;
2753         NTSTATUS status;
2754         struct dcesrv_call_state *call = substate->call;
2755
2756         ret = tstream_writev_queue_recv(subreq, &sys_errno);
2757         TALLOC_FREE(subreq);
2758         if (ret == -1) {
2759                 status = map_nt_error_from_unix_common(sys_errno);
2760                 dcesrv_terminate_connection(substate->dce_conn, nt_errstr(status));
2761                 return;
2762         }
2763
2764         talloc_free(substate);
2765         if (call) {
2766                 talloc_free(call);
2767         }
2768 }
2769
2770 static void dcesrv_call_terminate_step2(struct tevent_req *subreq);
2771
2772 static void dcesrv_call_terminate_step1(struct tevent_req *subreq)
2773 {
2774         struct dcesrv_call_state *call = tevent_req_callback_data(subreq,
2775                                                 struct dcesrv_call_state);
2776         bool ok;
2777         struct timeval tv;
2778
2779         /* make sure we stop send queue before removing subreq */
2780         tevent_queue_stop(call->conn->send_queue);
2781
2782         ok = tevent_queue_wait_recv(subreq);
2783         TALLOC_FREE(subreq);
2784         if (!ok) {
2785                 dcesrv_terminate_connection(call->conn, __location__);
2786                 return;
2787         }
2788
2789         /* disconnect after 200 usecs */
2790         tv = timeval_current_ofs_usec(200);
2791         subreq = tevent_wakeup_send(call, call->conn->event_ctx, tv);
2792         if (subreq == NULL) {
2793                 dcesrv_terminate_connection(call->conn, __location__);
2794                 return;
2795         }
2796         tevent_req_set_callback(subreq, dcesrv_call_terminate_step2,
2797                                 call);
2798 }
2799
2800 static void dcesrv_call_terminate_step2(struct tevent_req *subreq)
2801 {
2802         struct dcesrv_call_state *call = tevent_req_callback_data(subreq,
2803                                                 struct dcesrv_call_state);
2804         bool ok;
2805
2806         ok = tevent_wakeup_recv(subreq);
2807         TALLOC_FREE(subreq);
2808         if (!ok) {
2809                 dcesrv_terminate_connection(call->conn, __location__);
2810                 return;
2811         }
2812
2813         dcesrv_terminate_connection(call->conn, call->terminate_reason);
2814 }
2815
2816 static void dcesrv_conn_wait_done(struct tevent_req *subreq);
2817
2818 static void dcesrv_read_fragment_done(struct tevent_req *subreq)
2819 {
2820         struct dcesrv_connection *dce_conn = tevent_req_callback_data(subreq,
2821                                              struct dcesrv_connection);
2822         struct dcesrv_context *dce_ctx = dce_conn->dce_ctx;
2823         struct ncacn_packet *pkt;
2824         DATA_BLOB buffer;
2825         NTSTATUS status;
2826
2827         if (dce_conn->terminate) {
2828                 /*
2829                  * if the current connection is broken
2830                  * we need to clean it up before any other connection
2831                  */
2832                 dcesrv_terminate_connection(dce_conn, dce_conn->terminate);
2833                 dcesrv_cleanup_broken_connections(dce_ctx);
2834                 return;
2835         }
2836
2837         dcesrv_cleanup_broken_connections(dce_ctx);
2838
2839         status = dcerpc_read_ncacn_packet_recv(subreq, dce_conn,
2840                                                &pkt, &buffer);
2841         TALLOC_FREE(subreq);
2842         if (!NT_STATUS_IS_OK(status)) {
2843                 dcesrv_terminate_connection(dce_conn, nt_errstr(status));
2844                 return;
2845         }
2846
2847         status = dcesrv_process_ncacn_packet(dce_conn, pkt, buffer);
2848         if (!NT_STATUS_IS_OK(status)) {
2849                 dcesrv_terminate_connection(dce_conn, nt_errstr(status));
2850                 return;
2851         }
2852
2853         /*
2854          * This is used to block the connection during
2855          * pending authentication.
2856          */
2857         if (dce_conn->wait_send != NULL) {
2858                 subreq = dce_conn->wait_send(dce_conn,
2859                                              dce_conn->event_ctx,
2860                                              dce_conn->wait_private);
2861                 if (!subreq) {
2862                         status = NT_STATUS_NO_MEMORY;
2863                         dcesrv_terminate_connection(dce_conn, nt_errstr(status));
2864                         return;
2865                 }
2866                 tevent_req_set_callback(subreq, dcesrv_conn_wait_done, dce_conn);
2867                 return;
2868         }
2869
2870         subreq = dcerpc_read_ncacn_packet_send(dce_conn,
2871                                                dce_conn->event_ctx,
2872                                                dce_conn->stream);
2873         if (!subreq) {
2874                 status = NT_STATUS_NO_MEMORY;
2875                 dcesrv_terminate_connection(dce_conn, nt_errstr(status));
2876                 return;
2877         }
2878         tevent_req_set_callback(subreq, dcesrv_read_fragment_done, dce_conn);
2879 }
2880
2881 static void dcesrv_conn_wait_done(struct tevent_req *subreq)
2882 {
2883         struct dcesrv_connection *dce_conn = tevent_req_callback_data(subreq,
2884                                              struct dcesrv_connection);
2885         struct dcesrv_context *dce_ctx = dce_conn->dce_ctx;
2886         NTSTATUS status;
2887
2888         if (dce_conn->terminate) {
2889                 /*
2890                  * if the current connection is broken
2891                  * we need to clean it up before any other connection
2892                  */
2893                 dcesrv_terminate_connection(dce_conn, dce_conn->terminate);
2894                 dcesrv_cleanup_broken_connections(dce_ctx);
2895                 return;
2896         }
2897
2898         dcesrv_cleanup_broken_connections(dce_ctx);
2899
2900         status = dce_conn->wait_recv(subreq);
2901         dce_conn->wait_send = NULL;
2902         dce_conn->wait_recv = NULL;
2903         dce_conn->wait_private = NULL;
2904         TALLOC_FREE(subreq);
2905         if (!NT_STATUS_IS_OK(status)) {
2906                 dcesrv_terminate_connection(dce_conn, nt_errstr(status));
2907                 return;
2908         }
2909
2910         status = dcesrv_connection_loop_start(dce_conn);
2911         if (!NT_STATUS_IS_OK(status)) {
2912                 dcesrv_terminate_connection(dce_conn, nt_errstr(status));
2913                 return;
2914         }
2915 }
2916
2917 /**
2918  * retrieve credentials from a dce_call
2919  */
2920 _PUBLIC_ struct cli_credentials *dcesrv_call_credentials(struct dcesrv_call_state *dce_call)
2921 {
2922         struct dcesrv_auth *auth = dce_call->auth_state;
2923         SMB_ASSERT(auth->auth_finished);
2924         return auth->session_info->credentials;
2925 }
2926
2927 /**
2928  * returns true if this is an authenticated call
2929  */
2930 _PUBLIC_ bool dcesrv_call_authenticated(struct dcesrv_call_state *dce_call)
2931 {
2932         struct dcesrv_auth *auth = dce_call->auth_state;
2933         enum security_user_level level;
2934         SMB_ASSERT(auth->auth_finished);
2935         level = security_session_user_level(auth->session_info, NULL);
2936         return level >= SECURITY_USER;
2937 }
2938
2939 /**
2940  * retrieve account_name for a dce_call
2941  */
2942 _PUBLIC_ const char *dcesrv_call_account_name(struct dcesrv_call_state *dce_call)
2943 {
2944         struct dcesrv_auth *auth = dce_call->auth_state;
2945         SMB_ASSERT(auth->auth_finished);
2946         return auth->session_info->info->account_name;
2947 }
2948
2949 /**
2950  * retrieve session_info from a dce_call
2951  */
2952 _PUBLIC_ struct auth_session_info *dcesrv_call_session_info(struct dcesrv_call_state *dce_call)
2953 {
2954         struct dcesrv_auth *auth = dce_call->auth_state;
2955         SMB_ASSERT(auth->auth_finished);
2956         return auth->session_info;
2957 }
2958
2959 /**
2960  * retrieve auth type/level from a dce_call
2961  */
2962 _PUBLIC_ void dcesrv_call_auth_info(struct dcesrv_call_state *dce_call,
2963                                     enum dcerpc_AuthType *auth_type,
2964                                     enum dcerpc_AuthLevel *auth_level)
2965 {
2966         struct dcesrv_auth *auth = dce_call->auth_state;
2967
2968         SMB_ASSERT(auth->auth_finished);
2969
2970         if (auth_type != NULL) {
2971                 *auth_type = auth->auth_type;
2972         }
2973         if (auth_level != NULL) {
2974                 *auth_level = auth->auth_level;
2975         }
2976 }
2977
2978 _PUBLIC_ NTSTATUS dcesrv_connection_loop_start(struct dcesrv_connection *conn)
2979 {
2980         struct tevent_req *subreq;
2981
2982         subreq = dcerpc_read_ncacn_packet_send(conn,
2983                                                conn->event_ctx,
2984                                                conn->stream);
2985         if (subreq == NULL) {
2986                 return NT_STATUS_NO_MEMORY;
2987         }
2988         tevent_req_set_callback(subreq, dcesrv_read_fragment_done, conn);
2989
2990         return NT_STATUS_OK;
2991 }