Du kan inte välja fler än 25 ämnen Ämnen måste starta med en bokstav eller siffra, kan innehålla bindestreck ('-') och vara max 35 tecken långa.

TcpListener.java 4.4KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156
  1. /* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
  2. * Copyright (C) 2012 Brian P. Hinz
  3. *
  4. * This is free software; you can redistribute it and/or modify
  5. * it under the terms of the GNU General Public License as published by
  6. * the Free Software Foundation; either version 2 of the License, or
  7. * (at your option) any later version.
  8. *
  9. * This software is distributed in the hope that it will be useful,
  10. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. * GNU General Public License for more details.
  13. *
  14. * You should have received a copy of the GNU General Public License
  15. * along with this software; if not, write to the Free Software
  16. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
  17. * USA.
  18. */
  19. package com.tigervnc.network;
  20. import java.io.IOException;
  21. import java.lang.Exception;
  22. import java.nio.*;
  23. import java.nio.channels.*;
  24. import java.net.InetAddress;
  25. import java.net.InetSocketAddress;
  26. import java.net.SocketAddress;
  27. import java.net.UnknownHostException;
  28. import java.util.Set;
  29. import java.util.Iterator;
  30. public class TcpListener extends SocketListener {
  31. public static boolean socketsInitialised = false;
  32. public TcpListener(String listenaddr, int port, boolean localhostOnly,
  33. SocketDescriptor sock, boolean close_) throws Exception {
  34. closeFd = close_;
  35. if (sock != null) {
  36. fd = sock;
  37. return;
  38. }
  39. TcpSocket.initSockets();
  40. try {
  41. channel = ServerSocketChannel.open();
  42. channel.configureBlocking(false);
  43. } catch(IOException e) {
  44. throw new Exception("unable to create listening socket: "+e.toString());
  45. }
  46. // - Bind it to the desired port
  47. InetAddress addr = null;
  48. try {
  49. if (localhostOnly) {
  50. addr = InetAddress.getByName(null);
  51. } else if (listenaddr != null) {
  52. addr = java.net.InetAddress.getByName(listenaddr);
  53. } else {
  54. addr = InetAddress.getByName("0.0.0.0");
  55. }
  56. } catch (UnknownHostException e) {
  57. throw new Exception(e.getMessage());
  58. }
  59. try {
  60. channel.socket().bind(new InetSocketAddress(addr, port));
  61. } catch (IOException e) {
  62. throw new Exception("unable to bind listening socket: "+e.toString());
  63. }
  64. // - Set it to be a listening socket
  65. try {
  66. selector = Selector.open();
  67. channel.register(selector, SelectionKey.OP_ACCEPT);
  68. } catch (IOException e) {
  69. throw new Exception("unable to set socket to listening mode: "+e.toString());
  70. }
  71. }
  72. public TcpListener(String listenaddr, int port) throws Exception {
  73. this(listenaddr, port, false, null, true);
  74. }
  75. protected void finalize() throws Exception {
  76. if (closeFd)
  77. try {
  78. ((SocketDescriptor)getFd()).close();
  79. } catch (IOException e) {
  80. throw new Exception(e.getMessage());
  81. }
  82. }
  83. public void shutdown() throws Exception {
  84. try {
  85. ((SocketDescriptor)getFd()).shutdown();
  86. } catch (IOException e) {
  87. throw new Exception(e.getMessage());
  88. }
  89. }
  90. public TcpSocket accept() {
  91. SocketChannel new_sock = null;
  92. // Accept an incoming connection
  93. try {
  94. if (selector.select(0) > 0) {
  95. Set<SelectionKey> keys = selector.selectedKeys();
  96. Iterator<SelectionKey> iter = keys.iterator();
  97. while (iter.hasNext()) {
  98. SelectionKey key = (SelectionKey)iter.next();
  99. iter.remove();
  100. if (key.isAcceptable()) {
  101. new_sock = channel.accept();
  102. break;
  103. }
  104. }
  105. keys.clear();
  106. if (new_sock == null)
  107. return null;
  108. }
  109. } catch (IOException e) {
  110. throw new SocketException("unable to accept new connection: "+e.toString());
  111. }
  112. // Disable Nagle's algorithm, to reduce latency
  113. try {
  114. new_sock.socket().setTcpNoDelay(true);
  115. } catch (java.net.SocketException e) {
  116. throw new SocketException(e.getMessage());
  117. }
  118. // Create the socket object & check connection is allowed
  119. SocketDescriptor fd = null;
  120. try {
  121. fd = new SocketDescriptor();
  122. } catch (java.lang.Exception e) {
  123. throw new SocketException(e.getMessage());
  124. }
  125. fd.setChannel(new_sock);
  126. TcpSocket s = new TcpSocket(fd);
  127. return s;
  128. }
  129. public int getMyPort() {
  130. return ((SocketDescriptor)getFd()).socket().getLocalPort();
  131. }
  132. private boolean closeFd;
  133. private ServerSocketChannel channel;
  134. private Selector selector;
  135. }