public void Send() { if (m_context.IsClosing) { return; } if (Sent) { throw new InvalidOperationException("Everything have already been sent."); } if (m_context.MaxRequests == 0 || m_keepAlive == 0) { Connection = ConnectionType.Close; m_context.TimeoutKeepAlive = 0; } else { if (m_keepAlive > 0) { m_context.TimeoutKeepAlive = m_keepAlive * 1000; } } if (RawBuffer != null) { if (RawBufferStart > RawBuffer.Length) { return; } if (RawBufferStart < 0) { RawBufferStart = 0; } if (RawBufferLen < 0) { RawBufferLen = RawBuffer.Length; } if (RawBufferLen + RawBufferStart > RawBuffer.Length) { RawBufferLen = RawBuffer.Length - RawBufferStart; } } m_headerBytes = GetHeaders(); if (RawBuffer != null && RawBufferLen > 0) { int tlen = m_headerBytes.Length + RawBufferLen; if (tlen < 8 * 1024) { byte[] tmp = new byte[tlen]; Buffer.BlockCopy(m_headerBytes, 0, tmp, 0, m_headerBytes.Length); Buffer.BlockCopy(RawBuffer, RawBufferStart, tmp, m_headerBytes.Length, RawBufferLen); m_headerBytes = null; RawBuffer = tmp; RawBufferStart = 0; RawBufferLen = tlen; } if (RawBufferLen == 0) { RawBuffer = null; } } if (m_body != null && m_body.Length == 0) { m_body.Dispose(); m_body = null; } if (m_headerBytes == null && RawBuffer == null && m_body == null) { Sent = true; m_context.EndSendResponse(requestID, Connection); } else { m_context.StartSendResponse(this); } }
public async Task SendNextAsync(int bytesLimit) { if (m_headerBytes != null) { if (!await m_context.SendAsync(m_headerBytes, 0, m_headerBytes.Length).ConfigureAwait(false)) { if (m_context.CanSend()) { m_context.ContinueSendResponse(true); return; } if (m_body != null) { m_body.Dispose(); } RawBuffer = null; Sent = true; return; } bytesLimit -= m_headerBytes.Length; m_headerBytes = null; if (bytesLimit <= 0) { m_context.ContinueSendResponse(true); return; } } if (RawBuffer != null) { if (RawBufferLen > 0) { if (BandWitdhEvent != null) { bytesLimit = CheckBandwidth(RawBufferLen, bytesLimit); } bool sendRes; if (RawBufferLen > bytesLimit) { sendRes = (await m_context.SendAsync(RawBuffer, RawBufferStart, bytesLimit).ConfigureAwait(false)); if (sendRes) { RawBufferLen -= bytesLimit; RawBufferStart += bytesLimit; } } else { sendRes = await m_context.SendAsync(RawBuffer, RawBufferStart, RawBufferLen).ConfigureAwait(false); if (sendRes) { RawBufferLen = 0; } } if (!sendRes) { if (m_context.CanSend()) { m_context.ContinueSendResponse(true); return; } RawBuffer = null; if (m_body != null) { Body.Dispose(); } Sent = true; return; } } if (RawBufferLen <= 0) { RawBuffer = null; } else { m_context.ContinueSendResponse(true); return; } } if (m_body != null && m_body.Length != 0) { MemoryStream mb = m_body as MemoryStream; RawBuffer = mb.GetBuffer(); RawBufferStart = 0; // must be a internal buffer, or starting at 0 RawBufferLen = (int)mb.Length; mb.Dispose(); m_body = null; if (RawBufferLen > 0) { bool sendRes; if (RawBufferLen > bytesLimit) { sendRes = await m_context.SendAsync(RawBuffer, RawBufferStart, bytesLimit).ConfigureAwait(false); if (sendRes) { RawBufferLen -= bytesLimit; RawBufferStart += bytesLimit; } } else { sendRes = await m_context.SendAsync(RawBuffer, RawBufferStart, RawBufferLen).ConfigureAwait(false); if (sendRes) { RawBufferLen = 0; } } if (!sendRes) { if (m_context.CanSend()) { m_context.ContinueSendResponse(true); return; } RawBuffer = null; Sent = true; return; } } if (RawBufferLen > 0) { m_context.ContinueSendResponse(false); return; } } if (m_body != null) { m_body.Dispose(); } Sent = true; m_context.EndSendResponse(requestID, Connection); }