MT#63826 db_redis: lost patches during last upgrade

NGCP-Flow: mr13.5

During the last upgrade to the 6.0.6 upstream version,
db redis patches for key length protection were removed.
Resurrect them.

Change-Id: If430db81518b1ebc47d9cb883a152f0718b98798
mr13.5
Donat Zenichev 2 months ago
parent 78fb6ac49c
commit 9106e2c424

@ -43,6 +43,8 @@ sipwise/lost-add-method-parameter-to-http_connect-calls.patch
sipwise/usrloc-don-t-synchronize-on-destroy-for-DB_ONLY.patch
sipwise/presence_offline_cleanup.patch
### active development
sipwise/db_redis_protect_length_overflow.patch
sipwise/db_redis_support_null_key_values.patch
sipwise/permissions-don-t-allow-reloads-in-the-middle-of-ong.patch
sipwise/permissions_consider_db_mode_when_rpc_reload.patch

@ -0,0 +1,140 @@
From: Sipwise Development Team <support@sipwise.com>
Date: Tue, 13 Jan 2026 09:50:54 +0100
Subject: db_redis_protect_length_overflow
---
src/modules/db_redis/db_redis_mod.c | 2 ++
src/modules/db_redis/redis_dbase.c | 7 +++----
src/modules/db_redis/redis_table.c | 33 ++++++++++++++++++++++++++++-----
src/modules/db_redis/redis_table.h | 4 ++--
4 files changed, 35 insertions(+), 11 deletions(-)
diff --git a/src/modules/db_redis/db_redis_mod.c b/src/modules/db_redis/db_redis_mod.c
index 11c7b8c..fafafbb 100644
--- a/src/modules/db_redis/db_redis_mod.c
+++ b/src/modules/db_redis/db_redis_mod.c
@@ -42,6 +42,7 @@ MODULE_VERSION
str redis_keys = str_init("");
str redis_schema_path = str_init(SHARE_DIR "db_redis/kamailio");
int db_redis_verbosity = 1;
+unsigned int db_redis_max_key_len = 0;
static int db_redis_bind_api(db_func_t *dbb);
static int mod_init(void);
@@ -60,6 +61,7 @@ static param_export_t params[] = {
{"keys", PARAM_STRING | PARAM_USE_FUNC, (void *)keys_param},
{"schema_path", PARAM_STR, &redis_schema_path},
{"verbosity", PARAM_INT, &db_redis_verbosity},
+ {"max_key_length", PARAM_INT, &db_redis_max_key_len},
#ifdef WITH_SSL
{"opt_tls", PARAM_INT, &db_redis_opt_tls},
{"ca_path", PARAM_STRING, &db_redis_ca_path},
diff --git a/src/modules/db_redis/redis_dbase.c b/src/modules/db_redis/redis_dbase.c
index b98f401..6725bf5 100644
--- a/src/modules/db_redis/redis_dbase.c
+++ b/src/modules/db_redis/redis_dbase.c
@@ -876,7 +876,7 @@ static int db_redis_scan_query_keys_pattern(km_redis_con_t *con,
LM_ERR("Failed to add scan command to scan query\n");
goto err;
}
- if(db_redis_key_add_string(&query_v, index_key->s, index_key->len)
+ if(db_redis_key_add_str(&query_v, index_key)
!= 0) {
LM_ERR("Failed to add scan command to scan query\n");
goto err;
@@ -891,8 +891,7 @@ static int db_redis_scan_query_keys_pattern(km_redis_con_t *con,
LM_ERR("Failed to add match command to scan query\n");
goto err;
}
- if(db_redis_key_add_string(
- &query_v, match_pattern->s, match_pattern->len)
+ if (db_redis_key_add_str(&query_v, match_pattern)
!= 0) {
LM_ERR("Failed to add match pattern to scan query\n");
goto err;
@@ -907,7 +906,7 @@ static int db_redis_scan_query_keys_pattern(km_redis_con_t *con,
LM_ERR("Failed to print integer for scan query\n");
goto err;
}
- if(db_redis_key_add_string(&query_v, match_count_str, l) != 0) {
+ if(db_redis_key_add_string(&query_v, match_count_str, (size_t)l) != 0) {
LM_ERR("Failed to add count value to scan query\n");
goto err;
}
diff --git a/src/modules/db_redis/redis_table.c b/src/modules/db_redis/redis_table.c
index af3700d..2100884 100644
--- a/src/modules/db_redis/redis_table.c
+++ b/src/modules/db_redis/redis_table.c
@@ -24,14 +24,24 @@
#include <sys/stat.h>
#include <dirent.h>
-#include "db_redis_mod.h"
-#include "redis_connection.h"
#include "redis_table.h"
-int db_redis_key_add_string(redis_key_t **list, const char *entry, int len)
+extern unsigned int db_redis_max_key_len;
+
+int db_redis_key_add_string(redis_key_t **list, const char *entry, size_t len)
{
redis_key_t *k;
+ if (!entry || !len) {
+ LM_ERR("Empty entry or zero length\n");
+ return -1;
+ }
+
+ if (db_redis_max_key_len > 0 && len > db_redis_max_key_len) {
+ LM_ERR("Too big length for key being added: allowed '%u' / given '%zu'\n",
+ db_redis_max_key_len, len);
+ return -1;
+ }
k = (redis_key_t *)pkg_malloc(sizeof(redis_key_t));
if(!k) {
@@ -69,13 +79,26 @@ err:
int db_redis_key_add_str(redis_key_t **list, const str *entry)
{
- return db_redis_key_add_string(list, entry->s, entry->len);
+ if (entry->len < 0)
+ return -1;
+ return db_redis_key_add_string(list, entry->s, (size_t)entry->len);
}
-int db_redis_key_prepend_string(redis_key_t **list, const char *entry, int len)
+int db_redis_key_prepend_string(redis_key_t **list, const char *entry, size_t len)
{
redis_key_t *k;
+ if (!entry || !len) {
+ LM_ERR("Empty entry or zero length\n");
+ return -1;
+ }
+
+ if (db_redis_max_key_len > 0 && len > db_redis_max_key_len) {
+ LM_ERR("Too big length for key being prepended: allowed '%u' / given '%zu'\n",
+ db_redis_max_key_len, len);
+ return -1;
+ }
+
k = (redis_key_t *)pkg_malloc(sizeof(redis_key_t));
if(!k) {
LM_ERR("Failed to allocate memory for key list entry\n");
diff --git a/src/modules/db_redis/redis_table.h b/src/modules/db_redis/redis_table.h
index 6ba4e8c..879b50c 100644
--- a/src/modules/db_redis/redis_table.h
+++ b/src/modules/db_redis/redis_table.h
@@ -61,9 +61,9 @@ void db_redis_free_tables(km_redis_con_t *con);
int db_redis_parse_schema(km_redis_con_t *con);
int db_redis_parse_keys(km_redis_con_t *con);
-int db_redis_key_add_string(redis_key_t **list, const char *entry, int len);
+int db_redis_key_add_string(redis_key_t **list, const char *entry, size_t len);
int db_redis_key_add_str(redis_key_t **list, const str *entry);
-int db_redis_key_prepend_string(redis_key_t **list, const char *entry, int len);
+int db_redis_key_prepend_string(redis_key_t **list, const char *entry, size_t len);
int db_redis_key_list2arr(redis_key_t *list, char ***arr);
redis_key_t *db_redis_key_shift(redis_key_t **list);
void db_redis_key_free(redis_key_t **list);

@ -0,0 +1,41 @@
From: Sipwise Development Team <support@sipwise.com>
Date: Fri, 6 Mar 2026 10:37:29 +0100
Subject: db_redis_support_null_key_values
---
src/modules/db_redis/redis_table.c | 15 ++++++++-------
1 file changed, 8 insertions(+), 7 deletions(-)
diff --git a/src/modules/db_redis/redis_table.c b/src/modules/db_redis/redis_table.c
index 2100884..09b1225 100644
--- a/src/modules/db_redis/redis_table.c
+++ b/src/modules/db_redis/redis_table.c
@@ -32,11 +32,6 @@ int db_redis_key_add_string(redis_key_t **list, const char *entry, size_t len)
{
redis_key_t *k;
- if (!entry || !len) {
- LM_ERR("Empty entry or zero length\n");
- return -1;
- }
-
if (db_redis_max_key_len > 0 && len > db_redis_max_key_len) {
LM_ERR("Too big length for key being added: allowed '%u' / given '%zu'\n",
db_redis_max_key_len, len);
@@ -56,8 +51,14 @@ int db_redis_key_add_string(redis_key_t **list, const char *entry, size_t len)
goto err;
}
- memcpy(k->key.s, entry, len);
- k->key.s[len] = '\0';
+ /* run memcpy only on non-NULL pointer, because in fact it may happen
+ * it comes here empty and with len = 0, this is then an implicit
+ * conversion of <null> redis key value into the empty "" string.
+ * see `db_redis_val2str()`
+ * This is the allowed behavior, but avoid then running memcpy() on it. */
+ if (entry && len > 0)
+ memcpy(k->key.s, entry, len);
+ k->key.s[len] = '\0'; /* at least 1 byte is already pre-allocated before */
k->key.len = len;
if(!*list) {
Loading…
Cancel
Save