|void||clientStreamInit (dlink_list *list, CSR *func, CSD *rdetach, CSS *readstatus, ClientStreamData readdata, CSCB *callback, CSD *cdetach, ClientStreamData callbackdata, StoreIOBuffer tailBuffer)|
|void||clientStreamInsertHead (dlink_list *list, CSR *func, CSCB *callback, CSD *detach, CSS *status, ClientStreamData data)|
|void||clientStreamRead (clientStreamNode *thisObject, ClientHttpRequest *http, StoreIOBuffer readBuffer)|
|void||clientStreamDetach (clientStreamNode *thisObject, ClientHttpRequest *http)|
|void||clientStreamAbort (clientStreamNode *thisObject, ClientHttpRequest *http)|
|clientStream_status_t||clientStreamStatus (clientStreamNode *thisObject, ClientHttpRequest *http)|
- A client Stream is a uni directional pipe, with the usual non-blocking asynchronous approach present elsewhere in squid.
- Each pipe node has a data push function, and a data request function. This limits flexibility - the data flow is no longer assembled at each step.
- An alternative approach is to pass each node in the pipe the call- back to use on each IO call. This allows the callbacks to be changed very easily by a participating node, but requires more maintenance in each node (store the callback to the most recent IO request in the nodes context.) Such an approach also prevents dynamically changing the pipeline from outside without an additional interface method to extract the callback and context from the next node.
- One important characteristic of the stream is that the readfunc on the terminating node, and the callback on the first node will be NULL, and never used.
- Each node including the HEAD of the clientStream has a cbdataReference held by the stream. Freeing the stream then removes that reference and delete's every node. Any node with other References, and all nodes downstream will only free when those references are released. Stream nodes MAY hold references to the data member of the node.
- Specifically - on creation no reference is made. If you pass a data variable to a node, give it an initial reference. If the data member is non-null on FREE, cbdataFree WILL be called. This you must never call cbdataFree on your own context without explicitly setting the stream node data member to NULL and cbdataReferenceDone'ing it.
- No data member may hold a reference to it's stream node. The stream guarantees that DETACH will be called before freeing the node, allowing data members to cleanup.
- If a node's data holds a reference to something that needs to free the stream a circular reference list will occur. This results no data being freed until that reference is removed. One way to accomplish thisObject is to explicitly remove the data from your own node before freeing the stream.
TODO: rather than each node undeleting the next, have a clientStreamDelete that walks the list.
Abort the stream - detach every node in the pipeline.
thisObject ?? http ??
Referenced by ClientHttpRequest::freeResources().
Detach from the stream - only allowed for terminal members
thisObject ?? http ??
References assert, cbdataReference, cbdataReferenceDone, cbdataReferenceValid(), clientStreamNode::data, debugs, clientStreamNode::detach, RefCount< C >::getRaw(), dlink_node::next, clientStreamNode::node, NULL, clientStreamNode::prev(), and clientStreamNode::removeFromStream().
|void clientStreamInit||(||dlink_list *||list,|
Initialise a client Stream. list is the stream func is the read function for the head callback is the callback for the tail tailbuf and taillen are the initial buffer and length for the tail.
References callback, cbdataReference, clientStreamInsertHead(), dlink_node::data, dlinkAdd(), func, clientStreamNode::head, clientStreamNode::node, NULL, clientStreamNode::readBuffer, and dlink_list::tail.
Referenced by ConnStateData::abortRequestParsing(), ConnStateData::buildFakeRequest(), Downloader::buildRequest(), clientBeginRequest(), ConnStateData::parseHttpRequest(), and Ftp::Server::parseOneRequest().
|void clientStreamInsertHead||(||dlink_list *||list,|
Doesn't actually insert at head. Instead it inserts one after head. This is because HEAD is a special node, as is tail This function is not suitable for inserting the real HEAD.
References assert, callback, cbdataReference, data, dlink_node::data, debugs, dlinkAddAfter(), func, dlink_list::head, clientStreamNode::head, dlink_node::next, clientStreamNode::node, NULL, and clientStreamNode::readBuffer.
|void clientStreamRead||(||clientStreamNode *||thisObject,|
Call the previous node in the chain to read some data
thisObject ?? http ?? readBuffer ??
Referenced by constructHelperQuery(), ClientHttpRequest::doCallouts(), esiBufferRecipient(), esiProcessStream(), esiStreamRead(), Downloader::handleReply(), ClientRequestContext::hostHeaderVerifyFailed(), ClientHttpRequest::httpStart(), and Http::Stream::pullData().
|clientStream_status_t clientStreamStatus||(||clientStreamNode *||thisObject,|
Call the upstream node to find it's status
thisObject ?? http ??