]> git.ipfire.org Git - thirdparty/unbound.git/commitdiff
- Add redis-command-timeout: 20 and redis-connect-timeout: 200,
authorW.C.A. Wijngaards <wouter@nlnetlabs.nl>
Tue, 17 Sep 2024 11:10:34 +0000 (13:10 +0200)
committerW.C.A. Wijngaards <wouter@nlnetlabs.nl>
Tue, 17 Sep 2024 11:10:34 +0000 (13:10 +0200)
  that can set the timeout separately for commands and the
  connection set up to the redis server. If they are not
  specified, the redis-timeout value is used.

cachedb/redis.c
doc/Changelog
doc/example.conf.in
doc/unbound.conf.5.in
util/config_file.c
util/config_file.h
util/configlexer.lex
util/configparser.y

index 6cc975901df2a3d18e2bf502dd771eb274fdd621..68c033535a699351eaac0b9a341f343cca37bff9 100644 (file)
@@ -58,7 +58,8 @@ struct redis_moddata {
        int server_port;         /* server's TCP port */
        const char* server_path; /* server's unix path, or "", NULL if unused */
        const char* server_password; /* server's AUTH password, or "", NULL if unused */
-       struct timeval timeout;  /* timeout for connection setup and commands */
+       struct timeval command_timeout;  /* timeout for commands */
+       struct timeval connect_timeout;  /* timeout for connect */
        int logical_db;         /* the redis logical database to use */
 };
 
@@ -88,10 +89,10 @@ redis_connect(const struct redis_moddata* moddata)
 
        if(moddata->server_path && moddata->server_path[0]!=0) {
                ctx = redisConnectUnixWithTimeout(moddata->server_path,
-                       moddata->timeout);
+                       moddata->connect_timeout);
        } else {
                ctx = redisConnectWithTimeout(moddata->server_host,
-                       moddata->server_port, moddata->timeout);
+                       moddata->server_port, moddata->connect_timeout);
        }
        if(!ctx || ctx->err) {
                const char *errstr = "out of memory";
@@ -100,7 +101,7 @@ redis_connect(const struct redis_moddata* moddata)
                log_err("failed to connect to redis server: %s", errstr);
                goto fail;
        }
