All Downloads are FREE. Search and download functionalities are using the official Maven repository.

net.lightbody.bmp.proxy.jetty.http.ajp.AJP13OutputStream Maven / Gradle / Ivy

The newest version!
// ========================================================================
// $Id: AJP13OutputStream.java,v 1.14 2006/10/08 14:13:05 gregwilkins Exp $
// Copyright 2002-2004 Mort Bay Consulting Pty. Ltd.
// ------------------------------------------------------------------------
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at 
// http://www.apache.org/licenses/LICENSE-2.0
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
// ========================================================================

package net.lightbody.bmp.proxy.jetty.http.ajp;

import net.lightbody.bmp.proxy.jetty.http.BufferedOutputStream;
import net.lightbody.bmp.proxy.jetty.http.HttpMessage;
import net.lightbody.bmp.proxy.jetty.http.HttpResponse;
import net.lightbody.bmp.proxy.jetty.log.LogFactory;
import net.lightbody.bmp.proxy.jetty.util.LogSupport;
import org.apache.commons.logging.Log;

import java.io.IOException;
import java.io.OutputStream;
import java.util.Enumeration;

/**
 * OutputStream for AJP13 protocol.
 * 
 * 
 * @version $Revision: 1.14 $
 * @author Greg Wilkins (gregw)
 */
public class AJP13OutputStream extends BufferedOutputStream
{
    private static Log log=LogFactory.getLog(AJP13OutputStream.class);

    private AJP13ResponsePacket _packet;
    private boolean _complete;
    private boolean _completed;
    private boolean _persistent=true;
    private AJP13ResponsePacket _ajpResponse;

    /* ------------------------------------------------------------ */
    AJP13OutputStream(OutputStream out, int bufferSize)
    {
        super(out,bufferSize,AJP13ResponsePacket.__DATA_HDR,AJP13ResponsePacket.__DATA_HDR,1);
        setFixed(true);
        _packet=new AJP13ResponsePacket(_buf);
        _packet.prepare();

        setBypassBuffer(false);
        setFixed(true);

        _ajpResponse=new AJP13ResponsePacket(bufferSize);
        _ajpResponse.prepare();
    }

    /* ------------------------------------------------------------ */
    public void writeHeader(HttpMessage httpMessage) throws IOException
    {
        HttpResponse response=(HttpResponse)httpMessage;
        response.setState(HttpMessage.__MSG_SENDING);

        _ajpResponse.resetData();
        _ajpResponse.addByte(AJP13ResponsePacket.__SEND_HEADERS);
        _ajpResponse.addInt(response.getStatus());
        _ajpResponse.addString(response.getReason());

        int mark=_ajpResponse.getMark();
        _ajpResponse.addInt(0);
        int nh=0;
        Enumeration e1=response.getFieldNames();
        while (e1.hasMoreElements())
        {
            String h=(String)e1.nextElement();
            Enumeration e2=response.getFieldValues(h);
            while (e2.hasMoreElements())
            {
                _ajpResponse.addHeader(h);
                _ajpResponse.addString((String)e2.nextElement());
                nh++;
            }
        }

        if (nh>0)
            _ajpResponse.setInt(mark,nh);
        _ajpResponse.setDataSize();

        write(_ajpResponse);

        _ajpResponse.resetData();
    }

    /* ------------------------------------------------------------ */
    public void write(AJP13Packet packet) throws IOException
    {
        packet.write(_out);
    }

    /* ------------------------------------------------------------ */
    public void flush() throws IOException
    {
        super.flush();
        if (_complete&&!_completed)
        {
            _completed=true;

            _packet.resetData();
            _packet.addByte(AJP13ResponsePacket.__END_RESPONSE);
            _packet.addBoolean(_persistent);
            _packet.setDataSize();
            write(_packet);
            _packet.resetData();
        }
    }

    /* ------------------------------------------------------------ */
    public void close() throws IOException
    {
        _complete=true;
        flush();
    }

    /* ------------------------------------------------------------ */
    public void resetStream()
    {
        _complete=false;
        _completed=false;
        super.resetStream();
    }

    /* ------------------------------------------------------------ */
    public void destroy()
    {
        if (_packet!=null)
            _packet.destroy();
        _packet=null;
        if (_ajpResponse!=null)
            _ajpResponse.destroy();
        _ajpResponse=null;
        _out=null;
    }

    /* ------------------------------------------------------------ */
    public void end() throws IOException
    {
        _persistent=false;
    }

    /* ------------------------------------------------------------ */
    protected void wrapBuffer() throws IOException
    {
        if (size()==0)
            return;

        if (_buf!=_packet.getBuffer())
        {
            _packet=new AJP13ResponsePacket(_buf);
            _packet.prepare();
        }

        prewrite(_buf,0,AJP13ResponsePacket.__DATA_HDR);
        _packet.resetData();
        _packet.addByte(AJP13ResponsePacket.__SEND_BODY_CHUNK);
        _packet.setDataSize(size()-AJP13ResponsePacket.__HDR_SIZE);
        postwrite((byte)0);
    }

    /* ------------------------------------------------------------ */
    protected void bypassWrite(byte[] b, int offset, int length) throws IOException
    {
        log.warn(LogSupport.NOT_IMPLEMENTED);
    }


    /* ------------------------------------------------------------ */
    public void writeTo(OutputStream out) throws IOException
    {
        int sz=size();

        if (sz<=AJP13ResponsePacket.__MAX_BUF)
            super.writeTo(out);
        else
        {
            int offset=preReserve();
            int data=sz-AJP13ResponsePacket.__DATA_HDR;

            while (data>AJP13ResponsePacket.__MAX_DATA)
            {
                _packet.setDataSize(AJP13ResponsePacket.__MAX_BUF-AJP13ResponsePacket.__HDR_SIZE);
                if (offset>0)
                    System.arraycopy(_buf,0,_buf,offset,AJP13ResponsePacket.__DATA_HDR);
                out.write(_buf,offset,AJP13ResponsePacket.__MAX_BUF);

                data-=AJP13ResponsePacket.__MAX_DATA;
                offset+=AJP13ResponsePacket.__MAX_DATA;
            }

            int len=data+AJP13ResponsePacket.__DATA_HDR;
            _packet.setDataSize(len-AJP13ResponsePacket.__HDR_SIZE);
            if (offset>0)
                System.arraycopy(_buf,0,_buf,offset,AJP13ResponsePacket.__DATA_HDR);
            out.write(_buf,offset,len);
        }
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy