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