-       if(redisSetTimeout(ctx, moddata->timeout) != REDIS_OK) {
+       if(redisSetTimeout(ctx, moddata->command_timeout) != REDIS_OK) {
                log_err("failed to set redis timeout");
                goto fail;
        }
@@ -159,8 +160,24 @@ redis_init(struct module_env* env, struct cachedb_env* cachedb_env)
        moddata->server_port = env->cfg->redis_server_port;
        moddata->server_path = env->cfg->redis_server_path;
        moddata->server_password = env->cfg->redis_server_password;
-       moddata->timeout.tv_sec = env->cfg->redis_timeout / 1000;
-       moddata->timeout.tv_usec = (env->cfg->redis_timeout % 1000) * 1000;
+       moddata->command_timeout.tv_sec = env->cfg->redis_timeout / 1000;
+       moddata->command_timeout.tv_usec =
+               (env->cfg->redis_timeout % 1000) * 1000;
+       moddata->connect_timeout.tv_sec = env->cfg->redis_timeout / 1000;
+       moddata->connect_timeout.tv_usec =
+               (env->cfg->redis_timeout % 1000) * 1000;
+       if(env->cfg->redis_command_timeout != 0) {
+               moddata->command_timeout.tv_sec =
+                       env->cfg->redis_command_timeout / 1000;
+               moddata->command_timeout.tv_usec =
+                       (env->cfg->redis_command_timeout % 1000) * 1000;
+       }
+       if(env->cfg->redis_connect_timeout != 0) {
+               moddata->connect_timeout.tv_sec =
+                       env->cfg->redis_connect_timeout / 1000;
+               moddata->connect_timeout.tv_usec =
+                       (env->cfg->redis_connect_timeout % 1000) * 1000;
+       }
        moddata->logical_db = env->cfg->redis_logical_db;
        for(i = 0; i < moddata->numctxs; i++) {
                redisContext* ctx = redis_connect(moddata);
index e5d778f1d879c8ab8f9c3ee9b6946f1816ab74d0..ed3bc87003f16624aa915adb242bfd3c2bc7ba28 100644 (file)
@@ -1,3 +1,9 @@
+17 September 2024: Wouter
+       - Add redis-command-timeout: 20 and redis-connect-timeout: 200,
+         that can set the timeout separately for commands and the
+         connection set up to the redis server. If they are not
+         specified, the redis-timeout value is used.
+
 16 September 2024: Wouter
        - Merge #1140: Fix spelling mistake in comments.
 
index cce65c0f54b96be9c65137c85b0f4f48da81613e..e5bb5029f94617e04a63cd5c5514f93381ba79a4 100644 (file)
@@ -1301,6 +1301,10 @@ remote-control:
 #     # redis-server-password: ""
 #     # timeout (in ms) for communication with the redis server
 #     redis-timeout: 100
+#     # timeout (in ms) for commands, if 0, uses redis-timeout.
+#     redis-command-timeout: 0
+#     # timeout (in ms) for connection set up, if 0, uses redis-timeout.
+#     redis-connect-timeout: 0
 #     # set timeout on redis records based on DNS response TTL
 #     redis-expire-records: no
 #     # redis logical database to use, 0 is the default database.
index d051e8850cd806af58065e48e9ae5993466d211f..f4cf8177868bf3654819236811a12e7c2b5277bf 100644 (file)
@@ -2810,6 +2810,14 @@ if the Redis server does not have the requested data, and will try to
 re-establish a new connection later.
 This option defaults to 100 milliseconds.
 .TP
+.B redis-command-timeout: \fI<msec>\fR
+The timeout to use for redis commands, in milliseconds. If 0, it uses the
+redis\-timeout value. The default is 0.
+.TP
+.B redis-connect-timeout: \fI<msec>\fR
+The timeout to use for redis connection set up, in milliseconds. If 0, it
+uses the redis\-timeout value. The default is 0.
+.TP
 .B redis-expire-records: \fI<yes or no>
 If Redis record expiration is enabled.  If yes, Unbound sets timeout for Redis
 records so that Redis can evict keys that have expired automatically.  If
index d82e4374e760c38e45c608709cbe6390356c8e3f..ab63d3fed6ce02ea102afd5dd00022a9ecfbafdc 100644 (file)
@@ -399,6 +399,8 @@ config_create(void)
        cfg->redis_server_path = NULL;
        cfg->redis_server_password = NULL;
        cfg->redis_timeout = 100;
+       cfg->redis_command_timeout = 0;
+       cfg->redis_connect_timeout = 0;
        cfg->redis_server_port = 6379;
        cfg->redis_expire_records = 0;
        cfg->redis_logical_db = 0;
@@ -1364,6 +1366,8 @@ config_get_option(struct config_file* cfg, const char* opt,
        else O_STR(opt, "redis-server-path", redis_server_path)
        else O_STR(opt, "redis-server-password", redis_server_password)
        else O_DEC(opt, "redis-timeout", redis_timeout)
+       else O_DEC(opt, "redis-command-timeout", redis_command_timeout)
+       else O_DEC(opt, "redis-connect-timeout", redis_connect_timeout)
        else O_YNO(opt, "redis-expire-records", redis_expire_records)
        else O_DEC(opt, "redis-logical-db", redis_logical_db)
 #endif  /* USE_REDIS */
index ae9c9cb5b82dcee7737b0807d5dbdebe2d085468..29dd7162013097d35c15ea00c4ff93492e6fa38d 100644 (file)
@@ -739,6 +739,10 @@ struct config_file {
        char* redis_server_password;
        /** timeout (in ms) for communication with the redis server */
        int redis_timeout;
+       /** timeout (in ms) for redis commands */
+       int redis_command_timeout;
+       /** timeout (in ms) for redis connection set up */
+       int redis_connect_timeout;
        /** set timeout on redis records based on DNS response ttl */
        int redis_expire_records;
        /** set the redis logical database upon connection */
index 527d5bfb9524d54b3582d30c6ba975859ac2784f..b4442e913ef87159b28989277d839e93740b07d2 100644 (file)
@@ -574,6 +574,8 @@ redis-server-port{COLON}    { YDVAR(1, VAR_CACHEDB_REDISPORT) }
 redis-server-path{COLON}       { YDVAR(1, VAR_CACHEDB_REDISPATH) }
 redis-server-password{COLON}   { YDVAR(1, VAR_CACHEDB_REDISPASSWORD) }
 redis-timeout{COLON}           { YDVAR(1, VAR_CACHEDB_REDISTIMEOUT) }
+redis-command-timeout{COLON}   { YDVAR(1, VAR_CACHEDB_REDISCOMMANDTIMEOUT) }
+redis-connect-timeout{COLON}   { YDVAR(1, VAR_CACHEDB_REDISCONNECTTIMEOUT) }
 redis-expire-records{COLON}    { YDVAR(1, VAR_CACHEDB_REDISEXPIRERECORDS) }
 redis-logical-db{COLON}                { YDVAR(1, VAR_CACHEDB_REDISLOGICALDB) }
 ipset{COLON}                   { YDVAR(0, VAR_IPSET) }
index 4dc647f8291ec3c5b5969ef55ee1b8542802f92a..dfc0c58af9751c63956c9f91fa9e5ad39c09fb70 100644 (file)
@@ -182,6 +182,7 @@ extern struct config_parser_state* cfg_parser;
 %token VAR_CACHEDB_REDISHOST VAR_CACHEDB_REDISPORT VAR_CACHEDB_REDISTIMEOUT
 %token VAR_CACHEDB_REDISEXPIRERECORDS VAR_CACHEDB_REDISPATH VAR_CACHEDB_REDISPASSWORD
 %token VAR_CACHEDB_REDISLOGICALDB
+%token VAR_CACHEDB_REDISCOMMANDTIMEOUT VAR_CACHEDB_REDISCONNECTTIMEOUT
 %token VAR_UDP_UPSTREAM_WITHOUT_DOWNSTREAM VAR_FOR_UPSTREAM
 %token VAR_AUTH_ZONE VAR_ZONEFILE VAR_MASTER VAR_URL VAR_FOR_DOWNSTREAM
 %token VAR_FALLBACK_ENABLED VAR_TLS_ADDITIONAL_PORT VAR_LOW_RTT VAR_LOW_RTT_PERMIL
@@ -3838,7 +3839,8 @@ contents_cachedb: contents_cachedb content_cachedb
 content_cachedb: cachedb_backend_name | cachedb_secret_seed |
        redis_server_host | redis_server_port | redis_timeout |
        redis_expire_records | redis_server_path | redis_server_password |
-       cachedb_no_store | redis_logical_db | cachedb_check_when_serve_expired
+       cachedb_no_store | redis_logical_db | cachedb_check_when_serve_expired |
+       redis_command_timeout | redis_connect_timeout
        ;
 cachedb_backend_name: VAR_CACHEDB_BACKEND STRING_ARG
        {
@@ -3954,6 +3956,32 @@ redis_timeout: VAR_CACHEDB_REDISTIMEOUT STRING_ARG
                free($2);
        }
        ;
+redis_command_timeout: VAR_CACHEDB_REDISCOMMANDTIMEOUT STRING_ARG
+       {
+       #if defined(USE_CACHEDB) && defined(USE_REDIS)
+               OUTYY(("P(redis_command_timeout:%s)\n", $2));
+               if(atoi($2) == 0 && strcmp($2, "0") != 0)
+                       yyerror("redis command timeout value expected");
+               else cfg_parser->cfg->redis_command_timeout = atoi($2);
+       #else
+               OUTYY(("P(Compiled without cachedb or redis, ignoring)\n"));
+       #endif
+               free($2);
+       }
+       ;
+redis_connect_timeout: VAR_CACHEDB_REDISCONNECTTIMEOUT STRING_ARG
+       {
+       #if defined(USE_CACHEDB) && defined(USE_REDIS)
+               OUTYY(("P(redis_connect_timeout:%s)\n", $2));
+               if(atoi($2) == 0 && strcmp($2, "0") != 0)
+                       yyerror("redis connect timeout value expected");
+               else cfg_parser->cfg->redis_connect_timeout = atoi($2);
+       #else
+               OUTYY(("P(Compiled without cachedb or redis, ignoring)\n"));
+       #endif
+               free($2);
+       }
+       ;
 redis_expire_records: VAR_CACHEDB_REDISEXPIRERECORDS STRING_ARG
        {
        #if defined(USE_CACHEDB) && defined(USE_REDIS)