Mercurial Hosting > luan
comparison src/org/eclipse/jetty/http/HttpGenerator.java @ 983:23ec25435b8c
simplify AbstractGenerator
author | Franklin Schmidt <fschmidt@gmail.com> |
---|---|
date | Sun, 16 Oct 2016 22:58:41 -0600 |
parents | dbecd7faa1f5 |
children | 83cc6e05a58f |
comparison
equal
deleted
inserted
replaced
982:dbecd7faa1f5 | 983:23ec25435b8c |
---|---|
45 private static final Logger LOG = LoggerFactory.getLogger(HttpGenerator.class); | 45 private static final Logger LOG = LoggerFactory.getLogger(HttpGenerator.class); |
46 | 46 |
47 // Build cache of response lines for status | 47 // Build cache of response lines for status |
48 private static class Status | 48 private static class Status |
49 { | 49 { |
50 Buffer _reason; | |
51 Buffer _schemeCode; | 50 Buffer _schemeCode; |
52 Buffer _responseLine; | 51 Buffer _responseLine; |
53 } | 52 } |
54 private static final Status[] __status = new Status[HttpStatus.MAX_CODE+1]; | 53 private static final Status[] __status = new Status[HttpStatus.MAX_CODE+1]; |
55 static | 54 static |
73 bytes[versionLength+5+j]=(byte)reason.charAt(j); | 72 bytes[versionLength+5+j]=(byte)reason.charAt(j); |
74 bytes[versionLength+5+reason.length()]=HttpTokens.CARRIAGE_RETURN; | 73 bytes[versionLength+5+reason.length()]=HttpTokens.CARRIAGE_RETURN; |
75 bytes[versionLength+6+reason.length()]=HttpTokens.LINE_FEED; | 74 bytes[versionLength+6+reason.length()]=HttpTokens.LINE_FEED; |
76 | 75 |
77 __status[i] = new Status(); | 76 __status[i] = new Status(); |
78 __status[i]._reason=new ByteArrayBuffer(bytes,versionLength+5,bytes.length-versionLength-7,Buffer.IMMUTABLE); | |
79 __status[i]._schemeCode=new ByteArrayBuffer(bytes,0,versionLength+5,Buffer.IMMUTABLE); | 77 __status[i]._schemeCode=new ByteArrayBuffer(bytes,0,versionLength+5,Buffer.IMMUTABLE); |
80 __status[i]._responseLine=new ByteArrayBuffer(bytes,0,bytes.length,Buffer.IMMUTABLE); | 78 __status[i]._responseLine=new ByteArrayBuffer(bytes,0,bytes.length,Buffer.IMMUTABLE); |
81 } | 79 } |
82 } | |
83 | |
84 /* ------------------------------------------------------------------------------- */ | |
85 public static Buffer getReasonBuffer(int code) | |
86 { | |
87 Status status = code<__status.length?__status[code]:null; | |
88 if (status!=null) | |
89 return status._reason; | |
90 return null; | |
91 } | 80 } |
92 | 81 |
93 | 82 |
94 // common _content | 83 // common _content |
95 private static final byte[] LAST_CHUNK = | 84 private static final byte[] LAST_CHUNK = |
104 | 93 |
105 // other statics | 94 // other statics |
106 private static final int CHUNK_SPACE = 12; | 95 private static final int CHUNK_SPACE = 12; |
107 | 96 |
108 // data | 97 // data |
109 protected boolean _bypass = false; // True if _content buffer can be written directly to endp and bypass the content buffer | 98 private boolean _bypass = false; // True if _content buffer can be written directly to endp and bypass the content buffer |
110 private boolean _needCRLF = false; | 99 private boolean _needCRLF = false; |
111 private boolean _needEOC = false; | 100 private boolean _needEOC = false; |
112 private boolean _bufferChunked = false; | 101 private boolean _bufferChunked = false; |
113 | 102 |
114 | 103 |
115 /* ------------------------------------------------------------------------------- */ | |
116 /** | |
117 * Constructor. | |
118 * | |
119 * @param buffers buffer pool | |
120 * @param io the end point to use | |
121 */ | |
122 public HttpGenerator(Buffers buffers, EndPoint io) | 104 public HttpGenerator(Buffers buffers, EndPoint io) |
123 { | 105 { |
124 super(buffers,io); | 106 super(buffers,io); |
125 } | 107 } |
126 | 108 |
127 /* ------------------------------------------------------------------------------- */ | |
128 @Override | 109 @Override |
129 public void reset() | 110 public void reset() |
130 { | 111 { |
131 if (_persistent!=null && !_persistent && _endp!=null && !_endp.isOutputShutdown()) | 112 if (_persistent!=null && !_persistent && _endp!=null && !_endp.isOutputShutdown()) |
132 { | 113 { |
147 if (_content!=null) | 128 if (_content!=null) |
148 _content=null; | 129 _content=null; |
149 _bypass = false; | 130 _bypass = false; |
150 _needCRLF = false; | 131 _needCRLF = false; |
151 _needEOC = false; | 132 _needEOC = false; |
152 _bufferChunked=false; | 133 _bufferChunked = false; |
153 _method=null; | 134 _method=null; |
154 _uri=null; | 135 _uri=null; |
155 _noContent=false; | 136 _noContent=false; |
156 } | 137 } |
157 | 138 |
260 /** Prepare buffer for unchecked writes. | 241 /** Prepare buffer for unchecked writes. |
261 * Prepare the generator buffer to receive unchecked writes | 242 * Prepare the generator buffer to receive unchecked writes |
262 * @return the available space in the buffer. | 243 * @return the available space in the buffer. |
263 * @throws IOException | 244 * @throws IOException |
264 */ | 245 */ |
265 @Override | |
266 public int prepareUncheckedAddContent() throws IOException | 246 public int prepareUncheckedAddContent() throws IOException |
267 { | 247 { |
268 if (_noContent) | 248 if (_noContent) |
269 return -1; | 249 return -1; |
270 | 250 |
291 return Integer.MAX_VALUE; | 271 return Integer.MAX_VALUE; |
292 | 272 |
293 return _buffer.space()-(_contentLength == HttpTokens.CHUNKED_CONTENT?CHUNK_SPACE:0); | 273 return _buffer.space()-(_contentLength == HttpTokens.CHUNKED_CONTENT?CHUNK_SPACE:0); |
294 } | 274 } |
295 | 275 |
296 /* ------------------------------------------------------------ */ | |
297 @Override | 276 @Override |
298 public boolean isBufferFull() | 277 public boolean isBufferFull() |
299 { | 278 { |
300 // Should we flush the buffers? | 279 // Should we flush the buffers? |
301 return super.isBufferFull() || _bufferChunked || _bypass || (_contentLength == HttpTokens.CHUNKED_CONTENT && _buffer != null && _buffer.space() < CHUNK_SPACE); | 280 return super.isBufferFull() || _bufferChunked || _bypass || (_contentLength == HttpTokens.CHUNKED_CONTENT && _buffer != null && _buffer.space() < CHUNK_SPACE); |
302 } | 281 } |
303 | 282 |
304 /* ------------------------------------------------------------ */ | |
305 public void send1xx(int code) throws IOException | 283 public void send1xx(int code) throws IOException |
306 { | 284 { |
307 if (_state != STATE_HEADER) | 285 if (_state != STATE_HEADER) |
308 return; | 286 return; |
309 | 287 |
310 if (code<100||code>199) | 288 if (code<100||code>199) |
311 throw new IllegalArgumentException("!1xx"); | 289 throw new IllegalArgumentException("!1xx"); |
312 Status status=__status[code]; | 290 Status status = __status[code]; |
313 if (status==null) | 291 if (status==null) |
314 throw new IllegalArgumentException(code+"?"); | 292 throw new IllegalArgumentException(code+"?"); |
315 | 293 |
316 // get a header buffer | 294 // get a header buffer |
317 if (_header == null) | 295 if (_header == null) |
337 LOG.debug("",e); | 315 LOG.debug("",e); |
338 throw new InterruptedIOException(e.toString()); | 316 throw new InterruptedIOException(e.toString()); |
339 } | 317 } |
340 } | 318 } |
341 | 319 |
342 /* ------------------------------------------------------------ */ | |
343 @Override | 320 @Override |
344 public boolean isRequest() | 321 boolean isRequest() |
345 { | 322 { |
346 return _method!=null; | 323 return _method!=null; |
347 } | 324 } |
348 | 325 |
349 /* ------------------------------------------------------------ */ | 326 private boolean isResponse() |
350 @Override | |
351 public boolean isResponse() | |
352 { | 327 { |
353 return _method==null; | 328 return _method==null; |
354 } | 329 } |
355 | 330 |
356 /* ------------------------------------------------------------ */ | |
357 @Override | 331 @Override |
358 public void completeHeader(HttpFields fields, boolean allContentAdded) throws IOException | 332 public void completeHeader(HttpFields fields, boolean allContentAdded) throws IOException |
359 { | 333 { |
360 if (_state != STATE_HEADER) | 334 if (_state != STATE_HEADER) |
361 return; | 335 return; |
470 _content=null; | 444 _content=null; |
471 if (_buffer!=null) | 445 if (_buffer!=null) |
472 _buffer.clear(); | 446 _buffer.clear(); |
473 } | 447 } |
474 } | 448 } |
475 } | |
476 | |
477 // Add headers | |
478 if (_status>=200 && _date!=null) | |
479 { | |
480 _header.put(HttpHeaders.DATE_BUFFER); | |
481 _header.put((byte)':'); | |
482 _header.put((byte)' '); | |
483 _header.put(_date); | |
484 _header.put(CRLF); | |
485 } | 449 } |
486 | 450 |
487 // key field values | 451 // key field values |
488 HttpFields.Field content_length = null; | 452 HttpFields.Field content_length = null; |
489 HttpFields.Field transfer_encoding = null; | 453 HttpFields.Field transfer_encoding = null; |
789 } | 753 } |
790 | 754 |
791 flushBuffer(); | 755 flushBuffer(); |
792 } | 756 } |
793 | 757 |
794 /* ------------------------------------------------------------ */ | |
795 @Override | 758 @Override |
796 public int flushBuffer() throws IOException | 759 public int flushBuffer() throws IOException |
797 { | 760 { |
798 try | 761 try |
799 { | 762 { |
906 LOG.trace("",e); | 869 LOG.trace("",e); |
907 throw (e instanceof EofException) ? e:new EofException(e); | 870 throw (e instanceof EofException) ? e:new EofException(e); |
908 } | 871 } |
909 } | 872 } |
910 | 873 |
911 /* ------------------------------------------------------------ */ | |
912 private int flushMask() | 874 private int flushMask() |
913 { | 875 { |
914 return ((_header != null && _header.length() > 0)?4:0) | 876 return ((_header != null && _header.length() > 0)?4:0) |
915 | ((_buffer != null && _buffer.length() > 0)?2:0) | 877 | ((_buffer != null && _buffer.length() > 0)?2:0) |
916 | ((_bypass && _content != null && _content.length() > 0)?1:0); | 878 | ((_bypass && _content != null && _content.length() > 0)?1:0); |
917 } | 879 } |
918 | 880 |
919 /* ------------------------------------------------------------ */ | |
920 private void prepareBuffers() | 881 private void prepareBuffers() |
921 { | 882 { |
922 // if we are not flushing an existing chunk | 883 // if we are not flushing an existing chunk |
923 if (!_bufferChunked) | 884 if (!_bufferChunked) |
924 { | 885 { |
953 // Add the chunk size to the header | 914 // Add the chunk size to the header |
954 BufferUtil.putHexInt(_header, size); | 915 BufferUtil.putHexInt(_header, size); |
955 _header.put(HttpTokens.CRLF); | 916 _header.put(HttpTokens.CRLF); |
956 | 917 |
957 // Need a CRLF after the content | 918 // Need a CRLF after the content |
958 _needCRLF=true; | 919 _needCRLF = true; |
959 } | 920 } |
960 else if (_buffer!=null) | 921 else if (_buffer!=null) |
961 { | 922 { |
962 int size = _buffer.length(); | 923 int size = _buffer.length(); |
963 if (size > 0) | 924 if (size > 0) |
1051 } | 1012 } |
1052 | 1013 |
1053 if (_content != null && _content.length() == 0) | 1014 if (_content != null && _content.length() == 0) |
1054 _content = null; | 1015 _content = null; |
1055 | 1016 |
1056 } | |
1057 | |
1058 public int getBytesBuffered() | |
1059 { | |
1060 return(_header==null?0:_header.length())+ | |
1061 (_buffer==null?0:_buffer.length())+ | |
1062 (_content==null?0:_content.length()); | |
1063 } | |
1064 | |
1065 public boolean isEmpty() | |
1066 { | |
1067 return (_header==null||_header.length()==0) && | |
1068 (_buffer==null||_buffer.length()==0) && | |
1069 (_content==null||_content.length()==0); | |
1070 } | 1017 } |
1071 | 1018 |
1072 @Override | 1019 @Override |
1073 public String toString() | 1020 public String toString() |
1074 { | 1021 { |