View Javadoc

1   /**
2    *  BlueCove - Java library for Bluetooth
3    *  Copyright (C) 2006-2008 Vlad Skarzhevskyy
4    *
5    *  Licensed to the Apache Software Foundation (ASF) under one
6    *  or more contributor license agreements.  See the NOTICE file
7    *  distributed with this work for additional information
8    *  regarding copyright ownership.  The ASF licenses this file
9    *  to you under the Apache License, Version 2.0 (the
10   *  "License"); you may not use this file except in compliance
11   *  with the License.  You may obtain a copy of the License at
12   *
13   *    http://www.apache.org/licenses/LICENSE-2.0
14   *
15   *  Unless required by applicable law or agreed to in writing,
16   *  software distributed under the License is distributed on an
17   *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
18   *  KIND, either express or implied.  See the License for the
19   *  specific language governing permissions and limitations
20   *  under the License.
21   *
22   *  @author vlads
23   *  @version $Id: BluetoothL2CAPConnection.java 2476 2008-12-01 17:41:59Z skarzhevskyy $
24   */
25  package com.intel.bluetooth;
26  
27  import java.io.IOException;
28  
29  import javax.bluetooth.L2CAPConnection;
30  import javax.bluetooth.RemoteDevice;
31  import javax.bluetooth.ServiceRecord;
32  
33  /**
34   *
35   *
36   */
37  abstract class BluetoothL2CAPConnection implements L2CAPConnection, BluetoothConnectionAccess {
38  
39  	protected BluetoothStack bluetoothStack;
40  
41  	protected volatile long handle;
42  
43  	protected int securityOpt;
44  
45  	private RemoteDevice remoteDevice;
46  
47  	private boolean isClosed;
48  
49  	protected BluetoothL2CAPConnection(BluetoothStack bluetoothStack, long handle) {
50  		this.bluetoothStack = bluetoothStack;
51  		this.handle = handle;
52  		this.isClosed = false;
53  	}
54  
55  	/*
56  	 * (non-Javadoc)
57  	 *
58  	 * @see com.intel.bluetooth.BluetoothConnectionAccess#getRemoteAddress()
59  	 */
60  	public long getRemoteAddress() throws IOException {
61  		if (isClosed) {
62  			throw new IOException("Connection closed");
63  		}
64  		return bluetoothStack.l2RemoteAddress(handle);
65  	}
66  
67  	/*
68  	 * (non-Javadoc)
69  	 *
70  	 * @see javax.bluetooth.L2CAPConnection#getReceiveMTU()
71  	 */
72  	public int getReceiveMTU() throws IOException {
73  		if (isClosed) {
74  			throw new IOException("Connection closed");
75  		}
76  		return bluetoothStack.l2GetReceiveMTU(handle);
77  	}
78  
79  	/*
80  	 * (non-Javadoc)
81  	 *
82  	 * @see javax.bluetooth.L2CAPConnection#getTransmitMTU()
83  	 */
84  	public int getTransmitMTU() throws IOException {
85  		if (isClosed) {
86  			throw new IOException("Connection closed");
87  		}
88  		return bluetoothStack.l2GetTransmitMTU(handle);
89  	}
90  
91  	/*
92  	 * (non-Javadoc)
93  	 *
94  	 * @see javax.bluetooth.L2CAPConnection#ready()
95  	 */
96  	public boolean ready() throws IOException {
97  		if (isClosed) {
98  			throw new IOException("Connection closed");
99  		}
100 		return bluetoothStack.l2Ready(handle);
101 	}
102 
103 	/*
104 	 * (non-Javadoc)
105 	 *
106 	 * @see javax.bluetooth.L2CAPConnection#receive(byte[])
107 	 */
108 	public int receive(byte[] inBuf) throws IOException {
109 		if (isClosed) {
110 			throw new IOException("Connection closed");
111 		}
112 		if (inBuf == null) {
113 			throw new NullPointerException("inBuf is null");
114 		}
115 		return bluetoothStack.l2Receive(handle, inBuf);
116 	}
117 
118 	/*
119 	 * (non-Javadoc)
120 	 *
121 	 * @see javax.bluetooth.L2CAPConnection#send(byte[])
122 	 */
123 	public void send(byte[] data) throws IOException {
124 		if (isClosed) {
125 			throw new IOException("Connection closed");
126 		}
127 		if (data == null) {
128 			throw new NullPointerException("data is null");
129 		}
130 		bluetoothStack.l2Send(handle, data);
131 	}
132 
133 	abstract void closeConnectionHandle(long handle) throws IOException;
134 
135 	/*
136 	 * (non-Javadoc)
137 	 *
138 	 * @see javax.microedition.io.Connection#close()
139 	 */
140 	public void close() throws IOException {
141 		if (isClosed) {
142 			return;
143 		}
144 
145 		isClosed = true;
146 		shutdown();
147 	}
148 
149 	/*
150 	 * (non-Javadoc)
151 	 *
152 	 * @see com.intel.bluetooth.BluetoothConnectionAccess#shutdown()
153 	 */
154 	public void shutdown() throws IOException {
155 		if (handle != 0) {
156 			DebugLog.debug("closing L2CAP Connection", handle);
157 			// close() can be called safely in another thread
158 			long synchronizedHandle;
159 			synchronized (this) {
160 				synchronizedHandle = handle;
161 				handle = 0;
162 			}
163 			if (synchronizedHandle != 0) {
164 				closeConnectionHandle(synchronizedHandle);
165 			}
166 		}
167 	}
168 
169 	protected void finalize() {
170 		try {
171 			close();
172 		} catch (IOException e) {
173 		}
174 	}
175 
176 	/*
177 	 * (non-Javadoc)
178 	 *
179 	 * @see com.intel.bluetooth.BluetoothConnectionAccess#isClosed()
180 	 */
181 	public boolean isClosed() {
182 		return isClosed;
183 	}
184 
185 	/*
186 	 * (non-Javadoc)
187 	 *
188 	 * @see com.intel.bluetooth.BluetoothConnectionAccess#markAuthenticated()
189 	 */
190 	public void markAuthenticated() {
191 		if (this.securityOpt == ServiceRecord.NOAUTHENTICATE_NOENCRYPT) {
192 			this.securityOpt = ServiceRecord.AUTHENTICATE_NOENCRYPT;
193 		}
194 	}
195 
196 	/*
197 	 * (non-Javadoc)
198 	 *
199 	 * @see com.intel.bluetooth.BluetoothConnectionAccess#getSecurityOpt()
200 	 */
201 	public int getSecurityOpt() {
202 		try {
203 			this.securityOpt = bluetoothStack.l2GetSecurityOpt(this.handle, this.securityOpt);
204 		} catch (IOException notChanged) {
205 		}
206 		return this.securityOpt;
207 	}
208 
209 	/*
210 	 * (non-Javadoc)
211 	 *
212 	 * @see com.intel.bluetooth.BluetoothConnectionAccess#encrypt(boolean)
213 	 * @see javax.bluetooth.RemoteDevice#encrypt(Connection , boolean)
214 	 */
215 	public boolean encrypt(long address, boolean on) throws IOException {
216 		if (isClosed) {
217 			throw new IOException("L2CAP Connection is already closed");
218 		}
219 		boolean changed = bluetoothStack.l2Encrypt(address, this.handle, on);
220 		if (changed) {
221 			if (on) {
222 				this.securityOpt = ServiceRecord.AUTHENTICATE_ENCRYPT;
223 			} else {
224 				this.securityOpt = ServiceRecord.AUTHENTICATE_NOENCRYPT;
225 			}
226 		}
227 		return changed;
228 	}
229 
230 	/*
231 	 * (non-Javadoc)
232 	 *
233 	 * @see com.intel.bluetooth.BluetoothConnectionAccess#getRemoteDevice()
234 	 */
235 	public RemoteDevice getRemoteDevice() {
236 		return this.remoteDevice;
237 	}
238 
239 	/*
240 	 * (non-Javadoc)
241 	 *
242 	 * @see com.intel.bluetooth.BluetoothConnectionAccess#setRemoteDevice(javax.bluetooth.RemoteDevice)
243 	 */
244 	public void setRemoteDevice(RemoteDevice remoteDevice) {
245 		this.remoteDevice = remoteDevice;
246 	}
247 
248 	/*
249 	 * (non-Javadoc)
250 	 *
251 	 * @see com.intel.bluetooth.BluetoothConnectionAccess#getBluetoothStack()
252 	 */
253 	public BluetoothStack getBluetoothStack() {
254 		return bluetoothStack;
255 	}
256 
257 }