diff --git a/src/core/security/security_connector.c b/src/core/security/security_connector.c index 5512bb177a9d5b3c5cec52207a0b54d181a226e0..34cb0395a243560e787a47434defd37a8fb38a01 100644 --- a/src/core/security/security_connector.c +++ b/src/core/security/security_connector.c @@ -196,12 +196,12 @@ typedef struct { static void fake_channel_destroy(grpc_security_connector *sc) { grpc_channel_security_connector *c = (grpc_channel_security_connector *)sc; grpc_credentials_unref(c->request_metadata_creds); - grpc_auth_context_unref(sc->auth_context); + GRPC_AUTH_CONTEXT_UNREF(sc->auth_context, "connector"); gpr_free(sc); } static void fake_server_destroy(grpc_security_connector *sc) { - grpc_auth_context_unref(sc->auth_context); + GRPC_AUTH_CONTEXT_UNREF(sc->auth_context, "connector"); gpr_free(sc); } @@ -242,7 +242,7 @@ static grpc_security_status fake_check_peer(grpc_security_connector *sc, status = GRPC_SECURITY_ERROR; goto end; } - grpc_auth_context_unref(sc->auth_context); + GRPC_AUTH_CONTEXT_UNREF(sc->auth_context, "connector"); sc->auth_context = grpc_auth_context_create(NULL, 1); sc->auth_context->properties[0] = grpc_auth_property_init_from_cstring( GRPC_TRANSPORT_SECURITY_TYPE_PROPERTY_NAME, @@ -323,7 +323,7 @@ static void ssl_channel_destroy(grpc_security_connector *sc) { if (c->target_name != NULL) gpr_free(c->target_name); if (c->overridden_target_name != NULL) gpr_free(c->overridden_target_name); tsi_peer_destruct(&c->peer); - grpc_auth_context_unref(sc->auth_context); + GRPC_AUTH_CONTEXT_UNREF(sc->auth_context, "connector"); gpr_free(sc); } @@ -333,7 +333,7 @@ static void ssl_server_destroy(grpc_security_connector *sc) { if (c->handshaker_factory != NULL) { tsi_ssl_handshaker_factory_destroy(c->handshaker_factory); } - grpc_auth_context_unref(sc->auth_context); + GRPC_AUTH_CONTEXT_UNREF(sc->auth_context, "connector"); gpr_free(sc); } @@ -437,6 +437,9 @@ static grpc_security_status ssl_check_peer(grpc_security_connector *sc, gpr_log(GPR_ERROR, "Peer name %s is not in peer certificate", peer_name); return GRPC_SECURITY_ERROR; } + if (sc->auth_context != NULL) { + GRPC_AUTH_CONTEXT_UNREF(sc->auth_context, "connector"); + } sc->auth_context = tsi_ssl_peer_to_auth_context(peer); return GRPC_SECURITY_OK; } diff --git a/src/core/security/security_context.c b/src/core/security/security_context.c index 9aba1e7f910dd40c35de95494cc5abc4673cb50e..4d56549f9b6bb35a884f7ff0fa92970993d99b9b 100644 --- a/src/core/security/security_context.c +++ b/src/core/security/security_context.c @@ -89,7 +89,7 @@ grpc_client_security_context *grpc_client_security_context_create(void) { void grpc_client_security_context_destroy(void *ctx) { grpc_client_security_context *c = (grpc_client_security_context *)ctx; grpc_credentials_unref(c->creds); - grpc_auth_context_unref(c->auth_context); + GRPC_AUTH_CONTEXT_UNREF(c->auth_context, "client_security_context"); gpr_free(ctx); } @@ -104,7 +104,7 @@ grpc_server_security_context *grpc_server_security_context_create(void) { void grpc_server_security_context_destroy(void *ctx) { grpc_server_security_context *c = (grpc_server_security_context *)ctx; - grpc_auth_context_unref(c->auth_context); + GRPC_AUTH_CONTEXT_UNREF(c->auth_context, "server_security_context"); gpr_free(ctx); } @@ -120,21 +120,40 @@ grpc_auth_context *grpc_auth_context_create(grpc_auth_context *chained, memset(ctx->properties, 0, property_count * sizeof(grpc_auth_property)); ctx->property_count = property_count; gpr_ref_init(&ctx->refcount, 1); - if (chained != NULL) ctx->chained = grpc_auth_context_ref(chained); + if (chained != NULL) ctx->chained = GRPC_AUTH_CONTEXT_REF(chained, "chained"); return ctx; } +#ifdef GRPC_AUTH_CONTEXT_REFCOUNT_DEBUG +grpc_auth_context *grpc_auth_context_ref(grpc_auth_context *ctx, + const char *file, int line, + const char *reason) { + if (ctx == NULL) return NULL; + gpr_log(file, line, GPR_LOG_SEVERITY_DEBUG, + "AUTH_CONTEXT:%p ref %d -> %d %s", ctx, (int)ctx->refcount.count, + (int)ctx->refcount.count + 1, reason); +#else grpc_auth_context *grpc_auth_context_ref(grpc_auth_context *ctx) { if (ctx == NULL) return NULL; +#endif gpr_ref(&ctx->refcount); return ctx; } +#ifdef GRPC_AUTH_CONTEXT_REFCOUNT_DEBUG +void grpc_auth_context_unref(grpc_auth_context *ctx, const char *file, int line, + const char *reason) { + if (ctx == NULL) return; + gpr_log(file, line, GPR_LOG_SEVERITY_DEBUG, + "AUTH_CONTEXT:%p unref %d -> %d %s", ctx, (int)ctx->refcount.count, + (int)ctx->refcount.count - 1, reason); +#else void grpc_auth_context_unref(grpc_auth_context *ctx) { if (ctx == NULL) return; +#endif if (gpr_unref(&ctx->refcount)) { size_t i; - grpc_auth_context_unref(ctx->chained); + GRPC_AUTH_CONTEXT_UNREF(ctx->chained, "chained"); if (ctx->properties != NULL) { for (i = 0; i < ctx->property_count; i++) { grpc_auth_property_reset(&ctx->properties[i]); @@ -223,8 +242,8 @@ grpc_auth_property grpc_auth_property_init(const char *name, const char *value, } void grpc_auth_property_reset(grpc_auth_property *property) { - if (property->name != NULL) gpr_free(property->name); - if (property->value != NULL) gpr_free(property->value); + gpr_free(property->name); + gpr_free(property->value); memset(property, 0, sizeof(grpc_auth_property)); } diff --git a/src/core/security/security_context.h b/src/core/security/security_context.h index d8909cd6f1e29c664a70932a3f923cb7e15fc1fb..20c4390898a66a9ee7dc974da063afcfb07e0d65 100644 --- a/src/core/security/security_context.h +++ b/src/core/security/security_context.h @@ -55,9 +55,22 @@ grpc_auth_context *grpc_auth_context_create(grpc_auth_context *chained, size_t property_count); /* Refcounting. */ -grpc_auth_context *grpc_auth_context_ref( - grpc_auth_context *ctx); -void grpc_auth_context_unref(grpc_auth_context *ctx); +#ifdef GRPC_AUTH_CONTEXT_REFCOUNT_DEBUG +#define GRPC_AUTH_CONTEXT_REF(p, r) \ + grpc_auth_context_ref((p), __FILE__, __LINE__, (r)) +#define GRPC_AUTH_CONTEXT_UNREF(p, r) \ + grpc_auth_context_unref((p), __FILE__, __LINE__, (r)) +grpc_auth_context *grpc_auth_context_ref(grpc_auth_context *policy, + const char *file, int line, + const char *reason); +void grpc_auth_context_unref(grpc_auth_context *policy, const char *file, + int line, const char *reason); +#else +#define GRPC_AUTH_CONTEXT_REF(p, r) grpc_auth_context_ref((p)) +#define GRPC_AUTH_CONTEXT_UNREF(p, r) grpc_auth_context_unref((p)) +grpc_auth_context *grpc_auth_context_ref(grpc_auth_context *policy); +void grpc_auth_context_unref(grpc_auth_context *policy); +#endif grpc_auth_property grpc_auth_property_init_from_cstring(const char *name, const char *value); diff --git a/src/core/security/server_auth_filter.c b/src/core/security/server_auth_filter.c index b19160b8ed5637389006b0658aaa82f342e8bce8..b8639287a5dd5d812b9b7a9673d39fae167f73f2 100644 --- a/src/core/security/server_auth_filter.c +++ b/src/core/security/server_auth_filter.c @@ -82,9 +82,13 @@ static void init_call_elem(grpc_call_element *elem, /* Create a security context for the call and reference the auth context from the channel. */ + if (initial_op->context[GRPC_CONTEXT_SECURITY].value != NULL) { + initial_op->context[GRPC_CONTEXT_SECURITY].destroy( + initial_op->context[GRPC_CONTEXT_SECURITY].value); + } server_ctx = grpc_server_security_context_create(); - server_ctx->auth_context = - grpc_auth_context_ref(chand->security_connector->auth_context); + server_ctx->auth_context = GRPC_AUTH_CONTEXT_REF( + chand->security_connector->auth_context, "server_security_context"); initial_op->context[GRPC_CONTEXT_SECURITY].value = server_ctx; initial_op->context[GRPC_CONTEXT_SECURITY].destroy = grpc_server_security_context_destroy; diff --git a/test/core/security/auth_context_test.c b/test/core/security/auth_context_test.c index 2fb0c01f6f2c8cbc9a7ba3270eea6409d88f36d7..2b12551a069433de9d4c53db00769d708f4365a3 100644 --- a/test/core/security/auth_context_test.c +++ b/test/core/security/auth_context_test.c @@ -52,7 +52,7 @@ static void test_empty_context(void) { GPR_ASSERT(grpc_auth_property_iterator_next(&it) == NULL); it = grpc_auth_context_find_properties_by_name(ctx, "foo"); GPR_ASSERT(grpc_auth_property_iterator_next(&it) == NULL); - grpc_auth_context_unref(ctx); + GRPC_AUTH_CONTEXT_UNREF(ctx, "test"); } static void test_simple_context(void) { @@ -86,7 +86,7 @@ static void test_simple_context(void) { GPR_ASSERT(grpc_auth_property_iterator_next(&it) == &ctx->properties[1]); GPR_ASSERT(grpc_auth_property_iterator_next(&it) == NULL); - grpc_auth_context_unref(ctx); + GRPC_AUTH_CONTEXT_UNREF(ctx, "test"); } static void test_chained_context(void) { @@ -96,7 +96,7 @@ static void test_chained_context(void) { size_t i; gpr_log(GPR_INFO, "test_chained_context"); - grpc_auth_context_unref(chained); + GRPC_AUTH_CONTEXT_UNREF(chained, "chained"); chained->properties[0] = grpc_auth_property_init_from_cstring("name", "padapo"); chained->properties[1] = grpc_auth_property_init_from_cstring("foo", "baz"); @@ -129,7 +129,7 @@ static void test_chained_context(void) { GPR_ASSERT(grpc_auth_property_iterator_next(&it) == &chained->properties[0]); GPR_ASSERT(grpc_auth_property_iterator_next(&it) == NULL); - grpc_auth_context_unref(ctx); + GRPC_AUTH_CONTEXT_UNREF(ctx, "test"); } diff --git a/test/core/security/security_connector_test.c b/test/core/security/security_connector_test.c index 4ad8beb7270fc7a6bb5575a4238db0a3fe540f36..b37fd7213df2e4a9a4d5cde9f67f68f6eacb1df0 100644 --- a/test/core/security/security_connector_test.c +++ b/test/core/security/security_connector_test.c @@ -73,7 +73,7 @@ static void test_unauthenticated_ssl_peer(void) { GPR_ASSERT(check_transport_security_type(ctx)); tsi_peer_destruct(&peer); - grpc_auth_context_unref(ctx); + GRPC_AUTH_CONTEXT_UNREF(ctx, "test"); } static int check_identity(const grpc_auth_context *ctx, @@ -145,7 +145,7 @@ static void test_cn_only_ssl_peer_to_auth_context(void) { GPR_ASSERT(check_x509_cn(ctx, expected_cn)); tsi_peer_destruct(&peer); - grpc_auth_context_unref(ctx); + GRPC_AUTH_CONTEXT_UNREF(ctx, "test"); } static void test_cn_and_one_san_ssl_peer_to_auth_context(void) { @@ -171,7 +171,7 @@ static void test_cn_and_one_san_ssl_peer_to_auth_context(void) { GPR_ASSERT(check_x509_cn(ctx, expected_cn)); tsi_peer_destruct(&peer); - grpc_auth_context_unref(ctx); + GRPC_AUTH_CONTEXT_UNREF(ctx, "test"); } static void test_cn_and_multiple_sans_ssl_peer_to_auth_context(void) { @@ -202,7 +202,7 @@ static void test_cn_and_multiple_sans_ssl_peer_to_auth_context(void) { GPR_ASSERT(check_x509_cn(ctx, expected_cn)); tsi_peer_destruct(&peer); - grpc_auth_context_unref(ctx); + GRPC_AUTH_CONTEXT_UNREF(ctx, "test"); } static void test_cn_and_multiple_sans_and_others_ssl_peer_to_auth_context( @@ -238,8 +238,7 @@ static void test_cn_and_multiple_sans_and_others_ssl_peer_to_auth_context( GPR_ASSERT(check_x509_cn(ctx, expected_cn)); tsi_peer_destruct(&peer); - grpc_auth_context_unref(ctx); - + GRPC_AUTH_CONTEXT_UNREF(ctx, "test"); } int main(int argc, char **argv) {