BluetoothSocket.java revision 47e82dee6b18c33fab8c2cdf4f68b20d3663079e
1/* 2 * Copyright (C) 2009 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package android.bluetooth; 18 19import java.io.Closeable; 20import java.io.IOException; 21import java.io.InputStream; 22import java.io.OutputStream; 23 24/** 25 * Represents a connected or connecting Bluetooth Socket. 26 * 27 * Currently only supports RFCOMM sockets. 28 * 29 * RFCOMM is a connection orientated, streaming transport over Bluetooth. It is 30 * also known as the Serial Port Profile (SPP). 31 * 32 * TODO: Consider implementing SCO and L2CAP sockets. 33 * TODO: Clean up javadoc grammer and formatting. 34 * TODO: Remove @hide 35 * @hide 36 */ 37public final class BluetoothSocket implements Closeable { 38 private final int mPort; 39 private final String mAddress; /* remote address */ 40 private final boolean mAuth; 41 private final boolean mEncrypt; 42 private final BluetoothInputStream mInputStream; 43 private final BluetoothOutputStream mOutputStream; 44 45 private int mSocketData; /* used by native code only */ 46 47 /** 48 * Construct a secure RFCOMM socket ready to start an outgoing connection. 49 * Call #connect on the returned #BluetoothSocket to begin the connection. 50 * The remote device will be authenticated and communication on this socket 51 * will be encrypted. 52 * @param address remote Bluetooth address that this socket can connect to 53 * @param port remote port 54 * @return an RFCOMM BluetoothSocket 55 * @throws IOException on error, for example Bluetooth not available, or 56 * insufficient permissions. 57 */ 58 public static BluetoothSocket createRfcommSocket(String address, int port) 59 throws IOException { 60 return new BluetoothSocket(-1, true, true, address, port); 61 } 62 63 /** 64 * Construct an insecure RFCOMM socket ready to start an outgoing 65 * connection. 66 * Call #connect on the returned #BluetoothSocket to begin the connection. 67 * The remote device will not be authenticated and communication on this 68 * socket will not be encrypted. 69 * @param address remote Bluetooth address that this socket can connect to 70 * @param port remote port 71 * @return An RFCOMM BluetoothSocket 72 * @throws IOException On error, for example Bluetooth not available, or 73 * insufficient permissions. 74 */ 75 public static BluetoothSocket createInsecureRfcommSocket(String address, int port) 76 throws IOException { 77 return new BluetoothSocket(-1, false, false, address, port); 78 } 79 80 /** 81 * Construct a Bluetooth. 82 * @param fd fd to use for connected socket, or -1 for a new socket 83 * @param auth require the remote device to be authenticated 84 * @param encrypt require the connection to be encrypted 85 * @param address remote Bluetooth address that this socket can connect to 86 * @param port remote port 87 * @throws IOException On error, for example Bluetooth not available, or 88 * insufficient priveleges 89 */ 90 /*package*/ BluetoothSocket(int fd, boolean auth, boolean encrypt, String address, int port) 91 throws IOException { 92 mAuth = auth; 93 mEncrypt = encrypt; 94 mAddress = address; 95 mPort = port; 96 if (fd == -1) { 97 initSocketNative(); 98 } else { 99 initSocketFromFdNative(fd); 100 } 101 mInputStream = new BluetoothInputStream(this); 102 mOutputStream = new BluetoothOutputStream(this); 103 } 104 105 @Override 106 protected void finalize() throws Throwable { 107 try { 108 close(); 109 } finally { 110 super.finalize(); 111 } 112 } 113 114 /** 115 * Attempt to connect to a remote device. 116 * This method will block until a connection is made or the connection 117 * fails. If this method returns without an exception then this socket 118 * is now connected. #close can be used to abort this call from another 119 * thread. 120 * @throws IOException On error, for example connection failure 121 */ 122 public void connect() throws IOException { 123 connectNative(mAddress, mPort, -1); 124 } 125 126 /** 127 * Closes this socket. 128 * This will cause other blocking calls on this socket to immediately 129 * throw an IOException. 130 */ 131 public void close() throws IOException { 132 closeNative(); 133 } 134 135 /** 136 * Return the address we are connecting, or connected, to. 137 * @return Bluetooth address, or null if this socket has not yet attempted 138 * or established a connection. 139 */ 140 public String getAddress() { 141 return mAddress; 142 } 143 144 /** 145 * Get the input stream associated with this socket. 146 * The input stream will be returned even if the socket is not yet 147 * connected, but operations on that stream will throw IOException until 148 * the associated socket is connected. 149 * @return InputStream 150 */ 151 public InputStream getInputStream() throws IOException { 152 return mInputStream; 153 } 154 155 /** 156 * Get the output stream associated with this socket. 157 * The output stream will be returned even if the socket is not yet 158 * connected, but operations on that stream will throw IOException until 159 * the associated socket is connected. 160 * @return OutputStream 161 */ 162 public OutputStream getOutputStream() throws IOException { 163 return mOutputStream; 164 } 165 166 private native void initSocketNative(); 167 private native void initSocketFromFdNative(int fd); 168 private native void connectNative(String address, int port, int timeout); 169 /*package*/ native void bindListenNative(int port) throws IOException; 170 /*package*/ native BluetoothSocket acceptNative(int timeout) throws IOException; 171 /*package*/ native int availableNative(); 172 /*package*/ native int readNative(byte[] b, int offset, int length); 173 /*package*/ native int writeNative(byte[] b, int offset, int length); 174 /*package*/ native void closeNative(); 175 private native void destroyNative(); 176} 177