aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorXi Wang <xi.wang@gmail.com>2012-06-01 12:22:00 -0400
committerChristopher Li <sparse@chrisli.org>2012-06-04 15:36:31 -0700
commit4c982e9d3c6827afb529c7c7ce7fbe987eac24c6 (patch)
tree8d2366a1a2d97e2db8b658d339d8661b2377785f
parent970d7169d75068146152ba01a66381c800dbeb71 (diff)
downloadsparse-4c982e9d3c6827afb529c7c7ce7fbe987eac24c6.tar.gz
compile-i386: fix use-after-free in func_cleanup()
compile-i386 sometimes crashes due a use-after-free error. Since f->pseudo_list is freed first, which invalidates some atom->op* in f->atom_list. Further checks like `atom->op1->flags & STOR_WANTS_FREE' will read garbage, which may lead to a double free. This patch switches the cleanup order and frees f->atom_list first. Those marked as STOR_WANTS_FREE won't appear in f->pseudo_list. Signed-off-by: Xi Wang <xi.wang@gmail.com> Signed-off-by: Christopher Li <sparse@chrisli.org> Reviewed-by: Pekka Enberg <penberg@kernel.org>
-rw-r--r--compile-i386.c8
1 files changed, 4 insertions, 4 deletions
diff --git a/compile-i386.c b/compile-i386.c
index da3ee497..b4709525 100644
--- a/compile-i386.c
+++ b/compile-i386.c
@@ -761,10 +761,6 @@ static void func_cleanup(struct function *f)
struct storage *stor;
struct atom *atom;
- FOR_EACH_PTR(f->pseudo_list, stor) {
- free(stor);
- } END_FOR_EACH_PTR(stor);
-
FOR_EACH_PTR(f->atom_list, atom) {
if ((atom->type == ATOM_TEXT) && (atom->text))
free(atom->text);
@@ -775,6 +771,10 @@ static void func_cleanup(struct function *f)
free(atom);
} END_FOR_EACH_PTR(atom);
+ FOR_EACH_PTR(f->pseudo_list, stor) {
+ free(stor);
+ } END_FOR_EACH_PTR(stor);
+
free_ptr_list(&f->pseudo_list);
free(f);
}