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