1 16 17 package org.apache.ajp; 18 19 import java.io.IOException ; 20 import java.io.InputStream ; 21 import java.io.OutputStream ; 22 import java.net.Socket ; 23 24 import org.apache.tomcat.util.http.BaseRequest; 25 import org.apache.tomcat.util.http.HttpMessages; 26 import org.apache.tomcat.util.http.MimeHeaders; 27 28 47 public class Ajp13 { 48 49 public static final int MAX_PACKET_SIZE=8192; 50 public static final int H_SIZE=4; 52 public static final int MAX_READ_SIZE = MAX_PACKET_SIZE - H_SIZE - 2; 53 public static final int MAX_SEND_SIZE = MAX_PACKET_SIZE - H_SIZE - 4; 54 55 public static final int JK_AJP13_BAD_HEADER = -100; 57 public static final int JK_AJP13_NO_HEADER = -101; 58 public static final int JK_AJP13_COMM_CLOSED = -102; 59 public static final int JK_AJP13_COMM_BROKEN = -103; 60 public static final int JK_AJP13_BAD_BODY = -104; 61 public static final int JK_AJP13_INCOMPLETE_BODY = -105; 62 63 65 OutputStream out; 66 InputStream in; 67 68 public Ajp13Packet outBuf = new Ajp13Packet( MAX_PACKET_SIZE ); 70 Ajp13Packet inBuf = new Ajp13Packet( MAX_PACKET_SIZE ); 72 Ajp13Packet hBuf=new Ajp13Packet( MAX_PACKET_SIZE ); 74 75 byte []bodyBuff = new byte[MAX_READ_SIZE]; 77 78 int blen; int pos; 81 boolean end_of_stream; 83 public RequestHandler reqHandler; 85 boolean backwardCompat=true; 88 boolean logged=false; 89 String secret=null; 90 91 public Ajp13() { 92 super(); 93 initBuf(); 94 reqHandler=new RequestHandler(); 95 reqHandler.init( this ); 96 } 97 98 public Ajp13(RequestHandler reqHandler ) { 99 super(); 100 initBuf(); 101 this.reqHandler=reqHandler; 102 reqHandler.init( this ); 103 } 104 105 107 public void initBuf() { 108 outBuf = new Ajp13Packet( MAX_PACKET_SIZE ); 109 inBuf = new Ajp13Packet( MAX_PACKET_SIZE ); 110 hBuf=new Ajp13Packet( MAX_PACKET_SIZE ); 111 } 112 113 public void recycle() { 114 if (debug > 0) { 115 logger.log("recycle()"); 116 } 117 118 blen = 0; 120 pos = 0; 121 end_of_stream = false; 122 logged=false; 123 } 124 125 128 public void setSocket( Socket socket ) throws IOException { 129 if (debug > 0) { 130 logger.log("setSocket()"); 131 } 132 133 socket.setSoLinger( true, 100); 134 out = socket.getOutputStream(); 135 in = socket.getInputStream(); 136 pos = 0; 137 } 138 139 142 public void setBackward(boolean b) 143 { 144 backwardCompat=b; 145 } 146 147 public boolean isLogged() { 148 return logged; 149 } 150 151 void setLogged( boolean b ) { 152 logged=b; 153 } 154 155 public void setSecret( String s ) { 156 secret=s; 157 } 158 159 public String getSecret() { 160 return secret; 161 } 162 163 165 static final int MAX_HANDLERS=32; 166 static final int RESERVED=16; 168 AjpHandler handlers[]=new AjpHandler[MAX_HANDLERS]; 171 String handlerName[]=new String [MAX_HANDLERS]; 172 int currentId=RESERVED; 173 174 public int registerMessageType( int id, String name, AjpHandler h, 175 String sig[] ) 176 { 177 if( id < 0 ) { 178 for( int i=0; i< handlerName.length; i++ ) 180 if( name.equals( handlerName[i] ) ) return i; 181 handlerName[currentId]=name; 182 handlers[currentId]=h; 183 currentId++; 184 return currentId; 185 } 186 handlerName[id]=name; 188 handlers[id]=h; 189 return id; 190 } 191 192 194 205 public int receiveNextRequest(BaseRequest req) throws IOException { 206 if (debug > 0) { 207 logger.log("receiveNextRequest()"); 208 } 209 210 212 int err = 0; 213 214 try { 218 err = receive(hBuf); 219 } catch (IOException ioe) { 220 if(debug >0 ) logger.log( "IOException receiving message "); 221 return -1; } 223 224 if(err < 0) { 225 if(debug >0 ) logger.log( "Error receiving message "); 226 return 500; 227 } 228 229 int type = (int)hBuf.getByte(); 230 return handleMessage( type, hBuf, req ); 232 } 233 234 236 public int handleMessage( int type, Ajp13Packet hBuf, BaseRequest req ) 237 throws IOException 238 { 239 if( type > handlers.length ) { 240 logger.log( "Invalid handler " + type ); 241 return 500; 242 } 243 244 if( debug > 0 ) 245 logger.log( "Received " + type + " " + handlerName[type]); 246 247 if( ! backwardCompat && ! isLogged() ) { 249 if( type != NegociationHandler.JK_AJP14_LOGINIT_CMD && 250 type != NegociationHandler.JK_AJP14_LOGCOMP_CMD ) { 251 252 logger.log( "Ajp14 error: not logged " + 253 type + " " + handlerName[type]); 254 255 return 300; 256 } 257 } 259 260 switch(type) { 262 case RequestHandler.JK_AJP13_FORWARD_REQUEST: 263 return reqHandler.decodeRequest(this, hBuf, req); 264 265 case RequestHandler.JK_AJP13_CPING_REQUEST: 266 return reqHandler.sendCPong(this, outBuf); 267 268 case RequestHandler.JK_AJP13_SHUTDOWN: 269 return -2; 270 } 271 272 AjpHandler handler=handlers[type]; 274 if( handler==null ) { 275 logger.log( "Unknown message " + type + handlerName[type] ); 276 return 200; 277 } 278 279 if( debug > 0 ) 280 logger.log( "Ajp14 handler " + handler ); 281 return handler.handleAjpMessage( type, this, hBuf, req ); 282 } 283 284 286 288 289 290 public int available() throws IOException { 291 return reqHandler.available(this); 292 } 293 294 public int doRead() throws IOException 295 { 296 return reqHandler.doRead( this ); 297 } 298 299 public int doRead(byte[] b, int off, int len) throws IOException 300 { 301 return reqHandler.doRead( this, b, off, len ); 302 } 303 304 private boolean refillReadBuffer() throws IOException 305 { 306 return reqHandler.refillReadBuffer(this); 307 } 308 309 public void beginSendHeaders(int status, 310 String statusMessage, 311 int numHeaders) throws IOException { 312 reqHandler.beginSendHeaders( this, outBuf, 313 status, statusMessage, 314 numHeaders); 315 } 316 317 public void sendHeader(String name, String value) throws IOException { 318 reqHandler.sendHeader( outBuf, name, value ); 319 } 320 321 322 public void endSendHeaders() throws IOException { 323 reqHandler.endSendHeaders(this, outBuf); 324 } 325 326 public void sendHeaders(int status, MimeHeaders headers) 327 throws IOException 328 { 329 reqHandler.sendHeaders(this, outBuf, status, 330 HttpMessages.getMessage(status), 331 headers); 332 } 333 334 public void sendHeaders(int status, String statusMessage, 335 MimeHeaders headers) 336 throws IOException 337 { 338 reqHandler.sendHeaders( this, outBuf, status, 339 statusMessage, headers ); 340 } 341 342 public void finish() throws IOException { 343 reqHandler.finish(this, outBuf ); 344 } 345 346 public void doWrite(byte b[], int off, int len) throws IOException { 347 reqHandler.doWrite( this, outBuf, b, off, len ); 348 } 349 350 351 353 372 private int readN(InputStream in, byte[] b, int offset, int len) throws IOException { 373 int pos = 0; 374 int got; 375 376 while(pos < len) { 377 got = in.read(b, pos + offset, len - pos); 378 379 if (debug > 10) { 380 logger.log("read got # " + got); 381 } 382 383 if (got <= 0) { 385 return JK_AJP13_COMM_BROKEN; 389 } 390 391 pos += got; 392 } 393 return pos; 394 } 395 396 406 public int receive(Ajp13Packet msg) throws IOException { 407 if (debug > 0) { 408 logger.log("receive()"); 409 } 410 411 byte b[] = msg.getBuff(); 416 417 int rd = readN(in, b, 0, H_SIZE ); 418 419 if(rd < 0) { 423 return rd; 425 } 426 427 int len = msg.checkIn(); 428 if( debug > 5 ) 429 logger.log( "Received " + rd + " " + len + " " + b[0] ); 430 431 433 int total_read = 0; 434 435 total_read = readN(in, b, H_SIZE, len); 436 437 if (total_read < 0) { 440 logger.log("can't read body, waited #" + len); 441 return JK_AJP13_BAD_BODY; 442 } 443 444 if (total_read != len) { 445 logger.log( "incomplete read, waited #" + len + 446 " got only " + total_read); 447 return JK_AJP13_INCOMPLETE_BODY; 448 } 449 450 if (debug > 0) 451 logger.log("receive: total read = " + total_read); 452 return total_read; 453 } 454 455 461 public void send( Ajp13Packet msg ) throws IOException { 462 if (debug > 0) { 463 logger.log("send()"); 464 } 465 466 msg.end(); byte b[] = msg.getBuff(); 468 int len = msg.getLen(); 469 470 if (debug > 5 ) 471 logger.log("send() " + len + " " + b[0] ); 472 473 out.write( b, 0, len ); 474 } 475 476 481 public void close() throws IOException { 482 if (debug > 0) { 483 logger.log("close()"); 484 } 485 486 if(null != out) { 487 out.close(); 488 } 489 if(null !=in) { 490 in.close(); 491 } 492 setLogged( false ); } 494 495 protected int debug = 0; 497 498 public void setDebug(int debug) { 499 this.debug = debug; 500 this.reqHandler.setDebug(debug); 501 } 502 503 public void setLogger(Logger l) { 504 this.logger = l; 505 this.reqHandler.setLogger(l); 506 } 507 508 511 Logger logger = new Logger(); 512 } 513 | Popular Tags |