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