From 2d9cd5848ca3f4205cc86435e08c75cc98c391bf Mon Sep 17 00:00:00 2001 From: Wilfried Goesgens Date: Sat, 2 Apr 2011 17:56:18 +0200 Subject: [PATCH] Give event clients a citadel session context. --- citadel/context.c | 55 +++++++++++++++++++++ citadel/context.h | 2 + citadel/event_client.c | 11 +++++ citadel/modules/smtp/serv_smtpeventclient.c | 9 ++-- 4 files changed, 74 insertions(+), 3 deletions(-) diff --git a/citadel/context.c b/citadel/context.c index ad4332160..dce6841c0 100644 --- a/citadel/context.c +++ b/citadel/context.c @@ -413,6 +413,61 @@ CitContext *CreateNewContext(void) { } +/* + * Initialize a new context and place it in the list. The session number + * used to be the PID (which is why it's called cs_pid), but that was when we + * had one process per session. Now we just assign them sequentially, starting + * at 1 (don't change it to 0 because masterCC uses 0). + */ +CitContext *CloneContext(CitContext *CloneMe) { + CitContext *me; + static int next_pid = 0; + + me = (CitContext *) malloc(sizeof(CitContext)); + if (me == NULL) { + CtdlLogPrintf(CTDL_ALERT, "citserver: can't allocate memory!!\n"); + return NULL; + } + memcpy(me, CloneMe, sizeof(CitContext)); + + memset(&me->RecvBuf, 0, sizeof(IOBuffer)); + memset(&me->SendBuf, 0, sizeof(IOBuffer)); + memset(&me->SBuf, 0, sizeof(IOBuffer)); + me->MigrateBuf = NULL; + me->sMigrateBuf = NULL; + me->redirect_buffer = NULL; +#ifdef HAVE_OPENSSL + me->ssl = NULL; +#endif + + me->download_fp = NULL; + me->upload_fp = NULL; + /// TODO: what about the room/user? + me->ma = NULL; + me->openid_data = NULL; + me->ldap_dn = NULL; + me->session_specific_data = NULL; + + me->MigrateBuf = NewStrBuf(); + me->RecvBuf.Buf = NewStrBuf(); + + begin_critical_section(S_SESSION_TABLE); + { + me->cs_pid = ++next_pid; + me->prev = NULL; + me->next = ContextList; + me->lastcmd = time(NULL); /* set lastcmd to now to prevent idle timer infanticide */ + ContextList = me; + if (me->next != NULL) { + me->next->prev = me; + } + ++num_sessions; + } + end_critical_section(S_SESSION_TABLE); + return (me); +} + + /* * Return an array containing a copy of the context list. * This allows worker threads to perform "for each context" operations without diff --git a/citadel/context.h b/citadel/context.h index 3c47c62c3..eb9b01d2c 100644 --- a/citadel/context.h +++ b/citadel/context.h @@ -158,6 +158,8 @@ void InitializeMasterCC(void); void dead_session_purge(int force); void set_async_waiting(struct CitContext *ccptr); +CitContext *CloneContext(CitContext *CloneMe); + /* forcibly close and flush fd's on shutdown */ void terminate_stuck_sessions(void); diff --git a/citadel/event_client.c b/citadel/event_client.c index 2902b3d91..08a9fc24b 100644 --- a/citadel/event_client.c +++ b/citadel/event_client.c @@ -145,6 +145,7 @@ void ShutDownCLient(AsyncIO *IO) IO->DNSChannel = NULL; } assert(IO->Terminate); + become_session(IO->CitContext); IO->Terminate(IO); } @@ -154,6 +155,8 @@ eReadState HandleInbound(AsyncIO *IO) { eReadState Finished = eBufferNotEmpty; + become_session(IO->CitContext); + while ((Finished == eBufferNotEmpty) && (IO->NextState == eReadMessage)){ if (IO->RecvBuf.nBlobBytesWanted != 0) { @@ -208,6 +211,7 @@ IO_send_callback(struct ev_loop *loop, ev_io *watcher, int revents) int rc; AsyncIO *IO = watcher->data; + become_session(IO->CitContext); rc = StrBuf_write_one_chunk_callback(watcher->fd, 0/*TODO*/, &IO->SendBuf); if (rc == 0) @@ -282,6 +286,7 @@ set_start_callback(struct ev_loop *loop, AsyncIO *IO, int revents) break; case eSendReply: case eSendMore: + become_session(IO->CitContext); IO_send_callback(loop, &IO->send_event, revents); break; case eTerminateConnection: @@ -297,6 +302,8 @@ IO_Timout_callback(struct ev_loop *loop, ev_timer *watcher, int revents) AsyncIO *IO = watcher->data; ev_timer_stop (event_base, &IO->rw_timeout); + become_session(IO->CitContext); + assert(IO->Timeout); IO->Timeout(IO); } @@ -307,6 +314,8 @@ IO_connfail_callback(struct ev_loop *loop, ev_timer *watcher, int revents) ev_timer_stop (event_base, &IO->conn_fail); ev_io_stop(loop, &IO->conn_event); + become_session(IO->CitContext); + assert(IO->ConnFail); IO->ConnFail(IO); } @@ -343,6 +352,7 @@ IO_postdns_callback(struct ev_loop *loop, ev_idle *watcher, int revents) { AsyncIO *IO = watcher->data; CtdlLogPrintf(CTDL_DEBUG, "event: %s\n", __FUNCTION__); + become_session(IO->CitContext); IO->DNSQuery->PostDNS(IO); } @@ -438,6 +448,7 @@ eNextState InitEventIO(AsyncIO *IO, int ReadFirst) { IO->Data = pData; + become_session(IO->CitContext); if (ReadFirst) { IO->NextState = eReadMessage; diff --git a/citadel/modules/smtp/serv_smtpeventclient.c b/citadel/modules/smtp/serv_smtpeventclient.c index 15a55e799..a2913bb9b 100644 --- a/citadel/modules/smtp/serv_smtpeventclient.c +++ b/citadel/modules/smtp/serv_smtpeventclient.c @@ -158,6 +158,8 @@ void FinalizeMessageSend(SmtpOutMsg *Msg) RemoveQItem(Msg->MyQItem); } + + RemoveContext(Msg->IO.CitContext); DeleteSmtpOutMsg(Msg); } @@ -450,9 +452,10 @@ void smtp_try_one_queue_entry(OneQueItem *MyQItem, else SendMsg->msgtext = NewStrBufDup(MsgText); if (smtp_resolve_recipients(SendMsg)) { - - - + CitContext *SubC; + SubC = CloneContext (CC); + SubC->session_specific_data = (char*) SendMsg; + SendMsg->IO.CitContext = SubC; if (SendMsg->pCurrRelay == NULL) QueueEventContext(&SendMsg->IO, -- 2.30.2