diff mbox series

[BlueZ,v1,4/4] settings: limit the number of chars to be read in gatt_db_load()

Message ID 20240709120031.105038-5-r.smirnov@omp.ru (mailing list archive)
State Superseded
Headers show
Series fix errors found by SVACE static analyzer #3 | expand

Checks

Context Check Description
tedd_an/pre-ci_am success Success
tedd_an/CheckPatch success CheckPatch PASS
tedd_an/GitLint success Gitlint PASS
tedd_an/IncrementalBuild success Incremental Build PASS

Commit Message

Roman Smirnov July 9, 2024, noon UTC
It is necessary to limit the string length to prevent buffer overflow.
Find the string length, write it to the pattern and use it for
limiting.

Found with the SVACE static analysis tool.
---
 src/settings.c | 39 +++++++++++++++++++++++++++++++++++++--
 1 file changed, 37 insertions(+), 2 deletions(-)
diff mbox series

Patch

diff --git a/src/settings.c b/src/settings.c
index 4eccf0b4e..dcfbc5601 100644
--- a/src/settings.c
+++ b/src/settings.c
@@ -243,13 +243,32 @@  static int gatt_db_load(struct gatt_db *db, GKeyFile *key_file, char **keys)
 	struct gatt_db_attribute *current_service;
 	char **handle, *value, type[MAX_LEN_UUID_STR];
 	int ret;
+	char pattern[6];
+	char *colon_pos;
+	size_t len;
 
 	/* first load service definitions */
 	for (handle = keys; *handle; handle++) {
 		value = g_key_file_get_string(key_file, "Attributes", *handle,
 									NULL);
+		if (!value)
+			return -EIO;
+
+		colon_pos = memchr(value, ':', MAX_LEN_UUID_STR);
+		if (!colon_pos) {
+			g_free(value);
+			return -EIO;
+		}
+
+		len = colon_pos - value;
+		if (!len) {
+			g_free(value);
+			return -EIO;
+		}
 
-		if (!value || sscanf(value, "%[^:]:", type) != 1) {
+		snprintf(pattern, sizeof(pattern), "%%%lds:", len);
+
+		if (sscanf(value, pattern, type) != 1) {
 			g_free(value);
 			return -EIO;
 		}
@@ -271,8 +290,24 @@  static int gatt_db_load(struct gatt_db *db, GKeyFile *key_file, char **keys)
 	for (handle = keys; *handle; handle++) {
 		value = g_key_file_get_string(key_file, "Attributes", *handle,
 									NULL);
+		if (!value)
+			return -EIO;
+
+		colon_pos = memchr(value, ':', MAX_LEN_UUID_STR);
+		if (!colon_pos) {
+			g_free(value);
+			return -EIO;
+		}
+
+		len = colon_pos - value;
+		if (!len) {
+			g_free(value);
+			return -EIO;
+		}
+
+		snprintf(pattern, sizeof(pattern), "%%%lds:", len);
 
-		if (!value || sscanf(value, "%[^:]:", type) != 1) {
+		if (sscanf(value, pattern, type) != 1) {
 			g_free(value);
 			return -EIO;
 		}