Blame SOURCES/irqbalance-1.4.0-Fix-several-memleak-problems-found-by-covscan.patch

eb8d4c
From 9ed5c269bd59c95f41829aedf0520930c97b08d3 Mon Sep 17 00:00:00 2001
eb8d4c
From: Kairui Song <kasong@redhat.com>
eb8d4c
Date: Thu, 30 Aug 2018 17:45:53 +0800
eb8d4c
Subject: Fix several memleak problems found by covscan
eb8d4c
eb8d4c
Some memleak issues is found by static analysis tools, and can confirm
eb8d4c
irqbalance is leaking memory slowly when there are incomming connection
eb8d4c
to socket.
eb8d4c
eb8d4c
This patch could solve the memleak problem.
eb8d4c
---
eb8d4c
 irqbalance.c       | 16 ++++++++++++----
eb8d4c
 ui/irqbalance-ui.c | 31 +++++++++++++++++++++++++++----
eb8d4c
 ui/ui.c            |  2 ++
eb8d4c
 3 files changed, 41 insertions(+), 8 deletions(-)
eb8d4c
eb8d4c
diff --git a/irqbalance.c b/irqbalance.c
eb8d4c
index 6412447..4b3de54 100644
eb8d4c
--- a/irqbalance.c
eb8d4c
+++ b/irqbalance.c
eb8d4c
@@ -385,11 +385,11 @@ gboolean sock_handle(gint fd, GIOCondition condition, gpointer user_data __attri
eb8d4c
 		sock = accept(fd, NULL, NULL);
eb8d4c
 		if (sock < 0) {
eb8d4c
 			log(TO_ALL, LOG_WARNING, "Connection couldn't be accepted.\n");
eb8d4c
-			return TRUE;
eb8d4c
+			goto out;
eb8d4c
 		}
eb8d4c
 		if ((recv_size = recvmsg(sock, &msg, 0)) < 0) {
eb8d4c
 			log(TO_ALL, LOG_WARNING, "Error while receiving data.\n");
eb8d4c
-			return TRUE;
eb8d4c
+			goto out;
eb8d4c
 		}
eb8d4c
 		cmsg = CMSG_FIRSTHDR(&msg;;
eb8d4c
 		if ((cmsg->cmsg_level == SOL_SOCKET) &&
eb8d4c
@@ -401,7 +401,7 @@ gboolean sock_handle(gint fd, GIOCondition condition, gpointer user_data __attri
eb8d4c
 		}
eb8d4c
 		if (!valid_user) {
eb8d4c
 			log(TO_ALL, LOG_INFO, "Permission denied for user to connect to socket.\n");
eb8d4c
-			return TRUE;
eb8d4c
+			goto out;
eb8d4c
 		}
eb8d4c
 
eb8d4c
 		if (!strncmp(buff, "stats", strlen("stats"))) {
eb8d4c
@@ -421,6 +421,7 @@ gboolean sock_handle(gint fd, GIOCondition condition, gpointer user_data __attri
eb8d4c
 				if (new_iterval >= 1) {
eb8d4c
 					sleep_interval = new_iterval;
eb8d4c
 				}
eb8d4c
+				free(sleep_string);
eb8d4c
 			} else if (!(strncmp(buff + strlen("settings "), "ban irqs ",
eb8d4c
 							strlen("ban irqs ")))) {
eb8d4c
 				char *end;
eb8d4c
@@ -432,12 +433,14 @@ gboolean sock_handle(gint fd, GIOCondition condition, gpointer user_data __attri
eb8d4c
 				cl_banned_irqs = NULL;
eb8d4c
 				need_rescan = 1;
eb8d4c
 				if (!strncmp(irq_string, "NONE", strlen("NONE"))) {
eb8d4c
-					return TRUE;
eb8d4c
+					free(irq_string);
eb8d4c
+					goto out;
eb8d4c
 				}
eb8d4c
 				int irq = strtoul(irq_string, &end, 10);
eb8d4c
 				do {
eb8d4c
 					add_cl_banned_irq(irq);
eb8d4c
 				} while((irq = strtoul(end, &end, 10)));
eb8d4c
+				free(irq_string);
eb8d4c
 			} else if (!(strncmp(buff + strlen("settings "), "cpus ",
eb8d4c
 							strlen("cpus")))) {
eb8d4c
 				char *cpu_ban_string = malloc(
eb8d4c
@@ -449,6 +452,7 @@ gboolean sock_handle(gint fd, GIOCondition condition, gpointer user_data __attri
eb8d4c
 					banned_cpumask_from_ui = NULL;
eb8d4c
 				}
eb8d4c
 				need_rescan = 1;
eb8d4c
+				free(cpu_ban_string);
eb8d4c
 			}
eb8d4c
 		}
eb8d4c
 		if (!strncmp(buff, "setup", strlen("setup"))) {
eb8d4c
@@ -463,10 +467,14 @@ gboolean sock_handle(gint fd, GIOCondition condition, gpointer user_data __attri
eb8d4c
 			snprintf(setup + strlen(setup), strlen(banned) + 7 + 1,
eb8d4c
 					"BANNED %s", banned);
eb8d4c
 			send(sock, setup, strlen(setup), 0);
eb8d4c
+			free(setup);
eb8d4c
 		}
eb8d4c
 
eb8d4c
 		close(sock);
eb8d4c
 	}
eb8d4c
+
eb8d4c
+out:
eb8d4c
+	free(msg.msg_control);
eb8d4c
 	return TRUE;
eb8d4c
 }
eb8d4c
 
eb8d4c
diff --git a/ui/irqbalance-ui.c b/ui/irqbalance-ui.c
eb8d4c
index 3fc46af..99f2ca2 100644
eb8d4c
--- a/ui/irqbalance-ui.c
eb8d4c
+++ b/ui/irqbalance-ui.c
eb8d4c
@@ -41,6 +41,7 @@ struct msghdr * create_credentials_msg()
eb8d4c
 	cmsg->cmsg_len = CMSG_LEN(sizeof(struct ucred));
eb8d4c
 	memcpy(CMSG_DATA(cmsg), credentials, sizeof(struct ucred));
eb8d4c
 
eb8d4c
+	free(credentials);
eb8d4c
 	return msg;
eb8d4c
 }
eb8d4c
 
eb8d4c
@@ -87,6 +88,8 @@ void send_settings(char *data)
eb8d4c
 	sendmsg(socket_fd, msg, 0);
eb8d4c
 
eb8d4c
 	close(socket_fd);
eb8d4c
+	free(msg->msg_control);
eb8d4c
+	free(msg);
eb8d4c
 }
eb8d4c
 
eb8d4c
 char * get_data(char *string)
eb8d4c
@@ -115,6 +118,8 @@ char * get_data(char *string)
eb8d4c
 	int len = recv(socket_fd, data, 8192, 0);
eb8d4c
 	close(socket_fd);
eb8d4c
 	data[len] = '\0';
eb8d4c
+	free(msg->msg_control);
eb8d4c
+	free(msg);
eb8d4c
 	return data;
eb8d4c
 }
eb8d4c
 
eb8d4c
@@ -123,6 +128,7 @@ void parse_setup(char *setup_data)
eb8d4c
 	char *token, *ptr;
eb8d4c
 	int i,j;
eb8d4c
 	char *copy;
eb8d4c
+	irq_t *new_irq = NULL;
eb8d4c
 	if((setup_data == NULL) || (strlen(setup_data) == 0)) return;
eb8d4c
 	copy = strdup(setup_data);
eb8d4c
 	if (!copy)
eb8d4c
@@ -136,7 +142,7 @@ void parse_setup(char *setup_data)
eb8d4c
 	token = strtok_r(NULL, " ", &ptr);
eb8d4c
 	/* Parse banned IRQ data */
eb8d4c
 	while(!strncmp(token, "IRQ", strlen("IRQ"))) {
eb8d4c
-		irq_t *new_irq = malloc(sizeof(irq_t));
eb8d4c
+		new_irq = malloc(sizeof(irq_t));
eb8d4c
 		new_irq->vector = strtol(strtok_r(NULL, " ", &ptr), NULL, 10);
eb8d4c
 		token = strtok_r(NULL, " ", &ptr);
eb8d4c
 		if(strncmp(token, "LOAD", strlen("LOAD"))) goto out;
eb8d4c
@@ -151,6 +157,7 @@ void parse_setup(char *setup_data)
eb8d4c
 		new_irq->assigned_to = NULL;
eb8d4c
 		setup.banned_irqs = g_list_append(setup.banned_irqs, new_irq);
eb8d4c
 		token = strtok_r(NULL, " ", &ptr);
eb8d4c
+		new_irq = NULL;
eb8d4c
 	}
eb8d4c
 
eb8d4c
 	if(strncmp(token, "BANNED", strlen("BANNED"))) goto out;
eb8d4c
@@ -165,6 +172,7 @@ void parse_setup(char *setup_data)
eb8d4c
 								banned_cpu);
