| From 83d9a6e89af9caebe109c5f309c7bc2d82bd8fc4 Mon Sep 17 00:00:00 2001 |
| From: Jan Synacek <jan.synacek@gmail.com> |
| Date: Tue, 3 Jan 2017 21:34:36 +0100 |
| Subject: [PATCH] shared: fix double free in unmask (#5005) |
| |
| Easily reproducible: |
| 1) systemctl mask foo |
| 2) systemctl unmask foo foo |
| |
| The problem here is that the *i that is put into todo[] is later freed |
| in strv_uniq(), which is not directly visible from this patch. Somewhere |
| further in the code, the string that *i pointed to is freed again. That |
| happens only when multiple services with the same name/path are specified. |
| (cherry picked from commit dc7dd61de610e9330abe7014860acfa733887d5e) |
| --- |
| src/shared/install.c | 4 ++-- |
| 1 file changed, 2 insertions(+), 2 deletions(-) |
| |
| diff --git a/src/shared/install.c b/src/shared/install.c |
| index 96fba6e25b..5f0eec3ccb 100644 |
| --- a/src/shared/install.c |
| +++ b/src/shared/install.c |
| @@ -1861,7 +1861,7 @@ int unit_file_unmask( |
| |
| _cleanup_lookup_paths_free_ LookupPaths paths = {}; |
| _cleanup_set_free_free_ Set *remove_symlinks_to = NULL; |
| - _cleanup_free_ char **todo = NULL; |
| + _cleanup_strv_free_ char **todo = NULL; |
| size_t n_todo = 0, n_allocated = 0; |
| const char *config_path; |
| char **i; |
| @@ -1899,7 +1899,7 @@ int unit_file_unmask( |
| if (!GREEDY_REALLOC0(todo, n_allocated, n_todo + 2)) |
| return -ENOMEM; |
| |
| - todo[n_todo++] = *i; |
| + todo[n_todo++] = strdup(*i); |
| } |
| |
| strv_uniq(todo); |