Replace VLA with thread local vectors

This commit is contained in:
2025-08-22 18:04:12 -04:00
parent f51f257df6
commit c58a00a34f
3 changed files with 27 additions and 35 deletions

View File

@@ -17,6 +17,9 @@
#include <unistd.h>
#include <vector>
// Static thread-local storage for read buffer (used across different functions)
static thread_local std::vector<char> g_read_buffer;
std::shared_ptr<Server> Server::create(const weaseldb::Config &config,
ConnectionHandler &handler,
const std::vector<int> &listen_fds) {
@@ -285,15 +288,16 @@ void Server::start_io_threads(std::vector<std::thread> &threads) {
// Each thread uses its assigned epoll instance (round-robin)
int epollfd = get_epoll_for_thread(thread_id);
struct epoll_event events[config_.server.event_batch_size];
std::unique_ptr<Connection> batch[config_.server.event_batch_size];
int batch_events[config_.server.event_batch_size];
std::vector<epoll_event> events(config_.server.event_batch_size);
std::vector<std::unique_ptr<Connection>> batch(
config_.server.event_batch_size);
std::vector<int> batch_events(config_.server.event_batch_size);
std::vector<int>
ready_listen_fds; // Reused across iterations to avoid allocation
for (;;) {
int event_count =
epoll_wait(epollfd, events, config_.server.event_batch_size, -1);
int event_count = epoll_wait(epollfd, events.data(),
config_.server.event_batch_size, -1);
if (event_count == -1) {
if (errno == EINTR) {
continue;
@@ -336,8 +340,9 @@ void Server::start_io_threads(std::vector<std::thread> &threads) {
// Process existing connections in batch
if (batch_count > 0) {
process_connection_batch(epollfd, {batch, (size_t)batch_count},
{batch_events, (size_t)batch_count});
process_connection_batch(
epollfd, std::span(batch).subspan(0, batch_count),
std::span(batch_events).subspan(0, batch_count));
}
// Only accept on listen sockets that epoll indicates are ready
@@ -393,8 +398,9 @@ void Server::start_io_threads(std::vector<std::thread> &threads) {
// Process batch if full
if (batch_count == config_.server.event_batch_size) {
process_connection_batch(epollfd, {batch, (size_t)batch_count},
{batch_events, (size_t)batch_count});
process_connection_batch(
epollfd, {batch.data(), (size_t)batch_count},
{batch_events.data(), (size_t)batch_count});
batch_count = 0;
}
} // End inner accept loop
@@ -402,8 +408,9 @@ void Server::start_io_threads(std::vector<std::thread> &threads) {
// Process remaining accepted connections
if (batch_count > 0) {
process_connection_batch(epollfd, {batch, (size_t)batch_count},
{batch_events, (size_t)batch_count});
process_connection_batch(
epollfd, std::span(batch).subspan(0, batch_count),
std::span(batch_events).subspan(0, batch_count));
batch_count = 0;
}
}
@@ -417,7 +424,8 @@ void Server::process_connection_reads(std::unique_ptr<Connection> &conn,
// Handle EPOLLIN - read data and process it
if (events & EPOLLIN) {
auto buf_size = config_.server.read_buffer_size;
char buf[buf_size];
g_read_buffer.resize(buf_size);
char *buf = g_read_buffer.data();
int r = conn->readBytes(buf, buf_size);
if (r < 0) {