public BeginRequestBody (Record record) { if (record.Type != RecordType.BeginRequest) throw new ArgumentException ( Strings.BeginRequestBody_WrongType, "record"); if (record.BodyLength != 8) throw new ArgumentException ( Strings.BeginRequestBody_WrongSize, "record"); byte[] body = record.Body; role = (Role)Record.ReadUInt16 (body, 0); flags = (BeginRequestFlags)body [2]; }
public void SendRecord (Record record) { lock (sendQueue) { sendQueue.Enqueue (record); } //if we already have no other processes, then start to send if (Interlocked.CompareExchange (ref sendProcessing, 1, 0) == 0) { StartSendPackets (); } }
public virtual bool Process (ulong listenerTag, int requestNumber, byte[] header, byte[] recordBody) { bool stopReceive = false; Record record = new Record (); record.Version = header [0]; record.Type = (RecordType)header [1]; record.RequestId = (ushort)((header [2] << 8) + header [3]); record.BodyLength = (ushort)((header [4] << 8) + header [5]); record.PaddingLength = header [6]; record.Body = recordBody; if (debugEnabled) { Logger.Write (LogLevel.Debug, "lt={0} LT::ProcessRecord0 header={1} reqId={2}", listenerTag, record.Type, (ushort)((header [2] << 8) + header [3])); } ulong hash = ((ulong)record.RequestId << 32) ^ listenerTag; TransportRequest request = GetRequest (hash); if (request == null && record.Type == RecordType.BeginRequest) { BeginRequestBody brb = new BeginRequestBody (recordBody); TransportRequest req = new TransportRequest (record.RequestId); req.Hash = ((ulong)record.RequestId << 32) ^ listenerTag; req.fd = (uint)listenerTag; req.KeepAlive = (brb.Flags & BeginRequestFlags.KeepAlive) == BeginRequestFlags.KeepAlive; AddRequest (req); //try to find single app route GetRoute (req, null, -1, null); if (IsHostFound(req)) { CreateRequest (req); } FastCgiNetworkConnector connector = FastCgiNetworkConnector.GetConnector (req.fd); if (connector != null) { connector.KeepAlive = req.KeepAlive; } return stopReceive; } if (request != null) { switch (record.Type) { case RecordType.BeginRequest: break; case RecordType.Params: if (header != null) { if (debugEnabled) { Logger.Write (LogLevel.Debug, "lt={0} LT::ProcessRecord header={1} reqId={2}", listenerTag, header [1], (ushort)((header [2] << 8) + header [3])); } } if (recordBody != null) { FcgiUtils.ParseParameters (recordBody, AddHeader, request); } else { //FIXME: request.Host can be null HeadersSent (request); } if (debugEnabled) { Logger.Write (LogLevel.Debug, "lt={0} LT::ProcessRecord header={1} reqId={2}", listenerTag, header [1], (ushort)((header [2] << 8) + header [3])); } break; case RecordType.StandardInput: //Ready to process if (debugEnabled) { Logger.Write (LogLevel.Debug, "lt={0} LT::ProcessRecord header={1} reqId={2}", listenerTag, header [1], (ushort)((header [2] << 8) + header [3])); } bool final = record.BodyLength == 0; AddBodyPart (request, recordBody, final); if (final) { stopReceive = true; Process (request); } break; case RecordType.Data: break; case RecordType.GetValues: //TODO: return server values break; // Aborts a request when the server aborts. //TODO: make Thread.Abort for request case RecordType.AbortRequest: //FIXME: send it to the HostTransport as is //TODO: send error to Connector //TODO: send EndRequest to Connector // SendError (request.RequestId, Strings.Connection_AbortRecordReceived); // EndRequest (request.RequestId, -1, ProtocolStatus.RequestComplete); break; default: //TODO: CgiConnector.SendRecord // SendRecord (new Record (Record.ProtocolVersion, // RecordType.UnknownType, // request.RequestId, // new UnknownTypeBody (record.Type).GetData ())); break; } } return stopReceive; }
/// <summary> /// Sends the record to web listener /// </summary> /// <returns><c>true</c>, if record was sent, <c>false</c> otherwise.</returns> /// <param name="header">Header.</param> /// <param name="body">Body.</param> /// <description>This function sends record to web listener in listener domain</description> private bool SendRecord (uint listenerTag, byte[] header,byte[] body) { //get connector by it's tag if (debugEnabled) { Logger.Write (LogLevel.Debug, "lt={0} SendRecord", listenerTag); } FastCgiNetworkConnector connector = FastCgiNetworkConnector.GetConnector (listenerTag); if (connector != null) { //TODO: optimize it Record record = new Record (); record.Version = header [0]; record.Type = (RecordType)header [1]; record.RequestId = (ushort)((header [2] << 8) + header [3]); record.BodyLength = (ushort)((header [4] << 8) + header [5]); record.PaddingLength = header [6]; record.Body = body; connector.SendRecord (record); } return true; }