{ "setStaleCacheEntriesTTL", true, "n", "allows using cache entries expired for at most n seconds when there is no backend available to answer for a query" },
{ "setSyslogFacility", true, "facility", "set the syslog logging facility to 'facility'. Defaults to LOG_DAEMON" },
{ "setTCPDownstreamCleanupInterval", true, "interval", "minimum interval in seconds between two cleanups of the idle TCP downstream connections" },
+ { "setTCPFastOpenKey", true, "string", "TCP Fast Open Key" },
{ "setTCPDownstreamMaxIdleTime", true, "time", "Maximum time in seconds that a downstream TCP connection to a backend might stay idle" },
{ "setTCPInternalPipeBufferSize", true, "size", "Set the size in bytes of the internal buffer of the pipes used internally to distribute connections to TCP (and DoT) workers threads" },
{ "setTCPRecvTimeout", true, "n", "set the read timeout on TCP connections from the client, in seconds" },
#include <sys/types.h>
#include <sys/stat.h>
#include <thread>
+#include <vector>
#include "dnsdist.hh"
#include "dnsdist-carbon.hh"
});
luaCtx.writeFunction("setTCPInternalPipeBufferSize", [](uint64_t size) { g_tcpInternalPipeBufferSize = size; });
+ luaCtx.writeFunction("setTCPFastOpenKey", [](const std::string& keyString) {
+ setLuaSideEffect();
+ unsigned int key[4] = {};
+ auto ret = sscanf(keyString.c_str(), "%x-%x-%x-%x", &key[0], &key[1], &key[2], &key[3]);
+ if (ret != 4) {
+ g_outputBuffer = "Invalid value passed to setTCPFastOpenKey()!\n";
+ return;
+ }
+ extern vector<unsigned int> g_TCPFastOpenKey;
+ for (const auto i : key) {
+ g_TCPFastOpenKey.push_back(i);
+ }
+ });
#ifdef HAVE_NET_SNMP
luaCtx.writeFunction("snmpAgent", [client, configCheck](bool enableTraps, boost::optional<std::string> daemonSocket) {
std::vector<std::unique_ptr<ClientState>> g_frontends;
GlobalStateHolder<pools_t> g_pools;
size_t g_udpVectorSize{1};
-
+std::vector<unsigned int> g_TCPFastOpenKey;
/* UDP: the grand design. Per socket we listen on for incoming queries there is one thread.
Then we have a bunch of connected sockets for talking to downstream servers.
We send directly to those sockets.
if (cs->fastOpenQueueSize > 0) {
#ifdef TCP_FASTOPEN
SSetsockopt(fd, IPPROTO_TCP, TCP_FASTOPEN, cs->fastOpenQueueSize);
+ if (!g_TCPFastOpenKey.empty()) {
+ auto res = setsockopt(fd, IPPROTO_IP, TCP_FASTOPEN_KEY, g_TCPFastOpenKey.data(), g_TCPFastOpenKey.size() * sizeof(g_TCPFastOpenKey[0]));
+ if (res == -1)
+ throw runtime_error("setsockopt for level IPPROTO_TCP and opname TCP_FASTOPEN_KEY failed: " + stringerror());
+ }
#else
if (warn) {
warnlog("TCP Fast Open has been configured on local address '%s' but is not supported", cs->local.toStringWithPort());