1 22 package org.xsocket.datagram; 23 24 import java.io.IOException ; 25 import java.io.UnsupportedEncodingException ; 26 import java.net.InetAddress ; 27 import java.net.InetSocketAddress ; 28 import java.net.SocketAddress ; 29 import java.nio.BufferOverflowException ; 30 import java.nio.BufferUnderflowException ; 31 import java.nio.ByteBuffer ; 32 33 34 import org.xsocket.DataConverter; 35 import org.xsocket.IDataSink; 36 import org.xsocket.IDataSource; 37 import org.xsocket.MaxReadSizeExceededException; 38 39 40 41 42 48 public final class UserDatagram implements IDataSource, IDataSink { 49 50 private SocketAddress remoteSocketAddress = null; 51 private ByteBuffer data = null; 52 private String defaultEncoding = "UTF-8"; 53 54 55 60 public UserDatagram(int size) { 61 init(remoteSocketAddress, ByteBuffer.allocate(size), size); 62 } 63 64 65 72 public UserDatagram(String remoteHost, int remotePort, int size) { 73 init(new InetSocketAddress (remoteHost, remotePort), ByteBuffer.allocate(size), size); 74 } 75 76 77 84 public UserDatagram(InetAddress remoteAddress, int remotePort, int size) { 85 init(new InetSocketAddress (remoteAddress, remotePort), ByteBuffer.allocate(size), size); 86 } 87 88 94 public UserDatagram(SocketAddress address, int size) { 95 init(address, ByteBuffer.allocate(size), size); 96 } 97 98 99 104 public UserDatagram(ByteBuffer data) { 105 this(null, data); 106 } 107 108 109 116 public UserDatagram(SocketAddress remoteSocketAddress, ByteBuffer data) { 117 this(remoteSocketAddress, data, "UTF-8"); 118 } 119 120 121 129 UserDatagram(SocketAddress remoteSocketAddress, ByteBuffer data, String defaultEncoding) { 130 init(remoteSocketAddress, data, data.limit()); 131 this.defaultEncoding = defaultEncoding; 132 } 133 134 135 140 public UserDatagram(byte[] data) { 141 this(null, data); 142 } 143 144 145 153 public UserDatagram(String remoteHost, int remotePort, byte[] data) { 154 this(new InetSocketAddress (remoteHost, remotePort), data); 155 } 156 157 158 159 160 167 public UserDatagram(SocketAddress remoteSocketAddress, byte[] data) { 168 ByteBuffer buffer = ByteBuffer.wrap(data); 169 buffer.position(buffer.limit()); 170 init(remoteSocketAddress, buffer, data.length); 171 } 172 173 174 175 private void init(SocketAddress remoteSocketAddress, ByteBuffer data, int packetSize) { 176 this.remoteSocketAddress =remoteSocketAddress; 177 this.data = data; 178 } 179 180 181 185 void prepareForSend() { 186 data.clear(); 187 } 188 189 190 194 void setRemoteAddress(SocketAddress remoteSocketAddress) { 195 this.remoteSocketAddress = remoteSocketAddress; 196 } 197 198 199 204 protected ByteBuffer getData() { 205 return data; 206 } 207 208 209 215 public SocketAddress getRemoteSocketAddress() { 216 return remoteSocketAddress; 217 } 218 219 220 226 public InetAddress getRemoteAddress() { 227 if (remoteSocketAddress instanceof InetSocketAddress ) { 228 return ((InetSocketAddress ) remoteSocketAddress).getAddress(); 229 } else { 230 return null; 231 } 232 } 233 234 235 241 public int getRemotePort() { 242 if (remoteSocketAddress instanceof InetSocketAddress ) { 243 return ((InetSocketAddress ) remoteSocketAddress).getPort(); 244 } else { 245 return -1; 246 } 247 } 248 249 250 257 public byte readByte() throws IOException , BufferUnderflowException { 258 return data.get(); 259 } 260 261 262 263 264 272 public ByteBuffer readByteBufferByLength(int length) throws IOException , BufferUnderflowException { 273 int savedLimit = data.limit(); 274 int savedPosition = data.position(); 275 276 data.limit(data.position() + length); 277 ByteBuffer sliced = data.slice(); 278 279 data.position(savedPosition + length); 280 data.limit(savedLimit); 281 return sliced; 282 } 283 284 285 286 287 295 public byte[] readBytesByLength(int length) throws IOException , BufferUnderflowException { 296 return DataConverter.toBytes(readByteBufferByLength(length)); 297 } 298 299 300 301 302 312 public String readStringByLength(int length, String encoding) throws IOException , BufferUnderflowException , UnsupportedEncodingException { 313 return DataConverter.toString(readByteBufferByLength(length), encoding); 314 } 315 316 317 318 327 public String readStringByLength(int length) throws IOException , BufferUnderflowException , UnsupportedEncodingException { 328 return readStringByLength(length, defaultEncoding); 329 } 330 331 332 333 339 public double readDouble() throws IOException , BufferUnderflowException { 340 return data.getDouble(); 341 } 342 343 344 345 346 353 public int readInt() throws IOException , BufferUnderflowException { 354 return data.getInt(); 355 } 356 357 358 359 366 public short readShort() throws IOException , BufferUnderflowException { 367 return data.getShort(); 368 } 369 370 371 378 public long readLong() throws IOException , BufferUnderflowException { 379 return data.getLong(); 380 } 381 382 383 384 390 public ByteBuffer readByteBuffer() throws IOException { 391 ByteBuffer sliced = data.slice(); 392 data.position(data.limit()); 393 return sliced; 394 } 395 396 397 398 404 public byte[] readBytes() throws IOException { 405 return DataConverter.toBytes(readByteBuffer()); 406 } 407 408 409 410 417 public String readString() throws IOException , UnsupportedEncodingException { 418 return readString(defaultEncoding); 419 } 420 421 422 423 424 432 public String readString(String encoding) throws IOException , UnsupportedEncodingException { 433 return DataConverter.toString(readByteBuffer(), encoding); 434 } 435 436 437 446 public String readStringByDelimiter(String delimiter) throws IOException , BufferUnderflowException , UnsupportedEncodingException { 447 return readStringByDelimiter(delimiter, defaultEncoding, Integer.MAX_VALUE); 448 } 449 450 451 452 463 public String readStringByDelimiter(String delimiter, int maxLength) throws IOException , BufferUnderflowException , UnsupportedEncodingException , MaxReadSizeExceededException { 464 return readStringByDelimiter(delimiter, defaultEncoding, maxLength); 465 } 466 467 479 public String readStringByDelimiter(String delimiter, String encoding, int maxLength) throws IOException , BufferUnderflowException , UnsupportedEncodingException , MaxReadSizeExceededException { 480 ByteBuffer buffer = readByteBufferByDelimiter(delimiter, maxLength); 481 return DataConverter.toString(buffer, encoding); 482 } 483 484 485 498 public ByteBuffer readByteBufferByDelimiter(String delimiter, int maxLength) throws IOException , BufferUnderflowException , MaxReadSizeExceededException { 499 byte[] delimiterBytes = delimiter.getBytes(); 500 int startPos = findDelimiter(data, delimiterBytes, maxLength); 501 if (startPos >= 0) { 502 int savedLimit = data.limit(); 503 data.limit(startPos); 504 ByteBuffer result = data.slice(); 505 data.limit(savedLimit); 506 data.position(startPos + delimiterBytes.length); 507 508 return result; 509 } else { 510 throw new BufferUnderflowException (); 511 } 512 } 513 514 515 516 529 public byte[] readBytesByDelimiter(String delimiter,int maxLength) throws IOException , BufferUnderflowException , MaxReadSizeExceededException { 530 ByteBuffer buffer = readByteBufferByDelimiter(delimiter, maxLength); 531 return DataConverter.toBytes(buffer); 532 } 533 534 535 private static int findDelimiter(ByteBuffer buffer, byte[] delimiter, int maxLength) throws MaxReadSizeExceededException { 536 int result = -1; 537 538 int delimiterPosition = 0; 539 540 for (int pos = buffer.position(); pos < buffer.limit(); pos++) { 542 543 byte b = buffer.get(pos); 544 if (b == delimiter[delimiterPosition]) { 545 delimiterPosition++; 546 if (delimiterPosition == delimiter.length) { 547 result = (pos - delimiterPosition + 1); 548 break; 549 } 550 } else { 551 delimiterPosition = 0; 552 } 553 554 } 555 556 if (result > maxLength) { 557 throw new MaxReadSizeExceededException(); 558 } 559 560 return result; 561 } 562 563 564 565 566 574 public int write(byte b) throws IOException , BufferOverflowException { 575 data.put(b); 576 return 1; 577 } 578 579 580 588 public int write(short s) throws IOException , BufferOverflowException { 589 data.putShort(s); 590 return 2; 591 } 592 593 594 602 public int write(byte... bytes) throws IOException , BufferOverflowException { 603 data.put(bytes); 604 return bytes.length; 605 } 606 607 608 609 619 public int write(byte[] bytes, int offset, int length) throws IOException , BufferOverflowException { 620 data.put(bytes, offset, length); 621 return length; 622 } 623 624 625 633 public int write(ByteBuffer buffer) throws IOException , BufferOverflowException { 634 int length = buffer.remaining(); 635 data.put(buffer); 636 return length; 637 } 638 639 640 641 649 public long write(ByteBuffer [] buffers) throws IOException , BufferOverflowException { 650 int length = 0; 651 for (ByteBuffer buffer : buffers) { 652 length += write(buffer); 653 } 654 return length; 655 } 656 657 658 659 660 668 public int write(double d) throws IOException , BufferOverflowException { 669 data.putDouble(d); 670 return 8; 671 } 672 673 674 682 public int write(int i) throws IOException , BufferOverflowException { 683 data.putInt(i); 684 return 4; 685 } 686 687 688 696 public int write(long l) throws IOException , BufferOverflowException { 697 data.putLong(l); 698 return 8; 699 } 700 701 702 710 public int write(String message) throws IOException , BufferOverflowException { 711 return write(message, defaultEncoding); 712 } 713 714 715 724 public int write(String message, String encoding) throws IOException , BufferOverflowException { 725 byte[] bytes = message.getBytes(encoding); 726 data.put(bytes); 727 728 return bytes.length; 729 } 730 731 732 737 public int getSize() { 738 return data.limit(); 739 } 740 741 746 public int getRemaining() { 747 return data.remaining(); 748 } 749 750 751 752 @Override 753 public String toString() { 754 StringBuilder sb = new StringBuilder (); 755 756 if (remoteSocketAddress != null) { 757 sb.append("remoteAddress=" + remoteSocketAddress.toString() + " "); 758 } else { 759 sb.append("remoteAddress=null "); 760 } 761 762 if (data != null) { 763 sb.append("data=" + DataConverter.toHexString(new ByteBuffer [] {data.duplicate()}, 500) + " "); 764 } else { 765 sb.append("data=null "); 766 } 767 768 return sb.toString(); 769 } 770 } | Popular Tags |