From 31cda5ad65a2ad7095693cf72f193a4cf4ac05ef Mon Sep 17 00:00:00 2001 From: Massimiliano Pinto Date: Mon, 2 Sep 2013 10:26:34 +0200 Subject: [PATCH] Added session refcount in session.h The refcount is incremented in dcb_connect and in mysql_client.c after session_alloc --- server/core/dcb.c | 7 ++++++- server/core/session.c | 14 +++++++++++--- server/include/session.h | 5 ++++- server/modules/protocol/mysql_client.c | 2 ++ 4 files changed, 23 insertions(+), 5 deletions(-) diff --git a/server/core/dcb.c b/server/core/dcb.c index de7267aaf..7d91d514a 100644 --- a/server/core/dcb.c +++ b/server/core/dcb.c @@ -39,7 +39,8 @@ * for handling backend asynchronous protocol connection * and a generic lock for backend authentication * 16/07/2013 Massimiliano Pinto Added command type for dcb - * 23/07/13 Mark Riddoch Tidy up logging + * 23/07/2013 Mark Riddoch Tidy up logging + * 02/09/2013 Massimiliano Pinto Added session refcount * * @endverbatim */ @@ -314,6 +315,8 @@ GWPROTOCOL *funcs; memcpy(&(dcb->func), funcs, sizeof(GWPROTOCOL)); dcb->session = session; + atomic_add(&dcb->session->refcount, 1); + if ((dcb->fd = dcb->func.connect(dcb, server, session)) == -1) { dcb_final_free(dcb); @@ -646,6 +649,8 @@ dcb_close(DCB *dcb) pthread_self()); } } + } + if (dcb->session) { session_free(dcb->session); skygw_log_write_flush( LOGFILE_TRACE, diff --git a/server/core/session.c b/server/core/session.c index cb72ea0bd..ce0b77782 100644 --- a/server/core/session.c +++ b/server/core/session.c @@ -22,8 +22,9 @@ * @verbatim * Revision History * - * Date Who Description - * 17/06/13 Mark Riddoch Initial implementation + * Date Who Description + * 17/06/13 Mark Riddoch Initial implementation + * 02/09/13 Massimiliano Pinto Added session refcounter * * @endverbatim */ @@ -75,6 +76,9 @@ session_alloc(SERVICE *service, DCB *client) strerror(eno)); return NULL; } + + session->refcount = 0; + session->ses_chk_top = CHK_NUM_SESSION; session->ses_chk_tail = CHK_NUM_SESSION; spinlock_init(&session->ses_lock); @@ -149,8 +153,12 @@ SESSION *ptr; } spinlock_release(&session_spin); atomic_add(&session->service->stats.n_current, -1); + /* Clean up session and free the memory */ - free(session); + if (atomic_add(&session->refcount, -1) == 1) + { + free(session); + } } /** diff --git a/server/include/session.h b/server/include/session.h index e0de9a303..df25f8dd8 100644 --- a/server/include/session.h +++ b/server/include/session.h @@ -29,7 +29,9 @@ * 14-06-2013 Massimiliano Pinto Added void *data to session * for session specific data * 01-07-2013 Massimiliano Pinto Removed backends pointer - from struct session + * from struct session + * 02-09-2013 Massimiliano Pinto Added session ref counter + * * @endverbatim */ #include @@ -81,6 +83,7 @@ typedef struct session { struct service *service; /**< The service this session is using */ struct session *next; /**< Linked list of all sessions */ skygw_chk_t ses_chk_tail; + int refcount; /**< Reference count on the session */ } SESSION; #define SESSION_PROTOCOL(x, type) DCB_PROTOCOL((x)->client, type) diff --git a/server/modules/protocol/mysql_client.c b/server/modules/protocol/mysql_client.c index e123e0cf8..d2ccb0a8f 100644 --- a/server/modules/protocol/mysql_client.c +++ b/server/modules/protocol/mysql_client.c @@ -27,6 +27,7 @@ * 14/06/2013 Mark Riddoch Initial version * 17/06/2013 Massimiliano Pinto Added Client To Gateway routines * 24/06/2013 Massimiliano Pinto Added: fetch passwords from service users' hashtable + * 02/09/2013 Massimiliano Pinto Added: session refcount */ #include #include @@ -587,6 +588,7 @@ int gw_read_client_event(DCB* dcb) { //write to client mysql AUTH_OK packet, packet n. is 2 // start a new session, and connect to backends session = session_alloc(dcb->service, dcb); + atomic_add(&dcb->session->refcount, 1); CHK_SESSION(session); ss_dassert(session->state != SESSION_STATE_ALLOC); protocol->state = MYSQL_IDLE;