mirror of
https://github.com/tobast/libunwind-eh_elf.git
synced 2024-11-26 00:57:39 +01:00
(flush_script_cache): Drop addr_space_t argument. Initialize
hash-table, collision-chains, and hash-table in addition to clearing the script's IP value. The latter wasn't nearly sufficient because it could cause loops on the collision chain... (get_script_cache): Also lock the cache if global caching is in effect. Take additional "saved_sigmaskp" argument. After flushing the cache, update the cache generation here. (put_script_cache): New function. (ia64_get_cached_proc_info): Adjust for get_script_cache() and put_script_cache() changes. (ia64_find_save_locs): Ditto. (ia64_script_cache_init): Call flush_script_cache() instead of opening-coding the equivalent code. (Logical change 1.96)
This commit is contained in:
parent
29358553a9
commit
b3c1bf3f75
1 changed files with 83 additions and 88 deletions
|
@ -49,18 +49,26 @@ cache_match (struct ia64_script *script, unw_word_t ip, unw_word_t pr)
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline void
|
static inline void
|
||||||
flush_script_cache (unw_addr_space_t as, struct ia64_script_cache *cache)
|
flush_script_cache (struct ia64_script_cache *cache)
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
for (i = 0; i < IA64_UNW_CACHE_SIZE; ++i)
|
cache->lru_head = IA64_UNW_CACHE_SIZE - 1;
|
||||||
cache->buckets[i].ip = 0;
|
cache->lru_tail = 0;
|
||||||
|
|
||||||
cache->generation = as->cache_generation;
|
for (i = 0; i < IA64_UNW_CACHE_SIZE; ++i)
|
||||||
|
{
|
||||||
|
if (i > 0)
|
||||||
|
cache->buckets[i].lru_chain = (i - 1);
|
||||||
|
cache->buckets[i].coll_chain = -1;
|
||||||
|
cache->buckets[i].ip = 0;
|
||||||
|
}
|
||||||
|
for (i = 0; i<IA64_UNW_HASH_SIZE; ++i)
|
||||||
|
cache->hash[i] = -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline struct ia64_script_cache *
|
static inline struct ia64_script_cache *
|
||||||
get_script_cache (unw_addr_space_t as)
|
get_script_cache (unw_addr_space_t as, sigset_t *saved_sigmaskp)
|
||||||
{
|
{
|
||||||
struct ia64_script_cache *cache = &as->global_cache;
|
struct ia64_script_cache *cache = &as->global_cache;
|
||||||
|
|
||||||
|
@ -69,12 +77,31 @@ get_script_cache (unw_addr_space_t as)
|
||||||
cache = &ia64_per_thread_cache;
|
cache = &ia64_per_thread_cache;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (as->cache_generation != cache->generation)
|
if (likely (as->caching_policy == UNW_CACHE_GLOBAL))
|
||||||
flush_script_cache (as, cache);
|
{
|
||||||
|
sigprocmask (SIG_SETMASK, &unwi_full_sigmask, saved_sigmaskp);
|
||||||
|
mutex_lock (&cache->lock);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (as->cache_generation != cache->generation)
|
||||||
|
{
|
||||||
|
flush_script_cache (cache);
|
||||||
|
cache->generation = as->cache_generation;
|
||||||
|
}
|
||||||
return cache;
|
return cache;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static inline void
|
||||||
|
put_script_cache (unw_addr_space_t as, struct ia64_script_cache *cache,
|
||||||
|
sigset_t *saved_sigmaskp)
|
||||||
|
{
|
||||||
|
if (likely (as->caching_policy == UNW_CACHE_GLOBAL))
|
||||||
|
{
|
||||||
|
mutex_unlock (&cache->lock);
|
||||||
|
sigprocmask (SIG_SETMASK, saved_sigmaskp, NULL);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static struct ia64_script *
|
static struct ia64_script *
|
||||||
script_lookup (struct ia64_script_cache *cache, struct cursor *c)
|
script_lookup (struct ia64_script_cache *cache, struct cursor *c)
|
||||||
{
|
{
|
||||||
|
@ -111,28 +138,17 @@ script_lookup (struct ia64_script_cache *cache, struct cursor *c)
|
||||||
HIDDEN int
|
HIDDEN int
|
||||||
ia64_get_cached_proc_info (struct cursor *c)
|
ia64_get_cached_proc_info (struct cursor *c)
|
||||||
{
|
{
|
||||||
int global_cache = (c->as->caching_policy == UNW_CACHE_GLOBAL);
|
|
||||||
struct ia64_script_cache *cache;
|
struct ia64_script_cache *cache;
|
||||||
struct ia64_script *script;
|
struct ia64_script *script;
|
||||||
sigset_t saved_sigmask;
|
sigset_t saved_sigmask;
|
||||||
|
|
||||||
cache = get_script_cache (c->as);
|
cache = get_script_cache (c->as, &saved_sigmask);
|
||||||
|
|
||||||
if (likely (global_cache))
|
|
||||||
{
|
{
|
||||||
sigprocmask (SIG_SETMASK, &unwi_full_sigmask, &saved_sigmask);
|
|
||||||
mutex_lock (&cache->lock);
|
|
||||||
}
|
|
||||||
|
|
||||||
script = script_lookup (cache, c);
|
script = script_lookup (cache, c);
|
||||||
if (script)
|
if (script)
|
||||||
c->pi = script->pi;
|
c->pi = script->pi;
|
||||||
|
|
||||||
if (likely (global_cache))
|
|
||||||
{
|
|
||||||
mutex_unlock (&cache->lock);
|
|
||||||
sigprocmask (SIG_SETMASK, &saved_sigmask, NULL);
|
|
||||||
}
|
}
|
||||||
|
put_script_cache (c->as, cache, &saved_sigmask);
|
||||||
return script ? 0 : -UNW_ENOINFO;
|
return script ? 0 : -UNW_ENOINFO;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -475,7 +491,6 @@ run_script (struct ia64_script *script, struct cursor *c)
|
||||||
HIDDEN int
|
HIDDEN int
|
||||||
ia64_find_save_locs (struct cursor *c)
|
ia64_find_save_locs (struct cursor *c)
|
||||||
{
|
{
|
||||||
int global_cache = (c->as->caching_policy == UNW_CACHE_GLOBAL);
|
|
||||||
struct ia64_script_cache *cache = NULL;
|
struct ia64_script_cache *cache = NULL;
|
||||||
struct ia64_script *script = NULL;
|
struct ia64_script *script = NULL;
|
||||||
sigset_t saved_sigmask;
|
sigset_t saved_sigmask;
|
||||||
|
@ -485,14 +500,8 @@ ia64_find_save_locs (struct cursor *c)
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
cache = get_script_cache (c->as);
|
cache = get_script_cache (c->as, &saved_sigmask);
|
||||||
|
|
||||||
if (likely (global_cache))
|
|
||||||
{
|
{
|
||||||
sigprocmask (SIG_SETMASK, &unwi_full_sigmask, &saved_sigmask);
|
|
||||||
mutex_lock (&cache->lock);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (c->as->caching_policy == UNW_CACHE_NONE)
|
if (c->as->caching_policy == UNW_CACHE_NONE)
|
||||||
{
|
{
|
||||||
struct ia64_script tmp_script;
|
struct ia64_script tmp_script;
|
||||||
|
@ -506,6 +515,8 @@ ia64_find_save_locs (struct cursor *c)
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
script = script_lookup (cache, c);
|
script = script_lookup (cache, c);
|
||||||
|
debug (125, "%s: ip %lx %s in script cache\n",
|
||||||
|
__FUNCTION__, (long) c->ip, script ? "hit" : "missed");
|
||||||
if (!script)
|
if (!script)
|
||||||
{
|
{
|
||||||
script = script_new (cache, c->ip);
|
script = script_new (cache, c->ip);
|
||||||
|
@ -531,31 +542,15 @@ ia64_find_save_locs (struct cursor *c)
|
||||||
}
|
}
|
||||||
|
|
||||||
run_script (script, c);
|
run_script (script, c);
|
||||||
|
|
||||||
out:
|
|
||||||
if (likely (global_cache))
|
|
||||||
{
|
|
||||||
mutex_unlock (&cache->lock);
|
|
||||||
sigprocmask (SIG_SETMASK, &saved_sigmask, NULL);
|
|
||||||
}
|
}
|
||||||
|
out:
|
||||||
|
put_script_cache (c->as, cache, &saved_sigmask);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
HIDDEN void
|
HIDDEN void
|
||||||
ia64_script_cache_init (struct ia64_script_cache *cache)
|
ia64_script_cache_init (struct ia64_script_cache *cache)
|
||||||
{
|
{
|
||||||
int i;
|
|
||||||
|
|
||||||
mutex_init (&cache->lock);
|
mutex_init (&cache->lock);
|
||||||
cache->lru_head = IA64_UNW_CACHE_SIZE - 1;
|
flush_script_cache (cache);
|
||||||
cache->lru_tail = 0;
|
|
||||||
|
|
||||||
for (i = 0; i < IA64_UNW_CACHE_SIZE; ++i)
|
|
||||||
{
|
|
||||||
if (i > 0)
|
|
||||||
cache->buckets[i].lru_chain = (i - 1);
|
|
||||||
cache->buckets[i].coll_chain = -1;
|
|
||||||
}
|
|
||||||
for (i = 0; i<IA64_UNW_HASH_SIZE; ++i)
|
|
||||||
cache->hash[i] = -1;
|
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue