1 /* 2 * Copyright (c) 2003, 2006, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 package com.sun.jdi.connect.spi; 27 28 import java.io.IOException; 29 import com.sun.jdi.connect.TransportTimeoutException; 30 31 /** 32 * A transport service for connections between a debugger and 33 * a target VM. 34 * 35 * <p> A transport service is a concrete subclass of this class 36 * that has a zero-argument constructor and implements the abstract 37 * methods specified below. It is the underlying service 38 * used by a {@link com.sun.jdi.connect.Transport} for 39 * connections between a debugger and a target VM. 40 * 41 * <p> A transport service is used to establish a connection 42 * between a debugger and a target VM, and to transport Java 43 * Debug Wire Protocol (JDWP) packets over an underlying 44 * communication protocol. In essence a transport service 45 * implementation binds JDWP (as specified in the 46 * <a href="../../../../../../../../../technotes/guides/jpda/jdwp-spec.html"> 47 * JDWP specification</a>) to an underlying communication 48 * protocol. A transport service implementation provides 49 * a reliable JDWP packet transportation service. JDWP 50 * packets are sent to and from the target VM without duplication 51 * or data loss. A transport service implementation may be 52 * based on an underlying communication protocol that is 53 * reliable or unreliable. If the underlying communication 54 * protocol is reliable then the transport service implementation 55 * may be relatively simple and may only need to transport JDWP 56 * packets as payloads of the underlying communication 57 * protocol. In the case of an unreliable communication 58 * protocol the transport service implementation may include 59 * additional protocol support in order to ensure that packets 60 * are not duplicated and that there is no data loss. The 61 * details of such protocols are specific to the implementation 62 * but may involve techniques such as the <i>positive 63 * acknowledgment with retransmission</i> technique used in 64 * protocols such as the Transmission Control Protocol (TCP) 65 * (see <a href="http://www.ietf.org/rfc/rfc0793.txt"> RFC 793 66 * </a>). 67 * 68 * <p> A transport service can be used to initiate a connection 69 * to a target VM. This is done by invoking the {@link #attach} 70 * method. Alternatively, a transport service can listen and 71 * accept connections initiated by a target VM. This is done 72 * by invoking the {@link #startListening(String)} method to 73 * put the transport into listen mode. Then the {@link #accept} 74 * method is used to accept a connection initiated by a 75 * target VM. 76 * 77 * @since 1.5 78 */ 79 80 public abstract class TransportService { 81 82 /** 83 * Returns a name to identify the transport service. 84 * 85 * @return The name of the transport service 86 */ 87 public abstract String name(); 88 89 /** 90 * Returns a description of the transport service. 91 * 92 * @return The description of the transport service 93 */ 94 public abstract String description(); 95 96 /** 97 * The transport service capabilities. 98 */ 99 public static abstract class Capabilities { 100 101 /** 102 * Tells whether or not this transport service can support 103 * multiple concurrent connections to a single address that 104 * it is listening on. 105 * 106 * @return <tt>true</tt> if, and only if, this transport 107 * service supports multiple connections. 108 */ 109 public abstract boolean supportsMultipleConnections(); 110 111 112 /** 113 * Tell whether or not this transport service supports a timeout 114 * when attaching to a target VM. 115 * 116 * @return <tt>true</tt> if, and only if, this transport 117 * service supports attaching with a timeout. 118 * 119 * @see #attach(String,long,long) 120 */ 121 public abstract boolean supportsAttachTimeout(); 122 123 /** 124 * Tell whether or not this transport service supports a 125 * timeout while waiting for a target VM to connect. 126 * 127 * @return <tt>true</tt> if, and only if, this transport 128 * service supports timeout while waiting for 129 * a target VM to connect. 130 * 131 * @see #accept(TransportService.ListenKey,long,long) 132 */ 133 public abstract boolean supportsAcceptTimeout(); 134 135 /** 136 * Tells whether or not this transport service supports a 137 * timeout when handshaking with the target VM. 138 * 139 * @return <tt>true</tt> if, and only if, this transport 140 * service supports a timeout while handshaking 141 * with the target VM. 142 * 143 * @see #attach(String,long,long) 144 * @see #accept(TransportService.ListenKey,long,long) 145 */ 146 public abstract boolean supportsHandshakeTimeout(); 147 148 } 149 150 /** 151 * Returns the capabilities of the transport service. 152 * 153 * @return the transport service capabilities 154 */ 155 public abstract Capabilities capabilities(); 156 157 /** 158 * Attaches to the specified address. 159 * 160 * <p> Attaches to the specified address and returns a connection 161 * representing the bi-directional communication channel to the 162 * target VM. 163 * 164 * <p> Attaching to the target VM involves two steps: 165 * First, a connection is established to specified address. This 166 * is followed by a handshake to ensure that the connection is 167 * to a target VM. The handshake involves the exchange 168 * of a string <i>JDWP-Handshake</i> as specified in the <a 169 * href="../../../../../../../../../technotes/guides/jpda/jdwp-spec.html"> 170 * Java Debug Wire Protocol</a> specification. 171 * 172 * @param address 173 * The address of the target VM. 174 * 175 * @param attachTimeout 176 * If this transport service supports an attach timeout, 177 * and if <tt>attachTimeout</tt> is positive, then it specifies 178 * the timeout, in milliseconds (more or less), to use 179 * when attaching to the target VM. If the transport service 180 * does not support an attach timeout, or if <tt>attachTimeout</tt> 181 * is specified as zero then attach without any timeout. 182 * 183 * @param handshakeTimeout 184 * If this transport service supports a handshake timeout, 185 * and if <tt>handshakeTimeout</tt> is positive, then it 186 * specifies the timeout, in milliseconds (more or less), to 187 * use when handshaking with the target VM. The exact 188 * usage of the timeout are specific to the transport service. 189 * A transport service may, for example, use the handshake 190 * timeout as the inter-character timeout while waiting for 191 * the <i>JDWP-Handshake</i> message from the target VM. 192 * Alternatively, a transport service may, for example, 193 * use the handshakeTimeout as a timeout for the duration of the 194 * handshake exchange. 195 * If the transport service does not support a handshake 196 * timeout, or if <tt>handshakeTimeout</tt> is specified 197 * as zero then the handshake does not timeout if there 198 * isn't a response from the target VM. 199 * 200 * @return The Connection representing the bi-directional 201 * communication channel to the target VM. 202 * 203 * @throws TransportTimeoutException 204 * If a timeout occurs while establishing the connection. 205 * 206 * @throws IOException 207 * If an I/O error occurs (including a timeout when 208 * handshaking). 209 * 210 * @throws IllegalArgumentException 211 * If the address is invalid or the value of the 212 * attach timeout or handshake timeout is negative. 213 * 214 * @see TransportService.Capabilities#supportsAttachTimeout() 215 */ 216 public abstract Connection attach(String address, long attachTimeout, 217 long handshakeTimeout) throws IOException; 218 219 /** 220 * A <i>listen key</i>. 221 * 222 * <p> A <tt>TransportService</tt> may listen on multiple, yet 223 * different, addresses at the same time. To uniquely identify 224 * each <tt>listener</tt> a listen key is created each time that 225 * {@link #startListening startListening} is called. The listen 226 * key is used in calls to the {@link #accept accept} method 227 * to accept inbound connections to that listener. A listen 228 * key is valid until it is used as an argument to {@link 229 * #stopListening stopListening} to stop the transport 230 * service from listening on an address. 231 */ 232 public static abstract class ListenKey { 233 234 /** 235 * Returns a string representation of the listen key. 236 */ 237 public abstract String address(); 238 } 239 240 /** 241 * Listens on the specified address for inbound connections. 242 * 243 * <p> This method starts the transport service listening on 244 * the specified address so that it can subsequently accept 245 * an inbound connection. It does not wait until an inbound 246 * connection is established. 247 * 248 * @param address 249 * The address to start listening for connections, 250 * or <tt>null</tt> to listen on an address choosen 251 * by the transport service. 252 * 253 * @return a listen key to be used in subsequent calls to be 254 * {@link #accept accept} or {@link #stopListening 255 * stopListening} methods. 256 * 257 * @throws IOException 258 * If an I/O error occurs. 259 * 260 * @throws IllegalArgumentException 261 * If the specific address is invalid 262 */ 263 public abstract ListenKey startListening(String address) throws IOException; 264 265 /** 266 * Listens on an address choosen by the transport service. 267 * 268 * <p> This convenience method works as if by invoking {@link 269 * #startListening(String) startListening(<tt>null</tt>)}. </p> 270 * 271 * @return a listen key to be used in subsequent calls to be 272 * {@link #accept accept} or {@link #stopListening 273 * stopListening} methods. 274 * 275 * @throws IOException 276 * If an I/O error occurs. 277 */ 278 public abstract ListenKey startListening() throws IOException; 279 280 /** 281 * Stop listening for inbound connections. 282 * 283 * <p> Invoking this method while another thread is blocked 284 * in {@link #accept accept}, with the same listen key, 285 * waiting to accept a connection will cause that thread to 286 * throw an IOException. If the thread blocked in accept 287 * has already accepted a connection from a target VM and 288 * is in the process of handshaking with the target VM then 289 * invoking this method will not cause the thread to throw 290 * an exception. 291 * 292 * @param listenKey 293 * The listen key obtained from a previous call to {@link 294 * #startListening(String)} or {@link #startListening()}. 295 * 296 * @throws IllegalArgumentException 297 * If the listen key is invalid 298 * 299 * @throws IOException 300 * If an I/O error occurs. 301 */ 302 public abstract void stopListening(ListenKey listenKey) throws IOException; 303 304 /** 305 * Accept a connection from a target VM. 306 * 307 * <p> Waits (indefinitely or with timeout) to accept a connection 308 * from a target VM. Returns a connection representing the 309 * bi-directional communication channel to the target VM. 310 * 311 * <p> Accepting a connection from a target VM involves two 312 * steps. First, the transport service waits to accept 313 * the connection from the target VM. Once the connection is 314 * established a handshake is performed to ensure that the 315 * connection is indeed to a target VM. The handshake involves 316 * the exchange of a string <i>JDWP-Handshake</i> as specified 317 * in the <a 318 * href="../../../../../../../../../technotes/guides/jpda/jdwp-spec.html"> 319 * Java Debug Wire Protocol</a> specification. 320 * 321 * @param listenKey 322 * A listen key obtained from a previous call to {@link 323 * #startListening(String)} or {@link #startListening()}. 324 * 325 * @param acceptTimeout 326 * if this transport service supports an accept timeout, and 327 * if <tt>acceptTimeout</tt> is positive then block for up to 328 * <tt>acceptTimeout</tt> milliseconds, more or less, while waiting 329 * for the target VM to connect. 330 * If the transport service does not support an accept timeout 331 * or if <tt>acceptTimeout</tt> is zero then block indefinitely 332 * for a target VM to connect. 333 * 334 * @param handshakeTimeout 335 * If this transport service supports a handshake timeout, 336 * and if <tt>handshakeTimeout</tt> is positive, then it 337 * specifies the timeout, in milliseconds (more or less), to 338 * use when handshaking with the target VM. The exact 339 * usage of the timeout is specific to the transport service. 340 * A transport service may, for example, use the handshake 341 * timeout as the inter-character timeout while waiting for 342 * the <i>JDWP-Handshake</i> message from the target VM. 343 * Alternatively, a transport service may, for example, 344 * use the timeout as a timeout for the duration of the 345 * handshake exchange. 346 * If the transport service does not support a handshake 347 * timeout, of if <tt>handshakeTimeout</tt> is specified 348 * as zero then the handshake does not timeout if there 349 * isn't a response from the target VM. 350 * 351 * @return The Connection representing the bi-directional 352 * communication channel to the target VM. 353 * 354 * @throws TransportTimeoutException 355 * If a timeout occurs while waiting for a target VM 356 * to connect. 357 * 358 * @throws IOException 359 * If an I/O error occurs (including a timeout when 360 * handshaking). 361 * 362 * @throws IllegalArgumentException 363 * If the value of the acceptTimeout argument, or 364 * handshakeTimeout is negative, or an invalid listen key 365 * is provided. 366 * 367 * @throws IllegalStateException 368 * If {@link #stopListening stopListening} has already been 369 * called with this listen key and the transport service 370 * is no longer listening for inbound connections. 371 * 372 * @see TransportService.Capabilities#supportsAcceptTimeout() 373 */ 374 public abstract Connection accept(ListenKey listenKey, long acceptTimeout, 375 long handshakeTimeout) throws IOException; 376 377 }