#include "includes.h"
-extern int smb_echo_count;
-
-static enum smb_read_errors smb_read_error = SMB_READ_OK;
-
/*
* Size of data we can send to client. Set
* by the client for all protocols above CORE.
extern bool global_machine_password_needs_changing;
extern int max_send;
-/* Accessor function for smb_read_error for smbd functions. */
+static void construct_reply_common(struct smb_request *req, const char *inbuf,
+ char *outbuf);
-enum smb_read_errors *get_srv_read_error(void)
-{
- return &smb_read_error;
-}
+/* Accessor function for smb_read_error for smbd functions. */
/****************************************************************************
Send an smb to a fd.
if (is_encrypted_packet(inbuf)) {
return true;
}
- return (strncmp(smb_base(inbuf),"\377SMB",4) == 0);
+ /*
+ * This used to be (strncmp(smb_base(inbuf),"\377SMB",4) == 0)
+ * but it just looks weird to call strncmp for this one.
+ */
+ return (IVAL(smb_base(inbuf), 0) == 0x424D53FF);
}
/* Socket functions for smbd packet processing. */
if (len > (BUFFER_SIZE + LARGE_WRITEX_HDR_SIZE)) {
DEBUG(0,("Invalid packet length! (%lu bytes).\n",
(unsigned long)len));
- if (len > BUFFER_SIZE + (SAFETY_MARGIN/2)) {
- return false;
- }
+ return false;
}
return true;
}
return NT_STATUS_OK;
}
- return read_socket_with_timeout_ntstatus(fd, buffer, len, len,
- timeout, NULL);
+ return read_socket_with_timeout(fd, buffer, len, len, timeout, NULL);
}
/****************************************************************************
ssize_t toread;
NTSTATUS status;
- memcpy(writeX_header, lenbuf, sizeof(lenbuf));
+ memcpy(writeX_header, lenbuf, 4);
- status = read_socket_with_timeout_ntstatus(
+ status = read_socket_with_timeout(
fd, writeX_header + 4,
STANDARD_WRITE_AND_X_HEADER_SIZE,
STANDARD_WRITE_AND_X_HEADER_SIZE,
timeout, toread);
if (!NT_STATUS_IS_OK(status)) {
+ DEBUG(10, ("receive_smb_raw_talloc_partial_read: %s\n",
+ nt_errstr(status)));
return status;
}
}
if (CVAL(lenbuf,0) == 0 &&
min_recv_size &&
- smb_len_large(lenbuf) > min_recv_size && /* Could be a UNIX large writeX. */
+ smb_len_large(lenbuf) > (min_recv_size + STANDARD_WRITE_AND_X_HEADER_SIZE) && /* Could be a UNIX large writeX. */
!srv_is_signing_active()) {
- status = receive_smb_raw_talloc_partial_read(
- mem_ctx, lenbuf, fd, buffer, timeout, p_unread, &len);
-
- if (!NT_STATUS_IS_OK(status)) {
- DEBUG(10, ("receive_smb_raw: %s\n",
- nt_errstr(status)));
- return status;
- }
+ return receive_smb_raw_talloc_partial_read(
+ mem_ctx, lenbuf, fd, buffer, timeout, p_unread, plen);
}
if (!valid_packet_size(len)) {
size_t *p_unread, bool *p_encrypted,
size_t *p_len)
{
- size_t len;
+ size_t len = 0;
NTSTATUS status;
*p_encrypted = false;
(unsigned int)req_size ));
exit_server_cleanly("Invalid SMB request");
}
+ req->cmd = CVAL(inbuf, smb_com);
req->flags2 = SVAL(inbuf, smb_flg2);
req->smbpid = SVAL(inbuf, smb_pid);
req->mid = SVAL(inbuf, smb_mid);
req->vuid = SVAL(inbuf, smb_uid);
req->tid = SVAL(inbuf, smb_tid);
req->wct = CVAL(inbuf, smb_wct);
+ req->vwv = (uint16_t *)(inbuf+smb_vwv);
+ req->buflen = smb_buflen(inbuf);
+ req->buf = (const uint8_t *)smb_buf(inbuf);
req->unread_bytes = unread_bytes;
req->encrypted = encrypted;
req->conn = conn_find(req->tid);
+ req->chain_fsp = NULL;
/* Ensure we have at least wct words and 2 bytes of bcc. */
if (smb_size + req->wct*2 > req_size) {
exit_server_cleanly("Invalid SMB request");
}
/* Ensure bcc is correct. */
- if (((uint8 *)smb_buf(inbuf)) + smb_buflen(inbuf) > inbuf + req_size) {
+ if (((uint8 *)smb_buf(inbuf)) + req->buflen > inbuf + req_size) {
DEBUG(0,("init_smb_request: invalid bcc number %u "
"(wct = %u, size %u)\n",
- (unsigned int)smb_buflen(inbuf),
+ (unsigned int)req->buflen,
(unsigned int)req->wct,
(unsigned int)req_size));
exit_server_cleanly("Invalid SMB request");
}
- req->inbuf = inbuf;
req->outbuf = NULL;
}
The timeout is in milliseconds
****************************************************************************/
-static bool receive_message_or_smb(TALLOC_CTX *mem_ctx,
- char **buffer,
- size_t *buffer_len,
- int timeout,
- size_t *p_unread,
- bool *p_encrypted)
+static NTSTATUS receive_message_or_smb(TALLOC_CTX *mem_ctx, char **buffer,
+ size_t *buffer_len,
+ size_t *p_unread, bool *p_encrypted)
{
fd_set r_fds, w_fds;
int selrtn;
struct timeval to;
int maxfd = 0;
- size_t len;
+ size_t len = 0;
NTSTATUS status;
*p_unread = 0;
- set_smb_read_error(get_srv_read_error(),SMB_READ_OK);
- again:
-
- if (timeout >= 0) {
- to.tv_sec = timeout / 1000;
- to.tv_usec = (timeout % 1000) * 1000;
- } else {
- to.tv_sec = SMBD_SELECT_TIMEOUT;
- to.tv_usec = 0;
- }
+ to.tv_sec = SMBD_SELECT_TIMEOUT;
+ to.tv_usec = 0;
/*
* Note that this call must be before processing any SMB
pop_message = True;
} else {
struct timeval tv;
- SMB_BIG_INT tdif;
+ int64_t tdif;
GetTimeOfDay(&tv);
tdif = usec_time_diff(&msg->end_time, &tv);
msg->buf.length);
if (*buffer == NULL) {
DEBUG(0, ("talloc failed\n"));
- set_smb_read_error(get_srv_read_error(),SMB_READ_ERROR);
- return False;
+ return NT_STATUS_NO_MEMORY;
}
*buffer_len = msg->buf.length;
*p_encrypted = msg->encrypted;
/* We leave this message on the queue so the open code can
know this is a retry. */
DEBUG(5,("receive_message_or_smb: returning deferred open smb message.\n"));
- return True;
+ return NT_STATUS_OK;
}
}
* the state of the flag in fds for the server file descriptor is
* indeterminate - we may have done I/O on it in the oplock processing. JRA.
*/
- goto again;
+ return NT_STATUS_RETRY;
}
/*
if (timeval_is_zero(&to)) {
/* Process a timed event now... */
if (run_events(smbd_event_context(), 0, NULL, NULL)) {
- goto again;
+ return NT_STATUS_RETRY;
}
}
}
if (run_events(smbd_event_context(), selrtn, &r_fds, &w_fds)) {
- goto again;
+ return NT_STATUS_RETRY;
}
/* if we get EINTR then maybe we have received an oplock
* the state of the flag in fds for the server file descriptor is
* indeterminate - we may have done I/O on it in the oplock processing. JRA.
*/
- goto again;
+ return NT_STATUS_RETRY;
}
/* Check if error */
if (selrtn == -1) {
/* something is wrong. Maybe the socket is dead? */
- set_smb_read_error(get_srv_read_error(),SMB_READ_ERROR);
- return False;
- }
-
+ return map_nt_error_from_unix(errno);
+ }
+
/* Did we timeout ? */
if (selrtn == 0) {
- set_smb_read_error(get_srv_read_error(),SMB_READ_TIMEOUT);
- return False;
+ return NT_STATUS_RETRY;
}
/*
* the state of the flag in fds for the server file descriptor is
* indeterminate - we may have done I/O on it in the oplock processing. JRA.
*/
- goto again;
+ return NT_STATUS_RETRY;
}
+ /*
+ * We've just woken up from a protentially long select sleep.
+ * Ensure we process local messages as we need to synchronously
+ * process any messages from other smbd's to avoid file rename race
+ * conditions. This call is cheap if there are no messages waiting.
+ * JRA.
+ */
+ message_dispatch(smbd_messaging_context());
+
status = receive_smb_talloc(mem_ctx, smbd_server_fd(), buffer, 0,
p_unread, p_encrypted, &len);
if (!NT_STATUS_IS_OK(status)) {
- if (NT_STATUS_EQUAL(status, NT_STATUS_END_OF_FILE)) {
- set_smb_read_error(get_srv_read_error(), SMB_READ_EOF);
- return false;
- }
-
- if (NT_STATUS_EQUAL(status, NT_STATUS_IO_TIMEOUT)) {
- set_smb_read_error(get_srv_read_error(),
- SMB_READ_TIMEOUT);
- return false;
- }
-
- set_smb_read_error(get_srv_read_error(), SMB_READ_ERROR);
- return false;
+ return status;
}
*buffer_len = len;
- return True;
+ return NT_STATUS_OK;
}
/*
*/
static const struct smb_message_struct {
const char *name;
- void (*fn_new)(struct smb_request *req);
+ void (*fn)(struct smb_request *req);
int flags;
} smb_messages[256] = {
allocate and initialize a reply packet
********************************************************************/
-void reply_outbuf(struct smb_request *req, uint8 num_words, uint32 num_bytes)
+static bool create_outbuf(TALLOC_CTX *mem_ctx, struct smb_request *req,
+ const char *inbuf, char **outbuf, uint8_t num_words,
+ uint32_t num_bytes)
{
/*
* Protect against integer wrap
if ((num_bytes > 0xffffff)
|| ((num_bytes + smb_size + num_words*2) > 0xffffff)) {
char *msg;
- asprintf(&msg, "num_bytes too large: %u",
- (unsigned)num_bytes);
+ if (asprintf(&msg, "num_bytes too large: %u",
+ (unsigned)num_bytes) == -1) {
+ msg = CONST_DISCARD(char *, "num_bytes too large");
+ }
smb_panic(msg);
}
- if (!(req->outbuf = TALLOC_ARRAY(
- req, uint8,
- smb_size + num_words*2 + num_bytes))) {
- smb_panic("could not allocate output buffer\n");
+ *outbuf = TALLOC_ARRAY(mem_ctx, char,
+ smb_size + num_words*2 + num_bytes);
+ if (*outbuf == NULL) {
+ return false;
}
- construct_reply_common((char *)req->inbuf, (char *)req->outbuf);
- srv_set_message((char *)req->outbuf, num_words, num_bytes, false);
+ construct_reply_common(req, inbuf, *outbuf);
+ srv_set_message(*outbuf, num_words, num_bytes, false);
/*
* Zero out the word area, the caller has to take care of the bcc area
* himself
*/
if (num_words != 0) {
- memset(req->outbuf + smb_vwv0, 0, num_words*2);
+ memset(*outbuf + smb_vwv0, 0, num_words*2);
}
- return;
+ return true;
+}
+
+void reply_outbuf(struct smb_request *req, uint8 num_words, uint32 num_bytes)
+{
+ char *outbuf;
+ if (!create_outbuf(req, req, (char *)req->inbuf, &outbuf, num_words,
+ num_bytes)) {
+ smb_panic("could not allocate output buffer\n");
+ }
+ req->outbuf = (uint8_t *)outbuf;
}
if (len < 4) len = smb_len(data)+4;
for (i=1;i<100;i++) {
- asprintf(&fname, "/tmp/%s.%d.%s", name, i,
- type ? "req" : "resp");
- if (!fname) {
+ if (asprintf(&fname, "/tmp/%s.%d.%s", name, i,
+ type ? "req" : "resp") == -1) {
return;
}
fd = open(fname, O_WRONLY|O_CREAT|O_EXCL, 0644);
exit_server_cleanly("Non-SMB packet");
}
- if (smb_messages[type].fn_new == NULL) {
+ if (smb_messages[type].fn == NULL) {
DEBUG(0,("Unknown message type %d!\n",type));
smb_dump("Unknown", 1, (char *)req->inbuf, size);
reply_unknown_new(req, type);
if(session_tag != UID_FIELD_INVALID) {
vuser = get_valid_user_struct(session_tag);
if (vuser) {
- set_current_user_info(&vuser->user);
+ set_current_user_info(
+ vuser->server_info->sanitized_username,
+ vuser->server_info->unix_name,
+ pdb_get_fullname(vuser->server_info
+ ->sam_account),
+ pdb_get_domain(vuser->server_info
+ ->sam_account));
}
}
}
if (!change_to_user(conn,session_tag)) {
reply_nterror(req, NT_STATUS_DOS(ERRSRV, ERRbaduid));
+ remove_deferred_open_smb_message(req->mid);
return conn;
}
/* encrypted required from now on. */
conn->encrypt_level = Required;
} else if (ENCRYPTION_REQUIRED(conn)) {
- uint8 com = CVAL(req->inbuf,smb_com);
- if (com != SMBtrans2 && com != SMBtranss2) {
+ if (req->cmd != SMBtrans2 && req->cmd != SMBtranss2) {
exit_server_cleanly("encryption required "
"on connection");
return conn;
return conn;
}
- smb_messages[type].fn_new(req);
+ smb_messages[type].fn(req);
return req->conn;
}
static void construct_reply(char *inbuf, int size, size_t unread_bytes, bool encrypted)
{
- uint8 type = CVAL(inbuf,smb_com);
connection_struct *conn;
struct smb_request *req;
chain_size = 0;
- file_chain_reset();
- reset_chain_p();
if (!(req = talloc(talloc_tos(), struct smb_request))) {
smb_panic("could not allocate smb_request");
}
init_smb_request(req, (uint8 *)inbuf, unread_bytes, encrypted);
+ req->inbuf = (uint8_t *)talloc_move(req, &inbuf);
- conn = switch_message(type, req, size);
+ conn = switch_message(req->cmd, req, size);
if (req->unread_bytes) {
/* writeX failed. drain socket. */
DO_PROFILE_INC(smb_count);
- if (trans_num == 0) {
- char addr[INET6_ADDRSTRLEN];
-
- /* on the first packet, check the global hosts allow/ hosts
- deny parameters before doing any parsing of the packet
- passed to us by the client. This prevents attacks on our
- parsing code from hosts not in the hosts allow list */
-
- if (!check_access(smbd_server_fd(), lp_hostsallow(-1),
- lp_hostsdeny(-1))) {
- /* send a negative session response "not listening on calling name" */
- static unsigned char buf[5] = {0x83, 0, 0, 1, 0x81};
- DEBUG( 1, ( "Connection denied from %s\n",
- client_addr(get_client_fd(),addr,sizeof(addr)) ) );
- (void)srv_send_smb(smbd_server_fd(),(char *)buf,false);
- exit_server_cleanly("connection denied");
- }
- }
-
DEBUG( 6, ( "got message type 0x%x of len 0x%x\n", msg_type,
smb_len(inbuf) ) );
DEBUG( 3, ( "Transaction %d of length %d (%u toread)\n", trans_num,
common_flags2 &= ~v;
}
-void construct_reply_common(const char *inbuf, char *outbuf)
+static void construct_reply_common(struct smb_request *req, const char *inbuf,
+ char *outbuf)
{
srv_set_message(outbuf,0,0,false);
- SCVAL(outbuf,smb_com,CVAL(inbuf,smb_com));
+ SCVAL(outbuf, smb_com, req->cmd);
SIVAL(outbuf,smb_rcls,0);
SCVAL(outbuf,smb_flg, FLAG_REPLY | (CVAL(inbuf,smb_flg) & FLAG_CASELESS_PATHNAMES));
SSVAL(outbuf,smb_flg2,
SSVAL(outbuf,smb_mid,SVAL(inbuf,smb_mid));
}
+void construct_reply_common_req(struct smb_request *req, char *outbuf)
+{
+ construct_reply_common(req, (char *)req->inbuf, outbuf);
+}
+
/****************************************************************************
Construct a chained reply and add it to the already made reply
****************************************************************************/
char *outbuf = (char *)req->outbuf;
size_t outsize = smb_len(outbuf) + 4;
size_t outsize_padded;
+ size_t padding;
size_t ofs, to_move;
struct smb_request *req2;
*/
outsize_padded = (outsize + 3) & ~3;
+ padding = outsize_padded - outsize;
/*
* remember how much the caller added to the chain, only counting
* stuff after the parameter words
*/
- chain_size += outsize_padded - smb_wct;
+ chain_size += (outsize_padded - smb_wct);
/*
* work out pointers into the original packets. The
smb_panic("could not allocate smb_request");
}
init_smb_request(req2, (uint8 *)inbuf2,0, req->encrypted);
+ req2->inbuf = (uint8_t *)inbuf2;
+ req2->chain_fsp = req->chain_fsp;
/* process the request */
switch_message(smb_com2, req2, new_size);
SCVAL(outbuf, smb_vwv0, smb_com2);
SSVAL(outbuf, smb_vwv1, chain_size + smb_wct - 4);
- if (outsize_padded > outsize) {
+ if (padding != 0) {
/*
* Due to padding we have some uninitialized bytes after the
* caller's output
*/
- memset(outbuf + outsize, 0, outsize_padded - outsize);
+ memset(outbuf + outsize, 0, padding);
}
- smb_setlen(outbuf, outsize2 + chain_size - 4);
+ smb_setlen(outbuf, outsize2 + caller_outputlen + padding - 4);
/*
* restore the saved data, being careful not to overwrite any data
SAFE_FREE(caller_output);
TALLOC_FREE(req2);
- return;
-}
-
-/****************************************************************************
- Setup the needed select timeout in milliseconds.
-****************************************************************************/
-
-static int setup_select_timeout(void)
-{
- int select_timeout;
-
- select_timeout = SMBD_SELECT_TIMEOUT*1000;
+ /*
+ * Reset the chain_size for our caller's offset calculations
+ */
- if (print_notify_messages_pending()) {
- select_timeout = MIN(select_timeout, 1000);
- }
+ chain_size -= (outsize_padded - smb_wct);
- return select_timeout;
+ return;
}
/****************************************************************************
}
/****************************************************************************
- Process any timeout housekeeping. Return False if the caller should exit.
+ Process commands from the client
****************************************************************************/
-static bool timeout_processing(int *select_timeout,
- time_t *last_timeout_processing_time)
+void smbd_process(void)
{
- time_t t;
-
- if (*get_srv_read_error() == SMB_READ_EOF) {
- DEBUG(3,("timeout_processing: End of file from client (client has disconnected).\n"));
- return false;
- }
-
- if (*get_srv_read_error() == SMB_READ_ERROR) {
- DEBUG(3,("timeout_processing: receive_smb error (%s) Exiting\n",
- strerror(errno)));
- return false;
- }
-
- if (*get_srv_read_error() == SMB_READ_BAD_SIG) {
- DEBUG(3,("timeout_processing: receive_smb error bad smb signature. Exiting\n"));
- return false;
- }
-
- *last_timeout_processing_time = t = time(NULL);
-
- /* become root again if waiting */
- change_to_root_user();
-
- /* check if we need to reload services */
- check_reload(t);
-
- if(global_machine_password_needs_changing &&
- /* for ADS we need to do a regular ADS password change, not a domain
- password change */
- lp_security() == SEC_DOMAIN) {
-
- unsigned char trust_passwd_hash[16];
- time_t lct;
-
- /*
- * We're in domain level security, and the code that
- * read the machine password flagged that the machine
- * password needs changing.
- */
+ unsigned int num_smbs = 0;
+ size_t unread_bytes = 0;
- /*
- * First, open the machine password file with an exclusive lock.
- */
+ char addr[INET6_ADDRSTRLEN];
- if (secrets_lock_trust_account_password(lp_workgroup(), True) == False) {
- DEBUG(0,("process: unable to lock the machine account password for \
-machine %s in domain %s.\n", global_myname(), lp_workgroup() ));
- return True;
- }
-
- if(!secrets_fetch_trust_account_password(lp_workgroup(), trust_passwd_hash, &lct, NULL)) {
- DEBUG(0,("process: unable to read the machine account password for \
-machine %s in domain %s.\n", global_myname(), lp_workgroup()));
- secrets_lock_trust_account_password(lp_workgroup(), False);
- return True;
- }
+ /*
+ * Before the first packet, check the global hosts allow/ hosts deny
+ * parameters before doing any parsing of packets passed to us by the
+ * client. This prevents attacks on our parsing code from hosts not in
+ * the hosts allow list.
+ */
+ if (!check_access(smbd_server_fd(), lp_hostsallow(-1),
+ lp_hostsdeny(-1))) {
/*
- * Make sure someone else hasn't already done this.
+ * send a negative session response "not listening on calling
+ * name"
*/
-
- if(t < lct + lp_machine_password_timeout()) {
- global_machine_password_needs_changing = False;
- secrets_lock_trust_account_password(lp_workgroup(), False);
- return True;
- }
-
- /* always just contact the PDC here */
-
- change_trust_account_password( lp_workgroup(), NULL);
- global_machine_password_needs_changing = False;
- secrets_lock_trust_account_password(lp_workgroup(), False);
+ unsigned char buf[5] = {0x83, 0, 0, 1, 0x81};
+ DEBUG( 1, ("Connection denied from %s\n",
+ client_addr(get_client_fd(),addr,sizeof(addr)) ) );
+ (void)srv_send_smb(smbd_server_fd(),(char *)buf,false);
+ exit_server_cleanly("connection denied");
}
- /* update printer queue caches if necessary */
-
- update_monitored_printq_cache();
-
- /*
- * Now we are root, check if the log files need pruning.
- * Force a log file check.
- */
- force_check_log_size();
- check_log_size();
-
- /* Send any queued printer notify message to interested smbd's. */
-
- print_notify_send_messages(smbd_messaging_context(), 0);
-
- /*
- * Modify the select timeout depending upon
- * what we have remaining in our queues.
- */
-
- *select_timeout = setup_select_timeout();
-
- return True;
-}
-
-/****************************************************************************
- Process commands from the client
-****************************************************************************/
-
-void smbd_process(void)
-{
- time_t last_timeout_processing_time = time(NULL);
- unsigned int num_smbs = 0;
- size_t unread_bytes = 0;
-
max_recv = MIN(lp_maxxmit(),BUFFER_SIZE);
while (True) {
- int select_timeout = setup_select_timeout();
- int num_echos;
- char *inbuf;
- size_t inbuf_len;
+ NTSTATUS status;
+ char *inbuf = NULL;
+ size_t inbuf_len = 0;
bool encrypted = false;
TALLOC_CTX *frame = talloc_stackframe_pool(8192);
errno = 0;
- /* Did someone ask for immediate checks on things like blocking locks ? */
- if (select_timeout == 0) {
- if(!timeout_processing(&select_timeout,
- &last_timeout_processing_time))
- return;
- num_smbs = 0; /* Reset smb counter. */
- }
-
run_events(smbd_event_context(), 0, NULL, NULL);
- while (!receive_message_or_smb(talloc_tos(), &inbuf, &inbuf_len,
- select_timeout,
- &unread_bytes,
- &encrypted)) {
- if(!timeout_processing(&select_timeout,
- &last_timeout_processing_time))
- return;
- num_smbs = 0; /* Reset smb counter. */
- }
+ status = NT_STATUS_RETRY;
+ while (NT_STATUS_EQUAL(status, NT_STATUS_RETRY)) {
+ status = receive_message_or_smb(
+ talloc_tos(), &inbuf, &inbuf_len,
+ &unread_bytes, &encrypted);
+ }
- /*
- * Ensure we do timeout processing if the SMB we just got was
- * only an echo request. This allows us to set the select
- * timeout in 'receive_message_or_smb()' to any value we like
- * without worrying that the client will send echo requests
- * faster than the select timeout, thus starving out the
- * essential processing (change notify, blocking locks) that
- * the timeout code does. JRA.
- */
- num_echos = smb_echo_count;
+ if (!NT_STATUS_IS_OK(status)) {
+ DEBUG(3, ("receive_message_or_smb failed: %s, "
+ "exiting\n", nt_errstr(status)));
+ return;
+ }
process_smb(inbuf, inbuf_len, unread_bytes, encrypted);
- TALLOC_FREE(inbuf);
-
- if (smb_echo_count != num_echos) {
- if(!timeout_processing( &select_timeout, &last_timeout_processing_time))
- return;
- num_smbs = 0; /* Reset smb counter. */
- }
-
num_smbs++;
- /*
- * If we are getting smb requests in a constant stream
- * with no echos, make sure we attempt timeout processing
- * every select_timeout milliseconds - but only check for this
- * every 200 smb requests.
- */
-
- if ((num_smbs % 200) == 0) {
- time_t new_check_time = time(NULL);
- if(new_check_time - last_timeout_processing_time >= (select_timeout/1000)) {
- if(!timeout_processing(
- &select_timeout,
- &last_timeout_processing_time))
- return;
- num_smbs = 0; /* Reset smb counter. */
- last_timeout_processing_time = new_check_time; /* Reset time. */
- }
- }
-
/* The timeout_processing function isn't run nearly
often enough to implement 'max log size' without
overrunning the size of the file by many megabytes.