[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Libunwind-devel] [PATCH] dangling pointer in ia64/Gtables.c:unw_search_
From: |
Joel Brobecker |
Subject: |
[Libunwind-devel] [PATCH] dangling pointer in ia64/Gtables.c:unw_search_ia64_unwind_table |
Date: |
Mon, 26 Mar 2012 16:36:05 -0700 |
Hello,
We noticed the following problem after we started building libunwind
(version 0.98.5) with GCC 4.7.
What happens is that unw_search_ia64_unwind_table uses remote_lookup
to search a libunwind entry, and stores the result into a variable
defined locally; When the lookup succeeds, it then saves a reference
to that local in a variable whose scope is more global, thus creating
a dangling reference as soon as we leave the local variable's scope:
else
{
struct ia64_table_entry ent;
segbase = di->u.rti.segbase;
if ((ret = remote_lookup (as, di->u.rti.table_data,
di->u.rti.table_len * sizeof (unw_word_t),
ip - segbase, &ent, arg)) < 0)
return ret;
if (ret)
e = &ent;
}
[...]
pi->start_ip = e->start_offset + segbase;
pi->end_ip = e->end_offset + segbase;
It's been working so far, but some changes in GCC's optimizer now
make it inline the call to remote_lookup and then optimize out
the tail end of that function where it was supposed to set the
"info_offset" field of our struct ia64_table_entry.
The following patch was only tested with libunwin 0.98.5, but applied
almost cleanly on the HEAD, and it seems pretty clear that HEAD also
suffers from the same problem. I would test it further on the head,
but I haven't been able to fix the last build issue I had on ia64-hpux
(mentioned when I sent the my previous series of patches).
src/ia64:
* Gtables.c (unw_search_ia64_unwind_table): Move declaration
of variable "ent" outside of "else" block to avoid having
a dangling reference to an out-of-scope local.
---
src/ia64/Gtables.c | 3 +--
1 files changed, 1 insertions(+), 2 deletions(-)
diff --git a/src/ia64/Gtables.c b/src/ia64/Gtables.c
index 1a16a2e..5ed72f0 100644
--- a/src/ia64/Gtables.c
+++ b/src/ia64/Gtables.c
@@ -255,6 +255,7 @@ unw_search_ia64_unwind_table (unw_addr_space_t as,
unw_word_t ip,
unw_word_t addr, hdr_addr, info_addr, info_end_addr, hdr, *wp;
const struct ia64_table_entry *e = NULL;
unw_word_t handler_offset, segbase = 0;
+ struct ia64_table_entry ent;
int ret, is_local;
assert ((di->format == UNW_INFO_FORMAT_TABLE
@@ -275,8 +276,6 @@ unw_search_ia64_unwind_table (unw_addr_space_t as,
unw_word_t ip,
#ifndef UNW_LOCAL_ONLY
else
{
- struct ia64_table_entry ent;
-
segbase = di->u.rti.segbase;
if ((ret = remote_lookup (as, di->u.rti.table_data,
di->u.rti.table_len * sizeof (unw_word_t),
--
1.7.1
- [Libunwind-devel] [PATCH] dangling pointer in ia64/Gtables.c:unw_search_ia64_unwind_table,
Joel Brobecker <=