s3-smbd: Move rpc services init to smbd parent.
[amitay/samba.git] / source3 / smbd / process.c
1 /* 
2    Unix SMB/CIFS implementation.
3    process incoming packets - main loop
4    Copyright (C) Andrew Tridgell 1992-1998
5    Copyright (C) Volker Lendecke 2005-2007
6    
7    This program is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License as published by
9    the Free Software Foundation; either version 3 of the License, or
10    (at your option) any later version.
11    
12    This program is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15    GNU General Public License for more details.
16    
17    You should have received a copy of the GNU General Public License
18    along with this program.  If not, see <http://www.gnu.org/licenses/>.
19 */
20
21 #include "includes.h"
22 #include "smbd/globals.h"
23 #include "librpc/gen_ndr/netlogon.h"
24 #include "librpc/gen_ndr/messaging.h"
25
26 extern bool global_machine_password_needs_changing;
27
28 static void construct_reply_common(struct smb_request *req, const char *inbuf,
29                                    char *outbuf);
30 static struct pending_message_list *get_deferred_open_message_smb(uint64_t mid);
31
32 static bool smbd_lock_socket_internal(struct smbd_server_connection *sconn)
33 {
34         bool ok;
35
36         if (sconn->smb1.echo_handler.socket_lock_fd == -1) {
37                 return true;
38         }
39
40         sconn->smb1.echo_handler.ref_count++;
41
42         if (sconn->smb1.echo_handler.ref_count > 1) {
43                 return true;
44         }
45
46         DEBUG(10,("pid[%d] wait for socket lock\n", (int)sys_getpid()));
47
48         ok = fcntl_lock(sconn->smb1.echo_handler.socket_lock_fd,
49                         SMB_F_SETLKW, 0, 0, F_WRLCK);
50         if (!ok) {
51                 return false;
52         }
53
54         DEBUG(10,("pid[%d] got for socket lock\n", (int)sys_getpid()));
55
56         return true;
57 }
58
59 void smbd_lock_socket(struct smbd_server_connection *sconn)
60 {
61         if (!smbd_lock_socket_internal(sconn)) {
62                 exit_server_cleanly("failed to lock socket");
63         }
64 }
65
66 static bool smbd_unlock_socket_internal(struct smbd_server_connection *sconn)
67 {
68         bool ok;
69
70         if (sconn->smb1.echo_handler.socket_lock_fd == -1) {
71                 return true;
72         }
73
74         sconn->smb1.echo_handler.ref_count--;
75
76         if (sconn->smb1.echo_handler.ref_count > 0) {
77                 return true;
78         }
79
80         ok = fcntl_lock(sconn->smb1.echo_handler.socket_lock_fd,
81                         SMB_F_SETLKW, 0, 0, F_UNLCK);
82         if (!ok) {
83                 return false;
84         }
85
86         DEBUG(10,("pid[%d] unlocked socket\n", (int)sys_getpid()));
87
88         return true;
89 }
90
91 void smbd_unlock_socket(struct smbd_server_connection *sconn)
92 {
93         if (!smbd_unlock_socket_internal(sconn)) {
94                 exit_server_cleanly("failed to unlock socket");
95         }
96 }
97
98 /* Accessor function for smb_read_error for smbd functions. */
99
100 /****************************************************************************
101  Send an smb to a fd.
102 ****************************************************************************/
103
104 bool srv_send_smb(int fd, char *buffer,
105                   bool do_signing, uint32_t seqnum,
106                   bool do_encrypt,
107                   struct smb_perfcount_data *pcd)
108 {
109         size_t len = 0;
110         size_t nwritten=0;
111         ssize_t ret;
112         char *buf_out = buffer;
113
114         smbd_lock_socket(smbd_server_conn);
115
116         if (do_signing) {
117                 /* Sign the outgoing packet if required. */
118                 srv_calculate_sign_mac(smbd_server_conn, buf_out, seqnum);
119         }
120
121         if (do_encrypt) {
122                 NTSTATUS status = srv_encrypt_buffer(buffer, &buf_out);
123                 if (!NT_STATUS_IS_OK(status)) {
124                         DEBUG(0, ("send_smb: SMB encryption failed "
125                                 "on outgoing packet! Error %s\n",
126                                 nt_errstr(status) ));
127                         goto out;
128                 }
129         }
130
131         len = smb_len(buf_out) + 4;
132
133         ret = write_data(fd,buf_out+nwritten,len - nwritten);
134         if (ret <= 0) {
135                 DEBUG(0,("pid[%d] Error writing %d bytes to client. %d. (%s)\n",
136                         (int)sys_getpid(), (int)len,(int)ret, strerror(errno) ));
137                 srv_free_enc_buffer(buf_out);
138                 goto out;
139         }
140
141         SMB_PERFCOUNT_SET_MSGLEN_OUT(pcd, len);
142         srv_free_enc_buffer(buf_out);
143 out:
144         SMB_PERFCOUNT_END(pcd);
145
146         smbd_unlock_socket(smbd_server_conn);
147         return true;
148 }
149
150 /*******************************************************************
151  Setup the word count and byte count for a smb message.
152 ********************************************************************/
153
154 int srv_set_message(char *buf,
155                         int num_words,
156                         int num_bytes,
157                         bool zero)
158 {
159         if (zero && (num_words || num_bytes)) {
160                 memset(buf + smb_size,'\0',num_words*2 + num_bytes);
161         }
162         SCVAL(buf,smb_wct,num_words);
163         SSVAL(buf,smb_vwv + num_words*SIZEOFWORD,num_bytes);
164         smb_setlen(buf,(smb_size + num_words*2 + num_bytes - 4));
165         return (smb_size + num_words*2 + num_bytes);
166 }
167
168 static bool valid_smb_header(const uint8_t *inbuf)
169 {
170         if (is_encrypted_packet(inbuf)) {
171                 return true;
172         }
173         /*
174          * This used to be (strncmp(smb_base(inbuf),"\377SMB",4) == 0)
175          * but it just looks weird to call strncmp for this one.
176          */
177         return (IVAL(smb_base(inbuf), 0) == 0x424D53FF);
178 }
179
180 /* Socket functions for smbd packet processing. */
181
182 static bool valid_packet_size(size_t len)
183 {
184         /*
185          * A WRITEX with CAP_LARGE_WRITEX can be 64k worth of data plus 65 bytes
186          * of header. Don't print the error if this fits.... JRA.
187          */
188
189         if (len > (BUFFER_SIZE + LARGE_WRITEX_HDR_SIZE)) {
190                 DEBUG(0,("Invalid packet length! (%lu bytes).\n",
191                                         (unsigned long)len));
192                 return false;
193         }
194         return true;
195 }
196
197 static NTSTATUS read_packet_remainder(int fd, char *buffer,
198                                       unsigned int timeout, ssize_t len)
199 {
200         if (len <= 0) {
201                 return NT_STATUS_OK;
202         }
203
204         return read_fd_with_timeout(fd, buffer, len, len, timeout, NULL);
205 }
206
207 /****************************************************************************
208  Attempt a zerocopy writeX read. We know here that len > smb_size-4
209 ****************************************************************************/
210
211 /*
212  * Unfortunately, earlier versions of smbclient/libsmbclient
213  * don't send this "standard" writeX header. I've fixed this
214  * for 3.2 but we'll use the old method with earlier versions.
215  * Windows and CIFSFS at least use this standard size. Not
216  * sure about MacOSX.
217  */
218
219 #define STANDARD_WRITE_AND_X_HEADER_SIZE (smb_size - 4 + /* basic header */ \
220                                 (2*14) + /* word count (including bcc) */ \
221                                 1 /* pad byte */)
222
223 static NTSTATUS receive_smb_raw_talloc_partial_read(TALLOC_CTX *mem_ctx,
224                                                     const char lenbuf[4],
225                                                     int fd, char **buffer,
226                                                     unsigned int timeout,
227                                                     size_t *p_unread,
228                                                     size_t *len_ret)
229 {
230         /* Size of a WRITEX call (+4 byte len). */
231         char writeX_header[4 + STANDARD_WRITE_AND_X_HEADER_SIZE];
232         ssize_t len = smb_len_large(lenbuf); /* Could be a UNIX large writeX. */
233         ssize_t toread;
234         NTSTATUS status;
235
236         memcpy(writeX_header, lenbuf, 4);
237
238         status = read_fd_with_timeout(
239                 fd, writeX_header + 4,
240                 STANDARD_WRITE_AND_X_HEADER_SIZE,
241                 STANDARD_WRITE_AND_X_HEADER_SIZE,
242                 timeout, NULL);
243
244         if (!NT_STATUS_IS_OK(status)) {
245                 return status;
246         }
247
248         /*
249          * Ok - now try and see if this is a possible
250          * valid writeX call.
251          */
252
253         if (is_valid_writeX_buffer(smbd_server_conn,
254                                    (uint8_t *)writeX_header)) {
255                 /*
256                  * If the data offset is beyond what
257                  * we've read, drain the extra bytes.
258                  */
259                 uint16_t doff = SVAL(writeX_header,smb_vwv11);
260                 ssize_t newlen;
261
262                 if (doff > STANDARD_WRITE_AND_X_HEADER_SIZE) {
263                         size_t drain = doff - STANDARD_WRITE_AND_X_HEADER_SIZE;
264                         if (drain_socket(smbd_server_fd(), drain) != drain) {
265                                 smb_panic("receive_smb_raw_talloc_partial_read:"
266                                         " failed to drain pending bytes");
267                         }
268                 } else {
269                         doff = STANDARD_WRITE_AND_X_HEADER_SIZE;
270                 }
271
272                 /* Spoof down the length and null out the bcc. */
273                 set_message_bcc(writeX_header, 0);
274                 newlen = smb_len(writeX_header);
275
276                 /* Copy the header we've written. */
277
278                 *buffer = (char *)TALLOC_MEMDUP(mem_ctx,
279                                 writeX_header,
280                                 sizeof(writeX_header));
281
282                 if (*buffer == NULL) {
283                         DEBUG(0, ("Could not allocate inbuf of length %d\n",
284                                   (int)sizeof(writeX_header)));
285                         return NT_STATUS_NO_MEMORY;
286                 }
287
288                 /* Work out the remaining bytes. */
289                 *p_unread = len - STANDARD_WRITE_AND_X_HEADER_SIZE;
290                 *len_ret = newlen + 4;
291                 return NT_STATUS_OK;
292         }
293
294         if (!valid_packet_size(len)) {
295                 return NT_STATUS_INVALID_PARAMETER;
296         }
297
298         /*
299          * Not a valid writeX call. Just do the standard
300          * talloc and return.
301          */
302
303         *buffer = TALLOC_ARRAY(mem_ctx, char, len+4);
304
305         if (*buffer == NULL) {
306                 DEBUG(0, ("Could not allocate inbuf of length %d\n",
307                           (int)len+4));
308                 return NT_STATUS_NO_MEMORY;
309         }
310
311         /* Copy in what we already read. */
312         memcpy(*buffer,
313                 writeX_header,
314                 4 + STANDARD_WRITE_AND_X_HEADER_SIZE);
315         toread = len - STANDARD_WRITE_AND_X_HEADER_SIZE;
316
317         if(toread > 0) {
318                 status = read_packet_remainder(
319                         fd, (*buffer) + 4 + STANDARD_WRITE_AND_X_HEADER_SIZE,
320                         timeout, toread);
321
322                 if (!NT_STATUS_IS_OK(status)) {
323                         DEBUG(10, ("receive_smb_raw_talloc_partial_read: %s\n",
324                                    nt_errstr(status)));
325                         return status;
326                 }
327         }
328
329         *len_ret = len + 4;
330         return NT_STATUS_OK;
331 }
332
333 static NTSTATUS receive_smb_raw_talloc(TALLOC_CTX *mem_ctx, int fd,
334                                        char **buffer, unsigned int timeout,
335                                        size_t *p_unread, size_t *plen)
336 {
337         char lenbuf[4];
338         size_t len;
339         int min_recv_size = lp_min_receive_file_size();
340         NTSTATUS status;
341
342         *p_unread = 0;
343
344         status = read_smb_length_return_keepalive(fd, lenbuf, timeout, &len);
345         if (!NT_STATUS_IS_OK(status)) {
346                 DEBUG(10, ("receive_smb_raw: %s\n", nt_errstr(status)));
347                 return status;
348         }
349
350         if (CVAL(lenbuf,0) == 0 && min_recv_size &&
351             (smb_len_large(lenbuf) > /* Could be a UNIX large writeX. */
352                 (min_recv_size + STANDARD_WRITE_AND_X_HEADER_SIZE)) &&
353             !srv_is_signing_active(smbd_server_conn) &&
354             smbd_server_conn->smb1.echo_handler.trusted_fde == NULL) {
355
356                 return receive_smb_raw_talloc_partial_read(
357                         mem_ctx, lenbuf, fd, buffer, timeout, p_unread, plen);
358         }
359
360         if (!valid_packet_size(len)) {
361                 return NT_STATUS_INVALID_PARAMETER;
362         }
363
364         /*
365          * The +4 here can't wrap, we've checked the length above already.
366          */
367
368         *buffer = TALLOC_ARRAY(mem_ctx, char, len+4);
369
370         if (*buffer == NULL) {
371                 DEBUG(0, ("Could not allocate inbuf of length %d\n",
372                           (int)len+4));
373                 return NT_STATUS_NO_MEMORY;
374         }
375
376         memcpy(*buffer, lenbuf, sizeof(lenbuf));
377
378         status = read_packet_remainder(fd, (*buffer)+4, timeout, len);
379         if (!NT_STATUS_IS_OK(status)) {
380                 return status;
381         }
382
383         *plen = len + 4;
384         return NT_STATUS_OK;
385 }
386
387 static NTSTATUS receive_smb_talloc(TALLOC_CTX *mem_ctx, int fd,
388                                    char **buffer, unsigned int timeout,
389                                    size_t *p_unread, bool *p_encrypted,
390                                    size_t *p_len,
391                                    uint32_t *seqnum,
392                                    bool trusted_channel)
393 {
394         size_t len = 0;
395         NTSTATUS status;
396
397         *p_encrypted = false;
398
399         status = receive_smb_raw_talloc(mem_ctx, fd, buffer, timeout,
400                                         p_unread, &len);
401         if (!NT_STATUS_IS_OK(status)) {
402                 return status;
403         }
404
405         if (is_encrypted_packet((uint8_t *)*buffer)) {
406                 status = srv_decrypt_buffer(*buffer);
407                 if (!NT_STATUS_IS_OK(status)) {
408                         DEBUG(0, ("receive_smb_talloc: SMB decryption failed on "
409                                 "incoming packet! Error %s\n",
410                                 nt_errstr(status) ));
411                         return status;
412                 }
413                 *p_encrypted = true;
414         }
415
416         /* Check the incoming SMB signature. */
417         if (!srv_check_sign_mac(smbd_server_conn, *buffer, seqnum, trusted_channel)) {
418                 DEBUG(0, ("receive_smb: SMB Signature verification failed on "
419                           "incoming packet!\n"));
420                 return NT_STATUS_INVALID_NETWORK_RESPONSE;
421         }
422
423         *p_len = len;
424         return NT_STATUS_OK;
425 }
426
427 /*
428  * Initialize a struct smb_request from an inbuf
429  */
430
431 static bool init_smb_request(struct smb_request *req,
432                              struct smbd_server_connection *sconn,
433                              const uint8 *inbuf,
434                              size_t unread_bytes, bool encrypted,
435                              uint32_t seqnum)
436 {
437         size_t req_size = smb_len(inbuf) + 4;
438         /* Ensure we have at least smb_size bytes. */
439         if (req_size < smb_size) {
440                 DEBUG(0,("init_smb_request: invalid request size %u\n",
441                         (unsigned int)req_size ));
442                 return false;
443         }
444         req->cmd    = CVAL(inbuf, smb_com);
445         req->flags2 = SVAL(inbuf, smb_flg2);
446         req->smbpid = SVAL(inbuf, smb_pid);
447         req->mid    = (uint64_t)SVAL(inbuf, smb_mid);
448         req->seqnum = seqnum;
449         req->vuid   = SVAL(inbuf, smb_uid);
450         req->tid    = SVAL(inbuf, smb_tid);
451         req->wct    = CVAL(inbuf, smb_wct);
452         req->vwv    = (uint16_t *)(inbuf+smb_vwv);
453         req->buflen = smb_buflen(inbuf);
454         req->buf    = (const uint8_t *)smb_buf(inbuf);
455         req->unread_bytes = unread_bytes;
456         req->encrypted = encrypted;
457         req->sconn = sconn;
458         req->conn = conn_find(sconn,req->tid);
459         req->chain_fsp = NULL;
460         req->chain_outbuf = NULL;
461         req->done = false;
462         req->smb2req = NULL;
463         smb_init_perfcount_data(&req->pcd);
464
465         /* Ensure we have at least wct words and 2 bytes of bcc. */
466         if (smb_size + req->wct*2 > req_size) {
467                 DEBUG(0,("init_smb_request: invalid wct number %u (size %u)\n",
468                         (unsigned int)req->wct,
469                         (unsigned int)req_size));
470                 return false;
471         }
472         /* Ensure bcc is correct. */
473         if (((uint8 *)smb_buf(inbuf)) + req->buflen > inbuf + req_size) {
474                 DEBUG(0,("init_smb_request: invalid bcc number %u "
475                         "(wct = %u, size %u)\n",
476                         (unsigned int)req->buflen,
477                         (unsigned int)req->wct,
478                         (unsigned int)req_size));
479                 return false;
480         }
481
482         req->outbuf = NULL;
483         return true;
484 }
485
486 static void process_smb(struct smbd_server_connection *conn,
487                         uint8_t *inbuf, size_t nread, size_t unread_bytes,
488                         uint32_t seqnum, bool encrypted,
489                         struct smb_perfcount_data *deferred_pcd);
490
491 static void smbd_deferred_open_timer(struct event_context *ev,
492                                      struct timed_event *te,
493                                      struct timeval _tval,
494                                      void *private_data)
495 {
496         struct pending_message_list *msg = talloc_get_type(private_data,
497                                            struct pending_message_list);
498         TALLOC_CTX *mem_ctx = talloc_tos();
499         uint64_t mid = (uint64_t)SVAL(msg->buf.data,smb_mid);
500         uint8_t *inbuf;
501
502         inbuf = (uint8_t *)talloc_memdup(mem_ctx, msg->buf.data,
503                                          msg->buf.length);
504         if (inbuf == NULL) {
505                 exit_server("smbd_deferred_open_timer: talloc failed\n");
506                 return;
507         }
508
509         /* We leave this message on the queue so the open code can
510            know this is a retry. */
511         DEBUG(5,("smbd_deferred_open_timer: trigger mid %llu.\n",
512                 (unsigned long long)mid ));
513
514         /* Mark the message as processed so this is not
515          * re-processed in error. */
516         msg->processed = true;
517
518         process_smb(smbd_server_conn, inbuf,
519                     msg->buf.length, 0,
520                     msg->seqnum, msg->encrypted, &msg->pcd);
521
522         /* If it's still there and was processed, remove it. */
523         msg = get_deferred_open_message_smb(mid);
524         if (msg && msg->processed) {
525                 remove_deferred_open_message_smb(mid);
526         }
527 }
528
529 /****************************************************************************
530  Function to push a message onto the tail of a linked list of smb messages ready
531  for processing.
532 ****************************************************************************/
533
534 static bool push_queued_message(struct smb_request *req,
535                                 struct timeval request_time,
536                                 struct timeval end_time,
537                                 char *private_data, size_t private_len)
538 {
539         int msg_len = smb_len(req->inbuf) + 4;
540         struct pending_message_list *msg;
541
542         msg = TALLOC_ZERO_P(NULL, struct pending_message_list);
543
544         if(msg == NULL) {
545                 DEBUG(0,("push_message: malloc fail (1)\n"));
546                 return False;
547         }
548
549         msg->buf = data_blob_talloc(msg, req->inbuf, msg_len);
550         if(msg->buf.data == NULL) {
551                 DEBUG(0,("push_message: malloc fail (2)\n"));
552                 TALLOC_FREE(msg);
553                 return False;
554         }
555
556         msg->request_time = request_time;
557         msg->seqnum = req->seqnum;
558         msg->encrypted = req->encrypted;
559         msg->processed = false;
560         SMB_PERFCOUNT_DEFER_OP(&req->pcd, &msg->pcd);
561
562         if (private_data) {
563                 msg->private_data = data_blob_talloc(msg, private_data,
564                                                      private_len);
565                 if (msg->private_data.data == NULL) {
566                         DEBUG(0,("push_message: malloc fail (3)\n"));
567                         TALLOC_FREE(msg);
568                         return False;
569                 }
570         }
571
572         msg->te = event_add_timed(smbd_event_context(),
573                                   msg,
574                                   end_time,
575                                   smbd_deferred_open_timer,
576                                   msg);
577         if (!msg->te) {
578                 DEBUG(0,("push_message: event_add_timed failed\n"));
579                 TALLOC_FREE(msg);
580                 return false;
581         }
582
583         DLIST_ADD_END(deferred_open_queue, msg, struct pending_message_list *);
584
585         DEBUG(10,("push_message: pushed message length %u on "
586                   "deferred_open_queue\n", (unsigned int)msg_len));
587
588         return True;
589 }
590
591 /****************************************************************************
592  Function to delete a sharing violation open message by mid.
593 ****************************************************************************/
594
595 void remove_deferred_open_message_smb(uint64_t mid)
596 {
597         struct pending_message_list *pml;
598
599         if (smbd_server_conn->using_smb2) {
600                 remove_deferred_open_message_smb2(smbd_server_conn, mid);
601                 return;
602         }
603
604         for (pml = deferred_open_queue; pml; pml = pml->next) {
605                 if (mid == (uint64_t)SVAL(pml->buf.data,smb_mid)) {
606                         DEBUG(10,("remove_deferred_open_message_smb: "
607                                   "deleting mid %llu len %u\n",
608                                   (unsigned long long)mid,
609                                   (unsigned int)pml->buf.length ));
610                         DLIST_REMOVE(deferred_open_queue, pml);
611                         TALLOC_FREE(pml);
612                         return;
613                 }
614         }
615 }
616
617 /****************************************************************************
618  Move a sharing violation open retry message to the front of the list and
619  schedule it for immediate processing.
620 ****************************************************************************/
621
622 void schedule_deferred_open_message_smb(uint64_t mid)
623 {
624         struct pending_message_list *pml;
625         int i = 0;
626
627         if (smbd_server_conn->using_smb2) {
628                 schedule_deferred_open_message_smb2(smbd_server_conn, mid);
629                 return;
630         }
631
632         for (pml = deferred_open_queue; pml; pml = pml->next) {
633                 uint64_t msg_mid = (uint64_t)SVAL(pml->buf.data,smb_mid);
634
635                 DEBUG(10,("schedule_deferred_open_message_smb: [%d] "
636                         "msg_mid = %llu\n",
637                         i++,
638                         (unsigned long long)msg_mid ));
639
640                 if (mid == msg_mid) {
641                         struct timed_event *te;
642
643                         if (pml->processed) {
644                                 /* A processed message should not be
645                                  * rescheduled. */
646                                 DEBUG(0,("schedule_deferred_open_message_smb: LOGIC ERROR "
647                                         "message mid %llu was already processed\n",
648                                         (unsigned long long)msg_mid ));
649                                 continue;
650                         }
651
652                         DEBUG(10,("schedule_deferred_open_message_smb: "
653                                 "scheduling mid %llu\n",
654                                 (unsigned long long)mid ));
655
656                         te = event_add_timed(smbd_event_context(),
657                                              pml,
658                                              timeval_zero(),
659                                              smbd_deferred_open_timer,
660                                              pml);
661                         if (!te) {
662                                 DEBUG(10,("schedule_deferred_open_message_smb: "
663                                         "event_add_timed() failed, "
664                                         "skipping mid %llu\n",
665                                         (unsigned long long)msg_mid ));
666                         }
667
668                         TALLOC_FREE(pml->te);
669                         pml->te = te;
670                         DLIST_PROMOTE(deferred_open_queue, pml);
671                         return;
672                 }
673         }
674
675         DEBUG(10,("schedule_deferred_open_message_smb: failed to "
676                 "find message mid %llu\n",
677                 (unsigned long long)mid ));
678 }
679
680 /****************************************************************************
681  Return true if this mid is on the deferred queue and was not yet processed.
682 ****************************************************************************/
683
684 bool open_was_deferred(uint64_t mid)
685 {
686         struct pending_message_list *pml;
687
688         if (smbd_server_conn->using_smb2) {
689                 return open_was_deferred_smb2(smbd_server_conn, mid);
690         }
691
692         for (pml = deferred_open_queue; pml; pml = pml->next) {
693                 if (((uint64_t)SVAL(pml->buf.data,smb_mid)) == mid && !pml->processed) {
694                         return True;
695                 }
696         }
697         return False;
698 }
699
700 /****************************************************************************
701  Return the message queued by this mid.
702 ****************************************************************************/
703
704 static struct pending_message_list *get_deferred_open_message_smb(uint64_t mid)
705 {
706         struct pending_message_list *pml;
707
708         for (pml = deferred_open_queue; pml; pml = pml->next) {
709                 if (((uint64_t)SVAL(pml->buf.data,smb_mid)) == mid) {
710                         return pml;
711                 }
712         }
713         return NULL;
714 }
715
716 /****************************************************************************
717  Get the state data queued by this mid.
718 ****************************************************************************/
719
720 bool get_deferred_open_message_state(struct smb_request *smbreq,
721                                 struct timeval *p_request_time,
722                                 void **pp_state)
723 {
724         struct pending_message_list *pml;
725
726         if (smbd_server_conn->using_smb2) {
727                 return get_deferred_open_message_state_smb2(smbreq->smb2req,
728                                         p_request_time,
729                                         pp_state);
730         }
731
732         pml = get_deferred_open_message_smb(smbreq->mid);
733         if (!pml) {
734                 return false;
735         }
736         if (p_request_time) {
737                 *p_request_time = pml->request_time;
738         }
739         if (pp_state) {
740                 *pp_state = (void *)pml->private_data.data;
741         }
742         return true;
743 }
744
745 /****************************************************************************
746  Function to push a deferred open smb message onto a linked list of local smb
747  messages ready for processing.
748 ****************************************************************************/
749
750 bool push_deferred_open_message_smb(struct smb_request *req,
751                                struct timeval request_time,
752                                struct timeval timeout,
753                                struct file_id id,
754                                char *private_data, size_t priv_len)
755 {
756         struct timeval end_time;
757
758         if (req->smb2req) {
759                 return push_deferred_open_message_smb2(req->smb2req,
760                                                 request_time,
761                                                 timeout,
762                                                 id,
763                                                 private_data,
764                                                 priv_len);
765         }
766
767         if (req->unread_bytes) {
768                 DEBUG(0,("push_deferred_open_message_smb: logic error ! "
769                         "unread_bytes = %u\n",
770                         (unsigned int)req->unread_bytes ));
771                 smb_panic("push_deferred_open_message_smb: "
772                         "logic error unread_bytes != 0" );
773         }
774
775         end_time = timeval_sum(&request_time, &timeout);
776
777         DEBUG(10,("push_deferred_open_message_smb: pushing message "
778                 "len %u mid %llu timeout time [%u.%06u]\n",
779                 (unsigned int) smb_len(req->inbuf)+4,
780                 (unsigned long long)req->mid,
781                 (unsigned int)end_time.tv_sec,
782                 (unsigned int)end_time.tv_usec));
783
784         return push_queued_message(req, request_time, end_time,
785                                    private_data, priv_len);
786 }
787
788 struct idle_event {
789         struct timed_event *te;
790         struct timeval interval;
791         char *name;
792         bool (*handler)(const struct timeval *now, void *private_data);
793         void *private_data;
794 };
795
796 static void smbd_idle_event_handler(struct event_context *ctx,
797                                     struct timed_event *te,
798                                     struct timeval now,
799                                     void *private_data)
800 {
801         struct idle_event *event =
802                 talloc_get_type_abort(private_data, struct idle_event);
803
804         TALLOC_FREE(event->te);
805
806         DEBUG(10,("smbd_idle_event_handler: %s %p called\n",
807                   event->name, event->te));
808
809         if (!event->handler(&now, event->private_data)) {
810                 DEBUG(10,("smbd_idle_event_handler: %s %p stopped\n",
811                           event->name, event->te));
812                 /* Don't repeat, delete ourselves */
813                 TALLOC_FREE(event);
814                 return;
815         }
816
817         DEBUG(10,("smbd_idle_event_handler: %s %p rescheduled\n",
818                   event->name, event->te));
819
820         event->te = event_add_timed(ctx, event,
821                                     timeval_sum(&now, &event->interval),
822                                     smbd_idle_event_handler, event);
823
824         /* We can't do much but fail here. */
825         SMB_ASSERT(event->te != NULL);
826 }
827
828 struct idle_event *event_add_idle(struct event_context *event_ctx,
829                                   TALLOC_CTX *mem_ctx,
830                                   struct timeval interval,
831                                   const char *name,
832                                   bool (*handler)(const struct timeval *now,
833                                                   void *private_data),
834                                   void *private_data)
835 {
836         struct idle_event *result;
837         struct timeval now = timeval_current();
838
839         result = TALLOC_P(mem_ctx, struct idle_event);
840         if (result == NULL) {
841                 DEBUG(0, ("talloc failed\n"));
842                 return NULL;
843         }
844
845         result->interval = interval;
846         result->handler = handler;
847         result->private_data = private_data;
848
849         if (!(result->name = talloc_asprintf(result, "idle_evt(%s)", name))) {
850                 DEBUG(0, ("talloc failed\n"));
851                 TALLOC_FREE(result);
852                 return NULL;
853         }
854
855         result->te = event_add_timed(event_ctx, result,
856                                      timeval_sum(&now, &interval),
857                                      smbd_idle_event_handler, result);
858         if (result->te == NULL) {
859                 DEBUG(0, ("event_add_timed failed\n"));
860                 TALLOC_FREE(result);
861                 return NULL;
862         }
863
864         DEBUG(10,("event_add_idle: %s %p\n", result->name, result->te));
865         return result;
866 }
867
868 static void smbd_sig_term_handler(struct tevent_context *ev,
869                                   struct tevent_signal *se,
870                                   int signum,
871                                   int count,
872                                   void *siginfo,
873                                   void *private_data)
874 {
875         exit_server_cleanly("termination signal");
876 }
877
878 void smbd_setup_sig_term_handler(void)
879 {
880         struct tevent_signal *se;
881
882         se = tevent_add_signal(smbd_event_context(),
883                                smbd_event_context(),
884                                SIGTERM, 0,
885                                smbd_sig_term_handler,
886                                NULL);
887         if (!se) {
888                 exit_server("failed to setup SIGTERM handler");
889         }
890 }
891
892 static void smbd_sig_hup_handler(struct tevent_context *ev,
893                                   struct tevent_signal *se,
894                                   int signum,
895                                   int count,
896                                   void *siginfo,
897                                   void *private_data)
898 {
899         struct messaging_context *msg_ctx = talloc_get_type_abort(
900                 private_data, struct messaging_context);
901         change_to_root_user();
902         DEBUG(1,("Reloading services after SIGHUP\n"));
903         reload_services(msg_ctx, False);
904 }
905
906 void smbd_setup_sig_hup_handler(struct tevent_context *ev,
907                                 struct messaging_context *msg_ctx)
908 {
909         struct tevent_signal *se;
910
911         se = tevent_add_signal(ev, ev, SIGHUP, 0, smbd_sig_hup_handler,
912                                msg_ctx);
913         if (!se) {
914                 exit_server("failed to setup SIGHUP handler");
915         }
916 }
917
918 static NTSTATUS smbd_server_connection_loop_once(struct smbd_server_connection *conn)
919 {
920         fd_set r_fds, w_fds;
921         int selrtn;
922         struct timeval to;
923         int maxfd = 0;
924
925         to.tv_sec = SMBD_SELECT_TIMEOUT;
926         to.tv_usec = 0;
927
928         /*
929          * Setup the select fd sets.
930          */
931
932         FD_ZERO(&r_fds);
933         FD_ZERO(&w_fds);
934
935         /*
936          * Are there any timed events waiting ? If so, ensure we don't
937          * select for longer than it would take to wait for them.
938          */
939
940         {
941                 struct timeval now;
942                 GetTimeOfDay(&now);
943
944                 event_add_to_select_args(smbd_event_context(), &now,
945                                          &r_fds, &w_fds, &to, &maxfd);
946         }
947
948         /* Process a signal and timed events now... */
949         if (run_events(smbd_event_context(), 0, NULL, NULL)) {
950                 return NT_STATUS_RETRY;
951         }
952
953         {
954                 int sav;
955                 START_PROFILE(smbd_idle);
956
957                 selrtn = sys_select(maxfd+1,&r_fds,&w_fds,NULL,&to);
958                 sav = errno;
959
960                 END_PROFILE(smbd_idle);
961                 errno = sav;
962         }
963
964         if ((conn->smb1.echo_handler.trusted_fd != -1)
965             && FD_ISSET(smbd_server_fd(), &r_fds)
966             && FD_ISSET(conn->smb1.echo_handler.trusted_fd, &r_fds)) {
967                 /*
968                  * Prefer to read pending requests from the echo handler. To
969                  * quote Jeremy (da70f8ab1): This is a hack of monstrous
970                  * proportions...
971                  */
972                 FD_CLR(smbd_server_fd(), &r_fds);
973         }
974
975         if (run_events(smbd_event_context(), selrtn, &r_fds, &w_fds)) {
976                 return NT_STATUS_RETRY;
977         }
978
979         /* Check if error */
980         if (selrtn == -1) {
981                 /* something is wrong. Maybe the socket is dead? */
982                 return map_nt_error_from_unix(errno);
983         }
984
985         /* Did we timeout ? */
986         if (selrtn == 0) {
987                 return NT_STATUS_RETRY;
988         }
989
990         /* should not be reached */
991         return NT_STATUS_INTERNAL_ERROR;
992 }
993
994 /*
995  * Only allow 5 outstanding trans requests. We're allocating memory, so
996  * prevent a DoS.
997  */
998
999 NTSTATUS allow_new_trans(struct trans_state *list, uint64_t mid)
1000 {
1001         int count = 0;
1002         for (; list != NULL; list = list->next) {
1003
1004                 if (list->mid == mid) {
1005                         return NT_STATUS_INVALID_PARAMETER;
1006                 }
1007
1008                 count += 1;
1009         }
1010         if (count > 5) {
1011                 return NT_STATUS_INSUFFICIENT_RESOURCES;
1012         }
1013
1014         return NT_STATUS_OK;
1015 }
1016
1017 /*
1018 These flags determine some of the permissions required to do an operation 
1019
1020 Note that I don't set NEED_WRITE on some write operations because they
1021 are used by some brain-dead clients when printing, and I don't want to
1022 force write permissions on print services.
1023 */
1024 #define AS_USER (1<<0)
1025 #define NEED_WRITE (1<<1) /* Must be paired with AS_USER */
1026 #define TIME_INIT (1<<2)
1027 #define CAN_IPC (1<<3) /* Must be paired with AS_USER */
1028 #define AS_GUEST (1<<5) /* Must *NOT* be paired with AS_USER */
1029 #define DO_CHDIR (1<<6)
1030
1031 /* 
1032    define a list of possible SMB messages and their corresponding
1033    functions. Any message that has a NULL function is unimplemented -
1034    please feel free to contribute implementations!
1035 */
1036 static const struct smb_message_struct {
1037         const char *name;
1038         void (*fn)(struct smb_request *req);
1039         int flags;
1040 } smb_messages[256] = {
1041
1042 /* 0x00 */ { "SMBmkdir",reply_mkdir,AS_USER | NEED_WRITE},
1043 /* 0x01 */ { "SMBrmdir",reply_rmdir,AS_USER | NEED_WRITE},
1044 /* 0x02 */ { "SMBopen",reply_open,AS_USER },
1045 /* 0x03 */ { "SMBcreate",reply_mknew,AS_USER},
1046 /* 0x04 */ { "SMBclose",reply_close,AS_USER | CAN_IPC },
1047 /* 0x05 */ { "SMBflush",reply_flush,AS_USER},
1048 /* 0x06 */ { "SMBunlink",reply_unlink,AS_USER | NEED_WRITE },
1049 /* 0x07 */ { "SMBmv",reply_mv,AS_USER | NEED_WRITE },
1050 /* 0x08 */ { "SMBgetatr",reply_getatr,AS_USER},
1051 /* 0x09 */ { "SMBsetatr",reply_setatr,AS_USER | NEED_WRITE},
1052 /* 0x0a */ { "SMBread",reply_read,AS_USER},
1053 /* 0x0b */ { "SMBwrite",reply_write,AS_USER | CAN_IPC },
1054 /* 0x0c */ { "SMBlock",reply_lock,AS_USER},
1055 /* 0x0d */ { "SMBunlock",reply_unlock,AS_USER},
1056 /* 0x0e */ { "SMBctemp",reply_ctemp,AS_USER },
1057 /* 0x0f */ { "SMBmknew",reply_mknew,AS_USER},
1058 /* 0x10 */ { "SMBcheckpath",reply_checkpath,AS_USER},
1059 /* 0x11 */ { "SMBexit",reply_exit,DO_CHDIR},
1060 /* 0x12 */ { "SMBlseek",reply_lseek,AS_USER},
1061 /* 0x13 */ { "SMBlockread",reply_lockread,AS_USER},
1062 /* 0x14 */ { "SMBwriteunlock",reply_writeunlock,AS_USER},
1063 /* 0x15 */ { NULL, NULL, 0 },
1064 /* 0x16 */ { NULL, NULL, 0 },
1065 /* 0x17 */ { NULL, NULL, 0 },
1066 /* 0x18 */ { NULL, NULL, 0 },
1067 /* 0x19 */ { NULL, NULL, 0 },
1068 /* 0x1a */ { "SMBreadbraw",reply_readbraw,AS_USER},
1069 /* 0x1b */ { "SMBreadBmpx",reply_readbmpx,AS_USER},
1070 /* 0x1c */ { "SMBreadBs",reply_readbs,AS_USER },
1071 /* 0x1d */ { "SMBwritebraw",reply_writebraw,AS_USER},
1072 /* 0x1e */ { "SMBwriteBmpx",reply_writebmpx,AS_USER},
1073 /* 0x1f */ { "SMBwriteBs",reply_writebs,AS_USER},
1074 /* 0x20 */ { "SMBwritec", NULL,0},
1075 /* 0x21 */ { NULL, NULL, 0 },
1076 /* 0x22 */ { "SMBsetattrE",reply_setattrE,AS_USER | NEED_WRITE },
1077 /* 0x23 */ { "SMBgetattrE",reply_getattrE,AS_USER },
1078 /* 0x24 */ { "SMBlockingX",reply_lockingX,AS_USER },
1079 /* 0x25 */ { "SMBtrans",reply_trans,AS_USER | CAN_IPC },
1080 /* 0x26 */ { "SMBtranss",reply_transs,AS_USER | CAN_IPC},
1081 /* 0x27 */ { "SMBioctl",reply_ioctl,0},
1082 /* 0x28 */ { "SMBioctls", NULL,AS_USER},
1083 /* 0x29 */ { "SMBcopy",reply_copy,AS_USER | NEED_WRITE },
1084 /* 0x2a */ { "SMBmove", NULL,AS_USER | NEED_WRITE },
1085 /* 0x2b */ { "SMBecho",reply_echo,0},
1086 /* 0x2c */ { "SMBwriteclose",reply_writeclose,AS_USER},
1087 /* 0x2d */ { "SMBopenX",reply_open_and_X,AS_USER | CAN_IPC },
1088 /* 0x2e */ { "SMBreadX",reply_read_and_X,AS_USER | CAN_IPC },
1089 /* 0x2f */ { "SMBwriteX",reply_write_and_X,AS_USER | CAN_IPC },
1090 /* 0x30 */ { NULL, NULL, 0 },
1091 /* 0x31 */ { NULL, NULL, 0 },
1092 /* 0x32 */ { "SMBtrans2",reply_trans2, AS_USER | CAN_IPC },
1093 /* 0x33 */ { "SMBtranss2",reply_transs2, AS_USER | CAN_IPC },
1094 /* 0x34 */ { "SMBfindclose",reply_findclose,AS_USER},
1095 /* 0x35 */ { "SMBfindnclose",reply_findnclose,AS_USER},
1096 /* 0x36 */ { NULL, NULL, 0 },
1097 /* 0x37 */ { NULL, NULL, 0 },
1098 /* 0x38 */ { NULL, NULL, 0 },
1099 /* 0x39 */ { NULL, NULL, 0 },
1100 /* 0x3a */ { NULL, NULL, 0 },
1101 /* 0x3b */ { NULL, NULL, 0 },
1102 /* 0x3c */ { NULL, NULL, 0 },
1103 /* 0x3d */ { NULL, NULL, 0 },
1104 /* 0x3e */ { NULL, NULL, 0 },
1105 /* 0x3f */ { NULL, NULL, 0 },
1106 /* 0x40 */ { NULL, NULL, 0 },
1107 /* 0x41 */ { NULL, NULL, 0 },
1108 /* 0x42 */ { NULL, NULL, 0 },
1109 /* 0x43 */ { NULL, NULL, 0 },
1110 /* 0x44 */ { NULL, NULL, 0 },
1111 /* 0x45 */ { NULL, NULL, 0 },
1112 /* 0x46 */ { NULL, NULL, 0 },
1113 /* 0x47 */ { NULL, NULL, 0 },
1114 /* 0x48 */ { NULL, NULL, 0 },
1115 /* 0x49 */ { NULL, NULL, 0 },
1116 /* 0x4a */ { NULL, NULL, 0 },
1117 /* 0x4b */ { NULL, NULL, 0 },
1118 /* 0x4c */ { NULL, NULL, 0 },
1119 /* 0x4d */ { NULL, NULL, 0 },
1120 /* 0x4e */ { NULL, NULL, 0 },
1121 /* 0x4f */ { NULL, NULL, 0 },
1122 /* 0x50 */ { NULL, NULL, 0 },
1123 /* 0x51 */ { NULL, NULL, 0 },
1124 /* 0x52 */ { NULL, NULL, 0 },
1125 /* 0x53 */ { NULL, NULL, 0 },
1126 /* 0x54 */ { NULL, NULL, 0 },
1127 /* 0x55 */ { NULL, NULL, 0 },
1128 /* 0x56 */ { NULL, NULL, 0 },
1129 /* 0x57 */ { NULL, NULL, 0 },
1130 /* 0x58 */ { NULL, NULL, 0 },
1131 /* 0x59 */ { NULL, NULL, 0 },
1132 /* 0x5a */ { NULL, NULL, 0 },
1133 /* 0x5b */ { NULL, NULL, 0 },
1134 /* 0x5c */ { NULL, NULL, 0 },
1135 /* 0x5d */ { NULL, NULL, 0 },
1136 /* 0x5e */ { NULL, NULL, 0 },
1137 /* 0x5f */ { NULL, NULL, 0 },
1138 /* 0x60 */ { NULL, NULL, 0 },
1139 /* 0x61 */ { NULL, NULL, 0 },
1140 /* 0x62 */ { NULL, NULL, 0 },
1141 /* 0x63 */ { NULL, NULL, 0 },
1142 /* 0x64 */ { NULL, NULL, 0 },
1143 /* 0x65 */ { NULL, NULL, 0 },
1144 /* 0x66 */ { NULL, NULL, 0 },
1145 /* 0x67 */ { NULL, NULL, 0 },
1146 /* 0x68 */ { NULL, NULL, 0 },
1147 /* 0x69 */ { NULL, NULL, 0 },
1148 /* 0x6a */ { NULL, NULL, 0 },
1149 /* 0x6b */ { NULL, NULL, 0 },
1150 /* 0x6c */ { NULL, NULL, 0 },
1151 /* 0x6d */ { NULL, NULL, 0 },
1152 /* 0x6e */ { NULL, NULL, 0 },
1153 /* 0x6f */ { NULL, NULL, 0 },
1154 /* 0x70 */ { "SMBtcon",reply_tcon,0},
1155 /* 0x71 */ { "SMBtdis",reply_tdis,DO_CHDIR},
1156 /* 0x72 */ { "SMBnegprot",reply_negprot,0},
1157 /* 0x73 */ { "SMBsesssetupX",reply_sesssetup_and_X,0},
1158 /* 0x74 */ { "SMBulogoffX",reply_ulogoffX, 0}, /* ulogoff doesn't give a valid TID */
1159 /* 0x75 */ { "SMBtconX",reply_tcon_and_X,0},
1160 /* 0x76 */ { NULL, NULL, 0 },
1161 /* 0x77 */ { NULL, NULL, 0 },
1162 /* 0x78 */ { NULL, NULL, 0 },
1163 /* 0x79 */ { NULL, NULL, 0 },
1164 /* 0x7a */ { NULL, NULL, 0 },
1165 /* 0x7b */ { NULL, NULL, 0 },
1166 /* 0x7c */ { NULL, NULL, 0 },
1167 /* 0x7d */ { NULL, NULL, 0 },
1168 /* 0x7e */ { NULL, NULL, 0 },
1169 /* 0x7f */ { NULL, NULL, 0 },
1170 /* 0x80 */ { "SMBdskattr",reply_dskattr,AS_USER},
1171 /* 0x81 */ { "SMBsearch",reply_search,AS_USER},
1172 /* 0x82 */ { "SMBffirst",reply_search,AS_USER},
1173 /* 0x83 */ { "SMBfunique",reply_search,AS_USER},
1174 /* 0x84 */ { "SMBfclose",reply_fclose,AS_USER},
1175 /* 0x85 */ { NULL, NULL, 0 },
1176 /* 0x86 */ { NULL, NULL, 0 },
1177 /* 0x87 */ { NULL, NULL, 0 },
1178 /* 0x88 */ { NULL, NULL, 0 },
1179 /* 0x89 */ { NULL, NULL, 0 },
1180 /* 0x8a */ { NULL, NULL, 0 },
1181 /* 0x8b */ { NULL, NULL, 0 },
1182 /* 0x8c */ { NULL, NULL, 0 },
1183 /* 0x8d */ { NULL, NULL, 0 },
1184 /* 0x8e */ { NULL, NULL, 0 },
1185 /* 0x8f */ { NULL, NULL, 0 },
1186 /* 0x90 */ { NULL, NULL, 0 },
1187 /* 0x91 */ { NULL, NULL, 0 },
1188 /* 0x92 */ { NULL, NULL, 0 },
1189 /* 0x93 */ { NULL, NULL, 0 },
1190 /* 0x94 */ { NULL, NULL, 0 },
1191 /* 0x95 */ { NULL, NULL, 0 },
1192 /* 0x96 */ { NULL, NULL, 0 },
1193 /* 0x97 */ { NULL, NULL, 0 },
1194 /* 0x98 */ { NULL, NULL, 0 },
1195 /* 0x99 */ { NULL, NULL, 0 },
1196 /* 0x9a */ { NULL, NULL, 0 },
1197 /* 0x9b */ { NULL, NULL, 0 },
1198 /* 0x9c */ { NULL, NULL, 0 },
1199 /* 0x9d */ { NULL, NULL, 0 },
1200 /* 0x9e */ { NULL, NULL, 0 },
1201 /* 0x9f */ { NULL, NULL, 0 },
1202 /* 0xa0 */ { "SMBnttrans",reply_nttrans, AS_USER | CAN_IPC },
1203 /* 0xa1 */ { "SMBnttranss",reply_nttranss, AS_USER | CAN_IPC },
1204 /* 0xa2 */ { "SMBntcreateX",reply_ntcreate_and_X, AS_USER | CAN_IPC },
1205 /* 0xa3 */ { NULL, NULL, 0 },
1206 /* 0xa4 */ { "SMBntcancel",reply_ntcancel, 0 },
1207 /* 0xa5 */ { "SMBntrename",reply_ntrename, AS_USER | NEED_WRITE },
1208 /* 0xa6 */ { NULL, NULL, 0 },
1209 /* 0xa7 */ { NULL, NULL, 0 },
1210 /* 0xa8 */ { NULL, NULL, 0 },
1211 /* 0xa9 */ { NULL, NULL, 0 },
1212 /* 0xaa */ { NULL, NULL, 0 },
1213 /* 0xab */ { NULL, NULL, 0 },
1214 /* 0xac */ { NULL, NULL, 0 },
1215 /* 0xad */ { NULL, NULL, 0 },
1216 /* 0xae */ { NULL, NULL, 0 },
1217 /* 0xaf */ { NULL, NULL, 0 },
1218 /* 0xb0 */ { NULL, NULL, 0 },
1219 /* 0xb1 */ { NULL, NULL, 0 },
1220 /* 0xb2 */ { NULL, NULL, 0 },
1221 /* 0xb3 */ { NULL, NULL, 0 },
1222 /* 0xb4 */ { NULL, NULL, 0 },
1223 /* 0xb5 */ { NULL, NULL, 0 },
1224 /* 0xb6 */ { NULL, NULL, 0 },
1225 /* 0xb7 */ { NULL, NULL, 0 },
1226 /* 0xb8 */ { NULL, NULL, 0 },
1227 /* 0xb9 */ { NULL, NULL, 0 },
1228 /* 0xba */ { NULL, NULL, 0 },
1229 /* 0xbb */ { NULL, NULL, 0 },
1230 /* 0xbc */ { NULL, NULL, 0 },
1231 /* 0xbd */ { NULL, NULL, 0 },
1232 /* 0xbe */ { NULL, NULL, 0 },
1233 /* 0xbf */ { NULL, NULL, 0 },
1234 /* 0xc0 */ { "SMBsplopen",reply_printopen,AS_USER},
1235 /* 0xc1 */ { "SMBsplwr",reply_printwrite,AS_USER},
1236 /* 0xc2 */ { "SMBsplclose",reply_printclose,AS_USER},
1237 /* 0xc3 */ { "SMBsplretq",reply_printqueue,AS_USER},
1238 /* 0xc4 */ { NULL, NULL, 0 },
1239 /* 0xc5 */ { NULL, NULL, 0 },
1240 /* 0xc6 */ { NULL, NULL, 0 },
1241 /* 0xc7 */ { NULL, NULL, 0 },
1242 /* 0xc8 */ { NULL, NULL, 0 },
1243 /* 0xc9 */ { NULL, NULL, 0 },
1244 /* 0xca */ { NULL, NULL, 0 },
1245 /* 0xcb */ { NULL, NULL, 0 },
1246 /* 0xcc */ { NULL, NULL, 0 },
1247 /* 0xcd */ { NULL, NULL, 0 },
1248 /* 0xce */ { NULL, NULL, 0 },
1249 /* 0xcf */ { NULL, NULL, 0 },
1250 /* 0xd0 */ { "SMBsends",reply_sends,AS_GUEST},
1251 /* 0xd1 */ { "SMBsendb", NULL,AS_GUEST},
1252 /* 0xd2 */ { "SMBfwdname", NULL,AS_GUEST},
1253 /* 0xd3 */ { "SMBcancelf", NULL,AS_GUEST},
1254 /* 0xd4 */ { "SMBgetmac", NULL,AS_GUEST},
1255 /* 0xd5 */ { "SMBsendstrt",reply_sendstrt,AS_GUEST},
1256 /* 0xd6 */ { "SMBsendend",reply_sendend,AS_GUEST},
1257 /* 0xd7 */ { "SMBsendtxt",reply_sendtxt,AS_GUEST},
1258 /* 0xd8 */ { NULL, NULL, 0 },
1259 /* 0xd9 */ { NULL, NULL, 0 },
1260 /* 0xda */ { NULL, NULL, 0 },
1261 /* 0xdb */ { NULL, NULL, 0 },
1262 /* 0xdc */ { NULL, NULL, 0 },
1263 /* 0xdd */ { NULL, NULL, 0 },
1264 /* 0xde */ { NULL, NULL, 0 },
1265 /* 0xdf */ { NULL, NULL, 0 },
1266 /* 0xe0 */ { NULL, NULL, 0 },
1267 /* 0xe1 */ { NULL, NULL, 0 },
1268 /* 0xe2 */ { NULL, NULL, 0 },
1269 /* 0xe3 */ { NULL, NULL, 0 },
1270 /* 0xe4 */ { NULL, NULL, 0 },
1271 /* 0xe5 */ { NULL, NULL, 0 },
1272 /* 0xe6 */ { NULL, NULL, 0 },
1273 /* 0xe7 */ { NULL, NULL, 0 },
1274 /* 0xe8 */ { NULL, NULL, 0 },
1275 /* 0xe9 */ { NULL, NULL, 0 },
1276 /* 0xea */ { NULL, NULL, 0 },
1277 /* 0xeb */ { NULL, NULL, 0 },
1278 /* 0xec */ { NULL, NULL, 0 },
1279 /* 0xed */ { NULL, NULL, 0 },
1280 /* 0xee */ { NULL, NULL, 0 },
1281 /* 0xef */ { NULL, NULL, 0 },
1282 /* 0xf0 */ { NULL, NULL, 0 },
1283 /* 0xf1 */ { NULL, NULL, 0 },
1284 /* 0xf2 */ { NULL, NULL, 0 },
1285 /* 0xf3 */ { NULL, NULL, 0 },
1286 /* 0xf4 */ { NULL, NULL, 0 },
1287 /* 0xf5 */ { NULL, NULL, 0 },
1288 /* 0xf6 */ { NULL, NULL, 0 },
1289 /* 0xf7 */ { NULL, NULL, 0 },
1290 /* 0xf8 */ { NULL, NULL, 0 },
1291 /* 0xf9 */ { NULL, NULL, 0 },
1292 /* 0xfa */ { NULL, NULL, 0 },
1293 /* 0xfb */ { NULL, NULL, 0 },
1294 /* 0xfc */ { NULL, NULL, 0 },
1295 /* 0xfd */ { NULL, NULL, 0 },
1296 /* 0xfe */ { NULL, NULL, 0 },
1297 /* 0xff */ { NULL, NULL, 0 }
1298
1299 };
1300
1301 /*******************************************************************
1302  allocate and initialize a reply packet
1303 ********************************************************************/
1304
1305 static bool create_outbuf(TALLOC_CTX *mem_ctx, struct smb_request *req,
1306                           const char *inbuf, char **outbuf, uint8_t num_words,
1307                           uint32_t num_bytes)
1308 {
1309         /*
1310          * Protect against integer wrap
1311          */
1312         if ((num_bytes > 0xffffff)
1313             || ((num_bytes + smb_size + num_words*2) > 0xffffff)) {
1314                 char *msg;
1315                 if (asprintf(&msg, "num_bytes too large: %u",
1316                              (unsigned)num_bytes) == -1) {
1317                         msg = CONST_DISCARD(char *, "num_bytes too large");
1318                 }
1319                 smb_panic(msg);
1320         }
1321
1322         *outbuf = TALLOC_ARRAY(mem_ctx, char,
1323                                smb_size + num_words*2 + num_bytes);
1324         if (*outbuf == NULL) {
1325                 return false;
1326         }
1327
1328         construct_reply_common(req, inbuf, *outbuf);
1329         srv_set_message(*outbuf, num_words, num_bytes, false);
1330         /*
1331          * Zero out the word area, the caller has to take care of the bcc area
1332          * himself
1333          */
1334         if (num_words != 0) {
1335                 memset(*outbuf + smb_vwv0, 0, num_words*2);
1336         }
1337
1338         return true;
1339 }
1340
1341 void reply_outbuf(struct smb_request *req, uint8 num_words, uint32 num_bytes)
1342 {
1343         char *outbuf;
1344         if (!create_outbuf(req, req, (char *)req->inbuf, &outbuf, num_words,
1345                            num_bytes)) {
1346                 smb_panic("could not allocate output buffer\n");
1347         }
1348         req->outbuf = (uint8_t *)outbuf;
1349 }
1350
1351
1352 /*******************************************************************
1353  Dump a packet to a file.
1354 ********************************************************************/
1355
1356 static void smb_dump(const char *name, int type, const char *data, ssize_t len)
1357 {
1358         int fd, i;
1359         char *fname = NULL;
1360         if (DEBUGLEVEL < 50) {
1361                 return;
1362         }
1363
1364         if (len < 4) len = smb_len(data)+4;
1365         for (i=1;i<100;i++) {
1366                 if (asprintf(&fname, "/tmp/%s.%d.%s", name, i,
1367                              type ? "req" : "resp") == -1) {
1368                         return;
1369                 }
1370                 fd = open(fname, O_WRONLY|O_CREAT|O_EXCL, 0644);
1371                 if (fd != -1 || errno != EEXIST) break;
1372         }
1373         if (fd != -1) {
1374                 ssize_t ret = write(fd, data, len);
1375                 if (ret != len)
1376                         DEBUG(0,("smb_dump: problem: write returned %d\n", (int)ret ));
1377                 close(fd);
1378                 DEBUG(0,("created %s len %lu\n", fname, (unsigned long)len));
1379         }
1380         SAFE_FREE(fname);
1381 }
1382
1383 /****************************************************************************
1384  Prepare everything for calling the actual request function, and potentially
1385  call the request function via the "new" interface.
1386
1387  Return False if the "legacy" function needs to be called, everything is
1388  prepared.
1389
1390  Return True if we're done.
1391
1392  I know this API sucks, but it is the one with the least code change I could
1393  find.
1394 ****************************************************************************/
1395
1396 static connection_struct *switch_message(uint8 type, struct smb_request *req, int size)
1397 {
1398         int flags;
1399         uint16 session_tag;
1400         connection_struct *conn = NULL;
1401         struct smbd_server_connection *sconn = req->sconn;
1402
1403         errno = 0;
1404
1405         /* Make sure this is an SMB packet. smb_size contains NetBIOS header
1406          * so subtract 4 from it. */
1407         if (!valid_smb_header(req->inbuf)
1408             || (size < (smb_size - 4))) {
1409                 DEBUG(2,("Non-SMB packet of length %d. Terminating server\n",
1410                          smb_len(req->inbuf)));
1411                 exit_server_cleanly("Non-SMB packet");
1412         }
1413
1414         if (smb_messages[type].fn == NULL) {
1415                 DEBUG(0,("Unknown message type %d!\n",type));
1416                 smb_dump("Unknown", 1, (char *)req->inbuf, size);
1417                 reply_unknown_new(req, type);
1418                 return NULL;
1419         }
1420
1421         flags = smb_messages[type].flags;
1422
1423         /* In share mode security we must ignore the vuid. */
1424         session_tag = (lp_security() == SEC_SHARE)
1425                 ? UID_FIELD_INVALID : req->vuid;
1426         conn = req->conn;
1427
1428         DEBUG(3,("switch message %s (pid %d) conn 0x%lx\n", smb_fn_name(type),
1429                  (int)sys_getpid(), (unsigned long)conn));
1430
1431         smb_dump(smb_fn_name(type), 1, (char *)req->inbuf, size);
1432
1433         /* Ensure this value is replaced in the incoming packet. */
1434         SSVAL(req->inbuf,smb_uid,session_tag);
1435
1436         /*
1437          * Ensure the correct username is in current_user_info.  This is a
1438          * really ugly bugfix for problems with multiple session_setup_and_X's
1439          * being done and allowing %U and %G substitutions to work correctly.
1440          * There is a reason this code is done here, don't move it unless you
1441          * know what you're doing... :-).
1442          * JRA.
1443          */
1444
1445         if (session_tag != sconn->smb1.sessions.last_session_tag) {
1446                 user_struct *vuser = NULL;
1447
1448                 sconn->smb1.sessions.last_session_tag = session_tag;
1449                 if(session_tag != UID_FIELD_INVALID) {
1450                         vuser = get_valid_user_struct(sconn, session_tag);
1451                         if (vuser) {
1452                                 set_current_user_info(
1453                                         vuser->server_info->sanitized_username,
1454                                         vuser->server_info->unix_name,
1455                                         vuser->server_info->info3->base.domain.string);
1456                         }
1457                 }
1458         }
1459
1460         /* Does this call need to be run as the connected user? */
1461         if (flags & AS_USER) {
1462
1463                 /* Does this call need a valid tree connection? */
1464                 if (!conn) {
1465                         /*
1466                          * Amazingly, the error code depends on the command
1467                          * (from Samba4).
1468                          */
1469                         if (type == SMBntcreateX) {
1470                                 reply_nterror(req, NT_STATUS_INVALID_HANDLE);
1471                         } else {
1472                                 reply_nterror(req, NT_STATUS_NETWORK_NAME_DELETED);
1473                         }
1474                         return NULL;
1475                 }
1476
1477                 if (!change_to_user(conn,session_tag)) {
1478                         DEBUG(0, ("Error: Could not change to user. Removing "
1479                                 "deferred open, mid=%llu.\n",
1480                                 (unsigned long long)req->mid));
1481                         reply_force_doserror(req, ERRSRV, ERRbaduid);
1482                         return conn;
1483                 }
1484
1485                 /* All NEED_WRITE and CAN_IPC flags must also have AS_USER. */
1486
1487                 /* Does it need write permission? */
1488                 if ((flags & NEED_WRITE) && !CAN_WRITE(conn)) {
1489                         reply_nterror(req, NT_STATUS_MEDIA_WRITE_PROTECTED);
1490                         return conn;
1491                 }
1492
1493                 /* IPC services are limited */
1494                 if (IS_IPC(conn) && !(flags & CAN_IPC)) {
1495                         reply_nterror(req, NT_STATUS_ACCESS_DENIED);
1496                         return conn;
1497                 }
1498         } else {
1499                 /* This call needs to be run as root */
1500                 change_to_root_user();
1501         }
1502
1503         /* load service specific parameters */
1504         if (conn) {
1505                 if (req->encrypted) {
1506                         conn->encrypted_tid = true;
1507                         /* encrypted required from now on. */
1508                         conn->encrypt_level = Required;
1509                 } else if (ENCRYPTION_REQUIRED(conn)) {
1510                         if (req->cmd != SMBtrans2 && req->cmd != SMBtranss2) {
1511                                 exit_server_cleanly("encryption required "
1512                                         "on connection");
1513                                 return conn;
1514                         }
1515                 }
1516
1517                 if (!set_current_service(conn,SVAL(req->inbuf,smb_flg),
1518                                          (flags & (AS_USER|DO_CHDIR)
1519                                           ?True:False))) {
1520                         reply_nterror(req, NT_STATUS_ACCESS_DENIED);
1521                         return conn;
1522                 }
1523                 conn->num_smb_operations++;
1524         }
1525
1526         /* does this protocol need to be run as guest? */
1527         if ((flags & AS_GUEST)
1528             && (!change_to_guest() ||
1529                 !check_access(smbd_server_fd(), lp_hostsallow(-1),
1530                               lp_hostsdeny(-1)))) {
1531                 reply_nterror(req, NT_STATUS_ACCESS_DENIED);
1532                 return conn;
1533         }
1534
1535         smb_messages[type].fn(req);
1536         return req->conn;
1537 }
1538
1539 /****************************************************************************
1540  Construct a reply to the incoming packet.
1541 ****************************************************************************/
1542
1543 static void construct_reply(char *inbuf, int size, size_t unread_bytes,
1544                             uint32_t seqnum, bool encrypted,
1545                             struct smb_perfcount_data *deferred_pcd)
1546 {
1547         connection_struct *conn;
1548         struct smb_request *req;
1549
1550         if (!(req = talloc(talloc_tos(), struct smb_request))) {
1551                 smb_panic("could not allocate smb_request");
1552         }
1553
1554         if (!init_smb_request(req, smbd_server_conn, (uint8 *)inbuf,
1555                               unread_bytes, encrypted, seqnum)) {
1556                 exit_server_cleanly("Invalid SMB request");
1557         }
1558
1559         req->inbuf  = (uint8_t *)talloc_move(req, &inbuf);
1560
1561         /* we popped this message off the queue - keep original perf data */
1562         if (deferred_pcd)
1563                 req->pcd = *deferred_pcd;
1564         else {
1565                 SMB_PERFCOUNT_START(&req->pcd);
1566                 SMB_PERFCOUNT_SET_OP(&req->pcd, req->cmd);
1567                 SMB_PERFCOUNT_SET_MSGLEN_IN(&req->pcd, size);
1568         }
1569
1570         conn = switch_message(req->cmd, req, size);
1571
1572         if (req->unread_bytes) {
1573                 /* writeX failed. drain socket. */
1574                 if (drain_socket(smbd_server_fd(), req->unread_bytes) !=
1575                                 req->unread_bytes) {
1576                         smb_panic("failed to drain pending bytes");
1577                 }
1578                 req->unread_bytes = 0;
1579         }
1580
1581         if (req->done) {
1582                 TALLOC_FREE(req);
1583                 return;
1584         }
1585
1586         if (req->outbuf == NULL) {
1587                 return;
1588         }
1589
1590         if (CVAL(req->outbuf,0) == 0) {
1591                 show_msg((char *)req->outbuf);
1592         }
1593
1594         if (!srv_send_smb(smbd_server_fd(),
1595                         (char *)req->outbuf,
1596                         true, req->seqnum+1,
1597                         IS_CONN_ENCRYPTED(conn)||req->encrypted,
1598                         &req->pcd)) {
1599                 exit_server_cleanly("construct_reply: srv_send_smb failed.");
1600         }
1601
1602         TALLOC_FREE(req);
1603
1604         return;
1605 }
1606
1607 /****************************************************************************
1608  Process an smb from the client
1609 ****************************************************************************/
1610 static void process_smb(struct smbd_server_connection *conn,
1611                         uint8_t *inbuf, size_t nread, size_t unread_bytes,
1612                         uint32_t seqnum, bool encrypted,
1613                         struct smb_perfcount_data *deferred_pcd)
1614 {
1615         int msg_type = CVAL(inbuf,0);
1616
1617         DO_PROFILE_INC(smb_count);
1618
1619         DEBUG( 6, ( "got message type 0x%x of len 0x%x\n", msg_type,
1620                     smb_len(inbuf) ) );
1621         DEBUG( 3, ( "Transaction %d of length %d (%u toread)\n", trans_num,
1622                                 (int)nread,
1623                                 (unsigned int)unread_bytes ));
1624
1625         if (msg_type != 0) {
1626                 /*
1627                  * NetBIOS session request, keepalive, etc.
1628                  */
1629                 reply_special(conn, (char *)inbuf);
1630                 goto done;
1631         }
1632
1633         if (smbd_server_conn->using_smb2) {
1634                 /* At this point we're not really using smb2,
1635                  * we make the decision here.. */
1636                 if (smbd_is_smb2_header(inbuf, nread)) {
1637                         smbd_smb2_first_negprot(smbd_server_conn, inbuf, nread);
1638                         return;
1639                 } else if (nread >= smb_size && valid_smb_header(inbuf)
1640                                 && CVAL(inbuf, smb_com) != 0x72) {
1641                         /* This is a non-negprot SMB1 packet.
1642                            Disable SMB2 from now on. */
1643                         smbd_server_conn->using_smb2 = false;
1644                 }
1645         }
1646
1647         show_msg((char *)inbuf);
1648
1649         construct_reply((char *)inbuf,nread,unread_bytes,seqnum,encrypted,deferred_pcd);
1650         trans_num++;
1651
1652 done:
1653         conn->smb1.num_requests++;
1654
1655         /* The timeout_processing function isn't run nearly
1656            often enough to implement 'max log size' without
1657            overrunning the size of the file by many megabytes.
1658            This is especially true if we are running at debug
1659            level 10.  Checking every 50 SMBs is a nice
1660            tradeoff of performance vs log file size overrun. */
1661
1662         if ((conn->smb1.num_requests % 50) == 0 &&
1663             need_to_check_log_size()) {
1664                 change_to_root_user();
1665                 check_log_size();
1666         }
1667 }
1668
1669 /****************************************************************************
1670  Return a string containing the function name of a SMB command.
1671 ****************************************************************************/
1672
1673 const char *smb_fn_name(int type)
1674 {
1675         const char *unknown_name = "SMBunknown";
1676
1677         if (smb_messages[type].name == NULL)
1678                 return(unknown_name);
1679
1680         return(smb_messages[type].name);
1681 }
1682
1683 /****************************************************************************
1684  Helper functions for contruct_reply.
1685 ****************************************************************************/
1686
1687 void add_to_common_flags2(uint32 v)
1688 {
1689         common_flags2 |= v;
1690 }
1691
1692 void remove_from_common_flags2(uint32 v)
1693 {
1694         common_flags2 &= ~v;
1695 }
1696
1697 static void construct_reply_common(struct smb_request *req, const char *inbuf,
1698                                    char *outbuf)
1699 {
1700         srv_set_message(outbuf,0,0,false);
1701
1702         SCVAL(outbuf, smb_com, req->cmd);
1703         SIVAL(outbuf,smb_rcls,0);
1704         SCVAL(outbuf,smb_flg, FLAG_REPLY | (CVAL(inbuf,smb_flg) & FLAG_CASELESS_PATHNAMES)); 
1705         SSVAL(outbuf,smb_flg2,
1706                 (SVAL(inbuf,smb_flg2) & FLAGS2_UNICODE_STRINGS) |
1707                 common_flags2);
1708         memset(outbuf+smb_pidhigh,'\0',(smb_tid-smb_pidhigh));
1709
1710         SSVAL(outbuf,smb_tid,SVAL(inbuf,smb_tid));
1711         SSVAL(outbuf,smb_pid,SVAL(inbuf,smb_pid));
1712         SSVAL(outbuf,smb_uid,SVAL(inbuf,smb_uid));
1713         SSVAL(outbuf,smb_mid,SVAL(inbuf,smb_mid));
1714 }
1715
1716 void construct_reply_common_req(struct smb_request *req, char *outbuf)
1717 {
1718         construct_reply_common(req, (char *)req->inbuf, outbuf);
1719 }
1720
1721 /*
1722  * How many bytes have we already accumulated up to the current wct field
1723  * offset?
1724  */
1725
1726 size_t req_wct_ofs(struct smb_request *req)
1727 {
1728         size_t buf_size;
1729
1730         if (req->chain_outbuf == NULL) {
1731                 return smb_wct - 4;
1732         }
1733         buf_size = talloc_get_size(req->chain_outbuf);
1734         if ((buf_size % 4) != 0) {
1735                 buf_size += (4 - (buf_size % 4));
1736         }
1737         return buf_size - 4;
1738 }
1739
1740 /*
1741  * Hack around reply_nterror & friends not being aware of chained requests,
1742  * generating illegal (i.e. wct==0) chain replies.
1743  */
1744
1745 static void fixup_chain_error_packet(struct smb_request *req)
1746 {
1747         uint8_t *outbuf = req->outbuf;
1748         req->outbuf = NULL;
1749         reply_outbuf(req, 2, 0);
1750         memcpy(req->outbuf, outbuf, smb_wct);
1751         TALLOC_FREE(outbuf);
1752         SCVAL(req->outbuf, smb_vwv0, 0xff);
1753 }
1754
1755 /**
1756  * @brief Find the smb_cmd offset of the last command pushed
1757  * @param[in] buf       The buffer we're building up
1758  * @retval              Where can we put our next andx cmd?
1759  *
1760  * While chaining requests, the "next" request we're looking at needs to put
1761  * its SMB_Command before the data the previous request already built up added
1762  * to the chain. Find the offset to the place where we have to put our cmd.
1763  */
1764
1765 static bool find_andx_cmd_ofs(uint8_t *buf, size_t *pofs)
1766 {
1767         uint8_t cmd;
1768         size_t ofs;
1769
1770         cmd = CVAL(buf, smb_com);
1771
1772         SMB_ASSERT(is_andx_req(cmd));
1773
1774         ofs = smb_vwv0;
1775
1776         while (CVAL(buf, ofs) != 0xff) {
1777
1778                 if (!is_andx_req(CVAL(buf, ofs))) {
1779                         return false;
1780                 }
1781
1782                 /*
1783                  * ofs is from start of smb header, so add the 4 length
1784                  * bytes. The next cmd is right after the wct field.
1785                  */
1786                 ofs = SVAL(buf, ofs+2) + 4 + 1;
1787
1788                 SMB_ASSERT(ofs+4 < talloc_get_size(buf));
1789         }
1790
1791         *pofs = ofs;
1792         return true;
1793 }
1794
1795 /**
1796  * @brief Do the smb chaining at a buffer level
1797  * @param[in] poutbuf           Pointer to the talloc'ed buffer to be modified
1798  * @param[in] smb_command       The command that we want to issue
1799  * @param[in] wct               How many words?
1800  * @param[in] vwv               The words, already in network order
1801  * @param[in] bytes_alignment   How shall we align "bytes"?
1802  * @param[in] num_bytes         How many bytes?
1803  * @param[in] bytes             The data the request ships
1804  *
1805  * smb_splice_chain() adds the vwv and bytes to the request already present in
1806  * *poutbuf.
1807  */
1808
1809 static bool smb_splice_chain(uint8_t **poutbuf, uint8_t smb_command,
1810                              uint8_t wct, const uint16_t *vwv,
1811                              size_t bytes_alignment,
1812                              uint32_t num_bytes, const uint8_t *bytes)
1813 {
1814         uint8_t *outbuf;
1815         size_t old_size, new_size;
1816         size_t ofs;
1817         size_t chain_padding = 0;
1818         size_t bytes_padding = 0;
1819         bool first_request;
1820
1821         old_size = talloc_get_size(*poutbuf);
1822
1823         /*
1824          * old_size == smb_wct means we're pushing the first request in for
1825          * libsmb/
1826          */
1827
1828         first_request = (old_size == smb_wct);
1829
1830         if (!first_request && ((old_size % 4) != 0)) {
1831                 /*
1832                  * Align the wct field of subsequent requests to a 4-byte
1833                  * boundary
1834                  */
1835                 chain_padding = 4 - (old_size % 4);
1836         }
1837
1838         /*
1839          * After the old request comes the new wct field (1 byte), the vwv's
1840          * and the num_bytes field. After at we might need to align the bytes
1841          * given to us to "bytes_alignment", increasing the num_bytes value.
1842          */
1843
1844         new_size = old_size + chain_padding + 1 + wct * sizeof(uint16_t) + 2;
1845
1846         if ((bytes_alignment != 0) && ((new_size % bytes_alignment) != 0)) {
1847                 bytes_padding = bytes_alignment - (new_size % bytes_alignment);
1848         }
1849
1850         new_size += bytes_padding + num_bytes;
1851
1852         if ((smb_command != SMBwriteX) && (new_size > 0xffff)) {
1853                 DEBUG(1, ("splice_chain: %u bytes won't fit\n",
1854                           (unsigned)new_size));
1855                 return false;
1856         }
1857
1858         outbuf = TALLOC_REALLOC_ARRAY(NULL, *poutbuf, uint8_t, new_size);
1859         if (outbuf == NULL) {
1860                 DEBUG(0, ("talloc failed\n"));
1861                 return false;
1862         }
1863         *poutbuf = outbuf;
1864
1865         if (first_request) {
1866                 SCVAL(outbuf, smb_com, smb_command);
1867         } else {
1868                 size_t andx_cmd_ofs;
1869
1870                 if (!find_andx_cmd_ofs(outbuf, &andx_cmd_ofs)) {
1871                         DEBUG(1, ("invalid command chain\n"));
1872                         *poutbuf = TALLOC_REALLOC_ARRAY(
1873                                 NULL, *poutbuf, uint8_t, old_size);
1874                         return false;
1875                 }
1876
1877                 if (chain_padding != 0) {
1878                         memset(outbuf + old_size, 0, chain_padding);
1879                         old_size += chain_padding;
1880                 }
1881
1882                 SCVAL(outbuf, andx_cmd_ofs, smb_command);
1883                 SSVAL(outbuf, andx_cmd_ofs + 2, old_size - 4);
1884         }
1885
1886         ofs = old_size;
1887
1888         /*
1889          * Push the chained request:
1890          *
1891          * wct field
1892          */
1893
1894         SCVAL(outbuf, ofs, wct);
1895         ofs += 1;
1896
1897         /*
1898          * vwv array
1899          */
1900
1901         memcpy(outbuf + ofs, vwv, sizeof(uint16_t) * wct);
1902         ofs += sizeof(uint16_t) * wct;
1903
1904         /*
1905          * bcc (byte count)
1906          */
1907
1908         SSVAL(outbuf, ofs, num_bytes + bytes_padding);
1909         ofs += sizeof(uint16_t);
1910
1911         /*
1912          * padding
1913          */
1914
1915         if (bytes_padding != 0) {
1916                 memset(outbuf + ofs, 0, bytes_padding);
1917                 ofs += bytes_padding;
1918         }
1919
1920         /*
1921          * The bytes field
1922          */
1923
1924         memcpy(outbuf + ofs, bytes, num_bytes);
1925
1926         return true;
1927 }
1928
1929 /****************************************************************************
1930  Construct a chained reply and add it to the already made reply
1931 ****************************************************************************/
1932
1933 void chain_reply(struct smb_request *req)
1934 {
1935         size_t smblen = smb_len(req->inbuf);
1936         size_t already_used, length_needed;
1937         uint8_t chain_cmd;
1938         uint32_t chain_offset;  /* uint32_t to avoid overflow */
1939
1940         uint8_t wct;
1941         uint16_t *vwv;
1942         uint16_t buflen;
1943         uint8_t *buf;
1944
1945         if (IVAL(req->outbuf, smb_rcls) != 0) {
1946                 fixup_chain_error_packet(req);
1947         }
1948
1949         /*
1950          * Any of the AndX requests and replies have at least a wct of
1951          * 2. vwv[0] is the next command, vwv[1] is the offset from the
1952          * beginning of the SMB header to the next wct field.
1953          *
1954          * None of the AndX requests put anything valuable in vwv[0] and [1],
1955          * so we can overwrite it here to form the chain.
1956          */
1957
1958         if ((req->wct < 2) || (CVAL(req->outbuf, smb_wct) < 2)) {
1959                 if (req->chain_outbuf == NULL) {
1960                         req->chain_outbuf = TALLOC_REALLOC_ARRAY(
1961                                 req, req->outbuf, uint8_t,
1962                                 smb_len(req->outbuf) + 4);
1963                         if (req->chain_outbuf == NULL) {
1964                                 smb_panic("talloc failed");
1965                         }
1966                 }
1967                 req->outbuf = NULL;
1968                 goto error;
1969         }
1970
1971         /*
1972          * Here we assume that this is the end of the chain. For that we need
1973          * to set "next command" to 0xff and the offset to 0. If we later find
1974          * more commands in the chain, this will be overwritten again.
1975          */
1976
1977         SCVAL(req->outbuf, smb_vwv0, 0xff);
1978         SCVAL(req->outbuf, smb_vwv0+1, 0);
1979         SSVAL(req->outbuf, smb_vwv1, 0);
1980
1981         if (req->chain_outbuf == NULL) {
1982                 /*
1983                  * In req->chain_outbuf we collect all the replies. Start the
1984                  * chain by copying in the first reply.
1985                  *
1986                  * We do the realloc because later on we depend on
1987                  * talloc_get_size to determine the length of
1988                  * chain_outbuf. The reply_xxx routines might have
1989                  * over-allocated (reply_pipe_read_and_X used to be such an
1990                  * example).
1991                  */
1992                 req->chain_outbuf = TALLOC_REALLOC_ARRAY(
1993                         req, req->outbuf, uint8_t, smb_len(req->outbuf) + 4);
1994                 if (req->chain_outbuf == NULL) {
1995                         smb_panic("talloc failed");
1996                 }
1997                 req->outbuf = NULL;
1998         } else {
1999                 /*
2000                  * Update smb headers where subsequent chained commands
2001                  * may have updated them.
2002                  */
2003                 SCVAL(req->chain_outbuf, smb_tid, CVAL(req->outbuf, smb_tid));
2004                 SCVAL(req->chain_outbuf, smb_uid, CVAL(req->outbuf, smb_uid));
2005
2006                 if (!smb_splice_chain(&req->chain_outbuf,
2007                                       CVAL(req->outbuf, smb_com),
2008                                       CVAL(req->outbuf, smb_wct),
2009                                       (uint16_t *)(req->outbuf + smb_vwv),
2010                                       0, smb_buflen(req->outbuf),
2011                                       (uint8_t *)smb_buf(req->outbuf))) {
2012                         goto error;
2013                 }
2014                 TALLOC_FREE(req->outbuf);
2015         }
2016
2017         /*
2018          * We use the old request's vwv field to grab the next chained command
2019          * and offset into the chained fields.
2020          */
2021
2022         chain_cmd = CVAL(req->vwv+0, 0);
2023         chain_offset = SVAL(req->vwv+1, 0);
2024
2025         if (chain_cmd == 0xff) {
2026                 /*
2027                  * End of chain, no more requests from the client. So ship the
2028                  * replies.
2029                  */
2030                 smb_setlen((char *)(req->chain_outbuf),
2031                            talloc_get_size(req->chain_outbuf) - 4);
2032
2033                 if (!srv_send_smb(smbd_server_fd(), (char *)req->chain_outbuf,
2034                                   true, req->seqnum+1,
2035                                   IS_CONN_ENCRYPTED(req->conn)
2036                                   ||req->encrypted,
2037                                   &req->pcd)) {
2038                         exit_server_cleanly("chain_reply: srv_send_smb "
2039                                             "failed.");
2040                 }
2041                 TALLOC_FREE(req->chain_outbuf);
2042                 req->done = true;
2043                 return;
2044         }
2045
2046         /* add a new perfcounter for this element of chain */
2047         SMB_PERFCOUNT_ADD(&req->pcd);
2048         SMB_PERFCOUNT_SET_OP(&req->pcd, chain_cmd);
2049         SMB_PERFCOUNT_SET_MSGLEN_IN(&req->pcd, smblen);
2050
2051         /*
2052          * Check if the client tries to fool us. The request so far uses the
2053          * space to the end of the byte buffer in the request just
2054          * processed. The chain_offset can't point into that area. If that was
2055          * the case, we could end up with an endless processing of the chain,
2056          * we would always handle the same request.
2057          */
2058
2059         already_used = PTR_DIFF(req->buf+req->buflen, smb_base(req->inbuf));
2060         if (chain_offset < already_used) {
2061                 goto error;
2062         }
2063
2064         /*
2065          * Next check: Make sure the chain offset does not point beyond the
2066          * overall smb request length.
2067          */
2068
2069         length_needed = chain_offset+1; /* wct */
2070         if (length_needed > smblen) {
2071                 goto error;
2072         }
2073
2074         /*
2075          * Now comes the pointer magic. Goal here is to set up req->vwv and
2076          * req->buf correctly again to be able to call the subsequent
2077          * switch_message(). The chain offset (the former vwv[1]) points at
2078          * the new wct field.
2079          */
2080
2081         wct = CVAL(smb_base(req->inbuf), chain_offset);
2082
2083         /*
2084          * Next consistency check: Make the new vwv array fits in the overall
2085          * smb request.
2086          */
2087
2088         length_needed += (wct+1)*sizeof(uint16_t); /* vwv+buflen */
2089         if (length_needed > smblen) {
2090                 goto error;
2091         }
2092         vwv = (uint16_t *)(smb_base(req->inbuf) + chain_offset + 1);
2093
2094         /*
2095          * Now grab the new byte buffer....
2096          */
2097
2098         buflen = SVAL(vwv+wct, 0);
2099
2100         /*
2101          * .. and check that it fits.
2102          */
2103
2104         length_needed += buflen;
2105         if (length_needed > smblen) {
2106                 goto error;
2107         }
2108         buf = (uint8_t *)(vwv+wct+1);
2109
2110         req->cmd = chain_cmd;
2111         req->wct = wct;
2112         req->vwv = vwv;
2113         req->buflen = buflen;
2114         req->buf = buf;
2115
2116         switch_message(chain_cmd, req, smblen);
2117
2118         if (req->outbuf == NULL) {
2119                 /*
2120                  * This happens if the chained command has suspended itself or
2121                  * if it has called srv_send_smb() itself.
2122                  */
2123                 return;
2124         }
2125
2126         /*
2127          * We end up here if the chained command was not itself chained or
2128          * suspended, but for example a close() command. We now need to splice
2129          * the chained commands' outbuf into the already built up chain_outbuf
2130          * and ship the result.
2131          */
2132         goto done;
2133
2134  error:
2135         /*
2136          * We end up here if there's any error in the chain syntax. Report a
2137          * DOS error, just like Windows does.
2138          */
2139         reply_force_doserror(req, ERRSRV, ERRerror);
2140         fixup_chain_error_packet(req);
2141
2142  done:
2143         /*
2144          * This scary statement intends to set the
2145          * FLAGS2_32_BIT_ERROR_CODES flg2 field in req->chain_outbuf
2146          * to the value req->outbuf carries
2147          */
2148         SSVAL(req->chain_outbuf, smb_flg2,
2149               (SVAL(req->chain_outbuf, smb_flg2) & ~FLAGS2_32_BIT_ERROR_CODES)
2150               | (SVAL(req->outbuf, smb_flg2) & FLAGS2_32_BIT_ERROR_CODES));
2151
2152         /*
2153          * Transfer the error codes from the subrequest to the main one
2154          */
2155         SSVAL(req->chain_outbuf, smb_rcls, SVAL(req->outbuf, smb_rcls));
2156         SSVAL(req->chain_outbuf, smb_err, SVAL(req->outbuf, smb_err));
2157
2158         if (!smb_splice_chain(&req->chain_outbuf,
2159                               CVAL(req->outbuf, smb_com),
2160                               CVAL(req->outbuf, smb_wct),
2161                               (uint16_t *)(req->outbuf + smb_vwv),
2162                               0, smb_buflen(req->outbuf),
2163                               (uint8_t *)smb_buf(req->outbuf))) {
2164                 exit_server_cleanly("chain_reply: smb_splice_chain failed\n");
2165         }
2166         TALLOC_FREE(req->outbuf);
2167
2168         smb_setlen((char *)(req->chain_outbuf),
2169                    talloc_get_size(req->chain_outbuf) - 4);
2170
2171         show_msg((char *)(req->chain_outbuf));
2172
2173         if (!srv_send_smb(smbd_server_fd(), (char *)req->chain_outbuf,
2174                           true, req->seqnum+1,
2175                           IS_CONN_ENCRYPTED(req->conn)||req->encrypted,
2176                           &req->pcd)) {
2177                 exit_server_cleanly("construct_reply: srv_send_smb failed.");
2178         }
2179         TALLOC_FREE(req->chain_outbuf);
2180         req->done = true;
2181 }
2182
2183 /****************************************************************************
2184  Check if services need reloading.
2185 ****************************************************************************/
2186
2187 static void check_reload(struct messaging_context *msg_ctx, time_t t)
2188 {
2189         time_t printcap_cache_time = (time_t)lp_printcap_cache_time();
2190
2191         if(last_smb_conf_reload_time == 0) {
2192                 last_smb_conf_reload_time = t;
2193                 /* Our printing subsystem might not be ready at smbd start up.
2194                    Then no printer is available till the first printers check
2195                    is performed.  A lower initial interval circumvents this. */
2196                 if ( printcap_cache_time > 60 )
2197                         last_printer_reload_time = t - printcap_cache_time + 60;
2198                 else
2199                         last_printer_reload_time = t;
2200         }
2201
2202         if (mypid != getpid()) { /* First time or fork happened meanwhile */
2203                 /* randomize over 60 second the printcap reload to avoid all
2204                  * process hitting cupsd at the same time */
2205                 int time_range = 60;
2206
2207                 last_printer_reload_time += random() % time_range;
2208                 mypid = getpid();
2209         }
2210
2211         if (t >= last_smb_conf_reload_time+SMBD_RELOAD_CHECK) {
2212                 reload_services(msg_ctx, True);
2213                 last_smb_conf_reload_time = t;
2214         }
2215
2216         /* 'printcap cache time = 0' disable the feature */
2217
2218         if ( printcap_cache_time != 0 )
2219         { 
2220                 /* see if it's time to reload or if the clock has been set back */
2221
2222                 if ( (t >= last_printer_reload_time+printcap_cache_time) 
2223                         || (t-last_printer_reload_time  < 0) ) 
2224                 {
2225                         DEBUG( 3,( "Printcap cache time expired.\n"));
2226                         reload_printers(msg_ctx);
2227                         last_printer_reload_time = t;
2228                 }
2229         }
2230 }
2231
2232 static bool fd_is_readable(int fd)
2233 {
2234         fd_set fds;
2235         struct timeval timeout = {0, };
2236         int ret;
2237
2238         FD_ZERO(&fds);
2239         FD_SET(fd, &fds);
2240
2241         ret = sys_select(fd+1, &fds, NULL, NULL, &timeout);
2242         if (ret == -1) {
2243                 return false;
2244         }
2245         return FD_ISSET(fd, &fds);
2246 }
2247
2248 static void smbd_server_connection_write_handler(struct smbd_server_connection *conn)
2249 {
2250         /* TODO: make write nonblocking */
2251 }
2252
2253 static void smbd_server_connection_read_handler(
2254         struct smbd_server_connection *conn, int fd)
2255 {
2256         uint8_t *inbuf = NULL;
2257         size_t inbuf_len = 0;
2258         size_t unread_bytes = 0;
2259         bool encrypted = false;
2260         TALLOC_CTX *mem_ctx = talloc_tos();
2261         NTSTATUS status;
2262         uint32_t seqnum;
2263
2264         bool from_client = (smbd_server_fd() == fd);
2265
2266         if (from_client) {
2267                 smbd_lock_socket(conn);
2268
2269                 if (!fd_is_readable(smbd_server_fd())) {
2270                         DEBUG(10,("the echo listener was faster\n"));
2271                         smbd_unlock_socket(conn);
2272                         return;
2273                 }
2274
2275                 /* TODO: make this completely nonblocking */
2276                 status = receive_smb_talloc(mem_ctx, fd,
2277                                             (char **)(void *)&inbuf,
2278                                             0, /* timeout */
2279                                             &unread_bytes,
2280                                             &encrypted,
2281                                             &inbuf_len, &seqnum,
2282                                             false /* trusted channel */);
2283                 smbd_unlock_socket(conn);
2284         } else {
2285                 /* TODO: make this completely nonblocking */
2286                 status = receive_smb_talloc(mem_ctx, fd,
2287                                             (char **)(void *)&inbuf,
2288                                             0, /* timeout */
2289                                             &unread_bytes,
2290                                             &encrypted,
2291                                             &inbuf_len, &seqnum,
2292                                             true /* trusted channel */);
2293         }
2294
2295         if (NT_STATUS_EQUAL(status, NT_STATUS_RETRY)) {
2296                 goto process;
2297         }
2298         if (NT_STATUS_IS_ERR(status)) {
2299                 exit_server_cleanly("failed to receive smb request");
2300         }
2301         if (!NT_STATUS_IS_OK(status)) {
2302                 return;
2303         }
2304
2305 process:
2306         process_smb(conn, inbuf, inbuf_len, unread_bytes,
2307                     seqnum, encrypted, NULL);
2308 }
2309
2310 static void smbd_server_connection_handler(struct event_context *ev,
2311                                            struct fd_event *fde,
2312                                            uint16_t flags,
2313                                            void *private_data)
2314 {
2315         struct smbd_server_connection *conn = talloc_get_type(private_data,
2316                                               struct smbd_server_connection);
2317
2318         if (flags & EVENT_FD_WRITE) {
2319                 smbd_server_connection_write_handler(conn);
2320                 return;
2321         }
2322         if (flags & EVENT_FD_READ) {
2323                 smbd_server_connection_read_handler(conn, smbd_server_fd());
2324                 return;
2325         }
2326 }
2327
2328 static void smbd_server_echo_handler(struct event_context *ev,
2329                                      struct fd_event *fde,
2330                                      uint16_t flags,
2331                                      void *private_data)
2332 {
2333         struct smbd_server_connection *conn = talloc_get_type(private_data,
2334                                               struct smbd_server_connection);
2335
2336         if (flags & EVENT_FD_WRITE) {
2337                 smbd_server_connection_write_handler(conn);
2338                 return;
2339         }
2340         if (flags & EVENT_FD_READ) {
2341                 smbd_server_connection_read_handler(
2342                         conn, conn->smb1.echo_handler.trusted_fd);
2343                 return;
2344         }
2345 }
2346
2347 /****************************************************************************
2348 received when we should release a specific IP
2349 ****************************************************************************/
2350 static void release_ip(const char *ip, void *priv)
2351 {
2352         char addr[INET6_ADDRSTRLEN];
2353         char *p = addr;
2354
2355         client_socket_addr(get_client_fd(),addr,sizeof(addr));
2356
2357         if (strncmp("::ffff:", addr, 7) == 0) {
2358                 p = addr + 7;
2359         }
2360
2361         if ((strcmp(p, ip) == 0) || ((p != addr) && strcmp(addr, ip) == 0)) {
2362                 /* we can't afford to do a clean exit - that involves
2363                    database writes, which would potentially mean we
2364                    are still running after the failover has finished -
2365                    we have to get rid of this process ID straight
2366                    away */
2367                 DEBUG(0,("Got release IP message for our IP %s - exiting immediately\n",
2368                         ip));
2369                 /* note we must exit with non-zero status so the unclean handler gets
2370                    called in the parent, so that the brl database is tickled */
2371                 _exit(1);
2372         }
2373 }
2374
2375 static void msg_release_ip(struct messaging_context *msg_ctx, void *private_data,
2376                            uint32_t msg_type, struct server_id server_id, DATA_BLOB *data)
2377 {
2378         release_ip((char *)data->data, NULL);
2379 }
2380
2381 #ifdef CLUSTER_SUPPORT
2382 static int client_get_tcp_info(struct sockaddr_storage *server,
2383                                struct sockaddr_storage *client)
2384 {
2385         socklen_t length;
2386         if (server_fd == -1) {
2387                 return -1;
2388         }
2389         length = sizeof(*server);
2390         if (getsockname(server_fd, (struct sockaddr *)server, &length) != 0) {
2391                 return -1;
2392         }
2393         length = sizeof(*client);
2394         if (getpeername(server_fd, (struct sockaddr *)client, &length) != 0) {
2395                 return -1;
2396         }
2397         return 0;
2398 }
2399 #endif
2400
2401 /*
2402  * Send keepalive packets to our client
2403  */
2404 static bool keepalive_fn(const struct timeval *now, void *private_data)
2405 {
2406         struct smbd_server_connection *sconn = smbd_server_conn;
2407         bool ret;
2408
2409         if (sconn->using_smb2) {
2410                 /* Don't do keepalives on an SMB2 connection. */
2411                 return false;
2412         }
2413
2414         smbd_lock_socket(smbd_server_conn);
2415         ret = send_keepalive(smbd_server_fd());
2416         smbd_unlock_socket(smbd_server_conn);
2417
2418         if (!ret) {
2419                 DEBUG( 2, ( "Keepalive failed - exiting.\n" ) );
2420                 return False;
2421         }
2422         return True;
2423 }
2424
2425 /*
2426  * Do the recurring check if we're idle
2427  */
2428 static bool deadtime_fn(const struct timeval *now, void *private_data)
2429 {
2430         struct smbd_server_connection *sconn =
2431                 (struct smbd_server_connection *)private_data;
2432
2433         if (sconn->using_smb2) {
2434                 /* TODO: implement real idle check */
2435                 if (sconn->smb2.sessions.list) {
2436                         return true;
2437                 }
2438                 DEBUG( 2, ( "Closing idle SMB2 connection\n" ) );
2439                 messaging_send(sconn->msg_ctx, procid_self(),
2440                                MSG_SHUTDOWN, &data_blob_null);
2441                 return false;
2442         }
2443
2444         if ((conn_num_open(sconn) == 0)
2445             || (conn_idle_all(sconn, now->tv_sec))) {
2446                 DEBUG( 2, ( "Closing idle SMB1 connection\n" ) );
2447                 messaging_send(sconn->msg_ctx, procid_self(),
2448                                MSG_SHUTDOWN, &data_blob_null);
2449                 return False;
2450         }
2451
2452         return True;
2453 }
2454
2455 /*
2456  * Do the recurring log file and smb.conf reload checks.
2457  */
2458
2459 static bool housekeeping_fn(const struct timeval *now, void *private_data)
2460 {
2461         struct messaging_context *msg_ctx = talloc_get_type_abort(
2462                 private_data, struct messaging_context);
2463         change_to_root_user();
2464
2465         /* update printer queue caches if necessary */
2466         update_monitored_printq_cache(msg_ctx);
2467
2468         /* check if we need to reload services */
2469         check_reload(msg_ctx, time(NULL));
2470
2471         /* Change machine password if neccessary. */
2472         attempt_machine_password_change();
2473
2474         /*
2475          * Force a log file check.
2476          */
2477         force_check_log_size();
2478         check_log_size();
2479         return true;
2480 }
2481
2482 static int create_unlink_tmp(const char *dir)
2483 {
2484         char *fname;
2485         int fd;
2486
2487         fname = talloc_asprintf(talloc_tos(), "%s/listenerlock_XXXXXX", dir);
2488         if (fname == NULL) {
2489                 errno = ENOMEM;
2490                 return -1;
2491         }
2492         fd = mkstemp(fname);
2493         if (fd == -1) {
2494                 TALLOC_FREE(fname);
2495                 return -1;
2496         }
2497         if (unlink(fname) == -1) {
2498                 int sys_errno = errno;
2499                 close(fd);
2500                 TALLOC_FREE(fname);
2501                 errno = sys_errno;
2502                 return -1;
2503         }
2504         TALLOC_FREE(fname);
2505         return fd;
2506 }
2507
2508 struct smbd_echo_state {
2509         struct tevent_context *ev;
2510         struct iovec *pending;
2511         struct smbd_server_connection *sconn;
2512         int parent_pipe;
2513
2514         struct tevent_fd *parent_fde;
2515
2516         struct tevent_fd *read_fde;
2517         struct tevent_req *write_req;
2518 };
2519
2520 static void smbd_echo_writer_done(struct tevent_req *req);
2521
2522 static void smbd_echo_activate_writer(struct smbd_echo_state *state)
2523 {
2524         int num_pending;
2525
2526         if (state->write_req != NULL) {
2527                 return;
2528         }
2529
2530         num_pending = talloc_array_length(state->pending);
2531         if (num_pending == 0) {
2532                 return;
2533         }
2534
2535         state->write_req = writev_send(state, state->ev, NULL,
2536                                        state->parent_pipe, false,
2537                                        state->pending, num_pending);
2538         if (state->write_req == NULL) {
2539                 DEBUG(1, ("writev_send failed\n"));
2540                 exit(1);
2541         }
2542
2543         talloc_steal(state->write_req, state->pending);
2544         state->pending = NULL;
2545
2546         tevent_req_set_callback(state->write_req, smbd_echo_writer_done,
2547                                 state);
2548 }
2549
2550 static void smbd_echo_writer_done(struct tevent_req *req)
2551 {
2552         struct smbd_echo_state *state = tevent_req_callback_data(
2553                 req, struct smbd_echo_state);
2554         ssize_t written;
2555         int err;
2556
2557         written = writev_recv(req, &err);
2558         TALLOC_FREE(req);
2559         state->write_req = NULL;
2560         if (written == -1) {
2561                 DEBUG(1, ("writev to parent failed: %s\n", strerror(err)));
2562                 exit(1);
2563         }
2564         DEBUG(10,("echo_handler[%d]: forwarded pdu to main\n", (int)sys_getpid()));
2565         smbd_echo_activate_writer(state);
2566 }
2567
2568 static bool smbd_echo_reply(int fd,
2569                             uint8_t *inbuf, size_t inbuf_len,
2570                             uint32_t seqnum)
2571 {
2572         struct smb_request req;
2573         uint16_t num_replies;
2574         size_t out_len;
2575         char *outbuf;
2576         bool ok;
2577
2578         if (inbuf_len < smb_size) {
2579                 DEBUG(10, ("Got short packet: %d bytes\n", (int)inbuf_len));
2580                 return false;
2581         }
2582         if (!valid_smb_header(inbuf)) {
2583                 DEBUG(10, ("Got invalid SMB header\n"));
2584                 return false;
2585         }
2586
2587         if (!init_smb_request(&req, smbd_server_conn, inbuf, 0, false,
2588                               seqnum)) {
2589                 return false;
2590         }
2591         req.inbuf = inbuf;
2592
2593         DEBUG(10, ("smbecho handler got cmd %d (%s)\n", (int)req.cmd,
2594                    smb_messages[req.cmd].name
2595                    ? smb_messages[req.cmd].name : "unknown"));
2596
2597         if (req.cmd != SMBecho) {
2598                 return false;
2599         }
2600         if (req.wct < 1) {
2601                 return false;
2602         }
2603
2604         num_replies = SVAL(req.vwv+0, 0);
2605         if (num_replies != 1) {
2606                 /* Not a Windows "Hey, you're still there?" request */
2607                 return false;
2608         }
2609
2610         if (!create_outbuf(talloc_tos(), &req, (char *)req.inbuf, &outbuf,
2611                            1, req.buflen)) {
2612                 DEBUG(10, ("create_outbuf failed\n"));
2613                 return false;
2614         }
2615         req.outbuf = (uint8_t *)outbuf;
2616
2617         SSVAL(req.outbuf, smb_vwv0, num_replies);
2618
2619         if (req.buflen > 0) {
2620                 memcpy(smb_buf(req.outbuf), req.buf, req.buflen);
2621         }
2622
2623         out_len = smb_len(req.outbuf) + 4;
2624
2625         ok = srv_send_smb(smbd_server_fd(),
2626                           (char *)outbuf,
2627                           true, seqnum+1,
2628                           false, &req.pcd);
2629         TALLOC_FREE(outbuf);
2630         if (!ok) {
2631                 exit(1);
2632         }
2633
2634         return true;
2635 }
2636
2637 static void smbd_echo_exit(struct tevent_context *ev,
2638                            struct tevent_fd *fde, uint16_t flags,
2639                            void *private_data)
2640 {
2641         DEBUG(2, ("smbd_echo_exit: lost connection to parent\n"));
2642         exit(0);
2643 }
2644
2645 static void smbd_echo_reader(struct tevent_context *ev,
2646                              struct tevent_fd *fde, uint16_t flags,
2647                              void *private_data)
2648 {
2649         struct smbd_echo_state *state = talloc_get_type_abort(
2650                 private_data, struct smbd_echo_state);
2651         struct smbd_server_connection *sconn = state->sconn;
2652         size_t unread, num_pending;
2653         NTSTATUS status;
2654         struct iovec *tmp;
2655         uint32_t seqnum = 0;
2656         bool reply;
2657         bool ok;
2658         bool encrypted = false;
2659
2660         smb_msleep(1000);
2661
2662         ok = smbd_lock_socket_internal(sconn);
2663         if (!ok) {
2664                 DEBUG(0, ("%s: failed to lock socket\n",
2665                         __location__));
2666                 exit(1);
2667         }
2668
2669         if (!fd_is_readable(smbd_server_fd())) {
2670                 DEBUG(10,("echo_handler[%d] the parent smbd was faster\n",
2671                           (int)sys_getpid()));
2672                 ok = smbd_unlock_socket_internal(sconn);
2673                 if (!ok) {
2674                         DEBUG(1, ("%s: failed to unlock socket in\n",
2675                                 __location__));
2676                         exit(1);
2677                 }
2678                 return;
2679         }
2680
2681         num_pending = talloc_array_length(state->pending);
2682         tmp = talloc_realloc(state, state->pending, struct iovec,
2683                              num_pending+1);
2684         if (tmp == NULL) {
2685                 DEBUG(1, ("talloc_realloc failed\n"));
2686                 exit(1);
2687         }
2688         state->pending = tmp;
2689
2690         DEBUG(10,("echo_handler[%d]: reading pdu\n", (int)sys_getpid()));
2691
2692         status = receive_smb_talloc(state->pending, smbd_server_fd(),
2693                                     (char **)(void *)&state->pending[num_pending].iov_base,
2694                                     0 /* timeout */,
2695                                     &unread,
2696                                     &encrypted,
2697                                     &state->pending[num_pending].iov_len,
2698                                     &seqnum,
2699                                     false /* trusted_channel*/);
2700         if (!NT_STATUS_IS_OK(status)) {
2701                 DEBUG(1, ("echo_handler[%d]: receive_smb_raw_talloc failed: %s\n",
2702                           (int)sys_getpid(), nt_errstr(status)));
2703                 exit(1);
2704         }
2705
2706         ok = smbd_unlock_socket_internal(sconn);
2707         if (!ok) {
2708                 DEBUG(1, ("%s: failed to unlock socket in\n",
2709                         __location__));
2710                 exit(1);
2711         }
2712
2713         /*
2714          * place the seqnum in the packet so that the main process can reply
2715          * with signing
2716          */
2717         SIVAL((uint8_t *)state->pending[num_pending].iov_base, smb_ss_field, seqnum);
2718         SIVAL((uint8_t *)state->pending[num_pending].iov_base, smb_ss_field+4, NT_STATUS_V(NT_STATUS_OK));
2719
2720         reply = smbd_echo_reply(smbd_server_fd(),
2721                                 (uint8_t *)state->pending[num_pending].iov_base,
2722                                 state->pending[num_pending].iov_len,
2723                                 seqnum);
2724         if (reply) {
2725                 DEBUG(10,("echo_handler[%d]: replied to client\n", (int)sys_getpid()));
2726                 /* no check, shrinking by some bytes does not fail */
2727                 state->pending = talloc_realloc(state, state->pending,
2728                                                 struct iovec,
2729                                                 num_pending);
2730         } else {
2731                 DEBUG(10,("echo_handler[%d]: forward to main\n", (int)sys_getpid()));
2732                 smbd_echo_activate_writer(state);
2733         }
2734 }
2735
2736 static void smbd_echo_loop(struct smbd_server_connection *sconn,
2737                            int parent_pipe)
2738 {
2739         struct smbd_echo_state *state;
2740
2741         state = talloc_zero(sconn, struct smbd_echo_state);
2742         if (state == NULL) {
2743                 DEBUG(1, ("talloc failed\n"));
2744                 return;
2745         }
2746         state->sconn = sconn;
2747         state->parent_pipe = parent_pipe;
2748         state->ev = s3_tevent_context_init(state);
2749         if (state->ev == NULL) {
2750                 DEBUG(1, ("tevent_context_init failed\n"));
2751                 TALLOC_FREE(state);
2752                 return;
2753         }
2754         state->parent_fde = tevent_add_fd(state->ev, state, parent_pipe,
2755                                         TEVENT_FD_READ, smbd_echo_exit,
2756                                         state);
2757         if (state->parent_fde == NULL) {
2758                 DEBUG(1, ("tevent_add_fd failed\n"));
2759                 TALLOC_FREE(state);
2760                 return;
2761         }
2762         state->read_fde = tevent_add_fd(state->ev, state, smbd_server_fd(),
2763                                         TEVENT_FD_READ, smbd_echo_reader,
2764                                         state);
2765         if (state->read_fde == NULL) {
2766                 DEBUG(1, ("tevent_add_fd failed\n"));
2767                 TALLOC_FREE(state);
2768                 return;
2769         }
2770
2771         while (true) {
2772                 if (tevent_loop_once(state->ev) == -1) {
2773                         DEBUG(1, ("tevent_loop_once failed: %s\n",
2774                                   strerror(errno)));
2775                         break;
2776                 }
2777         }
2778         TALLOC_FREE(state);
2779 }
2780
2781 /*
2782  * Handle SMBecho requests in a forked child process
2783  */
2784 static bool fork_echo_handler(struct smbd_server_connection *sconn)
2785 {
2786         int listener_pipe[2];
2787         int res;
2788         pid_t child;
2789
2790         res = pipe(listener_pipe);
2791         if (res == -1) {
2792                 DEBUG(1, ("pipe() failed: %s\n", strerror(errno)));
2793                 return false;
2794         }
2795         sconn->smb1.echo_handler.socket_lock_fd = create_unlink_tmp(lp_lockdir());
2796         if (sconn->smb1.echo_handler.socket_lock_fd == -1) {
2797                 DEBUG(1, ("Could not create lock fd: %s\n", strerror(errno)));
2798                 goto fail;
2799         }
2800
2801         child = sys_fork();
2802         if (child == 0) {
2803                 NTSTATUS status;
2804
2805                 close(listener_pipe[0]);
2806
2807                 status = reinit_after_fork(sconn->msg_ctx,
2808                                            smbd_event_context(),
2809                                            procid_self(), false);
2810                 if (!NT_STATUS_IS_OK(status)) {
2811                         DEBUG(1, ("reinit_after_fork failed: %s\n",
2812                                   nt_errstr(status)));
2813                         exit(1);
2814                 }
2815                 smbd_echo_loop(sconn, listener_pipe[1]);
2816                 exit(0);
2817         }
2818         close(listener_pipe[1]);
2819         listener_pipe[1] = -1;
2820         sconn->smb1.echo_handler.trusted_fd = listener_pipe[0];
2821
2822         DEBUG(10,("fork_echo_handler: main[%d] echo_child[%d]\n", (int)sys_getpid(), child));
2823
2824         /*
2825          * Without smb signing this is the same as the normal smbd
2826          * listener. This needs to change once signing comes in.
2827          */
2828         sconn->smb1.echo_handler.trusted_fde = event_add_fd(smbd_event_context(),
2829                                         sconn,
2830                                         sconn->smb1.echo_handler.trusted_fd,
2831                                         EVENT_FD_READ,
2832                                         smbd_server_echo_handler,
2833                                         sconn);
2834         if (sconn->smb1.echo_handler.trusted_fde == NULL) {
2835                 DEBUG(1, ("event_add_fd failed\n"));
2836                 goto fail;
2837         }
2838
2839         return true;
2840
2841 fail:
2842         if (listener_pipe[0] != -1) {
2843                 close(listener_pipe[0]);
2844         }
2845         if (listener_pipe[1] != -1) {
2846                 close(listener_pipe[1]);
2847         }
2848         sconn->smb1.echo_handler.trusted_fd = -1;
2849         if (sconn->smb1.echo_handler.socket_lock_fd != -1) {
2850                 close(sconn->smb1.echo_handler.socket_lock_fd);
2851         }
2852         sconn->smb1.echo_handler.trusted_fd = -1;
2853         sconn->smb1.echo_handler.socket_lock_fd = -1;
2854         return false;
2855 }
2856
2857 /****************************************************************************
2858  Process commands from the client
2859 ****************************************************************************/
2860
2861 void smbd_process(struct smbd_server_connection *sconn)
2862 {
2863         TALLOC_CTX *frame = talloc_stackframe();
2864         struct sockaddr_storage ss;
2865         struct sockaddr *sa = NULL;
2866         socklen_t sa_len;
2867         struct tsocket_address *local_address = NULL;
2868         struct tsocket_address *remote_address = NULL;
2869         const char *remaddr = NULL;
2870         int ret;
2871
2872         if (lp_maxprotocol() == PROTOCOL_SMB2 &&
2873             lp_security() != SEC_SHARE &&
2874             !lp_async_smb_echo_handler()) {
2875                 /*
2876                  * We're not making the desion here,
2877                  * we're just allowing the client
2878                  * to decide between SMB1 and SMB2
2879                  * with the first negprot
2880                  * packet.
2881                  */
2882                 sconn->using_smb2 = true;
2883         }
2884
2885         /* Ensure child is set to blocking mode */
2886         set_blocking(smbd_server_fd(),True);
2887
2888         set_socket_options(smbd_server_fd(),"SO_KEEPALIVE");
2889         set_socket_options(smbd_server_fd(), lp_socket_options());
2890
2891         sa = (struct sockaddr *)(void *)&ss;
2892         sa_len = sizeof(ss);
2893         ret = getpeername(smbd_server_fd(), sa, &sa_len);
2894         if (ret != 0) {
2895                 int level = (errno == ENOTCONN)?2:0;
2896                 DEBUG(level,("getpeername() failed - %s\n", strerror(errno)));
2897                 exit_server_cleanly("getpeername() failed.\n");
2898         }
2899         ret = tsocket_address_bsd_from_sockaddr(sconn,
2900                                                 sa, sa_len,
2901                                                 &remote_address);
2902         if (ret != 0) {
2903                 DEBUG(0,("%s: tsocket_address_bsd_from_sockaddr remote failed - %s\n",
2904                         __location__, strerror(errno)));
2905                 exit_server_cleanly("tsocket_address_bsd_from_sockaddr remote failed.\n");
2906         }
2907
2908         sa = (struct sockaddr *)(void *)&ss;
2909         sa_len = sizeof(ss);
2910         ret = getsockname(smbd_server_fd(), sa, &sa_len);
2911         if (ret != 0) {
2912                 int level = (errno == ENOTCONN)?2:0;
2913                 DEBUG(level,("getsockname() failed - %s\n", strerror(errno)));
2914                 exit_server_cleanly("getsockname() failed.\n");
2915         }
2916         ret = tsocket_address_bsd_from_sockaddr(sconn,
2917                                                 sa, sa_len,
2918                                                 &local_address);
2919         if (ret != 0) {
2920                 DEBUG(0,("%s: tsocket_address_bsd_from_sockaddr remote failed - %s\n",
2921                         __location__, strerror(errno)));
2922                 exit_server_cleanly("tsocket_address_bsd_from_sockaddr remote failed.\n");
2923         }
2924
2925         sconn->local_address = local_address;
2926         sconn->remote_address = remote_address;
2927
2928         if (tsocket_address_is_inet(remote_address, "ip")) {
2929                 remaddr = tsocket_address_inet_addr_string(
2930                                 sconn->remote_address,
2931                                 talloc_tos());
2932                 if (remaddr == NULL) {
2933
2934                 }
2935         } else {
2936                 remaddr = "0.0.0.0";
2937         }
2938
2939         /* this is needed so that we get decent entries
2940            in smbstatus for port 445 connects */
2941         set_remote_machine_name(remaddr, false);
2942         reload_services(sconn->msg_ctx, true);
2943
2944         /*
2945          * Before the first packet, check the global hosts allow/ hosts deny
2946          * parameters before doing any parsing of packets passed to us by the
2947          * client. This prevents attacks on our parsing code from hosts not in
2948          * the hosts allow list.
2949          */
2950
2951         if (!check_access(smbd_server_fd(), lp_hostsallow(-1),
2952                           lp_hostsdeny(-1))) {
2953                 /*
2954                  * send a negative session response "not listening on calling
2955                  * name"
2956                  */
2957                 unsigned char buf[5] = {0x83, 0, 0, 1, 0x81};
2958                 DEBUG( 1, ("Connection denied from %s to %s\n",
2959                            tsocket_address_string(remote_address, talloc_tos()),
2960                            tsocket_address_string(local_address, talloc_tos())));
2961                 (void)srv_send_smb(smbd_server_fd(),(char *)buf, false,
2962                                    0, false, NULL);
2963                 exit_server_cleanly("connection denied");
2964         }
2965
2966         DEBUG(10, ("Connection allowed from %s to %s\n",
2967                    tsocket_address_string(remote_address, talloc_tos()),
2968                    tsocket_address_string(local_address, talloc_tos())));
2969
2970         init_modules();
2971
2972         smb_perfcount_init();
2973
2974         if (!init_account_policy()) {
2975                 exit_server("Could not open account policy tdb.\n");
2976         }
2977
2978         if (*lp_rootdir()) {
2979                 if (chroot(lp_rootdir()) != 0) {
2980                         DEBUG(0,("Failed to change root to %s\n", lp_rootdir()));
2981                         exit_server("Failed to chroot()");
2982                 }
2983                 if (chdir("/") == -1) {
2984                         DEBUG(0,("Failed to chdir to / on chroot to %s\n", lp_rootdir()));
2985                         exit_server("Failed to chroot()");
2986                 }
2987                 DEBUG(0,("Changed root to %s\n", lp_rootdir()));
2988         }
2989
2990         if (!srv_init_signing(sconn)) {
2991                 exit_server("Failed to init smb_signing");
2992         }
2993
2994         if (lp_async_smb_echo_handler() && !fork_echo_handler(sconn)) {
2995                 exit_server("Failed to fork echo handler");
2996         }
2997
2998         /* Setup oplocks */
2999         if (!init_oplocks(sconn->msg_ctx))
3000                 exit_server("Failed to init oplocks");
3001
3002         /* register our message handlers */
3003         messaging_register(sconn->msg_ctx, NULL,
3004                            MSG_SMB_FORCE_TDIS, msg_force_tdis);
3005         messaging_register(sconn->msg_ctx, NULL,
3006                            MSG_SMB_RELEASE_IP, msg_release_ip);
3007         messaging_register(sconn->msg_ctx, NULL,
3008                            MSG_SMB_CLOSE_FILE, msg_close_file);
3009
3010         /*
3011          * Use the default MSG_DEBUG handler to avoid rebroadcasting
3012          * MSGs to all child processes
3013          */
3014         messaging_deregister(sconn->msg_ctx,
3015                              MSG_DEBUG, NULL);
3016         messaging_register(sconn->msg_ctx, NULL,
3017                            MSG_DEBUG, debug_message);
3018
3019         if ((lp_keepalive() != 0)
3020             && !(event_add_idle(smbd_event_context(), NULL,
3021                                 timeval_set(lp_keepalive(), 0),
3022                                 "keepalive", keepalive_fn,
3023                                 NULL))) {
3024                 DEBUG(0, ("Could not add keepalive event\n"));
3025                 exit(1);
3026         }
3027
3028         if (!(event_add_idle(smbd_event_context(), NULL,
3029                              timeval_set(IDLE_CLOSED_TIMEOUT, 0),
3030                              "deadtime", deadtime_fn, sconn))) {
3031                 DEBUG(0, ("Could not add deadtime event\n"));
3032                 exit(1);
3033         }
3034
3035         if (!(event_add_idle(smbd_event_context(), NULL,
3036                              timeval_set(SMBD_SELECT_TIMEOUT, 0),
3037                              "housekeeping", housekeeping_fn,
3038                              sconn->msg_ctx))) {
3039                 DEBUG(0, ("Could not add housekeeping event\n"));
3040                 exit(1);
3041         }
3042
3043 #ifdef CLUSTER_SUPPORT
3044
3045         if (lp_clustering()) {
3046                 /*
3047                  * We need to tell ctdb about our client's TCP
3048                  * connection, so that for failover ctdbd can send
3049                  * tickle acks, triggering a reconnection by the
3050                  * client.
3051                  */
3052
3053                 struct sockaddr_storage srv, clnt;
3054
3055                 if (client_get_tcp_info(&srv, &clnt) == 0) {
3056
3057                         NTSTATUS status;
3058
3059                         status = ctdbd_register_ips(
3060                                 messaging_ctdbd_connection(procid_self()),
3061                                 &srv, &clnt, release_ip, NULL);
3062
3063                         if (!NT_STATUS_IS_OK(status)) {
3064                                 DEBUG(0, ("ctdbd_register_ips failed: %s\n",
3065                                           nt_errstr(status)));
3066                         }
3067                 } else
3068                 {
3069                         DEBUG(0,("Unable to get tcp info for "
3070                                  "CTDB_CONTROL_TCP_CLIENT: %s\n",
3071                                  strerror(errno)));
3072                 }
3073         }
3074
3075 #endif
3076
3077         sconn->nbt.got_session = false;
3078
3079         sconn->smb1.negprot.max_recv = MIN(lp_maxxmit(),BUFFER_SIZE);
3080
3081         sconn->smb1.sessions.done_sesssetup = false;
3082         sconn->smb1.sessions.max_send = BUFFER_SIZE;
3083         sconn->smb1.sessions.last_session_tag = UID_FIELD_INVALID;
3084         /* users from session setup */
3085         sconn->smb1.sessions.session_userlist = NULL;
3086         /* workgroup from session setup. */
3087         sconn->smb1.sessions.session_workgroup = NULL;
3088         /* this holds info on user ids that are already validated for this VC */
3089         sconn->smb1.sessions.validated_users = NULL;
3090         sconn->smb1.sessions.next_vuid = VUID_OFFSET;
3091         sconn->smb1.sessions.num_validated_vuids = 0;
3092
3093         conn_init(sconn);
3094         if (!init_dptrs(sconn)) {
3095                 exit_server("init_dptrs() failed");
3096         }
3097
3098         sconn->smb1.fde = event_add_fd(smbd_event_context(),
3099                                                   sconn,
3100                                                   smbd_server_fd(),
3101                                                   EVENT_FD_READ,
3102                                                   smbd_server_connection_handler,
3103                                                   sconn);
3104         if (!sconn->smb1.fde) {
3105                 exit_server("failed to create smbd_server_connection fde");
3106         }
3107
3108         TALLOC_FREE(frame);
3109
3110         while (True) {
3111                 NTSTATUS status;
3112
3113                 frame = talloc_stackframe_pool(8192);
3114
3115                 errno = 0;
3116
3117                 status = smbd_server_connection_loop_once(sconn);
3118                 if (!NT_STATUS_EQUAL(status, NT_STATUS_RETRY) &&
3119                     !NT_STATUS_IS_OK(status)) {
3120                         DEBUG(3, ("smbd_server_connection_loop_once failed: %s,"
3121                                   " exiting\n", nt_errstr(status)));
3122                         break;
3123                 }
3124
3125                 TALLOC_FREE(frame);
3126         }
3127
3128         exit_server_cleanly(NULL);
3129 }
3130
3131 bool req_is_in_chain(struct smb_request *req)
3132 {
3133         if (req->vwv != (uint16_t *)(req->inbuf+smb_vwv)) {
3134                 /*
3135                  * We're right now handling a subsequent request, so we must
3136                  * be in a chain
3137                  */
3138                 return true;
3139         }
3140
3141         if (!is_andx_req(req->cmd)) {
3142                 return false;
3143         }
3144
3145         if (req->wct < 2) {
3146                 /*
3147                  * Okay, an illegal request, but definitely not chained :-)
3148                  */
3149                 return false;
3150         }
3151
3152         return (CVAL(req->vwv+0, 0) != 0xFF);
3153 }