1ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh/* 22c0df0560ad5ae3fd6022b17b17a6a70143e216aHemant Gupta * Copyright (C) 2012-2014 The Android Open Source Project 3ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * 4ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * Licensed under the Apache License, Version 2.0 (the "License"); 5ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * you may not use this file except in compliance with the License. 6ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * You may obtain a copy of the License at 7ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * 8ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * http://www.apache.org/licenses/LICENSE-2.0 9ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * 10ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * Unless required by applicable law or agreed to in writing, software 11ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * distributed under the License is distributed on an "AS IS" BASIS, 12ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * See the License for the specific language governing permissions and 14ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * limitations under the License. 15ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 16ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 17ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshpackage com.android.bluetooth.btservice; 18ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 19ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshimport android.bluetooth.BluetoothAdapter; 20ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshimport android.bluetooth.BluetoothClass; 21ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshimport android.bluetooth.BluetoothDevice; 22ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshimport android.content.Intent; 23ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshimport android.os.Handler; 24ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshimport android.os.Message; 25ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshimport android.os.ParcelUuid; 26ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshimport android.util.Log; 27ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 28ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshimport com.android.bluetooth.Utils; 29ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 307aa3a71e508e4f95a0a74f41ab8389979809191bJay Civelliimport java.util.concurrent.atomic.AtomicInteger; 31ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshimport java.util.ArrayList; 32ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshimport java.util.HashMap; 33ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 34ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 35ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshfinal class RemoteDevices { 36fd1da115cbf09b7dd9bca3c7d3a4fb816a835dc5Matthew Xie private static final boolean DBG = false; 37ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private static final String TAG = "BluetoothRemoteDevices"; 38ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 3974ae04c73312403e89db0f8e9bd9601d403b4783fredc 40ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private static BluetoothAdapter mAdapter; 41ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private static AdapterService mAdapterService; 42ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private static ArrayList<BluetoothDevice> mSdpTracker; 43ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private Object mObject = new Object(); 44ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 45ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private static final int UUID_INTENT_DELAY = 6000; 46ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private static final int MESSAGE_UUID_INTENT = 1; 47ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 48ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private HashMap<BluetoothDevice, DeviceProperties> mDevices; 49ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 5074ae04c73312403e89db0f8e9bd9601d403b4783fredc RemoteDevices(AdapterService service) { 51ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh mAdapter = BluetoothAdapter.getDefaultAdapter(); 52ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh mAdapterService = service; 53ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh mSdpTracker = new ArrayList<BluetoothDevice>(); 54ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh mDevices = new HashMap<BluetoothDevice, DeviceProperties>(); 55ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 56ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 57ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 5874ae04c73312403e89db0f8e9bd9601d403b4783fredc void cleanup() { 5915d36984a79d6e35c659edb0efdf929f0b526bd5Fred if (mSdpTracker !=null) 6015d36984a79d6e35c659edb0efdf929f0b526bd5Fred mSdpTracker.clear(); 6115d36984a79d6e35c659edb0efdf929f0b526bd5Fred 6215d36984a79d6e35c659edb0efdf929f0b526bd5Fred if (mDevices != null) 6315d36984a79d6e35c659edb0efdf929f0b526bd5Fred mDevices.clear(); 646654f5c903de510a70f9e72cd5ad7837b615d93ffredc } 656654f5c903de510a70f9e72cd5ad7837b615d93ffredc 663a91ac3eefe23a22aa0abc1a89ac253a2b0dbae9Nick Kralevich @Override 673a91ac3eefe23a22aa0abc1a89ac253a2b0dbae9Nick Kralevich public Object clone() throws CloneNotSupportedException { 68ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh throw new CloneNotSupportedException(); 69ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 70ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 71ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh DeviceProperties getDeviceProperties(BluetoothDevice device) { 72ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh synchronized (mDevices) { 73ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return mDevices.get(device); 74ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 75ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 76ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 77ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh BluetoothDevice getDevice(byte[] address) { 78ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh for (BluetoothDevice dev : mDevices.keySet()) { 79ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (dev.getAddress().equals(Utils.getAddressStringFromByte(address))) { 80ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return dev; 81ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 82ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 83ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return null; 84ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 85ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 86ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh DeviceProperties addDeviceProperties(byte[] address) { 87ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh synchronized (mDevices) { 88ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh DeviceProperties prop = new DeviceProperties(); 89ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh BluetoothDevice device = 90ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh mAdapter.getRemoteDevice(Utils.getAddressStringFromByte(address)); 9174a598e0a8d50343227e3f96bbe56c6be1c240f9Ganesh Ganapathi Batta prop.mAddress = address; 92ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh mDevices.put(device, prop); 93ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return prop; 94ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 95ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 96ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 97ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh class DeviceProperties { 98ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private String mName; 99ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private byte[] mAddress; 100ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private int mBluetoothClass; 101ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private short mRssi; 102ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private ParcelUuid[] mUuids; 103ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private int mDeviceType; 104ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private String mAlias; 105ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private int mBondState; 106ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 107ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh DeviceProperties() { 108ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh mBondState = BluetoothDevice.BOND_NONE; 109ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 110ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 111ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh /** 112ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh * @return the mName 113ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 114ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh String getName() { 115ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh synchronized (mObject) { 116ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return mName; 117ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 118ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 119ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 120ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh /** 121ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh * @return the mClass 122ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 123ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int getBluetoothClass() { 124ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh synchronized (mObject) { 125ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return mBluetoothClass; 126ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 127ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 128ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 129ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh /** 130ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh * @return the mUuids 131ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 132ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh ParcelUuid[] getUuids() { 133ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh synchronized (mObject) { 134ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return mUuids; 135ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 136ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 137ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 138ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh /** 139ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh * @return the mAddress 140ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 141ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh byte[] getAddress() { 142ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh synchronized (mObject) { 143ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return mAddress; 144ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 145ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 146ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 147ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh /** 148ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh * @return mRssi 149ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 150ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh short getRssi() { 151ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh synchronized (mObject) { 152ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return mRssi; 153ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 154ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 155ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 156ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh /** 157ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh * @return mDeviceType 158ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 159ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int getDeviceType() { 160ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh synchronized (mObject) { 161ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return mDeviceType; 162ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 163ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 164ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 165ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh /** 166ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh * @return the mAlias 167ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 168ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh String getAlias() { 169ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh synchronized (mObject) { 170ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return mAlias; 171ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 172ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 173ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 174ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh /** 175ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh * @param mAlias the mAlias to set 176ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 17753b1dc1c00aea1aabbdbc6efd7be0cba6bf397a2Andre Eisenbach void setAlias(BluetoothDevice device, String mAlias) { 178ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh synchronized (mObject) { 17974277677d2a51d7c8ff60a778889f71e69763c21Matthew Xie this.mAlias = mAlias; 180ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh mAdapterService.setDevicePropertyNative(mAddress, 181ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh AbstractionLayer.BT_PROPERTY_REMOTE_FRIENDLY_NAME, mAlias.getBytes()); 18253b1dc1c00aea1aabbdbc6efd7be0cba6bf397a2Andre Eisenbach Intent intent = new Intent(BluetoothDevice.ACTION_ALIAS_CHANGED); 18353b1dc1c00aea1aabbdbc6efd7be0cba6bf397a2Andre Eisenbach intent.putExtra(BluetoothDevice.EXTRA_DEVICE, device); 18453b1dc1c00aea1aabbdbc6efd7be0cba6bf397a2Andre Eisenbach intent.putExtra(BluetoothDevice.EXTRA_NAME, mAlias); 18553b1dc1c00aea1aabbdbc6efd7be0cba6bf397a2Andre Eisenbach mAdapterService.sendBroadcast(intent, AdapterService.BLUETOOTH_PERM); 186ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 187ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 188ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 189ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh /** 190ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh * @param mBondState the mBondState to set 191ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 192ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh void setBondState(int mBondState) { 193ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh synchronized (mObject) { 194ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh this.mBondState = mBondState; 195d807ba48ed4418c1a60549abe1c3a98ced8c428dSreenidhi T if (mBondState == BluetoothDevice.BOND_NONE) 196d807ba48ed4418c1a60549abe1c3a98ced8c428dSreenidhi T { 197d807ba48ed4418c1a60549abe1c3a98ced8c428dSreenidhi T /* Clearing the Uuids local copy when the device is unpaired. If not cleared, 198d807ba48ed4418c1a60549abe1c3a98ced8c428dSreenidhi T cachedBluetoothDevice issued a connect using the local cached copy of uuids, 199d807ba48ed4418c1a60549abe1c3a98ced8c428dSreenidhi T without waiting for the ACTION_UUID intent. 200d807ba48ed4418c1a60549abe1c3a98ced8c428dSreenidhi T This was resulting in multiple calls to connect().*/ 201d807ba48ed4418c1a60549abe1c3a98ced8c428dSreenidhi T mUuids = null; 202d807ba48ed4418c1a60549abe1c3a98ced8c428dSreenidhi T } 203ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 204ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 205ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 206ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh /** 207ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh * @return the mBondState 208ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 209ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int getBondState() { 210ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh synchronized (mObject) { 211ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return mBondState; 212ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 213ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 2147aa3a71e508e4f95a0a74f41ab8389979809191bJay Civelli } 215ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 216ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private void sendUuidIntent(BluetoothDevice device) { 217ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh DeviceProperties prop = getDeviceProperties(device); 218ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh Intent intent = new Intent(BluetoothDevice.ACTION_UUID); 219ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh intent.putExtra(BluetoothDevice.EXTRA_DEVICE, device); 220c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc intent.putExtra(BluetoothDevice.EXTRA_UUID, prop == null? null: prop.mUuids); 22134409f35db6e9ca74f727e3fe92141388ae5b069Ganesh Ganapathi Batta mAdapterService.initProfilePriorities(device, prop.mUuids); 22274ae04c73312403e89db0f8e9bd9601d403b4783fredc mAdapterService.sendBroadcast(intent, AdapterService.BLUETOOTH_ADMIN_PERM); 223c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc 224c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc //Remove the outstanding UUID request 225c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc mSdpTracker.remove(device); 226ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 227ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 22811b41d8123241ba8e693e21c4db308bacff23f57Mudumba Ananth 229ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh void devicePropertyChangedCallback(byte[] address, int[] types, byte[][] values) { 230ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh Intent intent; 231ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh byte[] val; 232ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int type; 233ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh BluetoothDevice bdDevice = getDevice(address); 234ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh DeviceProperties device; 235ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (bdDevice == null) { 236ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh device = addDeviceProperties(address); 237ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh bdDevice = getDevice(address); 238ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } else { 239ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh device = getDeviceProperties(bdDevice); 240ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 241ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 242ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh for (int j = 0; j < types.length; j++) { 243ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh type = types[j]; 244ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh val = values[j]; 245caa3723eaa20e57aac086d54a41106108503debczzy if(val.length <= 0) 2465a60e47497f21f64e6d79420dc4c56c1907df22akschulz errorLog("devicePropertyChangedCallback: bdDevice: " + bdDevice 247bbb4110b455b3aa29106d5b4f0a37e1be8e09475Casper Bonde + ", value is empty for type: " + type); 248caa3723eaa20e57aac086d54a41106108503debczzy else { 249caa3723eaa20e57aac086d54a41106108503debczzy synchronized(mObject) { 250caa3723eaa20e57aac086d54a41106108503debczzy switch (type) { 251caa3723eaa20e57aac086d54a41106108503debczzy case AbstractionLayer.BT_PROPERTY_BDNAME: 252caa3723eaa20e57aac086d54a41106108503debczzy device.mName = new String(val); 253caa3723eaa20e57aac086d54a41106108503debczzy intent = new Intent(BluetoothDevice.ACTION_NAME_CHANGED); 254caa3723eaa20e57aac086d54a41106108503debczzy intent.putExtra(BluetoothDevice.EXTRA_DEVICE, bdDevice); 255caa3723eaa20e57aac086d54a41106108503debczzy intent.putExtra(BluetoothDevice.EXTRA_NAME, device.mName); 256caa3723eaa20e57aac086d54a41106108503debczzy intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT); 257caa3723eaa20e57aac086d54a41106108503debczzy mAdapterService.sendBroadcast(intent, mAdapterService.BLUETOOTH_PERM); 258caa3723eaa20e57aac086d54a41106108503debczzy debugLog("Remote Device name is: " + device.mName); 259caa3723eaa20e57aac086d54a41106108503debczzy break; 260caa3723eaa20e57aac086d54a41106108503debczzy case AbstractionLayer.BT_PROPERTY_REMOTE_FRIENDLY_NAME: 261caa3723eaa20e57aac086d54a41106108503debczzy if (device.mAlias != null) { 262caa3723eaa20e57aac086d54a41106108503debczzy System.arraycopy(val, 0, device.mAlias, 0, val.length); 263caa3723eaa20e57aac086d54a41106108503debczzy } 2640322ae1f5e8ea55c391145e7925cb5962a97c11fGanesh Ganapathi Batta else { 2650322ae1f5e8ea55c391145e7925cb5962a97c11fGanesh Ganapathi Batta device.mAlias = new String(val); 2660322ae1f5e8ea55c391145e7925cb5962a97c11fGanesh Ganapathi Batta } 267caa3723eaa20e57aac086d54a41106108503debczzy break; 268caa3723eaa20e57aac086d54a41106108503debczzy case AbstractionLayer.BT_PROPERTY_BDADDR: 269caa3723eaa20e57aac086d54a41106108503debczzy device.mAddress = val; 270caa3723eaa20e57aac086d54a41106108503debczzy debugLog("Remote Address is:" + Utils.getAddressStringFromByte(val)); 271caa3723eaa20e57aac086d54a41106108503debczzy break; 272caa3723eaa20e57aac086d54a41106108503debczzy case AbstractionLayer.BT_PROPERTY_CLASS_OF_DEVICE: 273caa3723eaa20e57aac086d54a41106108503debczzy device.mBluetoothClass = Utils.byteArrayToInt(val); 274caa3723eaa20e57aac086d54a41106108503debczzy intent = new Intent(BluetoothDevice.ACTION_CLASS_CHANGED); 275caa3723eaa20e57aac086d54a41106108503debczzy intent.putExtra(BluetoothDevice.EXTRA_DEVICE, bdDevice); 276caa3723eaa20e57aac086d54a41106108503debczzy intent.putExtra(BluetoothDevice.EXTRA_CLASS, 277caa3723eaa20e57aac086d54a41106108503debczzy new BluetoothClass(device.mBluetoothClass)); 278caa3723eaa20e57aac086d54a41106108503debczzy intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT); 279caa3723eaa20e57aac086d54a41106108503debczzy mAdapterService.sendBroadcast(intent, mAdapterService.BLUETOOTH_PERM); 280caa3723eaa20e57aac086d54a41106108503debczzy debugLog("Remote class is:" + device.mBluetoothClass); 281caa3723eaa20e57aac086d54a41106108503debczzy break; 282caa3723eaa20e57aac086d54a41106108503debczzy case AbstractionLayer.BT_PROPERTY_UUIDS: 283caa3723eaa20e57aac086d54a41106108503debczzy int numUuids = val.length/AbstractionLayer.BT_UUID_SIZE; 284caa3723eaa20e57aac086d54a41106108503debczzy device.mUuids = Utils.byteArrayToUuid(val); 285caa3723eaa20e57aac086d54a41106108503debczzy sendUuidIntent(bdDevice); 286caa3723eaa20e57aac086d54a41106108503debczzy break; 287caa3723eaa20e57aac086d54a41106108503debczzy case AbstractionLayer.BT_PROPERTY_TYPE_OF_DEVICE: 288d235269f06e99d76a0f63c8fe9e224e0f951f799Matthew Xie // The device type from hal layer, defined in bluetooth.h, 289d235269f06e99d76a0f63c8fe9e224e0f951f799Matthew Xie // matches the type defined in BluetoothDevice.java 290caa3723eaa20e57aac086d54a41106108503debczzy device.mDeviceType = Utils.byteArrayToInt(val); 291caa3723eaa20e57aac086d54a41106108503debczzy break; 292caa3723eaa20e57aac086d54a41106108503debczzy case AbstractionLayer.BT_PROPERTY_REMOTE_RSSI: 2933cedf3d57aff20e1876a5b450f41b05e975cb8e0Matthew Xie // RSSI from hal is in one byte 2943cedf3d57aff20e1876a5b450f41b05e975cb8e0Matthew Xie device.mRssi = val[0]; 295caa3723eaa20e57aac086d54a41106108503debczzy break; 296caa3723eaa20e57aac086d54a41106108503debczzy } 297ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 298ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 299ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 300ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 301ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 302ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh void deviceFoundCallback(byte[] address) { 303ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh // The device properties are already registered - we can send the intent 304ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh // now 305ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh BluetoothDevice device = getDevice(address); 306ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh debugLog("deviceFoundCallback: Remote Address is:" + device); 307ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh DeviceProperties deviceProp = getDeviceProperties(device); 308ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (deviceProp == null) { 309ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh errorLog("Device Properties is null for Device:" + device); 310ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 311ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 312ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 313ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh Intent intent = new Intent(BluetoothDevice.ACTION_FOUND); 314ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh intent.putExtra(BluetoothDevice.EXTRA_DEVICE, device); 315ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh intent.putExtra(BluetoothDevice.EXTRA_CLASS, 316bdf33c0f7176de2bee64b6488a8327d837599fc8Fyodor Kupolov new BluetoothClass(deviceProp.mBluetoothClass)); 317ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh intent.putExtra(BluetoothDevice.EXTRA_RSSI, deviceProp.mRssi); 318ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh intent.putExtra(BluetoothDevice.EXTRA_NAME, deviceProp.mName); 319ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 320bdf33c0f7176de2bee64b6488a8327d837599fc8Fyodor Kupolov mAdapterService.sendBroadcastMultiplePermissions(intent, 321bdf33c0f7176de2bee64b6488a8327d837599fc8Fyodor Kupolov new String[] {AdapterService.BLUETOOTH_PERM, 322bdf33c0f7176de2bee64b6488a8327d837599fc8Fyodor Kupolov android.Manifest.permission.ACCESS_COARSE_LOCATION}); 323ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 324ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 32501a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy void aclStateChangeCallback(int status, byte[] address, int newState) { 32601a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy BluetoothDevice device = getDevice(address); 32701a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy 32801a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy if (device == null) { 32901a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy errorLog("aclStateChangeCallback: Device is NULL"); 33001a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy return; 33101a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy } 332f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora int state = mAdapterService.getState(); 333f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora Log.e(TAG, "state" + state + "newState" + newState); 33401a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy 3357aa3a71e508e4f95a0a74f41ab8389979809191bJay Civelli DeviceProperties prop = getDeviceProperties(device); 3367aa3a71e508e4f95a0a74f41ab8389979809191bJay Civelli if (prop == null) { 337bbb4110b455b3aa29106d5b4f0a37e1be8e09475Casper Bonde // errorLog("aclStateChangeCallback reported unknown device " + Arrays.toString(address)); 3387aa3a71e508e4f95a0a74f41ab8389979809191bJay Civelli } 33901a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy Intent intent = null; 34001a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy if (newState == AbstractionLayer.BT_ACL_STATE_CONNECTED) { 341f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora if (state == BluetoothAdapter.STATE_ON || state == BluetoothAdapter.STATE_TURNING_ON) { 342f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora intent = new Intent(BluetoothDevice.ACTION_ACL_CONNECTED); 343f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora } else if (state == BluetoothAdapter.STATE_BLE_ON || state == BluetoothAdapter.STATE_BLE_TURNING_ON) { 344f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora intent = new Intent(BluetoothAdapter.ACTION_BLE_ACL_CONNECTED); 345f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora } 34601a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy debugLog("aclStateChangeCallback: State:Connected to Device:" + device); 34701a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy } else { 348f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora if (device.getBondState() == BluetoothDevice.BOND_BONDING) { 349f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora /*Broadcasting PAIRING_CANCEL intent as well in this case*/ 350f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora intent = new Intent(BluetoothDevice.ACTION_PAIRING_CANCEL); 351f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora intent.putExtra(BluetoothDevice.EXTRA_DEVICE, device); 352f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora mAdapterService.sendBroadcast(intent, mAdapterService.BLUETOOTH_PERM); 353f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora } 354f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora if (state == BluetoothAdapter.STATE_ON || state == BluetoothAdapter.STATE_TURNING_OFF) { 355f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora intent = new Intent(BluetoothDevice.ACTION_ACL_DISCONNECTED); 356f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora } else if (state == BluetoothAdapter.STATE_BLE_ON || state == BluetoothAdapter.STATE_BLE_TURNING_OFF) { 357f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora intent = new Intent(BluetoothAdapter.ACTION_BLE_ACL_DISCONNECTED); 358f19f1ac64a5fefb248ab15b918d009b926c99ddeNitin Arora } 35901a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy debugLog("aclStateChangeCallback: State:DisConnected to Device:" + device); 36001a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy } 36101a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy intent.putExtra(BluetoothDevice.EXTRA_DEVICE, device); 36201a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT); 36374ae04c73312403e89db0f8e9bd9601d403b4783fredc mAdapterService.sendBroadcast(intent, mAdapterService.BLUETOOTH_PERM); 36401a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy } 365ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 3662c0df0560ad5ae3fd6022b17b17a6a70143e216aHemant Gupta 3672c0df0560ad5ae3fd6022b17b17a6a70143e216aHemant Gupta 368c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc void fetchUuids(BluetoothDevice device) { 369ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (mSdpTracker.contains(device)) return; 370ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh mSdpTracker.add(device); 371ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 372ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh Message message = mHandler.obtainMessage(MESSAGE_UUID_INTENT); 373ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh message.obj = device; 374ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh mHandler.sendMessageDelayed(message, UUID_INTENT_DELAY); 375ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 376c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc mAdapterService.getRemoteServicesNative(Utils.getBytesFromAddress(device.getAddress())); 377ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 378ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 379ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private final Handler mHandler = new Handler() { 380ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh @Override 381ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh public void handleMessage(Message msg) { 382ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh switch (msg.what) { 383ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh case MESSAGE_UUID_INTENT: 384ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh BluetoothDevice device = (BluetoothDevice)msg.obj; 385ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (device != null) { 386ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh sendUuidIntent(device); 387ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 388ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh break; 389ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 390ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 391ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh }; 392ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 393ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private void errorLog(String msg) { 394ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh Log.e(TAG, msg); 395ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 396ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 397ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private void debugLog(String msg) { 3986458cffaca286611e898c75ad86e2d98c89008b6Matthew Xie if (DBG) Log.d(TAG, msg); 399ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 400ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 401ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private void infoLog(String msg) { 402ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (DBG) Log.i(TAG, msg); 403ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 404ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 405ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh private void warnLog(String msg) { 406ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh Log.w(TAG, msg); 407ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 40874ae04c73312403e89db0f8e9bd9601d403b4783fredc 409ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 410