--------------------- PatchSet 4042 Date: 2007/02/14 05:26:43 Author: rousskov Branch: squid3-icap Tag: (none) Log: - Deleted MsgPipe and related classes. Message pipes had two purposes: coordinate HTTP message adaptation (start, get the adapted headers, abort) and exchange HTTP message bodies. The latter is now done via BodyPipe API. The former can be implemented directly in ICAPModXact. Deleted ICAPClient* and related classes as (my) design failure. The original idea behind message pipes and ICAPClient* classes was to isolate ICAP code from the Squid core. The core code was supposed to use ICAPClient* classes for all ICAP-related needs, and ICAPClient* classes were supposed to translate core needs into "ICAP needs" and use message pipes to communicate with asynchronously running ICAP transactions. The latter part worked fine, but the former did not. The core code still did a lot of ICAP-specific work on its own. This could be because ICAP processing affects the flow so much or because the core code had not been refactored enough to minimize ICAP interactions. Whatever the reason, we ended up with a lot of complex code/logic coordinating the core code and ICAPClient* classes. While ICAPClient* classes were "translating", they could not hide the key actions or events (such as message body exchange or transaction aborts) from the core. The core code still had to support those actions or handle those events. Thus, every major action or event was handled twice: once in the core side code and once in a ICAPClient* class. Removing ICAPClient* "translation" step simplified the code and possibly improved performance. As for the "ICAP separation" goal, the current exposure to the ICAPModXact class can be hidden by a generic "Message Adaptation Transaction" class if we need to support more adaptation protocols. The core code should not be affected much by such a change. Members: src/ICAP/ICAPClientReqmodPrecache.cc:1.1.2.6->1.1.2.7(DEAD) src/ICAP/ICAPClientReqmodPrecache.h:1.1.2.3->1.1.2.4(DEAD) src/ICAP/ICAPClientRespmodPrecache.cc:1.1.2.6->1.1.2.7(DEAD) src/ICAP/ICAPClientRespmodPrecache.h:1.1.2.3->1.1.2.4(DEAD) src/ICAP/ICAPClientVector.cc:1.1.2.3->1.1.2.4(DEAD) src/ICAP/ICAPClientVector.h:1.1.2.2->1.1.2.3(DEAD) src/ICAP/MsgPipe.cc:1.1.2.4->1.1.2.5(DEAD) src/ICAP/MsgPipe.h:1.1.2.2->1.1.2.3(DEAD) src/ICAP/MsgPipeData.h:1.1.2.3->1.1.2.4(DEAD) src/ICAP/MsgPipeEnd.h:1.1.2.1->1.1.2.2(DEAD) src/ICAP/MsgPipeSink.h:1.1.2.1->1.1.2.2(DEAD) src/ICAP/MsgPipeSource.h:1.1.2.2->1.1.2.3(DEAD) --- squid3/src/ICAP/ICAPClientReqmodPrecache.cc Wed Feb 14 13:38:37 2007 +++ /dev/null Wed Feb 14 13:37:19 2007 @@ -1,178 +0,0 @@ -#include "squid.h" -#include "client_side_request.h" -#include "ClientRequestContext.h" -#include "MsgPipeData.h" -#include "HttpRequest.h" -#include "ICAPClientReqmodPrecache.h" -#include "ICAPServiceRep.h" -#include "ICAPClient.h" - -CBDATA_CLASS_INIT(ICAPClientReqmodPrecache); - -ICAPClientReqmodPrecache::ICAPClientReqmodPrecache(ICAPServiceRep::Pointer aService): - ICAPClientVector(aService, "ICAPClientReqmodPrecache"), http(NULL) -{ -} - -void ICAPClientReqmodPrecache::startReqMod(ClientHttpRequest *aHttp, HttpRequest *request) -{ - http = cbdataReference(aHttp); - startMod(http, NULL, request); -} - -void ICAPClientReqmodPrecache::tellSpaceAvailable() { - http->icapSpaceAvailable(); -} - -// ICAP client starts sending adapted response -// ICAP client has received new HTTP headers (if any) at this point -void ICAPClientReqmodPrecache::noteSourceStart(MsgPipe *p) -{ - debug(93,3)("ICAPClientReqmodPrecache::noteSourceStart() called\n"); - /* - * If adapted->data->header is NULL then the ICAP response did - * not have a req/res-hdr section. Send the NULL pointer to - * tell the other side to use the original request/response - * headers. - */ - HttpRequest *req = dynamic_cast(adapted->data->header); - - if (req && req->content_length > 0) { - assert(req->body_reader == NULL); - req->body_reader = new BodyReader(req->content_length, readBody, abortBody, kickBody, this); - } - - http->takeAdaptedHeaders(adapted->data->header); - noteSourceProgress(p); -} - -/* - * This is where we receive a notification from the other - * side of the MsgPipe that new adapted data is available. - * We, in turn, tell whoever is reading from the request's - * body_reader about the new data. - */ -void ICAPClientReqmodPrecache::noteSourceProgress(MsgPipe *p) -{ - debug(93,3)("ICAPClientReqmodPrecache::noteSourceProgress() called\n"); - //tell ClientHttpRequest to store a fresh portion of the adapted response - - if (p->data->body->hasContent()) { - /* - * NOTE: req will be NULL if this is a "request satisfaction" - * ICAP reply. In other words, the ICAP REQMOD reply may - * contain an HTTP response, in which case we'll have a body, but - * adapted->data->header will be an HttpReply, not an HttpRequest. - */ - HttpRequest *req = dynamic_cast(adapted->data->header); - - if (req) { - debugs(93,3,HERE << "notifying body_reader, contentSize() = " << p->data->body->contentSize()); - req->body_reader->notify(p->data->body->contentSize()); - } else { - http->takeAdaptedBody(adapted->data->body); - } - } -} - -void ICAPClientReqmodPrecache::tellDoneAdapting() -{ - debug(93,3)("ICAPClientReqmodPrecache::tellDoneAdapting() called\n"); - // tell ClientHttpRequest that we wil not call it any more - http->doneAdapting(); // deletes us (XXX: currently cannot: see below) - // We do not stop() here because our BodyReader may still need us. - // We need to revise our lifetime management to reflect BodyReader needs. -} - -void ICAPClientReqmodPrecache::tellAbortAdapting() -{ - debug(93,3)("ICAPClientReqmodPrecache::tellAbortAdapting() called\n"); - // tell ClientHttpRequest that we are aborting ICAP processing prematurely - http->abortAdapting(); -} - -// internal cleanup -void ICAPClientReqmodPrecache::stop(Notify notify) -{ -#ifdef DONT_FREE_ADAPTED - /* - * NOTE: We tell clean to ignore the "adapted" pipe because it may - * have an HTTP message body that needs to stay around a little - * while longer so that the HTTP server-side can forward it on. - */ - - // XXX: who will clean up the "adapted->sink" then? Does it happen - // when the owner deletes us? Is that why we are deleted when the - // owner is destroyed and not when ICAP adaptation is done, like - // in http.cc case? - - // XXX: "adapted->sink" does not really have an "HTTP message body", - // In fact, it simply points to "this". Should the above comment - // refer to adapted and adapted->data->body? - - ICAPClientVector::clean(notify, false); -#else - ICAPClientVector::stop(notify); -#endif -} - -/* - * Something that needs to read the adapated request body - * calls this function, via the BodyReader class. We copy - * the body data from our bodybuf object to the BodyReader - * MemBuf, which was passed as a reference to this function. - */ -size_t -ICAPClientReqmodPrecache::readBody(void *data, MemBuf &mb, size_t size) -{ - ICAPClientReqmodPrecache *icap = static_cast(data); - debugs(93,3,HERE << icap << " readBody requested size " << size); - assert(icap != NULL); - assert(icap->adapted != NULL); - assert(icap->adapted->data != NULL); - MemBuf *bodybuf = icap->adapted->data->body; - assert(bodybuf != NULL); - debugs(93,3,HERE << "readBody bodybuf size " << bodybuf->contentSize()); - - if ((mb_size_t) size > bodybuf->contentSize()) - size = bodybuf->contentSize(); - - debugs(93,3,HERE << "readBody actual size " << size); - - assert(size); - - mb.append(bodybuf->content(), size); - - bodybuf->consume(size); - - return size; -} - -void -ICAPClientReqmodPrecache::abortBody(void *data, size_t remaining) -{ - if (remaining >= 0) { - debugs(93,1,HERE << "ICAPClientReqmodPrecache::abortBody size " << remaining); - // more? - } - - ICAPClientReqmodPrecache *icap = static_cast(data); - icap->stop(notifyIcap); - // XXX: Should probably notify the owner as well: - // It was not the owner who called abortBody, so the owner probably - // does not know what has happened. The owner calls ownerAbort() when - // it knows. -} - -/* - * Restart reading the adapted response from the ICAP server in case - * the body buffer became full and we stopped reading. - */ -void -ICAPClientReqmodPrecache::kickBody(void *data) -{ - debugs(93,3,HERE << "ICAPClientReqmodPrecache::kickBody"); - ICAPClientReqmodPrecache *icap = static_cast(data); - assert(icap->adapted != NULL); - icap->adapted->sendSinkNeed(); -} --- squid3/src/ICAP/ICAPClientReqmodPrecache.h Wed Feb 14 13:38:37 2007 +++ /dev/null Wed Feb 14 13:37:19 2007 @@ -1,84 +0,0 @@ - -/* - * $Id: ICAPClientReqmodPrecache.h,v 1.1.2.3 2006/10/06 16:43:03 rousskov Exp $ - * - * - * SQUID Web Proxy Cache http://www.squid-cache.org/ - * ---------------------------------------------------------- - * - * Squid is the result of efforts by numerous individuals from - * the Internet community; see the CONTRIBUTORS file for full - * details. Many organizations have provided support for Squid's - * development; see the SPONSORS file for full details. Squid is - * Copyrighted (C) 2001 by the Regents of the University of - * California; see the COPYRIGHT file for full details. Squid - * incorporates software developed and/or copyrighted by other - * sources; see the CREDITS file for full details. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA. - * - */ - -#ifndef SQUID_ICAPCLIENTREQMODPRECACHE_H -#define SQUID_ICAPCLIENTREQMODPRECACHE_H - -#include "ICAPClientVector.h" - -/* - * ICAPClientReqmodPrecache implements the ICAP client-side pre-cache - * vectoring point using ICAPClientVector as a parent. - * ClientHttpRequest is the Owner of this vectoring point. - */ - -class ClientRequestContext; - -class ICAPClientReqmodPrecache: public ICAPClientVector -{ - -public: - ICAPClientReqmodPrecache(ICAPServiceRep::Pointer); - - // synchronous calls called by ClientHttpRequest - void startReqMod(ClientHttpRequest *, HttpRequest *); - - // pipe source methods; called by ICAP while receiving the virgin message - - - // pipe sink methods; called by ICAP while sending the adapted message - virtual void noteSourceStart(MsgPipe *p); - virtual void noteSourceProgress(MsgPipe *p); - -protected: - // used by ICAPClientVector because it does not know Owner type - virtual void tellSpaceAvailable(); - virtual void tellDoneAdapting(); - virtual void tellAbortAdapting(); - virtual void stop(Notify notify); - -public: - ClientHttpRequest *http; - BodyReader::Pointer body_reader; - -private: - // Hooks to BodyReader so HttpStateData can get the - // adapted request body - static BodyReadFunc readBody; - static BodyAbortFunc abortBody; - static BodyKickFunc kickBody; - - CBDATA_CLASS2(ICAPClientReqmodPrecache); -}; - -#endif /* SQUID_ICAPCLIENTSIDEHOOK_H */ --- squid3/src/ICAP/ICAPClientRespmodPrecache.cc Wed Feb 14 13:38:37 2007 +++ /dev/null Wed Feb 14 13:37:19 2007 @@ -1,93 +0,0 @@ -#include "squid.h" -#include "http.h" -#include "MsgPipeData.h" -#include "HttpRequest.h" -#include "HttpReply.h" -#include "ICAPClientRespmodPrecache.h" -#include "ICAPClient.h" -#include "ICAPServiceRep.h" - -CBDATA_CLASS_INIT(ICAPClientRespmodPrecache); - -ICAPClientRespmodPrecache::ICAPClientRespmodPrecache(ICAPServiceRep::Pointer aService): - ICAPClientVector(aService, "ICAPClientRespmodPrecache"), serverState(NULL) -{ -} - -void ICAPClientRespmodPrecache::startRespMod(ServerStateData *aServerState, HttpRequest *request, HttpReply *reply) -{ - serverState = cbdataReference(aServerState); - startMod(serverState, request, reply); -} - -// ICAP client starts sending adapted response -// ICAP client has received new HTTP headers (if any) at this point -void ICAPClientRespmodPrecache::noteSourceStart(MsgPipe *p) -{ - debugs(93,3, HERE << "ICAPClientRespmodPrecache::noteSourceStart() called"); - - HttpReply *reply = dynamic_cast(adapted->data->header); - /* - * The ICAP reply MUST have a new HTTP reply header, or else - * it is an invalid ICAP message. Invalid ICAP messages should - * be handled prior to this point. - */ - assert(reply); // check that ICAP xaction created the right object - assert(reply == adapted->data->header); - - /* - * Examine the HTTP reply headers to find out if there is an associated - * body. We should probably check the ICAP Encapsulated header values - * as well. - */ - ssize_t dummy; - bool expect_body = reply->expectingBody(virgin->data->cause->method, dummy); - - if (!serverState->takeAdaptedHeaders(reply)) // deletes us - return; - - if (expect_body) - noteSourceProgress(p); - else - noteSourceFinish(p); -} - -// ICAP client sends more data -void ICAPClientRespmodPrecache::noteSourceProgress(MsgPipe *p) -{ - debug(93,3)("ICAPClientRespmodPrecache::noteSourceProgress() called\n"); - //tell ServerStateData to store a fresh portion of the adapted response - - assert(serverState); - - if (p->data->body->hasContent()) { - if (!serverState->takeAdaptedBody(p->data->body)) - return; - - // HttpStateData::takeAdaptedBody does not detect when we have enough, - // so we always notify source that there more buffer space is available - if (p->data->body->hasPotentialSpace()) - adapted->sendSinkNeed(); - } -} - -void -ICAPClientRespmodPrecache::tellSpaceAvailable() -{ - serverState->icapSpaceAvailable(); -} - -void -ICAPClientRespmodPrecache::tellDoneAdapting() -{ - serverState->finishAdapting(); // deletes us -} - -void -ICAPClientRespmodPrecache::tellAbortAdapting() -{ - debug(93,3)("ICAPClientReqmodPrecache::tellAbortAdapting() called\n"); - // tell ClientHttpRequest that we are aborting ICAP processing prematurely - serverState->abortAdapting(); // deletes us -} - --- squid3/src/ICAP/ICAPClientRespmodPrecache.h Wed Feb 14 13:38:37 2007 +++ /dev/null Wed Feb 14 13:37:19 2007 @@ -1,74 +0,0 @@ - -/* - * $Id: ICAPClientRespmodPrecache.h,v 1.1.2.3 2006/10/06 16:43:03 rousskov Exp $ - * - * - * SQUID Web Proxy Cache http://www.squid-cache.org/ - * ---------------------------------------------------------- - * - * Squid is the result of efforts by numerous individuals from - * the Internet community; see the CONTRIBUTORS file for full - * details. Many organizations have provided support for Squid's - * development; see the SPONSORS file for full details. Squid is - * Copyrighted (C) 2001 by the Regents of the University of - * California; see the COPYRIGHT file for full details. Squid - * incorporates software developed and/or copyrighted by other - * sources; see the CREDITS file for full details. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA. - * - */ - -#ifndef SQUID_ICAPCLIENTRESPMODPRECACHE_H -#define SQUID_ICAPCLIENTRESPMODPRECACHE_H - -#include "ICAPClientVector.h" - -/* - * ICAPClientRespmodPrecache implements the server-side pre-cache ICAP - * vectoring point using ICAPClientVector as a parent. - * ServerStateData is the Owner of this vectoring point. - */ - -class ServerStateData; - -class ICAPClientRespmodPrecache: public ICAPClientVector -{ - -public: - ICAPClientRespmodPrecache(ICAPServiceRep::Pointer); - - // synchronous calls called by ServerStateData - void startRespMod(ServerStateData *anServerState, HttpRequest *request, HttpReply *reply); - - // pipe source methods; called by ICAP while receiving the virgin message - - // pipe sink methods; called by ICAP while sending the adapted message - virtual void noteSourceStart(MsgPipe *p); - virtual void noteSourceProgress(MsgPipe *p); - -protected: - virtual void tellSpaceAvailable(); - virtual void tellDoneAdapting(); // deletes us - virtual void tellAbortAdapting(); // deletes us - -public: - ServerStateData *serverState; - -private: - CBDATA_CLASS2(ICAPClientRespmodPrecache); -}; - -#endif /* SQUID_ICAPCLIENTRESPMODPRECACHE_H */ --- squid3/src/ICAP/ICAPClientVector.cc Wed Feb 14 13:38:37 2007 +++ /dev/null Wed Feb 14 13:37:19 2007 @@ -1,172 +0,0 @@ -#include "squid.h" -#include "MsgPipe.h" -#include "MsgPipeData.h" -#include "MsgPipeSource.h" -#include "MsgPipeSink.h" -#include "HttpRequest.h" -#include "ICAPClientVector.h" -#include "ICAPClient.h" - -ICAPClientVector::ICAPClientVector(ICAPServiceRep::Pointer aService, const char *aPoint): - theOwner(0), vPoint(aPoint), - service(aService), virgin(NULL), adapted(NULL) -{ - debug(93,3)("%s constructed, this=%p\n", vPoint, this); -} - -ICAPClientVector::~ICAPClientVector() -{ - stop(notifyNone); - debug(93,3)("%s destructed, this=%p\n", vPoint, this); -} - -void ICAPClientVector::startMod(void *anOwner, HttpRequest *cause, HttpMsg *header) -{ - debug(93,5)("%s starting, this=%p\n", vPoint, this); - - theOwner = anOwner; - - virgin = new MsgPipe("virgin"); // this is the place to create a refcount ptr - virgin->source = this; - virgin->data = new MsgPipeData; - virgin->data->setCause(cause); - virgin->data->setHeader(header); - virgin->data->body = new MemBuf; - virgin->data->body->init(ICAP::MsgPipeBufSizeMin, ICAP::MsgPipeBufSizeMax); - - adapted = new MsgPipe("adapted"); - adapted->sink = this; - -#if ICAP_ANCHOR_LOOPBACK - adapted->data = new MsgPipeData; - adapted->data->setCause(request); // should not hurt -#else - ICAPInitXaction(service, virgin, adapted); -#endif - - virgin->sendSourceStart(); // we may have virgin data to provide - adapted->sendSinkNeed(); // we want adapted response, eventially -} - -void ICAPClientVector::sendMoreData(StoreIOBuffer buf) -{ - debug(93,7)("%s::sendMoreData(%p)\n", vPoint, this); - //debugs(93,0,HERE << "appending " << buf.length << " bytes"); - //debugs(93,0,HERE << "body.contentSize = " << virgin->data->body->contentSize()); - //buf.dump(); - /* - * The caller is responsible for not giving us more data - * than will fit in body MemBuf. Caller should use - * potentialSpaceSize() to find out how much we can hold. - */ - virgin->data->body->append(buf.data, buf.length); - virgin->sendSourceProgress(); -} - -int -ICAPClientVector::potentialSpaceSize() -{ - if (virgin == NULL) - return 0; - - return (int) virgin->data->body->potentialSpaceSize(); -} - -// Owner says we have the entire HTTP message -void ICAPClientVector::doneSending() -{ - debug(93,3)("%s::doneSending(%p)\n", vPoint, this); - -#if ICAP_ANCHOR_LOOPBACK - /* simple assignments are not the right way to do this */ - adapted->data->setHeader(virgin->data->header); - adapted->data->body = virgin->data->body; - noteSourceFinish(adapted); - // checkDoneAdapting() does not support loopback mode - return; -#else - virgin->sendSourceFinish(); - checkDoneAdapting(); // may call the owner back, unfortunately -#endif -} - -// Owner tells us to abort -void ICAPClientVector::ownerAbort() -{ - debug(93,3)("%s::ownerAbort(%p)\n", vPoint, this); - stop(notifyIcap); -} - -// ICAP client needs more virgin response data -void ICAPClientVector::noteSinkNeed(MsgPipe *p) -{ - debug(93,3)("%s::noteSinkNeed(%p)\n", vPoint, this); - - if (virgin->data->body->potentialSpaceSize()) - tellSpaceAvailable(); -} - -// ICAP client aborting -void ICAPClientVector::noteSinkAbort(MsgPipe *p) -{ - debug(93,3)("%s::noteSinkAbort(%p)\n", vPoint, this); - stop(notifyOwner); // deletes us -} - -// ICAP client is done sending adapted response -void ICAPClientVector::noteSourceFinish(MsgPipe *p) -{ - debug(93,3)("%s::noteSourceFinish(%p)\n", vPoint, this); - checkDoneAdapting(); // may delete us -} - -void ICAPClientVector::checkDoneAdapting() { - debug(93,5)("%s::checkDoneAdapting(%p): %d & %d\n", vPoint, this, - (int)!virgin->source, (int)!adapted->source); - // done if we are not sending and are not receiving - if (!virgin->source && !adapted->source) - tellDoneAdapting(); // deletes us -} - -// ICAP client is aborting -void ICAPClientVector::noteSourceAbort(MsgPipe *p) -{ - debug(93,3)("%s::noteSourceAbort(%p)\n", vPoint, this); - stop(notifyOwner); // deletes us -} - -void ICAPClientVector::stop(Notify notify) -{ - debug(93,3)("%s::stop(%p, %d)\n", vPoint, this, (int)notify); - clean(notify, true); -} - -void ICAPClientVector::clean(Notify notify, bool cleanAdapted) -{ - if (virgin != NULL) { - if (notify == notifyIcap) - virgin->sendSourceAbort(); - else - virgin->source = NULL; - virgin = NULL; // refcounted - } - - if (cleanAdapted && adapted != NULL) { - if (notify == notifyIcap) - adapted->sendSinkAbort(); - else - adapted->sink = NULL; - adapted = NULL; // refcounted - } - - service = NULL; - - if (theOwner) { - if (notify == notifyOwner) - tellAbortAdapting(); // deletes us - else - cbdataReferenceDone(theOwner); - } - - // not safe to do anything here because we may have been deleted. -} --- squid3/src/ICAP/ICAPClientVector.h Wed Feb 14 13:38:37 2007 +++ /dev/null Wed Feb 14 13:37:19 2007 @@ -1,101 +0,0 @@ - -/* - * $Id: ICAPClientVector.h,v 1.1.2.2 2006/10/07 05:14:53 rousskov Exp $ - * - * - * SQUID Web Proxy Cache http://www.squid-cache.org/ - * ---------------------------------------------------------- - * - * Squid is the result of efforts by numerous individuals from - * the Internet community; see the CONTRIBUTORS file for full - * details. Many organizations have provided support for Squid's - * development; see the SPONSORS file for full details. Squid is - * Copyrighted (C) 2001 by the Regents of the University of - * California; see the COPYRIGHT file for full details. Squid - * incorporates software developed and/or copyrighted by other - * sources; see the CREDITS file for full details. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA. - * - */ - -#ifndef SQUID_ICAPVECTOR_H -#define SQUID_ICAPVECTOR_H - -#include "MsgPipe.h" -#include "MsgPipeSource.h" -#include "MsgPipeSink.h" -#include "ICAPServiceRep.h" - -/* - * The ICAP Vector helps its Owner to talk to the ICAP transaction, which - * implements asynchronous communication with the ICAP server. The Owner - * is either the HTTP client side (ClientHttpRequest) or the HTTP server - * side (ServerStateData). The Vector marshals the incoming/virgin HTTP - * message to the ICAP transaction, via the MsgPipe interface. The same - * interface is used to get the adapted HTTP message back. - * - * ICAPClientReqmodPrecache and ICAPClientRespmodPrecache classes use - * ICAPVector as a base and cover specifics of their vectoring point. - */ - -class ICAPClientVector: public MsgPipeSource, public MsgPipeSink -{ - -public: - ICAPClientVector(ICAPServiceRep::Pointer, const char *aPoint); - virtual ~ICAPClientVector(); - - // synchronous calls called by Owner - void sendMoreData(StoreIOBuffer buf); - void doneSending(); - void ownerAbort(); - int potentialSpaceSize(); /* how much data can we accept? */ - - // pipe source methods; called by ICAP while receiving the virgin message - virtual void noteSinkNeed(MsgPipe *p); - virtual void noteSinkAbort(MsgPipe *p); - - // pipe sink methods; called by ICAP while sending the adapted message - virtual void noteSourceStart(MsgPipe *p) = 0; - virtual void noteSourceProgress(MsgPipe *p) = 0; - virtual void noteSourceFinish(MsgPipe *p); - virtual void noteSourceAbort(MsgPipe *p); - -protected: - typedef enum { notifyNone, notifyOwner, notifyIcap } Notify; - - // implemented by kids because we do not have a common Owner parent - virtual void tellSpaceAvailable() = 0; - virtual void tellDoneAdapting() = 0; // may delete us - virtual void tellAbortAdapting() = 0; // may delete us - virtual void stop(Notify notify); // may delete us - - void startMod(void *anOwner, HttpRequest *cause, HttpMsg *header); - void clean(Notify notify, bool cleanAdapted = true); - -private: - void checkDoneAdapting(); - -public: - void *theOwner; - const char *vPoint; // unmanaged vectoring point name for debugging - - ICAPServiceRep::Pointer service; - MsgPipe::Pointer virgin; - MsgPipe::Pointer adapted; -}; - -#endif /* SQUID_ICAPVECTOR_H */ --- squid3/src/ICAP/MsgPipe.cc Wed Feb 14 13:38:37 2007 +++ /dev/null Wed Feb 14 13:37:19 2007 @@ -1,99 +0,0 @@ -#include "squid.h" -#include "MsgPipe.h" -#include "MsgPipeSource.h" -#include "MsgPipeSink.h" -#include "MsgPipeData.h" - -CBDATA_CLASS_INIT(MsgPipe); - -// static event callback template -// XXX: refcounting needed to make sure destination still exists -#define MsgPipe_MAKE_CALLBACK(callName, destination) \ -static \ -void MsgPipe_send ## callName(void *p) { \ - MsgPipe *pipe = static_cast(p); \ - if (pipe && pipe->canSend(pipe->destination, #callName, false)) \ - pipe->destination->note##callName(pipe); \ -} - -// static event callbacks -MsgPipe_MAKE_CALLBACK(SourceStart, sink) -MsgPipe_MAKE_CALLBACK(SourceProgress, sink) -MsgPipe_MAKE_CALLBACK(SourceFinish, sink) -MsgPipe_MAKE_CALLBACK(SourceAbort, sink) -MsgPipe_MAKE_CALLBACK(SinkNeed, source) -MsgPipe_MAKE_CALLBACK(SinkAbort, source) - - -MsgPipe::MsgPipe(const char *aName): name(aName), - data(NULL), source(NULL), sink(NULL) -{} - -MsgPipe::~MsgPipe() -{ - delete data; - assert(source == NULL); - assert(sink == NULL); -}; - -void MsgPipe::sendSourceStart() -{ - debug(99,5)("MsgPipe::sendSourceStart() called\n"); - sendLater("SourceStart", &MsgPipe_sendSourceStart, sink); -} - - - -void MsgPipe::sendSourceProgress() -{ - debug(99,5)("MsgPipe::sendSourceProgress() called\n"); - sendLater("SourceProgress", &MsgPipe_sendSourceProgress, sink); -} - -void MsgPipe::sendSourceFinish() -{ - debug(99,5)("MsgPipe::sendSourceFinish() called\n"); - sendLater("sendSourceFinish", &MsgPipe_sendSourceFinish, sink); - source = NULL; -} - -void MsgPipe::sendSourceAbort() -{ - debug(99,5)("MsgPipe::sendSourceAbort() called\n"); - sendLater("SourceAbort", &MsgPipe_sendSourceAbort, sink); - source = NULL; -} - - -void MsgPipe::sendSinkNeed() -{ - debug(99,5)("MsgPipe::sendSinkNeed() called\n"); - sendLater("SinkNeed", &MsgPipe_sendSinkNeed, source); -} - -void MsgPipe::sendSinkAbort() -{ - debug(99,5)("MsgPipe::sendSinkAbort() called\n"); - sendLater("SinkAbort", &MsgPipe_sendSinkAbort, source); - sink = NULL; -} - -void MsgPipe::sendLater(const char *callName, EVH * handler, MsgPipeEnd *destination) -{ - if (canSend(destination, callName, true)) - eventAdd(callName, handler, this, 0.0, 0, true); -} - -bool MsgPipe::canSend(MsgPipeEnd *destination, const char *callName, bool future) -{ - const bool res = destination != NULL; - const char *verb = future ? - (res ? "will send " : "wont send ") : - (res ? "sends " : "ignores "); - debugs(93,5, "MsgPipe " << name << "(" << this << ") " << - verb << callName << " to the " << - (destination ? destination->kind() : "destination") << "(" << - destination << "); " << - "data: " << data << "; source: " << source << "; sink " << sink); - return res; -} --- squid3/src/ICAP/MsgPipe.h Wed Feb 14 13:38:37 2007 +++ /dev/null Wed Feb 14 13:37:19 2007 @@ -1,89 +0,0 @@ - -/* - * $Id: MsgPipe.h,v 1.1.2.2 2006/09/29 23:27:15 dwsquid Exp $ - * - * - * SQUID Web Proxy Cache http://www.squid-cache.org/ - * ---------------------------------------------------------- - * - * Squid is the result of efforts by numerous individuals from - * the Internet community; see the CONTRIBUTORS file for full - * details. Many organizations have provided support for Squid's - * development; see the SPONSORS file for full details. Squid is - * Copyrighted (C) 2001 by the Regents of the University of - * California; see the COPYRIGHT file for full details. Squid - * incorporates software developed and/or copyrighted by other - * sources; see the CREDITS file for full details. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA. - * - */ - -#ifndef SQUID_MSGPIPE_H -#define SQUID_MSGPIPE_H - -#include "cbdata.h" -#include "event.h" - -// MsgPipe is a unidirectional communication channel for asynchronously -// transmitting potentially large messages. It aggregates the message -// being piped and pointers to the message sender and recepient. -// MsgPipe also provides convenience wrappers for asynchronous calls to -// recepient's and sender's note*() methods. - -class MsgPipeData; - -class MsgPipeEnd; - -class MsgPipeSource; - -class MsgPipeSink; - -class MsgPipe : public RefCountable -{ - -public: - typedef RefCount Pointer; - - MsgPipe(const char *aName = "anonym"); - ~MsgPipe(); - - // the pipe source calls these to notify the sink - void sendSourceStart(); - void sendSourceProgress(); - void sendSourceFinish(); - void sendSourceAbort(); - - // the pipe sink calls these to notify the source - void sendSinkNeed(); - void sendSinkAbort(); - - // private method exposed for the event handler only - bool canSend(MsgPipeEnd *destination, const char *callName, bool future); - -public: - const char *name; // unmanaged pointer used for debugging only - - MsgPipeData *data; - MsgPipeSource *source; - MsgPipeSink *sink; - -private: - void sendLater(const char *callName, EVH * handler, MsgPipeEnd *destination); - - CBDATA_CLASS2(MsgPipe); -}; - -#endif /* SQUID_MSGPIPE_H */ --- squid3/src/ICAP/MsgPipeData.h Wed Feb 14 13:38:37 2007 +++ /dev/null Wed Feb 14 13:37:19 2007 @@ -1,95 +0,0 @@ - -/* - * $Id: MsgPipeData.h,v 1.1.2.3 2006/10/06 17:05:03 rousskov Exp $ - * - * - * SQUID Web Proxy Cache http://www.squid-cache.org/ - * ---------------------------------------------------------- - * - * Squid is the result of efforts by numerous individuals from - * the Internet community; see the CONTRIBUTORS file for full - * details. Many organizations have provided support for Squid's - * development; see the SPONSORS file for full details. Squid is - * Copyrighted (C) 2001 by the Regents of the University of - * California; see the COPYRIGHT file for full details. Squid - * incorporates software developed and/or copyrighted by other - * sources; see the CREDITS file for full details. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA. - * - */ - -#ifndef SQUID_MSGPIPEDATA_H -#define SQUID_MSGPIPEDATA_H - -#include "HttpMsg.h" -#include "HttpRequest.h" -#include "HttpReply.h" -#include "MemBuf.h" - -// MsgPipeData contains information about the HTTP message being sent -// from the pipe source to the sink. Since the entire message body may be -// large, only partial information about the body is kept. For HTTP -// responses, request header information is also available as metadata. - -class HttpRequest; - -class MsgPipeData -{ - -public: - MsgPipeData(): header(0), body(0), cause(0) {} - - ~MsgPipeData() - { - HTTPMSGUNLOCK(cause); - HTTPMSGUNLOCK(header); - - if (body) { - body->clean(); - delete body; - } - } - - void setCause(HttpRequest *r) - { - if (r) { - HTTPMSGUNLOCK(cause); - cause = HTTPMSGLOCK(r); - } else { - assert(!cause); - } - } - - void setHeader(HttpMsg *msg) - { - HTTPMSGUNLOCK(header); - header = HTTPMSGLOCK(msg); - } - -public: - typedef HttpMsg Header; - typedef MemBuf Body; - - // message being piped - Header *header; // parsed HTTP status/request line and headers - Body *body; // a buffer for decoded HTTP body piping - - // HTTP request header for piped responses (the cause of the response) - HttpRequest *cause; - -}; - -#endif /* SQUID_MSGPIPEDATA_H */ --- squid3/src/ICAP/MsgPipeEnd.h Wed Feb 14 13:38:37 2007 +++ /dev/null Wed Feb 14 13:37:19 2007 @@ -1,50 +0,0 @@ - -/* - * $Id: MsgPipeEnd.h,v 1.1.2.1 2005/11/21 21:05:51 dwsquid Exp $ - * - * - * SQUID Web Proxy Cache http://www.squid-cache.org/ - * ---------------------------------------------------------- - * - * Squid is the result of efforts by numerous individuals from - * the Internet community; see the CONTRIBUTORS file for full - * details. Many organizations have provided support for Squid's - * development; see the SPONSORS file for full details. Squid is - * Copyrighted (C) 2001 by the Regents of the University of - * California; see the COPYRIGHT file for full details. Squid - * incorporates software developed and/or copyrighted by other - * sources; see the CREDITS file for full details. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA. - * - */ - -#ifndef SQUID_MSGPIPEEND_H -#define SQUID_MSGPIPEEND_H - -// MsgPipeEnd is a common part of the MsgPipeSource and MsgPipeSink interfaces. -// Mesage pipe ends must be refcounted so that the recepient does not disappear -// while a message is being [asynchoronously] delivered to it. - -class MsgPipeEnd: public RefCountable -{ - -public: - virtual ~MsgPipeEnd() {} - - virtual const char *kind() const = 0; // "sink" or "source", for debugging -}; - -#endif /* SQUID_MSGPIPEEND_H */ --- squid3/src/ICAP/MsgPipeSink.h Wed Feb 14 13:38:37 2007 +++ /dev/null Wed Feb 14 13:37:19 2007 @@ -1,56 +0,0 @@ - -/* - * $Id: MsgPipeSink.h,v 1.1.2.1 2005/11/21 21:05:51 dwsquid Exp $ - * - * - * SQUID Web Proxy Cache http://www.squid-cache.org/ - * ---------------------------------------------------------- - * - * Squid is the result of efforts by numerous individuals from - * the Internet community; see the CONTRIBUTORS file for full - * details. Many organizations have provided support for Squid's - * development; see the SPONSORS file for full details. Squid is - * Copyrighted (C) 2001 by the Regents of the University of - * California; see the COPYRIGHT file for full details. Squid - * incorporates software developed and/or copyrighted by other - * sources; see the CREDITS file for full details. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA. - * - */ - -#ifndef SQUID_MSGPIPESINK_H -#define SQUID_MSGPIPESINK_H - -#include "MsgPipeEnd.h" - -// MsgPipeSink is an interface for the recepient of a given message -// over a given message pipe. Use MsgPipe to call sink methods. - -class MsgPipe; - -class MsgPipeSink: public MsgPipeEnd -{ - -public: - virtual void noteSourceStart(MsgPipe *p) = 0; - virtual void noteSourceProgress(MsgPipe *p) = 0; - virtual void noteSourceFinish(MsgPipe *p) = 0; - virtual void noteSourceAbort(MsgPipe *p) = 0; - - virtual const char *kind() const { return "sink"; } -}; - -#endif /* SQUID_MSGPIPESINK_H */ --- squid3/src/ICAP/MsgPipeSource.h Wed Feb 14 13:38:37 2007 +++ /dev/null Wed Feb 14 13:37:19 2007 @@ -1,54 +0,0 @@ - -/* - * $Id: MsgPipeSource.h,v 1.1.2.2 2006/09/29 23:27:15 dwsquid Exp $ - * - * - * SQUID Web Proxy Cache http://www.squid-cache.org/ - * ---------------------------------------------------------- - * - * Squid is the result of efforts by numerous individuals from - * the Internet community; see the CONTRIBUTORS file for full - * details. Many organizations have provided support for Squid's - * development; see the SPONSORS file for full details. Squid is - * Copyrighted (C) 2001 by the Regents of the University of - * California; see the COPYRIGHT file for full details. Squid - * incorporates software developed and/or copyrighted by other - * sources; see the CREDITS file for full details. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA. - * - */ - -#ifndef SQUID_MSGPIPESOURCE_H -#define SQUID_MSGPIPESOURCE_H - -#include "MsgPipeEnd.h" - -// MsgPipeSource is an interface for the sender of a given message -// over a given message pipe. Use MsgPipe to call source methods. - -class MsgPipe; - -class MsgPipeSource: public MsgPipeEnd -{ - -public: - virtual const char *kind() const { return "source"; } - - virtual void noteSinkNeed(MsgPipe *p) = 0; - virtual void noteSinkAbort(MsgPipe *p) = 0; -}; - -#endif /* SQUID_MSGPIPESOURCE_H */