View Javadoc

1   // ========================================================================
2   // Copyright (c) 2004-2009 Mort Bay Consulting Pty. Ltd.
3   // ------------------------------------------------------------------------
4   // All rights reserved. This program and the accompanying materials
5   // are made available under the terms of the Eclipse Public License v1.0
6   // and Apache License v2.0 which accompanies this distribution.
7   // The Eclipse Public License is available at 
8   // http://www.eclipse.org/legal/epl-v10.html
9   // The Apache License v2.0 is available at
10  // http://www.opensource.org/licenses/apache2.0.php
11  // You may elect to redistribute this code under either of these licenses. 
12  // ========================================================================
13  
14  package org.eclipse.jetty.io;
15  
16  
17  /* ------------------------------------------------------------ */
18  /** Abstract Buffer pool.
19   * simple unbounded pool of buffers for header, request and response sizes.
20   *
21   */
22  public abstract class ThreadLocalBuffers implements Buffers
23  {
24      private int _bufferSize=12*1024;
25      private int _headerSize=6*1024;
26  
27      /* ------------------------------------------------------------ */
28      private final ThreadLocal<ThreadBuffers> _buffers=new ThreadLocal<ThreadBuffers>()
29      {
30          @Override
31          protected ThreadBuffers initialValue()
32          {
33              return new ThreadBuffers();
34          }
35      };
36  
37      /* ------------------------------------------------------------ */
38      public ThreadLocalBuffers()
39      {   
40      }
41  
42      /* ------------------------------------------------------------ */
43      public Buffer getBuffer()
44      {
45          ThreadBuffers buffers = _buffers.get();
46          if (buffers._buffer!=null)
47          {
48              Buffer b=buffers._buffer;
49              buffers._buffer=null;
50              return b;
51          }
52  
53          if (buffers._other!=null && buffers._other.capacity()==_bufferSize)
54          {
55              Buffer b=buffers._other;
56              buffers._other=null;
57              return b;
58          }
59  
60          return newBuffer(_bufferSize);
61      }
62  
63      /* ------------------------------------------------------------ */
64      public Buffer getHeader()
65      {
66          ThreadBuffers buffers = _buffers.get();
67          if (buffers._header!=null)
68          {
69              Buffer b=buffers._header;
70              buffers._header=null;
71              return b;
72          }
73  
74          if (buffers._other!=null && buffers._other.capacity()==_headerSize && isHeader(buffers._other))
75          {
76              Buffer b=buffers._other;
77              buffers._other=null;
78              return b;
79          }
80  
81          return newHeader(_headerSize);
82      }
83  
84      /* ------------------------------------------------------------ */
85      public Buffer getBuffer(int size)
86      {
87          ThreadBuffers buffers = _buffers.get();
88          if (buffers._other!=null && buffers._other.capacity()==size)
89          {
90              Buffer b=buffers._other;
91              buffers._other=null;
92              return b;
93          }
94  
95          return newBuffer(size);
96      }
97  
98      /* ------------------------------------------------------------ */
99      public void returnBuffer(Buffer buffer)
100     {
101         buffer.clear();
102         if (buffer.isVolatile() || buffer.isImmutable())
103             return;
104 
105         int size=buffer.capacity();
106         
107         ThreadBuffers buffers = _buffers.get();
108         
109         if (buffers._header==null && size==_headerSize && isHeader(buffer))
110             buffers._header=buffer;
111         else if (size==_bufferSize && buffers._buffer==null)
112             buffers._buffer=buffer;
113         else
114             buffers._other=buffer;
115     }
116 
117 
118 
119     /* ------------------------------------------------------------ */
120     /**
121      * @return Returns the buffer size in bytes.
122      */
123     public int getBufferSize()
124     {
125         return _bufferSize;
126     }
127 
128     /* ------------------------------------------------------------ */
129     /**
130      * @return Returns the header size in bytes.
131      */
132     public int getHeaderSize()
133     {
134         return _headerSize;
135     }
136 
137     /* ------------------------------------------------------------ */
138     /**
139      * Create a new content Buffer
140      * @param size
141      * @return new Buffer
142      */
143     protected abstract Buffer newBuffer(int size);
144 
145     /* ------------------------------------------------------------ */
146     /**
147      * Create a new header Buffer
148      * @param size
149      * @return new Buffer
150      */
151     protected abstract Buffer newHeader(int size);
152 
153     /* ------------------------------------------------------------ */
154     /**
155      * @param buffer
156      * @return True if the buffer is the correct type to be a Header buffer
157      */
158     protected abstract boolean isHeader(Buffer buffer);
159 
160     /* ------------------------------------------------------------ */
161     /**
162      * @param size The buffer size in bytes
163      */
164     public void setBufferSize( int size )
165     {
166         _bufferSize = size;
167     }
168 
169     /* ------------------------------------------------------------ */
170     /**
171      * @param size The header size in bytes
172      */
173     public void setHeaderSize( int size )
174     {
175         _headerSize = size;
176     }
177 
178     /* ------------------------------------------------------------ */
179     @Override
180     public String toString()
181     {
182         return "{{"+getHeaderSize()+","+getBufferSize()+"}}";
183     }
184     
185     /* ------------------------------------------------------------ */
186     /* ------------------------------------------------------------ */
187     protected static class ThreadBuffers
188     {
189         Buffer _buffer;
190         Buffer _header;
191         Buffer _other;
192     }
193 }