Add a timeout to scgi tasks.

A hundred connections sending a partial header held the whole task pool.
This commit is contained in:
xirvik
2026-08-17 15:31:20 +00:00
committed by Jari Sundell
parent 9066afc063
commit af6d8a10ad
2 changed files with 18 additions and 2 deletions
+11
View File
@@ -14,6 +14,7 @@
#include <torrent/runtime/socket_manager.h>
#include <torrent/system/callbacks.h>
#include <torrent/system/poll.h>
#include <torrent/system/scheduler.h>
#include <torrent/utils/log.h>
#include "control.h"
@@ -27,6 +28,8 @@ namespace rpc {
SCgiTask::SCgiTask()
: m_callback_id(torrent::system::make_callback_id()) {
m_task_timeout.slot() = [this]() { close(); };
reset_file_descriptor();
}
@@ -50,6 +53,8 @@ SCgiTask::open(SCgi* parent, int fd) {
torrent::this_thread::poll()->open(this);
torrent::this_thread::poll()->insert_read(this);
torrent::this_thread::scheduler()->update_wait_for_ceil_seconds(&m_task_timeout, timeout_request);
auto lock = std::lock_guard<std::mutex>(m_result_mutex);
// Leave room for terminating nul byte for parsing the header.
@@ -61,6 +66,8 @@ SCgiTask::cancel_open() {
if (!is_open())
return;
torrent::this_thread::scheduler()->erase(&m_task_timeout);
torrent::this_thread::poll()->remove_and_close(this);
torrent::fd_close(file_descriptor());
@@ -72,6 +79,8 @@ SCgiTask::close() {
if (!is_open())
return;
torrent::this_thread::scheduler()->erase(&m_task_timeout);
torrent::system::cancel_callback_and_wait(m_callback_id, scgi_thread::thread(), torrent::main_thread::thread());
torrent::runtime::socket_manager()->close_event_or_throw(this, [this]() {
@@ -158,6 +167,8 @@ SCgiTask::event_read() {
torrent::this_thread::poll()->remove_read(this);
torrent::this_thread::scheduler()->update_wait_for_ceil_seconds(&m_task_timeout, timeout_request);
if (m_parent->log_fd() >= 0) {
[[maybe_unused]] int result;
+7 -2
View File
@@ -1,10 +1,12 @@
#ifndef RTORRENT_RPC_SCGI_TASK_H
#define RTORRENT_RPC_SCGI_TASK_H
#include <chrono>
#include <memory>
#include <mutex>
#include <vector>
#include <torrent/system/event.h>
#include <torrent/system/scheduler.h>
namespace rpc {
@@ -16,6 +18,8 @@ public:
static constexpr int max_header_size = 2000;
static constexpr int max_content_size = (2 << 23);
static constexpr auto timeout_request = std::chrono::seconds(60);
enum ContentType { XML, JSON };
SCgiTask();
@@ -54,8 +58,9 @@ private:
void plaintext_response(const char* buffer, uint32_t content_length);
void gzip_response(const char* buffer, uint32_t content_length);
SCgi* m_parent{};
torrent::system::callback_id m_callback_id;
SCgi* m_parent{};
torrent::system::callback_id m_callback_id;
torrent::system::SchedulerEntry m_task_timeout;
std::mutex m_result_mutex;