summaryrefslogtreecommitdiffstats
path: root/xlators/features
diff options
context:
space:
mode:
authorMichael Adam <obnox@samba.org>2015-03-31 12:30:06 +0200
committerVijay Bellur <vbellur@redhat.com>2015-03-31 23:08:23 -0700
commit562cdace9152add786f156e38dc3fbc8805a69b7 (patch)
tree758c327eb3ba017ebdcd8add5d423e8f104e45ec /xlators/features
parentf5e4c943cf520c6ec2df3c231fef9ae4116097b8 (diff)
features/trash: fix storing/wiping of eliminate path (coverity)
Functions store_eliminate_path() and wipe_eliminate_path() take eliminate as a plain pointer not pointer to pointer. Hence store_eliminate_path fails to hand the allocated and filled eliminate data out to the caller (in particular leaking memory), and wipe_eliminate_path() fails to NULL the freed eliminate path. This leads to several leak and access after free errors found by Coverity. This patch fixes the issue by handing in eliminate by reference and in the case of wipe_eliminate path, also NULLing out the free'd pointer. This fixes the following coverity IDs: CID 1288759 CID 1288790 Change-Id: I7520ae42c5f6e369a145bea67b4ff95b75d2ae73 BUG: 789278 Signed-off-by: Michael Adam <obnox@samba.org> Reviewed-on: http://review.gluster.org/10068 Tested-by: Gluster Build System <jenkins@build.gluster.com> Reviewed-by: Anoop C S <achiraya@redhat.com> Reviewed-by: Vijay Bellur <vbellur@redhat.com>
Diffstat (limited to 'xlators/features')
-rw-r--r--xlators/features/trash/src/trash.c38
1 files changed, 25 insertions, 13 deletions
diff --git a/xlators/features/trash/src/trash.c b/xlators/features/trash/src/trash.c
index d0e48506d4a..fb9ca9a0ee5 100644
--- a/xlators/features/trash/src/trash.c
+++ b/xlators/features/trash/src/trash.c
@@ -173,7 +173,7 @@ check_whether_eliminate_path (trash_elim_path *trav, const char *path)
* Stores the eliminate path into internal eliminate path structure
*/
int
-store_eliminate_path (char *str, trash_elim_path *eliminate)
+store_eliminate_path (char *str, trash_elim_path **eliminate)
{
trash_elim_path *trav = NULL;
char *component = NULL;
@@ -181,6 +181,11 @@ store_eliminate_path (char *str, trash_elim_path *eliminate)
int ret = 0;
char *strtokptr = NULL;
+ if (eliminate == NULL) {
+ ret = EINVAL;
+ goto out;
+ }
+
component = strtok_r (str, ",", &strtokptr);
while (component) {
trav = GF_CALLOC (1, sizeof (*trav),
@@ -203,8 +208,8 @@ store_eliminate_path (char *str, trash_elim_path *eliminate)
gf_log ("trash", GF_LOG_DEBUG, "out of memory");
goto out;
}
- trav->next = eliminate;
- eliminate = trav;
+ trav->next = *eliminate;
+ *eliminate = trav;
component = strtok_r (NULL, ",", &strtokptr);
}
out:
@@ -259,13 +264,20 @@ out:
* recursive call
*/
void
-wipe_eliminate_path (trash_elim_path *trav)
+wipe_eliminate_path (trash_elim_path **trav)
{
- if (trav) {
- wipe_eliminate_path (trav->next);
- GF_FREE (trav->path);
- GF_FREE (trav);
+ if (trav == NULL) {
+ return;
}
+
+ if (*trav == NULL) {
+ return;
+ }
+
+ wipe_eliminate_path (&(*trav)->next);
+ GF_FREE ((*trav)->path);
+ GF_FREE (*trav);
+ *trav = NULL;
}
/**
@@ -1967,7 +1979,7 @@ reconfigure (xlator_t *this, dict_t *options)
"no option specified for 'eliminate', using NULL");
} else {
if (priv->eliminate)
- wipe_eliminate_path (priv->eliminate);
+ wipe_eliminate_path (&priv->eliminate);
tmp_str = gf_strdup (tmp);
if (!tmp_str) {
@@ -1975,7 +1987,7 @@ reconfigure (xlator_t *this, dict_t *options)
ret = ENOMEM;
goto out;
}
- ret = store_eliminate_path (tmp_str, priv->eliminate);
+ ret = store_eliminate_path (tmp_str, &priv->eliminate);
}
@@ -2256,7 +2268,7 @@ init (xlator_t *this)
ret = ENOMEM;
goto out;
}
- ret = store_eliminate_path (tmp_str, priv->eliminate);
+ ret = store_eliminate_path (tmp_str, &priv->eliminate);
}
tmp = NULL;
@@ -2326,7 +2338,7 @@ out:
if (priv->brick_path)
GF_FREE (priv->brick_path);
if (priv->eliminate)
- wipe_eliminate_path (priv->eliminate);
+ wipe_eliminate_path (&priv->eliminate);
GF_FREE (priv);
}
mem_pool_destroy (this->local_pool);
@@ -2353,7 +2365,7 @@ fini (xlator_t *this)
if (priv->brick_path)
GF_FREE (priv->brick_path);
if (priv->eliminate)
- wipe_eliminate_path (priv->eliminate);
+ wipe_eliminate_path (&priv->eliminate);
GF_FREE (priv);
}
mem_pool_destroy (this->local_pool);