diff options
author | eutarass | 2010-03-10 01:18:55 +0000 |
---|---|---|
committer | eutarass | 2010-03-10 01:18:55 +0000 |
commit | 1e87a684645553f95359b81b27c54525e7d3ff61 (patch) | |
tree | 251a87a799429076b6d31b4eda9a2abf4cd7a7dc /framework/cache.c | |
parent | a53eba17a4a7b83f4a56c011006d497194e5261d (diff) | |
download | org.eclipse.tcf.agent-1e87a684645553f95359b81b27c54525e7d3ff61.tar.gz org.eclipse.tcf.agent-1e87a684645553f95359b81b27c54525e7d3ff61.tar.xz org.eclipse.tcf.agent-1e87a684645553f95359b81b27c54525e7d3ff61.zip |
TCF Agent: more symbols value-add code.
Diffstat (limited to 'framework/cache.c')
-rw-r--r-- | framework/cache.c | 49 |
1 files changed, 35 insertions, 14 deletions
diff --git a/framework/cache.c b/framework/cache.c index b51c6f9f..5a118553 100644 --- a/framework/cache.c +++ b/framework/cache.c @@ -29,41 +29,55 @@ typedef struct WaitingCacheClient { CacheClient * client; Channel * channel; void * args; + size_t args_size; + int args_copy; } WaitingCacheClient; -static WaitingCacheClient current_client = {0, 0, 0}; +static WaitingCacheClient current_client = {0, 0, 0, 0, 0}; +static int client_exited = 0; static int cache_miss_cnt = 0; static WaitingCacheClient * wait_list_buf; static unsigned wait_list_max; -void cache_enter(CacheClient * client, Channel * channel, void * args) { +static void run_cache_client(void) { Trap trap; + OutputStream * out = ¤t_client.channel->bcg->out; - assert(is_dispatch_thread()); - assert(client != NULL); - assert(channel != NULL); - assert(current_client.client == NULL); - current_client.client = client; - current_client.channel = channel; - current_client.args = args; cache_miss_cnt = 0; + client_exited = 0; if (set_trap(&trap)) { - client(args); + current_client.client(current_client.args); clear_trap(&trap); assert(cache_miss_cnt == 0); - flush_stream(&channel->bcg->out); + assert(client_exited); + flush_stream(out); } - else if (get_error_code(trap.error) != ERR_CACHE_MISS || current_client.client == NULL) { + else if (get_error_code(trap.error) != ERR_CACHE_MISS || client_exited) { trace(LOG_ALWAYS, "Unhandled exception in data cache client: %d %s", trap.error, errno_to_str(trap.error)); } + if (cache_miss_cnt == 0 && current_client.args_copy) loc_free(current_client.args); memset(¤t_client, 0, sizeof(current_client)); } +void cache_enter(CacheClient * client, Channel * channel, void * args, size_t args_size) { + assert(is_dispatch_thread()); + assert(client != NULL); + assert(channel != NULL); + assert(current_client.client == NULL); + current_client.client = client; + current_client.channel = channel; + current_client.args = args; + current_client.args_size = args_size; + current_client.args_copy = 0; + run_cache_client(); +} + void cache_exit(void) { assert(is_dispatch_thread()); assert(current_client.client != NULL); + assert(!client_exited); if (cache_miss_cnt > 0) exception(ERR_CACHE_MISS); - memset(¤t_client, 0, sizeof(current_client)); + client_exited = 1; } void cache_wait(AbstractCache * cache) { @@ -73,6 +87,12 @@ void cache_wait(AbstractCache * cache) { cache->wait_list_max += 8; cache->wait_list_buf = (WaitingCacheClient *)loc_realloc(cache->wait_list_buf, cache->wait_list_max * sizeof(WaitingCacheClient)); } + if (current_client.args != NULL && !current_client.args_copy) { + void * mem = loc_alloc(current_client.args_size); + memcpy(mem, current_client.args, current_client.args_size); + current_client.args = mem; + current_client.args_copy = 1; + } cache->wait_list_buf[cache->wait_list_cnt++] = current_client; channel_lock(current_client.channel); } @@ -92,7 +112,8 @@ void cache_notify(AbstractCache * cache) { } memcpy(wait_list_buf, cache->wait_list_buf, cnt * sizeof(WaitingCacheClient)); for (i = 0; i < cnt; i++) { - cache_enter(wait_list_buf[i].client, wait_list_buf[i].channel, wait_list_buf[i].args); + current_client = wait_list_buf[i]; + run_cache_client(); channel_unlock(wait_list_buf[i].channel); } } |