eb8d4c
 			}
eb8d4c
 		}
eb8d4c
+		free(map);
eb8d4c
 	
eb8d4c
 	}
eb8d4c
 	free(copy);
eb8d4c
@@ -173,6 +181,9 @@ void parse_setup(char *setup_data)
eb8d4c
 out: {
eb8d4c
 	/* Invalid data presented */
eb8d4c
 	printf("Invalid data sent.  Unexpected token: %s", token);
eb8d4c
+	if (new_irq) {
eb8d4c
+		free(new_irq);
eb8d4c
+	}
eb8d4c
 	free(copy);
eb8d4c
 	g_list_free(tree);
eb8d4c
 	exit(1);
eb8d4c
@@ -240,7 +251,9 @@ void parse_into_tree(char *data)
eb8d4c
 	cpu_node_t *parent = NULL;
eb8d4c
 	char *copy;
eb8d4c
 	tree = NULL;
eb8d4c
-	
eb8d4c
+	irq_t *new_irq = NULL;
eb8d4c
+	cpu_node_t *new = NULL;
eb8d4c
+
eb8d4c
 	if (!data || strlen(data) == 0)
eb8d4c
 		return;
eb8d4c
 
eb8d4c
@@ -255,7 +268,7 @@ void parse_into_tree(char *data)
eb8d4c
 			free(copy);
eb8d4c
 			 goto out;
eb8d4c
 		}
eb8d4c
-		cpu_node_t *new = malloc(sizeof(cpu_node_t));
eb8d4c
+		new = malloc(sizeof(cpu_node_t));
eb8d4c
 		new->irqs = NULL;
eb8d4c
 		new->children = NULL;
eb8d4c
 		new->cpu_list = NULL;
eb8d4c
@@ -279,7 +292,7 @@ void parse_into_tree(char *data)
eb8d4c
 
eb8d4c
 		/* Parse assigned IRQ data */
eb8d4c
 		while((token != NULL) && (!strncmp(token, "IRQ", strlen("IRQ")))) {
eb8d4c
-			irq_t *new_irq = malloc(sizeof(irq_t));
eb8d4c
+			new_irq = malloc(sizeof(irq_t));
eb8d4c
 			new_irq->vector = strtol(strtok_r(NULL, " ", &ptr), NULL, 10);
eb8d4c
 			token = strtok_r(NULL, " ", &ptr);
eb8d4c
 			if(strncmp(token, "LOAD", strlen("LOAD"))) goto out;
eb8d4c
@@ -293,6 +306,7 @@ void parse_into_tree(char *data)
eb8d4c
 			new_irq->is_banned = 0;
eb8d4c
 			new->irqs = g_list_append(new->irqs, new_irq);
eb8d4c
 			token = strtok_r(NULL, " ", &ptr);
eb8d4c
+			new_irq = NULL;
eb8d4c
 		}
eb8d4c
 
eb8d4c
 		if((token == NULL) || (strncmp(token, "IRQ", strlen("IRQ")))) {
eb8d4c
@@ -306,6 +320,8 @@ void parse_into_tree(char *data)
eb8d4c
 				parent = new;
eb8d4c
 			}
eb8d4c
 		}
eb8d4c
+
eb8d4c
+		new = NULL;
eb8d4c
 	}
eb8d4c
 	free(copy);
eb8d4c
 	for_each_node(tree, assign_cpu_lists, NULL);
eb8d4c
@@ -315,6 +331,12 @@ void parse_into_tree(char *data)
eb8d4c
 out: {
eb8d4c
 	/* Invalid data presented */
eb8d4c
 	printf("Invalid data sent.  Unexpected token: %s\n", token);
eb8d4c
+	if (new_irq) {
eb8d4c
+		free(new_irq);
eb8d4c
+	}
eb8d4c
+	if (new) {
eb8d4c
+		free(new);
eb8d4c
+	}
eb8d4c
 	g_list_free(tree);
eb8d4c
 	exit(1);
eb8d4c
 }
eb8d4c
@@ -330,6 +352,7 @@ gboolean rescan_tree(gpointer data __attribute__((unused)))
eb8d4c
 		display_tree();
eb8d4c
 	}
eb8d4c
 	free(setup_data);
eb8d4c
+	free(irqbalance_data);
eb8d4c
 	return TRUE;
eb8d4c
 }
eb8d4c
 
eb8d4c
diff --git a/ui/ui.c b/ui/ui.c
eb8d4c
index 4054f0e..06ec472 100644
eb8d4c
--- a/ui/ui.c
eb8d4c
+++ b/ui/ui.c
eb8d4c
@@ -71,6 +71,7 @@ char * check_control_in_sleep_input(int max_len, int column_offest, int line_off
eb8d4c
 			attrset(COLOR_PAIR(6));
eb8d4c
 			break;
eb8d4c
 		case 27:
eb8d4c
+			free(input_to);
eb8d4c
 			return NULL;
eb8d4c
 		default:
eb8d4c
 			input_to[iteration] = new;
eb8d4c
@@ -115,6 +116,7 @@ int get_valid_sleep_input(int column_offest)
eb8d4c
 				input);
eb8d4c
 			refresh();
eb8d4c
 		}
eb8d4c
+		free(input);
eb8d4c
 	}
eb8d4c
 
eb8d4c
 	attrset(COLOR_PAIR(1));
eb8d4c
-- 
eb8d4c
2.17.1
eb8d4c