s3:param: make "servicename" a substituted option
[Samba.git] / source3 / smbd / process.c
blobdf6f22bc37056be813160b0daaa8f1bcc7eefc8f
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
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.
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.
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/>.
21 #include "includes.h"
22 #include "../lib/tsocket/tsocket.h"
23 #include "system/filesys.h"
24 #include "smbd/smbd.h"
25 #include "smbd/globals.h"
26 #include "librpc/gen_ndr/netlogon.h"
27 #include "../lib/async_req/async_sock.h"
28 #include "ctdbd_conn.h"
29 #include "../lib/util/select.h"
30 #include "printing/queue_process.h"
31 #include "system/select.h"
32 #include "passdb.h"
33 #include "auth.h"
34 #include "messages.h"
35 #include "lib/messages_ctdb.h"
36 #include "smbprofile.h"
37 #include "rpc_server/spoolss/srv_spoolss_nt.h"
38 #include "libsmb/libsmb.h"
39 #include "../lib/util/tevent_ntstatus.h"
40 #include "../libcli/security/dom_sid.h"
41 #include "../libcli/security/security_token.h"
42 #include "lib/id_cache.h"
43 #include "lib/util/sys_rw_data.h"
44 #include "system/threads.h"
45 #include "lib/pthreadpool/pthreadpool_tevent.h"
46 #include "util_event.h"
47 #include "libcli/smb/smbXcli_base.h"
48 #include "lib/util/time_basic.h"
50 /* Internal message queue for deferred opens. */
51 struct pending_message_list {
52 struct pending_message_list *next, *prev;
53 struct timeval request_time; /* When was this first issued? */
54 struct smbd_server_connection *sconn;
55 struct smbXsrv_connection *xconn;
56 struct tevent_timer *te;
57 struct smb_perfcount_data pcd;
58 uint32_t seqnum;
59 bool encrypted;
60 bool processed;
61 DATA_BLOB buf;
62 struct deferred_open_record *open_rec;
65 static void construct_reply_common(uint8_t cmd, const uint8_t *inbuf,
66 char *outbuf);
67 static struct pending_message_list *get_deferred_open_message_smb(
68 struct smbd_server_connection *sconn, uint64_t mid);
69 static bool smb_splice_chain(uint8_t **poutbuf, const uint8_t *andx_buf);
71 static void smbd_echo_init(struct smbXsrv_connection *xconn)
73 xconn->smb1.echo_handler.trusted_fd = -1;
74 xconn->smb1.echo_handler.socket_lock_fd = -1;
75 #ifdef HAVE_ROBUST_MUTEXES
76 xconn->smb1.echo_handler.socket_mutex = NULL;
77 #endif
80 static bool smbd_echo_active(struct smbXsrv_connection *xconn)
82 if (xconn->smb1.echo_handler.socket_lock_fd != -1) {
83 return true;
86 #ifdef HAVE_ROBUST_MUTEXES
87 if (xconn->smb1.echo_handler.socket_mutex != NULL) {
88 return true;
90 #endif
92 return false;
95 static bool smbd_lock_socket_internal(struct smbXsrv_connection *xconn)
97 if (!smbd_echo_active(xconn)) {
98 return true;
101 xconn->smb1.echo_handler.ref_count++;
103 if (xconn->smb1.echo_handler.ref_count > 1) {
104 return true;
107 DEBUG(10,("pid[%d] wait for socket lock\n", (int)getpid()));
109 #ifdef HAVE_ROBUST_MUTEXES
110 if (xconn->smb1.echo_handler.socket_mutex != NULL) {
111 int ret = EINTR;
113 while (ret == EINTR) {
114 ret = pthread_mutex_lock(
115 xconn->smb1.echo_handler.socket_mutex);
116 if (ret == 0) {
117 break;
120 if (ret != 0) {
121 DEBUG(1, ("pthread_mutex_lock failed: %s\n",
122 strerror(ret)));
123 return false;
126 #endif
128 if (xconn->smb1.echo_handler.socket_lock_fd != -1) {
129 bool ok;
131 do {
132 ok = fcntl_lock(
133 xconn->smb1.echo_handler.socket_lock_fd,
134 F_SETLKW, 0, 0, F_WRLCK);
135 } while (!ok && (errno == EINTR));
137 if (!ok) {
138 DEBUG(1, ("fcntl_lock failed: %s\n", strerror(errno)));
139 return false;
143 DEBUG(10,("pid[%d] got socket lock\n", (int)getpid()));
145 return true;
148 void smbd_lock_socket(struct smbXsrv_connection *xconn)
150 if (!smbd_lock_socket_internal(xconn)) {
151 exit_server_cleanly("failed to lock socket");
155 static bool smbd_unlock_socket_internal(struct smbXsrv_connection *xconn)
157 if (!smbd_echo_active(xconn)) {
158 return true;
161 xconn->smb1.echo_handler.ref_count--;
163 if (xconn->smb1.echo_handler.ref_count > 0) {
164 return true;
167 #ifdef HAVE_ROBUST_MUTEXES
168 if (xconn->smb1.echo_handler.socket_mutex != NULL) {
169 int ret;
170 ret = pthread_mutex_unlock(
171 xconn->smb1.echo_handler.socket_mutex);
172 if (ret != 0) {
173 DEBUG(1, ("pthread_mutex_unlock failed: %s\n",
174 strerror(ret)));
175 return false;
178 #endif
180 if (xconn->smb1.echo_handler.socket_lock_fd != -1) {
181 bool ok;
183 do {
184 ok = fcntl_lock(
185 xconn->smb1.echo_handler.socket_lock_fd,
186 F_SETLKW, 0, 0, F_UNLCK);
187 } while (!ok && (errno == EINTR));
189 if (!ok) {
190 DEBUG(1, ("fcntl_lock failed: %s\n", strerror(errno)));
191 return false;
195 DEBUG(10,("pid[%d] unlocked socket\n", (int)getpid()));
197 return true;
200 void smbd_unlock_socket(struct smbXsrv_connection *xconn)
202 if (!smbd_unlock_socket_internal(xconn)) {
203 exit_server_cleanly("failed to unlock socket");
207 /* Accessor function for smb_read_error for smbd functions. */
209 /****************************************************************************
210 Send an smb to a fd.
211 ****************************************************************************/
213 bool srv_send_smb(struct smbXsrv_connection *xconn, char *buffer,
214 bool do_signing, uint32_t seqnum,
215 bool do_encrypt,
216 struct smb_perfcount_data *pcd)
218 size_t len = 0;
219 ssize_t ret;
220 char *buf_out = buffer;
222 if (!NT_STATUS_IS_OK(xconn->transport.status)) {
224 * we're not supposed to do any io
226 return true;
229 smbd_lock_socket(xconn);
231 if (do_signing) {
232 NTSTATUS status;
234 /* Sign the outgoing packet if required. */
235 status = srv_calculate_sign_mac(xconn, buf_out, seqnum);
236 if (!NT_STATUS_IS_OK(status)) {
237 DBG_ERR("Failed to calculate signing mac: %s\n",
238 nt_errstr(status));
239 return false;
243 if (do_encrypt) {
244 NTSTATUS status = srv_encrypt_buffer(xconn, buffer, &buf_out);
245 if (!NT_STATUS_IS_OK(status)) {
246 DEBUG(0, ("send_smb: SMB encryption failed "
247 "on outgoing packet! Error %s\n",
248 nt_errstr(status) ));
249 ret = -1;
250 goto out;
254 len = smb_len_large(buf_out) + 4;
256 ret = write_data(xconn->transport.sock, buf_out, len);
257 if (ret <= 0) {
258 int saved_errno = errno;
260 * Try and give an error message saying what
261 * client failed.
263 DEBUG(1,("pid[%d] Error writing %d bytes to client %s. %d. (%s)\n",
264 (int)getpid(), (int)len,
265 smbXsrv_connection_dbg(xconn),
266 (int)ret, strerror(saved_errno)));
267 errno = saved_errno;
269 srv_free_enc_buffer(xconn, buf_out);
270 goto out;
273 SMB_PERFCOUNT_SET_MSGLEN_OUT(pcd, len);
274 srv_free_enc_buffer(xconn, buf_out);
275 out:
276 SMB_PERFCOUNT_END(pcd);
278 smbd_unlock_socket(xconn);
279 return (ret > 0);
282 /*******************************************************************
283 Setup the word count and byte count for a smb message.
284 ********************************************************************/
286 size_t srv_set_message(char *buf,
287 size_t num_words,
288 size_t num_bytes,
289 bool zero)
291 if (zero && (num_words || num_bytes)) {
292 memset(buf + smb_size,'\0',num_words*2 + num_bytes);
294 SCVAL(buf,smb_wct,num_words);
295 SSVAL(buf,smb_vwv + num_words*SIZEOFWORD,num_bytes);
296 smb_setlen(buf,(smb_size + num_words*2 + num_bytes - 4));
297 return (smb_size + num_words*2 + num_bytes);
300 static bool valid_smb_header(const uint8_t *inbuf)
302 if (is_encrypted_packet(inbuf)) {
303 return true;
306 * This used to be (strncmp(smb_base(inbuf),"\377SMB",4) == 0)
307 * but it just looks weird to call strncmp for this one.
309 return (IVAL(smb_base(inbuf), 0) == 0x424D53FF);
312 /* Socket functions for smbd packet processing. */
314 static bool valid_packet_size(size_t len)
317 * A WRITEX with CAP_LARGE_WRITEX can be 64k worth of data plus 65 bytes
318 * of header. Don't print the error if this fits.... JRA.
321 if (len > (LARGE_WRITEX_BUFFER_SIZE + LARGE_WRITEX_HDR_SIZE)) {
322 DEBUG(0,("Invalid packet length! (%lu bytes).\n",
323 (unsigned long)len));
324 return false;
326 return true;
329 static NTSTATUS read_packet_remainder(int fd, char *buffer,
330 unsigned int timeout, ssize_t len)
332 NTSTATUS status;
334 if (len <= 0) {
335 return NT_STATUS_OK;
338 status = read_fd_with_timeout(fd, buffer, len, len, timeout, NULL);
339 if (!NT_STATUS_IS_OK(status)) {
340 char addr[INET6_ADDRSTRLEN];
341 DEBUG(0, ("read_fd_with_timeout failed for client %s read "
342 "error = %s.\n",
343 get_peer_addr(fd, addr, sizeof(addr)),
344 nt_errstr(status)));
346 return status;
349 /****************************************************************************
350 Attempt a zerocopy writeX read. We know here that len > smb_size-4
351 ****************************************************************************/
354 * Unfortunately, earlier versions of smbclient/libsmbclient
355 * don't send this "standard" writeX header. I've fixed this
356 * for 3.2 but we'll use the old method with earlier versions.
357 * Windows and CIFSFS at least use this standard size. Not
358 * sure about MacOSX.
361 #define STANDARD_WRITE_AND_X_HEADER_SIZE (smb_size - 4 + /* basic header */ \
362 (2*14) + /* word count (including bcc) */ \
363 1 /* pad byte */)
365 static NTSTATUS receive_smb_raw_talloc_partial_read(TALLOC_CTX *mem_ctx,
366 const char lenbuf[4],
367 struct smbXsrv_connection *xconn,
368 int sock,
369 char **buffer,
370 unsigned int timeout,
371 size_t *p_unread,
372 size_t *len_ret)
374 /* Size of a WRITEX call (+4 byte len). */
375 char writeX_header[4 + STANDARD_WRITE_AND_X_HEADER_SIZE];
376 ssize_t len = smb_len_large(lenbuf); /* Could be a UNIX large writeX. */
377 ssize_t toread;
378 NTSTATUS status;
380 memcpy(writeX_header, lenbuf, 4);
382 status = read_fd_with_timeout(
383 sock, writeX_header + 4,
384 STANDARD_WRITE_AND_X_HEADER_SIZE,
385 STANDARD_WRITE_AND_X_HEADER_SIZE,
386 timeout, NULL);
388 if (!NT_STATUS_IS_OK(status)) {
389 DEBUG(0, ("read_fd_with_timeout failed for client %s read "
390 "error = %s.\n",
391 smbXsrv_connection_dbg(xconn),
392 nt_errstr(status)));
393 return status;
397 * Ok - now try and see if this is a possible
398 * valid writeX call.
401 if (is_valid_writeX_buffer(xconn, (uint8_t *)writeX_header)) {
403 * If the data offset is beyond what
404 * we've read, drain the extra bytes.
406 uint16_t doff = SVAL(writeX_header,smb_vwv11);
407 ssize_t newlen;
409 if (doff > STANDARD_WRITE_AND_X_HEADER_SIZE) {
410 size_t drain = doff - STANDARD_WRITE_AND_X_HEADER_SIZE;
411 if (drain_socket(sock, drain) != drain) {
412 smb_panic("receive_smb_raw_talloc_partial_read:"
413 " failed to drain pending bytes");
415 } else {
416 doff = STANDARD_WRITE_AND_X_HEADER_SIZE;
419 /* Spoof down the length and null out the bcc. */
420 set_message_bcc(writeX_header, 0);
421 newlen = smb_len(writeX_header);
423 /* Copy the header we've written. */
425 *buffer = (char *)talloc_memdup(mem_ctx,
426 writeX_header,
427 sizeof(writeX_header));
429 if (*buffer == NULL) {
430 DEBUG(0, ("Could not allocate inbuf of length %d\n",
431 (int)sizeof(writeX_header)));
432 return NT_STATUS_NO_MEMORY;
435 /* Work out the remaining bytes. */
436 *p_unread = len - STANDARD_WRITE_AND_X_HEADER_SIZE;
437 *len_ret = newlen + 4;
438 return NT_STATUS_OK;
441 if (!valid_packet_size(len)) {
442 return NT_STATUS_INVALID_PARAMETER;
446 * Not a valid writeX call. Just do the standard
447 * talloc and return.
450 *buffer = talloc_array(mem_ctx, char, len+4);
452 if (*buffer == NULL) {
453 DEBUG(0, ("Could not allocate inbuf of length %d\n",
454 (int)len+4));
455 return NT_STATUS_NO_MEMORY;
458 /* Copy in what we already read. */
459 memcpy(*buffer,
460 writeX_header,
461 4 + STANDARD_WRITE_AND_X_HEADER_SIZE);
462 toread = len - STANDARD_WRITE_AND_X_HEADER_SIZE;
464 if(toread > 0) {
465 status = read_packet_remainder(
466 sock,
467 (*buffer) + 4 + STANDARD_WRITE_AND_X_HEADER_SIZE,
468 timeout, toread);
470 if (!NT_STATUS_IS_OK(status)) {
471 DEBUG(10, ("receive_smb_raw_talloc_partial_read: %s\n",
472 nt_errstr(status)));
473 return status;
477 *len_ret = len + 4;
478 return NT_STATUS_OK;
481 static NTSTATUS receive_smb_raw_talloc(TALLOC_CTX *mem_ctx,
482 struct smbXsrv_connection *xconn,
483 int sock,
484 char **buffer, unsigned int timeout,
485 size_t *p_unread, size_t *plen)
487 char lenbuf[4];
488 size_t len;
489 int min_recv_size = lp_min_receive_file_size();
490 NTSTATUS status;
492 *p_unread = 0;
494 status = read_smb_length_return_keepalive(sock, lenbuf, timeout,
495 &len);
496 if (!NT_STATUS_IS_OK(status)) {
497 return status;
500 if (CVAL(lenbuf,0) == 0 && min_recv_size &&
501 (smb_len_large(lenbuf) > /* Could be a UNIX large writeX. */
502 (min_recv_size + STANDARD_WRITE_AND_X_HEADER_SIZE)) &&
503 !srv_is_signing_active(xconn) &&
504 xconn->smb1.echo_handler.trusted_fde == NULL) {
506 return receive_smb_raw_talloc_partial_read(
507 mem_ctx, lenbuf, xconn, sock, buffer, timeout,
508 p_unread, plen);
511 if (!valid_packet_size(len)) {
512 return NT_STATUS_INVALID_PARAMETER;
516 * The +4 here can't wrap, we've checked the length above already.
519 *buffer = talloc_array(mem_ctx, char, len+4);
521 if (*buffer == NULL) {
522 DEBUG(0, ("Could not allocate inbuf of length %d\n",
523 (int)len+4));
524 return NT_STATUS_NO_MEMORY;
527 memcpy(*buffer, lenbuf, sizeof(lenbuf));
529 status = read_packet_remainder(sock, (*buffer)+4, timeout, len);
530 if (!NT_STATUS_IS_OK(status)) {
531 return status;
534 *plen = len + 4;
535 return NT_STATUS_OK;
538 static NTSTATUS receive_smb_talloc(TALLOC_CTX *mem_ctx,
539 struct smbXsrv_connection *xconn,
540 int sock,
541 char **buffer, unsigned int timeout,
542 size_t *p_unread, bool *p_encrypted,
543 size_t *p_len,
544 uint32_t *seqnum,
545 bool trusted_channel)
547 size_t len = 0;
548 NTSTATUS status;
550 *p_encrypted = false;
552 status = receive_smb_raw_talloc(mem_ctx, xconn, sock, buffer, timeout,
553 p_unread, &len);
554 if (!NT_STATUS_IS_OK(status)) {
555 DEBUG(NT_STATUS_EQUAL(status, NT_STATUS_END_OF_FILE)?5:1,
556 ("receive_smb_raw_talloc failed for client %s "
557 "read error = %s.\n",
558 smbXsrv_connection_dbg(xconn),
559 nt_errstr(status)) );
560 return status;
563 if (is_encrypted_packet((uint8_t *)*buffer)) {
564 status = srv_decrypt_buffer(xconn, *buffer);
565 if (!NT_STATUS_IS_OK(status)) {
566 DEBUG(0, ("receive_smb_talloc: SMB decryption failed on "
567 "incoming packet! Error %s\n",
568 nt_errstr(status) ));
569 return status;
571 *p_encrypted = true;
574 /* Check the incoming SMB signature. */
575 if (!srv_check_sign_mac(xconn, *buffer, seqnum, trusted_channel)) {
576 DEBUG(0, ("receive_smb: SMB Signature verification failed on "
577 "incoming packet!\n"));
578 return NT_STATUS_INVALID_NETWORK_RESPONSE;
581 *p_len = len;
582 return NT_STATUS_OK;
586 * Initialize a struct smb_request from an inbuf
589 static bool init_smb_request(struct smb_request *req,
590 struct smbd_server_connection *sconn,
591 struct smbXsrv_connection *xconn,
592 const uint8_t *inbuf,
593 size_t unread_bytes, bool encrypted,
594 uint32_t seqnum)
596 struct smbXsrv_tcon *tcon;
597 NTSTATUS status;
598 NTTIME now;
599 size_t req_size = smb_len(inbuf) + 4;
601 /* Ensure we have at least smb_size bytes. */
602 if (req_size < smb_size) {
603 DEBUG(0,("init_smb_request: invalid request size %u\n",
604 (unsigned int)req_size ));
605 return false;
608 req->request_time = timeval_current();
609 now = timeval_to_nttime(&req->request_time);
611 req->cmd = CVAL(inbuf, smb_com);
612 req->flags2 = SVAL(inbuf, smb_flg2);
613 req->smbpid = SVAL(inbuf, smb_pid);
614 req->mid = (uint64_t)SVAL(inbuf, smb_mid);
615 req->seqnum = seqnum;
616 req->vuid = SVAL(inbuf, smb_uid);
617 req->tid = SVAL(inbuf, smb_tid);
618 req->wct = CVAL(inbuf, smb_wct);
619 req->vwv = (const uint16_t *)(inbuf+smb_vwv);
620 req->buflen = smb_buflen(inbuf);
621 req->buf = (const uint8_t *)smb_buf_const(inbuf);
622 req->unread_bytes = unread_bytes;
623 req->encrypted = encrypted;
624 req->sconn = sconn;
625 req->xconn = xconn;
626 req->conn = NULL;
627 if (xconn != NULL) {
628 status = smb1srv_tcon_lookup(xconn, req->tid, now, &tcon);
629 if (NT_STATUS_IS_OK(status)) {
630 req->conn = tcon->compat;
633 req->chain_fsp = NULL;
634 req->smb2req = NULL;
635 req->priv_paths = NULL;
636 req->chain = NULL;
637 req->posix_pathnames = lp_posix_pathnames();
638 smb_init_perfcount_data(&req->pcd);
640 /* Ensure we have at least wct words and 2 bytes of bcc. */
641 if (smb_size + req->wct*2 > req_size) {
642 DEBUG(0,("init_smb_request: invalid wct number %u (size %u)\n",
643 (unsigned int)req->wct,
644 (unsigned int)req_size));
645 return false;
647 /* Ensure bcc is correct. */
648 if (((const uint8_t *)smb_buf_const(inbuf)) + req->buflen > inbuf + req_size) {
649 DEBUG(0,("init_smb_request: invalid bcc number %u "
650 "(wct = %u, size %u)\n",
651 (unsigned int)req->buflen,
652 (unsigned int)req->wct,
653 (unsigned int)req_size));
654 return false;
657 req->outbuf = NULL;
658 return true;
661 static void process_smb(struct smbXsrv_connection *xconn,
662 uint8_t *inbuf, size_t nread, size_t unread_bytes,
663 uint32_t seqnum, bool encrypted,
664 struct smb_perfcount_data *deferred_pcd);
666 static void smbd_deferred_open_timer(struct tevent_context *ev,
667 struct tevent_timer *te,
668 struct timeval _tval,
669 void *private_data)
671 struct pending_message_list *msg = talloc_get_type(private_data,
672 struct pending_message_list);
673 struct smbd_server_connection *sconn = msg->sconn;
674 struct smbXsrv_connection *xconn = msg->xconn;
675 TALLOC_CTX *mem_ctx = talloc_tos();
676 uint64_t mid = (uint64_t)SVAL(msg->buf.data,smb_mid);
677 uint8_t *inbuf;
679 inbuf = (uint8_t *)talloc_memdup(mem_ctx, msg->buf.data,
680 msg->buf.length);
681 if (inbuf == NULL) {
682 exit_server("smbd_deferred_open_timer: talloc failed\n");
683 return;
686 /* We leave this message on the queue so the open code can
687 know this is a retry. */
688 DEBUG(5,("smbd_deferred_open_timer: trigger mid %llu.\n",
689 (unsigned long long)mid ));
691 /* Mark the message as processed so this is not
692 * re-processed in error. */
693 msg->processed = true;
695 process_smb(xconn, inbuf,
696 msg->buf.length, 0,
697 msg->seqnum, msg->encrypted, &msg->pcd);
699 /* If it's still there and was processed, remove it. */
700 msg = get_deferred_open_message_smb(sconn, mid);
701 if (msg && msg->processed) {
702 remove_deferred_open_message_smb(xconn, mid);
706 /****************************************************************************
707 Function to push a message onto the tail of a linked list of smb messages ready
708 for processing.
709 ****************************************************************************/
711 static bool push_queued_message(struct smb_request *req,
712 struct timeval request_time,
713 struct timeval end_time,
714 struct deferred_open_record *open_rec)
716 int msg_len = smb_len(req->inbuf) + 4;
717 struct pending_message_list *msg;
719 msg = talloc_zero(NULL, struct pending_message_list);
721 if(msg == NULL) {
722 DEBUG(0,("push_message: malloc fail (1)\n"));
723 return False;
725 msg->sconn = req->sconn;
726 msg->xconn = req->xconn;
728 msg->buf = data_blob_talloc(msg, req->inbuf, msg_len);
729 if(msg->buf.data == NULL) {
730 DEBUG(0,("push_message: malloc fail (2)\n"));
731 TALLOC_FREE(msg);
732 return False;
735 msg->request_time = request_time;
736 msg->seqnum = req->seqnum;
737 msg->encrypted = req->encrypted;
738 msg->processed = false;
739 SMB_PERFCOUNT_DEFER_OP(&req->pcd, &msg->pcd);
741 if (open_rec) {
742 msg->open_rec = talloc_move(msg, &open_rec);
745 #if 0
746 msg->te = tevent_add_timer(msg->sconn->ev_ctx,
747 msg,
748 end_time,
749 smbd_deferred_open_timer,
750 msg);
751 if (!msg->te) {
752 DEBUG(0,("push_message: event_add_timed failed\n"));
753 TALLOC_FREE(msg);
754 return false;
756 #endif
758 DLIST_ADD_END(req->sconn->deferred_open_queue, msg);
760 DEBUG(10,("push_message: pushed message length %u on "
761 "deferred_open_queue\n", (unsigned int)msg_len));
763 return True;
766 /****************************************************************************
767 Function to delete a sharing violation open message by mid.
768 ****************************************************************************/
770 void remove_deferred_open_message_smb(struct smbXsrv_connection *xconn,
771 uint64_t mid)
773 struct smbd_server_connection *sconn = xconn->client->sconn;
774 struct pending_message_list *pml;
776 if (sconn->using_smb2) {
777 remove_deferred_open_message_smb2(xconn, mid);
778 return;
781 for (pml = sconn->deferred_open_queue; pml; pml = pml->next) {
782 if (mid == (uint64_t)SVAL(pml->buf.data,smb_mid)) {
783 DEBUG(10,("remove_deferred_open_message_smb: "
784 "deleting mid %llu len %u\n",
785 (unsigned long long)mid,
786 (unsigned int)pml->buf.length ));
787 DLIST_REMOVE(sconn->deferred_open_queue, pml);
788 TALLOC_FREE(pml);
789 return;
794 /****************************************************************************
795 Move a sharing violation open retry message to the front of the list and
796 schedule it for immediate processing.
797 ****************************************************************************/
799 bool schedule_deferred_open_message_smb(struct smbXsrv_connection *xconn,
800 uint64_t mid)
802 struct smbd_server_connection *sconn = xconn->client->sconn;
803 struct pending_message_list *pml;
804 int i = 0;
806 if (sconn->using_smb2) {
807 return schedule_deferred_open_message_smb2(xconn, mid);
810 for (pml = sconn->deferred_open_queue; pml; pml = pml->next) {
811 uint64_t msg_mid = (uint64_t)SVAL(pml->buf.data,smb_mid);
813 DEBUG(10,("schedule_deferred_open_message_smb: [%d] "
814 "msg_mid = %llu\n",
815 i++,
816 (unsigned long long)msg_mid ));
818 if (mid == msg_mid) {
819 struct tevent_timer *te;
821 if (pml->processed) {
822 /* A processed message should not be
823 * rescheduled. */
824 DEBUG(0,("schedule_deferred_open_message_smb: LOGIC ERROR "
825 "message mid %llu was already processed\n",
826 (unsigned long long)msg_mid ));
827 continue;
830 DEBUG(10,("schedule_deferred_open_message_smb: "
831 "scheduling mid %llu\n",
832 (unsigned long long)mid ));
835 * smbd_deferred_open_timer() calls
836 * process_smb() to redispatch the request
837 * including the required impersonation.
839 * So we can just use the raw tevent_context.
841 te = tevent_add_timer(xconn->client->raw_ev_ctx,
842 pml,
843 timeval_zero(),
844 smbd_deferred_open_timer,
845 pml);
846 if (!te) {
847 DEBUG(10,("schedule_deferred_open_message_smb: "
848 "event_add_timed() failed, "
849 "skipping mid %llu\n",
850 (unsigned long long)msg_mid ));
853 TALLOC_FREE(pml->te);
854 pml->te = te;
855 DLIST_PROMOTE(sconn->deferred_open_queue, pml);
856 return true;
860 DEBUG(10,("schedule_deferred_open_message_smb: failed to "
861 "find message mid %llu\n",
862 (unsigned long long)mid ));
864 return false;
867 /****************************************************************************
868 Return true if this mid is on the deferred queue and was not yet processed.
869 ****************************************************************************/
871 bool open_was_deferred(struct smbXsrv_connection *xconn, uint64_t mid)
873 struct smbd_server_connection *sconn = xconn->client->sconn;
874 struct pending_message_list *pml;
876 if (sconn->using_smb2) {
877 return open_was_deferred_smb2(xconn, mid);
880 for (pml = sconn->deferred_open_queue; pml; pml = pml->next) {
881 if (((uint64_t)SVAL(pml->buf.data,smb_mid)) == mid && !pml->processed) {
882 return True;
885 return False;
888 /****************************************************************************
889 Return the message queued by this mid.
890 ****************************************************************************/
892 static struct pending_message_list *get_deferred_open_message_smb(
893 struct smbd_server_connection *sconn, uint64_t mid)
895 struct pending_message_list *pml;
897 for (pml = sconn->deferred_open_queue; pml; pml = pml->next) {
898 if (((uint64_t)SVAL(pml->buf.data,smb_mid)) == mid) {
899 return pml;
902 return NULL;
905 /****************************************************************************
906 Get the state data queued by this mid.
907 ****************************************************************************/
909 bool get_deferred_open_message_state(struct smb_request *smbreq,
910 struct timeval *p_request_time,
911 struct deferred_open_record **open_rec)
913 struct pending_message_list *pml;
915 if (smbreq->sconn->using_smb2) {
916 return get_deferred_open_message_state_smb2(smbreq->smb2req,
917 p_request_time,
918 open_rec);
921 pml = get_deferred_open_message_smb(smbreq->sconn, smbreq->mid);
922 if (!pml) {
923 return false;
925 if (p_request_time) {
926 *p_request_time = pml->request_time;
928 if (open_rec != NULL) {
929 *open_rec = pml->open_rec;
931 return true;
934 /****************************************************************************
935 Function to push a deferred open smb message onto a linked list of local smb
936 messages ready for processing.
937 ****************************************************************************/
939 bool push_deferred_open_message_smb(struct smb_request *req,
940 struct timeval timeout,
941 struct file_id id,
942 struct deferred_open_record *open_rec)
944 struct timeval_buf tvbuf;
945 struct timeval end_time;
947 if (req->smb2req) {
948 return push_deferred_open_message_smb2(req->smb2req,
949 req->request_time,
950 timeout,
952 open_rec);
955 if (req->unread_bytes) {
956 DEBUG(0,("push_deferred_open_message_smb: logic error ! "
957 "unread_bytes = %u\n",
958 (unsigned int)req->unread_bytes ));
959 smb_panic("push_deferred_open_message_smb: "
960 "logic error unread_bytes != 0" );
963 end_time = timeval_sum(&req->request_time, &timeout);
965 DBG_DEBUG("pushing message len %u mid %"PRIu64" timeout time [%s]\n",
966 (unsigned int) smb_len(req->inbuf)+4,
967 req->mid,
968 timeval_str_buf(&end_time, false, true, &tvbuf));
970 return push_queued_message(req, req->request_time, end_time, open_rec);
973 static void smbd_sig_term_handler(struct tevent_context *ev,
974 struct tevent_signal *se,
975 int signum,
976 int count,
977 void *siginfo,
978 void *private_data)
980 exit_server_cleanly("termination signal");
983 static void smbd_setup_sig_term_handler(struct smbd_server_connection *sconn)
985 struct tevent_signal *se;
987 se = tevent_add_signal(sconn->ev_ctx,
988 sconn,
989 SIGTERM, 0,
990 smbd_sig_term_handler,
991 sconn);
992 if (!se) {
993 exit_server("failed to setup SIGTERM handler");
997 static void smbd_sig_hup_handler(struct tevent_context *ev,
998 struct tevent_signal *se,
999 int signum,
1000 int count,
1001 void *siginfo,
1002 void *private_data)
1004 struct smbd_server_connection *sconn =
1005 talloc_get_type_abort(private_data,
1006 struct smbd_server_connection);
1008 change_to_root_user();
1009 DEBUG(1,("Reloading services after SIGHUP\n"));
1010 reload_services(sconn, conn_snum_used, false);
1013 static void smbd_setup_sig_hup_handler(struct smbd_server_connection *sconn)
1015 struct tevent_signal *se;
1017 se = tevent_add_signal(sconn->ev_ctx,
1018 sconn,
1019 SIGHUP, 0,
1020 smbd_sig_hup_handler,
1021 sconn);
1022 if (!se) {
1023 exit_server("failed to setup SIGHUP handler");
1027 static void smbd_conf_updated(struct messaging_context *msg,
1028 void *private_data,
1029 uint32_t msg_type,
1030 struct server_id server_id,
1031 DATA_BLOB *data)
1033 struct smbd_server_connection *sconn =
1034 talloc_get_type_abort(private_data,
1035 struct smbd_server_connection);
1037 DEBUG(10,("smbd_conf_updated: Got message saying smb.conf was "
1038 "updated. Reloading.\n"));
1039 change_to_root_user();
1040 reload_services(sconn, conn_snum_used, false);
1044 * Only allow 5 outstanding trans requests. We're allocating memory, so
1045 * prevent a DoS.
1048 NTSTATUS allow_new_trans(struct trans_state *list, uint64_t mid)
1050 int count = 0;
1051 for (; list != NULL; list = list->next) {
1053 if (list->mid == mid) {
1054 return NT_STATUS_INVALID_PARAMETER;
1057 count += 1;
1059 if (count > 5) {
1060 return NT_STATUS_INSUFFICIENT_RESOURCES;
1063 return NT_STATUS_OK;
1067 These flags determine some of the permissions required to do an operation
1069 Note that I don't set NEED_WRITE on some write operations because they
1070 are used by some brain-dead clients when printing, and I don't want to
1071 force write permissions on print services.
1073 #define AS_USER (1<<0)
1074 #define NEED_WRITE (1<<1) /* Must be paired with AS_USER */
1075 #define TIME_INIT (1<<2)
1076 #define CAN_IPC (1<<3) /* Must be paired with AS_USER */
1077 #define AS_GUEST (1<<5) /* Must *NOT* be paired with AS_USER */
1078 #define DO_CHDIR (1<<6)
1081 define a list of possible SMB messages and their corresponding
1082 functions. Any message that has a NULL function is unimplemented -
1083 please feel free to contribute implementations!
1085 static const struct smb_message_struct {
1086 const char *name;
1087 void (*fn)(struct smb_request *req);
1088 int flags;
1089 } smb_messages[256] = {
1091 /* 0x00 */ { "SMBmkdir",reply_mkdir,AS_USER | NEED_WRITE},
1092 /* 0x01 */ { "SMBrmdir",reply_rmdir,AS_USER | NEED_WRITE},
1093 /* 0x02 */ { "SMBopen",reply_open,AS_USER },
1094 /* 0x03 */ { "SMBcreate",reply_mknew,AS_USER},
1095 /* 0x04 */ { "SMBclose",reply_close,AS_USER | CAN_IPC },
1096 /* 0x05 */ { "SMBflush",reply_flush,AS_USER},
1097 /* 0x06 */ { "SMBunlink",reply_unlink,AS_USER | NEED_WRITE },
1098 /* 0x07 */ { "SMBmv",reply_mv,AS_USER | NEED_WRITE },
1099 /* 0x08 */ { "SMBgetatr",reply_getatr,AS_USER},
1100 /* 0x09 */ { "SMBsetatr",reply_setatr,AS_USER | NEED_WRITE},
1101 /* 0x0a */ { "SMBread",reply_read,AS_USER},
1102 /* 0x0b */ { "SMBwrite",reply_write,AS_USER | CAN_IPC },
1103 /* 0x0c */ { "SMBlock",reply_lock,AS_USER},
1104 /* 0x0d */ { "SMBunlock",reply_unlock,AS_USER},
1105 /* 0x0e */ { "SMBctemp",reply_ctemp,AS_USER },
1106 /* 0x0f */ { "SMBmknew",reply_mknew,AS_USER},
1107 /* 0x10 */ { "SMBcheckpath",reply_checkpath,AS_USER},
1108 /* 0x11 */ { "SMBexit",reply_exit,DO_CHDIR},
1109 /* 0x12 */ { "SMBlseek",reply_lseek,AS_USER},
1110 /* 0x13 */ { "SMBlockread",reply_lockread,AS_USER},
1111 /* 0x14 */ { "SMBwriteunlock",reply_writeunlock,AS_USER},
1112 /* 0x15 */ { NULL, NULL, 0 },
1113 /* 0x16 */ { NULL, NULL, 0 },
1114 /* 0x17 */ { NULL, NULL, 0 },
1115 /* 0x18 */ { NULL, NULL, 0 },
1116 /* 0x19 */ { NULL, NULL, 0 },
1117 /* 0x1a */ { "SMBreadbraw",reply_readbraw,AS_USER},
1118 /* 0x1b */ { "SMBreadBmpx",reply_readbmpx,AS_USER},
1119 /* 0x1c */ { "SMBreadBs",reply_readbs,AS_USER },
1120 /* 0x1d */ { "SMBwritebraw",reply_writebraw,AS_USER},
1121 /* 0x1e */ { "SMBwriteBmpx",reply_writebmpx,AS_USER},
1122 /* 0x1f */ { "SMBwriteBs",reply_writebs,AS_USER},
1123 /* 0x20 */ { "SMBwritec", NULL,0},
1124 /* 0x21 */ { NULL, NULL, 0 },
1125 /* 0x22 */ { "SMBsetattrE",reply_setattrE,AS_USER | NEED_WRITE },
1126 /* 0x23 */ { "SMBgetattrE",reply_getattrE,AS_USER },
1127 /* 0x24 */ { "SMBlockingX",reply_lockingX,AS_USER },
1128 /* 0x25 */ { "SMBtrans",reply_trans,AS_USER | CAN_IPC },
1129 /* 0x26 */ { "SMBtranss",reply_transs,AS_USER | CAN_IPC},
1130 /* 0x27 */ { "SMBioctl",reply_ioctl,0},
1131 /* 0x28 */ { "SMBioctls", NULL,AS_USER},
1132 /* 0x29 */ { "SMBcopy",reply_copy,AS_USER | NEED_WRITE },
1133 /* 0x2a */ { "SMBmove", NULL,AS_USER | NEED_WRITE },
1134 /* 0x2b */ { "SMBecho",reply_echo,0},
1135 /* 0x2c */ { "SMBwriteclose",reply_writeclose,AS_USER},
1136 /* 0x2d */ { "SMBopenX",reply_open_and_X,AS_USER | CAN_IPC },
1137 /* 0x2e */ { "SMBreadX",reply_read_and_X,AS_USER | CAN_IPC },
1138 /* 0x2f */ { "SMBwriteX",reply_write_and_X,AS_USER | CAN_IPC },
1139 /* 0x30 */ { NULL, NULL, 0 },
1140 /* 0x31 */ { NULL, NULL, 0 },
1141 /* 0x32 */ { "SMBtrans2",reply_trans2, AS_USER | CAN_IPC },
1142 /* 0x33 */ { "SMBtranss2",reply_transs2, AS_USER | CAN_IPC },
1143 /* 0x34 */ { "SMBfindclose",reply_findclose,AS_USER},
1144 /* 0x35 */ { "SMBfindnclose",reply_findnclose,AS_USER},
1145 /* 0x36 */ { NULL, NULL, 0 },
1146 /* 0x37 */ { NULL, NULL, 0 },
1147 /* 0x38 */ { NULL, NULL, 0 },
1148 /* 0x39 */ { NULL, NULL, 0 },
1149 /* 0x3a */ { NULL, NULL, 0 },
1150 /* 0x3b */ { NULL, NULL, 0 },
1151 /* 0x3c */ { NULL, NULL, 0 },
1152 /* 0x3d */ { NULL, NULL, 0 },
1153 /* 0x3e */ { NULL, NULL, 0 },
1154 /* 0x3f */ { NULL, NULL, 0 },
1155 /* 0x40 */ { NULL, NULL, 0 },
1156 /* 0x41 */ { NULL, NULL, 0 },
1157 /* 0x42 */ { NULL, NULL, 0 },
1158 /* 0x43 */ { NULL, NULL, 0 },
1159 /* 0x44 */ { NULL, NULL, 0 },
1160 /* 0x45 */ { NULL, NULL, 0 },
1161 /* 0x46 */ { NULL, NULL, 0 },
1162 /* 0x47 */ { NULL, NULL, 0 },
1163 /* 0x48 */ { NULL, NULL, 0 },
1164 /* 0x49 */ { NULL, NULL, 0 },
1165 /* 0x4a */ { NULL, NULL, 0 },
1166 /* 0x4b */ { NULL, NULL, 0 },
1167 /* 0x4c */ { NULL, NULL, 0 },
1168 /* 0x4d */ { NULL, NULL, 0 },
1169 /* 0x4e */ { NULL, NULL, 0 },
1170 /* 0x4f */ { NULL, NULL, 0 },
1171 /* 0x50 */ { NULL, NULL, 0 },
1172 /* 0x51 */ { NULL, NULL, 0 },
1173 /* 0x52 */ { NULL, NULL, 0 },
1174 /* 0x53 */ { NULL, NULL, 0 },
1175 /* 0x54 */ { NULL, NULL, 0 },
1176 /* 0x55 */ { NULL, NULL, 0 },
1177 /* 0x56 */ { NULL, NULL, 0 },
1178 /* 0x57 */ { NULL, NULL, 0 },
1179 /* 0x58 */ { NULL, NULL, 0 },
1180 /* 0x59 */ { NULL, NULL, 0 },
1181 /* 0x5a */ { NULL, NULL, 0 },
1182 /* 0x5b */ { NULL, NULL, 0 },
1183 /* 0x5c */ { NULL, NULL, 0 },
1184 /* 0x5d */ { NULL, NULL, 0 },
1185 /* 0x5e */ { NULL, NULL, 0 },
1186 /* 0x5f */ { NULL, NULL, 0 },
1187 /* 0x60 */ { NULL, NULL, 0 },
1188 /* 0x61 */ { NULL, NULL, 0 },
1189 /* 0x62 */ { NULL, NULL, 0 },
1190 /* 0x63 */ { NULL, NULL, 0 },
1191 /* 0x64 */ { NULL, NULL, 0 },
1192 /* 0x65 */ { NULL, NULL, 0 },
1193 /* 0x66 */ { NULL, NULL, 0 },
1194 /* 0x67 */ { NULL, NULL, 0 },
1195 /* 0x68 */ { NULL, NULL, 0 },
1196 /* 0x69 */ { NULL, NULL, 0 },
1197 /* 0x6a */ { NULL, NULL, 0 },
1198 /* 0x6b */ { NULL, NULL, 0 },
1199 /* 0x6c */ { NULL, NULL, 0 },
1200 /* 0x6d */ { NULL, NULL, 0 },
1201 /* 0x6e */ { NULL, NULL, 0 },
1202 /* 0x6f */ { NULL, NULL, 0 },
1203 /* 0x70 */ { "SMBtcon",reply_tcon,0},
1204 /* 0x71 */ { "SMBtdis",reply_tdis,DO_CHDIR},
1205 /* 0x72 */ { "SMBnegprot",reply_negprot,0},
1206 /* 0x73 */ { "SMBsesssetupX",reply_sesssetup_and_X,0},
1207 /* 0x74 */ { "SMBulogoffX",reply_ulogoffX, 0}, /* ulogoff doesn't give a valid TID */
1208 /* 0x75 */ { "SMBtconX",reply_tcon_and_X,0},
1209 /* 0x76 */ { NULL, NULL, 0 },
1210 /* 0x77 */ { NULL, NULL, 0 },
1211 /* 0x78 */ { NULL, NULL, 0 },
1212 /* 0x79 */ { NULL, NULL, 0 },
1213 /* 0x7a */ { NULL, NULL, 0 },
1214 /* 0x7b */ { NULL, NULL, 0 },
1215 /* 0x7c */ { NULL, NULL, 0 },
1216 /* 0x7d */ { NULL, NULL, 0 },
1217 /* 0x7e */ { NULL, NULL, 0 },
1218 /* 0x7f */ { NULL, NULL, 0 },
1219 /* 0x80 */ { "SMBdskattr",reply_dskattr,AS_USER},
1220 /* 0x81 */ { "SMBsearch",reply_search,AS_USER},
1221 /* 0x82 */ { "SMBffirst",reply_search,AS_USER},
1222 /* 0x83 */ { "SMBfunique",reply_search,AS_USER},
1223 /* 0x84 */ { "SMBfclose",reply_fclose,AS_USER},
1224 /* 0x85 */ { NULL, NULL, 0 },
1225 /* 0x86 */ { NULL, NULL, 0 },
1226 /* 0x87 */ { NULL, NULL, 0 },
1227 /* 0x88 */ { NULL, NULL, 0 },
1228 /* 0x89 */ { NULL, NULL, 0 },
1229 /* 0x8a */ { NULL, NULL, 0 },
1230 /* 0x8b */ { NULL, NULL, 0 },
1231 /* 0x8c */ { NULL, NULL, 0 },
1232 /* 0x8d */ { NULL, NULL, 0 },
1233 /* 0x8e */ { NULL, NULL, 0 },
1234 /* 0x8f */ { NULL, NULL, 0 },
1235 /* 0x90 */ { NULL, NULL, 0 },
1236 /* 0x91 */ { NULL, NULL, 0 },
1237 /* 0x92 */ { NULL, NULL, 0 },
1238 /* 0x93 */ { NULL, NULL, 0 },
1239 /* 0x94 */ { NULL, NULL, 0 },
1240 /* 0x95 */ { NULL, NULL, 0 },
1241 /* 0x96 */ { NULL, NULL, 0 },
1242 /* 0x97 */ { NULL, NULL, 0 },
1243 /* 0x98 */ { NULL, NULL, 0 },
1244 /* 0x99 */ { NULL, NULL, 0 },
1245 /* 0x9a */ { NULL, NULL, 0 },
1246 /* 0x9b */ { NULL, NULL, 0 },
1247 /* 0x9c */ { NULL, NULL, 0 },
1248 /* 0x9d */ { NULL, NULL, 0 },
1249 /* 0x9e */ { NULL, NULL, 0 },
1250 /* 0x9f */ { NULL, NULL, 0 },
1251 /* 0xa0 */ { "SMBnttrans",reply_nttrans, AS_USER | CAN_IPC },
1252 /* 0xa1 */ { "SMBnttranss",reply_nttranss, AS_USER | CAN_IPC },
1253 /* 0xa2 */ { "SMBntcreateX",reply_ntcreate_and_X, AS_USER | CAN_IPC },
1254 /* 0xa3 */ { NULL, NULL, 0 },
1255 /* 0xa4 */ { "SMBntcancel",reply_ntcancel, 0 },
1256 /* 0xa5 */ { "SMBntrename",reply_ntrename, AS_USER | NEED_WRITE },
1257 /* 0xa6 */ { NULL, NULL, 0 },
1258 /* 0xa7 */ { NULL, NULL, 0 },
1259 /* 0xa8 */ { NULL, NULL, 0 },
1260 /* 0xa9 */ { NULL, NULL, 0 },
1261 /* 0xaa */ { NULL, NULL, 0 },
1262 /* 0xab */ { NULL, NULL, 0 },
1263 /* 0xac */ { NULL, NULL, 0 },
1264 /* 0xad */ { NULL, NULL, 0 },
1265 /* 0xae */ { NULL, NULL, 0 },
1266 /* 0xaf */ { NULL, NULL, 0 },
1267 /* 0xb0 */ { NULL, NULL, 0 },
1268 /* 0xb1 */ { NULL, NULL, 0 },
1269 /* 0xb2 */ { NULL, NULL, 0 },
1270 /* 0xb3 */ { NULL, NULL, 0 },
1271 /* 0xb4 */ { NULL, NULL, 0 },
1272 /* 0xb5 */ { NULL, NULL, 0 },
1273 /* 0xb6 */ { NULL, NULL, 0 },
1274 /* 0xb7 */ { NULL, NULL, 0 },
1275 /* 0xb8 */ { NULL, NULL, 0 },
1276 /* 0xb9 */ { NULL, NULL, 0 },
1277 /* 0xba */ { NULL, NULL, 0 },
1278 /* 0xbb */ { NULL, NULL, 0 },
1279 /* 0xbc */ { NULL, NULL, 0 },
1280 /* 0xbd */ { NULL, NULL, 0 },
1281 /* 0xbe */ { NULL, NULL, 0 },
1282 /* 0xbf */ { NULL, NULL, 0 },
1283 /* 0xc0 */ { "SMBsplopen",reply_printopen,AS_USER},
1284 /* 0xc1 */ { "SMBsplwr",reply_printwrite,AS_USER},
1285 /* 0xc2 */ { "SMBsplclose",reply_printclose,AS_USER},
1286 /* 0xc3 */ { "SMBsplretq",reply_printqueue,AS_USER},
1287 /* 0xc4 */ { NULL, NULL, 0 },
1288 /* 0xc5 */ { NULL, NULL, 0 },
1289 /* 0xc6 */ { NULL, NULL, 0 },
1290 /* 0xc7 */ { NULL, NULL, 0 },
1291 /* 0xc8 */ { NULL, NULL, 0 },
1292 /* 0xc9 */ { NULL, NULL, 0 },
1293 /* 0xca */ { NULL, NULL, 0 },
1294 /* 0xcb */ { NULL, NULL, 0 },
1295 /* 0xcc */ { NULL, NULL, 0 },
1296 /* 0xcd */ { NULL, NULL, 0 },
1297 /* 0xce */ { NULL, NULL, 0 },
1298 /* 0xcf */ { NULL, NULL, 0 },
1299 /* 0xd0 */ { "SMBsends",reply_sends,AS_GUEST},
1300 /* 0xd1 */ { "SMBsendb", NULL,AS_GUEST},
1301 /* 0xd2 */ { "SMBfwdname", NULL,AS_GUEST},
1302 /* 0xd3 */ { "SMBcancelf", NULL,AS_GUEST},
1303 /* 0xd4 */ { "SMBgetmac", NULL,AS_GUEST},
1304 /* 0xd5 */ { "SMBsendstrt",reply_sendstrt,AS_GUEST},
1305 /* 0xd6 */ { "SMBsendend",reply_sendend,AS_GUEST},
1306 /* 0xd7 */ { "SMBsendtxt",reply_sendtxt,AS_GUEST},
1307 /* 0xd8 */ { NULL, NULL, 0 },
1308 /* 0xd9 */ { NULL, NULL, 0 },
1309 /* 0xda */ { NULL, NULL, 0 },
1310 /* 0xdb */ { NULL, NULL, 0 },
1311 /* 0xdc */ { NULL, NULL, 0 },
1312 /* 0xdd */ { NULL, NULL, 0 },
1313 /* 0xde */ { NULL, NULL, 0 },
1314 /* 0xdf */ { NULL, NULL, 0 },
1315 /* 0xe0 */ { NULL, NULL, 0 },
1316 /* 0xe1 */ { NULL, NULL, 0 },
1317 /* 0xe2 */ { NULL, NULL, 0 },
1318 /* 0xe3 */ { NULL, NULL, 0 },
1319 /* 0xe4 */ { NULL, NULL, 0 },
1320 /* 0xe5 */ { NULL, NULL, 0 },
1321 /* 0xe6 */ { NULL, NULL, 0 },
1322 /* 0xe7 */ { NULL, NULL, 0 },
1323 /* 0xe8 */ { NULL, NULL, 0 },
1324 /* 0xe9 */ { NULL, NULL, 0 },
1325 /* 0xea */ { NULL, NULL, 0 },
1326 /* 0xeb */ { NULL, NULL, 0 },
1327 /* 0xec */ { NULL, NULL, 0 },
1328 /* 0xed */ { NULL, NULL, 0 },
1329 /* 0xee */ { NULL, NULL, 0 },
1330 /* 0xef */ { NULL, NULL, 0 },
1331 /* 0xf0 */ { NULL, NULL, 0 },
1332 /* 0xf1 */ { NULL, NULL, 0 },
1333 /* 0xf2 */ { NULL, NULL, 0 },
1334 /* 0xf3 */ { NULL, NULL, 0 },
1335 /* 0xf4 */ { NULL, NULL, 0 },
1336 /* 0xf5 */ { NULL, NULL, 0 },
1337 /* 0xf6 */ { NULL, NULL, 0 },
1338 /* 0xf7 */ { NULL, NULL, 0 },
1339 /* 0xf8 */ { NULL, NULL, 0 },
1340 /* 0xf9 */ { NULL, NULL, 0 },
1341 /* 0xfa */ { NULL, NULL, 0 },
1342 /* 0xfb */ { NULL, NULL, 0 },
1343 /* 0xfc */ { NULL, NULL, 0 },
1344 /* 0xfd */ { NULL, NULL, 0 },
1345 /* 0xfe */ { NULL, NULL, 0 },
1346 /* 0xff */ { NULL, NULL, 0 }
1350 /*******************************************************************
1351 allocate and initialize a reply packet
1352 ********************************************************************/
1354 static bool create_outbuf(TALLOC_CTX *mem_ctx, struct smb_request *req,
1355 const uint8_t *inbuf, char **outbuf,
1356 uint8_t num_words, uint32_t num_bytes)
1358 size_t smb_len = MIN_SMB_SIZE + VWV(num_words) + num_bytes;
1361 * Protect against integer wrap.
1362 * The SMB layer reply can be up to 0xFFFFFF bytes.
1364 if ((num_bytes > 0xffffff) || (smb_len > 0xffffff)) {
1365 char *msg;
1366 if (asprintf(&msg, "num_bytes too large: %u",
1367 (unsigned)num_bytes) == -1) {
1368 msg = discard_const_p(char, "num_bytes too large");
1370 smb_panic(msg);
1374 * Here we include the NBT header for now.
1376 *outbuf = talloc_array(mem_ctx, char,
1377 NBT_HDR_SIZE + smb_len);
1378 if (*outbuf == NULL) {
1379 return false;
1382 construct_reply_common(req->cmd, inbuf, *outbuf);
1383 srv_set_message(*outbuf, num_words, num_bytes, false);
1385 * Zero out the word area, the caller has to take care of the bcc area
1386 * himself
1388 if (num_words != 0) {
1389 memset(*outbuf + (NBT_HDR_SIZE + HDR_VWV), 0, VWV(num_words));
1392 return true;
1395 void reply_outbuf(struct smb_request *req, uint8_t num_words, uint32_t num_bytes)
1397 char *outbuf;
1398 if (!create_outbuf(req, req, req->inbuf, &outbuf, num_words,
1399 num_bytes)) {
1400 smb_panic("could not allocate output buffer\n");
1402 req->outbuf = (uint8_t *)outbuf;
1406 /*******************************************************************
1407 Dump a packet to a file.
1408 ********************************************************************/
1410 static void smb_dump(const char *name, int type, const char *data)
1412 size_t len;
1413 int fd, i;
1414 char *fname = NULL;
1415 if (DEBUGLEVEL < 50) {
1416 return;
1419 len = smb_len_tcp(data)+4;
1420 for (i=1;i<100;i++) {
1421 fname = talloc_asprintf(talloc_tos(),
1422 "/tmp/%s.%d.%s",
1423 name,
1425 type ? "req" : "resp");
1426 if (fname == NULL) {
1427 return;
1429 fd = open(fname, O_WRONLY|O_CREAT|O_EXCL, 0644);
1430 if (fd != -1 || errno != EEXIST) break;
1431 TALLOC_FREE(fname);
1433 if (fd != -1) {
1434 ssize_t ret = write(fd, data, len);
1435 if (ret != len)
1436 DEBUG(0,("smb_dump: problem: write returned %d\n", (int)ret ));
1437 close(fd);
1438 DEBUG(0,("created %s len %lu\n", fname, (unsigned long)len));
1440 TALLOC_FREE(fname);
1443 static void smb1srv_update_crypto_flags(struct smbXsrv_session *session,
1444 struct smb_request *req,
1445 uint8_t type,
1446 bool *update_session_globalp,
1447 bool *update_tcon_globalp)
1449 connection_struct *conn = req->conn;
1450 struct smbXsrv_tcon *tcon = conn ? conn->tcon : NULL;
1451 uint8_t encrypt_flag = SMBXSRV_PROCESSED_UNENCRYPTED_PACKET;
1452 uint8_t sign_flag = SMBXSRV_PROCESSED_UNSIGNED_PACKET;
1453 bool update_session = false;
1454 bool update_tcon = false;
1456 if (req->encrypted) {
1457 encrypt_flag = SMBXSRV_PROCESSED_ENCRYPTED_PACKET;
1460 if (srv_is_signing_active(req->xconn)) {
1461 sign_flag = SMBXSRV_PROCESSED_SIGNED_PACKET;
1462 } else if ((type == SMBecho) || (type == SMBsesssetupX)) {
1464 * echo can be unsigned. Sesssion setup except final
1465 * session setup response too
1467 sign_flag &= ~SMBXSRV_PROCESSED_UNSIGNED_PACKET;
1470 update_session |= smbXsrv_set_crypto_flag(
1471 &session->global->encryption_flags, encrypt_flag);
1472 update_session |= smbXsrv_set_crypto_flag(
1473 &session->global->signing_flags, sign_flag);
1475 if (tcon) {
1476 update_tcon |= smbXsrv_set_crypto_flag(
1477 &tcon->global->encryption_flags, encrypt_flag);
1478 update_tcon |= smbXsrv_set_crypto_flag(
1479 &tcon->global->signing_flags, sign_flag);
1482 if (update_session) {
1483 session->global->channels[0].encryption_cipher = SMB_ENCRYPTION_GSSAPI;
1486 *update_session_globalp = update_session;
1487 *update_tcon_globalp = update_tcon;
1488 return;
1491 /****************************************************************************
1492 Prepare everything for calling the actual request function, and potentially
1493 call the request function via the "new" interface.
1495 Return False if the "legacy" function needs to be called, everything is
1496 prepared.
1498 Return True if we're done.
1500 I know this API sucks, but it is the one with the least code change I could
1501 find.
1502 ****************************************************************************/
1504 static connection_struct *switch_message(uint8_t type, struct smb_request *req)
1506 const struct loadparm_substitution *lp_sub =
1507 loadparm_s3_global_substitution();
1508 int flags;
1509 uint64_t session_tag;
1510 connection_struct *conn = NULL;
1511 struct smbXsrv_connection *xconn = req->xconn;
1512 NTTIME now = timeval_to_nttime(&req->request_time);
1513 struct smbXsrv_session *session = NULL;
1514 NTSTATUS status;
1516 errno = 0;
1518 if (!xconn->smb1.negprot.done) {
1519 switch (type) {
1521 * Without a negprot the request must
1522 * either be a negprot, or one of the
1523 * evil old SMB mailslot messaging types.
1525 case SMBnegprot:
1526 case SMBsendstrt:
1527 case SMBsendend:
1528 case SMBsendtxt:
1529 break;
1530 default:
1531 exit_server_cleanly("The first request "
1532 "should be a negprot");
1536 if (smb_messages[type].fn == NULL) {
1537 DEBUG(0,("Unknown message type %d!\n",type));
1538 smb_dump("Unknown", 1, (const char *)req->inbuf);
1539 reply_unknown_new(req, type);
1540 return NULL;
1543 flags = smb_messages[type].flags;
1545 /* In share mode security we must ignore the vuid. */
1546 session_tag = req->vuid;
1547 conn = req->conn;
1549 DEBUG(3,("switch message %s (pid %d) conn 0x%lx\n", smb_fn_name(type),
1550 (int)getpid(), (unsigned long)conn));
1552 smb_dump(smb_fn_name(type), 1, (const char *)req->inbuf);
1554 /* Ensure this value is replaced in the incoming packet. */
1555 SSVAL(discard_const_p(uint8_t, req->inbuf),smb_uid,session_tag);
1558 * Ensure the correct username is in current_user_info. This is a
1559 * really ugly bugfix for problems with multiple session_setup_and_X's
1560 * being done and allowing %U and %G substitutions to work correctly.
1561 * There is a reason this code is done here, don't move it unless you
1562 * know what you're doing... :-).
1563 * JRA.
1567 * lookup an existing session
1569 * Note: for now we only check for NT_STATUS_NETWORK_SESSION_EXPIRED
1570 * here, the main check is still in change_to_user()
1572 status = smb1srv_session_lookup(xconn,
1573 session_tag,
1574 now,
1575 &session);
1576 if (NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_SESSION_EXPIRED)) {
1577 switch (type) {
1578 case SMBsesssetupX:
1579 status = NT_STATUS_OK;
1580 break;
1581 default:
1582 DEBUG(1,("Error: session %llu is expired, mid=%llu.\n",
1583 (unsigned long long)session_tag,
1584 (unsigned long long)req->mid));
1585 reply_nterror(req, NT_STATUS_NETWORK_SESSION_EXPIRED);
1586 return conn;
1590 if (session != NULL && !(flags & AS_USER)) {
1591 struct user_struct *vuser = session->compat;
1594 * change_to_user() implies set_current_user_info()
1595 * and chdir_connect_service().
1597 * So we only call set_current_user_info if
1598 * we don't have AS_USER specified.
1600 if (vuser) {
1601 set_current_user_info(
1602 vuser->session_info->unix_info->sanitized_username,
1603 vuser->session_info->unix_info->unix_name,
1604 vuser->session_info->info->domain_name);
1608 /* Does this call need to be run as the connected user? */
1609 if (flags & AS_USER) {
1611 /* Does this call need a valid tree connection? */
1612 if (!conn) {
1614 * Amazingly, the error code depends on the command
1615 * (from Samba4).
1617 if (type == SMBntcreateX) {
1618 reply_nterror(req, NT_STATUS_INVALID_HANDLE);
1619 } else {
1620 reply_nterror(req, NT_STATUS_NETWORK_NAME_DELETED);
1622 return NULL;
1625 set_current_case_sensitive(conn, SVAL(req->inbuf,smb_flg));
1628 * change_to_user() implies set_current_user_info()
1629 * and chdir_connect_service().
1631 if (!change_to_user_and_service(conn,session_tag)) {
1632 DEBUG(0, ("Error: Could not change to user. Removing "
1633 "deferred open, mid=%llu.\n",
1634 (unsigned long long)req->mid));
1635 reply_force_doserror(req, ERRSRV, ERRbaduid);
1636 return conn;
1639 /* All NEED_WRITE and CAN_IPC flags must also have AS_USER. */
1641 /* Does it need write permission? */
1642 if ((flags & NEED_WRITE) && !CAN_WRITE(conn)) {
1643 reply_nterror(req, NT_STATUS_MEDIA_WRITE_PROTECTED);
1644 return conn;
1647 /* IPC services are limited */
1648 if (IS_IPC(conn) && !(flags & CAN_IPC)) {
1649 reply_nterror(req, NT_STATUS_ACCESS_DENIED);
1650 return conn;
1652 } else if (flags & AS_GUEST) {
1654 * Does this protocol need to be run as guest? (Only archane
1655 * messenger service requests have this...)
1657 if (!change_to_guest()) {
1658 reply_nterror(req, NT_STATUS_ACCESS_DENIED);
1659 return conn;
1661 } else {
1662 /* This call needs to be run as root */
1663 change_to_root_user();
1666 /* load service specific parameters */
1667 if (conn) {
1668 if (req->encrypted) {
1669 conn->encrypted_tid = true;
1670 /* encrypted required from now on. */
1671 conn->encrypt_level = SMB_SIGNING_REQUIRED;
1672 } else if (ENCRYPTION_REQUIRED(conn)) {
1673 if (req->cmd != SMBtrans2 && req->cmd != SMBtranss2) {
1674 DEBUG(1,("service[%s] requires encryption"
1675 "%s ACCESS_DENIED. mid=%llu\n",
1676 lp_servicename(talloc_tos(), lp_sub, SNUM(conn)),
1677 smb_fn_name(type),
1678 (unsigned long long)req->mid));
1679 reply_nterror(req, NT_STATUS_ACCESS_DENIED);
1680 return conn;
1684 if (flags & DO_CHDIR) {
1685 bool ok;
1687 ok = chdir_current_service(conn);
1688 if (!ok) {
1689 reply_nterror(req, NT_STATUS_ACCESS_DENIED);
1690 return conn;
1693 conn->num_smb_operations++;
1697 * Update encryption and signing state tracking flags that are
1698 * used by smbstatus to display signing and encryption status.
1700 if (session != NULL) {
1701 bool update_session_global = false;
1702 bool update_tcon_global = false;
1704 smb1srv_update_crypto_flags(session, req, type,
1705 &update_session_global,
1706 &update_tcon_global);
1708 if (update_session_global) {
1709 status = smbXsrv_session_update(session);
1710 if (!NT_STATUS_IS_OK(status)) {
1711 reply_nterror(req, NT_STATUS_UNSUCCESSFUL);
1712 return conn;
1716 if (update_tcon_global) {
1717 status = smbXsrv_tcon_update(req->conn->tcon);
1718 if (!NT_STATUS_IS_OK(status)) {
1719 reply_nterror(req, NT_STATUS_UNSUCCESSFUL);
1720 return conn;
1725 smb_messages[type].fn(req);
1726 return req->conn;
1729 /****************************************************************************
1730 Construct a reply to the incoming packet.
1731 ****************************************************************************/
1733 static void construct_reply(struct smbXsrv_connection *xconn,
1734 char *inbuf, int size, size_t unread_bytes,
1735 uint32_t seqnum, bool encrypted,
1736 struct smb_perfcount_data *deferred_pcd)
1738 struct smbd_server_connection *sconn = xconn->client->sconn;
1739 struct smb_request *req;
1741 if (!(req = talloc(talloc_tos(), struct smb_request))) {
1742 smb_panic("could not allocate smb_request");
1745 if (!init_smb_request(req, sconn, xconn, (uint8_t *)inbuf, unread_bytes,
1746 encrypted, seqnum)) {
1747 exit_server_cleanly("Invalid SMB request");
1750 req->inbuf = (uint8_t *)talloc_move(req, &inbuf);
1752 /* we popped this message off the queue - keep original perf data */
1753 if (deferred_pcd)
1754 req->pcd = *deferred_pcd;
1755 else {
1756 SMB_PERFCOUNT_START(&req->pcd);
1757 SMB_PERFCOUNT_SET_OP(&req->pcd, req->cmd);
1758 SMB_PERFCOUNT_SET_MSGLEN_IN(&req->pcd, size);
1761 req->conn = switch_message(req->cmd, req);
1763 if (req->outbuf == NULL) {
1765 * Request has suspended itself, will come
1766 * back here.
1768 return;
1770 if (CVAL(req->outbuf,0) == 0) {
1771 show_msg((char *)req->outbuf);
1773 smb_request_done(req);
1776 static void construct_reply_chain(struct smbXsrv_connection *xconn,
1777 char *inbuf, int size, uint32_t seqnum,
1778 bool encrypted,
1779 struct smb_perfcount_data *deferred_pcd)
1781 struct smb_request **reqs = NULL;
1782 struct smb_request *req;
1783 unsigned num_reqs;
1784 bool ok;
1786 ok = smb1_parse_chain(xconn, (uint8_t *)inbuf, xconn, encrypted,
1787 seqnum, &reqs, &num_reqs);
1788 if (!ok) {
1789 char errbuf[smb_size];
1790 error_packet(errbuf, 0, 0, NT_STATUS_INVALID_PARAMETER,
1791 __LINE__, __FILE__);
1792 if (!srv_send_smb(xconn, errbuf, true, seqnum, encrypted,
1793 NULL)) {
1794 exit_server_cleanly("construct_reply_chain: "
1795 "srv_send_smb failed.");
1797 return;
1800 req = reqs[0];
1801 req->inbuf = (uint8_t *)talloc_move(reqs, &inbuf);
1803 req->conn = switch_message(req->cmd, req);
1805 if (req->outbuf == NULL) {
1807 * Request has suspended itself, will come
1808 * back here.
1810 return;
1812 smb_request_done(req);
1816 * To be called from an async SMB handler that is potentially chained
1817 * when it is finished for shipping.
1820 void smb_request_done(struct smb_request *req)
1822 struct smb_request **reqs = NULL;
1823 struct smb_request *first_req;
1824 size_t i, num_reqs, next_index;
1825 NTSTATUS status;
1827 if (req->chain == NULL) {
1828 first_req = req;
1829 goto shipit;
1832 reqs = req->chain;
1833 num_reqs = talloc_array_length(reqs);
1835 for (i=0; i<num_reqs; i++) {
1836 if (reqs[i] == req) {
1837 break;
1840 if (i == num_reqs) {
1842 * Invalid chain, should not happen
1844 status = NT_STATUS_INTERNAL_ERROR;
1845 goto error;
1847 next_index = i+1;
1849 while ((next_index < num_reqs) && (IVAL(req->outbuf, smb_rcls) == 0)) {
1850 struct smb_request *next = reqs[next_index];
1851 struct smbXsrv_tcon *tcon;
1852 NTTIME now = timeval_to_nttime(&req->request_time);
1854 next->vuid = SVAL(req->outbuf, smb_uid);
1855 next->tid = SVAL(req->outbuf, smb_tid);
1856 status = smb1srv_tcon_lookup(req->xconn, next->tid,
1857 now, &tcon);
1859 if (NT_STATUS_IS_OK(status)) {
1860 next->conn = tcon->compat;
1861 } else {
1862 next->conn = NULL;
1864 next->chain_fsp = req->chain_fsp;
1865 next->inbuf = req->inbuf;
1867 req = next;
1868 req->conn = switch_message(req->cmd, req);
1870 if (req->outbuf == NULL) {
1872 * Request has suspended itself, will come
1873 * back here.
1875 return;
1877 next_index += 1;
1880 first_req = reqs[0];
1882 for (i=1; i<next_index; i++) {
1883 bool ok;
1885 ok = smb_splice_chain(&first_req->outbuf, reqs[i]->outbuf);
1886 if (!ok) {
1887 status = NT_STATUS_INTERNAL_ERROR;
1888 goto error;
1892 SSVAL(first_req->outbuf, smb_uid, SVAL(req->outbuf, smb_uid));
1893 SSVAL(first_req->outbuf, smb_tid, SVAL(req->outbuf, smb_tid));
1896 * This scary statement intends to set the
1897 * FLAGS2_32_BIT_ERROR_CODES flg2 field in first_req->outbuf
1898 * to the value last_req->outbuf carries
1900 SSVAL(first_req->outbuf, smb_flg2,
1901 (SVAL(first_req->outbuf, smb_flg2) & ~FLAGS2_32_BIT_ERROR_CODES)
1902 |(SVAL(req->outbuf, smb_flg2) & FLAGS2_32_BIT_ERROR_CODES));
1905 * Transfer the error codes from the subrequest to the main one
1907 SSVAL(first_req->outbuf, smb_rcls, SVAL(req->outbuf, smb_rcls));
1908 SSVAL(first_req->outbuf, smb_err, SVAL(req->outbuf, smb_err));
1910 _smb_setlen_large(
1911 first_req->outbuf, talloc_get_size(first_req->outbuf) - 4);
1913 shipit:
1914 if (!srv_send_smb(first_req->xconn,
1915 (char *)first_req->outbuf,
1916 true, first_req->seqnum+1,
1917 IS_CONN_ENCRYPTED(req->conn)||first_req->encrypted,
1918 &first_req->pcd)) {
1919 exit_server_cleanly("construct_reply_chain: srv_send_smb "
1920 "failed.");
1922 TALLOC_FREE(req); /* non-chained case */
1923 TALLOC_FREE(reqs); /* chained case */
1924 return;
1926 error:
1928 char errbuf[smb_size];
1929 error_packet(errbuf, 0, 0, status, __LINE__, __FILE__);
1930 if (!srv_send_smb(req->xconn, errbuf, true,
1931 req->seqnum+1, req->encrypted,
1932 NULL)) {
1933 exit_server_cleanly("construct_reply_chain: "
1934 "srv_send_smb failed.");
1937 TALLOC_FREE(req); /* non-chained case */
1938 TALLOC_FREE(reqs); /* chained case */
1941 /****************************************************************************
1942 Process an smb from the client
1943 ****************************************************************************/
1944 static void process_smb(struct smbXsrv_connection *xconn,
1945 uint8_t *inbuf, size_t nread, size_t unread_bytes,
1946 uint32_t seqnum, bool encrypted,
1947 struct smb_perfcount_data *deferred_pcd)
1949 struct smbd_server_connection *sconn = xconn->client->sconn;
1950 int msg_type = CVAL(inbuf,0);
1952 DO_PROFILE_INC(request);
1954 DEBUG( 6, ( "got message type 0x%x of len 0x%x\n", msg_type,
1955 smb_len(inbuf) ) );
1956 DEBUG(3, ("Transaction %d of length %d (%u toread)\n",
1957 sconn->trans_num, (int)nread, (unsigned int)unread_bytes));
1959 if (msg_type != NBSSmessage) {
1961 * NetBIOS session request, keepalive, etc.
1963 reply_special(xconn, (char *)inbuf, nread);
1964 goto done;
1967 if (sconn->using_smb2) {
1968 /* At this point we're not really using smb2,
1969 * we make the decision here.. */
1970 if (smbd_is_smb2_header(inbuf, nread)) {
1971 const uint8_t *inpdu = inbuf + NBT_HDR_SIZE;
1972 size_t pdulen = nread - NBT_HDR_SIZE;
1973 smbd_smb2_process_negprot(xconn, 0, inpdu, pdulen);
1974 return;
1976 if (nread >= smb_size && valid_smb_header(inbuf)
1977 && CVAL(inbuf, smb_com) != 0x72) {
1978 /* This is a non-negprot SMB1 packet.
1979 Disable SMB2 from now on. */
1980 sconn->using_smb2 = false;
1984 /* Make sure this is an SMB packet. smb_size contains NetBIOS header
1985 * so subtract 4 from it. */
1986 if ((nread < (smb_size - 4)) || !valid_smb_header(inbuf)) {
1987 DEBUG(2,("Non-SMB packet of length %d. Terminating server\n",
1988 smb_len(inbuf)));
1990 /* special magic for immediate exit */
1991 if ((nread == 9) &&
1992 (IVAL(inbuf, 4) == SMB_SUICIDE_PACKET) &&
1993 lp_parm_bool(-1, "smbd", "suicide mode", false)) {
1994 uint8_t exitcode = CVAL(inbuf, 8);
1995 DBG_WARNING("SUICIDE: Exiting immediately with code %d\n",
1996 (int)exitcode);
1997 exit(exitcode);
2000 exit_server_cleanly("Non-SMB packet");
2003 show_msg((char *)inbuf);
2005 if ((unread_bytes == 0) && smb1_is_chain(inbuf)) {
2006 construct_reply_chain(xconn, (char *)inbuf, nread,
2007 seqnum, encrypted, deferred_pcd);
2008 } else {
2009 construct_reply(xconn, (char *)inbuf, nread, unread_bytes,
2010 seqnum, encrypted, deferred_pcd);
2013 sconn->trans_num++;
2015 done:
2016 sconn->num_requests++;
2018 /* The timeout_processing function isn't run nearly
2019 often enough to implement 'max log size' without
2020 overrunning the size of the file by many megabytes.
2021 This is especially true if we are running at debug
2022 level 10. Checking every 50 SMBs is a nice
2023 tradeoff of performance vs log file size overrun. */
2025 if ((sconn->num_requests % 50) == 0 &&
2026 need_to_check_log_size()) {
2027 change_to_root_user();
2028 check_log_size();
2032 /****************************************************************************
2033 Return a string containing the function name of a SMB command.
2034 ****************************************************************************/
2036 const char *smb_fn_name(int type)
2038 const char *unknown_name = "SMBunknown";
2040 if (smb_messages[type].name == NULL)
2041 return(unknown_name);
2043 return(smb_messages[type].name);
2046 /****************************************************************************
2047 Helper functions for contruct_reply.
2048 ****************************************************************************/
2050 void add_to_common_flags2(uint32_t v)
2052 common_flags2 |= v;
2055 void remove_from_common_flags2(uint32_t v)
2057 common_flags2 &= ~v;
2060 static void construct_reply_common(uint8_t cmd, const uint8_t *inbuf,
2061 char *outbuf)
2063 uint16_t in_flags2 = SVAL(inbuf,smb_flg2);
2064 uint16_t out_flags2 = common_flags2;
2066 out_flags2 |= in_flags2 & FLAGS2_UNICODE_STRINGS;
2067 out_flags2 |= in_flags2 & FLAGS2_SMB_SECURITY_SIGNATURES;
2068 out_flags2 |= in_flags2 & FLAGS2_SMB_SECURITY_SIGNATURES_REQUIRED;
2070 srv_set_message(outbuf,0,0,false);
2072 SCVAL(outbuf, smb_com, cmd);
2073 SIVAL(outbuf,smb_rcls,0);
2074 SCVAL(outbuf,smb_flg, FLAG_REPLY | (CVAL(inbuf,smb_flg) & FLAG_CASELESS_PATHNAMES));
2075 SSVAL(outbuf,smb_flg2, out_flags2);
2076 memset(outbuf+smb_pidhigh,'\0',(smb_tid-smb_pidhigh));
2077 memcpy(outbuf+smb_ss_field, inbuf+smb_ss_field, 8);
2079 SSVAL(outbuf,smb_tid,SVAL(inbuf,smb_tid));
2080 SSVAL(outbuf,smb_pid,SVAL(inbuf,smb_pid));
2081 SSVAL(outbuf,smb_pidhigh,SVAL(inbuf,smb_pidhigh));
2082 SSVAL(outbuf,smb_uid,SVAL(inbuf,smb_uid));
2083 SSVAL(outbuf,smb_mid,SVAL(inbuf,smb_mid));
2086 void construct_reply_common_req(struct smb_request *req, char *outbuf)
2088 construct_reply_common(req->cmd, req->inbuf, outbuf);
2092 * @brief Find the smb_cmd offset of the last command pushed
2093 * @param[in] buf The buffer we're building up
2094 * @retval Where can we put our next andx cmd?
2096 * While chaining requests, the "next" request we're looking at needs to put
2097 * its SMB_Command before the data the previous request already built up added
2098 * to the chain. Find the offset to the place where we have to put our cmd.
2101 static bool find_andx_cmd_ofs(uint8_t *buf, size_t *pofs)
2103 uint8_t cmd;
2104 size_t ofs;
2106 cmd = CVAL(buf, smb_com);
2108 if (!smb1cli_is_andx_req(cmd)) {
2109 return false;
2112 ofs = smb_vwv0;
2114 while (CVAL(buf, ofs) != 0xff) {
2116 if (!smb1cli_is_andx_req(CVAL(buf, ofs))) {
2117 return false;
2121 * ofs is from start of smb header, so add the 4 length
2122 * bytes. The next cmd is right after the wct field.
2124 ofs = SVAL(buf, ofs+2) + 4 + 1;
2126 if (ofs+4 >= talloc_get_size(buf)) {
2127 return false;
2131 *pofs = ofs;
2132 return true;
2136 * @brief Do the smb chaining at a buffer level
2137 * @param[in] poutbuf Pointer to the talloc'ed buffer to be modified
2138 * @param[in] andx_buf Buffer to be appended
2141 static bool smb_splice_chain(uint8_t **poutbuf, const uint8_t *andx_buf)
2143 uint8_t smb_command = CVAL(andx_buf, smb_com);
2144 uint8_t wct = CVAL(andx_buf, smb_wct);
2145 const uint16_t *vwv = (const uint16_t *)(andx_buf + smb_vwv);
2146 uint32_t num_bytes = smb_buflen(andx_buf);
2147 const uint8_t *bytes = (const uint8_t *)smb_buf_const(andx_buf);
2149 uint8_t *outbuf;
2150 size_t old_size, new_size;
2151 size_t ofs;
2152 size_t chain_padding = 0;
2153 size_t andx_cmd_ofs;
2156 old_size = talloc_get_size(*poutbuf);
2158 if ((old_size % 4) != 0) {
2160 * Align the wct field of subsequent requests to a 4-byte
2161 * boundary
2163 chain_padding = 4 - (old_size % 4);
2167 * After the old request comes the new wct field (1 byte), the vwv's
2168 * and the num_bytes field.
2171 new_size = old_size + chain_padding + 1 + wct * sizeof(uint16_t) + 2;
2172 new_size += num_bytes;
2174 if ((smb_command != SMBwriteX) && (new_size > 0xffff)) {
2175 DEBUG(1, ("smb_splice_chain: %u bytes won't fit\n",
2176 (unsigned)new_size));
2177 return false;
2180 outbuf = talloc_realloc(NULL, *poutbuf, uint8_t, new_size);
2181 if (outbuf == NULL) {
2182 DEBUG(0, ("talloc failed\n"));
2183 return false;
2185 *poutbuf = outbuf;
2187 if (!find_andx_cmd_ofs(outbuf, &andx_cmd_ofs)) {
2188 DEBUG(1, ("invalid command chain\n"));
2189 *poutbuf = talloc_realloc(NULL, *poutbuf, uint8_t, old_size);
2190 return false;
2193 if (chain_padding != 0) {
2194 memset(outbuf + old_size, 0, chain_padding);
2195 old_size += chain_padding;
2198 SCVAL(outbuf, andx_cmd_ofs, smb_command);
2199 SSVAL(outbuf, andx_cmd_ofs + 2, old_size - 4);
2201 ofs = old_size;
2204 * Push the chained request:
2206 * wct field
2209 SCVAL(outbuf, ofs, wct);
2210 ofs += 1;
2213 * vwv array
2216 memcpy(outbuf + ofs, vwv, sizeof(uint16_t) * wct);
2219 * HACK ALERT
2221 * Read&X has an offset into its data buffer at
2222 * vwv[6]. reply_read_andx has no idea anymore that it's
2223 * running from within a chain, so we have to fix up the
2224 * offset here.
2226 * Although it looks disgusting at this place, I want to keep
2227 * it here. The alternative would be to push knowledge about
2228 * the andx chain down into read&x again.
2231 if (smb_command == SMBreadX) {
2232 uint8_t *bytes_addr;
2234 if (wct < 7) {
2236 * Invalid read&x response
2238 return false;
2241 bytes_addr = outbuf + ofs /* vwv start */
2242 + sizeof(uint16_t) * wct /* vwv array */
2243 + sizeof(uint16_t) /* bcc */
2244 + 1; /* padding byte */
2246 SSVAL(outbuf + ofs, 6 * sizeof(uint16_t),
2247 bytes_addr - outbuf - 4);
2250 ofs += sizeof(uint16_t) * wct;
2253 * bcc (byte count)
2256 SSVAL(outbuf, ofs, num_bytes);
2257 ofs += sizeof(uint16_t);
2260 * The bytes field
2263 memcpy(outbuf + ofs, bytes, num_bytes);
2265 return true;
2268 bool smb1_is_chain(const uint8_t *buf)
2270 uint8_t cmd, wct, andx_cmd;
2272 cmd = CVAL(buf, smb_com);
2273 if (!smb1cli_is_andx_req(cmd)) {
2274 return false;
2276 wct = CVAL(buf, smb_wct);
2277 if (wct < 2) {
2278 return false;
2280 andx_cmd = CVAL(buf, smb_vwv);
2281 return (andx_cmd != 0xFF);
2284 bool smb1_walk_chain(const uint8_t *buf,
2285 bool (*fn)(uint8_t cmd,
2286 uint8_t wct, const uint16_t *vwv,
2287 uint16_t num_bytes, const uint8_t *bytes,
2288 void *private_data),
2289 void *private_data)
2291 size_t smblen = smb_len(buf);
2292 const char *smb_buf = smb_base(buf);
2293 uint8_t cmd, chain_cmd;
2294 uint8_t wct;
2295 const uint16_t *vwv;
2296 uint16_t num_bytes;
2297 const uint8_t *bytes;
2299 cmd = CVAL(buf, smb_com);
2300 wct = CVAL(buf, smb_wct);
2301 vwv = (const uint16_t *)(buf + smb_vwv);
2302 num_bytes = smb_buflen(buf);
2303 bytes = (const uint8_t *)smb_buf_const(buf);
2305 if (!fn(cmd, wct, vwv, num_bytes, bytes, private_data)) {
2306 return false;
2309 if (!smb1cli_is_andx_req(cmd)) {
2310 return true;
2312 if (wct < 2) {
2313 return false;
2316 chain_cmd = CVAL(vwv, 0);
2318 while (chain_cmd != 0xff) {
2319 uint32_t chain_offset; /* uint32_t to avoid overflow */
2320 size_t length_needed;
2321 ptrdiff_t vwv_offset;
2323 chain_offset = SVAL(vwv+1, 0);
2326 * Check if the client tries to fool us. The chain
2327 * offset needs to point beyond the current request in
2328 * the chain, it needs to strictly grow. Otherwise we
2329 * might be tricked into an endless loop always
2330 * processing the same request over and over again. We
2331 * used to assume that vwv and the byte buffer array
2332 * in a chain are always attached, but OS/2 the
2333 * Write&X/Read&X chain puts the Read&X vwv array
2334 * right behind the Write&X vwv chain. The Write&X bcc
2335 * array is put behind the Read&X vwv array. So now we
2336 * check whether the chain offset points strictly
2337 * behind the previous vwv array. req->buf points
2338 * right after the vwv array of the previous
2339 * request. See
2340 * https://bugzilla.samba.org/show_bug.cgi?id=8360 for
2341 * more information.
2344 vwv_offset = ((const char *)vwv - smb_buf);
2345 if (chain_offset <= vwv_offset) {
2346 return false;
2350 * Next check: Make sure the chain offset does not
2351 * point beyond the overall smb request length.
2354 length_needed = chain_offset+1; /* wct */
2355 if (length_needed > smblen) {
2356 return false;
2360 * Now comes the pointer magic. Goal here is to set up
2361 * vwv and buf correctly again. The chain offset (the
2362 * former vwv[1]) points at the new wct field.
2365 wct = CVAL(smb_buf, chain_offset);
2367 if (smb1cli_is_andx_req(chain_cmd) && (wct < 2)) {
2368 return false;
2372 * Next consistency check: Make the new vwv array fits
2373 * in the overall smb request.
2376 length_needed += (wct+1)*sizeof(uint16_t); /* vwv+buflen */
2377 if (length_needed > smblen) {
2378 return false;
2380 vwv = (const uint16_t *)(smb_buf + chain_offset + 1);
2383 * Now grab the new byte buffer....
2386 num_bytes = SVAL(vwv+wct, 0);
2389 * .. and check that it fits.
2392 length_needed += num_bytes;
2393 if (length_needed > smblen) {
2394 return false;
2396 bytes = (const uint8_t *)(vwv+wct+1);
2398 if (!fn(chain_cmd, wct, vwv, num_bytes, bytes, private_data)) {
2399 return false;
2402 if (!smb1cli_is_andx_req(chain_cmd)) {
2403 return true;
2405 chain_cmd = CVAL(vwv, 0);
2407 return true;
2410 static bool smb1_chain_length_cb(uint8_t cmd,
2411 uint8_t wct, const uint16_t *vwv,
2412 uint16_t num_bytes, const uint8_t *bytes,
2413 void *private_data)
2415 unsigned *count = (unsigned *)private_data;
2416 *count += 1;
2417 return true;
2420 unsigned smb1_chain_length(const uint8_t *buf)
2422 unsigned count = 0;
2424 if (!smb1_walk_chain(buf, smb1_chain_length_cb, &count)) {
2425 return 0;
2427 return count;
2430 struct smb1_parse_chain_state {
2431 TALLOC_CTX *mem_ctx;
2432 const uint8_t *buf;
2433 struct smbd_server_connection *sconn;
2434 struct smbXsrv_connection *xconn;
2435 bool encrypted;
2436 uint32_t seqnum;
2438 struct smb_request **reqs;
2439 unsigned num_reqs;
2442 static bool smb1_parse_chain_cb(uint8_t cmd,
2443 uint8_t wct, const uint16_t *vwv,
2444 uint16_t num_bytes, const uint8_t *bytes,
2445 void *private_data)
2447 struct smb1_parse_chain_state *state =
2448 (struct smb1_parse_chain_state *)private_data;
2449 struct smb_request **reqs;
2450 struct smb_request *req;
2451 bool ok;
2453 reqs = talloc_realloc(state->mem_ctx, state->reqs,
2454 struct smb_request *, state->num_reqs+1);
2455 if (reqs == NULL) {
2456 return false;
2458 state->reqs = reqs;
2460 req = talloc(reqs, struct smb_request);
2461 if (req == NULL) {
2462 return false;
2465 ok = init_smb_request(req, state->sconn, state->xconn, state->buf, 0,
2466 state->encrypted, state->seqnum);
2467 if (!ok) {
2468 return false;
2470 req->cmd = cmd;
2471 req->wct = wct;
2472 req->vwv = vwv;
2473 req->buflen = num_bytes;
2474 req->buf = bytes;
2476 reqs[state->num_reqs] = req;
2477 state->num_reqs += 1;
2478 return true;
2481 bool smb1_parse_chain(TALLOC_CTX *mem_ctx, const uint8_t *buf,
2482 struct smbXsrv_connection *xconn,
2483 bool encrypted, uint32_t seqnum,
2484 struct smb_request ***reqs, unsigned *num_reqs)
2486 struct smbd_server_connection *sconn = NULL;
2487 struct smb1_parse_chain_state state;
2488 unsigned i;
2490 if (xconn != NULL) {
2491 sconn = xconn->client->sconn;
2494 state.mem_ctx = mem_ctx;
2495 state.buf = buf;
2496 state.sconn = sconn;
2497 state.xconn = xconn;
2498 state.encrypted = encrypted;
2499 state.seqnum = seqnum;
2500 state.reqs = NULL;
2501 state.num_reqs = 0;
2503 if (!smb1_walk_chain(buf, smb1_parse_chain_cb, &state)) {
2504 TALLOC_FREE(state.reqs);
2505 return false;
2507 for (i=0; i<state.num_reqs; i++) {
2508 state.reqs[i]->chain = state.reqs;
2510 *reqs = state.reqs;
2511 *num_reqs = state.num_reqs;
2512 return true;
2515 /****************************************************************************
2516 Check if services need reloading.
2517 ****************************************************************************/
2519 static void check_reload(struct smbd_server_connection *sconn, time_t t)
2522 if (last_smb_conf_reload_time == 0) {
2523 last_smb_conf_reload_time = t;
2526 if (t >= last_smb_conf_reload_time+SMBD_RELOAD_CHECK) {
2527 reload_services(sconn, conn_snum_used, true);
2528 last_smb_conf_reload_time = t;
2532 static bool fd_is_readable(int fd)
2534 int ret, revents;
2536 ret = poll_one_fd(fd, POLLIN|POLLHUP, 0, &revents);
2538 return ((ret > 0) && ((revents & (POLLIN|POLLHUP|POLLERR)) != 0));
2542 static void smbd_server_connection_write_handler(
2543 struct smbXsrv_connection *xconn)
2545 /* TODO: make write nonblocking */
2548 static void smbd_server_connection_read_handler(
2549 struct smbXsrv_connection *xconn, int fd)
2551 uint8_t *inbuf = NULL;
2552 size_t inbuf_len = 0;
2553 size_t unread_bytes = 0;
2554 bool encrypted = false;
2555 TALLOC_CTX *mem_ctx = talloc_tos();
2556 NTSTATUS status;
2557 uint32_t seqnum;
2559 bool async_echo = lp_async_smb_echo_handler();
2560 bool from_client = false;
2562 if (async_echo) {
2563 if (fd_is_readable(xconn->smb1.echo_handler.trusted_fd)) {
2565 * This is the super-ugly hack to prefer the packets
2566 * forwarded by the echo handler over the ones by the
2567 * client directly
2569 fd = xconn->smb1.echo_handler.trusted_fd;
2573 from_client = (xconn->transport.sock == fd);
2575 if (async_echo && from_client) {
2576 smbd_lock_socket(xconn);
2578 if (!fd_is_readable(fd)) {
2579 DEBUG(10,("the echo listener was faster\n"));
2580 smbd_unlock_socket(xconn);
2581 return;
2585 /* TODO: make this completely nonblocking */
2586 status = receive_smb_talloc(mem_ctx, xconn, fd,
2587 (char **)(void *)&inbuf,
2588 0, /* timeout */
2589 &unread_bytes,
2590 &encrypted,
2591 &inbuf_len, &seqnum,
2592 !from_client /* trusted channel */);
2594 if (async_echo && from_client) {
2595 smbd_unlock_socket(xconn);
2598 if (NT_STATUS_EQUAL(status, NT_STATUS_RETRY)) {
2599 goto process;
2601 if (NT_STATUS_IS_ERR(status)) {
2602 exit_server_cleanly("failed to receive smb request");
2604 if (!NT_STATUS_IS_OK(status)) {
2605 return;
2608 process:
2609 process_smb(xconn, inbuf, inbuf_len, unread_bytes,
2610 seqnum, encrypted, NULL);
2613 static void smbd_server_connection_handler(struct tevent_context *ev,
2614 struct tevent_fd *fde,
2615 uint16_t flags,
2616 void *private_data)
2618 struct smbXsrv_connection *xconn =
2619 talloc_get_type_abort(private_data,
2620 struct smbXsrv_connection);
2622 if (!NT_STATUS_IS_OK(xconn->transport.status)) {
2624 * we're not supposed to do any io
2626 TEVENT_FD_NOT_READABLE(xconn->transport.fde);
2627 TEVENT_FD_NOT_WRITEABLE(xconn->transport.fde);
2628 return;
2631 if (flags & TEVENT_FD_WRITE) {
2632 smbd_server_connection_write_handler(xconn);
2633 return;
2635 if (flags & TEVENT_FD_READ) {
2636 smbd_server_connection_read_handler(xconn, xconn->transport.sock);
2637 return;
2641 static void smbd_server_echo_handler(struct tevent_context *ev,
2642 struct tevent_fd *fde,
2643 uint16_t flags,
2644 void *private_data)
2646 struct smbXsrv_connection *xconn =
2647 talloc_get_type_abort(private_data,
2648 struct smbXsrv_connection);
2650 if (!NT_STATUS_IS_OK(xconn->transport.status)) {
2652 * we're not supposed to do any io
2654 TEVENT_FD_NOT_READABLE(xconn->smb1.echo_handler.trusted_fde);
2655 TEVENT_FD_NOT_WRITEABLE(xconn->smb1.echo_handler.trusted_fde);
2656 return;
2659 if (flags & TEVENT_FD_WRITE) {
2660 smbd_server_connection_write_handler(xconn);
2661 return;
2663 if (flags & TEVENT_FD_READ) {
2664 smbd_server_connection_read_handler(
2665 xconn, xconn->smb1.echo_handler.trusted_fd);
2666 return;
2670 struct smbd_release_ip_state {
2671 struct smbXsrv_connection *xconn;
2672 struct tevent_immediate *im;
2673 char addr[INET6_ADDRSTRLEN];
2676 static void smbd_release_ip_immediate(struct tevent_context *ctx,
2677 struct tevent_immediate *im,
2678 void *private_data)
2680 struct smbd_release_ip_state *state =
2681 talloc_get_type_abort(private_data,
2682 struct smbd_release_ip_state);
2683 struct smbXsrv_connection *xconn = state->xconn;
2685 if (!NT_STATUS_EQUAL(xconn->transport.status, NT_STATUS_ADDRESS_CLOSED)) {
2687 * smbd_server_connection_terminate() already triggered ?
2689 return;
2692 smbd_server_connection_terminate(xconn, "CTDB_SRVID_RELEASE_IP");
2695 /****************************************************************************
2696 received when we should release a specific IP
2697 ****************************************************************************/
2698 static int release_ip(struct tevent_context *ev,
2699 uint32_t src_vnn, uint32_t dst_vnn,
2700 uint64_t dst_srvid,
2701 const uint8_t *msg, size_t msglen,
2702 void *private_data)
2704 struct smbd_release_ip_state *state =
2705 talloc_get_type_abort(private_data,
2706 struct smbd_release_ip_state);
2707 struct smbXsrv_connection *xconn = state->xconn;
2708 const char *ip;
2709 const char *addr = state->addr;
2710 const char *p = addr;
2712 if (msglen == 0) {
2713 return 0;
2715 if (msg[msglen-1] != '\0') {
2716 return 0;
2719 ip = (const char *)msg;
2721 if (!NT_STATUS_IS_OK(xconn->transport.status)) {
2722 /* avoid recursion */
2723 return 0;
2726 if (strncmp("::ffff:", addr, 7) == 0) {
2727 p = addr + 7;
2730 DEBUG(10, ("Got release IP message for %s, "
2731 "our address is %s\n", ip, p));
2733 if ((strcmp(p, ip) == 0) || ((p != addr) && strcmp(addr, ip) == 0)) {
2734 DEBUG(0,("Got release IP message for our IP %s - exiting immediately\n",
2735 ip));
2737 * With SMB2 we should do a clean disconnect,
2738 * the previous_session_id in the session setup
2739 * will cleanup the old session, tcons and opens.
2741 * A clean disconnect is needed in order to support
2742 * durable handles.
2744 * Note: typically this is never triggered
2745 * as we got a TCP RST (triggered by ctdb event scripts)
2746 * before we get CTDB_SRVID_RELEASE_IP.
2748 * We used to call _exit(1) here, but as this was mostly never
2749 * triggered and has implication on our process model,
2750 * we can just use smbd_server_connection_terminate()
2751 * (also for SMB1).
2753 * We don't call smbd_server_connection_terminate() directly
2754 * as we might be called from within ctdbd_migrate(),
2755 * we need to defer our action to the next event loop
2757 tevent_schedule_immediate(state->im,
2758 xconn->client->raw_ev_ctx,
2759 smbd_release_ip_immediate,
2760 state);
2763 * Make sure we don't get any io on the connection.
2765 xconn->transport.status = NT_STATUS_ADDRESS_CLOSED;
2766 return EADDRNOTAVAIL;
2769 return 0;
2772 static NTSTATUS smbd_register_ips(struct smbXsrv_connection *xconn,
2773 struct sockaddr_storage *srv,
2774 struct sockaddr_storage *clnt)
2776 struct smbd_release_ip_state *state;
2777 struct ctdbd_connection *cconn;
2778 int ret;
2780 cconn = messaging_ctdb_connection();
2781 if (cconn == NULL) {
2782 return NT_STATUS_NO_MEMORY;
2785 state = talloc_zero(xconn, struct smbd_release_ip_state);
2786 if (state == NULL) {
2787 return NT_STATUS_NO_MEMORY;
2789 state->xconn = xconn;
2790 state->im = tevent_create_immediate(state);
2791 if (state->im == NULL) {
2792 return NT_STATUS_NO_MEMORY;
2794 if (print_sockaddr(state->addr, sizeof(state->addr), srv) == NULL) {
2795 return NT_STATUS_NO_MEMORY;
2798 ret = ctdbd_register_ips(cconn, srv, clnt, release_ip, state);
2799 if (ret != 0) {
2800 return map_nt_error_from_unix(ret);
2802 return NT_STATUS_OK;
2805 static void msg_kill_client_ip(struct messaging_context *msg_ctx,
2806 void *private_data, uint32_t msg_type,
2807 struct server_id server_id, DATA_BLOB *data)
2809 struct smbd_server_connection *sconn = talloc_get_type_abort(
2810 private_data, struct smbd_server_connection);
2811 const char *ip = (char *) data->data;
2812 char *client_ip;
2814 DBG_DEBUG("Got kill request for client IP %s\n", ip);
2816 client_ip = tsocket_address_inet_addr_string(sconn->remote_address,
2817 talloc_tos());
2818 if (client_ip == NULL) {
2819 return;
2822 if (strequal(ip, client_ip)) {
2823 DBG_WARNING("Got kill client message for %s - "
2824 "exiting immediately\n", ip);
2825 exit_server_cleanly("Forced disconnect for client");
2828 TALLOC_FREE(client_ip);
2832 * Send keepalive packets to our client
2834 static bool keepalive_fn(const struct timeval *now, void *private_data)
2836 struct smbd_server_connection *sconn = talloc_get_type_abort(
2837 private_data, struct smbd_server_connection);
2838 struct smbXsrv_connection *xconn = NULL;
2839 bool ret;
2841 if (sconn->using_smb2) {
2842 /* Don't do keepalives on an SMB2 connection. */
2843 return false;
2847 * With SMB1 we only have 1 connection
2849 xconn = sconn->client->connections;
2850 smbd_lock_socket(xconn);
2851 ret = send_keepalive(xconn->transport.sock);
2852 smbd_unlock_socket(xconn);
2854 if (!ret) {
2855 int saved_errno = errno;
2857 * Try and give an error message saying what
2858 * client failed.
2860 DEBUG(0, ("send_keepalive failed for client %s. "
2861 "Error %s - exiting\n",
2862 smbXsrv_connection_dbg(xconn),
2863 strerror(saved_errno)));
2864 errno = saved_errno;
2865 return False;
2867 return True;
2871 * Do the recurring check if we're idle
2873 static bool deadtime_fn(const struct timeval *now, void *private_data)
2875 struct smbd_server_connection *sconn =
2876 (struct smbd_server_connection *)private_data;
2878 if ((conn_num_open(sconn) == 0)
2879 || (conn_idle_all(sconn, now->tv_sec))) {
2880 DEBUG( 2, ( "Closing idle connection\n" ) );
2881 messaging_send(sconn->msg_ctx,
2882 messaging_server_id(sconn->msg_ctx),
2883 MSG_SHUTDOWN, &data_blob_null);
2884 return False;
2887 return True;
2891 * Do the recurring log file and smb.conf reload checks.
2894 static bool housekeeping_fn(const struct timeval *now, void *private_data)
2896 struct smbd_server_connection *sconn = talloc_get_type_abort(
2897 private_data, struct smbd_server_connection);
2899 DEBUG(5, ("housekeeping\n"));
2901 change_to_root_user();
2903 /* update printer queue caches if necessary */
2904 update_monitored_printq_cache(sconn->msg_ctx);
2906 /* check if we need to reload services */
2907 check_reload(sconn, time_mono(NULL));
2910 * Force a log file check.
2912 force_check_log_size();
2913 check_log_size();
2914 return true;
2918 * Read an smb packet in the echo handler child, giving the parent
2919 * smbd one second to react once the socket becomes readable.
2922 struct smbd_echo_read_state {
2923 struct tevent_context *ev;
2924 struct smbXsrv_connection *xconn;
2926 char *buf;
2927 size_t buflen;
2928 uint32_t seqnum;
2931 static void smbd_echo_read_readable(struct tevent_req *subreq);
2932 static void smbd_echo_read_waited(struct tevent_req *subreq);
2934 static struct tevent_req *smbd_echo_read_send(
2935 TALLOC_CTX *mem_ctx, struct tevent_context *ev,
2936 struct smbXsrv_connection *xconn)
2938 struct tevent_req *req, *subreq;
2939 struct smbd_echo_read_state *state;
2941 req = tevent_req_create(mem_ctx, &state,
2942 struct smbd_echo_read_state);
2943 if (req == NULL) {
2944 return NULL;
2946 state->ev = ev;
2947 state->xconn = xconn;
2949 subreq = wait_for_read_send(state, ev, xconn->transport.sock, false);
2950 if (tevent_req_nomem(subreq, req)) {
2951 return tevent_req_post(req, ev);
2953 tevent_req_set_callback(subreq, smbd_echo_read_readable, req);
2954 return req;
2957 static void smbd_echo_read_readable(struct tevent_req *subreq)
2959 struct tevent_req *req = tevent_req_callback_data(
2960 subreq, struct tevent_req);
2961 struct smbd_echo_read_state *state = tevent_req_data(
2962 req, struct smbd_echo_read_state);
2963 bool ok;
2964 int err;
2966 ok = wait_for_read_recv(subreq, &err);
2967 TALLOC_FREE(subreq);
2968 if (!ok) {
2969 tevent_req_nterror(req, map_nt_error_from_unix(err));
2970 return;
2974 * Give the parent smbd one second to step in
2977 subreq = tevent_wakeup_send(
2978 state, state->ev, timeval_current_ofs(1, 0));
2979 if (tevent_req_nomem(subreq, req)) {
2980 return;
2982 tevent_req_set_callback(subreq, smbd_echo_read_waited, req);
2985 static void smbd_echo_read_waited(struct tevent_req *subreq)
2987 struct tevent_req *req = tevent_req_callback_data(
2988 subreq, struct tevent_req);
2989 struct smbd_echo_read_state *state = tevent_req_data(
2990 req, struct smbd_echo_read_state);
2991 struct smbXsrv_connection *xconn = state->xconn;
2992 bool ok;
2993 NTSTATUS status;
2994 size_t unread = 0;
2995 bool encrypted;
2997 ok = tevent_wakeup_recv(subreq);
2998 TALLOC_FREE(subreq);
2999 if (!ok) {
3000 tevent_req_nterror(req, NT_STATUS_INTERNAL_ERROR);
3001 return;
3004 ok = smbd_lock_socket_internal(xconn);
3005 if (!ok) {
3006 tevent_req_nterror(req, map_nt_error_from_unix(errno));
3007 DEBUG(0, ("%s: failed to lock socket\n", __location__));
3008 return;
3011 if (!fd_is_readable(xconn->transport.sock)) {
3012 DEBUG(10,("echo_handler[%d] the parent smbd was faster\n",
3013 (int)getpid()));
3015 ok = smbd_unlock_socket_internal(xconn);
3016 if (!ok) {
3017 tevent_req_nterror(req, map_nt_error_from_unix(errno));
3018 DEBUG(1, ("%s: failed to unlock socket\n",
3019 __location__));
3020 return;
3023 subreq = wait_for_read_send(state, state->ev,
3024 xconn->transport.sock, false);
3025 if (tevent_req_nomem(subreq, req)) {
3026 return;
3028 tevent_req_set_callback(subreq, smbd_echo_read_readable, req);
3029 return;
3032 status = receive_smb_talloc(state, xconn,
3033 xconn->transport.sock,
3034 &state->buf,
3035 0 /* timeout */,
3036 &unread,
3037 &encrypted,
3038 &state->buflen,
3039 &state->seqnum,
3040 false /* trusted_channel*/);
3042 if (tevent_req_nterror(req, status)) {
3043 tevent_req_nterror(req, status);
3044 DEBUG(1, ("echo_handler[%d]: receive_smb_raw_talloc failed: %s\n",
3045 (int)getpid(), nt_errstr(status)));
3046 return;
3049 ok = smbd_unlock_socket_internal(xconn);
3050 if (!ok) {
3051 tevent_req_nterror(req, map_nt_error_from_unix(errno));
3052 DEBUG(1, ("%s: failed to unlock socket\n", __location__));
3053 return;
3055 tevent_req_done(req);
3058 static NTSTATUS smbd_echo_read_recv(struct tevent_req *req, TALLOC_CTX *mem_ctx,
3059 char **pbuf, size_t *pbuflen, uint32_t *pseqnum)
3061 struct smbd_echo_read_state *state = tevent_req_data(
3062 req, struct smbd_echo_read_state);
3063 NTSTATUS status;
3065 if (tevent_req_is_nterror(req, &status)) {
3066 return status;
3068 *pbuf = talloc_move(mem_ctx, &state->buf);
3069 *pbuflen = state->buflen;
3070 *pseqnum = state->seqnum;
3071 return NT_STATUS_OK;
3074 struct smbd_echo_state {
3075 struct tevent_context *ev;
3076 struct iovec *pending;
3077 struct smbd_server_connection *sconn;
3078 struct smbXsrv_connection *xconn;
3079 int parent_pipe;
3081 struct tevent_fd *parent_fde;
3083 struct tevent_req *write_req;
3086 static void smbd_echo_writer_done(struct tevent_req *req);
3088 static void smbd_echo_activate_writer(struct smbd_echo_state *state)
3090 int num_pending;
3092 if (state->write_req != NULL) {
3093 return;
3096 num_pending = talloc_array_length(state->pending);
3097 if (num_pending == 0) {
3098 return;
3101 state->write_req = writev_send(state, state->ev, NULL,
3102 state->parent_pipe, false,
3103 state->pending, num_pending);
3104 if (state->write_req == NULL) {
3105 DEBUG(1, ("writev_send failed\n"));
3106 exit(1);
3109 talloc_steal(state->write_req, state->pending);
3110 state->pending = NULL;
3112 tevent_req_set_callback(state->write_req, smbd_echo_writer_done,
3113 state);
3116 static void smbd_echo_writer_done(struct tevent_req *req)
3118 struct smbd_echo_state *state = tevent_req_callback_data(
3119 req, struct smbd_echo_state);
3120 ssize_t written;
3121 int err;
3123 written = writev_recv(req, &err);
3124 TALLOC_FREE(req);
3125 state->write_req = NULL;
3126 if (written == -1) {
3127 DEBUG(1, ("writev to parent failed: %s\n", strerror(err)));
3128 exit(1);
3130 DEBUG(10,("echo_handler[%d]: forwarded pdu to main\n", (int)getpid()));
3131 smbd_echo_activate_writer(state);
3134 static bool smbd_echo_reply(struct smbd_echo_state *state,
3135 uint8_t *inbuf, size_t inbuf_len,
3136 uint32_t seqnum)
3138 struct smb_request req;
3139 uint16_t num_replies;
3140 char *outbuf;
3141 bool ok;
3143 if ((inbuf_len == 4) && (CVAL(inbuf, 0) == NBSSkeepalive)) {
3144 DEBUG(10, ("Got netbios keepalive\n"));
3146 * Just swallow it
3148 return true;
3151 if (inbuf_len < smb_size) {
3152 DEBUG(10, ("Got short packet: %d bytes\n", (int)inbuf_len));
3153 return false;
3155 if (!valid_smb_header(inbuf)) {
3156 DEBUG(10, ("Got invalid SMB header\n"));
3157 return false;
3160 if (!init_smb_request(&req, state->sconn, state->xconn, inbuf, 0, false,
3161 seqnum)) {
3162 return false;
3164 req.inbuf = inbuf;
3166 DEBUG(10, ("smbecho handler got cmd %d (%s)\n", (int)req.cmd,
3167 smb_messages[req.cmd].name
3168 ? smb_messages[req.cmd].name : "unknown"));
3170 if (req.cmd != SMBecho) {
3171 return false;
3173 if (req.wct < 1) {
3174 return false;
3177 num_replies = SVAL(req.vwv+0, 0);
3178 if (num_replies != 1) {
3179 /* Not a Windows "Hey, you're still there?" request */
3180 return false;
3183 if (!create_outbuf(talloc_tos(), &req, req.inbuf, &outbuf,
3184 1, req.buflen)) {
3185 DEBUG(10, ("create_outbuf failed\n"));
3186 return false;
3188 req.outbuf = (uint8_t *)outbuf;
3190 SSVAL(req.outbuf, smb_vwv0, num_replies);
3192 if (req.buflen > 0) {
3193 memcpy(smb_buf(req.outbuf), req.buf, req.buflen);
3196 ok = srv_send_smb(req.xconn,
3197 (char *)outbuf,
3198 true, seqnum+1,
3199 false, &req.pcd);
3200 TALLOC_FREE(outbuf);
3201 if (!ok) {
3202 exit(1);
3205 return true;
3208 static void smbd_echo_exit(struct tevent_context *ev,
3209 struct tevent_fd *fde, uint16_t flags,
3210 void *private_data)
3212 DEBUG(2, ("smbd_echo_exit: lost connection to parent\n"));
3213 exit(0);
3216 static void smbd_echo_got_packet(struct tevent_req *req);
3218 static void smbd_echo_loop(struct smbXsrv_connection *xconn,
3219 int parent_pipe)
3221 struct smbd_echo_state *state;
3222 struct tevent_req *read_req;
3224 state = talloc_zero(xconn, struct smbd_echo_state);
3225 if (state == NULL) {
3226 DEBUG(1, ("talloc failed\n"));
3227 return;
3229 state->xconn = xconn;
3230 state->parent_pipe = parent_pipe;
3231 state->ev = samba_tevent_context_init(state);
3232 if (state->ev == NULL) {
3233 DEBUG(1, ("samba_tevent_context_init failed\n"));
3234 TALLOC_FREE(state);
3235 return;
3237 state->parent_fde = tevent_add_fd(state->ev, state, parent_pipe,
3238 TEVENT_FD_READ, smbd_echo_exit,
3239 state);
3240 if (state->parent_fde == NULL) {
3241 DEBUG(1, ("tevent_add_fd failed\n"));
3242 TALLOC_FREE(state);
3243 return;
3246 read_req = smbd_echo_read_send(state, state->ev, xconn);
3247 if (read_req == NULL) {
3248 DEBUG(1, ("smbd_echo_read_send failed\n"));
3249 TALLOC_FREE(state);
3250 return;
3252 tevent_req_set_callback(read_req, smbd_echo_got_packet, state);
3254 while (true) {
3255 if (tevent_loop_once(state->ev) == -1) {
3256 DEBUG(1, ("tevent_loop_once failed: %s\n",
3257 strerror(errno)));
3258 break;
3261 TALLOC_FREE(state);
3264 static void smbd_echo_got_packet(struct tevent_req *req)
3266 struct smbd_echo_state *state = tevent_req_callback_data(
3267 req, struct smbd_echo_state);
3268 NTSTATUS status;
3269 char *buf = NULL;
3270 size_t buflen = 0;
3271 uint32_t seqnum = 0;
3272 bool reply;
3274 status = smbd_echo_read_recv(req, state, &buf, &buflen, &seqnum);
3275 TALLOC_FREE(req);
3276 if (!NT_STATUS_IS_OK(status)) {
3277 DEBUG(1, ("smbd_echo_read_recv returned %s\n",
3278 nt_errstr(status)));
3279 exit(1);
3282 reply = smbd_echo_reply(state, (uint8_t *)buf, buflen, seqnum);
3283 if (!reply) {
3284 size_t num_pending;
3285 struct iovec *tmp;
3286 struct iovec *iov;
3288 num_pending = talloc_array_length(state->pending);
3289 tmp = talloc_realloc(state, state->pending, struct iovec,
3290 num_pending+1);
3291 if (tmp == NULL) {
3292 DEBUG(1, ("talloc_realloc failed\n"));
3293 exit(1);
3295 state->pending = tmp;
3297 if (buflen >= smb_size) {
3299 * place the seqnum in the packet so that the main process
3300 * can reply with signing
3302 SIVAL(buf, smb_ss_field, seqnum);
3303 SIVAL(buf, smb_ss_field+4, NT_STATUS_V(NT_STATUS_OK));
3306 iov = &state->pending[num_pending];
3307 iov->iov_base = talloc_move(state->pending, &buf);
3308 iov->iov_len = buflen;
3310 DEBUG(10,("echo_handler[%d]: forward to main\n",
3311 (int)getpid()));
3312 smbd_echo_activate_writer(state);
3315 req = smbd_echo_read_send(state, state->ev, state->xconn);
3316 if (req == NULL) {
3317 DEBUG(1, ("smbd_echo_read_send failed\n"));
3318 exit(1);
3320 tevent_req_set_callback(req, smbd_echo_got_packet, state);
3325 * Handle SMBecho requests in a forked child process
3327 bool fork_echo_handler(struct smbXsrv_connection *xconn)
3329 int listener_pipe[2];
3330 int res;
3331 pid_t child;
3332 bool use_mutex = false;
3334 res = pipe(listener_pipe);
3335 if (res == -1) {
3336 DEBUG(1, ("pipe() failed: %s\n", strerror(errno)));
3337 return false;
3340 #ifdef HAVE_ROBUST_MUTEXES
3341 use_mutex = tdb_runtime_check_for_robust_mutexes();
3343 if (use_mutex) {
3344 pthread_mutexattr_t a;
3346 xconn->smb1.echo_handler.socket_mutex =
3347 anonymous_shared_allocate(sizeof(pthread_mutex_t));
3348 if (xconn->smb1.echo_handler.socket_mutex == NULL) {
3349 DEBUG(1, ("Could not create mutex shared memory: %s\n",
3350 strerror(errno)));
3351 goto fail;
3354 res = pthread_mutexattr_init(&a);
3355 if (res != 0) {
3356 DEBUG(1, ("pthread_mutexattr_init failed: %s\n",
3357 strerror(res)));
3358 goto fail;
3360 res = pthread_mutexattr_settype(&a, PTHREAD_MUTEX_ERRORCHECK);
3361 if (res != 0) {
3362 DEBUG(1, ("pthread_mutexattr_settype failed: %s\n",
3363 strerror(res)));
3364 pthread_mutexattr_destroy(&a);
3365 goto fail;
3367 res = pthread_mutexattr_setpshared(&a, PTHREAD_PROCESS_SHARED);
3368 if (res != 0) {
3369 DEBUG(1, ("pthread_mutexattr_setpshared failed: %s\n",
3370 strerror(res)));
3371 pthread_mutexattr_destroy(&a);
3372 goto fail;
3374 res = pthread_mutexattr_setrobust(&a, PTHREAD_MUTEX_ROBUST);
3375 if (res != 0) {
3376 DEBUG(1, ("pthread_mutexattr_setrobust failed: "
3377 "%s\n", strerror(res)));
3378 pthread_mutexattr_destroy(&a);
3379 goto fail;
3381 res = pthread_mutex_init(xconn->smb1.echo_handler.socket_mutex,
3382 &a);
3383 pthread_mutexattr_destroy(&a);
3384 if (res != 0) {
3385 DEBUG(1, ("pthread_mutex_init failed: %s\n",
3386 strerror(res)));
3387 goto fail;
3390 #endif
3392 if (!use_mutex) {
3393 xconn->smb1.echo_handler.socket_lock_fd =
3394 create_unlink_tmp(lp_lock_directory());
3395 if (xconn->smb1.echo_handler.socket_lock_fd == -1) {
3396 DEBUG(1, ("Could not create lock fd: %s\n",
3397 strerror(errno)));
3398 goto fail;
3402 child = fork();
3403 if (child == 0) {
3404 NTSTATUS status;
3406 close(listener_pipe[0]);
3407 set_blocking(listener_pipe[1], false);
3409 status = smbd_reinit_after_fork(xconn->client->msg_ctx,
3410 xconn->client->raw_ev_ctx,
3411 true,
3412 "smbd-echo");
3413 if (!NT_STATUS_IS_OK(status)) {
3414 DEBUG(1, ("reinit_after_fork failed: %s\n",
3415 nt_errstr(status)));
3416 exit(1);
3418 initialize_password_db(true, xconn->client->raw_ev_ctx);
3419 smbd_echo_loop(xconn, listener_pipe[1]);
3420 exit(0);
3422 close(listener_pipe[1]);
3423 listener_pipe[1] = -1;
3424 xconn->smb1.echo_handler.trusted_fd = listener_pipe[0];
3426 DEBUG(10,("fork_echo_handler: main[%d] echo_child[%d]\n", (int)getpid(), (int)child));
3429 * Without smb signing this is the same as the normal smbd
3430 * listener. This needs to change once signing comes in.
3432 xconn->smb1.echo_handler.trusted_fde = tevent_add_fd(
3433 xconn->client->raw_ev_ctx,
3434 xconn,
3435 xconn->smb1.echo_handler.trusted_fd,
3436 TEVENT_FD_READ,
3437 smbd_server_echo_handler,
3438 xconn);
3439 if (xconn->smb1.echo_handler.trusted_fde == NULL) {
3440 DEBUG(1, ("event_add_fd failed\n"));
3441 goto fail;
3444 return true;
3446 fail:
3447 if (listener_pipe[0] != -1) {
3448 close(listener_pipe[0]);
3450 if (listener_pipe[1] != -1) {
3451 close(listener_pipe[1]);
3453 if (xconn->smb1.echo_handler.socket_lock_fd != -1) {
3454 close(xconn->smb1.echo_handler.socket_lock_fd);
3456 #ifdef HAVE_ROBUST_MUTEXES
3457 if (xconn->smb1.echo_handler.socket_mutex != NULL) {
3458 pthread_mutex_destroy(xconn->smb1.echo_handler.socket_mutex);
3459 anonymous_shared_free(xconn->smb1.echo_handler.socket_mutex);
3461 #endif
3462 smbd_echo_init(xconn);
3464 return false;
3467 static bool uid_in_use(const struct user_struct *user, uid_t uid)
3469 while (user) {
3470 if (user->session_info &&
3471 (user->session_info->unix_token->uid == uid)) {
3472 return true;
3474 user = user->next;
3476 return false;
3479 static bool gid_in_use(const struct user_struct *user, gid_t gid)
3481 while (user) {
3482 if (user->session_info != NULL) {
3483 int i;
3484 struct security_unix_token *utok;
3486 utok = user->session_info->unix_token;
3487 if (utok->gid == gid) {
3488 return true;
3490 for(i=0; i<utok->ngroups; i++) {
3491 if (utok->groups[i] == gid) {
3492 return true;
3496 user = user->next;
3498 return false;
3501 static bool sid_in_use(const struct user_struct *user,
3502 const struct dom_sid *psid)
3504 while (user) {
3505 struct security_token *tok;
3507 if (user->session_info == NULL) {
3508 continue;
3510 tok = user->session_info->security_token;
3511 if (tok == NULL) {
3513 * Not sure session_info->security_token can
3514 * ever be NULL. This check might be not
3515 * necessary.
3517 continue;
3519 if (security_token_has_sid(tok, psid)) {
3520 return true;
3522 user = user->next;
3524 return false;
3527 static bool id_in_use(const struct user_struct *user,
3528 const struct id_cache_ref *id)
3530 switch(id->type) {
3531 case UID:
3532 return uid_in_use(user, id->id.uid);
3533 case GID:
3534 return gid_in_use(user, id->id.gid);
3535 case SID:
3536 return sid_in_use(user, &id->id.sid);
3537 default:
3538 break;
3540 return false;
3543 static void smbd_id_cache_kill(struct messaging_context *msg_ctx,
3544 void *private_data,
3545 uint32_t msg_type,
3546 struct server_id server_id,
3547 DATA_BLOB* data)
3549 const char *msg = (data && data->data)
3550 ? (const char *)data->data : "<NULL>";
3551 struct id_cache_ref id;
3552 struct smbd_server_connection *sconn =
3553 talloc_get_type_abort(private_data,
3554 struct smbd_server_connection);
3556 if (!id_cache_ref_parse(msg, &id)) {
3557 DEBUG(0, ("Invalid ?ID: %s\n", msg));
3558 return;
3561 if (id_in_use(sconn->users, &id)) {
3562 exit_server_cleanly(msg);
3564 id_cache_delete_from_cache(&id);
3567 NTSTATUS smbXsrv_connection_init_tables(struct smbXsrv_connection *conn,
3568 enum protocol_types protocol)
3570 NTSTATUS status;
3572 conn->protocol = protocol;
3574 if (conn->client->session_table != NULL) {
3575 return NT_STATUS_OK;
3578 if (protocol >= PROTOCOL_SMB2_02) {
3579 status = smb2srv_session_table_init(conn);
3580 if (!NT_STATUS_IS_OK(status)) {
3581 conn->protocol = PROTOCOL_NONE;
3582 return status;
3585 status = smb2srv_open_table_init(conn);
3586 if (!NT_STATUS_IS_OK(status)) {
3587 conn->protocol = PROTOCOL_NONE;
3588 return status;
3590 } else {
3591 status = smb1srv_session_table_init(conn);
3592 if (!NT_STATUS_IS_OK(status)) {
3593 conn->protocol = PROTOCOL_NONE;
3594 return status;
3597 status = smb1srv_tcon_table_init(conn);
3598 if (!NT_STATUS_IS_OK(status)) {
3599 conn->protocol = PROTOCOL_NONE;
3600 return status;
3603 status = smb1srv_open_table_init(conn);
3604 if (!NT_STATUS_IS_OK(status)) {
3605 conn->protocol = PROTOCOL_NONE;
3606 return status;
3610 set_Protocol(protocol);
3611 return NT_STATUS_OK;
3614 struct smbd_tevent_trace_state {
3615 struct tevent_context *ev;
3616 TALLOC_CTX *frame;
3617 SMBPROFILE_BASIC_ASYNC_STATE(profile_idle);
3620 static void smbd_tevent_trace_callback(enum tevent_trace_point point,
3621 void *private_data)
3623 struct smbd_tevent_trace_state *state =
3624 (struct smbd_tevent_trace_state *)private_data;
3626 switch (point) {
3627 case TEVENT_TRACE_BEFORE_WAIT:
3628 if (!smbprofile_dump_pending()) {
3630 * If there's no dump pending
3631 * we don't want to schedule a new 1 sec timer.
3633 * Instead we want to sleep as long as nothing happens.
3635 smbprofile_dump_setup(NULL);
3637 SMBPROFILE_BASIC_ASYNC_START(idle, profile_p, state->profile_idle);
3638 break;
3639 case TEVENT_TRACE_AFTER_WAIT:
3640 SMBPROFILE_BASIC_ASYNC_END(state->profile_idle);
3641 if (!smbprofile_dump_pending()) {
3643 * We need to flush our state after sleeping
3644 * (hopefully a long time).
3646 smbprofile_dump();
3648 * future profiling events should trigger timers
3649 * on our main event context.
3651 smbprofile_dump_setup(state->ev);
3653 break;
3654 case TEVENT_TRACE_BEFORE_LOOP_ONCE:
3655 TALLOC_FREE(state->frame);
3656 state->frame = talloc_stackframe_pool(8192);
3657 break;
3658 case TEVENT_TRACE_AFTER_LOOP_ONCE:
3659 TALLOC_FREE(state->frame);
3660 break;
3663 errno = 0;
3667 * Create a debug string for the connection
3669 * This is allocated to talloc_tos() or a string constant
3670 * in certain corner cases. The returned string should
3671 * hence not be free'd directly but only via the talloc stack.
3673 const char *smbXsrv_connection_dbg(const struct smbXsrv_connection *xconn)
3675 const char *ret;
3678 * TODO: this can be improved later
3679 * maybe including the client guid or more
3681 ret = tsocket_address_string(xconn->remote_address, talloc_tos());
3682 if (ret == NULL) {
3683 return "<tsocket_address_string() failed>";
3686 return ret;
3689 NTSTATUS smbd_add_connection(struct smbXsrv_client *client, int sock_fd,
3690 struct smbXsrv_connection **_xconn)
3692 TALLOC_CTX *frame = talloc_stackframe();
3693 struct smbXsrv_connection *xconn;
3694 struct sockaddr_storage ss_srv;
3695 void *sp_srv = (void *)&ss_srv;
3696 struct sockaddr *sa_srv = (struct sockaddr *)sp_srv;
3697 struct sockaddr_storage ss_clnt;
3698 void *sp_clnt = (void *)&ss_clnt;
3699 struct sockaddr *sa_clnt = (struct sockaddr *)sp_clnt;
3700 socklen_t sa_socklen;
3701 struct tsocket_address *local_address = NULL;
3702 struct tsocket_address *remote_address = NULL;
3703 const char *remaddr = NULL;
3704 char *p;
3705 const char *rhost = NULL;
3706 int ret;
3707 int tmp;
3709 *_xconn = NULL;
3711 DO_PROFILE_INC(connect);
3713 xconn = talloc_zero(client, struct smbXsrv_connection);
3714 if (xconn == NULL) {
3715 DEBUG(0,("talloc_zero(struct smbXsrv_connection)\n"));
3716 TALLOC_FREE(frame);
3717 return NT_STATUS_NO_MEMORY;
3719 talloc_steal(frame, xconn);
3721 xconn->transport.sock = sock_fd;
3722 smbd_echo_init(xconn);
3723 xconn->protocol = PROTOCOL_NONE;
3725 /* Ensure child is set to blocking mode */
3726 set_blocking(sock_fd,True);
3728 set_socket_options(sock_fd, "SO_KEEPALIVE");
3729 set_socket_options(sock_fd, lp_socket_options());
3731 sa_socklen = sizeof(ss_clnt);
3732 ret = getpeername(sock_fd, sa_clnt, &sa_socklen);
3733 if (ret != 0) {
3734 int saved_errno = errno;
3735 int level = (errno == ENOTCONN)?2:0;
3736 DEBUG(level,("getpeername() failed - %s\n",
3737 strerror(saved_errno)));
3738 TALLOC_FREE(frame);
3739 return map_nt_error_from_unix_common(saved_errno);
3741 ret = tsocket_address_bsd_from_sockaddr(xconn,
3742 sa_clnt, sa_socklen,
3743 &remote_address);
3744 if (ret != 0) {
3745 int saved_errno = errno;
3746 DEBUG(0,("%s: tsocket_address_bsd_from_sockaddr remote failed - %s\n",
3747 __location__, strerror(saved_errno)));
3748 TALLOC_FREE(frame);
3749 return map_nt_error_from_unix_common(saved_errno);
3752 sa_socklen = sizeof(ss_srv);
3753 ret = getsockname(sock_fd, sa_srv, &sa_socklen);
3754 if (ret != 0) {
3755 int saved_errno = errno;
3756 int level = (errno == ENOTCONN)?2:0;
3757 DEBUG(level,("getsockname() failed - %s\n",
3758 strerror(saved_errno)));
3759 TALLOC_FREE(frame);
3760 return map_nt_error_from_unix_common(saved_errno);
3762 ret = tsocket_address_bsd_from_sockaddr(xconn,
3763 sa_srv, sa_socklen,
3764 &local_address);
3765 if (ret != 0) {
3766 int saved_errno = errno;
3767 DEBUG(0,("%s: tsocket_address_bsd_from_sockaddr remote failed - %s\n",
3768 __location__, strerror(saved_errno)));
3769 TALLOC_FREE(frame);
3770 return map_nt_error_from_unix_common(saved_errno);
3773 if (tsocket_address_is_inet(remote_address, "ip")) {
3774 remaddr = tsocket_address_inet_addr_string(remote_address,
3775 talloc_tos());
3776 if (remaddr == NULL) {
3777 DEBUG(0,("%s: tsocket_address_inet_addr_string remote failed - %s\n",
3778 __location__, strerror(errno)));
3779 TALLOC_FREE(frame);
3780 return NT_STATUS_NO_MEMORY;
3782 } else {
3783 remaddr = "0.0.0.0";
3787 * Before the first packet, check the global hosts allow/ hosts deny
3788 * parameters before doing any parsing of packets passed to us by the
3789 * client. This prevents attacks on our parsing code from hosts not in
3790 * the hosts allow list.
3793 ret = get_remote_hostname(remote_address,
3794 &p, talloc_tos());
3795 if (ret < 0) {
3796 int saved_errno = errno;
3797 DEBUG(0,("%s: get_remote_hostname failed - %s\n",
3798 __location__, strerror(saved_errno)));
3799 TALLOC_FREE(frame);
3800 return map_nt_error_from_unix_common(saved_errno);
3802 rhost = p;
3803 if (strequal(rhost, "UNKNOWN")) {
3804 rhost = remaddr;
3807 xconn->local_address = local_address;
3808 xconn->remote_address = remote_address;
3809 xconn->remote_hostname = talloc_strdup(xconn, rhost);
3810 if (xconn->remote_hostname == NULL) {
3811 return NT_STATUS_NO_MEMORY;
3814 if (!srv_init_signing(xconn)) {
3815 DEBUG(0, ("Failed to init smb_signing\n"));
3816 TALLOC_FREE(frame);
3817 return NT_STATUS_INTERNAL_ERROR;
3820 if (!allow_access(lp_hosts_deny(-1), lp_hosts_allow(-1),
3821 xconn->remote_hostname,
3822 remaddr)) {
3823 DEBUG( 1, ("Connection denied from %s to %s\n",
3824 tsocket_address_string(remote_address, talloc_tos()),
3825 tsocket_address_string(local_address, talloc_tos())));
3828 * We return a valid xconn
3829 * so that the caller can return an error message
3830 * to the client
3832 client->connections = xconn;
3833 xconn->client = client;
3834 talloc_steal(client, xconn);
3836 *_xconn = xconn;
3837 TALLOC_FREE(frame);
3838 return NT_STATUS_NETWORK_ACCESS_DENIED;
3841 DEBUG(10, ("Connection allowed from %s to %s\n",
3842 tsocket_address_string(remote_address, talloc_tos()),
3843 tsocket_address_string(local_address, talloc_tos())));
3845 if (lp_clustering()) {
3847 * We need to tell ctdb about our client's TCP
3848 * connection, so that for failover ctdbd can send
3849 * tickle acks, triggering a reconnection by the
3850 * client.
3852 NTSTATUS status;
3854 status = smbd_register_ips(xconn, &ss_srv, &ss_clnt);
3855 if (!NT_STATUS_IS_OK(status)) {
3856 DEBUG(0, ("ctdbd_register_ips failed: %s\n",
3857 nt_errstr(status)));
3861 tmp = lp_max_xmit();
3862 tmp = MAX(tmp, SMB_BUFFER_SIZE_MIN);
3863 tmp = MIN(tmp, SMB_BUFFER_SIZE_MAX);
3865 xconn->smb1.negprot.max_recv = tmp;
3867 xconn->smb1.sessions.done_sesssetup = false;
3868 xconn->smb1.sessions.max_send = SMB_BUFFER_SIZE_MAX;
3870 xconn->transport.fde = tevent_add_fd(client->raw_ev_ctx,
3871 xconn,
3872 sock_fd,
3873 TEVENT_FD_READ,
3874 smbd_server_connection_handler,
3875 xconn);
3876 if (!xconn->transport.fde) {
3877 TALLOC_FREE(frame);
3878 return NT_STATUS_NO_MEMORY;
3881 /* for now we only have one connection */
3882 DLIST_ADD_END(client->connections, xconn);
3883 xconn->client = client;
3884 talloc_steal(client, xconn);
3886 *_xconn = xconn;
3887 TALLOC_FREE(frame);
3888 return NT_STATUS_OK;
3891 /****************************************************************************
3892 Process commands from the client
3893 ****************************************************************************/
3895 void smbd_process(struct tevent_context *ev_ctx,
3896 struct messaging_context *msg_ctx,
3897 int sock_fd,
3898 bool interactive)
3900 struct smbd_tevent_trace_state trace_state = {
3901 .ev = ev_ctx,
3902 .frame = talloc_stackframe(),
3904 const struct loadparm_substitution *lp_sub =
3905 loadparm_s3_global_substitution();
3906 struct smbXsrv_client *client = NULL;
3907 struct smbd_server_connection *sconn = NULL;
3908 struct smbXsrv_connection *xconn = NULL;
3909 const char *locaddr = NULL;
3910 const char *remaddr = NULL;
3911 int ret;
3912 NTSTATUS status;
3913 struct timeval tv = timeval_current();
3914 NTTIME now = timeval_to_nttime(&tv);
3915 char *chroot_dir = NULL;
3916 int rc;
3918 status = smbXsrv_client_create(ev_ctx, ev_ctx, msg_ctx, now, &client);
3919 if (!NT_STATUS_IS_OK(status)) {
3920 DBG_ERR("smbXsrv_client_create(): %s\n", nt_errstr(status));
3921 exit_server_cleanly("talloc_zero(struct smbXsrv_client).\n");
3925 * TODO: remove this...:-)
3927 global_smbXsrv_client = client;
3929 sconn = talloc_zero(client, struct smbd_server_connection);
3930 if (sconn == NULL) {
3931 exit_server("failed to create smbd_server_connection");
3934 client->sconn = sconn;
3935 sconn->client = client;
3937 sconn->ev_ctx = ev_ctx;
3938 sconn->msg_ctx = msg_ctx;
3940 ret = pthreadpool_tevent_init(sconn, lp_aio_max_threads(),
3941 &sconn->pool);
3942 if (ret != 0) {
3943 exit_server("pthreadpool_tevent_init() failed.");
3946 if (lp_server_max_protocol() >= PROTOCOL_SMB2_02) {
3948 * We're not making the decision here,
3949 * we're just allowing the client
3950 * to decide between SMB1 and SMB2
3951 * with the first negprot
3952 * packet.
3954 sconn->using_smb2 = true;
3957 if (!interactive) {
3958 smbd_setup_sig_term_handler(sconn);
3959 smbd_setup_sig_hup_handler(sconn);
3962 status = smbd_add_connection(client, sock_fd, &xconn);
3963 if (NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_ACCESS_DENIED)) {
3965 * send a negative session response "not listening on calling
3966 * name"
3968 unsigned char buf[5] = {0x83, 0, 0, 1, 0x81};
3969 (void)srv_send_smb(xconn,(char *)buf, false,
3970 0, false, NULL);
3971 exit_server_cleanly("connection denied");
3972 } else if (!NT_STATUS_IS_OK(status)) {
3973 exit_server_cleanly(nt_errstr(status));
3976 sconn->local_address =
3977 tsocket_address_copy(xconn->local_address, sconn);
3978 if (sconn->local_address == NULL) {
3979 exit_server_cleanly("tsocket_address_copy() failed");
3981 sconn->remote_address =
3982 tsocket_address_copy(xconn->remote_address, sconn);
3983 if (sconn->remote_address == NULL) {
3984 exit_server_cleanly("tsocket_address_copy() failed");
3986 sconn->remote_hostname =
3987 talloc_strdup(sconn, xconn->remote_hostname);
3988 if (sconn->remote_hostname == NULL) {
3989 exit_server_cleanly("tsocket_strdup() failed");
3992 if (tsocket_address_is_inet(sconn->local_address, "ip")) {
3993 locaddr = tsocket_address_inet_addr_string(
3994 sconn->local_address,
3995 talloc_tos());
3996 if (locaddr == NULL) {
3997 DEBUG(0,("%s: tsocket_address_inet_addr_string remote failed - %s\n",
3998 __location__, strerror(errno)));
3999 exit_server_cleanly("tsocket_address_inet_addr_string remote failed.\n");
4001 } else {
4002 locaddr = "0.0.0.0";
4005 if (tsocket_address_is_inet(sconn->remote_address, "ip")) {
4006 remaddr = tsocket_address_inet_addr_string(
4007 sconn->remote_address,
4008 talloc_tos());
4009 if (remaddr == NULL) {
4010 DEBUG(0,("%s: tsocket_address_inet_addr_string remote failed - %s\n",
4011 __location__, strerror(errno)));
4012 exit_server_cleanly("tsocket_address_inet_addr_string remote failed.\n");
4014 } else {
4015 remaddr = "0.0.0.0";
4018 /* this is needed so that we get decent entries
4019 in smbstatus for port 445 connects */
4020 set_remote_machine_name(remaddr, false);
4021 reload_services(sconn, conn_snum_used, true);
4022 sub_set_socket_ids(remaddr,
4023 sconn->remote_hostname,
4024 locaddr);
4026 if (lp_preload_modules()) {
4027 smb_load_all_modules_absoute_path(lp_preload_modules());
4030 smb_perfcount_init();
4032 if (!init_account_policy()) {
4033 exit_server("Could not open account policy tdb.\n");
4036 chroot_dir = lp_root_directory(talloc_tos(), lp_sub);
4037 if (chroot_dir[0] != '\0') {
4038 rc = chdir(chroot_dir);
4039 if (rc != 0) {
4040 DBG_ERR("Failed to chdir to %s\n", chroot_dir);
4041 exit_server("Failed to chdir()");
4044 rc = chroot(chroot_dir);
4045 if (rc != 0) {
4046 DBG_ERR("Failed to change root to %s\n", chroot_dir);
4047 exit_server("Failed to chroot()");
4049 DBG_WARNING("Changed root to %s\n", chroot_dir);
4051 TALLOC_FREE(chroot_dir);
4054 if (!file_init(sconn)) {
4055 exit_server("file_init() failed");
4058 /* Setup oplocks */
4059 if (!init_oplocks(sconn))
4060 exit_server("Failed to init oplocks");
4062 /* register our message handlers */
4063 messaging_register(sconn->msg_ctx, sconn,
4064 MSG_SMB_FORCE_TDIS, msg_force_tdis);
4065 messaging_register(sconn->msg_ctx, sconn,
4066 MSG_SMB_CLOSE_FILE, msg_close_file);
4067 messaging_register(sconn->msg_ctx, sconn,
4068 MSG_SMB_FILE_RENAME, msg_file_was_renamed);
4070 id_cache_register_msgs(sconn->msg_ctx);
4071 messaging_deregister(sconn->msg_ctx, ID_CACHE_KILL, NULL);
4072 messaging_register(sconn->msg_ctx, sconn,
4073 ID_CACHE_KILL, smbd_id_cache_kill);
4075 messaging_deregister(sconn->msg_ctx,
4076 MSG_SMB_CONF_UPDATED, sconn->ev_ctx);
4077 messaging_register(sconn->msg_ctx, sconn,
4078 MSG_SMB_CONF_UPDATED, smbd_conf_updated);
4080 messaging_deregister(sconn->msg_ctx, MSG_SMB_KILL_CLIENT_IP,
4081 NULL);
4082 messaging_register(sconn->msg_ctx, sconn,
4083 MSG_SMB_KILL_CLIENT_IP,
4084 msg_kill_client_ip);
4086 messaging_deregister(sconn->msg_ctx, MSG_SMB_TELL_NUM_CHILDREN, NULL);
4089 * Use the default MSG_DEBUG handler to avoid rebroadcasting
4090 * MSGs to all child processes
4092 messaging_deregister(sconn->msg_ctx,
4093 MSG_DEBUG, NULL);
4094 messaging_register(sconn->msg_ctx, NULL,
4095 MSG_DEBUG, debug_message);
4097 if ((lp_keepalive() != 0)
4098 && !(event_add_idle(ev_ctx, NULL,
4099 timeval_set(lp_keepalive(), 0),
4100 "keepalive", keepalive_fn,
4101 sconn))) {
4102 DEBUG(0, ("Could not add keepalive event\n"));
4103 exit(1);
4106 if (!(event_add_idle(ev_ctx, NULL,
4107 timeval_set(IDLE_CLOSED_TIMEOUT, 0),
4108 "deadtime", deadtime_fn, sconn))) {
4109 DEBUG(0, ("Could not add deadtime event\n"));
4110 exit(1);
4113 if (!(event_add_idle(ev_ctx, NULL,
4114 timeval_set(SMBD_HOUSEKEEPING_INTERVAL, 0),
4115 "housekeeping", housekeeping_fn, sconn))) {
4116 DEBUG(0, ("Could not add housekeeping event\n"));
4117 exit(1);
4120 smbprofile_dump_setup(ev_ctx);
4122 if (!init_dptrs(sconn)) {
4123 exit_server("init_dptrs() failed");
4126 TALLOC_FREE(trace_state.frame);
4128 tevent_set_trace_callback(ev_ctx, smbd_tevent_trace_callback,
4129 &trace_state);
4131 ret = tevent_loop_wait(ev_ctx);
4132 if (ret != 0) {
4133 DEBUG(1, ("tevent_loop_wait failed: %d, %s,"
4134 " exiting\n", ret, strerror(errno)));
4137 TALLOC_FREE(trace_state.frame);
4139 exit_server_cleanly(NULL);
4142 bool req_is_in_chain(const struct smb_request *req)
4144 if (req->vwv != (const uint16_t *)(req->inbuf+smb_vwv)) {
4146 * We're right now handling a subsequent request, so we must
4147 * be in a chain
4149 return true;
4152 if (!smb1cli_is_andx_req(req->cmd)) {
4153 return false;
4156 if (req->wct < 2) {
4158 * Okay, an illegal request, but definitely not chained :-)
4160 return false;
4163 return (CVAL(req->vwv+0, 0) != 0xFF);