Make metadata leaks a warning, and not a fatal error

There's still a bug on Windows that will take some time to track down
pull/4188/head
Craig Tiller 9 years ago
parent c3ec1b9324
commit 340754466e
  1. 103
      src/core/transport/metadata.c

@ -142,7 +142,6 @@ static size_t g_static_mdtab_maxprobe;
static strtab_shard g_strtab_shard[STRTAB_SHARD_COUNT];
static mdtab_shard g_mdtab_shard[MDTAB_SHARD_COUNT];
static void discard_metadata(mdtab_shard *shard);
static void gc_mdtab(mdtab_shard *shard);
void grpc_mdctx_global_init(void) {
@ -215,14 +214,20 @@ void grpc_mdctx_global_shutdown(void) {
for (i = 0; i < MDTAB_SHARD_COUNT; i++) {
mdtab_shard *shard = &g_mdtab_shard[i];
gpr_mu_destroy(&shard->mu);
discard_metadata(shard);
GPR_ASSERT(shard->count == 0);
gc_mdtab(shard);
/* TODO(ctiller): GPR_ASSERT(shard->count == 0); */
if (shard->count != 0) {
gpr_log(GPR_DEBUG, "WARNING: %d metadata elements were leaked", shard->count);
}
gpr_free(shard->elems);
}
for (i = 0; i < STRTAB_SHARD_COUNT; i++) {
strtab_shard *shard = &g_strtab_shard[i];
gpr_mu_destroy(&shard->mu);
GPR_ASSERT(shard->count == 0);
/* TODO(ctiller): GPR_ASSERT(shard->count == 0); */
if (shard->count != 0) {
gpr_log(GPR_DEBUG, "WARNING: %d metadata strings were leaked", shard->count);
}
gpr_free(shard->strs);
}
}
@ -254,96 +259,6 @@ static void ref_md_locked(mdtab_shard *shard,
}
}
#if 0
grpc_mdctx *grpc_mdctx_create_with_seed(gpr_uint32 seed) {
grpc_mdctx *ctx = gpr_malloc(sizeof(grpc_mdctx));
size_t i, j;
memset(ctx, 0, sizeof(*ctx));
g_refs = 1;
g_hash_seed = seed;
gpr_mu_init(&g_mu);
g_strtab = gpr_malloc(sizeof(internal_string *) * INITIAL_STRTAB_CAPACITY);
memset(g_strtab, 0, sizeof(grpc_mdstr *) * INITIAL_STRTAB_CAPACITY);
g_strtab_count = 0;
g_strtab_capacity = INITIAL_STRTAB_CAPACITY;
g_mdtab = gpr_malloc(sizeof(internal_metadata *) * INITIAL_MDTAB_CAPACITY);
memset(g_mdtab, 0, sizeof(grpc_mdelem *) * INITIAL_MDTAB_CAPACITY);
g_mdtab_count = 0;
g_mdtab_capacity = INITIAL_MDTAB_CAPACITY;
g_mdtab_free = 0;
return ctx;
}
grpc_mdctx *grpc_mdctx_create(void) {
/* This seed is used to prevent remote connections from controlling hash table
* collisions. It needs to be somewhat unpredictable to a remote connection.
*/
return grpc_mdctx_create_with_seed(
(gpr_uint32)gpr_now(GPR_CLOCK_REALTIME).tv_nsec);
}
#endif
static void discard_metadata(mdtab_shard *shard) {
size_t i;
internal_metadata *next, *cur;
for (i = 0; i < shard->capacity; i++) {
cur = shard->elems[i];
while (cur) {
void *user_data = (void *)gpr_atm_no_barrier_load(&cur->user_data);
GPR_ASSERT(gpr_atm_acq_load(&cur->refcnt) == 0);
next = cur->bucket_next;
GRPC_MDSTR_UNREF((grpc_mdstr *)cur->key);
GRPC_MDSTR_UNREF((grpc_mdstr *)cur->value);
if (user_data != NULL) {
((destroy_user_data_func)gpr_atm_no_barrier_load(
&cur->destroy_user_data))(user_data);
}
gpr_mu_destroy(&cur->mu_user_data);
gpr_free(cur);
cur = next;
shard->free--;
shard->count--;
}
shard->elems[i] = NULL;
}
}
#if 0
static void metadata_context_destroy_locked(grpc_mdctx *ctx) {
GPR_ASSERT(g_strtab_count == 0);
GPR_ASSERT(g_mdtab_count == 0);
GPR_ASSERT(g_mdtab_free == 0);
gpr_free(g_strtab);
gpr_free(g_mdtab);
gpr_mu_unlock(&g_mu);
gpr_mu_destroy(&g_mu);
gpr_free(ctx);
}
void grpc_mdctx_ref(grpc_mdctx *ctx) {
GPR_TIMER_BEGIN("grpc_mdctx_ref", 0);
lock(ctx);
GPR_ASSERT(g_refs > 0);
g_refs++;
unlock(ctx);
GPR_TIMER_END("grpc_mdctx_ref", 0);
}
void grpc_mdctx_unref(grpc_mdctx *ctx) {
GPR_TIMER_BEGIN("grpc_mdctx_unref", 0);
lock(ctx);
GPR_ASSERT(g_refs > 0);
g_refs--;
unlock(ctx);
GPR_TIMER_END("grpc_mdctx_unref", 0);
}
#endif
static void grow_strtab(strtab_shard *shard) {
size_t capacity = shard->capacity * 2;
size_t i;

Loading…
Cancel
Save