1
0
mirror of https://github.com/samba-team/samba.git synced 2025-03-27 22:50:26 +03:00

s3/smbd: fix schedule_async_open() timer

schedule_async_open() was calling defer_open with sharemode lock = NULL,
as a result there was never an active 20 s timeout.

This has been broken since the commits in

$ git log --reverse -p -10 8283fd0e0090ed12b0b12d5acb550642d621b026

Just roll our own deferred record instead of calling defer_open() and
also set up timer that, as a last resort, catches stuck opens and just
exits for now.

Bug: https://bugzilla.samba.org/show_bug.cgi?id=7537

Signed-off-by: Ralph Boehme <slow@samba.org>
Reviewed-by: Jeremy Allison <jra@samba.org>
(cherry picked from commit ad8c36125f72e0d5f9ebfc94037a4ae9e7608aad)
This commit is contained in:
Ralph Boehme 2017-03-07 15:33:55 +01:00 committed by Karolin Seeger
parent 1d16e5fca1
commit dcde5b114d

View File

@ -44,6 +44,13 @@ struct deferred_open_record {
bool delayed_for_oplocks;
bool async_open;
struct file_id id;
/*
* Timer for async opens, needed because they don't use a watch on
* a locking.tdb record. This is currently only used for real async
* opens and just terminates smbd if the async open times out.
*/
struct tevent_timer *te;
};
/****************************************************************************
@ -2235,19 +2242,44 @@ static void schedule_defer_open(struct share_mode_lock *lck,
Reschedule an open call that went asynchronous.
****************************************************************************/
static void schedule_async_open_timer(struct tevent_context *ev,
struct tevent_timer *te,
struct timeval current_time,
void *private_data)
{
exit_server("async open timeout");
}
static void schedule_async_open(struct timeval request_time,
struct smb_request *req)
{
struct timeval timeout;
timeout = timeval_set(20, 0);
struct deferred_open_record *open_rec = NULL;
struct timeval timeout = timeval_set(20, 0);
bool ok;
if (request_timed_out(request_time, timeout)) {
return;
}
defer_open(NULL, request_time, timeout, req,
false, true, (struct file_id){0});
open_rec = deferred_open_record_create(false, true, (struct file_id){0});
if (open_rec == NULL) {
exit_server("deferred_open_record_create failed");
}
ok = push_deferred_open_message_smb(req, request_time, timeout,
(struct file_id){0}, open_rec);
if (!ok) {
exit_server("push_deferred_open_message_smb failed");
}
open_rec->te = tevent_add_timer(req->sconn->ev_ctx,
req,
timeval_current_ofs(20, 0),
schedule_async_open_timer,
open_rec);
if (open_rec->te == NULL) {
exit_server("tevent_add_timer failed");
}
}
/****************************************************************************